From dd0c748dde0a876937cd6fd98173b0d8ba2efbd2 Mon Sep 17 00:00:00 2001 From: Dimitris Panokostas Date: Sat, 31 Aug 2019 17:30:51 +0200 Subject: [PATCH] Merged latest WinUAE and uae4arm changes. Added 64-bit support. --- Makefile | 8 +- .../Amiberry-RPI1-Debug.vgdbsettings | 7 +- .../Amiberry-RPI1-Release.vgdbsettings | 7 +- VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj | 10 +- .../Amiberry-RPI1.vcxproj.filters | 6 - VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj | 1 - .../Amiberry-sdl1.vcxproj.filters | 3 - VisualGDB/Amiberry/Amiberry.sln | 26 +- VisualGDB/Amiberry/Amiberry.vcxproj | 1 - VisualGDB/Amiberry/Amiberry.vcxproj.filters | 3 - VisualGDB/guisan/guisan-Debug.vgdbsettings | 7 +- VisualGDB/guisan/guisan.vcxproj | 6 +- src/akiko.cpp | 308 +- src/ar.cpp | 147 +- src/audio.cpp | 197 +- src/autoconf.cpp | 92 +- src/blitfunc.cpp | 2564 +++--- src/blittable.cpp | 131 +- src/blitter.cpp | 443 +- src/blkdev.cpp | 78 +- src/blkdev_cdimage.cpp | 99 +- src/bsdsocket.cpp | 142 +- src/calc.cpp | 473 +- src/cd32_fmv.cpp | 63 +- src/cd32_fmv_genlock.cpp | 5 +- src/cdrom.cpp | 2 - src/cfgfile.cpp | 1222 ++- src/cia.cpp | 226 +- src/cpudefs.cpp | 1 + src/cpuemu_0.cpp | 574 +- src/cpuemu_11.cpp | 658 +- src/cpuemu_4.cpp | 220 +- src/cpuemu_40.cpp | 574 +- src/cpuemu_44.cpp | 220 +- src/custom.cpp | 807 +- src/def_icons.cpp | 79 - src/devices.cpp | 256 +- src/disk.cpp | 413 +- src/dlopen.cpp | 11 +- src/drawing.cpp | 1174 ++- src/events.cpp | 205 +- src/expansion.cpp | 646 +- src/fdi2raw.cpp | 367 +- src/filesys.cpp | 970 +-- src/fpp.cpp | 160 +- src/fsdb.cpp | 22 +- src/fsdb_unix.cpp | 50 +- src/fsusage.cpp | 2 - src/gayle.cpp | 305 +- src/gfxboard.cpp | 18 + src/gfxutil.cpp | 24 +- src/hardfile.cpp | 507 +- src/ide.cpp | 318 +- src/include/akiko.h | 6 +- src/include/ar.h | 2 + src/include/audio.h | 92 +- src/include/autoconf.h | 22 +- src/include/blitter.h | 7 +- src/include/blkdev.h | 67 +- src/include/bsdsocket.h | 8 +- src/include/cd32_fmv.h | 4 - src/include/cia.h | 1 + src/include/cpu_prefetch.h | 10 +- src/include/cpummu.h | 1 - src/include/custom.h | 37 +- src/include/devices.h | 43 +- src/include/disk.h | 51 +- src/include/drawing.h | 200 +- src/include/events.h | 36 +- src/include/filesys.h | 104 +- src/include/flashrom.h | 27 + src/include/fsdb.h | 79 +- src/include/gayle.h | 30 +- src/include/gensound.h | 3 + src/include/gfxboard.h | 84 + src/include/gui.h | 44 +- src/include/ide.h | 23 + src/include/inputdevice.h | 100 +- src/include/keybuf.h | 5 +- src/include/memory.h | 243 +- src/include/native2amiga_api.h | 2 + src/include/newcpu.h | 55 +- src/include/options.h | 80 +- src/include/readcpu.h | 35 +- src/include/rommgr.h | 23 +- src/include/rtc.h | 2 + src/include/savestate.h | 98 +- src/include/scsi.h | 266 +- src/include/statusline.h | 14 +- src/include/sysdeps.h | 28 +- src/include/traps.h | 13 + src/include/uae.h | 47 +- src/include/uae/dlopen.h | 2 +- src/include/uae/string.h | 4 +- src/include/xwin.h | 126 +- src/include/zarchive.h | 23 +- src/include/zfile.h | 31 +- src/inputdevice.cpp | 3009 +++++-- src/inputevents.def | 18 + src/jit/aarch64.h | 2127 +++++ src/jit/codegen_arm.cpp.in | 606 +- src/jit/codegen_arm.h | 5 +- src/jit/codegen_armA64.cpp.in | 1138 +++ src/jit/codegen_armA64.h | 482 ++ src/jit/compemu.cpp | 404 +- src/jit/compemu.h | 153 +- src/jit/compemu_fpp.cpp | 1632 ++-- src/jit/compemu_midfunc_arm.cpp.in | 231 +- src/jit/compemu_midfunc_arm.h | 37 +- src/jit/compemu_midfunc_arm2.cpp.in | 2409 +++--- src/jit/compemu_midfunc_arm2.h | 157 +- src/jit/compemu_midfunc_armA64.cpp.in | 1105 +++ src/jit/compemu_midfunc_armA64_2.cpp.in | 6950 +++++++++++++++++ src/jit/compemu_support.cpp | 442 +- src/jit/compstbl.cpp | 24 +- src/jit/comptbl.h | 12 + src/machdep/m68k.h | 2 +- src/machdep/maccess.h | 113 +- src/machdep/support.cpp | 20 +- src/main.cpp | 63 +- src/memory.cpp | 601 +- src/newcpu.cpp | 1450 ++-- src/newcpu_common.cpp | 871 ++- src/osdep/aarch64_helper.s | 1014 +++ src/osdep/amiberry.cpp | 47 +- src/osdep/amiberry_filesys.cpp | 18 +- src/osdep/amiberry_gfx.cpp | 72 +- src/osdep/amiberry_gui.cpp | 101 +- src/osdep/amiberry_hardfile.cpp | 7 +- src/osdep/amiberry_input.cpp | 6 +- src/osdep/amiberry_mem.cpp | 35 +- src/osdep/amiberry_rp9.cpp | 34 +- src/osdep/arm_helper.s | 35 +- src/osdep/bsdsocket_host.cpp | 208 +- src/osdep/cda_play.cpp | 91 +- src/osdep/cda_play.h | 24 +- src/osdep/charset.cpp | 12 +- src/osdep/gui/CreateFilesysHardfile.cpp | 2 +- src/osdep/gui/EditFilesysHardfile.cpp | 6 +- src/osdep/gui/EditFilesysVirtual.cpp | 6 +- src/osdep/gui/PanelCPU.cpp | 140 +- src/osdep/gui/PanelChipset.cpp | 60 +- src/osdep/gui/PanelConfig.cpp | 14 +- src/osdep/gui/PanelCustom.cpp | 42 +- src/osdep/gui/PanelDisplay.cpp | 74 +- src/osdep/gui/PanelFloppy.cpp | 68 +- src/osdep/gui/PanelHD.cpp | 74 +- src/osdep/gui/PanelInput.cpp | 96 +- src/osdep/gui/PanelMisc.cpp | 60 +- src/osdep/gui/PanelQuickstart.cpp | 116 +- src/osdep/gui/PanelRAM.cpp | 50 +- src/osdep/gui/PanelROM.cpp | 22 +- src/osdep/gui/PanelSavestate.cpp | 4 +- src/osdep/gui/PanelSound.cpp | 76 +- src/osdep/gui/gui_handling.h | 2 + src/osdep/neon_helper.s | 304 +- src/osdep/picasso96.cpp | 2018 +++-- src/osdep/picasso96.h | 207 +- src/osdep/sigsegv_handler.cpp | 1146 ++- src/osdep/sysconfig.h | 18 +- src/osdep/target.h | 76 +- src/readcpu.cpp | 867 +- src/rommgr.cpp | 62 +- src/rtc.cpp | 5 +- src/savestate.cpp | 267 +- src/scsi.cpp | 64 +- src/statusline.cpp | 8 +- src/threaddep/thread.h | 80 +- src/traps.cpp | 587 +- src/uaelib.cpp | 372 +- src/zfile.cpp | 396 +- src/zfile_archive.cpp | 57 +- 172 files changed, 33410 insertions(+), 16837 deletions(-) delete mode 100644 src/def_icons.cpp create mode 100644 src/jit/aarch64.h create mode 100644 src/jit/codegen_armA64.cpp.in create mode 100644 src/jit/codegen_armA64.h create mode 100644 src/jit/compemu_midfunc_armA64.cpp.in create mode 100644 src/jit/compemu_midfunc_armA64_2.cpp.in create mode 100644 src/osdep/aarch64_helper.s diff --git a/Makefile b/Makefile index f2987303..4ed75b85 100644 --- a/Makefile +++ b/Makefile @@ -273,9 +273,9 @@ XML_CFLAGS := $(shell xml2-config --cflags ) LDFLAGS += -flto -Wl,-O1 -Wl,--hash-style=gnu -Wl,--as-needed ifndef DEBUG - CFLAGS += -Ofast -frename-registers -falign-functions=16 + CFLAGS += -O3 -funroll-loops else - CFLAGS += -g -rdynamic -funwind-tables -mapcs-frame -DDEBUG -Wl,--export-dynamic + CFLAGS += -g -rdynamic -funwind-tables -DDEBUG -Wl,--export-dynamic endif ifdef GCC_PROFILE @@ -300,10 +300,10 @@ endif LDFLAGS += -lpthread -lz -lpng -lrt -lxml2 -lFLAC -lmpg123 -ldl -lmpeg2convert -lmpeg2 -ASFLAGS += $(CFLAGS) -falign-functions=16 +ASFLAGS += $(CFLAGS) -falign-functions export CFLAGS += -pipe -Wno-shift-overflow -Wno-narrowing $(EXTRA_CFLAGS) -export CXXFLAGS += $(CFLAGS) -std=gnu++14 -fpermissive +export CXXFLAGS += $(CFLAGS) -std=gnu++14 C_OBJS= \ src/archivers/7z/BraIA64.o \ diff --git a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Debug.vgdbsettings b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Debug.vgdbsettings index 77b61c7a..7a977c39 100644 --- a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Debug.vgdbsettings +++ b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Debug.vgdbsettings @@ -50,15 +50,14 @@ com.visualgdb.raspberry_pi - 6.3.0 - 7.12 - 4 + 8.3.0 + 8.2.1 + 1 Amiberry-RPI1.vcxproj - 1 true diff --git a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Release.vgdbsettings b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Release.vgdbsettings index 672a4f47..8bf36355 100644 --- a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Release.vgdbsettings +++ b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1-Release.vgdbsettings @@ -50,15 +50,14 @@ com.visualgdb.raspberry_pi - 6.3.0 - 7.12 - 4 + 8.3.0 + 8.2.1 + 1 Amiberry-RPI1.vcxproj - 1 true diff --git a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj index b4bfac83..488e254c 100644 --- a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj +++ b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj @@ -28,18 +28,18 @@ Debug com.visualgdb.raspberry_pi - 6.3.0/7.12/r4 + 8.3.0/8.2.1/r1 $(ProjectName)-sdl2 com.visualgdb.raspberry_pi - 6.3.0/7.12/r4 + 8.3.0/8.2.1/r1 GNUPP14 =/usr/local/include/SDL2;=/usr/include/libxml2;../../src;../../src/osdep;../../src/threaddep;../../src/include;../../guisan-dev/include;../../src/archivers;%(ClCompile.AdditionalIncludeDirectories) - DEBUG=1;_REENTRANT;AMIBERRY;CPU_arm;ARMV6_ASSEMBLY;ARM_HAS_DIV;USE_SDL2;_FILE_OFFSET_BITS=64;%(ClCompile.PreprocessorDefinitions) + DEBUG=1;_REENTRANT;AMIBERRY;CPU_arm;ARMV6_ASSEMBLY;ARM_HAS_DIV;USE_SDL2;_FILE_OFFSET_BITS=64;ARMV6T2;%(ClCompile.PreprocessorDefinitions) -march=armv6zk -mtune=arm1176jzf-s -mfpu=vfp -march=armv6zk -mtune=arm1176jzf-s -mfpu=vfp @@ -54,7 +54,7 @@ GNUPP14 =/usr/local/include/SDL2;=/usr/include/libxml2;../../src;../../src/osdep;../../src/threaddep;../../src/include;../../guisan-dev/include;../../src/archivers;%(ClCompile.AdditionalIncludeDirectories) - NDEBUG=1;RELEASE=1;_REENTRANT;AMIBERRY;CPU_arm;ARMV6_ASSEMBLY;ARM_HAS_DIV;USE_SDL2;_FILE_OFFSET_BITS=64;%(ClCompile.PreprocessorDefinitions) + NDEBUG=1;RELEASE=1;_REENTRANT;AMIBERRY;CPU_arm;ARMV6_ASSEMBLY;ARM_HAS_DIV;USE_SDL2;_FILE_OFFSET_BITS=64;ARMV6T2;%(ClCompile.PreprocessorDefinitions) -march=armv6zk -mtune=arm1176jzf-s -mfpu=vfp -mfloat-abi=hard -march=armv6zk -mtune=arm1176jzf-s -mfpu=vfp -mfloat-abi=hard @@ -87,7 +87,6 @@ - @@ -146,7 +145,6 @@ - diff --git a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj.filters b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj.filters index b2f11688..b171f2c4 100644 --- a/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj.filters +++ b/VisualGDB/Amiberry-RPI1/Amiberry-RPI1.vcxproj.filters @@ -164,9 +164,6 @@ Source files - - Source files - Source files @@ -338,9 +335,6 @@ Source files\archivers\7z - - Source files\archivers\7z - Source files\archivers\7z diff --git a/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj b/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj index febb9ca0..96a02f0c 100644 --- a/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj +++ b/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj @@ -221,7 +221,6 @@ - diff --git a/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj.filters b/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj.filters index a2fce81b..4c562883 100644 --- a/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj.filters +++ b/VisualGDB/Amiberry-sdl1/Amiberry-sdl1.vcxproj.filters @@ -719,9 +719,6 @@ Source files\archivers\7z - - Source files\archivers\7z - Source files\archivers\7z diff --git a/VisualGDB/Amiberry/Amiberry.sln b/VisualGDB/Amiberry/Amiberry.sln index 68e1db97..1a27493d 100644 --- a/VisualGDB/Amiberry/Amiberry.sln +++ b/VisualGDB/Amiberry/Amiberry.sln @@ -1,7 +1,7 @@  Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 15 -VisualStudioVersion = 15.0.27130.2036 +# Visual Studio Version 16 +VisualStudioVersion = 16.0.29209.62 MinimumVisualStudioVersion = 10.0.40219.1 Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Amiberry", "Amiberry.vcxproj", "{FDC6BF55-C4BC-44FB-85A9-3369784716E8}" ProjectSection(ProjectDependencies) = postProject @@ -10,8 +10,6 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Amiberry", "Amiberry.vcxpro EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "guisan", "..\guisan\guisan.vcxproj", "{E613050D-EE8C-4ED1-936D-EB9E0E155EA6}" EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Amiberry-sdl1", "..\Amiberry-sdl1\Amiberry-sdl1.vcxproj", "{14635D01-67B8-4863-9507-3FA5C8FB4B32}" -EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Amiberry-RPI1", "..\Amiberry-RPI1\Amiberry-RPI1.vcxproj", "{740C6C27-4C85-4927-A508-49116A0D36F9}" EndProject Global @@ -66,26 +64,6 @@ Global {E613050D-EE8C-4ED1-936D-EB9E0E155EA6}.Release-dispmanx|x64.Build.0 = Release|VisualGDB {E613050D-EE8C-4ED1-936D-EB9E0E155EA6}.Release-dispmanx|x86.ActiveCfg = Release|VisualGDB {E613050D-EE8C-4ED1-936D-EB9E0E155EA6}.Release-dispmanx|x86.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug|VisualGDB.ActiveCfg = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug|VisualGDB.Build.0 = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug|x64.ActiveCfg = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug|x86.ActiveCfg = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|VisualGDB.ActiveCfg = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|VisualGDB.Build.0 = Debug|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|x64.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|x64.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|x86.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Debug-dispmanx|x86.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release|VisualGDB.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release|VisualGDB.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release|x64.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release|x86.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|VisualGDB.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|VisualGDB.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|x64.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|x64.Build.0 = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|x86.ActiveCfg = Release|VisualGDB - {14635D01-67B8-4863-9507-3FA5C8FB4B32}.Release-dispmanx|x86.Build.0 = Release|VisualGDB {740C6C27-4C85-4927-A508-49116A0D36F9}.Debug|VisualGDB.ActiveCfg = Debug|VisualGDB {740C6C27-4C85-4927-A508-49116A0D36F9}.Debug|VisualGDB.Build.0 = Debug|VisualGDB {740C6C27-4C85-4927-A508-49116A0D36F9}.Debug|x64.ActiveCfg = Debug|VisualGDB diff --git a/VisualGDB/Amiberry/Amiberry.vcxproj b/VisualGDB/Amiberry/Amiberry.vcxproj index 3784525b..87a19390 100644 --- a/VisualGDB/Amiberry/Amiberry.vcxproj +++ b/VisualGDB/Amiberry/Amiberry.vcxproj @@ -203,7 +203,6 @@ - diff --git a/VisualGDB/Amiberry/Amiberry.vcxproj.filters b/VisualGDB/Amiberry/Amiberry.vcxproj.filters index 8a007596..8b3b8b41 100644 --- a/VisualGDB/Amiberry/Amiberry.vcxproj.filters +++ b/VisualGDB/Amiberry/Amiberry.vcxproj.filters @@ -160,9 +160,6 @@ Source files - - Source files - Source files diff --git a/VisualGDB/guisan/guisan-Debug.vgdbsettings b/VisualGDB/guisan/guisan-Debug.vgdbsettings index 21154e35..b3ceae52 100644 --- a/VisualGDB/guisan/guisan-Debug.vgdbsettings +++ b/VisualGDB/guisan/guisan-Debug.vgdbsettings @@ -45,15 +45,14 @@ com.visualgdb.raspberry_pi - 6.3.0 - 7.12 - 4 + 8.3.0 + 8.2.1 + 1 guisan.vcxproj - 1 true diff --git a/VisualGDB/guisan/guisan.vcxproj b/VisualGDB/guisan/guisan.vcxproj index c41d52f2..ced2118b 100644 --- a/VisualGDB/guisan/guisan.vcxproj +++ b/VisualGDB/guisan/guisan.vcxproj @@ -28,14 +28,14 @@ Debug com.visualgdb.raspberry_pi - 6.3.0/7.12/r4 + 8.3.0/8.2.1/r1 StaticLibrary $(SolutionDir)..\..\guisan-dev\lib\ lib$(ProjectName) com.visualgdb.raspberry_pi - 6.3.0/7.12/r4 + 8.3.0/8.2.1/r1 StaticLibrary $(SolutionDir)..\..\guisan-dev\lib\ lib$(ProjectName) @@ -43,7 +43,7 @@ GNUPP14 - =/usr/local/include/SDL2;=/opt/vc/include;=/opt/vc/include/interface/vcos/pthreads;=/opt/vc/include/interface/vmcs_host/linux;../../guisan-dev/include;%(ClCompile.AdditionalIncludeDirectories) + =/usr/include/SDL2;=/opt/vc/include;=/opt/vc/include/interface/vcos/pthreads;=/opt/vc/include/interface/vmcs_host/linux;../../guisan-dev/include;%(ClCompile.AdditionalIncludeDirectories) DEBUG=1;_REENTRANT;%(ClCompile.PreprocessorDefinitions) -march=armv8-a -mfpu=neon-fp-armv8 -mfloat-abi=hard %(AdditionalOptions) diff --git a/src/akiko.cpp b/src/akiko.cpp index 1e75ce1d..c31bd56c 100644 --- a/src/akiko.cpp +++ b/src/akiko.cpp @@ -10,33 +10,166 @@ * Copyright 2001-2016 Toni Wilen * */ -#include -#include -#include +/* + B80000-B80003: $C0CACAFE (Read-only identifier) + + B80004.L: INTREQ (RO) + B80008.L: INTENA (R/W) + + 31 $80000000 = Subcode interrupt (One subcode buffer filled and B0018.B has changed) + 30 $40000000 = Drive has received all command bytes and executed the command (PIO only) + 29 $20000000 = Drive has status data pending (PIO only) + 28 $10000000 = Drive command DMA transmit complete (DMA only) + 27 $08000000 = Drive status DMA receive complete (DMA only) + 26 $04000000 = Drive data DMA complete + 25 $02000000 = DMA overflow (lost data)? + + INTREQ is read-only, each interrupt has different method to clear the interrupt. + + B80010.L: DMA data base address (R/W. Must be 64k aligned) + + B80014.L: Command/Status/Subcode DMA base. (R/W. Must be 1024 byte aligned) + + Base + 0x000: 256 byte circular command DMA buffer. (Memory to drive) + Base + 0x100: Subcode DMA buffer (Doublebuffered, 2x128 byte buffers) + Base + 0x200: 256 byte circular status DMA buffer. (Drive to memory) + + B00018.B READ = Subcode DMA offset (ROM only checks if non-zero: second buffer in use) + B00018.B WRITE = Clear subcode interrupt (bit 31) + + B0001D.B READ = Transmit DMA circular buffer current position. + B0001D.B WRITE = Transmit DMA circular buffer end position. + + If written value is different than current: transmit DMA starts and sends command bytes to drive until value matches end position. + Clears also transmit interrupt (bit 28) + + B0001E.B READ = Receive DMA circular buffer current position. + B0001F.B WRITE = Receive DMA circular buffer end position. + + If written value is different than current: receive DMA fills DMA buffer if drive has response data remaining, until value matches end position. + Clears also Receive interrupt (bit 27) + + B80020.W WRITE = DMA transfer block enable + + Each bit marks position in DMA data address. + Bit 0 = DMA base address + 0 + Bit 1 = DMA base address + 0x1000 + .. + Bit 14 = DMA base address + 0xe000 + Bit 15 = DMA base address + 0xf000 + + When writing, if bit is one, matching register bit gets set, if bit is zero, nothing happens, it is not possible to clear already set bits. + All one bit blocks (CD sectors) are transferred one by one. Bit 15 is always checked and processed first, then 14 and so on.. + Interrupt is generated after each transferred block and matching register bit is cleared. + + Writing to this register also clears INTREQ bit 26. Writing zero will only clear interrupt. + If CONFIG data transfer DMA enable is not active: register gets cleared and writes are ignored. + + Structure of each block: + + 0-2: zeroed + 3: low 5 bits of sector number + 4 to 2352: 2348 bytes raw sector data (with first 4 bytes skipped) + 0xc00: 146 bytes of CD error correction data? + The rest is unused(?). + + B80020.W READ = Read current DMA transfer status. + + B80024.L: CONFIG (R/W) + + 31 $80000000 = Subcode DMA enable + 30 $40000000 = Command write (to CD) DMA enable + 29 $20000000 = Status read (from CD) DMA enable + 28 $10000000 = Memory access mode? + 27 $08000000 = Data transfer DMA enable + 26 $04000000 = CD interface enable? + 25 $02000000 = CD data mode? + 24 $01000000 = CD data mode? + 23 $00800000 = Akiko internal CIA faked vsync rate (0=50Hz,1=60Hz) + 00-22 = unused + + B80028.B WRITE = PIO write (If CONFIG bit 30 off). Clears also interrupt bit 30. + B80028.B READ = PIO read (If CONFIG bit 29 off). Clears also interrupt bit 29 if no data available anymore. + + B80030.B NVRAM I2C IO. Bit 7 = SCL, bit 6 = SDA + B80032.B NVRAM I2C DIRECTION. Bit 7 = SCL direction, bit 6 = SDA direction) + + B80038.L C2P + + Commands: + + 1 = STOP + + Size: 1 byte + Returns status response + + 2 = PAUSE + + Size: 1 byte + Returns status response + + 3 = UNPAUSE + + Size: 1 byte + Returns status response + + 4 = PLAY/READ + + Size: 12 bytes + Response: 2 bytes + + 5 = LED (2 bytes) + + Size: 2 bytes. Bit 7 set in second byte = response wanted. + Response: no response or 2 bytes. Second byte non-zero: led is currently lit. + + 6 = SUBCODE + + Size: 1 byte + Response: 15 bytes + + 7 = INFO + + Size: 1 byte + Response: 20 bytes (status and firmware version) + + Common status response: 2 bytes + Status second byte bit 7 = Error, bit 3 = Playing, bit 0 = Door closed. + + First byte of command is combined 4 bit counter and command code. + Command response's first byte is same as command. + Counter byte can be used to match command with response. + Command and response bytes have checksum byte appended. + +*/ + +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" -#include "include/memory.h" -#include "newcpu.h" +#include "memory.h" +//#include "events.h" #include "savestate.h" #include "blkdev.h" #include "zfile.h" #include "threaddep/thread.h" +#include "akiko.h" #include "gui.h" #include "crc32.h" #include "uae.h" #include "custom.h" +#include "newcpu.h" #include "flashrom.h" +#include "rommgr.h" +#include "devices.h" // 43 48 49 4E 4F 4E 20 20 4F 2D 36 35 38 2D 32 20 32 34 #define FIRMWAREVERSION "CHINON O-658-2 24" static void irq (void) { - if (!(intreq & 8)) { - INTREQ_0 (0x8000 | 0x0008); - } + safe_interrupt_set(false); } /* @@ -73,9 +206,11 @@ static void nvram_read (void) cd32_nvram = xmalloc(uae_u8, maxlen); } memset(cd32_nvram, 0, maxlen); - cd32_flashfile = zfile_fopen (currprefs.flashfile, _T("rb+"), ZFD_NORMAL); + TCHAR path[MAX_DPATH]; + cfgfile_resolve_path_out_load(currprefs.flashfile, path, MAX_DPATH, PATH_ROM); + cd32_flashfile = zfile_fopen (path, _T("rb+"), ZFD_NORMAL); if (!cd32_flashfile) - cd32_flashfile = zfile_fopen (currprefs.flashfile, _T("wb"), 0); + cd32_flashfile = zfile_fopen (path, _T("wb"), 0); if (cd32_flashfile) { int size = zfile_fread(cd32_nvram, 1, currprefs.cs_cd32nvram_size, cd32_flashfile); if (size < maxlen) @@ -275,7 +410,6 @@ static uae_u8 cdrom_command; static uae_u8 cdrom_last_rx; static int cdrom_toc_counter; -static uae_u32 cdrom_toc_crc; static uae_u8 cdrom_toc_buffer[MAX_TOC_ENTRIES * 13]; static struct cd_toc_head cdrom_toc_cd_buffer; static uae_u8 qcode_buf[SUBQ_SIZE]; @@ -300,14 +434,14 @@ static int sector_buffer_sector_1, sector_buffer_sector_2; static uae_u8 *sector_buffer_info_1, *sector_buffer_info_2; static int unitnum = -1; -static uae_u8 cdrom_door = 1; +static const uae_u8 cdrom_door = 1; static bool akiko_inited; static volatile int mediachanged, mediacheckcounter; static volatile int frame2counter; static smp_comm_pipe requests; static volatile int akiko_thread_running; -static uae_sem_t akiko_sem = 0, sub_sem = 0; +static uae_sem_t akiko_sem = 0, sub_sem = 0, cda_sem = 0; static void checkint (void) { @@ -323,7 +457,7 @@ static void set_status (uae_u32 status) cdrom_led ^= LED_CD_ACTIVE2; } -void rethink_akiko (void) +static void rethink_akiko(void) { checkint (); } @@ -376,18 +510,20 @@ static void subfunc (uae_u8 *data, int cnt) uae_sem_post (&sub_sem); } -static int statusfunc (int status, int playpos) +static int statusfunc(int status, int playpos) { if (status == -1) return 0; if (status == -2) return 10; + if (status < 0) + return 0; if (cdrom_audiostatus != status) { if (status == AUDIO_STATUS_IN_PROGRESS) { if (cdrom_playing == 0) - cdrom_playing = 1; + cdrom_playing = 1; cdrom_audiotimeout = 1; - } + } if (cdrom_playing && status != AUDIO_STATUS_IN_PROGRESS && status != AUDIO_STATUS_PAUSED && status != AUDIO_STATUS_NOT_SUPPORTED) { cdrom_audiotimeout = -1; } @@ -396,16 +532,25 @@ static int statusfunc (int status, int playpos) return 0; } -static void cdaudioplay_do (void) +static int statusfunc_imm(int status, int playpos) { - uae_u32 startlsn = read_comm_pipe_u32_blocking (&requests); - uae_u32 endlsn = read_comm_pipe_u32_blocking (&requests); - uae_u32 scan = read_comm_pipe_u32_blocking (&requests); + if (status == -3 || status > AUDIO_STATUS_IN_PROGRESS) + uae_sem_post(&cda_sem); + if (status < 0) + return 0; + return statusfunc(status, playpos); +} + +static void cdaudioplay_do(bool immediate) +{ + uae_u32 startlsn = read_comm_pipe_u32_blocking(&requests); + uae_u32 endlsn = read_comm_pipe_u32_blocking(&requests); + uae_u32 scan = read_comm_pipe_u32_blocking(&requests); qcode_valid = 0; if (unitnum < 0) return; - sys_command_cd_pause (unitnum, 0); - sys_command_cd_play (unitnum, startlsn, endlsn, scan, statusfunc, subfunc); + sys_command_cd_pause(unitnum, 0); + sys_command_cd_play(unitnum, startlsn, endlsn, scan, immediate ? statusfunc_imm : statusfunc, subfunc); } static bool isaudiotrack (int startlsn) @@ -550,7 +695,6 @@ static int get_cdrom_toc (void) if (s->point >= 2 && s->point < 100 && (s->control & 0x0c) != 0x04 && !secondtrack) secondtrack = addr; } - cdrom_toc_crc = get_crc32 (cdrom_toc_buffer, cdrom_toc_cd_buffer.points * 13); return 0; } static bool is_valid_data_sector(int sector) @@ -669,13 +813,6 @@ static int cdrom_command_led (void) return 0; } -static int cdrom_command_idle_status (void) -{ - cdrom_result_buffer[0] = 0x0a; - cdrom_result_buffer[1] = 0x70; - return 2; -} - static int cdrom_command_media_status (void) { cdrom_result_buffer[0] = 0x0a; @@ -973,7 +1110,7 @@ static void cdrom_run_command_run (void) /* DMA transfer one CD sector */ static void cdrom_run_read (void) { - int i, sector, inc; + int sector, inc; int sec; int seccnt; @@ -1005,9 +1142,9 @@ static void cdrom_run_read (void) buf[1] = 0; buf[2] = 0; buf[3] = cdrom_sector_counter & 31; - for (i = 0; i < 2352; i++) + for (int i = 0; i < 2352; i++) put_byte (cdrom_addressdata + seccnt * 4096 + i, buf[i]); - for (i = 0; i < 73 * 2; i++) + for (int i = 0; i < 73 * 2; i++) put_byte (cdrom_addressdata + seccnt * 4096 + 0xc00 + i, 0); cdrom_pbx &= ~(1 << seccnt); set_status (CDINTERRUPT_PBX); @@ -1122,24 +1259,28 @@ static void akiko_internal (void) } } -void AKIKO_hsync_handler (void) +static void AKIKO_hsync_handler (void) { bool framesync = false; if (!currprefs.cs_cd32cd || !akiko_inited) return; - static float framecounter; - framecounter--; - if (framecounter <= 0) { + static float framecounter1, framecounter2; + framecounter1--; + if (framecounter1 <= 0) { if (cdrom_seek_delay <= 0) { - cdrom_run_read (); + cdrom_run_read(); } else { cdrom_seek_delay--; } - framecounter += (float)maxvpos * vblank_hz / (75.0 * cdrom_speed); - if (currprefs.cd_speed == 0) - framecounter = 1; + framecounter1 += (float)maxvpos * vblank_hz / (75.0 * cdrom_speed); + if (currprefs.cd_speed == 0 || currprefs.turbo_emulation) + framecounter1 = 1; + } + framecounter2--; + if (framecounter2 <= 0) { + framecounter2 += (float)maxvpos * vblank_hz / (75.0 * cdrom_speed); framesync = true; } @@ -1184,9 +1325,9 @@ void AKIKO_hsync_handler (void) } /* cdrom data buffering thread */ -static void *akiko_thread (void *null) +static int akiko_thread (void *null) { - int i; + int secnum; uae_u8 *tmp1; uae_u8 *tmp2; int tmp3; @@ -1210,9 +1351,13 @@ static void *akiko_thread (void *null) case 0x0105: // mute change sys_command_cd_volume (unitnum, cdrom_muted ? 0 : 0x7fff, cdrom_muted ? 0 : 0x7fff); break; + case 0x0111: // instant play + sys_command_cd_volume(unitnum, cdrom_muted ? 0 : 0x7fff, cdrom_muted ? 0 : 0x7fff); + cdaudioplay_do(true); + break; case 0x0110: // do_play! sys_command_cd_volume (unitnum, cdrom_muted ? 0 : 0x7fff, cdrom_muted ? 0 : 0x7fff); - cdaudioplay_do (); + cdaudioplay_do(false); break; } } @@ -1249,12 +1394,12 @@ static void *akiko_thread (void *null) uae_sem_wait (&akiko_sem); sector = cdrom_current_sector; - for (i = 0; i < SECTOR_BUFFER_SIZE; i++) { - if (sector_buffer_info_1[i] == 0xff) + for (secnum = 0; secnum < SECTOR_BUFFER_SIZE; secnum++) { + if (sector_buffer_info_1[secnum] == 0xff) break; } if (sector >= 0 && is_valid_data_sector(sector) && - (sector_buffer_sector_1 < 0 || sector < sector_buffer_sector_1 || sector >= sector_buffer_sector_1 + SECTOR_BUFFER_SIZE * 2 / 3 || i != SECTOR_BUFFER_SIZE)) { + (sector_buffer_sector_1 < 0 || sector < sector_buffer_sector_1 || sector >= sector_buffer_sector_1 + SECTOR_BUFFER_SIZE * 2 / 3 || secnum != SECTOR_BUFFER_SIZE)) { int blocks; memset (sector_buffer_info_2, 0, SECTOR_BUFFER_SIZE); sector_buffer_sector_2 = sector; @@ -1271,10 +1416,10 @@ static void *akiko_thread (void *null) if (!ok) { int offset = 0; while (offset < SECTOR_BUFFER_SIZE) { - int ok = 0; + int readok = 0; if (is_valid_data_sector(sector)) - ok = sys_command_cd_rawread (unitnum, sector_buffer_2 + offset * 2352, sector, 1, 2352); - sector_buffer_info_2[offset] = ok ? 3 : 0; + readok = sys_command_cd_rawread (unitnum, sector_buffer_2 + offset * 2352, sector, 1, 2352); + sector_buffer_info_2[offset] = readok ? 3 : 0; offset++; sector++; } @@ -1314,8 +1459,6 @@ STATIC_INLINE void akiko_put_long (uae_u32 *p, int offset, int v) static uae_u32 REGPARAM3 akiko_lget (uaecptr) REGPARAM; static uae_u32 REGPARAM3 akiko_wget (uaecptr) REGPARAM; static uae_u32 REGPARAM3 akiko_bget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 akiko_lgeti (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 akiko_wgeti (uaecptr) REGPARAM; static void REGPARAM3 akiko_lput (uaecptr, uae_u32) REGPARAM; static void REGPARAM3 akiko_wput (uaecptr, uae_u32) REGPARAM; static void REGPARAM3 akiko_bput (uaecptr, uae_u32) REGPARAM; @@ -1650,14 +1793,14 @@ addrbank akiko_bank = { akiko_lget, akiko_wget, akiko_bget, akiko_lput, akiko_wput, akiko_bput, default_xlate, default_check, NULL, NULL, _T("Akiko"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; static const uae_u8 patchdata[]={0x0c,0x82,0x00,0x00,0x03,0xe8,0x64,0x00,0x00,0x46}; static void patchrom (void) { - int i; + int i; if (currprefs.cpu_model > 68020 || currprefs.cachesize || currprefs.m68k_speed != 0) { uae_u8 *p = extendedkickmem_bank.baseaddr; if (p) { @@ -1691,7 +1834,7 @@ static void akiko_cdrom_free (void) sector_buffer_info_2 = 0; } -void akiko_reset (void) +void akiko_reset (int hardreset) { cdaudiostop_do (); nvram_read (); @@ -1719,7 +1862,6 @@ void akiko_reset (void) akiko_thread_running = 0; while(akiko_thread_running == 0) sleep_millis (10); - destroy_comm_pipe(&requests); akiko_thread_running = 0; } akiko_cdrom_free (); @@ -1727,16 +1869,10 @@ void akiko_reset (void) akiko_inited = false; } -void akiko_free (void) +static void akiko_free(void) { - akiko_reset (); - akiko_cdrom_free (); - if(akiko_sem != 0) - uae_sem_destroy(&akiko_sem); - akiko_sem = 0; - if(sub_sem != 0) - uae_sem_destroy(&sub_sem); - sub_sem = 0; + akiko_reset(1); + akiko_cdrom_free(); } int akiko_init (void) @@ -1753,14 +1889,9 @@ int akiko_init (void) sector_buffer_info_2 = xmalloc (uae_u8, SECTOR_BUFFER_SIZE); sector_buffer_sector_1 = -1; sector_buffer_sector_2 = -1; - if(akiko_sem != 0) - uae_sem_destroy(&akiko_sem); - akiko_sem = 0; uae_sem_init (&akiko_sem, 0, 1); - if(sub_sem != 0) - uae_sem_destroy(&sub_sem); - sub_sem = 0; - uae_sem_init (&sub_sem, 0, 1); + uae_sem_init(&sub_sem, 0, 1); + uae_sem_init(&cda_sem, 0, 0); if (!savestate_state) { cdrom_playing = cdrom_paused = 0; cdrom_data_offset = -1; @@ -1773,6 +1904,11 @@ int akiko_init (void) } gui_flicker_led (LED_HD, 0, -1); akiko_inited = true; + + device_add_hsync(AKIKO_hsync_handler); + device_add_exit(akiko_free); + device_add_rethink(rethink_akiko); + return 1; } @@ -1829,7 +1965,7 @@ uae_u8 *save_akiko (int *len, uae_u8 *dstptr) save_u8 (cdrom_speed); save_u8 (cdrom_current_sector); - save_u32 (cdrom_toc_crc); + save_u32 (0); save_u8 (cdrom_toc_cd_buffer.points); save_u32 (cdrom_toc_cd_buffer.lastaddress); @@ -1913,15 +2049,21 @@ void restore_akiko_finish (void) akiko_init (); akiko_c2p_do (); get_cdrom_toc (); - write_comm_pipe_u32 (&requests, 0x0102, 1); // pause - write_comm_pipe_u32 (&requests, 0x0104, 1); // stop - write_comm_pipe_u32 (&requests, 0x0103, 1); // unpause - if (cdrom_playing && isaudiotrack (last_play_pos)) { - write_comm_pipe_u32 (&requests, 0x0103, 1); // unpause - write_comm_pipe_u32 (&requests, 0x0110, 0); // play - write_comm_pipe_u32 (&requests, last_play_pos, 0); - write_comm_pipe_u32 (&requests, last_play_end, 0); - write_comm_pipe_u32 (&requests, 0, 1); +} + +void restore_akiko_final(void) +{ + if (!currprefs.cs_cd32cd) + return; + write_comm_pipe_u32(&requests, 0x0102, 1); // pause + write_comm_pipe_u32(&requests, 0x0104, 1); // stop + write_comm_pipe_u32(&requests, 0x0103, 1); // unpause + if (cdrom_playing && isaudiotrack(last_play_pos)) { + write_comm_pipe_u32(&requests, 0x0111, 0); // play immediate + write_comm_pipe_u32(&requests, last_play_pos, 0); + write_comm_pipe_u32(&requests, last_play_end, 0); + write_comm_pipe_u32(&requests, 0, 1); + uae_sem_wait(&cda_sem); } cd_initialized = 2; } diff --git a/src/ar.cpp b/src/ar.cpp index 17502fc5..d1dd9f2d 100644 --- a/src/ar.cpp +++ b/src/ar.cpp @@ -201,10 +201,7 @@ * */ -#include -#include -#include - +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" @@ -217,6 +214,9 @@ #include "ar.h" #include "savestate.h" #include "crc32.h" +#include "akiko.h" +#include "xwin.h" +#include "gfxboard.h" static const TCHAR *cart_memnames[] = { NULL, _T("hrtmon"), _T("arhrtmon"), _T("superiv") }; @@ -264,18 +264,13 @@ static int stored_picasso_on = -1; static void cartridge_enter (void) { -#ifdef PICASSO96 - stored_picasso_on = picasso_requested_on; - picasso_requested_on = 0; -#endif + stored_picasso_on = gfxboard_set(false) ? 1 : 0; } static void cartridge_exit (void) { -#ifdef PICASSO96 if (stored_picasso_on > 0) - picasso_requested_on = 1; + gfxboard_set(true); stored_picasso_on = -1; -#endif } static uae_u32 REGPARAM2 hrtmem3_bget (uaecptr addr) @@ -467,21 +462,21 @@ static addrbank hrtmem_bank = { hrtmem_lget, hrtmem_wget, hrtmem_bget, hrtmem_lput, hrtmem_wput, hrtmem_bput, hrtmem_xlate, hrtmem_check, NULL, NULL, _T("Cartridge Bank"), - hrtmem_lget, hrtmem_wget, + hrtmem_wget, ABFLAG_RAM, S_READ, S_WRITE }; static addrbank hrtmem2_bank = { hrtmem2_lget, hrtmem2_wget, hrtmem2_bget, hrtmem2_lput, hrtmem2_wput, hrtmem2_bput, hrtmem2_xlate, hrtmem2_check, NULL, NULL, _T("Cartridge Bank 2"), - hrtmem2_lget, hrtmem2_wget, + hrtmem2_wget, ABFLAG_RAM, S_READ, S_WRITE }; static addrbank hrtmem3_bank = { hrtmem3_lget, hrtmem3_wget, hrtmem3_bget, hrtmem3_lput, hrtmem3_wput, hrtmem3_bput, hrtmem3_xlate, hrtmem3_check, NULL, NULL, _T("Cartridge Bank 3"), - hrtmem3_lget, hrtmem3_wget, + hrtmem3_wget, ABFLAG_RAM, S_READ, S_WRITE }; @@ -502,6 +497,7 @@ static void copytoamiga (uaecptr dst, uae_u8 *src, int len) } int action_replay_flag = ACTION_REPLAY_INACTIVE; +static int ar_state1 = -1, ar_state2 = -1, ar_hide; static int ar_rom_file_size; /* Use this for relocating AR? */ @@ -544,7 +540,7 @@ STATIC_INLINE int ar3a (uaecptr addr, uae_u8 b, int writing) ar_wait_pop = 0; /* We get (SP+2) here, as the first word on the stack is the status register. */ /* We want the following long, which is the return program counter. */ - wait_for_pc = longget (m68k_areg (regs, 7) + 2); /* Get (SP+2) */ + wait_for_pc = get_long (m68k_areg (regs, 7) + 2); /* Get (SP+2) */ set_special (SPCFLAG_ACTION_REPLAY); uaecptr pc = m68k_getpc (); @@ -644,29 +640,6 @@ void REGPARAM2 chipmem_wput_actionreplay23 (uaecptr addr, uae_u32 w) } -static uae_u32 REGPARAM3 arram_lget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 arram_wget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 arram_bget (uaecptr) REGPARAM; -static void REGPARAM3 arram_lput (uaecptr, uae_u32) REGPARAM; -static void REGPARAM3 arram_wput (uaecptr, uae_u32) REGPARAM; -static void REGPARAM3 arram_bput (uaecptr, uae_u32) REGPARAM; -static int REGPARAM3 arram_check (uaecptr addr, uae_u32 size) REGPARAM; -static uae_u8 *REGPARAM3 arram_xlate (uaecptr addr) REGPARAM; - -static uae_u32 REGPARAM3 arrom_lget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 arrom_wget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 arrom_bget (uaecptr) REGPARAM; -static void REGPARAM3 arrom_lput (uaecptr, uae_u32) REGPARAM; -static void REGPARAM3 arrom_wput (uaecptr, uae_u32) REGPARAM; -static void REGPARAM3 arrom_bput (uaecptr, uae_u32) REGPARAM; -static int REGPARAM3 arrom_check (uaecptr addr, uae_u32 size) REGPARAM; -static uae_u8 *REGPARAM3 arrom_xlate (uaecptr addr) REGPARAM; -static void action_replay_unmap_banks (void); - -static uae_u32 action_replay_calculate_checksum(void); -static uae_u8* get_checksum_location(void); -static void disable_rom_test(void); - static uae_u32 ar_null(int size) { if (size == 4) @@ -830,14 +803,14 @@ static addrbank arrom_bank = { arrom_lget, arrom_wget, arrom_bget, arrom_lput, arrom_wput, arrom_bput, arrom_xlate, arrom_check, NULL, NULL, _T("Action Replay ROM"), - arrom_lget, arrom_wget, + arrom_wget, ABFLAG_ROM, S_READ, S_WRITE }; static addrbank arram_bank = { arram_lget, arram_wget, arram_bget, arram_lput, arram_wput, arram_bput, arram_xlate, arram_check, NULL, NULL, _T("Action Replay RAM"), - arram_lget, arram_wget, + arram_wget, ABFLAG_RAM, S_READ, S_WRITE }; @@ -872,6 +845,7 @@ static void action_replay_unmap_banks (void) static void hide_cart (int hide) { + ar_hide = hide; #ifdef ACTION_REPLAY_HIDE_CARTRIDGE if(hide) { action_replay_unmap_banks (); @@ -1035,6 +1009,7 @@ void check_prefs_changed_carts (int in_memory_reset) void action_replay_reset (bool hardreset, bool keyboardreset) { + stored_picasso_on = -1; ar_mapped = -1; if (hrtmemory) { if (isrestore ()) { @@ -1046,17 +1021,8 @@ void action_replay_reset (bool hardreset, bool keyboardreset) } else { if (action_replay_flag == ACTION_REPLAY_INACTIVE) return; - - if (isrestore ()) { - if (m68k_getpc () >= arrom_start && m68k_getpc () <= arrom_start + arrom_size) { - action_replay_flag = ACTION_REPLAY_ACTIVE; - hide_cart (0); - } else { - action_replay_flag = ACTION_REPLAY_IDLE; - hide_cart (1); - } + if (isrestore ()) return; - } if (armodel == 1) { /* We need to mark it as active here, because the kickstart rom jumps directly into it. */ action_replay_flag = ACTION_REPLAY_ACTIVE; @@ -1164,13 +1130,6 @@ void hrtmon_hide(void) //write_log (_T("HRTMON: Exit\n")); } -void hrtmon_breakenter(void) -{ - //hrtmon_flag = ACTION_REPLAY_HIDE; - //set_special (SPCFLAG_ACTION_REPLAY); -} - - /* Disabling copperlist processing: * On: ar317 an rts at 41084c does it. * On: ar214: an rts at 41068e does it. @@ -1299,18 +1258,6 @@ static uae_u8* get_checksum_location (void) return (uae_u8*)checksum_end; } -/* Replaces the existing cart checksum with a correct one. */ -/* Useful if you want to patch the rom. */ -static void action_replay_fixup_checksum (uae_u32 new_checksum) -{ - uae_u32* checksum = (uae_u32*)get_checksum_location(); - if (checksum) - do_put_mem_long (checksum, new_checksum); - else - write_log (_T("Unable to locate Checksum in ROM.\n")); - return; -} - /* Longword search on word boundary * the search_value is assumed to already be in the local endian format * return 0 on failure @@ -1417,7 +1364,6 @@ static void action_replay_checksum_info (void) } - static void action_replay_setbanks (void) { if (!savestate_state && chipmem_bank.lput == chipmem_lput) { @@ -1461,22 +1407,6 @@ int action_replay_unload (int in_memory_reset) if (!armemory_rom && !hrtmemory) return 0; - if (armemory_rom && armodel == 1) { - if (is_ar_pc_in_ram() || is_ar_pc_in_rom() || action_replay_flag == ACTION_REPLAY_WAIT_PC) { - write_log (_T("Can't Unload Action Replay 1. It is Active.\n")); - return 0; - } - } else { - if (action_replay_flag != ACTION_REPLAY_IDLE && action_replay_flag != ACTION_REPLAY_INACTIVE) { - write_log (_T("Can't Unload Action Replay. It is Active.\n")); - return 0; /* Don't unload it whilst it's active, or it will crash the amiga if not the emulator */ - } - if (hrtmon_flag != ACTION_REPLAY_IDLE && hrtmon_flag != ACTION_REPLAY_INACTIVE) { - write_log (_T("Can't Unload Hrtmon. It is Active.\n")); - return 0; /* Don't unload it whilst it's active, or it will crash the amiga if not the emulator */ - } - } - unset_special (SPCFLAG_ACTION_REPLAY); /* This shouldn't be necessary here, but just in case. */ action_replay_flag = ACTION_REPLAY_INACTIVE; hrtmon_flag = ACTION_REPLAY_INACTIVE; @@ -2058,7 +1988,7 @@ uae_u8 *save_action_replay (int *len, uae_u8 *dstptr) dstbak = dst = dstptr; else dstbak = dst = xmalloc (uae_u8, arram_size + sizeof ar_custom + sizeof ar_ciaa + sizeof ar_ciab + 1024); - save_u8 (0); + save_u8 (1 | ((regs.spcflags & SPCFLAG_ACTION_REPLAY) ? 2 : 0) | (ar_hide ? 4 : 0)); save_u8 (armodel); save_u32 (get_crc32 (armemory_rom + 4, arrom_size - 4)); save_string (currprefs.cartfile); @@ -2075,6 +2005,9 @@ uae_u8 *save_action_replay (int *len, uae_u8 *dstptr) save_u32 (sizeof ar_ciab); memcpy (dst, ar_ciab, sizeof ar_ciab); dst += sizeof ar_ciab; + save_u8(action_replay_flag); + save_u8(armode_read); + save_u8(armode_write); *len = dst - dstbak; return dstbak; } @@ -2082,9 +2015,10 @@ uae_u8 *save_action_replay (int *len, uae_u8 *dstptr) uae_u8 *restore_action_replay (uae_u8 *src) { TCHAR *s; + uae_u32 flags; action_replay_unload (1); - restore_u8 (); + flags = restore_u8 (); armodel = restore_u8 (); if (!armodel) return src; @@ -2108,12 +2042,43 @@ uae_u8 *restore_action_replay (uae_u8 *src) src += sizeof ar_ciaa; restore_u32 (); src += sizeof ar_ciab; - action_replay_flag = ACTION_REPLAY_IDLE; - if (is_ar_pc_in_rom ()) - action_replay_flag = ACTION_REPLAY_ACTIVE; + armode_read = armode_write = 0; + ar_state1 = -1; + ar_state2 = -1; + if (flags & 1) { + ar_state1 = restore_u8(); + ar_state2 = 0; + armode_read = restore_u8(); + armode_write = restore_u8(); + if (flags & 2) + ar_state2 |= 1; + if (flags & 4) + ar_state2 |= 2; + } else { + action_replay_flag = ACTION_REPLAY_IDLE; + if (is_ar_pc_in_rom ()) + action_replay_flag = ACTION_REPLAY_ACTIVE; + } return src; } +void restore_ar_finish(void) +{ + if (ar_state2 < 0) { + if (m68k_getpc () >= arrom_start && m68k_getpc () <= arrom_start + arrom_size) { + action_replay_flag = ACTION_REPLAY_ACTIVE; + hide_cart (0); + } else { + action_replay_flag = ACTION_REPLAY_IDLE; + hide_cart (1); + } + } else { + action_replay_flag = ar_state1; + if (ar_state2 & 1) + set_special (SPCFLAG_ACTION_REPLAY); + hide_cart((ar_state2 & 2) ? 1 : 0); + } +} #define NPSIZE 65536 diff --git a/src/audio.cpp b/src/audio.cpp index 78abb7a3..34da0dfa 100644 --- a/src/audio.cpp +++ b/src/audio.cpp @@ -12,25 +12,30 @@ * */ -#include -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "memory.h" #include "custom.h" #include "newcpu.h" +#include "autoconf.h" #include "audio.h" #include "sounddep/sound.h" #include "savestate.h" #include "gui.h" +#include "xwin.h" +#include "threaddep/thread.h" + +#include #define PERIOD_MIN 4 #define PERIOD_MIN_NONCE 60 +int audio_channel_mask = 15; volatile bool cd_audio_mode_changed; -STATIC_INLINE bool isaudio(void) +STATIC_INLINE bool isaudio (void) { return currprefs.produce_sound != 0; } @@ -59,7 +64,8 @@ struct audio_channel_data2 sinc_queue_t sinc_queue[SINC_QUEUE_LENGTH]; int sinc_queue_time; int sinc_queue_head; - int vol; + int audvol; + int mixvol; unsigned int adk_mask; }; @@ -94,25 +100,23 @@ static void (*sample_prehandler) (unsigned long best_evtime); float scaled_sample_evtime; int sound_cd_volume[2]; -static int sound_paula_volume[2]; +int sound_paula_volume[2]; static unsigned long last_cycles; static float next_sample_evtime; typedef uae_s8 sample8_t; -#define DO_CHANNEL_1(v, c) do { (v) *= audio_channel[c].data.vol; } while (0) +#define DO_CHANNEL_1(v, c) do { (v) *= audio_channel[c].data.mixvol; } while (0) +#define SBASEVAL16(logn) ((logn) == 1 ? SOUND16_BASE_VAL >> 1 : SOUND16_BASE_VAL) STATIC_INLINE int FINISH_DATA(int data, int bits, int ch) { - if (bits == 16) { - return data; - } - else if (bits - 16 > 0) { - data >>= bits - 16; - } - else { + if (bits < 16) { int shift = 16 - bits; data <<= shift; + } else { + int shift = bits - 16; + data >>= shift; } data = data * sound_paula_volume[ch] / 32768; return data; @@ -120,19 +124,21 @@ STATIC_INLINE int FINISH_DATA(int data, int bits, int ch) static uae_u32 right_word_saved[SOUND_MAX_DELAY_BUFFER]; static uae_u32 left_word_saved[SOUND_MAX_DELAY_BUFFER]; -static int saved_ptr; +static uae_u32 right2_word_saved[SOUND_MAX_DELAY_BUFFER]; +static uae_u32 left2_word_saved[SOUND_MAX_DELAY_BUFFER]; +static int saved_ptr, saved_ptr2; static int mixed_on, mixed_stereo_size, mixed_mul1, mixed_mul2; static int led_filter_forced, sound_use_filter, sound_use_filter_sinc, led_filter_on; /* denormals are very small floating point numbers that force FPUs into slow - mode. All lowpass filters using floats are suspectible to denormals unless - a small offset is added to avoid very small floating point numbers. */ +mode. All lowpass filters using floats are suspectible to denormals unless +a small offset is added to avoid very small floating point numbers. */ #define DENORMAL_OFFSET (1E-10) static struct filter_state { - float rc1, rc2, rc3, rc4, rc5; -} sound_filter_state[2]; + float rc1, rc2, rc3, rc4, rc5; +} sound_filter_state[AUDIO_CHANNELS_PAULA]; static float a500e_filter1_a0; static float a500e_filter2_a0; @@ -145,19 +151,19 @@ enum { }; /* Amiga has two separate filtering circuits per channel, a static RC filter - * on A500 and the LED filter. This code emulates both. - * - * The Amiga filtering circuitry depends on Amiga model. Older Amigas seem - * to have a 6 dB/oct RC filter with cutoff frequency such that the -6 dB - * point for filter is reached at 6 kHz, while newer Amigas have no filtering. - * - * The LED filter is complicated, and we are modelling it with a pair of - * RC filters, the other providing a highboost. The LED starts to cut - * into signal somewhere around 5-6 kHz, and there's some kind of highboost - * in effect above 12 kHz. Better measurements are required. - * - * The current filtering should be accurate to 2 dB with the filter on, - * and to 1 dB with the filter off. +* on A500 and the LED filter. This code emulates both. +* +* The Amiga filtering circuitry depends on Amiga model. Older Amigas seem +* to have a 6 dB/oct RC filter with cutoff frequency such that the -6 dB +* point for filter is reached at 6 kHz, while newer Amigas have no filtering. +* +* The LED filter is complicated, and we are modelling it with a pair of +* RC filters, the other providing a highboost. The LED starts to cut +* into signal somewhere around 5-6 kHz, and there's some kind of highboost +* in effect above 12 kHz. Better measurements are required. +* +* The current filtering should be accurate to 2 dB with the filter on, +* and to 1 dB with the filter off. */ static int filter(int input, struct filter_state *fs) @@ -174,8 +180,8 @@ static int filter(int input, struct filter_state *fs) normal_output = fs->rc2; fs->rc3 = filter_a0 * normal_output + (1 - filter_a0) * fs->rc3; - fs->rc4 = filter_a0 * fs->rc3 + (1 - filter_a0) * fs->rc4; - fs->rc5 = filter_a0 * fs->rc4 + (1 - filter_a0) * fs->rc5; + fs->rc4 = filter_a0 * fs->rc3 + (1 - filter_a0) * fs->rc4; + fs->rc5 = filter_a0 * fs->rc4 + (1 - filter_a0) * fs->rc5; led_output = fs->rc5; break; @@ -184,8 +190,8 @@ static int filter(int input, struct filter_state *fs) normal_output = input; fs->rc2 = filter_a0 * normal_output + (1 - filter_a0) * fs->rc2 + DENORMAL_OFFSET; - fs->rc3 = filter_a0 * fs->rc2 + (1 - filter_a0) * fs->rc3; - fs->rc4 = filter_a0 * fs->rc3 + (1 - filter_a0) * fs->rc4; + fs->rc3 = filter_a0 * fs->rc2 + (1 - filter_a0) * fs->rc3; + fs->rc4 = filter_a0 * fs->rc3 + (1 - filter_a0) * fs->rc4; led_output = fs->rc4; break; @@ -284,13 +290,13 @@ static void anti_prehandler(unsigned long best_evtime) /* Handle accumulator antialiasiation */ for (i = 0; i < AUDIO_CHANNELS_PAULA; i++) { acd = audio_data[i]; - output = (acd->current_sample * acd->vol) & acd->adk_mask; + output = (acd->current_sample * acd->mixvol) & acd->adk_mask; acd->sample_accum += output * best_evtime; acd->sample_accum_time += best_evtime; } } -STATIC_INLINE void samplexx_anti_handler(int *datasp) +static void samplexx_anti_handler (int *datasp) { for (auto i = 0; i < AUDIO_CHANNELS_PAULA; i++) { auto acd = audio_data[i]; @@ -302,11 +308,13 @@ STATIC_INLINE void samplexx_anti_handler(int *datasp) static void sinc_prehandler_paula(unsigned long best_evtime) { - for (auto& i : audio_data) - { - auto acd = i; - auto vol = acd->vol; - int output = (acd->current_sample * vol) & acd->adk_mask; + int i, output; + struct audio_channel_data2 *acd; + + for (i = 0; i < AUDIO_CHANNELS_PAULA; i++) { + acd = audio_data[i]; + int vol = acd->mixvol; + output = (acd->current_sample * vol) & acd->adk_mask; /* if output state changes, record the state change and also * write data into sinc queue for mixing in the BLEP */ @@ -323,7 +331,7 @@ static void sinc_prehandler_paula(unsigned long best_evtime) /* this interpolator performs BLEP mixing (bleps are shaped like integrated sinc * functions) with a type of BLEP that matches the filtering configuration. */ -STATIC_INLINE void samplexx_sinc_handler(int *datasp) +static void samplexx_sinc_handler (int *datasp) { int n; @@ -375,15 +383,15 @@ void sample16_handler(void) { int data; if (audio_channel[0].data.adk_mask) - data = audio_channel[0].data.current_sample * audio_channel[0].data.vol; + data = audio_channel[0].data.current_sample * audio_channel[0].data.mixvol; else data = 0; if (audio_channel[1].data.adk_mask) - data += audio_channel[1].data.current_sample * audio_channel[1].data.vol; + data += audio_channel[1].data.current_sample * audio_channel[1].data.mixvol; if (audio_channel[2].data.adk_mask) - data += audio_channel[2].data.current_sample * audio_channel[2].data.vol; + data += audio_channel[2].data.current_sample * audio_channel[2].data.mixvol; if (audio_channel[3].data.adk_mask) - data += audio_channel[3].data.current_sample * audio_channel[3].data.vol; + data += audio_channel[3].data.current_sample * audio_channel[3].data.mixvol; data = FINISH_DATA(data, 16, 0); @@ -407,14 +415,17 @@ static void sample16i_anti_handler(void) static void sample16i_rh_handler(void) { - auto data0 = audio_channel[0].data.current_sample; - auto data1 = audio_channel[1].data.current_sample; - auto data2 = audio_channel[2].data.current_sample; - auto data3 = audio_channel[3].data.current_sample; - auto data0p = audio_channel[0].data.last_sample; - auto data1p = audio_channel[1].data.last_sample; - auto data2p = audio_channel[2].data.last_sample; - auto data3p = audio_channel[3].data.last_sample; + unsigned long delta, ratio; + + int data0 = audio_channel[0].data.current_sample; + int data1 = audio_channel[1].data.current_sample; + int data2 = audio_channel[2].data.current_sample; + int data3 = audio_channel[3].data.current_sample; + int data0p = audio_channel[0].data.last_sample; + int data1p = audio_channel[1].data.last_sample; + int data2p = audio_channel[2].data.last_sample; + int data3p = audio_channel[3].data.last_sample; + int data; DO_CHANNEL_1(data0, 0); DO_CHANNEL_1(data1, 1); @@ -435,8 +446,8 @@ static void sample16i_rh_handler(void) data3p &= audio_channel[3].data.adk_mask; /* linear interpolation and summing up... */ - unsigned long delta = audio_channel[0].per; - auto ratio = ((audio_channel[0].evtime % delta) << 8) / delta; + delta = audio_channel[0].per; + ratio = ((audio_channel[0].evtime % delta) << 8) / delta; data0 = (data0 * (256 - ratio) + data0p * ratio) >> 8; delta = audio_channel[1].per; ratio = ((audio_channel[1].evtime % delta) << 8) / delta; @@ -447,7 +458,7 @@ static void sample16i_rh_handler(void) delta = audio_channel[3].per; ratio = ((audio_channel[3].evtime % delta) << 8) / delta; data0 += (data3 * (256 - ratio) + data3p * ratio) >> 8; - auto data = data0; + data = data0; data = FINISH_DATA(data, 16, 0); put_sound_word_mono_func(data); @@ -456,14 +467,15 @@ static void sample16i_rh_handler(void) static void sample16i_crux_handler(void) { - auto data0 = audio_channel[0].data.current_sample; - auto data1 = audio_channel[1].data.current_sample; - auto data2 = audio_channel[2].data.current_sample; - auto data3 = audio_channel[3].data.current_sample; - auto data0p = audio_channel[0].data.last_sample; - auto data1p = audio_channel[1].data.last_sample; - auto data2p = audio_channel[2].data.last_sample; - auto data3p = audio_channel[3].data.last_sample; + int data0 = audio_channel[0].data.current_sample; + int data1 = audio_channel[1].data.current_sample; + int data2 = audio_channel[2].data.current_sample; + int data3 = audio_channel[3].data.current_sample; + int data0p = audio_channel[0].data.last_sample; + int data1p = audio_channel[1].data.last_sample; + int data2p = audio_channel[2].data.last_sample; + int data3p = audio_channel[3].data.last_sample; + int data; DO_CHANNEL_1(data0, 0); DO_CHANNEL_1(data1, 1); @@ -516,15 +528,13 @@ static void sample16i_crux_handler(void) data1 += data2; data0 += data3; data0 += data1; - auto data = data0; + data = data0; data = FINISH_DATA(data, 16, 0); put_sound_word_mono_func(data); check_sound_buffers(); } -#ifdef HAVE_STEREO_SUPPORT - /* This interpolator examines sample points when Paula switches the output * voltage and computes the average of Paula's output */ @@ -558,12 +568,12 @@ static void sample16si_sinc_handler(void) void sample16s_handler(void) { - auto data_l = audio_channel[0].data.adk_mask ? audio_channel[0].data.current_sample * audio_channel[0].data.vol : 0; - auto data_r = audio_channel[1].data.adk_mask ? audio_channel[1].data.current_sample * audio_channel[1].data.vol : 0; + int data_l = audio_channel[0].data.adk_mask ? audio_channel[0].data.current_sample * audio_channel[0].data.mixvol : 0; + int data_r = audio_channel[1].data.adk_mask ? audio_channel[1].data.current_sample * audio_channel[1].data.mixvol : 0; if (audio_channel[2].data.adk_mask) - data_r += audio_channel[2].data.current_sample * audio_channel[2].data.vol; + data_r += audio_channel[2].data.current_sample * audio_channel[2].data.mixvol; if (audio_channel[3].data.adk_mask) - data_l += audio_channel[3].data.current_sample * audio_channel[3].data.vol; + data_l += audio_channel[3].data.current_sample * audio_channel[3].data.mixvol; data_l = FINISH_DATA(data_l, 15, 0); data_r = FINISH_DATA(data_r, 15, 1); @@ -688,21 +698,6 @@ static void sample16si_rh_handler(void) check_sound_buffers(); } -#else -void sample16s_handler(void) -{ - sample16_handler(); -} -static void sample16si_crux_handler(void) -{ - sample16i_crux_handler(); -} -static void sample16si_rh_handler(void) -{ - sample16i_rh_handler(); -} -#endif - static int audio_work_to_do; static void zerostate(int nr) @@ -772,14 +767,15 @@ STATIC_INLINE int is_audio_active(void) return audio_work_to_do; } -STATIC_INLINE void update_volume(int nr, uae_u16 v) +static void update_volume(int nr, uae_u16 v) { auto cdp = audio_channel + nr; // 7 bit register in Paula. v &= 127; if (v > 64) v = 64; - cdp->data.vol = v; + cdp->data.audvol = v; + cdp->data.mixvol = v; } uae_u16 audio_dmal(void) @@ -801,7 +797,7 @@ static int isirq(int nr) return INTREQR() & (0x80 << nr); } -STATIC_INLINE void setirq(int nr, int which) +static void setirq (int nr, int which) { INTREQ_0(0x8000 | (0x80 << nr)); } @@ -851,7 +847,7 @@ static void loaddat(int nr) loaddat(nr, false); } -STATIC_INLINE void loadper(int nr) +static void loadper (int nr) { auto cdp = audio_channel + nr; @@ -1047,7 +1043,7 @@ void audio_reset(void) auto cdp = &i; memset(cdp, 0, sizeof *audio_channel); cdp->per = PERIOD_MAX - 1; - cdp->data.vol = 0; + cdp->data.mixvol = 0; cdp->evtime = MAX_EV; } } @@ -1100,7 +1096,7 @@ static float rc_calculate_a0(int sample_rate, int cutoff_freq) return out; } -void check_prefs_changed_audio(void) +void check_prefs_changed_audio (void) { if (sound_available) { auto ch = sound_prefs_changed(); @@ -1114,7 +1110,7 @@ void check_prefs_changed_audio(void) } } -void set_audio(void) +void set_audio (void) { const auto old_mixed_size = mixed_stereo_size; @@ -1224,8 +1220,10 @@ void set_audio(void) else if (sample_handler == sample16si_anti_handler || sample_handler == sample16i_anti_handler) { sample_prehandler = anti_prehandler; } - for (auto i = 0; i < AUDIO_CHANNELS_PAULA; i++) { - audio_data[i] = &audio_channel[i].data; + for (int i = 0; i < AUDIO_CHANNELS_PAULA; i++) { + struct audio_channel_data *cdp = audio_channel + i; + audio_data[i] = &cdp->data; + cdp->data.mixvol = cdp->data.audvol; } if (currprefs.sound_stereo) { @@ -1506,7 +1504,7 @@ uae_u8 *restore_audio(int nr, uae_u8 *src) zerostate(nr); acd->state = restore_u8(); - acd->data.vol = restore_u8(); + acd->data.audvol = restore_u8(); acd->intreq2 = restore_u8() != 0; const auto flags = restore_u8(); acd->dr = acd->dsr = false; @@ -1523,6 +1521,7 @@ uae_u8 *restore_audio(int nr, uae_u8 *src) acd->pt = restore_u32(); acd->evtime = restore_u32(); acd->dmaenstore = (dmacon & DMA_MASTER) && (dmacon & (1 << nr)); + acd->data.mixvol = acd->data.audvol; return src; } @@ -1536,7 +1535,7 @@ uae_u8 *save_audio(int nr, int *len, uae_u8 *dstptr) else dstbak = dst = xmalloc(uae_u8, 100); save_u8(acd->state); - save_u8(acd->data.vol); + save_u8 (acd->data.audvol); save_u8(acd->intreq2); save_u8((acd->dr ? 1 : 0) | (acd->dsr ? 2 : 0) | 0x80); save_u16(acd->len); diff --git a/src/autoconf.cpp b/src/autoconf.cpp index eebe806d..c287a1f7 100644 --- a/src/autoconf.cpp +++ b/src/autoconf.cpp @@ -1,20 +1,23 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * AutoConfig devices - * - * Copyright 1995, 1996 Bernd Schmidt - * Copyright 1996 Ed Hanway - */ +/* +* UAE - The Un*x Amiga Emulator +* +* AutoConfig devices +* +* Copyright 1995, 1996 Bernd Schmidt +* Copyright 1996 Ed Hanway +*/ -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "uae.h" #include "memory.h" #include "autoconf.h" +#include "traps.h" +#include "threaddep/thread.h" #include "inputdevice.h" +#include "devices.h" /* Commonly used autoconfig strings */ @@ -31,7 +34,7 @@ addrbank rtarea_bank = { rtarea_lget, rtarea_wget, rtarea_bget, rtarea_lput, rtarea_wput, rtarea_bput, rtarea_xlate, rtarea_check, NULL, _T("rtarea"), _T("UAE Boot ROM"), - rtarea_lget, rtarea_wget, + rtarea_wget, ABFLAG_ROMIN, S_READ, S_WRITE }; @@ -43,13 +46,13 @@ static uae_u8 *REGPARAM2 rtarea_xlate(uaecptr addr) return rtarea_bank.baseaddr + addr; } -static int REGPARAM2 rtarea_check(uaecptr addr, uae_u32 size) +static int REGPARAM2 rtarea_check (uaecptr addr, uae_u32 size) { addr &= 0xFFFF; return (addr + size) <= 0xFFFF; } -static uae_u32 REGPARAM2 rtarea_lget(uaecptr addr) +static uae_u32 REGPARAM2 rtarea_lget (uaecptr addr) { addr &= 0xFFFF; if (addr & 1) @@ -59,8 +62,7 @@ static uae_u32 REGPARAM2 rtarea_lget(uaecptr addr) return (rtarea_bank.baseaddr[addr + 0] << 24) | (rtarea_bank.baseaddr[addr + 1] << 16) | (rtarea_bank.baseaddr[addr + 2] << 8) | (rtarea_bank.baseaddr[addr + 3] << 0); } - -static uae_u32 REGPARAM2 rtarea_wget(uaecptr addr) +static uae_u32 REGPARAM2 rtarea_wget (uaecptr addr) { addr &= 0xFFFF; if (addr & 1) @@ -68,8 +70,7 @@ static uae_u32 REGPARAM2 rtarea_wget(uaecptr addr) return (rtarea_bank.baseaddr[addr] << 8) + rtarea_bank.baseaddr[addr + 1]; } - -static uae_u32 REGPARAM2 rtarea_bget(uaecptr addr) +static uae_u32 REGPARAM2 rtarea_bget (uaecptr addr) { addr &= 0xFFFF; @@ -95,7 +96,7 @@ static bool rtarea_write(uaecptr addr) return false; } -static void REGPARAM2 rtarea_bput(uaecptr addr, uae_u32 value) +static void REGPARAM2 rtarea_bput (uaecptr addr, uae_u32 value) { addr &= 0xffff; if (!rtarea_write(addr)) @@ -106,7 +107,7 @@ static void REGPARAM2 rtarea_bput(uaecptr addr, uae_u32 value) } } -static void REGPARAM2 rtarea_wput(uaecptr addr, uae_u32 value) +static void REGPARAM2 rtarea_wput (uaecptr addr, uae_u32 value) { addr &= 0xffff; value &= 0xffff; @@ -121,7 +122,7 @@ static void REGPARAM2 rtarea_wput(uaecptr addr, uae_u32 value) rtarea_bank.baseaddr[addr + 1] = (uae_u8)value; } -static void REGPARAM2 rtarea_lput(uaecptr addr, uae_u32 value) +static void REGPARAM2 rtarea_lput (uaecptr addr, uae_u32 value) { addr &= 0xffff; if (addr & 1) @@ -154,23 +155,23 @@ void rtarea_reset(void) static int rt_addr; static int rt_straddr; -uae_u32 addr(int ptr) +uae_u32 addr (int ptr) { return (uae_u32)ptr + rtarea_base; } -void db(uae_u8 data) +void db (uae_u8 data) { rtarea_bank.baseaddr[rt_addr++] = data; } -void dw(uae_u16 data) +void dw (uae_u16 data) { rtarea_bank.baseaddr[rt_addr++] = (uae_u8)(data >> 8); rtarea_bank.baseaddr[rt_addr++] = (uae_u8)data; } -void dl(uae_u32 data) +void dl (uae_u32 data) { rtarea_bank.baseaddr[rt_addr++] = data >> 24; rtarea_bank.baseaddr[rt_addr++] = data >> 16; @@ -180,31 +181,31 @@ void dl(uae_u32 data) uae_u8 dbg(uaecptr addr) { - addr -= rtarea_base; + addr &= 0xffff; return rtarea_bank.baseaddr[addr]; } /* store strings starting at the end of the rt area and working - * backward. store pointer at current address - */ +* backward. store pointer at current address +*/ -uae_u32 ds_ansi(const uae_char *str) +uae_u32 ds_ansi (const uae_char *str) { int len; if (!str) - return addr(rt_straddr); - len = strlen(str) + 1; + return addr (rt_straddr); + len = strlen (str) + 1; rt_straddr -= len; - strcpy((uae_char*)rtarea_bank.baseaddr + rt_straddr, str); - return addr(rt_straddr); + strcpy ((uae_char*)rtarea_bank.baseaddr + rt_straddr, str); + return addr (rt_straddr); } -uae_u32 ds(const TCHAR *str) +uae_u32 ds (const TCHAR *str) { - char *s = ua(str); - uae_u32 v = ds_ansi(s); - xfree(s); + char *s = ua (str); + uae_u32 v = ds_ansi (s); + xfree (s); return v; } @@ -251,20 +252,10 @@ static uae_u32 REGPARAM2 nullfunc(TrapContext *ctx) static uae_u32 REGPARAM2 getchipmemsize(TrapContext *ctx) { - trap_set_dreg(ctx, 1, 0); - trap_set_areg(ctx, 1, 0); return chipmem_bank.allocated_size; } -static uae_u32 REGPARAM2 uae_puts(TrapContext *ctx) -{ - uae_char buf[MAX_DPATH]; - trap_get_string(ctx, buf, trap_get_areg(ctx, 0), sizeof(uae_char)); - write_log(_T("%s"), buf); - return 0; -} - -void rtarea_init_mem(void) +static void rtarea_init_mem (void) { rtarea_bank.reserved_size = RTAREA_SIZE; rtarea_bank.start = rtarea_base; @@ -280,7 +271,6 @@ void rtarea_free(void) mapped_free(&rtarea_bank); } -ATTRIBUTE_NO_SANITIZE_ADDRESS void rtarea_init(void) { uae_u32 a; @@ -296,10 +286,10 @@ void rtarea_init(void) _stprintf(uaever, _T("uae-%d.%d.%d"), UAEMAJOR, UAEMINOR, UAESUBREV); - EXPANSION_uaeversion = ds(uaever); + ds (uaever); EXPANSION_explibname = ds(_T("expansion.library")); EXPANSION_doslibname = ds(_T("dos.library")); - EXPANSION_uaedevname = ds(_T("uae.device")); + ds (_T("uae.device")); dw(0); dw(0); @@ -319,10 +309,6 @@ void rtarea_init(void) calltrap(deftrapres(getchipmemsize, TRAPFLAG_DORET, _T("getchipmemsize"))); dw(RTS); - org(rtarea_base + 0xFF10); - calltrap(deftrapres(uae_puts, TRAPFLAG_NO_RETVAL, _T("uae_puts"))); - dw(RTS); - org(a); uae_boot_rom_size = here() - rtarea_base; diff --git a/src/blitfunc.cpp b/src/blitfunc.cpp index 616ec74a..6288ee28 100644 --- a/src/blitfunc.cpp +++ b/src/blitfunc.cpp @@ -1,1493 +1,1457 @@ +#include "sysconfig.h" #include "sysdeps.h" #include "savestate.h" #include "options.h" -#include "blitter.h" +#include "custom.h" #include "memory.h" +#include "blitter.h" +#include "blitfunc.h" -void blitdofast_0(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +void blitdofast_0 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (0) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } - } - if (ptd) ptd += b->bltdmod; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (0) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_0(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_0 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (0) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } - } - if (ptd) ptd -= b->bltdmod; +uae_u32 totald = 0; +int i,j; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (0) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((~srca & srcc)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } - } - if (pta) pta += b->bltamod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((~srca & srcc)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((~srca & srcc)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } - } - if (pta) pta -= b->bltamod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; +uae_u32 totald = 0; +int i,j; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((~srca & srcc)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_2a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_2a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & ~(srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & ~(srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_2a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_2a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & ~(srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & ~(srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_30(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_30 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca & ~srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca & ~srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_30(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_30 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca & ~srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca & ~srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_3a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_3a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcb ^ (srca | (srcb ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcb ^ (srca | (srcb ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_3a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_3a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcb ^ (srca | (srcb ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcb ^ (srca | (srcb ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_3c(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_3c (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca ^ srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca ^ srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_3c(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_3c (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca ^ srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca ^ srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_4a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_4a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & (srcb | srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & (srcb | srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_4a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_4a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & (srcb | srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & (srcb | srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_6a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_6a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_6a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_6a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_8a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_8a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & (~srca | srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & (~srca | srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_8a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_8a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & (~srca | srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & (~srca | srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_8c(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_8c (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcb & (~srca | srcc))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcb & (~srca | srcc))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_8c(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_8c (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcb & (~srca | srcc))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcb & (~srca | srcc))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_9a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_9a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & ~srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & ~srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_9a(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_9a (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & ~srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & ~srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_a8(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_a8 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & (srca | srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & (srca | srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_a8(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_a8 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc & (srca | srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc & (srca | srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_aa(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_aa (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srcc) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } - } - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srcc) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_aa(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_aa (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srcc) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } - } - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; +uae_u32 totald = 0; +int i,j; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srcc) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_b1(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_b1 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (~(srca ^ (srcc | (srca ^ srcb)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (~(srca ^ (srcc | (srca ^ srcb)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_b1(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_b1 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (~(srca ^ (srcc | (srca ^ srcb)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (~(srca ^ (srcc | (srca ^ srcb)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_ca(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_ca (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & (srcb ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & (srcb ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_ca(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_ca (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srca & (srcb ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srca & (srcb ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_cc(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_cc (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srcb) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (ptb) ptb += b->bltbmod; - if (ptd) ptd += b->bltdmod; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srcb) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptb) ptb += b->bltbmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_cc(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_cc (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srcb) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (ptb) ptb -= b->bltbmod; - if (ptd) ptd -= b->bltdmod; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srcb) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (ptb) ptb -= b->bltbmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_d8(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_d8 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca ^ (srcc & (srca ^ srcb)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca ^ (srcc & (srca ^ srcb)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_d8(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_d8 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca ^ (srcc & (srca ^ srcb)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca ^ (srcc & (srca ^ srcb)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_e2(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_e2 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srcb & (srca ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srcb & (srca ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_e2(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_e2 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc ^ (srcb & (srca ^ srcc)))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc ^ (srcb & (srca ^ srcc)))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_ea(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_ea (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc | (srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc | (srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_ea(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_ea (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srcc | (srca & srcb))) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srcc | (srca & srcb))) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_f0(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_f0 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srca) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } - } - if (pta) pta += b->bltamod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srca) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_f0(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_f0 (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = (srca) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } - } - if (pta) pta -= b->bltamod; - if (ptd) ptd -= b->bltdmod; +uae_u32 totald = 0; +int i,j; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = (srca) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_fa(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_fa (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc += 2; } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca | srcc)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } - } - if (pta) pta += b->bltamod; - if (ptc) ptc += b->bltcmod; - if (ptd) ptd += b->bltdmod; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc += 2; } + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca | srcc)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptc) ptc += b->bltcmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_fa(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_fa (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcc = b->bltcdat; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptc) { srcc = chipmem_wget_indirect(ptc); ptc -= 2; } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca | srcc)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } - } - if (pta) pta -= b->bltamod; - if (ptc) ptc -= b->bltcmod; - if (ptd) ptd -= b->bltdmod; +uae_u32 totald = 0; +int i,j; +uae_u32 srcc = b->bltcdat; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptc) { srcc = chipmem_wget_indirect (ptc); ptc -= 2; } + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca | srcc)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltcdat = srcc; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptc) ptc -= b->bltcmod; + if (ptd) ptd -= b->bltdmod; } -void blitdofast_fc(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltcdat = srcc; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_fc (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - int i, j; - uae_u32 totald = 0; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; +int i,j; +uae_u32 totald = 0; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd=0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb += 2; - srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta += 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca | srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd += 2; } + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb += 2; + srcb = (((uae_u32)b->bltbold << 16) | bltbdat) >> b->blitbshift; + b->bltbold = bltbdat; } - if (pta) pta += b->bltamod; - if (ptb) ptb += b->bltbmod; - if (ptd) ptd += b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta += 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)b->bltaold << 16) | bltadat) >> b->blitashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca | srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd += 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta += b->bltamod; + if (ptb) ptb += b->bltbmod; + if (ptd) ptd += b->bltdmod; } -void blitdofast_desc_fc(uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; +} +void blitdofast_desc_fc (uaecptr pta, uaecptr ptb, uaecptr ptc, uaecptr ptd, struct bltinfo *b) { - uae_u32 totald = 0; - int i, j; - uae_u32 srcb = b->bltbhold; - uae_u32 dstd = 0; - uaecptr dstp = 0; - for (j = 0; j < b->vblitsize; j++) { - for (i = 0; i < b->hblitsize; i++) { - uae_u32 bltadat, srca; - if (ptb) { - uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect(ptb); ptb -= 2; - srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; - b->bltbold = bltbdat; - } - if (pta) { bltadat = b->bltadat = chipmem_wget_indirect(pta); pta -= 2; } - else { bltadat = b->bltadat; } - bltadat &= blit_masktable[i]; - srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; - b->bltaold = bltadat; - if (dstp) chipmem_wput_indirect(dstp, dstd); - dstd = ((srca | srcb)) & 0xFFFF; - totald |= dstd; - if (ptd) { dstp = ptd; ptd -= 2; } +uae_u32 totald = 0; +int i,j; +uae_u32 srcb = b->bltbhold; +uae_u32 dstd = 0; +uaecptr dstp = 0; +for (j = 0; j < b->vblitsize; j++) { + for (i = 0; i < b->hblitsize; i++) { + uae_u32 bltadat, srca; + if (ptb) { + uae_u32 bltbdat = b->bltbdat = chipmem_wget_indirect (ptb); ptb -= 2; + srcb = ((bltbdat << 16) | b->bltbold) >> b->blitdownbshift; + b->bltbold = bltbdat; } - if (pta) pta -= b->bltamod; - if (ptb) ptb -= b->bltbmod; - if (ptd) ptd -= b->bltdmod; + if (pta) { bltadat = b->bltadat = chipmem_wget_indirect (pta); pta -= 2; } else { bltadat = b->bltadat; } + bltadat &= blit_masktable[i]; + srca = (((uae_u32)bltadat << 16) | b->bltaold) >> b->blitdownashift; + b->bltaold = bltadat; + if (dstp) chipmem_wput_indirect (dstp, dstd); + dstd = ((srca | srcb)) & 0xFFFF; + totald |= dstd; + if (ptd) { dstp = ptd; ptd -= 2; } } - b->bltbhold = srcb; - if (dstp) chipmem_wput_indirect(dstp, dstd); - if (totald != 0) b->blitzero = 0; + if (pta) pta -= b->bltamod; + if (ptb) ptb -= b->bltbmod; + if (ptd) ptd -= b->bltdmod; +} +b->bltbhold = srcb; + if (dstp) chipmem_wput_indirect (dstp, dstd); +if (totald != 0) b->blitzero = 0; } - diff --git a/src/blittable.cpp b/src/blittable.cpp index 504d9c57..5d7c2724 100644 --- a/src/blittable.cpp +++ b/src/blittable.cpp @@ -1,77 +1,78 @@ +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" +#include "custom.h" #include "memory.h" -//#include "newcpu.h" #include "savestate.h" #include "blitter.h" #include "blitfunc.h" blitter_func * const blitfunc_dofast[256] = { - blitdofast_0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_2a, 0, 0, 0, 0, 0, - blitdofast_30, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_3a, 0, blitdofast_3c, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_4a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_6a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_8a, 0, blitdofast_8c, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_9a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - blitdofast_a8, 0, blitdofast_aa, 0, 0, 0, 0, 0, - 0, blitdofast_b1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_ca, 0, blitdofast_cc, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - blitdofast_d8, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_e2, 0, 0, 0, 0, 0, - 0, 0, blitdofast_ea, 0, 0, 0, 0, 0, - blitdofast_f0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_fa, 0, blitdofast_fc, 0, 0, 0 +blitdofast_0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_2a, 0, 0, 0, 0, 0, +blitdofast_30, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_3a, 0, blitdofast_3c, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_4a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_6a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_8a, 0, blitdofast_8c, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_9a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +blitdofast_a8, 0, blitdofast_aa, 0, 0, 0, 0, 0, +0, blitdofast_b1, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_ca, 0, blitdofast_cc, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +blitdofast_d8, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_e2, 0, 0, 0, 0, 0, +0, 0, blitdofast_ea, 0, 0, 0, 0, 0, +blitdofast_f0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_fa, 0, blitdofast_fc, 0, 0, 0 }; blitter_func * const blitfunc_dofast_desc[256] = { - blitdofast_desc_0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_2a, 0, 0, 0, 0, 0, - blitdofast_desc_30, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_3a, 0, blitdofast_desc_3c, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_4a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_6a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_8a, 0, blitdofast_desc_8c, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_9a, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - blitdofast_desc_a8, 0, blitdofast_desc_aa, 0, 0, 0, 0, 0, - 0, blitdofast_desc_b1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_ca, 0, blitdofast_desc_cc, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - blitdofast_desc_d8, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_e2, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_ea, 0, 0, 0, 0, 0, - blitdofast_desc_f0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, blitdofast_desc_fa, 0, blitdofast_desc_fc, 0, 0, 0 +blitdofast_desc_0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_2a, 0, 0, 0, 0, 0, +blitdofast_desc_30, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_3a, 0, blitdofast_desc_3c, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_4a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_6a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_8a, 0, blitdofast_desc_8c, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_9a, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +blitdofast_desc_a8, 0, blitdofast_desc_aa, 0, 0, 0, 0, 0, +0, blitdofast_desc_b1, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_ca, 0, blitdofast_desc_cc, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, +blitdofast_desc_d8, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_e2, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_ea, 0, 0, 0, 0, 0, +blitdofast_desc_f0, 0, 0, 0, 0, 0, 0, 0, +0, 0, blitdofast_desc_fa, 0, blitdofast_desc_fc, 0, 0, 0 }; diff --git a/src/blitter.cpp b/src/blitter.cpp index dfff8611..5e26aee0 100644 --- a/src/blitter.cpp +++ b/src/blitter.cpp @@ -6,8 +6,8 @@ * (c) 1995 Bernd Schmidt, Alessandro Bissacco * (c) 2002 - 2005 Toni Wilen */ -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" @@ -18,7 +18,7 @@ #include "blitter.h" #include "blit.h" - /* we must not change ce-mode while blitter is running.. */ +/* we must not change ce-mode while blitter is running.. */ static int blitter_cycle_exact, immediate_blits; static int blt_statefile_type; @@ -179,30 +179,30 @@ There is at least one demo that does this.. /* Copper pointer to Blitter register copy bug -1: -d = D (-D) -2: -c = C (-C) -3: - (-CD) -4: - (-B-) -5: - (-BD) -6: - (-BC) -7: -BcD = C, -BCd = D -8: - (A-) -9: - (AD) -A: - (AC) -B: A (ACD) -C: - (AB-) -D: - (ABD-) -E: - (ABC) -F: AxBxCxD = -, aBxCxD = A, + 1: -d = D (-D) + 2: -c = C (-C) + 3: - (-CD) + 4: - (-B-) + 5: - (-BD) + 6: - (-BC) + 7: -BcD = C, -BCd = D + 8: - (A-) + 9: - (AD) + A: - (AC) + B: A (ACD) + C: - (AB-) + D: - (ABD-) + E: - (ABC) + F: AxBxCxD = -, aBxCxD = A, -1FE,8C,RGA,8C + 1FE,8C,RGA,8C -*/ + */ // 5 = internal "processing cycle" static const int blit_cycle_diagram_line[] = { - 4,0,3,5,4, 0,3,5,4 + 4, 0,3,5,4, 0,3,5,4 }; static const int blit_cycle_diagram_finald[] = @@ -215,7 +215,7 @@ static const int blit_cycle_diagram_finalld[] = 2, 0,0, 0,0 }; -static int get_cycle_diagram_type(const int *diag) +static int get_cycle_diagram_type (const int *diag) { for (int i = 0; i < 16; i++) { if (diag == &blit_cycle_diagram[i][0]) @@ -231,7 +231,7 @@ static int get_cycle_diagram_type(const int *diag) return 0x82; return 0xff; } -static const int *set_cycle_diagram_type(uae_u8 diag) +static const int *set_cycle_diagram_type (uae_u8 diag) { if (diag >= 0x00 && diag <= 0x0f) return &blit_cycle_diagram[diag][0]; @@ -246,7 +246,7 @@ static const int *set_cycle_diagram_type(uae_u8 diag) return NULL; } -void build_blitfilltable(void) +void build_blitfilltable (void) { unsigned int d, fillmask; int i; @@ -274,7 +274,7 @@ void build_blitfilltable(void) } } -STATIC_INLINE const int *get_ch(void) +STATIC_INLINE const int *get_ch (void) { if (blit_faulty) return &blit_diag[0]; @@ -283,25 +283,24 @@ STATIC_INLINE const int *get_ch(void) return blit_diag; } -STATIC_INLINE int channel_state(int cycles) +STATIC_INLINE int channel_state (int cycles) { const int *diag; if (cycles < 0) return 0; - diag = get_ch(); + diag = get_ch (); if (cycles < diag[0]) return diag[1 + cycles]; cycles -= diag[0]; cycles %= diag[0]; return diag[1 + diag[0] + cycles]; } - -STATIC_INLINE int channel_pos(int cycles) +STATIC_INLINE int channel_pos (int cycles) { const int *diag; if (cycles < 0) return 0; - diag = get_ch(); + diag = get_ch (); if (cycles < diag[0]) return cycles; cycles -= diag[0]; @@ -314,35 +313,35 @@ int blitter_channel_state(void) return channel_state(blit_cyclecounter); } -static void reset_channel_mods(void) +static void reset_channel_mods (void) { if (bltptxpos < 0) return; bltptxpos = -1; switch (bltptxc) { - case 1: + case 1: bltapt = bltptx; break; - case 2: + case 2: bltbpt = bltptx; break; - case 3: + case 3: bltcpt = bltptx; break; - case 4: + case 4: bltdpt = bltptx; break; } } -static void check_channel_mods(int hpos, int ch) +static void check_channel_mods (int hpos, int ch) { if (bltptxpos != hpos) return; if (ch == bltptxc) { bltptxpos = -1; - write_log(_T("BLITTER: %08X write to %cPT ignored! %08x\n"), bltptx, ch + 'A' - 1, m68k_getpc()); + write_log (_T("BLITTER: %08X write to %cPT ignored! %08x\n"), bltptx, ch + 'A' - 1, m68k_getpc ()); //activate_debugger(); } } @@ -380,11 +379,11 @@ STATIC_INLINE void chipmem_agnus_wput2 (uaecptr addr, uae_u32 w) chipmem_wput_indirect (addr, w); } -static void blitter_dofast(void) +static void blitter_dofast (void) { - int i,j; - uaecptr bltadatptr = 0, bltbdatptr = 0, bltcdatptr = 0, bltddatptr = 0; - uae_u8 mt = bltcon0 & 0xFF; + int i,j; + uaecptr bltadatptr = 0, bltbdatptr = 0, bltcdatptr = 0, bltddatptr = 0; + uae_u8 mt = bltcon0 & 0xFF; blit_masktable[0] = blt_info.bltafwm; blit_masktable[blt_info.hblitsize - 1] &= blt_info.bltalwm; @@ -420,7 +419,7 @@ static void blitter_dofast(void) for (i = 0; i < blt_info.hblitsize; i++) { uae_u32 bltadat, blitahold; if (bltadatptr) { - blt_info.bltadat = bltadat = chipmem_wget_indirect(bltadatptr); + blt_info.bltadat = bltadat = chipmem_wget_indirect (bltadatptr); bltadatptr += 2; } else @@ -430,7 +429,7 @@ static void blitter_dofast(void) blt_info.bltaold = bltadat; if (bltbdatptr) { - uae_u16 bltbdat = chipmem_wget_indirect(bltbdatptr); + uae_u16 bltbdat = chipmem_wget_indirect (bltbdatptr); bltbdatptr += 2; blitbhold = (((uae_u32)blt_info.bltbold << 16) | bltbdat) >> blt_info.blitbshift; blt_info.bltbold = bltbdat; @@ -438,12 +437,12 @@ static void blitter_dofast(void) } if (bltcdatptr) { - blt_info.bltcdat = chipmem_wget_indirect(bltcdatptr); + blt_info.bltcdat = chipmem_wget_indirect (bltcdatptr); bltcdatptr += 2; } if (dodst) - chipmem_agnus_wput2(dstp, blt_info.bltddat); - blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; + chipmem_agnus_wput2 (dstp, blt_info.bltddat); + blt_info.bltddat = blit_func (blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; if (blitfill) { uae_u16 d = blt_info.bltddat; int ifemode = blitife ? 2 : 0; @@ -470,7 +469,7 @@ static void blitter_dofast(void) bltddatptr += blt_info.bltdmod; } if (dodst) - chipmem_agnus_wput2(dstp, blt_info.bltddat); + chipmem_agnus_wput2 (dstp, blt_info.bltddat); blt_info.bltbhold = blitbhold; } blit_masktable[0] = 0xFFFF; @@ -481,29 +480,29 @@ static void blitter_dofast(void) static void blitter_dofast_desc(void) { - int i,j; - uaecptr bltadatptr = 0, bltbdatptr = 0, bltcdatptr = 0, bltddatptr = 0; - uae_u8 mt = bltcon0 & 0xFF; + int i,j; + uaecptr bltadatptr = 0, bltbdatptr = 0, bltcdatptr = 0, bltddatptr = 0; + uae_u8 mt = bltcon0 & 0xFF; - blit_masktable[0] = blt_info.bltafwm; - blit_masktable[blt_info.hblitsize - 1] &= blt_info.bltalwm; + blit_masktable[0] = blt_info.bltafwm; + blit_masktable[blt_info.hblitsize - 1] &= blt_info.bltalwm; - if (bltcon0 & 0x800) { - bltadatptr = bltapt; - bltapt -= (blt_info.hblitsize * 2 + blt_info.bltamod) * blt_info.vblitsize; - } - if (bltcon0 & 0x400) { - bltbdatptr = bltbpt; - bltbpt -= (blt_info.hblitsize * 2 + blt_info.bltbmod) * blt_info.vblitsize; - } - if (bltcon0 & 0x200) { - bltcdatptr = bltcpt; - bltcpt -= (blt_info.hblitsize * 2 + blt_info.bltcmod) * blt_info.vblitsize; - } - if (bltcon0 & 0x100) { - bltddatptr = bltdpt; - bltdpt -= (blt_info.hblitsize * 2 + blt_info.bltdmod) * blt_info.vblitsize; - } + if (bltcon0 & 0x800) { + bltadatptr = bltapt; + bltapt -= (blt_info.hblitsize * 2 + blt_info.bltamod) * blt_info.vblitsize; + } + if (bltcon0 & 0x400) { + bltbdatptr = bltbpt; + bltbpt -= (blt_info.hblitsize * 2 + blt_info.bltbmod) * blt_info.vblitsize; + } + if (bltcon0 & 0x200) { + bltcdatptr = bltcpt; + bltcpt -= (blt_info.hblitsize * 2 + blt_info.bltcmod) * blt_info.vblitsize; + } + if (bltcon0 & 0x100) { + bltddatptr = bltdpt; + bltdpt -= (blt_info.hblitsize * 2 + blt_info.bltdmod) * blt_info.vblitsize; + } if (blitfunc_dofast_desc[mt] && !blitfill) { (*blitfunc_dofast_desc[mt])(bltadatptr, bltbdatptr, bltcdatptr, bltddatptr, &blt_info); } @@ -513,91 +512,90 @@ static void blitter_dofast_desc(void) uaecptr dstp = 0; int dodst = 0; - for (j = 0; j < blt_info.vblitsize; j++) { - blitfc = !!(bltcon1 & 0x4); - for (i = 0; i < blt_info.hblitsize; i++) { - uae_u32 bltadat, blitahold; - if (bltadatptr) { - bltadat = blt_info.bltadat = chipmem_wget_indirect(bltadatptr); - bltadatptr -= 2; - } - else - bltadat = blt_info.bltadat; - bltadat &= blit_masktable[i]; - blitahold = (((uae_u32)bltadat << 16) | blt_info.bltaold) >> blt_info.blitdownashift; - blt_info.bltaold = bltadat; + for (j = 0; j < blt_info.vblitsize; j++) { + blitfc = !!(bltcon1 & 0x4); + for (i = 0; i < blt_info.hblitsize; i++) { + uae_u32 bltadat, blitahold; + if (bltadatptr) { + bltadat = blt_info.bltadat = chipmem_wget_indirect (bltadatptr); + bltadatptr -= 2; + } else + bltadat = blt_info.bltadat; + bltadat &= blit_masktable[i]; + blitahold = (((uae_u32)bltadat << 16) | blt_info.bltaold) >> blt_info.blitdownashift; + blt_info.bltaold = bltadat; - if (bltbdatptr) { - uae_u16 bltbdat = chipmem_wget_indirect(bltbdatptr); - bltbdatptr -= 2; - blitbhold = (((uae_u32)bltbdat << 16) | blt_info.bltbold) >> blt_info.blitdownbshift; - blt_info.bltbold = bltbdat; - blt_info.bltbdat = bltbdat; - } + if (bltbdatptr) { + uae_u16 bltbdat = chipmem_wget_indirect (bltbdatptr); + bltbdatptr -= 2; + blitbhold = (((uae_u32)bltbdat << 16) | blt_info.bltbold) >> blt_info.blitdownbshift; + blt_info.bltbold = bltbdat; + blt_info.bltbdat = bltbdat; + } - if (bltcdatptr) { - blt_info.bltcdat = blt_info.bltbdat = chipmem_wget_indirect(bltcdatptr); - bltcdatptr -= 2; - } - if (dodst) - chipmem_agnus_wput2(dstp, blt_info.bltddat); - blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; - if (blitfill) { - uae_u16 d = blt_info.bltddat; - int ifemode = blitife ? 2 : 0; - int fc1 = blit_filltable[d & 255][ifemode + blitfc][1]; - blt_info.bltddat = (blit_filltable[d & 255][ifemode + blitfc][0] - + (blit_filltable[d >> 8][ifemode + fc1][0] << 8)); - blitfc = blit_filltable[d >> 8][ifemode + fc1][1]; - } - if (blt_info.bltddat) - blt_info.blitzero = 0; - if (bltddatptr) { - dstp = bltddatptr; - dodst = 1; - bltddatptr -= 2; - } - } - if (bltadatptr) - bltadatptr -= blt_info.bltamod; - if (bltbdatptr) - bltbdatptr -= blt_info.bltbmod; - if (bltcdatptr) - bltcdatptr -= blt_info.bltcmod; - if (bltddatptr) - bltddatptr -= blt_info.bltdmod; - } - if (dodst) - chipmem_agnus_wput2(dstp, blt_info.bltddat); - blt_info.bltbhold = blitbhold; - } - blit_masktable[0] = 0xFFFF; - blit_masktable[blt_info.hblitsize - 1] = 0xFFFF; + if (bltcdatptr) { + blt_info.bltcdat = blt_info.bltbdat = chipmem_wget_indirect (bltcdatptr); + bltcdatptr -= 2; + } + if (dodst) + chipmem_agnus_wput2 (dstp, blt_info.bltddat); + blt_info.bltddat = blit_func (blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; + if (blitfill) { + uae_u16 d = blt_info.bltddat; + int ifemode = blitife ? 2 : 0; + int fc1 = blit_filltable[d & 255][ifemode + blitfc][1]; + blt_info.bltddat = (blit_filltable[d & 255][ifemode + blitfc][0] + + (blit_filltable[d >> 8][ifemode + fc1][0] << 8)); + blitfc = blit_filltable[d >> 8][ifemode + fc1][1]; + } + if (blt_info.bltddat) + blt_info.blitzero = 0; + if (bltddatptr) { + dstp = bltddatptr; + dodst = 1; + bltddatptr -= 2; + } + } + if (bltadatptr) + bltadatptr -= blt_info.bltamod; + if (bltbdatptr) + bltbdatptr -= blt_info.bltbmod; + if (bltcdatptr) + bltcdatptr -= blt_info.bltcmod; + if (bltddatptr) + bltddatptr -= blt_info.bltdmod; + } + if (dodst) + chipmem_agnus_wput2 (dstp, blt_info.bltddat); + blt_info.bltbhold = blitbhold; + } + blit_masktable[0] = 0xFFFF; + blit_masktable[blt_info.hblitsize - 1] = 0xFFFF; - bltstate = BLT_done; + bltstate = BLT_done; } -STATIC_INLINE void blitter_read(void) +STATIC_INLINE void blitter_read (void) { if (bltcon0 & 0x200) { - blt_info.bltcdat = chipmem_wget_indirect(bltcpt); + blt_info.bltcdat = chipmem_wget_indirect (bltcpt); last_custom_value1 = blt_info.bltcdat; } bltstate = BLT_work; } -STATIC_INLINE void blitter_write(void) +STATIC_INLINE void blitter_write (void) { if (blt_info.bltddat) blt_info.blitzero = 0; /* D-channel state has no effect on linedraw, but C must be enabled or nothing is drawn! */ if (bltcon0 & 0x200) { - chipmem_wput_indirect(bltdpt, blt_info.bltddat); + chipmem_wput_indirect (bltdpt, blt_info.bltddat); } bltstate = BLT_next; } -STATIC_INLINE void blitter_line_incx(void) +STATIC_INLINE void blitter_line_incx (void) { if (++blinea_shift == 16) { blinea_shift = 0; @@ -605,7 +603,7 @@ STATIC_INLINE void blitter_line_incx(void) } } -STATIC_INLINE void blitter_line_decx(void) +STATIC_INLINE void blitter_line_decx (void) { if (blinea_shift-- == 0) { blinea_shift = 15; @@ -613,30 +611,30 @@ STATIC_INLINE void blitter_line_decx(void) } } -STATIC_INLINE void blitter_line_decy(void) +STATIC_INLINE void blitter_line_decy (void) { bltcpt -= blt_info.bltcmod; blitonedot = 0; } -STATIC_INLINE void blitter_line_incy(void) +STATIC_INLINE void blitter_line_incy (void) { bltcpt += blt_info.bltcmod; blitonedot = 0; } -static void blitter_line(void) +static void blitter_line (void) { uae_u16 blitahold = (blinea & blt_info.bltafwm) >> blinea_shift; uae_u16 blitchold = blt_info.bltcdat; blt_info.bltbhold = (blineb & 1) ? 0xFFFF : 0; blitlinepixel = !blitsing || (blitsing && !blitonedot); - blt_info.bltddat = blit_func(blitahold, blt_info.bltbhold, blitchold, bltcon0 & 0xFF); + blt_info.bltddat = blit_func (blitahold, blt_info.bltbhold, blitchold, bltcon0 & 0xFF); blitonedot++; } -static void blitter_line_proc(void) +static void blitter_line_proc (void) { if (bltcon0 & 0x800) { if (blitsign) @@ -648,35 +646,33 @@ static void blitter_line_proc(void) if (!blitsign) { if (bltcon1 & 0x10) { if (bltcon1 & 0x8) - blitter_line_decy(); + blitter_line_decy (); else - blitter_line_incy(); - } - else { + blitter_line_incy (); + } else { if (bltcon1 & 0x8) - blitter_line_decx(); + blitter_line_decx (); else - blitter_line_incx(); + blitter_line_incx (); } } if (bltcon1 & 0x10) { if (bltcon1 & 0x4) - blitter_line_decx(); + blitter_line_decx (); else - blitter_line_incx(); - } - else { + blitter_line_incx (); + } else { if (bltcon1 & 0x4) - blitter_line_decy(); + blitter_line_decy (); else - blitter_line_incy(); + blitter_line_incy (); } blitsign = 0 > (uae_s16)bltapt; bltstate = BLT_write; } -STATIC_INLINE void blitter_nxline(void) +STATIC_INLINE void blitter_nxline (void) { blineb = (blineb << 1) | (blineb >> 15); blt_info.vblitsize--; @@ -689,15 +685,15 @@ static int blitter_cyclecounter; static int blitter_hcounter1, blitter_hcounter2; static int blitter_vcounter1, blitter_vcounter2; -static void decide_blitter_line(int hsync, int hpos) +static void decide_blitter_line (int hsync, int hpos) { if (blit_final && blt_info.vblitsize) blit_final = 0; while (last_blitter_hpos < hpos) { - int c = channel_state(blit_cyclecounter); + int c = channel_state (blit_cyclecounter); for (;;) { - int v = canblit(last_blitter_hpos); + int v = canblit (last_blitter_hpos); if (blit_waitcyclecounter) { blit_waitcyclecounter = 0; @@ -705,7 +701,7 @@ static void decide_blitter_line(int hsync, int hpos) } // final 2 idle cycles? does not need free bus - if (blit_final) { + if (blit_final) { blit_cyclecounter++; blit_totalcyclecounter++; if (blit_cyclecounter >= 2) { @@ -724,34 +720,32 @@ static void decide_blitter_line(int hsync, int hpos) blit_cyclecounter++; blit_totalcyclecounter++; - check_channel_mods(last_blitter_hpos, c); + check_channel_mods (last_blitter_hpos, c); if (c == 3) { - blitter_read(); - alloc_cycle_blitter(last_blitter_hpos, &bltcpt, 3); - record_dma_blit(0x70, blt_info.bltcdat, bltcpt, last_blitter_hpos); + blitter_read (); + alloc_cycle_blitter (last_blitter_hpos, &bltcpt, 3); + record_dma_blit (0x70, blt_info.bltcdat, bltcpt, last_blitter_hpos); blitter_nasty++; - } - else if (c == 5) { + } else if (c == 5) { if (ddat1use) { bltdpt = bltcpt; } ddat1use = 1; - blitter_line(); - blitter_line_proc(); - blitter_nxline(); + blitter_line (); + blitter_line_proc (); + blitter_nxline (); - } - else if (c == 4) { + } else if (c == 4) { /* onedot mode and no pixel = bus write access is skipped */ if (blitlinepixel) { - blitter_write(); - alloc_cycle_blitter(last_blitter_hpos, &bltdpt, 4); - record_dma_blit(0x00, blt_info.bltddat, bltdpt, last_blitter_hpos); + blitter_write (); + alloc_cycle_blitter (last_blitter_hpos, &bltdpt, 4); + record_dma_blit (0x00, blt_info.bltddat, bltdpt, last_blitter_hpos); blitlinepixel = 0; blitter_nasty++; } @@ -762,7 +756,7 @@ static void decide_blitter_line(int hsync, int hpos) blit_waitcyclecounter = 0; // blit finished bit is set and interrupt triggered // immediately after last D write - blitter_interrupt(last_blitter_hpos, 0); + blitter_interrupt (last_blitter_hpos, 0); break; } @@ -774,44 +768,43 @@ static void decide_blitter_line(int hsync, int hpos) } if (hsync) last_blitter_hpos = 0; - reset_channel_mods(); + reset_channel_mods (); } #endif -static void actually_do_blit(void) +static void actually_do_blit (void) { if (blitline) { do { - blitter_read(); + blitter_read (); if (ddat1use) bltdpt = bltcpt; ddat1use = 1; - blitter_line(); - blitter_line_proc(); - blitter_nxline(); + blitter_line (); + blitter_line_proc (); + blitter_nxline (); if (blitlinepixel) { - blitter_write(); + blitter_write (); blitlinepixel = 0; } if (blt_info.vblitsize == 0) bltstate = BLT_done; } while (bltstate != BLT_done); bltdpt = bltcpt; - } - else { + } else { if (blitdesc) - blitter_dofast_desc(); + blitter_dofast_desc (); else - blitter_dofast(); + blitter_dofast (); bltstate = BLT_done; } } -static void blitter_doit(void) +static void blitter_doit (void) { if (blt_info.vblitsize == 0 || (blitline && blt_info.hblitsize != 2)) { - blitter_done(current_hpos()); + blitter_done (current_hpos()); return; } @@ -871,8 +864,8 @@ static void blitter_force_finish(void) return; if (bltstate != BLT_done) { /* blitter is currently running - * force finish (no blitter state support yet) - */ + * force finish (no blitter state support yet) + */ odmacon = dmacon; dmacon |= DMA_MASTER | DMA_BLITTER; actually_do_blit(); @@ -896,8 +889,8 @@ static void blit_bltset (int con) blt_info.blitdownbshift = 16 - blt_info.blitbshift; if ((bltcon1 & 1) && !blitline_started) { write_log (_T("BLITTER: linedraw enabled after starting normal blit! %08x\n"), M68K_GETPC); - return; - } + return; + } } if (con & 1) { @@ -955,11 +948,12 @@ static void blit_bltset (int con) blit_nod = 0; } if (blit_dmacount2 == 0) { + ddat2use = 0; ddat1use = 0; } } -static void blit_modset(void) +static void blit_modset (void) { int mult; @@ -971,7 +965,7 @@ static void blit_modset(void) blit_modaddd = mult * blt_info.bltdmod; } -void reset_blit(int bltcon) +void reset_blit (int bltcon) { if (bltcon & 1) blinea_shift = bltcon0 >> 12; @@ -980,8 +974,8 @@ void reset_blit(int bltcon) if (bltstate == BLT_done) return; if (bltcon) - blit_bltset(bltcon); - blit_modset(); + blit_bltset (bltcon); + blit_modset (); } static bool waitingblits (void) @@ -1004,21 +998,21 @@ static bool waitingblits (void) } if (warned && waited) { warned--; - write_log(_T("waiting_blits detected PC=%08x\n"), M68K_GETPC); + write_log (_T("waiting_blits detected PC=%08x\n"), M68K_GETPC); } if (bltstate == BLT_done) return true; return false; } -static void blitter_start_init(void) +static void blitter_start_init (void) { blt_info.blitzero = 1; blit_frozen = 0; blitline_started = bltcon1 & 1; - blit_bltset(1 | 2); - blit_modset(); + blit_bltset (1 | 2); + blit_modset (); ddat1use = ddat2use = 0; blit_interrupt = 0; @@ -1079,21 +1073,21 @@ void do_blitter (int hpos) if (dmaen(DMA_BLITPRI)) set_special(SPCFLAG_BLTNASTY); - if (dmaen(DMA_BLITTER)) + if (dmaen (DMA_BLITTER)) bltstate = BLT_work; blit_maxcyclecounter = 0x7fffffff; blit_waitcyclecounter = 0; if (blt_info.vblitsize == 0 || (blitline && blt_info.hblitsize != 2)) { - if (dmaen(DMA_BLITTER)) - blitter_done(hpos); + if (dmaen (DMA_BLITTER)) + blitter_done (hpos); return; } if (immediate_blits) { - if (dmaen(DMA_BLITTER)) - blitter_doit(); + if (dmaen (DMA_BLITTER)) + blitter_doit (); return; } @@ -1134,7 +1128,7 @@ void maybe_blit2 (int hack) blitter_handler (0); } -void check_is_blit_dangerous(uaecptr *bplpt, int planes, int words) +void check_is_blit_dangerous (uaecptr *bplpt, int planes, int words) { blitter_dangerous_bpl = 0; if (bltstate == BLT_done || !blitter_cycle_exact) @@ -1170,7 +1164,7 @@ int blitnasty (void) } /* very approximate emulation of blitter slowdown caused by bitplane DMA */ -void blitter_slowdown(int ddfstrt, int ddfstop, int totalcycles, int freecycles) +void blitter_slowdown (int ddfstrt, int ddfstop, int totalcycles, int freecycles) { static int oddfstrt, oddfstop, ototal, ofree; static int slow; @@ -1195,7 +1189,7 @@ void blitter_slowdown(int ddfstrt, int ddfstop, int totalcycles, int freecycles) blit_misscyclecounter += slow; } -void blitter_reset(void) +void blitter_reset (void) { bltptxpos = -1; } @@ -1220,14 +1214,14 @@ void restore_blitter_finish (void) uae_u8 *restore_blitter (uae_u8 *src) { - uae_u32 flags = restore_u32(); + uae_u32 flags = restore_u32(); blt_statefile_type = 0; blt_delayed_irq = 0; bltstate = BLT_done; if (flags & 4) { - bltstate = (flags & 1) ? BLT_done : BLT_init; - } + bltstate = (flags & 1) ? BLT_done : BLT_init; + } if (flags & 2) { write_log (_T("blitter was force-finished when this statefile was saved\n")); write_log (_T("contact the author if restored program freezes\n")); @@ -1236,28 +1230,29 @@ uae_u8 *restore_blitter (uae_u8 *src) // interrupt.. blt_delayed_irq = -1; } - return src; + return src; } uae_u8 *save_blitter (int *len, uae_u8 *dstptr) { - uae_u8 *dstbak,*dst; - int forced; + uae_u8 *dstbak,*dst; + int forced; + + forced = 0; + if (bltstate != BLT_done && bltstate != BLT_init) { + write_log (_T("blitter is active, forcing immediate finish\n")); + /* blitter is active just now but we don't have blitter state support yet */ + blitter_force_finish(); + forced = 2; + } + if (dstptr) + dstbak = dst = dstptr; + else + dstbak = dst = xmalloc (uae_u8, 16); + save_u32 (((bltstate != BLT_done) ? 0 : 1) | forced | 4); + *len = dst - dstbak; + return dstbak; - forced = 0; - if (bltstate != BLT_done && bltstate != BLT_init) { - write_log (_T("blitter is active, forcing immediate finish\n")); - /* blitter is active just now but we don't have blitter state support yet */ - blitter_force_finish (); - forced = 2; - } - if (dstptr) - dstbak = dst = dstptr; - else - dstbak = dst = xmalloc (uae_u8, 16); - save_u32(((bltstate != BLT_done) ? 0 : 1) | forced | 4); - *len = dst - dstbak; - return dstbak; } // totally non-real-blitter-like state save but better than nothing.. @@ -1307,6 +1302,8 @@ uae_u8 *restore_blitter_new (uae_u8 *src) if (restore_u16 () != 0x1234) write_log (_T("error\n")); + blitter_nasty = restore_u8 (); + bltstate = BLT_done; if (state > 0) do_blitter (0); @@ -1371,6 +1368,8 @@ uae_u8 *save_blitter_new (int *len, uae_u8 *dstptr) save_u16 (0x1234); + save_u8 (blitter_nasty); + *len = dst - dstbak; return dstbak; } diff --git a/src/blkdev.cpp b/src/blkdev.cpp index 68746b46..185a8b6f 100644 --- a/src/blkdev.cpp +++ b/src/blkdev.cpp @@ -41,7 +41,7 @@ struct blkdevstate int wasopen; }; -struct blkdevstate state[MAX_TOTAL_SCSI_DEVICES]; +static struct blkdevstate state[MAX_TOTAL_SCSI_DEVICES]; static bool dev_init; @@ -115,11 +115,9 @@ static int cdscsidevicetype[MAX_TOTAL_SCSI_DEVICES]; static struct device_functions *devicetable[] = { NULL, - &devicefunc_cdimage, - NULL, - NULL + &devicefunc_cdimage }; -#define NUM_DEVICE_TABLE_ENTRIES 4 +#define NUM_DEVICE_TABLE_ENTRIES 2 static int driver_installed[NUM_DEVICE_TABLE_ENTRIES]; static void install_driver (int flags) @@ -277,46 +275,6 @@ static int sys_command_open_internal (int unitnum, const TCHAR *ident, cd_standa return ret; } -static int getunitinfo (int unitnum, int drive, cd_standard_unit csu, int *isaudio) -{ - struct device_info di; - if (sys_command_info (unitnum, &di, 0)) { - write_log (_T("Scanning drive %s: "), di.label); - if (di.media_inserted) { - if (isaudiotrack (&di.toc, 0)) { - if (*isaudio == 0) - *isaudio = drive; - write_log (_T("CDA")); - } - uae_u8 buffer[2048]; - if (sys_command_cd_read (unitnum, buffer, 16, 1)) { - if (!memcmp (buffer + 8, "CDTV", 4) || !memcmp (buffer + 8, "CD32", 4) || !memcmp (buffer + 8, "COMM", 4)) { - uae_u32 crc; - write_log (_T("CD32 or CDTV")); - if (sys_command_cd_read (unitnum, buffer, 21, 1)) { - crc = get_crc32 (buffer, sizeof buffer); - if (crc == 0xe56c340f) { - write_log (_T(" [CD32.TM]")); - if (csu == CD_STANDARD_UNIT_CD32) { - write_log (_T("\n")); - return 1; - } - } - } - if (csu == CD_STANDARD_UNIT_CDTV || csu == CD_STANDARD_UNIT_CD32) { - write_log (_T("\n")); - return 1; - } - } - } - } else { - write_log (_T("no media")); - } - } - write_log (_T("\n")); - return 0; -} - static int get_standard_cd_unit2 (struct uae_prefs *p, cd_standard_unit csu) { int unitnum = 0; @@ -424,7 +382,7 @@ void device_func_free(void) dev_init = false; } -int device_func_init (int flags) +static int device_func_init (int flags) { blkdev_fix_prefs (&currprefs); install_driver (flags); @@ -640,7 +598,7 @@ int sys_command_cd_toc (int unitnum, struct cd_toc_head *toc) } /* read one cd sector */ -int sys_command_cd_read (int unitnum, uae_u8 *data, int block, int size) +static int sys_command_cd_read (int unitnum, uae_u8 *data, int block, int size) { int v; if (failunit (unitnum)) @@ -689,7 +647,7 @@ int sys_command_ismedia (int unitnum, int quick) return v; } -struct device_info *sys_command_info_session (int unitnum, struct device_info *di, int quick, int session) +static struct device_info *sys_command_info_session (int unitnum, struct device_info *di, int quick, int session) { struct blkdevstate *st = &state[unitnum]; if (failunit (unitnum)) @@ -754,8 +712,8 @@ uae_u8 *save_cd (int num, int *len) return NULL; if (!currprefs.cs_cd32cd) return NULL; - dstbak = dst = xmalloc (uae_u8, 4 + 256 + 4 + 4); - save_u32 (4 | 8); + dstbak = dst = xmalloc (uae_u8, 4 + MAX_DPATH + 4 + 4 + 4 + 2 * MAX_DPATH); + save_u32 (4 | 8 | 16); save_path (currprefs.cdslots[num].name, SAVESTATE_PATH_CD); save_u32 (currprefs.cdslots[num].type); save_u32 (0); @@ -763,7 +721,8 @@ uae_u8 *save_cd (int num, int *len) sys_command_cd_qcode (num, st->play_qcode, -1, false); for (int i = 0; i < SUBQ_SIZE; i++) save_u8 (st->play_qcode[i]); - save_u32 (st->play_end_pos); + save_u32 (0); + save_path_full(currprefs.cdslots[num].name, SAVESTATE_PATH_CD); *len = dst - dstbak; return dstbak; } @@ -780,6 +739,16 @@ uae_u8 *restore_cd (int num, uae_u8 *src) s = restore_path (SAVESTATE_PATH_CD); int type = restore_u32 (); restore_u32 (); + if (flags & 8) { + restore_u32 (); + for (int i = 0; i < SUBQ_SIZE; i++) + st->play_qcode[i] = restore_u8 (); + restore_u32 (); + } + if (flags & 16) { + xfree(s); + s = restore_path_full(); + } if (flags & 4) { if (currprefs.cdslots[num].name[0] == 0 || zfile_exists (s)) { _tcscpy (changed_prefs.cdslots[num].name, s); @@ -788,12 +757,7 @@ uae_u8 *restore_cd (int num, uae_u8 *src) changed_prefs.cdslots[num].type = currprefs.cdslots[num].type = type; changed_prefs.cdslots[num].temporary = currprefs.cdslots[num].temporary = true; } - if (flags & 8) { - restore_u32 (); - for (int i = 0; i < SUBQ_SIZE; i++) - st->play_qcode[i] = restore_u8 (); - st->play_end_pos = restore_u32 (); - } + xfree(s); return src; } diff --git a/src/blkdev_cdimage.cpp b/src/blkdev_cdimage.cpp index 9aae79f8..a54fe272 100644 --- a/src/blkdev_cdimage.cpp +++ b/src/blkdev_cdimage.cpp @@ -34,8 +34,6 @@ #define FLAC__NO_DLL #include "FLAC/stream_decoder.h" -#define scsi_log write_log - #define CDDA_BUFFERS 12 enum audenc { AUDENC_NONE, AUDENC_PCM, AUDENC_MP3, AUDENC_FLAC }; @@ -51,7 +49,6 @@ struct cdtoc uae_s64 filesize; TCHAR *fname; - TCHAR *extrainfo; int address; uae_u8 adr, ctrl; int track; @@ -86,9 +83,12 @@ struct cdunit { int cdda_delay, cdda_delay_frames; bool thread_active; - TCHAR imgname[MAX_DPATH]; + TCHAR imgname_in[MAX_DPATH]; + TCHAR imgname_out[MAX_DPATH]; uae_sem_t sub_sem; struct device_info di; + volatile int cda_bufon[2]; + cda_audio *cda; }; static struct cdunit cdunits[MAX_TOTAL_SCSI_DEVICES]; @@ -242,7 +242,7 @@ void sub_to_interleaved (const uae_u8 *s, uae_u8 *d) d++; } } -void sub_to_deinterleaved (const uae_u8 *s, uae_u8 *d) +static void sub_to_deinterleaved (const uae_u8 *s, uae_u8 *d) { for (int i = 0; i < 8 * SUB_ENTRY_SIZE; i ++) { int dmask = 0x80; @@ -324,7 +324,7 @@ static int setstate (struct cdunit *cdu, int state, int playpos) return 0; } -static void *cdda_unpack_func (void *v) +static int cdda_unpack_func (void *v) { cdimage_unpack_thread = 1; mp3decoder *mp3dec = NULL; @@ -381,9 +381,6 @@ static void audio_unpack (struct cdunit *cdu, struct cdtoc *t) sleep_millis(10); } -static volatile int cda_bufon[2]; -static cda_audio *cda; - static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) { int cdda_pos = cdu->cdda_start; @@ -394,6 +391,7 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) bool foundsub; int oldtrack = -1; bool restart = false; + bool first = true; cdu->thread_active = true; @@ -401,10 +399,10 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) sleep_millis(10); oldplay = -1; - cda_bufon[0] = cda_bufon[1] = 0; + cdu->cda_bufon[0] = cdu->cda_bufon[1] = 0; bufnum = 0; - cda = new cda_audio (CDDA_BUFFERS, 2352, 44100); + cdu->cda = new cda_audio (CDDA_BUFFERS, 2352, 44100); while (cdu->cdda_play > 0) { @@ -498,9 +496,9 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) } } - cda->wait(bufnum); + cdu->cda->wait(bufnum); - cda_bufon[bufnum] = 0; + cdu->cda_bufon[bufnum] = 0; if (cdu->cdda_play <= 0) goto end; @@ -519,10 +517,10 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) setstate(cdu, AUDIO_STATUS_IN_PROGRESS, cdda_pos); - memset (cda->buffers[bufnum], 0, CDDA_BUFFERS * 2352); + memset (cdu->cda->buffers[bufnum], 0, CDDA_BUFFERS * 2352); for (cnt = 0; cnt < CDDA_BUFFERS && cdu->cdda_play > 0; cnt++) { - uae_u8 *dst = cda->buffers[bufnum] + cnt * 2352; + uae_u8 *dst = cdu->cda->buffers[bufnum] + cnt * 2352; uae_u8 subbuf[SUB_CHANNEL_SIZE]; sector = cdda_pos; @@ -587,14 +585,19 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) if (idleframes <= 0) cdu->cd_last_pos = cdda_pos; - cda_bufon[bufnum] = 1; - cda->setvolume (cdu->cdda_volume[0], cdu->cdda_volume[1]); - if (!cda->play (bufnum)) { + cdu->cda_bufon[bufnum] = 1; + cdu->cda->setvolume (cdu->cdda_volume[0], cdu->cdda_volume[1]); + if (!cdu->cda->play (bufnum)) { if (cdu->cdda_play > 0) setstate (cdu, AUDIO_STATUS_PLAY_ERROR, -1); goto end; } + if (first) { + first = false; + setstate(cdu, -3, -1); + } + if (dofinish) { cdda_pos = cdu->cdda_end + 1; if (cdu->cdda_play >= 0) @@ -604,7 +607,7 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) } - if (cda_bufon[0] == 0 && cda_bufon[1] == 0) { + if (cdu->cda_bufon[0] == 0 && cdu->cda_bufon[1] == 0) { while (cdu->cdda_paused && cdu->cdda_play == oldplay) sleep_millis(10); } @@ -619,20 +622,20 @@ static bool cdda_play_func2 (struct cdunit *cdu, int *outpos) end: *outpos = cdda_pos; - cda->wait (0); - cda->wait (1); + cdu->cda->wait (0); + cdu->cda->wait (1); while (cdimage_unpack_active == 1) sleep_millis(10); - delete cda; + delete cdu->cda; write_log (_T("IMAGE CDDA: thread killed (%s)\n"), restart ? _T("restart") : _T("play end")); cd_audio_mode_changed = false; return restart; } -static void *cdda_play_func (void *v) +static int cdda_play_func (void *v) { int outpos = -1; struct cdunit *cdu = (struct cdunit*)v; @@ -652,7 +655,7 @@ static void *cdda_play_func (void *v) cdu->cdda_play = 1; } cdu->thread_active = false; - return NULL; + return 0; } static void cdda_stop (struct cdunit *cdu) @@ -906,11 +909,6 @@ static int command_rawread (int unitnum, uae_u8 *data, int sector, int size, int } else { uae_u8 sectortype = extra >> 16; - uae_u8 cmd9 = extra >> 8; - int sync = (cmd9 >> 7) & 1; - int headercodes = (cmd9 >> 5) & 3; - int edcecc = (cmd9 >> 3) & 1; - int errorfield = (cmd9 >> 1) & 3; uae_u8 subs = extra & 7; if (subs != 0 && subs != 1 && subs != 2 && subs != 4) { ret = -1; @@ -1197,7 +1195,7 @@ static int parsemds (struct cdunit *cdu, struct zfile *zmds, const TCHAR *img) goto end; head = (MDS_Header*)mds; - if (!memcmp (head, MEDIA_DESCRIPTOR, strlen (MEDIA_DESCRIPTOR))) + if (!memcmp (head->signature, MEDIA_DESCRIPTOR, strlen (MEDIA_DESCRIPTOR))) goto end; if (head->version[0] != 1) { write_log (_T("unsupported MDS version %d, only v.1 supported\n"), head->version[0]); @@ -1603,6 +1601,9 @@ static int parsecue (struct cdunit *cdu, struct zfile *zcue, const TCHAR *img) if (!secoffset) { // secoffset == 0: same file contained also previous track t->offset = fileoffset - pregap * t->size; + } else { + // pregap was already added, do not add extra silence. + t->pregap = 0; } t->address += postgap; if (fnametypeid == AUDENC_PCM && t->handle) { @@ -1919,10 +1920,9 @@ static int parse_image (struct cdunit *cdu, const TCHAR *img) write_log (_T("%7d %02d:%02d:%02d"), t->address, (msf >> 16) & 0x7fff, (msf >> 8) & 0xff, (msf >> 0) & 0xff); if (i < cdu->tracks) { - write_log (_T(" %s %x %10lld %10lld %s%s"), + write_log (_T(" %s %x %10lld %10lld %s"), (t->ctrl & 4) ? _T("DATA ") : (t->subcode ? _T("CDA+SUB") : _T("CDA ")), t->ctrl, t->offset, t->filesize, - t->extrainfo ? t->extrainfo : _T(""), t->handle == NULL ? _T("[FILE ERROR]") : _T("")); } write_log (_T("\n")); @@ -1959,24 +1959,15 @@ static struct device_info *info_device (int unitnum, struct device_info *di, int if (!cdu->enabled) return NULL; di->open = cdu->open; - di->removable = 1; - di->bus = unitnum; - di->target = 0; - di->lun = 0; di->media_inserted = 0; - di->bytespersector = 2048; di->mediapath[0] = 0; - di->cylinders = 1; - di->trackspercylinder = 1; - di->sectorspertrack = (int)(cdu->cdsize / di->bytespersector); if (ismedia (unitnum, 1)) { di->media_inserted = 1; - _tcscpy (di->mediapath, cdu->imgname); + _tcscpy (di->mediapath, cdu->imgname_out); di->audio_playing = cdu->cdda_play > 0; } memset (&di->toc, 0, sizeof (struct cd_toc_head)); command_toc (unitnum, &di->toc); - di->write_protected = 1; di->type = INQ_ROMD; di->unitnum = unitnum + 1; if (di->mediapath[0]) { @@ -1985,10 +1976,6 @@ static struct device_info *info_device (int unitnum, struct device_info *di, int } else { _tcscpy (di->label, _T("IMG:")); } - _tcscpy (di->vendorid, _T("UAE")); - _stprintf (di->productid, _T("SCSICD%d"), unitnum); - _tcscpy (di->revision, _T("1.0")); - di->backend = _T("IMAGE"); return di; } @@ -2004,7 +1991,6 @@ static void unload_image (struct cdunit *cdu) xfree (t->fname); xfree (t->data); xfree (t->subdata); - xfree (t->extrainfo); } memset (cdu->toc, 0, sizeof cdu->toc); cdu->tracks = 0; @@ -2019,10 +2005,13 @@ static int open_device (int unitnum, const TCHAR *ident, int flags) if (!cdu->open) { uae_sem_init (&cdu->sub_sem, 0, 1); - cdu->imgname[0] = 0; - if (ident) - _tcscpy (cdu->imgname, ident); - parse_image (cdu, ident); + cdu->imgname_out[0] = 0; + cdu->imgname_in[0] = 0; + if (ident) { + _tcscpy(cdu->imgname_in, ident); + cfgfile_resolve_path_out_load(cdu->imgname_in, cdu->imgname_out, MAX_DPATH, PATH_CD); + parse_image(cdu, cdu->imgname_out); + } cdu->open = true; cdu->enabled = true; cdu->cdda_volume[0] = 0x7fff; @@ -2035,7 +2024,7 @@ static int open_device (int unitnum, const TCHAR *ident, int flags) } ret = 1; } - blkdev_cd_change (unitnum, cdu->imgname); + blkdev_cd_change (unitnum, cdu->imgname_out); return ret; } @@ -2057,7 +2046,7 @@ static void close_device (int unitnum) unload_image (cdu); uae_sem_destroy (&cdu->sub_sem); } - blkdev_cd_change (unitnum, cdu->imgname); + blkdev_cd_change (unitnum, cdu->imgname_out); } static void close_bus (void) @@ -2091,6 +2080,6 @@ struct device_functions devicefunc_cdimage = { _T("IMAGE"), open_bus, close_bus, open_device, close_device, info_device, command_pause, command_stop, command_play, command_volume, command_qcode, - command_toc, command_read, command_rawread, 0, - 0, ismedia + command_toc, command_read, command_rawread, + ismedia }; diff --git a/src/bsdsocket.cpp b/src/bsdsocket.cpp index 457ac098..9a2e89a4 100644 --- a/src/bsdsocket.cpp +++ b/src/bsdsocket.cpp @@ -8,25 +8,20 @@ * Library initialization code (c) Tauno Taipaleenmaki */ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - +#include "sysconfig.h" #include "sysdeps.h" +#include +#include #include "options.h" -#include "include/memory.h" +#include "memory.h" +#include "custom.h" +#include "newcpu.h" #include "autoconf.h" -#include "threaddep/thread.h" +#include "traps.h" #include "bsdsocket.h" +#include "threaddep/thread.h" #include "native2amiga.h" #ifdef BSDSOCKET @@ -106,13 +101,6 @@ static uae_u32 gettask (TrapContext *ctx) trap_set_areg(ctx, 1, a1); - if (ISBSDTRACE) { - uae_char name[256]; - trap_get_string(ctx, name, trap_get_long(ctx, currtask + 10), sizeof name); - tskname = au(name); - BSDTRACE ((_T("[%s] "), tskname)); - xfree (tskname); - } return currtask; } @@ -161,11 +149,9 @@ uae_u32 callfdcallback (TrapContext *ctx, SB, uae_u32 fd, uae_u32 action) uae_u32 v; if (!sb->fdcallback) return 0; - BSDTRACE((_T("FD_CALLBACK(%d,%d) "), fd, action)); trap_call_add_dreg(ctx, 0, fd); trap_call_add_dreg(ctx, 1, action); v = trap_call_func(ctx, sb->fdcallback); - BSDTRACE((_T("-> %d\n"), v)); return v; } @@ -189,7 +175,6 @@ bool checksd(TrapContext *ctx, SB, int sd) return true; } } - BSDTRACE((_T("checksd FALSE s 0x%x sd %d\n"),s,sd)); return false; } @@ -249,7 +234,6 @@ int getsd (TrapContext *ctx, SB, SOCKET_TYPE s) SOCKET_TYPE getsock (TrapContext *ctx, SB, int sd) { if ((unsigned int) (sd - 1) >= (unsigned int) sb->dtablesize) { - BSDTRACE ((_T("Invalid Socket Descriptor (%d)\n"), sd)); bsdsocklib_seterrno(ctx, sb, 38); /* ENOTSOCK */ return -1; } @@ -392,8 +376,6 @@ static struct socketbase *alloc_socketbase (TrapContext *ctx) free (sb); return NULL; } -// trap_get_dreg(ctx, 0) = SCRATCHBUFSIZE; -// trap_get_dreg(ctx, 1) = 0; sb->dtablesize = DEFAULT_DTABLE_SIZE; /* @@@ check malloc() result */ @@ -410,7 +392,6 @@ static struct socketbase *alloc_socketbase (TrapContext *ctx) if (!host_sbinit(ctx, sb)) { /* @@@ free everything */ - return NULL; } locksigqueue(); @@ -496,7 +477,6 @@ static void free_socketbase (TrapContext *ctx) static uae_u32 REGPARAM2 bsdsocklib_Expunge (TrapContext *ctx) { - BSDTRACE ((_T("Expunge() -> [ignored]\n"))); return 0; } @@ -508,8 +488,6 @@ static uae_u32 REGPARAM2 bsdsocklib_Open (TrapContext *ctx) int opencount; SB; - BSDTRACE ((_T("OpenLibrary() -> "))); - if ((sb = alloc_socketbase(ctx)) != NULL) { trap_put_word(ctx, SockLibBase + 32, opencount = trap_get_word(ctx, SockLibBase + 32) + 1); @@ -521,10 +499,7 @@ static uae_u32 REGPARAM2 bsdsocklib_Open (TrapContext *ctx) result = trap_call_lib(ctx, sb->sysbase, -0x54); /* MakeLibrary */ put_pointer(result + offsetof(struct UAEBSDBase, sb), sb); - - BSDTRACE ((_T("%0x [%d]\n"), result, opencount)); - } else - BSDTRACE ((_T("failed (out of memory)\n"))); + } return result; } @@ -544,8 +519,6 @@ static uae_u32 REGPARAM2 bsdsocklib_Close (TrapContext *ctx) trap_call_add_dreg(ctx, 0, negsize + trap_get_word(ctx, base + 18)); trap_call_lib(ctx, trap_get_long(ctx, 4), -0xD2); /* FreeMem */ - BSDTRACE ((_T("CloseLibrary() -> [%d]\n"), opencount)); - return 0; } @@ -692,7 +665,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SetSocketSignals (TrapContext *ctx) { struct socketbase *sb = get_socketbase (ctx); - BSDTRACE ((_T("SetSocketSignals(0x%08x,0x%08x,0x%08x) -> "), trap_get_dreg(ctx, 0), trap_get_dreg(ctx, 1), trap_get_dreg(ctx, 2))); sb->eintrsigs = trap_get_dreg(ctx, 0); sb->eventsigs = trap_get_dreg(ctx, 1); @@ -765,20 +737,15 @@ static uae_u32 REGPARAM2 bsdsocklib_ObtainSocket (TrapContext *ctx) id = trap_get_dreg(ctx, 0); - BSDTRACE ((_T("ObtainSocket(%d,%d,%d,%d) -> "), id, trap_get_dreg(ctx, 1), trap_get_dreg(ctx, 2), trap_get_dreg(ctx, 3))); - i = sockpoolindex (id); if (i == -1) { - BSDTRACE ((_T("[invalid key]\n"))); return -1; } s = sockdata->sockpoolsocks[i]; sd = getsd(ctx, sb, s); - BSDTRACE ((_T(" -> Socket=%d\n"), sd)); - if (sd != -1) { sb->ftable[sd - 1] = sockdata->sockpoolflags[i]; callfdcallback(ctx, sb, sd - 1, FDCB_ALLOC); @@ -803,7 +770,6 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseSocket (TrapContext *ctx) id = trap_get_dreg(ctx, 1); sd++; - BSDTRACE ((_T("ReleaseSocket(%d,%d) -> "), sd, id)); s = getsock (ctx, sb, sd); @@ -828,24 +794,19 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseSocket (TrapContext *ctx) id = curruniqid; } else if (id < 0 && id > 65535) { if (sockpoolindex (id) != -1) { - BSDTRACE ((_T("[unique ID already exists]\n"))); return -1; } } i = sockpoolindex (-1); if (i == -1) { - BSDTRACE ((_T("-1\n"))); write_log (_T("bsdsocket: ERROR: Global socket pool overflow\n")); return -1; } sockdata->sockpoolids[i] = id; sockdata->sockpoolsocks[i] = s; sockdata->sockpoolflags[i] = flags; - - BSDTRACE ((_T("id %d s 0x%x\n"), id,s)); } else { - BSDTRACE ((_T("[invalid socket descriptor]\n"))); return -1; } @@ -866,7 +827,6 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseCopyOfSocket (TrapContext *ctx) id = trap_get_dreg(ctx, 1); sd++; - BSDTRACE ((_T("ReleaseSocket(%d,%d) -> "), sd, id)); s = getsock (ctx, sb, sd); @@ -888,14 +848,12 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseCopyOfSocket (TrapContext *ctx) id = curruniqid; } else if (id < 0 && id > 65535) { if (sockpoolindex (id) != -1) { - BSDTRACE ((_T("[unique ID already exists]\n"))); return -1; } } i = sockpoolindex (-1); if (i == -1) { - BSDTRACE ((_T("-1\n"))); write_log (_T("bsdsocket: ERROR: Global socket pool overflow\n")); return -1; } @@ -903,11 +861,8 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseCopyOfSocket (TrapContext *ctx) sockdata->sockpoolsocks[i] = s; sockdata->sockpoolflags[i] = flags; - BSDTRACE ((_T("id %d s 0x%x\n"), id,s)); - } else { - BSDTRACE ((_T("[invalid socket descriptor]\n"))); return -1; } @@ -918,7 +873,6 @@ static uae_u32 REGPARAM2 bsdsocklib_ReleaseCopyOfSocket (TrapContext *ctx) static uae_u32 REGPARAM2 bsdsocklib_Errno (TrapContext *ctx) { struct socketbase *sb = get_socketbase (ctx); - BSDTRACE ((_T("Errno() -> %d\n"), sb->sb_errno)); return sb->sb_errno; } @@ -929,12 +883,9 @@ static uae_u32 REGPARAM2 bsdsocklib_SetErrnoPtr (TrapContext *ctx) uae_u32 errnoptr = trap_get_areg(ctx, 0); uae_u32 size = trap_get_dreg(ctx, 0); - BSDTRACE ((_T("SetErrnoPtr(0x%08x,%d) -> "), errnoptr, size)); - if (size == 1 || size == 2 || size == 4) { sb->errnoptr = errnoptr; sb->errnosize = size; - BSDTRACE ((_T("OK\n"))); return 0; } bsdsocklib_seterrno(ctx, sb, 22); /* EINVAL */ @@ -1054,6 +1005,9 @@ static uae_u32 REGPARAM2 bsdsocklib_Dup2Socket (TrapContext *ctx) return host_dup2socket(ctx, sb, trap_get_dreg(ctx, 0), trap_get_dreg(ctx, 1)); } +#define MSG_EOR 0x08 /* data completes record */ +#define MSG_TRUNC 0x10 /* data discarded before delivery */ + static uae_u32 REGPARAM2 bsdsocklib_sendmsg (TrapContext *ctx) { struct socketbase *sb = get_socketbase (ctx); @@ -1359,8 +1313,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) uae_u32 currtag; uae_u32 currval; - BSDTRACE ((_T("SocketBaseTagList("))); - for (;;) { currtag = trap_get_long(ctx, tagptr); currval = trap_get_long(ctx, tagptr + 4); @@ -1371,18 +1323,14 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) switch (currtag) { case TAG_DONE: - BSDTRACE ((_T("TAG_DONE"))); tagsprocessed = 0; goto done; case TAG_IGNORE: - BSDTRACE ((_T("TAG_IGNORE"))); break; case TAG_MORE: - BSDTRACE ((_T("TAG_MORE(0x%x)"), currval)); tagptr = currval; break; case TAG_SKIP: - BSDTRACE ((_T("TAG_SKIP(%d)"), currval)); tagptr += currval * 8; break; default: @@ -1393,37 +1341,26 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { - BSDTRACE ((_T("SBTM_"))); - BSDTRACE ((currtag & 0x0001 ? _T("SET") : _T("GET"))); - BSDTRACE ((currtag & 0x8000 ? _T("REF(") : _T("VAL("))); - switch ((currtag >> 1) & SBTS_CODE) { case SBTC_BREAKMASK: - BSDTRACE ((_T("SBTC_BREAKMASK),0x%x,0x%x"), currval, sb->eintrsigs)); tagcopy(ctx, currtag, currval, tagptr, &sb->eintrsigs); break; case SBTC_SIGIOMASK: - BSDTRACE ((_T("SBTC_SIGIOMASK),0x%x,0x%x"), currval, sb->eventsigs)); tagcopy(ctx, currtag, currval, tagptr, &sb->eventsigs); break; case SBTC_SIGURGMASK: - BSDTRACE ((_T("SBTC_SIGURGMASK),0x%x"), currval)); break; case SBTC_SIGEVENTMASK: - BSDTRACE ((_T("SBTC_SIGEVENTMASK),0x%x,0x%x"), currval, sb->eventsigs)); tagcopy(ctx, currtag, currval, tagptr, &sb->eventsigs); break; case SBTC_ERRNO: - BSDTRACE ((_T("SBTC_ERRNO),%x,%d"), currval, sb->sb_errno)); tagcopy(ctx, currtag, currval, tagptr, (uae_u32*)&sb->sb_errno); break; case SBTC_HERRNO: - BSDTRACE ((_T("SBTC_HERRNO),%x,%d"), currval, sb->sb_herrno)); tagcopy(ctx, currtag, currval, tagptr, (uae_u32*)&sb->sb_herrno); break; case SBTC_DTABLESIZE: - BSDTRACE ((_T("SBTC_DTABLESIZE),0x%x"), currval)); if (currtag & 1) { bsdsocklib_SetDTableSize(sb, currval); } else { @@ -1432,33 +1369,27 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_FDCALLBACK: - BSDTRACE ((_T("SBTC_FDCALLBACK),%08x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->fdcallback); break; case SBTC_LOGSTAT: - BSDTRACE ((_T("SBTC_LOGSTAT),%08x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->logstat); sb->logstat &= 0xff; break; case SBTC_LOGTAGPTR: - BSDTRACE ((_T("SBTC_LOGTAGPTR),%08x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->logptr); break; case SBTC_LOGFACILITY: - BSDTRACE ((_T("SBTC_LOGFACILITY),%08x"), currval)); if (((currtag & 1) && currval != 0 && (currval & ~LOG_FACMASK)) || !(currtag & 1)) tagcopy(ctx, currtag, currval, tagptr, &sb->logfacility); break; case SBTC_LOGMASK: - BSDTRACE ((_T("SBTC_LOGMASK),%08x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->logmask); sb->logmask &= 0xff; break; case SBTC_IOERRNOSTRPTR: if (currtag & 1) { - BSDTRACE ((_T("IOERRNOSTRPTR),invalid"))); goto done; } else { unsigned long ulTmp; @@ -1467,7 +1398,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { /* SBTM_GETVAL */ ulTmp = currval; } - BSDTRACE ((_T("IOERRNOSTRPTR),%lu"), ulTmp)); if (ulTmp < number_sys_error) { tagcopy(ctx, currtag, currval, tagptr, &iotextptrs[ulTmp]); } else { @@ -1477,7 +1407,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_S2ERRNOSTRPTR: if (currtag & 1) { - BSDTRACE ((_T("S2ERRNOSTRPTR),invalid"))); goto done; } else { unsigned long ulTmp; @@ -1486,7 +1415,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { /* SBTM_GETVAL */ ulTmp = currval; } - BSDTRACE ((_T("S2ERRNOSTRPTR),%lu"), ulTmp)); if (ulTmp < number_sys_error) { tagcopy(ctx, currtag, currval, tagptr, &sana2iotextptrs[ulTmp]); } else { @@ -1496,7 +1424,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_S2WERRNOSTRPTR: if (currtag & 1) { - BSDTRACE ((_T("S2WERRNOSTRPTR),invalid"))); goto done; } else { unsigned long ulTmp; @@ -1505,7 +1432,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { /* SBTM_GETVAL */ ulTmp = currval; } - BSDTRACE ((_T("S2WERRNOSTRPTR),%lu"), ulTmp)); if (ulTmp < number_sys_error) { tagcopy(ctx, currtag, currval, tagptr, &sana2wiretextptrs[ulTmp]); } else { @@ -1515,7 +1441,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_ERRNOSTRPTR: if (currtag & 1) { - BSDTRACE ((_T("ERRNOSTRPTR),invalid"))); goto done; } else { unsigned long ulTmp; @@ -1524,7 +1449,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { /* SBTM_GETVAL */ ulTmp = currval; } - BSDTRACE ((_T("ERRNOSTRPTR),%lu"), ulTmp)); if (ulTmp < number_sys_error) { tagcopy(ctx, currtag, currval, tagptr, &errnotextptrs[ulTmp]); } else { @@ -1534,7 +1458,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_HERRNOSTRPTR: if (currtag & 1) { - BSDTRACE ((_T("HERRNOSTRPTR),invalid"))); goto done; } else { unsigned long ulTmp; @@ -1543,7 +1466,6 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } else { /* SBTM_GETVAL */ ulTmp = currval; } - BSDTRACE ((_T("HERRNOSTRPTR),%lu"), ulTmp)); if (ulTmp < number_host_error) { tagcopy(ctx, currtag, currval, tagptr, &herrnotextptrs[ulTmp]); } else { @@ -1553,27 +1475,22 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) break; case SBTC_ERRNOBYTEPTR: - BSDTRACE ((_T("SBTC_ERRNOBYTEPTR),0x%x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->errnoptr); sb->errnosize = 1; break; case SBTC_ERRNOWORDPTR: - BSDTRACE ((_T("SBTC_ERRNOWORDPTR),0x%x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->errnoptr); sb->errnosize = 2; break; case SBTC_ERRNOLONGPTR: - BSDTRACE ((_T("SBTC_ERRNOLONGPTR),0x%x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->errnoptr); sb->errnosize = 4; break; case SBTC_HERRNOLONGPTR: - BSDTRACE ((_T("SBTC_HERRNOLONGPTR),0x%x"), currval)); tagcopy(ctx, currtag, currval, tagptr, &sb->herrnoptr); sb->herrnosize = 4; break; case SBTC_RELEASESTRPTR: - BSDTRACE((_T("SBTC_RELEASESTRPTR),0x%x"), currval)); if (!(currtag & 1)) { tagcopy(ctx, currtag, currval, tagptr, &strReleaseVer); } @@ -1585,13 +1502,10 @@ static uae_u32 REGPARAM2 bsdsocklib_SocketBaseTagList(TrapContext *ctx) } } - BSDTRACE ((_T(","))); tagptr += 8; } done: - BSDTRACE ((_T(") -> %d\n"), tagsprocessed)); - return tagsprocessed; } @@ -1603,8 +1517,6 @@ static uae_u32 REGPARAM2 bsdsocklib_GetSocketEvents(TrapContext *ctx) int flags; uae_u32 ptr = trap_get_areg(ctx, 0); - BSDTRACE ((_T("GetSocketEvents(0x%x) -> "), ptr)); - for (i = sb->dtablesize; i--; sb->eventindex++) { if (sb->eventindex >= sb->dtablesize) sb->eventindex = 0; @@ -1614,13 +1526,11 @@ static uae_u32 REGPARAM2 bsdsocklib_GetSocketEvents(TrapContext *ctx) if (flags) { sb->ftable[sb->eventindex] &= ~SET_ALL; trap_put_long(ctx, trap_get_areg(ctx, 0), flags >> 8); - BSDTRACE ((_T("%d (0x%x)\n"), sb->eventindex + 1, flags >> 8)); return sb->eventindex; // xxx } } } #endif - BSDTRACE ((_T("-1\n"))); return -1; } @@ -1644,34 +1554,20 @@ static uae_u32 REGPARAM2 bsdsocklib_init(TrapContext *ctx) if (SockLibBase) bsdlib_reset (); -#if NEWTRAP trap_call_add_areg(ctx, 0, functable); trap_call_add_areg(ctx, 1, datatable); trap_call_add_areg(ctx, 2, 0); trap_call_add_dreg(ctx, 0, LIBRARY_SIZEOF); trap_call_add_dreg(ctx, 1, 0); tmp1 = trap_call_lib(ctx, trap_get_areg(ctx, 6), -0x54); /* MakeLibrary */ -#else - trap_get_areg(ctx, 0) = functable; - trap_get_areg(ctx, 1) = datatable; - trap_get_areg(ctx, 2) = 0; - trap_get_dreg(ctx, 0) = LIBRARY_SIZEOF; - trap_get_dreg(ctx, 1) = 0; - tmp1 = CallLib(ctx, trap_get_areg(ctx, 6), -0x54); /* MakeLibrary */ -#endif if (!tmp1) { write_log (_T("bsdoscket: FATAL: Cannot create bsdsocket.library!\n")); return 0; } -#if NEWTRAP trap_call_add_areg(ctx, 1, tmp1); trap_call_lib(ctx, trap_get_areg(ctx, 6), -0x18c); /* AddLibrary */ -#else - trap_get_areg(ctx, 1) = tmp1; - CallLib (ctx, trap_get_areg(ctx, 6), -0x18c); /* AddLibrary */ -#endif SockLibBase = tmp1; @@ -1689,15 +1585,9 @@ static uae_u32 REGPARAM2 bsdsocklib_init(TrapContext *ctx) tmp1 += _tcslen(strErr) + 1; tmp1 += _tcslen(verStr) + 1; -#if NEWTRAP trap_call_add_dreg(ctx, 0, tmp1); trap_call_add_dreg(ctx, 1, 0); tmp1 = trap_call_lib(ctx, trap_get_areg(ctx, 6), -0xC6); /* AllocMem */ -#else - trap_get_dreg(ctx, 0) = tmp1; - trap_get_dreg(ctx, 1) = 0; - tmp1 = CallLib (ctx, trap_get_areg(ctx, 6), -0xC6); /* AllocMem */ -#endif if (!tmp1) { write_log (_T("bsdsocket: FATAL: Ran out of memory while creating bsdsocket.library!\n")); @@ -1745,9 +1635,6 @@ void bsdlib_reset (void) write_log (_T("BSDSOCK: cleanup end\n")); socketbases = NULL; -#if 1 - sbsigqueue = NULL; -#endif for (i = 0; i < SOCKPOOLSIZE; i++) { if (sockdata->sockpoolids[i] != UNIQUE_ID) { @@ -1825,8 +1712,11 @@ void bsdlib_install (void) sockdata->sockpoolids[i] = UNIQUE_ID; } - if (!init_socket_layer ()) + if (!init_socket_layer ()) { + res_name = 0; + res_id = 0; return; + } res_name = ds (_T("bsdsocket.library")); res_id = ds (_T("UAE bsdsocket.library 4.1")); diff --git a/src/calc.cpp b/src/calc.cpp index c3102446..9af955f9 100644 --- a/src/calc.cpp +++ b/src/calc.cpp @@ -12,11 +12,8 @@ */ -#define calc_log(x) -#include -#include #include "sysdeps.h" - + #define STACK_SIZE 32 #define MAX_VALUES 32 #define IOBUFFERS 256 @@ -31,43 +28,43 @@ static double parsedvalues[MAX_VALUES]; // 4 = right to left static int op_preced(const TCHAR c) { - switch(c) { - case '!': - return 4; + switch(c) { + case '!': + return 4; case '*': case '/': case '\\': case '%': - return 3; - case '+': case '-': - return 2; - case '=': - return 1; - } - return 0; + return 3; + case '+': case '-': + return 2; + case '=': + return 1; + } + return 0; } static bool op_left_assoc(const TCHAR c) { - switch(c) { - // left to right - case '*': case '/': case '%': case '+': case '-': - return true; - // right to left - case '=': case '!': - return false; - } - return false; + switch(c) { + // left to right + case '*': case '/': case '%': case '+': case '-': + return true; + // right to left + case '=': case '!': + return false; + } + return false; } static unsigned int op_arg_count(const TCHAR c) { - switch(c) { - case '*': case '/': case '%': case '+': case '-': case '=': - return 2; - case '!': - return 1; - default: - return c - 'A'; - } - return 0; + switch(c) { + case '*': case '/': case '%': case '+': case '-': case '=': + return 2; + case '!': + return 1; + default: + return c - 'A'; + } + return 0; } #define is_operator(c) (c == '+' || c == '-' || c == '/' || c == '*' || c == '!' || c == '%' || c == '=') @@ -76,136 +73,133 @@ static unsigned int op_arg_count(const TCHAR c) static bool shunting_yard(const TCHAR *input, TCHAR *output) { - const TCHAR *strpos = input, *strend = input + _tcslen(input); - TCHAR c, *outpos = output; + const TCHAR *strpos = input, *strend = input + _tcslen(input); + TCHAR c, *outpos = output; - TCHAR stack[STACK_SIZE]; // operator stack - unsigned int sl = 0; // stack length - TCHAR sc; // used for record stack element + TCHAR stack[STACK_SIZE]; // operator stack + unsigned int sl = 0; // stack length + TCHAR sc; // used for record stack element - while(strpos < strend) { - if (sl >= STACK_SIZE) - return false; + while(strpos < strend) { + if (sl >= STACK_SIZE) + return false; - // read one token from the input stream - c = *strpos; - if(c != ' ') { - // If the token is a number (identifier), then add it to the output queue. - if(is_ident(c)) { - *outpos = c; ++outpos; - } - // If the token is a function token, then push it onto the stack. - else if(is_function(c)) { - stack[sl] = c; - ++sl; - } - // If the token is a function argument separator (e.g., a comma): - else if(c == ',') { - bool pe = false; - while(sl > 0) { - sc = stack[sl - 1]; - if(sc == '(') { - pe = true; - break; - } - else { - // Until the token at the top of the stack is a left parenthesis, - // pop operators off the stack onto the output queue. - *outpos = sc; - ++outpos; - sl--; - } - } - // If no left parentheses are encountered, either the separator was misplaced - // or parentheses were mismatched. - if(!pe) { - calc_log ((_T("Error: separator or parentheses mismatched\n"))); - return false; - } - } - // If the token is an operator, op1, then: - else if(is_operator(c)) { - while(sl > 0) { - sc = stack[sl - 1]; - // While there is an operator token, o2, at the top of the stack - // op1 is left-associative and its precedence is less than or equal to that of op2, - // or op1 is right-associative and its precedence is less than that of op2, - if(is_operator(sc) && - ((op_left_assoc(c) && (op_preced(c) <= op_preced(sc))) || - (!op_left_assoc(c) && (op_preced(c) < op_preced(sc))))) { - // Pop o2 off the stack, onto the output queue; - *outpos = sc; - ++outpos; - sl--; - } - else { - break; - } - } - // push op1 onto the stack. - stack[sl] = c; - ++sl; - } - // If the token is a left parenthesis, then push it onto the stack. - else if(c == '(') { - stack[sl] = c; - ++sl; - } - // If the token is a right parenthesis: - else if(c == ')') { - bool pe = false; - // Until the token at the top of the stack is a left parenthesis, - // pop operators off the stack onto the output queue - while(sl > 0) { - sc = stack[sl - 1]; - if(sc == '(') { - pe = true; - break; - } - else { - *outpos = sc; - ++outpos; - sl--; - } - } - // If the stack runs out without finding a left parenthesis, then there are mismatched parentheses. - if(!pe) { - calc_log ((_T("Error: parentheses mismatched\n"))); - return false; - } - // Pop the left parenthesis from the stack, but not onto the output queue. - sl--; - // If the token at the top of the stack is a function token, pop it onto the output queue. - if(sl > 0) { - sc = stack[sl - 1]; - if(is_function(sc)) { - *outpos = sc; - ++outpos; - sl--; - } - } - } - else { - calc_log ((_T("Unknown token %c\n"), c)); - return false; // Unknown token - } + // read one token from the input stream + c = *strpos; + if(c != ' ') { + // If the token is a number (identifier), then add it to the output queue. + if(is_ident(c)) { + *outpos = c; ++outpos; + } + // If the token is a function token, then push it onto the stack. + else if(is_function(c)) { + stack[sl] = c; + ++sl; + } + // If the token is a function argument separator (e.g., a comma): + else if(c == ',') { + bool pe = false; + while(sl > 0) { + sc = stack[sl - 1]; + if(sc == '(') { + pe = true; + break; + } + else { + // Until the token at the top of the stack is a left parenthesis, + // pop operators off the stack onto the output queue. + *outpos = sc; + ++outpos; + sl--; + } } - ++strpos; - } - // When there are no more tokens to read: - // While there are still operator tokens in the stack: - while(sl > 0) { - sc = stack[sl - 1]; - if(sc == '(' || sc == ')') { - printf("Error: parentheses mismatched\n"); - return false; + // If no left parentheses are encountered, either the separator was misplaced + // or parentheses were mismatched. + if(!pe) { + return false; } - *outpos = sc; - ++outpos; - --sl; + } + // If the token is an operator, op1, then: + else if(is_operator(c)) { + while(sl > 0) { + sc = stack[sl - 1]; + // While there is an operator token, o2, at the top of the stack + // op1 is left-associative and its precedence is less than or equal to that of op2, + // or op1 is right-associative and its precedence is less than that of op2, + if(is_operator(sc) && + ((op_left_assoc(c) && (op_preced(c) <= op_preced(sc))) || + (!op_left_assoc(c) && (op_preced(c) < op_preced(sc))))) { + // Pop o2 off the stack, onto the output queue; + *outpos = sc; + ++outpos; + sl--; + } + else { + break; + } + } + // push op1 onto the stack. + stack[sl] = c; + ++sl; + } + // If the token is a left parenthesis, then push it onto the stack. + else if(c == '(') { + stack[sl] = c; + ++sl; + } + // If the token is a right parenthesis: + else if(c == ')') { + bool pe = false; + // Until the token at the top of the stack is a left parenthesis, + // pop operators off the stack onto the output queue + while(sl > 0) { + sc = stack[sl - 1]; + if(sc == '(') { + pe = true; + break; + } + else { + *outpos = sc; + ++outpos; + sl--; + } + } + // If the stack runs out without finding a left parenthesis, then there are mismatched parentheses. + if(!pe) { + return false; + } + // Pop the left parenthesis from the stack, but not onto the output queue. + sl--; + // If the token at the top of the stack is a function token, pop it onto the output queue. + if(sl > 0) { + sc = stack[sl - 1]; + if(is_function(sc)) { + *outpos = sc; + ++outpos; + sl--; + } + } + } + else { + return false; // Unknown token + } } - *outpos = 0; // Null terminator - return true; + ++strpos; + } + // When there are no more tokens to read: + // While there are still operator tokens in the stack: + while(sl > 0) { + sc = stack[sl - 1]; + if(sc == '(' || sc == ')') { + printf("Error: parentheses mismatched\n"); + return false; + } + *outpos = sc; + ++outpos; + --sl; + } + *outpos = 0; // Null terminator + return true; } @@ -229,7 +223,6 @@ static double docalcx(TCHAR op, double v1, double v2) return v1 / v2; case '\\': return (int)v1 % (int)v2; - } return 0; } @@ -271,96 +264,84 @@ static TCHAR *chartostack(TCHAR c) static bool execution_order(const TCHAR *input, double *outval) { - const TCHAR *strpos = input, *strend = input + _tcslen(input); - TCHAR c, res[4]; - unsigned int sl = 0, rn = 0; + const TCHAR *strpos = input, *strend = input + _tcslen(input); + TCHAR c, res[4]; + unsigned int sl = 0, rn = 0; struct calcstack stack[STACK_SIZE] = { { 0 } }, *sc, *sc2; double val = 0; int i; bool ok = false; // While there are input tokens left - while(strpos < strend) { + while(strpos < strend) { - if (sl >= STACK_SIZE) - return false; + if (sl >= STACK_SIZE) + return false; - // Read the next token from input. - c = *strpos; - // If the token is a value or identifier - if(is_ident(c)) { - // Push it onto the stack. - stack[sl].s = chartostack (c); - ++sl; - } - // Otherwise, the token is an operator (operator here includes both operators, and functions). - else if(is_operator(c) || is_function(c)) { - _stprintf(res, _T("_%02d"), rn); - calc_log ((_T("%s = "), res)); - ++rn; - // It is known a priori that the operator takes n arguments. - unsigned int nargs = op_arg_count(c); - // If there are fewer than n values on the stack - if(sl < nargs) { - // (Error) The user has not input sufficient values in the expression. - return false; - } - // Else, Pop the top n values from the stack. - // Evaluate the operator, with the values as arguments. - if(is_function(c)) { - calc_log ((_T("%c("), c)); - while(nargs > 0){ - sc = &stack[sl - nargs]; // to remove reverse order of arguments - if(nargs > 1) { - calc_log ((_T("%s, "), sc)); - } - else { - calc_log ((_T("%s)\n"), sc)); - } - --nargs; - } - sl-=op_arg_count(c); - } - else { - if(nargs == 1) { - sc = &stack[sl - 1]; - sl--; - val = docalc1 (c, sc, val); - calc_log ((_T("%c %s = %f;\n"), c, stacktostr(sc), val)); - } - else { - sc = &stack[sl - 2]; - calc_log ((_T("%s %c "), stacktostr(sc), c)); - sc2 = &stack[sl - 1]; - val = docalc2 (c, sc, sc2); - sl--;sl--; - calc_log ((_T("%s = %f;\n"), stacktostr(sc2), val)); - } - } - // Push the returned results, if any, back onto the stack. - stack[sl].val = val; - stack[sl].s = NULL; - ++sl; - } - ++strpos; + // Read the next token from input. + c = *strpos; + // If the token is a value or identifier + if(is_ident(c)) { + // Push it onto the stack. + stack[sl].s = chartostack (c); + ++sl; } - // If there is only one value in the stack - // That value is the result of the calculation. - if(sl == 1) { - sc = &stack[sl - 1]; - sl--; - calc_log ((_T("result = %f\n"), val)); - if (outval) - *outval = val; - ok = true; - } - for (i = 0; i < STACK_SIZE; i++) - xfree (stack[i].s); + // Otherwise, the token is an operator (operator here includes both operators, and functions). + else if(is_operator(c) || is_function(c)) { + _stprintf(res, _T("_%02d"), rn); + ++rn; + // It is known a priori that the operator takes n arguments. + unsigned int nargs = op_arg_count(c); + // If there are fewer than n values on the stack + if(sl < nargs) { + // (Error) The user has not input sufficient values in the expression. + return false; + } + // Else, Pop the top n values from the stack. + // Evaluate the operator, with the values as arguments. + if(is_function(c)) { + while(nargs > 0){ + sc = &stack[sl - nargs]; // to remove reverse order of arguments + --nargs; + } + sl-=op_arg_count(c); + } + else { + if(nargs == 1) { + sc = &stack[sl - 1]; + sl--; + val = docalc1 (c, sc, val); + } + else { + sc = &stack[sl - 2]; + sc2 = &stack[sl - 1]; + val = docalc2 (c, sc, sc2); + sl--;sl--; + } + } + // Push the returned results, if any, back onto the stack. + stack[sl].val = val; + stack[sl].s = NULL; + ++sl; + } + ++strpos; + } + // If there is only one value in the stack + // That value is the result of the calculation. + if(sl == 1) { + sc = &stack[sl - 1]; + sl--; + if (outval) + *outval = val; + ok = true; + } + for (i = 0; i < STACK_SIZE; i++) + xfree (stack[i].s); - // If there are more values in the stack - // (Error) The user input has too many values. + // If there are more values in the stack + // (Error) The user input has too many values. - return ok; + return ok; } static bool is_separator(TCHAR c) @@ -425,28 +406,14 @@ static bool parse_values(const TCHAR *ins, TCHAR *out) bool calc(const TCHAR *input, double *outval) { - TCHAR output[IOBUFFERS], output2[IOBUFFERS]; - calc_log ((_T("IN: '%s'\n"), input)); + TCHAR output[IOBUFFERS], output2[IOBUFFERS]; if (parse_values(input, output2)) { if(shunting_yard(output2, output)) { - calc_log ((_T("RPN OUT: %s\n"), output)); if(!execution_order(output, outval)) { - calc_log ((_T("PARSE ERROR!\n"))); } else { return true; } } - } - return false; + } + return false; } - -bool iscalcformula (const TCHAR *formula) -{ - for (int i = 0; i < _tcslen (formula); i++) { - TCHAR c = formula[i]; - if (is_operator (c)) - return true; - } - return false; -} - diff --git a/src/cd32_fmv.cpp b/src/cd32_fmv.cpp index 224772ba..3d74f651 100644 --- a/src/cd32_fmv.cpp +++ b/src/cd32_fmv.cpp @@ -7,11 +7,6 @@ * */ -#include -#include -#include -#include - #include "sysdeps.h" #include "options.h" @@ -22,7 +17,8 @@ #include "cda_play.h" #include "archivers/mp2/kjmp2.h" -#ifndef WIN32 +#include "devices.h" +#ifndef _WIN32 extern "C" { #include "mpeg2dec/mpeg2.h" #include "mpeg2dec/mpeg2convert.h" @@ -208,8 +204,6 @@ static double cl450_scr; #define CL450_IMEM_WORDS (2 * 512) #define CL450_TMEM_WORDS 128 #define CL450_HMEM_WORDS 16 -static uae_u16 cl450_imem[CL450_IMEM_WORDS]; -static uae_u16 cl450_tmem[CL450_TMEM_WORDS]; static uae_u16 cl450_hmem[CL450_HMEM_WORDS]; #define CL450_VID_REGS 16 static uae_u16 cl450_vid[CL450_VID_REGS]; @@ -253,7 +247,6 @@ static int cl450_video_hsync_wait; static int cl450_videoram_read; static int cl450_videoram_write; static int cl450_videoram_cnt; -static int cl450_frame_cnt; static uae_u16 l64111_regs[32]; static uae_u16 l64111intmask[2], l64111intstatus[2]; @@ -266,9 +259,7 @@ static const mpeg2_info_t *mpeg_info; static void do_irq(void) { - if (!(intreq & 8)) { - INTREQ_0(0x8000 | 0x0008); - } + safe_interrupt_set(false); } static bool l64111_checkint(bool enabled) @@ -300,7 +291,7 @@ static addrbank fmv_bank = { fmv_lget, fmv_wget, fmv_bget, fmv_lput, fmv_wput, fmv_bput, default_xlate, default_check, NULL, NULL, _T("CD32 FMV IO"), - fmv_lget, fmv_wget, + fmv_wget, ABFLAG_IO, S_READ, S_WRITE }; @@ -309,7 +300,7 @@ static addrbank fmv_rom_bank = { fmv_rom_lget, fmv_rom_wget, fmv_rom_bget, fmv_rom_lput, fmv_rom_wput, fmv_rom_bput, fmv_rom_xlate, fmv_rom_check, NULL, _T("*"), _T("CD32 FMV ROM"), - fmv_rom_lget, fmv_rom_wget, + fmv_rom_wget, ABFLAG_ROM, S_READ, S_WRITE }; @@ -318,14 +309,14 @@ static addrbank fmv_ram_bank = { fmv_ram_lget, fmv_ram_wget, fmv_ram_bget, fmv_ram_lput, fmv_ram_wput, fmv_ram_bput, fmv_ram_xlate, fmv_ram_check, NULL, _T("*"), _T("CD32 FMV RAM"), - fmv_ram_lget, fmv_ram_wget, + fmv_ram_wget, ABFLAG_RAM, S_READ, S_WRITE }; MEMORY_FUNCTIONS(fmv_rom); MEMORY_FUNCTIONS(fmv_ram); -void rethink_cd32fmv(void) +static void rethink_cd32fmv(void) { if (!fmv_ram_bank.baseaddr) return; @@ -348,8 +339,6 @@ static cda_audio *cda; static int audio_data_remaining; static int audio_skip_size; -struct zfile *fdump; - struct fmv_pcmaudio { bool ready; @@ -930,9 +919,6 @@ static void cl450_reset_cmd(void) static void cl450_newcmd(void) { -// write_log(_T("* CL450 Command %04x\n"), cl450_hmem[0]); -// for (int i = 1; i <= 4; i++) -// write_log(_T("%02d: %04x\n"), i, cl450_hmem[i]); switch (cl450_hmem[0]) { case CL_Play: @@ -1128,7 +1114,6 @@ static void cl450_wput(uaecptr addr, uae_u16 v) break; case CPU_imem: cl450_regs[CPU_iaddr] &= CL450_IMEM_WORDS - 1; - cl450_imem[CPU_iaddr] = v; cl450_regs[CPU_iaddr]++; cl450_regs[CPU_iaddr] &= CL450_IMEM_WORDS - 1; break; @@ -1138,7 +1123,6 @@ static void cl450_wput(uaecptr addr, uae_u16 v) break; case CPU_tmem: cl450_regs[CPU_taddr] &= CL450_TMEM_WORDS - 1; - cl450_tmem[CPU_taddr] = v; cl450_regs[CPU_taddr]++; cl450_regs[CPU_taddr] &= CL450_TMEM_WORDS - 1; break; @@ -1214,7 +1198,7 @@ static void io_wput(uaecptr addr, uae_u16 v) static uae_u32 REGPARAM2 fmv_wget (uaecptr addr) { - uae_u32 v; + uae_u32 v = 0; addr -= fmv_start & fmv_bank.mask; addr &= fmv_bank.mask; int mask = addr & BANK_MASK; @@ -1237,7 +1221,7 @@ static uae_u32 REGPARAM2 fmv_lget (uaecptr addr) static uae_u32 REGPARAM2 fmv_bget (uaecptr addr) { - uae_u32 v; + uae_u32 v = 0; addr -= fmv_start & fmv_bank.mask; addr &= fmv_bank.mask; int mask = addr & BANK_MASK; @@ -1302,7 +1286,14 @@ static void cd32_fmv_audio_handler(void) if (!fmv_ram_bank.baseaddr) return; - cd_audio_mode_changed = false; + if (cd_audio_mode_changed || (cl450_play && !cda)) { + cd_audio_mode_changed = false; + if (cl450_play) { + delete cda; + cda = new cda_audio(PCM_SECTORS, KJMP2_SAMPLES_PER_FRAME * 4, 44100); + l64111_setvolume(); + } + } if (cl450_buffer_offset == 0) { if (cl450_buffer_empty_cnt >= 2) @@ -1347,7 +1338,7 @@ static void cd32_fmv_audio_handler(void) l64111_regs[A_CB_STATUS] -= PCM_SECTORS; } -void cd32_fmv_hsync_handler(void) +static void cd32_fmv_hsync_handler(void) { if (!fmv_ram_bank.baseaddr) return; @@ -1398,14 +1389,14 @@ void cd32_fmv_hsync_handler(void) } -void cd32_fmv_reset(void) +static void cd32_fmv_reset(int hardreset) { if (fmv_ram_bank.baseaddr) memset(fmv_ram_bank.baseaddr, 0, fmv_ram_bank.allocated_size); cd32_fmv_state(0); } -void cd32_fmv_free(void) +static void cd32_fmv_free(void) { mapped_free(&fmv_rom_bank); mapped_free(&fmv_ram_bank); @@ -1430,6 +1421,7 @@ void cd32_fmv_free(void) addrbank *cd32_fmv_init (struct autoconfig_info *aci) { + device_add_reset_imm(cd32_fmv_reset); cd32_fmv_free(); write_log (_T("CD32 FMV mapped @$%x\n"), expamem_board_pointer); if (expamem_board_pointer != fmv_start) { @@ -1461,12 +1453,7 @@ addrbank *cd32_fmv_init (struct autoconfig_info *aci) mapped_malloc(&fmv_ram_bank); if (!pcmaudio) pcmaudio = xcalloc(struct fmv_pcmaudio, L64111_CHANNEL_BUFFERS); - kjmp2_init(&mp2); - if (!cda) { - cda = new cda_audio(PCM_SECTORS, KJMP2_SAMPLES_PER_FRAME * 4, 44100); - l64111_setvolume(); - } if (!mpeg_decoder) { mpeg_decoder = mpeg2_init(); mpeg_info = mpeg2_info(mpeg_decoder); @@ -1475,6 +1462,12 @@ addrbank *cd32_fmv_init (struct autoconfig_info *aci) map_banks(&fmv_rom_bank, (fmv_start + ROM_BASE) >> 16, fmv_rom_size >> 16, 0); map_banks(&fmv_ram_bank, (fmv_start + RAM_BASE) >> 16, fmv_ram_size >> 16, 0); map_banks(&fmv_bank, (fmv_start + IO_BASE) >> 16, (RAM_BASE - IO_BASE) >> 16, 0); - cd32_fmv_reset(); + cd32_fmv_reset(1); + + device_add_hsync(cd32_fmv_hsync_handler); + //device_add_vsync_pre(cd32_fmv_vsync_handler); + device_add_exit(cd32_fmv_free); + device_add_rethink(rethink_cd32fmv); + return &fmv_rom_bank; } diff --git a/src/cd32_fmv_genlock.cpp b/src/cd32_fmv_genlock.cpp index cdae8c57..4bdac2d4 100644 --- a/src/cd32_fmv_genlock.cpp +++ b/src/cd32_fmv_genlock.cpp @@ -7,8 +7,6 @@ * */ -#include - #include "sysdeps.h" #include "xwin.h" @@ -63,7 +61,6 @@ void cd32_fmv_state(int state) // slow software method but who cares. - static void genlock_32(struct vidbuffer *vbin, struct vidbuffer *vbout, int w, int h, int d, int hoffset, int voffset, int mult) { for (int hh = 0, sh = -voffset; hh < h; sh++, hh += mult) { @@ -179,7 +176,7 @@ void cd32_fmv_genlock(struct vidbuffer *vbin, struct vidbuffer *vbout) if(mult == 1) genlock_16_nomult(vbin, vbout, w, h, d, hoffset, voffset); else - genlock_16(vbin, vbout, w, h, d, hoffset, voffset, mult); + genlock_16(vbin, vbout, w, h, d, hoffset, voffset, mult); } else genlock_32(vbin, vbout, w, h, d, hoffset, voffset, mult); diff --git a/src/cdrom.cpp b/src/cdrom.cpp index 304e28bf..9f274ff5 100644 --- a/src/cdrom.cpp +++ b/src/cdrom.cpp @@ -1,5 +1,3 @@ -#include - #include "sysconfig.h" /* CDROM MODE 1 EDC/ECC code (from Reed-Solomon library by Heiko Eissfeldt) */ diff --git a/src/cfgfile.cpp b/src/cfgfile.cpp index f5242431..e819ffd5 100644 --- a/src/cfgfile.cpp +++ b/src/cfgfile.cpp @@ -54,11 +54,83 @@ struct cfg_lines const TCHAR *config_label, *config_help; }; -static const TCHAR* guimode1[] = {_T("no"), _T("yes"), _T("nowait"), nullptr}; -static const TCHAR* guimode2[] = {_T("false"), _T("true"), _T("nowait"), nullptr}; -static const TCHAR* guimode3[] = {_T("0"), _T("1"), _T("nowait"), nullptr}; -static const TCHAR* csmode[] = {_T("ocs"), _T("ecs_agnus"), _T("ecs_denise"), _T("ecs"), _T("aga"), nullptr}; -static const TCHAR* linemode[] = { +static const struct cfg_lines opttable[] = +{ + {_T("help"), _T("Prints this help") }, + {_T("config_description"), _T("") }, + {_T("config_info"), _T("") }, + {_T("use_gui"), _T("Enable the GUI? If no, then goes straight to emulator") }, + {_T("use_debugger"), _T("Enable the debugger?") }, + {_T("cpu_speed"), _T("can be max, real, or a number between 1 and 20") }, + {_T("cpu_model"), _T("Can be 68000, 68010, 68020, 68030, 68040, 68060") }, + {_T("fpu_model"), _T("Can be 68881, 68882, 68040, 68060") }, + {_T("cpu_compatible"), _T("yes enables compatibility-mode") }, + {_T("cpu_24bit_addressing"), _T("must be set to 'no' in order for Z3mem or P96mem to work") }, + {_T("autoconfig"), _T("yes = add filesystems and extra ram") }, + {_T("log_illegal_mem"), _T("print illegal memory access by Amiga software?") }, + {_T("fastmem_size"), _T("Size in megabytes of fast-memory") }, + {_T("chipmem_size"), _T("Size in megabytes of chip-memory") }, + {_T("bogomem_size"), _T("Size in megabytes of bogo-memory at 0xC00000") }, + {_T("a3000mem_size"), _T("Size in megabytes of A3000 memory") }, + {_T("gfxcard_size"), _T("Size in megabytes of Picasso96 graphics-card memory") }, + {_T("z3mem_size"), _T("Size in megabytes of Zorro-III expansion memory") }, + {_T("gfx_test_speed"), _T("Test graphics speed?") }, + {_T("gfx_framerate"), _T("Print every nth frame") }, + {_T("gfx_width"), _T("Screen width") }, + {_T("gfx_height"), _T("Screen height") }, + {_T("gfx_refreshrate"), _T("Fullscreen refresh rate") }, + {_T("gfx_vsync"), _T("Sync screen refresh to refresh rate") }, + {_T("gfx_lores"), _T("Treat display as lo-res?") }, + {_T("gfx_linemode"), _T("Can be none, double, or scanlines") }, + {_T("gfx_fullscreen_amiga"), _T("Amiga screens are fullscreen?") }, + {_T("gfx_fullscreen_picasso"), _T("Picasso screens are fullscreen?") }, + {_T("gfx_center_horizontal"), _T("Center display horizontally?") }, + {_T("gfx_center_vertical"), _T("Center display vertically?") }, + {_T("gfx_colour_mode"), _T("") }, + {_T("32bit_blits"), _T("Enable 32 bit blitter emulation") }, + {_T("immediate_blits"), _T("Perform blits immediately") }, + {_T("show_leds"), _T("LED display") }, + {_T("keyboard_leds"), _T("Keyboard LEDs") }, + {_T("gfxlib_replacement"), _T("Use graphics.library replacement?") }, + {_T("sound_output"), _T("") }, + {_T("sound_frequency"), _T("") }, + {_T("sound_bits"), _T("") }, + {_T("sound_channels"), _T("") }, + {_T("sound_max_buff"), _T("") }, + {_T("comp_trustbyte"), _T("How to access bytes in compiler (direct/indirect/indirectKS/afterPic") }, + {_T("comp_trustword"), _T("How to access words in compiler (direct/indirect/indirectKS/afterPic") }, + {_T("comp_trustlong"), _T("How to access longs in compiler (direct/indirect/indirectKS/afterPic") }, + {_T("comp_nf"), _T("Whether to optimize away flag generation where possible") }, + {_T("comp_fpu"), _T("Whether to provide JIT FPU emulation") }, + {_T("cachesize"), _T("How many MB to use to buffer translated instructions")}, + {_T("override_dga_address"),_T("Address from which to map the frame buffer (upper 16 bits) (DANGEROUS!)")}, + {_T("avoid_dga"), _T("Set to yes if the use of DGA extension creates problems") }, + {_T("avoid_vid"), _T("Set to yes if the use of the Vidmode extension creates problems") }, + {_T("parallel_on_demand"), _T("") }, + {_T("serial_on_demand"), _T("") }, + {_T("scsi"), _T("scsi.device emulation") }, + {_T("joyport0"), _T("") }, + {_T("joyport1"), _T("") }, + {_T("pci_devices"), _T("List of PCI devices to make visible to the emulated Amiga") }, + {_T("kickstart_rom_file"), _T("Kickstart ROM image, (C) Copyright Amiga, Inc.") }, + {_T("kickstart_ext_rom_file"), _T("Extended Kickstart ROM image, (C) Copyright Amiga, Inc.") }, + {_T("kickstart_key_file"), _T("Key-file for encrypted ROM images (from Cloanto's Amiga Forever)") }, + {_T("flash_ram_file"), _T("Flash/battery backed RAM image file.") }, + {_T("cart_file"), _T("Freezer cartridge ROM image file.") }, + {_T("floppy0"), _T("Diskfile for drive 0") }, + {_T("floppy1"), _T("Diskfile for drive 1") }, + {_T("floppy2"), _T("Diskfile for drive 2") }, + {_T("floppy3"), _T("Diskfile for drive 3") }, + {_T("hardfile"), _T("access,sectors, surfaces, reserved, blocksize, path format") }, + {_T("filesystem"), _T("access,'Amiga volume-name':'host directory path' - where 'access' can be 'read-only' or 'read-write'") }, + {_T("catweasel"), _T("Catweasel board io base address") } +}; + +static const TCHAR *guimode1[] = { _T("no"), _T("yes"), _T("nowait"), 0 }; +static const TCHAR *guimode2[] = { _T("false"), _T("true"), _T("nowait"), 0 }; +static const TCHAR *guimode3[] = { _T("0"), _T("1"), _T("nowait"), 0 }; +static const TCHAR *csmode[] = { _T("ocs"), _T("ecs_agnus"), _T("ecs_denise"), _T("ecs"), _T("aga"), 0 }; +static const TCHAR *linemode[] = { _T("none"), _T("double"), _T("scanlines"), _T("scanlines2p"), _T("scanlines3p"), _T("double2"), _T("scanlines2"), _T("scanlines2p2"), _T("scanlines2p3"), @@ -212,6 +284,17 @@ static const TCHAR* obsolete[] = { _T("gfx_filter_vert_zoom"),_T("gfx_filter_horiz_zoom"), _T("gfx_filter_vert_zoom_mult"), _T("gfx_filter_horiz_zoom_mult"), _T("gfx_filter_vert_offset"), _T("gfx_filter_horiz_offset"), + _T("gfx_tearing"), _T("gfx_tearing_rtg"), + + // created by some buggy beta + _T("uaehf0%s,%s"), + _T("uaehf1%s,%s"), + _T("uaehf2%s,%s"), + _T("uaehf3%s,%s"), + _T("uaehf4%s,%s"), + _T("uaehf5%s,%s"), + _T("uaehf6%s,%s"), + _T("uaehf7%s,%s"), _T("pcibridge_rom_file"), _T("pcibridge_rom_options"), @@ -518,6 +601,10 @@ static TCHAR* cfgfile_subst_path2(const TCHAR* path, const TCHAR* subst, const T _tcscat(p, file + l); p2 = target_expand_environment(p, nullptr, 0); xfree (p); + if (p2 && p2[0] == '$') { + xfree(p2); + return NULL; + } return p2; } return nullptr; @@ -532,6 +619,63 @@ TCHAR* cfgfile_subst_path(const TCHAR* path, const TCHAR* subst, const TCHAR* fi return s; } +static TCHAR *cfgfile_get_multipath2 (struct multipath *mp, const TCHAR *path, const TCHAR *file, bool dir) +{ + for (int i = 0; i < MAX_PATHS; i++) { + if (mp->path[i][0] && _tcscmp (mp->path[i], _T(".\\")) != 0 && _tcscmp (mp->path[i], _T("./")) != 0 && (file[0] != '/' && file[0] != '\\' && !_tcschr(file, ':'))) { + TCHAR *s = NULL; + if (path) + s = cfgfile_subst_path2 (path, mp->path[i], file); + if (!s) { + TCHAR np[MAX_DPATH]; + _tcscpy (np, mp->path[i]); + fixtrailing (np); + _tcscat (np, file); + //fullpath (np, sizeof np / sizeof (TCHAR)); + s = my_strdup (np); + } + if (dir) { + if (my_existsdir (s)) + return s; + } else { + if (zfile_exists (s)) + return s; + } + xfree (s); + } + } + return NULL; +} + +static TCHAR *cfgfile_get_multipath (struct multipath *mp, const TCHAR *path, const TCHAR *file, bool dir) +{ + TCHAR *s = cfgfile_get_multipath2 (mp, path, file, dir); + if (s) + return s; + return my_strdup (file); +} + +static TCHAR *cfgfile_put_multipath (struct multipath *mp, const TCHAR *s) +{ + for (int i = 0; i < MAX_PATHS; i++) { + if (mp->path[i][0] && _tcscmp (mp->path[i], _T(".\\")) != 0 && _tcscmp (mp->path[i], _T("./")) != 0) { + if (_tcsnicmp (mp->path[i], s, _tcslen (mp->path[i])) == 0) { + return my_strdup (s + _tcslen (mp->path[i])); + } + } + } + return my_strdup (s); +} + + +static TCHAR *cfgfile_subst_path_load (const TCHAR *path, struct multipath *mp, const TCHAR *file, bool dir) +{ + TCHAR *s = cfgfile_get_multipath2 (mp, path, file, dir); + if (s) + return s; + return cfgfile_subst_path (path, mp->path[0], file); +} + static bool isdefault(const TCHAR* s) { TCHAR tmp[MAX_DPATH]; @@ -586,7 +730,11 @@ static void cfg_dowrite(struct zfile* f, const TCHAR* option, const TCHAR* optio return; cfg_write(tmp, f); } - +static void cfgfile_dwrite_coords(struct zfile *f, const TCHAR *option, int x, int y) +{ + if (x || y) + cfgfile_dwrite(f, option, _T("%d,%d"), x, y); +} static void cfg_dowrite(struct zfile* f, const TCHAR* option, const TCHAR* value, int d, int target) { cfg_dowrite(f, option, nullptr, value, d, target); @@ -728,9 +876,10 @@ void cfgfile_target_dwrite(struct zfile* f, const TCHAR* option, const TCHAR* fo va_end (parms); } -static void cfgfile_write_rom(struct zfile* f, const TCHAR* path, const TCHAR* romfile, const TCHAR* name) +static void cfgfile_write_rom (struct zfile *f, struct multipath *mp, const TCHAR *romfile, const TCHAR *name) { - TCHAR* str = cfgfile_subst_path(path, UNEXPANDED, romfile); + TCHAR *str = cfgfile_subst_path (mp->path[0], UNEXPANDED, romfile); + str = cfgfile_put_multipath (mp, str); cfgfile_write_str(f, name, str); struct zfile* zf = zfile_fopen(str, _T("rb"), ZFD_ALL); if (zf) @@ -747,25 +896,161 @@ static void cfgfile_write_rom(struct zfile* f, const TCHAR* path, const TCHAR* r zfile_fclose(zf); } xfree (str); + } -static void cfgfile_write_path(struct zfile* f, const TCHAR* path, const TCHAR* option, const TCHAR* value) +static void cfgfile_to_path_save(const TCHAR *in, TCHAR *out, int type) { - TCHAR* s = cfgfile_subst_path(path, UNEXPANDED, value); + if (_tcschr(in, '%')) { + _tcscpy(out, in); + } else { + cfgfile_resolve_path_out_save(in, out, MAX_DPATH, type); + } +} + +static void cfgfile_write_path2(struct zfile *f, const TCHAR *option, const TCHAR *value, int type) +{ + if (_tcschr(value, '%')) { + cfgfile_write_str(f, option, value); + } else { + TCHAR path[MAX_DPATH]; + cfgfile_resolve_path_out_save(value, path, MAX_DPATH, type); + cfgfile_write_str(f, option, path); + } +} +static void cfgfile_dwrite_path2(struct zfile *f, const TCHAR *option, const TCHAR *value, int type) +{ + if (_tcschr(value, '%')) { + cfgfile_dwrite_str(f, option, value); + } else { + TCHAR path[MAX_DPATH]; + cfgfile_resolve_path_out_save(value, path, MAX_DPATH, type); + cfgfile_dwrite_str(f, option, path); + } +} + +static void cfgfile_write_path (struct zfile *f, struct multipath *mp, const TCHAR *option, const TCHAR *value) +{ + TCHAR *s = cfgfile_put_multipath (mp, value); cfgfile_write_str(f, option, s); xfree (s); } - -static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, - const TCHAR* default_path, struct zfile* f) +static void cfgfile_dwrite_path (struct zfile *f, struct multipath *mp, const TCHAR *option, const TCHAR *value) { - TCHAR tmp[MAX_DPATH], tmp2[MAX_DPATH], tmp3[MAX_DPATH], hdcs[MAX_DPATH]; + TCHAR *s = cfgfile_put_multipath (mp, value); + cfgfile_dwrite_str (f, option, s); + xfree (s); +} - for (int i = 0; i < p->mountitems; i++) +static void cfgfile_write_multichoice(struct zfile *f, const TCHAR *option, const TCHAR *table[], int value) +{ + TCHAR tmp[MAX_DPATH]; + if (!value) + return; + tmp[0] = 0; + int i = 0; + while (value && table[i]) { + if (value & (1 << i) && table[i][0] && table[i][0] != '|') { + if (tmp[0]) + _tcscat(tmp, _T(",")); + _tcscat(tmp, table[i]); + } + i++; + } + if (tmp[0]) + cfgfile_write(f, option, tmp); +} + + +static void cfgfile_adjust_path(TCHAR *path, int maxsz, struct multipath *mp) +{ + if (path[0] == 0) + return; + TCHAR *s = target_expand_environment(path, NULL, 0); + _tcsncpy(path, s, maxsz - 1); + path[maxsz - 1] = 0; + if (mp) { + for (int i = 0; i < MAX_PATHS; i++) { + if (mp->path[i][0] && _tcscmp(mp->path[i], _T(".\\")) != 0 && _tcscmp(mp->path[i], _T("./")) != 0 && (path[0] != '/' && path[0] != '\\' && !_tcschr(path, ':'))) { + TCHAR np[MAX_DPATH]; + _tcscpy(np, mp->path[i]); + fixtrailing(np); + _tcscat(np, s); + //fullpath(np, sizeof np / sizeof(TCHAR)); + if (zfile_exists(np)) { + _tcsncpy(path, np, maxsz - 1); + path[maxsz - 1] = 0; + xfree(s); + return; + } + } + } + } + //fullpath(path, maxsz); + xfree(s); +} + +static void cfgfile_resolve_path_out_all(const TCHAR *path, TCHAR *out, int size, int type, bool save) +{ + struct uae_prefs *p = &currprefs; + TCHAR *s = NULL; + switch (type) { + case PATH_DIR: + s = cfgfile_subst_path_load(UNEXPANDED, &p->path_hardfile, path, true); + break; + case PATH_HDF: + s = cfgfile_subst_path_load(UNEXPANDED, &p->path_hardfile, path, false); + break; + case PATH_CD: + s = cfgfile_subst_path_load(UNEXPANDED, &p->path_cd, path, false); + break; + case PATH_ROM: + s = cfgfile_subst_path_load(UNEXPANDED, &p->path_rom, path, false); + break; + case PATH_FLOPPY: + _tcscpy(out, path); + cfgfile_adjust_path(out, MAX_DPATH, &p->path_floppy); + break; + default: + s = cfgfile_subst_path(NULL, NULL, path); + break; + } + if (s) { + _tcscpy(out, s); + xfree(s); + } + //if (!save) { + // my_resolvesoftlink(out, size, true); + //} +} + +void cfgfile_resolve_path_out_load(const TCHAR *path, TCHAR *out, int size, int type) +{ + cfgfile_resolve_path_out_all(path, out, size, type, false); +} +void cfgfile_resolve_path_load(TCHAR *path, int size, int type) +{ + cfgfile_resolve_path_out_all(path, path, size, type, false); +} +void cfgfile_resolve_path_out_save(const TCHAR *path, TCHAR *out, int size, int type) +{ + cfgfile_resolve_path_out_all(path, out, size, type, true); +} +void cfgfile_resolve_path_save(TCHAR *path, int size, int type) +{ + cfgfile_resolve_path_out_all(path, path, size, type, true); +} + + +static void write_filesys_config (struct uae_prefs *p, struct zfile *f) + { + TCHAR tmp[MAX_DPATH], tmp2[MAX_DPATH], tmp3[MAX_DPATH], str1[MAX_DPATH], hdcs[MAX_DPATH]; + + for (int i = 0; i < p->mountitems; i++) { struct uaedev_config_data* uci = &p->mountconfig[i]; struct uaedev_config_info* ci = &uci->ci; - TCHAR *str1, *str1b, *str1c, *str2b; + TCHAR *str1b, *str1c, *str2b; const TCHAR* str2; int bp = ci->bootpri; @@ -774,7 +1059,7 @@ static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, { TCHAR* ptr; // separate harddrive names - str1 = my_strdup(ci->rootdir); + _tcscpy(str1, ci->rootdir); ptr = _tcschr(str1 + 1, ':'); if (ptr) { @@ -784,72 +1069,49 @@ static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, if (ptr) *ptr = 0; } - } - else - { - str1 = cfgfile_subst_path(default_path, unexpanded, ci->rootdir); + } else { + cfgfile_to_path_save(ci->rootdir, str1, ci->type == UAEDEV_DIR ? PATH_DIR : (ci->type == UAEDEV_CD ? PATH_CD : (ci->type == UAEDEV_HDF ? PATH_HDF : PATH_TAPE))); } int ct = ci->controller_type; int romtype = 0; - if (ct >= HD_CONTROLLER_TYPE_SCSI_EXPANSION_FIRST && ct <= HD_CONTROLLER_TYPE_SCSI_LAST) - { - _stprintf(hdcs, _T("scsi%d_%s"), ci->controller_unit, - expansionroms[ct - HD_CONTROLLER_TYPE_SCSI_EXPANSION_FIRST].name); + if (ct >= HD_CONTROLLER_TYPE_SCSI_EXPANSION_FIRST && ct <= HD_CONTROLLER_TYPE_SCSI_LAST) { + _stprintf(hdcs, _T("scsi%d_%s"), ci->controller_unit, expansionroms[ct - HD_CONTROLLER_TYPE_SCSI_EXPANSION_FIRST].name); romtype = expansionroms[ct - HD_CONTROLLER_TYPE_SCSI_EXPANSION_FIRST].romtype; - } - else if (ct >= HD_CONTROLLER_TYPE_IDE_EXPANSION_FIRST && ct <= HD_CONTROLLER_TYPE_IDE_LAST) - { - _stprintf(hdcs, _T("ide%d_%s"), ci->controller_unit, - expansionroms[ct - HD_CONTROLLER_TYPE_IDE_EXPANSION_FIRST].name); + } else if (ct >= HD_CONTROLLER_TYPE_IDE_EXPANSION_FIRST && ct <= HD_CONTROLLER_TYPE_IDE_LAST) { + _stprintf(hdcs, _T("ide%d_%s"), ci->controller_unit, expansionroms[ct - HD_CONTROLLER_TYPE_IDE_EXPANSION_FIRST].name); romtype = expansionroms[ct - HD_CONTROLLER_TYPE_IDE_EXPANSION_FIRST].romtype; - } - else if (ct == HD_CONTROLLER_TYPE_SCSI_AUTO) - { + //} else if (ct >= HD_CONTROLLER_TYPE_CUSTOM_FIRST && ct <= HD_CONTROLLER_TYPE_CUSTOM_LAST) { + // _stprintf(hdcs, _T("custom%d_%s"), ci->controller_unit, expansionroms[ct - HD_CONTROLLER_TYPE_CUSTOM_FIRST].name); + // romtype = expansionroms[ct - HD_CONTROLLER_TYPE_CUSTOM_FIRST].romtype; + } else if (ct == HD_CONTROLLER_TYPE_SCSI_AUTO) { _stprintf(hdcs, _T("scsi%d"), ci->controller_unit); - } - else if (ct == HD_CONTROLLER_TYPE_IDE_AUTO) - { + } else if (ct == HD_CONTROLLER_TYPE_IDE_AUTO) { _stprintf(hdcs, _T("ide%d"), ci->controller_unit); - } - else if (ct == HD_CONTROLLER_TYPE_PCMCIA) - { - if (ci->controller_type_unit == 0) - _tcscpy(hdcs, _T("scsram")); - else - _tcscpy(hdcs, _T("scide")); - } - else if (ct == HD_CONTROLLER_TYPE_UAE) - { + } else if (ct == HD_CONTROLLER_TYPE_UAE) { _stprintf(hdcs, _T("uae%d"), ci->controller_unit); } - if (romtype) - { - for (int j = 0; hdcontrollers[j].label; j++) - { - if (hdcontrollers[j].romtype == (romtype & ROMTYPE_MASK)) - { + if (romtype) { + for (int j = 0; hdcontrollers[j].label; j++) { + if (hdcontrollers[j].romtype == (romtype & ROMTYPE_MASK)) { _stprintf(hdcs, hdcontrollers[j].label, ci->controller_unit); break; } } } - if (ci->controller_type_unit > 0 && ct != HD_CONTROLLER_TYPE_PCMCIA) + if (ci->controller_type_unit > 0) _stprintf(hdcs + _tcslen(hdcs), _T("-%d"), ci->controller_type_unit + 1); str1b = cfgfile_escape(str1, _T(":,"), true); str1c = cfgfile_escape_min(str1); str2b = cfgfile_escape(str2, _T(":,"), true); - if (ci->type == UAEDEV_DIR) - { + if (ci->type == UAEDEV_DIR) { _stprintf(tmp, _T("%s,%s:%s:%s,%d"), ci->readonly ? _T("ro") : _T("rw"), ci->devname ? ci->devname : _T(""), ci->volname, str1c, bp); cfgfile_write_str(f, _T("filesystem2"), tmp); _tcscpy(tmp3, tmp); - } - else if (ci->type == UAEDEV_HDF) - { + } else if (ci->type == UAEDEV_HDF || ci->type == UAEDEV_CD || ci->type == UAEDEV_TAPE) { TCHAR filesyspath[MAX_DPATH]; - _tcscpy(filesyspath, ci->filesys); + cfgfile_to_path_save(ci->filesys, filesyspath, PATH_HDF); TCHAR* sfilesys = cfgfile_escape_min(filesyspath); _stprintf(tmp, _T("%s,%s:%s,%d,%d,%d,%d,%d,%s,%s"), ci->readonly ? _T("ro") : _T("rw"), @@ -879,15 +1141,21 @@ static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, _tcscat(tmp, _T(",CF")); _tcscat(tmp3, _T(",CF")); } - const TCHAR* extras = nullptr; - if (ct >= HD_CONTROLLER_TYPE_IDE_FIRST && ct <= HD_CONTROLLER_TYPE_IDE_LAST) - { - if (ci->unit_feature_level == HD_LEVEL_ATA_1) - { - extras = _T("ATA1"); + const TCHAR *extras = NULL; + if (ct >= HD_CONTROLLER_TYPE_SCSI_FIRST && ct <= HD_CONTROLLER_TYPE_SCSI_LAST) { + if (ci->unit_feature_level == HD_LEVEL_SCSI_1){ + extras = _T("SCSI1"); + } else if (ci->unit_feature_level == HD_LEVEL_SASI) { + extras = _T("SASI"); + } else if (ci->unit_feature_level == HD_LEVEL_SASI_ENHANCED) { + extras = _T("SASIE"); + } else if (ci->unit_feature_level == HD_LEVEL_SASI_CHS) { + extras = _T("SASI_CHS"); } - else if (ci->unit_feature_level == HD_LEVEL_ATA_2S) - { + } else if (ct >= HD_CONTROLLER_TYPE_IDE_FIRST && ct <= HD_CONTROLLER_TYPE_IDE_LAST) { + if (ci->unit_feature_level == HD_LEVEL_ATA_1) { + extras = _T("ATA1"); + } else if (ci->unit_feature_level == HD_LEVEL_ATA_2S) { extras = _T("ATA2+S"); } } @@ -915,16 +1183,19 @@ static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, cfgfile_write_str(f, _T("hardfile2"), tmp); } _stprintf(tmp2, _T("uaehf%d"), i); + if (ci->type == UAEDEV_CD) { + cfgfile_write (f, tmp2, _T("cd%d,%s"), ci->device_emu_unit, tmp); + } else if (ci->type == UAEDEV_TAPE) { + cfgfile_write (f, tmp2, _T("tape%d,%s"), ci->device_emu_unit, tmp); + } else { cfgfile_write(f, tmp2, _T("%s,%s"), ci->type == UAEDEV_HDF ? _T("hdf") : _T("dir"), tmp3); - if (ci->type == UAEDEV_DIR) - { + } + if (ci->type == UAEDEV_DIR) { bool add_extra = false; - if (ci->inject_icons) - { + if (ci->inject_icons) { add_extra = true; } - if (add_extra) - { + if (add_extra) { _stprintf(tmp2, _T("%s,inject_icons=%s"), ci->devname, ci->inject_icons ? _T("true") : _T("false")); cfgfile_write(f, _T("filesystem_extra"), tmp2); } @@ -932,7 +1203,6 @@ static void write_filesys_config(struct uae_prefs* p, const TCHAR* unexpanded, xfree(str1b); xfree(str1c); xfree(str2b); - xfree(str1); } } @@ -944,6 +1214,8 @@ static void write_compatibility_cpu(struct zfile* f, struct uae_prefs* p) model = p->cpu_model; if (model == 68030) model = 68020; + if (model == 68060) + model = 68040; if (p->address_space_24 && model == 68020) _tcscpy(tmp, _T("68ec020")); else @@ -953,14 +1225,170 @@ static void write_compatibility_cpu(struct zfile* f, struct uae_prefs* p) cfgfile_write(f, _T("cpu_type"), tmp); } +static void write_leds (struct zfile *f, const TCHAR *name, int mask) +{ + TCHAR tmp[MAX_DPATH]; + tmp[0] = 0; + for (int i = 0; leds[i]; i++) { + bool got = false; + for (int j = 0; leds[j]; j++) { + if (leds_order[j] == i) { + if (mask & (1 << j)) { + if (got) + _tcscat (tmp, _T(":")); + _tcscat (tmp, leds[j]); + got = true; + } + } + } + if (leds[i + 1] && got) + _tcscat (tmp, _T(",")); + } + while (tmp[0] && tmp[_tcslen (tmp) - 1] == ',') + tmp[_tcslen (tmp) - 1] = 0; + cfgfile_dwrite_str (f, name, tmp); +} + static void write_resolution(struct zfile* f, const TCHAR* ws, const TCHAR* hs, struct wh* wh) { cfgfile_write(f, ws, _T("%d"), wh->width); cfgfile_write(f, hs, _T("%d"), wh->height); } -static void cfgfile_write_board_rom(struct uae_prefs* prefs, struct zfile* f, const TCHAR* path, - struct boardromconfig* br) +#ifndef AMIBERRY +static int cfgfile_read_rom_settings(const struct expansionboardsettings *ebs, const TCHAR *buf, TCHAR *configtext) +{ + int settings = 0; + int bitcnt = 0; + int sstr = 0; + if (configtext) + configtext[0] = 0; + TCHAR *ct = configtext; + for (int i = 0; ebs[i].name; i++) { + const struct expansionboardsettings *eb = &ebs[i]; + bitcnt += eb->bitshift; + if (eb->type == EXPANSIONBOARD_STRING) { + TCHAR *p = cfgfile_option_get(buf, eb->configname); + if (p) { + _tcscpy(ct, p); + ct += _tcslen(ct); + xfree(p); + } + *ct++ = 0; + } else if (eb->type == EXPANSIONBOARD_MULTI) { + int itemcnt = -1; + int itemfound = 0; + const TCHAR *p = eb->configname; + while (p[0]) { + if (itemcnt >= 0) { + if (cfgfile_option_find(buf, p)) { + itemfound = itemcnt; + } + } + itemcnt++; + p += _tcslen(p) + 1; + } + int cnt = 1; + int bits = 1; + for (int i = 0; i < 8; i++) { + if ((1 << i) >= itemcnt) { + cnt = 1 << i; + bits = i; + break; + } + } + int multimask = cnt - 1; + if (eb->invert) + itemfound ^= 0x7fffffff; + itemfound &= multimask; + settings |= itemfound << bitcnt; + bitcnt += bits; + } else { + int mask = 1 << bitcnt; + if (cfgfile_option_find(buf, eb->configname)) { + settings |= mask; + } + if (eb->invert) + settings ^= mask; + bitcnt++; + } + } + return settings; +} + +static void cfgfile_write_rom_settings(const struct expansionboardsettings *ebs, TCHAR *buf, int settings, const TCHAR *settingstring) +{ + int bitcnt = 0; + int sstr = 0; + for (int j = 0; ebs[j].name; j++) { + const struct expansionboardsettings *eb = &ebs[j]; + bitcnt += eb->bitshift; + if (eb->type == EXPANSIONBOARD_STRING) { + if (settingstring) { + TCHAR tmp[MAX_DPATH]; + const TCHAR *p = settingstring; + for (int i = 0; i < sstr; i++) { + p += _tcslen(p) + 1; + } + if (buf[0]) + _tcscat(buf, _T(",")); + TCHAR *cs = cfgfile_escape_min(p); + _stprintf(tmp, _T("%s=%s"), eb->configname, cs); + _tcscat(buf, tmp); + xfree(cs); + sstr++; + } + } else if (eb->type == EXPANSIONBOARD_MULTI) { + int itemcnt = -1; + const TCHAR *p = eb->configname; + while (p[0]) { + itemcnt++; + p += _tcslen(p) + 1; + } + int cnt = 1; + int bits = 1; + for (int i = 0; i < 8; i++) { + if ((1 << i) >= itemcnt) { + cnt = 1 << i; + bits = i; + break; + } + } + int multimask = cnt - 1; + int multivalue = settings; + if (eb->invert) + multivalue ^= 0x7fffffff; + multivalue = (multivalue >> bitcnt) & multimask; + p = eb->configname; + while (multivalue >= 0) { + multivalue--; + p += _tcslen(p) + 1; + } + if (buf[0]) + _tcscat(buf, _T(",")); + _tcscat(buf, p); + bitcnt += bits; + } else { + int value = settings; + if (eb->invert) + value ^= 0x7fffffff; + if (value & (1 << bitcnt)) { + if (buf[0]) + _tcscat(buf, _T(",")); + _tcscat(buf, eb->configname); + } + bitcnt++; + } + } +} +#endif + +static bool is_custom_romboard(struct boardromconfig *br) +{ + return ((br->device_type & ROMTYPE_MASK) == ROMTYPE_UAEBOARDZ2 || (br->device_type & ROMTYPE_MASK) == ROMTYPE_UAEBOARDZ3); +} + +static void cfgfile_write_board_rom(struct uae_prefs *prefs, struct zfile *f, struct multipath *mp, struct boardromconfig *br) { TCHAR buf[MAX_DPATH]; TCHAR name[256]; @@ -971,29 +1399,41 @@ static void cfgfile_write_board_rom(struct uae_prefs* prefs, struct zfile* f, co ert = get_device_expansion_rom(br->device_type); if (!ert) return; - for (int i = 0; i < MAX_BOARD_ROMS; i++) - { + for (int i = 0; i < MAX_BOARD_ROMS; i++) { + struct romconfig *rc = &br->roms[i]; if (br->device_num == 0) _tcscpy(name, ert->name); else _stprintf(name, _T("%s-%d"), ert->name, br->device_num + 1); - if (i == 0 || _tcslen(br->roms[i].romfile)) - { + if (i == 0 || _tcslen(br->roms[i].romfile)) { _stprintf(buf, _T("%s%s_rom_file"), name, i ? _T("_ext") : _T("")); - cfgfile_write_rom(f, path, br->roms[i].romfile, buf); - if (br->roms[i].romident[0]) - { + cfgfile_write_rom (f, mp, br->roms[i].romfile, buf); + if (rc->romident[0]) { _stprintf(buf, _T("%s%s_rom"), name, i ? _T("_ext") : _T("")); - cfgfile_dwrite_str(f, buf, br->roms[i].romident); + cfgfile_dwrite_str (f, buf, rc->romident); } - if (br->roms[i].autoboot_disabled || br->device_order > 0) - { +#ifndef AMIBERRY + if (rc->autoboot_disabled || rc->inserted || ert->subtypes || ert->settings || ert->id_jumper || br->device_order > 0 || is_custom_romboard(br)) { TCHAR buf2[256], *p; buf2[0] = 0; p = buf2; _stprintf(buf, _T("%s%s_rom_options"), name, i ? _T("_ext") : _T("")); - if (br->roms[i].autoboot_disabled) - { + if (ert->subtypes) { + const struct expansionsubromtype *srt = ert->subtypes; + int k = rc->subtype; + while (k && srt[1].name) { + srt++; + k--; + } + _stprintf(p, _T("subtype=%s"), srt->configname); + } + if (br->device_order > 0 && prefs->autoconfig_custom_sort) { + if (buf2[0]) + _tcscat(buf2, _T(",")); + TCHAR *p2 = buf2 + _tcslen(buf2); + _stprintf(p2, _T("order=%d"), br->device_order); + } + if (rc->autoboot_disabled) { if (buf2[0]) _tcscat(buf2, _T(",")); _tcscat(buf2, _T("autoboot_disabled=true")); @@ -1001,29 +1441,79 @@ static void cfgfile_write_board_rom(struct uae_prefs* prefs, struct zfile* f, co if (buf2[0]) cfgfile_dwrite_str(f, buf, buf2); } - - if (br->roms[i].board_ram_size) - { +#endif + if (rc->board_ram_size) { _stprintf(buf, _T("%s%s_mem_size"), name, i ? _T("_ext") : _T("")); - cfgfile_write(f, buf, _T("%d"), br->roms[i].board_ram_size / 0x40000); + cfgfile_write(f, buf, _T("%d"), rc->board_ram_size / 0x40000); } } } } -static bool cfgfile_readramboard(const TCHAR* option, const TCHAR* value, const TCHAR* name, struct ramboard* rbp) +static bool cfgfile_readromboard(const TCHAR *option, const TCHAR *value, struct romboard *rbp) { TCHAR tmp1[MAX_DPATH]; int v; - for (int i = 0; i < MAX_RAM_BOARDS; i++) - { - struct ramboard* rb = &rbp[i]; + for (int i = 0; i < MAX_ROM_BOARDS; i++) { + struct romboard *rb = &rbp[i]; + if (i > 0) + _stprintf(tmp1, _T("romboard%d_options"), i + 1); + else + _tcscpy(tmp1, _T("romboard_options")); + if (!_tcsicmp(option, tmp1)) { + TCHAR *endptr; + TCHAR *s1, *s2; + s1 = cfgfile_option_get(value, _T("start")); + s2 = cfgfile_option_get(value, _T("end")); + rb->size = 0; + if (s1 && s2) { + rb->start_address = _tcstol(s1, &endptr, 16); + rb->end_address = _tcstol(s2, &endptr, 16); + if (rb->end_address && rb->end_address > rb->start_address) { + rb->size = (rb->end_address - rb->start_address + 65535) & ~65535; + } + } + xfree(s1); + xfree(s2); + s1 = cfgfile_option_get(value, _T("file")); + if (s1) { + TCHAR *p = cfgfile_unescape(s1, NULL); + _tcscpy(rb->lf.loadfile, p); + xfree(p); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("offset")); + if (s1) { + rb->lf.loadoffset = _tcstol(s1, &endptr, 16); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("fileoffset")); + if (s1) { + rb->lf.fileoffset = _tcstol(s1, &endptr, 16); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("filesize")); + if (s1) { + rb->lf.filesize = _tcstol(s1, &endptr, 16); + } + xfree(s1); + return true; + } + } + return false; +} + +static bool cfgfile_readramboard(const TCHAR *option, const TCHAR *value, const TCHAR *name, struct ramboard *rbp) +{ + TCHAR tmp1[MAX_DPATH]; + int v; + for (int i = 0; i < MAX_RAM_BOARDS; i++) { + struct ramboard *rb = &rbp[i]; if (i > 0) _stprintf(tmp1, _T("%s%d_size"), name, i + 1); else _stprintf(tmp1, _T("%s_size"), name); - if (!_tcsicmp(option, tmp1)) - { + if (!_tcsicmp(option, tmp1)) { v = 0; cfgfile_intval(option, value, tmp1, &v, 0x100000); rb->size = v; @@ -1033,19 +1523,125 @@ static bool cfgfile_readramboard(const TCHAR* option, const TCHAR* value, const _stprintf(tmp1, _T("%s%d_size_k"), name, i + 1); else _stprintf(tmp1, _T("%s_size_k"), name); - if (!_tcsicmp(option, tmp1)) - { + if (!_tcsicmp(option, tmp1)) { v = 0; cfgfile_intval(option, value, tmp1, &v, 1024); rb->size = v; return true; } + if (i > 0) + _stprintf(tmp1, _T("%s%d_options"), name, i + 1); + else + _stprintf(tmp1, _T("%s_options"), name); + if (!_tcsicmp(option, tmp1)) { + TCHAR *endptr; + TCHAR *s, *s1, *s2; + s = cfgfile_option_get(value, _T("order")); + if (s) + rb->device_order = _tstol(s); + xfree(s); + s = cfgfile_option_get(value, _T("mid")); + if (s) + rb->manufacturer = (uae_u16)_tstol(s); + xfree(s); + s = cfgfile_option_get(value, _T("pid")); + if (s) + rb->product = (uae_u8)_tstol(s); + xfree(s); + s = cfgfile_option_get(value, _T("no_reset_unmap")); + if (s) + rb->no_reset_unmap = true; + xfree(s); + s = cfgfile_option_get(value, _T("data")); + if (s && _tcslen(s) >= 3 * 16 - 1) { + rb->autoconfig_inuse = true; + for (int i = 0; i < sizeof rb->autoconfig; i++) { + TCHAR *s2 = &s[i * 3]; + if (i + 1 < sizeof rb->autoconfig && s2[2] != '.') + break; + TCHAR *endptr; + s[2] = 0; + rb->autoconfig[i] = (uae_u8)_tcstol(s2, &endptr, 16); + } + } + xfree(s); + s1 = cfgfile_option_get(value, _T("start")); + s2 = cfgfile_option_get(value, _T("end")); + if (s1 && s2) { + rb->start_address = _tcstol(s1, &endptr, 16); + rb->end_address = _tcstol(s2, &endptr, 16); + if (rb->start_address && rb->end_address > rb->start_address) { + rb->manual_config = true; + rb->autoconfig_inuse = false; + } + } + xfree(s1); + xfree(s2); + s1 = cfgfile_option_get(value, _T("write_address")); + if (s1) { + TCHAR *endptr; + rb->write_address = _tcstol(s1, &endptr, 16); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("file")); + if (s1) { + TCHAR *p = cfgfile_unescape(s1, NULL); + _tcscpy(rb->lf.loadfile, p); + xfree(p); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("offset")); + if (s1) { + rb->lf.loadoffset = _tcstol(s1, &endptr, 16); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("fileoffset")); + if (s1) { + rb->lf.fileoffset = _tcstol(s1, &endptr, 16); + } + xfree(s1); + s1 = cfgfile_option_get(value, _T("filesize")); + if (s1) { + rb->lf.filesize = _tcstol(s1, &endptr, 16); + } + xfree(s1); + rb->readonly = cfgfile_option_find(value, _T("read-only")); + return true; + } } return false; } -static void cfgfile_writeramboard(struct uae_prefs* prefs, struct zfile* f, const TCHAR* name, int num, - struct ramboard* rb) +static void cfgfile_writeromboard(struct uae_prefs *prefs, struct zfile *f, int num, struct romboard *rb) +{ + TCHAR tmp1[MAX_DPATH], tmp2[MAX_DPATH]; + if (!rb->end_address) + return; + if (num > 0) + _stprintf(tmp1, _T("romboard%d_options"), num + 1); + else + _tcscpy(tmp1, _T("romboard_options")); + tmp2[0] = 0; + TCHAR *p = tmp2; + _stprintf(p, _T("start=%08x,end=%08x"), rb->start_address, rb->end_address); + p += _tcslen(p); + if (rb->lf.loadfile[0]) { + _tcscat(p, _T(",")); + p += _tcslen(p); + TCHAR *path = cfgfile_escape(rb->lf.loadfile, NULL, true); + if (rb->lf.loadoffset || rb->lf.fileoffset || rb->lf.filesize) { + _stprintf(p, _T("offset=%u,fileoffset=%u,filesize=%u,"), rb->lf.loadoffset, rb->lf.fileoffset, rb->lf.filesize); + p += _tcslen(p); + } + _stprintf(p, _T("file=%s"), path); + xfree(path); + } + if (tmp2[0]) { + cfgfile_write(f, tmp1, tmp2); + } +} + +static void cfgfile_writeramboard(struct uae_prefs *prefs, struct zfile *f, const TCHAR *name, int num, struct ramboard *rb) { TCHAR tmp1[MAX_DPATH], tmp2[MAX_DPATH]; if (num > 0) @@ -1053,16 +1649,59 @@ static void cfgfile_writeramboard(struct uae_prefs* prefs, struct zfile* f, cons else _stprintf(tmp1, _T("%s_options"), name); tmp2[0] = 0; - TCHAR* p = tmp2; - if (rb->manufacturer) - { + TCHAR *p = tmp2; + if (rb->device_order > 0 && prefs->autoconfig_custom_sort) { + if (tmp2[0]) + *p++ = ','; + _stprintf(p, _T("order=%d"), rb->device_order); + p += _tcslen(p); + } + if (rb->manufacturer) { if (tmp2[0]) *p++ = ','; _stprintf(p, _T("mid=%u,pid=%u"), rb->manufacturer, rb->product); p += _tcslen(p); } - if (tmp2[0]) - { + if (rb->no_reset_unmap) { + if (tmp2[0]) + *p++ = ','; + _tcscpy(p, _T("no_reset_unmap=true")); + p += _tcslen(p); + } + if (rb->autoconfig_inuse) { + uae_u8 *ac = rb->autoconfig; + if (tmp2[0]) + *p++ = ','; + _stprintf(p, _T("data=%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x"), + ac[0], ac[1], ac[2], ac[3], ac[4], ac[5], ac[6], ac[7], + ac[8], ac[9], ac[10], ac[11], ac[12], ac[13], ac[14], ac[15]); + p += _tcslen(p); + } + if (rb->manual_config && rb->start_address && rb->end_address) { + if (tmp2[0]) + *p++ = ','; + _stprintf(p, _T("start=%08x,end=%08x"), rb->start_address, rb->end_address); + p += _tcslen(p); + } + if (rb->write_address) { + _stprintf(p, _T(",write_address=%08x"), rb->write_address); + p += _tcslen(p); + } + if (rb->lf.loadfile[0]) { + if (tmp2[0]) { + _tcscat(p, _T(",")); + p += _tcslen(p); + } + TCHAR *path = cfgfile_escape(rb->lf.loadfile, NULL, true); + _stprintf(p, _T("offset=%u,fileoffset=%u,filesize=%u,file=%s"), rb->lf.loadoffset, rb->lf.fileoffset, rb->lf.filesize, path); + xfree(path); + } + if (rb->readonly) { + if (tmp2[0]) + _tcscat(p, _T(",")); + _tcscat(p, _T("readonly")); + } + if (tmp2[0]) { cfgfile_write(f, tmp1, tmp2); } } @@ -1074,26 +1713,54 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) int i; cfgfile_write_str(f, _T("config_description"), p->description); + if (p->category[0]) + cfgfile_write_str(f, _T("config_category"), p->category); + if (p->tags[0]) + cfgfile_write_str(f, _T("config_tags"), p->tags); cfgfile_write_bool(f, _T("config_hardware"), type & CONFIG_TYPE_HARDWARE); cfgfile_write_bool(f, _T("config_host"), !!(type & CONFIG_TYPE_HOST)); if (p->info[0]) cfgfile_write(f, _T("config_info"), p->info); cfgfile_write(f, _T("config_version"), _T("%d.%d.%d"), UAEMAJOR, UAEMINOR, UAESUBREV); + cfgfile_write_str (f, _T("config_hardware_path"), p->config_hardware_path); + cfgfile_write_str (f, _T("config_host_path"), p->config_host_path); + cfgfile_write_str (f, _T("config_all_path"), p->config_all_path); + if (p->config_window_title[0]) + cfgfile_write_str (f, _T("config_window_title"), p->config_window_title); - for (sl = p->all_lines; sl; sl = sl->next) - if (sl->unknown) + for (sl = p->all_lines; sl; sl = sl->next) { + if (sl->unknown) { if (sl->option) cfgfile_write_str(f, sl->option, sl->value); + } + } - _stprintf(tmp, _T("%s.rom_path"), TARGET_NAME); - cfgfile_write_str(f, tmp, p->path_rom); - _stprintf(tmp, _T("%s.floppy_path"), TARGET_NAME); - cfgfile_write_str(f, tmp, p->path_floppy); - _stprintf(tmp, _T("%s.hardfile_path"), TARGET_NAME); - cfgfile_write_str(f, tmp, p->path_hardfile); - _stprintf(tmp, _T("%s.cd_path"), TARGET_NAME); - cfgfile_write_str(f, tmp, p->path_cd); - + for (i = 0; i < MAX_PATHS; i++) { + if (p->path_rom.path[i][0]) { + _stprintf (tmp, _T("%s.rom_path"), TARGET_NAME); + cfgfile_write_str (f, tmp, p->path_rom.path[i]); + } + } + for (i = 0; i < MAX_PATHS; i++) { + if (p->path_floppy.path[i][0]) { + _stprintf (tmp, _T("%s.floppy_path"), TARGET_NAME); + cfgfile_write_str (f, tmp, p->path_floppy.path[i]); + } + } + for (i = 0; i < MAX_PATHS; i++) { + if (p->path_hardfile.path[i][0]) { + _stprintf (tmp, _T("%s.hardfile_path"), TARGET_NAME); + cfgfile_write_str (f, tmp, p->path_hardfile.path[i]); + } + } + for (i = 0; i < MAX_PATHS; i++) { + if (p->path_cd.path[i][0]) { + _stprintf (tmp, _T("%s.cd_path"), TARGET_NAME); + cfgfile_write_str (f, tmp, p->path_cd.path[i]); + } + } + +#ifdef AMIBERRY cfg_write(_T("; "), f); cfg_write(_T("; *** Controller/Input Configuration"), f); cfg_write(_T("; "), f); @@ -1281,7 +1948,8 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfg_write(_T("; "), f); } - +#endif + cfgfile_dwrite_str(f, _T("absolute_mouse"), abspointers[p->input_tablet]); write_inputdevice_config(p, f); @@ -1315,8 +1983,8 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfgfile_write_str(f, _T("use_gui"), guimode1[p->start_gui]); cfgfile_dwrite_bool(f, _T("show_leds"), p->leds_on_screen); - cfgfile_write_rom(f, p->path_rom, p->romfile, _T("kickstart_rom_file")); - cfgfile_write_rom(f, p->path_rom, p->romextfile, _T("kickstart_ext_rom_file")); + cfgfile_write_rom(f, &p->path_rom, p->romfile, _T("kickstart_rom_file")); + cfgfile_write_rom(f, &p->path_rom, p->romextfile, _T("kickstart_ext_rom_file")); if (p->romident[0]) cfgfile_dwrite_str(f, _T("kickstart_rom"), p->romident); if (p->romextident[0]) @@ -1324,7 +1992,7 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) for (int i = 0; i < MAX_EXPANSION_BOARDS; i++) { - cfgfile_write_board_rom(p, f, p->path_rom, &p->expansionboard[i]); + cfgfile_write_board_rom(p, f, &p->path_rom, &p->expansionboard[i]); } cfgfile_write_str(f, _T("flash_file"), p->flashfile); @@ -1340,12 +2008,12 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) for (i = 0; i < 4; i++) { _stprintf(tmp, _T("floppy%d"), i); - cfgfile_write_path(f, p->path_floppy, tmp, p->floppyslots[i].df); - _stprintf(tmp, _T("floppy%dwp"), i); - cfgfile_dwrite_bool(f, tmp, p->floppyslots[i].forcedwriteprotect); - _stprintf(tmp, _T("floppy%dtype"), i); - cfgfile_dwrite(f, tmp, _T("%d"), p->floppyslots[i].dfxtype); - if (p->floppyslots[i].dfxtype < 0 && p->nr_floppies > i) + cfgfile_write_path2(f, tmp, p->floppyslots[i].df, PATH_FLOPPY); + _stprintf (tmp, _T("floppy%dwp"), i); + cfgfile_dwrite_bool (f, tmp, p->floppyslots[i].forcedwriteprotect); + _stprintf (tmp, _T("floppy%dtype"), i); + cfgfile_dwrite (f, tmp, _T("%d"), p->floppyslots[i].dfxtype); + if (p->floppyslots[i].dfxtype < 0 && p->nr_floppies > i) p->nr_floppies = i; } @@ -1355,20 +2023,15 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) { TCHAR tmp2[MAX_DPATH]; _stprintf(tmp, _T("cdimage%d"), i); - TCHAR* s = cfgfile_subst_path(p->path_cd, UNEXPANDED, p->cdslots[i].name); - _tcscpy(tmp2, s); - xfree(s); - if (p->cdslots[i].type != SCSI_UNIT_DEFAULT || _tcschr(p->cdslots[i].name, ',') || p->cdslots[i].delayed) - { - _tcscat(tmp2, _T(",")); - if (p->cdslots[i].delayed) - { - _tcscat(tmp2, _T("delay")); - _tcscat(tmp2, _T(":")); + cfgfile_to_path_save(p->cdslots[i].name, tmp2, PATH_CD); + if (p->cdslots[i].type != SCSI_UNIT_DEFAULT || _tcschr (p->cdslots[i].name, ',') || p->cdslots[i].delayed) { + _tcscat (tmp2, _T(",")); + if (p->cdslots[i].delayed) { + _tcscat (tmp2, _T("delay")); + _tcscat (tmp2, _T(":")); } - if (p->cdslots[i].type != SCSI_UNIT_DEFAULT) - { - _tcscat(tmp2, cdmodes[p->cdslots[i].type + 1]); + if (p->cdslots[i].type != SCSI_UNIT_DEFAULT) { + _tcscat (tmp2, cdmodes[p->cdslots[i].type + 1]); } } cfgfile_write_str(f, tmp, tmp2); @@ -1384,7 +2047,7 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfg_write(_T("; "), f); #ifdef FILESYS - write_filesys_config(p, UNEXPANDED, p->path_hardfile, f); + write_filesys_config (p, f); cfgfile_dwrite(f, _T("filesys_max_size"), _T("%d"), p->filesys_limit); cfgfile_dwrite(f, _T("filesys_max_name_length"), _T("%d"), p->filesys_max_name); cfgfile_dwrite_bool(f, _T("filesys_inject_icons"), p->filesys_inject_icons); @@ -1410,7 +2073,9 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfg_write(_T("; "), f); cfgfile_write(f, _T("gfx_framerate"), _T("%d"), p->gfx_framerate); - write_resolution(f, _T("gfx_width"), _T("gfx_height"), &p->gfx_size); /* compatibility with old versions */ + write_resolution (f, _T("gfx_width"), _T("gfx_height"), &p->gfx_monitor.gfx_size); /* compatibility with old versions */ + cfgfile_write (f, _T("gfx_top_windowed"), _T("%d"), p->gfx_monitor.gfx_size.y); + cfgfile_write(f, _T("gfx_left_windowed"), _T("%d"), p->gfx_monitor.gfx_size.x); cfgfile_write(f, _T("gfx_refreshrate"), _T("%d"), p->gfx_apmode[0].gfx_refreshrate); cfgfile_dwrite(f, _T("gfx_refreshrate_rtg"), _T("%d"), p->gfx_apmode[1].gfx_refreshrate); @@ -1532,7 +2197,6 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfgfile_write(f, _T("addmem2"), _T("0x%x,0x%x"), p->custom_memory_addrs[1], p->custom_memory_sizes[1]); } - cfg_write(_T("; "), f); cfg_write(_T("; *** Chipset"), f); cfg_write(_T("; "), f); @@ -1570,10 +2234,12 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) s += _stprintf(s, _T(",v=%d"), cr->vert); if (cr->locked) _tcscat(s, _T(",locked")); - if (cr->ntsc > 0) + if (cr->ntsc == 1) _tcscat(s, _T(",ntsc")); else if (cr->ntsc == 0) _tcscat(s, _T(",pal")); + else if (cr->ntsc == 2) + _tcscat(s, _T(",custom")); if (cr->lace > 0) _tcscat(s, _T(",lace")); else if (cr->lace == 0) @@ -1628,7 +2294,6 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfgfile_dwrite_str(f, _T("waiting_blits"), waitblits[p->waiting_blits]); cfgfile_write_bool(f, _T("fast_copper"), p->fast_copper); - cfg_write(_T("; "), f); cfg_write(_T("; *** Sound Options"), f); cfg_write(_T("; "), f); @@ -1645,7 +2310,6 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) if (p->sound_volume_cd >= 0) cfgfile_write(f, _T("sound_volume_cd"), _T("%d"), p->sound_volume_cd); - cfg_write(_T("; "), f); cfg_write(_T("; *** Misc. Options"), f); cfg_write(_T("; "), f); @@ -1655,6 +2319,21 @@ void cfgfile_save_options(struct zfile* f, struct uae_prefs* p, int type) cfgfile_dwrite_str(f, _T("uaeboard"), uaeboard[p->uaeboard]); } +static int cfgfile_coords(const TCHAR *option, const TCHAR *value, const TCHAR *name, int *x, int *y) +{ + if (name != NULL && _tcscmp (option, name) != 0) + return 0; + TCHAR tmp[MAX_DPATH]; + _tcscpy(tmp, value); + TCHAR *p = _tcschr(tmp, ','); + if (!p) + return 0; + *p++ = 0; + *x = _tstol(tmp); + *y = _tstol(p); + return 1; +} + static int cfgfile_yesno(const TCHAR* option, const TCHAR* value, const TCHAR* name, int* location, bool numbercheck) { if (name != nullptr && _tcscmp(option, name) != 0) @@ -1707,8 +2386,7 @@ static int cfgfile_doubleval(const TCHAR* option, const TCHAR* value, const TCHA return 1; } -static int cfgfile_floatval(const TCHAR* option, const TCHAR* value, const TCHAR* name, const TCHAR* nameext, - float* location) +static int cfgfile_floatval (const TCHAR *option, const TCHAR *value, const TCHAR *name, const TCHAR *nameext, float *location) { TCHAR* endptr; if (name == nullptr) @@ -1735,8 +2413,7 @@ static int cfgfile_floatval(const TCHAR* option, const TCHAR* value, const TCHAR return cfgfile_floatval(option, value, name, nullptr, location); } -static int cfgfile_intval(const TCHAR* option, const TCHAR* value, const TCHAR* name, const TCHAR* nameext, - unsigned int* location, int scale) +static int cfgfile_intval (const TCHAR *option, const TCHAR *value, const TCHAR *name, const TCHAR *nameext, unsigned int *location, int scale) { int base = 10; TCHAR* endptr; @@ -1793,9 +2470,7 @@ int cfgfile_intval(const TCHAR* option, const TCHAR* value, const TCHAR* name, i *location = (int)v; return r; } - -static int cfgfile_intval(const TCHAR* option, const TCHAR* value, const TCHAR* name, const TCHAR* nameext, - int* location, int scale) +static int cfgfile_intval (const TCHAR *option, const TCHAR *value, const TCHAR *name, const TCHAR *nameext, int *location, int scale) { unsigned int v = 0; int r = cfgfile_intval(option, value, name, nameext, &v, scale); @@ -1805,8 +2480,7 @@ static int cfgfile_intval(const TCHAR* option, const TCHAR* value, const TCHAR* return r; } -static int cfgfile_strval(const TCHAR* option, const TCHAR* value, const TCHAR* name, const TCHAR* nameext, - int* location, const TCHAR* table[], int more) +static int cfgfile_strval (const TCHAR *option, const TCHAR *value, const TCHAR *name, const TCHAR *nameext, int *location, const TCHAR *table[], int more) { int val; TCHAR tmp[MAX_DPATH]; @@ -1846,15 +2520,12 @@ static int cfgfile_strval(const TCHAR* option, const TCHAR* value, const TCHAR* *location = val; return 1; } - -int cfgfile_strval(const TCHAR* option, const TCHAR* value, const TCHAR* name, int* location, const TCHAR* table[], - int more) +int cfgfile_strval (const TCHAR *option, const TCHAR *value, const TCHAR *name, int *location, const TCHAR *table[], int more) { return cfgfile_strval(option, value, name, nullptr, location, table, more); } -static int cfgfile_strboolval(const TCHAR* option, const TCHAR* value, const TCHAR* name, bool* location, - const TCHAR* table[], int more) +static int cfgfile_strboolval (const TCHAR *option, const TCHAR *value, const TCHAR *name, bool *location, const TCHAR *table[], int more) { int locationint; if (!cfgfile_strval(option, value, name, &locationint, table, more)) @@ -1872,8 +2543,7 @@ int cfgfile_string(const TCHAR* option, const TCHAR* value, const TCHAR* name, T return 1; } -static int cfgfile_string(const TCHAR* option, const TCHAR* value, const TCHAR* name, const TCHAR* nameext, - TCHAR* location, int maxsz) +static int cfgfile_string (const TCHAR *option, const TCHAR *value, const TCHAR *name, const TCHAR *nameext, TCHAR *location, int maxsz) { if (nameext) { @@ -1893,14 +2563,49 @@ static int cfgfile_string(const TCHAR* option, const TCHAR* value, const TCHAR* return 1; } -static int cfgfile_path(const TCHAR* option, const TCHAR* value, const TCHAR* name, TCHAR* location, int maxsz) +static bool cfgfile_multichoice(const TCHAR *option, const TCHAR *value, const TCHAR *name, int *location, const TCHAR *table[]) +{ + if (_tcscmp(option, name) != 0) + return false; + int v = 0; + for (int i = 0; table[i]; i++) { + if (cfgfile_option_find(value, table[i])) { + v |= 1 << i; + } + } + *location = v; + return true; +} + +static int cfgfile_path (const TCHAR *option, const TCHAR *value, const TCHAR *name, TCHAR *location, int maxsz, struct multipath *mp) { if (!cfgfile_string(option, value, name, location, maxsz)) return 0; - TCHAR* s = target_expand_environment(location, nullptr, 0); - _tcsncpy(location, s, maxsz - 1); - location[maxsz - 1] = 0; - xfree (s); + cfgfile_adjust_path(location, maxsz, mp); + return 1; +} + +static int cfgfile_path (const TCHAR *option, const TCHAR *value, const TCHAR *name, TCHAR *location, int maxsz) +{ + return cfgfile_path (option, value, name, location, maxsz, NULL); +} + +static int cfgfile_multipath (const TCHAR *option, const TCHAR *value, const TCHAR *name, struct multipath *mp, struct uae_prefs *p) +{ + TCHAR tmploc[MAX_DPATH]; + if (!cfgfile_string (option, value, name, tmploc, MAX_DPATH)) + return 0; + for (int i = 0; i < MAX_PATHS; i++) { + if (mp->path[i][0] == 0 || (i == 0 && (!_tcscmp (mp->path[i], _T(".\\")) || !_tcscmp (mp->path[i], _T("./"))))) { + TCHAR *s = target_expand_environment (tmploc, NULL, 0); + _tcsncpy (mp->path[i], s, PATH_MAX - 1); + mp->path[i][PATH_MAX - 1] = 0; + fixtrailing (mp->path[i]); + xfree (s); + //target_multipath_modified(p); + return 1; + } + } return 1; } @@ -2079,17 +2784,13 @@ static int cfgfile_option_bool(TCHAR* s, const TCHAR* option) } } -static void set_chipset_mask(struct uae_prefs* p, int val) +static void set_chipset_mask (struct uae_prefs *p, int val) { - p->chipset_mask = (val == 0 - ? 0 - : val == 1 - ? CSMASK_ECS_AGNUS - : val == 2 - ? CSMASK_ECS_DENISE - : val == 3 - ? CSMASK_ECS_DENISE | CSMASK_ECS_AGNUS - : CSMASK_AGA | CSMASK_ECS_DENISE | CSMASK_ECS_AGNUS); + p->chipset_mask = (val == 0 ? 0 + : val == 1 ? CSMASK_ECS_AGNUS + : val == 2 ? CSMASK_ECS_DENISE + : val == 3 ? CSMASK_ECS_DENISE | CSMASK_ECS_AGNUS + : CSMASK_AGA | CSMASK_ECS_DENISE | CSMASK_ECS_AGNUS); } static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) @@ -2108,6 +2809,7 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) return 1; } +#ifdef AMIBERRY // custom options LOADING for (int i = 0; i < 4; ++i) // Loop 1 ... all 4 joyports { @@ -2166,6 +2868,7 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) } // close loop 3 } // close loop 2 } // close loop 1 +#endif for (tmpp = option; *tmpp != '\0'; tmpp++) if (_istupper(*tmpp)) @@ -2179,10 +2882,10 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) if (_tcscmp(section, TARGET_NAME) == 0) { /* We special case the various path options here. */ - if (cfgfile_path(option, value, _T("rom_path"), p->path_rom, sizeof p->path_rom / sizeof(TCHAR)) - || cfgfile_path(option, value, _T("floppy_path"), p->path_floppy, sizeof p->path_floppy / sizeof(TCHAR)) - || cfgfile_path(option, value, _T("cd_path"), p->path_cd, sizeof p->path_cd / sizeof(TCHAR)) - || cfgfile_path(option, value, _T("hardfile_path"), p->path_hardfile, sizeof p->path_hardfile / sizeof(TCHAR))) + if (cfgfile_multipath (option, value, _T("rom_path"), &p->path_rom, p) + || cfgfile_multipath (option, value, _T("floppy_path"), &p->path_floppy, p) + || cfgfile_multipath (option, value, _T("cd_path"), &p->path_cd, p) + || cfgfile_multipath (option, value, _T("hardfile_path"), &p->path_hardfile, p)) return 1; return target_parse_option(p, option, value); } @@ -2248,11 +2951,12 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) *next2++ = 0; cfgfile_intval(option, next, tmp, &unitnum, 1); } - if (_tcslen(value) > 0) - { - TCHAR* s = cfgfile_subst_path(UNEXPANDED, p->path_cd, value); - _tcsncpy(p->cdslots[i].name, s, sizeof p->cdslots[i].name / sizeof(TCHAR)); - xfree(s); + if (value[0] == 0 || !_tcsicmp(value, _T("empty")) || !_tcscmp(value, _T("."))) { + value[0] = 0; + p->cdslots[i].name[0] = 0; + } + if (_tcslen (value) > 0) { + _tcsncpy (p->cdslots[i].name, value, sizeof p->cdslots[i].name / sizeof (TCHAR)); } p->cdslots[i].name[sizeof p->cdslots[i].name - 1] = 0; p->cdslots[i].inuse = true; @@ -2276,6 +2980,8 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) || cfgfile_intval(option, value, _T("sound_stereo_mixing_delay"), &p->sound_mixed_stereo_delay, 1) || cfgfile_intval(option, value, _T("gfx_framerate"), &p->gfx_framerate, 1) + || cfgfile_intval(option, value, _T("gfx_top_windowed"), &p->gfx_monitor.gfx_size.y, 1) + || cfgfile_intval(option, value, _T("gfx_left_windowed"), &p->gfx_monitor.gfx_size.x, 1) || cfgfile_intval(option, value, _T("gfx_refreshrate"), &p->gfx_apmode[APMODE_NATIVE].gfx_refreshrate, 1) || cfgfile_intval(option, value, _T("gfx_refreshrate_rtg"), &p->gfx_apmode[APMODE_RTG].gfx_refreshrate, 1) @@ -2362,8 +3068,8 @@ static int cfgfile_parse_host(struct uae_prefs* p, TCHAR* option, TCHAR* value) if (_tcscmp(option, _T("gfx_width")) == 0 || _tcscmp(option, _T("gfx_height")) == 0) { - cfgfile_intval(option, value, _T("gfx_width"), &p->gfx_size.width, 1); - cfgfile_intval(option, value, _T("gfx_height"), &p->gfx_size.height, 1); + cfgfile_intval (option, value, _T("gfx_width"), &p->gfx_monitor.gfx_size.width, 1); + cfgfile_intval (option, value, _T("gfx_height"), &p->gfx_monitor.gfx_size.height, 1); return 1; } @@ -3243,8 +3949,6 @@ empty_fs: memmove(uci.rootdir, uci.rootdir + 2, (_tcslen(uci.rootdir + 2) + 1) * sizeof (TCHAR)); uci.rootdir[0] = ':'; } - str = cfgfile_subst_path(UNEXPANDED, p->path_hardfile, uci.rootdir); - _tcscpy(uci.rootdir, str); } #ifdef FILESYS add_filesys_config(p, nr, &uci); @@ -3389,7 +4093,7 @@ static int cfgfile_parse_filesys(struct uae_prefs* p, const TCHAR* option, TCHAR goto invalid_fs; _tcscpy(uci.rootdir, value); } - str = cfgfile_subst_path(UNEXPANDED, p->path_hardfile, uci.rootdir); + str = cfgfile_subst_path_load (UNEXPANDED, &p->path_hardfile, uci.rootdir, true); #ifdef FILESYS uci.type = hdf ? UAEDEV_HDF : UAEDEV_DIR; add_filesys_config(p, -1, &uci); @@ -3453,7 +4157,7 @@ static int cfgfile_parse_filesys(struct uae_prefs* p, const TCHAR* option, TCHAR return 0; } -static bool cfgfile_read_board_rom(struct uae_prefs* p, const TCHAR* option, const TCHAR* value) +static bool cfgfile_read_board_rom(struct uae_prefs *p, const TCHAR *option, const TCHAR *value, struct multipath *mp) { TCHAR buf[256], buf2[MAX_DPATH], buf3[MAX_DPATH]; bool dummy; @@ -3482,7 +4186,7 @@ static bool cfgfile_read_board_rom(struct uae_prefs* p, const TCHAR* option, con } _stprintf(buf, _T("%s_rom_file"), name); - if (cfgfile_path(option, value, buf, buf2, MAX_DPATH / sizeof (TCHAR))) + if (cfgfile_path(option, value, buf, buf2, MAX_DPATH / sizeof (TCHAR), mp)) { if (buf2[0]) { @@ -3655,11 +4359,13 @@ static int cfgfile_parse_hardware(struct uae_prefs* p, const TCHAR* option, TCHA return 1; } - if (cfgfile_path(option, value, _T("kickstart_rom_file"), p->romfile, sizeof p->romfile / sizeof (TCHAR)) - || cfgfile_path(option, value, _T("kickstart_ext_rom_file"), p->romextfile, sizeof p->romextfile / sizeof (TCHAR)) - || cfgfile_path(option, value, _T("flash_file"), p->flashfile, sizeof p->flashfile / sizeof (TCHAR)) - || cfgfile_path(option, value, _T("cart_file"), p->cartfile, sizeof p->cartfile / sizeof (TCHAR))) - return 1; + if (cfgfile_path (option, value, _T("kickstart_rom_file"), p->romfile, sizeof p->romfile / sizeof (TCHAR), &p->path_rom) + || cfgfile_path (option, value, _T("kickstart_ext_rom_file"), p->romextfile, sizeof p->romextfile / sizeof (TCHAR), &p->path_rom) + || cfgfile_rom(option, value, _T("kickstart_rom_file_id"), p->romfile, sizeof p->romfile / sizeof(TCHAR)) + || cfgfile_rom (option, value, _T("kickstart_ext_rom_file_id"), p->romextfile, sizeof p->romextfile / sizeof (TCHAR)) + || cfgfile_string (option, value, _T("flash_file"), p->flashfile, sizeof p->flashfile / sizeof (TCHAR)) + || cfgfile_path (option, value, _T("cart_file"), p->cartfile, sizeof p->cartfile / sizeof (TCHAR), &p->path_rom)) + return 1; if (cfgfile_string(option, value, _T("uaeboard_options"), tmpbuf, sizeof tmpbuf / sizeof(TCHAR))) { @@ -3781,15 +4487,17 @@ static int cfgfile_parse_hardware(struct uae_prefs* p, const TCHAR* option, TCHA return 1; } - if (cfgfile_read_board_rom(p, option, value)) + if (cfgfile_read_board_rom(p, option, value, &p->path_rom)) return 1; - for (i = 0; i < 4; i++) - { - _stprintf(tmpbuf, _T("floppy%d"), i); - if (cfgfile_path(option, value, tmpbuf, p->floppyslots[i].df, sizeof p->floppyslots[i].df / sizeof (TCHAR))) - return 1; - } + for (i = 0; i < 4; i++) { + _stprintf (tmpbuf, _T("floppy%d"), i); + if (cfgfile_string(option, value, tmpbuf, p->floppyslots[i].df, sizeof p->floppyslots[i].df / sizeof(TCHAR))) { + if (!_tcscmp(p->floppyslots[i].df, _T("."))) + p->floppyslots[i].df[0] = 0; + return 1; + } + } if (cfgfile_intval(option, value, _T("chipmem_size"), &dummyint, 1)) { @@ -4006,7 +4714,7 @@ void cfgfile_compatibility_romtype(struct uae_prefs* p) addbcromtype(p, ROMTYPE_CD32CART, p->cs_cd32fmv, p->cartfile, 0); } -static bool createconfigstore(struct uae_prefs*); + static int getconfigstoreline(const TCHAR* option, TCHAR* value); static void calcformula(struct uae_prefs* prefs, TCHAR* in) @@ -4020,7 +4728,7 @@ static void calcformula(struct uae_prefs* prefs, TCHAR* in) if (_tcslen(in) < 2 || in[0] != '[' || in[_tcslen(in) - 1] != ']') return; if (!configstore || updatestore) - createconfigstore(prefs); + cfgfile_createconfigstore(prefs); updatestore = false; if (!configstore) return; @@ -4301,19 +5009,20 @@ static int getconfigstoreline(const TCHAR* option, TCHAR* value) } } -static bool createconfigstore(struct uae_prefs* p) +bool cfgfile_createconfigstore (struct uae_prefs *p) { - uae_u8 zeros[4] = {0}; - zfile_fclose(configstore); - configstore = zfile_fopen_empty(nullptr, _T("configstore"), 50000); + uae_u8 zeros[4] = { 0 }; + zfile_fclose (configstore); + configstore = zfile_fopen_empty (NULL, _T("configstore"), 50000); if (!configstore) return false; - zfile_fseek(configstore, 0, SEEK_SET); + zfile_fseek (configstore, 0, SEEK_SET); uaeconfig++; - cfgfile_save_options(configstore, p, 0); + cfgfile_save_options (configstore, p, 0); uaeconfig--; - zfile_fwrite(zeros, 1, sizeof zeros, configstore); - zfile_fseek(configstore, 0, SEEK_SET); + zfile_fwrite (zeros, 1, sizeof zeros, configstore); + zfile_truncate(configstore, zfile_ftell(configstore)); + zfile_fseek (configstore, 0, SEEK_SET); return true; } @@ -4403,20 +5112,19 @@ static int cfgfile_load_2(struct uae_prefs* p, const TCHAR* filename, bool real, cfgfile_parse_line(p, line, 0); } - for (i = 0; i < 4; i++) - { - subst(p->path_floppy, p->floppyslots[i].df, sizeof p->floppyslots[i].df / sizeof (TCHAR)); - if (i >= p->nr_floppies) - p->floppyslots[i].dfxtype = DRV_NONE; + for (i = 0; i < 4; i++) { + subst (p->path_floppy.path[0], p->floppyslots[i].df, sizeof p->floppyslots[i].df / sizeof (TCHAR)); + if(i >= p->nr_floppies) + p->floppyslots[i].dfxtype = DRV_NONE; } - subst(p->path_rom, p->romfile, sizeof p->romfile / sizeof (TCHAR)); - subst(p->path_rom, p->romextfile, sizeof p->romextfile / sizeof (TCHAR)); + subst (p->path_rom.path[0], p->romfile, sizeof p->romfile / sizeof (TCHAR)); + subst (p->path_rom.path[0], p->romextfile, sizeof p->romextfile / sizeof (TCHAR)); for (i = 0; i < MAX_EXPANSION_BOARDS; i++) { for (int j = 0; j < MAX_BOARD_ROMS; j++) { - subst(p->path_rom, p->expansionboard[i].roms[j].romfile, MAX_DPATH / sizeof(TCHAR)); + subst(p->path_rom.path[0], p->expansionboard[i].roms[j].romfile, MAX_DPATH / sizeof(TCHAR)); } } @@ -4461,28 +5169,40 @@ int cfgfile_save(struct uae_prefs* p, const TCHAR* filename, int type) return 1; } -int cfgfile_get_description(const TCHAR* filename, TCHAR* description) +struct uae_prefs *cfgfile_open(const TCHAR *filename, int *type) { - int result = 0; - struct uae_prefs* p = xmalloc (struct uae_prefs, 1); - - p->description[0] = 0; - if (cfgfile_load_2(p, filename, false, nullptr)) - { - result = 1; - if (description) - _tcscpy(description, p->description); - } - xfree (p); - return result; + struct uae_prefs *p = xcalloc(struct uae_prefs, 1); + if (cfgfile_load_2(p, filename, false, type)) + return p; + xfree(p); + return NULL; } -int cfgfile_configuration_change(int v) +void cfgfile_close(struct uae_prefs *p) { - static int mode; - if (v >= 0) - mode = v; - return mode; + xfree(p); +} + +int cfgfile_get_description (struct uae_prefs *p, const TCHAR *filename, TCHAR *description, int *type) +{ + bool alloc = false; + + if (!p) { + p = xmalloc(struct uae_prefs, 1); + alloc = true; + } + if (!p) { + alloc = true; + p = cfgfile_open(filename, type); + } + if (!p) + return 0; + if (description) + _tcscpy (description, p->description); + if (alloc) { + cfgfile_close(p); + } + return 1; } static void parse_sound_spec(struct uae_prefs* p, const TCHAR* spec) @@ -4715,6 +5435,8 @@ int parse_cmdline_option(struct uae_prefs* p, TCHAR c, const TCHAR* arg) switch (c) { + case 'h': usage (); exit (0); + case '0': cmdpath(p->floppyslots[0].df, arg, 255); break; case '1': cmdpath(p->floppyslots[1].df, arg, 255); @@ -4919,7 +5641,7 @@ int cfgfile_searchconfig(const TCHAR *in, int index, TCHAR *out, int outsize) *out = 0; if (!configstore) - createconfigstore(&currprefs); + cfgfile_createconfigstore(&currprefs); if (!configstore) return 20; @@ -5033,7 +5755,7 @@ uae_u32 cfgfile_modify(uae_u32 index, const TCHAR* parms, uae_u32 size, TCHAR* o if (argv <= 1 && index == 0xffffffff) { - createconfigstore(&currprefs); + cfgfile_createconfigstore(&currprefs); xfree (configsearch); configsearch = nullptr; if (!configstore) @@ -5384,8 +6106,8 @@ void default_prefs(struct uae_prefs* p, bool reset, int type) p->gfx_framerate = 0; p->gfx_autoframerate = 50; - p->gfx_size.width = 640; //TODO: Default WinUAE prefs indicate this should be 720x568 - p->gfx_size.height = 256; + p->gfx_monitor.gfx_size.width = 640; //TODO: Default WinUAE prefs indicate this should be 720x568 + p->gfx_monitor.gfx_size.height = 256; p->gfx_resolution = RES_HIRES; p->gfx_vresolution = VRES_NONDOUBLE; p->gfx_iscanlines = 0; @@ -5475,10 +6197,10 @@ void default_prefs(struct uae_prefs* p, bool reset, int type) _tcscpy(p->cartfile, _T("")); _tcscpy (p->rtcfile, _T("")); - sprintf(p->path_rom, _T("%s/kickstarts/"), start_path_data); - sprintf(p->path_floppy, _T("%s/disks/"), start_path_data); - sprintf(p->path_hardfile, _T("%s/"), start_path_data); - sprintf(p->path_cd, _T("%s/cd32/"), start_path_data); + sprintf (p->path_rom.path[0], _T("%s/kickstarts/"), start_path_data); + sprintf (p->path_floppy.path[0], _T("%s/disks/"), start_path_data); + sprintf (p->path_hardfile.path[0], _T("%s/"), start_path_data); + sprintf (p->path_cd.path[0], _T("%s/cd32/"), start_path_data); p->prtname[0] = 0; p->sername[0] = 0; diff --git a/src/cia.cpp b/src/cia.cpp index 17c76918..828354c9 100644 --- a/src/cia.cpp +++ b/src/cia.cpp @@ -1,17 +1,15 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * CIA chip support - * - * Copyright 1995 Bernd Schmidt, Alessandro Bissacco - * Copyright 1996, 1997 Stefan Reinauer, Christian Schmitt - */ -#include -#include -#include +/* +* UAE - The Un*x Amiga Emulator +* +* CIA chip support +* +* Copyright 1995 Bernd Schmidt, Alessandro Bissacco +* Copyright 1996, 1997 Stefan Reinauer, Christian Schmitt +*/ + +#include "sysconfig.h" #include "sysdeps.h" - #include "options.h" #include "memory.h" #include "custom.h" @@ -21,11 +19,12 @@ #include "gui.h" #include "savestate.h" #include "inputdevice.h" -#include "include/ar.h" +#include "ar.h" #include "akiko.h" #include "audio.h" #include "keyboard.h" #include "rtc.h" +#include "uae.h" /* Akiko internal CIA differences: @@ -34,8 +33,8 @@ */ /* e-clock is 10 CPU cycles, 4 cycles high, 6 low - * data transfer happens during 4 high cycles - */ +* data transfer happens during 4 high cycles +*/ #define ECLOCK_DATA_CYCLE 4 #define ECLOCK_WAIT_CYCLE 6 @@ -74,28 +73,30 @@ static struct rtc_ricoh_data rtc_ricoh; STATIC_INLINE void setclr (unsigned int *p, unsigned int val) { - if (val & 0x80) { - *p |= val & 0x7F; - } else { - *p &= ~val; - } + if (val & 0x80) { + *p |= val & 0x7F; + } else { + *p &= ~val; + } } STATIC_INLINE void ICR (uae_u32 data) { - INTREQ_0 (0x8000 | data); + safe_interrupt_set((data & 0x2000) != 0); } -STATIC_INLINE void ICRA(uae_u32 data) +STATIC_INLINE void ICRA(uae_u32 dummy) { - ciaaicr |= 0x40; + if (ciaaicr & 0x80) + ciaaicr |= 0x40; ciaaicr |= 0x20; ICR (0x0008); } -STATIC_INLINE void ICRB(uae_u32 data) +STATIC_INLINE void ICRB(uae_u32 dummy) { - ciabicr |= 0x40; + if (ciabicr & 0x80) + ciabicr |= 0x40; ciabicr |= 0x20; ICR (0x2000); } @@ -105,7 +106,7 @@ STATIC_INLINE void RethinkICRA (void) if (ciaaicr & ciaaimask) { if (!(ciaaicr & 0x80)) { ciaaicr |= 0x80; - ICRA (0x0008); + ICRA (0); } } } @@ -129,25 +130,25 @@ void rethink_cias (void) } /* Figure out how many CIA timer cycles have passed for each timer since the - last call of CIA_calctimers. */ +last call of CIA_calctimers. */ static void compute_passed_time (void) { - unsigned long int ccount = (get_cycles () - eventtab[ev_cia].oldcycles + div10); - unsigned long int ciaclocks = ccount / DIV10; + unsigned long int ccount = (get_cycles () - eventtab[ev_cia].oldcycles + div10); + unsigned long int ciaclocks = ccount / DIV10; - ciaata_passed = ciaatb_passed = ciabta_passed = ciabtb_passed = 0; + ciaata_passed = ciaatb_passed = ciabta_passed = ciabtb_passed = 0; - /* CIA A timers */ - if ((ciaacra & 0x21) == 0x01) { + /* CIA A timers */ + if ((ciaacra & 0x21) == 0x01) { unsigned long int cc = ciaclocks; if (cc > ciaastarta) cc -= ciaastarta; else cc = 0; ciaata_passed = cc; - } - if ((ciaacrb & 0x61) == 0x01) { + } + if ((ciaacrb & 0x61) == 0x01) { unsigned long int cc = ciaclocks; if (cc > ciaastartb) cc -= ciaastartb; @@ -156,16 +157,16 @@ static void compute_passed_time (void) ciaatb_passed = cc; } - /* CIA B timers */ - if ((ciabcra & 0x21) == 0x01) { + /* CIA B timers */ + if ((ciabcra & 0x21) == 0x01) { unsigned long int cc = ciaclocks; if (cc > ciabstarta) cc -= ciabstarta; else cc = 0; ciabta_passed = cc; - } - if ((ciabcrb & 0x61) == 0x01) { + } + if ((ciabcrb & 0x61) == 0x01) { unsigned long int cc = ciaclocks; if (cc > ciabstartb) cc -= ciabstartb; @@ -181,8 +182,8 @@ static void compute_passed_time (void) static int CIA_update_check (void) { - unsigned long int ccount = (get_cycles () - eventtab[ev_cia].oldcycles + div10); - unsigned long int ciaclocks = ccount / DIV10; + unsigned long int ccount = (get_cycles () - eventtab[ev_cia].oldcycles + div10); + unsigned long int ciaclocks = ccount / DIV10; int aovfla = 0, aovflb = 0, asp = 0, bovfla = 0, bovflb = 0, bsp = 0; int icr = 0; @@ -328,7 +329,7 @@ static void CIA_update (void) static void CIA_calctimers (void) { - long int ciaatimea = -1, ciaatimeb = -1, ciabtimea = -1, ciabtimeb = -1; + long int ciaatimea = -1, ciaatimeb = -1, ciabtimea = -1, ciabtimeb = -1; int div10diff = DIV10 - div10; eventtab[ev_cia].oldcycles = get_cycles (); @@ -350,7 +351,7 @@ static void CIA_calctimers (void) eventtab[ev_cia].active = (ciaatimea != -1 || ciaatimeb != -1 || ciabtimea != -1 || ciabtimeb != -1); if (eventtab[ev_cia].active) { - unsigned long int ciatime = ~0L; + unsigned long int ciatime = ~0L; if (ciaatimea != -1) ciatime = ciaatimea; if (ciaatimeb != -1 && ciaatimeb < ciatime) @@ -376,7 +377,7 @@ void cia_diskindex (void) RethinkICRB(); } -static bool checkalarm (unsigned long tod, unsigned long alarm, bool inc) +static bool checkalarm (unsigned long tod, unsigned long alarm, bool inc, int ab) { if (tod == alarm) return true; @@ -395,7 +396,7 @@ static bool checkalarm (unsigned long tod, unsigned long alarm, bool inc) return false; } -STATIC_INLINE void ciab_checkalarm (bool inc, bool irq) +STATIC_INLINE bool ciab_checkalarm (bool inc, bool irq) { // hack: do not trigger alarm interrupt if KS code and both // tod and alarm == 0. This incorrectly triggers on non-cycle exact @@ -404,19 +405,21 @@ STATIC_INLINE void ciab_checkalarm (bool inc, bool irq) // old value. if ((munge24 (m68k_getpc ()) & 0xFFF80000) != 0xF80000) { if (ciabtod == 0 && ciabalarm == 0) - return; + return false; } - if (checkalarm (ciabtod, ciabalarm, inc)) { + if (checkalarm (ciabtod, ciabalarm, inc, 1)) { if (irq) { ciabicr |= 4; RethinkICRB (); } + return true; } + return false; } STATIC_INLINE void ciaa_checkalarm (bool inc) { - if (checkalarm (ciaatod, ciaaalarm, inc)) { + if (checkalarm (ciaatod, ciaaalarm, inc, 0)) { ciaaicr |= 4; RethinkICRA (); } @@ -486,7 +489,7 @@ void CIAB_tod_handler (int hoffset) return; ciab_tod_hoffset = hoffset + TOD_INC_DELAY; ciab_tod_event_state = 1; // TOD inc needed - if (checkalarm ((ciabtod + 1) & 0xffffff, ciabalarm, true)) { + if (checkalarm ((ciabtod + 1) & 0xffffff, ciabalarm, true, 1)) { // causes interrupt on this line, add event ciab_tod_event_state = 2; // event active event2_newevent_xx (-1, ciab_tod_hoffset, 0, CIAB_tod_inc_event); @@ -534,9 +537,9 @@ void CIA_hsync_posthandler (bool ciahsync) } } -static void calc_led(int old_led) +static void calc_led (int old_led) { - unsigned long c = get_cycles(); + unsigned long c = get_cycles (); unsigned long t = (c - led_cycle) / CYCLE_UNIT; if (old_led) led_cycles_on += t; @@ -545,11 +548,11 @@ static void calc_led(int old_led) led_cycle = c; } -static void led_vsync(void) +static void led_vsync (void) { int v; - calc_led(led); + calc_led (led); if (led_cycles_on && !led_cycles_off) v = 255; else if (led_cycles_off && !led_cycles_on) @@ -569,16 +572,16 @@ static void led_vsync(void) led_cycles_off = 0; if (led_old_brightness != gui_data.powerled_brightness) { gui_data.powerled = gui_data.powerled_brightness > 96; - gui_led(LED_POWER, gui_data.powerled, gui_data.powerled_brightness); - led_filter_audio(); + gui_led (LED_POWER, gui_data.powerled, gui_data.powerled_brightness); + led_filter_audio (); } led_old_brightness = gui_data.powerled_brightness; - led_cycle = get_cycles(); + led_cycle = get_cycles (); } void CIA_vsync_prehandler (void) { - led_vsync(); + led_vsync (); CIA_handler (); if (kblostsynccnt > 0) { kblostsynccnt -= maxvpos; @@ -589,11 +592,11 @@ void CIA_vsync_prehandler (void) } } -static void CIAA_tod_handler(uae_u32 v) +static void CIAA_tod_handler (uae_u32 v) { ciaatod++; - ciaatod &= 0xFFFFFF; - ciaa_checkalarm(true); + ciaatod &= 0xFFFFFF; + ciaa_checkalarm (true); } void CIAA_tod_inc (int cycles) @@ -603,15 +606,15 @@ void CIAA_tod_inc (int cycles) event2_newevent_xx (-1, cycles + TOD_INC_DELAY, 0, CIAA_tod_handler); } -static void check_led(void) +STATIC_INLINE void check_led (void) { - uae_u8 v = ciaapra; + uae_u8 v = ciaapra; bool led2; - v |= ~ciaadra; /* output is high when pin's direction is input */ + v |= ~ciaadra; /* output is high when pin's direction is input */ led2 = (v & 2) ? 0 : 1; if (led2 != led) { - calc_led(led); + calc_led (led); led = led2; led_old_brightness = -1; } @@ -659,11 +662,7 @@ static uae_u8 ReadCIAA (unsigned int addr, uae_u32 *flags) return v; } case 1: -#if defined(INPUTDEVICE_SIMPLE) && !defined(AMIBERRY) - tmp = (ciaaprb & ciaadrb) | (ciaadrb ^ 0xff); -#else tmp = handle_parport_joystick (0, ciaaprb, ciaadrb); -#endif if (ciaacrb & 2) { int pb7 = 0; if (ciaacrb & 4) @@ -743,11 +742,13 @@ static uae_u8 ReadCIAB (unsigned int addr, uae_u32 *flags) switch (reg) { case 0: tmp = 0; -#if defined(INPUTDEVICE_SIMPLE) && !defined(AMIBERRY) - tmp = ((ciabpra & ciabdra) | (ciabdra ^ 0xff)) & 0x7; -#else tmp |= handle_parport_joystick (1, ciabpra, ciabdra); -#endif + + if (currprefs.cs_ciatype[1]) { + tmp &= ~ciabdra; + tmp |= ciabpra & ciabdra; + } + return tmp; case 1: tmp = ciabprb; @@ -1117,7 +1118,7 @@ void CIA_reset (void) } #ifdef CD32 if (!isrestore ()) { - akiko_reset (); + akiko_reset (1); if (!akiko_init ()) currprefs.cs_cd32cd = changed_prefs.cs_cd32cd = 0; } @@ -1131,43 +1132,40 @@ addrbank cia_bank = { cia_lget, cia_wget, cia_bget, cia_lput, cia_wput, cia_bput, default_xlate, default_check, NULL, NULL, _T("CIA"), - cia_lgeti, cia_wgeti, + cia_wgeti, ABFLAG_IO | ABFLAG_CIA, S_READ, S_WRITE, NULL, 0x3f01, 0xbfc000 }; -static void cia_wait_pre(void) +static void cia_wait_pre (void) { if (currprefs.cachesize) return; - int div = (get_cycles() - eventtab[ev_cia].oldcycles) % DIV10; - int cycles; + int div = (get_cycles () - eventtab[ev_cia].oldcycles) % DIV10; + int cycles; - if (div >= DIV10 * ECLOCK_DATA_CYCLE / 10) { - cycles = DIV10 - div; - cycles += DIV10 * ECLOCK_DATA_CYCLE / 10; - } - else if (div) { + if (div >= DIV10 * ECLOCK_DATA_CYCLE / 10) { + cycles = DIV10 - div; + cycles += DIV10 * ECLOCK_DATA_CYCLE / 10; + } else if (div) { cycles = DIV10 + DIV10 * ECLOCK_DATA_CYCLE / 10 - div; - } - else { - cycles = DIV10 * ECLOCK_DATA_CYCLE / 10 - div; - } + } else { + cycles = DIV10 * ECLOCK_DATA_CYCLE / 10 - div; + } if (cycles) { - do_cycles(cycles); - } + do_cycles (cycles); + } } -static void cia_wait_post(uae_u32 value) +static void cia_wait_post (void) { if (currprefs.cachesize) { - do_cycles(8 * CYCLE_UNIT / 2); - } - else { + do_cycles (8 * CYCLE_UNIT / 2); + } else { int c = 6 * CYCLE_UNIT / 2; - do_cycles(c); - } + do_cycles (c); + } } // Gayle or Fat Gary does not enable CIA /CS lines if both CIAs are selected @@ -1235,7 +1233,7 @@ static uae_u32 REGPARAM2 cia_bget (uaecptr addr) if (!issinglecia ()) { cia_wait_pre (); v = (addr & 1) ? ReadCIAA (r, &flags) : ReadCIAB (r, &flags); - cia_wait_post (v); + cia_wait_post (); } break; case 1: @@ -1245,7 +1243,7 @@ static uae_u32 REGPARAM2 cia_bget (uaecptr addr) } else { v = (addr & 1) ? dummy_get_safe(addr, 1, false, 0) : ReadCIAB (r, &flags); } - cia_wait_post (v); + cia_wait_post (); break; case 2: cia_wait_pre (); @@ -1253,13 +1251,13 @@ static uae_u32 REGPARAM2 cia_bget (uaecptr addr) v = (addr & 1) ? ReadCIAA (r, &flags) : regs.irc >> 8; else v = (addr & 1) ? ReadCIAA (r, &flags) : dummy_get_safe(addr, 1, false, 0); - cia_wait_post (v); + cia_wait_post (); break; case 3: if (currprefs.cpu_model == 68000 && currprefs.cpu_compatible) { cia_wait_pre (); v = (addr & 1) ? regs.irc : regs.irc >> 8; - cia_wait_post (v); + cia_wait_post (); } break; } @@ -1290,27 +1288,29 @@ static uae_u32 REGPARAM2 cia_wget (uaecptr addr) { cia_wait_pre (); v = (ReadCIAB (r, &flags) << 8) | ReadCIAA (r, &flags); - cia_wait_post (v); + cia_wait_post (); } break; case 1: cia_wait_pre (); v = (ReadCIAB (r, &flags) << 8) | dummy_get_safe(addr, 1, false, 0); - cia_wait_post (v); + cia_wait_post (); break; case 2: cia_wait_pre (); v = (dummy_get_safe(addr, 1, false, 0) << 8) | ReadCIAA (r, &flags); - cia_wait_post (v); + cia_wait_post (); break; case 3: if (currprefs.cpu_model == 68000 && currprefs.cpu_compatible) { cia_wait_pre (); v = regs.irc; - cia_wait_post (v); + cia_wait_post (); } break; } + if (addr & 1) + v = (v << 8) | (v >> 8); #ifdef ACTION_REPLAY if (flags) { action_replay_cia_access((flags & 2) != 0); @@ -1333,12 +1333,6 @@ static uae_u32 REGPARAM2 cia_wgeti (uaecptr addr) return dummy_wgeti(addr); return cia_wget(addr); } -static uae_u32 REGPARAM2 cia_lgeti (uaecptr addr) -{ - if (currprefs.cpu_model >= 68020) - return dummy_lgeti(addr); - return cia_lget(addr); -} static void REGPARAM2 cia_bput (uaecptr addr, uae_u32 value) { @@ -1360,7 +1354,7 @@ static void REGPARAM2 cia_bput (uaecptr addr, uae_u32 value) WriteCIAB (r, value, &flags); if ((cs & 1) == 0) WriteCIAA (r, value); - cia_wait_post (value); + cia_wait_post (); #ifdef ACTION_REPLAY if (flags) { action_replay_cia_access((flags & 2) != 0); @@ -1369,7 +1363,7 @@ static void REGPARAM2 cia_bput (uaecptr addr, uae_u32 value) } } -static void REGPARAM2 cia_wput (uaecptr addr, uae_u32 value) +static void REGPARAM2 cia_wput (uaecptr addr, uae_u32 v) { int r = (addr & 0xf00) >> 8; @@ -1380,16 +1374,19 @@ static void REGPARAM2 cia_wput (uaecptr addr, uae_u32 value) if (!isgaylenocia (addr)) return; + if (addr & 1) + v = (v << 8) | (v >> 8); + int cs = cia_chipselect(addr); if (!issinglecia ()|| (cs & 3) != 0) { uae_u32 flags = 0; cia_wait_pre (); if ((cs & 2) == 0) - WriteCIAB (r, value >> 8, &flags); + WriteCIAB (r, v >> 8, &flags); if ((cs & 1) == 0) - WriteCIAA (r, value & 0xff); - cia_wait_post (value); + WriteCIAA (r, v & 0xff); + cia_wait_post (); #ifdef ACTION_REPLAY if (flags) { action_replay_cia_access((flags & 2) != 0); @@ -1417,7 +1414,7 @@ addrbank clock_bank = { clock_lget, clock_wget, clock_bget, clock_lput, clock_wput, clock_bput, default_xlate, default_check, NULL, NULL, _T("Battery backed up clock (none)"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO, S_READ, S_WRITE, NULL, 0x3f, 0xd80000 }; @@ -1538,6 +1535,7 @@ void restore_cia_start (void) { /* Fixes very old statefiles without keyboard state */ kbstate = 3; + setcapslockstate (0); kblostsynccnt = 0; } @@ -1701,6 +1699,7 @@ uae_u8 *save_keyboard (int *len, uae_u8 *dstptr) dstbak = dst = dstptr; else dstbak = dst = xmalloc (uae_u8, 4 + 4 + 1 + 1 + 1 + 1 + 1 + 2); + save_u32 (getcapslockstate () ? 1 : 0); save_u32 (1); save_u8 (kbstate); save_u8 (0); @@ -1714,6 +1713,7 @@ uae_u8 *save_keyboard (int *len, uae_u8 *dstptr) uae_u8 *restore_keyboard (uae_u8 *src) { + setcapslockstate (restore_u32 () & 1); uae_u32 v = restore_u32 (); kbstate = restore_u8 (); restore_u8 (); diff --git a/src/cpudefs.cpp b/src/cpudefs.cpp index 2f12728d..7984d2b7 100644 --- a/src/cpudefs.cpp +++ b/src/cpudefs.cpp @@ -1,3 +1,4 @@ +#include "sysconfig.h" #include "sysdeps.h" #include "readcpu.h" struct instr_def defs68k[] = { diff --git a/src/cpuemu_0.cpp b/src/cpuemu_0.cpp index 6ca1772f..acc9ef02 100644 --- a/src/cpuemu_0.cpp +++ b/src/cpuemu_0.cpp @@ -490,11 +490,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00d0_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -511,11 +514,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00e8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -533,11 +539,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f0_0)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -552,11 +561,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -572,11 +584,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f9_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -594,11 +609,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00fa_0)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -618,11 +636,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00fb_0)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte (dsta); upper = (uae_s32)(uae_s8)get_byte (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1758,11 +1779,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02d0_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1779,11 +1803,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02e8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1801,11 +1828,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f0_0)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1820,11 +1850,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1840,11 +1873,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f9_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -1862,11 +1898,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02fa_0)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1886,11 +1925,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02fb_0)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word (dsta); upper = (uae_s32)(uae_s16)get_word (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2460,10 +2502,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04d0_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2480,10 +2525,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04e8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2501,10 +2549,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f0_0)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2519,10 +2570,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f8_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2538,10 +2592,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f9_0)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -2559,10 +2616,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04fa_0)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2582,10 +2642,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04fb_0)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long (dsta); upper = get_long (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -5330,9 +5393,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e10_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5355,10 +5418,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e18_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += areg_byteinc[dstreg]; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5382,10 +5445,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e20_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - areg_byteinc[dstreg]; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5409,9 +5472,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e28_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5434,10 +5497,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e30_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5458,9 +5521,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e38_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5482,9 +5545,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e39_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -5507,9 +5570,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e50_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5532,10 +5595,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e58_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += 2; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5559,10 +5622,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e60_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 2; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5586,9 +5649,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e68_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5611,10 +5674,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e70_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5635,9 +5698,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e78_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5659,9 +5722,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e79_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -5684,9 +5747,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e90_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5709,10 +5772,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e98_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += 4; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5736,10 +5799,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0ea0_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5763,9 +5826,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0ea8_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5788,10 +5851,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb0_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5812,9 +5875,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb8_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5836,9 +5899,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb9_0)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -12216,16 +12279,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4100_0)(uae_u32 opcode) {{ uae_s32 src = m68k_dreg (regs, srcreg); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 6 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}return 8 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12240,16 +12304,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4110_0)(uae_u32 opcode) { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12265,16 +12330,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4118_0)(uae_u32 opcode) m68k_areg (regs, srcreg) += 4; { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12290,16 +12356,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4120_0)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 13 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12314,16 +12381,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4128_0)(uae_u32 opcode) { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12338,16 +12406,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4130_0)(uae_u32 opcode) { srca = get_disp_ea_020 (m68k_areg (regs, srcreg), 0); { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12361,16 +12430,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4138_0)(uae_u32 opcode) { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12384,16 +12454,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4139_0)(uae_u32 opcode) { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 15 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 15 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12408,16 +12479,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413a_0)(uae_u32 opcode) { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12433,16 +12505,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413b_0)(uae_u32 opcode) srca = get_disp_ea_020 (tmppc, 0); { uae_s32 src = get_long (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12455,16 +12528,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413c_0)(uae_u32 opcode) src = get_dilong (2); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}return 13 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12477,16 +12551,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4180_0)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 6 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 8 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12501,16 +12576,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4190_0)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12526,16 +12602,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4198_0)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12551,16 +12628,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_0)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 13 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12575,16 +12653,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a8_0)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12599,16 +12678,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b0_0)(uae_u32 opcode) { srca = get_disp_ea_020 (m68k_areg (regs, srcreg), 0); { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12622,16 +12702,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b8_0)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12645,16 +12726,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b9_0)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 15 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 15 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12669,16 +12751,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41ba_0)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12694,16 +12777,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bb_0)(uae_u32 opcode) srca = get_disp_ea_020 (tmppc, 0); { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12715,16 +12799,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bc_0)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 9 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 11 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -14562,10 +14647,10 @@ return 6 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_4808_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s32 offs; offs = get_dilong (2); put_long (olda,src); @@ -16704,10 +16789,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e40_0)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e50_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s16 offs = get_diword (2); put_long (olda,src); m68k_areg (regs, srcreg) = (m68k_areg(regs, 7)); @@ -16722,11 +16807,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e58_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); {{ uae_s32 src = m68k_areg (regs, srcreg); - m68k_areg (regs, 7) = src; -{ uaecptr olda; - olda = m68k_areg (regs, 7); +{ uae_u32 olda = src; { uae_s32 old = get_long (olda); - m68k_areg (regs, 7) += 4; + m68k_areg (regs, 7) = src + 4; m68k_areg (regs, srcreg) = (old); }}}} m68k_incpc (2); return 7 * CYCLE_UNIT / 2; @@ -16811,7 +16894,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_0)(uae_u32 opcode) else if (frame == 0x3) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x4) { m68k_areg (regs, 7) += offset + 8; break; } else if (frame == 0x7) { m68k_areg (regs, 7) += offset + 52; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -16940,8 +17023,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e90_0)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -16958,8 +17041,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ea8_0)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 15 * CYCLE_UNIT / 2; } @@ -16977,8 +17060,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb0_0)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}}return 17 * CYCLE_UNIT / 2; } @@ -16994,8 +17077,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb8_0)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -17011,8 +17094,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb9_0)(uae_u32 opcode) exception3i (opcode, srca); return 12 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -17029,8 +17112,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eba_0)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 15 * CYCLE_UNIT / 2; } @@ -17049,8 +17132,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ebb_0)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}}return 17 * CYCLE_UNIT / 2; } @@ -22953,10 +23036,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_8148_0)(uae_u32 opcode) uae_u32 srcreg = (opcode & 7); uae_u32 dstreg = (opcode >> 9) & 7; { uae_u16 val; - m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; - val = (uae_u16)(get_byte (m68k_areg (regs, srcreg)) & 0xff); - m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; - val = val | ((uae_u16)(get_byte (m68k_areg (regs, srcreg)) & 0xff) << 8); + m68k_areg (regs, srcreg) -= 2; + val = (uae_u16)(get_word (m68k_areg (regs, srcreg))); val += get_diword (2); m68k_areg (regs, dstreg) -= areg_byteinc[dstreg]; put_byte (m68k_areg (regs, dstreg),((val >> 4) & 0xf0) | (val & 0xf)); @@ -23121,9 +23202,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_8188_0)(uae_u32 opcode) m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; val = (uae_u16)(get_byte (m68k_areg (regs, srcreg)) & 0xff); val = (((val << 4) & 0xf00) | (val & 0xf)) + get_diword (2); - m68k_areg (regs, dstreg) -= 2 * areg_byteinc[dstreg]; - put_byte (m68k_areg (regs, dstreg) + areg_byteinc[dstreg], val); - put_byte (m68k_areg (regs, dstreg), val >> 8); + m68k_areg (regs, dstreg) -= 2; + put_word (m68k_areg (regs, dstreg), val); } m68k_incpc (4); return 13 * CYCLE_UNIT / 2; } @@ -30705,7 +30785,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -30713,7 +30793,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -30821,7 +30901,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -30829,7 +30909,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -30941,7 +31021,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -30949,7 +31029,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -31060,7 +31140,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -31068,7 +31148,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -31179,7 +31259,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -31187,7 +31267,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -31295,7 +31375,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_0)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -31303,7 +31383,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_0)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -35627,13 +35707,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_f5c8_0)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_f600_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = m68k_areg (regs, srcreg); { uaecptr memda; memda = get_dilong (2); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long (memsa); v[1] = get_long (memsa + 4); v[2] = get_long (memsa + 8); @@ -35651,13 +35731,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f608_0)(uae_u32 opcode) { uae_u32 dstreg = opcode & 7; -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = get_dilong (2); { uaecptr memda; memda = m68k_areg (regs, dstreg); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long (memsa); v[1] = get_long (memsa + 4); v[2] = get_long (memsa + 8); @@ -35675,13 +35755,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f610_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = m68k_areg (regs, srcreg); { uaecptr memda; memda = get_dilong (2); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long (memsa); v[1] = get_long (memsa + 4); v[2] = get_long (memsa + 8); @@ -35698,13 +35778,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f618_0)(uae_u32 opcode) { uae_u32 dstreg = opcode & 7; -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = get_dilong (2); { uaecptr memda; memda = m68k_areg (regs, dstreg); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long (memsa); v[1] = get_long (memsa + 4); v[2] = get_long (memsa + 8); @@ -35722,10 +35802,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_f620_0)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); uae_u32 dstreg = 0; -{ uae_u32 v[4]; - uaecptr mems = m68k_areg (regs, srcreg) & ~15, memd; +{ uaecptr mems = m68k_areg (regs, srcreg) & ~15, memd; dstreg = (get_diword (2) >> 12) & 7; memd = m68k_areg (regs, dstreg) & ~15; + uae_u32 v[4]; v[0] = get_long (mems); v[1] = get_long (mems + 4); v[2] = get_long (mems + 8); @@ -35818,7 +35898,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_1)(uae_u32 opcode) else if (frame == 0x3) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x4) { m68k_areg (regs, 7) += offset + 8; break; } else if (frame == 0x7) { m68k_areg (regs, 7) += offset + 52; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -35887,6 +35967,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4800_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, srcreg) = (m68k_dreg (regs, srcreg) & ~0xff) | ((newv) & 0xff); }}} m68k_incpc (2); return 6 * CYCLE_UNIT / 2; @@ -35913,6 +35994,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4810_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -35940,6 +36022,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4818_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -35967,6 +36050,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4820_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (2); return 13 * CYCLE_UNIT / 2; @@ -35993,6 +36077,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4828_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (4); return 13 * CYCLE_UNIT / 2; @@ -36020,6 +36105,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4830_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}}}return 15 * CYCLE_UNIT / 2; } @@ -36044,6 +36130,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4838_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (4); return 12 * CYCLE_UNIT / 2; @@ -36069,6 +36156,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4839_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (srca,newv); }}}} m68k_incpc (6); return 12 * CYCLE_UNIT / 2; @@ -36108,7 +36196,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_2)(uae_u32 opcode) else if (frame == 0x9) { m68k_areg (regs, 7) += offset + 12; break; } else if (frame == 0xa) { m68k_areg (regs, 7) += offset + 24; break; } else if (frame == 0xb) { m68k_areg (regs, 7) += offset + 84; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -36147,6 +36235,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8100_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, dstreg) = (m68k_dreg (regs, dstreg) & ~0xff) | ((newv) & 0xff); }}}} m68k_incpc (2); return 4 * CYCLE_UNIT / 2; @@ -36177,6 +36266,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8108_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (dsta,newv); }}}}}} m68k_incpc (2); return 16 * CYCLE_UNIT / 2; @@ -36205,6 +36295,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c100_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, dstreg) = (m68k_dreg (regs, dstreg) & ~0xff) | ((newv) & 0xff); }}}} m68k_incpc (2); return 4 * CYCLE_UNIT / 2; @@ -36236,6 +36327,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c108_2)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte (dsta,newv); }}}}}} m68k_incpc (2); return 16 * CYCLE_UNIT / 2; @@ -36302,7 +36394,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_3)(uae_u32 opcode) else if (frame == 0x9) { m68k_areg (regs, 7) += offset + 12; break; } else if (frame == 0xa) { m68k_areg (regs, 7) += offset + 24; break; } else if (frame == 0xb) { m68k_areg (regs, 7) += offset + 84; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } diff --git a/src/cpuemu_11.cpp b/src/cpuemu_11.cpp index c0b8cb3a..6120275d 100644 --- a/src/cpuemu_11.cpp +++ b/src/cpuemu_11.cpp @@ -289,6 +289,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0060_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -515,7 +516,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_00a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -1694,6 +1696,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0260_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -1920,7 +1923,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_02a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -2353,6 +2357,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0460_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -2602,7 +2607,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_04a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -3060,6 +3066,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0660_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -3309,7 +3316,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_06a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -4391,6 +4399,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0a60_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -4617,7 +4626,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_0aa0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -5031,6 +5041,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_0c60_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -5264,7 +5275,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_0ca0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (8); + m68k_incpci (6); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -7414,7 +7426,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_2020_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -7540,6 +7553,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_203a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -7566,6 +7580,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_203b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -7684,7 +7699,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_2060_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -7795,6 +7811,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_207a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -7818,6 +7835,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_207b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -7914,6 +7932,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2090_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -7947,6 +7966,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2098_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -7970,7 +7990,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_20a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -7980,6 +8001,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20a0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -8012,6 +8034,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20a8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8044,6 +8067,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20b0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -8075,6 +8099,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20b8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8107,6 +8132,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20b9_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -8131,6 +8157,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -8139,6 +8166,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20ba_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8164,6 +8192,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -8172,6 +8201,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20bb_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -8282,6 +8312,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20d0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -8316,6 +8347,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20d8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -8340,7 +8372,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_20e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -8350,6 +8383,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20e0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -8383,6 +8417,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20e8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8416,6 +8451,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20f0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -8448,6 +8484,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20f8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8481,6 +8518,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20f9_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -8506,6 +8544,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -8514,6 +8553,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20fa_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -8540,6 +8580,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -8548,6 +8589,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_20fb_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -8601,6 +8643,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2100_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; @@ -8628,6 +8671,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2108_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; @@ -8662,6 +8706,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2110_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; @@ -8697,6 +8742,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2118_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; @@ -8722,7 +8768,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_2120_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -8732,6 +8779,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2120_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; @@ -8766,6 +8814,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2128_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; @@ -8800,6 +8849,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2130_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; @@ -8833,6 +8883,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2138_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; @@ -8867,6 +8918,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2139_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; @@ -8893,6 +8945,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_213a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -8901,6 +8954,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_213a_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; @@ -8928,6 +8982,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_213b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -8936,6 +8991,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_213b_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; @@ -8964,6 +9020,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_213c_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); dsta += 2; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; @@ -8991,6 +9048,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2140_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -9016,6 +9074,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2148_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -9048,6 +9107,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2150_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -9081,6 +9141,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2158_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -9104,7 +9165,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_2160_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -9114,6 +9176,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -9146,6 +9209,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2168_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9178,6 +9242,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2170_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9209,6 +9274,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2178_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9241,6 +9307,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2179_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 24 * CYCLE_UNIT / 2; } @@ -9265,6 +9332,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_217a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -9273,6 +9341,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_217a_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9298,6 +9367,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_217b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -9306,6 +9376,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_217b_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9332,6 +9403,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_217c_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -9357,6 +9429,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2180_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -9382,6 +9455,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2188_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -9414,6 +9488,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2190_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -9447,6 +9522,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_2198_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -9473,7 +9549,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_21a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -9483,6 +9560,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21a0_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9515,6 +9593,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21a8_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9547,6 +9626,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21b0_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 24 * CYCLE_UNIT / 2; } @@ -9578,6 +9658,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21b8_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9610,6 +9691,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21b9_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (8)); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 26 * CYCLE_UNIT / 2; } @@ -9634,6 +9716,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -9642,6 +9725,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21ba_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9667,6 +9751,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -9675,6 +9760,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21bb_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 24 * CYCLE_UNIT / 2; } @@ -9701,6 +9787,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21bc_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (8)); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_HNZ(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -9725,6 +9812,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21c0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -9749,6 +9837,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21c8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -9780,6 +9869,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21d0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -9812,6 +9902,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21d8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -9834,7 +9925,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_21e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -9844,6 +9936,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21e0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -9875,6 +9968,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21e8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9906,6 +10000,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21f0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -9936,6 +10031,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21f8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -9967,6 +10063,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21f9_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 24 * CYCLE_UNIT / 2; } @@ -9990,6 +10087,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -9998,6 +10096,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21fa_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -10022,6 +10121,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -10030,6 +10130,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21fb_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -10055,6 +10156,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_21fc_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -10080,6 +10182,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23c0_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -10105,6 +10208,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23c8_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -10137,6 +10241,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23d0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -10171,6 +10276,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23d8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -10194,7 +10300,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_23e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -10205,6 +10312,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23e0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -10238,6 +10346,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23e8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -10271,6 +10380,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23f0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -10303,6 +10413,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23f8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -10336,6 +10447,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23f9_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (10); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 24 * CYCLE_UNIT / 2; } @@ -10360,6 +10472,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -10369,6 +10482,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23fa_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -10394,6 +10508,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -10403,6 +10518,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23fb_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_long_move_ae_LZN(src); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -10430,6 +10546,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_23fc_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (10); if (dsta & 1) { m68k_incpci (10); + ccr_68000_long_move_ae_normal(src); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -10541,6 +10658,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3020_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -10666,6 +10784,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_303a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -10692,6 +10811,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_303b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -10813,6 +10933,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -10928,6 +11049,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_307a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -10952,6 +11074,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_307b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -10991,6 +11114,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3080_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11016,6 +11140,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3088_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11048,6 +11173,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3090_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11081,6 +11207,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3098_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11105,6 +11232,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30a0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -11114,6 +11242,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30a0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -11146,6 +11275,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30a8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11178,6 +11308,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30b0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -11209,6 +11340,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30b8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11241,6 +11373,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30b9_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -11265,6 +11398,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -11273,6 +11407,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30ba_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11298,6 +11433,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -11306,6 +11442,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30bb_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -11330,6 +11467,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30bc_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11355,6 +11493,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30c0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11381,6 +11520,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30c8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11414,6 +11554,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30d0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11448,6 +11589,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30d8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11473,6 +11615,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -11482,6 +11625,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30e0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -11515,6 +11659,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30e8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11548,6 +11693,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30f0_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -11580,6 +11726,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30f8_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11613,6 +11760,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30f9_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -11638,6 +11786,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -11646,6 +11795,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30fa_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11672,6 +11822,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -11680,6 +11831,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30fb_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -11705,6 +11857,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_30fc_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11731,6 +11884,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3100_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11757,6 +11913,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3108_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -11790,6 +11949,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3110_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11824,6 +11986,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3118_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -11849,6 +12014,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3120_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -11858,6 +12024,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3120_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -11891,6 +12060,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3128_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11924,6 +12096,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3130_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -11956,6 +12131,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3138_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -11989,6 +12167,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_3139_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (8); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -12014,6 +12195,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_313a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -12022,6 +12204,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_313a_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12048,6 +12233,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_313b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -12056,6 +12242,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_313b_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12081,6 +12270,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_313c_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (6); + opcode = regs.irc | 0x00080000; + ccr_68000_word_move_ae_normal((uae_s16)(src)); + m68k_areg (regs, dstreg) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -12107,6 +12299,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3140_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -12132,6 +12325,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3148_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -12164,6 +12358,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3150_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12197,6 +12392,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3158_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12221,6 +12417,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3160_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -12230,6 +12427,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12262,6 +12460,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3168_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -12294,6 +12493,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3170_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -12325,6 +12525,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3178_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -12357,6 +12558,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3179_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -12381,6 +12583,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_317a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -12389,6 +12592,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_317a_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -12414,6 +12618,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_317b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -12422,6 +12627,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_317b_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -12446,6 +12652,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_317c_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12471,6 +12678,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3180_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -12496,6 +12704,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3188_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -12528,6 +12737,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3190_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12561,6 +12771,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_3198_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12585,6 +12796,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31a0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -12594,6 +12806,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31a0_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (4)); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -12626,6 +12839,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31a8_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -12658,6 +12872,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31b0_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -12689,6 +12904,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31b8_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -12721,6 +12937,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31b9_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (8)); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 22 * CYCLE_UNIT / 2; } @@ -12745,6 +12962,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -12753,6 +12971,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31ba_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -12778,6 +12997,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -12786,6 +13006,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31bb_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -12810,6 +13031,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31bc_11)(uae_u32 opcode) dsta = get_disp_ea_000 (m68k_areg (regs, dstreg), get_word_000_prefetch (6)); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12834,6 +13056,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31c0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -12858,6 +13081,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31c8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -12889,6 +13113,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31d0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12921,6 +13146,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31d8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -12944,6 +13170,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -12953,6 +13180,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31e0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (4); if (dsta & 1) { m68k_incpci (4); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -12984,6 +13212,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31e8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13015,6 +13244,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31f0_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -13045,6 +13275,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31f8_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13076,6 +13307,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31f9_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -13099,6 +13331,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -13107,6 +13340,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31fa_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13131,6 +13365,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -13139,6 +13374,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31fb_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -13162,6 +13398,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_31fc_11)(uae_u32 opcode) dsta = (uae_s32)(uae_s16)get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -13187,6 +13424,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33c0_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -13212,6 +13450,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33c8_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (6); if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -13244,6 +13483,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33d0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -13278,6 +13518,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33d8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -13302,6 +13543,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -13312,6 +13554,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33e0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (6); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 14 * CYCLE_UNIT / 2; } @@ -13345,6 +13588,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33e8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13378,6 +13622,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33f0_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -13410,6 +13655,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33f8_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13443,6 +13689,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33f9_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (10); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 20 * CYCLE_UNIT / 2; } @@ -13467,6 +13714,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -13476,6 +13724,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33fa_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13501,6 +13750,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -13510,6 +13760,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33fb_11)(uae_u32 opcode) dsta |= regs.irc; if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 18 * CYCLE_UNIT / 2; } @@ -13535,6 +13786,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_33fc_11)(uae_u32 opcode) dsta |= get_word_000_prefetch (8); if (dsta & 1) { m68k_incpci (8); + ccr_68000_word_move_ae_normal((uae_s16)(src)); exception3_write(opcode, dsta); return 16 * CYCLE_UNIT / 2; } @@ -13841,6 +14093,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -14074,7 +14327,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_40a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -14288,6 +14542,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_40e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_write(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -14402,16 +14657,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4180_11)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}return 10 * CYCLE_UNIT / 2 + count_cycles; @@ -14434,16 +14690,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4190_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 14 * CYCLE_UNIT / 2 + count_cycles; @@ -14467,16 +14724,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4198_11)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 14 * CYCLE_UNIT / 2 + count_cycles; @@ -14493,6 +14751,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -14500,16 +14759,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_11)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 16 * CYCLE_UNIT / 2 + count_cycles; @@ -14532,16 +14792,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a8_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 18 * CYCLE_UNIT / 2 + count_cycles; @@ -14564,16 +14825,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b0_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 20 * CYCLE_UNIT / 2 + count_cycles; @@ -14595,16 +14857,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b8_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 18 * CYCLE_UNIT / 2 + count_cycles; @@ -14627,16 +14890,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b9_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 22 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 22 * CYCLE_UNIT / 2 + count_cycles; @@ -14653,22 +14917,24 @@ uae_u32 REGPARAM2 CPUFUNC(op_41ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 18 * CYCLE_UNIT / 2 + count_cycles; @@ -14686,22 +14952,24 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } {{ uae_s16 src = get_word_000 (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}}}return 20 * CYCLE_UNIT / 2 + count_cycles; @@ -14716,16 +14984,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bc_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000_prefetch (4); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpci (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); regs.ir = regs.irc; get_word_000_prefetch (2); }}}return 14 * CYCLE_UNIT / 2 + count_cycles; @@ -15059,6 +15328,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4260_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_write(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -15237,6 +15507,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_42a0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_write(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -15409,6 +15680,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_42e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_write(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -15800,6 +16072,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4460_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -16033,7 +16306,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_44a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -16253,6 +16527,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_44e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -16378,6 +16653,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_44fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -16404,6 +16680,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_44fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -16674,6 +16951,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4660_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -16867,7 +17145,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_46a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -17060,6 +17339,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_46e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -17180,6 +17460,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_46fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -17205,6 +17486,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_46fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -17503,6 +17785,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4850_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 4 * CYCLE_UNIT / 2; } @@ -17526,6 +17809,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4868_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -17549,6 +17833,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4870_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -17571,6 +17856,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4878_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -17594,6 +17880,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4879_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (8); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 12 * CYCLE_UNIT / 2; } @@ -17617,6 +17904,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_487a_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 8 * CYCLE_UNIT / 2; } @@ -17641,6 +17929,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_487b_11)(uae_u32 opcode) dsta = m68k_areg (regs, 7) - 4; if (dsta & 1) { m68k_incpci (6); + m68k_areg (regs, 7) = dsta; exception3_write(opcode, dsta); return 10 * CYCLE_UNIT / 2; } @@ -18313,6 +18602,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4a60_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -18490,7 +18780,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4aa0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -19363,15 +19654,16 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e50_11)(uae_u32 opcode) { int count_cycles = 0; uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; if (olda & 1) { m68k_incpci (4); + m68k_areg (regs, 7) = olda; exception3_write(opcode, olda); return 4 * CYCLE_UNIT / 2; } { m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s16 offs = get_word_000_prefetch (4); put_word_000 (olda, src >> 16); put_word_000 (olda + 2, src); m68k_areg (regs, srcreg) = (m68k_areg (regs, 7)); @@ -19389,16 +19681,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e58_11)(uae_u32 opcode) int count_cycles = 0; uae_u32 srcreg = (opcode & 7); {{ uae_s32 src = m68k_areg (regs, srcreg); - m68k_areg (regs, 7) = src; -{ uaecptr olda; - olda = m68k_areg (regs, 7); +{ uae_u32 olda = src; if (olda & 1) { m68k_incpci (2); exception3_read(opcode, olda); return 4 * CYCLE_UNIT / 2; } {{ uae_s32 old = get_word_000 (olda) << 16; old |= get_word_000 (olda + 2); - m68k_areg (regs, 7) += 4; + m68k_areg (regs, 7) = src + 4; regs.ir = regs.irc; get_word_000_prefetch (4); m68k_areg (regs, srcreg) = (old); @@ -19491,7 +19781,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_11)(uae_u32 opcode) newsr = sr; newpc = pc; if (frame == 0x0) { m68k_areg (regs, 7) += offset; break; } else if (frame == 0x8) { m68k_areg (regs, 7) += offset + 50; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR(); } @@ -19541,6 +19831,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e75_11)(uae_u32 opcode) { int count_cycles = 0; { uaecptr pc = m68k_getpci (); + if (m68k_areg(regs, 7) & 1) { + exception3_read(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } m68k_do_rtsi (); if (m68k_getpci () & 1) { uaecptr faultpc = m68k_getpci (); @@ -19657,9 +19951,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e90_11)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19680,9 +19978,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ea8_11)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 6 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19704,9 +20006,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb0_11)(uae_u32 opcode) return 4 * CYCLE_UNIT / 2; } nextpc += 2; + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19726,9 +20032,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb8_11)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 6 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19749,9 +20059,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb9_11)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 8 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19772,9 +20086,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eba_11)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 6 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -19797,9 +20115,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ebb_11)(uae_u32 opcode) return 4 * CYCLE_UNIT / 2; } nextpc += 2; + m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } m68k_setpci_j(srca); get_word_000_prefetch (0); - m68k_areg (regs, 7) -= 4; put_word_000 (m68k_areg (regs, 7), nextpc >> 16); put_word_000 (m68k_areg (regs, 7) + 2, nextpc); regs.ir = regs.irc; @@ -20274,6 +20596,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_5060_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -20540,7 +20863,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_50a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -21187,6 +21511,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_5160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -21453,7 +21778,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_51a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -24092,6 +24418,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6100_11)(uae_u32 opcode) exception3b (opcode, m68k_getpci () + s, 0, 1, m68k_getpci () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpci () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsri (m68k_getpci () + 4, s); get_word_000_prefetch (0); regs.ir = regs.irc; @@ -24112,6 +24443,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6101_11)(uae_u32 opcode) exception3b (opcode, m68k_getpci () + s, 0, 1, m68k_getpci () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpci () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsri (m68k_getpci () + 2, s); get_word_000_prefetch (0); regs.ir = regs.irc; @@ -24131,6 +24467,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_61ff_11)(uae_u32 opcode) exception3b (opcode, m68k_getpci () + s, 0, 1, m68k_getpci () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpci () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsri (m68k_getpci () + 2, s); get_word_000_prefetch (0); regs.ir = regs.irc; @@ -25366,6 +25707,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -25501,6 +25843,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_807a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -25529,6 +25872,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_807b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -25649,7 +25993,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_80a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -25785,6 +26130,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -25813,6 +26159,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -25861,6 +26208,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80c0_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -25902,6 +26250,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d0_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -25944,6 +26293,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d8_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -25978,6 +26328,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -25986,6 +26337,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e0_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -26027,6 +26379,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e8_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -26068,6 +26421,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f0_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -26108,6 +26462,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f8_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -26149,6 +26504,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f9_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -26183,6 +26539,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -26190,6 +26547,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fa_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -26225,6 +26583,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -26232,6 +26591,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fb_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -26265,6 +26625,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fc_11)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpci (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -26572,6 +26933,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -26761,7 +27123,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_81a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -26895,6 +27258,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81c0_11)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -26940,6 +27304,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d0_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -26986,6 +27351,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d8_11)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -27025,6 +27391,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -27032,6 +27399,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e0_11)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -27077,6 +27445,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e8_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -27122,6 +27491,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f0_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -27166,6 +27536,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f8_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -27211,6 +27582,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f9_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -27250,12 +27622,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -27296,12 +27670,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } {{ uae_s16 src = get_word_000 (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -27339,6 +27715,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fc_11)(uae_u32 opcode) {{ uae_s16 src = get_word_000_prefetch (4); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpci (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -27787,6 +28164,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_9060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -27947,6 +28325,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_907a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -27980,6 +28359,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_907b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -28150,7 +28530,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_90a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -28311,6 +28692,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_90ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -28344,6 +28726,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_90bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -28485,6 +28868,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_90e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -28605,6 +28989,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_90fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -28630,6 +29015,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_90fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -28940,6 +29326,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_9148_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { + m68k_areg (regs, srcreg) = srca; m68k_incpci (2); exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; @@ -28949,6 +29336,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_9148_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { + m68k_areg (regs, dstreg) = dsta; m68k_incpci (2); exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; @@ -29048,6 +29436,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_9160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -29340,7 +29729,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_91a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -29582,7 +29972,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_91e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -29703,6 +30094,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_91fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -29728,6 +30120,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_91fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -30149,6 +30542,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -30299,6 +30693,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b07a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -30330,6 +30725,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b07b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -30488,7 +30884,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -30642,6 +31039,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -30673,6 +31071,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -30834,6 +31233,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -30984,6 +31384,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -31015,6 +31416,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b0fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -31386,6 +31788,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -31634,7 +32037,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_b1a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -31875,7 +32279,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_b1e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -32026,6 +32431,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b1fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -32057,6 +32463,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_b1fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -32425,6 +32832,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -32560,6 +32968,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c07a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -32588,6 +32997,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c07b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -32708,7 +33118,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -32844,6 +33255,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -32872,6 +33284,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -32998,6 +33411,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -33138,6 +33552,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -33167,6 +33582,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c0fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -33524,6 +33940,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -33730,7 +34147,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_c1a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -33943,6 +34361,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c1e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -34083,6 +34502,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c1fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -34112,6 +34532,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c1fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -34569,6 +34990,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d060_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -34729,6 +35151,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d07a_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -34762,6 +35185,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d07b_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -34932,7 +35356,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0a0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -35093,6 +35518,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0ba_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -35126,6 +35552,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0bb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -35267,6 +35694,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0e0_11)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -35387,6 +35815,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -35412,6 +35841,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d0fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -35722,6 +36152,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d148_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { + m68k_areg (regs, srcreg) = srca; m68k_incpci (2); exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; @@ -35731,6 +36162,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d148_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { + m68k_areg (regs, dstreg) = dsta; m68k_incpci (2); exception3_read(opcode, dsta); return 10 * CYCLE_UNIT / 2; @@ -35830,6 +36262,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d160_11)(uae_u32 opcode) dsta = m68k_areg (regs, dstreg) - 2; if (dsta & 1) { m68k_incpci (4); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -36122,7 +36555,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_d1a0_11)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; if (dsta & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, dstreg) = dsta; exception3_read(opcode, dsta); return 6 * CYCLE_UNIT / 2; } @@ -36364,7 +36798,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_d1e0_11)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -36485,6 +36920,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d1fa_11)(uae_u32 opcode) srca += (uae_s32)(uae_s16)get_word_000_prefetch (4); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 8 * CYCLE_UNIT / 2; } @@ -36510,6 +36946,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_d1fb_11)(uae_u32 opcode) srca = get_disp_ea_000 (tmppc, get_word_000_prefetch (4)); if (srca & 1) { m68k_incpci (2); + opcode |= 0x01020000; exception3_read(opcode, srca); return 10 * CYCLE_UNIT / 2; } @@ -36558,7 +36995,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -36566,7 +37003,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -36694,7 +37131,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -36702,7 +37139,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -36834,7 +37271,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -36842,7 +37279,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -36973,7 +37410,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -36981,7 +37418,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -37112,7 +37549,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -37120,7 +37557,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -37248,7 +37685,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_11)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -37256,7 +37693,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_11)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -37440,6 +37877,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -38477,6 +38915,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e1e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -38696,6 +39135,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e2e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -38900,6 +39340,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e3e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -39106,6 +39547,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e4e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -39317,6 +39759,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e5e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -39526,6 +39969,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e6e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -39730,6 +40174,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e7e0_11)(uae_u32 opcode) dataa = m68k_areg (regs, srcreg) - 2; if (dataa & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = dataa; exception3_read(opcode, dataa); return 6 * CYCLE_UNIT / 2; } @@ -39955,6 +40400,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_40e0_12)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_write(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -40282,6 +40728,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4260_12)(uae_u32 opcode) srca = m68k_areg (regs, srcreg) - 2; if (srca & 1) { m68k_incpci (4); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } @@ -40467,7 +40914,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_42a0_12)(uae_u32 opcode) {{ uaecptr srca; srca = m68k_areg (regs, srcreg) - 4; if (srca & 1) { - m68k_incpci (4); + m68k_incpci (2); + m68k_areg (regs, srcreg) = srca; exception3_read(opcode, srca); return 6 * CYCLE_UNIT / 2; } diff --git a/src/cpuemu_4.cpp b/src/cpuemu_4.cpp index 2aec191b..bcab3e47 100644 --- a/src/cpuemu_4.cpp +++ b/src/cpuemu_4.cpp @@ -10350,16 +10350,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4180_4)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 10 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10374,16 +10375,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4190_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10399,16 +10401,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4198_4)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10424,16 +10427,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_4)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 16 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10448,16 +10452,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a8_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10472,16 +10477,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b0_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 20 * CYCLE_UNIT / 2; } /* 4 4,0 */ @@ -10495,16 +10501,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b8_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10518,16 +10525,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b9_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 22 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 22 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -10542,16 +10550,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41ba_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10567,16 +10576,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bb_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 20 * CYCLE_UNIT / 2; } /* 4 4,0 */ @@ -10588,16 +10598,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bc_4)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -14020,10 +14031,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e40_4)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e50_4)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s16 offs = get_diword (2); put_long (olda, src); m68k_areg (regs, srcreg) = (m68k_areg (regs, 7)); @@ -14038,11 +14049,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e58_4)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); {{ uae_s32 src = m68k_areg (regs, srcreg); - m68k_areg (regs, 7) = src; -{ uaecptr olda; - olda = m68k_areg (regs, 7); +{ uae_u32 olda = src; { uae_s32 old = get_long (olda); - m68k_areg (regs, 7) += 4; + m68k_areg (regs, 7) = src + 4; m68k_areg (regs, srcreg) = (old); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -14118,10 +14127,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_4)(uae_u32 opcode) int offset = 8; newsr = sr; newpc = pc; if (frame == 0x0) { m68k_areg (regs, 7) += offset; break; } - else if (frame == 0x1) { m68k_areg (regs, 7) += offset; } - else if (frame == 0x2) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x8) { m68k_areg (regs, 7) += offset + 50; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -14158,6 +14165,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e74_4)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e75_4)(uae_u32 opcode) { { uaecptr pc = m68k_getpc (); + if (m68k_areg(regs, 7) & 1) { + exception3_read(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } m68k_do_rts (); if (m68k_getpc () & 1) { uaecptr faultpc = m68k_getpc (); @@ -14247,8 +14258,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e90_4)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 16 * CYCLE_UNIT / 2; } @@ -14265,8 +14280,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ea8_4)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14283,8 +14302,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb0_4)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 14 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 22 * CYCLE_UNIT / 2; } @@ -14300,8 +14323,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb8_4)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14317,8 +14344,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb9_4)(uae_u32 opcode) exception3i (opcode, srca); return 12 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 12 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 20 * CYCLE_UNIT / 2; } @@ -14335,8 +14366,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eba_4)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14354,8 +14389,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ebb_4)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 14 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long (m68k_areg (regs, 7), nextpc); }}}return 22 * CYCLE_UNIT / 2; } @@ -17817,6 +17856,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6100_4)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 8 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 8 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 4, s); }}return 18 * CYCLE_UNIT / 2; } @@ -17833,6 +17877,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6101_4)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 2, s); }}return 18 * CYCLE_UNIT / 2; } @@ -17848,6 +17897,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_61ff_4)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 2, s); }return 18 * CYCLE_UNIT / 2; } @@ -19155,6 +19209,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80c0_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -19189,6 +19244,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d0_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19224,6 +19280,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d8_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19259,6 +19316,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e0_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -19293,6 +19351,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e8_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19327,6 +19386,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f0_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -19360,6 +19420,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f8_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19393,6 +19454,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f9_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -19427,6 +19489,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fa_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19462,6 +19525,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fb_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -19493,6 +19557,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fc_4)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19979,6 +20044,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81c0_4)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -20017,6 +20083,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d0_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -20056,6 +20123,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d8_4)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -20095,6 +20163,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e0_4)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -20133,6 +20202,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e8_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20171,6 +20241,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f0_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -20208,6 +20279,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f8_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20245,6 +20317,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f9_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -20283,6 +20356,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fa_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20322,6 +20396,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fb_4)(uae_u32 opcode) { uae_s16 src = get_word (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -20357,6 +20432,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fc_4)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -27474,7 +27550,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -27482,7 +27558,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -27602,7 +27678,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -27610,7 +27686,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -27734,7 +27810,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -27742,7 +27818,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -27865,7 +27941,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -27873,7 +27949,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -27996,7 +28072,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -28004,7 +28080,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -28124,7 +28200,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_4)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -28132,7 +28208,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_4)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); diff --git a/src/cpuemu_40.cpp b/src/cpuemu_40.cpp index 0911c143..3ecdbc11 100644 --- a/src/cpuemu_40.cpp +++ b/src/cpuemu_40.cpp @@ -490,11 +490,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00d0_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -511,11 +514,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00e8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -533,11 +539,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f0_40)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -552,11 +561,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -572,11 +584,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00f9_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -594,11 +609,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00fa_40)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -618,11 +636,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_00fb_40)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s8)get_byte_jit (dsta); upper = (uae_s32)(uae_s8)get_byte_jit (dsta + 1); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 0 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1758,11 +1779,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02d0_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1779,11 +1803,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02e8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1801,11 +1828,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f0_40)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -1820,11 +1850,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1840,11 +1873,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02f9_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -1862,11 +1898,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02fa_40)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -1886,11 +1925,14 @@ uae_u32 REGPARAM2 CPUFUNC(op_02fb_40)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = (uae_s32)(uae_s16)get_word_jit (dsta); upper = (uae_s32)(uae_s16)get_word_jit (dsta + 2); if ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg; - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 1 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2460,10 +2502,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04d0_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2480,10 +2525,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04e8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2501,10 +2549,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f0_40)(uae_u32 opcode) { uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -2519,10 +2570,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f8_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2538,10 +2592,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04f9_40)(uae_u32 opcode) {{ uae_s16 extra = get_diword (2); { uaecptr dsta; dsta = get_dilong (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } @@ -2559,10 +2616,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04fa_40)(uae_u32 opcode) { uaecptr dsta; dsta = m68k_getpc () + 4; dsta += (uae_s32)(uae_s16)get_diword (4); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } @@ -2582,10 +2642,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_04fb_40)(uae_u32 opcode) m68k_incpc (4); { tmppc = m68k_getpc (); dsta = get_disp_ea_020 (tmppc, 0); - {uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; + {uae_u32 upper,lower,reg = regs.regs[(extra >> 12) & 15]; lower = get_long_jit (dsta); upper = get_long_jit (dsta + 4); - SET_ZFLG (upper == reg || lower == reg); - SET_CFLG_ALWAYS (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower); + setchk2undefinedflags(lower, upper, reg, (extra & 0x8000) ? 2 : 2); + upper -= lower; + reg -= lower; + SET_ZFLG (upper == reg || 0 == reg); + SET_CFLG_ALWAYS (reg > upper); if ((extra & 0x800) && GET_CFLG ()) { Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } @@ -5330,9 +5393,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e10_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5355,10 +5418,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e18_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += areg_byteinc[dstreg]; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5382,10 +5445,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e20_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - areg_byteinc[dstreg]; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5409,9 +5472,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e28_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5434,10 +5497,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e30_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5458,9 +5521,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e38_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5482,9 +5545,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e39_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_byte_jit (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -5507,9 +5570,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e50_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5532,10 +5595,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e58_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += 2; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5559,10 +5622,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e60_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 2; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5586,9 +5649,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e68_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5611,10 +5674,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e70_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5635,9 +5698,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e78_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5659,9 +5722,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e79_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_word_jit (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -5684,9 +5747,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e90_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5709,10 +5772,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0e98_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg); m68k_areg (regs, dstreg) += 4; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5736,10 +5799,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0ea0_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) - 4; m68k_areg (regs, dstreg) = dsta; + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (4); }}else{{ uaecptr srca; @@ -5763,9 +5826,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0ea8_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = m68k_areg (regs, dstreg) + (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5788,10 +5851,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb0_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; m68k_incpc (4); { dsta = get_disp_ea_020 (m68k_areg (regs, dstreg), 0); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); }}}else{{ uaecptr srca; m68k_incpc (4); @@ -5812,9 +5875,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb8_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = (uae_s32)(uae_s16)get_diword (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (6); }}else{{ uaecptr srca; @@ -5836,9 +5899,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_0eb9_40)(uae_u32 opcode) {if (!regs.s) { Exception (8); return 4 * CYCLE_UNIT / 2; } {{ uae_s16 extra = get_diword (2); if (extra & 0x800) -{ uae_u32 src = regs.regs[(extra >> 12) & 15]; -{ uaecptr dsta; +{{ uaecptr dsta; dsta = get_dilong (4); + uae_u32 src = regs.regs[(extra >> 12) & 15]; put_long_jit (dsta,src); m68k_incpc (8); }}else{{ uaecptr srca; @@ -12216,16 +12279,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4100_40)(uae_u32 opcode) {{ uae_s32 src = m68k_dreg (regs, srcreg); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 6 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}return 8 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12240,16 +12304,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4110_40)(uae_u32 opcode) { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12265,16 +12330,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4118_40)(uae_u32 opcode) m68k_areg (regs, srcreg) += 4; { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12290,16 +12356,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4120_40)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 13 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12314,16 +12381,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4128_40)(uae_u32 opcode) { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12338,16 +12406,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4130_40)(uae_u32 opcode) { srca = get_disp_ea_020 (m68k_areg (regs, srcreg), 0); { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12361,16 +12430,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4138_40)(uae_u32 opcode) { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12384,16 +12454,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4139_40)(uae_u32 opcode) { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 15 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 15 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12408,16 +12479,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413a_40)(uae_u32 opcode) { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12433,16 +12505,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413b_40)(uae_u32 opcode) srca = get_disp_ea_020 (tmppc, 0); { uae_s32 src = get_long_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12455,16 +12528,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_413c_40)(uae_u32 opcode) src = get_dilong (2); { uae_s32 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 2); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 2); }}}return 13 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12477,16 +12551,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4180_40)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 6 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 8 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12501,16 +12576,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4190_40)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12526,16 +12602,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4198_40)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 12 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12551,16 +12628,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_40)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 13 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -12575,16 +12653,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a8_40)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12599,16 +12678,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b0_40)(uae_u32 opcode) { srca = get_disp_ea_020 (m68k_areg (regs, srcreg), 0); { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12622,16 +12702,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b8_40)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12645,16 +12726,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b9_40)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 13 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 15 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 15 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -12669,16 +12751,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41ba_40)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -12694,16 +12777,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bb_40)(uae_u32 opcode) srca = get_disp_ea_020 (tmppc, 0); { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}}return 16 * CYCLE_UNIT / 2; } /* 2 2,0 */ @@ -12715,16 +12799,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bc_40)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 9 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 11 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 11 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -14562,10 +14647,10 @@ return 6 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_4808_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s32 offs; offs = get_dilong (2); put_long_jit (olda,src); @@ -16704,10 +16789,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e40_40)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e50_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s16 offs = get_diword (2); put_long_jit (olda,src); m68k_areg (regs, srcreg) = (m68k_areg(regs, 7)); @@ -16722,11 +16807,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e58_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); {{ uae_s32 src = m68k_areg (regs, srcreg); - m68k_areg (regs, 7) = src; -{ uaecptr olda; - olda = m68k_areg (regs, 7); +{ uae_u32 olda = src; { uae_s32 old = get_long_jit (olda); - m68k_areg (regs, 7) += 4; + m68k_areg (regs, 7) = src + 4; m68k_areg (regs, srcreg) = (old); }}}} m68k_incpc (2); return 7 * CYCLE_UNIT / 2; @@ -16811,7 +16894,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_40)(uae_u32 opcode) else if (frame == 0x3) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x4) { m68k_areg (regs, 7) += offset + 8; break; } else if (frame == 0x7) { m68k_areg (regs, 7) += offset + 52; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -16940,8 +17023,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e90_40)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -16958,8 +17041,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ea8_40)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 15 * CYCLE_UNIT / 2; } @@ -16977,8 +17060,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb0_40)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}}return 17 * CYCLE_UNIT / 2; } @@ -16994,8 +17077,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb8_40)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -17011,8 +17094,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb9_40)(uae_u32 opcode) exception3i (opcode, srca); return 12 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 13 * CYCLE_UNIT / 2; } @@ -17029,8 +17112,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eba_40)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 15 * CYCLE_UNIT / 2; } @@ -17049,8 +17132,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ebb_40)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}}return 17 * CYCLE_UNIT / 2; } @@ -22953,10 +23036,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_8148_40)(uae_u32 opcode) uae_u32 srcreg = (opcode & 7); uae_u32 dstreg = (opcode >> 9) & 7; { uae_u16 val; - m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; - val = (uae_u16)(get_byte_jit (m68k_areg (regs, srcreg)) & 0xff); - m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; - val = val | ((uae_u16)(get_byte_jit (m68k_areg (regs, srcreg)) & 0xff) << 8); + m68k_areg (regs, srcreg) -= 2; + val = (uae_u16)(get_word_jit (m68k_areg (regs, srcreg))); val += get_diword (2); m68k_areg (regs, dstreg) -= areg_byteinc[dstreg]; put_byte_jit (m68k_areg (regs, dstreg),((val >> 4) & 0xf0) | (val & 0xf)); @@ -23121,9 +23202,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_8188_40)(uae_u32 opcode) m68k_areg (regs, srcreg) -= areg_byteinc[srcreg]; val = (uae_u16)(get_byte_jit (m68k_areg (regs, srcreg)) & 0xff); val = (((val << 4) & 0xf00) | (val & 0xf)) + get_diword (2); - m68k_areg (regs, dstreg) -= 2 * areg_byteinc[dstreg]; - put_byte_jit (m68k_areg (regs, dstreg) + areg_byteinc[dstreg], val); - put_byte_jit (m68k_areg (regs, dstreg), val >> 8); + m68k_areg (regs, dstreg) -= 2; + put_word_jit (m68k_areg (regs, dstreg), val); } m68k_incpc (4); return 13 * CYCLE_UNIT / 2; } @@ -30705,7 +30785,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -30713,7 +30793,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -30821,7 +30901,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -30829,7 +30909,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -30941,7 +31021,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -30949,7 +31029,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -31060,7 +31140,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -31068,7 +31148,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -31179,7 +31259,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -31187,7 +31267,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -31295,7 +31375,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_40)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -31303,7 +31383,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_40)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -35627,13 +35707,13 @@ uae_u32 REGPARAM2 CPUFUNC(op_f5c8_40)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_f600_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = m68k_areg (regs, srcreg); { uaecptr memda; memda = get_dilong (2); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long_jit (memsa); v[1] = get_long_jit (memsa + 4); v[2] = get_long_jit (memsa + 8); @@ -35651,13 +35731,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f608_40)(uae_u32 opcode) { uae_u32 dstreg = opcode & 7; -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = get_dilong (2); { uaecptr memda; memda = m68k_areg (regs, dstreg); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long_jit (memsa); v[1] = get_long_jit (memsa + 4); v[2] = get_long_jit (memsa + 8); @@ -35675,13 +35755,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f610_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = m68k_areg (regs, srcreg); { uaecptr memda; memda = get_dilong (2); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long_jit (memsa); v[1] = get_long_jit (memsa + 4); v[2] = get_long_jit (memsa + 8); @@ -35698,13 +35778,13 @@ return 12 * CYCLE_UNIT / 2; uae_u32 REGPARAM2 CPUFUNC(op_f618_40)(uae_u32 opcode) { uae_u32 dstreg = opcode & 7; -{ uae_u32 v[4]; -{ uaecptr memsa; +{{ uaecptr memsa; memsa = get_dilong (2); { uaecptr memda; memda = m68k_areg (regs, dstreg); memsa &= ~15; memda &= ~15; + uae_u32 v[4]; v[0] = get_long_jit (memsa); v[1] = get_long_jit (memsa + 4); v[2] = get_long_jit (memsa + 8); @@ -35722,10 +35802,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_f620_40)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); uae_u32 dstreg = 0; -{ uae_u32 v[4]; - uaecptr mems = m68k_areg (regs, srcreg) & ~15, memd; +{ uaecptr mems = m68k_areg (regs, srcreg) & ~15, memd; dstreg = (get_diword (2) >> 12) & 7; memd = m68k_areg (regs, dstreg) & ~15; + uae_u32 v[4]; v[0] = get_long_jit (mems); v[1] = get_long_jit (mems + 4); v[2] = get_long_jit (mems + 8); @@ -35818,7 +35898,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_41)(uae_u32 opcode) else if (frame == 0x3) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x4) { m68k_areg (regs, 7) += offset + 8; break; } else if (frame == 0x7) { m68k_areg (regs, 7) += offset + 52; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -35887,6 +35967,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4800_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, srcreg) = (m68k_dreg (regs, srcreg) & ~0xff) | ((newv) & 0xff); }}} m68k_incpc (2); return 6 * CYCLE_UNIT / 2; @@ -35913,6 +35994,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4810_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -35940,6 +36022,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4818_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -35967,6 +36050,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4820_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (2); return 13 * CYCLE_UNIT / 2; @@ -35993,6 +36077,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4828_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (4); return 13 * CYCLE_UNIT / 2; @@ -36020,6 +36105,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4830_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}}}return 15 * CYCLE_UNIT / 2; } @@ -36044,6 +36130,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4838_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (4); return 12 * CYCLE_UNIT / 2; @@ -36069,6 +36156,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4839_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (srca,newv); }}}} m68k_incpc (6); return 12 * CYCLE_UNIT / 2; @@ -36108,7 +36196,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_42)(uae_u32 opcode) else if (frame == 0x9) { m68k_areg (regs, 7) += offset + 12; break; } else if (frame == 0xa) { m68k_areg (regs, 7) += offset + 24; break; } else if (frame == 0xb) { m68k_areg (regs, 7) += offset + 84; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -36147,6 +36235,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8100_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, dstreg) = (m68k_dreg (regs, dstreg) & ~0xff) | ((newv) & 0xff); }}}} m68k_incpc (2); return 4 * CYCLE_UNIT / 2; @@ -36177,6 +36266,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_8108_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (dsta,newv); }}}}}} m68k_incpc (2); return 16 * CYCLE_UNIT / 2; @@ -36205,6 +36295,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c100_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); m68k_dreg (regs, dstreg) = (m68k_dreg (regs, dstreg) & ~0xff) | ((newv) & 0xff); }}}} m68k_incpc (2); return 4 * CYCLE_UNIT / 2; @@ -36236,6 +36327,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_c108_42)(uae_u32 opcode) COPY_CARRY (); SET_ZFLG (GET_ZFLG () & (((uae_s8)(newv)) == 0)); SET_NFLG (((uae_s8)(newv)) < 0); + SET_VFLG(0); put_byte_jit (dsta,newv); }}}}}} m68k_incpc (2); return 16 * CYCLE_UNIT / 2; @@ -36302,7 +36394,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_43)(uae_u32 opcode) else if (frame == 0x9) { m68k_areg (regs, 7) += offset + 12; break; } else if (frame == 0xa) { m68k_areg (regs, 7) += offset + 24; break; } else if (frame == 0xb) { m68k_areg (regs, 7) += offset + 84; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } diff --git a/src/cpuemu_44.cpp b/src/cpuemu_44.cpp index ec233c57..8ec5e3fd 100644 --- a/src/cpuemu_44.cpp +++ b/src/cpuemu_44.cpp @@ -10350,16 +10350,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4180_44)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 8 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 10 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 10 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10374,16 +10375,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4190_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10399,16 +10401,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_4198_44)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 14 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10424,16 +10427,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a0_44)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (2); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 16 * CYCLE_UNIT / 2; } /* 2 0,0 */ @@ -10448,16 +10452,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41a8_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10472,16 +10477,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b0_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 20 * CYCLE_UNIT / 2; } /* 4 4,0 */ @@ -10495,16 +10501,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b8_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10518,16 +10525,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41b9_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (6); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 22 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 22 * CYCLE_UNIT / 2; } /* 6 0,0 */ @@ -10542,16 +10550,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41ba_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 16 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 18 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -10567,16 +10576,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bb_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 18 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 20 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}}return 20 * CYCLE_UNIT / 2; } /* 4 4,0 */ @@ -10588,16 +10598,17 @@ uae_u32 REGPARAM2 CPUFUNC(op_41bc_44)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s16 dst = m68k_dreg (regs, dstreg); m68k_incpc (4); - if (dst > src) { - SET_NFLG (0); + if ((uae_s32)dst < 0) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 12 * CYCLE_UNIT / 2; } - if ((uae_s32)dst < 0) { - SET_NFLG (1); + if (dst > src) { + setchkundefinedflags(src, dst, 1); Exception_cpu(6); return 14 * CYCLE_UNIT / 2; } + setchkundefinedflags(src, dst, 1); }}}return 14 * CYCLE_UNIT / 2; } /* 4 0,0 */ @@ -14020,10 +14031,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e40_44)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e50_44)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); -{{ uaecptr olda; +{{ uae_s32 src = m68k_areg (regs, srcreg); +{ uaecptr olda; olda = m68k_areg (regs, 7) - 4; m68k_areg (regs, 7) = olda; -{ uae_s32 src = m68k_areg (regs, srcreg); { uae_s16 offs = get_diword (2); put_long_jit (olda, src); m68k_areg (regs, srcreg) = (m68k_areg (regs, 7)); @@ -14038,11 +14049,9 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e58_44)(uae_u32 opcode) { uae_u32 srcreg = (opcode & 7); {{ uae_s32 src = m68k_areg (regs, srcreg); - m68k_areg (regs, 7) = src; -{ uaecptr olda; - olda = m68k_areg (regs, 7); +{ uae_u32 olda = src; { uae_s32 old = get_long_jit (olda); - m68k_areg (regs, 7) += 4; + m68k_areg (regs, 7) = src + 4; m68k_areg (regs, srcreg) = (old); }}}} m68k_incpc (2); return 12 * CYCLE_UNIT / 2; @@ -14118,10 +14127,8 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e73_44)(uae_u32 opcode) int offset = 8; newsr = sr; newpc = pc; if (frame == 0x0) { m68k_areg (regs, 7) += offset; break; } - else if (frame == 0x1) { m68k_areg (regs, 7) += offset; } - else if (frame == 0x2) { m68k_areg (regs, 7) += offset + 4; break; } else if (frame == 0x8) { m68k_areg (regs, 7) += offset + 50; break; } - else { m68k_areg (regs, 7) += offset; Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } + else { Exception_cpu(14); return 4 * CYCLE_UNIT / 2; } regs.sr = newsr; MakeFromSR_T0(); } @@ -14158,6 +14165,10 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e74_44)(uae_u32 opcode) uae_u32 REGPARAM2 CPUFUNC(op_4e75_44)(uae_u32 opcode) { { uaecptr pc = m68k_getpc (); + if (m68k_areg(regs, 7) & 1) { + exception3_read(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } m68k_do_rts (); if (m68k_getpc () & 1) { uaecptr faultpc = m68k_getpc (); @@ -14247,8 +14258,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4e90_44)(uae_u32 opcode) exception3i (opcode, srca); return 4 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 4 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 16 * CYCLE_UNIT / 2; } @@ -14265,8 +14280,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ea8_44)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14283,8 +14302,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb0_44)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 14 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 22 * CYCLE_UNIT / 2; } @@ -14300,8 +14323,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb8_44)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14317,8 +14344,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eb9_44)(uae_u32 opcode) exception3i (opcode, srca); return 12 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 12 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 20 * CYCLE_UNIT / 2; } @@ -14335,8 +14366,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4eba_44)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 10 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 18 * CYCLE_UNIT / 2; } @@ -14354,8 +14389,12 @@ uae_u32 REGPARAM2 CPUFUNC(op_4ebb_44)(uae_u32 opcode) exception3i (opcode, srca); return 8 * CYCLE_UNIT / 2; } - m68k_setpc_j(srca); m68k_areg (regs, 7) -= 4; + if (m68k_areg(regs, 7) & 1) { + exception3_write(opcode, m68k_areg(regs, 7)); + return 14 * CYCLE_UNIT / 2; + } + m68k_setpc_j(srca); put_long_jit (m68k_areg (regs, 7), nextpc); }}}return 22 * CYCLE_UNIT / 2; } @@ -17817,6 +17856,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6100_44)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 8 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 8 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 4, s); }}return 18 * CYCLE_UNIT / 2; } @@ -17833,6 +17877,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_6101_44)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 2, s); }}return 18 * CYCLE_UNIT / 2; } @@ -17848,6 +17897,11 @@ uae_u32 REGPARAM2 CPUFUNC(op_61ff_44)(uae_u32 opcode) exception3b (opcode, m68k_getpc () + s, 0, 1, m68k_getpc () + s); return 4 * CYCLE_UNIT / 2; } + if (m68k_areg(regs, 7) & 1) { + m68k_areg(regs, 7) -= 4; + exception3b(opcode, m68k_areg(regs, 7), true, false, m68k_getpc () + 2); + return 4 * CYCLE_UNIT / 2; + } m68k_do_bsr (m68k_getpc () + 2, s); }return 18 * CYCLE_UNIT / 2; } @@ -19155,6 +19209,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80c0_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -19189,6 +19244,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d0_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19224,6 +19280,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80d8_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19259,6 +19316,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e0_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -19293,6 +19351,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80e8_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19327,6 +19386,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f0_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -19360,6 +19420,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f8_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19393,6 +19454,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80f9_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -19427,6 +19489,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fa_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -19462,6 +19525,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fb_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -19493,6 +19557,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_80fc_44)(uae_u32 opcode) { uae_s32 dst = m68k_dreg (regs, dstreg); CLEAR_CZNV (); if (src == 0) { + divbyzero_special (0, dst); m68k_incpc (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -19979,6 +20044,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81c0_44)(uae_u32 opcode) {{ uae_s16 src = m68k_dreg (regs, srcreg); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 4 * CYCLE_UNIT / 2; @@ -20017,6 +20083,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d0_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -20056,6 +20123,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81d8_44)(uae_u32 opcode) m68k_areg (regs, srcreg) += 2; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -20095,6 +20163,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e0_44)(uae_u32 opcode) m68k_areg (regs, srcreg) = srca; { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (2); Exception_cpu(5); return 10 * CYCLE_UNIT / 2; @@ -20133,6 +20202,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81e8_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20171,6 +20241,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f0_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -20208,6 +20279,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f8_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20245,6 +20317,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81f9_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (6); Exception_cpu(5); return 16 * CYCLE_UNIT / 2; @@ -20283,6 +20356,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fa_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 12 * CYCLE_UNIT / 2; @@ -20322,6 +20396,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fb_44)(uae_u32 opcode) { uae_s16 src = get_word_jit (srca); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 14 * CYCLE_UNIT / 2; @@ -20357,6 +20432,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_81fc_44)(uae_u32 opcode) {{ uae_s16 src = get_diword (2); { uae_s32 dst = m68k_dreg (regs, dstreg); if (src == 0) { + divbyzero_special (1, dst); m68k_incpc (4); Exception_cpu(5); return 8 * CYCLE_UNIT / 2; @@ -27474,7 +27550,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -27482,7 +27558,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e000_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -27602,7 +27678,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 8) { - val = 0xff & (uae_u32)-sign; + val = 0xff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -27610,7 +27686,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e020_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xff << (8 - cnt)) & (uae_u32)-sign; + val |= (0xff << (8 - cnt)) & (uae_u32)(0-sign); val &= 0xff; } SET_ZFLG (((uae_s8)(val)) == 0); @@ -27734,7 +27810,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -27742,7 +27818,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e040_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -27865,7 +27941,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 16) { - val = 0xffff & (uae_u32)-sign; + val = 0xffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -27873,7 +27949,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e060_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffff << (16 - cnt)) & (uae_u32)-sign; + val |= (0xffff << (16 - cnt)) & (uae_u32)(0-sign); val &= 0xffff; } SET_ZFLG (((uae_s16)(val)) == 0); @@ -27996,7 +28072,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else { @@ -28004,7 +28080,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e080_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); @@ -28124,7 +28200,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_44)(uae_u32 opcode) cnt &= 63; CLEAR_CZNV (); if (cnt >= 32) { - val = 0xffffffff & (uae_u32)-sign; + val = 0xffffffff & (uae_u32)(0-sign); SET_CFLG (sign); COPY_CARRY (); } else if (cnt > 0) { @@ -28132,7 +28208,7 @@ uae_u32 REGPARAM2 CPUFUNC(op_e0a0_44)(uae_u32 opcode) SET_CFLG (val & 1); COPY_CARRY (); val >>= 1; - val |= (0xffffffff << (32 - cnt)) & (uae_u32)-sign; + val |= (0xffffffff << (32 - cnt)) & (uae_u32)(0-sign); val &= 0xffffffff; } SET_ZFLG (((uae_s32)(val)) == 0); diff --git a/src/custom.cpp b/src/custom.cpp index b1fdb07e..37087a27 100644 --- a/src/custom.cpp +++ b/src/custom.cpp @@ -7,19 +7,18 @@ * Copyright 1995 Alessandro Bissacco * Copyright 2000-2015 Toni Wilen */ -#include -#include -#include -#include -#include -#include +#include "sysconfig.h" #include "sysdeps.h" +#include +#include +#include + #include "options.h" #include "uae.h" #include "audio.h" -#include "include/memory.h" +#include "memory.h" #include "custom.h" #include "newcpu.h" #include "cia.h" @@ -57,7 +56,10 @@ extern int speedup_timelimit_nonjit_turbo; STATIC_INLINE bool nocustom (void) { - return picasso_on; + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on) + return true; + return false; } static void uae_abort (const TCHAR *format,...) @@ -127,30 +129,18 @@ static bool graphicsbuffer_retry; static int scanlinecount; static int cia_hsync; static bool toscr_scanline_complex_bplcon1; -static bool spr_width_64_seen; #define LOF_TOGGLES_NEEDED 3 //#define NLACE_CNT_NEEDED 50 static int lof_togglecnt_lace, lof_togglecnt_nlace; //, nlace_cnt; -/* Stupid genlock-detection prevention hack. -* We should stop calling vsync_handler() and -* hstop_handler() completely but it is not -* worth the trouble.. -*/ static int vpos_previous, hpos_previous; -static int vpos_lpen, hpos_lpen, lightpen_triggered; -int lightpen_x[2], lightpen_y[2]; -int lightpen_cx[2], lightpen_cy[2], lightpen_active, lightpen_enabled, lightpen_enabled2; static uae_u32 sprtaba[256],sprtabb[256]; static uae_u32 sprite_ab_merge[256]; /* Tables for collision detection. */ static uae_u32 sprclx[16], clxmask[16]; -/* T genlock bit in ECS Denise and AGA color registers */ -static uae_u8 color_regs_genlock[256]; - /* * Hardware registers of all sorts. */ @@ -188,6 +178,7 @@ bool programmedmode; int syncbase; static int fmode_saved, fmode; uae_u16 beamcon0, new_beamcon0; +static uae_u16 beamcon0_saved; static bool varsync_changed; uae_u16 vtotal = MAXVPOS_PAL, htotal = MAXHPOS_PAL; static int maxvpos_stored, maxhpos_stored; @@ -335,10 +326,10 @@ struct copper { /* When we schedule a copper event, knowing a few things about the future of the copper list can reduce the number of sync_with_cpu calls dramatically. */ - unsigned int first_sync; unsigned int regtypes_modified; #endif int strobe; /* COPJMP1 / COPJMP2 accessed */ + int last_strobe; int moveaddr, movedata, movedelay; }; @@ -366,8 +357,8 @@ static int copper_enabled_thisline; static int cop_min_waittime; /* - * Statistics - */ +* Statistics +*/ unsigned long int frametime = 0, lastframetime = 0, timeframes = 0; unsigned long hsync_counter = 0, vsync_counter = 0; unsigned long int idletime; @@ -455,8 +446,8 @@ enum fetchstate { } fetch_state; /* - * helper functions - */ +* helper functions +*/ STATIC_INLINE int ecsshres(void) { @@ -465,7 +456,8 @@ STATIC_INLINE int ecsshres(void) STATIC_INLINE int nodraw(void) { - return framecnt != 0; + struct amigadisplay *ad = &adisplays; + return ad->framecnt != 0; } static int doflickerfix (void) @@ -499,7 +491,7 @@ void set_speedup_values(void) } #endif -uae_u32 get_copper_address(int copno) +uae_u32 get_copper_address (int copno) { switch (copno) { case 1: return cop1lc; @@ -515,9 +507,9 @@ void reset_frame_rate_hack (void) return; rpt_did_reset = 1; - is_syncline = 0; - vsyncmintime = read_processor_time() + vsynctimebase; - write_log(_T("Resetting frame rate hack\n")); + events_reset_syncline(); + vsyncmintime = read_processor_time () + vsynctimebase; + write_log (_T("Resetting frame rate hack\n")); } STATIC_INLINE void setclr (uae_u16 *p, uae_u16 val) @@ -528,7 +520,7 @@ STATIC_INLINE void setclr (uae_u16 *p, uae_u16 val) *p &= ~val; } -static void set_chipset_mode(void) +STATIC_INLINE void set_chipset_mode(void) { if (currprefs.chipset_mask & CSMASK_AGA) { fmode = fmode_saved; @@ -541,6 +533,7 @@ static void set_chipset_mode(void) static void update_mirrors (void) { aga_mode = (currprefs.chipset_mask & CSMASK_AGA) != 0; + direct_rgb = aga_mode; if (currprefs.chipset_mask & CSMASK_AGA) sprite_sprctlmask = 0x01 | 0x08 | 0x10; else if (currprefs.chipset_mask & CSMASK_ECS_DENISE) @@ -552,10 +545,10 @@ static void update_mirrors (void) STATIC_INLINE uae_u8 *pfield_xlateptr (uaecptr plpt, int bytecount) { - plpt &= chipmem_bank.mask; - if ((plpt + bytecount) > chipmem_bank.allocated_size) - return NULL; - return chipmem_bank.baseaddr + plpt; + plpt &= chipmem_bank.mask; + if((plpt + bytecount) > chipmem_bank.reserved_size) + return NULL; + return chipmem_bank.baseaddr + plpt; } static void docols (struct color_entry *colentry) { @@ -655,8 +648,8 @@ STATIC_INLINE int get_equ_vblank_endline (void) #define HARD_DDF_START (HARD_DDF_LIMITS_DISABLED ? 0x04 : 0x14) /* Called to determine the state of the horizontal display window state - * machine at the current position. It might have changed since we last - * checked. */ +* machine at the current position. It might have changed since we last +* checked. */ static void decide_diw(int hpos) { /* Last hpos = hpos + 0.5, eg. normal PAL end hpos is 227.5 * 2 = 455 @@ -698,7 +691,7 @@ static int fetchmode_size_hr, fetchmode_mask_hr; static int real_bitplane_number[3][3][9]; /* Disable bitplane DMA if planes > available DMA slots. This is needed - e.g. by the Sanity WOC demo (at the "Party Effect"). */ +e.g. by the Sanity WOC demo (at the "Party Effect"). */ STATIC_INLINE int GET_PLANES_LIMIT(uae_u16 bc0) { int res = GET_RES_AGNUS(bc0); @@ -884,7 +877,6 @@ static void create_cycle_diagram_table(void) } } - /* Used by the copper. */ static int estimated_last_fetch_cycle; static int cycle_diagram_shift; @@ -944,15 +936,15 @@ static bool bplcon1_written; #define PLANE_RESET_HPOS 8 static int planesactiveatresetpoint; -/* The number of bits left from the last fetched words. - This is an optimization - conceptually, we have to make sure the result is - the same as if toscr is called in each clock cycle. However, to speed this - up, we accumulate display data; this variable keeps track of how much. - Thus, once we do call toscr_nbits (which happens at least every 16 bits), - we can do more work at once. */ +/* The number of bits left from the last fetched words. +This is an optimization - conceptually, we have to make sure the result is +the same as if toscr is called in each clock cycle. However, to speed this +up, we accumulate display data; this variable keeps track of how much. +Thus, once we do call toscr_nbits (which happens at least every 16 bits), +we can do more work at once. */ static int toscr_nbits; -static void record_color_change2(int hpos, int regno, uae_u32 value) +static void record_color_change2 (int hpos, int regno, uae_u32 value) { int pos = (hpos * 2) * 4; @@ -995,7 +987,8 @@ STATIC_INLINE int isocs7planes (void) return !(currprefs.chipset_mask & CSMASK_AGA) && bplcon0_res == 0 && bplcon0_planes == 7; } -int is_bitplane_dma (int hpos) + +STATIC_INLINE int is_bitplane_dma (int hpos) { if (hpos < bpl_hstart || fetch_state == fetch_not_started || plf_state == plf_wait) { if (bitplane_overrun && hpos < bitplane_overrun_hpos) { @@ -1009,21 +1002,7 @@ int is_bitplane_dma (int hpos) return curr_diagram[(hpos - cycle_diagram_shift) & fetchstart_mask]; } -STATIC_INLINE int is_bitplane_dma_inline (int hpos) -{ - if (hpos < bpl_hstart || fetch_state == fetch_not_started || plf_state == plf_wait) { - if (bitplane_overrun && hpos < bitplane_overrun_hpos) { - return curr_diagram[(hpos - bitplane_overrun_cycle_diagram_shift) & fetchstart_mask]; - } - return 0; - } - if ((plf_state >= plf_end && hpos >= thisline_decision.plfright) - || hpos >= estimated_last_fetch_cycle) - return 0; - return curr_diagram[(hpos - cycle_diagram_shift) & fetchstart_mask]; -} - -static int islinetoggle (void) +STATIC_INLINE int islinetoggle (void) { int linetoggle = 0; if (!(beamcon0 & 0x0800) && !(beamcon0 & 0x0020) && (currprefs.chipset_mask & CSMASK_ECS_AGNUS)) { @@ -1055,7 +1034,6 @@ static void compute_toscr_delay (int bplcon1) toscr_delay[1] |= shdelay2 >> (RES_MAX - toscr_res); } -#if SPEEDUP /* SPEEDUP code still needs this hack */ int delayoffset = fetchmode_size - (((bpl_hstart - (HARD_DDF_START_REAL + DDF_OFFSET)) & fetchstart_mask) << 1); delay1 += delayoffset; @@ -1064,7 +1042,6 @@ static void compute_toscr_delay (int bplcon1) toscr_delay_adjusted[0] |= shdelay1 >> (RES_MAX - toscr_res); toscr_delay_adjusted[1] = (delay2 & delaymask) << toscr_res; toscr_delay_adjusted[1] |= shdelay2 >> (RES_MAX - toscr_res); -#endif } static void set_delay_lastcycle (void) @@ -1152,10 +1129,6 @@ static void setup_fmodes (int hpos) curr_diagram = cycle_diagram_table[fetchmode][bplcon0_res][bplcon0_planes_limit]; estimate_last_fetch_cycle(hpos); -#ifdef DEBUGGER - if (bpldmasetuphpos >= 0 && debug_dma) - record_dma_event(DMA_EVENT_BPLFETCHUPDATE, hpos, vpos); -#endif bpldmasetuphpos = -1; bpldmasetupphase = 0; toscr_nr_planes_agnus = bplcon0_planes; @@ -1174,7 +1147,7 @@ static void BPLCON0_Denise (int hpos, uae_u16 v, bool); #define BPLCON_AGNUS_DELAY (3 + (copper_access ? 1 : 0) + (bplcon0_planes == 8 ? 1 : 0)) #define BPLCON_DENISE_DELAY (copper_access ? 1 : 0) -static void maybe_setup_fmodes (int hpos) +STATIC_INLINE void maybe_setup_fmodes (int hpos) { switch (bpldmasetupphase) { @@ -1511,7 +1484,7 @@ STATIC_INLINE void do_delays_3_ecs (int nbits) delay += fetchmode_size; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc (oddeven, 2, diff, 0); nbits2 -= diff; if (todisplay_fetched[oddeven]) { @@ -1533,7 +1506,7 @@ STATIC_INLINE void do_delays_fast_3_ecs (int nbits) delay += fetchmode_size; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc (0, 1, diff, 0); nbits2 -= diff; if (todisplay_fetched[0]) { @@ -1556,7 +1529,7 @@ STATIC_INLINE void do_delays_3_aga (int nbits, int fm) delay += fetchmode_size; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc (oddeven, 2, diff, fm); nbits2 -= diff; if (todisplay_fetched[oddeven]) { @@ -1578,7 +1551,7 @@ STATIC_INLINE void do_delays_fast_3_aga (int nbits, int fm) delay += fetchmode_size; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc (0, 1, diff, fm); nbits2 -= diff; if (todisplay_fetched[0]) { @@ -1602,7 +1575,7 @@ STATIC_INLINE void do_delays_3_aga_hr(int nbits, int fm) delay += fetchmode_size_hr; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc_hr(oddeven, 2, diff, fm); nbits2 -= diff; if (todisplay_fetched[oddeven]) { @@ -1625,7 +1598,7 @@ STATIC_INLINE void do_delays_fast_3_aga_hr(int nbits, int fm) delay += fetchmode_size_hr; int diff = delay - delaypos; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_tosrc_hr(0, 1, diff, fm); nbits2 -= diff; if (todisplay_fetched[0]) { @@ -1736,7 +1709,7 @@ static void toscr_right_edge (int nbits, int fm) // (Result is ugly shift in graphics in far right overscan) int diff = delay_lastcycle[lol] - delay_cycles; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { do_delays (diff, fm); nbits2 -= diff; delay_cycles = 0; @@ -1759,7 +1732,7 @@ static void toscr_right_edge_hr(int nbits, int fm) { int diff = delay_lastcycle[lol] - delay_cycles; int nbits2 = nbits; - if (nbits2 >= diff) { + if (nbits2 > diff) { if (toscr_scanline_complex_bplcon1) do_delays_hr(diff, fm); else @@ -1851,7 +1824,7 @@ static void toscr_1_hr(int nbits, int fm) } } -static void toscr_1_select(int nbits, int fm) +STATIC_INLINE void toscr_1_select(int nbits, int fm) { if (currprefs.chipset_hr) toscr_1_hr(nbits, fm); @@ -1988,7 +1961,7 @@ static int flush_plane_data_hr(int fm) return i >> (1 + toscr_res_hr); } -static int flush_plane_data(int fm) +STATIC_INLINE int flush_plane_data(int fm) { if (currprefs.chipset_hr) return flush_plane_data_hr(fm); @@ -2065,7 +2038,7 @@ static void update_denise_shifter_planes (int hpos) } } -static void update_denise_vars(void) +STATIC_INLINE void update_denise_vars(void) { int res = GET_RES_DENISE(bplcon0d); if (res == toscr_res_old) @@ -2118,9 +2091,9 @@ STATIC_INLINE void fetch_start (int hpos) } /* Called when all planes have been fetched, i.e. when a new block - of data is available to be displayed. The data in fetched[] is - moved into todisplay[]. */ -static void beginning_of_plane_block (int hpos, int fm) +of data is available to be displayed. The data in fetched[] is +moved into todisplay[]. */ +STATIC_INLINE void beginning_of_plane_block (int hpos, int fm) { int i; @@ -2142,8 +2115,6 @@ static void beginning_of_plane_block (int hpos, int fm) } -#if SPEEDUP - /* The usual inlining tricks - don't touch unless you know what you are doing. */ STATIC_INLINE void long_fetch_16 (int plane, int nwords, int weird_number_of_bits, int dma) { @@ -2194,15 +2165,8 @@ STATIC_INLINE void long_fetch_16 (int plane, int nwords, int weird_number_of_bit shiftbuffer <<= 16; nwords--; if (dma) { -#ifdef ARMV6_ASSEMBLY - __asm__( - "ldrh %[val], [%[pt]], #2 \n\t" - "rev16 %[val], %[val] \n\t" - : [val] "=r" (fetchval), [pt] "+r" (real_pt)); -#else fetchval = do_get_mem_word (real_pt); real_pt++; -#endif } } fetched[plane] = fetchval; @@ -2265,15 +2229,7 @@ STATIC_INLINE void long_fetch_32 (int plane, int nwords, int weird_number_of_bit } nwords -= 2; if (dma) { -#ifdef ARMV6_ASSEMBLY - __asm__( - "ldr %[val], [%[pt]], #4 \n\t" - "rev %[val], %[val] \n\t" - : [val] "=r" (fetchval), [pt] "+r" (real_pt)); -#else - fetchval = do_get_mem_long(real_pt); - real_pt++; -#endif + fetchval = do_get_mem_long (real_pt); if (unaligned) { fetchval &= 0x0000ffff; fetchval |= fetchval << 16; @@ -2281,7 +2237,7 @@ STATIC_INLINE void long_fetch_32 (int plane, int nwords, int weird_number_of_bit fetchval &= 0xffff0000; fetchval |= fetchval >> 16; } - + real_pt++; } } @@ -2324,8 +2280,6 @@ STATIC_INLINE void aga_shift_n (uae_u64 *p, int n) p[1] >>= n; } -#endif - STATIC_INLINE void long_fetch_64 (int plane, int nwords, int weird_number_of_bits, int dma) { uae_u32 *real_pt = (uae_u32 *)pfield_xlateptr (bplpt[plane] & ~7, nwords * 2); @@ -2879,7 +2833,7 @@ static void update_fetch_x (int until, int fm) flush_display (fm); } -static void update_fetch (int until, int fm) +STATIC_INLINE void update_fetch (int until, int fm) { int pos; int dma = dmaen (DMA_BITPLANE); @@ -2910,14 +2864,10 @@ static void update_fetch (int until, int fm) return; } -#if SPEEDUP /* Unrolled version of the for loop below. */ if (plf_state == plf_active && !line_cyclebased && dma && (fetch_cycle & fetchstart_mask) == (fm_maxplane & fetchstart_mask) && !badmode && !currprefs.chipset_hr -#ifdef DEBUGGER - && !debug_dma -#endif && toscr_nr_planes == toscr_nr_planes_agnus) { int ddfstop_to_test_ddf = HARD_DDF_STOP; @@ -2969,7 +2919,7 @@ static void update_fetch (int until, int fm) fetch_cycle += count; } } -#endif + for (; pos < until; pos++) { if (fetch_state == fetch_was_plane0) { @@ -2993,7 +2943,7 @@ static void update_fetch_0 (int hpos) { update_fetch (hpos, 0); } static void update_fetch_1 (int hpos) { update_fetch (hpos, 1); } static void update_fetch_2 (int hpos) { update_fetch (hpos, 2); } -static void decide_fetch (int hpos) +STATIC_INLINE void decide_fetch (int hpos) { if (hpos > last_fetch_hpos) { if (bitplane_overrun) { @@ -3276,6 +3226,7 @@ static void decide_line (int hpos) do_sprites (hpos); return; } + } if (ecs) { @@ -3636,13 +3587,13 @@ static void record_sprite_1 (int sprxp, uae_u16 *buf, uae_u32 datab, int num, in } /* DATAB contains the sprite data; 16 pixels in two-bit packets. Bits 0/1 - determine the color of the leftmost pixel, bits 2/3 the color of the next - etc. - This function assumes that for all sprites in a given line, SPRXP either - stays equal or increases between successive calls. +determine the color of the leftmost pixel, bits 2/3 the color of the next +etc. +This function assumes that for all sprites in a given line, SPRXP either +stays equal or increases between successive calls. - The data is recorded either in lores pixels (if OCS/ECS), or in hires or - superhires pixels (if AGA). */ +The data is recorded either in lores pixels (if OCS/ECS), or in hires or +superhires pixels (if AGA). */ static void record_sprite (int line, int num, int sprxp, uae_u16 *data, uae_u16 *datb, unsigned int ctl) { @@ -3719,8 +3670,8 @@ static void record_sprite (int line, int num, int sprxp, uae_u16 *data, uae_u16 e->has_attached = 1; } /* 64 pixel wide sprites' first 32 pixels work differently than - * last 32 pixels if FMODE is changed when sprite is being drawn - */ + * last 32 pixels if FMODE is changed when sprite is being drawn + */ if (spr_width == 64) { uae_u16 *stbfm = spixstate.stbfm + word_offs; uae_u16 state = (3 << (2 * num)); @@ -3735,7 +3686,6 @@ static void record_sprite (int line, int num, int sprxp, uae_u16 *data, uae_u16 stbfm[7] |= state; stbfm += 8; } - spr_width_64_seen = true; } } @@ -3901,11 +3851,11 @@ static void decide_sprites(int hpos, bool usepointx, bool quick) } #endif } -static void decide_sprites(int hpos) +STATIC_INLINE void decide_sprites(int hpos) { decide_sprites(hpos, false, false); } -static void maybe_decide_sprites(int spnr, int hpos) +STATIC_INLINE void maybe_decide_sprites(int spnr, int hpos) { struct sprite *s = &spr[spnr]; if (!s->armed) @@ -3961,8 +3911,9 @@ static int color_changes_differ (struct draw_info *dip, struct draw_info *dip_ol /* End of a horizontal scan line. Finish off all decisions that were not * made yet. */ -static void finish_decisions(void) +STATIC_INLINE void finish_decisions(void) { + struct amigadisplay *ad = &adisplays; struct draw_info *dip; struct draw_info *dip_old; struct decision *dp; @@ -4011,7 +3962,7 @@ static void finish_decisions(void) dip = curr_drawinfo + next_lineno; dip_old = prev_drawinfo + next_lineno; dp = line_decisions + next_lineno; - changed = thisline_changed | custom_frame_redraw_necessary; + changed = int(thisline_changed) | ad->custom_frame_redraw_necessary; if (thisline_decision.plfleft >= 0 && thisline_decision.nr_planes > 0) record_diw_line (thisline_decision.plfleft, diwfirstword, diwlastword); @@ -4218,7 +4169,15 @@ void compute_vsynctime (void) if (!fake_vblank_hz) fake_vblank_hz = vblank_hz; - vsynctimebase = int(syncbase / fake_vblank_hz); + if (currprefs.turbo_emulation) { + if (currprefs.turbo_emulation_limit > 0) { + vsynctimebase = (int)(syncbase / currprefs.turbo_emulation_limit); + } else { + vsynctimebase = 1; + } + } else { + vsynctimebase = (int)(syncbase / fake_vblank_hz); + } vsynctimebase_orig = vsynctimebase; if (islinetoggle ()) { @@ -4231,7 +4190,7 @@ void compute_vsynctime (void) } if (currprefs.produce_sound > 1) { double clk = svpos * shpos * fake_vblank_hz; - devices_update_sound(clk, syncadjust); + devices_update_sound(clk); } devices_update_sync(svpos, syncadjust); } @@ -4251,6 +4210,7 @@ int current_maxvpos (void) struct chipset_refresh *get_chipset_refresh(struct uae_prefs *p) { + struct amigadisplay *ad = &adisplays; int islace = interlace_seen ? 1 : 0; int isntsc = (beamcon0 & 0x20) ? 0 : 1; int custom = (beamcon0 & 0x80) ? 1 : 0; @@ -4270,7 +4230,7 @@ struct chipset_refresh *get_chipset_refresh(struct uae_prefs *p) (cr->lace < 0 || (cr->lace > 0 && islace) || (cr->lace == 0 && !islace)) && (cr->resolution == 0 || cr->resolution == 7) && (cr->framelength < 0 || (cr->framelength > 0 && lof_store) || (cr->framelength == 0 && !lof_store) || (cr->framelength >= 0 && islace)) && - ((cr->rtg && picasso_on) || (!cr->rtg && !picasso_on)) && + ((cr->rtg && ad->picasso_on) || (!cr->rtg && !ad->picasso_on)) && (cr->vsync < 0 || (cr->vsync > 0 && isvsync_chipset ()) || (cr->vsync == 0 && !isvsync_chipset ()))) return cr; } @@ -4287,6 +4247,7 @@ static bool changed_chipset_refresh (void) void compute_framesync(void) { + struct amigadisplay *ad = &adisplays; int islace = interlace_seen ? 1 : 0; int isntsc = (beamcon0 & 0x20) ? 0 : 1; bool found = false; @@ -4302,7 +4263,7 @@ void compute_framesync(void) struct chipset_refresh *cr = get_chipset_refresh(&currprefs); while (cr) { double v = -1; - if (!picasso_on && !picasso_requested_on) { + if (!ad->picasso_on && !ad->picasso_requested_on) { if (isvsync_chipset()) { if (cr->index == CHIPSET_REFRESH_PAL || cr->index == CHIPSET_REFRESH_NTSC) { if ((fabs(vblank_hz - 50) < 1 || fabs(vblank_hz - 60) < 1 || fabs(vblank_hz - 100) < 1 || fabs(vblank_hz - 120) < 1)) { @@ -4370,7 +4331,7 @@ void compute_framesync(void) maxhpos, maxvpos, lof_store ? 1 : 0, cr ? cr->index : -1, cr != NULL && cr->label != NULL ? cr->label : _T(""), - currprefs.gfx_apmode[picasso_on ? 1 : 0].gfx_display, picasso_on, picasso_requested_on + currprefs.gfx_apmode[ad->picasso_on ? 1 : 0].gfx_display, ad->picasso_on, ad->picasso_requested_on ); set_config_changed (); @@ -4495,23 +4456,10 @@ static void init_hz (bool checkvposw) maxvpos_total = (currprefs.chipset_mask & CSMASK_ECS_AGNUS) ? (MAXVPOS_LINES_ECS - 1) : (MAXVPOS_LINES_OCS - 1); if (maxvpos_total > MAXVPOS) maxvpos_total = MAXVPOS; -#ifdef PICASSO96 - if (!p96refresh_active) { - maxvpos_stored = maxvpos; - maxhpos_stored = maxhpos; - vblank_hz_stored = vblank_hz; - } -#endif compute_framesync (); - -#ifdef PICASSO96 - init_hz_p96(); -#endif inputdevice_tablet_strobe(); - - varsync_changed = false; } static void init_hz_vposw (void) @@ -4617,7 +4565,7 @@ static uae_u32 REGPARAM2 timehack_helper (TrapContext *context) /* * register functions */ -static uae_u16 DENISEID(int *missing) +STATIC_INLINE uae_u16 DENISEID(int *missing) { *missing = 0; if (currprefs.cs_deniserev >= 0) @@ -4648,46 +4596,27 @@ STATIC_INLINE uae_u16 INTENAR (void) { return intena; } -uae_u16 INTREQR (void) -{ - return intreq; -} +//uae_u16 INTREQR (void) +//{ +// return intreq; +//} STATIC_INLINE uae_u16 ADKCONR (void) { return adkcon; } -STATIC_INLINE int islightpentriggered (void) -{ - if (beamcon0 & 0x2000) // LPENDIS - return 0; - return lightpen_triggered != 0; -} STATIC_INLINE int issyncstopped (void) { - return (bplcon0 & 2) && !currprefs.genlock; + return (bplcon0 & 2); } STATIC_INLINE int GETVPOS (void) { - return islightpentriggered () ? vpos_lpen : (issyncstopped () ? vpos_previous : vpos); + return issyncstopped () ? vpos_previous : vpos; } STATIC_INLINE int GETHPOS (void) { - return islightpentriggered () ? hpos_lpen : (issyncstopped () ? hpos_previous : current_hpos ()); -} - -// fake changing hpos when rom genlock test runs and genlock is connected -static bool hsyncdelay (void) -{ - if (!currprefs.genlock) - return false; - if (currprefs.cpu_memory_cycle_exact || currprefs.m68k_speed >= 0) - return false; - if (bplcon0 == (0x0100 | 0x0002)) { - return true; - } - return false; + return issyncstopped () ? hpos_previous : current_hpos (); } #define CPU_ACCURATE (currprefs.cpu_model < 68020 || (currprefs.cpu_model == 68020 && currprefs.cpu_memory_cycle_exact)) @@ -4697,7 +4626,7 @@ static bool hsyncdelay (void) #define HPOS_OFFSET (CPU_ACCURATE ? HPOS_SHIFT : 0) #define VPOS_INC_DELAY (HPOS_OFFSET ? 1 : 0) -static uae_u16 VPOSR (void) +STATIC_INLINE uae_u16 VPOSR (void) { unsigned int csbit = 0; uae_u16 vp = GETVPOS (); @@ -4733,7 +4662,6 @@ static uae_u16 VPOSR (void) vp |= (lof ? 0x8000 : 0) | csbit; if (currprefs.chipset_mask & CSMASK_ECS_AGNUS) vp |= lol ? 0x80 : 0; - hsyncdelay(); return vp; } @@ -4779,7 +4707,7 @@ static void VHPOSW (uae_u16 v) if (currprefs.cpu_memory_cycle_exact && currprefs.cpu_model == 68000) { /* Special hack for Smooth Copper in CoolFridge / Upfront demo */ - int chp = current_hpos(); + int chp = current_hpos_safe(); int hp = v & 0xff; if (chp >= 0x21 && chp <= 0x29 && hp == 0x2d) { hack_delay_shift = 4; @@ -4800,7 +4728,7 @@ static void VHPOSW (uae_u16 v) } } -static uae_u16 VHPOSR (void) +STATIC_INLINE uae_u16 VHPOSR (void) { static uae_u16 oldhp; uae_u16 vp = GETVPOS (); @@ -4823,13 +4751,6 @@ static uae_u16 VHPOSR (void) } vp <<= 8; - - if (hsyncdelay ()) { - // fake continuously changing hpos in fastest possible modes - hp = oldhp % maxhpos; - oldhp++; - } - vp |= hp; return vp; } @@ -4975,6 +4896,7 @@ static void COPJMP (int num, int vblank) cop_state.hpos = current_hpos () & ~1; copper_enabled_thisline = 0; cop_state.strobe = num; + cop_state.last_strobe = num; #ifdef AMIBERRY eventtab[ev_copper].active = 0; @@ -5002,7 +4924,7 @@ STATIC_INLINE void COPCON (uae_u16 a) copcon = a; } -static void check_copper_stop(void) +STATIC_INLINE void check_copper_stop(void) { if (copper_enabled_thisline < 0 && !((dmacon & DMA_COPPER) && (dmacon & DMA_MASTER))) { copper_enabled_thisline = 0; @@ -5010,7 +4932,7 @@ static void check_copper_stop(void) } } -static void copper_stop(void) +STATIC_INLINE void copper_stop(void) { if (copper_enabled_thisline) { // let MOVE to finish @@ -5144,7 +5066,7 @@ void rethink_uae_int(void) safe_interrupt_set(false); } -static void rethink_intreq (void) +STATIC_INLINE void rethink_intreq (void) { devices_rethink(); } @@ -5246,36 +5168,6 @@ static void BEAMCON0 (uae_u16 v) } } -static void varsync (void) -{ - if (!(currprefs.chipset_mask & CSMASK_ECS_AGNUS)) - return; -#ifdef PICASSO96 - if (picasso_on && p96refresh_active) { - vtotal = p96refresh_active; - return; - } -#endif - if (!(beamcon0 & 0x80)) - return; - varsync_changed = true; -} - -#ifdef PICASSO96 -void set_picasso_hack_rate (int hz) -{ - if (!picasso_on) - return; - vpos_count = 0; - p96refresh_active = int(maxvpos_stored * vblank_hz_stored / hz); - if (!currprefs.cs_ciaatod) - changed_prefs.cs_ciaatod = currprefs.cs_ciaatod = currprefs.ntscmode ? 2 : 1; - if (p96refresh_active > 0) { - new_beamcon0 |= 0x80; - } -} -#endif - /* "Dangerous" blitter D-channel: Writing to memory which is also currently * read by bitplane DMA */ @@ -5391,17 +5283,6 @@ static void BPLCON0 (int hpos, uae_u16 v) bplcon0_interlace_seen = true; } - if ((v & 8) && !lightpen_triggered && vpos < sprite_vblank_endline) { - // setting lightpen bit immediately freezes VPOSR if inside vblank and not already frozen - lightpen_triggered = 1; - vpos_lpen = vpos; - hpos_lpen = hpos; - } - if (!(v & 8)) { - // clearing lightpen bit immediately returns VPOSR back to normal - lightpen_triggered = 0; - } - bplcon0 = v; bpldmainitdelay (hpos); @@ -5410,7 +5291,7 @@ static void BPLCON0 (int hpos, uae_u16 v) BPLCON0_Denise (hpos, v, true); } -static void BPLCON1 (int hpos, uae_u16 v) +STATIC_INLINE void BPLCON1 (int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_AGA)) v &= 0xff; @@ -5424,7 +5305,7 @@ static void BPLCON1 (int hpos, uae_u16 v) hack_shres_delay(hpos); } -static void BPLCON2(int hpos, uae_u16 v) +STATIC_INLINE void BPLCON2(int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_AGA)) v &= ~(0x100 | 0x80); // RDRAM and SOGEN @@ -5439,7 +5320,7 @@ static void BPLCON2(int hpos, uae_u16 v) } #ifdef ECS_DENISE -static void BPLCON3(int hpos, uae_u16 v) +STATIC_INLINE void BPLCON3(int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_ECS_DENISE)) return; @@ -5460,7 +5341,7 @@ static void BPLCON3(int hpos, uae_u16 v) } #endif #ifdef AGA -static void BPLCON4(int hpos, uae_u16 v) +STATIC_INLINE void BPLCON4(int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_AGA)) return; @@ -5687,14 +5568,14 @@ static void BLTBDAT (int hpos, uae_u16 v) blt_info.bltbdat = v; blt_info.bltbold = v; } -static void BLTCDAT(int hpos, uae_u16 v) { maybe_blit(0); blt_info.bltcdat = v; reset_blit(0); } +STATIC_INLINE void BLTCDAT(int hpos, uae_u16 v) { maybe_blit(0); blt_info.bltcdat = v; reset_blit(0); } -static void BLTAMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltamod = uae_s16(v & 0xFFFE); reset_blit(0); } -static void BLTBMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltbmod = uae_s16(v & 0xFFFE); reset_blit(0); } -static void BLTCMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltcmod = uae_s16(v & 0xFFFE); reset_blit(0); } -static void BLTDMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltdmod = uae_s16(v & 0xFFFE); reset_blit(0); } +STATIC_INLINE void BLTAMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltamod = uae_s16(v & 0xFFFE); reset_blit(0); } +STATIC_INLINE void BLTBMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltbmod = uae_s16(v & 0xFFFE); reset_blit(0); } +STATIC_INLINE void BLTCMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltcmod = uae_s16(v & 0xFFFE); reset_blit(0); } +STATIC_INLINE void BLTDMOD(int hpos, uae_u16 v) { maybe_blit(1); blt_info.bltdmod = uae_s16(v & 0xFFFE); reset_blit(0); } -static void BLTCON0(int hpos, uae_u16 v) { maybe_blit(2); bltcon0 = v; reset_blit(1); } +STATIC_INLINE void BLTCON0(int hpos, uae_u16 v) { maybe_blit(2); bltcon0 = v; reset_blit(1); } /* The next category is "Most useless hardware register". * And the winner is... */ @@ -5706,53 +5587,53 @@ static void BLTCON0L (int hpos, uae_u16 v) bltcon0 = (bltcon0 & 0xFF00) | (v & 0xFF); reset_blit(1); } -static void BLTCON1(int hpos, uae_u16 v) { maybe_blit (2); bltcon1 = v; reset_blit (2); } +STATIC_INLINE void BLTCON1(int hpos, uae_u16 v) { maybe_blit (2); bltcon1 = v; reset_blit (2); } -static void BLTAFWM(int hpos, uae_u16 v) { maybe_blit (2); blt_info.bltafwm = v; reset_blit(0); } -static void BLTALWM(int hpos, uae_u16 v) { maybe_blit (2); blt_info.bltalwm = v; reset_blit(0); } +STATIC_INLINE void BLTAFWM(int hpos, uae_u16 v) { maybe_blit (2); blt_info.bltafwm = v; reset_blit(0); } +STATIC_INLINE void BLTALWM(int hpos, uae_u16 v) { maybe_blit (2); blt_info.bltalwm = v; reset_blit(0); } -static void BLTAPTH(int hpos, uae_u16 v) +STATIC_INLINE void BLTAPTH(int hpos, uae_u16 v) { maybe_blit(0); bltapt = (bltapt & 0xffff) | (uae_u32(v) << 16); } -static void BLTAPTL (int hpos, uae_u16 v) +STATIC_INLINE void BLTAPTL (int hpos, uae_u16 v) { maybe_blit(0); bltapt = (bltapt & ~0xffff) | (v & 0xFFFE); } -static void BLTBPTH (int hpos, uae_u16 v) +STATIC_INLINE void BLTBPTH (int hpos, uae_u16 v) { maybe_blit(0); bltbpt = (bltbpt & 0xffff) | (uae_u32(v) << 16); } -static void BLTBPTL (int hpos, uae_u16 v) +STATIC_INLINE void BLTBPTL (int hpos, uae_u16 v) { maybe_blit(0); bltbpt = (bltbpt & ~0xffff) | (v & 0xFFFE); } -static void BLTCPTH (int hpos, uae_u16 v) +STATIC_INLINE void BLTCPTH (int hpos, uae_u16 v) { maybe_blit(0); bltcpt = (bltcpt & 0xffff) | (uae_u32(v) << 16); } -static void BLTCPTL (int hpos, uae_u16 v) +STATIC_INLINE void BLTCPTL (int hpos, uae_u16 v) { maybe_blit(0); bltcpt = (bltcpt & ~0xffff) | (v & 0xFFFE); } -static void BLTDPTH (int hpos, uae_u16 v) +STATIC_INLINE void BLTDPTH (int hpos, uae_u16 v) { maybe_blit(0); bltdpt = (bltdpt & 0xffff) | (uae_u32(v) << 16); } -static void BLTDPTL (int hpos, uae_u16 v) +STATIC_INLINE void BLTDPTL (int hpos, uae_u16 v) { maybe_blit(0); bltdpt = (bltdpt & ~0xffff) | (v & 0xFFFE); } -static void BLTSIZE (int hpos, uae_u16 v) +STATIC_INLINE void BLTSIZE (int hpos, uae_u16 v) { maybe_blit(0); @@ -5766,7 +5647,7 @@ static void BLTSIZE (int hpos, uae_u16 v) dcheck_is_blit_dangerous(); } -static void BLTSIZV (int hpos, uae_u16 v) +STATIC_INLINE void BLTSIZV (int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_ECS_AGNUS)) return; @@ -5774,7 +5655,7 @@ static void BLTSIZV (int hpos, uae_u16 v) blt_info.vblitsize = v & 0x7FFF; } -static void BLTSIZH (int hpos, uae_u16 v) +STATIC_INLINE void BLTSIZH (int hpos, uae_u16 v) { if (!(currprefs.chipset_mask & CSMASK_ECS_AGNUS)) return; @@ -5811,7 +5692,7 @@ STATIC_INLINE void sprstartstop (struct sprite *s) s->dmastate = 0; } -static void SPRxCTLPOS(int num) +STATIC_INLINE void SPRxCTLPOS(int num) { int sprxp; struct sprite *s = &spr[num]; @@ -5843,7 +5724,7 @@ static void SPRxCTLPOS(int num) sprstartstop (s); } -static void SPRxCTL_1(uae_u16 v, int num, int hpos) +STATIC_INLINE void SPRxCTL_1(uae_u16 v, int num, int hpos) { struct sprite *s = &spr[num]; if (hpos >= maxhpos - 2 && s->ctl != v && vpos < maxvpos - 1) { @@ -5858,7 +5739,7 @@ static void SPRxCTL_1(uae_u16 v, int num, int hpos) SPRxCTLPOS(num); } -static void SPRxPOS_1(uae_u16 v, int num, int hpos) +STATIC_INLINE void SPRxPOS_1(uae_u16 v, int num, int hpos) { struct sprite *s = &spr[num]; if (hpos >= maxhpos - 2 && s->pos != v && vpos < maxvpos - 1) { @@ -5872,7 +5753,7 @@ static void SPRxPOS_1(uae_u16 v, int num, int hpos) SPRxCTLPOS(num); } -static void SPRxDATA_1(uae_u16 v, int num, int hpos) +STATIC_INLINE void SPRxDATA_1(uae_u16 v, int num, int hpos) { struct sprite *s = &spr[num]; s->data[0] = v; @@ -5887,7 +5768,7 @@ static void SPRxDATA_1(uae_u16 v, int num, int hpos) spr_arm(num, 1); } -static void SPRxDATB_1(uae_u16 v, int num, int hpos) +STATIC_INLINE void SPRxDATB_1(uae_u16 v, int num, int hpos) { struct sprite *s = &spr[num]; s->datb[0] = v; @@ -5905,7 +5786,7 @@ static void SPRxDATB_1(uae_u16 v, int num, int hpos) // cycle is DMA fetch: sprite's first 32 pixels get replaced with bitplane data. static void sprite_get_bpl_data(int hpos, struct sprite *s, uae_u16 *dat) { - int nr = is_bitplane_dma_inline(hpos + 1); + int nr = is_bitplane_dma(hpos + 1); uae_u32 v = (fmode & 3) ? fetched_aga[nr] : fetched_aga_spr[nr]; dat[0] = v >> 16; dat[1] = uae_u16(v); @@ -5926,7 +5807,7 @@ static void sprite_get_bpl_data(int hpos, struct sprite *s, uae_u16 *dat) for future use. (SPRxCTL not tested) */ -static void SPRxDATA (int hpos, uae_u16 v, int num) +STATIC_INLINE void SPRxDATA (int hpos, uae_u16 v, int num) { struct sprite *s = &spr[num]; decide_sprites(hpos, true, false); @@ -5935,21 +5816,21 @@ static void SPRxDATA (int hpos, uae_u16 v, int num) // - first 16 pixel part: previous chipset bus data // - following 16 pixel parts: written data if (fmode & 8) { - if ((fmode & 4) && is_bitplane_dma_inline(hpos - 1)) { + if ((fmode & 4) && is_bitplane_dma(hpos - 1)) { sprite_get_bpl_data(hpos, s, &s->data[0]); } else { s->data[0] = last_custom_value2; } } } -static void SPRxDATB (int hpos, uae_u16 v, int num) +STATIC_INLINE void SPRxDATB (int hpos, uae_u16 v, int num) { struct sprite *s = &spr[num]; decide_sprites(hpos, true, false); SPRxDATB_1(v, num, hpos); // See above if (fmode & 8) { - if ((fmode & 4) && is_bitplane_dma_inline(hpos - 1)) { + if ((fmode & 4) && is_bitplane_dma(hpos - 1)) { sprite_get_bpl_data(hpos, s, &s->datb[0]); } else { s->datb[0] = last_custom_value2; @@ -5957,13 +5838,13 @@ static void SPRxDATB (int hpos, uae_u16 v, int num) } } -static void SPRxCTL (int hpos, uae_u16 v, int num) +STATIC_INLINE void SPRxCTL (int hpos, uae_u16 v, int num) { decide_sprites(hpos); SPRxCTL_1(v, num, hpos); } -static void SPRxPOS (int hpos, uae_u16 v, int num) +STATIC_INLINE void SPRxPOS (int hpos, uae_u16 v, int num) { struct sprite *s = &spr[num]; int oldvpos; @@ -6038,8 +5919,6 @@ static uae_u16 COLOR_READ(int num) cval = ((cr & 15) << 8) | ((cg & 15) << 4) | ((cb & 15) << 0); } else { cval = ((cr >> 4) << 8) | ((cg >> 4) << 4) | ((cb >> 4) << 0); - if (color_regs_genlock[num]) - cval |= 0x8000; } return cval; } @@ -6097,9 +5976,8 @@ static void COLOR_WRITE (int hpos, uae_u16 v, int num) cr = r + (r << 4); cg = g + (g << 4); cb = b + (b << 4); - color_regs_genlock[colreg] = v >> 15; } - cval = (cr << 16) | (cg << 8) | cb | (color_regs_genlock[colreg] ? 0x80000000 : 0); + cval = (cr << 16) | (cg << 8) | cb; if (cval == current_colors.color_regs_aga[colreg]) return; @@ -6118,7 +5996,6 @@ static void COLOR_WRITE (int hpos, uae_u16 v, int num) v &= 0x8fff; if (!(currprefs.chipset_mask & CSMASK_ECS_DENISE)) v &= 0xfff; - color_regs_genlock[num] = v >> 15; if (current_colors.color_regs_ecs[num] == v) return; if (num == 0) @@ -6180,7 +6057,7 @@ STATIC_INLINE int copper_cant_read(int hpos) if ((hpos == maxhpos - 3) && (maxhpos & 1)) { return -1; } - return is_bitplane_dma_inline (hpos); + return is_bitplane_dma(hpos); } #ifdef AMIBERRY @@ -6204,110 +6081,132 @@ static void predict_copper (void) enum copper_states state = cop_state.state; unsigned int w1, w2, cycle_count; unsigned int modified = REGTYPE_FORCE; + unsigned int vcmp; + int vp; + + if (cop_state.ignore_next || cop_state.movedelay) + return; + + int until_hpos = maxhpos - 3; + int force_exit = 0; + + w1 = cop_state.saved_i1; + w2 = cop_state.saved_i2; switch (state) { - case COP_read1: - break; - - case COP_read2: - w1 = cop_state.i1; - w2 = chipmem_wget_indirect (ip); - if (w1 & 1) { - if (w2 & 1) - return; // SKIP - state = COP_wait; // WAIT - c_hpos += 4; - } else { // MOVE - modified |= regtypes[w1 & 0x1FE]; - state = COP_read1; - c_hpos += 2; - } - ip += 2; - break; - - case COP_strobe_delay2: - case COP_strobe_delay2x: - case COP_start_delay: - c_hpos += 2; - state = COP_read1; - break; - - case COP_strobe_extra: - c_hpos += 6; - state = COP_read1; - break; - - case COP_strobe_delay1: - case COP_strobe_delay1x: - c_hpos += 4; - state = COP_read1; - break; - case COP_stop: case COP_waitforever: case COP_bltwait: case COP_skip_in2: case COP_skip1: return; - - case COP_wait_in2: - c_hpos += 2; - case COP_wait1: - w1 = cop_state.i1; - w2 = cop_state.i2; - state = COP_wait; + + case COP_wait: + vcmp = (w1 & (w2 | 0x8000)) >> 8; + vp = vpos & (((w2 >> 8) & 0x7F) | 0x80); + if (vp < cop_state.vcmp) + c_hpos = until_hpos; // run till end of line + break; + } + + while(c_hpos < until_hpos && !force_exit) { + c_hpos += 2; + + switch(state) { + case COP_wait_in2: + state = COP_wait1; break; - case COP_wait: - w1 = cop_state.i1; - w2 = cop_state.i2; + case COP_skip_in2: + state = COP_skip1; + break; + + case COP_strobe_extra: + state = COP_strobe_delay1; break; - default: - return; - } - /* Only needed for COP_wait, but let's shut up the compiler. */ - cop_state.first_sync = c_hpos; + case COP_strobe_delay1: + state = COP_strobe_delay2; + break; + + case COP_strobe_delay1x: + state = COP_strobe_delay2x; + break; + + case COP_strobe_delay2: + case COP_strobe_delay2x: + state = COP_read1; + if(cop_state.strobe == 1) + ip = cop1lc; + else + ip = cop2lc; + break; + + case COP_start_delay: + state = COP_read1; + ip = cop1lc; + break; + + case COP_read1: + w1 = chipmem_wget_indirect (ip); + ip += 2; + state = COP_read2; + break; - while (c_hpos + 1 < maxhpos) { - if (state == COP_read1) { - w1 = chipmem_wget_indirect (ip); - if (w1 & 1) { - w2 = chipmem_wget_indirect (ip + 2); + case COP_read2: + w2 = chipmem_wget_indirect (ip); + ip += 2; + if (w1 & 1) { // WAIT or SKIP if (w2 & 1) - break; // SKIP - state = COP_wait; // WAIT - c_hpos += 6; + state = COP_skip_in2; + else + state = COP_wait_in2; } else { // MOVE - modified |= regtypes[w1 & 0x1FE]; - c_hpos += 4; + unsigned int reg = w1 & 0x1FE; + state = COP_read1; + // check from test_copper_dangerous() + if (reg < ((copcon & 2) ? ((currprefs.chipset_mask & CSMASK_ECS_AGNUS) ? 0 : 0x40) : 0x80)) { + force_exit = 1; + break; + } + if(reg == 0x88 || reg == 0x8a) { // next is strobe + force_exit = 1; + break; + } + modified |= regtypes[reg]; } - ip += 4; - } else { // state is COP_wait - if ((w2 & 0xFE) != 0xFE) + break; + + case COP_wait1: + if (w1 == 0xFFFF && w2 == 0xFFFE) { + c_hpos = until_hpos; // new state is COP_waitforever -> run till end of line break; - else { - unsigned int vcmp = (w1 & (w2 | 0x8000)) >> 8; - unsigned int hcmp = (w1 & 0xFE); + } + + state = COP_wait; + + vcmp = (w1 & (w2 | 0x8000)) >> 8; + vp = vpos & (((w2 >> 8) & 0x7F) | 80); - unsigned int vp = vpos & (((w2 >> 8) & 0x7F) | 0x80); - if (vp < vcmp) { - /* Whee. We can wait until the end of the line! */ - c_hpos = maxhpos; - } else if (vp > vcmp || hcmp <= c_hpos) { + if(vp < vcmp) + c_hpos = until_hpos; // run till end of line + break; + + case COP_wait: + { + unsigned int hcmp = (w1 & w2 & 0xFE); + + int hp = c_hpos & (w2 & 0xFE); + if(vp == vcmp && hp < hcmp) + break; // position not reached state = COP_read1; - /* minimum wakeup time */ - c_hpos += 2; - } else { - state = COP_read1; - c_hpos = hcmp + 2; } - /* If this is the current instruction, remember that we don't - need to sync CPU and copper anytime soon. */ - if (cop_state.ip == ip) { - cop_state.first_sync = c_hpos; - } - } + break; + + case COP_skip1: + // must be handled by real code + force_exit = 1; + break; } } @@ -6322,7 +6221,7 @@ static void predict_copper (void) } #endif -static int custom_wput_copper (int hpos, uaecptr addr, uae_u32 value, int noget) +STATIC_INLINE int custom_wput_copper (int hpos, uaecptr addr, uae_u32 value, int noget) { int v; @@ -6501,7 +6400,6 @@ static void update_copper (int until_hpos) cop_state.strobe = 0; break; - case COP_start_delay: // cycle after vblank strobe fetches word from old pointer first if (copper_cant_read(old_hpos)) @@ -6543,14 +6441,18 @@ static void update_copper (int until_hpos) if (!copper_enabled_thisline) goto out; // was "dangerous" register -> copper stopped - if (cop_state.ignore_next) + if (cop_state.ignore_next) { reg = 0x1fe; + cop_state.ignore_next = 0; + } if (reg == 0x88) { cop_state.strobe = 1; + cop_state.last_strobe = 1; cop_state.state = COP_strobe_delay1; } else if (reg == 0x8a) { cop_state.strobe = 2; + cop_state.last_strobe = 2; cop_state.state = COP_strobe_delay1; } else { @@ -6615,19 +6517,28 @@ static void update_copper (int until_hpos) hp = ch_comp & (cop_state.saved_i2 & 0xFE); if (vp == cop_state.vcmp && hp < cop_state.hcmp) { /* Position not reached yet. */ - if (currprefs.fast_copper) { - if ((cop_state.saved_i2 & 0xFE) == 0xFE) { - int wait_finish = cop_state.hcmp - 2; - /* This will leave c_hpos untouched if it's equal to wait_finish. */ - if (wait_finish < c_hpos) - return; - else if (wait_finish <= until_hpos) { - c_hpos = wait_finish; - } - else - c_hpos = until_hpos; - } - } +#ifdef AMIBERRY + if(currprefs.fast_copper) { + while(c_hpos < until_hpos) { + int redo_hpos = c_hpos; + + if (c_hpos == maxhpos - 3) + c_hpos += 1; + else + c_hpos += 2; + + ch_comp = c_hpos; + if (ch_comp & 1) + ch_comp = 0; + + hp = ch_comp & (cop_state.saved_i2 & 0xFE); + if(hp >= cop_state.hcmp) { + c_hpos = redo_hpos; // run outer loop with last c_hpos + break; + } + } + } +#endif break; } cop_state.state = COP_read1; @@ -6772,11 +6683,6 @@ STATIC_INLINE void sync_copper_with_cpu(int hpos, int do_schedule, unsigned int #ifdef AMIBERRY if (eventtab[ev_copper].active) { if (hpos != maxhpos) { - /* There might be reasons why we don't actually need to bother - updating the copper. */ - if (hpos < cop_state.first_sync) - return; - if ((cop_state.regtypes_modified & regtypes[addr & 0x1FE]) == 0) return; } @@ -6822,7 +6728,7 @@ static void cursorsprite (void) //} } -static uae_u16 sprite_fetch(struct sprite *s, uaecptr pt, bool dma, int hpos, int cycle, int mode) +STATIC_INLINE uae_u16 sprite_fetch(struct sprite *s, uaecptr pt, bool dma, int hpos, int cycle, int mode) { uae_u16 data = last_custom_value1; if (dma) { @@ -6836,7 +6742,7 @@ static uae_u16 sprite_fetch(struct sprite *s, uaecptr pt, bool dma, int hpos, in return data; } -static void sprite_fetch_full(struct sprite *s, int hpos, int cycle, int mode, uae_u16 *v0, uae_u32 *v1, uae_u32 *v2) +STATIC_INLINE void sprite_fetch_full(struct sprite *s, int hpos, int cycle, int mode, uae_u16 *v0, uae_u32 *v1, uae_u32 *v2) { uae_u32 data321 = 0, data322 = 0; uae_u16 data16; @@ -6892,7 +6798,7 @@ static void sprite_fetch_full(struct sprite *s, int hpos, int cycle, int mode, u *v2 = data322; } -static void do_sprites_1(int num, int cycle, int hpos) +STATIC_INLINE void do_sprites_1(int num, int cycle, int hpos) { struct sprite *s = &spr[num]; int posctl = 0; @@ -6951,7 +6857,6 @@ static void do_sprites_1(int num, int cycle, int hpos) } } if (vpos == sprite_vblank_endline) { - // s->vstart == sprite_vblank_endline won't enable the sprite. s->dmastate = 0; } } @@ -7117,9 +7022,8 @@ void init_hardware_for_drawing_frame (void) int npixels = prev_sprite_entries[prev_next_sprite_entry].first_pixel - first_pixel; memset (spixels + first_pixel, 0, npixels * sizeof *spixels); memset(spixstate.stb + first_pixel, 0, npixels * sizeof *spixstate.stb); - if (spr_width_64_seen) { + if (currprefs.chipset_mask & CSMASK_AGA) { memset(spixstate.stbfm + first_pixel, 0, npixels * sizeof *spixstate.stbfm); - spr_width_64_seen = false; } } prev_next_sprite_entry = next_sprite_entry; @@ -7158,7 +7062,7 @@ static int rpt_vsync () return v; } -static void rtg_vsync (void) +STATIC_INLINE void rtg_vsync (void) { #ifdef PICASSO96 frame_time_t start, end; @@ -7207,6 +7111,7 @@ static int mavg (struct mavg_data *md, int newval, int size) static bool framewait(void) { + struct amigadisplay *ad = &adisplays; frame_time_t curr_time; frame_time_t start; frame_time_t time_for_next_frame = vsynctimebase; @@ -7223,7 +7128,7 @@ static bool framewait(void) if (vs > 0) { if (!nodraw()) { - if (!frame_rendered && !picasso_on) + if (!frame_rendered && !ad->picasso_on) frame_rendered = render_screen(false); if (!frame_shown) { @@ -7261,7 +7166,7 @@ static bool framewait(void) if (currprefs.m68k_speed < 0) { - if (!frame_rendered && !picasso_on) + if (!frame_rendered && !ad->picasso_on) frame_rendered = render_screen(false); curr_time = read_processor_time(); @@ -7288,7 +7193,7 @@ static bool framewait(void) int t = 0; start = read_processor_time(); - if (!frame_rendered && !picasso_on) { + if (!frame_rendered && !ad->picasso_on) { frame_rendered = render_screen(false); t = read_processor_time() - start; } @@ -7391,6 +7296,7 @@ static void fpscounter (bool frameok) // vsync functions that are not hardware timing related static void vsync_handler_pre(void) { + struct amigadisplay *ad = &adisplays; if (bogusframe > 0) bogusframe--; @@ -7413,7 +7319,7 @@ static void vsync_handler_pre(void) bool frameok = framewait(); - if (!picasso_on && !nodraw()) { + if (!ad->picasso_on && !nodraw()) { if (!frame_rendered) { frame_rendered = render_screen(false); } @@ -7425,7 +7331,7 @@ static void vsync_handler_pre(void) // GUI check here, must be after frame rendering devices_vsync_pre(); - if (!nodraw() || picasso_on) + if (!nodraw() || ad->picasso_on) fpscounter(frameok); bool waspaused = false; @@ -7446,7 +7352,7 @@ static void vsync_handler_pre(void) if (quit_program > 0) { /* prevent possible infinite loop at wait_cycles().. */ - framecnt = 0; + ad->framecnt = 0; reset_decisions(); return; } @@ -7471,9 +7377,6 @@ static void vsync_handler_post(void) if (bplcon0 & 4) { lof_store = lof_store ? 0 : 1; } - if ((bplcon0 & 2) && currprefs.genlock) { - genlockvtoggle = lof_store ? 1 : 0; - } if (lof_prev_lastline != lof_lastline) { if (lof_togglecnt_lace < LOF_TOGGLES_NEEDED) @@ -7524,15 +7427,7 @@ static void vsync_handler_post(void) lof_lace = false; } -#ifdef PICASSO96 - if (p96refresh_active) { - vpos_count = p96refresh_active; - vpos_count_diff = p96refresh_active; - vtotal = vpos_count; - } -#endif - - if (varsync_changed || (beamcon0 & (0x10 | 0x20 | 0x80 | 0x100 | 0x200)) != (new_beamcon0 & (0x10 | 0x20 | 0x80 | 0x100 | 0x200))) { + if ((beamcon0 & (0x10 | 0x20 | 0x80 | 0x100 | 0x200)) != (new_beamcon0 & (0x10 | 0x20 | 0x80 | 0x100 | 0x200))) { init_hz_normal(); } else if (vpos_count > 0 && abs (vpos_count - vpos_count_diff) > 1 && vposw_change < 4) { init_hz_vposw(); @@ -7748,13 +7643,6 @@ static void events_dmal_hsync (void) events_dmal (7); } -static void lightpen_trigger_func(uae_u32 v) -{ - vpos_lpen = vpos; - hpos_lpen = v; - lightpen_triggered = 1; -} - static bool is_custom_vsync (void) { int vp = vpos + 1; @@ -7848,12 +7736,8 @@ static void hsync_handler_post (bool onvsync) } #endif - // genlock active: - // vertical: interlaced = toggles every other field, non-interlaced = both fields (normal) - // horizontal: PAL = every line, NTSC = every other line - genlockhtoggle = !genlockhtoggle; - bool ciahsyncs = !(bplcon0 & 2) || ((bplcon0 & 2) && currprefs.genlock && (!currprefs.ntscmode || genlockhtoggle)); - bool ciavsyncs = !(bplcon0 & 2) || ((bplcon0 & 2) && currprefs.genlock && genlockvtoggle); + bool ciahsyncs = !(bplcon0 & 2); + bool ciavsyncs = !(bplcon0 & 2); CIA_hsync_posthandler(false); if (currprefs.cs_cd32cd) { @@ -7912,7 +7796,6 @@ static void hsync_handler_post (bool onvsync) } if (onvsync) { - // vpos_count >= MAXVPOS just to not crash if VPOSW writes prevent vsync completely vpos = 0; vsync_handler_post(); vpos_count = 0; @@ -8015,7 +7898,6 @@ static void hsync_handler_post (bool onvsync) cop_state.hpos = 0; compute_spcflag_copper (maxhpos); - //copper_check (2); if (GET_PLANES (bplcon0) > 0 && dmaen (DMA_BITPLANE)) { if (first_bplcon0 == 0) @@ -8204,17 +8086,9 @@ void custom_reset (bool hardreset, bool keyboardreset) board_prefs_changed(-1, -1); target_reset(); - reset_all_systems(); + devices_reset(hardreset); write_log(_T("Reset at %08X. Chipset mask = %08X\n"), M68K_GETPC, currprefs.chipset_mask); - lightpen_active = -1; - lightpen_triggered = 0; - lightpen_cx[0] = lightpen_cy[0] = -1; - lightpen_cx[1] = lightpen_cy[1] = -1; - lightpen_x[0] = -1; - lightpen_y[0] = -1; - lightpen_x[1] = -1; - lightpen_y[1] = -1; nr_armed = 0; memset(custom_storage, 0, sizeof(custom_storage)); @@ -8226,7 +8100,6 @@ void custom_reset (bool hardreset, bool keyboardreset) currprefs.chipset_mask = changed_prefs.chipset_mask; update_mirrors (); - if (hardreset) { if (!aga_mode) { uae_u16 c = (((currprefs.chipset_mask & CSMASK_ECS_DENISE) && !(currprefs.chipset_mask & CSMASK_AGA)) || currprefs.cs_denisenoehb) ? 0xfff : 0x000; @@ -8278,8 +8151,6 @@ void custom_reset (bool hardreset, bool keyboardreset) init_sprites (); } - devices_reset(hardreset); - unset_special (~(SPCFLAG_BRK | SPCFLAG_MODE_CHANGE)); vpos = 0; @@ -8310,7 +8181,6 @@ void custom_reset (bool hardreset, bool keyboardreset) init_hz_normal(); // init_hz sets vpos_count vpos_count = 0; - vpos_lpen = -1; lof_changing = 0; lof_togglecnt_nlace = lof_togglecnt_lace = 0; @@ -8392,12 +8262,6 @@ void custom_reset (bool hardreset, bool keyboardreset) setup_fmodes (0); shdelay_disabled = false; - // must be after audio reset - // this inits first autoconfig board -#ifdef AUTOCONFIG - expamem_reset(); -#endif - #ifdef ACTION_REPLAY /* Doing this here ensures we can use the 'reset' command from within AR */ action_replay_reset(hardreset, keyboardreset); @@ -8406,8 +8270,9 @@ void custom_reset (bool hardreset, bool keyboardreset) if (hardreset) rtc_hardreset(); -#ifdef PICASSO96 - picasso_reset(); +// must be last +#ifdef AUTOCONFIG + expamem_reset(hardreset); #endif } @@ -8481,7 +8346,6 @@ int custom_init (void) static uae_u32 REGPARAM3 custom_lget (uaecptr) REGPARAM; static uae_u32 REGPARAM3 custom_wget (uaecptr) REGPARAM; static uae_u32 REGPARAM3 custom_bget (uaecptr) REGPARAM; -static uae_u32 REGPARAM3 custom_lgeti (uaecptr) REGPARAM; static uae_u32 REGPARAM3 custom_wgeti (uaecptr) REGPARAM; static void REGPARAM3 custom_lput (uaecptr, uae_u32) REGPARAM; static void REGPARAM3 custom_wput (uaecptr, uae_u32) REGPARAM; @@ -8491,7 +8355,7 @@ addrbank custom_bank = { custom_lget, custom_wget, custom_bget, custom_lput, custom_wput, custom_bput, default_xlate, default_check, NULL, NULL, _T("Custom chipset"), - custom_lgeti, custom_wgeti, + custom_wgeti, ABFLAG_IO, S_READ, S_WRITE, NULL, 0x1ff, 0xdff000 }; @@ -8501,24 +8365,21 @@ static uae_u32 REGPARAM2 custom_wgeti (uaecptr addr) return dummy_wgeti (addr); return custom_wget (addr); } -static uae_u32 REGPARAM2 custom_lgeti (uaecptr addr) -{ - if (currprefs.cpu_model >= 68020) - return dummy_lgeti (addr); - return custom_lget (addr); -} -static uae_u32 REGPARAM2 custom_wget_1(int hpos, uaecptr addr, int noput, bool isbyte) +STATIC_INLINE uae_u32 REGPARAM2 custom_wget_1(int hpos, uaecptr addr, int noput) { uae_u16 v; int missing; addr &= 0xfff; switch (addr & 0x1fe) { + case 0x000: v = 0xffff; break; /* BPLDDAT */ case 0x002: v = DMACONR (hpos); break; case 0x004: v = VPOSR (); break; case 0x006: v = VHPOSR (); break; + case 0x008: v = 0xffff; break; + case 0x00A: v = JOY0DAT (); break; case 0x00C: v = JOY1DAT (); break; case 0x00E: v = CLXDAT (); break; @@ -8570,7 +8431,7 @@ writeonly: int bmdma; uae_u16 l; - if (aga_mode) { + if (currprefs.chipset_mask & CSMASK_AGA) { l = 0; } else { @@ -8615,13 +8476,13 @@ writeonly: return v; } -static uae_u32 custom_wget2(uaecptr addr, bool byte) +STATIC_INLINE uae_u32 custom_wget2(uaecptr addr, bool byte) { uae_u32 v; int hpos = current_hpos (); - sync_copper_with_cpu(hpos, 1, addr); - v = custom_wget_1(hpos, addr, 0, byte); + sync_copper_with_cpu (hpos, 1, addr); + v = custom_wget_1 (hpos, addr, 0); #ifdef ACTION_REPLAY #ifdef ACTION_REPLAY_COMMON addr &= 0x1fe; @@ -8849,17 +8710,17 @@ static int REGPARAM2 custom_wput_1 (int hpos, uaecptr addr, uae_u32 value, int n #endif case 0x1DC: BEAMCON0 (value); break; - case 0x1C0: if (htotal != value) { htotal = value & (MAXHPOS_ROWS - 1); varsync (); } break; - case 0x1C2: if (hsstop != value) { hsstop = value & (MAXHPOS_ROWS - 1); varsync (); } break; - case 0x1C4: if (hbstrt != value) { hbstrt = value & (MAXHPOS_ROWS - 1); varsync (); } break; - case 0x1C6: if (hbstop != value) { hbstop = value & (MAXHPOS_ROWS - 1); varsync ();} break; - case 0x1C8: if (vtotal != value) { vtotal = value & (MAXVPOS_LINES_ECS - 1); varsync (); } break; - case 0x1CA: if (vsstop != value) { vsstop = value & (MAXVPOS_LINES_ECS - 1); varsync (); } break; - case 0x1CC: if (vbstrt < value || vbstrt > (value & (MAXVPOS_LINES_ECS - 1)) + 1) { vbstrt = value & (MAXVPOS_LINES_ECS - 1); varsync (); } break; - case 0x1CE: if (vbstop < value || vbstop > (value & (MAXVPOS_LINES_ECS - 1)) + 1) { vbstop = value & (MAXVPOS_LINES_ECS - 1); varsync (); } break; - case 0x1DE: if (hsstrt != value) { hsstrt = value & (MAXHPOS_ROWS - 1); varsync (); } break; - case 0x1E0: if (vsstrt != value) { vsstrt = value & (MAXVPOS_LINES_ECS - 1); varsync (); } break; - case 0x1E2: if (hcenter != value) { hcenter = value & (MAXHPOS_ROWS - 1); varsync (); } break; + case 0x1C0: if (htotal != value) { htotal = value & (MAXHPOS_ROWS - 1); } break; + case 0x1C2: if (hsstop != value) { hsstop = value & (MAXHPOS_ROWS - 1); } break; + case 0x1C4: if (hbstrt != value) { hbstrt = value & (MAXHPOS_ROWS - 1); } break; + case 0x1C6: if (hbstop != value) { hbstop = value & (MAXHPOS_ROWS - 1); } break; + case 0x1C8: if (vtotal != value) { vtotal = value & (MAXVPOS_LINES_ECS - 1); } break; + case 0x1CA: if (vsstop != value) { vsstop = value & (MAXVPOS_LINES_ECS - 1); } break; + case 0x1CC: if (vbstrt < value || vbstrt > (value & (MAXVPOS_LINES_ECS - 1)) + 1) { vbstrt = value & (MAXVPOS_LINES_ECS - 1); } break; + case 0x1CE: if (vbstop < value || vbstop > (value & (MAXVPOS_LINES_ECS - 1)) + 1) { vbstop = value & (MAXVPOS_LINES_ECS - 1); } break; + case 0x1DE: if (hsstrt != value) { hsstrt = value & (MAXHPOS_ROWS - 1); } break; + case 0x1E0: if (vsstrt != value) { vsstrt = value & (MAXVPOS_LINES_ECS - 1); } break; + case 0x1E2: if (hcenter != value) { hcenter = value & (MAXHPOS_ROWS - 1); } break; #ifdef AGA case 0x1FC: FMODE (hpos, value); break; @@ -8869,7 +8730,7 @@ static int REGPARAM2 custom_wput_1 (int hpos, uaecptr addr, uae_u32 value, int n /* writing to read-only register causes read access */ default: if (!noget) { - custom_wget_1 (hpos, addr, 1, false); + custom_wget_1 (hpos, addr, 1); } return 1; } @@ -9050,7 +8911,6 @@ uae_u8 *restore_custom (uae_u8 *src) fetched[i] = RW; /* BPLXDAT */ for(i = 0; i < 32; i++) { uae_u16 v = RW; - color_regs_genlock[i] = (v & 0x8000) != 0; current_colors.color_regs_ecs[i] = v & 0xfff; /* 180 COLORxx */ } htotal = RW; /* 1C0 HTOTAL */ @@ -9233,8 +9093,6 @@ uae_u8 *save_custom (int *len, uae_u8 *dstptr, int full) SW (v2); } else { uae_u16 v = current_colors.color_regs_ecs[i]; - if (color_regs_genlock[i]) - v |= 0x8000; SW (v); /* 180-1BE COLORxx */ } } @@ -9282,10 +9140,7 @@ uae_u8 *restore_custom_agacolors(uae_u8 *src) for (i = 0; i < 256; i++) { #ifdef AGA uae_u32 v = RL; - color_regs_genlock[i] = 0; - if (v & 0x80000000) - color_regs_genlock[i] = 1; - v &= 0x80ffffff; + v &= 0x00ffffff; current_colors.color_regs_aga[i] = v; #else RL; @@ -9298,13 +9153,23 @@ uae_u8 *save_custom_agacolors (int *len, uae_u8 *dstptr) { uae_u8 *dstbak, *dst; + if (!(currprefs.chipset_mask & CSMASK_AGA)) { + int i; + for (i = 0; i < 256; i++) { + if (current_colors.color_regs_aga[i]) + break; + } + if (i == 256) + return NULL; + } + if (dstptr) dstbak = dst = dstptr; else dstbak = dst = xmalloc (uae_u8, 256 * 4); for (int i = 0; i < 256; i++) #ifdef AGA - SL (current_colors.color_regs_aga[i] | (color_regs_genlock[i] ? 0x80000000 : 0)); + SL (current_colors.color_regs_aga[i]); #else SL (0); #endif @@ -9485,8 +9350,16 @@ void check_prefs_changed_custom (void) if (!config_changed) return; currprefs.gfx_framerate = changed_prefs.gfx_framerate; - if (inputdevice_config_change_test()) - inputdevice_copyconfig(&changed_prefs, &currprefs); + if (currprefs.turbo_emulation_limit != changed_prefs.turbo_emulation_limit) { + currprefs.turbo_emulation_limit = changed_prefs.turbo_emulation_limit; + if (changed_prefs.turbo_emulation) { + warpmode (changed_prefs.turbo_emulation); + } + } + if (currprefs.turbo_emulation != changed_prefs.turbo_emulation) + warpmode (changed_prefs.turbo_emulation); + if (inputdevice_config_change_test ()) + inputdevice_copyconfig (&changed_prefs, &currprefs); currprefs.immediate_blits = changed_prefs.immediate_blits; currprefs.waiting_blits = changed_prefs.waiting_blits; currprefs.collision_level = changed_prefs.collision_level; diff --git a/src/def_icons.cpp b/src/def_icons.cpp deleted file mode 100644 index acf1ec09..00000000 --- a/src/def_icons.cpp +++ /dev/null @@ -1,79 +0,0 @@ -unsigned char def_drawer[] = { -0xe3, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x19, -0x00, 0x05, 0x00, 0x03, 0x00, 0x01, 0x10, 0x12, 0x15, 0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, -0x00, 0x00, 0x10, 0x25, 0xa6, 0xc8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32, -0x00, 0x32, 0x01, 0x90, 0x00, 0x64, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x02, 0x7f, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x5a, 0x00, 0x28, 0xff, 0xff, 0xff, 0xff, 0x00, 0x01, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x18, 0x00, 0x01, -0x00, 0x06, 0xfc, 0x4c, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0xff, 0xf0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0xf0, 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x70, 0x39, 0xff, 0xff, 0x9f, 0xe7, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0x9f, 0xe7, 0xff, 0xfe, 0x70, 0x39, 0xff, 0xff, 0x80, 0x07, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0x80, 0x07, 0xff, 0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, -0xfe, 0x70, 0x39, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x70, 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x70, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0xff, 0xf0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 -}; -unsigned int def_drawer_len = 352; - -unsigned char def_tool[] = { -0xe3, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x33, 0x00, 0x17, -0x00, 0x04, 0x00, 0x01, 0x00, 0x01, 0x10, 0x12, 0xdc, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x33, 0x00, 0x16, 0x00, 0x02, 0x00, 0x06, 0xe8, 0xf8, 0x03, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0x80, 0x00, 0x3c, 0x0f, 0xf0, 0x00, 0x1f, 0xff, 0x80, 0x00, 0x3d, 0xf7, 0xcf, 0xff, 0xe3, 0xff, -0x80, 0x00, 0x3d, 0xf8, 0x3f, 0xff, 0xfc, 0x7f, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0x9f, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xef, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, -0x80, 0x00, 0x3d, 0xf8, 0x3f, 0xff, 0xe0, 0x07, 0x80, 0x00, 0x3d, 0xf7, 0xdf, 0xff, 0xdf, 0xff, -0x80, 0x00, 0x3c, 0x0f, 0xe7, 0xff, 0x3f, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xf9, 0xfc, 0xff, 0xff, -0x80, 0x00, 0x3f, 0xff, 0xfd, 0xfd, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xfd, 0xfd, 0xff, 0xff, -0x80, 0x00, 0x3f, 0xff, 0xfd, 0xfd, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xfc, 0x01, 0xff, 0xff, -0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00 -}; -unsigned int def_tool_len = 450; - -unsigned char def_project[] = { -0xe3, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x31, 0x00, 0x15, -0x00, 0x04, 0x00, 0x01, 0x00, 0x01, 0x10, 0x14, 0x47, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x31, 0x00, 0x14, 0x00, 0x01, 0x00, 0x03, 0x61, 0x34, 0x01, 0x00, 0x00, 0x00, -0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, -0x00, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0x80, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x7f, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xfe, 0xbf, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xfe, 0xdf, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xfe, 0xef, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xfe, 0x07, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, -0x80, 0x00, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x80, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x07, -0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, -0x80, 0x00 -}; -unsigned int def_project_len = 258; diff --git a/src/devices.cpp b/src/devices.cpp index 89cf23ac..def999f4 100644 --- a/src/devices.cpp +++ b/src/devices.cpp @@ -1,16 +1,17 @@ +#include "sysconfig.h" #include "sysdeps.h" +#include "devices.h" + #include "options.h" -#include "thread.h" +#include "threaddep/thread.h" #include "memory.h" #include "audio.h" #include "cd32_fmv.h" #include "akiko.h" -#include "gayle.h" #include "disk.h" #include "cia.h" #include "inputdevice.h" -#include "picasso96.h" #include "blkdev.h" #include "autoconf.h" #include "newcpu.h" @@ -29,31 +30,174 @@ #include "jit/compemu.h" #endif +#define MAX_DEVICE_ITEMS 64 + +static void add_device_item(DEVICE_VOID *pp, int *cnt, DEVICE_VOID p) +{ + for (int i = 0; i < *cnt; i++) { + if (pp[i] == p) + return; + } + if (*cnt >= MAX_DEVICE_ITEMS) { + return; + } + pp[(*cnt)++] = p; +} +static void execute_device_items(DEVICE_VOID *pp, int cnt) +{ + for (int i = 0; i < cnt; i++) { + pp[i](); + } +} + +static int device_configs_cnt; +static DEVICE_VOID device_configs[MAX_DEVICE_ITEMS]; +static int device_vsync_pre_cnt; +static DEVICE_VOID device_vsyncs_pre[MAX_DEVICE_ITEMS]; +static int device_vsync_post_cnt; +static DEVICE_VOID device_vsyncs_post[MAX_DEVICE_ITEMS]; +static int device_hsync_cnt; +static DEVICE_VOID device_hsyncs[MAX_DEVICE_ITEMS]; +static int device_rethink_cnt; +static DEVICE_VOID device_rethinks[MAX_DEVICE_ITEMS]; +static int device_leave_cnt; +static DEVICE_VOID device_leaves[MAX_DEVICE_ITEMS]; +static int device_resets_cnt; +static DEVICE_INT device_resets[MAX_DEVICE_ITEMS]; +static bool device_reset_done[MAX_DEVICE_ITEMS]; + +static void reset_device_items(void) +{ + device_configs_cnt = 0; + device_vsync_pre_cnt = 0; + device_vsync_post_cnt = 0; + device_hsync_cnt = 0; + device_rethink_cnt = 0; + device_resets_cnt = 0; + device_leave_cnt = 0; + memset(device_reset_done, 0, sizeof(device_reset_done)); +} + +void device_add_vsync_pre(DEVICE_VOID p) +{ + add_device_item(device_vsyncs_pre, &device_vsync_pre_cnt, p); +} +void device_add_vsync_post(DEVICE_VOID p) +{ + add_device_item(device_vsyncs_post, &device_vsync_post_cnt, p); +} +void device_add_hsync(DEVICE_VOID p) +{ + add_device_item(device_hsyncs, &device_hsync_cnt, p); +} +void device_add_rethink(DEVICE_VOID p) +{ + add_device_item(device_rethinks, &device_rethink_cnt, p); +} +void device_add_check_config(DEVICE_VOID p) +{ + add_device_item(device_configs, &device_configs_cnt, p); +} +void device_add_exit(DEVICE_VOID p) +{ + add_device_item(device_leaves, &device_leave_cnt, p); +} +void device_add_reset(DEVICE_INT p) +{ + for (int i = 0; i < device_resets_cnt; i++) { + if (device_resets[i] == p) + return; + } + device_resets[device_resets_cnt++] = p; +} +void device_add_reset_imm(DEVICE_INT p) +{ + for (int i = 0; i < device_resets_cnt; i++) { + if (device_resets[i] == p) + return; + } + device_reset_done[device_resets_cnt] = true; + device_resets[device_resets_cnt++] = p; + p(1); +} + void device_check_config(void) { + execute_device_items(device_configs, device_configs_cnt); + + //check_prefs_changed_cd(); check_prefs_changed_audio(); check_prefs_changed_custom(); check_prefs_changed_cpu(); check_prefs_picasso(); } +void devices_reset_ext(int hardreset) +{ + for (int i = 0; i < device_resets_cnt; i++) { + if (!device_reset_done[i]) { + device_resets[i](hardreset); + device_reset_done[i] = true; + } + } +} + void devices_reset(int hardreset) { - gayle_reset(hardreset); + memset(device_reset_done, 0, sizeof(device_reset_done)); + // must be first + init_eventtab(); + init_shm(); + memory_reset(); DISK_reset(); CIA_reset(); - gayle_reset(0); + //a1000_reset(); #ifdef JIT compemu_reset(); #endif +#ifdef WITH_PPC + uae_ppc_reset(is_hardreset()); +#endif + native2amiga_reset(); +#ifdef SCSIEMU + scsi_reset(); + scsidev_reset(); + scsidev_start_threads(); +#endif +#ifdef GFXBOARD + gfxboard_reset (); +#endif +#ifdef DRIVESOUND + driveclick_reset(); +#endif + //ethernet_reset(); +#ifdef FILESYS + filesys_prepare_reset(); + filesys_reset(); +#endif +#if defined (BSDSOCKET) + bsdlib_reset(); +#endif +#ifdef FILESYS + filesys_start_threads(); + hardfile_reset(); +#endif +#ifdef UAESERIAL + uaeserialdev_reset(); + uaeserialdev_start_threads(); +#endif +#if defined (PARALLEL_PORT) + initparallel(); +#endif + //dongle_reset(); + //sampler_init(); + device_func_reset(); #ifdef AUTOCONFIG - expamem_reset(); rtarea_reset(); #endif uae_int_requested = 0; } - void devices_vsync_pre(void) { blkdev_vsync(); @@ -61,34 +205,41 @@ void devices_vsync_pre(void) inputdevice_vsync(); filesys_vsync(); statusline_vsync(); + + execute_device_items(device_vsyncs_pre, device_vsync_pre_cnt); +} + +void devices_vsync_post(void) +{ + execute_device_items(device_vsyncs_post, device_vsync_post_cnt); } void devices_hsync(void) { -#ifdef CD32 - AKIKO_hsync_handler(); - cd32_fmv_hsync_handler(); -#endif - decide_blitter(-1); - -#ifdef PICASSO96 - picasso_handle_hsync(); -#endif DISK_hsync(); audio_hsync(); - gayle_hsync(); + //CIA_hsync_prehandler(); + + decide_blitter (-1); + //serial_hsynchandler (); + + execute_device_items(device_hsyncs, device_hsync_cnt); +} + +void devices_rethink_all(void func(void)) +{ + func(); } -// these really should be dynamically allocated.. void devices_rethink(void) { - rethink_cias(); -#ifdef CD32 - rethink_akiko(); - rethink_cd32fmv(); -#endif - rethink_gayle(); + rethink_cias (); + + execute_device_items(device_rethinks, device_rethink_cnt); + rethink_uae_int(); + /* cpuboard_rethink must be last */ + //cpuboard_rethink(); } void devices_update_sound(double clk, double syncadjust) @@ -101,51 +252,23 @@ void devices_update_sync(double svpos, double syncadjust) cd32_fmv_set_sync(svpos, syncadjust); } -void reset_all_systems(void) +void do_leave_program (void) { - init_eventtab(); - -#ifdef PICASSO96 - picasso_reset(); +#ifdef WITH_PPC + // must be first + uae_ppc_free(); #endif -#ifdef FILESYS - filesys_prepare_reset(); - filesys_reset(); -#endif - init_shm(); - memory_reset(); -#if defined (BSDSOCKET) - bsdlib_reset(); -#endif -#ifdef FILESYS - filesys_start_threads(); - hardfile_reset(); -#endif - native2amiga_reset(); - device_func_reset(); - uae_int_requested = 0; -} - -void do_leave_program(void) -{ -#ifdef JIT - compiler_exit(); -#endif - picasso_free(); graphics_leave(); inputdevice_close(); DISK_free(); close_sound(); dump_counts(); -#ifdef CD32 - akiko_free(); - cd32_fmv_free(); -#endif - gui_exit(); + + if (! no_gui) + gui_exit (); #if defined (USE_SDL1) || defined(USE_SDL2) SDL_Quit(); #endif - hardfile_reset(); #ifdef AUTOCONFIG expansion_cleanup(); #endif @@ -155,18 +278,22 @@ void do_leave_program(void) #ifdef BSDSOCKET bsdlib_reset(); #endif - gayle_free(); device_func_free(); memory_cleanup(); - cfgfile_addcfgparam(nullptr); + free_shm (); + cfgfile_addcfgparam (0); machdep_free(); rtarea_free(); + + execute_device_items(device_leaves, device_leave_cnt); } -void virtualdevice_init(void) +void virtualdevice_init (void) { + reset_device_items(); + #ifdef AUTOCONFIG - rtarea_setup(); + rtarea_setup (); #endif #ifdef FILESYS rtarea_init(); @@ -178,7 +305,7 @@ void virtualdevice_init(void) emulib_install(); #endif #ifdef FILESYS - filesys_install(); + filesys_install (); #endif #if defined (BSDSOCKET) bsdlib_install(); @@ -198,6 +325,7 @@ void devices_restore_start(void) } changed_prefs.mbresmem_low_size = 0; changed_prefs.mbresmem_high_size = 0; + restore_expansion_boards(NULL); } void devices_pause(void) diff --git a/src/disk.cpp b/src/disk.cpp index 41649fdd..ae89e6ff 100644 --- a/src/disk.cpp +++ b/src/disk.cpp @@ -19,8 +19,6 @@ #include "sysdeps.h" -#define MFM_VALIDATOR 0 - #include "uae.h" #include "options.h" #include "memory.h" @@ -40,8 +38,6 @@ #include "crc32.h" #include "fsdb.h" -static int longwritemode = 0; - /* support HD floppies */ #define FLOPPY_DRIVE_HD /* writable track length with normal 2us bitcell/300RPM motor, 12667 PAL, 12797 NTSC */ @@ -73,8 +69,8 @@ static int longwritemode = 0; * L track length in bits */ -static int side, direction, reserved_side; -static uae_u8 selected = 15, disabled, reserved; +static int side, direction; +static uae_u8 selected = 15, disabled; static uae_u8 writebuffer[544 * MAX_SECTORS]; @@ -101,7 +97,7 @@ static uae_u16 word, dsksync; static unsigned long dsksync_cycles; #define WORDSYNC_TIME 11 /* Always carried through to the next line. */ -int disk_hpos; +static int disk_hpos; static int disk_jitter; static int indexdecay; static uae_u8 prev_data; @@ -135,11 +131,10 @@ typedef struct { #define DRIVE_ID_35HD 0xAAAAAAAA #define DRIVE_ID_525SD 0x55555555 /* 40 track 5.25 drive , kickstart does not recognize this */ -typedef enum { ADF_NONE = -1, ADF_NORMAL, ADF_EXT1, ADF_EXT2, ADF_FDI, ADF_IPF, ADF_SCP, ADF_CATWEASEL, ADF_PCDOS, ADF_KICK, ADF_SKICK } drive_filetype; +typedef enum { ADF_NONE = -1, ADF_NORMAL, ADF_EXT1, ADF_EXT2, ADF_FDI, ADF_IPF, ADF_PCDOS, ADF_KICK, ADF_SKICK } drive_filetype; typedef struct { struct zfile *diskfile; struct zfile *writediskfile; - struct zfile *pcdecodedfile; drive_filetype filetype; trackid trackdata[MAX_TRACKS]; trackid writetrackdata[MAX_TRACKS]; @@ -197,7 +192,6 @@ typedef struct { static uae_u16 bigmfmbufw[0x4000 * DDHDMULT]; static drive floppy[MAX_FLOPPY_DRIVES]; -static TCHAR dfxhistory[HISTORY_MAX][MAX_PREVIOUS_IMAGES][MAX_DPATH]; static uae_u8 exeheader[]={0x00,0x00,0x03,0xf3,0x00,0x00,0x00,0x00}; static uae_u8 bootblock_ofs[]={ @@ -532,24 +526,21 @@ static int get_floppy_speed (void) return m; } -static int get_floppy_speed2 (drive *drv) +static int get_floppy_speed_from_image(drive *drv) { - int m = get_floppy_speed () * drv->tracklen / (2 * 8 * FLOPPY_WRITE_LEN * drv->ddhd); + int l, m; + + l = drv->tracklen; + m = get_floppy_speed () * l / (2 * 8 * FLOPPY_WRITE_LEN * drv->ddhd); + + // 4us track? + if (l < (FLOPPY_WRITE_LEN_PAL * 8) * 4 / 6) + m *= 2; + if (m <= 0) m = 1; - return m; -} -static const TCHAR *drive_id_name(drive *drv) -{ - switch (drv->drive_id) - { - case DRIVE_ID_35HD : return _T("3.5HD"); - case DRIVE_ID_525SD: return _T("5.25SD"); - case DRIVE_ID_35DD : return _T("3.5DD"); - case DRIVE_ID_NONE : return _T("NONE"); - } - return _T("UNKNOWN"); + return m; } /* Simulate exact behaviour of an A3000T 3.5 HD disk drive. @@ -583,8 +574,9 @@ static void drive_settype_id (drive *drv) drv->drive_id = DRIVE_ID_525SD; break; case DRV_NONE: - case DRV_PC_ONLY_40: - case DRV_PC_ONLY_80: + case DRV_PC_525_ONLY_40: + case DRV_PC_525_40_80: + case DRV_PC_35_ONLY_80: drv->drive_id = DRIVE_ID_NONE; break; } @@ -611,8 +603,6 @@ static void drive_image_free(drive *drv) drv->diskfile = NULL; zfile_fclose(drv->writediskfile); drv->writediskfile = NULL; - zfile_fclose(drv->pcdecodedfile); - drv->pcdecodedfile = NULL; } static int drive_insert (drive * drv, struct uae_prefs *p, int dnum, const TCHAR *fname, bool fake, bool writeprotected); @@ -628,7 +618,8 @@ static void reset_drive_gui(int num) static bool ispcbridgedrive(int num) { - return currprefs.floppyslots[num].dfxtype == DRV_PC_ONLY_40 || currprefs.floppyslots[num].dfxtype == DRV_PC_ONLY_80; + int type = currprefs.floppyslots[num].dfxtype; + return type == DRV_PC_525_ONLY_40 || type == DRV_PC_35_ONLY_80 || type == DRV_PC_525_40_80; } static void reset_drive(int num) @@ -640,12 +631,10 @@ static void reset_drive(int num) drv->idbit = 0; drv->drive_id = 0; drv->drive_id_scnt = 0; + drv->lastdataacesstrack = -1; disabled &= ~(1 << num); - reserved &= ~(1 << num); if (currprefs.floppyslots[num].dfxtype < 0 || ispcbridgedrive(num)) disabled |= 1 << num; - if (ispcbridgedrive(num)) - reserved |= 1 << num; reset_drive_gui(num); /* most internal Amiga floppy drives won't enable * diskready until motor is running at full speed @@ -688,30 +677,34 @@ static void update_drive_gui (int num, bool force) gui_data.crc32[num] = drv->crc32; gui_data.drive_motor[num] = drv->state; gui_data.drive_track[num] = drv->cyl; - if (reserved & (1 << num)) - gui_data.drive_side = reserved_side; - else - gui_data.drive_side = side; + gui_data.drive_side = side; gui_data.drive_writing[num] = writ; gui_led (num + LED_DF0, (gui_data.drive_motor[num] ? 1 : 0) | (gui_data.drive_writing[num] ? 2 : 0), -1); } static void drive_fill_bigbuf (drive *drv, int); -int DISK_validate_filename (struct uae_prefs *p, const TCHAR *fname, int leave_open, bool *wrprot, uae_u32 *crc32, struct zfile **zf) +int DISK_validate_filename (struct uae_prefs *p, const TCHAR *fname_in, TCHAR *outfname, int leave_open, bool *wrprot, uae_u32 *crc32, struct zfile **zf) { + TCHAR outname[MAX_DPATH]; + if (zf) *zf = NULL; if (crc32) *crc32 = 0; if (wrprot) *wrprot = p->floppy_read_only ? 1 : 0; + + cfgfile_resolve_path_out_load(fname_in, outname, MAX_DPATH, PATH_FLOPPY); + if (outfname) + _tcscpy(outfname, outname); + if (leave_open || !zf) { - struct zfile *f = zfile_fopen (fname, _T("r+b"), ZFD_NORMAL | ZFD_DISKHISTORY); + struct zfile *f = zfile_fopen (outname, _T("r+b"), ZFD_NORMAL | ZFD_DISKHISTORY); if (!f) { if (wrprot) *wrprot = 1; - f = zfile_fopen (fname, _T("rb"), ZFD_NORMAL | ZFD_DISKHISTORY); + f = zfile_fopen (outname, _T("rb"), ZFD_NORMAL | ZFD_DISKHISTORY); } if (f && crc32) *crc32 = zfile_crc32 (f); @@ -721,11 +714,11 @@ int DISK_validate_filename (struct uae_prefs *p, const TCHAR *fname, int leave_o *zf = f; return f ? 1 : 0; } else { - if (zfile_exists (fname)) { + if (zfile_exists (outname)) { if (wrprot && !p->floppy_read_only) *wrprot = 0; if (crc32) { - struct zfile *f = zfile_fopen (fname, _T("rb"), ZFD_NORMAL | ZFD_DISKHISTORY); + struct zfile *f = zfile_fopen (outname, _T("rb"), ZFD_NORMAL | ZFD_DISKHISTORY); if (f) *crc32 = zfile_crc32 (f); zfile_fclose (f); @@ -869,7 +862,7 @@ static TCHAR *DISK_get_default_saveimagepath (const TCHAR *name) // -1 = as configured // 0 = saveimages-dir // 1 = image dir -TCHAR *DISK_get_saveimagepath(const TCHAR *name, int type) +static TCHAR *DISK_get_saveimagepath(const TCHAR *name, int type) { int typev = type; @@ -899,13 +892,15 @@ static struct zfile *getexistingwritefile(struct uae_prefs *p, const TCHAR *name { struct zfile *zf = NULL; TCHAR *path; + TCHAR outname[MAX_DPATH]; + path = DISK_get_saveimagepath(name, 0); - DISK_validate_filename (p, path, 1, wrprot, NULL, &zf); + DISK_validate_filename (p, path, outname, 1, wrprot, NULL, &zf); xfree(path); if (zf) return zf; - path = DISK_get_saveimagepath(name, -1); - DISK_validate_filename (p, path, 1, wrprot, NULL, &zf); + path = DISK_get_saveimagepath(name, 1); + DISK_validate_filename (p, path, outname, 1, wrprot, NULL, &zf); xfree(path); return zf; } @@ -919,16 +914,20 @@ static int iswritefileempty (struct uae_prefs *p, const TCHAR *name) int tracks, ddhd, i, ret; zf = getexistingwritefile (p, name, &wrprot); - if (!zf) return 1; + if (!zf) + return 1; zfile_fread (buffer, sizeof (char), 8, zf); - if (strncmp ((uae_char*)buffer, "UAE-1ADF", 8)) + if (strncmp ((uae_char*)buffer, "UAE-1ADF", 8)) { + zfile_fclose(zf); return 0; + } ret = read_header_ext2 (zf, td, &tracks, &ddhd); zfile_fclose (zf); if (!ret) return 1; for (i = 0; i < tracks; i++) { - if (td[i].bitlen) return 0; + if (td[i].bitlen) + return 0; } return 1; } @@ -954,22 +953,23 @@ static int openwritefile (struct uae_prefs *p, drive *drv, int create) return drv->writediskfile ? 1 : 0; } -static bool diskfile_iswriteprotect(struct uae_prefs *p, const TCHAR *fname, int *needwritefile, drive_type *drvtype) +static bool diskfile_iswriteprotect (struct uae_prefs *p, const TCHAR *fname_in, int *needwritefile, drive_type *drvtype) { struct zfile *zf1, *zf2; bool wrprot1 = 0, wrprot2 = 1; uae_char buffer[25]; + TCHAR outname[MAX_DPATH]; *needwritefile = 0; *drvtype = DRV_35_DD; - DISK_validate_filename(p, fname, 1, &wrprot1, NULL, &zf1); + DISK_validate_filename (p, fname_in, outname, 1, &wrprot1, NULL, &zf1); if (!zf1) return 1; if (zfile_iscompressed(zf1)) { wrprot1 = 1; *needwritefile = 1; } - zf2 = getexistingwritefile(p, fname, &wrprot2); + zf2 = getexistingwritefile(p, fname_in, &wrprot2); zfile_fclose(zf2); zfile_fread(buffer, sizeof(char), 25, zf1); zfile_fclose(zf1); @@ -1008,17 +1008,20 @@ static bool isrecognizedext (const TCHAR *name) return false; } -static int drive_insert(drive * drv, struct uae_prefs *p, int dnum, const TCHAR *fname, bool fake, bool forcedwriteprotect) +static int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di); + +static int drive_insert (drive * drv, struct uae_prefs *p, int dnum, const TCHAR *fname_in, bool fake, bool forcedwriteprotect) { uae_u8 buffer[2 + 2 + 4 + 4]; trackid *tid; int num_tracks, size; int canauto; + TCHAR outname[MAX_DPATH]; drive_image_free (drv); if (!fake) DISK_examine_image(p, dnum, &disk_info_data); - DISK_validate_filename (p, fname, 1, &drv->wrprot, &drv->crc32, &drv->diskfile); + DISK_validate_filename (p, fname_in, outname, 1, &drv->wrprot, &drv->crc32, &drv->diskfile); drv->forcedwrprot = forcedwriteprotect; if (drv->forcedwrprot) drv->wrprot = true; @@ -1038,23 +1041,23 @@ static int drive_insert(drive * drv, struct uae_prefs *p, int dnum, const TCHAR drv->dskready_down_time = 0; } - if (drv->diskfile == 0) { + if (drv->diskfile == NULL) { track_reset (drv); return 0; } if (!fake) { - if (currprefs.floppyslots[dnum].df != fname) { - _tcsncpy (currprefs.floppyslots[dnum].df, fname, 255); + if (currprefs.floppyslots[dnum].df != fname_in) { + _tcsncpy (currprefs.floppyslots[dnum].df, fname_in, 255); currprefs.floppyslots[dnum].df[255] = 0; } currprefs.floppyslots[dnum].forcedwriteprotect = forcedwriteprotect; - _tcsncpy (changed_prefs.floppyslots[dnum].df, fname, 255); + _tcsncpy (changed_prefs.floppyslots[dnum].df, fname_in, 255); changed_prefs.floppyslots[dnum].df[255] = 0; changed_prefs.floppyslots[dnum].forcedwriteprotect = forcedwriteprotect; - _tcscpy (drv->newname, fname); + _tcscpy (drv->newname, fname_in); drv->newnamewriteprotected = forcedwriteprotect; - gui_filename (dnum, fname); + gui_filename (dnum, outname); } memset (buffer, 0, sizeof buffer); @@ -1067,21 +1070,23 @@ static int drive_insert(drive * drv, struct uae_prefs *p, int dnum, const TCHAR } canauto = 0; - if (isrecognizedext (fname)) + if (isrecognizedext (outname)) canauto = 1; if (!canauto && drv->diskfile && isrecognizedext (zfile_getname (drv->diskfile))) canauto = 1; - // if PC-only drive, make sure PC-like floppies are alwayss detected + // if PC-only drive, make sure PC-like floppies are always detected if (!canauto && ispcbridgedrive(dnum)) canauto = 1; if (0) { + + #ifdef CAPS - } - else if (strncmp((char*)buffer, "CAPS", 4) == 0) { - drv->wrprot = false; - if (!caps_loadimage(drv->diskfile, drv - floppy, &num_tracks)) { - zfile_fclose(drv->diskfile); + } else if (strncmp ((char*)buffer, "CAPS", 4) == 0) { + + drv->wrprot = true; + if (!caps_loadimage (drv->diskfile, drv - floppy, &num_tracks)) { + zfile_fclose (drv->diskfile); drv->diskfile = 0; return 0; } @@ -1175,32 +1180,35 @@ static int drive_insert(drive * drv, struct uae_prefs *p, int dnum, const TCHAR size == 9 * 82 * 1 * 512 || size == 18 * 82 * 1 * 512 || size == 10 * 82 * 1 * 512 || size == 20 * 82 * 1 * 512)) { /* PC formatted image */ int side, sd; + int dfxtype = p->floppyslots[dnum].dfxtype; drv->num_secs = 9; drv->ddhd = 1; sd = 0; - bool can40 = p->floppyslots[dnum].dfxtype == DRV_525_DD || p->floppyslots[dnum].dfxtype == DRV_PC_ONLY_40; + bool can40 = dfxtype == DRV_525_DD || dfxtype == DRV_PC_525_ONLY_40 || dfxtype == DRV_PC_525_40_80; + bool can80 = dfxtype == DRV_35_HD || dfxtype == DRV_PC_35_ONLY_80 || dfxtype == DRV_PC_525_40_80; + bool drv525 = dfxtype == DRV_525_DD || dfxtype == DRV_PC_525_ONLY_40 || dfxtype == DRV_PC_525_40_80; for (side = 2; side > 0; side--) { - if (drv->hard_num_cyls >= 80 && !can40) { + if (drv->hard_num_cyls >= 80 && can80) { if ( size == 9 * 80 * side * 512 || size == 9 * 81 * side * 512 || size == 9 * 82 * side * 512) { drv->num_secs = 9; drv->ddhd = 1; break; - } else if (size == 18 * 80 * side * 512 || size == 18 * 81 * side * 512 || size == 18 * 82 * side * 512) { + } else if (!drv525 && (size == 18 * 80 * side * 512 || size == 18 * 81 * side * 512 || size == 18 * 82 * side * 512)) { drv->num_secs = 18; drv->ddhd = 2; break; - } else if (size == 10 * 80 * side * 512 || size == 10 * 81 * side * 512 || size == 10 * 82 * side * 512) { + } else if (!drv525 && (size == 10 * 80 * side * 512 || size == 10 * 81 * side * 512 || size == 10 * 82 * side * 512)) { drv->num_secs = 10; drv->ddhd = 1; break; - } else if (size == 20 * 80 * side * 512 || size == 20 * 81 * side * 512 || size == 20 * 82 * side * 512) { + } else if (!drv525 && (size == 20 * 80 * side * 512 || size == 20 * 81 * side * 512 || size == 20 * 82 * side * 512)) { drv->num_secs = 20; drv->ddhd = 2; break; - } else if (size == 21 * 80 * side * 512 || size == 21 * 81 * side * 512 || size == 21 * 82 * side * 512) { + } else if (!drv525 && (size == 21 * 80 * side * 512 || size == 21 * 81 * side * 512 || size == 21 * 82 * side * 512)) { drv->num_secs = 21; drv->ddhd = 2; break; @@ -1766,7 +1774,6 @@ static void drive_fill_bigbuf(drive * drv, int force) drv->tracktiming[0] = 0; drv->skipoffset = -1; drv->revolutions = 1; - retrytrack = drv->lastdataacesstrack == drv->cyl * 2 + side; if (!dskdmaen && !retrytrack) drv->track_access_done = false; @@ -1783,6 +1790,7 @@ static void drive_fill_bigbuf(drive * drv, int force) *mfm = 256 * *data + *(data + 1); } } else if (drv->filetype == ADF_IPF) { + #ifdef CAPS caps_loadtrack(drv->bigmfmbuf, drv->tracktiming, drv - floppy, tr, &drv->tracklen, &drv->multi_revolution, &drv->skipoffset, &drv->lastrev, retrytrack); #endif @@ -1833,7 +1841,7 @@ static void drive_fill_bigbuf(drive * drv, int force) memset(drv->bigmfmbuf, 0, FLOPPY_WRITE_LEN * 2 * drv->ddhd); } - drv->trackspeed = get_floppy_speed2(drv); + drv->trackspeed = get_floppy_speed_from_image (drv); updatemfmpos(drv); } @@ -1872,26 +1880,6 @@ static uae_u32 getmfmlong (uae_u16 *mbuf, int shift) return ((getmfmword (mbuf, shift) << 16) | getmfmword (mbuf + 1, shift)) & MFMMASK; } -#if MFM_VALIDATOR -static void check_valid_mfm (uae_u16 *mbuf, int words, int sector) -{ - int prevbit = 0; - for (int i = 0; i < words * 8; i++) { - int wordoffset = i / 8; - uae_u16 w = mbuf[wordoffset]; - uae_u16 wp = mbuf[wordoffset - 1]; - int bitoffset = (7 - (i & 7)) * 2; - int clockbit = w & (1 << (bitoffset + 1)); - int databit = w & (1 << (bitoffset + 0)); - - if ((clockbit && databit) || (clockbit && !databit && prevbit) || (!clockbit && !databit && !prevbit)) { - write_log (_T("illegal mfm sector %d data %04x %04x, bit %d:%d\n"), sector, wp, w, wordoffset, bitoffset); - } - prevbit = databit; - } -} -#endif - static int decode_buffer (uae_u16 *mbuf, int cyl, int drvsec, int ddhd, int filetype, int *drvsecp, int *sectable, int checkmode) { int i, secwritten = 0; @@ -1939,9 +1927,6 @@ static int decode_buffer (uae_u16 *mbuf, int cyl, int drvsec, int ddhd, int file return 2; continue; } -#if MFM_VALIDATOR - check_valid_mfm (mbuf - 4, 544 - 4 + 1, trackoffs); -#endif issechead = false; chksum = odd ^ even; for (i = 0; i < 4; i++) { @@ -2208,6 +2193,7 @@ static bool convert_adf_to_ext2 (drive *drv, int mode) zfile_fclose (tmp); return false; } + zfile_fclose(tmp); } else { return false; } @@ -2240,7 +2226,7 @@ static void drive_write_data (drive * drv) } if (drv->writediskfile) { drive_write_ext2 (drv->bigmfmbuf, drv->writediskfile, &drv->writetrackdata[tr], - longwritemode ? dsklength2 * 8 : drv->tracklen); + drv->tracklen); } switch (drv->filetype) { case ADF_NORMAL: @@ -2263,14 +2249,15 @@ static void drive_write_data (drive * drv) case ADF_EXT1: break; case ADF_EXT2: - if (!longwritemode) - ret = drive_write_adf_amigados (drv); + ret = drive_write_adf_amigados (drv); if (ret) { write_log (_T("not an amigados track %d (error %d), writing as raw track\n"), drv->cyl * 2 + side, ret); drive_write_ext2 (drv->bigmfmbuf, drv->diskfile, &drv->trackdata[drv->cyl * 2 + side], - longwritemode ? dsklength2 * 8 : drv->tracklen); + drv->tracklen); } return; + case ADF_IPF: + break; case ADF_PCDOS: ret = drive_write_pcdos (drv, drv->diskfile, 0); if (ret < 0) @@ -2290,6 +2277,7 @@ static void drive_eject (drive * drv) drv->dskready = 0; drv->dskready_up_time = 0; drv->dskready_down_time = 0; + drv->forcedwrprot = false; drv->crc32 = 0; drive_settype_id (drv); /* Back to 35 DD */ } @@ -2341,7 +2329,7 @@ bool disk_creatediskfile (struct uae_prefs *p, const TCHAR *name, int type, driv tracks = 2 * 80; file_size = 880 * 1024; sectors = 11; - if (adftype == DRV_PC_ONLY_40 || adftype == DRV_PC_ONLY_80) { + if (adftype == DRV_PC_525_ONLY_40 || adftype == DRV_PC_35_ONLY_80 || adftype == DRV_PC_525_40_80) { file_size = 720 * 1024; sectors = 9; } @@ -2353,7 +2341,10 @@ bool disk_creatediskfile (struct uae_prefs *p, const TCHAR *name, int type, driv file_size *= 2; track_len *= 2; ddhd = 2; - } else if (adftype == DRV_PC_ONLY_40) { + if (adftype == DRV_PC_525_40_80) { + file_size = 15 * 512 * 80 * 2; + } + } else if (adftype == DRV_PC_525_ONLY_40) { file_size /= 2; tracks /= 2; } @@ -2478,7 +2469,7 @@ void DISK_reinsert (int num) setdskchangetime (&floppy[num], 2 * 50 * 312); } -int disk_setwriteprotect (struct uae_prefs *p, int num, const TCHAR *name, bool writeprotected) +int disk_setwriteprotect (struct uae_prefs *p, int num, const TCHAR *fname_in, bool writeprotected) { int needwritefile, oldprotect; struct zfile *zf1, *zf2; @@ -2486,38 +2477,45 @@ int disk_setwriteprotect (struct uae_prefs *p, int num, const TCHAR *name, bool int i; TCHAR *name2; drive_type drvtype; + TCHAR outfname[MAX_DPATH]; - write_log(_T("disk_setwriteprotect %d '%s' %d\n"), num, name, writeprotected); + write_log(_T("disk_setwriteprotect %d '%s' %d\n"), num, fname_in, writeprotected); - oldprotect = diskfile_iswriteprotect (p, name, &needwritefile, &drvtype); - DISK_validate_filename (p, name, 1, &wrprot1, NULL, &zf1); + oldprotect = diskfile_iswriteprotect (p, fname_in, &needwritefile, &drvtype); + DISK_validate_filename (p, fname_in, outfname, 1, &wrprot1, NULL, &zf1); if (!zf1) return 0; write_log(_T("old = %d writeprot = %d master = %d\n"), oldprotect, wrprot1, p->floppy_read_only); - if (wrprot1 && p->floppy_read_only) + if (wrprot1 && p->floppy_read_only) { + zfile_fclose(zf1); return 0; + } if (zfile_iscompressed (zf1)) wrprot1 = 1; zfile_fclose (zf1); - zf2 = getexistingwritefile(p, name, &wrprot2); - name2 = DISK_get_saveimagepath(name, -2); + zf2 = getexistingwritefile(p, fname_in, &wrprot2); + name2 = DISK_get_saveimagepath(fname_in, -2); - if (needwritefile && zf2 == 0) + if (needwritefile && zf2 == NULL) disk_creatediskfile (p, name2, 1, drvtype, -1, NULL, false, false, NULL); zfile_fclose (zf2); - if (writeprotected && iswritefileempty (p, name)) { + if (writeprotected && iswritefileempty (p, fname_in)) { for (i = 0; i < MAX_FLOPPY_DRIVES; i++) { - if (!_tcscmp (name, floppy[i].newname)) + if (!_tcscmp (fname_in, floppy[i].newname)) drive_eject (&floppy[i]); } _wunlink (name2); } if (!needwritefile) - diskfile_readonly (name, writeprotected); + diskfile_readonly (outfname, writeprotected); diskfile_readonly (name2, writeprotected); + + floppy[num].forcedwrprot = false; + floppy[num].newnamewriteprotected = false; + return 1; } @@ -2531,54 +2529,6 @@ void disk_eject (int num) update_drive_gui (num, true); } -int DISK_history_add (const TCHAR *name, int idx, int type, int donotcheck) -{ - int i; - - if (idx >= MAX_PREVIOUS_IMAGES) - return 0; - if (name == NULL) { - if (idx < 0) - return 0; - dfxhistory[type][idx][0] = 0; - return 1; - } - if (name[0] == 0) - return 0; - if (idx >= 0) { - if (idx >= MAX_PREVIOUS_IMAGES) - return 0; - dfxhistory[type][idx][0] = 0; - for (i = 0; i < MAX_PREVIOUS_IMAGES; i++) { - if (!_tcsicmp (dfxhistory[type][i], name)) - return 0; - } - _tcscpy (dfxhistory[type][idx], name); - return 1; - } - for (i = 0; i < MAX_PREVIOUS_IMAGES; i++) { - if (!_tcscmp (dfxhistory[type][i], name)) { - while (i < MAX_PREVIOUS_IMAGES - 1) { - _tcscpy (dfxhistory[type][i], dfxhistory[type][i + 1]); - i++; - } - dfxhistory[type][MAX_PREVIOUS_IMAGES - 1][0] = 0; - break; - } - } - for (i = MAX_PREVIOUS_IMAGES - 2; i >= 0; i--) - _tcscpy (dfxhistory[type][i + 1], dfxhistory[type][i]); - _tcscpy (dfxhistory[type][0], name); - return 1; -} - -TCHAR *DISK_history_get (int idx, int type) -{ - if (idx >= MAX_PREVIOUS_IMAGES) - return NULL; - return dfxhistory[type][idx]; -} - static void disk_insert_2 (int num, const TCHAR *name, bool forced, bool forcedwriteprotect) { drive *drv = floppy + num; @@ -2594,7 +2544,6 @@ static void disk_insert_2 (int num, const TCHAR *name, bool forced, bool forcedw drv->newnamewriteprotected = forcedwriteprotect; _tcscpy (currprefs.floppyslots[num].df, name); currprefs.floppyslots[num].forcedwriteprotect = forcedwriteprotect; - DISK_history_add (name, -1, HISTORY_FLOPPY, 0); if (name[0] == 0) { disk_eject (num); } else if (!drive_empty(drv) || drv->dskchange_time > 0) { @@ -2618,10 +2567,6 @@ void disk_insert (int num, const TCHAR *name) target_addtorecent (name, 0); disk_insert_2 (num, name, 0, false); } -void disk_insert_force (int num, const TCHAR *name, bool forcedwriteprotect) -{ - disk_insert_2 (num, name, 1, forcedwriteprotect); -} static void DISK_check_change (void) { @@ -2664,14 +2609,6 @@ int disk_empty (int num) return drive_empty (floppy + num); } -static TCHAR *tobin (uae_u8 v) -{ - static TCHAR buf[9]; - for (int i = 7; i >= 0; i--) - buf[7 - i] = v & (1 << i) ? '1' : '0'; - return buf; -} - static void fetch_DISK_select(uae_u8 data) { selected = (data >> 3) & 15; @@ -2824,7 +2761,6 @@ STATIC_INLINE uae_u32 getonebit (uae_u16 * mfmbuf, int mfmpos) static void disk_dmafinished (void) { INTREQ (0x8000 | 0x0002); - longwritemode = 0; dskdmaen = DSKDMA_OFF; dsklength = 0; dsklen = 0; @@ -2834,7 +2770,7 @@ static void fetchnextrevolution(drive *drv) { if (drv->revolution_check) return; - drv->trackspeed = get_floppy_speed2(drv); + drv->trackspeed = get_floppy_speed_from_image (drv); drv->revolution_check = 2; if (!drv->multi_revolution) return; @@ -2903,8 +2839,12 @@ static void disk_doupdate_write (drive * drv, int floppybits) while (floppybits >= drv->trackspeed) { for (dr = 0; dr < MAX_FLOPPY_DRIVES; dr++) { if (drives[dr]) { - floppy[dr].mfmpos++; - floppy[dr].mfmpos %= drv->tracklen; + drive *drv2 = &floppy[dr]; + drv2->mfmpos++; + drv2->mfmpos %= drv2->tracklen; + if (drv2->mfmpos == drv2->indexoffset) { + do_disk_index(); + } } } if (dmaen (DMA_DISK) && dskdmaen == DSKDMA_WRITE && dsklength > 0 && fifo_filled) { @@ -2958,7 +2898,7 @@ static void updatetrackspeed (drive *drv, int mfmpos) { if (dskdmaen < DSKDMA_WRITE) { int t = drv->tracktiming[mfmpos / 8]; - int ts = get_floppy_speed2 (drv) * t / 1000; + int ts = get_floppy_speed_from_image (drv) * t / 1000; if (ts < 700 || ts > 3000) { } else { drv->trackspeed = ts; @@ -2984,8 +2924,7 @@ static void disk_doupdate_predict (int startcycle) updatetrackspeed (drv, mfmpos); int diskevent_flag = 0; uae_u32 tword = word; - //int diff = drv->floppybitcounter % drv->trackspeed; - int countcycle = startcycle; // + (diff ? drv->trackspeed - diff : 0); + int countcycle = startcycle; while (countcycle < (maxhpos << 8)) { if (drv->tracktiming[0]) updatetrackspeed (drv, mfmpos); @@ -3099,7 +3038,7 @@ static void wordsync_detected(bool startup) dma_enable = 1; INTREQ (0x8000 | 0x1000); } - if (adkcon & 0x0400) { + if (adkcon & 0x0400) { // WORDSYNC bitoffset = 15; } } @@ -3125,8 +3064,11 @@ static void disk_doupdate_read (drive * drv, int floppybits) mfmbuf[7] = 0x4444; */ while (floppybits >= drv->trackspeed) { + bool skipbit = false; + if (drv->tracktiming[0]) updatetrackspeed (drv, drv->mfmpos); + word <<= 1; if (!drive_empty (drv)) { @@ -3135,6 +3077,7 @@ static void disk_doupdate_read (drive * drv, int floppybits) else word |= getonebit (drv->bigmfmbuf, drv->mfmpos); } + if (doreaddma () < 0) { word >>= 1; return; @@ -3166,14 +3109,34 @@ static void disk_doupdate_read (drive * drv, int floppybits) } } } - if ((bitoffset & 7) == 7) { + + // MSBSYNC + if (adkcon & 0x200) { + if ((word & 0x0001) == 0 && bitoffset == 0) { + word = 0; + skipbit = true; + } + if ((word & 0x0001) == 0 && bitoffset == 8) { + word >>= 1; + skipbit = true; + } + } + + if (!skipbit && (bitoffset & 7) == 7) { dskbytr_val = word & 0xff; dskbytr_val |= 0x8000; } - if (word == dsksync) + + // WORDSYNC + if (!(adkcon & 0x200) && word == dsksync) { wordsync_detected(false); - bitoffset++; - bitoffset &= 15; + } + + if (!skipbit) { + bitoffset++; + bitoffset &= 15; + } + floppybits -= drv->trackspeed; } } @@ -3198,6 +3161,10 @@ uae_u16 DSKBYTR (int hpos) drive *drv = &floppy[dr]; if (drv->motoroff) continue; + if (!((selected | disabled) & (1 << dr))) { + drv->lastdataacesstrack = drv->cyl * 2 + side; + drv->track_access_done = true; + } } return v; } @@ -3218,7 +3185,7 @@ static void DISK_start (void) if (dskdmaen == DSKDMA_WRITE) { word = 0; - drv->tracklen = longwritemode ? FLOPPY_WRITE_MAXLEN : FLOPPY_WRITE_LEN * drv->ddhd * 8 * 2; + drv->tracklen = FLOPPY_WRITE_LEN * drv->ddhd * 8 * 2; drv->trackspeed = get_floppy_speed(); drv->skipoffset = -1; updatemfmpos (drv); @@ -3352,7 +3319,9 @@ void DISK_update (int tohpos) void DSKLEN (uae_u16 v, int hpos) { - int dr, prev = dsklen; + int dr; + int prevlen = dsklen; + int prevdatalen = dsklength; int noselected = 0; int motormask; @@ -3361,10 +3330,10 @@ void DSKLEN (uae_u16 v, int hpos) dsklen = v; dsklength2 = dsklength = dsklen & 0x3fff; - if ((v & 0x8000) && (prev & 0x8000)) { - if (dskdmaen == DSKDMA_READ) { + if ((v & 0x8000) && (prevlen & 0x8000)) { + if (dskdmaen == DSKDMA_READ && !(v & 0x4000)) { // update only currently active DMA length, don't change DMA state - write_log(_T("warning: Disk read DMA length rewrite %d -> %d. (%04x) PC=%08x\n"), prev & 0x3fff, v & 0x3fff, v, M68K_GETPC); + write_log(_T("warning: Disk read DMA length rewrite %d -> %d. (%04x) PC=%08x\n"), prevlen & 0x3fff, v & 0x3fff, v, M68K_GETPC); return; } dskdmaen = DSKDMA_READ; @@ -3374,7 +3343,7 @@ void DSKLEN (uae_u16 v, int hpos) if (dskdmaen != DSKDMA_OFF) { /* Megalomania and Knightmare does this */ if (dskdmaen == DSKDMA_WRITE) { - write_log (_T("warning: Disk write DMA aborted, %d words left PC=%x\n"), dsklength, M68K_GETPC); + write_log (_T("warning: Disk write DMA aborted, %d words left PC=%x\n"), prevdatalen, M68K_GETPC); // did program write something that needs to be stored to file? for (dr = 0; dr < MAX_FLOPPY_DRIVES; dr++) { drive *drv2 = &floppy[dr]; @@ -3395,7 +3364,7 @@ void DSKLEN (uae_u16 v, int hpos) return; } - if ((v & 0x4000) && (prev & 0x4000)) { + if ((v & 0x4000) && (prevlen & 0x4000)) { if (dsklength == 0) return; if (dsklength == 1) { @@ -3403,7 +3372,7 @@ void DSKLEN (uae_u16 v, int hpos) return; } if (dskdmaen == DSKDMA_WRITE) { - write_log(_T("warning: Disk write DMA length rewrite %d -> %d\n"), prev & 0x3fff, v & 0x3fff); + write_log(_T("warning: Disk write DMA length rewrite %d -> %d\n"), prevlen & 0x3fff, v & 0x3fff); return; } dskdmaen = DSKDMA_WRITE; @@ -3416,6 +3385,10 @@ void DSKLEN (uae_u16 v, int hpos) continue; if (selected & (1 << dr)) continue; + if (dskdmaen == DSKDMA_READ) { + drv->lastdataacesstrack = drv->cyl * 2 + side; + drv->track_access_done = true; + } } motormask = 0; @@ -3519,6 +3492,7 @@ void DSKLEN (uae_u16 v, int hpos) } } if (!done && noselected) { + int bits = -1; while (dsklength-- > 0) { if (dskdmaen == DSKDMA_WRITE) { uae_u16 w = chipmem_wget_indirect (dskpt); @@ -3527,9 +3501,13 @@ void DSKLEN (uae_u16 v, int hpos) } dskpt += 2; } - INTREQ (0x8000 | 0x1000); - done = 2; - } + if (bits == 0) { + done = 1; + } else { + INTREQ (0x8000 | 0x1000); + done = 2; + } + } if (done) { linecounter = done; @@ -3683,7 +3661,7 @@ static void load_track (int num, int cyl, int side, int *sectable) drv->buffered_cyl = -1; } -int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) +static int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) { int drvsec; int ret, i; @@ -3696,7 +3674,6 @@ int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) ret = 0; memset (di, 0, sizeof (struct diskinfo)); - di->unreadable = true; oldcyl = drv->cyl; oldside = side; drv->cyl = 0; @@ -3707,7 +3684,6 @@ int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) return 1; } di->crc32 = zfile_crc32 (drv->diskfile); - di->unreadable = false; decode_buffer (drv->bigmfmbuf, drv->cyl, 11, drv->ddhd, drv->filetype, &drvsec, sectable, 1); di->hd = drv->ddhd == 2; drv->cyl = oldcyl; @@ -3742,11 +3718,7 @@ int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) ret = 3; goto end; } - di->bb_crc_valid = true; writebuffer[4] = writebuffer[5] = writebuffer[6] = writebuffer[7] = 0; - if (get_crc32 (writebuffer, 0x31) == 0xae5e282c) { - di->bootblocktype = 1; - } if (dos == 0x444f5300) ret = 10; else if (dos == 0x444f5301 || dos == 0x444f5302 || dos == 0x444f5303) @@ -3756,9 +3728,6 @@ int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di) else ret = 4; v = get_crc32 (writebuffer + 8, 0x5c - 8); - if (ret >= 10 && v == 0xe158ca4b) { - di->bootblocktype = 2; - } end: load_track (num, 40, 0, sectable); if (sectable[0]) { @@ -3895,11 +3864,16 @@ uae_u8 *restore_disk(int num,uae_u8 *src) drv->dskchange_time = 0; restore_u32 (); s = restore_path (SAVESTATE_PATH_FLOPPY); - _tcscpy (old, currprefs.floppyslots[num].df); - _tcsncpy(changed_prefs.floppyslots[num].df, s,255); - xfree (s); int dskready_up_time = restore_u16 (); int dskready_down_time = restore_u16 (); + if (restore_u32() & 1) { + xfree(s); + s = restore_path_full(); + } + _tcscpy (old, currprefs.floppyslots[num].df); + _tcsncpy(changed_prefs.floppyslots[num].df, s, MAX_DPATH); + xfree (s); + newis = changed_prefs.floppyslots[num].df[0] ? 1 : 0; if (!(disabled & (1 << num))) { if (!newis && old[0]) { @@ -3908,7 +3882,7 @@ uae_u8 *restore_disk(int num,uae_u8 *src) } else if (newis) { drive_insert (floppy + num, &currprefs, num, changed_prefs.floppyslots[num].df, false, false); if (drive_empty (floppy + num)) { - if (newis && old[0]) { + if (newis && zfile_exists(old)) { _tcscpy (changed_prefs.floppyslots[num].df, old); drive_insert (floppy + num, &currprefs, num, changed_prefs.floppyslots[num].df, false, false); if (drive_empty (floppy + num)) @@ -3916,6 +3890,8 @@ uae_u8 *restore_disk(int num,uae_u8 *src) } else { drv->dskchange_time = -1; _tcscpy(drv->newname, changed_prefs.floppyslots[num].df); + _tcscpy(currprefs.floppyslots[num].df, drv->newname); + write_log(_T("Disk image not found, faking inserted disk.\n")); } } } @@ -3958,7 +3934,7 @@ uae_u8 *save_disk (int num, int *len, uae_u8 *dstptr, bool usepath) if (dstptr) dstbak = dst = dstptr; else - dstbak = dst = xmalloc (uae_u8, 2 + 1 + 1 + 1 + 1 + 4 + 4 + 256); + dstbak = dst = xmalloc (uae_u8, 2 + 1 + 1 + 1 + 1 + 4 + 4 + MAX_DPATH + 2 + 2 + 4 + 2 * MAX_DPATH); save_u32 (drv->drive_id); /* drive type ID */ save_u8 ((drv->motoroff ? 0 : 1) | ((disabled & (1 << num)) ? 2 : 0) | (drv->idbit ? 4 : 0) | (drv->dskchange ? 8 : 0) | (side ? 16 : 0) | (drv->wrprot ? 32 : 0)); save_u8 (drv->cyl); /* cylinder */ @@ -3969,6 +3945,11 @@ uae_u8 *save_disk (int num, int *len, uae_u8 *dstptr, bool usepath) save_path (usepath ? currprefs.floppyslots[num].df : _T(""), SAVESTATE_PATH_FLOPPY);/* image name */ save_u16 (drv->dskready_up_time); save_u16 (drv->dskready_down_time); + if (usepath) { + save_u32(1); + save_path_full(currprefs.floppyslots[num].df, SAVESTATE_PATH_FLOPPY); + } + *len = dst - dstbak; return dstbak; } @@ -3982,9 +3963,11 @@ uae_u8 *save_disk2 (int num, int *len, uae_u8 *dstptr) int size = 0; if (drv->motoroff == 0 && drv->buffered_side >= 0 && drv->tracklen > 0) { m = 1; - if (drv->tracktiming[0]) - m |= 2; size += ((drv->tracklen + 15) * 2) / 8; + if (drv->tracktiming[0]) { + m |= 2; + size *= 2; + } } if (!m) return NULL; diff --git a/src/dlopen.cpp b/src/dlopen.cpp index b04669f0..ab4c2b23 100644 --- a/src/dlopen.cpp +++ b/src/dlopen.cpp @@ -1,8 +1,6 @@ #include "sysdeps.h" #include "uae/dlopen.h" -#define FSUAE - #ifdef _WIN32 #include "windows.h" #else @@ -36,11 +34,6 @@ UAE_DLHANDLE uae_dlopen(const TCHAR *path) void *uae_dlsym(UAE_DLHANDLE handle, const char *name) { -#if 0 - if (handle == NULL) { - return NULL; - } -#endif #ifdef _WIN32 return (void *) GetProcAddress(handle, name); #else @@ -57,7 +50,7 @@ void uae_dlclose(UAE_DLHANDLE handle) #endif } -#ifdef FSUAE // NL +#ifdef AMIBERRY #include "uae/uae.h" static amiga_plugin_lookup_function plugin_lookup; /*UAE_EXTERN_C*/ void amiga_set_plugin_lookup_function( @@ -69,7 +62,7 @@ static amiga_plugin_lookup_function plugin_lookup; UAE_DLHANDLE uae_dlopen_plugin(const TCHAR *name) { -#if defined(FSUAE) // ME +#if defined(AMIBERRY) // ME const TCHAR *path = NULL; if (plugin_lookup) { path = plugin_lookup(name); diff --git a/src/drawing.cpp b/src/drawing.cpp index 3c1f9a31..1ad9e743 100644 --- a/src/drawing.cpp +++ b/src/drawing.cpp @@ -47,6 +47,8 @@ #include "audio.h" #include "devices.h" +struct amigadisplay adisplays; + typedef enum { CMODE_NORMAL, @@ -72,8 +74,6 @@ int lores_shift, shres_shift; static void pfield_set_linetoscr(void); -int debug_bpl_mask = 0xff, debug_bpl_mask_one; - static void lores_set(int lores) { int old = lores_shift; @@ -142,8 +142,7 @@ static int sprite_offs[256]; static uae_u32 clxtab[256]; /* Video buffer description structure. Filled in by the graphics system - * dependent code. */ -struct vidbuf_description gfxvidinfo; +* dependent code. */ /* OCS/ECS color lookup table. */ xcolnr xcolors[4096]; @@ -259,9 +258,6 @@ static int last_redraw_point; #define MAX_STOP 30000 static int first_drawn_line, last_drawn_line; -static int first_block_line, last_block_line; - -#define NO_BLOCK -3 /* These are generated by the drawing code from the line_decisions array for each line that needs to be drawn. These are basically extracted out of @@ -279,20 +275,28 @@ static bool ecs_genlock_features_active; static uae_u8 ecs_genlock_features_mask; static bool ecs_genlock_features_colorkey; static int hsync_shift_hack; -static bool sprite_smaller_than_64; - -bool picasso_requested_on, picasso_requested_forced_on, picasso_on; +static bool sprite_smaller_than_64, sprite_smaller_than_64_inuse; uae_sem_t gui_sem; -int inhibit_frame; -int framecnt; -int custom_frame_redraw_necessary; -static int frame_redraw_necessary; -static int picasso_redraw_necessary; +void set_inhibit_frame(int bit) +{ + struct amigadisplay *ad = &adisplays; + ad->inhibit_frame |= 1 << bit; +} +void clear_inhibit_frame(int bit) +{ + struct amigadisplay *ad = &adisplays; + ad->inhibit_frame &= ~(1 << bit); +} +void toggle_inhibit_frame(int bit) +{ + struct amigadisplay *ad = &adisplays; + ad->inhibit_frame ^= 1 << bit; +} #ifdef XLINECHECK -static void xlinecheck(unsigned int start, unsigned int end) +static void xlinecheck (unsigned int start, unsigned int end) { unsigned int xstart = (unsigned int)xlinebuffer + start * gfxvidinfo.drawbuffer.pixbytes; unsigned int xend = (unsigned int)xlinebuffer + end * gfxvidinfo.drawbuffer.pixbytes; @@ -339,11 +343,12 @@ static void reset_decision_table(void) STATIC_INLINE void count_frame(void) { - framecnt++; - if (framecnt > currprefs.gfx_framerate) - framecnt = 0; - if (inhibit_frame) - framecnt = 1; + struct amigadisplay *ad = &adisplays; + ad->framecnt++; + if (ad->framecnt > currprefs.gfx_framerate) + ad->framecnt = 0; + if (ad->inhibit_frame) + ad->framecnt = 1; } STATIC_INLINE int xshift(int x, int shift) @@ -357,12 +362,14 @@ STATIC_INLINE int xshift(int x, int shift) int coord_native_to_amiga_x(int x) { x += visible_left_border; - x = xshift(x, 1 - lores_shift); + x = xshift (x, 1 - lores_shift); return x + 2 * DISPLAY_LEFT_SHIFT - 2 * DIW_DDF_OFFSET; } int coord_native_to_amiga_y (int y) { + if (!native2amiga_line_map) + return -1; return native2amiga_line_map[y] + thisframe_y_adjust - minfirstline; } @@ -373,17 +380,18 @@ STATIC_INLINE int res_shift_from_window(int x) return x << -res_shift; } -STATIC_INLINE int res_shift_from_amiga(int x) +STATIC_INLINE int res_shift_from_amiga (int x) { if (res_shift >= 0) return x >> res_shift; return x << -res_shift; } -void notice_screen_contents_lost(void) +void notice_screen_contents_lost() { - picasso_redraw_necessary = 1; - frame_redraw_necessary = 2; + struct amigadisplay *ad = &adisplays; + ad->picasso_redraw_necessary = 1; + ad->frame_redraw_necessary = 2; } extern int plffirstline_total, plflastline_total; @@ -402,7 +410,7 @@ extern int lof_store; static int gclow, gcloh, gclox, gcloy, gclorealh; static int stored_left_start, stored_top_start, stored_width, stored_height; -void get_custom_topedge(int *xp, int *yp, bool max) +void get_custom_topedge (int *xp, int *yp, bool max) { if (!max) { int x, y; @@ -411,42 +419,40 @@ void get_custom_topedge(int *xp, int *yp, bool max) *xp = x; *yp = y; - } - else { + } else { *xp = 0; *yp = 0; } } -static void reset_custom_limits(void) +static void reset_custom_limits (void) { gclow = gcloh = gclox = gcloy = 0; gclorealh = -1; center_reset = true; } -static void set_blanking_limits(void) +static void set_blanking_limits (void) { hblank_left_start = visible_left_start; hblank_right_stop = visible_right_stop; if (programmedmode) { - if (hblank_left_start < coord_hw_to_window_x(hsyncendpos * 2)) - hblank_left_start = coord_hw_to_window_x(hsyncendpos * 2); - if (hblank_right_stop > coord_hw_to_window_x(hsyncstartpos * 2)) - hblank_right_stop = coord_hw_to_window_x(hsyncstartpos * 2); + if (hblank_left_start < coord_hw_to_window_x (hsyncendpos * 2)) + hblank_left_start = coord_hw_to_window_x (hsyncendpos * 2); + if (hblank_right_stop > coord_hw_to_window_x (hsyncstartpos * 2)) + hblank_right_stop = coord_hw_to_window_x (hsyncstartpos * 2); } } -void get_custom_raw_limits(int *pw, int *ph, int *pdx, int *pdy) +void get_custom_raw_limits (int *pw, int *ph, int *pdx, int *pdy) { if (stored_width > 0) { *pw = stored_width; *ph = stored_height; *pdx = stored_left_start; *pdy = stored_top_start; - } - else { + } else { int x = visible_left_border; if (x < visible_left_start) x = visible_left_start; @@ -469,10 +475,11 @@ void get_custom_raw_limits(int *pw, int *ph, int *pdx, int *pdy) void check_custom_limits(void) { struct gfx_filterdata *fd = &currprefs.gf[0]; - int left = fd->gfx_filter_left_border >> (RES_MAX - currprefs.gfx_resolution); - int right = fd->gfx_filter_right_border >> (RES_MAX - currprefs.gfx_resolution); - int top = fd->gfx_filter_top_border; - int bottom = fd->gfx_filter_bottom_border; + + int left = fd->gfx_filter_left_border < 0 ? 0 : fd->gfx_filter_left_border >> (RES_MAX - currprefs.gfx_resolution); + int right = fd->gfx_filter_right_border < 0 ? 0 : fd->gfx_filter_right_border >> (RES_MAX - currprefs.gfx_resolution); + int top = fd->gfx_filter_top_border < 0 ? 0 : fd->gfx_filter_top_border; + int bottom = fd->gfx_filter_bottom_border < 0 ? 0 : fd->gfx_filter_bottom_border; if (left > visible_left_start) visible_left_start = left; @@ -483,17 +490,27 @@ void check_custom_limits(void) visible_top_start = top; if (bottom > top && bottom < visible_bottom_stop) visible_bottom_stop = bottom; - - set_blanking_limits(); + + set_blanking_limits (); } -void set_custom_limits(int w, int h, int dx, int dy) +void set_custom_limits (int w, int h, int dx, int dy) { + struct gfx_filterdata *fd = &currprefs.gf[0]; int vls = visible_left_start; int vrs = visible_right_stop; int vts = visible_top_start; int vbs = visible_bottom_stop; + if (fd->gfx_filter_left_border == 0) { + w = 0; + dx = 0; + } + if (fd->gfx_filter_top_border == 0) { + h = 0; + dy = 0; + } + //if (specialmonitor_uses_control_lines()) { // w = -1; // h = -1; @@ -502,16 +519,14 @@ void set_custom_limits(int w, int h, int dx, int dy) if (w <= 0 || dx < 0) { visible_left_start = 0; visible_right_stop = MAX_STOP; - } - else { + } else { visible_left_start = visible_left_border + dx; visible_right_stop = visible_left_start + w; } if (h <= 0 || dy < 0) { visible_top_start = 0; visible_bottom_stop = MAX_STOP; - } - else { + } else { visible_top_start = min_ypos_for_screen + dy; visible_bottom_stop = visible_top_start + h; } @@ -523,7 +538,7 @@ void set_custom_limits(int w, int h, int dx, int dy) check_custom_limits(); } -void store_custom_limits(int w, int h, int x, int y) +void store_custom_limits (int w, int h, int x, int y) { stored_left_start = x; stored_top_start = y; @@ -531,14 +546,14 @@ void store_custom_limits(int w, int h, int x, int y) stored_height = h; } -int get_custom_limits(int *pw, int *ph, int *pdx, int *pdy, int *prealh) +int get_custom_limits (int *pw, int *ph, int *pdx, int *pdy, int *prealh) { - struct vidbuf_description *vidinfo = &gfxvidinfo; + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int w, h, dx, dy, y1, y2, dbl1, dbl2; int ret = 0; if (!pw || !ph || !pdx || !pdy) { - reset_custom_limits(); + reset_custom_limits (); return 0; } @@ -573,12 +588,12 @@ int get_custom_limits(int *pw, int *ph, int *pdx, int *pdy, int *prealh) if (plflastline_total < 4) plflastline_total = last_planes_vpos; - ddffirstword_total = coord_hw_to_window_x(ddffirstword_total * 2 + DIW_DDF_OFFSET); - ddflastword_total = coord_hw_to_window_x(ddflastword_total * 2 + DIW_DDF_OFFSET); + ddffirstword_total = coord_hw_to_window_x (ddffirstword_total * 2 + DIW_DDF_OFFSET); + ddflastword_total = coord_hw_to_window_x (ddflastword_total * 2 + DIW_DDF_OFFSET); if (doublescan <= 0 && !programmedmode) { - int min = coord_diw_lores_to_window_x(92); - int max = coord_diw_lores_to_window_x(460); + int min = coord_diw_lores_to_window_x (92); + int max = coord_diw_lores_to_window_x (460); if (diwfirstword_total < min) diwfirstword_total = min; if (diwlastword_total > max) @@ -627,13 +642,13 @@ int get_custom_limits(int *pw, int *ph, int *pdx, int *pdy, int *prealh) if (!programmedmode && first_planes_vpos) { int th = (maxvpos - minfirstline) * 95 / 100; if (th > h) { - th = xshift(th, dbl1); + th = xshift (th, dbl1); *prealh = th; } } - dy = xshift(dy, dbl2); - h = xshift(h, dbl1); + dy = xshift (dy, dbl2); + h = xshift (h, dbl1); if (w == 0 || h == 0) return 0; @@ -679,8 +694,8 @@ int get_custom_limits(int *pw, int *ph, int *pdx, int *pdy, int *prealh) *pdx = dx; *pdy = dy; #if 1 - write_log(_T("Display Size: %dx%d Offset: %dx%d\n"), w, h, dx, dy); - write_log(_T("First: %d Last: %d MinV: %d MaxV: %d Min: %d\n"), + write_log (_T("Display Size: %dx%d Offset: %dx%d\n"), w, h, dx, dy); + write_log (_T("First: %d Last: %d MinV: %d MaxV: %d Min: %d\n"), plffirstline_total, plflastline_total, first_planes_vpos, last_planes_vpos, minfirstline); #endif @@ -688,7 +703,7 @@ int get_custom_limits(int *pw, int *ph, int *pdx, int *pdy, int *prealh) return 1; } -void get_custom_mouse_limits(int *pw, int *ph, int *pdx, int *pdy, int dbl) +void get_custom_mouse_limits (int *pw, int *ph, int *pdx, int *pdy, int dbl) { int delay1, delay2; int w, h, dx, dy, dbl1, dbl2, y1, y2; @@ -711,12 +726,12 @@ void get_custom_mouse_limits(int *pw, int *ph, int *pdx, int *pdy, int dbl) if (*pw > 0) w = *pw; - w = xshift(w, res_shift); + w = xshift (w, res_shift); if (*ph > 0) h = *ph; - dx = xshift(dx, res_shift); + dx = xshift (dx, res_shift); dbl2 = dbl1 = currprefs.gfx_vresolution; if ((doublescan > 0 || interlace_seen > 0) && !dbl) { @@ -727,8 +742,8 @@ void get_custom_mouse_limits(int *pw, int *ph, int *pdx, int *pdy, int dbl) dbl2++; if (interlace_seen <= 0 && dbl) dbl2--; - h = xshift(h, dbl1); - dy = xshift(dy, dbl2); + h = xshift (h, dbl1); + dy = xshift (dy, dbl2); if (w < 1) w = 1; @@ -746,7 +761,7 @@ static struct decision *dp_for_drawing; static struct draw_info *dip_for_drawing; /* Record DIW of the current line for use by centering code. */ -void record_diw_line(int plfstrt, int first, int last) +void record_diw_line (int plfstrt, int first, int last) { if (last > max_diwstop) max_diwstop = last; @@ -777,8 +792,9 @@ STATIC_INLINE int get_shdelay_add(void) static int playfield_start_pre, playfield_end_pre; static int playfield_start, playfield_end; static int real_playfield_start, real_playfield_end; +static int playfield_diff; static int sprite_playfield_start; -static bool may_require_hard_way; +static int may_require_hard_way; static int linetoscr_diw_start, linetoscr_diw_end; static int native_ddf_left, native_ddf_right; @@ -802,9 +818,9 @@ static void set_res_shift(void) } /* Initialize the variables necessary for drawing a line. - * This involves setting up start/stop positions and display window - * borders. */ -static void pfield_init_linetoscr(bool border) +* This involves setting up start/stop positions and display window +* borders. */ +static void pfield_init_linetoscr (bool border) { /* First, get data fetch start/stop in DIW coordinates. */ int ddf_left = dp_for_drawing->plfleft * 2 + DIW_DDF_OFFSET; @@ -814,16 +830,17 @@ static void pfield_init_linetoscr(bool border) bool expanded = false; hsync_shift_hack = 0; - + if (border) ddf_left = DISPLAY_LEFT_SHIFT; /* Compute datafetch start/stop in pixels; native display coordinates. */ - native_ddf_left = coord_hw_to_window_x(ddf_left); - native_ddf_right = coord_hw_to_window_x(ddf_right); + native_ddf_left = coord_hw_to_window_x (ddf_left); + native_ddf_right = coord_hw_to_window_x (ddf_right); // Blerkenwiegel/Scoopex workaround native_ddf_left2 = native_ddf_left; + if (native_ddf_left < 0) native_ddf_left = 0; if (native_ddf_right > MAX_PIXELS_PER_LINE) @@ -870,14 +887,13 @@ static void pfield_init_linetoscr(bool border) if (playfield_end < linetoscr_diw_end && hblank_right_stop > playfield_end) { playfield_end = linetoscr_diw_end; } - int left = coord_hw_to_window_x(dp_for_drawing->plfleft * 2); + int left = coord_hw_to_window_x (dp_for_drawing->plfleft * 2); if (left < visible_left_border) left = visible_left_border; if (left < playfield_start && left >= linetoscr_diw_start) { playfield_start = left; } - } - else { + } else { sprite_playfield_start = 0; if (playfield_end < linetoscr_diw_end && hblank_right_stop > playfield_end) { playfield_end = linetoscr_diw_end; @@ -886,14 +902,15 @@ static void pfield_init_linetoscr(bool border) } #ifdef AGA - // if BPLCON4 is non-zero: it will affect background color until end of DIW. - if (dp_for_drawing->xor_seen) { + // if BPLCON4 is non-zero or borderblank: it can affect background color until end of DIW. + if (dp_for_drawing->xor_seen || ce_is_borderblank(colors_for_drawing.extra)) { if (playfield_end < linetoscr_diw_end && hblank_right_stop > playfield_end) { playfield_end = linetoscr_diw_end; expanded = true; } } - may_require_hard_way = false; + playfield_diff = 0; + may_require_hard_way = 0; if (dp_for_drawing->bordersprite_seen && !ce_is_borderblank(colors_for_drawing.extra) && dip_for_drawing->nr_sprites) { int min = visible_right_border, max = visible_left_border, i; for (i = 0; i < dip_for_drawing->nr_sprites; i++) { @@ -906,8 +923,8 @@ static void pfield_init_linetoscr(bool border) if (x > max) max = x; } - min = coord_hw_to_window_x(min >> sprite_buffer_res) + (DIW_DDF_OFFSET << lores_shift); - max = coord_hw_to_window_x(max >> sprite_buffer_res) + (DIW_DDF_OFFSET << lores_shift); + min = coord_hw_to_window_x (min >> sprite_buffer_res) + (DIW_DDF_OFFSET << lores_shift); + max = coord_hw_to_window_x (max >> sprite_buffer_res) + (DIW_DDF_OFFSET << lores_shift); if (min < playfield_start) playfield_start = min; @@ -918,7 +935,7 @@ static void pfield_init_linetoscr(bool border) if (playfield_end > visible_right_border) playfield_end = visible_right_border; sprite_playfield_start = 0; - may_require_hard_way = true; + may_require_hard_way = 1; } #endif @@ -931,7 +948,7 @@ static void pfield_init_linetoscr(bool border) } unpainted = visible_left_border < playfield_start ? 0 : visible_left_border - playfield_start; - unpainted = res_shift_from_window(unpainted); + unpainted = res_shift_from_window (unpainted); int first_x = sprite_first_x; int last_x = sprite_last_x; @@ -947,7 +964,7 @@ static void pfield_init_linetoscr(bool border) if (last_x > MAX_PIXELS_PER_LINE - 2) last_x = MAX_PIXELS_PER_LINE - 2; if (first_x < last_x) - memset(spritepixels + first_x, 0, sizeof(struct spritepixelsbuf) * (last_x - first_x + 1)); + memset (spritepixels + first_x, 0, sizeof (struct spritepixelsbuf) * (last_x - first_x + 1)); } sprite_last_x = 0; @@ -961,10 +978,21 @@ static void pfield_init_linetoscr(bool border) pixels_offset = MAX_PIXELS_PER_LINE - ddf_left; leftborderhidden = playfield_start - native_ddf_left2; + if (hblank_left_start > playfield_start) leftborderhidden += hblank_left_start - playfield_start; + src_pixel = MAX_PIXELS_PER_LINE + res_shift_from_window(leftborderhidden); + if (may_require_hard_way) { + // must use "hard_way" rendering if negative leftborderhidden + if (src_pixel < MAX_PIXELS_PER_LINE) + may_require_hard_way = -1; + if (playfield_start < real_playfield_start) { + playfield_diff = res_shift_from_window(real_playfield_start - playfield_start); + } + } + if (dip_for_drawing->nr_sprites == 0 && !expanded) return; @@ -973,8 +1001,7 @@ static void pfield_init_linetoscr(bool border) if (add) { if (sprite_playfield_start > 0) { sprite_playfield_start -= add; - } - else { + } else { ;// this is most likely wrong: playfield_start -= add; } } @@ -982,62 +1009,63 @@ static void pfield_init_linetoscr(bool border) /* We need to clear parts of apixels. */ if (linetoscr_diw_start < native_ddf_left) { - int size = res_shift_from_window(native_ddf_left - linetoscr_diw_start); + int size = res_shift_from_window (native_ddf_left - linetoscr_diw_start); linetoscr_diw_start = native_ddf_left; - memset(pixdata.apixels + MAX_PIXELS_PER_LINE - size, 0, size); + memset (pixdata.apixels + MAX_PIXELS_PER_LINE - size, 0, size); } if (linetoscr_diw_end > native_ddf_right) { - int pos = res_shift_from_window(native_ddf_right - native_ddf_left); - int size = res_shift_from_window(linetoscr_diw_end - native_ddf_right); + int pos = res_shift_from_window (native_ddf_right - native_ddf_left); + int size = res_shift_from_window (linetoscr_diw_end - native_ddf_right); if (pos + size > MAX_PIXELS_PER_LINE) size = MAX_PIXELS_PER_LINE - pos; if (size > 0) - memset(pixdata.apixels + MAX_PIXELS_PER_LINE + pos, 0, size); + memset (pixdata.apixels + MAX_PIXELS_PER_LINE + pos, 0, size); linetoscr_diw_start = native_ddf_left; } } // erase sprite graphics in pixdata if they were outside of ddf -static void pfield_erase_hborder_sprites(void) +static void pfield_erase_hborder_sprites (void) { if (sprite_first_x < native_ddf_left) { - int size = res_shift_from_window(native_ddf_left - sprite_first_x); - memset(pixdata.apixels + MAX_PIXELS_PER_LINE - size, 0, size); + int size = res_shift_from_window (native_ddf_left - sprite_first_x); + memset (pixdata.apixels + MAX_PIXELS_PER_LINE - size, 0, size); } if (sprite_last_x > native_ddf_right) { - int pos = res_shift_from_window(native_ddf_right - native_ddf_left); - int size = res_shift_from_window(sprite_last_x - native_ddf_right); + int pos = res_shift_from_window (native_ddf_right - native_ddf_left); + int size = res_shift_from_window (sprite_last_x - native_ddf_right); if (pos + size > MAX_PIXELS_PER_LINE) size = MAX_PIXELS_PER_LINE - pos; if (size > 0) - memset(pixdata.apixels + MAX_PIXELS_PER_LINE + pos, 0, size); + memset (pixdata.apixels + MAX_PIXELS_PER_LINE + pos, 0, size); } } // erase whole viewable area if sprite in upper or lower border -static void pfield_erase_vborder_sprites(void) +static void pfield_erase_vborder_sprites (void) { if (visible_right_border <= visible_left_border) return; int pos = 0; int size = 0; if (visible_left_border < native_ddf_left) { - size = res_shift_from_window(native_ddf_left - visible_left_border); + size = res_shift_from_window (native_ddf_left - visible_left_border); pos = -size; } if (visible_right_border > native_ddf_left) - size += res_shift_from_window(visible_right_border - native_ddf_left); - memset(pixdata.apixels + MAX_PIXELS_PER_LINE - pos, 0, size); + size += res_shift_from_window (visible_right_border - native_ddf_left); + memset (pixdata.apixels + MAX_PIXELS_PER_LINE - pos, 0, size); } -STATIC_INLINE uae_u16 merge_2pixel16(uae_u16 p1, uae_u16 p2) + +STATIC_INLINE uae_u16 merge_2pixel16 (uae_u16 p1, uae_u16 p2) { uae_u16 v = ((((p1 >> xredcolor_s) & xredcolor_m) + ((p2 >> xredcolor_s) & xredcolor_m)) / 2) << xredcolor_s; v |= ((((p1 >> xbluecolor_s) & xbluecolor_m) + ((p2 >> xbluecolor_s) & xbluecolor_m)) / 2) << xbluecolor_s; v |= ((((p1 >> xgreencolor_s) & xgreencolor_m) + ((p2 >> xgreencolor_s) & xgreencolor_m)) / 2) << xgreencolor_s; return v; } -STATIC_INLINE uae_u32 merge_2pixel32(uae_u32 p1, uae_u32 p2) +STATIC_INLINE uae_u32 merge_2pixel32 (uae_u32 p1, uae_u32 p2) { uae_u32 v = ((((p1 >> 16) & 0xff) + ((p2 >> 16) & 0xff)) / 2) << 16; v |= ((((p1 >> 8) & 0xff) + ((p2 >> 8) & 0xff)) / 2) << 8; @@ -1050,9 +1078,9 @@ STATIC_INLINE void fill_line_16 (uae_u8 *buf, int start, int stop, int blank) uae_u16 *b = (uae_u16 *)buf; unsigned int i; unsigned int rem = 0; - xcolnr col = getbgc(blank); + xcolnr col = getbgc (blank); if (((uintptr_t)&b[start]) & 1) - b[start++] = (uae_u16)col; + b[start++] = (uae_u16) col; if (start >= stop) return; if (((uintptr_t)&b[stop]) & 1) { @@ -1071,18 +1099,19 @@ STATIC_INLINE void fill_line_32 (uae_u8 *buf, int start, int stop, int blank) { uae_u32 *b = (uae_u32 *)buf; unsigned int i; - xcolnr col = getbgc(blank); + xcolnr col = getbgc (blank); for (i = start; i < stop; i++) b[i] = col; } static void pfield_do_fill_line (int start, int stop, int blank) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; if (stop <= start) return; - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: fill_line_16(xlinebuffer, start, stop, blank); break; - case 4: fill_line_32(xlinebuffer, start, stop, blank); break; + switch (vidinfo->drawbuffer.pixbytes) { + case 2: fill_line_16 (xlinebuffer, start, stop, blank); break; + case 4: fill_line_32 (xlinebuffer, start, stop, blank); break; default: return; } //if (need_genlock_data) { @@ -1090,33 +1119,34 @@ static void pfield_do_fill_line (int start, int stop, int blank) //} } -static void fill_line2(int startpos, int len) +static void fill_line2 (int startpos, int len) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int shift; int nints, nrem; int *start; xcolnr val; shift = 0; - if (gfxvidinfo.drawbuffer.pixbytes == 2) - shift = 1; - if (gfxvidinfo.drawbuffer.pixbytes == 4) + if (vidinfo->drawbuffer.pixbytes == 2) + shift = 1; + if (vidinfo->drawbuffer.pixbytes == 4) shift = 2; nints = len >> (2 - shift); nrem = nints & 7; nints &= ~7; start = (int *)(((uae_u8*)xlinebuffer) + (startpos << shift)); - val = getbgc(false); + val = getbgc(0); for (; nints > 0; nints -= 8, start += 8) { *start = val; - *(start + 1) = val; - *(start + 2) = val; - *(start + 3) = val; - *(start + 4) = val; - *(start + 5) = val; - *(start + 6) = val; - *(start + 7) = val; + *(start+1) = val; + *(start+2) = val; + *(start+3) = val; + *(start+4) = val; + *(start+5) = val; + *(start+6) = val; + *(start+7) = val; } switch (nrem) { @@ -1137,15 +1167,16 @@ static void fill_line2(int startpos, int len) } } -static void fill_line_border(int lineno) +STATIC_INLINE void fill_line_border (int lineno) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int lastpos = visible_left_border; - int endpos = visible_left_border + gfxvidinfo.drawbuffer.outwidth; + int endpos = visible_left_border + vidinfo->drawbuffer.outwidth; if (lineno < visible_top_start || lineno >= visible_bottom_stop) { int b = hposblank; hposblank = 3; - fill_line2(lastpos, gfxvidinfo.drawbuffer.outwidth); + fill_line2(lastpos, vidinfo->drawbuffer.outwidth); //if (need_genlock_data) { // memset(xlinebuffer_genlock + lastpos, 0, gfxvidinfo.drawbuffer.outwidth); //} @@ -1156,7 +1187,7 @@ static void fill_line_border(int lineno) // full hblank if (hposblank) { hposblank = 3; - fill_line2(lastpos, gfxvidinfo.drawbuffer.outwidth); + fill_line2(lastpos, vidinfo->drawbuffer.outwidth); //if (need_genlock_data) { // memset(xlinebuffer_genlock + lastpos, 0, gfxvidinfo.drawbuffer.outwidth); //} @@ -1164,7 +1195,7 @@ static void fill_line_border(int lineno) } // hblank not visible if (hblank_left_start <= lastpos && hblank_right_stop >= endpos) { - fill_line2(lastpos, gfxvidinfo.drawbuffer.outwidth); + fill_line2(lastpos, vidinfo->drawbuffer.outwidth); //if (need_genlock_data) { // memset(xlinebuffer_genlock + lastpos, 0, gfxvidinfo.drawbuffer.outwidth); //} @@ -1188,7 +1219,6 @@ static void fill_line_border(int lineno) } static int sprite_shdelay; -#define SPRITE_DEBUG 0 static uae_u8 render_sprites(int pos, int dualpf, uae_u8 apixel, int aga) { struct spritepixelsbuf *spb = &spritepixels[pos]; @@ -1199,7 +1229,7 @@ static uae_u8 render_sprites(int pos, int dualpf, uae_u8 apixel, int aga) // If 64 pixel wide sprite and FMODE gets lowered when sprite's // first 32 pixels are being drawn: matching pixel(s) in second // 32 pixel part gets blanked. - if (aga && spb->stfmdata && sprite_smaller_than_64) { + if (aga && spb->stfmdata && sprite_smaller_than_64_inuse && sprite_smaller_than_64) { spb[32 << currprefs.gfx_resolution].data &= ~spb->stfmdata; } @@ -1211,9 +1241,8 @@ static uae_u8 render_sprites(int pos, int dualpf, uae_u8 apixel, int aga) maskshift = shift_lookup[apixel]; plfmask = (plf_sprite_mask >> maskshift) >> maskshift; v &= ~plfmask; - /* Extra 1 sprite pixel at DDFSTRT is only possible if at least 1 plane is active */ - if ((bplplanecnt > 0 || pos >= sprite_playfield_start) && (v != 0 || SPRITE_DEBUG)) { + if ((bplplanecnt > 0 || pos >= sprite_playfield_start) && (v != 0)) { unsigned int vlo, vhi, col; unsigned int v1 = v & 255; /* OFFS determines the sprite pair with the highest priority that has @@ -1232,17 +1261,13 @@ static uae_u8 render_sprites(int pos, int dualpf, uae_u8 apixel, int aga) /* Shift highest priority sprite pair down to bit zero. */ v >>= offs * 2; v &= 15; -#if SPRITE_DEBUG > 0 - v ^= 8; -#endif if (spb->attach && (spb->stdata & (3 << offs))) { col = v; if (aga) col += sbasecol[1]; else col += 16; - } - else { + } else { /* This sequence computes the correct color value. We have to select either the lower-numbered or the higher-numbered sprite in the pair. We have to select the high one if the low one has all bits zero. @@ -1260,8 +1285,7 @@ static uae_u8 render_sprites(int pos, int dualpf, uae_u8 apixel, int aga) col += sbasecol[1]; else col += sbasecol[0]; - } - else { + } else { col += 16; } col += offs * 2; @@ -1283,8 +1307,7 @@ static bool get_genlock_very_rare_and_complex_case(uae_u8 v) if (currprefs.chipset_mask & CSMASK_AGA) { if (colors_for_drawing.color_regs_aga[v] & 0x80000000) return false; - } - else { + } else { if (colors_for_drawing.color_regs_ecs[v] & 0x8000) return false; } @@ -1294,14 +1317,14 @@ static bool get_genlock_very_rare_and_complex_case(uae_u8 v) return false; return true; } - // false = transparent STATIC_INLINE bool get_genlock_transparency(uae_u8 v) { if (!ecs_genlock_features_active) { - return v != 0; - } - else { + if (v == 0) + return false; + return true; + } else { return get_genlock_very_rare_and_complex_case(v); } } @@ -1315,16 +1338,16 @@ STATIC_INLINE bool get_genlock_transparency(uae_u8 v) #define PUTBPIX(x) buf[dpix] = (x); -STATIC_INLINE uae_u32 shsprite(int dpix, uae_u32 spix_val, uae_u32 v, int spr) +STATIC_INLINE uae_u32 shsprite (int dpix, uae_u32 spix_val, uae_u32 v, int spr) { uae_u8 sprcol; uae_u16 scol; if (!spr) return v; - sprcol = render_sprites(dpix, 0, spix_val, 0); + sprcol = render_sprites (dpix, 0, spix_val, 0); if (!sprcol) return v; - /* good enough for now.. */ + /* good enough for now.. */ scol = colors_for_drawing.color_regs_ecs[sprcol] & 0xccc; scol |= scol >> 2; return xcolors[scol]; @@ -1332,7 +1355,7 @@ STATIC_INLINE uae_u32 shsprite(int dpix, uae_u32 spix_val, uae_u32 v, int spr) static int NOINLINE linetoscr_16_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u16 *buf = (uae_u16 *)xlinebuffer; + uae_u16 *buf = (uae_u16 *) xlinebuffer; while (dpix < stoppos) { uae_u16 spix_val1, spix_val2; @@ -1343,11 +1366,11 @@ static int NOINLINE linetoscr_16_sh_func(int spix, int dpix, int stoppos, int sp off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); dpix++; v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val2, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val2, xcolors[v], spr)); dpix++; } return spix; @@ -1362,7 +1385,7 @@ static int linetoscr_16_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_32_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u32 *buf = (uae_u32 *)xlinebuffer; + uae_u32 *buf = (uae_u32 *) xlinebuffer; while (dpix < stoppos) { uae_u32 spix_val1, spix_val2; @@ -1373,11 +1396,11 @@ static int NOINLINE linetoscr_32_sh_func(int spix, int dpix, int stoppos, int sp off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); dpix++; v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val2, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val2, xcolors[v], spr)); dpix++; } return spix; @@ -1392,7 +1415,7 @@ static int linetoscr_32_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_32_shrink1_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u32 *buf = (uae_u32 *)xlinebuffer; + uae_u32 *buf = (uae_u32 *) xlinebuffer; while (dpix < stoppos) { uae_u32 spix_val1, spix_val2; @@ -1403,7 +1426,7 @@ static int NOINLINE linetoscr_32_shrink1_sh_func(int spix, int dpix, int stoppos off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); dpix++; } return spix; @@ -1418,7 +1441,7 @@ static int linetoscr_32_shrink1_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_32_shrink1f_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u32 *buf = (uae_u32 *)xlinebuffer; + uae_u32 *buf = (uae_u32 *) xlinebuffer; while (dpix < stoppos) { uae_u32 spix_val1, spix_val2, dpix_val1, dpix_val2; @@ -1433,7 +1456,7 @@ static int NOINLINE linetoscr_32_shrink1f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - PUTBPIX(shsprite(dpix, spix_val1, merge_2pixel32(dpix_val1, dpix_val2), spr)); + PUTBPIX(shsprite (dpix, spix_val1, merge_2pixel32 (dpix_val1, dpix_val2), spr)); dpix++; } return spix; @@ -1448,7 +1471,7 @@ static int linetoscr_32_shrink1f_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_16_shrink1_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u16 *buf = (uae_u16 *)xlinebuffer; + uae_u16 *buf = (uae_u16 *) xlinebuffer; while (dpix < stoppos) { uae_u16 spix_val1, spix_val2; @@ -1459,7 +1482,7 @@ static int NOINLINE linetoscr_16_shrink1_sh_func(int spix, int dpix, int stoppos off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); dpix++; } return spix; @@ -1474,7 +1497,7 @@ static int linetoscr_16_shrink1_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_16_shrink1f_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u16 *buf = (uae_u16 *)xlinebuffer; + uae_u16 *buf = (uae_u16 *) xlinebuffer; while (dpix < stoppos) { uae_u16 spix_val1, spix_val2, dpix_val1, dpix_val2; @@ -1489,7 +1512,7 @@ static int NOINLINE linetoscr_16_shrink1f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - PUTBPIX(shsprite(dpix, spix_val1, merge_2pixel16(dpix_val1, dpix_val2), spr)); + PUTBPIX(shsprite (dpix, spix_val1, merge_2pixel16 (dpix_val1, dpix_val2), spr)); dpix++; } return spix; @@ -1504,7 +1527,7 @@ static int linetoscr_16_shrink1f_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_32_shrink2_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u32 *buf = (uae_u32 *)xlinebuffer; + uae_u32 *buf = (uae_u32 *) xlinebuffer; while (dpix < stoppos) { uae_u32 spix_val1, spix_val2; @@ -1515,8 +1538,8 @@ static int NOINLINE linetoscr_32_shrink2_sh_func(int spix, int dpix, int stoppos off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); - spix += 2; + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); + spix+=2; dpix++; } return spix; @@ -1531,7 +1554,7 @@ static int linetoscr_32_shrink2_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_32_shrink2f_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u32 *buf = (uae_u32 *)xlinebuffer; + uae_u32 *buf = (uae_u32 *) xlinebuffer; while (dpix < stoppos) { uae_u32 spix_val1, spix_val2, dpix_val1, dpix_val2, dpix_val3, dpix_val4; @@ -1546,7 +1569,7 @@ static int NOINLINE linetoscr_32_shrink2f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - dpix_val3 = merge_2pixel32(dpix_val1, dpix_val2); + dpix_val3 = merge_2pixel32 (dpix_val1, dpix_val2); spix_val1 = pixdata.apixels[spix++]; spix_val2 = pixdata.apixels[spix++]; off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); @@ -1556,8 +1579,8 @@ static int NOINLINE linetoscr_32_shrink2f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - dpix_val4 = merge_2pixel32(dpix_val1, dpix_val2); - PUTBPIX(shsprite(dpix, spix_val1, merge_2pixel32(dpix_val3, dpix_val4), spr)); + dpix_val4 = merge_2pixel32 (dpix_val1, dpix_val2); + PUTBPIX(shsprite (dpix, spix_val1, merge_2pixel32 (dpix_val3, dpix_val4), spr)); dpix++; } return spix; @@ -1572,7 +1595,7 @@ static int linetoscr_32_shrink2f_sh(int spix, int dpix, int stoppos) } static int NOINLINE linetoscr_16_shrink2_sh_func(int spix, int dpix, int stoppos, int spr) { - uae_u16 *buf = (uae_u16 *)xlinebuffer; + uae_u16 *buf = (uae_u16 *) xlinebuffer; while (dpix < stoppos) { uae_u16 spix_val1, spix_val2; @@ -1583,8 +1606,8 @@ static int NOINLINE linetoscr_16_shrink2_sh_func(int spix, int dpix, int stoppos off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); v = (colors_for_drawing.color_regs_ecs[off] & 0xccc) << 0; v |= v >> 2; - PUTBPIX(shsprite(dpix, spix_val1, xcolors[v], spr)); - spix += 2; + PUTBPIX(shsprite (dpix, spix_val1, xcolors[v], spr)); + spix+=2; dpix++; } return spix; @@ -1597,9 +1620,9 @@ static int linetoscr_16_shrink2_sh(int spix, int dpix, int stoppos) { return linetoscr_16_shrink2_sh_func(spix, dpix, stoppos, false); } -static int NOINLINE linetoscr_16_shrink2f_sh_func(int spix, int dpix, int stoppos, int spr) +static int NOINLINE linetoscr_16_shrink2f_sh_func (int spix, int dpix, int stoppos, int spr) { - uae_u16 *buf = (uae_u16 *)xlinebuffer; + uae_u16 *buf = (uae_u16 *) xlinebuffer; while (dpix < stoppos) { uae_u16 spix_val1, spix_val2, dpix_val1, dpix_val2, dpix_val3, dpix_val4; @@ -1614,7 +1637,7 @@ static int NOINLINE linetoscr_16_shrink2f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - dpix_val3 = merge_2pixel32(dpix_val1, dpix_val2); + dpix_val3 = merge_2pixel32 (dpix_val1, dpix_val2); spix_val1 = pixdata.apixels[spix++]; spix_val2 = pixdata.apixels[spix++]; off = ((spix_val2 & 3) * 4) + (spix_val1 & 3) + ((spix_val1 | spix_val2) & 16); @@ -1624,8 +1647,8 @@ static int NOINLINE linetoscr_16_shrink2f_sh_func(int spix, int dpix, int stoppo v = (colors_for_drawing.color_regs_ecs[off] & 0x333) << 2; v |= v >> 2; dpix_val2 = xcolors[v]; - dpix_val4 = merge_2pixel32(dpix_val1, dpix_val2); - PUTBPIX(shsprite(dpix, spix_val1, merge_2pixel16(dpix_val3, dpix_val4), spr)); + dpix_val4 = merge_2pixel32 (dpix_val1, dpix_val2); + PUTBPIX(shsprite (dpix, spix_val1, merge_2pixel16 (dpix_val3, dpix_val4), spr)); dpix++; } return spix; @@ -1665,8 +1688,9 @@ static call_linetoscr pfield_do_linetoscr_shdelay_sprite; static int pfield_do_linetoscr_normal_shdelay(int spix, int dpix, int dpix_end) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int add = get_shdelay_add(); - int add2 = add * gfxvidinfo.drawbuffer.pixbytes; + int add2 = add * vidinfo->drawbuffer.pixbytes; if (add) { // Fill skipped pixel(s). pfield_do_linetoscr_shdelay_sprite(spix - 1, dpix, dpix + add); @@ -1678,6 +1702,7 @@ static int pfield_do_linetoscr_normal_shdelay(int spix, int dpix, int dpix_end) } static int pfield_do_linetoscr_sprite_shdelay(int spix, int dpix, int dpix_end) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int out = spix; if (dpix < real_playfield_start && dpix_end > real_playfield_start) { // Crosses real_playfield_start. @@ -1685,15 +1710,14 @@ static int pfield_do_linetoscr_sprite_shdelay(int spix, int dpix, int dpix_end) int len = real_playfield_start - dpix; out = pfield_do_linetoscr_spriteonly(out, dpix, dpix + len); dpix = real_playfield_start; - } - else if (dpix_end <= real_playfield_start) { + } else if (dpix_end <= real_playfield_start) { // Does not cross real_playfield_start, nothing special needed. out = pfield_do_linetoscr_spriteonly(out, dpix, dpix_end); return out; } // Render bitplane with subpixel scroll, from real_playfield_start to end. int add = get_shdelay_add(); - int add2 = add * gfxvidinfo.drawbuffer.pixbytes; + int add2 = add * vidinfo->drawbuffer.pixbytes; if (add) { pfield_do_linetoscr_shdelay_sprite(out - 1, dpix, dpix + add); } @@ -1707,8 +1731,9 @@ static int pfield_do_linetoscr_sprite_shdelay(int spix, int dpix, int dpix_end) return out; } -static void pfield_set_linetoscr(void) +static void pfield_set_linetoscr (void) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; xlinecheck(start, stop); p_acolors = colors_for_drawing.acolors; p_xcolors = xcolors; @@ -1721,100 +1746,94 @@ static void pfield_set_linetoscr(void) #ifdef AGA if (currprefs.chipset_mask & CSMASK_AGA) { if (res_shift == 0) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_aga_genlock : linetoscr_16_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_aga_spr_genlock : linetoscr_16_aga_spr; - pfield_do_linetoscr_spriteonly = linetoscr_16_aga_spronly; + pfield_do_linetoscr_spriteonly = linetoscr_16_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_aga_genlock : linetoscr_32_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_aga_spr_genlock : linetoscr_32_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_aga_spronly; break; } - } - else if (res_shift == 2) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else if (res_shift == 2) { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_stretch2_aga_genlock : linetoscr_16_stretch2_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_stretch2_aga_spr_genlock : linetoscr_16_stretch2_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_16_stretch2_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_stretch2_aga_genlock : linetoscr_32_stretch2_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_stretch2_aga_spr_genlock : linetoscr_32_stretch2_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_stretch2_aga_spronly; break; } - } - else if (res_shift == 1) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else if (res_shift == 1) { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_stretch1_aga_genlock : linetoscr_16_stretch1_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_stretch1_aga_spr_genlock : linetoscr_16_stretch1_aga_spr; - pfield_do_linetoscr_spriteonly = linetoscr_16_stretch1_aga_spronly; + pfield_do_linetoscr_spriteonly = linetoscr_16_stretch1_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_stretch1_aga_genlock : linetoscr_32_stretch1_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_stretch1_aga_spr_genlock : linetoscr_32_stretch1_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_stretch1_aga_spronly; break; } - } - else if (res_shift == -1) { + } else if (res_shift == -1) { if (currprefs.gfx_lores_mode) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink1f_aga_genlock : linetoscr_16_shrink1f_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink1f_aga_spr_genlock : linetoscr_16_shrink1f_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_16_shrink1f_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink1f_aga_genlock : linetoscr_32_shrink1f_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink1f_aga_spr_genlock : linetoscr_32_shrink1f_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_shrink1f_aga_spronly; break; } - } - else { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink1_aga_genlock : linetoscr_16_shrink1_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink1_aga_spr_genlock : linetoscr_16_shrink1_aga_spr; - pfield_do_linetoscr_spriteonly = linetoscr_16_shrink1_aga_spronly; + pfield_do_linetoscr_spriteonly = linetoscr_16_shrink1_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink1_aga_genlock : linetoscr_32_shrink1_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink1_aga_spr_genlock : linetoscr_32_shrink1_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_shrink1_aga_spronly; break; } } - } - else if (res_shift == -2) { + } else if (res_shift == -2) { if (currprefs.gfx_lores_mode) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink2f_aga_genlock : linetoscr_16_shrink2f_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink2f_aga_spr_genlock : linetoscr_16_shrink2f_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_16_shrink2f_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink2f_aga_genlock : linetoscr_32_shrink2f_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink2f_aga_spr_genlock : linetoscr_32_shrink2f_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_shrink2f_aga_spronly; break; } - } - else { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink2_aga_genlock : linetoscr_16_shrink2_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink2_aga_spr_genlock : linetoscr_16_shrink2_aga_spr; - pfield_do_linetoscr_spriteonly = linetoscr_16_shrink2_aga_spronly; + pfield_do_linetoscr_spriteonly = linetoscr_16_shrink2_aga_spronly; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink2_aga_genlock : linetoscr_32_shrink2_aga; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink2_aga_spr_genlock : linetoscr_32_shrink2_aga_spr; pfield_do_linetoscr_spriteonly = linetoscr_32_shrink2_aga_spronly; @@ -1834,63 +1853,59 @@ static void pfield_set_linetoscr(void) if (!(currprefs.chipset_mask & CSMASK_AGA) && ecsshres) { // TODO: genlock support if (res_shift == 0) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: - pfield_do_linetoscr_normal = linetoscr_16_sh; - pfield_do_linetoscr_sprite = linetoscr_16_sh_spr; + switch (vidinfo->drawbuffer.pixbytes) { + case 2: + pfield_do_linetoscr_normal = linetoscr_16_sh; + pfield_do_linetoscr_sprite = linetoscr_16_sh_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = linetoscr_32_sh; pfield_do_linetoscr_sprite = linetoscr_32_sh_spr; break; } - } - else if (res_shift == -1) { + } else if (res_shift == -1) { if (currprefs.gfx_lores_mode) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = linetoscr_16_shrink1f_sh; pfield_do_linetoscr_sprite = linetoscr_16_shrink1f_sh_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = linetoscr_32_shrink1f_sh; pfield_do_linetoscr_sprite = linetoscr_32_shrink1f_sh_spr; break; } - } - else { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: - pfield_do_linetoscr_normal = linetoscr_16_shrink1_sh; - pfield_do_linetoscr_sprite = linetoscr_16_shrink1_sh_spr; + } else { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: + pfield_do_linetoscr_normal = linetoscr_16_shrink1_sh; + pfield_do_linetoscr_sprite = linetoscr_16_shrink1_sh_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = linetoscr_32_shrink1_sh; pfield_do_linetoscr_sprite = linetoscr_32_shrink1_sh_spr; break; } } - } - else if (res_shift == -2) { + } else if (res_shift == -2) { if (currprefs.gfx_lores_mode) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = linetoscr_16_shrink2f_sh; pfield_do_linetoscr_sprite = linetoscr_16_shrink2f_sh_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = linetoscr_32_shrink2f_sh; pfield_do_linetoscr_sprite = linetoscr_32_shrink2f_sh_spr; break; } - } - else { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: - pfield_do_linetoscr_normal = linetoscr_16_shrink2_sh; - pfield_do_linetoscr_sprite = linetoscr_16_shrink2_sh_spr; + } else { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: + pfield_do_linetoscr_normal = linetoscr_16_shrink2_sh; + pfield_do_linetoscr_sprite = linetoscr_16_shrink2_sh_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = linetoscr_32_shrink2_sh; pfield_do_linetoscr_sprite = linetoscr_32_shrink2_sh_spr; break; @@ -1901,61 +1916,57 @@ static void pfield_set_linetoscr(void) #endif if (!(currprefs.chipset_mask & CSMASK_AGA) && !ecsshres) { if (res_shift == 0) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_genlock : linetoscr_16; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_spr_genlock : linetoscr_16_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_genlock : linetoscr_32; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_spr_genlock : linetoscr_32_spr; break; } - } - else if (res_shift == 2) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else if (res_shift == 2) { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_stretch2_genlock : linetoscr_16_stretch2; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_stretch2_spr_genlock : linetoscr_16_stretch2_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_stretch2_genlock : linetoscr_32_stretch2; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_stretch2_spr_genlock : linetoscr_32_stretch2_spr; break; } - } - else if (res_shift == 1) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else if (res_shift == 1) { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_stretch1_genlock : linetoscr_16_stretch1; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_stretch1_spr_genlock : linetoscr_16_stretch1_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_stretch1_genlock : linetoscr_32_stretch1; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_stretch1_spr_genlock : linetoscr_32_stretch1_spr; break; } - } - else if (res_shift == -1) { - if (currprefs.gfx_lores_mode) { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else if (res_shift == -1) { + if (currprefs.gfx_lores_mode) { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink1f_genlock : linetoscr_16_shrink1f; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink1f_spr_genlock : linetoscr_16_shrink1f_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink1f_genlock : linetoscr_32_shrink1f; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink1f_spr_genlock : linetoscr_32_shrink1f_spr; break; } - } - else { - switch (gfxvidinfo.drawbuffer.pixbytes) { - case 2: + } else { + switch (vidinfo->drawbuffer.pixbytes) { + case 2: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_16_shrink1_genlock : linetoscr_16_shrink1; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_16_shrink1_spr_genlock : linetoscr_16_shrink1_spr; break; - case 4: + case 4: pfield_do_linetoscr_normal = need_genlock_data ? linetoscr_32_shrink1_genlock : linetoscr_32_shrink1; pfield_do_linetoscr_sprite = need_genlock_data ? linetoscr_32_shrink1_spr_genlock : linetoscr_32_shrink1_spr; break; @@ -1987,12 +1998,12 @@ static unsigned int ham_lastcolor; * when decode_ham runs. * */ -static void init_ham_decoding(void) +static void init_ham_decoding (void) { int unpainted_amiga = unpainted; ham_decode_pixel = src_pixel; - ham_lastcolor = color_reg_get(&colors_for_drawing, 0); + ham_lastcolor = color_reg_get (&colors_for_drawing, 0); if (!bplham) { if (unpainted_amiga > 0) { @@ -2019,8 +2030,7 @@ static void init_ham_decoding(void) case 0x3: ham_lastcolor &= 0xFF03FF; ham_lastcolor |= (pw & 0xFC) << 8; break; } } - } - else { /* AGA mode HAM6 */ + } else { /* AGA mode HAM6 */ while (unpainted_amiga-- > 0) { int pw = pixdata.apixels[ham_decode_pixel++]; int pv = pw ^ bplxor; @@ -2052,7 +2062,7 @@ static void init_ham_decoding(void) static void decode_ham (int pix, int stoppos, int blank) { - int todraw_amiga = res_shift_from_window(stoppos - pix); + int todraw_amiga = res_shift_from_window (stoppos - pix); if (!bplham) { while (todraw_amiga-- > 0) { @@ -2082,8 +2092,7 @@ static void decode_ham (int pix, int stoppos, int blank) } ham_linebuf[ham_decode_pixel++] = ham_lastcolor; } - } - else { /* AGA mode HAM6 */ + } else { /* AGA mode HAM6 */ while (todraw_amiga-- > 0) { int pw = pixdata.apixels[ham_decode_pixel]; int pv = pw ^ bplxor; @@ -2121,12 +2130,12 @@ static void erase_ham_right_border(int pix, int stoppos, bool blank) return; // erase right border in HAM modes or old HAM data may be visible // if DDFSTOP < DIWSTOP (Uridium II title screen) - int todraw_amiga = res_shift_from_window(stoppos - pix); + int todraw_amiga = res_shift_from_window (stoppos - pix); while (todraw_amiga-- > 0) ham_linebuf[ham_decode_pixel++] = 0; } -static void gen_pfield_tables(void) +static void gen_pfield_tables (void) { int i; @@ -2166,7 +2175,7 @@ static void gen_pfield_tables(void) } - memset(all_ones, 0xff, MAX_PIXELS_PER_LINE); + memset (all_ones, 0xff, MAX_PIXELS_PER_LINE); } @@ -2215,7 +2224,7 @@ static void NOINLINE draw_sprites_normal_dp_at (struct sprite_entry *e) { draw_s #ifdef AGA /* not very optimized */ -STATIC_INLINE void draw_sprites_aga (struct sprite_entry *e, int aga) +STATIC_INLINE void draw_sprites_aga (struct sprite_entry *e) { draw_sprites_1 (e, bpldualpf, e->has_attached); } @@ -2228,8 +2237,7 @@ STATIC_INLINE void draw_sprites_ecs (struct sprite_entry *e) draw_sprites_normal_dp_at (e); else draw_sprites_normal_sp_at (e); - } - else { + } else { if (bpldualpf) draw_sprites_normal_dp_nat (e); else @@ -2239,7 +2247,7 @@ STATIC_INLINE void draw_sprites_ecs (struct sprite_entry *e) #ifdef AGA /* clear possible bitplane data outside DIW area */ -static void clear_bitplane_border_aga(void) +static void clear_bitplane_border_aga (void) { int len, shift = res_shift; uae_u8 v = 0; @@ -2247,20 +2255,33 @@ static void clear_bitplane_border_aga(void) if (shift < 0) { shift = -shift; len = (real_playfield_start - playfield_start) << shift; - memset(pixdata.apixels + pixels_offset + (playfield_start << shift), v, len); + int offset = playfield_start << shift; + memset (pixdata.apixels + pixels_offset + offset, v, len); + if (bplham) + memset(ham_linebuf + pixels_offset + offset, v, len * sizeof(uae_u32)); + len = (playfield_end - real_playfield_end) << shift; - memset(pixdata.apixels + pixels_offset + (real_playfield_end << shift), v, len); - } - else { + offset = real_playfield_end << shift; + memset (pixdata.apixels + pixels_offset + offset, v, len); + if (bplham) + memset(ham_linebuf + pixels_offset + offset, v, len * sizeof(uae_u32)); + } else { len = (real_playfield_start - playfield_start) >> shift; - memset(pixdata.apixels + pixels_offset + (playfield_start >> shift), v, len); + int offset = playfield_start >> shift; + memset (pixdata.apixels + pixels_offset + offset, v, len); + if (bplham) + memset(ham_linebuf + pixels_offset + offset, v, len * sizeof(uae_u32)); + len = (playfield_end - real_playfield_end) >> shift; - memset(pixdata.apixels + pixels_offset + (real_playfield_end >> shift), v, len); + offset = real_playfield_end >> shift; + memset (pixdata.apixels + pixels_offset + offset, v, len); + if (bplham) + memset(ham_linebuf + pixels_offset + offset, v, len * sizeof(uae_u32)); } } #endif -static void weird_bitplane_fix(int start, int end) +static void weird_bitplane_fix (int start, int end) { int sh = lores_shift; uae_u8 *p = pixdata.apixels + pixels_offset; @@ -2279,8 +2300,7 @@ static void weird_bitplane_fix(int start, int end) p[i] = 0x10; } } - } - else if (plf1pri >= 5 || plf2pri >= 5) { + } else if (plf1pri >= 5 || plf2pri >= 5) { // If PFx is invalid (>=5), matching playfield's color becomes transparent // (COLOR00). Priorities keep working normally: "transparent" playfield // will still hide lower priority playfield behind it. @@ -2317,7 +2337,7 @@ Don't touch this if you don't know what you are doing. */ #define DATA_POINTER(n) (line_data[lineno] + (n) * MAX_WORDS_PER_LINE * 2) -#if defined(USE_ARMNEON) && !defined(ANDROID) +#if defined(CPU_AARCH64) || defined(USE_ARMNEON) && !defined(ANDROID) // FIXME: these neon helper functions caused text rel problem on android #ifdef __cplusplus @@ -2327,7 +2347,9 @@ Don't touch this if you don't know what you are doing. */ void NEON_doline_n2(uae_u32 *pixels, int wordcount, int lineno); void NEON_doline_n3(uae_u32 *pixels, int wordcount, int lineno); void NEON_doline_n4(uae_u32 *pixels, int wordcount, int lineno); + void NEON_doline_n5(uae_u32 *pixels, int wordcount, int lineno); void NEON_doline_n6(uae_u32 *pixels, int wordcount, int lineno); + void NEON_doline_n7(uae_u32 *pixels, int wordcount, int lineno); void NEON_doline_n8(uae_u32 *pixels, int wordcount, int lineno); #ifdef __cplusplus } @@ -2338,127 +2360,11 @@ static void pfield_doline_n0 (uae_u32 *pixels, int wordcount, int lineno) memset(pixels, 0, wordcount << 5); } -#define MERGE_0(a,b,mask,shift) {\ - uae_u32 tmp = mask & (b>>shift); \ - a = tmp; \ - b ^= (tmp << shift); \ -} - -static void pfield_doline_n5 (uae_u32 *pixels, int wordcount, int lineno) -{ - uae_u8 *real_bplpt[5]; - - real_bplpt[0] = DATA_POINTER (0); - real_bplpt[1] = DATA_POINTER (1); - real_bplpt[2] = DATA_POINTER (2); - real_bplpt[3] = DATA_POINTER (3); - real_bplpt[4] = DATA_POINTER (4); - - while (wordcount-- > 0) { - uae_u32 b0,b1,b2,b3,b4,b5,b6,b7; - b3 = GETLONG ((uae_u32 *)real_bplpt[4]); real_bplpt[4] += 4; - b4 = GETLONG ((uae_u32 *)real_bplpt[3]); real_bplpt[3] += 4; - b5 = GETLONG ((uae_u32 *)real_bplpt[2]); real_bplpt[2] += 4; - b6 = GETLONG ((uae_u32 *)real_bplpt[1]); real_bplpt[1] += 4; - b7 = GETLONG ((uae_u32 *)real_bplpt[0]); real_bplpt[0] += 4; - - MERGE_0(b2, b3, 0x55555555, 1); - MERGE (b4, b5, 0x55555555, 1); - MERGE (b6, b7, 0x55555555, 1); - - MERGE_0(b0, b2, 0x33333333, 2); - MERGE_0(b1, b3, 0x33333333, 2); - MERGE (b4, b6, 0x33333333, 2); - MERGE (b5, b7, 0x33333333, 2); - - MERGE (b0, b4, 0x0f0f0f0f, 4); - MERGE (b1, b5, 0x0f0f0f0f, 4); - MERGE (b2, b6, 0x0f0f0f0f, 4); - MERGE (b3, b7, 0x0f0f0f0f, 4); - - MERGE (b0, b1, 0x00ff00ff, 8); - MERGE (b2, b3, 0x00ff00ff, 8); - MERGE (b4, b5, 0x00ff00ff, 8); - MERGE (b6, b7, 0x00ff00ff, 8); - - MERGE (b0, b2, 0x0000ffff, 16); - do_put_mem_long(pixels, b0); - do_put_mem_long(pixels + 4, b2); - MERGE (b1, b3, 0x0000ffff, 16); - do_put_mem_long(pixels + 2, b1); - do_put_mem_long(pixels + 6, b3); - MERGE (b4, b6, 0x0000ffff, 16); - do_put_mem_long(pixels + 1, b4); - do_put_mem_long(pixels + 5, b6); - MERGE (b5, b7, 0x0000ffff, 16); - do_put_mem_long(pixels + 3, b5); - do_put_mem_long(pixels + 7, b7); - pixels += 8; - } -} - -static void pfield_doline_n7 (uae_u32 *pixels, int wordcount, int lineno) -{ - uae_u8 *real_bplpt[7]; - real_bplpt[0] = DATA_POINTER (0); - real_bplpt[1] = DATA_POINTER (1); - real_bplpt[2] = DATA_POINTER (2); - real_bplpt[3] = DATA_POINTER (3); - real_bplpt[4] = DATA_POINTER (4); - real_bplpt[5] = DATA_POINTER (5); - real_bplpt[6] = DATA_POINTER (6); - - while (wordcount-- > 0) { - uae_u32 b0,b1,b2,b3,b4,b5,b6,b7; - b1 = GETLONG ((uae_u32 *)real_bplpt[6]); real_bplpt[6] += 4; - b2 = GETLONG ((uae_u32 *)real_bplpt[5]); real_bplpt[5] += 4; - b3 = GETLONG ((uae_u32 *)real_bplpt[4]); real_bplpt[4] += 4; - b4 = GETLONG ((uae_u32 *)real_bplpt[3]); real_bplpt[3] += 4; - b5 = GETLONG ((uae_u32 *)real_bplpt[2]); real_bplpt[2] += 4; - b6 = GETLONG ((uae_u32 *)real_bplpt[1]); real_bplpt[1] += 4; - b7 = GETLONG ((uae_u32 *)real_bplpt[0]); real_bplpt[0] += 4; - - MERGE_0(b0, b1, 0x55555555, 1); - MERGE (b2, b3, 0x55555555, 1); - MERGE (b4, b5, 0x55555555, 1); - MERGE (b6, b7, 0x55555555, 1); - - MERGE (b0, b2, 0x33333333, 2); - MERGE (b1, b3, 0x33333333, 2); - MERGE (b4, b6, 0x33333333, 2); - MERGE (b5, b7, 0x33333333, 2); - - MERGE (b0, b4, 0x0f0f0f0f, 4); - MERGE (b1, b5, 0x0f0f0f0f, 4); - MERGE (b2, b6, 0x0f0f0f0f, 4); - MERGE (b3, b7, 0x0f0f0f0f, 4); - - MERGE (b0, b1, 0x00ff00ff, 8); - MERGE (b2, b3, 0x00ff00ff, 8); - MERGE (b4, b5, 0x00ff00ff, 8); - MERGE (b6, b7, 0x00ff00ff, 8); - - MERGE (b0, b2, 0x0000ffff, 16); - do_put_mem_long(pixels, b0); - do_put_mem_long(pixels + 4, b2); - MERGE (b1, b3, 0x0000ffff, 16); - do_put_mem_long(pixels + 2, b1); - do_put_mem_long(pixels + 6, b3); - MERGE (b4, b6, 0x0000ffff, 16); - do_put_mem_long(pixels + 1, b4); - do_put_mem_long(pixels + 5, b6); - MERGE (b5, b7, 0x0000ffff, 16); - do_put_mem_long(pixels + 3, b5); - do_put_mem_long(pixels + 7, b7); - pixels += 8; - } -} - typedef void (*pfield_doline_func)(uae_u32 *, int, int); static pfield_doline_func pfield_doline_n[9]={ pfield_doline_n0, ARM_doline_n1, NEON_doline_n2, NEON_doline_n3, - NEON_doline_n4, pfield_doline_n5, NEON_doline_n6, pfield_doline_n7, + NEON_doline_n4, NEON_doline_n5, NEON_doline_n6, NEON_doline_n7, NEON_doline_n8 }; @@ -2608,7 +2514,7 @@ static void pfield_doline (int lineno) int wordcount = dp_for_drawing->plflinelen; uae_u32 *data = pixdata.apixels_l + MAX_PIXELS_PER_LINE / sizeof(uae_u32); -#if defined(USE_ARMNEON) && !defined(ANDROID) +#if defined(CPU_AARCH64) || defined(USE_ARMNEON) && !defined(ANDROID) pfield_doline_n[bplplanecnt](data, wordcount, lineno); #else real_bplpt[0] = DATA_POINTER(0); @@ -2660,42 +2566,44 @@ static void pfield_doline (int lineno) void init_row_map(void) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; static uae_u8 *oldbufmem; static int oldheight, oldpitch; //static bool oldgenlock; int i, j; - if (gfxvidinfo.drawbuffer.outheight > max_uae_height) { - write_log(_T("Resolution too high, aborting\n")); - abort(); + if (vidinfo->drawbuffer.outheight > max_uae_height) { + write_log (_T("Resolution too high, aborting\n")); + abort (); } if (!row_map) { row_map = xmalloc(uae_u8*, max_uae_height + 1); } - if (oldbufmem && oldbufmem == gfxvidinfo.drawbuffer.bufmem && - oldheight == gfxvidinfo.drawbuffer.outheight && - oldpitch == gfxvidinfo.drawbuffer.rowbytes) + if (oldbufmem && oldbufmem == vidinfo->drawbuffer.bufmem && + oldheight == vidinfo->drawbuffer.outheight && + oldpitch == vidinfo->drawbuffer.rowbytes) return; xfree(row_map_color_burst_buffer); row_map_color_burst_buffer = NULL; if (currprefs.cs_color_burst) { - row_map_color_burst_buffer = xcalloc(uae_u8, gfxvidinfo.drawbuffer.outheight + 2); + row_map_color_burst_buffer = xcalloc(uae_u8, vidinfo->drawbuffer.outheight + 2); } j = oldheight == 0 ? max_uae_height : oldheight; - for (i = gfxvidinfo.drawbuffer.outheight; i < max_uae_height + 1 && i < j + 1; i++) { - row_map[i] = row_tmp; - } - for (i = 0, j = 0; i < gfxvidinfo.drawbuffer.outheight; i++, j += gfxvidinfo.drawbuffer.rowbytes) { - row_map[i] = gfxvidinfo.drawbuffer.bufmem + j; - } - oldbufmem = gfxvidinfo.drawbuffer.bufmem; - oldheight = gfxvidinfo.drawbuffer.outheight; - oldpitch = gfxvidinfo.drawbuffer.rowbytes; + for (i = vidinfo->drawbuffer.outheight; i < max_uae_height + 1 && i < j + 1; i++) { + row_map[i] = row_tmp; + } + for (i = 0, j = 0; i < vidinfo->drawbuffer.outheight; i++, j += vidinfo->drawbuffer.rowbytes) { + row_map[i] = vidinfo->drawbuffer.bufmem + j; + } + oldbufmem = vidinfo->drawbuffer.bufmem; + oldheight = vidinfo->drawbuffer.outheight; + oldpitch = vidinfo->drawbuffer.rowbytes; } static void init_aspect_maps(void) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int i; linedbld = linedbl = currprefs.gfx_vresolution; @@ -2713,7 +2621,7 @@ static void init_aspect_maps(void) visible_bottom_stop = MAX_STOP; set_blanking_limits(); - const int h = gfxvidinfo.drawbuffer.outheight; + const int h = vidinfo->drawbuffer.outheight; if (h == 0) /* Do nothing if the gfx driver hasn't initialized the screen yet */ return; @@ -2822,6 +2730,8 @@ static void pfield_expand_dp_bplcon(void) bpldelay_sh = sh; pfield_mode_changed = true; } + if (sprite_smaller_than_64 && (dp_for_drawing->fmode & 0x0c) == 0x0c) + sprite_smaller_than_64_inuse = true; sprite_smaller_than_64 = (dp_for_drawing->fmode & 0x0c) != 0x0c; #endif ecs_genlock_features_active = (currprefs.chipset_mask & CSMASK_ECS_DENISE) && ((dp_for_drawing->bplcon2 & 0x0c00) || ce_is_borderntrans(colors_for_drawing.extra)) ? 1 : 0; @@ -2830,7 +2740,7 @@ static void pfield_expand_dp_bplcon(void) ecs_genlock_features_mask = 0; if (dp_for_drawing->bplcon3 & 0x0800) { ecs_genlock_features_mask = 1 << ((dp_for_drawing->bplcon2 >> 12) & 7); - } + } if (dp_for_drawing->bplcon3 & 0x0400) { ecs_genlock_features_colorkey = true; } @@ -2843,17 +2753,16 @@ static void pfield_expand_dp_bplcon(void) static bool isham(uae_u16 bplcon0) { - int p = GET_PLANES(bplcon0); + int p = GET_PLANES (bplcon0); if (!(bplcon0 & 0x800)) return 0; if (currprefs.chipset_mask & CSMASK_AGA) { // AGA only has 6 or 8 plane HAM if (p == 6 || p == 8) return 1; - } - else { + } else { // OCS/ECS also supports 5 plane HAM - if (GET_RES_DENISE(bplcon0) > 0) + if (GET_RES_DENISE (bplcon0) > 0) return 0; if (p >= 5) return 1; @@ -2872,9 +2781,9 @@ static void pfield_expand_dp_bplconx(int regno, int v) { case 0x100: // BPLCON0 dp_for_drawing->bplcon0 = v; - dp_for_drawing->bplres = GET_RES_DENISE(v); - dp_for_drawing->nr_planes = GET_PLANES(v); - dp_for_drawing->ham_seen = isham(v); + dp_for_drawing->bplres = GET_RES_DENISE (v); + dp_for_drawing->nr_planes = GET_PLANES (v); + dp_for_drawing->ham_seen = isham (v); if (currprefs.chipset_hr && dp_for_drawing->bplres < currprefs.gfx_resolution) dp_for_drawing->bplres = currprefs.gfx_resolution; break; @@ -2895,7 +2804,7 @@ static void pfield_expand_dp_bplconx(int regno, int v) break; #endif } - pfield_expand_dp_bplcon(); + pfield_expand_dp_bplcon (); set_res_shift(); } @@ -2903,51 +2812,68 @@ static int drawing_color_matches; static enum { color_match_acolors, color_match_full } color_match_type; /* Set up colors_for_drawing to the state at the beginning of the currently drawn - line. Try to avoid copying color tables around whenever possible. */ -static void adjust_drawing_colors(int ctable, int need_full) +line. Try to avoid copying color tables around whenever possible. */ +static void adjust_drawing_colors (int ctable, int need_full) { if (drawing_color_matches != ctable || need_full < 0) { if (need_full) { - color_reg_cpy(&colors_for_drawing, curr_color_tables + ctable); + color_reg_cpy (&colors_for_drawing, curr_color_tables + ctable); color_match_type = color_match_full; - } - else { - memcpy(colors_for_drawing.acolors, curr_color_tables[ctable].acolors, + } else { + memcpy (colors_for_drawing.acolors, curr_color_tables[ctable].acolors, sizeof colors_for_drawing.acolors); colors_for_drawing.extra = curr_color_tables[ctable].extra; color_match_type = color_match_acolors; } drawing_color_matches = ctable; - } - else if (need_full && color_match_type != color_match_full) { - color_reg_cpy(&colors_for_drawing, &curr_color_tables[ctable]); + } else if (need_full && color_match_type != color_match_full) { + color_reg_cpy (&colors_for_drawing, &curr_color_tables[ctable]); color_match_type = color_match_full; } } static void playfield_hard_way(line_draw_func worker_pfield, int first, int last) { - if (first < real_playfield_start) { + int stop = last < real_playfield_end ? last : real_playfield_end; + + src_pixel += playfield_diff; + ham_decode_pixel += playfield_diff; + + if (first < real_playfield_start) { int next = last < real_playfield_start ? last : real_playfield_start; - int diff = next - first; + // left border sprite pfield_do_linetoscr_bordersprite_aga(first, next, false); - if (res_shift >= 0) - diff >>= res_shift; - else - diff <<= res_shift; - src_pixel += diff; - first = next; + // bitplanes + if (stop > real_playfield_start) { + (*worker_pfield)(real_playfield_start, stop, false); + // right border sprite + if (last > real_playfield_end) { + int sfirst = first > real_playfield_end ? first : real_playfield_end; + pfield_do_linetoscr_bordersprite_aga(sfirst, last, false); + } + } + } else { + // bitplanes + if (stop > real_playfield_start) { + (*worker_pfield)(first, stop, false); + // right border sprite + if (last > real_playfield_end) { + int sfirst = first > real_playfield_end ? first : real_playfield_end; + pfield_do_linetoscr_bordersprite_aga(sfirst, last, false); + } + } } - (*worker_pfield)(first, last < real_playfield_end ? last : real_playfield_end, false); - if (last > real_playfield_end) - pfield_do_linetoscr_bordersprite_aga(real_playfield_end, last, false); + + src_pixel -= playfield_diff; + ham_decode_pixel -= playfield_diff; } -static void do_color_changes(line_draw_func worker_border, line_draw_func worker_pfield, int vp) +static void do_color_changes (line_draw_func worker_border, line_draw_func worker_pfield, int vp) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; int i; int lastpos = visible_left_border; - int endpos = visible_left_border + gfxvidinfo.drawbuffer.outwidth; + int endpos = visible_left_border + vidinfo->drawbuffer.outwidth; for (i = dip_for_drawing->first_color_change; i <= dip_for_drawing->last_color_change; i++) { int regno = curr_color_changes[i].regno; @@ -2957,7 +2883,7 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker if (i == dip_for_drawing->last_color_change) nextpos = endpos; else - nextpos = shres_coord_hw_to_window_x(curr_color_changes[i].linepos); + nextpos = shres_coord_hw_to_window_x (curr_color_changes[i].linepos); nextpos_in_range = nextpos; if (nextpos > endpos) @@ -2983,17 +2909,18 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker // playfield if (nextpos_in_range > lastpos && lastpos >= playfield_start && lastpos < playfield_end) { int t = nextpos_in_range <= playfield_end ? nextpos_in_range : playfield_end; - if ((plf2pri >= 5 || plf1pri >= 5) && !(currprefs.chipset_mask & CSMASK_AGA)) + if ((plf2pri >= 5 || plf1pri >= 5) && !(currprefs.chipset_mask & CSMASK_AGA)) { weird_bitplane_fix(lastpos, t); - if (bplxor && may_require_hard_way && worker_pfield != pfield_do_linetoscr_bordersprite_aga) + } + if (may_require_hard_way && (may_require_hard_way < 0 || (bplxor && may_require_hard_way && worker_pfield != pfield_do_linetoscr_bordersprite_aga))) { playfield_hard_way(worker_pfield, lastpos, t); - else + } else { (*worker_pfield) (lastpos, t, 0); + } lastpos = t; } - } - else { + } else { // special AGA borderblank 1 hires pixel delay // borderblank left border (hblank end to playfield_start_pre) @@ -3012,10 +2939,11 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker // playfield with last hires pixel not drawn. if (nextpos_in_range > lastpos && lastpos >= playfield_start && lastpos < playfield_end_pre) { int t = nextpos_in_range <= playfield_end_pre ? nextpos_in_range : playfield_end_pre; - if (bplxor && may_require_hard_way && worker_pfield != pfield_do_linetoscr_bordersprite_aga) + if (may_require_hard_way && (may_require_hard_way < 0 || (bplxor && may_require_hard_way && worker_pfield != pfield_do_linetoscr_bordersprite_aga))) { playfield_hard_way(worker_pfield, lastpos, t); - else + } else { (*worker_pfield) (lastpos, t, 0); + } lastpos = t; } @@ -3042,13 +2970,11 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker } if (regno >= 0x1000) { - pfield_expand_dp_bplconx(regno, value); - } - else if (regno >= 0 && !(value & COLOR_CHANGE_MASK)) { + pfield_expand_dp_bplconx (regno, value); + } else if (regno >= 0 && !(value & COLOR_CHANGE_MASK)) { color_reg_set(&colors_for_drawing, regno, value); colors_for_drawing.acolors[regno] = getxcolor(value); - } - else if (regno == 0 && (value & COLOR_CHANGE_MASK)) { + } else if (regno == 0 && (value & COLOR_CHANGE_MASK)) { if (value & COLOR_CHANGE_BRDBLANK) { colors_for_drawing.extra &= ~(1 << CE_BORDERBLANK); colors_for_drawing.extra &= ~(1 << CE_BORDERNTRANS); @@ -3056,14 +2982,12 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker colors_for_drawing.extra |= (value & 1) != 0 ? (1 << CE_BORDERBLANK) : 0; colors_for_drawing.extra |= (value & 3) == 2 ? (1 << CE_BORDERSPRITE) : 0; colors_for_drawing.extra |= (value & 5) == 4 ? (1 << CE_BORDERNTRANS) : 0; - } - else if (value & COLOR_CHANGE_SHRES_DELAY) { + } else if (value & COLOR_CHANGE_SHRES_DELAY) { colors_for_drawing.extra &= ~(1 << CE_SHRES_DELAY); colors_for_drawing.extra &= ~(1 << (CE_SHRES_DELAY + 1)); colors_for_drawing.extra |= (value & 3) << CE_SHRES_DELAY; pfield_expand_dp_bplcon(); - } - else if (value & COLOR_CHANGE_HSYNC_HACK) { + } else if (value & COLOR_CHANGE_HSYNC_HACK) { hsync_shift_hack = (uae_s8)value; } } @@ -3075,15 +2999,15 @@ static void do_color_changes(line_draw_func worker_border, line_draw_func worker // outside of visible area // Just overwrite with black. Above code needs to run because of custom registers, // not worth the trouble for separate code path just for max 10 lines or so - (*worker_border) (visible_left_border, visible_left_border + gfxvidinfo.drawbuffer.outwidth, true); + (*worker_border) (visible_left_border, visible_left_border + vidinfo->drawbuffer.outwidth, 1); } #endif if (hsync_shift_hack > 0) { // hpos shift hack - int shift = (hsync_shift_hack << lores_shift) * gfxvidinfo.drawbuffer.pixbytes; + int shift = (hsync_shift_hack << lores_shift) * vidinfo->drawbuffer.pixbytes; if (shift) { - int firstpos = visible_left_border * gfxvidinfo.drawbuffer.pixbytes; - int lastpos = (visible_left_border + gfxvidinfo.drawbuffer.outwidth) * gfxvidinfo.drawbuffer.pixbytes; + int firstpos = visible_left_border * vidinfo->drawbuffer.pixbytes; + int lastpos = (visible_left_border + vidinfo->drawbuffer.outwidth) * vidinfo->drawbuffer.pixbytes; memmove(xlinebuffer + firstpos, xlinebuffer + firstpos + shift, lastpos - firstpos - shift); memset(xlinebuffer + lastpos - shift, 0, shift); } @@ -3103,8 +3027,9 @@ enum double_how { dh_emerg }; -static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int follow_ypos) +static void pfield_draw_line (struct vidbuffer *vb, int lineno, int gfx_ypos, int follow_ypos) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; static int warned = 0; int border = 0; int do_double = 0; @@ -3123,8 +3048,8 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int switch (ls) { case LINE_REMEMBERED_AS_PREVIOUS: - // if (!warned) // happens when program messes up with VPOSW - // write_log (_T("Shouldn't get here... this is a bug.\n")), warned++; +// if (!warned) // happens when program messes up with VPOSW +// write_log (_T("Shouldn't get here... this is a bug.\n")), warned++; return; case LINE_BLACK: @@ -3163,6 +3088,7 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int } have_color_changes = is_color_changes(dip_for_drawing); + sprite_smaller_than_64_inuse = false; xlinebuffer = row_map[gfx_ypos], dh = dh_buf; xlinebuffer -= linetoscr_x_adjust_pixbytes; @@ -3173,11 +3099,11 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int if (border == 0) { - pfield_expand_dp_bplcon(); - pfield_init_linetoscr(false); - pfield_doline(lineno); + pfield_expand_dp_bplcon (); + pfield_init_linetoscr (false); + pfield_doline (lineno); - adjust_drawing_colors(dp_for_drawing->ctable, dp_for_drawing->ham_seen || bplehb || ecsshres); + adjust_drawing_colors (dp_for_drawing->ctable, dp_for_drawing->ham_seen || bplehb || ecsshres); /* The problem is that we must call decode_ham() BEFORE we do the sprites. */ if (dp_for_drawing->ham_seen) { @@ -3187,17 +3113,17 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int uae_u16 b3 = dp_for_drawing->bplcon3; uae_u16 b4 = dp_for_drawing->bplcon4; uae_u16 fm = dp_for_drawing->fmode; - init_ham_decoding(); - do_color_changes(dummy_worker, decode_ham, lineno); + init_ham_decoding (); + do_color_changes (dummy_worker, decode_ham, lineno); if (have_color_changes) { // do_color_changes() did color changes and register changes, restore them. - adjust_drawing_colors(dp_for_drawing->ctable, -1); + adjust_drawing_colors (dp_for_drawing->ctable, -1); dp_for_drawing->bplcon0 = b0; dp_for_drawing->bplcon2 = b2; dp_for_drawing->bplcon3 = b3; dp_for_drawing->bplcon4 = b4; dp_for_drawing->fmode = fm; - pfield_expand_dp_bplcon(); + pfield_expand_dp_bplcon (); } hposblank = ohposblank; ham_decode_pixel = src_pixel; @@ -3209,54 +3135,53 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int int i; #ifdef AGA if (ce_is_bordersprite(colors_for_drawing.extra) && dp_for_drawing->bordersprite_seen && !ce_is_borderblank(colors_for_drawing.extra)) - clear_bitplane_border_aga(); + clear_bitplane_border_aga (); #endif for (i = 0; i < dip_for_drawing->nr_sprites; i++) { #ifdef AGA if (currprefs.chipset_mask & CSMASK_AGA) - draw_sprites_aga(curr_sprite_entries + dip_for_drawing->first_sprite_entry + i, 1); + draw_sprites_aga (curr_sprite_entries + dip_for_drawing->first_sprite_entry + i); else #endif - draw_sprites_ecs(curr_sprite_entries + dip_for_drawing->first_sprite_entry + i); + draw_sprites_ecs (curr_sprite_entries + dip_for_drawing->first_sprite_entry + i); } } #ifdef AGA if (dip_for_drawing->nr_sprites && ce_is_bordersprite(colors_for_drawing.extra) && !ce_is_borderblank(colors_for_drawing.extra) && dp_for_drawing->bordersprite_seen) - do_color_changes(pfield_do_linetoscr_bordersprite_aga, pfield_do_linetoscr_spr, lineno); + do_color_changes (pfield_do_linetoscr_bordersprite_aga, pfield_do_linetoscr_spr, lineno); else #endif - do_color_changes(pfield_do_fill_line, dip_for_drawing->nr_sprites ? pfield_do_linetoscr_spr : pfield_do_linetoscr, lineno); + do_color_changes (pfield_do_fill_line, dip_for_drawing->nr_sprites ? pfield_do_linetoscr_spr : pfield_do_linetoscr, lineno); if (dh == dh_emerg) - memcpy(row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy (row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); if (do_double) { if (dh == dh_emerg) - memcpy(row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy (row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); else if (dh == dh_buf) - memcpy(row_map[follow_ypos], row_map[gfx_ypos], gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy (row_map[follow_ypos], row_map[gfx_ypos], vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); if (need_genlock_data) - memcpy(row_map_genlock[follow_ypos], row_map_genlock[gfx_ypos], gfxvidinfo.drawbuffer.outwidth); + memcpy(row_map_genlock[follow_ypos], row_map_genlock[gfx_ypos], vidinfo->drawbuffer.outwidth); } if (dip_for_drawing->nr_sprites) - pfield_erase_hborder_sprites(); + pfield_erase_hborder_sprites (); - } - else if (border > 0) { // border > 0: top or bottom border + } else if (border > 0) { // border > 0: top or bottom border bool dosprites = false; - adjust_drawing_colors(dp_for_drawing->ctable, 0); + adjust_drawing_colors (dp_for_drawing->ctable, 0); #ifdef AGA /* this makes things complex.. */ if (dp_for_drawing->bordersprite_seen && !ce_is_borderblank(colors_for_drawing.extra) && dip_for_drawing->nr_sprites) { dosprites = true; - pfield_expand_dp_bplcon(); - pfield_init_linetoscr(true); - pfield_erase_vborder_sprites(); + pfield_expand_dp_bplcon (); + pfield_init_linetoscr (true); + pfield_erase_vborder_sprites (); } #endif @@ -3267,8 +3192,7 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int hposblank = 1; fill_line_border(lineno); hposblank = tmp; - } - else { + } else { // normal border line fill_line_border(lineno); } @@ -3289,46 +3213,47 @@ static void pfield_draw_line(struct vidbuffer *vb, int lineno, int gfx_ypos, int if (dosprites) { for (int i = 0; i < dip_for_drawing->nr_sprites; i++) - draw_sprites_aga(curr_sprite_entries + dip_for_drawing->first_sprite_entry + i, 1); - do_color_changes(pfield_do_linetoscr_bordersprite_aga, pfield_do_linetoscr_bordersprite_aga, lineno); + draw_sprites_aga (curr_sprite_entries + dip_for_drawing->first_sprite_entry + i); + do_color_changes (pfield_do_linetoscr_bordersprite_aga, pfield_do_linetoscr_bordersprite_aga, lineno); #else if (0) { #endif - } - else { + } else { playfield_start = visible_right_border; playfield_end = visible_right_border; playfield_start_pre = playfield_start; playfield_end_pre = playfield_end; - do_color_changes(pfield_do_fill_line, pfield_do_fill_line, lineno); + do_color_changes (pfield_do_fill_line, pfield_do_fill_line, lineno); } if (dh == dh_emerg) - memcpy(row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy(row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); if (do_double) { if (dh == dh_emerg) - memcpy(row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy(row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_pixbytes, vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); else if (dh == dh_buf) - memcpy(row_map[follow_ypos], row_map[gfx_ypos], gfxvidinfo.drawbuffer.pixbytes * gfxvidinfo.drawbuffer.outwidth); + memcpy(row_map[follow_ypos], row_map[gfx_ypos], vidinfo->drawbuffer.pixbytes * vidinfo->drawbuffer.outwidth); } - } - else { + } else { // top or bottom blanking region int tmp = hposblank; hposblank = 1; fill_line_border(lineno); hposblank = tmp; + } } static void center_image() { - const int deltaToBorder = (gfxvidinfo.drawbuffer.outwidth >> currprefs.gfx_resolution) - 320; + struct amigadisplay *ad = &adisplays; + struct vidbuf_description *vidinfo = &ad->gfxvidinfo; + const int deltaToBorder = (vidinfo->drawbuffer.outwidth >> currprefs.gfx_resolution) - 320; visible_left_border = 73 - (deltaToBorder >> 1); visible_right_border = 393 + (deltaToBorder >> 1); @@ -3336,11 +3261,11 @@ static void center_image() visible_right_border <<= lores_shift; linetoscr_x_adjust_pixels = visible_left_border; - linetoscr_x_adjust_pixbytes = linetoscr_x_adjust_pixels * gfxvidinfo.drawbuffer.pixbytes; + linetoscr_x_adjust_pixbytes = linetoscr_x_adjust_pixels * vidinfo->drawbuffer.pixbytes; int max_drawn_amiga_line_tmp = max_drawn_amiga_line; - if (max_drawn_amiga_line_tmp > gfxvidinfo.drawbuffer.outheight) - max_drawn_amiga_line_tmp = gfxvidinfo.drawbuffer.outheight; + if (max_drawn_amiga_line_tmp > vidinfo->drawbuffer.outheight) + max_drawn_amiga_line_tmp = vidinfo->drawbuffer.outheight; max_drawn_amiga_line_tmp >>= linedbl; thisframe_y_adjust = minfirstline + currprefs.vertical_offset; @@ -3359,7 +3284,8 @@ static int frame_res_cnt; static int autoswitch_old_resolution; static void init_drawing_frame(void) { - int maxline; + struct amigadisplay *ad = &adisplays; + int i, maxline; static int frame_res_old; int largest_res = 0; @@ -3384,8 +3310,7 @@ static void init_drawing_frame(void) if (can_use_lores > AUTO_LORES_FRAMES && 0) { lores_factor = 1; lores_set(0); - } - else { + } else { can_use_lores++; lores_reset(); } @@ -3418,14 +3343,12 @@ static void init_drawing_frame(void) last_drawn_line = 0; first_drawn_line = 32767; - first_block_line = last_block_line = NO_BLOCK; - if (frame_redraw_necessary) { + if (ad->frame_redraw_necessary) { reset_decision_table(); - custom_frame_redraw_necessary = 1; - frame_redraw_necessary--; - } - else { - custom_frame_redraw_necessary = 0; + ad->custom_frame_redraw_necessary = 1; + ad->frame_redraw_necessary--; + } else { + ad->custom_frame_redraw_necessary = 0; } center_image(); @@ -3436,7 +3359,7 @@ static void init_drawing_frame(void) drawing_color_matches = -1; } -void putpixel(uae_u8* buf, uae_u8* genlockbuf, int bpp, int x, xcolnr c8, int opaq) +void putpixel(uae_u8 *buf, uae_u8 *genlockbuf, int bpp, int x, xcolnr c8, int opaq) { if (x <= 0) return; @@ -3444,39 +3367,39 @@ void putpixel(uae_u8* buf, uae_u8* genlockbuf, int bpp, int x, xcolnr c8, int op if (genlockbuf) genlockbuf[x] = 0xff; - switch (bpp) - { + switch (bpp) { case 1: buf[x] = (uae_u8)c8; break; case 2: - { - uae_u16* p = (uae_u16*)buf + x; - *p = (uae_u16)c8; - break; - } + { + uae_u16 *p = (uae_u16*)buf + x; + *p = (uae_u16)c8; + break; + } case 3: /* no 24 bit yet */ break; case 4: - { - int i; - uae_u32* p = (uae_u32*)buf + x; - *p = c8; - break; - } + { + int i; + uae_u32 *p = (uae_u32*)buf + x; + *p = c8; + break; + } } } static void draw_status_line(int line, int statusy) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; xlinebuffer = row_map[line]; uae_u8 *buf = xlinebuffer; if (!buf) return; if (statusy < 0) return; - draw_status_line_single(buf, gfxvidinfo.drawbuffer.pixbytes, statusy, gfxvidinfo.drawbuffer.outwidth, xredcolors, xgreencolors, xbluecolors, NULL); + draw_status_line_single(buf, vidinfo->drawbuffer.pixbytes, statusy, vidinfo->drawbuffer.outwidth, xredcolors, xgreencolors, xbluecolors, NULL); } static void refresh_indicator_init(void) @@ -3501,7 +3424,7 @@ static const int refresh_indicator_colors[] = { 0x777, 0x0f0, 0x00f, 0xff0, 0xf0 static void refresh_indicator_update(struct vidbuffer *vb) { - struct vidbuf_description *vidinfo = &gfxvidinfo; + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; for (int i = 0; i < max_ypos_thisframe; i++) { int i1 = i + min_ypos_for_screen; int line = i + thisframe_y_adjust_real; @@ -3525,8 +3448,7 @@ static void refresh_indicator_update(struct vidbuffer *vb) int color2 = 0; if (pixel <= 4) { color1 = color2 = refresh_indicator_colors[pixel]; - } - else if (pixel <= 8) { + } else if (pixel <= 8) { color2 = refresh_indicator_colors[pixel - 5]; } for (int x = 0; x < 8; x++) { @@ -3538,48 +3460,51 @@ static void refresh_indicator_update(struct vidbuffer *vb) } } -static void draw_frame2(struct vidbuffer *vbin, struct vidbuffer *vbout) +static void draw_frame2() { + struct amigadisplay *ad = &adisplays; + if (ad->framecnt == 0) { + struct vidbuf_description *vidinfo = &ad->gfxvidinfo; + struct vidbuffer *vb = &vidinfo->drawbuffer; + + for (int i = 0; i < max_ypos_thisframe; i++) { + int i1 = i + min_ypos_for_screen; + int line = i + thisframe_y_adjust_real; + int whereline = amiga2aspect_line_map[i1]; + int wherenext = amiga2aspect_line_map[i1 + 1]; - for (int i = 0; i < max_ypos_thisframe; i++) { - int i1 = i + min_ypos_for_screen; - int line = i + thisframe_y_adjust_real; - int whereline = amiga2aspect_line_map[i1]; - int wherenext = amiga2aspect_line_map[i1 + 1]; - - if (whereline >= vbin->outheight) + if (whereline >= vb->outheight) break; if (whereline < 0) continue; hposblank = 0; - pfield_draw_line(vbout, line, whereline, wherenext); + pfield_draw_line(vb, line, whereline, wherenext); } + } } bool draw_frame(struct vidbuffer *vb) { + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; uae_u8 oldstate[LINESTATE_SIZE]; struct vidbuffer oldvb{}; - memcpy(&oldvb, &gfxvidinfo.drawbuffer, sizeof(struct vidbuffer)); - memcpy(&gfxvidinfo.drawbuffer, vb, sizeof(struct vidbuffer)); + memcpy(&oldvb, &vidinfo->drawbuffer, sizeof(struct vidbuffer)); + memcpy(&vidinfo->drawbuffer, vb, sizeof(struct vidbuffer)); init_row_map(); - memcpy(oldstate, linestate, LINESTATE_SIZE); + memcpy (oldstate, linestate, LINESTATE_SIZE); for (int i = 0; i < LINESTATE_SIZE; i++) { uae_u8 v = linestate[i]; if (v == LINE_REMEMBERED_AS_PREVIOUS) { linestate[i - 1] = LINE_DECIDED_DOUBLE; v = LINE_AS_PREVIOUS; - } - else if (v == LINE_DONE_AS_PREVIOUS) { + } else if (v == LINE_DONE_AS_PREVIOUS) { linestate[i - 1] = LINE_DECIDED_DOUBLE; v = LINE_AS_PREVIOUS; - } - else if (v == LINE_REMEMBERED_AS_BLACK) { + } else if (v == LINE_REMEMBERED_AS_BLACK) { v = LINE_BLACK; - } - else if (v == LINE_DONE) { + } else if (v == LINE_DONE) { v = LINE_DECIDED; } // if (i < maxvpos) @@ -3589,27 +3514,32 @@ bool draw_frame(struct vidbuffer *vb) last_drawn_line = 0; first_drawn_line = 32767; drawing_color_matches = -1; - draw_frame2(vb, NULL); + draw_frame2(); last_drawn_line = 0; first_drawn_line = 32767; drawing_color_matches = -1; memcpy(linestate, oldstate, LINESTATE_SIZE); - memcpy(&gfxvidinfo.drawbuffer, &oldvb, sizeof(struct vidbuffer)); + memcpy (&vidinfo->drawbuffer, &oldvb, sizeof (struct vidbuffer)); init_row_map(); return true; } static void setnativeposition(struct vidbuffer *vb) { - vb->outwidth = gfxvidinfo.drawbuffer.outwidth; - vb->outheight = gfxvidinfo.drawbuffer.outheight; + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; + vb->outwidth = vidinfo->drawbuffer.outwidth; + vb->outheight = vidinfo->drawbuffer.outheight; } static void finish_drawing_frame(bool drawlines) { - struct vidbuffer *vb = &gfxvidinfo.drawbuffer; + struct amigadisplay *ad = &adisplays; + struct vidbuf_description *vidinfo = &ad->gfxvidinfo; + struct vidbuffer *vb = &vidinfo->drawbuffer; -if (!drawlines) { + vb->last_drawn_line = 0; + + if (!drawlines) { return; } @@ -3618,18 +3548,18 @@ if (!drawlines) { return; } - draw_frame2(vb, vb); + draw_frame2(); if (currprefs.leds_on_screen) { for (int i = 0; i < TD_TOTAL_HEIGHT; i++) { - int line = gfxvidinfo.drawbuffer.outheight - TD_TOTAL_HEIGHT + i; + int line = vidinfo->drawbuffer.outheight - TD_TOTAL_HEIGHT + i; draw_status_line(line, i); } } if (currprefs.cs_cd32fmv) { if (cd32_fmv_active) { - cd32_fmv_genlock(vb, &gfxvidinfo.drawbuffer); + cd32_fmv_genlock(vb, &vidinfo->drawbuffer); setnativeposition(vb); } } @@ -3640,23 +3570,24 @@ if (!drawlines) { void check_prefs_picasso(void) { #ifdef PICASSO96 - if (picasso_on && picasso_redraw_necessary) + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on && ad->picasso_redraw_necessary) picasso_refresh(); - picasso_redraw_necessary = 0; + ad->picasso_redraw_necessary = 0; - if (picasso_requested_on == picasso_on && !picasso_requested_forced_on) + if (ad->picasso_requested_on == ad->picasso_on && !ad->picasso_requested_forced_on) return; - picasso_requested_forced_on = false; - picasso_on = picasso_requested_on; + ad->picasso_requested_forced_on = false; + ad->picasso_on = ad->picasso_requested_on; - if (!picasso_on) + if (!ad->picasso_on) clear_inhibit_frame(IHF_PICASSO); else set_inhibit_frame(IHF_PICASSO); - gfx_set_picasso_state(picasso_on); - picasso_enablescreen(picasso_requested_on); + gfx_set_picasso_state(ad->picasso_on); + picasso_enablescreen(ad->picasso_requested_on); notice_screen_contents_lost(); notice_new_xcolors(); @@ -3679,15 +3610,16 @@ void redraw_frame(void) void full_redraw_all(void) { bool redraw = false; - struct vidbuf_description *vidinfo = &gfxvidinfo; + struct amigadisplay *ad = &adisplays; + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; if (vidinfo->drawbuffer.outheight && amiga2aspect_line_map) { notice_screen_contents_lost(); - if (!picasso_on) { + if (!ad->picasso_on) { redraw_frame(); redraw = true; } } - if (picasso_on) { + if (ad->picasso_on) { picasso_refresh(); redraw = true; } @@ -3722,11 +3654,12 @@ bool vsync_handle_check(void) void vsync_handle_redraw(int long_field, int lof_changed, uae_u16 bplcon0p, uae_u16 bplcon3p, bool drawlines) { + struct amigadisplay *ad = &adisplays; last_redraw_point++; if (lof_changed || interlace_seen <= 0 || (currprefs.gfx_iscanlines && interlace_seen > 0) || last_redraw_point >= 2 || long_field || doublescan < 0) { last_redraw_point = 0; - if (framecnt == 0) { + if (ad->framecnt == 0) { if (render_tid) { while (render_thread_busy) sleep_millis(1); @@ -3758,7 +3691,7 @@ void vsync_handle_redraw(int long_field, int lof_changed, uae_u16 bplcon0p, uae_ count_frame(); - if (framecnt == 0) { + if (ad->framecnt == 0) { init_drawing_frame(); } } @@ -3767,13 +3700,14 @@ void vsync_handle_redraw(int long_field, int lof_changed, uae_u16 bplcon0p, uae_ void hsync_record_line_state(int lineno, enum nln_how how, int changed) { + struct amigadisplay *ad = &adisplays; uae_u8 *state; - if (framecnt != 0) + if (ad->framecnt != 0) return; state = linestate + lineno; - changed |= frame_redraw_necessary != 0 || refresh_indicator_buffer != NULL; + changed |= ad->frame_redraw_necessary != 0 || refresh_indicator_buffer != NULL; switch (how) { case nln_normal: @@ -3806,15 +3740,15 @@ void hsync_record_line_state(int lineno, enum nln_how how, int changed) case nln_lower_black_always: state[1] = LINE_BLACK; *state = LINE_DECIDED; - // if (lineno == (maxvpos + lof_store) * 2 - 1) - // *state = LINE_BLACK; +// if (lineno == (maxvpos + lof_store) * 2 - 1) +// *state = LINE_BLACK; break; case nln_lower_black: changed |= state[0] != LINE_DONE; state[1] = LINE_DONE; *state = changed ? LINE_DECIDED : LINE_DONE; - // if (lineno == (maxvpos + lof_store) * 2 - 1) - // *state = LINE_BLACK; +// if (lineno == (maxvpos + lof_store) * 2 - 1) +// *state = LINE_BLACK; break; case nln_upper_black_always: *state = LINE_DECIDED; @@ -3868,8 +3802,7 @@ bool notice_interlace_seen(bool lace) changed = true; } interlace_seen = currprefs.gfx_vresolution ? 1 : -1; - } - else { + } else { if (interlace_seen) { changed = true; } @@ -3935,9 +3868,8 @@ static void gen_direct_drawing_table(void) #endif } -static void *render_thread(void *unused) +static int render_thread(void *unused) { - struct vidbuffer *vb = &gfxvidinfo.drawbuffer; for (;;) { render_thread_busy = false; uae_u32 signal = read_comm_pipe_u32_blocking(render_pipe); @@ -3945,7 +3877,7 @@ static void *render_thread(void *unused) switch (signal) { case RENDER_SIGNAL_PARTIAL: - draw_frame2(vb, vb); + draw_frame2(); break; case RENDER_SIGNAL_FRAME_DONE: @@ -3955,13 +3887,16 @@ static void *render_thread(void *unused) case RENDER_SIGNAL_QUIT: render_tid = nullptr; - return nullptr; + return 0; } } } void drawing_init(void) { + struct amigadisplay *ad = &adisplays; + struct vidbuf_description *vidinfo = &ad->gfxvidinfo; + refresh_indicator_init(); gen_pfield_tables(); @@ -3984,36 +3919,39 @@ void drawing_init(void) #ifdef PICASSO96 if (!isrestore()) { - picasso_on = 0; - picasso_requested_on = 0; + ad->picasso_on = 0; + ad->picasso_requested_on = 0; gfx_set_picasso_state(0); } #endif - xlinebuffer = gfxvidinfo.drawbuffer.bufmem; + xlinebuffer = vidinfo->drawbuffer.bufmem; xlinebuffer_genlock = NULL; - inhibit_frame = 0; + ad->inhibit_frame = 0; reset_drawing(); } -int isvsync_chipset(void) -{ - if (picasso_on) - return 0; - return 1; -} +//int isvsync_chipset(void) +//{ +// struct amigadisplay *ad = &adisplays; +// if (ad->picasso_on) +// return 0; +// return 1; +//} int isvsync_rtg(void) { - if (!picasso_on) + struct amigadisplay *ad = &adisplays; + if (!ad->picasso_on) return 0; return 1; } int isvsync(void) { - if (picasso_on) + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on) return isvsync_rtg(); return isvsync_chipset(); } diff --git a/src/events.cpp b/src/events.cpp index 8ac16f67..02dc2000 100644 --- a/src/events.cpp +++ b/src/events.cpp @@ -7,8 +7,6 @@ * Copyright 1995 Alessandro Bissacco * Copyright 2000-2012 Toni Wilen */ -#include - #include "sysdeps.h" #include "options.h" @@ -34,12 +32,12 @@ void events_reset_syncline(void) void events_schedule(void) { - int i; - unsigned long int mintime = ~0L; - for (i = 0; i < ev_max; i++) { - if (eventtab[i].active) { - unsigned long int eventtime = eventtab[i].evtime - currcycle; + for (auto& i : eventtab) + { + if (i.active) + { + auto eventtime = i.evtime - currcycle; if (eventtime < mintime) mintime = eventtime; } @@ -50,13 +48,16 @@ void events_schedule(void) static bool event_check_vsync(void) { /* Keep only CPU emulation running while waiting for sync point. */ - if (is_syncline) { + if (is_syncline) + { int rpt = read_processor_time(); int v = rpt - vsyncmintime; - if (v > vsynctimebase || v < -vsynctimebase) { + if (v > vsynctimebase || v < -vsynctimebase) + { v = 0; } - if (v < speedup_timelimit) { + if (v < speedup_timelimit) + { regs.pissoff = pissoff_value; return true; } @@ -65,60 +66,54 @@ static bool event_check_vsync(void) return false; } -void do_cycles_cpu_fastest (unsigned long cycles_to_add) +void do_cycles_cpu_fastest(uae_u32 cycles_to_add) { - if ((regs.pissoff -= cycles_to_add) > 0) - return; + if ((regs.pissoff -= cycles_to_add) > 0) + return; - cycles_to_add = -regs.pissoff; - regs.pissoff = 0; + cycles_to_add = -regs.pissoff; + regs.pissoff = 0; - /* Keep only CPU emulation running while waiting for sync point. */ - if (is_syncline) { - int rpt = read_processor_time (); - int v = rpt - vsyncmintime; - if (v > vsynctimebase || v < -vsynctimebase) { - v = 0; - } - if (v < speedup_timelimit) { - regs.pissoff = pissoff_value; - return; - } - is_syncline = 0; - } + if (is_syncline) + { + if (event_check_vsync()) + return; + } - while ((nextevent - currcycle) <= cycles_to_add) { - int i; + while ((nextevent - currcycle) <= cycles_to_add) + { + cycles_to_add -= (nextevent - currcycle); + currcycle = nextevent; - cycles_to_add -= (nextevent - currcycle); - currcycle = nextevent; - - for (i = 0; i < ev_max; i++) { - if (eventtab[i].active && eventtab[i].evtime == currcycle) { - (*eventtab[i].handler)(); - } - } - events_schedule(); - } - currcycle += cycles_to_add; + for (auto& i : eventtab) + { + if (i.active && i.evtime == currcycle) + { + (*i.handler)(); + } + } + events_schedule(); + } + currcycle += cycles_to_add; } -void do_cycles_cpu_norm (unsigned long cycles_to_add) +void do_cycles_cpu_norm(uae_u32 cycles_to_add) { - while ((nextevent - currcycle) <= cycles_to_add) { - int i; + while ((nextevent - currcycle) <= cycles_to_add) + { + cycles_to_add -= (nextevent - currcycle); + currcycle = nextevent; - cycles_to_add -= (nextevent - currcycle); - currcycle = nextevent; - - for (i = 0; i < ev_max; i++) { - if (eventtab[i].active && eventtab[i].evtime == currcycle) { - (*eventtab[i].handler)(); - } - } - events_schedule(); - } - currcycle += cycles_to_add; + for (auto& i : eventtab) + { + if (i.active && i.evtime == currcycle) + { + (*i.handler)(); + } + } + events_schedule(); + } + currcycle += cycles_to_add; } do_cycles_func do_cycles = do_cycles_cpu_norm; @@ -128,56 +123,67 @@ void MISC_handler(void) static bool dorecheck; bool recheck; int i; - evt mintime; - evt ct = get_cycles(); - static int recursive; + evt mintime; + evt ct = get_cycles(); + static int recursive; - if (recursive) { + if (recursive) + { dorecheck = true; - return; + return; } - recursive++; - eventtab[ev_misc].active = 0; + recursive++; + eventtab[ev_misc].active = false; recheck = true; - while (recheck) { + while (recheck) + { recheck = false; - mintime = ~0L; - for (i = 0; i < ev2_max; i++) { - if (eventtab2[i].active) { - if (eventtab2[i].evtime == ct) { - eventtab2[i].active = false; - eventtab2[i].handler(eventtab2[i].data); - if (dorecheck || eventtab2[i].active) { + mintime = ~0L; + for (i = 0; i < ev2_max; i++) + { + if (eventtab2[i].active) + { + if (eventtab2[i].evtime == ct) + { + eventtab2[i].active = false; + eventtab2[i].handler(eventtab2[i].data); + if (dorecheck || eventtab2[i].active) + { recheck = true; dorecheck = false; - } - } else { - evt eventtime = eventtab2[i].evtime - ct; - if (eventtime < mintime) - mintime = eventtime; - } - } - } + } + } + else + { + auto eventtime = eventtab2[i].evtime - ct; + if (eventtime < mintime) + mintime = eventtime; + } + } + } } - if (mintime != ~0UL) { + if (mintime != ~0UL) + { eventtab[ev_misc].active = true; - eventtab[ev_misc].evtime = ct + mintime; - events_schedule(); - } - recursive--; + eventtab[ev_misc].evtime = ct + mintime; + events_schedule(); + } + recursive--; } -void event2_newevent_xx (int no, evt t, uae_u32 data, evfunc2 func) +void event2_newevent_xx(int no, evt t, uae_u32 data, evfunc2 func) { - evt et; static int next = ev2_misc; - et = t + get_cycles (); - if (no < 0) { + auto et = t + get_cycles(); + if (no < 0) + { no = next; - for (;;) { - if (!eventtab2[no].active) { + for (;;) + { + if (!eventtab2[no].active) + { break; } if (eventtab2[no].evtime == et && eventtab2[no].handler == func && eventtab2[no].data == data) @@ -185,8 +191,9 @@ void event2_newevent_xx (int no, evt t, uae_u32 data, evfunc2 func) no++; if (no == ev2_max) no = ev2_misc; - if (no == next) { - write_log (_T("out of event2's!\n")); + if (no == next) + { + write_log(_T("out of event2's!\n")); return; } } @@ -196,19 +203,5 @@ void event2_newevent_xx (int no, evt t, uae_u32 data, evfunc2 func) eventtab2[no].evtime = et; eventtab2[no].handler = func; eventtab2[no].data = data; - MISC_handler (); -} - -void event2_newevent_x_replace(evt t, uae_u32 data, evfunc2 func) -{ - for (int i = 0; i < ev2_max; i++) { - if (eventtab2[i].active && eventtab2[i].handler == func) { - eventtab2[i].active = false; - } - } - if (((int)t) <= 0) { - func(data); - return; - } - event2_newevent_xx(-1, t * CYCLE_UNIT, data, func); + MISC_handler(); } diff --git a/src/expansion.cpp b/src/expansion.cpp index f27aaed2..d4424cb8 100644 --- a/src/expansion.cpp +++ b/src/expansion.cpp @@ -1,27 +1,31 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * AutoConfig (tm) Expansions (ZorroII/III) - * - * Copyright 1996,1997 Stefan Reinauer - * Copyright 1997 Brian King - * - added gfxcard code - * - */ -#include -#include +/* +* UAE - The Un*x Amiga Emulator +* +* AutoConfig (tm) Expansions (ZorroII/III) +* +* Copyright 1996,1997 Stefan Reinauer +* Copyright 1997 Brian King +* - added gfxcard code +* +*/ +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" +#include "uae.h" +#include "traps.h" #include "memory.h" #include "rommgr.h" +#include "custom.h" #include "newcpu.h" #include "savestate.h" #include "gfxboard.h" #include "cd32_fmv.h" #include "gayle.h" #include "autoconf.h" +#include "devices.h" + #define CARD_FLAG_CAN_Z3 1 @@ -43,14 +47,14 @@ /* 00 / 02 */ /* er_Type */ -#define Z2_MEM_8MB 0x00 /* Size of Memory Block */ -#define Z2_MEM_4MB 0x07 -#define Z2_MEM_2MB 0x06 -#define Z2_MEM_1MB 0x05 +#define Z2_MEM_8MB 0x00 /* Size of Memory Block */ +#define Z2_MEM_4MB 0x07 +#define Z2_MEM_2MB 0x06 +#define Z2_MEM_1MB 0x05 #define Z2_MEM_512KB 0x04 #define Z2_MEM_256KB 0x03 #define Z2_MEM_128KB 0x02 -#define Z2_MEM_64KB 0x01 +#define Z2_MEM_64KB 0x01 /* extended definitions */ #define Z3_MEM_16MB 0x00 #define Z3_MEM_32MB 0x01 @@ -75,19 +79,8 @@ /* Manufacturer */ #define commodore_g 513 /* Commodore Braunschweig (Germany) */ #define commodore 514 /* Commodore West Chester */ -#define gvp 2017 /* GVP */ -#define ass 2102 /* Advanced Systems & Software */ #define hackers_id 2011 /* Special ID for test cards */ -/* Card Type */ -#define commodore_a2091 3 /* A2091 / A590 Card from C= */ -#define commodore_a2091_ram 10 /* A2091 / A590 Ram on HD-Card */ -#define commodore_a2232 70 /* A2232 Multiport Expansion */ -#define ass_nexus_scsi 1 /* Nexus SCSI Controller */ - -#define gvp_series_2_scsi 11 -#define gvp_iv_24_gfx 32 - /* ********************************************************** */ /* 08 - 0A */ /* er_Flags */ @@ -136,7 +129,6 @@ #define rom_install (0x01<<12) /* run code at install time */ #define rom_binddrv (0x02<<12) /* run code with binddrivers */ -uaecptr ROM_filesys_resname, ROM_filesys_resid; uaecptr ROM_filesys_diagentry; uaecptr ROM_hardfile_resname, ROM_hardfile_resid; uaecptr ROM_hardfile_init; @@ -171,6 +163,7 @@ static struct card_data cards_set[MAX_EXPANSION_BOARD_SPACE]; static struct card_data *cards[MAX_EXPANSION_BOARD_SPACE]; static int ecard, cardno, z3num; +static int restore_cardno; static addrbank *expamem_bank_current; static uae_u16 uae_id; @@ -196,35 +189,34 @@ static bool ks11orolder(void) /* ********************************************************** */ /* Please note: ZorroIII implementation seems to work different - * than described in the HRM. This claims that ZorroIII config - * address is 0xff000000 while the ZorroII config space starts - * at 0x00e80000. In reality, both, Z2 and Z3 cards are - * configured in the ZorroII config space. Kickstart 3.1 doesn't - * even do a single read or write access to the ZorroIII space. - * The original Amiga include files tell the same as the HRM. - * ZorroIII: If you set ext_size in er_Flags and give a Z2-size - * in er_Type you can very likely add some ZorroII address space - * to a ZorroIII card on a real Amiga. This is not implemented - * yet. - * -- Stefan - * - * Surprising that 0xFF000000 isn't used. Maybe it depends on the - * ROM. Anyway, the HRM says that Z3 cards may appear in Z2 config - * space, so what we are doing here is correct. - * -- Bernd - */ +* than described in the HRM. This claims that ZorroIII config +* address is 0xff000000 while the ZorroII config space starts +* at 0x00e80000. In reality, both, Z2 and Z3 cards are +* configured in the ZorroII config space. Kickstart 3.1 doesn't +* even do a single read or write access to the ZorroIII space. +* The original Amiga include files tell the same as the HRM. +* ZorroIII: If you set ext_size in er_Flags and give a Z2-size +* in er_Type you can very likely add some ZorroII address space +* to a ZorroIII card on a real Amiga. This is not implemented +* yet. +* -- Stefan +* +* Surprising that 0xFF000000 isn't used. Maybe it depends on the +* ROM. Anyway, the HRM says that Z3 cards may appear in Z2 config +* space, so what we are doing here is correct. +* -- Bernd +*/ /* Autoconfig address space at 0xE80000 */ -static uae_u8 expamem[65536]; +static uae_u8 expamem[65536 + 4]; #define AUTOMATIC_AUTOCONFIG_MAX_ADDRESS 0x80 static int expamem_autoconfig_mode; static addrbank*(*expamem_map)(struct autoconfig_info*); static uae_u8 expamem_lo; static uae_u16 expamem_hi; -uaecptr expamem_z3_pointer_real, expamem_z3_pointer_uae; -uaecptr expamem_z3_highram_real, expamem_z3_highram_uae; -uaecptr expamem_highmem_pointer; +static uaecptr expamem_z3_pointer_real, expamem_z3_pointer_uae; +static uaecptr expamem_z3_highram_real, expamem_z3_highram_uae; uae_u32 expamem_board_size; uaecptr expamem_board_pointer; static uae_u8 slots_e8[8] = { 0 }; @@ -237,7 +229,7 @@ void set_expamem_z3_hack_mode(int mode) z3hack_override = mode; } -bool expamem_z3hack(struct uae_prefs *p) +static bool expamem_z3hack(struct uae_prefs *p) { if (z3hack_override == Z3MAPPING_UAE) return true; @@ -283,19 +275,21 @@ static void addextrachip (uae_u32 sysbase) uae_u32 first = get_long (ml + 16); put_long (ml + 24, currprefs.chipmem_size); // mh_Upper put_long (ml + 28, get_long (ml + 28) + added); // mh_Free - uae_u32 next; + uae_u32 next = 0; while (first) { next = first; first = get_long (next); } - uae_u32 bytes = get_long (next + 4); - if (next + bytes == 0x00200000) { - put_long (next + 4, currprefs.chipmem_size - next); - } else { - put_long (0x00200000 + 0, 0); - put_long (0x00200000 + 4, added); - put_long (next, 0x00200000); - } + if (next) { + uae_u32 bytes = get_long (next + 4); + if (next + bytes == 0x00200000) { + put_long (next + 4, currprefs.chipmem_size - next); + } else { + put_long (0x00200000 + 0, 0); + put_long (0x00200000 + 4, added); + put_long (next, 0x00200000); + } + } return; } } @@ -307,24 +301,18 @@ addrbank expamem_bank = { expamem_lget, expamem_wget, expamem_bget, expamem_lput, expamem_wput, expamem_bput, default_xlate, default_check, NULL, NULL, _T("Autoconfig Z2"), - dummy_lgeti, dummy_wgeti, - ABFLAG_IO | ABFLAG_SAFE | ABFLAG_PPCIOSPACE, S_READ, S_WRITE + dummy_wgeti, + ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; DECLARE_MEMORY_FUNCTIONS(expamemz3); static addrbank expamemz3_bank = { expamemz3_lget, expamemz3_wget, expamemz3_bget, expamemz3_lput, expamemz3_wput, expamemz3_bput, default_xlate, default_check, NULL, NULL, _T("Autoconfig Z3"), - dummy_lgeti, dummy_wgeti, - ABFLAG_IO | ABFLAG_SAFE | ABFLAG_PPCIOSPACE, S_READ, S_WRITE + dummy_wgeti, + ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; -static addrbank *expamem_map_clear (void) -{ - write_log (_T("expamem_map_clear() got called. Shouldn't happen.\n")); - return NULL; -} - static void expamem_init_clear (void) { memset (expamem, 0xff, sizeof expamem); @@ -386,6 +374,8 @@ static int REGPARAM2 expamem_type (void) return expamem_read(0) & 0xc0; } +static void expamem_next (addrbank *mapped, addrbank *next); + static void call_card_init(int index) { addrbank *ab, *abe; @@ -429,26 +419,8 @@ static void call_card_init(int index) abe = &expamem_bank; expamem_autoconfig_mode = 0; if (abe != &expamem_bank) { - if (aci->autoconfig_automatic) { - if (aci->autoconfigp) { - memset(expamem, 0xff, AUTOMATIC_AUTOCONFIG_MAX_ADDRESS); - for (int i = 0; i < 16; i++) { - expamem_write(i * 4, aci->autoconfig_bytes[i]); - } - expamem_autoconfig_mode = 1; - } else if (aci->autoconfig_bytes) { - memset(expamem, 0xff, AUTOMATIC_AUTOCONFIG_MAX_ADDRESS); - for (int i = 0; i < 16; i++) { - expamem_write(i * 4, aci->autoconfig_bytes[i]); - } - expamem_autoconfig_mode = 1; - } else if (aci->autoconfig_raw) { - memcpy(expamem, aci->autoconfig_raw, sizeof aci->autoconfig_raw); - } - } else { - for (int i = 0; i < 16 * 4; i++) { - expamem[i] = abe->sub_banks ? abe->sub_banks[0].bank->bget(i) : abe->bget(i); - } + for (int i = 0; i < 16 * 4; i++) { + expamem[i] = abe->sub_banks ? abe->sub_banks[0].bank->bget(i) : abe->bget(i); } } @@ -496,15 +468,7 @@ static void boardmessage(addrbank *mapped, bool success) success ? _T("") : _T(" [SHUT UP]")); } -void expamem_shutup(addrbank *mapped) -{ - if (mapped) { - mapped->start = 0xffffffff; - boardmessage(mapped, false); - } -} - -void expamem_next(addrbank *mapped, addrbank *next) +static void expamem_next(addrbank *mapped, addrbank *next) { if (mapped) boardmessage(mapped, mapped->start != 0xffffffff); @@ -632,6 +596,12 @@ static void REGPARAM2 expamem_wput (uaecptr addr, uae_u32 value) expamem_next(expamem_map(&cd->aci), NULL); return; } + if (expamem_autoconfig_mode) { + map_banks_z2(cd->aci.addrbankp, expamem_board_pointer >> 16, expamem_board_size >> 16); + cd->initrc(&cd->aci); + expamem_next(cd->aci.addrbankp, NULL); + return; + } if (expamem_bank_current && expamem_bank_current != &expamem_bank) { expamem_bank_current->sub_banks ? expamem_bank_current->sub_banks[0].bank->bput(addr, value >> 8) : expamem_bank_current->bput(addr, value >> 8); return; @@ -846,7 +816,7 @@ addrbank fastmem_bank[MAX_RAM_BOARDS] = fastmem0_lget, fastmem0_wget, fastmem0_bget, fastmem0_lput, fastmem0_wput, fastmem0_bput, fastmem0_xlate, fastmem0_check, NULL, _T("*"), _T("Fast memory"), - fastmem0_lget, fastmem0_wget, + fastmem0_wget, ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 } }; @@ -862,8 +832,8 @@ addrbank filesys_bank = { filesys_lget, filesys_wget, filesys_bget, filesys_lput, filesys_wput, filesys_bput, filesys_xlate, filesys_check, NULL, _T("*"), _T("Filesystem autoconfig"), - filesys_lget, filesys_wget, - ABFLAG_IO | ABFLAG_SAFE | ABFLAG_PPCIOSPACE, S_READ, S_WRITE + filesys_wget, + ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; static bool filesys_write(uaecptr addr) @@ -947,19 +917,13 @@ addrbank uaeboard_bank = { uaeboard_lget, uaeboard_wget, uaeboard_bget, uaeboard_lput, uaeboard_wput, uaeboard_bput, uaeboard_xlate, uaeboard_check, NULL, _T("*"), _T("UAE Board"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; -uae_u32 uaeboard_base; /* Determined by the OS */ +static uae_u32 uaeboard_base; /* Determined by the OS */ #define UAEBOARD_WRITEOFFSET 0x4000 -uae_u8 *uaeboard_map_ram(uaecptr p) -{ - p -= filesys_bank.start; - return filesys_bank.baseaddr + p; -} - static bool uaeboard_write(uaecptr addr) { if (addr >= UAEBOARD_WRITEOFFSET) @@ -1048,11 +1012,6 @@ static bool get_params_filesys(struct uae_prefs *prefs, struct expansion_params p->device_order = prefs->uaeboard_order; return true; } -static bool set_params_filesys(struct uae_prefs *prefs, struct expansion_params *p) -{ - prefs->uaeboard_order = p->device_order; - return true; -} static void add_rtarea_pointer(struct autoconfig_info *aci) { @@ -1078,7 +1037,6 @@ static bool expamem_init_uaeboard(struct autoconfig_info *aci) aci->label = _T("UAE Boot ROM"); aci->addrbankp = &uaeboard_bank; aci->get_params = get_params_filesys; - aci->set_params = set_params_filesys; expamem_init_clear(); expamem_write(0x00, Z2_MEM_64KB | zorroII); @@ -1123,7 +1081,7 @@ addrbank z3fastmem_bank[MAX_RAM_BOARDS] = z3fastmem0_lget, z3fastmem0_wget, z3fastmem0_bget, z3fastmem0_lput, z3fastmem0_wput, z3fastmem0_bput, z3fastmem0_xlate, z3fastmem0_check, NULL, _T("*"), _T("Zorro III Fast RAM"), - z3fastmem0_lget, z3fastmem0_wget, + z3fastmem0_wget, ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 } }; @@ -1136,8 +1094,9 @@ addrbank z3fastmem_bank[MAX_RAM_BOARDS] = static addrbank *expamem_map_fastcard(struct autoconfig_info *aci) { + int devnum = aci->devnum; uae_u32 start = ((expamem_hi | (expamem_lo >> 4)) << 16); - addrbank *ab = &fastmem_bank[aci->devnum]; + addrbank *ab = &fastmem_bank[devnum]; if (start == 0x00ff0000) return ab; uae_u32 size = ab->allocated_size; @@ -1169,10 +1128,6 @@ static bool fastmem_autoconfig(struct uae_prefs *p, struct autoconfig_info *aci, rb = &p->fastmem[boardnum]; if (rb->autoconfig[0]) { forceac = rb->autoconfig; - } else if (rb->manufacturer) { - mid = rb->manufacturer; - pid = rb->product; - serial = 0; } else { pid = 81; } @@ -1185,10 +1140,6 @@ static bool fastmem_autoconfig(struct uae_prefs *p, struct autoconfig_info *aci, rb = &p->z3fastmem[boardnum]; if (rb->autoconfig[0]) { forceac = rb->autoconfig; - } else if (rb->manufacturer) { - mid = rb->manufacturer; - pid = rb->product; - serial = 0; } else { pid = 83; } @@ -1291,10 +1242,6 @@ static bool expamem_init_fastcard(struct autoconfig_info *aci) { return expamem_init_fastcard_2(aci, 2); } -static bool expamem_init_fastcard_z1(struct autoconfig_info *aci) -{ - return expamem_init_fastcard_2(aci, 1); -} /* ********************************************************** */ @@ -1391,7 +1338,6 @@ static bool expamem_init_filesys(struct autoconfig_info *aci) if (aci) { aci->label = ks12 ? _T("Pre-KS 1.3 UAE FS ROM") : _T("UAE FS ROM"); aci->get_params = get_params_filesys; - aci->set_params = set_params_filesys; aci->addrbankp = &filesys_bank; } @@ -1401,7 +1347,7 @@ static bool expamem_init_filesys(struct autoconfig_info *aci) 0x02, 0x00, /* da_Size */ FILESYS_DIAGPOINT >> 8, FILESYS_DIAGPOINT & 0xff, FILESYS_BOOTPOINT >> 8, FILESYS_BOOTPOINT & 0xff, - 0, (uae_u8)(14), // Name offset + 0, (uae_u8)14, // Name offset 0, 0, 0, 0, (uae_u8)('U'), (uae_u8)('A'), (uae_u8)('E'), 0 }; @@ -1467,8 +1413,9 @@ static addrbank *expamem_map_z3fastmem (struct autoconfig_info *aci) uaecptr z3fs = expamem_board_pointer; uae_u32 size = currprefs.z3fastmem[devnum].size; - if (ab->allocated_size) + if (ab->allocated_size) { map_banks_z3(ab, z3fs >> 16, size >> 16); + } return ab; } @@ -1534,27 +1481,27 @@ static addrbank *expamem_map_gfxcard_z2 (struct autoconfig_info *aci) return gfxmem_banks[devnum]; } -static bool expamem_init_gfxcard(struct autoconfig_info *aci, bool z3) +static bool expamem_init_gfxcard (struct autoconfig_info *aci, bool z3) { int devnum = aci->devnum; struct uae_prefs *p = aci->prefs; int size = p->rtgboards[devnum].rtgmem_size; - int code = (size == 0x100000 ? Z2_MEM_1MB - : size == 0x200000 ? Z2_MEM_2MB - : size == 0x400000 ? Z2_MEM_4MB - : size == 0x800000 ? Z2_MEM_8MB - : size == 0x1000000 ? Z3_MEM_16MB - : size == 0x2000000 ? Z3_MEM_32MB - : size == 0x4000000 ? Z3_MEM_64MB - : size == 0x8000000 ? Z3_MEM_128MB - : size == 0x10000000 ? Z3_MEM_256MB - : size == 0x20000000 ? Z3_MEM_512MB - : Z3_MEM_1GB); - int subsize = (size == 0x100000 ? Z3_SS_MEM_1MB - : size == 0x200000 ? Z3_SS_MEM_2MB - : size == 0x400000 ? Z3_SS_MEM_4MB - : size == 0x800000 ? Z3_SS_MEM_8MB - : Z3_SS_MEM_SAME); + int code = (size == 0x100000 ? Z2_MEM_1MB + : size == 0x200000 ? Z2_MEM_2MB + : size == 0x400000 ? Z2_MEM_4MB + : size == 0x800000 ? Z2_MEM_8MB + : size == 0x1000000 ? Z3_MEM_16MB + : size == 0x2000000 ? Z3_MEM_32MB + : size == 0x4000000 ? Z3_MEM_64MB + : size == 0x8000000 ? Z3_MEM_128MB + : size == 0x10000000 ? Z3_MEM_256MB + : size == 0x20000000 ? Z3_MEM_512MB + : Z3_MEM_1GB); + int subsize = (size == 0x100000 ? Z3_SS_MEM_1MB + : size == 0x200000 ? Z3_SS_MEM_2MB + : size == 0x400000 ? Z3_SS_MEM_4MB + : size == 0x800000 ? Z3_SS_MEM_8MB + : Z3_SS_MEM_SAME); aci->label = _T("UAE RTG"); aci->direct_vram = true; @@ -1562,24 +1509,24 @@ static bool expamem_init_gfxcard(struct autoconfig_info *aci, bool z3) if (size < 0x1000000 && z3) code = Z3_MEM_16MB; /* Z3 physical board size is always at least 16M */ - expamem_init_clear(); - expamem_write(0x00, (z3 ? zorroIII : zorroII) | code); + expamem_init_clear(); + expamem_write (0x00, (z3 ? zorroIII : zorroII) | code); - expamem_write(0x08, care_addr | (z3 ? (force_z3 | (size > 0x800000 ? ext_size : subsize)) : 0)); - expamem_write(0x04, 96); + expamem_write (0x08, care_addr | (z3 ? (force_z3 | (size > 0x800000 ? ext_size: subsize)) : 0)); + expamem_write (0x04, 96); - expamem_write(0x10, uae_id >> 8); - expamem_write(0x14, uae_id & 0xff); + expamem_write (0x10, uae_id >> 8); + expamem_write (0x14, uae_id & 0xff); - expamem_write(0x18, 0x00); /* ser.no. Byte 0 */ - expamem_write(0x1c, 0x00); /* ser.no. Byte 1 */ - expamem_write(0x20, 0x00); /* ser.no. Byte 2 */ - expamem_write(0x24, 0x01); /* ser.no. Byte 3 */ + expamem_write (0x18, 0x00); /* ser.no. Byte 0 */ + expamem_write (0x1c, 0x00); /* ser.no. Byte 1 */ + expamem_write (0x20, 0x00); /* ser.no. Byte 2 */ + expamem_write (0x24, 0x01); /* ser.no. Byte 3 */ - expamem_write(0x28, 0x00); /* ROM-Offset hi */ - expamem_write(0x2c, 0x00); /* ROM-Offset lo */ + expamem_write (0x28, 0x00); /* ROM-Offset hi */ + expamem_write (0x2c, 0x00); /* ROM-Offset lo */ - expamem_write(0x40, 0x00); /* Ctrl/Statusreg.*/ + expamem_write (0x40, 0x00); /* Ctrl/Statusreg.*/ memcpy(aci->autoconfig_raw, expamem, sizeof aci->autoconfig_raw); aci->addrbankp = gfxmem_banks[devnum]; @@ -1630,112 +1577,78 @@ static bool mapped_malloc_dynamic (uae_u32 *currpsize, uae_u32 *changedpsize, ad return false; } -uaecptr expansion_startaddress(struct uae_prefs *p, uaecptr addr, uae_u32 size) -{ - if (!size) - return addr; - if (addr < 0x10000000) { - return (addr + size - 1) & ~(size - 1); - } else { - if (size < 16 * 1024 * 1024) - size = 16 * 1024 * 1024; - if (!expamem_z3hack(p)) - return (addr + size - 1) & ~(size - 1); - } - return addr; -} - -static void allocate_expamem(void) +static void allocate_expamem (void) { for (int i = 0; i < MAX_RTG_BOARDS; i++) { memcpy(&currprefs.rtgboards[i], &changed_prefs.rtgboards[i], sizeof(struct rtgboardconfig)); } for (int i = 0; i < MAX_RAM_BOARDS; i++) { - currprefs.fastmem[i].size = changed_prefs.fastmem[i].size; - currprefs.z3fastmem[i].size = changed_prefs.z3fastmem[i].size; - } + currprefs.fastmem[i].size = changed_prefs.fastmem[i].size; + currprefs.z3fastmem[i].size = changed_prefs.z3fastmem[i].size; + } for (int i = 0; i < MAX_RAM_BOARDS; i++) { - if (fastmem_bank[i].reserved_size != currprefs.fastmem[i].size) { - free_fastmemory(i); + if (fastmem_bank[i].reserved_size != currprefs.fastmem[i].size) { + free_fastmemory (i); if (fastmem_bank[i].start == 0xffffffff) { fastmem_bank[i].reserved_size = 0; + } else { + fastmem_bank[i].reserved_size = currprefs.fastmem[i].size; + fastmem_bank[i].mask = fastmem_bank[i].reserved_size - 1; + if (fastmem_bank[i].reserved_size && fastmem_bank[i].start != 0xffffffff) { + mapped_malloc (&fastmem_bank[i]); + if (fastmem_bank[i].baseaddr == 0) { + write_log (_T("Out of memory for fastmem card.\n")); + } + } } - else { - fastmem_bank[i].reserved_size = currprefs.fastmem[i].size; - fastmem_bank[i].mask = fastmem_bank[i].reserved_size - 1; - if (fastmem_bank[i].reserved_size && fastmem_bank[i].start != 0xffffffff) { - mapped_malloc(&fastmem_bank[i]); - if (fastmem_bank[i].baseaddr == 0) { - write_log(_T("Out of memory for fastmem card.\n")); - } - } - } - memory_hardreset(1); - } - } + memory_hardreset(1); + } + } - if (z3fastmem_bank[0].reserved_size != currprefs.z3fastmem[0].size) { - mapped_free(&z3fastmem_bank[0]); - mapped_malloc_dynamic(&currprefs.z3fastmem[0].size, &changed_prefs.z3fastmem[0].size, &z3fastmem_bank[0], 1, _T("*")); - memory_hardreset(1); - } - for (int i = 1; i < MAX_RAM_BOARDS; i++) { - if (currprefs.z3fastmem[i].size && z3fastmem_bank[i].start == 0xffffffff) { - z3fastmem_bank[i].start = expansion_startaddress(&currprefs, z3fastmem_bank[i - 1].start, currprefs.z3fastmem[i - 1].size); - } - if (z3fastmem_bank[i].reserved_size != currprefs.z3fastmem[i].size) { - mapped_free(&z3fastmem_bank[i]); + if (z3fastmem_bank[0].reserved_size != currprefs.z3fastmem[0].size) { + mapped_free (&z3fastmem_bank[0]); + mapped_malloc_dynamic (&currprefs.z3fastmem[0].size, &changed_prefs.z3fastmem[0].size, &z3fastmem_bank[0], 1, _T("*")); + memory_hardreset(1); + } - z3fastmem_bank[i].reserved_size = currprefs.z3fastmem[i].size; - z3fastmem_bank[i].mask = z3fastmem_bank[i].reserved_size - 1; - - if (z3fastmem_bank[i].reserved_size) { - mapped_malloc(&z3fastmem_bank[i]); - if (z3fastmem_bank[i].baseaddr == 0) { - write_log(_T("Out of memory for 32 bit fast memory #%d.\n"), i); - } - } - memory_hardreset(1); - } - } #ifdef PICASSO96 struct rtgboardconfig *rbc = &currprefs.rtgboards[0]; if (gfxmem_banks[0]->reserved_size != rbc->rtgmem_size) { - mapped_free(gfxmem_banks[0]); - mapped_malloc_dynamic(&rbc->rtgmem_size, &changed_prefs.rtgboards[0].rtgmem_size, gfxmem_banks[0], 1, NULL); - memory_hardreset(1); - } + mapped_free (gfxmem_banks[0]); + mapped_malloc_dynamic (&rbc->rtgmem_size, &changed_prefs.rtgboards[0].rtgmem_size, gfxmem_banks[0], 1, NULL); + memory_hardreset(1); + } #endif #ifdef SAVESTATE - if (savestate_state == STATE_RESTORE) { + if (savestate_state == STATE_RESTORE) { for (int i = 0; i < MAX_RAM_BOARDS; i++) { - if (fastmem_bank[i].allocated_size > 0) { - restore_ram(fast_filepos[i], fastmem_bank[i].baseaddr); - if (!fastmem_bank[i].start) { - // old statefile compatibility support - fastmem_bank[i].start = 0x00200000; - } - map_banks(&fastmem_bank[i], fastmem_bank[i].start >> 16, currprefs.fastmem[i].size >> 16, - fastmem_bank[i].allocated_size); - } - if (z3fastmem_bank[i].allocated_size > 0) { - restore_ram(z3_filepos[i], z3fastmem_bank[i].baseaddr); - map_banks(&z3fastmem_bank[i], z3fastmem_bank[i].start >> 16, currprefs.z3fastmem[i].size >> 16, - z3fastmem_bank[i].allocated_size); - } - } + if (fastmem_bank[i].allocated_size > 0) { + restore_ram (fast_filepos[i], fastmem_bank[i].baseaddr); + if (!fastmem_bank[i].start) { + // old statefile compatibility support + fastmem_bank[i].start = 0x00200000; + } + map_banks (&fastmem_bank[i], fastmem_bank[i].start >> 16, currprefs.fastmem[i].size >> 16, + fastmem_bank[i].allocated_size); + } + if (z3fastmem_bank[i].allocated_size > 0) { + restore_ram (z3_filepos[i], z3fastmem_bank[i].baseaddr); + map_banks (&z3fastmem_bank[i], z3fastmem_bank[i].start >> 16, currprefs.z3fastmem[i].size >> 16, + z3fastmem_bank[i].allocated_size); + } + } #ifdef PICASSO96 if (gfxmem_banks[0]->allocated_size > 0 && gfxmem_banks[0]->start > 0) { - restore_ram(p96_filepos, gfxmem_banks[0]->baseaddr); + restore_ram (p96_filepos, gfxmem_banks[0]->baseaddr); map_banks(gfxmem_banks[0], gfxmem_banks[0]->start >> 16, currprefs.rtgboards[0].rtgmem_size >> 16, gfxmem_banks[0]->allocated_size); - } + } #endif - } + } #endif /* SAVESTATE */ } @@ -1913,12 +1826,6 @@ static void reset_ac_data(struct uae_prefs *p) expamem_z3_highram_real = 0; expamem_z3_highram_uae = 0; - expamem_highmem_pointer = 0; - if (p->mbresmem_low_size) - expamem_highmem_pointer = 0x08000000; - if (p->mbresmem_high_size) - expamem_highmem_pointer = 0x08000000 + p->mbresmem_high_size; - if (p->mbresmem_high_size >= 128 * 1024 * 1024) expamem_z3_pointer_uae += (p->mbresmem_high_size - 128 * 1024 * 1024) + 16 * 1024 * 1024; expamem_board_pointer = 0; @@ -1950,9 +1857,11 @@ static void reset_ac(struct uae_prefs *p) uae_id = hackers_id; - for (int i = 0; i < MAX_EXPANSION_BOARD_SPACE; i++) { - memset(&cards_set[i], 0, sizeof(struct card_data)); - } + if (restore_cardno == 0) { + for (int i = 0; i < MAX_EXPANSION_BOARD_SPACE; i++) { + memset(&cards_set[i], 0, sizeof(struct card_data)); + } + } ecard = 0; cardno = 0; @@ -1965,14 +1874,6 @@ void expansion_generate_autoconfig_info(struct uae_prefs *p) expansion_scan_autoconfig(p, true); } -struct autoconfig_info *expansion_get_autoconfig_data(struct uae_prefs *p, int index) -{ - if (index >= cardno) - return NULL; - struct card_data *cd = cards[index]; - return &cd->aci; -} - struct autoconfig_info *expansion_get_autoconfig_by_address(struct uae_prefs *p, uaecptr addr) { for (int i = 0; i < cardno; i++) { @@ -1983,28 +1884,6 @@ struct autoconfig_info *expansion_get_autoconfig_by_address(struct uae_prefs *p, return NULL; } -struct autoconfig_info *expansion_get_autoconfig_info(struct uae_prefs *p,int romtype, int devnum) -{ - for (int i = 0; i < cardno; i++) { - struct card_data *cd = cards[i]; - if (cd->rc) { - if (cd->rc->back->device_type == romtype && cd->rc->back->device_num == devnum) { - return &cd->aci; - } - } else { - // z2 and z3 ram boards are "fake" - if ((romtype == ROMTYPE_RAMZ2 && !_tcsicmp(cd->name, _T("Z2Fast"))) - || (romtype == ROMTYPE_RAMZ3 && !_tcsicmp(cd->name, _T("Z3Fast"))) - || (romtype == ROMTYPE_MEGACHIP && !_tcsicmp(cd->name, _T("MegaChipRAM")))) - { - if (((cd->flags >> 16) & 255) == devnum) - return &cd->aci; - } - } - } - return NULL; -} - static void expansion_init_cards(struct uae_prefs *p) { reset_ac_data(p); @@ -2094,11 +1973,6 @@ static void expansion_parse_cards(struct uae_prefs *p, bool log) aci->rc = cd->rc; ok = cd->initrc(aci); } - if (aci->last_high_ram > expamem_highmem_pointer) { - expamem_highmem_pointer = aci->last_high_ram; - if (log) - write_log(_T("Non-Autoconfig highmem increased to %08x\n"), expamem_highmem_pointer); - } if (log) write_log(_T("Card %02d: "), i + 1); if (ok) { @@ -2320,7 +2194,6 @@ static void expansion_autoconfig_sort(struct uae_prefs *p) for (int i = 0; i < cardno; i++) { struct autoconfig_info *aci = &cards[i]->aci; tcards[i] = cards[i]; - tcards[i]->aci.can_sort = get_order(p, cards[i]) < EXPANSION_ORDER_MAX - 1 && get_order(p, cards[i]) >= 0; } new_cardno = 0; @@ -2469,7 +2342,7 @@ void expansion_scan_autoconfig(struct uae_prefs *p, bool log) expansion_parse_cards(p, log); } -void expamem_reset (void) +void expamem_reset (int hardreset) { reset_ac(&currprefs); @@ -2483,6 +2356,9 @@ void expamem_reset (void) expansion_autoconfig_sort(&currprefs); expansion_parse_cards(&currprefs, true); + // this also resets all autoconfig devices + devices_reset_ext(hardreset); + if (cardno == 0 || savestate_state) { expamem_init_clear_zero (); } else { @@ -2599,104 +2475,158 @@ uae_u8 *save_pram (int *len) return gfxmem_banks[0]->baseaddr; } -void restore_fram(int len, size_t filepos, int num) +void restore_fram (int len, size_t filepos, int num) { fast_filepos[num] = filepos; - changed_prefs.fastmem[num].size = len; + changed_prefs.fastmem[num].size = len; } -void restore_zram(int len, size_t filepos, int num) +void restore_zram (int len, size_t filepos, int num) { z3_filepos[num] = filepos; - changed_prefs.z3fastmem[num].size = len; + changed_prefs.z3fastmem[num].size = len; } -void restore_pram(int len, size_t filepos) +void restore_pram (int len, size_t filepos) { - p96_filepos = filepos; + p96_filepos = filepos; changed_prefs.rtgboards[0].rtgmem_size = len; } -uae_u8 *save_expansion(int *len, uae_u8 *dstptr) +uae_u8 *save_expansion (int *len, uae_u8 *dstptr) { uae_u8 *dst, *dstbak; + if (dstptr) + dst = dstbak = dstptr; + else + dstbak = dst = xmalloc (uae_u8, 6 * 4); + save_u32 (fastmem_bank[0].start); + save_u32 (z3fastmem_bank[0].start); + save_u32 (gfxmem_banks[0]->start); + save_u32 (rtarea_base); + *len = dst - dstbak; + return dstbak; +} + +uae_u8 *restore_expansion (uae_u8 *src) +{ + fastmem_bank[0].start = restore_u32 (); + z3fastmem_bank[0].start = restore_u32 (); + gfxmem_banks[0]->start = restore_u32 (); + rtarea_base = restore_u32 (); + if (rtarea_base != 0 && rtarea_base != RTAREA_DEFAULT && rtarea_base != RTAREA_BACKUP && (rtarea_base < 0xe90000 || rtarea_base >= 0xf00000)) + rtarea_base = 0; + return src; +} + +uae_u8 *save_expansion_boards(int *len, uae_u8 *dstptr, int cardnum) +{ + uae_u8 *dst, *dstbak; + if (cardnum >= cardno) + return NULL; if (dstptr) dst = dstbak = dstptr; else - dstbak = dst = xmalloc(uae_u8, 6 * 4); - save_u32(fastmem_bank[0].start); - save_u32(z3fastmem_bank[0].start); - save_u32(gfxmem_banks[0]->start); - save_u32(rtarea_base); + dstbak = dst = xmalloc(uae_u8, 1000); + save_u32(3); save_u32(0); - *len = dst - dstbak; - return dstbak; -} - -uae_u8 *restore_expansion(uae_u8 *src) -{ - fastmem_bank[0].start = restore_u32(); - z3fastmem_bank[0].start = restore_u32(); - gfxmem_banks[0]->start = restore_u32(); - rtarea_base = restore_u32(); - restore_u32(); - if (rtarea_base != 0 && rtarea_base != RTAREA_DEFAULT && rtarea_base != RTAREA_BACKUP) - rtarea_base = 0; - return src; -} - -uae_u8 *save_expansion_info(int *len, uae_u8 *dstptr) -{ - uae_u8 *dst, *dstbak; - if (dstptr) - dst = dstbak = dstptr; - else - dstbak = dst = xmalloc(uae_u8, 100 + MAX_EXPANSION_BOARD_SPACE * 100); - save_u32(1); - save_u32(0); - save_u32(cardno); - for (int i = 0; i < cardno; i++) { - struct card_data *ec = cards[i]; - if (ec->rc) { - save_u32(ec->rc->back->device_type); - save_u32(ec->rc->back->device_num); - save_string(ec->rc->romfile); - save_string(ec->rc->romident); - } else { - save_u32(0xffffffff); - } - save_u32(ec->base); - save_u32(ec->size); - save_u32(ec->flags); - save_string(ec->name); + save_u32(cardnum); + struct card_data *ec = cards[cardnum]; + save_u32(ec->base); + save_u32(ec->size); + save_u32(ec->flags); + save_string(ec->name); + for (int j = 0; j < 16; j++) { + save_u8(ec->aci.autoconfig_bytes[j]); + } + struct romconfig *rc = ec->rc; + if (rc) { + save_u32(rc->back->device_type); + save_u32(rc->back->device_num); + save_string(rc->romfile); + save_string(rc->romident); + } else { + save_u32(0xffffffff); } - save_u32(0); *len = dst - dstbak; return dstbak; } -uae_u8 *restore_expansion_info(uae_u8 *src) +uae_u8 *restore_expansion_boards(uae_u8 *src) { - if (restore_u32() != 1) + if (!src) { + restore_cardno = 0; + return NULL; + } + TCHAR *s; + uae_u32 flags = restore_u32(); + if (!(flags & 2)) return src; restore_u32(); - int num = restore_u32(); - for (int i = 0; i < num; i++) { - int romtype = restore_u32(); - if (romtype != 0xffffffff) { - restore_u32(); - restore_string(); - restore_string(); - } - restore_u32(); - restore_u32(); - restore_u32(); - restore_string(); + int cardnum = restore_u32(); + restore_cardno = cardnum + 1; + struct card_data *ec = &cards_set[cardnum]; + cards[cardnum] = ec; + + ec->base = restore_u32(); + ec->size = restore_u32(); + ec->flags = restore_u32(); + s = restore_string(); + xfree(s); + for (int j = 0; j < 16; j++) { + ec->aci.autoconfig_bytes[j] = restore_u8(); + } + + uae_u32 dev_num = 0; + uae_u32 romtype = restore_u32(); + if (romtype != 0xffffffff) { + dev_num = restore_u32(); + ec->aci.devnum = dev_num; + struct boardromconfig* brc = get_device_rom(&currprefs, romtype, dev_num, NULL); + if (!brc) { + brc = get_device_rom_new(&currprefs, romtype, dev_num, NULL); + } + struct romconfig *rc = get_device_romconfig(&currprefs, romtype, dev_num); + if (rc) { + ec->rc = rc; + rc->back = brc; + ec->ert = get_device_expansion_rom(romtype); + s = restore_string(); + _tcscpy(rc->romfile, s); + xfree(s); + s = restore_string(); + _tcscpy(rc->romident, s); + xfree(s); + } } - restore_u32(); return src; } +void restore_expansion_finish(void) +{ + cardno = restore_cardno; + for (int i = 0; i < cardno; i++) { + struct card_data *ec = &cards_set[i]; + cards[i] = ec; + struct romconfig *rc = ec->rc; + // Handle only IO boards, RAM boards are handled differently + if (rc && ec->ert) { + ec->aci.doinit = false; + ec->aci.start = ec->base; + ec->aci.size = ec->size; + _tcscpy(ec->aci.name, ec->ert->friendlyname); + if (ec->ert->init) { + if (ec->ert->init(&ec->aci)) { + if (ec->aci.addrbankp) { + map_banks(ec->aci.addrbankp, ec->base >> 16, ec->size >> 16, 0); + } + } + } + ec->aci.doinit = true; + } + } +} + #endif /* SAVESTATE */ const struct expansionromtype expansionroms[] = { @@ -2714,7 +2644,7 @@ const struct expansionromtype expansionroms[] = { }, { _T("pcmcia_mb"), _T("A600/A1200 PCMCIA"), _T("Commodore"), - gayle_pcmcia_init, gayle_add_pcmcia_unit, ROMTYPE_MB_PCMCIA | ROMTYPE_NOT, BOARD_NONAUTOCONFIG_BEFORE, + gayle_init_pcmcia, NULL, ROMTYPE_MB_PCMCIA | ROMTYPE_NOT, BOARD_NONAUTOCONFIG_BEFORE, EXPANSIONTYPE_INTERNAL }, diff --git a/src/fdi2raw.cpp b/src/fdi2raw.cpp index 23a33a5e..fcaf2c6c 100644 --- a/src/fdi2raw.cpp +++ b/src/fdi2raw.cpp @@ -41,69 +41,9 @@ with this program; if not, write to the Free Software Foundation, Inc., #include "fdi2raw.h" #include "crc32.h" -#undef DEBUG -#define VERBOSE - -#ifdef DEBUG -static TCHAR *datalog (uae_u8 *src, int len) -{ - static TCHAR buf[1000]; - static int offset; - int i = 0, offset2; - - offset2 = offset; - buf[offset++]='\''; - while (len--) { - _stprintf (buf + offset, "%02X", src[i]); - offset += 2; - i++; - if (i > 10) break; - } - buf[offset++]='\''; - buf[offset++] = 0; - if (offset >= 900) offset = 0; - return buf + offset2; -} -#else -static const TCHAR *datalog (uae_u8 *src, int len) { return _T(""); } -#endif - -#ifdef DEBUG -#define debuglog write_log -#else -#define debuglog(fmt, ...) -#endif -#ifdef VERBOSE -#define outlog write_log -#else -#define outlog(fmt, ...) -#endif - -static int fdi_allocated; -#ifdef DEBUG -static void fdi_free (void *p) -{ - int size; - if (!p) - return; - size = ((int*)p)[-1]; - fdi_allocated -= size; - write_log (_T("%d freed (%d)\n"), size, fdi_allocated); - free ((int*)p - 1); -} -static void *fdi_malloc (int size) -{ - void *p = xmalloc (size + sizeof (int)); - ((int*)p)[0] = size; - fdi_allocated += size; - write_log (_T("%d allocated (%d)\n"), size, fdi_allocated); - return (int*)p + 1; -} -#else #define fdi_free xfree #define fdi_malloc xmalloc -#endif #define MAX_SRC_BUFFER 4194304 #define MAX_DST_BUFFER 40000 @@ -131,11 +71,7 @@ struct fdi { uae_u8 track_type; int current_track; int last_track; - int last_head; - int rotation_speed; - int bit_rate; int disk_type; - int write_protect; int reversed_side; int err; uae_u8 header[2048]; @@ -144,9 +80,6 @@ struct fdi { int out; int mfmsync_offset; int *mfmsync_buffer; - /* sector described only */ - int index_offset; - int encoding_type; /* bit handling */ int nextdrop; struct fdi_cache cache[MAX_TRACKS]; @@ -154,13 +87,6 @@ struct fdi { #define get_u32(x) ((((x)[0])<<24)|(((x)[1])<<16)|(((x)[2])<<8)|((x)[3])) #define get_u24(x) ((((x)[0])<<16)|(((x)[1])<<8)|((x)[2])) -STATIC_INLINE void put_u32 (uae_u8 *d, uae_u32 v) -{ - d[0] = v >> 24; - d[1] = v >> 16; - d[2] = v >> 8; - d[3] = v; -} struct node { uae_u16 v; @@ -325,14 +251,10 @@ static int decode_raw_track (FDI *fdi) /* unknown track */ static void zxx (FDI *fdi) { - outlog (_T("track %d: unknown track type 0x%02X\n"), fdi->current_track, fdi->track_type); - // return -1; } /* unsupported track */ static void zyy (FDI *fdi) { - outlog (_T("track %d: unsupported track type 0x%02X\n"), fdi->current_track, fdi->track_type); - // return -1; } /* empty track */ static void track_empty (FDI *fdi) @@ -343,13 +265,11 @@ static void track_empty (FDI *fdi) /* unknown sector described type */ static void dxx (FDI *fdi) { - outlog (_T("\ntrack %d: unknown sector described type 0x%02X\n"), fdi->current_track, fdi->track_type); fdi->err = 1; } /* unsupported sector described type */ static void dyy (FDI *fdi) { - outlog (_T("\ntrack %d: unsupported sector described 0x%02X\n"), fdi->current_track, fdi->track_type); fdi->err = 1; } /* add position of mfm sync bit */ @@ -361,12 +281,10 @@ static void add_mfm_sync_bit (FDI *fdi) } fdi->mfmsync_buffer[fdi->mfmsync_offset++] = fdi->out; if (fdi->out == 0) { - outlog (_T("illegal position for mfm sync bit, offset=%d\n"),fdi->out); fdi->err = 1; } if (fdi->mfmsync_offset >= MAX_MFM_SYNC_BUFFER) { fdi->mfmsync_offset = 0; - outlog (_T("mfmsync buffer overflow\n")); fdi->err = 1; } fdi->out++; @@ -387,7 +305,6 @@ static void bit_add (FDI *fdi, int bit) fdi->track_dst[BIT_BYTEOFFSET] |= (1 << BIT_BITOFFSET); fdi->out++; if (fdi->out >= MAX_DST_BUFFER * 8) { - outlog (_T("destination buffer overflow\n")); fdi->err = 1; fdi->out = 1; } @@ -401,25 +318,17 @@ static void bit_mfm_add (FDI *fdi, int bit) /* remove following bit */ static void bit_drop_next (FDI *fdi) { - if (fdi->nextdrop > 0) { - outlog (_T("multiple bit_drop_next() called")); - } else if (fdi->nextdrop < 0) { + if (fdi->nextdrop < 0) { fdi->nextdrop = 0; - debuglog (":DNN:"); return; } - debuglog (":DN:"); fdi->nextdrop = 1; } /* ignore next bit_drop_next() */ static void bit_dedrop (FDI *fdi) { - if (fdi->nextdrop) { - outlog (_T("bit_drop_next called before bit_dedrop")); - } fdi->nextdrop = -1; - debuglog (":BDD:"); } /* add one byte */ @@ -472,7 +381,6 @@ static void s08(FDI *fdi) int bytes = *fdi->track_src++; uae_u8 byte = *fdi->track_src++; if (bytes == 0) bytes = 256; - debuglog ("s08:len=%d,data=%02X",bytes,byte); while(bytes--) byte_add (fdi, byte); } /* RLE MFM-decoded data */ @@ -482,7 +390,6 @@ static void s09(FDI *fdi) uae_u8 byte = *fdi->track_src++; if (bytes == 0) bytes = 256; bit_drop_next (fdi); - debuglog ("s09:len=%d,data=%02X",bytes,byte); while(bytes--) byte_mfm_add (fdi, byte); } /* MFM-encoded data */ @@ -491,7 +398,6 @@ static void s0a(FDI *fdi) int i, bits = (fdi->track_src[0] << 8) | fdi->track_src[1]; uae_u8 b; fdi->track_src += 2; - debuglog ("s0a:bits=%d,data=%s", bits, datalog (fdi->track_src, (bits + 7) / 8)); while (bits >= 8) { byte_add (fdi, *fdi->track_src++); bits -= 8; @@ -511,7 +417,6 @@ static void s0b(FDI *fdi) int i, bits = ((fdi->track_src[0] << 8) | fdi->track_src[1]) + 65536; uae_u8 b; fdi->track_src += 2; - debuglog ("s0b:bits=%d,data=%s", bits, datalog (fdi->track_src, (bits + 7) / 8)); while (bits >= 8) { byte_add (fdi, *fdi->track_src++); bits -= 8; @@ -532,7 +437,6 @@ static void s0c(FDI *fdi) uae_u8 b; fdi->track_src += 2; bit_drop_next (fdi); - debuglog ("s0c:bits=%d,data=%s", bits, datalog (fdi->track_src, (bits + 7) / 8)); while (bits >= 8) { byte_mfm_add (fdi, *fdi->track_src++); bits -= 8; @@ -553,7 +457,6 @@ static void s0d(FDI *fdi) uae_u8 b; fdi->track_src += 2; bit_drop_next (fdi); - debuglog ("s0d:bits=%d,data=%s", bits, datalog (fdi->track_src, (bits + 7) / 8)); while (bits >= 8) { byte_mfm_add (fdi, *fdi->track_src++); bits -= 8; @@ -572,196 +475,6 @@ static void s0d(FDI *fdi) /* AMIGA */ /* ***** */ -/* just for testing integrity of Amiga sectors */ - -static void rotateonebit (uae_u8 *start, uae_u8 *end, int shift) -{ - if (shift == 0) - return; - while (start <= end) { - start[0] <<= shift; - start[0] |= start[1] >> (8 - shift); - start++; - } -} - -static int check_offset; -static uae_u16 getmfmword (uae_u8 *mbuf) -{ - uae_u32 v; - - v = (mbuf[0] << 8) | (mbuf[1] << 0); - if (check_offset == 0) - return v; - v <<= 8; - v |= mbuf[2]; - v >>= check_offset; - return v; -} - -#define MFMMASK 0x55555555 -static uae_u32 getmfmlong (uae_u8 * mbuf) -{ - return ((getmfmword (mbuf) << 16) | getmfmword (mbuf + 2)) & MFMMASK; -} - -static int amiga_check_track (FDI *fdi) -{ - int i, j, secwritten = 0; - int fwlen = fdi->out / 8; - int length = 2 * fwlen; - int drvsec = 11; - uae_u32 odd, even, chksum, id, dlong; - uae_u8 *secdata; - uae_u8 secbuf[544]; - uae_u8 bigmfmbuf[60000]; - uae_u8 *mbuf, *mbuf2, *mend; - TCHAR sectable[22]; - uae_u8 *raw = fdi->track_dst_buffer; - int slabel, off; - int ok = 1; - - memset (bigmfmbuf, 0, sizeof (bigmfmbuf)); - mbuf = bigmfmbuf; - check_offset = 0; - for (i = 0; i < (fdi->out + 7) / 8; i++) - *mbuf++ = raw[i]; - off = fdi->out & 7; -#if 1 - if (off > 0) { - mbuf--; - *mbuf &= ~((1 << (8 - off)) - 1); - } - j = 0; - while (i < (fdi->out + 7) / 8 + 600) { - *mbuf++ |= (raw[j] >> off) | ((raw[j + 1]) << (8 - off)); - j++; - i++; - } -#endif - mbuf = bigmfmbuf; - - memset (sectable, 0, sizeof (sectable)); - //memcpy (mbuf + fwlen, mbuf, fwlen * sizeof (uae_u16)); - mend = bigmfmbuf + length; - mend -= (4 + 16 + 8 + 512); - - while (secwritten < drvsec) { - int trackoffs; - - for (;;) { - rotateonebit (bigmfmbuf, mend, 1); - if (getmfmword (mbuf) == 0) - break; - if (secwritten == 10) { - mbuf[0] = 0x44; - mbuf[1] = 0x89; - } - // check_offset++; - if (check_offset > 7) { - check_offset = 0; - mbuf++; - if (mbuf >= mend || *mbuf == 0) - break; - } - if (getmfmword (mbuf) == 0x4489) - break; - } - if (mbuf >= mend || *mbuf == 0) - break; - - rotateonebit (bigmfmbuf, mend, check_offset); - check_offset = 0; - - while (getmfmword (mbuf) == 0x4489) - mbuf+= 1 * 2; - mbuf2 = mbuf + 8; - - odd = getmfmlong (mbuf); - even = getmfmlong (mbuf + 2 * 2); - mbuf += 4 * 2; - id = (odd << 1) | even; - - trackoffs = (id & 0xff00) >> 8; - if (trackoffs + 1 > drvsec) { - outlog (_T("illegal sector offset %d\n"),trackoffs); - ok = 0; - mbuf = mbuf2; - continue; - } - if ((id >> 24) != 0xff) { - outlog (_T("sector %d format type %02X?\n"), trackoffs, id >> 24); - ok = 0; - } - chksum = odd ^ even; - slabel = 0; - for (i = 0; i < 4; i++) { - odd = getmfmlong (mbuf); - even = getmfmlong (mbuf + 8 * 2); - mbuf += 2* 2; - - dlong = (odd << 1) | even; - if (dlong) slabel = 1; - chksum ^= odd ^ even; - } - mbuf += 8 * 2; - odd = getmfmlong (mbuf); - even = getmfmlong (mbuf + 2 * 2); - mbuf += 4 * 2; - if (((odd << 1) | even) != chksum) { - outlog (_T("sector %d header crc error\n"), trackoffs); - ok = 0; - mbuf = mbuf2; - continue; - } - outlog (_T("sector %d header crc ok\n"), trackoffs); - if (((id & 0x00ff0000) >> 16) != (uae_u32)fdi->current_track) { - outlog (_T("illegal track number %d <> %d\n"),fdi->current_track,(id & 0x00ff0000) >> 16); - ok++; - mbuf = mbuf2; - continue; - } - odd = getmfmlong (mbuf); - even = getmfmlong (mbuf + 2 * 2); - mbuf += 4 * 2; - chksum = (odd << 1) | even; - secdata = secbuf + 32; - for (i = 0; i < 128; i++) { - odd = getmfmlong (mbuf); - even = getmfmlong (mbuf + 256 * 2); - mbuf += 2 * 2; - dlong = (odd << 1) | even; - *secdata++ = (uae_u8) (dlong >> 24); - *secdata++ = (uae_u8) (dlong >> 16); - *secdata++ = (uae_u8) (dlong >> 8); - *secdata++ = (uae_u8) dlong; - chksum ^= odd ^ even; - } - mbuf += 256 * 2; - if (chksum) { - outlog (_T("sector %d data checksum error\n"),trackoffs); - ok = 0; - } else if (sectable[trackoffs]) { - outlog (_T("sector %d already found?\n"), trackoffs); - mbuf = mbuf2; - } else { - outlog (_T("sector %d ok\n"),trackoffs); - if (slabel) outlog (_T("(non-empty sector header)\n")); - sectable[trackoffs] = 1; - secwritten++; - if (trackoffs == 9) - mbuf += 0x228; - } - } - for (i = 0; i < drvsec; i++) { - if (!sectable[i]) { - outlog (_T("sector %d missing\n"), i); - ok = 0; - } - } - return ok; -} - static void amiga_data_raw (FDI *fdi, uae_u8 *secbuf, uae_u8 *crc, int len) { int i; @@ -875,7 +588,6 @@ static void amiga_sector_header (FDI *fdi, uae_u8 *header, uae_u8 *data, int sec static void s20 (FDI *fdi) { bit_drop_next (fdi); - debuglog ("s20:header=%s,data=%s", datalog (fdi->track_src, 4), datalog (fdi->track_src + 4, 16)); amiga_sector_header (fdi, fdi->track_src, fdi->track_src + 4, 0, 0); fdi->track_src += 4 + 16; } @@ -883,7 +595,6 @@ static void s20 (FDI *fdi) static void s21 (FDI *fdi) { bit_drop_next (fdi); - debuglog ("s21:header=%s", datalog (fdi->track_src, 4)); amiga_sector_header (fdi, fdi->track_src, 0, 0, 0); fdi->track_src += 4; } @@ -891,14 +602,12 @@ static void s21 (FDI *fdi) static void s22 (FDI *fdi) { bit_drop_next (fdi); - debuglog ("s22:sector=%d,untilgap=%d", fdi->track_src[0], fdi->track_src[1]); amiga_sector_header (fdi, 0, 0, fdi->track_src[0], fdi->track_src[1]); fdi->track_src += 2; } /* standard 512-byte, CRC-correct Amiga data */ static void s23 (FDI *fdi) { - debuglog ("s23:data=%s", datalog (fdi->track_src, 512)); amiga_data (fdi, fdi->track_src); fdi->track_src += 512; } @@ -906,7 +615,6 @@ static void s23 (FDI *fdi) static void s24 (FDI *fdi) { int shift = *fdi->track_src++; - debuglog ("s24:shift=%d,data=%s", shift, datalog (fdi->track_src, 128 << shift)); amiga_data_raw (fdi, fdi->track_src, 0, 128 << shift); fdi->track_src += 128 << shift; } @@ -914,7 +622,6 @@ static void s24 (FDI *fdi) static void s25 (FDI *fdi) { int shift = *fdi->track_src++; - debuglog ("s25:shift=%d,crc=%s,data=%s", shift, datalog (fdi->track_src, 4), datalog (fdi->track_src + 4, 128 << shift)); amiga_data_raw (fdi, fdi->track_src + 4, fdi->track_src, 128 << shift); fdi->track_src += 4 + (128 << shift); } @@ -922,7 +629,6 @@ static void s25 (FDI *fdi) static void s26 (FDI *fdi) { s21 (fdi); - debuglog ("s26:data=%s", datalog (fdi->track_src, 512)); amiga_data (fdi, fdi->track_src); fdi->track_src += 512; } @@ -930,7 +636,6 @@ static void s26 (FDI *fdi) static void s27 (FDI *fdi) { s22 (fdi); - debuglog ("s27:data=%s", datalog (fdi->track_src, 512)); amiga_data (fdi, fdi->track_src); fdi->track_src += 512; } @@ -1051,14 +756,12 @@ static void s12(FDI *fdi) static void s13(FDI *fdi) { bit_drop_next (fdi); - debuglog ("s13:header=%s", datalog (fdi->track_src, 4)); ibm_sector_header (fdi, fdi->track_src, 0, -1, 1); fdi->track_src += 4; } /* standard mini-extended IBM sector header */ static void s14(FDI *fdi) { - debuglog ("s14:header=%s", datalog (fdi->track_src, 4)); ibm_sector_header (fdi, fdi->track_src, 0, -1, 0); fdi->track_src += 4; } @@ -1066,33 +769,28 @@ static void s14(FDI *fdi) static void s15(FDI *fdi) { bit_drop_next (fdi); - debuglog ("s15:sector=%d", *fdi->track_src); ibm_sector_header (fdi, 0, 0, *fdi->track_src++, 1); } /* standard mini-short IBM sector header */ static void s16(FDI *fdi) { - debuglog ("s16:track=%d", *fdi->track_src); ibm_sector_header (fdi, 0, 0, *fdi->track_src++, 0); } /* standard CRC-incorrect mini-extended IBM sector header */ static void s17(FDI *fdi) { - debuglog ("s17:header=%s,crc=%s", datalog (fdi->track_src, 4), datalog (fdi->track_src + 4, 2)); ibm_sector_header (fdi, fdi->track_src, fdi->track_src + 4, -1, 0); fdi->track_src += 4 + 2; } /* standard CRC-incorrect mini-short IBM sector header */ static void s18(FDI *fdi) { - debuglog ("s18:sector=%d,header=%s", *fdi->track_src, datalog (fdi->track_src + 1, 4)); ibm_sector_header (fdi, 0, fdi->track_src + 1, *fdi->track_src, 0); fdi->track_src += 1 + 4; } /* standard 512-byte CRC-correct IBM data */ static void s19(FDI *fdi) { - debuglog ("s19:data=%s", datalog (fdi->track_src , 512)); ibm_data (fdi, fdi->track_src, 0, 512); fdi->track_src += 512; } @@ -1100,7 +798,6 @@ static void s19(FDI *fdi) static void s1a(FDI *fdi) { int shift = *fdi->track_src++; - debuglog ("s1a:shift=%d,data=%s", shift, datalog (fdi->track_src , 128 << shift)); ibm_data (fdi, fdi->track_src, 0, 128 << shift); fdi->track_src += 128 << shift; } @@ -1108,7 +805,6 @@ static void s1a(FDI *fdi) static void s1b(FDI *fdi) { int shift = *fdi->track_src++; - debuglog ("s1b:shift=%d,crc=%s,data=%s", shift, datalog (fdi->track_src + (128 << shift), 2), datalog (fdi->track_src , 128 << shift)); ibm_data (fdi, fdi->track_src, fdi->track_src + (128 << shift), 128 << shift); fdi->track_src += (128 << shift) + 2; } @@ -1308,29 +1004,20 @@ static int handle_sectors_described_track (FDI *fdi) { int oldout; uae_u8 *start_src = fdi->track_src ; - fdi->encoding_type = *fdi->track_src++; - fdi->index_offset = get_u32(fdi->track_src); - fdi->index_offset >>= 8; fdi->track_src += 3; - outlog (_T("sectors_described, index offset: %d\n"),fdi->index_offset); do { fdi->track_type = *fdi->track_src++; - outlog (_T("%06X %06X %02X:"), (int) (fdi->track_src - start_src + 0x200), fdi->out/8, fdi->track_type); oldout = fdi->out; decode_sectors_described_track[fdi->track_type](fdi); - outlog (_T(" %d\n"), fdi->out - oldout); oldout = fdi->out; if (fdi->out < 0 || fdi->err) { - outlog (_T("\nin %d bytes, out %d bits\n"), (int) (fdi->track_src - fdi->track_src_buffer), fdi->out); return -1; } if (fdi->track_src - fdi->track_src_buffer >= fdi->track_src_len) { - outlog (_T("source buffer overrun, previous type: %02X\n"), fdi->track_type); return -1; } } while (fdi->track_type != 0xff); - outlog (_T("\n")); fix_mfm_sync (fdi); return fdi->out; } @@ -1420,7 +1107,6 @@ static void fdi2_decode (FDI *fdi, unsigned long totalavg, uae_u32 *avgp, uae_u3 || (minp[i] < (standard_MFM_2_bit_cell_size - (standard_MFM_2_bit_cell_size / 4))) ) ) i++; if (i == pulses) { - outlog (_T("FDI: No stable and long-enough pulse in track.\n")); return; } nexti = i; @@ -1497,13 +1183,6 @@ static void fdi2_decode (FDI *fdi, unsigned long totalavg, uae_u32 *avgp, uae_u3 jitter = (randval * (max_pulse - avg_pulse)) / UAE_RAND_MAX; } avg_pulse += jitter; - if ((avg_pulse < min_pulse) || (avg_pulse > max_pulse)) { - outlog (_T("FDI: avg_pulse outside bounds! avg=%u min=%u max=%u\n"), avg_pulse, min_pulse, max_pulse); - outlog (_T("FDI: avgp=%u (%u) minp=%u (%u) maxp=%u (%u) jitter=%d i=%d ni=%d\n"), - avgp[i], avgp[nexti], minp[i], minp[nexti], maxp[i], maxp[nexti], jitter, i, nexti); - } - if (avg_pulse < ref_pulse) - outlog (_T("FDI: avg_pulse < ref_pulse! (%u < %u)\n"), avg_pulse, ref_pulse); pulse += avg_pulse - ref_pulse; ref_pulse = 0; if (i == eodat) @@ -1776,8 +1455,6 @@ static int decode_lowlevel_track (FDI *fdi, int track, struct fdi_cache *cache) idxp[i] = sum; } len = totalavg / 100000; - debuglog ("totalavg=%u index=%d (%d) maxidx=%d weakbits=%d len=%d\n", - totalavg, indexoffset, maxidx, weakbits, len); cache->avgp = avgp; cache->idxp = idxp; cache->minp = minp; @@ -1797,7 +1474,6 @@ static int decode_lowlevel_track (FDI *fdi, int track, struct fdi_cache *cache) } static uae_char fdiid[] = {"Formatted Disk Image file"}; -static int bit_rate_table[16] = { 125,150,250,300,500,1000 }; void fdi2raw_header_free (FDI *fdi) { @@ -1819,7 +1495,6 @@ void fdi2raw_header_free (FDI *fdi) fdi_free (c->maxp); } fdi_free (fdi); - debuglog ("FREE: memory allocated %d\n", fdi_allocated); } int fdi2raw_get_last_track (FDI *fdi) @@ -1834,38 +1509,17 @@ int fdi2raw_get_num_sector (FDI *fdi) return 11; } -int fdi2raw_get_last_head (FDI *fdi) -{ - return fdi->last_head; -} - -int fdi2raw_get_rotation (FDI *fdi) -{ - return fdi->rotation_speed; -} - -int fdi2raw_get_bit_rate (FDI *fdi) -{ - return fdi->bit_rate; -} - int fdi2raw_get_type (FDI *fdi) { return fdi->disk_type; } -int fdi2raw_get_write_protect (FDI *fdi) -{ - return fdi->write_protect; -} - FDI *fdi2raw_header(struct zfile *f) { int i, offset, oldseek; uae_u8 type, size; FDI *fdi; - debuglog ("ALLOC: memory allocated %d\n", fdi_allocated); fdi = fdi_malloc (FDI, 1); memset (fdi, 0, sizeof (FDI)); fdi->file = f; @@ -1886,7 +1540,6 @@ FDI *fdi2raw_header(struct zfile *f) uae_u32 crc = get_crc32(fdi->header, 508); uae_u32 crc2 = (fdi->header[508] << 24) | (fdi->header[509] << 16) | (fdi->header[510] << 8) | fdi->header[511]; if (crc != crc2) { - outlog (_T("FDI: header checksum error\n")); fdi_free(fdi); return NULL; } @@ -1903,13 +1556,8 @@ FDI *fdi2raw_header(struct zfile *f) write_log (_T("FDI: last_track >= MAX_TRACKS (%d >= %d)\n"), fdi->last_track, MAX_TRACKS); fdi->last_track = MAX_TRACKS - 1; } - fdi->last_head = fdi->header[144]; fdi->disk_type = fdi->header[145]; - fdi->rotation_speed = fdi->header[146] + 128; - fdi->write_protect = fdi->header[147] & 1; fdi->reversed_side = (fdi->header[147] & 4) ? 1 : 0; - outlog (_T("FDI version %d.%d\n"), fdi->header[140], fdi->header[141]); - outlog (_T("last_track=%d rotation_speed=%d\n"), fdi->last_track, fdi->rotation_speed); offset = 512; i = fdi->last_track; @@ -1949,8 +1597,6 @@ static int fdi2raw_loadrevolution_2 (FDI *fdi, uae_u16 *mfmbuf, uae_u16 *trackti cache->avgp, cache->minp, cache->maxp, cache->idxp, cache->maxidx, &idx, cache->pulses, mfm); //fdi2_gcr_decode (fdi, totalavg, avgp, minp, maxp, idxp, idx_off1, idx_off2, idx_off3, maxidx, pulses); - debuglog ("track %d: nbits=%d avg len=%.2f weakbits=%d idx=%d\n", - track, bitoffset, (double)cache->totalavg / bitoffset, cache->weakbits, cache->indexoffset); len = fdi->out; if (cache->weakbits >= 10 && multirev) *multirev = 1; @@ -1995,18 +1641,9 @@ int fdi2raw_loadtrack (FDI *fdi, uae_u16 *mfmbuf, uae_u16 *tracktiming, int trac p = fdi->header + 152 + fdi->current_track * 2; fdi->track_type = *p++; fdi->track_len = *p++; - fdi->bit_rate = 0; fdi->out = 0; fdi->mfmsync_offset = 0; - if ((fdi->track_type & 0xf0) == 0xf0 || (fdi->track_type & 0xf0) == 0xe0) - fdi->bit_rate = bit_rate_table[fdi->track_type & 0x0f]; - else - fdi->bit_rate = 250; - - debuglog ("track %d: srclen: %d track_type: %02X, bitrate: %d\n", - fdi->current_track, fdi->track_src_len, fdi->track_type, fdi->bit_rate); - if ((fdi->track_type & 0xc0) == 0x80) { outlen = decode_lowlevel_track (fdi, track, cache); @@ -2037,8 +1674,6 @@ int fdi2raw_loadtrack (FDI *fdi, uae_u16 *mfmbuf, uae_u16 *tracktiming, int trac } - // amiga_check_track (fdi); - if (fdi->err) return 0; diff --git a/src/filesys.cpp b/src/filesys.cpp index f09166a8..71d94f29 100644 --- a/src/filesys.cpp +++ b/src/filesys.cpp @@ -48,8 +48,6 @@ #include "picasso96.h" #include "rommgr.h" -#define TRAPMD 1 - #define KS12_BOOT_HACK 1 #define UNIT_LED(unit) (LED_HD) @@ -61,7 +59,7 @@ static uae_u32 dlg (uae_u32 a) return (dbg (a + 0) << 24) | (dbg (a + 1) << 16) | (dbg (a + 2) << 8) | (dbg (a + 3) << 0); } -#define UAEFS_VERSION "UAEfs 0.5" +#define UAEFS_VERSION "UAE fs 0.6" uaecptr filesys_initcode, filesys_initcode_ptr, filesys_initcode_real; static uaecptr bootrom_start; @@ -104,7 +102,6 @@ typedef struct { bool wasisempty; /* if true, this unit was created empty */ bool canremove; /* if true, this unit can be safely ejected and remounted */ bool configureddrive; /* if true, this is drive that was manually configured */ - bool inject_icons; /* inject icons if directory filesystem */ struct hardfiledata hf; @@ -162,13 +159,15 @@ int nr_directory_units (struct uae_prefs *p) return cnt; } +static int is_hardfile(int unit_no); + static int is_virtual (int unit_no) { int t = is_hardfile (unit_no); return t == FILESYS_VIRTUAL; } -int is_hardfile (int unit_no) +static int is_hardfile (int unit_no) { if (mountinfo.ui[unit_no].volname || mountinfo.ui[unit_no].wasisempty || mountinfo.ui[unit_no].unknown_media) { return FILESYS_VIRTUAL; @@ -227,49 +226,40 @@ int get_filesys_unitconfig (struct uae_prefs *p, int index, struct mountedinfo * UnitInfo *ui = getuip(p, index); struct uaedev_config_data *uci = &p->mountconfig[index]; UnitInfo uitmp; + TCHAR filepath[MAX_DPATH]; memset(mi, 0, sizeof (struct mountedinfo)); memset(&uitmp, 0, sizeof uitmp); - _tcscpy (mi->rootdir, uci->ci.rootdir); if (!ui) { ui = &uitmp; if (uci->ci.type == UAEDEV_DIR) { + cfgfile_resolve_path_out_load(uci->ci.rootdir, filepath, MAX_DPATH, PATH_DIR); mi->ismounted = 1; - if (uci->ci.rootdir && _tcslen (uci->ci.rootdir) == 0) + if (filepath[0] == 0) return FILESYS_VIRTUAL; - if (my_existsfile (uci->ci.rootdir)) { - mi->ismedia = 1; + if (my_existsfile (filepath)) { return FILESYS_VIRTUAL; } - if (my_getvolumeinfo (uci->ci.rootdir) < 0) + if (my_getvolumeinfo (filepath) < 0) return -1; - mi->ismedia = true; return FILESYS_VIRTUAL; } else if (uci->ci.type == UAEDEV_HDF) { + cfgfile_resolve_path_out_load(uci->ci.rootdir, filepath, MAX_DPATH, PATH_HDF); ui->hf.ci.readonly = true; ui->hf.ci.blocksize = uci->ci.blocksize; - int err = hdf_open (&ui->hf, uci->ci.rootdir); + int err = hdf_open (&ui->hf, filepath); if (err <= 0) { - mi->ismedia = false; mi->ismounted = true; - mi->error = err; if (uci->ci.reserved == 0 && uci->ci.sectors == 0 && uci->ci.surfaces == 0) { return FILESYS_HARDFILE_RDB; } return -1; } - mi->ismedia = true; - if (ui->hf.drive_empty) - mi->ismedia = 0; hdf_close (&ui->hf); } } else { if (ui->hf.ci.controller_type == HD_CONTROLLER_TYPE_UAE) { // what is this? || (ui->controller && p->cs_ide)) { mi->ismounted = 1; - if (uci->ci.type == UAEDEV_HDF) - mi->ismedia = ui->hf.drive_empty ? false : true; - else - mi->ismedia = true; } } @@ -277,9 +267,9 @@ int get_filesys_unitconfig (struct uae_prefs *p, int index, struct mountedinfo * return -1; mi->size = ui->hf.virtsize; if (uci->ci.highcyl) { - uci->ci.cyls = mi->nrcyls = uci->ci.highcyl; + uci->ci.cyls = uci->ci.highcyl; } else { - uci->ci.cyls = mi->nrcyls = (int)(uci->ci.sectors * uci->ci.surfaces ? (ui->hf.virtsize / uci->ci.blocksize) / (uci->ci.sectors * uci->ci.surfaces) : 0); + uci->ci.cyls = (int)(uci->ci.sectors * uci->ci.surfaces ? (ui->hf.virtsize / uci->ci.blocksize) / (uci->ci.sectors * uci->ci.surfaces) : 0); } if (uci->ci.type == UAEDEV_DIR) return FILESYS_VIRTUAL; @@ -291,10 +281,10 @@ int get_filesys_unitconfig (struct uae_prefs *p, int index, struct mountedinfo * static void stripsemicolon(TCHAR *s) { - if (!s) - return; - while(_tcslen(s) > 0 && s[_tcslen(s) - 1] == ':') - s[_tcslen(s) - 1] = 0; + if (!s) + return; + while(_tcslen(s) > 0 && s[_tcslen(s) - 1] == ':') + s[_tcslen(s) - 1] = 0; } static void stripspace (TCHAR *s) { @@ -351,11 +341,14 @@ TCHAR *filesys_createvolname (const TCHAR *volname, const TCHAR *rootdir, struct TCHAR *nvol = NULL; int i, archivehd; TCHAR *p = NULL; + TCHAR path[MAX_DPATH]; + + cfgfile_resolve_path_out_load(rootdir, path, MAX_DPATH, PATH_DIR); archivehd = -1; - if (my_existsfile(rootdir)) + if (my_existsfile(path)) archivehd = 1; - else if (my_existsdir(rootdir)) + else if (my_existsdir(path)) archivehd = 0; if (zv && zv->volumename && _tcslen(zv->volumename) > 0) { @@ -364,8 +357,8 @@ TCHAR *filesys_createvolname (const TCHAR *volname, const TCHAR *rootdir, struct return nvol; } - if ((!volname || _tcslen (volname) == 0) && rootdir && archivehd >= 0) { - p = my_strdup (rootdir); + if ((!volname || _tcslen (volname) == 0) && path && archivehd >= 0) { + p = my_strdup (path); for (i = _tcslen (p) - 1; i >= 0; i--) { TCHAR c = p[i]; if (c == ':' || c == '/' || c == '\\') { @@ -374,7 +367,7 @@ TCHAR *filesys_createvolname (const TCHAR *volname, const TCHAR *rootdir, struct if (!_tcscmp (p + i, _T(":\\"))) { xfree (p); p = xmalloc (TCHAR, 10); - p[0] = rootdir[0]; + p[0] = path[0]; p[1] = 0; i = 0; } else { @@ -445,12 +438,71 @@ void uci_set_defaults (struct uaedev_config_info *uci, bool rdb) uci->bufmemtype = 1; uci->buffers = 50; uci->stacksize = 4000; - uci->priority = -129; + uci->bootpri = 0; + uci->priority = 10; uci->sectorsperblock = 1; - uci->device_emu_unit = -1; } -static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci) +static void get_usedblocks(struct fs_usage *fsu, bool fs, int *pblocksize, uae_s64 *pnumblocks, uae_s64 *pinuse, bool reduce) +{ + uae_s64 numblocks = 0, inuse; + int blocksize = *pblocksize; + + if (fs && currprefs.filesys_limit) { + if (fsu->total > (uae_s64)currprefs.filesys_limit * 1024) { + uae_s64 oldtotal = fsu->total; + fsu->total = currprefs.filesys_limit * 1024; + fsu->avail = ((fsu->avail / 1024) * (fsu->total / 1024)) / (oldtotal / 1024); + fsu->avail *= 1024; + } + } + if (reduce) { + while (blocksize < 32768 || numblocks == 0) { + numblocks = fsu->total / blocksize; + if (numblocks <= 10) + numblocks = 10; + // Value that does not overflow when multiplied by 100 (uses 128 to keep it simple) + if (numblocks < 0x02000000) + break; + blocksize *= 2; + } + } + numblocks = fsu->total / blocksize; + inuse = (numblocks * blocksize - fsu->avail) / blocksize; + if (inuse > numblocks) + inuse = numblocks; + if (pnumblocks) + *pnumblocks = numblocks; + if (pinuse) + *pinuse = inuse; + if (pblocksize) + *pblocksize = blocksize; +} + +static bool get_blocks(const TCHAR *rootdir, int unit, int flags, int *pblocksize, uae_s64 *pnumblocks, uae_s64 *pinuse, bool reduce) +{ + struct fs_usage fsu; + int ret; + bool fs = false; + int blocksize; + + blocksize = 512; + if (flags & MYVOLUMEINFO_ARCHIVE) { + ret = zfile_fs_usage_archive(rootdir, 0, &fsu); + fs = true; + } else { + ret = get_fs_usage(rootdir, 0, &fsu); + fs = true; + } + if (ret) + return false; + get_usedblocks(&fsu, fs, &blocksize, pnumblocks, pinuse, reduce); + if (pblocksize) + *pblocksize = blocksize; + return ret == 0; +} + +static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci, bool custom) { UnitInfo *ui; int i; @@ -480,14 +532,17 @@ static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci) return nr; } - for (i = 0; i < MAX_FILESYSTEM_UNITS; i++) { - if (nr == i || !mountinfo.ui[i].open || mountinfo.ui[i].rootdir == NULL) - continue; - if (_tcslen (c.rootdir) > 0 && !_tcsicmp (mountinfo.ui[i].rootdir, c.rootdir)) { - error_log (_T("directory/hardfile '%s' already added."), c.rootdir); - return -1; + if (!custom) + cfgfile_resolve_path_load(c.rootdir, MAX_DPATH, (ci->volname[0] ? PATH_DIR : PATH_HDF)); + + for (i = 0; i < MAX_FILESYSTEM_UNITS; i++) { + if (nr == i || !mountinfo.ui[i].open || mountinfo.ui[i].rootdir == NULL) + continue; + if (_tcslen(c.rootdir) > 0 && samepath(mountinfo.ui[i].rootdir, c.rootdir)) { + error_log (_T("directory/hardfile '%s' already added."), c.rootdir); + return -1; + } } - } for (;;) { bool retry = false; for (i = 0; i < MAX_FILESYSTEM_UNITS; i++) { @@ -516,6 +571,8 @@ static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci) if (c.volname[0]) { int flags = 0; + uae_s64 numblocks; + emptydrive = 1; if (c.rootdir[0]) { if (set_filesys_volume (c.rootdir, &flags, &c.readonly, &emptydrive, &ui->zarchive) < 0) @@ -523,6 +580,25 @@ static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci) } ui->volname = filesys_createvolname (c.volname, c.rootdir, ui->zarchive, _T("harddrive")); ui->volflags = flags; + TCHAR *vs = au(UAEFS_VERSION); + TCHAR *vsp = vs + _tcslen(vs) - 1; + while (vsp != vs) { + if (*vsp == ' ') { + *vsp++ = 0; + break; + } + vsp--; + } + _tcscpy(ui->hf.vendor_id, _T("UAE")); + _tcscpy(ui->hf.product_id, vs); + _tcscpy(ui->hf.product_rev, vsp); + xfree(vs); + ui->hf.ci.unit_feature_level = HD_LEVEL_SCSI_2; + if (get_blocks(c.rootdir, nr, flags, &ui->hf.ci.blocksize, &numblocks, NULL, false)) + ui->hf.ci.max_lba = numblocks > 0xffffffff ? 0xffffffff : numblocks; + else + ui->hf.ci.max_lba = 0x00ffffff; + } else { ui->unit_type = UNIT_FILESYSTEM; ui->hf.unitnum = nr; @@ -584,7 +660,6 @@ static int set_filesys_unit_1 (int nr, struct uaedev_config_info *ci) if (c.bootpri > 127) c.bootpri = 127; ui->bootpri = c.bootpri; - ui->inject_icons = c.inject_icons; ui->open = 1; return nr; @@ -594,23 +669,23 @@ err: return -1; } -static int set_filesys_unit (int nr, struct uaedev_config_info *ci) +static int set_filesys_unit (int nr, struct uaedev_config_info *ci, bool custom) { int ret; - ret = set_filesys_unit_1 (nr, ci); + ret = set_filesys_unit_1 (nr, ci, custom); return ret; } -static int add_filesys_unit (struct uaedev_config_info *ci) +static int add_filesys_unit (struct uaedev_config_info *ci, bool custom) { - int ret; + int nr; if (nr_units() >= MAX_FILESYSTEM_UNITS) return -1; - ret = set_filesys_unit_1 (-1, ci); - return ret; + nr = set_filesys_unit_1 (-1, ci, custom); + return nr; } int kill_filesys_unitconfig (struct uae_prefs *p, int nr) @@ -621,8 +696,9 @@ int kill_filesys_unitconfig (struct uae_prefs *p, int nr) return 0; uci = getuci (p->mountconfig, nr); hardfile_do_disk_change (uci, 0); - if (uci->configoffset >= 0 && uci->ci.controller_type == HD_CONTROLLER_TYPE_UAE) + if (uci->configoffset >= 0 && uci->ci.controller_type == HD_CONTROLLER_TYPE_UAE) { filesys_media_change (uci->ci.rootdir, 0, uci); + } while (nr < MOUNT_CONFIG_SIZE) { memmove (&p->mountconfig[nr], &p->mountconfig[nr + 1], sizeof (struct uaedev_config_data)); nr++; @@ -632,20 +708,6 @@ int kill_filesys_unitconfig (struct uae_prefs *p, int nr) return 1; } -int move_filesys_unitconfig (struct uae_prefs *p, int nr, int to) -{ - struct uaedev_config_data *uci1, *uci2, tmpuci; - - uci1 = getuci (p->mountconfig, nr); - uci2 = getuci (p->mountconfig, to); - if (nr == to) - return 0; - memcpy (&tmpuci, uci1, sizeof (struct uaedev_config_data)); - memcpy (uci1, uci2, sizeof (struct uaedev_config_data)); - memcpy (uci2, &tmpuci, sizeof (struct uaedev_config_data)); - return 1; -} - static void allocuci (struct uae_prefs *p, int nr, int idx, int unitnum) { struct uaedev_config_data *uci = &p->mountconfig[nr]; @@ -665,11 +727,6 @@ static void allocuci (struct uae_prefs *p, int nr, int idx) allocuci (p, nr, idx, -1); } -static const TCHAR *getunittype(struct uaedev_config_info *uci) -{ - return _T("HD"); -} - static bool add_ide_unit(int type, int unit, struct uaedev_config_info *uci) { bool added = false; @@ -680,7 +737,7 @@ static bool add_ide_unit(int type, int unit, struct uaedev_config_info *uci) if ((ert->deviceflags & 2) && is_board_enabled(&currprefs, ert->romtype, uci->controller_type_unit)) { if (ert->add) { struct romconfig *rc = get_device_romconfig(&currprefs, ert->romtype, uci->controller_type_unit); - write_log(_T("Adding IDE %s '%s' unit %d ('%s')\n"), getunittype(uci), + write_log(_T("Adding IDE %s '%s' unit %d ('%s')\n"), _T("HD"), ert->name, unit, uci->rootdir); ert->add(unit, uci, rc); } @@ -705,7 +762,7 @@ static void initialize_mountinfo(void) struct uaedev_config_info ci; memcpy (&ci, &uci->ci, sizeof (struct uaedev_config_info)); ci.flags = MYVOLUMEINFO_REUSABLE; - int idx = set_filesys_unit_1 (-1, &ci); + int idx = set_filesys_unit_1 (-1, &ci, false); allocuci (&currprefs, nr, idx); } } @@ -731,6 +788,7 @@ static void initialize_mountinfo(void) int type = uci->controller_type; int unit = uci->controller_unit; bool added = false; + uci->uae_unitnum = nr; if (type == HD_CONTROLLER_TYPE_UAE) { continue; } else if (type != HD_CONTROLLER_TYPE_IDE_AUTO && type >= HD_CONTROLLER_TYPE_IDE_FIRST && type <= HD_CONTROLLER_TYPE_IDE_LAST) { @@ -741,33 +799,12 @@ static void initialize_mountinfo(void) if (added) break; } - } else if (type == HD_CONTROLLER_TYPE_PCMCIA) { - if (uci->controller_type_unit == 0) { - gayle_add_pcmcia_sram_unit (uci); - added = true; - } else { - gayle_add_pcmcia_ide_unit (uci); - added = true; - } } if (added) allocuci (&currprefs, nr, -1); } } -int sprintf_filesys_unit (TCHAR *buffer, int num) -{ - UnitInfo *uip = mountinfo.ui; - - if (uip[num].volname != 0) - _stprintf (buffer, _T("(DH%d:) Filesystem, %s: %s %s"), num, uip[num].volname, - uip[num].rootdir, uip[num].readonly ? _T("ro") : _T("")); - else - _stprintf (buffer, _T("(DH%d:) Hardfile, \"%s\", size %d Mbytes"), num, - uip[num].rootdir, (int)(uip[num].hf.virtsize / (1024 * 1024))); - return 0; -} - static void free_mountinfo (void) { int i; @@ -780,7 +817,7 @@ struct hardfiledata *get_hardfile_data_controller(int nr) { UnitInfo *uip = mountinfo.ui; for (int i = 0; i < MAX_FILESYSTEM_UNITS; i++) { - if (uip[i].open == 0 || is_virtual(i)) + if (uip[i].open == 0) continue; if (uip[i].hf.ci.controller_unit == nr) return &uip[i].hf; @@ -1025,15 +1062,12 @@ typedef struct _unit { a_inode rootnode; unsigned int aino_cache_size; a_inode *aino_hash[MAX_AINO_HASH]; - unsigned int nr_cache_hits; - unsigned int nr_cache_lookups; struct notify *notifyhash[NOTIFY_HASH_SIZE]; int volflags; uae_u32 lockkey; bool inhibited; - bool canremovable; /* increase when media is changed. * used to detect if cached aino is valid */ @@ -1041,11 +1075,6 @@ typedef struct _unit { int mount_changed; struct zvolume *zarchive; - TCHAR *mount_volume; - TCHAR *mount_rootdir; - bool mount_readonly; - int mount_flags; - int reinsertdelay; TCHAR *newvolume; TCHAR *newrootdir; @@ -1076,8 +1105,6 @@ static uae_u32 a_uniq, key_uniq; #define GET_PCK64_ARG1(p) ((uae_s32)(get_long_host((p)->packet_data + dp64_Arg1))) #define GET_PCK64_ARG2(p) ( (((uae_s64)(get_long_host((p)->packet_data + dp64_Arg2))) << 32) | (((uae_s64)(get_long_host((p)->packet_data + dp64_Arg2 + 4))) << 0) ) #define GET_PCK64_ARG3(p) ((uae_s32)(get_long_host((p)->packet_data + dp64_Arg3))) -#define GET_PCK64_ARG4(p) ((uae_s32)(get_long_host((p)->packet_data + dp64_Arg4))) -#define GET_PCK64_ARG5(p) ( (((uae_s64)(get_long_host((p)->packet_data + dp64_Arg5))) << 32) | (((uae_s64)(get_long_host((p)->packet_data + dp64_Arg5 + 4))) << 0) ) static void readdpacket(TrapContext *ctx, dpacket *packet, uaecptr pck) { @@ -1125,15 +1152,7 @@ static TCHAR *char1 (TrapContext *ctx, uaecptr addr) { uae_char buf[1024]; -#if TRAPMD trap_get_string(ctx, (uae_u8*)buf, addr, sizeof(buf)); -#else - unsigned int i = 0; - do { - buf[i] = trap_get_byte(ctx, addr); - addr++; - } while (buf[i++] && i < sizeof(buf)); -#endif return au_fs(buf); } @@ -1143,12 +1162,7 @@ static TCHAR *bstr1 (TrapContext *ctx, uaecptr addr) int n = trap_get_byte(ctx, addr); addr++; -#if TRAPMD trap_get_bytes(ctx, (uae_u8*)buf, addr, n); -#else - for (int i = 0; i < n; i++, addr++) - buf[i] = trap_get_byte(ctx, addr); -#endif buf[n] = 0; return au_fs(buf); } @@ -1159,24 +1173,11 @@ static TCHAR *bstr (TrapContext *ctx, Unit *unit, uaecptr addr) uae_char buf[257]; addr++; -#if TRAPMD trap_get_bytes(ctx, (uae_u8*)buf, addr, n); -#else - for (int i = 0; i < n; i++, addr++) - buf[i] = trap_get_byte(ctx, addr); -#endif buf[n] = 0; au_fs_copy (unit->tmpbuf3, sizeof (unit->tmpbuf3) / sizeof (TCHAR), buf); return unit->tmpbuf3; } -static TCHAR *cstr (TrapContext *ctx, Unit *unit, uaecptr addr) -{ - uae_char buf[257]; - - trap_get_string(ctx, buf, addr, sizeof buf); - au_fs_copy (unit->tmpbuf3, sizeof (unit->tmpbuf3) / sizeof (TCHAR), buf); - return unit->tmpbuf3; -} static TCHAR *bstr_cut (TrapContext *ctx, Unit *unit, uaecptr addr) { @@ -1353,14 +1354,10 @@ static uae_u32 fs_fsize (struct fs_filehandle *fsf) static uae_s64 key_filesize(Key *k) { - if (k->aino->vfso) - return k->aino->vfso->size; return fs_fsize64 (k->fd); } static uae_s64 key_seek(Key *k, uae_s64 offset, int whence) { - if (k->aino->vfso) - return k->file_pos; return fs_lseek64 (k->fd, offset, whence); } @@ -1429,22 +1426,7 @@ static void clear_exkeys(Unit *unit) } } -static void filesys_delayed_change (Unit *u, int frames, const TCHAR *rootdir, const TCHAR *volume, bool readonly, int flags) -{ - u->reinsertdelay = 50; - u->newflags = flags; - u->newreadonly = readonly; - u->newrootdir = my_strdup (rootdir); - if (volume) - u->newvolume = my_strdup (volume); - filesys_eject(u->unit); - if (!rootdir || _tcslen (rootdir) == 0) - u->reinsertdelay = 0; - if (u->reinsertdelay > 0) - write_log (_T("FILESYS: delayed insert %d: '%s' ('%s')\n"), u->unit, volume ? volume : _T(""), rootdir); -} - -int filesys_eject (int nr) +static int filesys_eject (int nr) { UnitInfo *ui = &mountinfo.ui[nr]; Unit *u = ui->self; @@ -1466,6 +1448,21 @@ int filesys_eject (int nr) return 1; } +static void filesys_delayed_change (Unit *u, int frames, const TCHAR *rootdir, const TCHAR *volume, bool readonly, int flags) +{ + u->reinsertdelay = 50; + u->newflags = flags; + u->newreadonly = readonly; + u->newrootdir = my_strdup (rootdir); + if (volume) + u->newvolume = my_strdup (volume); + filesys_eject(u->unit); + if (!rootdir || _tcslen (rootdir) == 0) + u->reinsertdelay = 0; + if (u->reinsertdelay > 0) + write_log (_T("FILESYS: delayed insert %d: '%s' ('%s')\n"), u->unit, volume ? volume : _T(""), rootdir); +} + static uae_u32 heartbeat; static int heartbeat_count, heartbeat_count_cont; static int heartbeat_task; @@ -1476,7 +1473,7 @@ bool filesys_heartbeat(void) } // This uses filesystem process to reduce resource usage -void setsystime(void) +void setsystime (void) { if (!currprefs.tod_hack || !rtarea_bank.baseaddr) return; @@ -1485,38 +1482,15 @@ void setsystime(void) heartbeat_count = 10; } -static uae_u32 REGPARAM2 debugger_helper(TrapContext *ctx) -{ - int mode = trap_get_dreg(ctx, 1); - switch (mode) - { - case 1: - // Execute debugger_boot() to get here. - write_log(_T("debugger #1\n")); - // return RunCommand(() parameters - // does nothing if D1 == 0. - break; - case 2: - // called when RunCommand() returns - // D0 = RunCommand() return code. - write_log(_T("debugger #2\n")); - break; - default: - write_log(_T("Unknown debugger hook %d\n"), mode); - return 0; - } - return 1; -} - -static void debugger_boot(void) +static void setsystime_vblank (void) { Unit *u; TrapContext *ctx = NULL; for (u = units; u; u = u->next) { if (is_virtual(u->unit) && filesys_isvolume(u)) { - put_byte(u->volume + 173 - 32, get_byte(u->volume + 173 - 32) | 2); - uae_Signal (get_long (u->volume + 176 - 32), 1 << 13); + put_byte(u->volume + 173 - 32, get_byte(u->volume + 173 - 32) | 1); + uae_Signal(get_long(u->volume + 176 - 32), 1 << 13); break; } } @@ -1569,10 +1543,6 @@ int filesys_insert (int nr, const TCHAR *volume, const TCHAR *rootdir, bool read } u->mountcount++; u->mount_changed = 1; - u->mount_volume = volume ? my_strdup (volume) : NULL; - u->mount_rootdir = my_strdup (rootdir); - u->mount_readonly = readonly; - u->mount_flags = flags; write_log (_T("filesys_insert %d done!\n"), nr); @@ -1674,7 +1644,7 @@ int filesys_media_change (const TCHAR *rootdir, int inserted, struct uaedev_conf _tcscpy (ci.volname, volptr); _tcscpy (ci.rootdir, rootdir); ci.flags = MYVOLUMEINFO_REUSABLE; - nr = add_filesys_unit (&ci); + nr = add_filesys_unit (&ci, true); if (nr < 0) return 0; if (inserted > 1) @@ -1689,17 +1659,6 @@ int filesys_media_change (const TCHAR *rootdir, int inserted, struct uaedev_conf return 0; } -int hardfile_added (struct uaedev_config_info *ci) -{ - if (ci->controller_type == HD_CONTROLLER_TYPE_PCMCIA) { - if (ci->controller_type_unit == 1) - return gayle_add_pcmcia_ide_unit(ci); - if (ci->controller_type_unit == 0) - return gayle_add_pcmcia_sram_unit(ci); - } - return 0; -} - int hardfile_media_change (struct hardfiledata *hfd, struct uaedev_config_info *ci, bool inserted, bool timer) { if (!hfd) @@ -1714,7 +1673,7 @@ int hardfile_media_change (struct hardfiledata *hfd, struct uaedev_config_info * if (hfd->delayedci.rootdir[0]) { hfd->reinsertdelay = 50; hfd->isreinsert = true; - write_log (_T("HARDFILE: delayed insert %d: '%s'\n"), hfd->unitnum, ci->rootdir ? ci->rootdir : _T("")); + write_log (_T("HARDFILE: delayed insert %d: '%s'\n"), hfd->unitnum, ci->rootdir[0] ? ci->rootdir : _T("")); return 0; } else { return 1; @@ -1734,7 +1693,7 @@ int hardfile_media_change (struct hardfiledata *hfd, struct uaedev_config_info * if (hfd && !hfd->drive_empty) { hfd->reinsertdelay = 50; hfd->isreinsert = false; - write_log (_T("HARDFILE: delayed eject %d: '%s'\n"), hfd->unitnum, hfd->ci.rootdir ? hfd->ci.rootdir : _T("")); + write_log (_T("HARDFILE: delayed eject %d: '%s'\n"), hfd->unitnum, hfd->ci.rootdir[0] ? hfd->ci.rootdir : _T("")); return 0; } if (!hfd) { @@ -1757,10 +1716,6 @@ int hardfile_media_change (struct hardfiledata *hfd, struct uaedev_config_info * return 0; } -static void prepare_for_open (TCHAR *name) -{ -} - static void de_recycle_aino (Unit *unit, a_inode *aino) { if (aino->next == 0 || aino == &unit->rootnode) @@ -1874,10 +1829,6 @@ static void recycle_aino (Unit *unit, a_inode *new_aino) unit->aino_cache_size++; } -void filesys_flush_cache (void) -{ -} - static void update_child_names (Unit *unit, a_inode *a, a_inode *parent) { int l0 = _tcslen (parent->nname) + 2; @@ -1989,9 +1940,6 @@ static a_inode *lookup_aino (Unit *unit, uae_u32 uniq) a = unit->aino_hash[hash]; if (a == 0 || a->uniq != uniq) a = lookup_sub (&unit->rootnode, uniq); - else - unit->nr_cache_hits++; - unit->nr_cache_lookups++; unit->aino_hash[hash] = a; return a; } @@ -2010,15 +1958,6 @@ TCHAR *build_nname (const TCHAR *d, const TCHAR *n) return p; } -TCHAR *build_aname (const TCHAR *d, const TCHAR *n) -{ - TCHAR *p = xmalloc (TCHAR, _tcslen (d) + 1 + _tcslen (n) + 1); - _tcscpy (p, d); - _tcscat (p, _T("/")); - _tcscat (p, n); - return p; -} - /* This gets called to translate an Amiga name that some program used to * a name that we can use on the native filesystem. */ static TCHAR *get_nname (Unit *unit, a_inode *base, TCHAR *rel, TCHAR **modified_rel, uae_u64 *uniq_ext) @@ -2234,7 +2173,7 @@ static a_inode *lookup_child_aino (Unit *unit, a_inode *base, TCHAR *rel, int *e } /* Different version because for this one, REL is an nname. */ -static a_inode *lookup_child_aino_for_exnext (Unit *unit, a_inode *base, TCHAR *rel, uae_u32 *err, uae_u64 uniq_external, struct virtualfilesysobject *vfso) +static a_inode *lookup_child_aino_for_exnext (Unit *unit, a_inode *base, TCHAR *rel, uae_u32 *err, uae_u64 uniq_external) { a_inode *c = base->child; int l0 = _tcslen (rel); @@ -2251,7 +2190,7 @@ static a_inode *lookup_child_aino_for_exnext (Unit *unit, a_inode *base, TCHAR * } if (c != 0) return c; - if (!isvirtual && !vfso) + if (!isvirtual) c = fsdb_lookup_aino_nname (base, rel); if (c == 0) { c = xcalloc (a_inode, 1); @@ -2265,17 +2204,12 @@ static a_inode *lookup_child_aino_for_exnext (Unit *unit, a_inode *base, TCHAR * c->comment = 0; c->uniq_external = uniq_external; c->has_dbentry = 0; - if (vfso) { - c->dir = vfso->dir; - c->comment = my_strdup(vfso->comment); - c->amigaos_mode = vfso->amigaos_mode; - c->vfso = vfso; - } else if (!fill_file_attrs (unit, base, c)) { + if (!fill_file_attrs (unit, base, c)) { xfree (c); *err = ERROR_NO_FREE_STORE; return 0; } - if (c->dir && !isvirtual && !vfso) + if (c->dir && !isvirtual) fsdb_clean_dir (c); } init_child_aino (unit, base, c); @@ -2442,7 +2376,7 @@ static Unit *startup_create_unit (TrapContext *ctx, UnitInfo *uinfo, int num) } #ifdef UAE_FILESYS_THREADS -static void *filesys_thread (void *unit_v); +static int filesys_thread (void *unit_v); #endif static void filesys_start_thread (UnitInfo *ui, int nr) { @@ -2570,7 +2504,7 @@ static uae_u32 REGPARAM2 startup_handler (TrapContext *ctx) put_byte (unit->volume + 64, 0); if (!uinfo->wasisempty && !uinfo->unknown_media) { - int isvirtual = unit->volflags & (MYVOLUMEINFO_ARCHIVE); + int isvirtual = unit->volflags & MYVOLUMEINFO_ARCHIVE; /* Set volume if non-empty */ set_volume_name (unit, &ctime); if (!isvirtual) @@ -2593,33 +2527,32 @@ static bool is_writeprotected(Unit *unit) static void do_info(TrapContext *ctx, Unit *unit, dpacket *packet, uaecptr info, bool disk_info) { - struct fs_usage fsu; + struct fs_usage fsu; int ret, err = ERROR_NO_FREE_STORE; int blocksize, nr; uae_u32 dostype; bool fs = false, media = false; - uae_u8 buf[36] = { 0 }; // InfoData + uae_u8 buf[36] = { 0 }; // InfoData blocksize = 512; dostype = get_long(unit->volume + 32); nr = unit->unit; - if (unit->volflags & MYVOLUMEINFO_ARCHIVE) { - ret = zfile_fs_usage_archive(unit->ui.rootdir, 0, &fsu); + if (unit->volflags & MYVOLUMEINFO_ARCHIVE) { + ret = zfile_fs_usage_archive (unit->ui.rootdir, 0, &fsu); fs = true; - media = filesys_isvolume(unit) != 0; - } - else { - ret = get_fs_usage(unit->ui.rootdir, 0, &fsu); + media = filesys_isvolume (unit) != 0; + } else { + ret = get_fs_usage (unit->ui.rootdir, 0, &fsu); if (ret) - err = dos_errno(); + err = dos_errno (); fs = true; - media = filesys_isvolume(unit) != 0; - } - if (ret != 0) { - PUT_PCK_RES1(packet, DOS_FALSE); - PUT_PCK_RES2(packet, err); - return; + media = filesys_isvolume (unit) != 0; } + if (ret != 0) { + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, err); + return; + } put_long_host(buf, 0); /* errors */ put_long_host(buf + 4, nr); /* unit number */ put_long_host(buf + 8, is_writeprotected(unit) ? 80 : 82); /* state */ @@ -2627,57 +2560,36 @@ static void do_info(TrapContext *ctx, Unit *unit, dpacket *packet, uaecptr info, put_long_host(buf + 32, 0); /* inuse */ if (unit->ui.unknown_media) { if (!disk_info) { - PUT_PCK_RES1(packet, DOS_FALSE); - PUT_PCK_RES2(packet, ERROR_NOT_A_DOS_DISK); + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, ERROR_NOT_A_DOS_DISK); return; } put_long_host(buf + 12, 0); put_long_host(buf + 16, 0); put_long_host(buf + 24, ('B' << 24) | ('A' << 16) | ('D' << 8) | (0 << 0)); /* ID_UNREADABLE_DISK */ put_long_host(buf + 28, 0); - } - else if (!media) { + } else if (!media) { if (!disk_info) { - PUT_PCK_RES1(packet, DOS_FALSE); - PUT_PCK_RES2(packet, ERROR_NO_DISK); + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, ERROR_NO_DISK); return; } put_long_host(buf + 12, 0); put_long_host(buf + 16, 0); put_long_host(buf + 24, -1); /* ID_NO_DISK_PRESENT */ put_long_host(buf + 28, 0); - } - else { - if (fs && currprefs.filesys_limit) { - if (fsu.total > (uae_s64)currprefs.filesys_limit * 1024) { - uae_s64 oldtotal = fsu.total; - fsu.total = currprefs.filesys_limit * 1024; - fsu.avail = ((fsu.avail / 1024) * (fsu.total / 1024)) / (oldtotal / 1024); - fsu.avail *= 1024; - } - } - uae_s64 numblocks = 0; - while (blocksize < 32768 || numblocks == 0) { - numblocks = fsu.total / blocksize; - if (numblocks <= 10) - numblocks = 10; - if (numblocks < 0x02000000) - break; - blocksize *= 2; - } - uae_s64 inuse = (numblocks * blocksize - fsu.avail) / blocksize; - if (inuse > numblocks) - inuse = numblocks; - + } else { + uae_s64 numblocks, inuse; + get_usedblocks(&fsu, fs, &blocksize, &numblocks, &inuse, true); put_long_host(buf + 12, (uae_u32)numblocks); /* numblocks */ put_long_host(buf + 16, (uae_u32)inuse); /* inuse */ put_long_host(buf + 20, blocksize); /* bytesperblock */ - put_long_host(buf + 24, dostype); /* disk type */ + put_long_host(buf + 24, dostype == DISK_TYPE_DOS && kickstart_version >= 36 ? DISK_TYPE_DOS_FFS : dostype); /* disk type */ put_long_host(buf + 28, unit->volume >> 2); /* volume node */ put_long_host(buf + 32, (get_long(unit->volume + 28) || unit->keys) ? -1 : 0); /* inuse */ } trap_put_bytes(ctx, buf, info, sizeof buf); - PUT_PCK_RES1(packet, DOS_TRUE); + PUT_PCK_RES1 (packet, DOS_TRUE); } static void action_disk_info(TrapContext *ctx, Unit *unit, dpacket *packet) @@ -2762,13 +2674,11 @@ static a_inode *find_aino (TrapContext *ctx, Unit *unit, uaecptr lock, const TCH return a; } -static uaecptr make_lock (TrapContext *ctx, Unit *unit, uae_u32 uniq, long mode) +static uaecptr make_lock (TrapContext *ctx, Unit *unit, uae_u32 uniq, uae_s32 mode) { /* allocate lock from the list kept by the assembly code */ uaecptr lock; -#if TRAPMD - struct trapmd md1[] = { { TRAPCMD_GET_LONG, { unit->locklist }, 1, 0 }, @@ -2778,15 +2688,6 @@ static uaecptr make_lock (TrapContext *ctx, Unit *unit, uae_u32 uniq, long mode) trap_multi(ctx, md1, sizeof md1 / sizeof(struct trapmd)); lock = md1[0].params[0] + 4; -#else - - lock = trap_get_long(ctx, unit->locklist); - trap_put_long(ctx, unit->locklist, trap_get_long(ctx, lock)); - lock += 4; - -#endif - -#if TRAPMD struct trapmd md2[] = { { TRAPCMD_PUT_LONG, { lock + 4, uniq } }, @@ -2801,19 +2702,6 @@ static uaecptr make_lock (TrapContext *ctx, Unit *unit, uae_u32 uniq, long mode) }; trap_multi(ctx, md2, sizeof md2 / sizeof(struct trapmd)); -#else - - trap_put_long(ctx, lock + 4, uniq); - trap_put_long(ctx, lock + 8, mode); - trap_put_long(ctx, lock + 12, unit->port); - trap_put_long(ctx, lock + 16, unit->volume >> 2); - - /* prepend to lock chain */ - trap_put_long(ctx, lock, trap_get_long(ctx, unit->volume + 28)); - trap_put_long(ctx, unit->volume + 28, lock >> 2); - -#endif - return lock; } @@ -2950,7 +2838,6 @@ static void free_lock (TrapContext *ctx, Unit *unit, uaecptr lock) trap_put_long(ctx, current << 2, trap_get_long(ctx, lock)); } lock -= 4; -#if TRAPMD struct trapmd md2[] = { { TRAPCMD_GET_LONG, { unit->locklist }, 1, 1 }, @@ -2958,10 +2845,6 @@ static void free_lock (TrapContext *ctx, Unit *unit, uaecptr lock) { TRAPCMD_PUT_LONG, { unit->locklist, lock } } }; trap_multi(ctx, md2, sizeof md2 / sizeof(struct trapmd)); -#else - trap_put_long(ctx, lock, trap_get_long(ctx, unit->locklist)); - trap_put_long(ctx, unit->locklist, lock); -#endif } static void action_lock(TrapContext *ctx, Unit *unit, dpacket *packet) @@ -3107,12 +2990,7 @@ static void get_fileinfo(TrapContext *ctx, Unit *unit, dpacket *packet, uaecptr buf = get_real_address(info); } - if (aino->vfso) { - statbuf.mode = aino->vfso->amigaos_mode; - statbuf.mtime.tv_sec = 0; - statbuf.mtime.tv_usec = 0; - statbuf.size = aino->vfso->size; - } else if (!get_statinfo(unit, aino, &statbuf)) { + if (!get_statinfo(unit, aino, &statbuf)) { PUT_PCK_RES1 (packet, DOS_FALSE); PUT_PCK_RES2 (packet, ERROR_NOT_A_DOS_DISK); return; @@ -3589,7 +3467,7 @@ static int action_examine_all_do (TrapContext *ctx, Unit *unit, uaecptr lock, Ex xfree (eak->fn); eak->fn = NULL; } - aino = lookup_child_aino_for_exnext (unit, base, fn, &err, uniq, NULL); + aino = lookup_child_aino_for_exnext (unit, base, fn, &err, uniq); if (!aino) return 0; eak->id = unit->exallid++; @@ -3790,70 +3668,6 @@ static void action_examine_object(TrapContext *ctx, Unit *unit, dpacket *packet) get_fileinfo(ctx, unit, packet, info, aino, false); } -extern unsigned char def_tool[]; -extern unsigned int def_tool_len; -extern unsigned char def_project[]; -extern unsigned int def_project_len; -extern unsigned char def_drawer[]; -extern unsigned int def_drawer_len; -static struct virtualfilesysobject vfso_icon_tool; -static struct virtualfilesysobject vfso_icon_project; -static struct virtualfilesysobject vfso_icon_drawer; - -static void load_injected_icon(struct virtualfilesysobject *vfso, const TCHAR *fn, uae_u8 *default_data, int default_size) -{ - uae_u8 *data = NULL; - int size; - - xfree(vfso->data); - if (fn && fn[0]) - data = zfile_load_file(fn, &size); - if (!data) { - vfso->data = xmalloc(uae_u8, default_size); - memcpy(vfso->data, default_data, default_size); - vfso->size = default_size; - return; - } - vfso->data = data; - vfso->size = size; -} - -static void load_injected_icons(void) -{ - load_injected_icon(&vfso_icon_tool, currprefs.filesys_inject_icons_tool, def_tool, def_tool_len); - load_injected_icon(&vfso_icon_project, currprefs.filesys_inject_icons_project, def_project, def_project_len); - load_injected_icon(&vfso_icon_drawer, currprefs.filesys_inject_icons_drawer, def_drawer, def_drawer_len); -} - -static void inject_icons_to_directory(Unit *unit, a_inode *base) -{ - for (a_inode *aino = base->child; aino; aino = aino->sibling) { - int len = _tcslen(aino->aname); - if (len >= 5 && !_tcsicmp(aino->aname + len - 5, _T(".info"))) - continue; - TCHAR tmp[256]; - _stprintf(tmp, _T("%s.info"), aino->aname); - bool match = false; - for (a_inode *aino2 = base->child; aino2; aino2 = aino2->sibling) { - if (!_tcsicmp(aino2->aname, tmp)) - match = true; - } - if (match) - continue; - uae_u32 err; - struct virtualfilesysobject *vfso; - if (aino->dir) { - vfso = &vfso_icon_drawer; - } else { - if (aino->amigaos_mode & A_FIBF_EXECUTE) - vfso = &vfso_icon_project; - else - vfso = &vfso_icon_tool; - } - lookup_child_aino_for_exnext(unit, base, tmp, &err, 0, vfso); - } -} - /* Read a directory's contents, create a_inodes for each file, and mark them as locked in memory so that recycle_aino will not reap them. @@ -3888,11 +3702,9 @@ static void populate_directory (Unit *unit, a_inode *base) break; /* This calls init_child_aino, which will notice that the parent is being ExNext()ed, and it will increment the locked counts. */ - aino = lookup_child_aino_for_exnext (unit, base, fn, &err, uniq, NULL); + aino = lookup_child_aino_for_exnext (unit, base, fn, &err, uniq); } fs_closedir (d); - if (currprefs.filesys_inject_icons || unit->ui.inject_icons) - inject_icons_to_directory(unit, base); } static bool do_examine(TrapContext *ctx, Unit *unit, dpacket *packet, a_inode *aino, uaecptr info, bool longfilesize) @@ -3903,7 +3715,7 @@ static bool do_examine(TrapContext *ctx, Unit *unit, dpacket *packet, a_inode *a break; name = aino->nname; get_fileinfo (ctx, unit, packet, info, aino, longfilesize); - if (!aino->vfso && !(unit->volflags & MYVOLUMEINFO_ARCHIVE) && !fsdb_exists(name)) { + if (!(unit->volflags & MYVOLUMEINFO_ARCHIVE) && !fsdb_exists(name)) { return false; } return true; @@ -4019,11 +3831,6 @@ static void do_find(TrapContext *ctx, Unit *unit, dpacket *packet, int mode, int PUT_PCK_RES2 (packet, ERROR_OBJECT_IN_USE); return; } - if (create && aino->vfso) { - PUT_PCK_RES1 (packet, DOS_FALSE); - PUT_PCK_RES2 (packet, ERROR_DELETE_PROTECTED); - return; - } if (create == 2 && (aino->amigaos_mode & A_FIBF_DELETE) != 0) { PUT_PCK_RES1 (packet, DOS_FALSE); PUT_PCK_RES2 (packet, ERROR_DELETE_PROTECTED); @@ -4070,24 +3877,20 @@ static void do_find(TrapContext *ctx, Unit *unit, dpacket *packet, int mode, int aino_created = 1; } - prepare_for_open (aino->nname); - - if (!aino->vfso) { - openmode = (((mode & A_FIBF_READ) == 0 ? O_WRONLY - : (mode & A_FIBF_WRITE) == 0 ? O_RDONLY - : O_RDWR) - | (create ? O_CREAT : 0) - | (create == 2 ? O_TRUNC : 0)); - - fd = fs_openfile (unit, aino, openmode | O_BINARY); - if (fd == NULL) { - if (aino_created) - delete_aino (unit, aino); - PUT_PCK_RES1 (packet, DOS_FALSE); - /* archive and fd == NULL = corrupt archive or out of memory */ - PUT_PCK_RES2 (packet, isvirtual ? ERROR_OBJECT_NOT_AROUND : dos_errno ()); - return; - } + openmode = (((mode & A_FIBF_READ) == 0 ? O_WRONLY + : (mode & A_FIBF_WRITE) == 0 ? O_RDONLY + : O_RDWR) + | (create ? O_CREAT : 0) + | (create == 2 ? O_TRUNC : 0)); + + fd = fs_openfile (unit, aino, openmode | O_BINARY); + if (fd == NULL) { + if (aino_created) + delete_aino (unit, aino); + PUT_PCK_RES1 (packet, DOS_FALSE); + /* archive and fd == NULL = corrupt archive or out of memory */ + PUT_PCK_RES2 (packet, isvirtual ? ERROR_OBJECT_NOT_AROUND : dos_errno ()); + return; } k = new_key (unit); @@ -4139,8 +3942,6 @@ static void action_fh_from_lock(TrapContext *ctx, Unit *unit, dpacket *packet) mode = aino->amigaos_mode; /* Use same mode for opened filehandle as existing Lock() */ - prepare_for_open (aino->nname); - openmode = (((mode & A_FIBF_READ) ? O_WRONLY : (mode & A_FIBF_WRITE) ? O_RDONLY : O_RDWR)); @@ -4249,15 +4050,6 @@ static void action_read(TrapContext *ctx, Unit *unit, dpacket *packet) if (size == 0) { PUT_PCK_RES1 (packet, 0); PUT_PCK_RES2 (packet, 0); - } else if (k->aino->vfso) { - uae_s64 filesize = k->aino->vfso->size; - for (int i = 0; i < size && k->file_pos < filesize; i++) { - trap_put_byte(ctx, addr + i, k->aino->vfso->data[k->file_pos]); - k->file_pos++; - actual++; - } - PUT_PCK_RES1 (packet, actual); - size = 0; } else { /* check if filesize < size */ uae_s64 filesize, cur; @@ -4345,7 +4137,7 @@ static void action_write(TrapContext *ctx, Unit *unit, dpacket *packet) gui_flicker_led (UNIT_LED(unit), unit->unit, 2); - if (is_writeprotected(unit) || k->aino->vfso) { + if (is_writeprotected(unit)) { PUT_PCK_RES1 (packet, DOS_FALSE); PUT_PCK_RES2 (packet, ERROR_DISK_WRITE_PROTECTED); return; @@ -4559,7 +4351,7 @@ static void action_change_mode(TrapContext *ctx, Unit *unit, dpacket *packet) * or MODE_OLDFILE/MODE_NEWFILE/MODE_READWRITE if CHANGE_FH * * Above is wrong, it is always *_LOCK. TW. */ int mode = GET_PCK_ARG3 (packet); - unsigned long uniq; + uae_u32 uniq; a_inode *a = NULL, *olda = NULL; int err = 0; @@ -4608,7 +4400,7 @@ static void action_change_mode(TrapContext *ctx, Unit *unit, dpacket *packet) } } -static void action_parent_common(TrapContext *ctx, Unit *unit, dpacket *packet, unsigned long uniq) +static void action_parent_common(TrapContext *ctx, Unit *unit, dpacket *packet, uae_u32 uniq) { a_inode *olda = lookup_aino (unit, uniq); if (olda == 0) { @@ -4739,11 +4531,6 @@ static void action_set_file_size(TrapContext *ctx, Unit *unit, dpacket *packet) PUT_PCK_RES2 (packet, ERROR_OBJECT_NOT_AROUND); return; } - if (k->aino->vfso) { - PUT_PCK_RES1 (packet, DOS_FALSE); - PUT_PCK_RES2 (packet, ERROR_DISK_WRITE_PROTECTED); - return; - } /* Fail if file is >=2G, it is not safe operation. */ if (key_filesize(k) > MAXFILESIZE32_2G) { @@ -4864,23 +4651,21 @@ static void action_delete_object(TrapContext *ctx, Unit *unit, dpacket *packet) PUT_PCK_RES2 (packet, ERROR_OBJECT_IN_USE); return; } - if (!a->vfso) { - if (a->dir) { - /* This should take care of removing the fsdb if no files remain. */ - fsdb_dir_writeback (a); - if (my_rmdir (a->nname) == -1) { - PUT_PCK_RES1 (packet, DOS_FALSE); - PUT_PCK_RES2 (packet, dos_errno()); - return; - } - } else { - if (my_unlink (a->nname) == -1) { - PUT_PCK_RES1 (packet, DOS_FALSE); - PUT_PCK_RES2 (packet, dos_errno()); - return; - } - } - } + if (a->dir) { + /* This should take care of removing the fsdb if no files remain. */ + fsdb_dir_writeback (a); + if (my_rmdir (a->nname) == -1) { + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, dos_errno()); + return; + } + } else { + if (my_unlink (a->nname) == -1) { + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, dos_errno()); + return; + } + } notify_check(ctx, unit, a); updatedirtime (a, 1); if (a->child != 0) { @@ -4914,12 +4699,10 @@ static void action_set_date(TrapContext *ctx, Unit *unit, dpacket *packet) PUT_PCK_RES2 (packet, err); return; } - if (!a->vfso) { - amiga_to_timeval (&tv, trap_get_long(ctx, date), trap_get_long(ctx, date + 4), trap_get_long(ctx, date + 8), 50); - //write_log (_T("%llu.%u (%d,%d,%d) %s\n"), tv.tv_sec, tv.tv_usec, trap_get_long(ctx, date), trap_get_long(ctx, date + 4), trap_get_long(ctx, date + 8), a->nname); - if (!my_utime (a->nname, &tv)) - err = dos_errno (); - } + amiga_to_timeval (&tv, trap_get_long(ctx, date), trap_get_long(ctx, date + 4), trap_get_long(ctx, date + 8), 50); + //write_log (_T("%llu.%u (%d,%d,%d) %s\n"), tv.tv_sec, tv.tv_usec, trap_get_long(ctx, date), trap_get_long(ctx, date + 4), trap_get_long(ctx, date + 8), a->nname); + if (!my_utime (a->nname, &tv)) + err = dos_errno (); if (err != 0) { PUT_PCK_RES1 (packet, DOS_FALSE); PUT_PCK_RES2 (packet, err); @@ -4990,24 +4773,22 @@ static void action_rename_object(TrapContext *ctx, Unit *unit, dpacket *packet) return; } - if (!a1->vfso) { - if (-1 == my_rename (a1->nname, a2->nname)) { - int ret = -1; - /* maybe we have open file handles that caused failure? */ - write_log (_T("rename '%s' -> '%s' failed, trying relocking..\n"), a1->nname, a2->nname); - wehavekeys = relock_do(unit, a1); - /* try again... */ - ret = my_rename (a1->nname, a2->nname); - /* restore locks */ - relock_re(unit, a1, a2, ret == -1 ? 1 : 0); - if (ret == -1) { - delete_aino (unit, a2); - PUT_PCK_RES1 (packet, DOS_FALSE); - PUT_PCK_RES2 (packet, dos_errno ()); - return; - } + if (-1 == my_rename (a1->nname, a2->nname)) { + int ret = -1; + /* maybe we have open file handles that caused failure? */ + write_log (_T("rename '%s' -> '%s' failed, trying relocking..\n"), a1->nname, a2->nname); + wehavekeys = relock_do(unit, a1); + /* try again... */ + ret = my_rename (a1->nname, a2->nname); + /* restore locks */ + relock_re(unit, a1, a2, ret == -1 ? 1 : 0); + if (ret == -1) { + delete_aino (unit, a2); + PUT_PCK_RES1 (packet, DOS_FALSE); + PUT_PCK_RES2 (packet, dos_errno ()); + return; } - } + } notify_check(ctx, unit, a1); notify_check(ctx, unit, a2); @@ -5020,7 +4801,6 @@ static void action_rename_object(TrapContext *ctx, Unit *unit, dpacket *packet) a2->has_dbentry = a1->has_dbentry; a2->db_offset = a1->db_offset; a2->dirty = 0; - a2->vfso = a1->vfso; move_exkeys (unit, a1, a2); move_aino_children (unit, a1, a2); delete_aino (unit, a1); @@ -5190,7 +4970,7 @@ static void action_change_file_position64(TrapContext *ctx, Unit *unit, dpacket Key *k = lookup_key (unit, GET_PCK64_ARG1 (packet)); uae_s64 pos = GET_PCK64_ARG2 (packet); int mode = (uae_s32)GET_PCK64_ARG3 (packet); - long whence = SEEK_CUR; + uae_s32 whence = SEEK_CUR; uae_s64 res, cur; PUT_PCK64_RES0 (packet, DP64_INIT); @@ -5394,7 +5174,7 @@ static void action_seek64(TrapContext *ctx, Unit *unit, dpacket *packet) Key *k = lookup_key(unit, GET_PCK_ARG1(packet)); uae_s64 pos = get_quadp(ctx, GET_PCK64_ARG2(packet)); int mode = GET_PCK_ARG3(packet); - long whence = SEEK_CUR; + uae_s32 whence = SEEK_CUR; uae_s64 res, cur; if (k == 0) { @@ -5787,7 +5567,6 @@ static int filesys_iteration(UnitInfo *ui) readdpacket(ctx, &packet, pck); int isvolume = 0; -#if TRAPMD trapmd md[] = { { TRAPCMD_GET_LONG, { morelocks }, 2, 0 }, { TRAPCMD_GET_LONG, { ui->self->locklist }, 2, 1 }, @@ -5800,13 +5579,6 @@ static int filesys_iteration(UnitInfo *ui) if (ui->self->volume) { isvolume = md[4].params[0] || ui->self->ui.unknown_media; } -#else - trap_put_long(ctx, trap_get_long(ctx, morelocks), trap_get_long(ctx, ui->self->locklist)); - trap_put_long(ctx, ui->self->locklist, morelocks); - if (ui->self->volume) { - isvolume = trap_get_byte(ctx, ui->self->volume + 64) || ui->self->ui.unknown_media; - } -#endif int ret = handle_packet(ctx, ui->self, &packet, msg, isvolume); if (!ret) { @@ -5846,7 +5618,7 @@ static int filesys_iteration(UnitInfo *ui) } -static void *filesys_thread (void *unit_v) +static int filesys_thread (void *unit_v) { UnitInfo *ui = (UnitInfo *)unit_v; @@ -5884,7 +5656,6 @@ static uae_u32 REGPARAM2 filesys_handler (TrapContext *ctx) goto error; /* Get two more locks and hand them over to the other thread. */ -#if TRAPMD struct trapmd md[] = { // morelocks = trap_get_long(ctx, trap_get_areg(ctx, 3)); /* 0 */ { TRAPCMD_GET_LONG, { trap_get_areg(ctx, 3) }, 1, 0 }, @@ -5905,16 +5676,6 @@ static uae_u32 REGPARAM2 filesys_handler (TrapContext *ctx) }; trap_multi(ctx, md, sizeof md / sizeof(struct trapmd)); morelocks = md[0].params[0]; -#else - uae_u32 morelocksptr; - morelocks = trap_get_long(ctx, trap_get_areg(ctx, 3)); - morelocksptr = trap_get_long(ctx, morelocks); - trap_put_long(ctx, trap_get_areg(ctx, 3), trap_get_long(ctx, morelocksptr)); - trap_put_long(ctx, morelocksptr, 0); - - /* The packet wasn't processed yet. */ - trap_put_long(ctx, message_addr + 4, 0); -#endif write_comm_pipe_pvoid(unit->ui.unit_pipe, ctx, 0); write_comm_pipe_u32 (unit->ui.unit_pipe, packet_addr, 0); @@ -5958,7 +5719,7 @@ void filesys_start_threads (void) } } -void filesys_free_handles(void) +static void filesys_free_handles(void) { Unit *u, *u1; for (u = units; u; u = u1) { @@ -6006,7 +5767,6 @@ void filesys_reset (void) { if (isrestore ()) return; - load_injected_icons(); filesys_reset2 (); initialize_mountinfo(); } @@ -6226,15 +5986,15 @@ static uae_u32 REGPARAM2 filesys_diagentry (TrapContext *ctx) baseaddr = filesys_bank.baseaddr; resaddr += 0x10; - put_long_host(baseaddr + 0x2100, EXPANSION_explibname); - put_long_host(baseaddr + 0x2104, filesys_configdev); - put_long_host(baseaddr + 0x2108, EXPANSION_doslibname); - put_word_host(baseaddr + 0x210c, 0); - put_word_host(baseaddr + 0x210e, nr_units()); - put_word_host(baseaddr + 0x2110, 0); - put_word_host(baseaddr + 0x2112, 1); - - native2amiga_startup(); + if (baseaddr) { + put_long_host(baseaddr + 0x2100, EXPANSION_explibname); + put_long_host(baseaddr + 0x2104, filesys_configdev); + put_long_host(baseaddr + 0x2108, EXPANSION_doslibname); + put_word_host(baseaddr + 0x210c, 0); + put_word_host(baseaddr + 0x210e, nr_units()); + put_word_host(baseaddr + 0x2110, 0); + put_word_host(baseaddr + 0x2112, 1); + } write_log (_T("filesystem: diagentry %08x configdev %08x\n"), resaddr, filesys_configdev); @@ -6295,7 +6055,7 @@ static uae_u32 REGPARAM2 filesys_diagentry (TrapContext *ctx) putmsg_hack_filesystemtask = 0; ks12hack_deviceproc = 0; - if (KS12_BOOT_HACK && nr_units() && filesys_configdev == 0) { + if (KS12_BOOT_HACK && nr_units() && filesys_configdev == 0 && baseaddr) { resaddr_hack = resaddr; putmsg_hack_state = -1; if (uip[0].bootpri > -128) { @@ -7037,8 +6797,8 @@ static void addfakefilesys (TrapContext *ctx, uaecptr parmpacket, uae_u32 dostyp trap_put_long(ctx, parmpacket + PP_FSHDSTART + 12 + 4 * 4, ci->stacksize); flags |= 0x10; - if (ci->priority != -129) { - trap_put_long(ctx, parmpacket + PP_FSHDSTART + 12 + 5 * 4, ci->priority); + if (ci->bootpri != -129) { + trap_put_long(ctx, parmpacket + PP_FSHDSTART + 12 + 5 * 4, ci->bootpri); flags |= 0x20; } trap_put_long(ctx, parmpacket + PP_FSHDSTART + 12 + 8 * 4, dostype == DISK_TYPE_DOS || bcplonlydos() ? 0 : -1); // globvec @@ -7106,7 +6866,7 @@ static int dofakefilesys (TrapContext *ctx, UnitInfo *uip, uaecptr parmpacket, s tmp[0] = 0; if (uip->filesysdir && _tcslen (uip->filesysdir) > 0) { - _tcscpy (tmp, uip->filesysdir); + cfgfile_resolve_path_out_load(uip->filesysdir, tmp, MAX_DPATH, PATH_HDF); } else if ((dostype & 0xffffff00) == DISK_TYPE_DOS) { _tcscpy (tmp, currprefs.romfile); int i = _tcslen (tmp); @@ -7211,13 +6971,19 @@ static int dofakefilesys (TrapContext *ctx, UnitInfo *uip, uaecptr parmpacket, s } /* Fill in per-unit fields of a parampacket */ -static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) +static uae_u32 REGPARAM2 filesys_dev_storeinfo (TrapContext *ctx) { - UnitInfo *uip = mountinfo.ui; int no = trap_get_dreg(ctx, 6) & 0x7fffffff; - int unit_no = no & 65535; - int sub_no = no >> 16; - int type; + int unit_no = no & 65535; + int sub_no = no >> 16; + int type; + + if (unit_no >= MAX_FILESYSTEM_UNITS) + return -2; + if (sub_no >= MAX_FILESYSTEM_UNITS) + return -2; + + UnitInfo *uip = mountinfo.ui; uaecptr parmpacket = trap_get_areg(ctx, 0); struct uaedev_config_info *ci = &uip[unit_no].hf.ci; @@ -7228,16 +6994,16 @@ static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) trap_put_long(ctx, parmpacket + PP_ADDTOFSRES, 0); trap_put_long(ctx, parmpacket + PP_FSSIZE, 0); - gui_flicker_led(LED_HD, unit_no, 0); - type = is_hardfile(unit_no); + gui_flicker_led (LED_HD, unit_no, 0); + type = is_hardfile (unit_no); if (type == FILESYS_HARDFILE_RDB) { /* RDB hardfile */ uip[unit_no].devno = uip[unit_no].hf.ci.controller_unit; - return rdb_mount(ctx, &uip[unit_no], unit_no, sub_no, parmpacket); + return rdb_mount (ctx, &uip[unit_no], unit_no, sub_no, parmpacket); } - if (sub_no) - return -2; - write_log(_T("Mounting uaehf.device:%d %d (%d):\n"), uip->hf.ci.controller_unit, unit_no, sub_no); + if (sub_no) + return -2; + write_log (_T("Mounting uaehf.device:%d %d (%d):\n"), uip->hf.ci.controller_unit, unit_no, sub_no); get_new_device(ctx, type, parmpacket, &uip[unit_no].devname, &uip[unit_no].devname_amiga, unit_no); uip[unit_no].devno = uip[unit_no].hf.ci.controller_unit; trap_put_long(ctx, parmpacket, uip[unit_no].devname_amiga); @@ -7253,23 +7019,22 @@ static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) trap_put_long(ctx, parmpacket + 72, 0xFFFFFFFE); /* dma mask */ trap_put_long(ctx, parmpacket + 76, uip[unit_no].bootpri); /* bootPri */ if (type == FILESYS_VIRTUAL) { - // generate some sane-looking geometry if some program really cares.. - uae_s64 hicyl = 100; - uae_u32 heads = 16; - if (currprefs.filesys_limit) { - hicyl = ((currprefs.filesys_limit * 1024) / 512) / (heads * 127); - } - else { - struct fs_usage fsu; - if (!get_fs_usage(uip[unit_no].rootdir, 0, &fsu)) { - for (;;) { - hicyl = (fsu.total / 512) / (heads * 127); - if (hicyl < 65536 || heads == 64) - break; - heads *= 2; + // generate some sane-looking geometry if some program really cares.. + uae_s64 hicyl = 100; + uae_u32 heads = 16; + if (currprefs.filesys_limit) { + hicyl = ((currprefs.filesys_limit * 1024) / 512) / (heads * 127); + } else { + struct fs_usage fsu; + if (!get_fs_usage(uip[unit_no].rootdir, 0, &fsu)) { + for (;;) { + hicyl = (fsu.total / 512) / (heads * 127); + if (hicyl < 65536 || heads == 64) + break; + heads *= 2; + } } } - } trap_put_long(ctx, parmpacket + 4, fsdevname); trap_put_long(ctx, parmpacket + 20, 512 >> 2); /* longwords per block */ trap_put_long(ctx, parmpacket + 28, heads); /* heads */ @@ -7278,9 +7043,8 @@ static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) trap_put_long(ctx, parmpacket + 40, 2); /* reserved blocks */ trap_put_long(ctx, parmpacket + 52, 1); /* lowCyl */ trap_put_long(ctx, parmpacket + 56, (uae_u32)hicyl); /* hiCyl */ - trap_put_long(ctx, parmpacket + 80, DISK_TYPE_DOS); /* DOS\0 */ - } - else { + trap_put_long(ctx, parmpacket + 80, DISK_TYPE_DOS); /* DOS\0 */ + } else { uae_u8 buf[512]; trap_put_long(ctx, parmpacket + 4, ROM_hardfile_resname); trap_put_long(ctx, parmpacket + 20, ci->blocksize >> 2); /* longwords per block */ @@ -7299,9 +7063,8 @@ static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) memset(buf, 0, sizeof buf); if (ci->dostype) { // forced dostype? trap_put_long(ctx, parmpacket + 80, ci->dostype); /* dostype */ - } - else if (hdf_read(&uip[unit_no].hf, buf, 0, sizeof buf)) { - uae_u32 dt = rl(buf); + } else if (hdf_read (&uip[unit_no].hf, buf, 0, sizeof buf)) { + uae_u32 dt = rl (buf); if (dt != 0x00000000 && dt != 0xffffffff) trap_put_long(ctx, parmpacket + 80, dt); } @@ -7315,12 +7078,12 @@ static uae_u32 REGPARAM2 filesys_dev_storeinfo(TrapContext *ctx) buf[i + 128] = trap_get_byte(ctx, parmpacket + 16 + i); } if (type == FILESYS_HARDFILE) - type = dofakefilesys(ctx, &uip[unit_no], parmpacket, ci); - if (uip[unit_no].bootpri < -127 || (type == FILESYS_HARDFILE && ci->rootdir[0] == 0)) - trap_set_dreg(ctx, 7, trap_get_dreg(ctx, 7) & ~1); /* do not boot */ - if (uip[unit_no].bootpri < -128) - return -1; /* do not mount */ - return type; + type = dofakefilesys (ctx, &uip[unit_no], parmpacket, ci); + if (uip[unit_no].bootpri < -127 || (type == FILESYS_HARDFILE && ci->rootdir[0] == 0)) + trap_set_dreg(ctx, 7, trap_get_dreg(ctx, 7) & ~1); /* do not boot */ + if (uip[unit_no].bootpri < -128) + return -1; /* do not mount */ + return type; } static uae_u32 REGPARAM2 mousehack_done (TrapContext *ctx) @@ -7331,19 +7094,6 @@ static uae_u32 REGPARAM2 mousehack_done (TrapContext *ctx) uaecptr dispinfo = trap_get_areg(ctx, 3); uaecptr vp = trap_get_areg(ctx, 4); return input_mousehack_status(ctx, mode, diminfo, dispinfo, vp, trap_get_dreg(ctx, 2)); - } else if (mode == 10) { - } else if (mode == 11) { - } else if (mode == 12) { - return 0; - } else if (mode == 13) { - return 0; - } else if (mode == 14) { - } else if (mode == 15) { - } else if (mode == 16) { - uaecptr a2 = trap_get_areg(ctx, 2); - input_mousehack_mouseoffset (a2); - } else if (mode == 17) { - return 0; } else if (mode == 18) { put_long_host(rtarea_bank.baseaddr + RTAREA_EXTERTASK, trap_get_dreg(ctx, 0)); put_long_host(rtarea_bank.baseaddr + RTAREA_TRAPTASK, trap_get_dreg(ctx, 2)); @@ -7355,9 +7105,6 @@ static uae_u32 REGPARAM2 mousehack_done (TrapContext *ctx) } else if (mode == 20) { // boot rom copy done return 0; - } else if (mode == 21) { - // keymap hook - return 1; } else { write_log (_T("Unknown mousehack hook %d\n"), mode); } @@ -7425,10 +7172,10 @@ void filesys_install (void) uae_sem_init (&singlethread_int_sem, 0, 1); - ROM_filesys_resname = ds_ansi ("UAEfs.resource"); - ROM_filesys_resid = ds_ansi (UAEFS_VERSION); + ds_ansi ("UAEfs.resource"); + ds_ansi (UAEFS_VERSION); - fsdevname = ds_ansi ("uae.device"); /* does not really exist */ + fsdevname = ROM_hardfile_resname; fshandlername = ds_bstr_ansi ("uaefs"); afterdos_name = ds_ansi("UAE afterdos"); @@ -7474,7 +7221,7 @@ void filesys_install (void) dw (RTS); org (rtarea_base + 0xFF38); - calltrap (deftrap2 (mousehack_done, 0, _T("mousehack_done"))); + calltrap (deftrapres(mousehack_done, 0, _T("misc_funcs"))); dw (RTS); org (rtarea_base + 0xFF40); @@ -7497,10 +7244,6 @@ void filesys_install (void) calltrap(deftrap2(filesys_bcpl_wrapper, 0, _T("filesys_bcpl_wrapper"))); dw(RTS); - org(rtarea_base + 0xFF78); - calltrap(deftrap2(debugger_helper, 0, _T("debugger_helper"))); - dw(RTS); - org (loop); create_ks12_boot(); @@ -7526,6 +7269,35 @@ void filesys_install_code (void) b = bootrom_start + bootrom_header + 3 * 4 - 4; filesys_initcode = bootrom_start + dlg (b) + bootrom_header - 4; afterdos_initcode = filesys_get_entry(8); + + // Fill struct resident + TCHAR buf[256]; + TCHAR *s = au(UAEFS_VERSION); + int y, m, d; + target_getdate(&y, &m, &d); + _stprintf(buf, _T("%s (%d.%d.%d)\r\n"), s, d, m, y); + uaecptr idstring = ds(buf); + xfree(s); + + b = here(); + items = dlg(bootrom_start) * 2; + for (int i = 0; i < items; i += 2) { + if (((dbg(bootrom_start + i + 0) << 8) | (dbg(bootrom_start + i + 1) << 0)) == 0x4afc) { + org(bootrom_start + i + 2); + dl(bootrom_start + i); + dl(dlg(here()) + bootrom_start + i); // endskip + db(0); // flags + db(1); // version + db(0); // type + db(0); // pri + dl(dlg(here()) + bootrom_start + i); // name + dl(idstring); // idstring + dl(dlg(here()) + bootrom_start + i); // init + break; + } + } + org(b); + } #ifdef _WIN32 @@ -8079,6 +7851,9 @@ static uae_u8 *save_filesys_virtual (UnitInfo *ui, uae_u8 *dst) return dst; } + +static TCHAR *new_filesys_root_path, *new_filesys_fs_path; + uae_u8 *save_filesys_common (int *len) { uae_u8 *dstbak, *dst; @@ -8100,14 +7875,49 @@ uae_u8 *restore_filesys_common (uae_u8 *src) filesys_reset2 (); a_uniq = restore_u64 (); key_uniq = restore_u64 (); + + xfree(new_filesys_root_path); + xfree(new_filesys_fs_path); + new_filesys_root_path = NULL; + new_filesys_fs_path = NULL; return src; } +uae_u8 *save_filesys_paths(int num, int *len) +{ + uae_u8 *dstbak, *dst; + UnitInfo *ui; + int type = is_hardfile(num); + int ptype; + + ui = &mountinfo.ui[num]; + if (ui->open <= 0) + return NULL; + dstbak = dst = xmalloc(uae_u8, 4 + 4 + 2 + 2 * 2 * MAX_DPATH); + + if (type == FILESYS_VIRTUAL) + ptype = SAVESTATE_PATH_VDIR; + else if (type == FILESYS_HARDFILE || type == FILESYS_HARDFILE_RDB) + ptype = SAVESTATE_PATH_HDF; + else + ptype = SAVESTATE_PATH; + + save_u32(0); + save_u32(ui->devno); + save_u16(type); + save_path_full(ui->rootdir, ptype); + save_path_full(ui->filesysdir, SAVESTATE_PATH); + + *len = dst - dstbak; + return dstbak; +} + uae_u8 *save_filesys (int num, int *len) { uae_u8 *dstbak, *dst; UnitInfo *ui; int type = is_hardfile (num); + int ptype; ui = &mountinfo.ui[num]; if (ui->open <= 0) @@ -8121,11 +7931,12 @@ uae_u8 *save_filesys (int num, int *len) save_u32 (ui->devno); save_u16 (type); if (type == FILESYS_VIRTUAL) - save_path (ui->rootdir, SAVESTATE_PATH_VDIR); + ptype = SAVESTATE_PATH_VDIR; else if (type == FILESYS_HARDFILE || type == FILESYS_HARDFILE_RDB) - save_path (ui->rootdir, SAVESTATE_PATH_HDF); + ptype = SAVESTATE_PATH_HDF; else - save_path (ui->rootdir, SAVESTATE_PATH); + ptype = SAVESTATE_PATH; + save_path(ui->rootdir, ptype); save_string (ui->devname); save_string (ui->volname); save_path (ui->filesysdir, SAVESTATE_PATH); @@ -8141,6 +7952,16 @@ uae_u8 *save_filesys (int num, int *len) return dstbak; } +uae_u8 *restore_filesys_paths(uae_u8 *src) +{ + restore_u32(); + restore_u32(); + restore_u16(); + new_filesys_root_path = restore_path_full(); + new_filesys_fs_path = restore_path_full(); + return src; +} + uae_u8 *restore_filesys (uae_u8 *src) { int type, devno; @@ -8150,7 +7971,7 @@ uae_u8 *restore_filesys (uae_u8 *src) struct uaedev_config_info *ci; if (restore_u32 () != 2) - return src; + goto end2; devno = restore_u32 (); ui = &mountinfo.ui[devno]; ci = &ui->hf.ci; @@ -8170,6 +7991,18 @@ uae_u8 *restore_filesys (uae_u8 *src) ci->readonly = restore_u8 () != 0; startup = restore_u32 (); filesys_configdev = restore_u32 (); + + if (new_filesys_root_path) { + xfree(rootdir); + rootdir = new_filesys_root_path; + new_filesys_root_path = NULL; + } + if (new_filesys_fs_path) { + xfree(filesysdir); + filesysdir = new_filesys_fs_path; + new_filesys_fs_path = NULL; + } + if (type == FILESYS_HARDFILE || type == FILESYS_HARDFILE_RDB) { src = restore_filesys_hardfile(ui, src); xfree (volname); @@ -8180,7 +8013,7 @@ uae_u8 *restore_filesys (uae_u8 *src) _tcscpy (ci->volname, volname ? volname : _T("")); _tcscpy (ci->filesys, filesysdir); - if (set_filesys_unit (devno, ci) < 0) { + if (set_filesys_unit (devno, ci, false) < 0) { write_log (_T("filesys '%s' failed to restore\n"), rootdir); goto end; } @@ -8194,12 +8027,17 @@ end: xfree (devname); xfree (volname); xfree (filesysdir); +end2: + xfree(new_filesys_root_path); + xfree(new_filesys_fs_path); + new_filesys_root_path = NULL; + new_filesys_fs_path = NULL; return src; } int save_filesys_cando(void) { - if (nr_units() == 0) - return -1; - return filesys_in_interrupt ? 0 : 1; + if (nr_units() == 0) + return -1; + return filesys_in_interrupt ? 0 : 1; } diff --git a/src/fpp.cpp b/src/fpp.cpp index 9c866189..7b7ced69 100644 --- a/src/fpp.cpp +++ b/src/fpp.cpp @@ -12,10 +12,12 @@ #include #include - -//#include "sysconfig.h" #include "sysdeps.h" +#include "options.h" +#include "memory.h" +#include "newcpu.h" +#include "fpp.h" #include "savestate.h" static void fpsr_set_exception(uae_u32 exception); @@ -97,7 +99,7 @@ static const struct fpp_cr_entry_undef fpp_cr_undef[] = { { {0x407f0000, 0x00060000, 0x00000000} } }; -uae_u32 xhex_nan[] ={0x7fff0000, 0xffffffff, 0xffffffff}; +static uae_u32 xhex_nan[] ={0x7fff0000, 0xffffffff, 0xffffffff}; static bool fpu_mmu_fixup; @@ -388,6 +390,16 @@ static void fpp_set_fpsr (uae_u32 val) #endif } +static void fpp_set_fpiar(uae_u32 val) +{ + regs.fpiar = val; +} + +static uae_u32 fpp_get_fpiar(void) +{ + return regs.fpiar; +} + static bool fpu_get_constant(fpdata *fpd, int cr) { uae_u32 f[3] = { 0, 0, 0 }; @@ -617,7 +629,7 @@ static void fp_unimp_datatype(uae_u16 opcode, uae_u16 extra, uae_u32 ea, uaecptr fsave_data.stag = 7; // undocumented } else { fpp_from_exten(src, &fsave_data.et[0], &fsave_data.et[1], &fsave_data.et[2]); - fsave_data.stag = get_ftag(src, (opclass == 0) ? -1U : size); + fsave_data.stag = get_ftag(src, (opclass == 0) ? 0xffffffff : size); if (fsave_data.stag == 5) { fsave_data.et[0] = (size == 1) ? 0x3f800000 : 0x3c000000; // exponent for denormalized single and double } @@ -1320,8 +1332,8 @@ void fpuop_dbcc (uae_u32 opcode, uae_u16 extra) if (fp_exception_pending(true)) return; - regs.fp_exception = false; + if (fault_if_no_6888x (opcode, extra, pc - 4)) return; @@ -1355,7 +1367,6 @@ void fpuop_scc (uae_u32 opcode, uae_u16 extra) if (fp_exception_pending(true)) return; - regs.fp_exception = false; if (fault_if_no_6888x (opcode, extra, pc)) @@ -1391,8 +1402,8 @@ void fpuop_trapcc (uae_u32 opcode, uaecptr oldpc, uae_u16 extra) if (fp_exception_pending(true)) return; - regs.fp_exception = false; + if (fault_if_no_fpu_u (opcode, extra, 0, oldpc)) return; @@ -1414,8 +1425,8 @@ void fpuop_bcc (uae_u32 opcode, uaecptr oldpc, uae_u32 extra) if (fp_exception_pending(true)) return; - regs.fp_exception = false; + if (fault_if_no_fpu (opcode, extra, 0, oldpc - 2)) return; @@ -1463,7 +1474,7 @@ void fpuop_save (uae_u32 opcode) if (incr < 0) ad -= 4; adp = ad; - x_put_long (ad, frame_id); + x_cp_put_long (ad, frame_id); ad += 4; } else { /* 44 (rev $40) and 52 (rev $41) byte 68040 unimplemented instruction frame */ @@ -1474,60 +1485,60 @@ void fpuop_save (uae_u32 opcode) if (incr < 0) ad -= frame_size; adp = ad; - x_put_long (ad, frame_id); + x_cp_put_long (ad, frame_id); ad += 4; if (regs.fpu_exp_state == 2) { /* BUSY frame */ - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, 0); // CU_SAVEPC (Software shouldn't care) + x_cp_put_long(ad, 0); // CU_SAVEPC (Software shouldn't care) ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, fsave_data.wbt[0]); // WBTS/WBTE + x_cp_put_long(ad, fsave_data.wbt[0]); // WBTS/WBTE ad += 4; - x_put_long(ad, fsave_data.wbt[1]); // WBTM + x_cp_put_long(ad, fsave_data.wbt[1]); // WBTM ad += 4; - x_put_long(ad, fsave_data.wbt[2]); // WBTM + x_cp_put_long(ad, fsave_data.wbt[2]); // WBTM ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, fsave_data.fpiarcu); // FPIARCU (same as FPU PC or something else?) + x_cp_put_long(ad, fsave_data.fpiarcu); // FPIARCU (same as FPU PC or something else?) ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; - x_put_long(ad, 0); + x_cp_put_long(ad, 0); ad += 4; } if (fpu_version >= 0x41 || regs.fpu_exp_state == 2) { - x_put_long(ad, fsave_data.cmdreg3b << 16); // CMDREG3B + x_cp_put_long(ad, fsave_data.cmdreg3b << 16); // CMDREG3B ad += 4; - x_put_long (ad, 0); + x_cp_put_long (ad, 0); ad += 4; } - x_put_long (ad, (fsave_data.stag << 29) | (fsave_data.wbtm66 << 26) | (fsave_data.grs << 23)); // STAG + x_cp_put_long (ad, (fsave_data.stag << 29) | (fsave_data.wbtm66 << 26) | (fsave_data.grs << 23)); // STAG ad += 4; - x_put_long (ad, fsave_data.cmdreg1b << 16); // CMDREG1B + x_cp_put_long (ad, fsave_data.cmdreg1b << 16); // CMDREG1B ad += 4; - x_put_long (ad, (fsave_data.dtag << 29) | (fsave_data.wbte15 << 20)); // DTAG + x_cp_put_long (ad, (fsave_data.dtag << 29) | (fsave_data.wbte15 << 20)); // DTAG ad += 4; - x_put_long (ad, (fsave_data.e1 << 26) | (fsave_data.e3 << 25) | (fsave_data.t << 20)); + x_cp_put_long (ad, (fsave_data.e1 << 26) | (fsave_data.e3 << 25) | (fsave_data.t << 20)); ad += 4; - x_put_long(ad, fsave_data.fpt[0]); // FPTS/FPTE + x_cp_put_long(ad, fsave_data.fpt[0]); // FPTS/FPTE ad += 4; - x_put_long(ad, fsave_data.fpt[1]); // FPTM + x_cp_put_long(ad, fsave_data.fpt[1]); // FPTM ad += 4; - x_put_long(ad, fsave_data.fpt[2]); // FPTM + x_cp_put_long(ad, fsave_data.fpt[2]); // FPTM ad += 4; - x_put_long(ad, fsave_data.et[0]); // ETS/ETE + x_cp_put_long(ad, fsave_data.et[0]); // ETS/ETE ad += 4; - x_put_long(ad, fsave_data.et[1]); // ETM + x_cp_put_long(ad, fsave_data.et[1]); // ETM ad += 4; - x_put_long(ad, fsave_data.et[2]); // ETM + x_cp_put_long(ad, fsave_data.et[2]); // ETM ad += 4; } } else { /* 68881/68882 */ @@ -1547,26 +1558,26 @@ void fpuop_save (uae_u32 opcode) if (incr < 0) ad -= frame_size; adp = ad; - x_put_long(ad, frame_id); // frame id + x_cp_put_long(ad, frame_id); // frame id ad += 4; if (regs.fpu_state != 0) { // idle frame - x_put_long(ad, fsave_data.ccr); // command/condition register + x_cp_put_long(ad, fsave_data.ccr); // command/condition register ad += 4; if(currprefs.fpu_model == 68882) { for(i = 0; i < 32; i += 4) { - x_put_long(ad, 0x00000000); // internal + x_cp_put_long(ad, 0x00000000); // internal ad += 4; } } - x_put_long(ad, fsave_data.eo[0]); // exceptional operand hi + x_cp_put_long(ad, fsave_data.eo[0]); // exceptional operand hi ad += 4; - x_put_long(ad, fsave_data.eo[1]); // exceptional operand mid + x_cp_put_long(ad, fsave_data.eo[1]); // exceptional operand mid ad += 4; - x_put_long(ad, fsave_data.eo[2]); // exceptional operand lo + x_cp_put_long(ad, fsave_data.eo[2]); // exceptional operand lo ad += 4; - x_put_long(ad, 0x00000000); // operand register + x_cp_put_long(ad, 0x00000000); // operand register ad += 4; - x_put_long(ad, biu_flags); // biu flags + x_cp_put_long(ad, biu_flags); // biu flags ad += 4; } } @@ -1606,7 +1617,7 @@ void fpuop_restore (uae_u32 opcode) // FRESTORE does not support predecrement - d = x_get_long (ad); + d = x_cp_get_long (ad); frame_version = (d >> 24) & 0xff; @@ -1623,32 +1634,32 @@ retry: uae_u32 tmp, v, opclass, cmdreg1b, fpte15, et15, cusavepc; ad += 0x4; // offset to CU_SAVEPC field - tmp = x_get_long (ad); + tmp = x_cp_get_long (ad); cusavepc = tmp >> 24; ad += 0x20; // offset to FPIARCU field - regs.fpiar = x_get_long (ad); + regs.fpiar = x_cp_get_long (ad); ad += 0x14; // offset to ET15 field - tmp = x_get_long (ad); + tmp = x_cp_get_long (ad); et15 = (tmp & 0x10000000) >> 28; ad += 0x4; // offset to CMDREG1B field - fsave_data.cmdreg1b = x_get_long (ad); + fsave_data.cmdreg1b = x_cp_get_long (ad); fsave_data.cmdreg1b >>= 16; cmdreg1b = fsave_data.cmdreg1b; ad += 0x4; // offset to FPTE15 field - tmp = x_get_long (ad); + tmp = x_cp_get_long (ad); fpte15 = (tmp & 0x10000000) >> 28; ad += 0x8; // offset to FPTE field - fsave_data.fpt[0] = x_get_long (ad); + fsave_data.fpt[0] = x_cp_get_long (ad); ad += 0x4; - fsave_data.fpt[1] = x_get_long (ad); + fsave_data.fpt[1] = x_cp_get_long (ad); ad += 0x4; - fsave_data.fpt[2] = x_get_long (ad); + fsave_data.fpt[2] = x_cp_get_long (ad); ad += 0x4; // offset to ET field - fsave_data.et[0] = x_get_long (ad); + fsave_data.et[0] = x_cp_get_long (ad); ad += 0x4; - fsave_data.et[1] = x_get_long (ad); + fsave_data.et[1] = x_cp_get_long (ad); ad += 0x4; - fsave_data.et[2] = x_get_long (ad); + fsave_data.et[2] = x_cp_get_long (ad); ad += 0x4; opclass = (cmdreg1b >> 13) & 0x7; // just to be sure @@ -1706,19 +1717,20 @@ retry: regs.fpu_state = 1; if (frame_size == 0x18 || frame_size == 0x38) { // idle - fsave_data.ccr = x_get_long (ad); + + fsave_data.ccr = x_cp_get_long (ad); ad += 4; // 68882 internal registers (32 bytes, unused) ad += frame_size - 24; - fsave_data.eo[0] = x_get_long (ad); + fsave_data.eo[0] = x_cp_get_long (ad); ad += 4; - fsave_data.eo[1] = x_get_long (ad); + fsave_data.eo[1] = x_cp_get_long (ad); ad += 4; - fsave_data.eo[2] = x_get_long (ad); + fsave_data.eo[2] = x_cp_get_long (ad); ad += 4; // operand register (unused) ad += 4; - biu_flags = x_get_long (ad); + biu_flags = x_cp_get_long (ad); ad += 4; if ((biu_flags & 0x08000000) == 0x00000000) { @@ -1770,9 +1782,9 @@ static uaecptr fmovem2mem (uaecptr ad, uae_u32 list, int incr, int regdir) fpp_from_exten(®s.fp[reg], &wrd1, &wrd2, &wrd3); if (incr < 0) ad -= 3 * 4; - x_put_long(ad + 0, wrd1); - x_put_long(ad + 4, wrd2); - x_put_long(ad + 8, wrd3); + x_cp_put_long(ad + 0, wrd1); + x_cp_put_long(ad + 4, wrd2); + x_cp_put_long(ad + 8, wrd3); if (incr > 0) ad += 3 * 4; } @@ -1794,9 +1806,9 @@ static uaecptr fmovem2fpp (uaecptr ad, uae_u32 list, int incr, int regdir) if (list & 0x80) { if (incr < 0) ad -= 3 * 4; - wrd1 = x_get_long (ad + 0); - wrd2 = x_get_long (ad + 4); - wrd3 = x_get_long (ad + 8); + wrd1 = x_cp_get_long (ad + 0); + wrd2 = x_cp_get_long (ad + 4); + wrd3 = x_cp_get_long (ad + 8); if (incr > 0) ad += 3 * 4; fpp_to_exten (®s.fp[reg], wrd1, wrd2, wrd3); @@ -2030,7 +2042,7 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) regs.fpiar = pc; fpsr_clear_status(); src = regs.fp[(extra >> 7) & 7]; - v = put_fp_value (&src, opcode, extra, pc, & ad); + v = put_fp_value(&src, opcode, extra, pc, static_cast(& ad)); if (v <= 0) { if (v == 0) fpu_noinst (opcode, pc); @@ -2060,14 +2072,14 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) if (extra & 0x0800) m68k_dreg (regs, opcode & 7) = fpp_get_fpsr (); if ((extra & 0x0400) || !bits) - m68k_dreg (regs, opcode & 7) = regs.fpiar; + m68k_dreg (regs, opcode & 7) = fpp_get_fpiar(); } else { if (extra & 0x1000) fpp_set_fpcr(m68k_dreg (regs, opcode & 7)); if (extra & 0x0800) fpp_set_fpsr(m68k_dreg (regs, opcode & 7)); if ((extra & 0x0400) || !bits) - regs.fpiar = m68k_dreg (regs, opcode & 7); + fpp_set_fpiar(m68k_dreg (regs, opcode & 7)); } } else if ((opcode & 0x38) == 0x08) { // An @@ -2104,7 +2116,7 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) if (extra & 0x0800) fpp_set_fpsr(ext[1]); if (extra & 0x0400) - regs.fpiar = ext[2]; + fpp_set_fpiar(ext[2]); } else { // immediate as destination fpu_noinst (opcode, pc); @@ -2145,7 +2157,7 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) ad += 4; } if (extra & 0x0400) { - x_cp_put_long (ad, regs.fpiar); + x_cp_put_long(ad, fpp_get_fpiar()); ad += 4; } ad -= incr; @@ -2183,7 +2195,7 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) ad += 4; } if (extra & 0x0400) { - regs.fpiar = x_cp_get_long (ad); + fpp_set_fpiar(x_cp_get_long (ad)); ad += 4; } if ((opcode & 0x38) == 0x18) @@ -2279,7 +2291,7 @@ static void fpuop_arithmetic2 (uae_u32 opcode, uae_u16 extra) fpsr_clear_status(); - v = get_fp_value (opcode, extra, &src, pc, &ad); + v = get_fp_value(opcode, extra, &src, pc, static_cast(& ad)); if (v <= 0) { if (v == 0) fpu_noinst (opcode, pc); @@ -2326,15 +2338,15 @@ void fpuop_arithmetic (uae_u32 opcode, uae_u16 extra) void fpu_reset (void) { - currprefs.fpu_mode = changed_prefs.fpu_mode; #if defined(CPU_i386) || defined(CPU_x86_64) init_fpucw_x87(); #endif - regs.fpiar = 0; regs.fpu_exp_state = 0; + regs.fp_unimp_pend = 0; fpp_set_fpcr (0); fpp_set_fpsr (0); + fpp_set_fpiar (0); // reset precision fpp_set_mode(0x00000080 | 0x00000010); fpp_set_mode(0x00000000); diff --git a/src/fsdb.cpp b/src/fsdb.cpp index f487ad07..6a6fea3c 100644 --- a/src/fsdb.cpp +++ b/src/fsdb.cpp @@ -26,14 +26,7 @@ * Offset 519, 81 bytes, comment */ -#define TRACING_ENABLED 0 -#if TRACING_ENABLED -#define TRACE(x) do { write_log x; } while(0) -#else -#define TRACE(x) -#endif - -TCHAR *nname_begin (TCHAR *nname) +static TCHAR *nname_begin (TCHAR *nname) { TCHAR *p = _tcsrchr (nname, FSDB_DIR_SEPARATOR); if (p) @@ -107,7 +100,6 @@ static void fsdb_fixup (FILE *f, uae_u8 *buf, int size, a_inode *base) xfree (nname); return; } - TRACE ((_T("uaefsdb '%s' deleted\n"), nname)); /* someone deleted this file/dir outside of emulation.. */ buf[0] = 0; xfree (nname); @@ -283,7 +275,6 @@ static void write_aino (FILE *f, a_inode *aino) aino->db_offset = ftell (f); fwrite (buf, 1, sizeof buf, f); aino->has_dbentry = aino->needs_dbentry; - TRACE ((_T("%d '%s' '%s' written\n"), aino->db_offset, aino->aname, aino->nname)); } /* Write back the db file for a directory. */ @@ -297,15 +288,9 @@ void fsdb_dir_writeback (a_inode *dir) uae_u8 *tmpbuf; int size, i; - TRACE ((_T("fsdb writeback %s\n"), dir->aname)); /* First pass: clear dirty bits where unnecessary, and see if any work * needs to be done. */ for (aino = dir->child; aino; aino = aino->sibling) { - /* - int old_needs_dbentry = aino->needs_dbentry || aino->has_dbentry; - aino->needs_dbentry = needs_dbentry (aino); - entries_needed |= aino->has_dbentry | aino->needs_dbentry; - */ int old_needs_dbentry = aino->has_dbentry; int need = needs_dbentry (aino); aino->needs_dbentry = need; @@ -319,12 +304,10 @@ void fsdb_dir_writeback (a_inode *dir) } if (! entries_needed) { kill_fsdb (dir); - TRACE ((_T("fsdb removed\n"))); return; } if (! changes_needed) { - TRACE ((_T("not modified\n"))); return; } @@ -332,7 +315,6 @@ void fsdb_dir_writeback (a_inode *dir) if (f == 0) { f = get_fsdb (dir, _T("w+b")); if (f == 0) { - TRACE ((_T("failed\n"))); /* This shouldn't happen... */ return; } @@ -345,7 +327,6 @@ void fsdb_dir_writeback (a_inode *dir) tmpbuf = (uae_u8 *)malloc (size); fread (tmpbuf, 1, size, f); } - TRACE ((_T("**** updating '%s' %d\n"), dir->aname, size)); for (aino = dir->child; aino; aino = aino->sibling) { if (! aino->dirty) @@ -371,7 +352,6 @@ void fsdb_dir_writeback (a_inode *dir) } write_aino (f, aino); } - TRACE ((_T("end\n"))); fclose (f); xfree (tmpbuf); } diff --git a/src/fsdb_unix.cpp b/src/fsdb_unix.cpp index 9da406bf..a71651d2 100644 --- a/src/fsdb_unix.cpp +++ b/src/fsdb_unix.cpp @@ -16,6 +16,7 @@ #include "sysdeps.h" #include "fsdb.h" +#include "uae.h" /* these are deadly (but I think allowed on the Amiga): */ #define NUM_EVILCHARS 7 @@ -77,15 +78,15 @@ int fsdb_exists (const TCHAR *nname) * native fs, fill in information about this file/directory. */ int fsdb_fill_file_attrs (a_inode *base, a_inode *aino) { - struct stat statbuf; - /* This really shouldn't happen... */ - if (stat (aino->nname, &statbuf) == -1) - return 0; - aino->dir = S_ISDIR (statbuf.st_mode) ? 1 : 0; - - aino->amigaos_mode = ((S_IXUSR & statbuf.st_mode ? 0 : A_FIBF_EXECUTE) - | (S_IWUSR & statbuf.st_mode ? 0 : A_FIBF_WRITE) - | (S_IRUSR & statbuf.st_mode ? 0 : A_FIBF_READ)); + struct stat statbuf; + /* This really shouldn't happen... */ + if (stat (aino->nname, &statbuf) == -1) + return 0; + aino->dir = S_ISDIR (statbuf.st_mode) ? 1 : 0; + + aino->amigaos_mode = ((S_IXUSR & statbuf.st_mode ? 0 : A_FIBF_EXECUTE) + | (S_IWUSR & statbuf.st_mode ? 0 : A_FIBF_WRITE) + | (S_IRUSR & statbuf.st_mode ? 0 : A_FIBF_READ)); #if defined(WIN32) || defined(AMIBERRY) // Always give execute & read permission @@ -93,7 +94,7 @@ int fsdb_fill_file_attrs (a_inode *base, a_inode *aino) aino->amigaos_mode &= ~A_FIBF_EXECUTE; aino->amigaos_mode &= ~A_FIBF_READ; #endif - return 1; + return 1; } int fsdb_set_file_attrs (a_inode *aino) @@ -102,33 +103,30 @@ int fsdb_set_file_attrs (a_inode *aino) int mode; uae_u32 mask = aino->amigaos_mode; - if (aino->vfso) - return 1; - - if (stat (aino->nname, &statbuf) == -1) - return ERROR_OBJECT_NOT_AROUND; + if (stat (aino->nname, &statbuf) == -1) + return ERROR_OBJECT_NOT_AROUND; - mode = statbuf.st_mode; + mode = statbuf.st_mode; if (mask & A_FIBF_READ) - mode &= ~S_IRUSR; + mode &= ~S_IRUSR; else - mode |= S_IRUSR; + mode |= S_IRUSR; if (mask & A_FIBF_WRITE) - mode &= ~S_IWUSR; + mode &= ~S_IWUSR; else - mode |= S_IWUSR; + mode |= S_IWUSR; if (mask & A_FIBF_EXECUTE) - mode &= ~S_IXUSR; + mode &= ~S_IXUSR; else - mode |= S_IXUSR; + mode |= S_IXUSR; chmod (aino->nname, mode); - aino->dirty = 1; - return 0; + aino->dirty = 1; + return 0; } /* Return nonzero if we can represent the amigaos_mode of AINO within the @@ -140,8 +138,6 @@ int fsdb_mode_representable_p (const a_inode *aino, int amigaos_mode) if (0 && aino->dir) return amigaos_mode == 0; - if (aino->vfso) - return 1; if (mask & A_FIBF_SCRIPT) /* script */ return 0; if ((mask & 15) == 15) /* xxxxRWED == OK */ @@ -183,7 +179,7 @@ TCHAR *fsdb_create_unique_nname (a_inode *base, const TCHAR *suggestion) /* tmpnam isn't reentrant and I don't really want to hack configure * right now to see whether tmpnam_r is available... */ for (i = 0; i < 8; i++) { - tmp[i+8] = "_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"[rand () % 63]; + tmp[i+8] = "_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"[uaerand () % 63]; } } } diff --git a/src/fsusage.cpp b/src/fsusage.cpp index f2611e5d..472ae548 100644 --- a/src/fsusage.cpp +++ b/src/fsusage.cpp @@ -90,8 +90,6 @@ int get_fs_usage (const TCHAR *path, const TCHAR *disk, struct fs_usage *fsp) #else /* ! _WIN32 */ -int statfs (); - #if HAVE_UNISTD_H # include #endif diff --git a/src/gayle.cpp b/src/gayle.cpp index 1142d927..33cd882b 100644 --- a/src/gayle.cpp +++ b/src/gayle.cpp @@ -10,13 +10,11 @@ #define MBRES_LOG 0 #define PCMCIA_LOG 0 -#include -#include -#include -#include - +#include "sysconfig.h" #include "sysdeps.h" + #include "options.h" + #include "memory.h" #include "custom.h" #include "newcpu.h" @@ -27,6 +25,7 @@ #include "threaddep/thread.h" #include "ide.h" #include "autoconf.h" +#include "devices.h" #define PCMCIA_SRAM 1 #define PCMCIA_IDE 2 @@ -51,6 +50,11 @@ DD2000 to DDFFFF A4000 IDE DE0000 to DEFFFF 64 KB Motherboard resources */ +/* A4000T NCR */ +#define NCR_OFFSET 0x40 +#define NCR_ALT_OFFSET 0x80 +#define NCR_MASK 0x3f + /* Gayle definitions from Linux drivers and preliminary Gayle datasheet */ /* PCMCIA stuff */ @@ -132,7 +136,7 @@ DE0000 to DEFFFF 64 KB Motherboard resources #define PCMCIA_IDE_ID 2 static struct ide_hdf *idedrive[TOTAL_IDE * 2]; -struct hd_hardfiledata *pcmcia_sram; +struct hd_hardfiledata *pcmcia_disk; static int pcmcia_card; static int pcmcia_readonly; @@ -146,12 +150,12 @@ static int ide_splitter; static struct ide_thread_state gayle_its; +static void gayle_reset(int hardreset); + static void pcmcia_reset (void) { memset (pcmcia_configuration, 0, sizeof pcmcia_configuration); pcmcia_configured = -1; - if (PCMCIA_LOG > 0) - write_log (_T("PCMCIA reset\n")); } static uae_u8 checkpcmciaideirq (void) @@ -184,7 +188,7 @@ static uae_u8 checkgayleideirq (void) return irq ? GAYLE_IRQ_IDE : 0; } -void rethink_gayle (void) +static void rethink_gayle (void) { int lev2 = 0; int lev6 = 0; @@ -192,8 +196,8 @@ void rethink_gayle (void) if (currprefs.cs_ide == IDE_A4000) { gayle_irq |= checkgayleideirq (); - if ((gayle_irq & GAYLE_IRQ_IDE) && !(intreq & 0x0008)) - INTREQ_0 (0x8000 | 0x0008); + if (gayle_irq & GAYLE_IRQ_IDE) + safe_interrupt_set(false); return; } @@ -218,10 +222,10 @@ void rethink_gayle (void) else lev2 = 1; } - if (lev2 && !(intreq & 0x0008)) - INTREQ_0 (0x8000 | 0x0008); - if (lev6 && !(intreq & 0x2000)) - INTREQ_0 (0x8000 | 0x2000); + if (lev2) + safe_interrupt_set(false); + if (lev6) + safe_interrupt_set(true); } static void gayle_cs_change (uae_u8 mask, int onoff) @@ -263,7 +267,7 @@ static void card_trigger (int insert) gayle_cs_change (GAYLE_CS_WR, 0); gayle_cs_change (GAYLE_CS_BSY, 0); } - rethink_gayle (); + devices_rethink_all(rethink_gayle); } static void write_gayle_cfg (uae_u8 val) @@ -303,8 +307,6 @@ static void write_gayle_cs (uae_u8 val) gayle_map_pcmcia (); /* PCMCIA disable -> enable */ card_trigger (!(gayle_cs & GAYLE_CS_DIS) ? 1 : 0); - if (PCMCIA_LOG) - write_log (_T("PCMCIA slot: %s PC=%08X\n"), !(gayle_cs & 1) ? _T("enabled") : _T("disabled"), M68K_GETPC); } } static uae_u8 read_gayle_cs (void) @@ -344,8 +346,6 @@ static uae_u32 gayle_read2 (uaecptr addr) int ide_reg; addr &= 0xffff; - if ((GAYLE_LOG > 3 && (addr != 0x2000 && addr != 0x2001 && addr != 0x3020 && addr != 0x3021 && addr != GAYLE_IRQ_1200)) || GAYLE_LOG > 5) - write_log (_T("IDE_READ %08X PC=%X\n"), addr, M68K_GETPC); if (currprefs.cs_ide <= 0) { if (addr == 0x201c) // AR1200 IDE detection hack return 0x7f; @@ -383,8 +383,6 @@ static void gayle_write2 (uaecptr addr, uae_u32 val) struct ide_hdf *ide = NULL; int ide_reg; - if ((GAYLE_LOG > 3 && (addr != 0x2000 && addr != 0x2001 && addr != 0x3020 && addr != 0x3021 && addr != GAYLE_IRQ_1200)) || GAYLE_LOG > 5) - write_log (_T("IDE_WRITE %08X=%02X PC=%X\n"), addr, (uae_u32)val & 0xff, M68K_GETPC); if (currprefs.cs_ide <= 0) return; if (currprefs.cs_ide == IDE_A600A1200) { @@ -426,19 +424,13 @@ static int gayle_read (uaecptr addr) if (addr == GAYLE_CS_1200) { v = read_gayle_cs (); got = 1; - if (PCMCIA_LOG) - write_log (_T("PCMCIA STATUS READ %08X=%02X PC=%08X\n"), oaddr, (uae_u32)v & 0xff, M68K_GETPC); } else if (addr == GAYLE_CFG_1200) { v = read_gayle_cfg (); got = 1; - if (PCMCIA_LOG) - write_log (_T("PCMCIA CONFIG READ %08X=%02X PC=%08X\n"), oaddr, (uae_u32)v & 0xff, M68K_GETPC); } } if (!got) v = gayle_read2 (addr); - if (GAYLE_LOG) - write_log (_T("GAYLE_READ %08X=%02X PC=%08X\n"), oaddr, (uae_u32)v & 0xff, M68K_GETPC); return v; } @@ -464,18 +456,12 @@ static void gayle_write (uaecptr addr, int val) if (addr == GAYLE_CS_1200) { write_gayle_cs (val); got = 1; - if (PCMCIA_LOG > 1) - write_log (_T("PCMCIA STATUS WRITE %08X=%02X PC=%08X\n"), oaddr, (uae_u32)val & 0xff, M68K_GETPC); } else if (addr == GAYLE_CFG_1200) { write_gayle_cfg (val); got = 1; - if (PCMCIA_LOG > 1) - write_log (_T("PCMCIA CONFIG WRITE %08X=%02X PC=%08X\n"), oaddr, (uae_u32)val & 0xff, M68K_GETPC); } } - if (GAYLE_LOG) - write_log (_T("GAYLE_WRITE %08X=%02X PC=%08X\n"), oaddr, (uae_u32)val & 0xff, M68K_GETPC); if (!got) gayle_write2 (addr, val); } @@ -485,7 +471,7 @@ addrbank gayle_bank = { gayle_lget, gayle_wget, gayle_bget, gayle_lput, gayle_wput, gayle_bput, default_xlate, default_check, NULL, NULL, _T("Gayle (low)"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO, S_READ, S_WRITE }; @@ -498,8 +484,6 @@ static uae_u32 REGPARAM2 gayle_lget (uaecptr addr) if (ide_reg == IDE_DATA) { v = ide_get_data (ide) << 16; v |= ide_get_data (ide); - if (GAYLE_LOG > 4) - write_log(_T("IDE_DATA_LONG %08X=%08X PC=%X\n"), addr, v, M68K_GETPC); return v; } v = gayle_wget (addr) << 16; @@ -514,8 +498,6 @@ static uae_u32 REGPARAM2 gayle_wget (uaecptr addr) ide_reg = get_gayle_ide_reg (addr, &ide); if (ide_reg == IDE_DATA) { v = ide_get_data (ide); - if (GAYLE_LOG > 4) - write_log(_T("IDE_DATA_WORD %08X=%04X PC=%X\n"), addr, v & 0xffff, M68K_GETPC); return v; } v = gayle_bget (addr) << 8; @@ -586,7 +568,7 @@ addrbank gayle2_bank = { gayle2_lget, gayle2_wget, gayle2_bget, gayle2_lput, gayle2_wput, gayle2_bput, default_xlate, default_check, NULL, NULL, _T("Gayle (high)"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO, S_READ, S_WRITE }; @@ -627,7 +609,6 @@ static void REGPARAM2 gayle2_bput (uaecptr addr, uae_u32 value) } static uae_u8 ramsey_config; -static int garyidoffset; static int gary_coldboot; int gary_timeout; int gary_toenb; @@ -635,13 +616,9 @@ int gary_toenb; static void mbres_write (uaecptr addr, uae_u32 val, int size) { addr &= 0xffff; - if (MBRES_LOG > 0) - write_log (_T("MBRES_WRITE %08X=%08X (%d) PC=%08X S=%d\n"), addr, val, size, M68K_GETPC, regs.s); - if (addr < 0x8000 && (1 || regs.s)) { /* CPU FC = supervisor only */ + if (addr < 0x8000) { uae_u32 addr2 = addr & 3; uae_u32 addr64 = (addr >> 6) & 3; - if (addr == 0x1002) - garyidoffset = -1; if (addr64 == 0 && addr2 == 0x03) ramsey_config = val; if (addr2 == 0x02) @@ -659,50 +636,38 @@ static uae_u32 mbres_read (uaecptr addr, int size) addr &= 0xffff; - if (1 || regs.s) { /* CPU FC = supervisor only (only newest ramsey/gary? never implemented?) */ - uae_u32 addr2 = addr & 3; - uae_u32 addr64 = (addr >> 6) & 3; - /* Gary ID (I don't think this exists in real chips..) */ - if (addr == 0x1002 && currprefs.cs_fatgaryrev >= 0) { - garyidoffset++; - garyidoffset &= 7; - v = (currprefs.cs_fatgaryrev << garyidoffset) & 0x80; - } - for (;;) { - if (addr64 == 1 && addr2 == 0x03) { /* RAMSEY revision */ - if (currprefs.cs_ramseyrev >= 0) - v = currprefs.cs_ramseyrev; - break; - } - if (addr64 == 0 && addr2 == 0x03) { /* RAMSEY config */ - if (currprefs.cs_ramseyrev >= 0) - v = ramsey_config; - break; - } - if (addr2 == 0x03) { - v = 0xff; - break; - } - if (addr2 == 0x02) { /* coldreboot flag */ - if (currprefs.cs_fatgaryrev >= 0) - v = gary_coldboot ? 0x80 : 0x00; - } - if (addr2 == 0x01) { /* toenb flag */ - if (currprefs.cs_fatgaryrev >= 0) - v = gary_toenb ? 0x80 : 0x00; - } - if (addr2 == 0x00) { /* timeout flag */ - if (currprefs.cs_fatgaryrev >= 0) - v = gary_timeout ? 0x80 : 0x00; - } - v |= 0x7f; + uae_u32 addr2 = addr & 3; + uae_u32 addr64 = (addr >> 6) & 3; + for (;;) { + if (addr64 == 1 && addr2 == 0x03) { /* RAMSEY revision */ + if (currprefs.cs_ramseyrev >= 0) + v = currprefs.cs_ramseyrev; break; } - } else { - v = 0xff; + if (addr64 == 0 && addr2 == 0x03) { /* RAMSEY config */ + if (currprefs.cs_ramseyrev >= 0) + v = ramsey_config; + break; + } + if (addr2 == 0x03) { + v = 0xff; + break; + } + if (addr2 == 0x02) { /* coldreboot flag */ + if (currprefs.cs_fatgaryrev >= 0) + v = gary_coldboot ? 0x80 : 0x00; + } + if (addr2 == 0x01) { /* toenb flag */ + if (currprefs.cs_fatgaryrev >= 0) + v = gary_toenb ? 0x80 : 0x00; + } + if (addr2 == 0x00) { /* timeout flag */ + if (currprefs.cs_fatgaryrev >= 0) + v = gary_timeout ? 0x80 : 0x00; + } + v |= 0x7f; + break; } - if (MBRES_LOG > 0) - write_log (_T("MBRES_READ %08X=%08X (%d) PC=%08X S=%d\n"), addr, v, size, M68K_GETPC, regs.s); return v; } @@ -749,7 +714,7 @@ static addrbank mbres_sub_bank = { mbres_lget, mbres_wget, mbres_bget, mbres_lput, mbres_wput, mbres_bput, default_xlate, default_check, NULL, NULL, _T("Motherboard Resources"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO, S_READ, S_WRITE }; @@ -763,7 +728,7 @@ addrbank mbres_bank = { sub_bank_lget, sub_bank_wget, sub_bank_bget, sub_bank_lput, sub_bank_wput, sub_bank_bput, sub_bank_xlate, sub_bank_check, NULL, NULL, _T("Motherboard Resources"), - sub_bank_lgeti, sub_bank_wgeti, + sub_bank_wgeti, ABFLAG_IO, S_READ, S_WRITE, mbres_sub_banks }; @@ -773,12 +738,6 @@ static uae_u8 *pcmcia_attrs; static int pcmcia_write_min, pcmcia_write_max; static uae_u16 pcmcia_idedata; -void gayle_hsync(void) -{ - if (ide_interrupt_hsync(idedrive[0]) || ide_interrupt_hsync(idedrive[2]) || ide_interrupt_hsync(idedrive[4])) - rethink_gayle(); -} - static uaecptr from_gayle_pcmcmia(uaecptr addr) { addr &= 0x80000 - 1; @@ -843,12 +802,8 @@ static uae_u32 gayle_attr_read (uaecptr addr) struct ide_hdf *ide = NULL; uae_u8 v = 0; - if (PCMCIA_LOG > 1) - write_log (_T("PCMCIA ATTR R: %x %x\n"), addr, M68K_GETPC); addr &= 0x80000 - 1; if (addr >= 0x40000) { - if (PCMCIA_LOG > 0) - write_log (_T("GAYLE: Reset disabled\n")); return v; } if (addr >= pcmcia_attrs_size) @@ -881,12 +836,8 @@ static uae_u32 gayle_attr_read (uaecptr addr) static void gayle_attr_write (uaecptr addr, uae_u32 v) { struct ide_hdf *ide = NULL; - if (PCMCIA_LOG > 1) - write_log (_T("PCMCIA ATTR W: %x=%x %x\n"), addr, v, M68K_GETPC); addr &= 0x80000 - 1; if (addr >= 0x40000) { - if (PCMCIA_LOG > 0) - write_log (_T("GAYLE: Reset enabled\n")); pcmcia_reset (); } else if (addr < pcmcia_attrs_size) { if (pcmcia_type == PCMCIA_IDE) { @@ -931,7 +882,7 @@ static void initscideattr (int readonly) { uae_u8 *rp; uae_u8 *p = pcmcia_attrs; - struct hardfiledata *hfd = &pcmcia_sram->hfd; + struct hardfiledata *hfd = &pcmcia_disk->hfd; /* Mostly just copied from real CF cards.. */ @@ -1022,7 +973,7 @@ static void initsramattr (int size, int readonly) uae_u8 *rp; uae_u8 *p = pcmcia_attrs; int sm, su, code, units; - struct hardfiledata *hfd = &pcmcia_sram->hfd; + struct hardfiledata *hfd = &pcmcia_disk->hfd; code = 0; su = 512; @@ -1084,9 +1035,11 @@ static void initsramattr (int size, int readonly) *p++ = 0xff; } -static void checkflush (int addr) +static void check_sram_flush (int addr) { - if (pcmcia_card == 0 || pcmcia_sram == 0) + if (pcmcia_card == 0 || pcmcia_disk == 0) + return; + if (pcmcia_readonly) return; if (addr >= 0 && pcmcia_common[0] == 0 && pcmcia_common[1] == 0 && pcmcia_common[2] == 0) return; // do not flush periodically if used as a ram expension @@ -1096,13 +1049,13 @@ static void checkflush (int addr) } if (pcmcia_write_min >= 0) { if (abs (pcmcia_write_min - addr) >= 512 || abs (pcmcia_write_max - addr) >= 512) { - int blocksize = pcmcia_sram->hfd.ci.blocksize; + int blocksize = pcmcia_disk->hfd.ci.blocksize; int mask = ~(blocksize - 1); int start = pcmcia_write_min & mask; int end = (pcmcia_write_max + blocksize - 1) & mask; int len = end - start; if (len > 0) { - hdf_write (&pcmcia_sram->hfd, pcmcia_common + start, start, len); + hdf_write (&pcmcia_disk->hfd, pcmcia_common + start, start, len); pcmcia_write_min = -1; pcmcia_write_max = -1; } @@ -1116,14 +1069,14 @@ static void checkflush (int addr) static int freepcmcia (int reset) { - if (pcmcia_sram) { - checkflush (-1); + if (pcmcia_disk) { + check_sram_flush(-1); if (reset) { - hdf_hd_close (pcmcia_sram); - xfree (pcmcia_sram); - pcmcia_sram = NULL; + hdf_hd_close (pcmcia_disk); + xfree (pcmcia_disk); + pcmcia_disk = NULL; } else { - pcmcia_sram->hfd.drive_empty = 1; + pcmcia_disk->hfd.drive_empty = 1; } } remove_ide_unit(idedrive, PCMCIA_IDE_ID * 2); @@ -1151,24 +1104,24 @@ static int initpcmcia (const TCHAR *path, int readonly, int type, int reset, str if (currprefs.cs_pcmcia == 0) return 0; freepcmcia (reset); - if (!pcmcia_sram) - pcmcia_sram = xcalloc (struct hd_hardfiledata, 1); - if (!pcmcia_sram->hfd.handle_valid) + if (!pcmcia_disk) + pcmcia_disk = xcalloc (struct hd_hardfiledata, 1); + if (!pcmcia_disk->hfd.handle_valid) reset = 1; if (path != NULL) - _tcscpy (pcmcia_sram->hfd.ci.rootdir, path); - pcmcia_sram->hfd.ci.readonly = readonly != 0; - pcmcia_sram->hfd.ci.blocksize = 512; + _tcscpy (pcmcia_disk->hfd.ci.rootdir, path); + pcmcia_disk->hfd.ci.readonly = readonly != 0; + pcmcia_disk->hfd.ci.blocksize = 512; if (type == PCMCIA_SRAM) { if (reset) { if (path) - hdf_hd_open (pcmcia_sram); + hdf_hd_open (pcmcia_disk); } else { - pcmcia_sram->hfd.drive_empty = 0; + pcmcia_disk->hfd.drive_empty = 0; } - if (pcmcia_sram->hfd.ci.readonly) + if (pcmcia_disk->hfd.ci.readonly) readonly = 1; pcmcia_common_size = 0; pcmcia_readonly = readonly; @@ -1176,15 +1129,15 @@ static int initpcmcia (const TCHAR *path, int readonly, int type, int reset, str pcmcia_attrs = xcalloc (uae_u8, pcmcia_attrs_size); pcmcia_type = type; - if (!pcmcia_sram->hfd.drive_empty) { - pcmcia_common_size = pcmcia_sram->hfd.virtsize; - if (pcmcia_sram->hfd.virtsize > 4 * 1024 * 1024) { - write_log (_T("PCMCIA SRAM: too large device, %llu bytes\n"), pcmcia_sram->hfd.virtsize); + if (!pcmcia_disk->hfd.drive_empty) { + pcmcia_common_size = pcmcia_disk->hfd.virtsize; + if (pcmcia_disk->hfd.virtsize > 4 * 1024 * 1024) { + write_log (_T("PCMCIA SRAM: too large device, %llu bytes\n"), pcmcia_disk->hfd.virtsize); pcmcia_common_size = 4 * 1024 * 1024; } pcmcia_common = xcalloc (uae_u8, pcmcia_common_size); write_log (_T("PCMCIA SRAM: '%s' open, size=%d\n"), path, pcmcia_common_size); - hdf_read (&pcmcia_sram->hfd, pcmcia_common, 0, pcmcia_common_size); + hdf_read (&pcmcia_disk->hfd, pcmcia_common, 0, pcmcia_common_size); pcmcia_card = 1; initsramattr (pcmcia_common_size, readonly); } @@ -1217,11 +1170,9 @@ static int initpcmcia (const TCHAR *path, int readonly, int type, int reset, str return 1; } -static uae_u32 gayle_common_read (uaecptr addr) +static uae_u32 gayle_common_read_byte(uaecptr addr) { uae_u8 v = 0; - if (PCMCIA_LOG > 2) - write_log (_T("PCMCIA COMMON R: %x %x\n"), addr, M68K_GETPC); if (!pcmcia_common_size) return 0; addr -= PCMCIA_COMMON_START & (PCMCIA_COMMON_SIZE - 1); @@ -1231,19 +1182,17 @@ static uae_u32 gayle_common_read (uaecptr addr) return v; } -static void gayle_common_write (uaecptr addr, uae_u32 v) +static void gayle_common_write_byte(uaecptr addr, uae_u32 v) { - if (PCMCIA_LOG > 2) - write_log (_T("PCMCIA COMMON W: %x=%x %x\n"), addr, v, M68K_GETPC); if (!pcmcia_common_size) return; - if (pcmcia_readonly) - return; addr -= PCMCIA_COMMON_START & (PCMCIA_COMMON_SIZE - 1); addr &= PCMCIA_COMMON_SIZE - 1; if (addr < pcmcia_common_size) { + if (pcmcia_readonly) + return; if (pcmcia_common[addr] != v) { - checkflush (addr); + check_sram_flush(addr); pcmcia_common[addr] = v; } } @@ -1276,7 +1225,7 @@ static addrbank gayle_common_bank = { gayle_common_lget, gayle_common_wget, gayle_common_bget, gayle_common_lput, gayle_common_wput, gayle_common_bput, gayle_common_xlate, gayle_common_check, NULL, NULL, _T("Gayle PCMCIA Common"), - gayle_common_lget, gayle_common_wget, + gayle_common_wget, ABFLAG_RAM | ABFLAG_SAFE, S_READ, S_WRITE }; @@ -1292,7 +1241,7 @@ static addrbank gayle_attr_bank = { gayle_attr_lget, gayle_attr_wget, gayle_attr_bget, gayle_attr_lput, gayle_attr_wput, gayle_attr_bput, default_xlate, default_check, NULL, NULL, _T("Gayle PCMCIA Attribute/Misc"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_IO | ABFLAG_SAFE, S_READ, S_WRITE }; @@ -1372,7 +1321,7 @@ static uae_u32 REGPARAM2 gayle_common_wget (uaecptr addr) } static uae_u32 REGPARAM2 gayle_common_bget (uaecptr addr) { - return gayle_common_read (addr); + return gayle_common_read_byte(addr); } static void REGPARAM2 gayle_common_lput (uaecptr addr, uae_u32 value) { @@ -1386,20 +1335,21 @@ static void REGPARAM2 gayle_common_wput (uaecptr addr, uae_u32 value) } static void REGPARAM2 gayle_common_bput (uaecptr addr, uae_u32 value) { - gayle_common_write (addr, value); + gayle_common_write_byte(addr, value); } void gayle_map_pcmcia (void) { if (currprefs.cs_pcmcia == 0) return; + struct autoconfig_info *aci = expansion_get_autoconfig_by_address(&currprefs, 6 * 1024 * 1024); if (pcmcia_card == 0 || (gayle_cs & GAYLE_CS_DIS)) { map_banks_cond (&dummy_bank, 0xa0, 8, 0); - if (currprefs.chipmem_size <= 4 * 1024 * 1024 && !expansion_get_autoconfig_by_address(&currprefs, 4 * 1024 * 1024)) + if (currprefs.chipmem_size <= 4 * 1024 * 1024 && (!aci || aci->zorro == 0)) map_banks_cond (&dummy_bank, PCMCIA_COMMON_START >> 16, PCMCIA_COMMON_SIZE >> 16, 0); } else { map_banks_cond (&gayle_attr_bank, 0xa0, 8, 0); - if (currprefs.chipmem_size <= 4 * 1024 * 1024 && !expansion_get_autoconfig_by_address(&currprefs, 4 * 1024 * 1024)) + if (currprefs.chipmem_size <= 4 * 1024 * 1024 && (!aci || aci->zorro == 0)) map_banks_cond (&gayle_common_bank, PCMCIA_COMMON_START >> 16, PCMCIA_COMMON_SIZE >> 16, 0); } } @@ -1421,6 +1371,8 @@ void gayle_add_ide_unit (int ch, struct uaedev_config_info *ci, struct romconfig ide = add_ide_unit (idedrive, TOTAL_IDE * 2, ch, ci, NULL); } +static void gayle_init(void); + bool gayle_ide_init(struct autoconfig_info *aci) { aci->zorro = 0; @@ -1431,51 +1383,32 @@ bool gayle_ide_init(struct autoconfig_info *aci) aci->start = GAYLE_BASE_4000; aci->size = 0x1000; } + device_add_reset(gayle_reset); + if (aci->doinit) + gayle_init(); return true; } -int gayle_add_pcmcia_sram_unit (struct uaedev_config_info *uci) +bool gayle_init_pcmcia(struct autoconfig_info *aci) { - return initpcmcia (uci->rootdir, uci->readonly, PCMCIA_SRAM, 1, NULL); -} - -int gayle_add_pcmcia_ide_unit (struct uaedev_config_info *uci) -{ - return initpcmcia (uci->rootdir, 0, PCMCIA_IDE, 1, uci); -} - -int gayle_modify_pcmcia_sram_unit (struct uaedev_config_info *uci, int insert) -{ - if (insert) - return initpcmcia (uci->rootdir, uci->readonly, PCMCIA_SRAM, pcmcia_sram ? 0 : 1, NULL); - else - return freepcmcia (0); -} - -int gayle_modify_pcmcia_ide_unit (struct uaedev_config_info *uci, int insert) -{ - if (insert) - return initpcmcia (uci->rootdir, 0, PCMCIA_IDE, pcmcia_sram ? 0 : 1, uci); - else - return freepcmcia (0); -} - -void gayle_add_pcmcia_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc) -{ -} -bool gayle_pcmcia_init(struct autoconfig_info *aci) -{ - aci->start = 0x600000; + aci->start = PCMCIA_COMMON_START; aci->size = 0xa80000 - aci->start; aci->zorro = 0; + device_add_reset(gayle_reset); + if (aci->doinit) + gayle_init(); return true; } +static void gayle_hsync(void) +{ + if (ide_interrupt_hsync(idedrive[0]) || ide_interrupt_hsync(idedrive[2]) || ide_interrupt_hsync(idedrive[4])) + rethink_gayle(); +} static void initide (void) { gayle_its.idetable = idedrive; - gayle_its.idetotal = TOTAL_IDE * 2; start_ide_thread(&gayle_its); alloc_ide_mem (idedrive, TOTAL_IDE * 2, &gayle_its); ide_initialize(idedrive, GAYLE_IDE_ID); @@ -1491,12 +1424,20 @@ static void initide (void) gayle_irq = gayle_int = 0; } -void gayle_free (void) +static void gayle_free (void) { stop_ide_thread(&gayle_its); + //stop_ide_thread(&pcmcia_its); } -void gayle_reset (int hardreset) +static void check_prefs_changed_gayle(void) +{ + if (!currprefs.cs_pcmcia) + return; + //pcmcia_card_check(1, -1); +} + +static void gayle_reset (int hardreset) { static TCHAR bankname[100]; @@ -1524,6 +1465,14 @@ uae_u8 *restore_gayle (uae_u8 *src) return src; } +static void gayle_init(void) +{ + device_add_check_config(check_prefs_changed_gayle); + device_add_rethink(rethink_gayle); + device_add_hsync(gayle_hsync); + device_add_exit(gayle_free); +} + uae_u8 *save_gayle (int *len, uae_u8 *dstptr) { uae_u8 *dstbak, *dst; diff --git a/src/gfxboard.cpp b/src/gfxboard.cpp index 2d72f414..0f9caa46 100644 --- a/src/gfxboard.cpp +++ b/src/gfxboard.cpp @@ -7,10 +7,14 @@ * */ +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "gfxboard.h" +#include "rommgr.h" +#include "xwin.h" +#include "devices.h" const TCHAR *gfxboard_get_name(int type) { @@ -21,6 +25,20 @@ const TCHAR *gfxboard_get_name(int type) return NULL; } +bool gfxboard_set(bool rtg) +{ + bool r; + struct amigadisplay *ad = &adisplays; + r = ad->picasso_on; + if (rtg) { + ad->picasso_requested_on = 1; + } else { + ad->picasso_requested_on = 0; + } + set_config_changed(); + return r; +} + const TCHAR *gfxboard_get_configname(int type) { if (type == GFXBOARD_UAE_Z2) diff --git a/src/gfxutil.cpp b/src/gfxutil.cpp index b4c2ec1c..da80d4c5 100644 --- a/src/gfxutil.cpp +++ b/src/gfxutil.cpp @@ -18,7 +18,7 @@ #define GRN 1 #define BLU 2 -unsigned int doMask(int p, int bits, int shift) +unsigned int doMask (int p, int bits, int shift) { /* scale to 0..255, shift to align msb with mask, and apply mask */ uae_u32 val; @@ -99,7 +99,7 @@ static uae_u32 lowbits(int v, int shift, int lsize) return v; } -void alloc_colors_picasso(int rw, int gw, int bw, int rs, int gs, int bs, int rgbfmt) +void alloc_colors_picasso (int rw, int gw, int bw, int rs, int gs, int bs, int rgbfmt, uae_u32 *rgbx16) { #ifdef PICASSO96 int byte_swap = 0; @@ -133,6 +133,8 @@ void alloc_colors_picasso(int rw, int gw, int bw, int rs, int gs, int bs, int rg blue_shift = 0; byte_swap = 1; break; + case RGBFB_Y4U2V2: + case RGBFB_Y4U1V1: case RGBFB_R5G5B5: red_bits = green_bits = blue_bits = 5; red_shift = 10; @@ -168,27 +170,25 @@ void alloc_colors_picasso(int rw, int gw, int bw, int rs, int gs, int bs, int rg byte_swap = !byte_swap; #endif - memset(p96_rgbx16, 0, sizeof p96_rgbx16); + memset (rgbx16, 0, 65536 * sizeof(uae_u32)); - if (red_bits) - { + if (red_bits) { int lrbits = 8 - red_bits; int lgbits = 8 - green_bits; int lbbits = 8 - blue_bits; int lrmask = (1 << red_bits) - 1; int lgmask = (1 << green_bits) - 1; int lbmask = (1 << blue_bits) - 1; - for (i = 65535; i >= 0; i--) - { + for (i = 65535; i >= 0; i--) { uae_u32 r, g, b, c; - uae_u32 j = byte_swap ? bswap_16(i) : i; - r = (((j >> red_shift) & lrmask) << lrbits) | lowbits(j, red_shift, lrbits); - g = (((j >> green_shift) & lgmask) << lgbits) | lowbits(j, green_shift, lgbits); - b = (((j >> blue_shift) & lbmask) << lbbits) | lowbits(j, blue_shift, lbbits); + uae_u32 j = byte_swap ? bswap_16 (i) : i; + r = (((j >> red_shift) & lrmask) << lrbits) | lowbits (j, red_shift, lrbits); + g = (((j >> green_shift) & lgmask) << lgbits) | lowbits (j, green_shift, lgbits); + b = (((j >> blue_shift) & lbmask) << lbbits) | lowbits (j, blue_shift, lbbits); c = doMask(r, rw, rs) | doMask(g, gw, gs) | doMask(b, bw, bs); if (bpp <= 16) c *= 0x00010001; - p96_rgbx16[i] = c; + rgbx16[i] = c; } } #endif diff --git a/src/hardfile.cpp b/src/hardfile.cpp index cbe5cd7e..6ddf8912 100644 --- a/src/hardfile.cpp +++ b/src/hardfile.cpp @@ -23,31 +23,11 @@ #include "scsi.h" #include "gayle.h" #include "execio.h" +#include "zfile.h" #define HDF_SUPPORT_NSD 1 #define HDF_SUPPORT_TD64 1 #define HDF_SUPPORT_DS 1 -#define HDF_SUPPORT_DS_PARTITION 0 - -#undef DEBUGME -#define hf_log(fmt, ...) -#define hf_log2(fmt, ...) -#define scsi_log(fmt, ...) -#define hf_log3(fmt, ...) - -//#define DEBUGME -#ifdef DEBUGME -#undef hf_log -#define hf_log write_log -#undef hf_log2 -#define hf_log2 write_log -#undef hf_log3 -#define hf_log3 write_log -#undef scsi_log -#define scsi_log write_log -#endif - -int enable_ds_partition_hdf; #define MAX_ASYNC_REQUESTS 50 #define ASYNC_REQUEST_NONE 0 @@ -59,14 +39,15 @@ struct hardfileprivdata { uae_u8 *d_request_iobuf[MAX_ASYNC_REQUESTS]; int d_request_type[MAX_ASYNC_REQUESTS]; uae_u32 d_request_data[MAX_ASYNC_REQUESTS]; - smp_comm_pipe requests; - int thread_running; - uae_thread_id thread_id; - uae_sem_t sync_sem; - uaecptr base; - int changenum; - uaecptr changeint; + smp_comm_pipe requests; + int thread_running; + uae_thread_id thread_id; + uae_sem_t sync_sem; + uaecptr base; + int changenum; + uaecptr changeint; struct scsi_data *sd; + bool directorydrive; }; #define HFD_CHD_OTHER 5 @@ -109,13 +90,6 @@ static void getchs2 (struct hardfiledata *hfd, int *cyl, int *cylsec, int *head, int heads; int sectors = 63; - if (hfd->ci.physical_geometry) { - *cyl = hfd->ci.pcyls; - *tracksec = hfd->ci.psecs; - *head = hfd->ci.pheads; - *cylsec = (*head) * (*tracksec); - return; - } /* do we have RDB values? */ if (hfd->rdbcylinders) { *cyl = hfd->rdbcylinders; @@ -156,9 +130,6 @@ static void getchs2 (struct hardfiledata *hfd, int *cyl, int *cylsec, int *head, static void getchsx (struct hardfiledata *hfd, int *cyl, int *cylsec, int *head, int *tracksec) { getchs2 (hfd, cyl, cylsec, head, tracksec); - hf_log (_T("CHS: %08X-%08X %d %d %d %d %d\n"), - (uae_u32)(hfd->virtsize >> 32),(uae_u32)hfd->virtsize, - *cyl, *cylsec, *head, *tracksec); } static void getchsgeometry2 (uae_u64 size, int *pcyl, int *phead, int *psectorspertrack, int mode) @@ -219,42 +190,6 @@ void getchsgeometry (uae_u64 size, int *pcyl, int *phead, int *psectorspertrack) getchsgeometry2 (size, pcyl, phead, psectorspertrack, 0); } -void getchsgeometry_hdf (struct hardfiledata *hfd, uae_u64 size, int *pcyl, int *phead, int *psectorspertrack) -{ - uae_u8 block[512]; - int i; - uae_u64 minsize = 512 * 1024 * 1024; - - if (size <= minsize) { - *phead = 1; - *psectorspertrack = 32; - } - memset (block, 0, sizeof block); - if (hfd) { - hdf_read (hfd, block, 0, 512); - if (block[0] == 'D' && block[1] == 'O' && block[2] == 'S') { - int mode; - for (mode = 0; mode < 2; mode++) { - uae_u32 rootblock; - uae_u32 chk = 0; - getchsgeometry2 (size, pcyl, phead, psectorspertrack, mode); - rootblock = (2 + ((*pcyl) * (*phead) * (*psectorspertrack) - 1)) / 2; - memset (block, 0, sizeof block); - hdf_read (hfd, block, (uae_u64)rootblock * 512, 512); - for (i = 0; i < 512; i += 4) - chk += (block[i] << 24) | (block[i + 1] << 16) | (block[i + 2] << 8) | (block[i + 3] << 0); - if (!chk && block[0] == 0 && block[1] == 0 && block[2] == 0 && block[3] == 2 && - block[4] == 0 && block[5] == 0 && block[6] == 0 && block[7] == 0 && - block[8] == 0 && block[9] == 0 && block[10] == 0 && block[11] == 0 && - block[508] == 0 && block[509] == 0 && block[510] == 0 && block[511] == 1) { - return; - } - } - } - } - getchsgeometry2 (size, pcyl, phead, psectorspertrack, size <= minsize ? 1 : 2); -} - void getchspgeometry (uae_u64 total, int *pcyl, int *phead, int *psectorspertrack, bool idegeometry) { uae_u64 blocks = total / 512; @@ -351,26 +286,56 @@ static uae_u32 get_filesys_version(uae_u8 *fs, int size) return (ver << 16) | rev; } +// hardware block size is always 256 or 512 +// filesystem block size can be 256, 512 or larger static void create_virtual_rdb (struct hardfiledata *hfd) { - uae_u8 *rdb, *part, *denv; + uae_u8 *rdb, *part, *denv, *fs; + int fsblocksize = hfd->ci.blocksize; + int hardblocksize = fsblocksize >= 512 ? 512 : 256; int cyl = hfd->ci.surfaces * hfd->ci.sectors; - int cyls = 262144 / (cyl * 512); - int size = cyl * cyls * 512; + int cyls = (262144 + (cyl * fsblocksize) - 1) / (cyl * fsblocksize); + int size = cyl * cyls * fsblocksize; + int idx = 0; + uae_u8 *filesys = NULL; + int filesyslen = 0; + uae_u32 fsver = 0; + + write_log(_T("Creating virtual RDB (RDB size=%d, %d blocks). H=%d S=%d HBS=%d FSBS=%d)\n"), + size, size / hardblocksize, hfd->ci.surfaces, hfd->ci.sectors, hardblocksize, fsblocksize); + + if (hfd->ci.filesys[0]) { + struct zfile *f = NULL; + TCHAR fspath[MAX_DPATH]; + cfgfile_resolve_path_out_load(hfd->ci.filesys, fspath, MAX_DPATH, PATH_HDF); + filesys = zfile_load_file(fspath, &filesyslen); + if (filesys) { + fsver = get_filesys_version(filesys, filesyslen); + if (fsver == 0xffffffff) + fsver = (99 << 16) | 99; + if (filesyslen & 3) { + xfree(filesys); + filesys = NULL; + filesyslen = 0; + } + } + } + + int filesysblocks = (filesyslen + hardblocksize - 5 * 4 - 1) / (hardblocksize - 5 * 4); rdb = xcalloc (uae_u8, size); hfd->virtual_rdb = rdb; hfd->virtual_size = size; - part = rdb + 512; - pl(rdb, 0, 0x5244534b); - pl(rdb, 1, 64); + + pl(rdb, 0, 0x5244534b); // "RDSK" + pl(rdb, 1, 256 / 4); pl(rdb, 2, 0); // chksum pl(rdb, 3, 7); // hostid - pl(rdb, 4, 512); // blockbytes + pl(rdb, 4, hardblocksize); // blockbytes pl(rdb, 5, 0); // flags pl(rdb, 6, -1); // badblock - pl(rdb, 7, 1); // part - pl(rdb, 8, -1); // fs + pl(rdb, 7, idx + 1); // part + pl(rdb, 8, filesys ? idx + 2 : -1); // fs pl(rdb, 9, -1); // driveinit pl(rdb, 10, -1); // reserved pl(rdb, 11, -1); // reserved @@ -378,10 +343,10 @@ static void create_virtual_rdb (struct hardfiledata *hfd) pl(rdb, 13, -1); // reserved pl(rdb, 14, -1); // reserved pl(rdb, 15, -1); // reserved - pl(rdb, 16, hfd->ci.highcyl); + pl(rdb, 16, hfd->ci.highcyl + cyls - 1); pl(rdb, 17, hfd->ci.sectors); - pl(rdb, 18, hfd->ci.surfaces); - pl(rdb, 19, hfd->ci.interleave); // interleave + pl(rdb, 18, hfd->ci.surfaces * fsblocksize / hardblocksize); + pl(rdb, 19, hfd->ci.interleave); pl(rdb, 20, 0); // park pl(rdb, 21, -1); // res pl(rdb, 22, -1); // res @@ -395,24 +360,26 @@ static void create_virtual_rdb (struct hardfiledata *hfd) pl(rdb, 30, -1); // res pl(rdb, 31, -1); // res pl(rdb, 32, 0); // rdbblockslo - pl(rdb, 33, cyl * cyls); // rdbblockshi + pl(rdb, 33, cyl * cyls * fsblocksize / hardblocksize - 1); // rdbblockshi pl(rdb, 34, cyls); // locyl - pl(rdb, 35, hfd->ci.highcyl + cyls); // hicyl - pl(rdb, 36, cyl); // cylblocks + pl(rdb, 35, hfd->ci.highcyl + cyls - 1); // hicyl + pl(rdb, 36, cyl * fsblocksize / hardblocksize); // cylblocks pl(rdb, 37, 0); // autopark - pl(rdb, 38, 2); // highrdskblock + pl(rdb, 38, (1 + 1 + (filesysblocks ? 2 + filesysblocks : 0) - 1)); // highrdskblock pl(rdb, 39, -1); // res ua_copy ((char*)rdb + 40 * 4, 8, hfd->vendor_id); ua_copy ((char*)rdb + 42 * 4, 16, hfd->product_id); ua_copy ((char*)rdb + 46 * 4, 4, _T("UAE")); rdb_crc (rdb); + idx++; - pl(part, 0, 0x50415254); - pl(part, 1, 64); - pl(part, 2, 0); - pl(part, 3, 0); - pl(part, 4, -1); - pl(part, 5, 1); // bootable + part = rdb + hardblocksize * idx; + pl(part, 0, 0x50415254); // "PART" + pl(part, 1, 256 / 4); + pl(part, 2, 0); // chksum + pl(part, 3, 7); // hostid + pl(part, 4, -1); // next + pl(part, 5, hfd->ci.bootpri < -128 ? 2 : hfd->ci.bootpri == -128 ? 0 : 1); // bootable/nomount pl(part, 6, -1); pl(part, 7, -1); pl(part, 8, 0); // devflags @@ -420,11 +387,11 @@ static void create_virtual_rdb (struct hardfiledata *hfd) ua_copy ((char*)part + 9 * 4 + 1, 30, hfd->ci.devname); denv = part + 128; - pl(denv, 0, 80); - pl(denv, 1, 512 / 4); + pl(denv, 0, 16); + pl(denv, 1, fsblocksize / 4); pl(denv, 2, 0); // secorg pl(denv, 3, hfd->ci.surfaces); - pl(denv, 4, hfd->ci.blocksize / 512); + pl(denv, 4, 1); pl(denv, 5, hfd->ci.sectors); pl(denv, 6, hfd->ci.reserved); pl(denv, 7, 0); // prealloc @@ -438,9 +405,54 @@ static void create_virtual_rdb (struct hardfiledata *hfd) pl(denv, 15, hfd->ci.bootpri); pl(denv, 16, hfd->ci.dostype); rdb_crc (part); + idx++; + + if (filesys) { + fs = rdb + hardblocksize * idx; + pl(fs, 0, 0x46534844); // "FSHD" + pl(fs, 1, 256 / 4); + pl(fs, 2, 0); // chksum + pl(fs, 3, 7); // hostid + pl(fs, 4, -1); // next + pl(fs, 5, 0); // flags + pl(fs, 8, hfd->ci.dostype); + pl(fs, 9, fsver); // version + pl(fs, 10, 0x100 | 0x80 | 0x20 | 0x10); // patchflags: seglist + globvec + pri + stack + pl(fs, 15, hfd->ci.stacksize); // stack + pl(fs, 16, hfd->ci.priority); // priority + pl(fs, 18, idx + 1); // first lseg + pl(fs, 19, -1); // globvec + rdb_crc(fs); + idx++; + + int offset = 0; + for (;;) { + uae_u8 *lseg = rdb + hardblocksize * idx; + int lsegdatasize = hardblocksize - 5 * 4; + if (lseg + hardblocksize > rdb + size) + break; + pl(lseg, 0, 0x4c534547); // "LSEG" + pl(lseg, 1, hardblocksize / 4); + pl(lseg, 2, 0); // chksum + pl(lseg, 3, 7); // hostid + int v = filesyslen - offset; + if (v <= lsegdatasize) { + memcpy(lseg + 5 * 4, filesys + offset, v); + pl(lseg, 4, -1); + pl(lseg, 1, 5 + v / 4); + rdb_crc(lseg); + break; + } + memcpy(lseg + 5 * 4, filesys + offset, lsegdatasize); + offset += lsegdatasize; + idx++; + pl(lseg, 4, idx); // next + rdb_crc(lseg); + } + xfree(filesys); + } hfd->virtsize += size; - } void hdf_hd_close (struct hd_hardfiledata *hfd) @@ -450,35 +462,29 @@ void hdf_hd_close (struct hd_hardfiledata *hfd) hdf_close (&hfd->hfd); } -int hdf_hd_open(struct hd_hardfiledata *hfd) +int hdf_hd_open (struct hd_hardfiledata *hfd) { struct uaedev_config_info *ci = &hfd->hfd.ci; - if (hdf_open(&hfd->hfd) <= 0) + if (hdf_open (&hfd->hfd) <= 0) return 0; hfd->hfd.unitnum = ci->uae_unitnum; - if (ci->physical_geometry) { - hfd->cyls = ci->pcyls; - hfd->heads = ci->pheads; - hfd->secspertrack = ci->psecs; - } - else if (ci->highcyl && ci->surfaces && ci->sectors) { + if (ci->highcyl && ci->surfaces && ci->sectors) { hfd->cyls = ci->highcyl; hfd->heads = ci->surfaces; hfd->secspertrack = ci->sectors; - } - else { - getchshd(&hfd->hfd, &hfd->cyls, &hfd->heads, &hfd->secspertrack); + } else { + getchshd (&hfd->hfd, &hfd->cyls, &hfd->heads, &hfd->secspertrack); } hfd->cyls_def = hfd->cyls; hfd->secspertrack_def = hfd->secspertrack; hfd->heads_def = hfd->heads; if (ci->surfaces && ci->sectors) { uae_u8 buf[512] = { 0 }; - hdf_read(&hfd->hfd, buf, 0, 512); - if (buf[0] != 0 && memcmp(buf, _T("RDSK"), 4)) { + hdf_read (&hfd->hfd, buf, 0, 512); + if (buf[0] != 0 && memcmp (buf, _T("RDSK"), 4)) { ci->highcyl = (hfd->hfd.virtsize / ci->blocksize) / (ci->sectors * ci->surfaces); - ci->dostype = rl(buf); - create_virtual_rdb(&hfd->hfd); + ci->dostype = rl (buf); + create_virtual_rdb (&hfd->hfd); while (ci->highcyl * ci->surfaces * ci->sectors > hfd->cyls_def * hfd->secspertrack_def * hfd->heads_def) { hfd->cyls_def++; } @@ -488,20 +494,6 @@ int hdf_hd_open(struct hd_hardfiledata *hfd) return 1; } -static uae_u32 vhd_checksum(uae_u8 *p, int offset) -{ - int i; - uae_u32 sum; - - sum = 0; - for (i = 0; i < 512; i++) { - if (offset >= 0 && i >= offset && i < offset + 4) - continue; - sum += p[i]; - } - return ~sum; -} - static int hdf_write2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); static int hdf_read2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); @@ -518,40 +510,78 @@ static int hdf_cache_write (struct hardfiledata *hfd, void *buffer, uae_u64 offs int hdf_open (struct hardfiledata *hfd, const TCHAR *pname) { int ret; + TCHAR filepath[MAX_DPATH]; if ((!pname || pname[0] == 0) && hfd->ci.rootdir[0] == 0) return 0; hfd->byteswap = 0; - hfd->hfd_type = 0; hfd->virtual_size = 0; hfd->virtual_rdb = NULL; if (!pname) pname = hfd->ci.rootdir; - ret = hdf_open_target (hfd, pname); + cfgfile_resolve_path_out_load(pname, filepath, MAX_DPATH, PATH_HDF); + ret = hdf_open_target (hfd, filepath); if (ret <= 0) return ret; - hfd->hfd_type = 0; return 1; } int hdf_open (struct hardfiledata *hfd) { - return hdf_open (hfd, NULL); + int v = hdf_open (hfd, NULL); + return v; } void hdf_close (struct hardfiledata *hfd) { hdf_close_target (hfd); - hfd->hfd_type = 0; } static int hdf_read2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { - return hdf_read_target (hfd, buffer, offset, len); + int ret = 0, extra = 0; + if (offset < hfd->virtual_size) { + uae_s64 len2 = offset + len <= hfd->virtual_size ? len : hfd->virtual_size - offset; + if (!hfd->virtual_rdb) + return 0; + memcpy(buffer, hfd->virtual_rdb + offset, len2); + len -= len2; + if (len <= 0) + return len2; + offset += len2; + buffer = (uae_u8*)buffer + len2; + extra = len2; + } + offset -= hfd->virtual_size; + + ret = hdf_read_target (hfd, buffer, offset, len); + + if (ret <= 0) + return ret; + ret += extra; + return ret; } static int hdf_write2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { - return hdf_write_target (hfd, buffer, offset, len); + int ret = 0, extra = 0; + // writes to virtual RDB are ignored + if (offset < hfd->virtual_size) { + uae_s64 len2 = offset + len <= hfd->virtual_size ? len : hfd->virtual_size - offset; + len -= len2; + if (len <= 0) + return len2; + offset += len2; + buffer = (uae_u8*)buffer + len2; + extra = len2; + } + offset -= hfd->virtual_size; + + ret = hdf_write_target (hfd, buffer, offset, len); + + if (ret <= 0) + return ret; + ret += extra; + return ret; } static void hdf_byteswap (void *v, int len) @@ -588,9 +618,6 @@ int hdf_read (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { int v; - hf_log3 (_T("cmd_read: %p %04x-%08x (%d) %08x (%d)\n"), - buffer, (uae_u32)(offset >> 32), (uae_u32)offset, (uae_u32)(offset / hfd->ci.blocksize), (uae_u32)len, (uae_u32)(len / hfd->ci.blocksize)); - v = hdf_cache_read (hfd, buffer, offset, len); if (hfd->byteswap) hdf_byteswap (buffer, len); @@ -601,9 +628,6 @@ int hdf_write (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { int v; - hf_log3 (_T("cmd_write: %p %04x-%08x (%d) %08x (%d)\n"), - buffer, (uae_u32)(offset >> 32), (uae_u32)offset, (uae_u32)(offset / hfd->ci.blocksize), (uae_u32)len, (uae_u32)(len / hfd->ci.blocksize)); - if (hfd->byteswap) hdf_byteswap (buffer, len); v = hdf_cache_write (hfd, buffer, offset, len); @@ -623,10 +647,12 @@ static uae_u64 cmd_read(TrapContext *ctx, struct hardfiledata *hfd, uaecptr data return 0; if (!ctx) { addrbank *bank_data = &get_mem_bank (dataptr); - if (!bank_data || !bank_data->check (dataptr, len)) + if (!bank_data) return 0; - uae_u8 *buffer = bank_data->xlateaddr (dataptr); - return cmd_readx (hfd, buffer, offset, len); + if (bank_data->check (dataptr, len)) { + uae_u8 *buffer = bank_data->xlateaddr (dataptr); + return cmd_readx (hfd, buffer, offset, len); + } } int total = 0; while (len > 0) { @@ -655,10 +681,12 @@ static uae_u64 cmd_write(TrapContext *ctx, struct hardfiledata *hfd, uaecptr dat return 0; if (!ctx) { addrbank *bank_data = &get_mem_bank (dataptr); - if (!bank_data || !bank_data->check (dataptr, len)) + if (!bank_data) return 0; - uae_u8 *buffer = bank_data->xlateaddr (dataptr); - return cmd_writex (hfd, buffer, offset, len); + if (bank_data->check(dataptr, len)) { + uae_u8 *buffer = bank_data->xlateaddr (dataptr); + return cmd_writex (hfd, buffer, offset, len); + } } int total = 0; while (len > 0) { @@ -693,7 +721,7 @@ static int checkbounds (struct hardfiledata *hfd, uae_u64 offset, uae_u64 len, i static bool is_writeprotected(struct hardfiledata *hfd) { - return hfd->ci.readonly || hfd->dangerous || currprefs.harddrive_read_only; + return hfd->ci.readonly || currprefs.harddrive_read_only; } static int nodisk (struct hardfiledata *hfd) @@ -1179,7 +1207,7 @@ int scsi_hd_emulate (struct hardfiledata *hfd, struct hd_hardfiledata *hdhfd, ua bdsize = 0; if (!dbd) { uae_u32 blocks = (uae_u32)(hfd->virtsize / hfd->ci.blocksize); - wl(p + 0, blocks < 0x01000000 ? blocks : 0); + wl(p + 0, blocks >= 0x00ffffff ? 0x00ffffff : blocks); wl(p + 4, hfd->ci.blocksize); bdsize = 8; p += bdsize; @@ -1265,11 +1293,11 @@ int scsi_hd_emulate (struct hardfiledata *hfd, struct hd_hardfiledata *hdhfd, ua { int pmi = cmdbuf[8] & 1; uae_u32 lba = (cmdbuf[2] << 24) | (cmdbuf[3] << 16) | (cmdbuf[4] << 8) | cmdbuf[5]; - uae_u32 blocks; + uae_u64 blocks; int cyl, head, tracksec; if (nodisk (hfd)) goto nodisk; - blocks = (uae_u32)(hfd->virtsize / hfd->ci.blocksize); + blocks = hfd->virtsize / hfd->ci.blocksize; if (hfd->ci.max_lba) blocks = hfd->ci.max_lba; if (hdhfd) { @@ -1290,7 +1318,7 @@ int scsi_hd_emulate (struct hardfiledata *hfd, struct hd_hardfiledata *hdhfd, ua lba = blocks; blocks = lba; } - wl (r, blocks - 1); + wl (r, (uae_u32)(blocks <= 0x100000000 ? blocks - 1 : 0xffffffff)); wl (r + 4, hfd->ci.blocksize); scsi_len = lr = 8; } @@ -1505,7 +1533,7 @@ scsi_done: return status; } -static int handle_scsi (TrapContext *ctx, uae_u8 *iobuf, uaecptr request, struct hardfiledata *hfd, struct scsi_data *sd) +static int handle_scsi (TrapContext *ctx, uae_u8 *iobuf, uaecptr request, struct hardfiledata *hfd, struct scsi_data *sd, bool safeonly) { int ret = 0; @@ -1526,46 +1554,46 @@ static int handle_scsi (TrapContext *ctx, uae_u8 *iobuf, uaecptr request, struct scsi_sense_len = (scsi_flags & 4) ? 4 : /* SCSIF_OLDAUTOSENSE */ (scsi_flags & 2) ? scsi_sense_len : /* SCSIF_AUTOSENSE */ 32; - scsi_log (_T("hdf scsiemu: cmd=%02X,%d flags=%02X sense=%p,%d data=%p,%d\n"), - cmd, scsi_cmd_len, scsi_flags, scsi_sense, scsi_sense_len, scsi_data, scsi_len); sd->cmd_len = scsi_cmd_len; sd->data_len = scsi_len; trap_get_bytes(ctx, sd->cmd, scsi_cmd, sd->cmd_len); - for (int i = 0; i < sd->cmd_len; i++) { - scsi_log (_T("%02X%c"), sd->cmd[i], i < sd->cmd_len - 1 ? '.' : ' '); - } - scsi_log (_T("\n")); - scsi_emulate_analyze(sd); - scsi_start_transfer(sd); - if (sd->direction > 0) { - trap_get_bytes(ctx, sd->buffer, scsi_data, sd->data_len); - scsi_emulate_cmd(sd); + if (safeonly && !scsi_cmd_is_safe(sd->cmd[0])) { + sd->reply_len = 0; + sd->data_len = 0; + sd->status = 2; + sd->sense_len = 18; + sd->sense[0] = 0x70; + sd->sense[2] = 5; /* ILLEGAL REQUEST */ + sd->sense[12] = 0x30; /* INCOMPATIBLE MEDIUM INSERTED */ } else { - scsi_emulate_cmd(sd); - if (sd->direction < 0) - trap_put_bytes(ctx, sd->buffer, scsi_data, sd->data_len); + scsi_emulate_analyze(sd); + if (sd->direction > 0) { + trap_get_bytes(ctx, sd->buffer, scsi_data, sd->data_len); + scsi_emulate_cmd(sd); + } else { + scsi_emulate_cmd(sd); + if (sd->direction < 0) + trap_put_bytes(ctx, sd->buffer, scsi_data, sd->data_len); + } } put_word_host(scsicmd + 18, sd->status != 0 ? 0 : sd->cmd_len); /* fake scsi_CmdActual */ put_byte_host(scsicmd + 21, sd->status); /* scsi_Status */ if (sd->reply_len > 0) { trap_put_bytes(ctx, sd->reply, scsi_data, sd->reply_len); - scsi_log (_T("RD:")); - int i = 0; - while (i < sd->reply_len && i < 24) { - scsi_log (_T("%02X%c"), sd->reply[i], i < sd->reply_len - 1 ? '.' : ' '); - i++; - } - scsi_log (_T("\n")); } if (scsi_sense) { - trap_put_bytes(ctx, sd->sense, scsi_sense, sd->sense_len < scsi_sense_len ? sd->sense_len : scsi_sense_len); + int slen = sd->sense_len < scsi_sense_len ? sd->sense_len : scsi_sense_len; + trap_put_bytes(ctx, sd->sense, scsi_sense, slen); if (scsi_sense_len > sd->sense_len) { trap_set_bytes(ctx, scsi_sense + sd->sense_len, 0, scsi_sense_len - sd->sense_len); } + put_word_host(scsicmd + 28, slen); /* scsi_SenseActual */ + } else { + put_word_host(scsicmd + 28, 0); } if (sd->data_len < 0) { put_long_host(scsicmd + 8, 0); /* scsi_Actual */ @@ -1604,14 +1632,6 @@ void hardfile_do_disk_change (struct uaedev_config_data *uci, bool insert) int fsid = uci->configoffset; struct hardfiledata *hfd; - if (uci->ci.controller_type == HD_CONTROLLER_TYPE_PCMCIA) { - if (uci->ci.controller_type_unit == 0) { - gayle_modify_pcmcia_sram_unit (&uci->ci, insert); - } else { - gayle_modify_pcmcia_ide_unit (&uci->ci, insert); - } - return; - } hfd = get_hardfile_data (fsid); if (!hfd) return; @@ -1627,7 +1647,6 @@ static int add_async_request (struct hardfileprivdata *hfpd, uae_u8 *iobuf, uaec if (hfpd->d_request[i] == request) { hfpd->d_request_type[i] = type; hfpd->d_request_data[i] = data; - hf_log (_T("old async request %p (%d) added\n"), request, type); return 0; } i++; @@ -1639,12 +1658,10 @@ static int add_async_request (struct hardfileprivdata *hfpd, uae_u8 *iobuf, uaec hfpd->d_request_iobuf[i] = iobuf; hfpd->d_request_type[i] = type; hfpd->d_request_data[i] = data; - hf_log (_T("async request %p (%d) added (total=%d)\n"), request, type, i); return 0; } i++; } - hf_log (_T("async request overflow %p!\n"), request); return -1; } @@ -1660,19 +1677,16 @@ static int release_async_request (struct hardfileprivdata *hfpd, uaecptr request hfpd->d_request_iobuf[i] = 0; hfpd->d_request_data[i] = 0; hfpd->d_request_type[i] = 0; - hf_log (_T("async request %p removed\n"), request); return type; } i++; } - hf_log (_T("tried to remove non-existing request %p\n"), request); return -1; } static void abort_async (struct hardfileprivdata *hfpd, uaecptr request, int errcode, int type) { int i; - hf_log (_T("aborting async request %p\n"), request); i = 0; while (i < MAX_ASYNC_REQUESTS) { if (hfpd->d_request[i] == request && hfpd->d_request_type[i] == ASYNC_REQUEST_TEMP) { @@ -1684,12 +1698,9 @@ static void abort_async (struct hardfileprivdata *hfpd, uaecptr request, int err i++; } i = release_async_request (hfpd, request); - if (i >= 0) { - hf_log (_T("asyncronous request=%08X aborted, error=%d\n"), request, errcode); - } } -static void *hardfile_thread (void *devs); +static int hardfile_thread (void *devs); static int start_thread (TrapContext *ctx, int unit) { struct hardfileprivdata *hfpd = &hardfpd[unit]; @@ -1730,20 +1741,34 @@ static uae_u32 REGPARAM2 hardfile_open (TrapContext *ctx) if (unit >= 0 && unit < MAX_FILESYSTEM_UNITS) { struct hardfileprivdata *hfpd = &hardfpd[unit]; struct hardfiledata *hfd = get_hardfile_data_controller(unit); - if (hfd && (hfd->handle_valid || hfd->drive_empty) && start_thread (ctx, unit)) { - trap_put_word(ctx, hfpd->base + 32, trap_get_word(ctx, hfpd->base + 32) + 1); - trap_put_long(ctx, ioreq + 24, unit); /* io_Unit */ - trap_put_byte(ctx, ioreq + 31, 0); /* io_Error */ - trap_put_byte(ctx, ioreq + 8, 7); /* ln_type = NT_REPLYMSG */ - if (!hfpd->sd) - hfpd->sd = scsi_alloc_generic(hfd, UAEDEV_HDF); - hf_log (_T("hardfile_open, unit %d (%d), OK\n"), unit, trap_get_dreg (ctx, 0)); - return 0; + if (hfd) { + if (hfd->ci.type == UAEDEV_DIR) { + if (start_thread(ctx, unit)) { + hfpd->directorydrive = true; + trap_put_word(ctx, hfpd->base + 32, trap_get_word(ctx, hfpd->base + 32) + 1); + trap_put_long(ctx, ioreq + 24, unit); /* io_Unit */ + trap_put_byte(ctx, ioreq + 31, 0); /* io_Error */ + trap_put_byte(ctx, ioreq + 8, 7); /* ln_type = NT_REPLYMSG */ + if (!hfpd->sd) + hfpd->sd = scsi_alloc_generic(hfd, UAEDEV_DIR, unit); + return 0; + } + } else { + if ((hfd->handle_valid || hfd->drive_empty) && start_thread(ctx, unit)) { + hfpd->directorydrive = false; + trap_put_word(ctx, hfpd->base + 32, trap_get_word(ctx, hfpd->base + 32) + 1); + trap_put_long(ctx, ioreq + 24, unit); /* io_Unit */ + trap_put_byte(ctx, ioreq + 31, 0); /* io_Error */ + trap_put_byte(ctx, ioreq + 8, 7); /* ln_type = NT_REPLYMSG */ + if (!hfpd->sd) + hfpd->sd = scsi_alloc_generic(hfd, UAEDEV_HDF, unit); + return 0; + } + } } } - if (unit < 1000 || is_hardfile(unit) == FILESYS_VIRTUAL) + if (unit < 1000) err = 50; /* HFERR_NoBoard */ - hf_log (_T("hardfile_open, unit %d (%d), ERR=%d\n"), unit, trap_get_dreg(ctx, 0), err); trap_put_long(ctx, ioreq + 20, (uae_u32)err); trap_put_byte(ctx, ioreq + 31, (uae_u8)err); return (uae_u32)err; @@ -1789,6 +1814,11 @@ static void unaligned (int cmd, uae_u64 offset, uae_u64 len, int blocksize) blocksize); } +static bool vdisk(struct hardfileprivdata *hfdp) +{ + return hfdp->directorydrive; +} + static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struct hardfileprivdata *hfpd, uae_u8 *iobuf, uaecptr request) { uae_u32 dataptr, offset, actual = 0, cmd; @@ -1806,6 +1836,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc case CMD_READ: if (nodisk (hfd)) goto no_disk; + if (vdisk(hfpd)) + goto v_disk; offset = get_long_host(iobuf + 44); len = get_long_host(iobuf + 36); /* io_Length */ if (offset & bmask) { @@ -1832,6 +1864,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc #if defined(HDF_SUPPORT_NSD) || defined(HDF_SUPPORT_TD64) if (nodisk (hfd)) goto no_disk; + if (vdisk(hfpd)) + goto v_disk; offset64 = get_long_host(iobuf + 44) | ((uae_u64)get_long_host(iobuf + 32) << 32); len = get_long_host(iobuf + 36); /* io_Length */ if (offset64 & bmask) { @@ -1854,6 +1888,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc case CMD_FORMAT: /* Format */ if (nodisk (hfd)) goto no_disk; + if (vdisk(hfpd)) + goto v_disk; if (is_writeprotected(hfd)) { error = 28; /* write protect */ } else { @@ -1886,6 +1922,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc #if defined(HDF_SUPPORT_NSD) || defined(HDF_SUPPORT_TD64) if (nodisk (hfd)) goto no_disk; + if (vdisk(hfpd)) + goto v_disk; if (is_writeprotected(hfd)) { error = 28; /* write protect */ } else { @@ -1910,6 +1948,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc #if HDF_SUPPORT_NSD case NSCMD_DEVICEQUERY: + if (vdisk(hfpd)) + goto v_disk; trap_put_long(ctx, dataptr + 0, 0); trap_put_long(ctx, dataptr + 4, 16); /* size */ trap_put_word(ctx, dataptr + 8, NSDEVTYPE_TRACKDISK); @@ -1920,8 +1960,14 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc #endif case CMD_GETDRIVETYPE: + if (vdisk(hfpd)) + goto v_disk; +#if HDF_SUPPORT_NSD actual = DRIVE_NEWSTYLE; break; +#else + goto no_cmd; +#endif case CMD_GETNUMTRACKS: { @@ -1938,6 +1984,8 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc getchsx (hfd, &cyl, &cylsec, &head, &tracksec); trap_put_long(ctx, dataptr + 0, hfd->ci.blocksize); size = hfd->virtsize / hfd->ci.blocksize; + if (!size) + size = hfd->ci.max_lba; if (size > 0x00ffffffff) size = 0xffffffff; trap_put_long(ctx, dataptr + 4, (uae_u32)size); @@ -1967,9 +2015,20 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc case CMD_CLEAR: case CMD_MOTOR: case CMD_SEEK: + break; + +#if HDF_SUPPORT_TD64 case TD_SEEK64: + if (vdisk(hfpd)) + goto v_disk; + break; +#endif +#ifdef HDF_SUPPORT_NSD case NSCMD_TD_SEEK64: - break; + if (vdisk(hfpd)) + goto v_disk; + break; +#endif case CMD_REMOVE: hfpd->changeint = get_long (request + 40); @@ -1980,26 +2039,34 @@ static uae_u32 hardfile_do_io (TrapContext *ctx, struct hardfiledata *hfd, struc break; case CMD_ADDCHANGEINT: + if (vdisk(hfpd)) + goto v_disk; error = add_async_request (hfpd, iobuf, request, ASYNC_REQUEST_CHANGEINT, get_long_host(iobuf + 40)); if (!error) async = 1; break; case CMD_REMCHANGEINT: + if (vdisk(hfpd)) + goto v_disk; release_async_request (hfpd, request); break; #if HDF_SUPPORT_DS case HD_SCSICMD: /* SCSI */ - if (!hfd->ci.sectors && !hfd->ci.surfaces && !hfd->ci.reserved) { - error = handle_scsi(ctx, iobuf, request, hfd, hfpd->sd); + if (vdisk(hfpd)) { + error = handle_scsi(ctx, iobuf, request, hfd, hfpd->sd, true); + } else if (!hfd->ci.sectors && !hfd->ci.surfaces && !hfd->ci.reserved) { + error = handle_scsi(ctx, iobuf, request, hfd, hfpd->sd, false); } else { /* we don't want users trashing their "partition" hardfiles with hdtoolbox */ - error = IOERR_NOCMD; - write_log (_T("UAEHF: HD_SCSICMD tried on regular HDF, unit %d\n"), unit); + error = handle_scsi(ctx, iobuf, request, hfd, hfpd->sd, true); } + actual = 30; // sizeof(struct SCSICmd) break; #endif case CD_EJECT: + if (vdisk(hfpd)) + goto v_disk; if (hfd->ci.sectors && hfd->ci.surfaces) { int len = get_long_host(iobuf + 36); if (len) { @@ -2024,6 +2091,9 @@ bad_command: bad_len: error = IOERR_BADLENGTH; break; +v_disk: + error = IOERR_BadDriveType; + break; no_disk: error = 29; /* no disk */ break; @@ -2036,9 +2106,6 @@ no_disk: put_long_host(iobuf + 32, actual); put_byte_host(iobuf + 31, error); - hf_log2 (_T("hf: unit=%d, request=%p, cmd=%d offset=%u len=%d, actual=%d error%=%d\n"), unit, request, - get_word_host(iobuf + 28), get_long_host(iobuf + 44), get_long_host(iobuf + 36), actual, error); - return async; } @@ -2049,15 +2116,12 @@ static uae_u32 REGPARAM2 hardfile_abortio (TrapContext *ctx) struct hardfiledata *hfd = get_hardfile_data_controller(unit); struct hardfileprivdata *hfpd = &hardfpd[unit]; - hf_log2 (_T("uaehf.device abortio ")); start_thread(ctx, unit); if (!hfd || !hfpd || !hfpd->thread_running) { trap_put_byte(ctx, request + 31, 32); - hf_log2 (_T("error\n")); return trap_get_byte(ctx, request + 31); } trap_put_byte(ctx, request + 31, -2); - hf_log2 (_T("unit=%d, request=%08X\n"), unit, request); abort_async (hfpd, request, -2, 0); return 0; } @@ -2117,10 +2181,7 @@ static uae_u32 REGPARAM2 hardfile_beginio (TrapContext *ctx) put_byte_host(iobuf + 31, 0); canquick = hardfile_canquick(ctx, hfd, iobuf); if (((flags & 1) && canquick) || (canquick < 0)) { - hf_log (_T("hf quickio unit=%d request=%p cmd=%d\n"), unit, request, cmd); - if (hardfile_do_io(ctx, hfd, hfpd, iobuf, request)) { - hf_log2 (_T("uaehf.device cmd %d bug with IO_QUICK\n"), cmd); - } + hardfile_do_io(ctx, hfd, hfpd, iobuf, request); uae_u8 v = get_byte_host(iobuf + 31); trap_put_bytes(ctx, iobuf + 8, request + 8, 48 - 8); xfree(iobuf); @@ -2128,7 +2189,6 @@ static uae_u32 REGPARAM2 hardfile_beginio (TrapContext *ctx) uae_ReplyMsg (request); return v; } else { - hf_log2 (_T("hf asyncio unit=%d request=%p cmd=%d\n"), unit, request, cmd); add_async_request(hfpd, iobuf, request, ASYNC_REQUEST_TEMP, 0); put_byte_host(iobuf + 30, get_byte_host(iobuf + 30) & ~1); trap_put_bytes(ctx, iobuf + 8, request + 8, 48 - 8); @@ -2139,7 +2199,7 @@ static uae_u32 REGPARAM2 hardfile_beginio (TrapContext *ctx) } } -static void *hardfile_thread (void *devs) +static int hardfile_thread (void *devs) { struct hardfileprivdata *hfpd = (struct hardfileprivdata *)devs; @@ -2162,7 +2222,6 @@ static void *hardfile_thread (void *devs) release_async_request (hfpd, request); uae_ReplyMsg (request); } else { - hf_log2 (_T("async request %08X\n"), request); trap_put_bytes(ctx, iobuf + 8, request + 8, 48 - 8); } uae_sem_post (&change_sem); @@ -2216,7 +2275,7 @@ void hardfile_install (void) uae_sem_init (&change_sem, 0, 1); ROM_hardfile_resname = ds (_T("uaehf.device")); - ROM_hardfile_resid = ds (_T("UAE hardfile.device 0.4")); + ROM_hardfile_resid = ds (_T("UAE hardfile.device 0.6")); nscmd_cmd = here (); dw (NSCMD_DEVICEQUERY); diff --git a/src/ide.cpp b/src/ide.cpp index a3db3636..3ca7dffd 100644 --- a/src/ide.cpp +++ b/src/ide.cpp @@ -6,10 +6,6 @@ * (c) 2006 - 2015 Toni Wilen */ -#define IDE_LOG 0 -#include -#include - #include "sysdeps.h" #include "options.h" @@ -20,7 +16,6 @@ #include "savestate.h" #include "scsi.h" #include "ide.h" -#include "newcpu.h" /* STATUS bits */ #define IDE_STATUS_ERR 0x01 // 0 @@ -45,16 +40,17 @@ #define ATAPI_MAX_TRANSFER 32768 -void ata_parse_identity(uae_u8 *out, struct uaedev_config_info *uci, bool *lba48, int *max_multiple) +void ata_parse_identity(uae_u8 *out, struct uaedev_config_info *uci, bool *lba, bool *lba48, int *max_multiple) { - *lba48 = false; - *max_multiple = 0; struct uaedev_config_info uci2; - uae_u16 v; memcpy(&uci2, uci, sizeof(struct uaedev_config_info)); + *lba = false; + *lba48 = false; + *max_multiple = 0; + uci->blocksize = 512; uci->pcyls = (out[1 * 2 + 0] << 8) | (out[1 * 2 + 1] << 0); @@ -67,9 +63,9 @@ void ata_parse_identity(uae_u8 *out, struct uaedev_config_info *uci, bool *lba48 uci->psecs = uci2.psecs; } - v = (out[59 * 2 + 0] << 8) | (out[59 * 2 + 1] << 0); - if (v & 1) { // multiple mode? - *max_multiple = ((out[47 * 2 + 0] << 8) | (out[47 * 2 + 1] << 0)) & 0xff; + v = (out[47 * 2 + 0] << 8) | (out[47 * 2 + 1] << 0); + if (v & 255) { // multiple mode? + *max_multiple = v & 255; } v = (out[53 * 2 + 0] << 8) | (out[53 * 2 + 1] << 0); @@ -82,9 +78,10 @@ void ata_parse_identity(uae_u8 *out, struct uaedev_config_info *uci, bool *lba48 v = (out[49 * 2 + 0] << 8) | (out[49 * 2 + 1] << 0); if (v & (1 << 9)) { // LBA supported? uci->max_lba = (out[60 * 2 + 0] << 24) | (out[60 * 2 + 1] << 16) | (out[61 * 2 + 0] << 8) | (out[61 * 2 + 1] << 0); + *lba = true; } v = (out[83 * 2 + 0] << 8) | (out[83 * 2 + 1] << 0); - if ((v & 0xc000) == 0x4000 && (v & (1 << 10))) { // LBA48 supported? + if ((v & 0xc000) == 0x4000 && (v & (1 << 10)) && (*lba)) { // LBA48 supported? *lba48 = true; uci->max_lba = (out[100 * 2 + 0] << 24) | (out[100 * 2 + 1] << 16) | (out[101 * 2 + 0] << 8) | (out[101 * 2 + 1] << 0); uci->max_lba <<= 32; @@ -126,7 +123,7 @@ static void ql(uae_u8 *d, int o) d[o + 7] = t; } -void ata_byteswapidentity(uae_u8 *d) +static void ata_byteswapidentity(uae_u8 *d) { for (int i = 0; i < 512; i += 2) { @@ -146,6 +143,28 @@ void ata_byteswapidentity(uae_u8 *d) ql(d, 230); } +static void pl(struct ide_hdf *ide, int offset, uae_u32 l) +{ + if (ide->byteswap) { + l = ((l >> 24) & 0x000000ff) | ((l >> 8) & 0x0000ff00) | ((l << 8) & 0x00ff0000) | ((l << 24) & 0xff000000); + } + ide->secbuf[offset * 2 + 0] = l; + ide->secbuf[offset * 2 + 1] = l >> 8; + ide->secbuf[offset * 2 + 2] = l >> 16; + ide->secbuf[offset * 2 + 3] = l >> 24; +} + +static void pq(struct ide_hdf *ide, int offset, uae_u64 q) +{ + if (ide->byteswap) { + pl(ide, offset + 0, q >> 32); + pl(ide, offset + 2, q >> 0); + } else { + pl(ide, offset + 0, q >> 0); + pl(ide, offset + 2, q >> 32); + } +} + static void pw (struct ide_hdf *ide, int offset, uae_u16 w) { if (ide->byteswap) { @@ -224,8 +243,6 @@ static bool ide_interrupt_do (struct ide_hdf *ide) if (ide->intdrq) ide->regs.ide_status |= IDE_STATUS_DRQ; ide->regs.ide_status &= ~IDE_STATUS_BSY; - if (IDE_LOG > 1) - write_log (_T("IDE INT %02X -> %02X\n"), os, ide->regs.ide_status); ide->intdrq = false; ide->irq_delay = 0; if (ide->regs.ide_devcon & 2) @@ -235,36 +252,6 @@ static bool ide_interrupt_do (struct ide_hdf *ide) return true; } -bool ide_drq_check(struct ide_hdf *idep) -{ - for (int i = 0; idep && i < 2; i++) { - struct ide_hdf *ide = i == 0 ? idep : idep->pair; - if (ide) { - if (ide->regs.ide_status & IDE_STATUS_DRQ) - return true; - } - } - return false; -} - -bool ide_irq_check(struct ide_hdf *idep, bool edge_triggered) -{ - for (int i = 0; idep && i < 2; i++) { - struct ide_hdf *ide = i == 0 ? idep : idep->pair; - if (ide->irq) { - if (edge_triggered) { - if (ide->irq_new) { - ide->irq_new = false; - return true; - } - continue; - } - return true; - } - } - return false; -} - bool ide_interrupt_hsync(struct ide_hdf *idep) { bool irq = false; @@ -344,71 +331,63 @@ static void ide_identity_buffer(struct ide_hdf *ide) else _stprintf (tmp, _T("UAE-IDE %s"), ide->hdhfd.hfd.product_id); ps (ide, 27, tmp, 40); /* model */ - pw (ide, 47, ide->max_multiple_mode >> (ide->blocksize / 512 - 1)); /* max sectors in multiple mode */ + pw(ide, 47, ide->max_multiple_mode ? (0x8000 | (ide->max_multiple_mode >> (ide->blocksize / 512 - 1))) : 0); /* max sectors in multiple mode */ pw (ide, 48, 1); - pw (ide, 49, (1 << 9) | (1 << 8)); /* LBA and DMA supported */ + pw(ide, 49, (ide->lba ? (1 << 9) : 0) | (1 << 8)); /* LBA and DMA supported */ pw (ide, 51, 0x200); /* PIO cycles */ pw (ide, 52, 0x200); /* DMA cycles */ - pw (ide, 53, 1 | 2 | 4); + pw(ide, 53, 1 | (ide->lba ? 2 | 4 : 0)); // b0 = 54-58 valid b1 = 64-70 valid b2 = 88 valid pw (ide, 54, ide->hdhfd.cyls); pw (ide, 55, ide->hdhfd.heads); pw (ide, 56, ide->hdhfd.secspertrack); - uae_u64 totalsecs = ide->hdhfd.cyls * ide->hdhfd.heads * ide->hdhfd.secspertrack; - pw (ide, 57, (uae_u16)totalsecs); - pw (ide, 58, (uae_u16)(totalsecs >> 16)); - pw (ide, 59, 1); /* Multiple mode supported */ - totalsecs = ide->blocksize ? ide->hdhfd.size / ide->blocksize : 0; - if (totalsecs > 0x0fffffff) - totalsecs = 0x0fffffff; - pw (ide, 60, (uae_u16)totalsecs); - pw (ide, 61, (uae_u16)(totalsecs >> 16)); - pw (ide, 62, 0x0f); - pw (ide, 63, 0x0f); - if (ide->ata_level) { - pw (ide, 64, ide->ata_level ? 0x03 : 0x00); /* PIO3 and PIO4 */ - pw (ide, 65, 120); /* MDMA2 supported */ - pw (ide, 66, 120); - pw (ide, 67, 120); - pw (ide, 68, 120); - pw (ide, 80, (1 << 1) | (1 << 2) | (1 << 3) | (1 << 4) | (1 << 5) | (1 << 6)); /* ATA-1 to ATA-6 */ - pw (ide, 81, 0x1c); /* ATA revision */ - pw (ide, 82, (1 << 14) | (atapi ? 0x10 | 4 : 0)); /* NOP, ATAPI: PACKET and Removable media features supported */ - pw (ide, 83, (1 << 14) | (1 << 13) | (1 << 12) | (ide->lba48 ? (1 << 10) : 0)); /* cache flushes, LBA 48 supported */ - pw (ide, 84, 1 << 14); - pw (ide, 85, 1 << 14); - pw (ide, 86, (1 << 14) | (1 << 13) | (1 << 12) | (ide->lba48 ? (1 << 10) : 0)); /* cache flushes, LBA 48 enabled */ - pw (ide, 87, 1 << 14); - pw (ide, 88, (1 << 5) | (1 << 4) | (1 << 3) | (1 << 2) | (1 << 1) | (1 << 0)); /* UDMA modes */ - pw (ide, 93, (1 << 14) | (1 << 13) | (1 << 0)); - if (ide->lba48) { - totalsecs = ide->hdhfd.size / ide->blocksize; - pw (ide, 100, (uae_u16)(totalsecs >> 0)); - pw (ide, 101, (uae_u16)(totalsecs >> 16)); - pw (ide, 102, (uae_u16)(totalsecs >> 32)); - pw (ide, 103, (uae_u16)(totalsecs >> 48)); - } + uae_u64 totalsecs = (uae_u64)ide->hdhfd.cyls * ide->hdhfd.heads * ide->hdhfd.secspertrack; + pl(ide, 57, totalsecs); + pw(ide, 59, ide->max_multiple_mode ? (0x100 | ide->max_multiple_mode >> (ide->blocksize / 512 - 1)) : 0); /* Multiple mode supported */ + pw(ide, 62, 0x0f); + pw(ide, 63, 0x0f); + if (ide->lba) { + totalsecs = ide->blocksize ? ide->hdhfd.size / ide->blocksize : 0; + if (totalsecs > 0x0fffffff) + totalsecs = 0x0fffffff; + pl(ide, 60, totalsecs); + if (ide->ata_level > 0) { + pw (ide, 64, ide->ata_level ? 0x03 : 0x00); /* PIO3 and PIO4 */ + pw (ide, 65, 120); /* MDMA2 supported */ + pw (ide, 66, 120); + pw (ide, 67, 120); + pw (ide, 68, 120); + pw (ide, 80, (1 << 1) | (1 << 2) | (1 << 3) | (1 << 4) | (1 << 5) | (1 << 6)); /* ATA-1 to ATA-6 */ + pw (ide, 81, 0x1c); /* ATA revision */ + pw (ide, 82, (1 << 14) | (atapi ? 0x10 | 4 : 0)); /* NOP, ATAPI: PACKET and Removable media features supported */ + pw (ide, 83, (1 << 14) | (1 << 13) | (1 << 12) | (ide->lba48 ? (1 << 10) : 0)); /* cache flushes, LBA 48 supported */ + pw (ide, 84, 1 << 14); + pw (ide, 85, 1 << 14); + pw (ide, 86, (1 << 14) | (1 << 13) | (1 << 12) | (ide->lba48 ? (1 << 10) : 0)); /* cache flushes, LBA 48 enabled */ + pw (ide, 87, 1 << 14); + pw (ide, 88, (1 << 5) | (1 << 4) | (1 << 3) | (1 << 2) | (1 << 1) | (1 << 0)); /* UDMA modes */ + pw (ide, 93, (1 << 14) | (1 << 13) | (1 << 0)); + if (ide->lba48) { + totalsecs = ide->hdhfd.size / ide->blocksize; + pq(ide, 100, totalsecs); + } + } } v = ide->multiple_mode; pwor(ide, 59, v > 0 ? 0x100 : 0); - if (!atapi && cf) - { + if (!atapi && cf) { pw(ide, 0, 0x848a); - } - else if (!atapi && !cf) - { + } else if (!atapi && !cf) { pwand(ide, 0, 0x8000); } } static void ide_identify_drive (struct ide_hdf *ide) { - if (!ide_isdrive (ide)) { + if (!ide_isdrive (ide) || ide->ata_level < 0) { ide_fail (ide); return; } - if (IDE_LOG > 0) - write_log (_T("IDE%d identify drive\n"), ide->num); ide_data_ready (ide); ide->direction = 0; ide_identity_buffer(ide); @@ -441,11 +420,6 @@ static void reset_device (struct ide_hdf *ide, bool both) set_signature (ide->pair); } -void ide_reset_device(struct ide_hdf *ide) -{ - reset_device(ide, true); -} - static void ide_execute_drive_diagnostics (struct ide_hdf *ide, bool irq) { reset_device (ide, irq); @@ -463,7 +437,7 @@ static void ide_initialize_drive_parameters (struct ide_hdf *ide) if (ide->hdhfd.hfd.ci.pcyls) ide->hdhfd.cyls = ide->hdhfd.hfd.ci.pcyls; else - ide->hdhfd.cyls = (ide->hdhfd.size / ide->blocksize) / (ide->hdhfd.secspertrack * ide->hdhfd.heads); + ide->hdhfd.cyls = (ide->hdhfd.size / ide->blocksize) / ((uae_u64)ide->hdhfd.secspertrack * ide->hdhfd.heads); if (ide->hdhfd.heads * ide->hdhfd.cyls * ide->hdhfd.secspertrack > 16515072 || ide->lba48) { if (ide->hdhfd.hfd.ci.pcyls) ide->hdhfd.cyls = ide->hdhfd.hfd.ci.pcyls; @@ -481,22 +455,29 @@ static void ide_initialize_drive_parameters (struct ide_hdf *ide) ide_interrupt (ide); } -static void ide_set_multiple_mode(struct ide_hdf *ide) +static void ide_set_multiple_mode (struct ide_hdf *ide) { - write_log(_T("IDE%d drive multiple mode = %d\n"), ide->num, ide->regs.ide_nsector); - if (ide->regs.ide_nsector > (ide->max_multiple_mode >> (ide->blocksize / 512 - 1))) - { + if (ide->ata_level < 0) { ide_fail(ide); + return; } - else - { - ide->multiple_mode = ide->regs.ide_nsector; + + write_log (_T("IDE%d drive multiple mode = %d\n"), ide->num, ide->regs.ide_nsector); + if (ide->regs.ide_nsector > (ide->max_multiple_mode >> (ide->blocksize / 512 - 1))) { + ide_fail(ide); + } else { + ide->multiple_mode = ide->regs.ide_nsector; } - ide_interrupt(ide); + ide_interrupt (ide); } static void ide_set_features (struct ide_hdf *ide) { + if (ide->ata_level < 0) { + ide_fail(ide); + return; + } + int type = ide->regs.ide_nsector >> 3; int mode = ide->regs.ide_nsector & 7; @@ -505,11 +486,9 @@ static void ide_set_features (struct ide_hdf *ide) { // 8-bit mode case 1: - ide->mode_8bit = true; ide_interrupt(ide); break; case 0x81: - ide->mode_8bit = false; ide_interrupt(ide); break; // write cache @@ -523,27 +502,21 @@ static void ide_set_features (struct ide_hdf *ide) } } -static void get_lbachs(struct ide_hdf *ide, uae_u64 *lbap, unsigned int *cyl, unsigned int *head, unsigned int *sec) +static void get_lbachs (struct ide_hdf *ide, uae_u64 *lbap, unsigned int *cyl, unsigned int *head, unsigned int *sec) { - if (ide->lba48 && ide->lba48cmd && (ide->regs.ide_select & 0x40)) - { + if (ide->lba48 && ide->lba48cmd && (ide->regs.ide_select & 0x40)) { uae_u64 lba; lba = (ide->regs.ide_hcyl << 16) | (ide->regs.ide_lcyl << 8) | ide->regs.ide_sector; - lba |= ((ide->regs.ide_hcyl2 << 16) | (ide->regs.ide_lcyl2 << 8) | ide->regs.ide_sector2) << 24; + lba |= ((uae_u64)(((ide->regs.ide_hcyl2 << 16) | (ide->regs.ide_lcyl2 << 8) | ide->regs.ide_sector2))) << 24; *lbap = lba; - } - else - { - if (ide->regs.ide_select & 0x40) - { + } else { + if ((ide->regs.ide_select & 0x40) && ide->lba) { *lbap = ((ide->regs.ide_select & 15) << 24) | (ide->regs.ide_hcyl << 16) | (ide->regs.ide_lcyl << 8) | ide->regs.ide_sector; - } - else - { + } else { *cyl = (ide->regs.ide_hcyl << 8) | ide->regs.ide_lcyl; *head = ide->regs.ide_select & 15; *sec = ide->regs.ide_sector; - *lbap = (((*cyl) * ide->hdhfd.heads + (*head)) * ide->hdhfd.secspertrack) + (*sec) - 1; + *lbap = (((uae_u64)(*cyl) * ide->hdhfd.heads + (*head)) * ide->hdhfd.secspertrack) + (*sec) - 1; } } } @@ -582,7 +555,7 @@ static void put_lbachs (struct ide_hdf *ide, uae_u64 lba, unsigned int cyl, unsi ide->regs.ide_lcyl2 = (lba >> 8) & 0xff; ide->regs.ide_sector2 = lba & 0xff; } else { - if (ide->regs.ide_select & 0x40) { + if ((ide->regs.ide_select & 0x40) && ide->lba) { lba += inc; ide->regs.ide_select &= ~15; ide->regs.ide_select |= (lba >> 24) & 15; @@ -682,8 +655,6 @@ static bool atapi_set_size (struct ide_hdf *ide) } else { ide->packet_transfer_size = 12; } - if (IDE_LOG > 1) - write_log (_T("ATAPI data transfer %d/%d bytes\n"), ide->packet_transfer_size, ide->data_size); return true; } @@ -694,8 +665,6 @@ static void atapi_packet (struct ide_hdf *ide) if (ide->packet_data_size == 65535) ide->packet_data_size = 65534; ide->data_size = 12; - if (IDE_LOG > 0) - write_log (_T("ATAPI packet command. Data size = %d\n"), ide->packet_data_size); ide->packet_state = 1; ide->data_multi = 1; ide->data_offset = 0; @@ -709,11 +678,6 @@ static void do_packet_command (struct ide_hdf *ide) { memcpy (ide->scsi->cmd, ide->secbuf, 12); ide->scsi->cmd_len = 12; - if (IDE_LOG > 0) { - uae_u8 *c = ide->scsi->cmd; - write_log (_T("ATASCSI %02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x.%02x\n"), - c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7], c[8], c[9], c[10], c[11]); - } ide->direction = 0; scsi_emulate_analyze (ide->scsi); if (ide->scsi->direction <= 0) { @@ -762,8 +726,6 @@ static void do_process_packet_command (struct ide_hdf *ide) if (atapi_set_size (ide)) { ide->intdrq = true; } else { - if (IDE_LOG > 1) - write_log(_T("IDE%d ATAPI write finished, %d bytes\n"), ide->num, ide->data_size); memcpy (&ide->scsi->buffer, ide->secbuf, ide->data_size); ide->scsi->data_len = ide->data_size; scsi_emulate_cmd (ide->scsi); @@ -789,12 +751,8 @@ static void do_process_rw_command (struct ide_hdf *ide) nsec = get_nsec (ide); get_lbachs (ide, &lba, &cyl, &head, &sec); - if (IDE_LOG > 1) - write_log (_T("IDE%d off=%d, nsec=%d (%d) lba48=%d\n"), ide->num, (uae_u32)lba, nsec, ide->multiple_mode, ide->lba48 + ide->lba48cmd); if (nsec > ide->max_lba - lba) { nsec = ide->max_lba - lba; - if (IDE_LOG > 1) - write_log (_T("IDE%d nsec changed to %d\n"), ide->num, nsec); } if (nsec <= 0) { ide_data_ready (ide); @@ -814,16 +772,10 @@ static void do_process_rw_command (struct ide_hdf *ide) } if (ide->direction) { - if (IDE_LOG > 1) - write_log (_T("IDE%d write, %d/%d bytes, buffer offset %d\n"), ide->num, nsec * ide->blocksize, nsec_total * ide->blocksize, ide->buffer_offset); } else { if (ide->buffer_offset == 0) { hdf_read(&ide->hdhfd.hfd, ide->secbuf, ide->start_lba * ide->blocksize, ide->start_nsec * ide->blocksize); - if (IDE_LOG > 1) - write_log(_T("IDE%d initial read, %d bytes\n"), ide->num, nsec_total * ide->blocksize); } - if (IDE_LOG > 1) - write_log (_T("IDE%d read, read %d/%d bytes, buffer offset=%d\n"), ide->num, nsec * ide->blocksize, nsec_total * ide->blocksize, ide->buffer_offset); } ide->intdrq = true; last = dec_nsec (ide, nsec) == 0; @@ -832,8 +784,6 @@ static void do_process_rw_command (struct ide_hdf *ide) put_lbachs (ide, lba, cyl, head, sec, last ? nsec - 1 : nsec); } if (last && ide->direction) { - if (IDE_LOG > 1) - write_log(_T("IDE%d write finished, %d bytes\n"), ide->num, ide->start_nsec * ide->blocksize); ide->intdrq = false; hdf_write (&ide->hdhfd.hfd, ide->secbuf, ide->start_lba * ide->blocksize, ide->start_nsec * ide->blocksize); } @@ -861,12 +811,12 @@ static void ide_read_sectors (struct ide_hdf *ide, int flags) int multi = flags & 1; ide->lba48cmd = (flags & 2) != 0; - if (multi && ide->multiple_mode == 0) { + if (multi && (ide->multiple_mode == 0 || ide->ata_level < 0)) { ide_fail (ide); return; } check_maxtransfer (ide, 1); - gui_flicker_led (LED_HD, ide->num, 1); + gui_flicker_led (LED_HD, ide->uae_unitnum, 1); nsec = get_nsec (ide); get_lbachs (ide, &lba, &cyl, &head, &sec); if (lba >= ide->max_lba) { @@ -874,9 +824,6 @@ static void ide_read_sectors (struct ide_hdf *ide, int flags) ide_fail_err (ide, IDE_ERR_IDNF); return; } - if (IDE_LOG > 0) - write_log (_T("IDE%d %s off=%d, sec=%d (%d) lba48=%d\n"), - ide->num, (flags & 4) ? _T("verify") : _T("read"), (uae_u32)lba, nsec, ide->multiple_mode, ide->lba48 + ide->lba48cmd); if (flags & 4) { // verify ide_interrupt(ide); @@ -899,12 +846,12 @@ static void ide_write_sectors (struct ide_hdf *ide, int flags) int multi = flags & 1; ide->lba48cmd = (flags & 2) != 0; - if (multi && ide->multiple_mode == 0) { + if (multi && (ide->multiple_mode == 0 || ide->ata_level < 0)) { ide_fail (ide); return; } check_maxtransfer (ide, 1); - gui_flicker_led (LED_HD, ide->num, 2); + gui_flicker_led (LED_HD, ide->uae_unitnum, 2); nsec = get_nsec (ide); get_lbachs (ide, &lba, &cyl, &head, &sec); if (lba >= ide->max_lba) { @@ -912,8 +859,6 @@ static void ide_write_sectors (struct ide_hdf *ide, int flags) ide_fail_err (ide, IDE_ERR_IDNF); return; } - if (IDE_LOG > 0) - write_log (_T("IDE%d write off=%d, sec=%d (%d) lba48=%d\n"), ide->num, (uae_u32)lba, nsec, ide->multiple_mode, ide->lba48 + ide->lba48cmd); if (nsec > ide->max_lba - lba) nsec = ide->max_lba - lba; if (nsec <= 0) { @@ -936,17 +881,15 @@ static void ide_format_track(struct ide_hdf *ide) unsigned int cyl, head, sec; uae_u64 lba; - gui_flicker_led(LED_HD, ide->num, 2); + gui_flicker_led(LED_HD, ide->uae_unitnum, 2); cyl = (ide->regs.ide_hcyl << 8) | ide->regs.ide_lcyl; head = ide->regs.ide_select & 15; sec = ide->regs.ide_nsector; - lba = (((cyl) * ide->hdhfd.heads + (head)) * ide->hdhfd.secspertrack); + lba = (((uae_u64)(cyl) * ide->hdhfd.heads + (head)) * ide->hdhfd.secspertrack); if (lba >= ide->max_lba) { ide_interrupt(ide); return; } - if (IDE_LOG > 0) - write_log(_T("IDE%d format cyl=%d, head=%d, sectors=%d\n"), ide->num, cyl, head, sec); ide->data_multi = 1; ide->data_offset = 0; @@ -963,8 +906,6 @@ static void ide_do_command (struct ide_hdf *ide, uae_u8 cmd) { int lba48 = ide->lba48; - if (IDE_LOG > 1) - write_log (_T("**** IDE%d command %02X\n"), ide->num, cmd); ide->regs.ide_status &= ~ (IDE_STATUS_DRDY | IDE_STATUS_DRQ | IDE_STATUS_ERR); ide->regs.ide_error = 0; ide->intdrq = false; @@ -1030,7 +971,11 @@ static void ide_do_command (struct ide_hdf *ide, uae_u8 cmd) } else if (cmd == 0x70) { /* seek */ ide_interrupt (ide); } else if (cmd == 0xe0 || cmd == 0xe1 || cmd == 0xe7 || cmd == 0xea) { /* standby now/idle/flush cache/flush cache ext */ - ide_interrupt (ide); + if (ide->ata_level < 0) { + ide_fail(ide); + } else { + ide_interrupt (ide); + } } else if (cmd == 0xe5) { /* check power mode */ ide->regs.ide_nsector = 0xff; ide_interrupt (ide); @@ -1048,8 +993,6 @@ static uae_u16 ide_get_data_2(struct ide_hdf *ide, int bussize) int inc = bussize ? 2 : 1; if (ide->data_size == 0) { - if (IDE_LOG > 0) - write_log (_T("IDE%d DATA but no data left!? %02X PC=%08X\n"), ide->num, ide->regs.ide_status, m68k_getpc ()); if (!ide_isdrive (ide)) return 0xffff; return 0; @@ -1060,21 +1003,15 @@ static uae_u16 ide_get_data_2(struct ide_hdf *ide, int bussize) } else { v = ide->secbuf[(ide->packet_data_offset + ide->data_offset)]; } - if (IDE_LOG > 4) - write_log (_T("IDE%d DATA read %04x\n"), ide->num, v); ide->data_offset += inc; if (ide->data_size < 0) ide->data_size += inc; else ide->data_size -= inc; if (ide->data_offset == ide->packet_transfer_size) { - if (IDE_LOG > 1) - write_log (_T("IDE%d ATAPI partial read finished, %d bytes remaining\n"), ide->num, ide->data_size); if (ide->data_size == 0 || ide->data_size == 1) { // 1 byte remaining: ignore, ATAPI has word transfer size. ide->packet_state = 0; atapi_data_done (ide); - if (IDE_LOG > 1) - write_log (_T("IDE%d ATAPI read finished, %d bytes\n"), ide->num, ide->packet_data_offset + ide->data_offset); irq = true; } else { process_packet_command (ide); @@ -1086,8 +1023,6 @@ static uae_u16 ide_get_data_2(struct ide_hdf *ide, int bussize) } else { v = ide->secbuf[(ide->buffer_offset + ide->data_offset)]; } - if (IDE_LOG > 4) - write_log (_T("IDE%d DATA read %04x %d/%d\n"), ide->num, v, ide->data_offset, ide->data_size); ide->data_offset += inc; if (ide->data_size < 0) { ide->data_size += inc; @@ -1105,8 +1040,6 @@ static uae_u16 ide_get_data_2(struct ide_hdf *ide, int bussize) write_log (_T("IDE%d read finished but DRQ was not active?\n"), ide->num); } ide->regs.ide_status &= ~IDE_STATUS_DRQ; - if (IDE_LOG > 1) - write_log (_T("IDE%d read finished\n"), ide->num); } } if (irq) @@ -1118,19 +1051,11 @@ uae_u16 ide_get_data(struct ide_hdf *ide) { return ide_get_data_2(ide, 1); } -uae_u8 ide_get_data_8bit(struct ide_hdf *ide) -{ - return (uae_u8)ide_get_data_2(ide, 0); -} static void ide_put_data_2(struct ide_hdf *ide, uae_u16 v, int bussize) { int inc = bussize ? 2 : 1; - if (IDE_LOG > 4) - write_log (_T("IDE%d DATA write %04x %d/%d\n"), ide->num, v, ide->data_offset, ide->data_size); if (ide->data_size == 0) { - if (IDE_LOG > 0) - write_log (_T("IDE%d DATA write without request!? %02X PC=%08X\n"), ide->num, ide->regs.ide_status, m68k_getpc ()); return; } ide_grow_buffer(ide, ide->packet_data_offset + ide->data_offset + 2); @@ -1153,10 +1078,6 @@ static void ide_put_data_2(struct ide_hdf *ide, uae_u16 v, int bussize) ide->data_size -= inc; if (ide->packet_state) { if (ide->data_offset == ide->packet_transfer_size) { - if (IDE_LOG > 0) { - uae_u16 v = (ide->regs.ide_hcyl << 8) | ide->regs.ide_lcyl; - write_log (_T("Data size after command received = %d (%d)\n"), v, ide->packet_data_size); - } process_packet_command (ide); } } else { @@ -1174,10 +1095,6 @@ void ide_put_data(struct ide_hdf *ide, uae_u16 v) { ide_put_data_2(ide, v, 1); } -void ide_put_data_8bit(struct ide_hdf *ide, uae_u8 v) -{ - ide_put_data_2(ide, v, 0); -} uae_u32 ide_read_reg (struct ide_hdf *ide, int ide_reg) { @@ -1274,8 +1191,6 @@ uae_u32 ide_read_reg (struct ide_hdf *ide, int ide_reg) break; } end: - if (IDE_LOG > 2 && ide_reg > 0 && (1 || ide->num > 0)) - write_log (_T("IDE%d GET register %d->%02X (%08X)\n"), ide->num, ide_reg, (uae_u32)v & 0xff, m68k_getpc ()); return v; } @@ -1286,8 +1201,6 @@ void ide_write_reg (struct ide_hdf *ide, int ide_reg, uae_u32 val) ide->regs1->ide_devcon &= ~0x80; /* clear HOB */ ide->regs0->ide_devcon &= ~0x80; /* clear HOB */ - if (IDE_LOG > 2 && ide_reg > 0 && (1 || ide->num > 0)) - write_log (_T("IDE%d PUT register %d=%02X (%08X)\n"), ide->num, ide_reg, (uae_u32)val & 0xff, m68k_getpc ()); switch (ide_reg) { @@ -1296,8 +1209,6 @@ void ide_write_reg (struct ide_hdf *ide, int ide_reg, uae_u32 val) case IDE_DEVCON: if ((ide->regs.ide_devcon & 4) == 0 && (val & 4) != 0) { reset_device (ide, true); - if (IDE_LOG > 1) - write_log (_T("IDE%d: SRST\n"), ide->num); } ide->regs0->ide_devcon = val; ide->regs1->ide_devcon = val; @@ -1337,10 +1248,6 @@ void ide_write_reg (struct ide_hdf *ide, int ide_reg, uae_u32 val) case IDE_SELECT: ide->regs0->ide_select = val; ide->regs1->ide_select = val; -#if IDE_LOG > 2 - if (ide->ide_drv != (val & 0x10) ? 1 : 0) - write_log (_T("DRIVE=%d\n"), (val & 0x10) ? 1 : 0); -#endif ide->pair->ide_drv = ide->ide_drv = (val & 0x10) ? 1 : 0; break; case IDE_STATUS: @@ -1354,7 +1261,7 @@ void ide_write_reg (struct ide_hdf *ide, int ide_reg, uae_u32 val) } } -static void *ide_thread (void *idedata) +static int ide_thread (void *idedata) { struct ide_thread_state *its = (struct ide_thread_state*)idedata; for (;;) { @@ -1398,6 +1305,9 @@ void ide_initialize(struct ide_hdf **idetable, int chpair) struct ide_hdf *ide0 = idetable[chpair * 2 + 0]; struct ide_hdf *ide1 = idetable[chpair * 2 + 1]; + if (!ide0 || !ide1) + return; + ide0->regs0 = &ide0->regs; ide0->regs1 = &ide1->regs; ide0->pair = ide1; @@ -1418,7 +1328,6 @@ void alloc_ide_mem (struct ide_hdf **idetable, int max, struct ide_thread_state struct ide_hdf *ide; if (!idetable[i]) { ide = idetable[i] = xcalloc (struct ide_hdf, 1); - ide->cd_unit_num = -1; } ide = idetable[i]; ide_grow_buffer(ide, 1024); @@ -1460,11 +1369,12 @@ struct ide_hdf *add_ide_unit (struct ide_hdf **idetable, int max, int ch, struct return NULL; ide->max_multiple_mode = 128; - ide->blocksize = ide->hdhfd.hfd.ci.blocksize; + ide->blocksize = ide->hdhfd.hfd.virtual_rdb ? 512 : ide->hdhfd.hfd.ci.blocksize; ide->max_lba = ide->hdhfd.size / ide->blocksize; ide->lba48 = (ide->hdhfd.hfd.ci.unit_special_flags & 1) || ide->hdhfd.size >= 128 * (uae_u64)0x40000000 ? 1 : 0; - gui_flicker_led (LED_HD, ch, -1); - ide->cd_unit_num = -1; + ide->lba = true; + ide->uae_unitnum = ci->uae_unitnum; + gui_flicker_led (LED_HD, ide->uae_unitnum, -1); ide->media_type = ci->controller_media_type; ide->ata_level = ci->unit_feature_level; if (!ide->ata_level && (ide->hdhfd.size >= 4 * (uae_u64)0x40000000 || ide->media_type)) @@ -1474,7 +1384,7 @@ struct ide_hdf *add_ide_unit (struct ide_hdf **idetable, int max, int ch, struct if (!ide->byteswap) ata_byteswapidentity(ide->secbuf); struct uaedev_config_info ci = { 0 }; - ata_parse_identity(ide->secbuf, &ci, &ide->lba48, &ide->max_multiple_mode); + ata_parse_identity(ide->secbuf, &ci, &ide->lba, &ide->lba48, &ide->max_multiple_mode); ide->hdhfd.cyls = ide->hdhfd.cyls_def = ci.pcyls; ide->hdhfd.heads = ide->hdhfd.heads_def = ci.pheads; ide->hdhfd.secspertrack = ide->hdhfd.secspertrack_def = ci.psecs; diff --git a/src/include/akiko.h b/src/include/akiko.h index b9dd591a..2649c953 100644 --- a/src/include/akiko.h +++ b/src/include/akiko.h @@ -4,14 +4,10 @@ #define AKIKO_BASE 0xb80000 #define AKIKO_BASE_END 0xb80100 /* ?? */ -extern void akiko_reset (void); extern int akiko_init (void); -extern void akiko_free (void); +extern void akiko_reset(int); -extern void AKIKO_hsync_handler (void); extern void akiko_mute (int); extern bool akiko_ntscmode(void); -extern void rethink_akiko (void); - #endif /* UAE_AKIKO_H */ diff --git a/src/include/ar.h b/src/include/ar.h index 806c290b..eab7d56c 100644 --- a/src/include/ar.h +++ b/src/include/ar.h @@ -70,4 +70,6 @@ extern uae_u32 hrtmem_start, hrtmem_size; extern uae_u8 ar_custom[2*256], ar_ciaa[16], ar_ciab[16]; +extern int hrtmon_lang; + #endif /* UAE_AR_H */ diff --git a/src/include/audio.h b/src/include/audio.h index 1cd0e00e..8b149a0e 100644 --- a/src/include/audio.h +++ b/src/include/audio.h @@ -1,10 +1,10 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * Sound emulation stuff - * - * Copyright 1995, 1996, 1997 Bernd Schmidt - */ +/* + * UAE - The Un*x Amiga Emulator + * + * Sound emulation stuff + * + * Copyright 1995, 1996, 1997 Bernd Schmidt + */ #ifndef UAE_AUDIO_H #define UAE_AUDIO_H @@ -15,6 +15,7 @@ #define MAX_EV ~0u void AUDxDAT (int nr, uae_u16 value); +void AUDxDAT (int nr, uae_u16 value, uaecptr addr); void AUDxVOL (int nr, uae_u16 value); void AUDxPER (int nr, uae_u16 value); void AUDxLCH (int nr, uae_u16 value); @@ -31,21 +32,88 @@ void audio_evhandler (void); void audio_hsync (void); void audio_update_adkmasks (void); void update_sound (double clk); +void update_cda_sound (double clk); void led_filter_audio (void); -void set_audio(void); -int audio_activate(void); +void set_audio (void); +int audio_activate (void); void audio_deactivate (void); +void audio_vsync (void); +void audio_sampleripper(int); +void write_wavheader (struct zfile *wavfile, uae_u32 size, uae_u32 freq); + +int audio_is_pull(void); +int audio_pull_buffer(void); +bool audio_finish_pull(void); +bool audio_is_pull_event(void); +bool audio_is_event_frame_possible(int); + +extern int sampleripper_enabled; + +typedef void(*CDA_CALLBACK)(int, void*); +typedef bool(*SOUND_STREAM_CALLBACK)(int, void*); + +extern int audio_enable_stream(bool, int, int, SOUND_STREAM_CALLBACK, void*); +extern void audio_state_stream_state(int, int*, int, unsigned int); + +struct cd_audio_state +{ + uae_s16 *cda_bufptr; + int cda_length, cda_userdata; + CDA_CALLBACK cda_next_cd_audio_buffer_callback; + void *cb_data; + int cda_volume[2]; + int cda_streamid = -1; +}; + +extern void audio_cda_new_buffer(struct cd_audio_state *cas, uae_s16 *buffer, int length, int userdata, CDA_CALLBACK next_cd_audio_buffer_callback, void *cb_data); +extern void audio_cda_volume(struct cd_audio_state *cas, int left, int right); extern int sound_cd_volume[2]; +extern int sound_paula_volume[2]; + +#define AUDIO_CHANNEL_MAX_STREAM_CH 8 +#define AUDIO_CHANNEL_STREAMS 9 #define AUDIO_CHANNELS_PAULA 4 enum { - SND_MONO, - SND_STEREO, - SND_NONE + SND_MONO, + SND_STEREO, + SND_4CH_CLONEDSTEREO, + SND_4CH, + SND_6CH_CLONEDSTEREO, + SND_6CH, + SND_NONE }; +static inline int get_audio_stereomode (int channels) +{ + switch (channels) + { + case 1: + return SND_MONO; + case 2: + return SND_STEREO; + case 4: + return SND_4CH; + case 6: + return SND_6CH; + } + return SND_STEREO; +} + +STATIC_INLINE int get_audio_nativechannels (int stereomode) +{ + int ch[] = { 1, 2, 4, 4, 6, 6, 0 }; + return ch[stereomode]; +} + +STATIC_INLINE int get_audio_amigachannels (int stereomode) +{ + int ch[] = { 1, 2, 2, 4, 2, 4, 0 }; + return ch[stereomode]; +} + STATIC_INLINE int get_audio_ismono (int stereomode) { return stereomode == 0; diff --git a/src/include/autoconf.h b/src/include/autoconf.h index 74d7fc16..1291517b 100644 --- a/src/include/autoconf.h +++ b/src/include/autoconf.h @@ -16,6 +16,7 @@ #define RTAREA_DEFAULT 0xf00000 #define RTAREA_BACKUP 0xef0000 +#define RTAREA_BACKUP_2 0xdb0000 #define RTAREA_SIZE 0x10000 #define RTAREA_TRAPS 0x3000 @@ -61,7 +62,9 @@ extern uae_u32 addr (int); extern void db (uae_u8); extern void dw (uae_u16); extern void dl (uae_u32); -extern uae_u32 ds_ansi (const uae_char*); +extern void df(uae_u8 b, int len); +extern uae_u32 dsf(uae_u8, int); +extern uae_u32 ds_ansi(const uae_char*); extern uae_u32 ds (const TCHAR*); extern uae_u32 ds_bstr_ansi (const uae_char*); extern uae_u8 dbg (uaecptr); @@ -69,6 +72,9 @@ extern void calltrap (uae_u32); extern void org (uae_u32); extern uae_u32 here (void); extern uaecptr makedatatable (uaecptr resid, uaecptr resname, uae_u8 type, uae_s8 priority, uae_u16 ver, uae_u16 rev); +//extern uae_u32 boot_rom_copy(TrapContext*, uaecptr, int); +//extern void add_rom_absolute(uaecptr addr); +//extern void save_rom_absolute(uaecptr addr); extern void align (int); @@ -88,18 +94,18 @@ extern uaecptr ROM_hardfile_resname, ROM_hardfile_resid; extern uaecptr ROM_hardfile_init; extern uaecptr filesys_initcode, filesys_initcode_ptr, filesys_initcode_real; -extern int is_hardfile (int unit_no); +//extern int is_hardfile (int unit_no); extern int nr_units (void); extern int nr_directory_units (struct uae_prefs*); extern uaecptr need_uae_boot_rom(struct uae_prefs*); struct mountedinfo { - uae_s64 size; - bool ismounted; - bool ismedia; + uae_s64 size; + bool ismounted; + bool ismedia; int error; - int nrcyls; + int nrcyls; TCHAR rootdir[MAX_DPATH]; }; @@ -110,7 +116,7 @@ extern TCHAR *validatedevicename (TCHAR *s, const TCHAR *def); extern TCHAR *validatevolumename (TCHAR *s, const TCHAR *def); int filesys_insert (int nr, const TCHAR *volume, const TCHAR *rootdir, bool readonly, int flags); -int filesys_eject (int nr); +//int filesys_eject (int nr); int filesys_media_change (const TCHAR *rootdir, int inserted, struct uaedev_config_data *uci); extern TCHAR *filesys_createvolname (const TCHAR *volname, const TCHAR *rootdir, struct zvolume *zv, const TCHAR *def); @@ -123,7 +129,7 @@ extern void filesys_cleanup (void); extern void filesys_prepare_reset (void); extern void filesys_start_threads (void); extern void filesys_flush_cache (void); -extern void filesys_free_handles (void); +//extern void filesys_free_handles (void); extern void filesys_vsync (void); extern void filesys_install (void); diff --git a/src/include/blitter.h b/src/include/blitter.h index 4470552d..fbfd269e 100644 --- a/src/include/blitter.h +++ b/src/include/blitter.h @@ -13,8 +13,8 @@ struct bltinfo { int blitzero; - int blitashift,blitbshift,blitdownashift,blitdownbshift; - uae_u16 bltadat, bltbdat, bltcdat,bltddat; + int blitashift, blitbshift, blitdownashift, blitdownbshift; + uae_u16 bltadat, bltbdat, bltcdat, bltddat; uae_u16 bltaold, bltahold, bltbold, bltbhold, bltafwm, bltalwm; int vblitsize,hblitsize; int bltamod,bltbmod,bltcmod,bltdmod; @@ -28,7 +28,7 @@ extern struct bltinfo blt_info; extern int blitter_nasty, blit_interrupt, blitter_dangerous_bpl; -extern void check_is_blit_dangerous(uaecptr *bplpt, int planes, int words); +extern void check_is_blit_dangerous (uaecptr *bplpt, int planes, int words); extern uae_u16 bltsize; extern uae_u16 bltcon0,bltcon1; @@ -47,6 +47,7 @@ STATIC_INLINE void maybe_blit(int hack) } extern void reset_blit (int); extern int blitnasty (void); +extern int blitnnasty (int); extern void blitter_handler (uae_u32); extern void build_blitfilltable (void); extern void do_blitter (int); diff --git a/src/include/blkdev.h b/src/include/blkdev.h index 32db4330..9459c1e5 100644 --- a/src/include/blkdev.h +++ b/src/include/blkdev.h @@ -9,9 +9,6 @@ #define SCSI_UNIT_DEFAULT 0 #define SCSI_UNIT_IMAGE 1 -//#define device_debug write_log -#define device_debug - #define INQ_DASD 0x00 /* Direct-access device (disk) */ #define INQ_SEQD 0x01 /* Sequential-access device (tape) */ #define INQ_PRTD 0x02 /* Printer device */ @@ -31,7 +28,6 @@ #define INQ_NOTPR 0x1F /* Logical unit not present (SCSI-1) */ #define MAX_TOC_ENTRIES 103 - struct cd_toc { uae_u8 adr, control; @@ -43,7 +39,6 @@ struct cd_toc uae_u8 zero; uae_u8 crc[2]; }; - struct cd_toc_head { int first_track, first_track_offset; @@ -69,23 +64,12 @@ struct cd_toc_head struct device_info { bool open; - int type; - int media_inserted; + int type; + int media_inserted; int audio_playing; - int removable; - int write_protected; - int cylinders; - int trackspercylinder; - int sectorspertrack; - int bytespersector; - int bus, target, lun; - int unitnum; - TCHAR label[MAX_DPATH]; + int unitnum; + TCHAR label[MAX_DPATH]; TCHAR mediapath[MAX_DPATH]; - TCHAR vendorid[10]; - TCHAR productid[18]; - TCHAR revision[6]; - const TCHAR* backend; struct cd_toc_head toc; TCHAR system_id[33]; TCHAR volume_id[33]; @@ -146,34 +130,23 @@ struct device_functions toc_func toc; read_func read; rawread_func rawread; - write_func write; - isatapi_func isatapi; ismedia_func ismedia; - - scsiemu_func scsiemu; }; -extern int device_func_init(int flags); +static int device_func_init(int flags); extern void device_func_free(void); extern void device_func_reset(void); -extern int sys_command_open(int unitnum); -extern void sys_command_close(int unitnum); -extern struct device_info* sys_command_info(int unitnum, struct device_info* di, int); -extern int sys_command_cd_pause(int unitnum, int paused); -extern void sys_command_cd_stop(int unitnum); -extern int sys_command_cd_play(int unitnum, int startlsn, int endlsn, int); -extern int sys_command_cd_play(int unitnum, int startlsn, int endlsn, int scan, play_status_callback statusfunc, - play_subchannel_callback subfunc); -extern uae_u32 sys_command_cd_volume(int unitnum, uae_u16 volume_left, uae_u16 volume_right); -extern int sys_command_cd_qcode(int unitnum, uae_u8*, int lsn, bool all); -extern int sys_command_cd_toc(int unitnum, struct cd_toc_head*); -extern int sys_command_cd_read(int unitnum, uae_u8* data, int block, int size); -extern int sys_command_cd_rawread(int unitnum, uae_u8* data, int sector, int size, int sectorsize); -int sys_command_cd_rawread(int unitnum, uae_u8* data, int sector, int size, int sectorsize, uae_u8 sectortype, - uae_u8 scsicmd9, uae_u8 subs); -extern int sys_command_ismedia(int unitnum, int quick); -extern struct device_info* sys_command_info_session(int unitnum, struct device_info* di, int, int); +extern void sys_command_close (int unitnum); +extern struct device_info *sys_command_info (int unitnum, struct device_info *di, int); +extern int sys_command_cd_pause (int unitnum, int paused); +extern void sys_command_cd_stop (int unitnum); +extern int sys_command_cd_play (int unitnum, int startlsn, int endlsn, int scan, play_status_callback statusfunc, play_subchannel_callback subfunc); +extern uae_u32 sys_command_cd_volume (int unitnum, uae_u16 volume_left, uae_u16 volume_right); +extern int sys_command_cd_qcode (int unitnum, uae_u8*, int lsn, bool all); +extern int sys_command_cd_toc (int unitnum, struct cd_toc_head*); +extern int sys_command_cd_rawread (int unitnum, uae_u8 *data, int sector, int size, int sectorsize); +extern int sys_command_ismedia (int unitnum, int quick); extern void blkdev_vsync(void); extern void restore_blkdev_start(void); @@ -185,12 +158,10 @@ extern uae_u8 tobcd(uae_u8 v); extern int fromlongbcd(uae_u8 * p); extern void tolongbcd(uae_u8* p, int v); -extern void blkdev_default_prefs(struct uae_prefs* p); -extern void blkdev_fix_prefs(struct uae_prefs* p); -extern int isaudiotrack(struct cd_toc_head*, int block); -extern int isdatatrack(struct cd_toc_head*, int block); -void sub_to_interleaved(const uae_u8* s, uae_u8* d); -void sub_to_deinterleaved(const uae_u8* s, uae_u8* d); +extern void blkdev_default_prefs (struct uae_prefs *p); +extern void blkdev_fix_prefs (struct uae_prefs *p); +extern int isaudiotrack (struct cd_toc_head*, int block); +void sub_to_interleaved (const uae_u8 *s, uae_u8 *d); enum cd_standard_unit { diff --git a/src/include/bsdsocket.h b/src/include/bsdsocket.h index 04fd25b8..9cdef9f9 100644 --- a/src/include/bsdsocket.h +++ b/src/include/bsdsocket.h @@ -11,11 +11,7 @@ #define UAE_BSDSOCKET_H #include "uae/types.h" - -#define BSD_TRACING_ENABLED 0 - -#define ISBSDTRACE (BSD_TRACING_ENABLED) -#define BSDTRACE(x) do { if (ISBSDTRACE) { write_log x; } } while(0) +#include "thread.h" extern int init_socket_layer (void); extern void deinit_socket_layer (void); @@ -94,7 +90,7 @@ struct socketbase { uae_u32 timeout; uae_u32 sigmp; #endif - TrapContext *context; + TrapContext *context; }; #define LIBRARY_SIZEOF 36 diff --git a/src/include/cd32_fmv.h b/src/include/cd32_fmv.h index ea47f285..f04d226d 100644 --- a/src/include/cd32_fmv.h +++ b/src/include/cd32_fmv.h @@ -4,10 +4,6 @@ #include "uae/types.h" extern addrbank *cd32_fmv_init (struct autoconfig_info *aci); -extern void cd32_fmv_reset(void); -extern void cd32_fmv_free(void); -extern void rethink_cd32fmv(void); -extern void cd32_fmv_hsync_handler(void); extern void cd32_fmv_state(int state); extern void cd32_fmv_new_image(int, int, int, uae_u8*); diff --git a/src/include/cia.h b/src/include/cia.h index c7d192ff..1ba6989b 100644 --- a/src/include/cia.h +++ b/src/include/cia.h @@ -21,6 +21,7 @@ extern void CIAB_tod_handler (int); extern void cia_diskindex (void); extern void rethink_cias (void); +extern int resetwarning_do (int); extern void cia_set_overlay (bool); extern void rtc_hardreset(void); diff --git a/src/include/cpu_prefetch.h b/src/include/cpu_prefetch.h index 1237acd5..f4fe28cb 100644 --- a/src/include/cpu_prefetch.h +++ b/src/include/cpu_prefetch.h @@ -34,11 +34,11 @@ STATIC_INLINE void put_word_000(uaecptr addr, uae_u32 v) STATIC_INLINE uae_u32 get_disp_ea_000 (uae_u32 base, uae_u32 dp) { - int reg = (dp >> 12) & 15; - uae_s32 regd = regs.regs[reg]; - if ((dp & 0x800) == 0) - regd = (uae_s32)(uae_s16)regd; - return base + (uae_s8)dp + regd; + int reg = (dp >> 12) & 15; + uae_s32 regd = regs.regs[reg]; + if ((dp & 0x800) == 0) + regd = (uae_s32)(uae_s16)regd; + return base + (uae_s8)dp + regd; } #endif /* UAE_CPU_PREFETCH_H */ diff --git a/src/include/cpummu.h b/src/include/cpummu.h index e3fa1587..e982c4e2 100644 --- a/src/include/cpummu.h +++ b/src/include/cpummu.h @@ -36,7 +36,6 @@ #define MMU_TTR_BIT_ENABLED (1 << 15) #define MMU_TTR_BIT_SFIELD_ENABLED (1 << 14) #define MMU_TTR_BIT_SFIELD_SUPER (1 << 13) -#define MMU_TTR_SFIELD_SHIFT 13 #define MMU_TTR_BIT_WRITE_PROTECT (1 << 2) #define MMU_MMUSR_T (1 << 1) diff --git a/src/include/custom.h b/src/include/custom.h index a85a058d..cc784ea5 100644 --- a/src/include/custom.h +++ b/src/include/custom.h @@ -1,10 +1,10 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * custom chip support - * - * (c) 1995 Bernd Schmidt - */ +/* +* UAE - The Un*x Amiga Emulator +* +* custom chip support +* +* (c) 1995 Bernd Schmidt +*/ #ifndef UAE_CUSTOM_H #define UAE_CUSTOM_H @@ -13,7 +13,7 @@ #include "machdep/rpt.h" /* These are the masks that are ORed together in the chipset_mask option. - * If CSMASK_AGA is set, the ECS bits are guaranteed to be set as well. */ +* If CSMASK_AGA is set, the ECS bits are guaranteed to be set as well. */ #define CSMASK_ECS_AGNUS 1 #define CSMASK_ECS_DENISE 2 #define CSMASK_AGA 4 @@ -28,7 +28,6 @@ #define HPOS_SHIFT 3 extern void set_speedup_values(void); - extern int custom_init (void); extern void custom_prepare (void); extern void custom_reset (bool hardreset, bool keyboardreset); @@ -87,7 +86,10 @@ STATIC_INLINE void send_interrupt (int num) INTREQ_0 (0x8000 | (1 << num)); } extern void rethink_uae_int(void); -extern uae_u16 INTREQR(void); +STATIC_INLINE uae_u16 INTREQR (void) +{ + return intreq; +} STATIC_INLINE void safe_interrupt_set(bool i6) { @@ -164,9 +166,13 @@ extern unsigned long frametime, timeframes; extern uae_u16 htotal, vtotal, beamcon0; /* 100 words give you 1600 horizontal pixels. Should be more than enough for - * superhires. Don't forget to update the definition in genp2c.c as well. - * needs to be larger for superhires support */ +* superhires. Don't forget to update the definition in genp2c.c as well. +* needs to be larger for superhires support */ +#ifdef CUSTOM_SIMPLE +#define MAX_WORDS_PER_LINE 50 +#else #define MAX_WORDS_PER_LINE 100 +#endif extern uae_u32 hirestab_h[256][2]; extern uae_u32 lorestab_h[256][4]; @@ -195,13 +201,13 @@ extern int xbluecolor_s, xbluecolor_b, xbluecolor_m; #define RES_SHIFT(res) ((res) == RES_LORES ? 8 : (res) == RES_HIRES ? 4 : 2) /* get resolution from bplcon0 */ -STATIC_INLINE int GET_RES_DENISE(uae_u16 con0) +STATIC_INLINE int GET_RES_DENISE (uae_u16 con0) { if (!(currprefs.chipset_mask & CSMASK_ECS_DENISE)) con0 &= ~0x40; // SUPERHIRES return ((con0) & 0x40) ? RES_SUPERHIRES : ((con0) & 0x8000) ? RES_HIRES : RES_LORES; } -STATIC_INLINE int GET_RES_AGNUS(uae_u16 con0) +STATIC_INLINE int GET_RES_AGNUS (uae_u16 con0) { if (!(currprefs.chipset_mask & CSMASK_ECS_AGNUS)) con0 &= ~0x40; // SUPERHIRES @@ -235,8 +241,7 @@ extern bool isvga(void); extern int current_maxvpos (void); extern struct chipset_refresh *get_chipset_refresh(struct uae_prefs*); extern void compute_framesync(void); -extern void getsyncregisters(uae_u16 *phsstrt, uae_u16 *phsstop, uae_u16 *pvsstrt, uae_u16 *pvsstop); - +//extern void getsyncregisters(uae_u16 *phsstrt, uae_u16 *phsstop, uae_u16 *pvsstrt, uae_u16 *pvsstop); void custom_cpuchange(void); struct custom_store diff --git a/src/include/devices.h b/src/include/devices.h index 6dc067f8..96bad746 100644 --- a/src/include/devices.h +++ b/src/include/devices.h @@ -2,17 +2,56 @@ #define UAE_DEVICES_H void devices_reset(int hardreset); +void devices_reset_ext(int hardreset); void devices_vsync_pre(void); +void devices_vsync_post(void); void devices_hsync(void); void devices_rethink(void); -void devices_update_sound(double clk, double syncadjust); +void devices_rethink_all(void func(void)); +void devices_syncchange(void); +void update_sound (double clk); +STATIC_INLINE void devices_update_sound(double clk) +{ + update_sound (clk); +} + void devices_update_sync(double svpos, double syncadjust); -void reset_all_systems(void); void do_leave_program(void); void virtualdevice_init(void); void devices_restore_start(void); void device_check_config(void); void devices_pause(void); void devices_unpause(void); +void devices_unsafeperiod(void); + +typedef void (*DEVICE_INT)(int hardreset); +typedef void (*DEVICE_VOID)(void); + +void device_add_vsync_pre(DEVICE_VOID p); +void device_add_vsync_post(DEVICE_VOID p); +void device_add_hsync(DEVICE_VOID p); +void device_add_rethink(DEVICE_VOID p); +void device_add_check_config(DEVICE_VOID p); +void device_add_reset(DEVICE_INT p); +void device_add_reset_imm(DEVICE_INT p); +void device_add_exit(DEVICE_VOID p); + +#define IRQ_SOURCE_PCI 0 +#define IRQ_SOURCE_SOUND 1 +#define IRQ_SOURCE_NE2000 2 +#define IRQ_SOURCE_A2065 3 +#define IRQ_SOURCE_NCR 4 +#define IRQ_SOURCE_NCR9X 5 +#define IRQ_SOURCE_CPUBOARD 6 +#define IRQ_SOURCE_UAE 7 +#define IRQ_SOURCE_SCSI 8 +#define IRQ_SOURCE_WD 9 +#define IRQ_SOURCE_X86 10 +#define IRQ_SOURCE_GAYLE 11 +#define IRQ_SOURCE_CIA 12 +#define IRQ_SOURCE_CD32CDTV 13 +#define IRQ_SOURCE_IDE 14 +#define IRQ_SOURCE_MAX 15 + #endif /* UAE_DEVICES_H */ diff --git a/src/include/disk.h b/src/include/disk.h index df696c73..ce638e4b 100644 --- a/src/include/disk.h +++ b/src/include/disk.h @@ -11,14 +11,20 @@ #include "uae/types.h" -typedef enum { DRV_NONE = -1, DRV_35_DD = 0, DRV_35_HD, DRV_525_SD, DRV_35_DD_ESCOM, DRV_PC_ONLY_40, DRV_PC_ONLY_80, DRV_525_DD } drive_type; +typedef enum { DRV_NONE = -1, DRV_35_DD = 0, DRV_35_HD, DRV_525_SD, DRV_35_DD_ESCOM, DRV_PC_525_ONLY_40, DRV_PC_35_ONLY_80, DRV_PC_525_40_80, DRV_525_DD } drive_type; #define HISTORY_FLOPPY 0 #define HISTORY_CD 1 #define HISTORY_DIR 2 #define HISTORY_HDF 3 #define HISTORY_FS 4 -#define HISTORY_MAX 5 +#define HISTORY_TAPE 5 +#define HISTORY_GENLOCK_IMAGE 6 +#define HISTORY_GENLOCK_VIDEO 7 +#define HISTORY_GEO 8 +#define HISTORY_STATEFILE 9 +#define HISTORY_CONFIGFILE 10 +#define HISTORY_MAX 11 struct diskinfo { @@ -31,18 +37,41 @@ struct diskinfo TCHAR diskname[110]; }; +#define FLOPPY_RATE_500K 0 +#define FLOPPY_RATE_300K 1 +#define FLOPPY_RATE_250K 2 +#define FLOPPY_RATE_1M 3 + +struct floppy_reserved +{ + int num; + struct zfile *img; + bool wrprot; + int cyl; + int cyls; + int heads; + int secs; + int drive_cyls; + bool disk_changed; + int rate; +}; +void disk_reserved_setinfo(int num, int cyl, int head, int motor); +bool disk_reserved_getinfo(int num, struct floppy_reserved *fr); +void disk_reserved_reset_disk_change(int num); + extern void DISK_init (void); extern void DISK_free (void); extern void DISK_select (uae_u8 data); extern void DISK_select_set (uae_u8 data); extern uae_u8 DISK_status_ciaa (void); +extern uae_u8 DISK_status_ciab (uae_u8); extern void disk_eject (int num); extern int disk_empty (int num); extern void disk_insert (int num, const TCHAR *name); extern void disk_insert (int num, const TCHAR *name, bool forcedwriteprotect); extern void disk_insert_force (int num, const TCHAR *name, bool forcedwriteprotect); extern void DISK_vsync (void); -extern int DISK_validate_filename (struct uae_prefs *p, const TCHAR *fname, int leave_open, bool *wrprot, uae_u32 *crc32, struct zfile **zf); +extern int DISK_validate_filename (struct uae_prefs *p, const TCHAR *fname, TCHAR *outfname, int leave_open, bool *wrprot, uae_u32 *crc32, struct zfile **zf); extern void DISK_handler (uae_u32); extern void DISK_update (int hpos); extern void DISK_update_adkcon (int hpos, uae_u16 v); @@ -51,11 +80,16 @@ extern void DISK_reset (void); extern int disk_getwriteprotect (struct uae_prefs *p, const TCHAR *name); extern int disk_setwriteprotect (struct uae_prefs *p, int num, const TCHAR *name, bool writeprotected); extern bool disk_creatediskfile (struct uae_prefs *p, const TCHAR *name, int type, drive_type adftype, int hd, const TCHAR *disk_name, bool ffs, bool bootable, struct zfile *copyfrom); +extern void dumpdisk (const TCHAR*); extern int DISK_history_add (const TCHAR *name, int idx, int type, int donotcheck); extern TCHAR *DISK_history_get (int idx, int type); -int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di); -extern TCHAR *DISK_get_saveimagepath(const TCHAR *name, int type); +//int DISK_examine_image (struct uae_prefs *p, int num, struct diskinfo *di); +//extern TCHAR *DISK_get_saveimagepath(const TCHAR *name, int type); extern void DISK_reinsert (int num); +extern int disk_prevnext (int drive, int dir); +extern int disk_prevnext_name (TCHAR *img, int dir); + +extern bool gui_ask_disk(int drv, TCHAR*); extern void DSKLEN (uae_u16 v, int hpos); extern uae_u16 DSKBYTR (int hpos); @@ -68,6 +102,13 @@ extern uae_u16 disk_dmal (void); extern uaecptr disk_getpt (void); extern int disk_fifostatus (void); +extern int disk_debug_logging; +extern int disk_debug_mode; +extern int disk_debug_track; +#define DISK_DEBUG_DMA_READ 1 +#define DISK_DEBUG_DMA_WRITE 2 +#define DISK_DEBUG_PIO 4 + #define MAX_PREVIOUS_IMAGES 50 #endif /* UAE_DISK_H */ diff --git a/src/include/drawing.h b/src/include/drawing.h index d78e3948..91716665 100644 --- a/src/include/drawing.h +++ b/src/include/drawing.h @@ -1,8 +1,8 @@ /* - * Data used for communication between custom.c and drawing.c. - * - * Copyright 1996-1998 Bernd Schmidt - */ +* Data used for communication between custom.c and drawing.c. +* +* Copyright 1996-1998 Bernd Schmidt +*/ #ifndef UAE_DRAWING_H #define UAE_DRAWING_H @@ -11,8 +11,28 @@ #define SMART_UPDATE 1 -#define MAX_PLANES 8 +#ifdef SUPPORT_PENGUINS +#undef SMART_UPDATE +#define SMART_UPDATE 1 +#endif +#ifdef AGA +#define MAX_PLANES 8 +#else +#define MAX_PLANES 6 +#endif + +#define AMIGA_WIDTH_MAX (752 / 2) +#define AMIGA_HEIGHT_MAX (576 / 2) + +//#define NEWHSYNC + +#ifdef NEWHSYNC +#define DIW_DDF_OFFSET 9 +/* this many cycles starting from hpos=0 are visible on right border */ +#define HBLANK_OFFSET 13 +#define DISPLAY_LEFT_SHIFT 0x40 +#else /* According to the HRM, pixel data spends a couple of cycles somewhere in the chips before it appears on-screen. (TW: display emulation now does this automatically) */ #define DIW_DDF_OFFSET 1 @@ -20,17 +40,20 @@ before it appears on-screen. (TW: display emulation now does this automatically) /* this many cycles starting from hpos=0 are visible on right border */ #define HBLANK_OFFSET 9 /* We ignore that many lores pixels at the start of the display. These are - * invisible anyway due to hardware DDF limits. */ +* invisible anyway due to hardware DDF limits. */ #define DISPLAY_LEFT_SHIFT 0x38 #define DISPLAY_LEFT_SHIFT_SHRES (DISPLAY_LEFT_SHIFT << 2) +#endif #define PIXEL_XPOS(HPOS) (((HPOS)*2 - DISPLAY_LEFT_SHIFT + DIW_DDF_OFFSET - 1) << lores_shift) #define min_diwlastword (0) -#define max_diwlastword (PIXEL_XPOS(0x1d4>> 1)) +#define max_diwlastword (PIXEL_XPOS(0x1d4 >> 1)) extern int lores_shift, shres_shift, interlace_seen; -extern bool aga_mode; +extern bool aga_mode, direct_rgb; +extern int visible_left_border, visible_right_border; +extern int detected_screen_resolution; STATIC_INLINE int shres_coord_hw_to_window_x (int x) { @@ -42,14 +65,14 @@ STATIC_INLINE int shres_coord_hw_to_window_x (int x) STATIC_INLINE int coord_hw_to_window_x (int x) { - x -= DISPLAY_LEFT_SHIFT; + x -= DISPLAY_LEFT_SHIFT; return x << lores_shift; } STATIC_INLINE int coord_window_to_hw_x (int x) { x >>= lores_shift; - return x + DISPLAY_LEFT_SHIFT; + return x + DISPLAY_LEFT_SHIFT; } STATIC_INLINE int coord_diw_lores_to_window_x(int x) @@ -57,29 +80,22 @@ STATIC_INLINE int coord_diw_lores_to_window_x(int x) return (x - DISPLAY_LEFT_SHIFT + DIW_DDF_OFFSET - 1) << lores_shift; } -STATIC_INLINE int coord_diw_shres_to_window_x(int x) +STATIC_INLINE int coord_diw_shres_to_window_x (int x) { return (x - DISPLAY_LEFT_SHIFT_SHRES + DIW_DDF_OFFSET_SHRES - (1 << 2)) >> shres_shift; } -STATIC_INLINE int coord_diw_to_window_x (int x) -{ - return (x - DISPLAY_LEFT_SHIFT + DIW_DDF_OFFSET - 1) << lores_shift; -} - STATIC_INLINE int coord_window_to_diw_x (int x) { - x = coord_window_to_hw_x (x); - return x - DIW_DDF_OFFSET; + x = coord_window_to_hw_x (x); + return x - DIW_DDF_OFFSET; } -extern int framecnt; - /* color values in two formats: 12 (OCS/ECS) or 24 (AGA) bit Amiga RGB (color_regs), - * and the native color value; both for each Amiga hardware color register. - * - * !!! See color_reg_xxx functions below before touching !!! - */ +* and the native color value; both for each Amiga hardware color register. +* +* !!! See color_reg_xxx functions below before touching !!! +*/ #define CE_BORDERBLANK 0 #define CE_BORDERNTRANS 1 #define CE_BORDERSPRITE 2 @@ -100,104 +116,120 @@ STATIC_INLINE bool ce_is_borderntrans(uae_u8 data) struct color_entry { uae_u16 color_regs_ecs[32]; +#ifndef AGA + xcolnr acolors[32]; +#else xcolnr acolors[256]; uae_u32 color_regs_aga[256]; +#endif uae_u8 extra; }; +#ifdef AGA /* convert 24 bit AGA Amiga RGB to native color */ +/* warning: this is still ugly, but now works with either byte order */ #ifdef WORDS_BIGENDIAN # define CONVERT_RGB(c) \ ( xbluecolors[((uae_u8*)(&c))[3]] | xgreencolors[((uae_u8*)(&c))[2]] | xredcolors[((uae_u8*)(&c))[1]] ) #else -#define CONVERT_RGB(c) \ - ( xbluecolors[((uae_u8*)(&c))[0]] | xgreencolors[((uae_u8*)(&c))[1]] | xredcolors[((uae_u8*)(&c))[2]] ) -#define CONVERT_RGB_16(c) \ - ( xbluecolors[((uae_u8*)(&c))[0]] | xgreencolors[((uae_u8*)(&c))[1]] | xredcolors[((uae_u8*)(&c))[2]] ) +# define CONVERT_RGB(c) \ + ( xbluecolors[((uae_u8*)(&c))[0]] | xgreencolors[((uae_u8*)(&c))[1]] | xredcolors[((uae_u8*)(&c))[2]] ) +#endif +#else +#define CONVERT_RGB(c) 0 #endif -STATIC_INLINE xcolnr getxcolor (int c) +STATIC_INLINE xcolnr getxcolor(int c) { - if (aga_mode) +#ifdef AGA + if (direct_rgb) return CONVERT_RGB(c); else +#endif return xcolors[c]; } /* functions for reading, writing, copying and comparing struct color_entry */ STATIC_INLINE int color_reg_get (struct color_entry *ce, int c) { +#ifdef AGA if (aga_mode) return ce->color_regs_aga[c]; else +#endif return ce->color_regs_ecs[c]; } - STATIC_INLINE void color_reg_set (struct color_entry *ce, int c, int v) { +#ifdef AGA if (aga_mode) ce->color_regs_aga[c] = v; else +#endif ce->color_regs_ecs[c] = v; } - -STATIC_INLINE int color_reg_cmp(struct color_entry *ce1, struct color_entry *ce2) +STATIC_INLINE int color_reg_cmp (struct color_entry *ce1, struct color_entry *ce2) { int v; #ifdef AGA if (aga_mode) - v = memcmp(ce1->color_regs_aga, ce2->color_regs_aga, sizeof(uae_u32) * 256); + v = memcmp (ce1->color_regs_aga, ce2->color_regs_aga, sizeof (uae_u32) * 256); else #endif - v = memcmp(ce1->color_regs_ecs, ce2->color_regs_ecs, sizeof(uae_u16) * 32); + v = memcmp (ce1->color_regs_ecs, ce2->color_regs_ecs, sizeof (uae_u16) * 32); if (!v && ce1->extra == ce2->extra) return 0; return 1; } - /* ugly copy hack, is there better solution? */ STATIC_INLINE void color_reg_cpy (struct color_entry *dst, struct color_entry *src) { dst->extra = src->extra; - if (aga_mode) - /* copy acolors and color_regs_aga */ - memcpy (dst->acolors, src->acolors, sizeof(struct color_entry) - sizeof(uae_u16) * 32); - else - /* copy first 32 acolors and color_regs_ecs */ - memcpy(dst->color_regs_ecs, src->color_regs_ecs, sizeof(uae_u16) * 32 + sizeof(xcolnr) * 32); +#ifdef AGA + if (aga_mode) + /* copy acolors and color_regs_aga */ + memcpy (dst->acolors, src->acolors, sizeof(struct color_entry) - sizeof(uae_u16) * 32); + else +#endif + /* copy first 32 acolors and color_regs_ecs */ + memcpy (dst->color_regs_ecs, src->color_regs_ecs, sizeof(struct color_entry)); } /* - * The idea behind this code is that at some point during each horizontal - * line, we decide how to draw this line. There are many more-or-less - * independent decisions, each of which can be taken at a different horizontal - * position. - * Sprites and color changes are handled specially: There isn't a single decision, - * but a list of structures containing information on how to draw the line. - */ +* The idea behind this code is that at some point during each horizontal +* line, we decide how to draw this line. There are many more-or-less +* independent decisions, each of which can be taken at a different horizontal +* position. +* Sprites and color changes are handled specially: There isn't a single decision, +* but a list of structures containing information on how to draw the line. +*/ #define COLOR_CHANGE_BRDBLANK 0x80000000 #define COLOR_CHANGE_SHRES_DELAY 0x40000000 #define COLOR_CHANGE_HSYNC_HACK 0x20000000 #define COLOR_CHANGE_MASK 0xf0000000 struct color_change { - int linepos; - int regno; - unsigned int value; + int linepos; + int regno; + unsigned int value; }; /* 440 rather than 880, since sprites are always lores. */ +#ifdef UAE_MINI +#define MAX_PIXELS_PER_LINE 880 +#else #define MAX_PIXELS_PER_LINE 1760 +#endif -/* No divisors for MAX_PIXELS_PER_LINE; we support AGA and SHRES sprites */ -#define MAX_SPR_PIXELS (((MAXVPOS + 1)*2 + 1) * MAX_PIXELS_PER_LINE) +/* No divisors for MAX_PIXELS_PER_LINE; we support AGA and SHRES sprites */ +#define MAX_SPR_PIXELS (((MAXVPOS + 1) * 2 + 1) * MAX_PIXELS_PER_LINE) struct sprite_entry { - unsigned short pos; - unsigned short max; - unsigned int first_pixel; - bool has_attached; + unsigned short pos; + unsigned short max; + unsigned int first_pixel; + bool has_attached; }; struct sprite_stb @@ -217,7 +249,7 @@ extern uae_u16 spixels[MAX_SPR_PIXELS * 2]; #endif /* Way too much... */ -#define MAX_REG_CHANGE ((MAXVPOS + 1) * MAXHPOS) +#define MAX_REG_CHANGE ((MAXVPOS + 1) * 2 * MAXHPOS) extern struct color_entry *curr_color_tables, *prev_color_tables; @@ -226,7 +258,7 @@ extern struct color_change *curr_color_changes, *prev_color_changes; extern struct draw_info *curr_drawinfo, *prev_drawinfo; /* struct decision contains things we save across drawing frames for - * comparison (smart update stuff). */ +* comparison (smart update stuff). */ struct decision { /* Records the leftmost access of BPL1DAT. */ int plfleft, plfright, plflinelen; @@ -251,11 +283,11 @@ struct decision { }; /* Anything related to changes in hw registers during the DDF for one - * line. */ +* line. */ struct draw_info { - int first_sprite_entry, last_sprite_entry; - int first_color_change, last_color_change; - int nr_color_changes, nr_sprites; + int first_sprite_entry, last_sprite_entry; + int first_color_change, last_color_change; + int nr_color_changes, nr_sprites; }; extern struct decision line_decisions[2 * (MAXVPOS + 2) + 1]; @@ -266,8 +298,7 @@ extern uae_u8 line_data[(MAXVPOS + 2) * 2][MAX_PLANES * MAX_WORDS_PER_LINE * 2]; extern int coord_native_to_amiga_y (int); extern int coord_native_to_amiga_x (int); -extern void record_diw_line(int plfstrt, int first, int last); -extern void hardware_line_completed(int lineno); +extern void record_diw_line (int plfstrt, int first, int last); /* Determine how to draw a scan line. */ enum nln_how { @@ -287,17 +318,29 @@ enum nln_how { nln_lower_black_always }; -extern void hsync_record_line_state(int lineno, enum nln_how, int changed); -extern void halt_draw_frame(void); -extern void vsync_handle_redraw(int long_field, int lof_changed, uae_u16, uae_u16, bool drawlines); +extern void hsync_record_line_state (int lineno, enum nln_how, int changed); +extern void vsync_handle_redraw (int long_field, int lof_changed, uae_u16, uae_u16, bool drawlines); extern bool vsync_handle_check (void); +extern void draw_lines(int end, int section); extern void init_hardware_for_drawing_frame (void); extern void reset_drawing (void); extern void drawing_init (void); -extern bool notice_interlace_seen(bool); -extern void notice_resolution_seen(int, bool); +extern bool notice_interlace_seen (bool); +extern void notice_resolution_seen (int, bool); +//extern bool frame_drawn (); extern void redraw_frame(void); -extern void putpixel(uae_u8* buf, uae_u8* genlockbuf, int bpp, int x, xcolnr c8, int opaq); +extern void full_redraw_all(void); +extern bool draw_frame (struct vidbuffer*); +extern int get_custom_limits (int *pw, int *ph, int *pdx, int *pdy, int *prealh); +extern void store_custom_limits (int w, int h, int dx, int dy); +extern void set_custom_limits (int w, int h, int dx, int dy); +extern void check_custom_limits (void); +extern void get_custom_topedge (int *x, int *y, bool max); +extern void get_custom_raw_limits (int *pw, int *ph, int *pdx, int *pdy); +void get_custom_mouse_limits (int *pw, int *ph, int *pdx, int *pdy, int dbl); +extern void putpixel (uae_u8 *buf, uae_u8 *genlockbuf, int bpp, int x, xcolnr c8, int opaq); +extern void allocvidbuffer(struct vidbuffer *buf, int width, int height, int depth); +extern void freevidbuffer(struct vidbuffer *buf); extern void check_prefs_picasso(void); /* Finally, stuff that shouldn't really be shared. */ @@ -308,15 +351,8 @@ extern int thisframe_first_drawn_line, thisframe_last_drawn_line; #define IHF_QUIT_PROGRAM 1 #define IHF_PICASSO 2 -extern int inhibit_frame; - -STATIC_INLINE void set_inhibit_frame (int bit) -{ - inhibit_frame |= 1 << bit; -} -STATIC_INLINE void clear_inhibit_frame (int bit) -{ - inhibit_frame &= ~(1 << bit); -} +void set_inhibit_frame(int monid, int bit); +void clear_inhibit_frame(int monid, int bit); +void toggle_inhibit_frame(int monid, int bit); #endif /* UAE_DRAWING_H */ diff --git a/src/include/events.h b/src/include/events.h index 0a1d773a..083ed785 100644 --- a/src/include/events.h +++ b/src/include/events.h @@ -13,28 +13,32 @@ #define UAE_EVENTS_H #include "uae/types.h" - #include "machdep/rpt.h" -extern frame_time_t vsyncmintime, vsyncmaxtime, vsyncwaittime; +extern frame_time_t vsyncmintime, vsyncmintimepre; +extern frame_time_t vsyncmaxtime, vsyncwaittime; extern int vsynctimebase, syncbase; extern void reset_frame_rate_hack (void); +extern unsigned long int vsync_cycles; +extern unsigned long start_cycles; +extern int event2_count; +extern bool event_wait; extern int speedup_timelimit; extern void compute_vsynctime (void); extern void init_eventtab (void); extern void events_schedule (void); +extern void events_reset_syncline(void); extern unsigned long currcycle, nextevent; -extern int is_syncline; +extern int is_syncline, is_syncline_end; typedef void (*evfunc)(void); typedef void (*evfunc2)(uae_u32); -typedef void (*do_cycles_func)(unsigned long); +typedef void (*do_cycles_func)(uae_u32); extern do_cycles_func do_cycles; -void do_cycles_cpu_fastest (unsigned long cycles_to_add); -void do_cycles_cpu_norm (unsigned long cycles_to_add); -extern void events_reset_syncline(void); +void do_cycles_cpu_fastest (uae_u32 cycles_to_add); +void do_cycles_cpu_norm (uae_u32 cycles_to_add); typedef unsigned long int evt; @@ -71,6 +75,9 @@ extern int pissoff_value; extern struct ev eventtab[ev_max]; extern struct ev2 eventtab2[ev2_max]; +extern int hpos_offset; +extern int maxhpos; + STATIC_INLINE void cycles_do_special (void) { #ifdef JIT @@ -89,30 +96,35 @@ STATIC_INLINE void do_extra_cycles (unsigned long cycles_to_add) regs.pissoff -= cycles_to_add; } -STATIC_INLINE unsigned long int get_cycles(void) +STATIC_INLINE unsigned long int get_cycles (void) { return currcycle; } -STATIC_INLINE void set_cycles(unsigned long int x) +STATIC_INLINE void set_cycles (unsigned long int x) { currcycle = x; eventtab[ev_hsync].oldcycles = x; } -STATIC_INLINE int current_hpos(void) +STATIC_INLINE int current_hpos_safe (void) { - int hp = (get_cycles() - eventtab[ev_hsync].oldcycles) / CYCLE_UNIT; + int hp = (get_cycles () - eventtab[ev_hsync].oldcycles) / CYCLE_UNIT; return hp; } +STATIC_INLINE int current_hpos (void) +{ + return current_hpos_safe(); +} + STATIC_INLINE bool cycles_in_range (unsigned long endcycles) { signed long c = get_cycles (); return (signed long)endcycles - c > 0; } -extern void MISC_handler(void); +extern void MISC_handler (void); extern void event2_newevent_xx (int no, evt t, uae_u32 data, evfunc2 func); extern void event2_newevent_x_replace(evt t, uae_u32 data, evfunc2 func); diff --git a/src/include/filesys.h b/src/include/filesys.h index 210b0c51..8b487128 100644 --- a/src/include/filesys.h +++ b/src/include/filesys.h @@ -12,45 +12,78 @@ #include "uae/types.h" #include "traps.h" +struct hardfilehandle; + +#define MAX_HDF_CACHE_BLOCKS 128 #define MAX_SCSI_SENSE 36 +struct hdf_cache +{ + bool valid; + uae_u8 *data; + uae_u64 block; + bool dirty; + int readcount; + int writecount; + time_t lastaccess; +}; struct hardfiledata { - uae_u64 virtsize; // virtual size - uae_u64 physsize; // physical size (dynamic disk) - uae_u64 offset; + uae_u64 virtsize; // virtual size + uae_u64 physsize; // physical size (dynamic disk) + uae_u64 offset; struct uaedev_config_info ci; - struct hardfilehandle *handle; - int handle_valid; - int dangerous; - int flags; - uae_u8 *cache; - int cache_valid; - uae_u64 cache_offset; - TCHAR vendor_id[8 + 1]; - TCHAR product_id[16 + 1]; - TCHAR product_rev[4 + 1]; - /* geometry from possible RDSK block */ - int rdbcylinders; - int rdbsectors; - int rdbheads; - uae_u8 *virtual_rdb; - uae_u64 virtual_size; - int unitnum; - int byteswap; - int hfd_type; + struct hardfilehandle *handle; + int handle_valid; + int dangerous; + int flags; + uae_u8 *cache; + int cache_valid; + uae_u64 cache_offset; + TCHAR vendor_id[8 + 1]; + TCHAR product_id[16 + 1]; + TCHAR product_rev[4 + 1]; + /* geometry from possible RDSK block */ + int rdbcylinders; + int rdbsectors; + int rdbheads; + uae_u8 *virtual_rdb; + uae_u64 virtual_size; + int unitnum; + int byteswap; + int adide; + int hfd_type; - int drive_empty; - TCHAR *emptyname; + uae_u8 *vhd_header; + uae_u32 vhd_bamoffset; + uae_u32 vhd_bamsize; + uae_u32 vhd_blocksize; + uae_u8 *vhd_sectormap; + uae_u64 vhd_sectormapblock; + uae_u32 vhd_bitmapsize; + uae_u64 vhd_footerblock; + void *chd_handle; + + int drive_empty; + TCHAR *emptyname; + + struct hdf_cache bcache[MAX_HDF_CACHE_BLOCKS]; uae_u8 scsi_sense[MAX_SCSI_SENSE]; uae_u8 sector_buffer[512]; + uae_u8 identity[512]; struct uaedev_config_info delayedci; int reinsertdelay; bool isreinsert; bool unit_stopped; + + struct ini_data *geometry; + int specialaccessmode; }; +#define HFD_FLAGS_REALDRIVE 1 +#define HFD_FLAGS_REALDRIVEPARTITION 2 + struct hd_hardfiledata { struct hardfiledata hfd; uae_u64 size; @@ -63,8 +96,8 @@ struct hd_hardfiledata { int ansi_version; }; -#define HD_CONTROLLER_EXPANSION_MAX 50 -#define HD_CONTROLLER_NEXT_UNIT 200 +#define HD_CONTROLLER_EXPANSION_MAX 120 +#define HD_CONTROLLER_NEXT_UNIT 300 #define HD_CONTROLLER_TYPE_UAE 0 #define HD_CONTROLLER_TYPE_IDE_AUTO (HD_CONTROLLER_TYPE_UAE + 1) @@ -83,21 +116,26 @@ struct hd_hardfiledata { #define FILESYS_HARDFILE 1 #define FILESYS_HARDFILE_RDB 2 #define FILESYS_HARDDRIVE 3 +#define FILESYS_CD 4 +#define FILESYS_TAPE 5 #define MAX_FILESYSTEM_UNITS 30 struct uaedev_mount_info; extern struct uaedev_mount_info options_mountinfo; -extern struct hardfiledata *get_hardfile_data (int nr); +extern struct hardfiledata *get_hardfile_data(int nr); extern struct hardfiledata *get_hardfile_data_controller(int nr); #define FILESYS_MAX_BLOCKSIZE 2048 extern int hdf_open (struct hardfiledata *hfd); extern int hdf_open (struct hardfiledata *hfd, const TCHAR *altname); +extern int hdf_dup (struct hardfiledata *dhfd, const struct hardfiledata *shfd); extern void hdf_close (struct hardfiledata *hfd); extern int hdf_read_rdb (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); -extern int hdf_read (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); -extern int hdf_write (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); +extern int hdf_read(struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); +extern int hdf_write(struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); +extern int hdf_getnumharddrives (void); +extern TCHAR *hdf_getnameharddrive (int index, int flags, int *sectorsize, int *dangerousdrive, uae_u32 *outflags); extern int get_native_path(TrapContext *ctx, uae_u32 lock, TCHAR *out); extern void hardfile_do_disk_change (struct uaedev_config_data *uci, bool insert); extern void hardfile_send_disk_change (struct hardfiledata *hfd, bool insert); @@ -107,12 +145,20 @@ extern int hardfile_added (struct uaedev_config_info *ci); void hdf_hd_close(struct hd_hardfiledata *hfd); int hdf_hd_open(struct hd_hardfiledata *hfd); + +extern int vhd_create (const TCHAR *name, uae_u64 size, uae_u32); + +extern int hdf_init_target (void); extern int hdf_open_target (struct hardfiledata *hfd, const TCHAR *name); +extern int hdf_dup_target (struct hardfiledata *dhfd, const struct hardfiledata *shfd); extern void hdf_close_target (struct hardfiledata *hfd); extern int hdf_read_target (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); extern int hdf_write_target (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len); +extern int hdf_resize_target (struct hardfiledata *hfd, uae_u64 newsize); extern void getchsgeometry (uae_u64 size, int *pcyl, int *phead, int *psectorspertrack); extern void getchsgeometry_hdf (struct hardfiledata *hfd, uae_u64 size, int *pcyl, int *phead, int *psectorspertrack); extern void getchspgeometry (uae_u64 total, int *pcyl, int *phead, int *psectorspertrack, bool idegeometry); +void add_cpuboard_unit(int unit, struct uaedev_config_info *uci, struct romconfig *rc); + #endif /* UAE_FILESYS_H */ diff --git a/src/include/flashrom.h b/src/include/flashrom.h index 0c5a052b..2f12bad4 100644 --- a/src/include/flashrom.h +++ b/src/include/flashrom.h @@ -3,6 +3,16 @@ #include "uae/types.h" +/* FLASH */ + +void *flash_new(uae_u8 *rom, int flashsize, int allocsize, uae_u8 mfgcode, uae_u8 devcode, struct zfile *zf, int flags); +void flash_free(void *fdv); + +bool flash_write(void *fdv, uaecptr addr, uae_u8 v); +uae_u32 flash_read(void *fdv, uaecptr addr); +bool flash_active(void *fdv, uaecptr addr); +int flash_size(void *fdv); + /* I2C EEPROM */ #define BITBANG_I2C_SDA 0 @@ -13,4 +23,21 @@ void eeprom_free(void *i2c); void eeprom_reset(void *i2c); int eeprom_i2c_set(void *i2c, int line, int level); +#define FLASHROM_EVERY_OTHER_BYTE 1 +#define FLASHROM_EVERY_OTHER_BYTE_ODD 2 +#define FLASHROM_PARALLEL_EEPROM 4 + +void *i2c_new(uae_u8 device_address, int size, uae_u8(*read_func)(uae_u8 addr), void(*write_func)(uae_u8 addr, uae_u8 v)); +void i2c_free(void *i2c); +int i2c_set(void *i2c, int line, int level); +void i2c_reset(void *i2c); + +/* MICROWIRE EEPROM */ + +void eeprom93xx_write(void *eepromp, int eecs, int eesk, int eedi); +uae_u16 eeprom93xx_read(void *eepromp); +void *eeprom93xx_new(const uae_u8 *memory, int nwords, struct zfile *zf); +void eeprom93xx_free(void *eepromp); +uae_u8 eeprom93xx_read_byte(void *eepromp, int offset); + #endif /* UAE_FLASHROM_H */ diff --git a/src/include/fsdb.h b/src/include/fsdb.h index 54a0b841..ec12da1a 100644 --- a/src/include/fsdb.h +++ b/src/include/fsdb.h @@ -21,27 +21,27 @@ #endif /* AmigaOS errors */ -#define ERROR_NO_FREE_STORE 103 +#define ERROR_NO_FREE_STORE 103 #define ERROR_BAD_NUMBER 115 #define ERROR_LINE_TOO_LONG 120 -#define ERROR_OBJECT_IN_USE 202 -#define ERROR_OBJECT_EXISTS 203 -#define ERROR_DIR_NOT_FOUND 204 +#define ERROR_OBJECT_IN_USE 202 +#define ERROR_OBJECT_EXISTS 203 +#define ERROR_DIR_NOT_FOUND 204 #define ERROR_OBJECT_NOT_AROUND 205 #define ERROR_ACTION_NOT_KNOWN 209 -#define ERROR_INVALID_LOCK 211 +#define ERROR_INVALID_LOCK 211 #define ERROR_OBJECT_WRONG_TYPE 212 #define ERROR_DISK_WRITE_PROTECTED 214 #define ERROR_DIRECTORY_NOT_EMPTY 216 #define ERROR_DEVICE_NOT_MOUNTED 218 -#define ERROR_SEEK_ERROR 219 +#define ERROR_SEEK_ERROR 219 #define ERROR_COMMENT_TOO_BIG 220 -#define ERROR_DISK_IS_FULL 221 +#define ERROR_DISK_IS_FULL 221 #define ERROR_DELETE_PROTECTED 222 #define ERROR_WRITE_PROTECTED 223 #define ERROR_READ_PROTECTED 224 #define ERROR_NOT_A_DOS_DISK 225 -#define ERROR_NO_DISK 226 +#define ERROR_NO_DISK 226 #define ERROR_NO_MORE_ENTRIES 232 #define ERROR_IS_SOFT_LINK 233 #define ERROR_NOT_IMPLEMENTED 236 @@ -88,32 +88,32 @@ typedef struct a_inode_struct { /* For a directory that is being ExNext()ed, the number of child ainos which must be kept locked in core. */ unsigned int locked_children; - /* How many ExNext()s are going on in this directory? */ + /* How many ExNext()s are going on in this directory? */ unsigned int exnext_count; - /* AmigaOS locking bits. */ - int shlock; - long db_offset; - unsigned int dir:1; - unsigned int softlink:2; - unsigned int elock:1; - /* Nonzero if this came from an entry in our database. */ - unsigned int has_dbentry:1; - /* Nonzero if this will need an entry in our database. */ - unsigned int needs_dbentry:1; - /* This a_inode possibly needs writing back to the database. */ - unsigned int dirty:1; - /* If nonzero, this represents a deleted file; the corresponding - * entry in the database must be cleared. */ - unsigned int deleted:1; - /* target volume flag */ - unsigned int volflags; - /* not equaling unit.mountcount -> not in this volume */ - unsigned int mountcount; + /* AmigaOS locking bits. */ + int shlock; + long db_offset; + unsigned int dir:1; + unsigned int softlink:2; + unsigned int elock:1; + /* Nonzero if this came from an entry in our database. */ + unsigned int has_dbentry:1; + /* Nonzero if this will need an entry in our database. */ + unsigned int needs_dbentry:1; + /* This a_inode possibly needs writing back to the database. */ + unsigned int dirty:1; + /* If nonzero, this represents a deleted file; the corresponding + * entry in the database must be cleared. */ + unsigned int deleted:1; + /* target volume flag */ + unsigned int volflags; + /* not equaling unit.mountcount -> not in this volume */ + unsigned int mountcount; uae_u64 uniq_external; struct virtualfilesysobject *vfso; } a_inode; -extern TCHAR *nname_begin (TCHAR *); +//extern TCHAR *nname_begin (TCHAR *); extern TCHAR *build_nname (const TCHAR *d, const TCHAR *n); extern TCHAR *build_aname (const TCHAR *d, const TCHAR *n); @@ -129,7 +129,7 @@ extern int fsdb_exists (const TCHAR *nname); STATIC_INLINE int same_aname (const TCHAR *an1, const TCHAR *an2) { - return stricmp(an1, an2) == 0; + return strcasecmp (an1, an2) == 0; } /* Filesystem-dependent functions. */ @@ -138,6 +138,7 @@ extern int fsdb_name_invalid_dir (a_inode *, const TCHAR *n); extern int fsdb_fill_file_attrs (a_inode *, a_inode *); extern int fsdb_set_file_attrs (a_inode *); extern int fsdb_mode_representable_p (const a_inode *, int); +extern int fsdb_mode_supported (const a_inode *); extern TCHAR *fsdb_create_unique_nname (a_inode *base, const TCHAR *); struct my_opendir_s; @@ -145,14 +146,16 @@ struct my_openfile_s; extern struct my_opendir_s *my_opendir (const TCHAR*, const TCHAR*); extern struct my_opendir_s *my_opendir (const TCHAR*); -extern void my_closedir (struct my_opendir_s *); -extern int my_readdir (struct my_opendir_s *, TCHAR*); +extern void my_closedir (struct my_opendir_s*); +extern int my_readdir (struct my_opendir_s*, TCHAR*); extern int my_rmdir (const TCHAR*); extern int my_mkdir (const TCHAR*); extern int my_unlink (const TCHAR*); extern int my_rename (const TCHAR*, const TCHAR*); extern int my_setcurrentdir (const TCHAR *curdir, TCHAR *oldcur); +bool my_isfilehidden (const TCHAR *path); +void my_setfilehidden (const TCHAR *path, bool hidden); extern struct my_openfile_s *my_open (const TCHAR*, int); extern void my_close (struct my_openfile_s*); @@ -169,13 +172,25 @@ extern FILE *my_opentext (const TCHAR*); extern bool my_stat (const TCHAR *name, struct mystat *ms); extern bool my_utime (const TCHAR *name, struct mytimeval *tv); extern bool my_chmod (const TCHAR *name, uae_u32 mode); +extern bool my_resolveshortcut(TCHAR *linkfile, int size); +extern bool my_resolvessymboliclink(TCHAR *linkfile, int size); +extern bool my_resolvesoftlink(TCHAR *linkfile, int size, bool linkonly); extern const TCHAR *my_getfilepart(const TCHAR *filename); +extern void my_canonicalize_path(const TCHAR *path, TCHAR *out, int size); +extern int my_issamevolume(const TCHAR *path1, const TCHAR *path2, TCHAR *path); extern bool my_issamepath(const TCHAR *path1, const TCHAR *path2); +extern bool my_createsoftlink(const TCHAR *path, const TCHAR *target); +extern bool my_createshortcut(const TCHAR *source, const TCHAR *target, const TCHAR *description); + +extern a_inode *custom_fsdb_lookup_aino_aname (a_inode *base, const TCHAR *aname); +extern a_inode *custom_fsdb_lookup_aino_nname (a_inode *base, const TCHAR *nname); +extern int custom_fsdb_used_as_nname (a_inode *base, const TCHAR *nname); #define MYVOLUMEINFO_READONLY 1 #define MYVOLUMEINFO_STREAMS 2 #define MYVOLUMEINFO_ARCHIVE 4 #define MYVOLUMEINFO_REUSABLE 8 +#define MYVOLUMEINFO_CDFS 16 extern int my_getvolumeinfo (const TCHAR *root); diff --git a/src/include/gayle.h b/src/include/gayle.h index 346d8978..d3138eff 100644 --- a/src/include/gayle.h +++ b/src/include/gayle.h @@ -3,25 +3,25 @@ #include "uae/types.h" -extern void gayle_reset (int); -extern void gayle_hsync (void); -extern void gayle_free (void); -extern void gayle_add_ide_unit (int ch, struct uaedev_config_info *ci, struct romconfig *rc); -extern bool gayle_ide_init(struct autoconfig_info*); -extern int gayle_modify_pcmcia_sram_unit (struct uaedev_config_info*, int insert); -extern int gayle_modify_pcmcia_ide_unit (struct uaedev_config_info*, int insert); -extern int gayle_add_pcmcia_sram_unit (struct uaedev_config_info*); -extern int gayle_add_pcmcia_ide_unit (struct uaedev_config_info*); -extern void gayle_free_units (void); -extern void rethink_gayle (void); -extern void gayle_map_pcmcia (void); -extern void gayle_add_pcmcia_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); -extern bool gayle_pcmcia_init(struct autoconfig_info*); +void gayle_add_ide_unit (int ch, struct uaedev_config_info *ci, struct romconfig *rc); +bool gayle_ide_init(struct autoconfig_info*); +void gayle_free_units (void); +void gayle_map_pcmcia (void); +bool gayle_init_pcmcia(struct autoconfig_info *aci); +bool gayle_init_board_io_pcmcia(struct autoconfig_info *aci); +bool gayle_init_board_common_pcmcia(struct autoconfig_info *aci); +void pcmcia_eject(struct uae_prefs *p); +void pcmcia_reinsert(struct uae_prefs*); +bool pcmcia_disk_reinsert(struct uae_prefs *p, struct uaedev_config_info *uci, bool ejectonly); extern int gary_toenb; // non-existing memory access = bus error. -extern int gary_timeout; // non-existing memory access = delay +//extern int gary_timeout; // non-existing memory access = delay #define PCMCIA_COMMON_START 0x600000 #define PCMCIA_COMMON_SIZE 0x400000 +#define PCMCIA_ATTRIBUTE_START 0xa00000 +#define PCMCIA_ATTRIBUTE_SIZE 0x80000 + +void gayle_dataflyer_enable(bool); #endif /* UAE_GAYLE_H */ diff --git a/src/include/gensound.h b/src/include/gensound.h index 9f580f15..24c589ae 100644 --- a/src/include/gensound.h +++ b/src/include/gensound.h @@ -25,6 +25,9 @@ extern int init_sound (void); extern void close_sound (void); extern void sample16_handler (void); +extern void sample8_handler (void); extern void sample16s_handler (void); +extern void sample16ss_handler (void); +extern void sample8s_handler (void); #endif /* UAE_GENSOUND_H */ diff --git a/src/include/gfxboard.h b/src/include/gfxboard.h index 6d0ef890..100d06fe 100644 --- a/src/include/gfxboard.h +++ b/src/include/gfxboard.h @@ -1,12 +1,96 @@ #ifndef UAE_GFXBOARD_H #define UAE_GFXBOARD_H +#include "picasso96.h" + +extern bool gfxboard_init_memory (struct autoconfig_info*); +extern bool gfxboard_init_memory_p4_z2(struct autoconfig_info*); +extern bool gfxboard_init_registers(struct autoconfig_info*); +extern void gfxboard_free (void); +extern void gfxboard_reset (void); +//extern void gfxboard_vsync_handler (bool, bool); extern int gfxboard_get_configtype (struct rtgboardconfig*); +extern bool gfxboard_is_registers (struct rtgboardconfig*); +extern int gfxboard_get_vram_min (struct rtgboardconfig*); +extern int gfxboard_get_vram_max (struct rtgboardconfig*); +extern bool gfxboard_need_byteswap (struct rtgboardconfig*); +extern int gfxboard_get_autoconfig_size(struct rtgboardconfig*); +extern double gfxboard_get_vsync (void); +//extern void gfxboard_refresh (); +extern int gfxboard_toggle (int monid, int mode, int msg); +extern int gfxboard_num_boards (struct rtgboardconfig*); +extern uae_u32 gfxboard_get_romtype(struct rtgboardconfig*); extern const TCHAR *gfxboard_get_name(int); +extern const TCHAR *gfxboard_get_manufacturername(int); extern const TCHAR *gfxboard_get_configname(int); +extern struct gfxboard_func *gfxboard_get_func(struct rtgboardconfig *rbc); + +extern bool gfxboard_allocate_slot(int, int); +extern void gfxboard_free_slot(int); +extern bool gfxboard_rtg_enable_initial(int monid, int); +extern void gfxboard_rtg_disable(int monid, int); +extern bool gfxboard_init_board(struct autoconfig_info*); +extern bool gfxboard_set(int monid, bool rtg); + +extern struct gfxboard_func a2410_func; +extern struct gfxboard_func harlequin_func; + +extern void vga_io_put(int board, int portnum, uae_u8 v); +extern uae_u8 vga_io_get(int board, int portnum); +extern void vga_ram_put(int board, int offset, uae_u8 v); +extern uae_u8 vga_ram_get(int board, int offset); +extern void vgalfb_ram_put(int board, int offset, uae_u8 v); +extern uae_u8 vgalfb_ram_get(int board, int offset); + +void gfxboard_get_a8_vram(int index); +void gfxboard_free_vram(int index); + +int gfxboard_get_devnum(struct uae_prefs *p, int index); +extern bool gfxboard_set(bool rtg); #define GFXBOARD_UAE_Z2 0 #define GFXBOARD_UAE_Z3 1 #define GFXBOARD_HARDWARE 2 +#define GFXBOARD_PICASSO2 2 +#define GFXBOARD_PICASSO2PLUS 3 +#define GFXBOARD_PICCOLO_Z2 4 +#define GFXBOARD_PICCOLO_Z3 5 +#define GFXBOARD_SD64_Z2 6 +#define GFXBOARD_SD64_Z3 7 +#define GFXBOARD_SPECTRUM_Z2 8 +#define GFXBOARD_SPECTRUM_Z3 9 +#define GFXBOARD_PICASSO4_Z2 10 +#define GFXBOARD_PICASSO4_Z3 11 +#define GFXBOARD_A2410 12 +#define GFXBOARD_VGA 13 + +struct gfxboard_mode +{ + int width; + int height; + RGBFTYPE mode; + bool redraw_required; +}; + +typedef bool(*GFXBOARD_INIT)(struct autoconfig_info*); +typedef void(*GFXBOARD_FREE)(void*); +typedef void(*GFXBOARD_RESET)(void*); +typedef void(*GFXBOARD_HSYNC)(void*); +typedef bool(*GFXBOARD_VSYNC)(void*, struct gfxboard_mode*); +typedef bool(*GFXBOARD_TOGGLE)(void*, int); +typedef void(*GFXBOARD_CONFIGURED)(void*, uae_u32); + +struct gfxboard_func +{ + GFXBOARD_INIT init; + GFXBOARD_FREE free; + GFXBOARD_RESET reset; + GFXBOARD_HSYNC hsync; + GFXBOARD_VSYNC vsync; + GFXBOARD_TOGGLE toggle; + GFXBOARD_CONFIGURED configured; +}; + + #endif /* UAE_GFXBOARD_H */ diff --git a/src/include/gui.h b/src/include/gui.h index a742b596..4ef284a3 100644 --- a/src/include/gui.h +++ b/src/include/gui.h @@ -14,17 +14,22 @@ extern int gui_init (void); extern int gui_update (void); extern void gui_exit (void); -#ifdef WIN32 extern void gui_led (int, int, int); -#else -STATIC_INLINE void gui_led (int led, int on, int brightness) { } -#endif +extern void gui_handle_events (void); extern void gui_filename (int, const TCHAR *); -extern void gui_fps(int fps, int idle, int color); +extern void gui_fps (int fps, int idle, int color); +extern void gui_changesettings (void); +extern void gui_lock (void); +extern void gui_unlock (void); extern void gui_flicker_led (int, int, int); +extern void gui_disk_image_change (int, const TCHAR *, bool writeprotected); +extern unsigned int gui_ledstate; extern void gui_display (int shortcut); -extern bool no_gui; +//extern void gui_gameport_button_change (int port, int button, int onoff); +//extern void gui_gameport_axis_change (int port, int axis, int state, int max); + +extern bool no_gui, quit_to_gui; #define LED_CD_ACTIVE 1 #define LED_CD_ACTIVE2 2 @@ -46,30 +51,33 @@ extern bool no_gui; struct gui_info { - bool drive_motor[4]; /* motor on off */ - uae_u8 drive_track[4]; /* rw-head track */ - bool drive_writing[4]; /* drive is writing */ - bool drive_disabled[4]; /* drive is disabled */ - bool powerled; /* state of power led */ - uae_u8 powerled_brightness; /* 0 to 255 */ - uae_s8 drive_side; /* floppy side */ - uae_s8 hd; /* harddrive */ - uae_s8 cd; /* CD */ + bool drive_motor[4]; /* motor on off */ + uae_u8 drive_track[4]; /* rw-head track */ + bool drive_writing[4]; /* drive is writing */ + bool drive_disabled[4]; /* drive is disabled */ + bool powerled; /* state of power led */ + uae_u8 powerled_brightness; /* 0 to 255 */ + uae_s8 drive_side; /* floppy side */ + uae_s8 hd; /* harddrive */ + uae_s8 cd; /* CD */ uae_s8 md; /* CD32 or CDTV internal storage */ uae_s8 net; /* network */ int cpu_halted; - int fps, idle; + int fps, idle; int fps_color; int sndbuf, sndbuf_status; bool sndbuf_avail; - TCHAR df[4][256]; /* inserted image */ - uae_u32 crc32[4]; /* crc32 of image */ + TCHAR df[4][256]; /* inserted image */ + uae_u32 crc32[4]; /* crc32 of image */ }; #define NUM_LEDS (LED_MAX) #define VISIBLE_LEDS (LED_MAX - 1) extern struct gui_info gui_data; +/* Functions to be called when prefs are changed by non-gui code. */ +extern void gui_update_gfx (void); + void notify_user (int msg); void notify_user_parms (int msg, const TCHAR *parms, ...); int translate_message (int msg, TCHAR *out); diff --git a/src/include/ide.h b/src/include/ide.h index ae7bc9e1..2824224e 100644 --- a/src/include/ide.h +++ b/src/include/ide.h @@ -27,6 +27,8 @@ struct ide_registers struct ide_thread_state; struct ide_hdf; +typedef void (*hsync_func)(struct ide_board*); + #define MAX_IDE_PORTS_BOARD 3 struct ide_board { @@ -44,10 +46,20 @@ struct ide_board bool irq; bool intena; bool enabled; + bool intlev6; int state; + uae_u8 state2[8]; int type; + int userdata; + int subtype; uae_u16 data_latch; + uae_u32 dma_ptr; + uae_u32 dma_cnt; + int hsync_cnt; + hsync_func hsync_code; + struct romconfig *rc, *original_rc; struct ide_board **self_ptr; + struct autoconfig_info *aci; }; struct ide_hdf @@ -60,6 +72,7 @@ struct ide_hdf struct ide_hdf *pair; // master<>slave struct ide_thread_state *its; bool byteswap; + bool adide; uae_u8 *secbuf; int secbuf_size; @@ -69,6 +82,7 @@ struct ide_hdf int data_multi; int direction; // 0 = read, 1 = write bool intdrq; + bool lba; bool lba48; bool lba48cmd; uae_u64 start_lba; @@ -86,8 +100,10 @@ struct ide_hdf int ide_drv; int media_type; bool mode_8bit; + int uae_unitnum; bool atapi; + int atapi_device_type; bool atapi_drdy; int cd_unit_num; int packet_state; @@ -122,9 +138,16 @@ void remove_ide_unit(struct ide_hdf **idetable, int ch); void alloc_ide_mem (struct ide_hdf **ide, int max, struct ide_thread_state *its); void ide_reset_device(struct ide_hdf *ide); +//void ata_byteswapidentity(uae_u8 *d); +void ata_parse_identity(uae_u8 *out, struct uaedev_config_info *uci, bool *lba48, int *max_multiple); +bool ata_get_identity(struct ini_data *ini, uae_u8 *out, bool overwrite); + void start_ide_thread(struct ide_thread_state *its); void stop_ide_thread(struct ide_thread_state *its); +uae_u16 adide_decode_word(uae_u16 w); +uae_u16 adide_encode_word(uae_u16 w); + uae_u8 *ide_save_state(uae_u8 *dst, struct ide_hdf *ide); uae_u8 *ide_restore_state(uae_u8 *src, struct ide_hdf *ide); diff --git a/src/include/inputdevice.h b/src/include/inputdevice.h index e13eafee..c2e71a84 100644 --- a/src/include/inputdevice.h +++ b/src/include/inputdevice.h @@ -32,6 +32,8 @@ #define JOYBUTTON_CD32_RED 8 #define JOYBUTTON_CD32_BLUE 9 +#define JOYBUTTON_LIGHTPEN2 10 + #define IDTYPE_JOYSTICK 0 #define IDTYPE_MOUSE 1 #define IDTYPE_KEYBOARD 2 @@ -90,7 +92,8 @@ struct inputevent { #define ID_FLAG_INVERT 32 #define ID_FLAG_RESERVEDGAMEPORTSCUSTOM 64 #define ID_FLAG_SET_ONOFF 128 -#define ID_FLAG_SET_ONOFF_VAL 256 +#define ID_FLAG_SET_ONOFF_VAL1 256 +#define ID_FLAG_SET_ONOFF_VAL2 512 #define ID_FLAG_GAMEPORTSCUSTOM_MASK (ID_FLAG_GAMEPORTSCUSTOM1 | ID_FLAG_GAMEPORTSCUSTOM2) #define ID_FLAG_AUTOFIRE_MASK (ID_FLAG_TOGGLE | ID_FLAG_INVERTTOGGLE | ID_FLAG_AUTOFIRE) @@ -113,7 +116,7 @@ struct inputevent { #define ID_FLAG_QUALIFIER_MASK 0xfffffff00000000ULL #define ID_FLAG_QUALIFIER_MASK_R 0xaaaaaaa00000000ULL -#define ID_FLAG_SAVE_MASK_CONFIG 0x000001ff +#define ID_FLAG_SAVE_MASK_CONFIG 0x000003ff #define ID_FLAG_SAVE_MASK_QUALIFIERS ID_FLAG_QUALIFIER_MASK #define ID_FLAG_SAVE_MASK_FULL (ID_FLAG_SAVE_MASK_CONFIG | ID_FLAG_SAVE_MASK_QUALIFIERS) @@ -131,7 +134,8 @@ struct inputevent { #define IDEV_MAPPED_GAMEPORTSCUSTOM2 32 #define IDEV_MAPPED_INVERT 64 #define IDEV_MAPPED_SET_ONOFF 128 -#define IDEV_MAPPED_SET_ONOFF_VAL 256 +#define IDEV_MAPPED_SET_ONOFF_VAL1 256 +#define IDEV_MAPPED_SET_ONOFF_VAL2 512 #define IDEV_MAPPED_QUALIFIER1 0x000000100000000ULL #define IDEV_MAPPED_QUALIFIER2 0x000000400000000ULL @@ -150,19 +154,21 @@ struct inputevent { #define SET_ONOFF_PRESSREL_VALUE 0x7fffff30 #define SET_ONOFF_PRESS_VALUE 0x7fffff20 -#define SET_ONOFF_ON_VALUE 0x7fffff01 +#define SET_ONOFF_ON_VALUE 0x7fffff10 #define SET_ONOFF_OFF_VALUE 0x7fffff00 #define SET_ONOFF_MASK_PRESS 15 +#ifdef AMIBERRY #define ID_BUTTON_OFFSET 0 #define ID_BUTTON_TOTAL 128 #define ID_AXIS_OFFSET 128 #define ID_AXIS_TOTAL 64 - -//#define ID_BUTTON_OFFSET 0 -//#define ID_BUTTON_TOTAL 32 -//#define ID_AXIS_OFFSET 32 -//#define ID_AXIS_TOTAL 32 +#else +#define ID_BUTTON_OFFSET 0 +#define ID_BUTTON_TOTAL 32 +#define ID_AXIS_OFFSET 32 +#define ID_AXIS_TOTAL 32 +#endif #define MAX_COMPA_INPUTLIST 30 @@ -187,22 +193,24 @@ extern int inputdevice_set_mapping (int devnum, int num, const TCHAR *name, TCHA extern int inputdevice_get_mapping (int devnum, int num, uae_u64 *pflags, int *port, TCHAR *name, TCHAR *custom, int sub); extern void inputdevice_copyconfig (struct uae_prefs *src, struct uae_prefs *dst); extern void inputdevice_copy_single_config (struct uae_prefs *p, int src, int dst, int devnum, int selectedwidget); -extern void inputdevice_copyjports(struct uae_prefs *srcprefs, struct uae_prefs *dstprefs); +//extern void inputdevice_copyjports(struct uae_prefs *srcprefs, struct uae_prefs *dstprefs); extern void inputdevice_swap_ports (struct uae_prefs *p, int devnum); extern void inputdevice_swap_compa_ports (struct uae_prefs *p, int portswap); extern void inputdevice_config_change (void); extern int inputdevice_config_change_test (void); -extern int inputdevice_get_device_index (int devnum); +//extern int inputdevice_get_device_index (int devnum); extern const TCHAR *inputdevice_get_device_name (int type, int devnum); extern const TCHAR *inputdevice_get_device_name2 (int devnum); extern const TCHAR *inputdevice_get_device_unique_name (int type, int devnum); -extern int inputdevice_get_device_status (int devnum); +//extern int inputdevice_get_device_status (int devnum); extern void inputdevice_set_device_status (int devnum, int enabled); extern int inputdevice_get_device_total (int type); extern int inputdevice_get_widget_num (int devnum); extern int inputdevice_get_widget_type (int devnum, int num, TCHAR *name, bool inccode); +extern int send_input_event (int nr, int state, int max, int autofire); extern int input_get_default_mouse (struct uae_input_device *uid, int num, int port, int af, bool gp, bool wheel, bool joymouseswap); +extern int input_get_default_lightpen (struct uae_input_device *uid, int num, int port, int af, bool gp, bool joymouseswap); extern int input_get_default_joystick (struct uae_input_device *uid, int num, int port, int af, int mode, bool gp, bool joymouseswap); extern int input_get_default_joystick_analog (struct uae_input_device *uid, int num, int port, int af, bool gp, bool joymouseswap); extern int input_get_default_keyboard (int num); @@ -221,11 +229,24 @@ extern void handle_cd32_joystick_cia (uae_u8, uae_u8); extern uae_u8 handle_parport_joystick (int port, uae_u8 pra, uae_u8 dra); extern uae_u8 handle_joystick_buttons (uae_u8, uae_u8); +#define MAGICMOUSE_BOTH 0 +#define MAGICMOUSE_NATIVE_ONLY 1 +#define MAGICMOUSE_HOST_ONLY 2 + +extern int magicmouse_alive (void); +//extern int is_tablet (void); +extern int is_touch_lightpen (void); extern int inputdevice_is_tablet (void); extern int input_mousehack_status(TrapContext *ctx, int mode, uaecptr diminfo, uaecptr dispinfo, uaecptr vp, uae_u32 moffset); extern void input_mousehack_mouseoffset (uaecptr pointerprefs); +extern int mousehack_alive (void); extern void mousehack_wakeup(void); +extern void mousehack_write(int reg, uae_u16 val); +extern void setmouseactive(int); +extern bool ismouseactive(void); +extern void setmousebuttonstateall (int mouse, uae_u32 buttonbits, uae_u32 buttonmask); +extern void setjoybuttonstateall (int joy, uae_u32 buttonbits, uae_u32 buttonmask); extern void setjoybuttonstate (int joy, int button, int state); extern void setmousebuttonstate (int mouse, int button, int state); extern void setjoystickstate (int joy, int axle, int state, int max); @@ -233,21 +254,31 @@ extern int getjoystickstate (int mouse); void setmousestate (int mouse, int axis, int data, int isabs); extern int getmousestate (int mouse); extern void inputdevice_updateconfig (struct uae_prefs *srcprefs, struct uae_prefs *dstprefs); -extern void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_prefs *dstprefs); -extern void inputdevice_devicechange (struct uae_prefs *prefs); +//extern void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_prefs *dstprefs); +extern bool inputdevice_devicechange (struct uae_prefs *prefs); -extern int inputdevice_translatekeycode (int keyboard, int scancode, int state); +#define INTERNALEVENT_CPURESET 0 +#define INTERNALEVENT_KBRESET 1 +#define INTERNALEVENT_TOUCHLIGHTPEN 2 + +extern void send_internalevent (int eventid); + +extern int inputdevice_translatekeycode (int keyboard, int scancode, int state, bool alwaysrelease); extern void inputdevice_checkqualifierkeycode (int keyboard, int scancode, int state); extern void inputdevice_setkeytranslation (struct uae_input_device_kbr_default **trans, int **kbmaps); extern void inputdevice_do_keyboard (int code, int state); extern int inputdevice_iskeymapped (int keyboard, int scancode); -extern int inputdevice_get_compatibility_input (struct uae_prefs*, int index, int *typelist, int *inputlist, const int **at); +extern int inputdevice_synccapslock (int, int*); +extern void inputdevice_testrecord (int type, int num, int wtype, int wnum, int state, int max); +//extern int inputdevice_get_compatibility_input (struct uae_prefs*, int index, int *typelist, int *inputlist, const int **at); extern const struct inputevent *inputdevice_get_eventinfo (int evt); -extern bool inputdevice_get_eventname (const struct inputevent *ie, TCHAR *out); +//extern bool inputdevice_get_eventname (const struct inputevent *ie, TCHAR *out); extern void inputdevice_compa_prepare_custom (struct uae_prefs *prefs, int index, int mode, bool removeold); extern void inputdevice_compa_clear (struct uae_prefs *prefs, int index); extern int intputdevice_compa_get_eventtype (int evt, const int **axistable); extern void inputdevice_sparecopy (struct uae_input_device *uid, int num, int sub); +extern void inputdevice_parse_jport_custom(struct uae_prefs *pr, int index, int port, TCHAR *outname); +extern void inputdevice_generate_jport_custom(struct uae_prefs *pr, int port); extern void inputdevice_forget_unplugged_device(int portnum); extern uae_u16 potgo_value; @@ -262,13 +293,13 @@ extern void JOYSET (int num, uae_u16 v); extern uae_u16 JOYGET (int num); extern void inputdevice_vsync (void); -extern void inputdevice_hsync (bool forceread); +extern void inputdevice_hsync (bool); extern void inputdevice_reset (void); extern void write_inputdevice_config (struct uae_prefs *p, struct zfile *f); extern void read_inputdevice_config (struct uae_prefs *p, const TCHAR *option, TCHAR *value); extern void reset_inputdevice_config (struct uae_prefs *pr, bool reset); -extern int inputdevice_joyport_config(struct uae_prefs *p, const TCHAR *value1, const TCHAR *value2, int portnum, int mode, int type, bool candefault); +//extern int inputdevice_joyport_config(struct uae_prefs *p, const TCHAR *value1, const TCHAR *value2, int portnum, int mode, int type, bool candefault); extern void inputdevice_joyport_config_store(struct uae_prefs *p, const TCHAR *value, int portnum, int mode, int type); extern int inputdevice_getjoyportdevice (int port, int val); extern void inputdevice_validate_jports (struct uae_prefs *p, int changedport, bool *fixedports); @@ -279,19 +310,29 @@ extern void inputdevice_close (void); extern void inputdevice_default_prefs (struct uae_prefs *p); extern void inputdevice_acquire (int allmode); -extern void inputdevice_unacquire (void); -extern void inputdevice_unacquire(bool emulationactive, int inputmask); +extern void inputdevice_unacquire(void); +//extern void inputdevice_unacquire(bool emulationactive, int inputmask); +extern void inputdevice_releasebuttons(void); -extern void pausemode(int mode); +extern void indicator_leds (int num, int state); -extern void inputdevice_add_inputcode(int code, int state, const TCHAR *); +extern void warpmode (int mode); +extern void pausemode (int mode); + +extern void inputdevice_add_inputcode (int code, int state, const TCHAR *); extern void inputdevice_handle_inputcode (void); +extern void inputdevice_tablet (int x, int y, int z, + int pressure, uae_u32 buttonbits, int inproximity, + int ax, int ay, int az, int devid); +extern void inputdevice_tablet_info (int maxx, int maxy, int maxz, int maxax, int maxay, int maxaz, int xres, int yres); extern void inputdevice_tablet_strobe (void); +extern void tablet_lightpen(int x, int y, int maxx, int maxy, int touch, int buttonmask, bool touchmode, int devid, int lpnum); +extern int inputdevice_get_lightpen_id(void); extern uae_u64 input_getqualifiers (void); -extern void setsystime(void); +extern void setsystime (void); #define JSEM_MODE_DEFAULT 0 #define JSEM_MODE_WHEELMOUSE 1 @@ -312,6 +353,7 @@ extern void setsystime(void); #define JSEM_ISNUMPAD(port,p) (jsem_iskbdjoy(port,p) == JSEM_KBDLAYOUT) #define JSEM_ISCURSOR(port,p) (jsem_iskbdjoy(port,p) == JSEM_KBDLAYOUT + 1) #define JSEM_ISSOMEWHEREELSE(port,p) (jsem_iskbdjoy(port,p) == JSEM_KBDLAYOUT + 2) +#define JSEM_ISCUSTOM(port,p) ((p)->jports[port].id >= JSEM_CUSTOM && (p)->jports[port].id < JSEM_CUSTOM + MAX_JPORTS_CUSTOM) #define JSEM_GETCUSTOMIDX(port,p) ((p)->jports[port].id - JSEM_CUSTOM) #define JSEM_LASTKBD 3 #define JSEM_ISANYKBD(port,p) (jsem_iskbdjoy(port,p) >= JSEM_KBDLAYOUT && jsem_iskbdjoy(port,p) < JSEM_KBDLAYOUT + JSEM_LASTKBD) @@ -322,10 +364,17 @@ extern int jsem_iskbdjoy (int port, const struct uae_prefs *p); extern int inputdevice_uaelib (const TCHAR *, const TCHAR *); extern int inputdevice_uaelib(const TCHAR *s, int parm, int max, bool autofire); +extern int handle_custom_event (const TCHAR *custom, int append); +extern int inputdevice_geteventid(const TCHAR *s); + +extern int inputdevice_testread (int*, int*, int*, bool); +extern int inputdevice_istest (void); +extern void inputdevice_settest (int); +extern int inputdevice_testread_count (void); extern bool target_can_autoswitchdevice(void); - +#ifdef AMIBERRY struct host_input_button { int north_button; int east_button; @@ -399,5 +448,6 @@ struct host_keyboard_button { extern struct host_input_button host_input_buttons[MAX_INPUT_DEVICES]; extern int multipler_maps[MAX_JPORTS]; extern int find_in_array(const int arr[], int n, int key); +#endif #endif /* UAE_INPUTDEVICE_H */ diff --git a/src/include/keybuf.h b/src/include/keybuf.h index 90d6aab8..5c47174f 100644 --- a/src/include/keybuf.h +++ b/src/include/keybuf.h @@ -13,7 +13,10 @@ extern int get_next_key (void); extern int keys_available (void); extern int record_key (int); -extern int record_key_direct(int); +extern int record_key_direct (int); extern void keybuf_init (void); +extern int getcapslockstate (void); +extern void setcapslockstate (int); +extern void keybuf_inject(const uae_char*); #endif /* UAE_KEYBUF_H */ diff --git a/src/include/memory.h b/src/include/memory.h index 0b34d3ad..aa7e8222 100644 --- a/src/include/memory.h +++ b/src/include/memory.h @@ -1,15 +1,17 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * memory management - * - * Copyright 1995 Bernd Schmidt - */ +/* +* UAE - The Un*x Amiga Emulator +* +* memory management +* +* Copyright 1995 Bernd Schmidt +*/ #ifndef UAE_MEMORY_H #define UAE_MEMORY_H -extern void memory_reset (void); +extern void memory_reset(void); +extern void memory_restore(void); +extern void a1000_reset(void); #ifdef JIT extern int special_mem; @@ -19,6 +21,7 @@ extern int special_mem; #define S_WRITE 2 bool init_shm (void); +void free_shm (void); #define Z3BASE_UAE 0x10000000 #define Z3BASE_REAL 0x40000000 @@ -40,11 +43,11 @@ typedef int (REGPARAM3 *check_func)(uaecptr, uae_u32) REGPARAM; extern uae_u32 max_z3fastmem; -#undef DIRECT_MEMFUNCS_SUCCESSFUL #include "machdep/maccess.h" #define chipmem_start_addr 0x00000000 #define bogomem_start_addr 0x00C00000 +#define cardmem_start_addr 0x00E00000 #define kickmem_start_addr 0x00F80000 #define ROM_SIZE_512 524288 @@ -56,38 +59,37 @@ extern uae_u16 kickstart_version; extern int uae_boot_rom_type; extern int uae_boot_rom_size; extern uaecptr rtarea_base; -extern uaecptr uaeboard_base; enum { ABFLAG_UNK = 0, ABFLAG_RAM = 1, ABFLAG_ROM = 2, ABFLAG_ROMIN = 4, ABFLAG_IO = 8, ABFLAG_NONE = 16, ABFLAG_SAFE = 32, ABFLAG_INDIRECT = 64, ABFLAG_NOALLOC = 128, ABFLAG_RTG = 256, ABFLAG_THREADSAFE = 512, ABFLAG_DIRECTMAP = 1024, ABFLAG_ALLOCINDIRECT = 2048, - ABFLAG_CHIPRAM = 4096, ABFLAG_CIA = 8192, ABFLAG_PPCIOSPACE = 16384, + ABFLAG_CHIPRAM = 4096, ABFLAG_CIA = 8192, ABFLAG_PPCIOSPACE = 16384 }; typedef struct { - /* These ones should be self-explanatory... */ - mem_get_func lget, wget, bget; - mem_put_func lput, wput, bput; - /* Use xlateaddr to translate an Amiga address to a uae_u8 * that can - * be used to address memory without calling the wget/wput functions. - * This doesn't work for all memory banks, so this function may call - * abort(). */ - xlate_func xlateaddr; - /* To prevent calls to abort(), use check before calling xlateaddr. - * It checks not only that the memory bank can do xlateaddr, but also - * that the pointer points to an area of at least the specified size. - * This is used for example to translate bitplane pointers in custom.c */ - check_func check; - /* For those banks that refer to real memory, we can save the whole trouble - of going through function calls, and instead simply grab the memory - ourselves. This holds the memory address where the start of memory is - for this particular bank. */ - uae_u8 *baseaddr; + /* These ones should be self-explanatory... */ + mem_get_func lget, wget, bget; + mem_put_func lput, wput, bput; + /* Use xlateaddr to translate an Amiga address to a uae_u8 * that can + * be used to address memory without calling the wget/wput functions. + * This doesn't work for all memory banks, so this function may call + * abort(). */ + xlate_func xlateaddr; + /* To prevent calls to abort(), use check before calling xlateaddr. + * It checks not only that the memory bank can do xlateaddr, but also + * that the pointer points to an area of at least the specified size. + * This is used for example to translate bitplane pointers in custom.c */ + check_func check; + /* For those banks that refer to real memory, we can save the whole trouble + of going through function calls, and instead simply grab the memory + ourselves. This holds the memory address where the start of memory is + for this particular bank. */ + uae_u8 *baseaddr; const TCHAR *label; const TCHAR *name; /* for instruction opcode/operand fetches */ - mem_get_func lgeti, wgeti; + mem_get_func wgeti; int flags; int jit_read_flag, jit_write_flag; struct addrbank_sub *sub_banks; @@ -118,19 +120,15 @@ struct autoconfig_info uae_u8 autoconfig_bytes[16]; TCHAR name[128]; const uae_u8 *autoconfigp; - bool autoconfig_automatic; uae_u32 start; uae_u32 size; int zorro; const TCHAR *label; addrbank *addrbankp; struct romconfig *rc; - uae_u32 last_high_ram; const struct expansionromtype *ert; bool direct_vram; - bool can_sort; bool (*get_params)(struct uae_prefs*, struct expansion_params*); - bool (*set_params)(struct uae_prefs*, struct expansion_params*); }; #define MEMORY_LGET(name) \ @@ -208,7 +206,6 @@ static uae_u8 *REGPARAM2 name ## _xlate (uaecptr addr) \ #define DECLARE_MEMORY_FUNCTIONS(name) \ static uae_u32 REGPARAM3 NOWARN_UNUSED(name ## _lget) (uaecptr) REGPARAM; \ -static uae_u32 REGPARAM3 NOWARN_UNUSED(name ## _lgeti) (uaecptr) REGPARAM; \ static uae_u32 REGPARAM3 NOWARN_UNUSED(name ## _wget) (uaecptr) REGPARAM; \ static uae_u32 REGPARAM3 NOWARN_UNUSED(name ## _wgeti) (uaecptr) REGPARAM; \ static uae_u32 REGPARAM3 NOWARN_UNUSED(name ## _bget) (uaecptr) REGPARAM; \ @@ -336,18 +333,12 @@ extern addrbank extendedkickmem2_bank; extern addrbank custmem1_bank; extern addrbank custmem2_bank; -extern void rtarea_init (void); +extern void rtarea_init(void); extern void rtarea_free(void); -extern void rtarea_init_mem (void); extern void rtarea_setup (void); -extern void expamem_reset (void); -extern void expamem_next (addrbank *mapped, addrbank *next); -extern void expamem_shutup (addrbank *mapped); -extern bool expamem_z3hack(struct uae_prefs*); +extern void expamem_reset(int); extern void set_expamem_z3_hack_mode(int); -extern uaecptr expamem_board_pointer, expamem_highmem_pointer; -extern uaecptr expamem_z3_pointer_real, expamem_z3_pointer_uae; -extern uae_u32 expamem_z3_highram_real, expamem_z3_highram_uae; +extern uaecptr expamem_board_pointer; extern uae_u32 expamem_board_size; extern uae_u32 last_custom_value1; @@ -360,7 +351,6 @@ extern uae_u32 dummy_get_safe(uaecptr addr, int size, bool inst, uae_u32 defvalu extern int REGPARAM3 default_check(uaecptr addr, uae_u32 size) REGPARAM; extern uae_u8 *REGPARAM3 default_xlate(uaecptr addr) REGPARAM; /* 680x0 opcode fetches */ -extern uae_u32 REGPARAM3 dummy_lgeti (uaecptr addr) REGPARAM; extern uae_u32 REGPARAM3 dummy_wgeti (uaecptr addr) REGPARAM; /* sub bank support */ @@ -370,7 +360,6 @@ extern uae_u32 REGPARAM3 sub_bank_bget(uaecptr) REGPARAM; extern void REGPARAM3 sub_bank_lput(uaecptr, uae_u32) REGPARAM; extern void REGPARAM3 sub_bank_wput(uaecptr, uae_u32) REGPARAM; extern void REGPARAM3 sub_bank_bput(uaecptr, uae_u32) REGPARAM; -extern uae_u32 REGPARAM3 sub_bank_lgeti(uaecptr) REGPARAM; extern uae_u32 REGPARAM3 sub_bank_wgeti(uaecptr) REGPARAM; extern int REGPARAM3 sub_bank_check(uaecptr addr, uae_u32 size) REGPARAM; extern uae_u8 *REGPARAM3 sub_bank_xlate(uaecptr addr) REGPARAM; @@ -382,14 +371,11 @@ extern addrbank *mem_banks[MEMORY_BANKS]; #define get_mem_bank(addr) (*mem_banks[bankindex(addr)]) -extern void memory_init (void); extern void memory_cleanup (void); extern void map_banks (addrbank *bank, int first, int count, int realsize); extern void map_banks_z2 (addrbank *bank, int first, int count); extern void map_banks_z3(addrbank *bank, int first, int count); extern bool validate_banks_z2(addrbank *bank, int start, int size); -extern bool validate_banks_z3(addrbank *bank, int start, int size); -extern void map_banks_quick (addrbank *bank, int first, int count, int realsize); extern void map_banks_cond (addrbank *bank, int first, int count, int realsize); extern void map_overlay (int chip); extern void memory_hardreset (int); @@ -397,29 +383,57 @@ extern void memory_clear (void); extern void free_fastmemory (int); extern bool read_kickstart_version(struct uae_prefs *p); -#define longget(addr) (call_mem_get_func(get_mem_bank(addr).lget, addr)) -#define wordget(addr) (call_mem_get_func(get_mem_bank(addr).wget, addr)) -#define byteget(addr) (call_mem_get_func(get_mem_bank(addr).bget, addr)) -#define wordgeti(addr) (call_mem_get_func(get_mem_bank(addr).wgeti, addr)) -#define longput(addr,l) (call_mem_put_func(get_mem_bank(addr).lput, addr, l)) -#define wordput(addr,w) (call_mem_put_func(get_mem_bank(addr).wput, addr, w)) -#define byteput(addr,b) (call_mem_put_func(get_mem_bank(addr).bput, addr, b)) +#define memory_get_long(addr) (call_mem_get_func(get_mem_bank(addr).lget, addr)) +#define memory_get_word(addr) (call_mem_get_func(get_mem_bank(addr).wget, addr)) +#define memory_get_byte(addr) (call_mem_get_func(get_mem_bank(addr).bget, addr)) +#define memory_get_wordi(addr) (call_mem_get_func(get_mem_bank(addr).wgeti, addr)) STATIC_INLINE uae_u32 get_long(uaecptr addr) { - return longget(addr); + return memory_get_long(addr); } STATIC_INLINE uae_u32 get_word(uaecptr addr) { - return wordget(addr); + return memory_get_word(addr); } STATIC_INLINE uae_u32 get_byte(uaecptr addr) { - return byteget(addr); + return memory_get_byte(addr); } STATIC_INLINE uae_u32 get_wordi(uaecptr addr) { - return wordgeti(addr); + return memory_get_wordi(addr); +} + +// do split memory access if it can cross memory banks +STATIC_INLINE uae_u32 get_long_compatible(uaecptr addr) +{ + if ((addr &0xffff) < 0xfffd) { + return memory_get_long(addr); + } else if (addr & 1) { + uae_u8 v0 = memory_get_byte(addr + 0); + uae_u16 v1 = memory_get_word(addr + 1); + uae_u8 v3 = memory_get_byte(addr + 3); + return (v0 << 24) | (v1 << 8) | (v3 << 0); + } else { + uae_u16 v0 = memory_get_word(addr + 0); + uae_u16 v1 = memory_get_word(addr + 2); + return (v0 << 16) | (v1 << 0); + } +} +STATIC_INLINE uae_u32 get_word_compatible(uaecptr addr) +{ + if ((addr & 0xffff) < 0xffff) { + return memory_get_word(addr); + } else { + uae_u8 v0 = memory_get_byte(addr + 0); + uae_u8 v1 = memory_get_byte(addr + 1); + return (v0 << 8) | (v1 << 0); + } +} +STATIC_INLINE uae_u32 get_byte_compatible(uaecptr addr) +{ + return memory_get_byte(addr); } STATIC_INLINE uae_u32 get_long_jit(uaecptr addr) @@ -456,40 +470,69 @@ STATIC_INLINE uae_u32 get_byte_jit(uaecptr addr) # if SIZEOF_VOID_P == 8 STATIC_INLINE void *get_pointer (uaecptr addr) { - const unsigned int n = SIZEOF_VOID_P / 4; - union { - void *ptr; - uae_u32 longs[SIZEOF_VOID_P / 4]; - } p; - unsigned int i; + const unsigned int n = SIZEOF_VOID_P / 4; + union { + void *ptr; + uae_u32 longs[SIZEOF_VOID_P / 4]; + } p; + unsigned int i; - for (i = 0; i < n; i++) { -#ifdef WORDS_BIGENDIAN - p.longs[i] = get_long (addr + i * 4); -#else - p.longs[n - 1 - i] = get_long (addr + i * 4); -#endif - } - return p.ptr; + for (i = 0; i < n; i++) { + p.longs[n - 1 - i] = get_long (addr + i * 4); + } + return p.ptr; } # else # error "Unknown or unsupported pointer size." # endif #endif -STATIC_INLINE void put_long(uaecptr addr, uae_u32 l) +#define memory_put_long(addr,l) (call_mem_put_func(get_mem_bank(addr).lput, addr, l)) +#define memory_put_word(addr,w) (call_mem_put_func(get_mem_bank(addr).wput, addr, w)) +#define memory_put_byte(addr,b) (call_mem_put_func(get_mem_bank(addr).bput, addr, b)) + +STATIC_INLINE void put_long (uaecptr addr, uae_u32 l) { - longput(addr, l); + memory_put_long(addr, l); } -STATIC_INLINE void put_word(uaecptr addr, uae_u32 w) +STATIC_INLINE void put_word (uaecptr addr, uae_u32 w) { - wordput(addr, w); + memory_put_word(addr, w); } -STATIC_INLINE void put_byte(uaecptr addr, uae_u32 b) +STATIC_INLINE void put_byte (uaecptr addr, uae_u32 b) { - byteput(addr, b); + memory_put_byte(addr, b); } +// do split memory access if it can cross memory banks +STATIC_INLINE void put_long_compatible(uaecptr addr, uae_u32 l) +{ + if ((addr & 0xffff) < 0xfffd) { + memory_put_long(addr, l); + } else if (addr & 1) { + memory_put_byte(addr + 0, l >> 24); + memory_put_word(addr + 1, l >> 8); + memory_put_byte(addr + 3, l >> 0); + } else { + memory_put_word(addr + 0, l >> 16); + memory_put_word(addr + 2, l >> 0); + } +} +STATIC_INLINE void put_word_compatible(uaecptr addr, uae_u32 w) +{ + if ((addr & 0xffff) < 0xffff) { + memory_put_word(addr, w); + } else { + memory_put_byte(addr + 0, w >> 8); + memory_put_byte(addr + 1, w >> 0); + } +} +STATIC_INLINE void put_byte_compatible(uaecptr addr, uae_u32 b) +{ + memory_put_byte(addr, b); +} + + STATIC_INLINE void put_long_jit(uaecptr addr, uae_u32 l) { addrbank *bank = &get_mem_bank(addr); @@ -516,30 +559,26 @@ STATIC_INLINE void put_byte_jit(uaecptr addr, uae_u32 l) } /* - * Store host pointer v at addr - */ +* Store host pointer v at addr +*/ #if SIZEOF_VOID_P == 4 # define put_pointer(addr, p) (put_long((addr), (uae_u32)(p))) #else # if SIZEOF_VOID_P == 8 STATIC_INLINE void put_pointer (uaecptr addr, void *v) { - const unsigned int n = SIZEOF_VOID_P / 4; - union { - void *ptr; - uae_u32 longs[SIZEOF_VOID_P / 4]; - } p; - unsigned int i; + const unsigned int n = SIZEOF_VOID_P / 4; + union { + void *ptr; + uae_u32 longs[SIZEOF_VOID_P / 4]; + } p; + unsigned int i; - p.ptr = v; + p.ptr = v; - for (i = 0; i < n; i++) { -#ifdef WORDS_BIGENDIAN - put_long (addr + i * 4, p.longs[i]); -#else - put_long (addr + i * 4, p.longs[n - 1 - i]); -#endif - } + for (i = 0; i < n; i++) { + put_long (addr + i * 4, p.longs[n - 1 - i]); + } } # endif #endif @@ -549,16 +588,11 @@ STATIC_INLINE uae_u8 *get_real_address(uaecptr addr) return get_mem_bank(addr).xlateaddr(addr); } -STATIC_INLINE int valid_address(uaecptr addr, uae_u32 size) +STATIC_INLINE int valid_address (uaecptr addr, uae_u32 size) { return get_mem_bank(addr).check(addr, size); } -STATIC_INLINE void put_quad_host(void *addr, uae_u64 v) -{ - do_put_mem_long((uae_u32*)addr, v >> 32); - do_put_mem_long(((uae_u32*)addr) + 1, (uae_u32)v); -} STATIC_INLINE void put_long_host(void *addr, uae_u32 v) { do_put_mem_long((uae_u32*)addr, v); @@ -590,7 +624,7 @@ STATIC_INLINE uae_u32 get_byte_host(void *addr) return *((uae_u8*)addr); } -extern int addr_valid (const TCHAR*,uaecptr,uae_u32); +extern int addr_valid (const TCHAR*, uaecptr,uae_u32); /* For faster access in custom chip emulation. */ extern void REGPARAM3 chipmem_lput (uaecptr, uae_u32) REGPARAM; @@ -615,10 +649,7 @@ extern bool mapped_malloc (addrbank*); extern void mapped_free (addrbank*); extern uaecptr strcpyha_safe (uaecptr dst, const uae_char *src); -extern uae_char *strcpyah_safe (uae_char *dst, uaecptr src, int maxsize); extern void memcpyha_safe (uaecptr dst, const uae_u8 *src, int size); extern void memcpyha (uaecptr dst, const uae_u8 *src, int size); -extern void memcpyah_safe (uae_u8 *dst, uaecptr src, int size); -extern void memcpyah (uae_u8 *dst, uaecptr src, int size); #endif /* UAE_MEMORY_H */ diff --git a/src/include/native2amiga_api.h b/src/include/native2amiga_api.h index e7dfb40a..8c21b74b 100644 --- a/src/include/native2amiga_api.h +++ b/src/include/native2amiga_api.h @@ -16,7 +16,9 @@ void uae_Cause(uaecptr interrupt); void uae_ReplyMsg(uaecptr msg); void uae_PutMsg(uaecptr port, uaecptr msg); void uae_Signal(uaecptr task, uae_u32 mask); +void uae_Signal_with_Func(uaecptr task, uae_u32 mask, UAE_PROCESSED state); void uae_NotificationHack(uaecptr, uaecptr); +void uae_ShellExecute(TCHAR *command); #endif int native2amiga_isfree(void); void uae_nativesem_wait(void); diff --git a/src/include/newcpu.h b/src/include/newcpu.h index 3ea035f1..4f971b20 100644 --- a/src/include/newcpu.h +++ b/src/include/newcpu.h @@ -20,24 +20,19 @@ extern int movem_index1[256]; extern int movem_index2[256]; extern int movem_next[256]; -#ifdef FPUEMU -extern int fpp_movem_index1[256]; -extern int fpp_movem_index2[256]; -extern int fpp_movem_next[256]; -#endif - typedef uae_u32 REGPARAM3 cpuop_func (uae_u32) REGPARAM; typedef void REGPARAM3 cpuop_func_ce (uae_u32) REGPARAM; struct cputbl { - cpuop_func *handler; - uae_u16 opcode; + cpuop_func *handler; + uae_u16 opcode; uae_s8 length; uae_s8 disp020[2]; uae_u8 branch; }; #ifdef JIT +#define MIN_JIT_CACHE 128 #define MAX_JIT_CACHE 16384 typedef uae_u32 REGPARAM3 compop_func (uae_u32) REGPARAM; @@ -49,11 +44,12 @@ typedef uae_u32 REGPARAM3 compop_func (uae_u32) REGPARAM; #define COMP_OPCODE_USES_FPU 0x0020 struct comptbl { - compop_func *handler; - uae_u32 specific; - uae_u32 opcode; + compop_func *handler; + uae_u32 opcode; + int specific; }; #else +#define MIN_JIT_CACHE 0 #define MAX_JIT_CACHE 0 #endif @@ -78,6 +74,11 @@ typedef struct fptype fp; } fpdata; +#ifdef JIT +#include "jit/comptbl.h" +#include "jit/compemu.h" +#endif + struct regstruct { uae_u32 regs[16]; @@ -129,6 +130,17 @@ struct regstruct uae_s32 pissoff; uae_u8* natmem_offset; + +#ifdef JIT + /* store scratch regs also in this struct to avoid load of mem pointer */ + uae_u32 scratchregs[VREGS - 16]; + fpu_register scratchfregs[VFREGS - 8]; + uae_u32 jit_exception; + + /* pointer to real arrays/structs for easier access in JIT */ + uae_u32 *raw_cputbl_count; + uintptr mem_banks; +#endif }; extern struct regstruct regs; @@ -139,7 +151,7 @@ extern struct regstruct regs; STATIC_INLINE uae_u32 munge24(uae_u32 x) { - return x & regs.address_space_mask; + return x & regs.address_space_mask; } extern int cpu_cycles; @@ -148,7 +160,7 @@ extern int m68k_pc_indirect; STATIC_INLINE void set_special (uae_u32 x) { atomic_or(®s.spcflags, x); - cycles_do_special(); + cycles_do_special(); } STATIC_INLINE void unset_special (uae_u32 x) @@ -294,7 +306,6 @@ extern void check_t0_trace(void); #define x_do_cycles(c) do_cycles(c) extern void m68k_setstopped (void); -extern void m68k_resumestopped (void); #define get_disp_ea_020(base,idx) _get_disp_ea_020(base) extern uae_u32 REGPARAM3 _get_disp_ea_020 (uae_u32 base) REGPARAM; @@ -305,7 +316,6 @@ extern void REGPARAM3 put_bitfield (uae_u32 dst, uae_u32 bdata[2], uae_u32 val, extern int get_cpu_model(void); extern void set_cpu_caches (bool flush); -extern void flush_cpu_caches(bool flush); extern void flush_cpu_caches_040(uae_u16 opcode); extern void REGPARAM3 MakeSR (void) REGPARAM; extern void REGPARAM3 MakeFromSR (void) REGPARAM; @@ -327,7 +337,19 @@ extern int getDivs68kCycles(uae_s32 dividend, uae_s16 divisor); extern void divbyzero_special (bool issigned, uae_s32 dst); extern void setdivuoverflowflags(uae_u32 dividend, uae_u16 divisor); extern void setdivsoverflowflags(uae_s32 dividend, uae_s16 divisor); +extern void setchkundefinedflags(uae_s32 src, uae_s32 dst, int size); +extern void setchk2undefinedflags(uae_u32 lower, uae_u32 upper, uae_u32 val, int size); extern void protect_roms (bool); +extern void Exception_build_stack_frame_common(uae_u32 oldpc, uae_u32 currpc, int nr); +extern void Exception_build_stack_frame(uae_u32 oldpc, uae_u32 currpc, uae_u32 ssw, int nr, int format); +extern void Exception_build_68000_address_error_stack_frame(uae_u16 mode, uae_u16 opcode, uaecptr fault_addr, uaecptr pc); +extern uae_u32 exception_pc(int nr); + +void ccr_68000_long_move_ae_LZN(uae_s32 src); +void ccr_68000_long_move_ae_LN(uae_s32 src); +void ccr_68000_long_move_ae_HNZ(uae_s32 src); +void ccr_68000_long_move_ae_normal(uae_s32 src); +void ccr_68000_word_move_ae_normal(uae_s16 src); STATIC_INLINE int bitset_count16(uae_u16 data) { @@ -358,7 +380,6 @@ extern void fpu_reset (void); extern void exception3_read(uae_u32 opcode, uaecptr addr); extern void exception3_write(uae_u32 opcode, uaecptr addr); -extern void exception3_notinstruction(uae_u32 opcode, uaecptr addr); extern void exception3i (uae_u32 opcode, uaecptr addr); extern void exception3b (uae_u32 opcode, uaecptr addr, bool w, bool i, uaecptr pc); extern void exception2 (uaecptr addr, bool read, int size, uae_u32 fc); @@ -400,8 +421,6 @@ extern void compemu_reset(void); #endif bool check_prefs_changed_comp (bool); -extern int movec_illg (int regno); - #define CPU_HALT_BUS_ERROR_DOUBLE_FAULT 1 #define CPU_HALT_DOUBLE_FAULT 2 #define CPU_HALT_OPCODE_FETCH_FROM_NON_EXISTING_ADDRESS 3 diff --git a/src/include/options.h b/src/include/options.h index a5965624..1076c15a 100644 --- a/src/include/options.h +++ b/src/include/options.h @@ -15,10 +15,8 @@ #include "traps.h" #define UAEMAJOR 4 -#define UAEMINOR 1 -#define UAESUBREV 0 - -#define MAX_AMIGADISPLAYS 1 +#define UAEMINOR 2 +#define UAESUBREV 1 typedef enum { KBD_LANG_US, KBD_LANG_DK, KBD_LANG_DE, KBD_LANG_SE, KBD_LANG_FR, KBD_LANG_IT, KBD_LANG_ES } KbdLang; @@ -64,17 +62,6 @@ struct strlist { #define INTERNALEVENT_COUNT 1 -#if 0 -struct uae_input_device_event -{ - uae_s16 eventid[MAX_INPUT_SUB_EVENT_ALL]; - TCHAR *custom[MAX_INPUT_SUB_EVENT_ALL]; - uae_u64 flags[MAX_INPUT_SUB_EVENT_ALL]; - uae_u8 port[MAX_INPUT_SUB_EVENT_ALL]; - uae_s16 extra; -}; -#endif - struct uae_input_device { TCHAR *name; TCHAR *configname; @@ -394,7 +381,7 @@ struct gfx_filterdata float gfx_filter_horiz_offset, gfx_filter_vert_offset; int gfx_filter_left_border, gfx_filter_right_border; int gfx_filter_top_border, gfx_filter_bottom_border; - int gfx_filter_filtermode; + int gfx_filter_filtermodeh, gfx_filter_filtermodev; int gfx_filter_bilinear; int gfx_filter_noise, gfx_filter_blur; int gfx_filter_saturation, gfx_filter_luminance, gfx_filter_contrast; @@ -442,7 +429,21 @@ struct rtgboardconfig int device_order; int monitor_id; }; -#define MAX_RAM_BOARDS 1 +struct boardloadfile +{ + uae_u32 loadoffset; + uae_u32 fileoffset, filesize; + TCHAR loadfile[MAX_DPATH]; +}; +#define MAX_ROM_BOARDS 4 +struct romboard +{ + uae_u32 size; + uae_u32 start_address; + uae_u32 end_address; + struct boardloadfile lf; +}; +#define MAX_RAM_BOARDS 4 struct ramboard { uae_u32 size; @@ -457,9 +458,7 @@ struct ramboard uae_u32 end_address; uae_u32 write_address; bool readonly; - uae_u32 loadoffset; - uae_u32 fileoffset, filesize; - TCHAR loadfile[MAX_DPATH]; + struct boardloadfile lf; }; struct expansion_params { @@ -536,6 +535,7 @@ struct uae_prefs { bool sound_stereo_swap_ahi; bool sound_auto; bool sound_cdaudio; + bool sound_volcnt; int sampler_freq; int sampler_buffer; @@ -554,14 +554,13 @@ struct uae_prefs { bool fpu_strict; int fpu_mode; - struct monconfig gfx_monitor[MAX_AMIGADISPLAYS]; + struct monconfig gfx_monitor; int gfx_framerate, gfx_autoframerate; bool gfx_autoresolution_vga; int gfx_autoresolution; int gfx_autoresolution_delay; int gfx_autoresolution_minv, gfx_autoresolution_minh; bool gfx_scandoubler; - struct wh gfx_size; //TODO take this away? struct apmode gfx_apmode[2]; int gfx_resolution; int gfx_vresolution; @@ -655,6 +654,7 @@ struct uae_prefs { TCHAR filesys_inject_icons_drawer[MAX_DPATH]; int uaescsidevmode; bool reset_delay; + bool crash_auto_reset; int cs_compatible; int cs_ciaatod; @@ -697,6 +697,7 @@ struct uae_prefs { int cs_unmapped_space; int cs_hacks; int cs_ciatype[2]; + int cs_kbhandshake; struct boardromconfig expansionboard[MAX_EXPANSION_BOARDS]; @@ -722,14 +723,14 @@ struct uae_prefs { TCHAR quitstatefile[MAX_DPATH]; TCHAR statefile[MAX_DPATH]; TCHAR inprecfile[MAX_DPATH]; + TCHAR trainerfile[MAX_DPATH]; bool inprec_autoplay; bool refresh_indicator; - //TODO replace these with multipath structs - TCHAR path_floppy[MAX_DPATH]; - TCHAR path_hardfile[MAX_DPATH]; - TCHAR path_rom[MAX_DPATH]; - TCHAR path_cd[MAX_DPATH]; + struct multipath path_floppy; + struct multipath path_hardfile; + struct multipath path_rom; + struct multipath path_cd; int m68k_speed; double m68k_speed_throttle; @@ -755,6 +756,7 @@ struct uae_prefs { uae_u32 z3autoconfig_start; struct ramboard z3fastmem[MAX_RAM_BOARDS]; struct ramboard fastmem[MAX_RAM_BOARDS]; + struct romboard romboards[MAX_ROM_BOARDS]; uae_u32 z3chipmem_size; uae_u32 z3chipmem_start; uae_u32 chipmem_size; @@ -906,7 +908,7 @@ extern void config_check_vsync (void); extern void set_config_changed (void); /* Contains the filename of .uaerc */ -extern TCHAR optionsfile[]; +//extern TCHAR optionsfile[]; extern void save_options (struct zfile *, struct uae_prefs *, int); extern void cfgfile_write (struct zfile *, const TCHAR *option, const TCHAR *format,...); @@ -935,6 +937,7 @@ extern bool is_error_log (void); extern void default_prefs (struct uae_prefs *, bool, int); extern void discard_prefs (struct uae_prefs *, int); +extern void copy_prefs(struct uae_prefs *src, struct uae_prefs *dst); extern int bip_a500 (struct uae_prefs *p, int rom); extern int bip_a500plus (struct uae_prefs *p, int rom); extern int bip_a1200 (struct uae_prefs *p, int rom); @@ -942,7 +945,7 @@ extern int bip_a2000 (struct uae_prefs *p, int rom); extern int bip_a4000 (struct uae_prefs *p, int rom); extern int bip_cd32 (struct uae_prefs *p, int rom); -int parse_cmdline_option (struct uae_prefs *, TCHAR, const TCHAR *); +int parse_cmdline_option (struct uae_prefs *, TCHAR, const TCHAR*); extern int cfgfile_separate_linea (const TCHAR *filename, char *line, TCHAR *line1b, TCHAR *line2b); extern int cfgfile_yesno (const TCHAR *option, const TCHAR *value, const TCHAR *name, bool *location); @@ -975,25 +978,32 @@ extern int cfgfile_save (struct uae_prefs *p, const TCHAR *filename, int); extern void cfgfile_parse_line (struct uae_prefs *p, TCHAR *, int); extern void cfgfile_parse_lines (struct uae_prefs *p, const TCHAR *, int); extern int cfgfile_parse_option (struct uae_prefs *p, const TCHAR *option, TCHAR *value, int); -extern int cfgfile_get_description (const TCHAR *filename, TCHAR *description); -extern uae_u32 cfgfile_uaelib (TrapContext *ctx, int mode, uae_u32 name, uae_u32 dst, uae_u32 maxlen); -extern uae_u32 cfgfile_uaelib_modify (TrapContext *ctx, uae_u32 mode, uae_u32 parms, uae_u32 size, uae_u32 out, uae_u32 outsize); +extern int cfgfile_get_description (struct uae_prefs *p, const TCHAR *filename, TCHAR *description, int *type); +extern void cfgfile_show_usage (void); +extern int cfgfile_searchconfig(const TCHAR *in, int index, TCHAR *out, int outsize); +extern uae_u32 cfgfile_uaelib(TrapContext *ctx, int mode, uae_u32 name, uae_u32 dst, uae_u32 maxlen); +extern uae_u32 cfgfile_uaelib_modify(TrapContext *ctx, uae_u32 mode, uae_u32 parms, uae_u32 size, uae_u32 out, uae_u32 outsize); extern uae_u32 cfgfile_modify (uae_u32 index, const TCHAR *parms, uae_u32 size, TCHAR *out, uae_u32 outsize); extern void cfgfile_addcfgparam (TCHAR *); extern int built_in_prefs (struct uae_prefs *p, int model, int config, int compa, int romcheck); extern int built_in_chipset_prefs (struct uae_prefs *p); -extern int cfgfile_configuration_change(int); +extern int built_in_cpuboard_prefs(struct uae_prefs *p); +//extern int cmdlineparser (const TCHAR *s, TCHAR *outp[], int max); extern void fixup_prefs_dimensions (struct uae_prefs *prefs); extern void fixup_prefs (struct uae_prefs *prefs, bool userconfig); extern void fixup_cpu (struct uae_prefs *prefs); extern void cfgfile_compatibility_romtype(struct uae_prefs *p); extern void cfgfile_compatibility_rtg(struct uae_prefs *p); +extern bool cfgfile_detect_art(struct uae_prefs *p, TCHAR *path); +extern const TCHAR *cfgfile_getconfigdata(int *len); +extern bool cfgfile_createconfigstore(struct uae_prefs *p); +extern void cfgfile_get_shader_config(struct uae_prefs *p, int rtg); - +#ifdef AMIBERRY extern void whdload_auto_prefs (struct uae_prefs *p, char* filename); extern void cd_auto_prefs (struct uae_prefs *p, char* filename); extern void symlink_roms(struct uae_prefs *p); - +#endif extern void check_prefs_changed_custom (void); extern void check_prefs_changed_cpu (void); diff --git a/src/include/readcpu.h b/src/include/readcpu.h index f29a3485..363fb65f 100644 --- a/src/include/readcpu.h +++ b/src/include/readcpu.h @@ -40,9 +40,9 @@ ENUMDECL { } ENUMNAME (instrmnem); struct mnemolookup { - instrmnem mnemo; - const TCHAR *name; - const TCHAR *friendlyname; + instrmnem mnemo; + const TCHAR *name; + const TCHAR *friendlyname; }; extern struct mnemolookup lookuptab[]; @@ -77,20 +77,20 @@ ENUMDECL { } ENUMNAME (bitvals); struct instr_def { - unsigned int bits; - int n_variable; - uae_u8 bitpos[16]; - unsigned int mask; - int cpulevel; + unsigned int bits; + int n_variable; + uae_u8 bitpos[16]; + unsigned int mask; + int cpulevel; int unimpcpulevel; - int plevel; - struct { - unsigned int flaguse:3; - unsigned int flagset:3; - } flaginfo[5]; - unsigned char cflow; - uae_u8 sduse; - const TCHAR *opcstr; + int plevel; + struct { + unsigned int flaguse:3; + unsigned int flagset:3; + } flaginfo[5]; + unsigned char cflow; + uae_u8 sduse; + const TCHAR *opcstr; // 68020/030 timing int head, tail, clocks, fetchmode; }; @@ -116,9 +116,10 @@ extern struct instr { unsigned int dmode:5; unsigned int suse:1; unsigned int duse:1; + unsigned int ccuse:1; unsigned int clev:3, unimpclev:3; unsigned int cflow:3; - unsigned int unused3:7; + unsigned int unused3:6; char head, tail, clocks, fetchmode; } *table68k; diff --git a/src/include/rommgr.h b/src/include/rommgr.h index e731547f..a206df9a 100644 --- a/src/include/rommgr.h +++ b/src/include/rommgr.h @@ -50,6 +50,7 @@ extern int decode_cloanto_rom_do (uae_u8 *mem, int size, int real_size); #define ROMTYPE_CB_TYPHOON2 0x0004001d #define ROMTYPE_CB_QUIKPAK 0x0004001e #define ROMTYPE_CB_12GAUGE 0x0004001f +#define ROMTYPE_CB_HARMS3KP 0x00040020 #define ROMTYPE_FREEZER 0x00080000 #define ROMTYPE_AR 0x00080001 @@ -179,6 +180,18 @@ extern int decode_cloanto_rom_do (uae_u8 *mem, int size, int real_size); #define ROMTYPE_SBISA 0x00100075 #define ROMTYPE_X86MOUSE 0x00100076 #define ROMTYPE_ACCESSX 0x00100077 +#define ROMTYPE_OVERDRIVE 0x00100078 +#define ROMTYPE_IVSTC 0x00100079 +#define ROMTYPE_IVST500AT 0x0010007a +#define ROMTYPE_TRIFECTA 0x0010007b +#define ROMTYPE_PRELUDE 0x0010007c +#define ROMTYPE_PRELUDE1200 0x0010007d +#define ROMTYPE_TANDEM 0x0010007e +#define ROMTYPE_ARCHOSHD 0x0010007f +#define ROMTYPE_PCMCIASRAM 0x00100080 +#define ROMTYPE_PCMCIAIDE 0x00100081 +#define ROMTYPE_SSQUIRREL 0x00100082 +#define ROMTYPE_MASTERCARD 0x00100083 #define ROMTYPE_NOT 0x00800000 #define ROMTYPE_QUAD 0x01000000 @@ -237,17 +250,17 @@ extern struct romdata *getarcadiarombyname (const TCHAR *name); extern struct romlist **getromlistbyident (int ver, int rev, int subver, int subrev, const TCHAR *model, int romflags, bool all); extern void getromname (const struct romdata*, TCHAR*); extern struct romdata *getromdatabyname (const TCHAR*); -extern struct romlist *getromlistbyids (const int *ids, const TCHAR *romname); -extern struct romlist *getromlistbyromtype(uae_u32 romtype, const TCHAR *romname); +//extern struct romlist *getromlistbyids (const int *ids, const TCHAR *romname); +//extern struct romlist *getromlistbyromtype(uae_u32 romtype, const TCHAR *romname); extern void romwarning(const int *ids); extern void romwarning(int romtype); extern struct romlist *getromlistbyromdata (const struct romdata *rd); extern void romlist_add (const TCHAR *path, struct romdata *rd); extern TCHAR *romlist_get (const struct romdata *rd); extern void romlist_clear (void); -extern struct zfile *read_rom (struct romdata *rd); +//extern struct zfile *read_rom (struct romdata *rd); extern struct zfile *read_rom_name (const TCHAR *filename); -extern struct zfile *read_device_from_romconfig(struct romconfig *rc, uae_u32 romtype); +//extern struct zfile *read_device_from_romconfig(struct romconfig *rc, uae_u32 romtype); extern int load_keyring (struct uae_prefs *p, const TCHAR *path); extern uae_u8 *target_load_keyfile (struct uae_prefs *p, const TCHAR *path, int *size, TCHAR *name); @@ -258,7 +271,7 @@ extern void descramble_nordicpro (uae_u8*, int, int); extern int kickstart_checksum (uae_u8 *mem, int size); extern int decode_rom (uae_u8 *mem, int size, int mode, int real_size); extern struct zfile *rom_fopen (const TCHAR *name, const TCHAR *mode, int mask); -extern struct zfile *read_rom_name_guess (const TCHAR *filename); +extern struct zfile *read_rom_name_guess (const TCHAR *filename, TCHAR *out); extern void addkeydir (const TCHAR *path); extern void addkeyfile (const TCHAR *path); extern int romlist_count (void); diff --git a/src/include/rtc.h b/src/include/rtc.h index 7b01ac0c..e394e9b6 100644 --- a/src/include/rtc.h +++ b/src/include/rtc.h @@ -4,6 +4,7 @@ struct rtc_msm_data uae_u8 clock_control_d; uae_u8 clock_control_e; uae_u8 clock_control_f; + int delayed_write; bool yearmode; }; @@ -14,6 +15,7 @@ struct rtc_ricoh_data uae_u8 clock_control_e; uae_u8 clock_control_f; uae_u8 rtc_memory[RF5C01A_RAM_SIZE], rtc_alarm[RF5C01A_RAM_SIZE]; + int delayed_write; }; uae_u8 get_clock_msm(struct rtc_msm_data *data, int addr, struct tm *ct); diff --git a/src/include/savestate.h b/src/include/savestate.h index 0e4759de..b6e9645f 100644 --- a/src/include/savestate.h +++ b/src/include/savestate.h @@ -11,6 +11,19 @@ #include "uae/types.h" +/* functions to save byte,word or long word + * independent of CPU's endianness */ + +extern void save_store_pos_func (uae_u8 **); +extern void save_store_size_func (uae_u8 **); +extern void restore_store_pos_func (uae_u8 **); +extern void restore_store_size_func (uae_u8 **); + +#define save_store_pos() save_store_pos_func (&dst) +#define save_store_size() save_store_size_func (&dst) +#define restore_store_pos() restore_store_pos_func (&src) +#define restore_store_size() restore_store_size_func (&src) + extern void save_u64_func (uae_u8 **, uae_u64); extern void save_u32_func (uae_u8 **, uae_u32); extern void save_u16_func (uae_u8 **, uae_u16); @@ -32,7 +45,9 @@ extern TCHAR *restore_string_func (uae_u8 **); #define SAVESTATE_PATH_CD 5 extern void save_path_func (uae_u8 **, const TCHAR*, int type); -extern TCHAR *restore_path_func (uae_u8 **, int type); +extern void save_path_full_func(uae_u8 **, const TCHAR*, int type); +extern TCHAR *restore_path_func(uae_u8 **, int type); +extern TCHAR *restore_path_full_func(uae_u8 **); #define save_u64(x) save_u64_func (&dst, (x)) #define save_u32(x) save_u32_func (&dst, (x)) @@ -48,7 +63,9 @@ extern TCHAR *restore_path_func (uae_u8 **, int type); #define restore_string() restore_string_func (&src) #define save_path(x, p) save_path_func (&dst, (x), p) +#define save_path_full(x, p) save_path_full_func (&dst, (x), p) #define restore_path(p) restore_path_func (&src, p) +#define restore_path_full() restore_path_full_func (&src) /* save, restore and initialize routines for Amiga's subsystems */ @@ -58,6 +75,11 @@ extern void restore_cpu_finish (void); extern uae_u8 *save_cpu (int *, uae_u8 *); extern uae_u8 *restore_cpu_extra (uae_u8 *); extern uae_u8 *save_cpu_extra (int *, uae_u8 *); +extern uae_u8 *save_cpu_trace (int *, uae_u8 *); +extern uae_u8 *restore_cpu_trace (uae_u8 *); + +extern uae_u8 *restore_mmu (uae_u8 *); +extern uae_u8 *save_mmu (int *, uae_u8 *); extern uae_u8 *restore_fpu (uae_u8 *); extern uae_u8 *save_fpu (int *, uae_u8 *); @@ -83,6 +105,9 @@ extern uae_u8 *save_custom_sprite (int num, int *len, uae_u8 *); extern uae_u8 *restore_custom_agacolors (uae_u8 *src); extern uae_u8 *save_custom_agacolors (int *len, uae_u8 *); +extern uae_u8 *restore_custom_event_delay (uae_u8 *src); +extern uae_u8 *save_custom_event_delay (int *len, uae_u8 *dstptr); + extern uae_u8 *restore_blitter (uae_u8 *src); extern uae_u8 *save_blitter (int *len, uae_u8 *); extern uae_u8 *restore_blitter_new (uae_u8 *src); @@ -110,12 +135,31 @@ extern uae_u8 *save_keyboard (int *,uae_u8*); extern uae_u8 *restore_akiko (uae_u8 *src); extern uae_u8 *save_akiko (int *len, uae_u8*); -extern void restore_akiko_finish (void); +extern void restore_akiko_finish(void); +extern void restore_akiko_final(void); + +extern uae_u8 *restore_cdtv (uae_u8 *src); +extern uae_u8 *save_cdtv (int *len, uae_u8*); +extern void restore_cdtv_finish(void); +extern void restore_cdtv_final(void); + +extern uae_u8 *restore_cdtv_dmac (uae_u8 *src); +extern uae_u8 *save_cdtv_dmac (int *len, uae_u8*); +extern uae_u8 *restore_scsi_dmac (int wdtype, uae_u8 *src); +extern uae_u8 *save_scsi_dmac (int wdtype, int *len, uae_u8*); + +extern uae_u8 *save_scsi_device (int wdtype, int num, int *len, uae_u8 *dstptr); +extern uae_u8 *restore_scsi_device (int wdtype, uae_u8 *src); + +extern uae_u8 *save_scsidev (int num, int *len, uae_u8 *dstptr); +extern uae_u8 *restore_scsidev (uae_u8 *src); extern uae_u8 *restore_filesys (uae_u8 *src); extern uae_u8 *save_filesys (int num, int *len); extern uae_u8 *restore_filesys_common (uae_u8 *src); extern uae_u8 *save_filesys_common (int *len); +extern uae_u8 *restore_filesys_paths(uae_u8 *src); +extern uae_u8 *save_filesys_paths(int num, int *len); extern int save_filesys_cando(void); extern uae_u8 *restore_gayle(uae_u8 *src); @@ -125,10 +169,33 @@ extern uae_u8 *save_gayle_ide (int num, int *len, uae_u8*); extern uae_u8 *save_cd (int num, int *len); extern uae_u8 *restore_cd (int, uae_u8 *src); +extern void restore_cd_finish (void); + +extern uae_u8 *save_configuration (int *len, bool fullconfig); +extern uae_u8 *restore_configuration (uae_u8 *src); +extern uae_u8 *save_log (int, int *len); +//extern uae_u8 *restore_log (uae_u8 *src); extern uae_u8 *restore_input (uae_u8 *src); extern uae_u8 *save_input (int *len, uae_u8 *dstptr); +extern uae_u8 *restore_inputstate (uae_u8 *src); +extern uae_u8 *save_inputstate (int *len, uae_u8 *dstptr); +extern void clear_inputstate (void); + +extern uae_u8 *save_a2065 (int *len, uae_u8 *dstptr); +extern uae_u8 *restore_a2065 (uae_u8 *src); +extern void restore_a2065_finish (void); + +extern uae_u8 *restore_debug_memwatch (uae_u8 *src); +extern uae_u8 *save_debug_memwatch (int *len, uae_u8 *dstptr); +extern void restore_debug_memwatch_finish (void); + +extern uae_u8 *save_screenshot(int monid, int *len); + +extern uae_u8 *save_cycles (int *len, uae_u8 *dstptr); +extern uae_u8 *restore_cycles (uae_u8 *src); + extern void restore_cram (int, size_t); extern void restore_bram (int, size_t); extern void restore_fram (int, size_t, int); @@ -152,19 +219,25 @@ extern uae_u8 *save_a3000hram (int *); extern uae_u8 *restore_rom (uae_u8 *); extern uae_u8 *save_rom (int, int *, uae_u8 *); -extern uae_u8 *save_expansion_info(int*, uae_u8*); -extern uae_u8 *restore_expansion_info(uae_u8*); +extern uae_u8 *save_expansion_boards(int*, uae_u8*, int); +extern uae_u8 *restore_expansion_boards(uae_u8*); +extern void restore_expansion_finish(void); extern uae_u8 *restore_action_replay (uae_u8 *); extern uae_u8 *save_action_replay (int *, uae_u8 *); extern uae_u8 *restore_hrtmon (uae_u8 *); extern uae_u8 *save_hrtmon (int *, uae_u8 *); +extern void restore_ar_finish (void); -extern void savestate_initsave (const TCHAR *filename, int docompress, int nodialogs, bool save); +extern void savestate_initsave (const TCHAR *filename); extern int save_state (const TCHAR *filename, const TCHAR *description); extern void restore_state (const TCHAR *filename); -extern void savestate_restore_finish (void); +extern bool savestate_restore_finish(void); +extern void savestate_restore_final(void); +extern void savestate_memorysave (void); + +extern void custom_save_state (void); extern void custom_prepare_savestate (void); extern bool savestate_check (void); @@ -182,7 +255,18 @@ extern struct zfile *savestate_file; STATIC_INLINE bool isrestore (void) { - return savestate_state == STATE_RESTORE; + return savestate_state == STATE_RESTORE || savestate_state == STATE_REWIND; } +extern void savestate_quick (int slot, int save); + +extern void savestate_capture (int); +extern void savestate_free (void); +extern void savestate_init (void); +extern void savestate_rewind (void); +extern int savestate_dorewind (int); +extern void savestate_listrewind (void); +extern void statefile_save_recording (const TCHAR*); +extern void savestate_capture_request (void); + #endif /* UAE_SAVESTATE_H */ diff --git a/src/include/scsi.h b/src/include/scsi.h index 3971d81c..50f966fa 100644 --- a/src/include/scsi.h +++ b/src/include/scsi.h @@ -6,6 +6,26 @@ #define SCSI_DEFAULT_DATA_BUFFER_SIZE (256 * 512) +struct scsi_data_tape +{ + TCHAR tape_dir[MAX_DPATH]; + int file_number; + uae_s64 file_offset; + int blocksize; + bool realdir; + struct zdirectory *zd; + struct my_opendir_s *od; + struct zfile *zf; + struct zfile *index; + int beom; + bool wp; + bool nomedia; + bool unloaded; + bool init_loaded; + bool pending_filemark; + bool last_filemark; +}; + struct scsi_data { int id; @@ -29,23 +49,265 @@ struct scsi_data int buffer_size; struct hd_hardfiledata *hdhfd; struct hardfiledata *hfd; + struct scsi_data_tape *tape; int device_type; + int nativescsiunit; + int cd_emu_unit; bool atapi; uae_u32 unit_attention; + int uae_unitnum; }; -extern struct scsi_data *scsi_alloc_generic(struct hardfiledata *hfd, int type); +extern struct scsi_data *scsi_alloc_generic(struct hardfiledata *hfd, int type, int); +extern struct scsi_data *scsi_alloc_hd(int, struct hd_hardfiledata*, int); +extern struct scsi_data *scsi_alloc_cd(int, int, bool, int); +extern struct scsi_data *scsi_alloc_tape(int id, const TCHAR *tape_directory, bool readonly, int); +extern struct scsi_data *scsi_alloc_native(int, int); extern void scsi_free(struct scsi_data*); +extern void scsi_reset(void); extern void scsi_start_transfer(struct scsi_data*); +extern int scsi_send_data(struct scsi_data*, uae_u8); +extern int scsi_receive_data(struct scsi_data*, uae_u8*, bool next); extern void scsi_emulate_cmd(struct scsi_data *sd); -extern void scsi_clear_sense(struct scsi_data *sd); +extern void scsi_illegal_lun(struct scsi_data *sd); +extern bool scsi_cmd_is_safe(uae_u8 cmd); extern int scsi_hd_emulate(struct hardfiledata *hfd, struct hd_hardfiledata *hdhfd, uae_u8 *cmdbuf, int scsi_cmd_len, uae_u8 *scsi_data, int *data_len, uae_u8 *r, int *reply_len, uae_u8 *s, int *sense_len); +extern int scsi_tape_emulate(struct scsi_data_tape *sd, uae_u8 *cmdbuf, int scsi_cmd_len, + uae_u8 *scsi_data, int *data_len, uae_u8 *r, int *reply_len, uae_u8 *s, int *sense_len); extern bool scsi_emulate_analyze (struct scsi_data*); +extern bool tape_get_info (int, struct device_info*); +extern struct scsi_data_tape *tape_alloc (int unitnum, const TCHAR *tape_directory, bool readonly); +extern void tape_free (struct scsi_data_tape*); +extern void tape_media_change (int unitnum, struct uaedev_config_info*); + +int add_scsi_device(struct scsi_data **sd, int ch, struct uaedev_config_info *ci, struct romconfig *rc); +int add_scsi_hd (struct scsi_data **sd, int ch, struct hd_hardfiledata *hfd, struct uaedev_config_info *ci); +int add_scsi_cd (struct scsi_data **sd, int ch, int unitnum); +int add_scsi_tape (struct scsi_data **sd, int ch, const TCHAR *tape_directory, bool readonly); +void free_scsi (struct scsi_data *sd); +bool tape_can_write(const TCHAR *tape_directory); + +void scsi_freenative(struct scsi_data **sd, int max); +void scsi_addnative(struct scsi_data **sd); + +#define SCSI_NO_SENSE_DATA 0x00 +#define SCSI_NOT_READY 0x04 +#define SCSI_NOT_LOADED 0x09 +#define SCSI_INSUF_CAPACITY 0x0a +#define SCSI_HARD_DATA_ERROR 0x11 +#define SCSI_WRITE_PROTECT 0x17 +#define SCSI_CORRECTABLE_ERROR 0x18 +#define SCSI_FILE_MARK 0x1c +#define SCSI_INVALID_COMMAND 0x20 +#define SCSI_INVALID_FIELD 0x24 +#define SCSI_INVALID_LUN 0x25 +#define SCSI_UNIT_ATTENTION 0x30 +#define SCSI_END_OF_MEDIA 0x34 +#define SCSI_MEDIUM_NOT_PRESENT 0x3a + +#define SCSI_SK_NO_SENSE 0x0 +#define SCSI_SK_REC_ERR 0x1 /* recovered error */ +#define SCSI_SK_NOT_READY 0x2 +#define SCSI_SK_MED_ERR 0x3 /* medium error */ +#define SCSI_SK_HW_ERR 0x4 /* hardware error */ +#define SCSI_SK_ILLEGAL_REQ 0x5 +#define SCSI_SK_UNIT_ATT 0x6 /* unit attention */ +#define SCSI_SK_DATA_PROTECT 0x7 +#define SCSI_SK_BLANK_CHECK 0x8 +#define SCSI_SK_VENDOR_SPEC 0x9 +#define SCSI_SK_COPY_ABORTED 0xA +#define SCSI_SK_ABORTED_CMND 0xB +#define SCSI_SK_VOL_OVERFLOW 0xD +#define SCSI_SK_MISCOMPARE 0xE + #define SCSI_STATUS_GOOD 0x00 #define SCSI_STATUS_CHECK_CONDITION 0x02 +#define SCSI_STATUS_CONDITION_MET 0x04 +#define SCSI_STATUS_BUSY 0x08 +#define SCSI_STATUS_INTERMEDIATE 0x10 +#define SCSI_STATUS_ICM 0x14 /* intermediate condition met */ +#define SCSI_STATUS_RESERVATION_CONFLICT 0x18 +#define SCSI_STATUS_COMMAND_TERMINATED 0x22 +#define SCSI_STATUS_QUEUE_FULL 0x28 +#define SCSI_STATUS_ACA_ACTIVE 0x30 + +#define SCSI_MEMORY_FUNCTIONS(x, y, z) \ +static void REGPARAM2 x ## _bput(uaecptr addr, uae_u32 b) \ +{ \ + y ## _bput(&z, addr, b); \ +} \ +static void REGPARAM2 x ## _wput(uaecptr addr, uae_u32 b) \ +{ \ + y ## _wput(&z, addr, b); \ +} \ +static void REGPARAM2 x ## _lput(uaecptr addr, uae_u32 b) \ +{ \ + y ## _lput(&z, addr, b); \ +} \ +static uae_u32 REGPARAM2 x ## _bget(uaecptr addr) \ +{ \ +return y ## _bget(&z, addr); \ +} \ +static uae_u32 REGPARAM2 x ## _wget(uaecptr addr) \ +{ \ +return y ## _wget(&z, addr); \ +} \ +static uae_u32 REGPARAM2 x ## _lget(uaecptr addr) \ +{ \ +return y ## _lget(&z, addr); \ +} + +void soft_scsi_put(uaecptr addr, int size, uae_u32 v); +uae_u32 soft_scsi_get(uaecptr addr, int size); + +void apollo_scsi_bput(uaecptr addr, uae_u8 v, uae_u32 config); +uae_u8 apollo_scsi_bget(uaecptr addr, uae_u32 config); +void apollo_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +void ivsvector_scsi_bput(uaecptr addr, uae_u8 v); +uae_u8 ivsvector_scsi_bget(uaecptr addr); +void ivsvector_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); +bool ivsvector_init(struct autoconfig_info *aci); + +void twelvegauge_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); +bool twelvegauge_init(struct autoconfig_info *aci); + +uae_u8 parallel_port_scsi_read(int reg, uae_u8 data, uae_u8 dir); +void parallel_port_scsi_write(int reg, uae_u8 v, uae_u8 dir); +extern bool parallel_port_scsi; + +bool supra_init(struct autoconfig_info*); +void supra_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool golem_init(struct autoconfig_info*); +void golem_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool stardrive_init(struct autoconfig_info*); +void stardrive_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool kommos_init(struct autoconfig_info*); +void kommos_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool vector_init(struct autoconfig_info*); +void vector_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool protar_init(struct autoconfig_info *aci); +void protar_add_ide_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool add500_init(struct autoconfig_info *aci); +void add500_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool kronos_init(struct autoconfig_info *aci); +void kronos_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool adscsi_init(struct autoconfig_info *aci); +void adscsi_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool trifecta_init(struct autoconfig_info *aci); +void trifecta_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +void rochard_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); +bool rochard_scsi_init(struct romconfig *rc, uaecptr baseaddress); + +bool cltda1000scsi_init(struct autoconfig_info *aci); +void cltda1000scsi_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool ptnexus_init(struct autoconfig_info *aci); +void ptnexus_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool dataflyer_init(struct autoconfig_info *aci); +void dataflyer_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool dataflyerplus_scsi_init(struct romconfig *rc, uaecptr baseaddress); +void dataflyerplus_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool tecmar_init(struct autoconfig_info *aci); +void tecmar_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool xebec_init(struct autoconfig_info *aci); +void xebec_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool microforge_init(struct autoconfig_info *aci); +void microforge_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool paradox_init(struct autoconfig_info *aci); +void paradox_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool hda506_init(struct autoconfig_info *aci); +void hda506_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool alf1_init(struct autoconfig_info *aci); +void alf1_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool promigos_init(struct autoconfig_info *aci); +void promigos_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool system2000_preinit(struct autoconfig_info *aci); +bool system2000_init(struct autoconfig_info *aci); +void system2000_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool omtiadapter_init(struct autoconfig_info *aci); +void omtiadapter_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool phoenixboard_init(struct autoconfig_info *aci); +void phoenixboard_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool trumpcard_init(struct autoconfig_info*); +void trumpcard_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool trumpcardpro_init(struct autoconfig_info*); +void trumpcardpro_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool scram5380_init(struct autoconfig_info*); +void scram5380_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool ossi_init(struct autoconfig_info*); +void ossi_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool hardframe_init(struct autoconfig_info*); +void hardframe_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool malibu_init(struct autoconfig_info*); +void malibu_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool addhard_init(struct autoconfig_info*); +void addhard_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool inmate_init(struct autoconfig_info*); +void inmate_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool emplant_init(struct autoconfig_info*); +void emplant_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool hd3000_init(struct autoconfig_info *aci); +void hd3000_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool wedge_preinit(struct autoconfig_info *aci); +bool wedge_init(struct autoconfig_info *aci); +void wedge_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool eveshamref_init(struct autoconfig_info *aci); +void eveshamref_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool profex_init(struct autoconfig_info *aci); +void profex_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool fasttrak_init(struct autoconfig_info *aci); +void fasttrak_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +bool overdrive_init(struct autoconfig_info *aci); +void overdrive_add_scsi_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); + +uae_u8 idescsi_scsi_get(uaecptr addr); +void idescsi_scsi_put(uaecptr addr, uae_u8 v); + +void x86_rt1000_bput(int, uae_u8); +uae_u8 x86_rt1000_bget(int); +bool x86_rt1000_init(struct autoconfig_info *aci); +void x86_rt1000_add_unit(int ch, struct uaedev_config_info *ci, struct romconfig *rc); #endif /* UAE_SCSI_H */ diff --git a/src/include/statusline.h b/src/include/statusline.h index 4cd2ee35..b4852b5e 100644 --- a/src/include/statusline.h +++ b/src/include/statusline.h @@ -12,7 +12,7 @@ #define TD_RIGHT 1 #define TD_BOTTOM 2 -static int td_pos = (TD_RIGHT|TD_BOTTOM); +static int td_pos = (TD_RIGHT | TD_BOTTOM); #define TD_NUM_WIDTH 7 #define TD_NUM_HEIGHT 7 @@ -27,7 +27,10 @@ static int td_pos = (TD_RIGHT|TD_BOTTOM); #define STATUSLINE_RTG 2 #define STATUSLINE_TARGET 0x80 -extern void draw_status_line_single(uae_u8* buf, int bpp, int y, int totalwidth, uae_u32 *rc, uae_u32 *gc, uae_u32 *bc, uae_u32 *alpha); +extern void draw_status_line_single(uae_u8 *buf, int bpp, int y, int totalwidth, uae_u32 *rc, uae_u32 *gc, uae_u32 *bc, uae_u32 *alpha); +extern void statusline_single_erase(uae_u8 *buf, int bpp, int y, int totalwidth); +extern void statusline_getpos(int *x, int *y, int width, int height, int hx, int vx); +extern bool softstatusline(void); #define STATUSTYPE_FLOPPY 1 #define STATUSTYPE_DISPLAY 2 @@ -35,7 +38,14 @@ extern void draw_status_line_single(uae_u8* buf, int bpp, int y, int totalwidth, #define STATUSTYPE_CD 4 #define STATUSTYPE_OTHER 5 +extern bool createstatusline(int); +extern void deletestatusline(int); +extern void statusline_render(int, uae_u8 *buf, int bpp, int pitch, int width, int height, uae_u32 *rc, uae_u32 *gc, uae_u32 *bc, uae_u32 *alpha); +//extern void statusline_add_message(int statustype, const TCHAR *format, ...); extern void statusline_clear(void); extern void statusline_vsync(void); +extern void statusline_updated(int); +extern bool has_statusline_updated(void); +extern const TCHAR *statusline_fetch(void); #endif /* UAE_STATUSLINE_H */ diff --git a/src/include/sysdeps.h b/src/include/sysdeps.h index 8114e11b..b5252987 100644 --- a/src/include/sysdeps.h +++ b/src/include/sysdeps.h @@ -43,7 +43,7 @@ using namespace std; #if defined(__x86_64__) || defined(_M_AMD64) #define CPU_x86_64 1 #define CPU_64_BIT 1 -#elif defined(__i386__) || defined(_M_IX86) && !defined(__arm__) +#elif defined(__i386__) || defined(_M_IX86) && !defined(__arm__) && !defined(__aarch64__) #define CPU_i386 1 #elif defined(__arm__) || defined(_M_ARM) || defined(__aarch64__) #define CPU_arm 1 @@ -54,7 +54,7 @@ using namespace std; #endif #ifndef __STDC__ -#ifndef _MSC_VER_ +#ifndef _MSC_VER #error "Your compiler is not ANSI. Get a real one." #endif #endif @@ -325,7 +325,7 @@ extern void gui_message (const TCHAR *,...); #endif #define NOINLINE __attribute__ ((noinline)) #define NORETURN __attribute__ ((noreturn)) -#elif _MSC_VER_ +#elif _MSC_VER #define STATIC_INLINE static __forceinline #define NOINLINE __declspec(noinline) #define NORETURN __declspec(noreturn) @@ -368,7 +368,7 @@ extern void gui_message (const TCHAR *,...); STATIC_INLINE uae_u32 do_byteswap_32(uae_u32 v) { __asm__ ( - "rev %0, %0" + "rev %0, %0" : "=r" (v) : "0" (v) ); return v; } @@ -380,6 +380,24 @@ STATIC_INLINE uae_u32 do_byteswap_16(uae_u32 v) { } #define bswap_16(x) do_byteswap_16(x) #define bswap_32(x) do_byteswap_32(x) + +#elif defined(CPU_AARCH64) + +STATIC_INLINE uae_u32 do_byteswap_32(uae_u32 v) { + __asm__ ( + "rev %w0, %w0" + : "=r" (v) : "0" (v) ); return v; +} + +STATIC_INLINE uae_u32 do_byteswap_16(uae_u32 v) { + __asm__ ( + "rev16 %w0, %w0\n\t" + "uxth %w0, %w0" + : "=r" (v) : "0" (v) ); return v; +} +#define bswap_16(x) do_byteswap_16(x) +#define bswap_32(x) do_byteswap_32(x) + #else /* Try to use system bswap_16/bswap_32 functions. */ @@ -419,8 +437,6 @@ STATIC_INLINE uae_u32 do_byteswap_16(uae_u32 v) { #endif -#define DBLEQU(f, i) (abs ((f) - (i)) < 0.000001) - #ifdef HAVE_VAR_ATTRIBUTE_UNUSED #define NOWARN_UNUSED(x) __attribute__((unused)) x #else diff --git a/src/include/traps.h b/src/include/traps.h index 52036667..7a97330b 100644 --- a/src/include/traps.h +++ b/src/include/traps.h @@ -81,6 +81,7 @@ extern uae_u32 CallFunc (TrapContext *context, uaecptr func); * Initialization */ void init_traps(void); +void free_traps(void); void init_extended_traps(void); #define deftrap(f) define_trap((f), 0, _T(#f)) @@ -89,11 +90,23 @@ void init_extended_traps(void); /* New trap system */ +void call_hardware_trap(uae_u8*, uaecptr, int); +void trap_set_background(TrapContext *ctx); +void trap_background_set_complete(TrapContext *ctx); bool trap_valid_address(TrapContext *ctx, uaecptr addr, uae_u32 size); +bool trap_is_indirect(void); +void trap_dos_active(void); +void trap_reset(void); +typedef uae_u32 (*TRAP_CALLBACK)(TrapContext*, void*); +void trap_callback(TRAP_CALLBACK, void*); void trap_memcpyha_safe(TrapContext *ctx, uaecptr dst, const uae_u8 *src, int size); void trap_memcpyah_safe(TrapContext *ctx, uae_u8 *dst, uaecptr src, int size); +TrapContext *alloc_host_main_trap_context(void); +TrapContext *alloc_host_thread_trap_context(void); +void free_host_trap_context(TrapContext*); + uae_u32 trap_get_dreg(TrapContext *ctx, int reg); uae_u32 trap_get_areg(TrapContext *ctx, int reg); void trap_set_dreg(TrapContext *ctx, int reg, uae_u32 v); diff --git a/src/include/uae.h b/src/include/uae.h index 9a1f41db..69a029a7 100644 --- a/src/include/uae.h +++ b/src/include/uae.h @@ -11,18 +11,13 @@ #include "uae/types.h" -#if defined(__clang__) || defined (__GNUC__) -#define ATTRIBUTE_NO_SANITIZE_ADDRESS __attribute__((no_sanitize_address)) -#else -# define ATTRIBUTE_NO_SANITIZE_ADDRESS -#endif - -extern void do_start_program (void); -extern void start_program (void); -extern void leave_program (void); extern void real_main (int, TCHAR **); +extern void usage (void); extern void sleep_millis (int ms); extern int sleep_millis_main(int ms); +extern int sleep_millis_amiga(int ms); +extern void sleep_cpu_wakeup(void); +extern int sleep_resolution; #define UAE_QUIT 1 #define UAE_RESET 2 @@ -38,16 +33,30 @@ extern void target_addtorecent (const TCHAR*, int); extern void target_run (void); extern void target_quit (void); extern void target_restart (void); +extern void target_getdate(int *y, int *m, int *d); extern void target_startup_msg(const TCHAR *title, const TCHAR *msg); +extern void target_cpu_speed(void); +extern int target_sleep_nanos(int); +extern bool get_plugin_path (TCHAR *out, int size, const TCHAR *path); extern void stripslashes (TCHAR *p); extern void fixtrailing (TCHAR *p); +extern void fullpath(TCHAR *path, int size); +extern void fullpath(TCHAR *path, int size, bool userelative); extern void getpathpart (TCHAR *outpath, int size, const TCHAR *inpath); extern void getfilepart (TCHAR *out, int size, const TCHAR *path); +extern bool samepath(const TCHAR *p1, const TCHAR *p2); +extern bool target_isrelativemode(void); extern uae_u32 getlocaltime (void); +extern bool isguiactive(void); +extern bool is_mainthread(void); extern int quit_program; +extern bool console_emulation; -extern TCHAR start_path_data[MAX_DPATH]; +extern TCHAR warning_buffer[256]; +extern TCHAR start_path_data[]; +extern TCHAR start_path_data_exe[]; +extern TCHAR start_path_plugins[]; /* This structure is used to define menus. The val field can hold key * shortcuts, or one of these special codes: @@ -63,9 +72,25 @@ struct bstring { int val; }; +extern TCHAR *colormodes[]; +extern int saveimageoriginalpath; extern void fetch_saveimagepath (TCHAR*, int, int); +extern void fetch_configurationpath (TCHAR *out, int size); +extern void fetch_luapath (TCHAR *out, int size); +extern void fetch_screenshotpath (TCHAR *out, int size); +extern void fetch_ripperpath (TCHAR *out, int size); +extern void fetch_statefilepath (TCHAR *out, int size); +extern void fetch_inputfilepath (TCHAR *out, int size); extern void fetch_datapath (TCHAR *out, int size); extern void fetch_rompath (TCHAR *out, int size); -#define uaerand() rand() +//extern uae_u32 uaerand (void); +#define uaerand() ((uae_u32)rand()) +extern uae_u32 uaesrand (uae_u32 seed); +extern uae_u32 uaerandgetseed (void); + +/* the following prototypes should probably be moved somewhere else */ + +int get_guid_target (uae_u8 *out); +void filesys_addexternals (void); #endif /* UAE_UAE_H */ diff --git a/src/include/uae/dlopen.h b/src/include/uae/dlopen.h index e6c97a1a..5468d29b 100644 --- a/src/include/uae/dlopen.h +++ b/src/include/uae/dlopen.h @@ -14,7 +14,7 @@ #ifdef _WIN32 #define UAE_DLHANDLE HINSTANCE #else - #define UAE_DLHANDLE void * +#define UAE_DLHANDLE void * #endif /* General loadable module support */ diff --git a/src/include/uae/string.h b/src/include/uae/string.h index ab5335c1..22608bef 100644 --- a/src/include/uae/string.h +++ b/src/include/uae/string.h @@ -56,7 +56,7 @@ #define _vsntprintf vsnprintf #endif -static size_t uae_tcslcpy(char *dst, const TCHAR *src, size_t size) +static inline size_t uae_tcslcpy(char *dst, const TCHAR *src, size_t size) { if (size == 0) { return 0; @@ -71,7 +71,7 @@ static size_t uae_tcslcpy(char *dst, const TCHAR *src, size_t size) return src_len; } -static size_t uae_strlcpy(char *dst, const char *src, size_t size) +static inline size_t uae_strlcpy(char *dst, const char *src, size_t size) { if (size == 0) { return 0; diff --git a/src/include/xwin.h b/src/include/xwin.h index 0b71ce4b..5b9aa3f1 100644 --- a/src/include/xwin.h +++ b/src/include/xwin.h @@ -21,72 +21,108 @@ extern uae_u32 p96_rgbx16[65536]; extern int graphics_setup (void); extern int graphics_init (bool); -extern void graphics_leave (void); -extern bool handle_events(void); +extern void graphics_leave(void); +extern void graphics_reset(bool); +extern bool handle_events (void); extern int handle_msgpump (void); +extern void setup_brkhandler (void); +extern int isfullscreen (void); +extern void toggle_fullscreen(int); +extern bool toggle_rtg(int); +extern void close_rtg(); -extern bool vsync_switchmode (int); -extern int isvsync_chipset(void); -extern int isvsync_rtg(void); -extern int isvsync(void); +extern void toggle_mousegrab (void); +//void setmouseactivexy(int x, int y, int dir); -extern bool render_screen (bool); -extern void show_screen (int); -extern bool show_screen_maybe (bool); +extern void desktop_coords(int *dw, int *dh, int *x, int *y, int *w, int *h); +extern bool vsync_switchmode(int hz); +extern void vsync_clear(void); +extern int vsync_isdone(frame_time_t*); +extern void doflashscreen (void); +//extern int flashscreen; +extern void updatedisplayarea(); -extern int lockscr (void); -extern void unlockscr (void); -extern bool target_graphics_buffer_update (void); +extern int isvsync_rtg (void); +extern int isvsync (void); -extern void screenshot (int); +extern void flush_line(struct vidbuffer*, int); +extern void flush_block(struct vidbuffer*, int, int); +extern void flush_screen(struct vidbuffer*, int, int); +extern void flush_clear_screen(struct vidbuffer*); +extern bool render_screen(bool); +extern void show_screen(int mode); +extern bool show_screen_maybe(bool); + +extern int lockscr(); +extern void unlockscr(); +extern bool target_graphics_buffer_update(); +extern float target_adjust_vblank_hz(float); +extern int target_get_display_scanline(int displayindex); +extern void target_spin(int); + +//void getgfxoffset(float *dxp, float *dyp, float *mxp, float *myp); +float target_getcurrentvblankrate(); + +extern int debuggable (void); +extern void screenshot(int,int); +void refreshtitle (void); extern int bits_in_mask (unsigned long mask); extern int mask_shift (unsigned long mask); extern unsigned int doMask (int p, int bits, int shift); extern unsigned int doMask256 (int p, int bits, int shift); -extern void alloc_colors64k(int, int, int, int, int, int, int, int, int, int, bool); -extern void alloc_colors_rgb(int rw, int gw, int bw, int rs, int gs, int bs, int aw, int as, int alpha, int byte_swap, - uae_u32 *rc, uae_u32 *gc, uae_u32 *bc); -extern void alloc_colors_picasso (int rw, int gw, int bw, int rs, int gs, int bs, int rgbfmt); +extern void alloc_colors64k (int, int, int, int, int, int, int, int, int, int, bool); +extern void alloc_colors_rgb (int rw, int gw, int bw, int rs, int gs, int bs, int aw, int as, int alpha, int byte_swap, + uae_u32 *rc, uae_u32 *gc, uae_u32 *bc); +extern void alloc_colors_picasso (int rw, int gw, int bw, int rs, int gs, int bs, int rgbfmt, uae_u32 *rgbx16); +//extern float getvsyncrate(float hz, int *mult); -/* The graphics code has a choice whether it wants to use a large buffer -* for the whole display, or only a small buffer for a single line. -* If you use a large buffer: -* - set bufmem to point at it -* - set linemem to 0 -* - if memcpy within bufmem would be very slow, i.e. because bufmem is -* in graphics card memory, also set emergmem to point to a buffer -* that is large enough to hold a single line. -* - implement flush_line to be a no-op. -* If you use a single line buffer: -* - set bufmem and emergmem to 0 -* - set linemem to point at your buffer -* - implement flush_line to copy a single line to the screen -*/ + /* The graphics code has a choice whether it wants to use a large buffer + * for the whole display, or only a small buffer for a single line. + * If you use a large buffer: + * - set bufmem to point at it + * - set linemem to 0 + * - if memcpy within bufmem would be very slow, i.e. because bufmem is + * in graphics card memory, also set emergmem to point to a buffer + * that is large enough to hold a single line. + * - implement flush_line to be a no-op. + * If you use a single line buffer: + * - set bufmem and emergmem to 0 + * - set linemem to point at your buffer + * - implement flush_line to copy a single line to the screen + */ struct vidbuffer { + /* Function implemented by graphics driver */ + void (*flush_line) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb, int line_no); + void (*flush_block) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb, int first_line, int end_line); + void (*flush_screen) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb, int first_line, int end_line); + void (*flush_clear_screen) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb); + int (*lockscr) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb); + void (*unlockscr) (struct vidbuf_description *gfxinfo, struct vidbuffer *vb); + uae_u8 *linemem; + uae_u8 *emergmem; + uae_u8 *bufmem; - int rowbytes; /* Bytes per row in the memory pointed at by bufmem. */ - int pixbytes; /* Bytes per pixel. */ - /* size of max visible image */ + int rowbytes; /* Bytes per row in the memory pointed at by bufmem. */ + int pixbytes; /* Bytes per pixel. */ + /* size of this buffer */ + /* size of max visible image */ int outwidth; int outheight; + int last_drawn_line; }; extern int max_uae_width, max_uae_height; struct vidbuf_description { - struct vidbuffer drawbuffer; + struct vidbuffer drawbuffer; }; -extern struct vidbuf_description gfxvidinfo; - -extern int custom_frame_redraw_necessary; - struct amigadisplay { - bool picasso_requested_on; + volatile bool picasso_requested_on; bool picasso_requested_forced_on; bool picasso_on; int picasso_redraw_necessary; @@ -100,6 +136,14 @@ struct amigadisplay struct vidbuf_description gfxvidinfo; }; -//extern struct amigadisplay adisplays[MAX_AMIGADISPLAYS]; +extern struct amigadisplay adisplays; + +STATIC_INLINE int isvsync_chipset (void) +{ + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on) + return 0; + return 1; +} #endif /* UAE_XWIN_H */ diff --git a/src/include/zarchive.h b/src/include/zarchive.h index 7d580455..d309627d 100644 --- a/src/include/zarchive.h +++ b/src/include/zarchive.h @@ -8,13 +8,13 @@ typedef uae_s64 (*ZFILEWRITE)(const void*, uae_u64, uae_u64, struct zfile*); typedef uae_s64 (*ZFILESEEK)(struct zfile*, uae_s64, int); struct zfile { - TCHAR *name; - TCHAR *zipname; - TCHAR *mode; + TCHAR *name; + TCHAR *zipname; + TCHAR *mode; TCHAR *originalname; - FILE *f; // real file handle if physical file - uae_u8 *data; // unpacked data - int dataseek; // use seek position even if real file + FILE *f; // real file handle if physical file + uae_u8 *data; // unpacked data + int dataseek; // use seek position even if real file struct zfile *archiveparent; // set if parent is archive and this has not yet been unpacked (datasize < size) int archiveid; uae_s64 size; // real size @@ -111,19 +111,20 @@ struct zarchive_info extern int zfile_is_ignore_ext (const TCHAR *name); extern struct zvolume *zvolume_alloc (struct zfile *z, unsigned int id, void *handle, const TCHAR*); -extern struct zvolume *zvolume_alloc_empty (struct zvolume *zv, const TCHAR *name); +//extern struct zvolume *zvolume_alloc_empty (struct zvolume *zv, const TCHAR *name); extern struct znode *zvolume_addfile_abs (struct zvolume *zv, struct zarchive_info*); extern struct znode *zvolume_adddir_abs (struct zvolume *zv, struct zarchive_info *zai); -extern struct znode *znode_adddir (struct znode *parent, const TCHAR *name, struct zarchive_info*); +//extern struct znode *znode_adddir (struct znode *parent, const TCHAR *name, struct zarchive_info*); extern struct zvolume *archive_directory_plain (struct zfile *zf); extern struct zvolume *archive_directory_lha(struct zfile *zf); extern struct zfile *archive_access_lha (struct znode *zn); extern struct zvolume *archive_directory_zip(struct zfile *zf); extern struct zvolume *archive_directory_7z (struct zfile *z); +//extern struct zfile *archive_access_7z (struct znode *zn); extern struct zvolume *archive_directory_rar (struct zfile *z); -extern struct zfile *archive_access_rar (struct znode *zn); +//extern struct zfile *archive_access_rar (struct znode *zn); extern struct zvolume *archive_directory_lzx (struct zfile *in_file); extern struct zfile *archive_access_lzx (struct znode *zn); extern struct zvolume *archive_directory_arcacc (struct zfile *z, unsigned int id); @@ -132,7 +133,7 @@ extern struct zvolume *archive_directory_adf (struct znode *zn, struct zfile *z) extern struct zvolume *archive_directory_rdb (struct zfile *z); extern struct zvolume *archive_directory_fat (struct zfile *z); extern struct zvolume *archive_directory_tar (struct zfile *zf); -extern struct zfile *archive_access_tar (struct znode *zn); +//extern struct zfile *archive_access_tar (struct znode *zn); extern struct zfile *archive_access_select (struct znode *parent, struct zfile *zf, unsigned int id, int doselect, int *retcode, int index); extern struct zfile *archive_access_arcacc_select (struct zfile *zf, unsigned int id, int *retcode); @@ -145,6 +146,6 @@ extern void archive_access_close (void *handle, unsigned int id); extern struct zfile *archive_getzfile (struct znode *zn, unsigned int id, int flags); extern struct zfile *archive_unpackzfile (struct zfile *zf); -extern struct zfile *decompress_zfd (struct zfile*); +//extern struct zfile *decompress_zfd (struct zfile*); #endif /* UAE_ZARCHIVE_H */ diff --git a/src/include/zfile.h b/src/include/zfile.h index 640ce537..913684f8 100644 --- a/src/include/zfile.h +++ b/src/include/zfile.h @@ -17,6 +17,7 @@ struct zdirectory; #define FS_DIRECTORY 0 #define FS_ARCHIVE 1 +#define FS_CDFS 2 struct fs_dirhandle { @@ -24,6 +25,7 @@ struct fs_dirhandle union { struct zdirectory *zd; struct my_opendir_s *od; + struct cd_opendir_s *isod; }; }; struct fs_filehandle @@ -32,6 +34,7 @@ struct fs_filehandle union { struct zfile *zf; struct my_openfile_s *of; + struct cd_openfile_s *isof; }; }; @@ -44,9 +47,10 @@ extern struct zfile *zfile_fopen_empty (struct zfile*, const TCHAR *name, uae_u6 extern struct zfile *zfile_fopen_empty (struct zfile*, const TCHAR *name); extern struct zfile *zfile_fopen_data (const TCHAR *name, uae_u64 size, const uae_u8 *data); extern struct zfile *zfile_fopen_load_zfile (struct zfile *f); -extern uae_u8 *zfile_load_data (const TCHAR *name, const uae_u8 *data,int datalen, int *outlen); +//extern uae_u8 *zfile_load_data (const TCHAR *name, const uae_u8 *data,int datalen, int *outlen); extern uae_u8 *zfile_load_file(const TCHAR *name, int *outlen); extern struct zfile *zfile_fopen_parent (struct zfile*, const TCHAR*, uae_u64 offset, uae_u64 size); +//extern uae_u8 *zfile_get_data_pointer(struct zfile *z, int *len); extern int zfile_exists (const TCHAR *name); extern void zfile_fclose (struct zfile *); @@ -57,29 +61,30 @@ extern size_t zfile_fread (void *b, size_t l1, size_t l2, struct zfile *z); extern size_t zfile_fwrite (const void *b, size_t l1, size_t l2, struct zfile *z); extern TCHAR *zfile_fgets (TCHAR *s, int size, struct zfile *z); extern char *zfile_fgetsa (char *s, int size, struct zfile *z); -extern size_t zfile_fputs (struct zfile *z, const TCHAR *s); +//extern size_t zfile_fputs (struct zfile *z, const TCHAR *s); extern int zfile_getc (struct zfile *z); extern int zfile_putc (int c, struct zfile *z); extern int zfile_ferror (struct zfile *z); extern uae_u8 *zfile_getdata (struct zfile *z, uae_s64 offset, int len, int *outlen); extern void zfile_exit (void); -extern int execute_command (TCHAR *); +//extern int execute_command (TCHAR *); extern int zfile_iscompressed (struct zfile *z); extern int zfile_zcompress (struct zfile *dst, void *src, int size); extern int zfile_zuncompress (void *dst, int dstsize, struct zfile *src, int srcsize); extern int zfile_gettype (struct zfile *z); extern int zfile_zopen (const TCHAR *name, zfile_callback zc, void *user); extern TCHAR *zfile_getname (struct zfile *f); +//extern TCHAR *zfile_getoriginalname (struct zfile *f); extern TCHAR *zfile_getfilename (struct zfile *f); extern uae_u32 zfile_crc32 (struct zfile *f); extern struct zfile *zfile_dup (struct zfile *f); extern struct zfile *zfile_gunzip (struct zfile *z); extern int zfile_is_diskimage (const TCHAR *name); extern int iszip (struct zfile *z); -extern int zfile_convertimage (const TCHAR *src, const TCHAR *dst); +//extern int zfile_convertimage (const TCHAR *src, const TCHAR *dst); extern struct zfile *zuncompress (struct znode*, struct zfile *z, int dodefault, int mask, int *retcode, int index); extern void zfile_seterror (const TCHAR *format, ...); -extern TCHAR *zfile_geterror (void); +//extern TCHAR *zfile_geterror (void); extern int zfile_truncate (struct zfile *z, uae_s64 size); #define ZFD_NONE 0 @@ -111,22 +116,22 @@ extern int zfile_truncate (struct zfile *z, uae_s64 size); #define ZFILE_CDIMAGE 9 extern const TCHAR *uae_archive_extensions[]; -extern const TCHAR *uae_ignoreextensions[]; -extern const TCHAR *uae_diskimageextensions[]; +//extern const TCHAR *uae_ignoreextensions[]; +//extern const TCHAR *uae_diskimageextensions[]; extern struct zvolume *zfile_fopen_archive (const TCHAR *filename); -extern struct zvolume *zfile_fopen_archive (const TCHAR *filename, int flags); -extern struct zvolume *zfile_fopen_archive_root (const TCHAR *filename, int flags); +//extern struct zvolume *zfile_fopen_archive (const TCHAR *filename, int flags); +//extern struct zvolume *zfile_fopen_archive_root (const TCHAR *filename, int flags); extern void zfile_fclose_archive (struct zvolume *zv); extern int zfile_fs_usage_archive (const TCHAR *path, const TCHAR *disk, struct fs_usage *fsp); extern int zfile_stat_archive (const TCHAR *path, struct mystat *statbuf); extern struct zdirectory *zfile_opendir_archive (const TCHAR *path); -extern struct zdirectory *zfile_opendir_archive (const TCHAR *path, int flags); +//extern struct zdirectory *zfile_opendir_archive (const TCHAR *path, int flags); extern void zfile_closedir_archive (struct zdirectory *); extern int zfile_readdir_archive (struct zdirectory *, TCHAR*); -extern int zfile_readdir_archive (struct zdirectory *, TCHAR*, bool fullpath); -extern struct zfile *zfile_readdir_archive_open (struct zdirectory *zd, const TCHAR *mode); -extern void zfile_resetdir_archive (struct zdirectory *); +//extern int zfile_readdir_archive (struct zdirectory *, TCHAR*, bool fullpath); +//extern struct zfile *zfile_readdir_archive_open (struct zdirectory *zd, const TCHAR *mode); +//extern void zfile_resetdir_archive (struct zdirectory *); extern int zfile_fill_file_attrs_archive (const TCHAR *path, int *isdir, int *flags, TCHAR **comment); extern uae_s64 zfile_lseek_archive (struct zfile *d, uae_s64 offset, int whence); extern uae_s64 zfile_fsize_archive (struct zfile *d); diff --git a/src/inputdevice.cpp b/src/inputdevice.cpp index a9c799a7..5605be7a 100644 --- a/src/inputdevice.cpp +++ b/src/inputdevice.cpp @@ -15,11 +15,8 @@ * - fully backward compatible with old joystick/mouse configuration * */ -#include -#include -#include -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" @@ -29,7 +26,7 @@ #include "custom.h" #include "xwin.h" #include "drawing.h" -#include "include/memory.h" +#include "memory.h" #include "newcpu.h" #include "uae.h" #include "picasso96.h" @@ -40,6 +37,8 @@ #include "sounddep/sound.h" #include "disk.h" #include "amiberry_gfx.h" +#include "statusline.h" +#include "cia.h" #define COMPA_RESERVED_FLAGS (ID_FLAG_INVERT) @@ -56,6 +55,8 @@ #define INPUTEVENT_JOY1_CD32_LAST INPUTEVENT_JOY1_CD32_BLUE #define INPUTEVENT_JOY2_CD32_LAST INPUTEVENT_JOY2_CD32_BLUE +#define JOYMOUSE_CDTV 8 + #define DEFEVENT(A, B, C, D, E, F) {_T(#A), B, NULL, C, D, E, F, 0 }, #define DEFEVENT2(A, B, B2, C, D, E, F, G) {_T(#A), B, B2, C, D, E, F, G }, static const struct inputevent events[] = { @@ -86,20 +87,35 @@ struct uae_input_device2 { int states[MAX_INPUT_DEVICE_EVENTS / 2][MAX_INPUT_SUB_EVENT + 1]; }; +#define INPUT_MATCH_CONFIG_NAME_ONLY 1 +#define INPUT_MATCH_FRIENDLY_NAME_ONLY 2 +#define INPUT_MATCH_BOTH 4 +#define INPUT_MATCH_ALL 7 + static struct uae_input_device2 joysticks2[MAX_INPUT_DEVICES]; static struct uae_input_device2 mice2[MAX_INPUT_DEVICES]; static uae_u8 scancodeused[MAX_INPUT_DEVICES][256]; static uae_u64 qualifiers, qualifiers_r; static uae_s16 *qualifiers_evt[MAX_INPUT_QUALIFIERS]; +// fire/left mouse button pullup resistors enabled? +static bool mouse_pullup = true; + static int joymodes[MAX_JPORTS]; static const int *joyinputs[MAX_JPORTS]; static int input_acquired; +static int bouncy; +static signed long bouncy_cycles; static int autopause; -static int handle_input_event (int nr, int state, int max, int autofire); +#define HANDLE_IE_FLAG_CANSTOPPLAYBACK 1 +#define HANDLE_IE_FLAG_PLAYBACKEVENT 2 +#define HANDLE_IE_FLAG_AUTOFIRE 4 +#define HANDLE_IE_FLAG_ABSOLUTE 8 + +static int handle_input_event (int nr, int state, int max, int flags); static struct inputdevice_functions idev[IDTYPE_MAX]; @@ -136,6 +152,20 @@ static int isdevice (struct uae_input_device *id) static void check_enable(int ei); +int inputdevice_geteventid(const TCHAR *s) +{ + for (int i = 1; events[i].name; i++) { + const struct inputevent *ie = &events[i]; + if (!_tcscmp(ie->confname, s)) + return i; + } + for (int i = 0; akss[i].name; i++) { + if (!_tcscmp(s, akss[i].name)) + return i + AKS_FIRST; + } + return 0; +} + int inputdevice_uaelib (const TCHAR *s, const TCHAR *parm) { if (!_tcsncmp(s, _T("KEY_RAW_"), 8)) { @@ -169,7 +199,7 @@ int inputdevice_uaelib (const TCHAR *s, const TCHAR *parm) parm = NULL; else v = 1; - inputdevice_add_inputcode(akss[i].aks, v, nullptr); + inputdevice_add_inputcode(akss[i].aks, v, parm); return 1; } } @@ -190,7 +220,7 @@ int inputdevice_uaelib(const TCHAR *s, int parm, int max, bool autofire) for (int i = 1; events[i].name; i++) { if (!_tcscmp(s, events[i].confname)) { check_enable(i); - handle_input_event(i, parm, max, autofire); + handle_input_event(i, parm, max, autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0); return 1; } } @@ -209,14 +239,16 @@ static int getdevnum(int type, int devnum) return jcnt + devnum; else if (type == IDTYPE_KEYBOARD) return jcnt + mcnt + devnum; + else if (type == IDTYPE_INTERNALEVENT) + return jcnt + mcnt + kcnt + devnum; return -1; } -static int gettype (int devnum) +static int gettype(int devnum) { - int jcnt = idev[IDTYPE_JOYSTICK].get_num (); - int mcnt = idev[IDTYPE_MOUSE].get_num (); - int kcnt = idev[IDTYPE_KEYBOARD].get_num (); + int jcnt = idev[IDTYPE_JOYSTICK].get_num(); + int mcnt = idev[IDTYPE_MOUSE].get_num(); + int kcnt = idev[IDTYPE_KEYBOARD].get_num(); if (devnum < jcnt) return IDTYPE_JOYSTICK; @@ -224,12 +256,14 @@ static int gettype (int devnum) return IDTYPE_MOUSE; else if (devnum < jcnt + mcnt + kcnt) return IDTYPE_KEYBOARD; + else if (devnum < jcnt + mcnt + kcnt + INTERNALEVENT_COUNT) + return IDTYPE_INTERNALEVENT; return -1; } -static struct inputdevice_functions *getidf (int devnum) +static struct inputdevice_functions *getidf(int devnum) { - int type = gettype (devnum); + int type = gettype(devnum); if (type < 0) return NULL; return &idev[type]; @@ -242,9 +276,36 @@ const struct inputevent *inputdevice_get_eventinfo(int evt) return &events[evt]; } +static uae_u64 inputdevice_flag_to_idev(uae_u64 flag) +{ + uae_u64 flags = 0; + if (flag & ID_FLAG_AUTOFIRE) + flags |= IDEV_MAPPED_AUTOFIRE_SET; + if (flag & ID_FLAG_TOGGLE) + flags |= IDEV_MAPPED_TOGGLE; + if (flag & ID_FLAG_INVERTTOGGLE) + flags |= IDEV_MAPPED_INVERTTOGGLE; + if (flag & ID_FLAG_INVERT) + flags |= IDEV_MAPPED_INVERT; + if (flag & ID_FLAG_GAMEPORTSCUSTOM1) + flags |= IDEV_MAPPED_GAMEPORTSCUSTOM1; + if (flag & ID_FLAG_GAMEPORTSCUSTOM2) + flags |= IDEV_MAPPED_GAMEPORTSCUSTOM2; + if (flag & ID_FLAG_QUALIFIER_MASK) + flags |= flag & ID_FLAG_QUALIFIER_MASK; + if (flag & ID_FLAG_SET_ONOFF) + flags |= IDEV_MAPPED_SET_ONOFF; + if (flag & ID_FLAG_SET_ONOFF_VAL1) + flags |= IDEV_MAPPED_SET_ONOFF_VAL1; + if (flag & ID_FLAG_SET_ONOFF_VAL2) + flags |= IDEV_MAPPED_SET_ONOFF_VAL2; + return flags; +} + static struct uae_input_device *joysticks; static struct uae_input_device *mice; static struct uae_input_device *keyboards; +static struct uae_input_device *internalevents; static struct uae_input_device_kbr_default *keyboard_default, **keyboard_default_table; static int default_keyboard_layout[MAX_JPORTS]; @@ -262,6 +323,8 @@ static int default_keyboard_layout[MAX_JPORTS]; #define KBR_DEFAULT_MAP_CD32_NP 6 #define KBR_DEFAULT_MAP_CD32_CK 7 #define KBR_DEFAULT_MAP_CD32_SE 8 +#define KBR_DEFAULT_MAP_ARCADIA 9 +#define KBR_DEFAULT_MAP_CDTV 10 static int **keyboard_default_kbmaps; static int mouse_axis[MAX_INPUT_DEVICES][MAX_INPUT_DEVICE_EVENTS]; @@ -272,34 +335,31 @@ static int oldm_axis[MAX_INPUT_DEVICES][MAX_INPUT_DEVICE_EVENTS]; static uae_s16 mouse_x[MAX_JPORTS], mouse_y[MAX_JPORTS]; static uae_s16 mouse_delta[MAX_JPORTS][MOUSE_AXIS_TOTAL]; static uae_s16 mouse_deltanoreset[MAX_JPORTS][MOUSE_AXIS_TOTAL]; +static uae_s16 lightpen_delta[2][2]; +static uae_s16 lightpen_deltanoreset[2][2]; +static int lightpen_trigger2; static int joybutton[MAX_JPORTS]; static int joydir[MAX_JPORTS]; -#ifndef INPUTDEVICE_SIMPLE static int joydirpot[MAX_JPORTS][2]; -#endif static uae_s16 mouse_frame_x[MAX_JPORTS], mouse_frame_y[MAX_JPORTS]; static int mouse_port[NORMAL_JPORTS]; static int cd32_shifter[NORMAL_JPORTS]; static int cd32_pad_enabled[NORMAL_JPORTS]; - -#if !defined(INPUTDEVICE_SIMPLE) || defined(AMIBERRY) static int parport_joystick_enabled; -#endif - static int oleft[MAX_JPORTS], oright[MAX_JPORTS], otop[MAX_JPORTS], obot[MAX_JPORTS]; +static int horizclear[MAX_JPORTS], vertclear[MAX_JPORTS]; static int relativecount[MAX_JPORTS][2]; uae_u16 potgo_value; -#ifndef INPUTDEVICE_SIMPLE static int pot_cap[NORMAL_JPORTS][2]; -#endif static uae_u8 pot_dat[NORMAL_JPORTS][2]; static int pot_dat_act[NORMAL_JPORTS][2]; -#ifndef INPUTDEVICE_SIMPLE static int analog_port[NORMAL_JPORTS][2]; -#endif static int digital_port[NORMAL_JPORTS][2]; +static int lightpen_port[NORMAL_JPORTS]; +int cubo_enabled; +uae_u32 cubo_flag; #define POTDAT_DELAY_PAL 8 #define POTDAT_DELAY_NTSC 7 @@ -307,13 +367,10 @@ static int use_joysticks[MAX_INPUT_DEVICES]; static int use_mice[MAX_INPUT_DEVICES]; static int use_keyboards[MAX_INPUT_DEVICES]; -#ifdef INPUTDEVICE_SIMPLE -#define INPUT_QUEUE_SIZE 6 -#else #define INPUT_QUEUE_SIZE 16 -#endif struct input_queue_struct { int evt, storedstate, state, max, linecnt, nextlinecnt; + TCHAR *custom; }; static struct input_queue_struct input_queue[INPUT_QUEUE_SIZE]; @@ -322,11 +379,7 @@ uae_u8 *restore_input (uae_u8 *src) restore_u32 (); for (int i = 0; i < 2; i++) { for (int j = 0; j < 2; j++) { -#ifndef INPUTDEVICE_SIMPLE pot_cap[i][j] = restore_u16 (); -#else - restore_u16(); -#endif } } return src; @@ -342,11 +395,7 @@ uae_u8 *save_input (int *len, uae_u8 *dstptr) save_u32 (0); for (int i = 0; i < 2; i++) { for (int j = 0; j < 2; j++) { -#ifndef INPUTDEVICE_SIMPLE save_u16 (pot_cap[i][j]); -#else - save_u16(0); -#endif } } *len = dst - dstbak; @@ -369,11 +418,13 @@ static void copyjport (const struct uae_prefs *src, struct uae_prefs *dst, int n dst->jports[num].id = src->jports[num].id; dst->jports[num].mode = src->jports[num].mode; dst->jports[num].autofire = src->jports[num].autofire; - dst->jports[num].mousemap = src->jports[num].mousemap; - dst->jports[num].amiberry_custom_none = src->jports[num].amiberry_custom_none; - dst->jports[num].amiberry_custom_hotkey = src->jports[num].amiberry_custom_hotkey; - dst->jports[num].amiberry_custom_left_trigger = src->jports[num].amiberry_custom_left_trigger; - dst->jports[num].amiberry_custom_right_trigger = src->jports[num].amiberry_custom_right_trigger; +#ifdef AMIBERRY + dst->jports[num].mousemap = src->jports[num].mousemap; + dst->jports[num].amiberry_custom_none = src->jports[num].amiberry_custom_none; + dst->jports[num].amiberry_custom_hotkey = src->jports[num].amiberry_custom_hotkey; + dst->jports[num].amiberry_custom_left_trigger = src->jports[num].amiberry_custom_left_trigger; + dst->jports[num].amiberry_custom_right_trigger = src->jports[num].amiberry_custom_right_trigger; +#endif dst->jports[num].nokeyboardoverride = src->jports[num].nokeyboardoverride; } @@ -385,11 +436,11 @@ struct stored_jport bool defaultports; uae_u32 age; }; -static struct stored_jport stored_jports[MAX_JPORTS][8]; +static struct stored_jport stored_jports[MAX_JPORTS][MAX_STORED_JPORTS]; static uae_u32 stored_jport_cnt; // return port where idc was previously plugged if any and forgot it. -static int inputdevice_get_unplugged_device(struct inputdevconfig *idc) +static int inputdevice_get_unplugged_device(struct inputdevconfig *idc, struct stored_jport **sjp) { for (int portnum = 0; portnum < MAX_JPORTS; portnum++) { for (int i = 0; i < MAX_STORED_JPORTS; i++) { @@ -397,6 +448,7 @@ static int inputdevice_get_unplugged_device(struct inputdevconfig *idc) if (jp->inuse && jp->jp.id == JPORT_UNPLUGGED) { if (!_tcscmp(idc->name, jp->jp.idc.name) && !_tcscmp(idc->configname, jp->jp.idc.configname)) { jp->inuse = false; + *sjp = jp; return portnum; } } @@ -526,7 +578,7 @@ static void inputdevice_store_used_device(struct jport *jps, int portnum, bool d static void inputdevice_store_unplugged_port(struct uae_prefs *p, struct inputdevconfig *idc) { - struct jport jpt = { }; + struct jport jpt = { 0 }; _tcscpy(jpt.idc.configname, idc->configname); _tcscpy(jpt.idc.name, idc->name); jpt.id = JPORT_UNPLUGGED; @@ -534,6 +586,8 @@ static void inputdevice_store_unplugged_port(struct uae_prefs *p, struct inputde struct jport *jp = &p->jports[i]; if (!_tcscmp(jp->idc.name, idc->name) && !_tcscmp(jp->idc.configname, idc->configname)) { write_log(_T("On the fly unplugged stored, port %d '%s' (%s)\n"), i, jpt.idc.name, jpt.idc.configname); + jpt.mode = jp->mode; + jpt.autofire = jp->autofire; inputdevice_store_used_device(&jpt, i, false); } } @@ -601,7 +655,7 @@ static bool write_config_head (struct zfile *f, int idnum, int devnum, const TCH cfgfile_write_bool (f, tmp2, true); if (id->enabled) { _stprintf (tmp2, _T("input.%d.%s.%d.disabled"), idnum + 1, name, devnum); - cfgfile_write_bool (f, tmp2, id->enabled == 0); + cfgfile_write_bool (f, tmp2, id->enabled ? false : true); } return false; } @@ -613,7 +667,7 @@ static bool write_config_head (struct zfile *f, int idnum, int devnum, const TCH _stprintf (tmp2, _T("input.%d.%s.%d.empty"), idnum + 1, name, devnum); cfgfile_write_bool (f, tmp2, false); _stprintf (tmp2, _T("input.%d.%s.%d.disabled"), idnum + 1, name, devnum); - cfgfile_write_bool (f, tmp2, id->enabled == 0); + cfgfile_write_bool (f, tmp2, id->enabled ? false : true); } return true; } @@ -638,12 +692,12 @@ static bool write_slot (TCHAR *p, struct uae_input_device *uid, int i, int j) if (ok && (flags & ID_FLAG_SAVE_MASK_QUALIFIERS)) { TCHAR *p2 = p + _tcslen (p); *p2++ = '.'; - for (int i = 0; i < MAX_INPUT_QUALIFIERS * 2; i++) { - if ((ID_FLAG_QUALIFIER1 << i) & flags) { - if (i & 1) - _stprintf (p2, _T("%c"), 'a' + i / 2); + for (int k = 0; k < MAX_INPUT_QUALIFIERS * 2; k++) { + if ((ID_FLAG_QUALIFIER1 << k) & flags) { + if (k & 1) + _stprintf (p2, _T("%c"), 'a' + k / 2); else - _stprintf (p2, _T("%c"), 'A' + i / 2); + _stprintf (p2, _T("%c"), 'A' + k / 2); p2++; } } @@ -651,6 +705,8 @@ static bool write_slot (TCHAR *p, struct uae_input_device *uid, int i, int j) return ok; } +static struct inputdevice_functions *getidf (int devnum); + static void kbrlabel (TCHAR *s) { while (*s) { @@ -851,7 +907,7 @@ void write_inputdevice_config (struct uae_prefs *p, struct zfile *f) int i, id; // cfgfile_write (f, _T("input.config"), _T("%d"), p->input_selected_setting == GAMEPORT_INPUT_SETTINGS ? 0 : p->input_selected_setting + 1); - cfgfile_write (f, _T("input.joymouse_speed_analog"), _T("%d"), p->input_joymouse_multiplier); + cfgfile_write (f, _T("input.joymouse_speed_analog"), _T("%d"), p->input_joymouse_multiplier); cfgfile_write (f, _T("input.joymouse_speed_digital"), _T("%d"), p->input_joymouse_speed); cfgfile_write (f, _T("input.joymouse_deadzone"), _T("%d"), p->input_joymouse_deadzone); cfgfile_write (f, _T("input.joystick_deadzone"), _T("%d"), p->input_joystick_deadzone); @@ -859,10 +915,11 @@ void write_inputdevice_config (struct uae_prefs *p, struct zfile *f) cfgfile_write (f, _T("input.analog_joystick_offset"), _T("%d"), p->input_analog_joystick_offset); cfgfile_write (f, _T("input.mouse_speed"), _T("%d"), p->input_mouse_speed); cfgfile_write (f, _T("input.autofire_speed"), _T("%d"), p->input_autofire_linecnt); + cfgfile_write (f, _T("input.autoswitch"), _T("%d"), p->input_autoswitch); cfgfile_dwrite_str (f, _T("input.keyboard_type"), kbtypes[p->input_keyboard_type]); - // not required config saving - // +// not required config saving +// // for (id = 0; id < MAX_INPUT_SETTINGS; id++) { // TCHAR tmp[MAX_DPATH]; // if (id < GAMEPORT_INPUT_SETTINGS) { @@ -926,15 +983,15 @@ static int getnum (const TCHAR **pp) } static TCHAR *getstring (const TCHAR **pp) { - int i; + int i; static TCHAR str[CONFIG_BLEN]; - const TCHAR *p = *pp; + const TCHAR *p = *pp; bool quoteds = false; bool quotedd = false; - if (*p == 0) - return 0; - i = 0; + if (*p == 0) + return 0; + i = 0; while (*p != 0 && i < 1000 - 1) { if (*p == '\"') quotedd = quotedd ? false : true; @@ -944,13 +1001,13 @@ static TCHAR *getstring (const TCHAR **pp) if (*p == '.' || *p == ',') break; } - str[i++] = *p++; + str[i++] = *p++; } - if (*p == '.' || *p == ',') - p++; - str[i] = 0; - *pp = p; - return str; + if (*p == '.' || *p == ',') + p++; + str[i] = 0; + *pp = p; + return str; } static void reset_inputdevice_settings (struct uae_input_device *uid) @@ -960,11 +1017,11 @@ static void reset_inputdevice_settings (struct uae_input_device *uid) uid->eventid[l][i] = 0; uid->flags[l][i] = 0; if (uid->custom[l][i]) { - xfree (uid->custom[l][i]); - uid->custom[l][i] = NULL; - } - } - } + xfree (uid->custom[l][i]); + uid->custom[l][i] = NULL; + } + } + } } static void reset_inputdevice_slot (struct uae_prefs *prefs, int slot) { @@ -996,7 +1053,7 @@ static void reset_inputdevice_config_temp(void) void reset_inputdevice_config (struct uae_prefs *prefs, bool reset) { - for (int i = 0; i< MAX_INPUT_SETTINGS; i++) + for (int i = 0; i < MAX_INPUT_SETTINGS; i++) reset_inputdevice_slot (prefs, i); reset_inputdevice_config_temp(); @@ -1074,7 +1131,7 @@ static void set_kbr_default (struct uae_prefs *p, int index, int devnum, struct id->get_widget_type (j, i, 0, &scancode); kbr->extra[i] = scancode; if (j == 0 || kbr->enabled) - set_kbr_default_event (kbr, trans, i); + set_kbr_default_event (kbr, trans, i); } } } @@ -1112,28 +1169,31 @@ static const int af_port4[] = { }; static const int *af_ports[] = { af_port1, af_port2, af_port3, af_port4 }; -static void setautofireevent (struct uae_input_device *uid, int num, int sub, int af, int index) +static void setautofireevent(struct uae_input_device *uid, int num, int sub, int af, int index) { if (!af) return; +#ifdef RETROPLATFORM + // don't override custom AF autofire mappings + if (rp_isactive()) + return; +#endif const int *afp = af_ports[index]; for (int k = 0; afp[k] >= 0; k++) { if (afp[k] == uid->eventid[num][sub]) { uid->flags[num][sub] &= ~ID_FLAG_AUTOFIRE_MASK; if (af >= JPORT_AF_NORMAL) uid->flags[num][sub] |= ID_FLAG_AUTOFIRE; -#ifndef INPUTDEVICE_SIMPLE if (af == JPORT_AF_TOGGLE) uid->flags[num][sub] |= ID_FLAG_TOGGLE; if (af == JPORT_AF_ALWAYS) uid->flags[num][sub] |= ID_FLAG_INVERTTOGGLE; -#endif return; } } } -static void setcompakbevent(struct uae_prefs *p, struct uae_input_device *uid, int l, int evt, int port, int af) +static void setcompakbevent(struct uae_prefs *p, struct uae_input_device *uid, int l, int evt, int port, int af, uae_u64 flags) { inputdevice_sparecopy(uid, l, 0); if (p->jports[port].nokeyboardoverride && uid->port[l][0] == 0) { @@ -1144,13 +1204,16 @@ static void setcompakbevent(struct uae_prefs *p, struct uae_input_device *uid, i } uid->eventid[l][0] = evt; uid->flags[l][0] &= COMPA_RESERVED_FLAGS; + uid->flags[l][0] |= flags; uid->port[l][0] = port + 1; xfree(uid->custom[l][0]); uid->custom[l][0] = NULL; - setautofireevent(uid, l, 0, af, port); + if (!JSEM_ISCUSTOM(port, p)) { + setautofireevent(uid, l, 0, af, port); + } } -static int matchdevice(struct inputdevice_functions *inf, const TCHAR *configname, const TCHAR *name) +static int matchdevice(struct uae_prefs *p, struct inputdevice_functions *inf, const TCHAR *configname, const TCHAR *name) { int match = -1; for (int j = 0; j < 2; j++) { @@ -1158,8 +1221,15 @@ static int matchdevice(struct inputdevice_functions *inf, const TCHAR *confignam for (int i = 0; i < inf->get_num(); i++) { const TCHAR* aname1 = inf->get_friendlyname(i); const TCHAR* aname2 = inf->get_uniquename(i); - if (fullmatch && (!aname1 || !name)) - continue; + if (fullmatch) { + if (!aname1 || !name) + continue; + if (!(p->input_device_match_mask & INPUT_MATCH_BOTH)) + continue; + } else { + if (!(p->input_device_match_mask & INPUT_MATCH_CONFIG_NAME_ONLY)) + continue; + } if (aname2 && configname) { bool matched = false; TCHAR bname[MAX_DPATH]; @@ -1209,8 +1279,15 @@ static int matchdevice(struct inputdevice_functions *inf, const TCHAR *confignam if (aname2 && configname) { const TCHAR *bname2 = configname; bool matched = false; - if (fullmatch && (!aname1 || !name)) - continue; + if (fullmatch) { + if (!aname1 || !name) + continue; + if (!(p->input_device_match_mask & INPUT_MATCH_BOTH)) + continue; + } else { + if (!(p->input_device_match_mask & INPUT_MATCH_CONFIG_NAME_ONLY)) + continue; + } if (aname2 && bname2 && !_tcscmp(aname2, bname2)) matched = true; if (matched && fullmatch && _tcscmp(aname1, name) != 0) @@ -1233,6 +1310,8 @@ static int matchdevice(struct inputdevice_functions *inf, const TCHAR *confignam // no match, try friendly names for (int i = 0; i < inf->get_num(); i++) { const TCHAR* aname1 = inf->get_friendlyname(i); + if (!(p->input_device_match_mask & INPUT_MATCH_FRIENDLY_NAME_ONLY)) + continue; if (aname1 && name) { const TCHAR *bname1 = name; if (aname1 && bname1 && !_tcscmp(aname1, bname1)) { @@ -1334,7 +1413,7 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * struct uae_input_device *id = NULL; const struct inputevent *ie; int devnum, num, button, joystick, subnum, idnum, keynum, devtype; - const TCHAR *p; + const TCHAR *p; TCHAR *p2, *custom; struct temp_uids *tid = &temp_uid; struct inputdevice_functions *idf = NULL; @@ -1366,11 +1445,19 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * pr->input_analog_joystick_mult = _tstol (value); if (!_tcsicmp (p, _T("analog_joystick_offset"))) pr->input_analog_joystick_offset = _tstol (value); + if (!_tcsicmp (p, _T("autoswitch"))) + pr->input_autoswitch = _tstol (value); if (!_tcsicmp (p, _T("keyboard_type"))) { - cfgfile_strval (option, value, nullptr, &pr->input_keyboard_type, kbtypes, 0); + cfgfile_strval (p, value, p, &pr->input_keyboard_type, kbtypes, 0); keyboard_default = keyboard_default_table[pr->input_keyboard_type]; inputdevice_default_kb_all (pr); } + if (!strcasecmp(p, _T("devicematchflags"))) { + pr->input_device_match_mask = _tstol(value); + write_log(_T("input_device_match_mask = %d\n"), pr->input_device_match_mask); + } + if (!strcasecmp (p, _T("contact_bounce"))) + pr->input_contact_bounce = _tstol (value); idnum = _tstol (p); if (idnum <= 0 || idnum > MAX_INPUT_SETTINGS) @@ -1394,6 +1481,8 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * p = option + 9; } else if (_tcsncmp (option, _T("keyboard."), 9) == 0) { p = option + 9; + } else if (_tcsncmp (option, _T("internal."), 9) == 0) { + p = option + 9; } else return; @@ -1417,6 +1506,12 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * id = &pr->keyboard_settings[idnum][devnum]; joystick = -1; devtype = IDTYPE_KEYBOARD; + } else if (_tcsncmp (option, _T("internal."), 9) == 0) { + if (devnum >= INTERNALEVENT_COUNT) + return; + id = &pr->internalevent_settings[idnum][devnum]; + joystick = 2; + devtype = IDTYPE_INTERNALEVENT; } if (!id) return; @@ -1485,7 +1580,7 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * tid->disabled = false; tid->empty = false; } else { - newdevnum = matchdevice(idf, tid->configname, tid->name); + newdevnum = matchdevice(pr, idf, tid->configname, tid->name); } } else { // match devices with empty names to first free slot @@ -1497,9 +1592,9 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * } } } else { - newdevnum = matchdevice(idf, tid->configname, tid->name); - } - } + newdevnum = matchdevice(pr, idf, tid->configname, tid->name); + } + } newdev = true; if (newdevnum >= 0) { temp_uid_index[devnum][tid->devtype] = newdevnum; @@ -1519,7 +1614,6 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * } } } - devnum = temp_uid_index[devnum][tid->devtype]; if (devnum < 0) { if (devnum == -1) @@ -1534,6 +1628,10 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * id = &pr->joystick_settings[idnum][devnum]; } else if (tid->devtype == IDTYPE_KEYBOARD) { id = &pr->keyboard_settings[idnum][devnum]; + } else if (tid->devtype == IDTYPE_INTERNALEVENT) { + if (devnum >= INTERNALEVENT_COUNT) + return; + id = &pr->internalevent_settings[idnum][devnum]; } else { return; } @@ -1584,8 +1682,6 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * } p = value; - bool oldcustommapping = false; - custom = NULL; for (subnum = 0; subnum < MAX_INPUT_SUB_EVENT; subnum++) { uae_u64 flags; int port; @@ -1605,8 +1701,6 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * if (p[-1] == '.') port = getnum (&p) + 1; } - if (flags & ID_FLAG_RESERVEDGAMEPORTSCUSTOM) - oldcustommapping = true; if (idnum == GAMEPORT_INPUT_SETTINGS && port == 0) continue; if (p[-1] == '.' && idnum != GAMEPORT_INPUT_SETTINGS) { @@ -1632,19 +1726,334 @@ void read_inputdevice_config (struct uae_prefs *pr, const TCHAR *option, TCHAR * continue; custom = NULL; } - if (joystick < 0 && !oldcustommapping) + if (joystick < 0) tid->kbreventcnt[devnum]++; xfree (custom); } -static int mousehack_alive_cnt; +static void generate_jport_custom_item(struct uae_input_device *uid, int num, int port, int devtype, TCHAR *out) +{ + struct uae_input_device *uid2 = &uid[num]; + for (int i = 0; i < MAX_INPUT_DEVICE_EVENTS; i++) { + for (int j = 0; j < MAX_INPUT_SUB_EVENT; j++) { + int evt = uid2->eventid[i][j]; + uae_u64 flags = uid2->flags[i][j]; + if (flags & ID_FLAG_GAMEPORTSCUSTOM_MASK) { + if (uid2->port[i][j] == port + 1 && evt > 0) { + const struct inputevent *ie = &events[evt]; + TCHAR *p = out + _tcslen(out); + if (out[0]) + *p++= ' '; + if (devtype == IDTYPE_KEYBOARD) { + _stprintf(p, _T("k.%d.b.%d"), num, uid2->extra[i]); + } else if (devtype == IDTYPE_JOYSTICK || devtype == IDTYPE_MOUSE) { + TCHAR type = devtype == IDTYPE_JOYSTICK ? 'j' : 'm'; + if (i >= ID_BUTTON_OFFSET && i < ID_BUTTON_OFFSET + ID_BUTTON_TOTAL) { + _stprintf(p, _T("%c.%d.b.%d"), type, num, i - ID_BUTTON_OFFSET); + } else if (i >= ID_AXIS_OFFSET && i < ID_AXIS_OFFSET + ID_AXIS_TOTAL) { + _stprintf(p, _T("%c.%d.a.%d"), type, num, i - ID_AXIS_OFFSET); +} +} + TCHAR *p3 = p + _tcslen(p); + _stprintf(p3, _T(".%d"), (int)(flags & (ID_FLAG_AUTOFIRE | ID_FLAG_TOGGLE | ID_FLAG_INVERTTOGGLE | ID_FLAG_INVERT))); + if (flags & ID_FLAG_SAVE_MASK_QUALIFIERS) { + TCHAR *p2 = p + _tcslen(p); + *p2++ = '.'; + for (int k = 0; k < MAX_INPUT_QUALIFIERS * 2; k++) { + if ((ID_FLAG_QUALIFIER1 << k) & flags) { + if (k & 1) + _stprintf(p2, _T("%c"), 'a' + k / 2); + else + _stprintf(p2, _T("%c"), 'A' + k / 2); + p2++; + } +} + } + _tcscat(p, _T("=")); + _tcscat(p, ie->confname); +} + } +} + } +} + +void inputdevice_generate_jport_custom(struct uae_prefs *pr, int port) +{ + if (!JSEM_ISCUSTOM(port, pr)) + return; + struct jport_custom *jpc = &pr->jports_custom[JSEM_GETCUSTOMIDX(port, pr)]; + jpc->custom[0] = 0; + for (int l = 0; l < MAX_INPUT_DEVICES; l++) { + generate_jport_custom_item(pr->joystick_settings[pr->input_selected_setting], l, port, IDTYPE_JOYSTICK, jpc->custom); + generate_jport_custom_item(pr->mouse_settings[pr->input_selected_setting], l, port, IDTYPE_MOUSE, jpc->custom); + generate_jport_custom_item(pr->keyboard_settings[pr->input_selected_setting], l, port, IDTYPE_KEYBOARD, jpc->custom); + } + } + +static int custom_autoswitch_joy[MAX_JPORTS_CUSTOM]; +static int custom_autoswitch_mouse[MAX_JPORTS_CUSTOM]; + +void inputdevice_parse_jport_custom(struct uae_prefs *pr, int index, int port, TCHAR *outname) +{ + const TCHAR *eventstr = pr->jports_custom[index].custom; + TCHAR data[CONFIG_BLEN]; + TCHAR *bufp, devtype, dt; + int cnt = 0, devindex, devnum, evt, pid, num, keynum, flags; + const inputevent* ie; + const struct inputdevice_functions* idf; + + custom_autoswitch_joy[index] = -1; + + if (eventstr == NULL || eventstr[0] == 0) + return; + if (outname) + outname[0] = 0; + + write_log(_T("parse_custom port %d, '%s'\n"), port, eventstr ? eventstr : _T("")); + + _tcscpy(data, eventstr); + _tcscat(data, _T(" ")); + bufp = data; + for (;;) { + TCHAR *next = bufp; + while (next != NULL && *next != ' ' && *next != 0) + next++; + if (!next || *next == 0) + break; + *next++ = 0; + const TCHAR *bufp2 = bufp; + struct uae_input_device *id = 0; + int joystick = 0; + TCHAR *p = getstring(&bufp2); + if (!p) + goto skip; + + devindex = getnum(&bufp2); + if (*bufp == 0) + goto skip; + if (devindex < 0 || devindex >= MAX_INPUT_DEVICES) + goto skip; + + devtype = _totupper(*p); + + devnum = 0; + if (devtype == 'M') { + id = &pr->mouse_settings[pr->input_selected_setting][devindex]; + joystick = 0; + devnum = getdevnum(IDTYPE_MOUSE, devindex); + if (gettype(devnum) != IDTYPE_MOUSE) + goto skip; + } else if (devtype == 'J') { + id = &pr->joystick_settings[pr->input_selected_setting][devindex]; + joystick = 1; + devnum = getdevnum(IDTYPE_JOYSTICK, devindex); + if (gettype(devnum) != IDTYPE_JOYSTICK) + goto skip; + } else if (devtype == 'K') { + // always use keyboard 0 + devindex = 0; + id = &pr->keyboard_settings[pr->input_selected_setting][devindex]; + joystick = -1; + devnum = getdevnum(IDTYPE_KEYBOARD, devindex); + if (gettype(devnum) != IDTYPE_KEYBOARD) { + write_log(_T("parse_custom keyboard missing!?\n")); + goto skip; + } + } + if (!id) + goto skip; + + p = getstring(&bufp2); + if (!p) + goto skip; + + num = -1; + keynum = 0; + if (joystick < 0) { + num = getnum(&bufp2); + if (*bufp == 0) + goto skip; + for (keynum = 0; keynum < MAX_INPUT_DEVICE_EVENTS; keynum++) { + if (id->extra[keynum] == num) + break; + } + if (keynum >= MAX_INPUT_DEVICE_EVENTS) { + write_log(_T("parse_custom keyboard missing key %02x!\n"), num); + goto skip; + } + num = keynum; + } else { + dt = _totupper(*p); + idf = getidf(devnum); + num = getnum(&bufp2); + if (dt == 'A') { + num += idf->get_widget_first(devnum, IDEV_WIDGET_AXIS); + } else if (dt == 'B') { + num += idf->get_widget_first(devnum, IDEV_WIDGET_BUTTON); + } else { + goto skip; + } + } + + flags = 0; + if (*bufp2 != '=') { + flags = getnum(&bufp2); + } + + while (*bufp2 != '=' && *bufp2 != 0) + bufp2++; + if (*bufp2 == 0) + goto skip; + bufp2++; + + p = getstring(&bufp2); + if (!p) + goto skip; + + ie = readevent(p, NULL); + if (ie) { + // Different port? Find matching request port event. + if (port >= 0 && ie->unit > 0 && ie->unit != port + 1) { + pid = ie->portid; + if (!pid) + goto skip; + for (int i = 1; events[i].name; i++) { + auto ie2 = &events[i]; + if (ie2->portid == pid && ie2->unit == port + 1) { + ie = ie2; + break; + } + } + if (ie->unit != port + 1) + goto skip; + } + if (outname == NULL) { + evt = ie - &events[0]; + if (joystick < 0) { + if (port >= 0) { + // all active keyboards + for (int i = 0; i < MAX_INPUT_DEVICES; i++) { + id = &pr->keyboard_settings[pr->input_selected_setting][i]; + if (i == 0 || id->enabled) { + setcompakbevent(pr, id, num, evt, port, 0, ID_FLAG_GAMEPORTSCUSTOM_MASK | flags); + } + } + } + } else { + if (port >= 0) { + auto iflags = IDEV_MAPPED_GAMEPORTSCUSTOM1 | IDEV_MAPPED_GAMEPORTSCUSTOM2 | inputdevice_flag_to_idev(flags); + inputdevice_set_gameports_mapping(pr, devnum, num, evt, iflags, port, pr->input_selected_setting); + } + if (evt == INPUTEVENT_JOY1_FIRE_BUTTON || evt == INPUTEVENT_JOY2_FIRE_BUTTON) { + if (joystick > 0) + custom_autoswitch_joy[index] = devindex; + else + custom_autoswitch_mouse[index] = devindex; + } + } + } else { + TCHAR tmp[MAX_DPATH]; + if (outname[0] != 0) + _tcscat(outname, _T(", ")); + auto ps = ie->shortname ? ie->shortname : ie->name; + if (inputdevice_get_widget_type(devnum, num, tmp, false)) { + if (tmp[0]) { + _tcscat(outname, tmp); + _tcscat(outname, _T("=")); + } + } + _tcscat(outname, ps); + if (flags & ID_FLAG_AUTOFIRE) + _tcscat(outname, _T(" AF")); + } + } else { + write_log(_T("parse_custom missing event %s\n"), p); + } +skip: + bufp = next; + } +} + +static int mouseedge_alive, mousehack_alive_cnt; static int lastmx, lastmy; -static int mouseoffset_x, mouseoffset_y; +static int lastmxy_abs[2][2]; +static uaecptr magicmouse_ibase, magicmouse_gfxbase; +static int dimensioninfo_width, dimensioninfo_height, dimensioninfo_dbl; +static int vp_xoffset, vp_yoffset, mouseoffset_x, mouseoffset_y; +static int tablet_maxx, tablet_maxy, tablet_maxz; +static int tablet_resx, tablet_resy; +static int tablet_maxax, tablet_maxay, tablet_maxaz; static int tablet_data; -STATIC_INLINE int mousehack_alive (void) +int mousehack_alive (void) { - return mousehack_alive_cnt > 0 ? mousehack_alive_cnt : 0; + return mousehack_alive_cnt > 0 ? mousehack_alive_cnt : 0; +} + +static uaecptr get_base (const uae_char *name) +{ + //if (trap_is_indirect()) + // return 0; + + uaecptr v = get_long (4); + addrbank *b = &get_mem_bank(v); + + if (!b || !b->check (v, 400) || !(b->flags & ABFLAG_RAM)) + return 0; + v += 378; // liblist + while ((v = get_long (v))) { + uae_u32 v2; + uae_u8 *p; + b = &get_mem_bank (v); + if (!b || !b->check (v, 32) || !(b->flags & ABFLAG_RAM)) + goto fail; + v2 = get_long (v + 10); // name + b = &get_mem_bank (v2); + if (!b || !b->check (v2, 20)) + goto fail; + if (!(b->flags & ABFLAG_ROM) && !(b->flags & ABFLAG_RAM)) + return 0; + p = b->xlateaddr (v2); + if (!memcmp (p, name, strlen (name) + 1)) { + TCHAR *s = au (name); + write_log (_T("get_base('%s')=%08x\n"), s, v); + xfree (s); + return v; + } + } + return 0; +fail: + { + TCHAR *s = au (name); + write_log (_T("get_base('%s') failed, invalid library list\n"), s); + xfree (s); + } + return 0xffffffff; +} + +static uaecptr get_intuitionbase (void) +{ + if (magicmouse_ibase == 0xffffffff) + return 0; + if (magicmouse_ibase) + return magicmouse_ibase; + if (rtarea_bank.baseaddr) + magicmouse_ibase = get_long_host(rtarea_bank.baseaddr + RTAREA_INTBASE); + if (!magicmouse_ibase) + magicmouse_ibase = get_base("intuition.library"); + return magicmouse_ibase; +} +static uaecptr get_gfxbase (void) +{ + if (magicmouse_gfxbase == 0xffffffff) + return 0; + if (magicmouse_gfxbase) + return magicmouse_gfxbase; + if (rtarea_bank.baseaddr) + magicmouse_gfxbase = get_long_host(rtarea_bank.baseaddr + RTAREA_GFXBASE); + if (!magicmouse_gfxbase) + magicmouse_gfxbase = get_base("graphics.library"); + return magicmouse_gfxbase; } #define MH_E 0 @@ -1674,13 +2083,13 @@ STATIC_INLINE int mousehack_alive (void) int inputdevice_is_tablet (void) { - if (uae_boot_rom_type <= 0) - return 0; - if (currprefs.input_tablet == TABLET_OFF) - return 0; - if (currprefs.input_tablet == TABLET_MOUSEHACK) - return -1; - return 0; + if (uae_boot_rom_type <= 0) + return 0; + if (currprefs.input_tablet == TABLET_OFF) + return 0; + if (currprefs.input_tablet == TABLET_MOUSEHACK) + return -1; + return 0; } static uae_u8 *mousehack_address; @@ -1688,9 +2097,12 @@ static bool mousehack_enabled; static void mousehack_reset (void) { - mouseoffset_x = mouseoffset_y = 0; - mousehack_alive_cnt = 0; - tablet_data = 0; + dimensioninfo_width = dimensioninfo_height = 0; + mouseoffset_x = mouseoffset_y = 0; + dimensioninfo_dbl = 0; + mousehack_alive_cnt = 0; + vp_xoffset = vp_yoffset = 0; + tablet_data = 0; if (rtarea_bank.baseaddr) { put_long_host(rtarea_bank.baseaddr + RTAREA_INTXY, 0xffffffff); if (mousehack_address) @@ -1702,27 +2114,98 @@ static void mousehack_reset (void) static bool mousehack_enable (void) { - int mode; + int mode; if (uae_boot_rom_type <= 0 || currprefs.input_tablet == TABLET_OFF) - return false; + return false; if (mousehack_address && mousehack_enabled) - return true; - mode = 0x80; - if (currprefs.input_tablet == TABLET_MOUSEHACK) - mode |= 1; + return true; + mode = 0x80; + if (currprefs.input_tablet == TABLET_MOUSEHACK) + mode |= 1; + if (inputdevice_is_tablet () > 0) + mode |= 2; if (mousehack_address && rtarea_bank.baseaddr) { - write_log (_T("Mouse driver enabled (%s)\n"), _T("mousehack")); + write_log (_T("Mouse driver enabled (%s)\n"), ((mode & 3) == 3 ? _T("tablet+mousehack") : ((mode & 3) == 2) ? _T("tablet") : _T("mousehack"))); put_byte_host(mousehack_address + MH_E, mode); mousehack_enabled = true; } return true; } -void input_mousehack_mouseoffset (uaecptr pointerprefs) +static void inputdevice_update_tablet_params(void) { - mouseoffset_x = (uae_s16)get_word (pointerprefs + 28); - mouseoffset_y = (uae_s16)get_word (pointerprefs + 30); + uae_u8 *p; + if (inputdevice_is_tablet() <= 0 || !mousehack_address) + return; + p = mousehack_address; + + p[MH_MAXX] = tablet_maxx >> 8; + p[MH_MAXX + 1] = tablet_maxx; + p[MH_MAXY] = tablet_maxy >> 8; + p[MH_MAXY + 1] = tablet_maxy; + p[MH_MAXZ] = tablet_maxz >> 8; + p[MH_MAXZ + 1] = tablet_maxz; + + p[MH_RESX] = tablet_resx >> 8; + p[MH_RESX + 1] = tablet_resx; + p[MH_RESY] = tablet_resy >> 8; + p[MH_RESY + 1] = tablet_resy; + + p[MH_MAXAX] = tablet_maxax >> 8; + p[MH_MAXAX + 1] = tablet_maxax; + p[MH_MAXAY] = tablet_maxay >> 8; + p[MH_MAXAY + 1] = tablet_maxay; + p[MH_MAXAZ] = tablet_maxaz >> 8; + p[MH_MAXAZ + 1] = tablet_maxaz; +} + +void input_mousehack_mouseoffset(uaecptr pointerprefs) +{ + mouseoffset_x = (uae_s16)get_word (pointerprefs + 28); + mouseoffset_y = (uae_s16)get_word (pointerprefs + 30); +} + +static bool get_mouse_position(int *xp, int *yp, int inx, int iny) +{ + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; + struct amigadisplay *ad = &adisplays; + struct picasso96_state_struct *state = &picasso96_state; + int x, y; + float fdy, fdx, fmx, fmy; + bool ob = false; + + x = inx; + y = iny; + + //getgfxoffset(&fdx, &fdy, &fmx, &fmy); + + //write_log("%.2f*%.2f %.2f*%.2f\n", fdx, fdy, fmx, fmy); + +#ifdef PICASSO96 + if (ad->picasso_on) { + x -= state->XOffset; + y -= state->YOffset; + x = (int)(x * fmx); + y = (int)(y * fmy); + x += (int)(fdx * fmx); + y += (int)(fdy * fmy); + } else +#endif + { + x = (int)(x * fmx); + y = (int)(y * fmy); + x -= (int)(fdx * fmx) - 1; + y -= (int)(fdy * fmy) - 2; + x = coord_native_to_amiga_x(x); + if (y >= 0) + y = coord_native_to_amiga_y(y) * 2; + if (x < 0 || y < 0 || x >= vidinfo->drawbuffer.outwidth || y >= vidinfo->drawbuffer.outheight) + ob = true; + } + *xp = x; + *yp = y; + return ob == false; } void mousehack_wakeup(void) @@ -1743,88 +2226,389 @@ int input_mousehack_status(TrapContext *ctx, int mode, uaecptr diminfo, uaecptr } else if (mode == 5) { mousehack_address = (trap_get_dreg(ctx, 0) & 0xffff) + rtarea_bank.baseaddr; mousehack_enable (); + inputdevice_update_tablet_params (); } else if (mode == 0) { if (mousehack_address) { uae_u8 v = get_byte_host(mousehack_address + MH_E); v |= 0x40; put_byte_host(mousehack_address + MH_E, v); - write_log (_T("Tablet driver running (%08x,%02x)\n"), mousehack_address, v); + write_log (_T("Tablet driver running (%p,%02x)\n"), mousehack_address, v); } - } + } else if (mode == 1) { + int x1 = -1, y1 = -1, x2 = -1, y2 = -1; + uae_u32 props = 0; + dimensioninfo_width = -1; + dimensioninfo_height = -1; + vp_xoffset = 0; + vp_yoffset = 0; + if (diminfo) { + x1 = trap_get_word(ctx, diminfo + 50); + y1 = trap_get_word(ctx, diminfo + 52); + x2 = trap_get_word(ctx, diminfo + 54); + y2 = trap_get_word(ctx, diminfo + 56); + dimensioninfo_width = x2 - x1 + 1; + dimensioninfo_height = y2 - y1 + 1; + } + if (vp) { + vp_xoffset = trap_get_word(ctx, vp + 28); + vp_yoffset = trap_get_word(ctx, vp + 30); + } + if (dispinfo) + props = trap_get_long(ctx, dispinfo + 18); + dimensioninfo_dbl = (props & 0x00020000) ? 1 : 0; + write_log (_T("%08x %08x %08x (%dx%d)-(%dx%d) d=%dx%d %s\n"), + diminfo, props, vp, x1, y1, x2, y2, vp_xoffset, vp_yoffset, + (props & 0x00020000) ? _T("dbl") : _T("")); + } return 1; } void inputdevice_tablet_strobe (void) { - mousehack_enable (); + mousehack_enable (); if (uae_boot_rom_type <= 0) - return; - if (!tablet_data) - return; + return; + if (!tablet_data) + return; if (mousehack_address) put_byte_host(mousehack_address + MH_CNT, get_byte_host(mousehack_address + MH_CNT) + 1); } +#ifndef AMIBERRY +int inputdevice_get_lightpen_id(void) +{ + if (!alg_flag) { + if (lightpen_enabled2) + return alg_get_player(potgo_value); + return -1; + } else { + return alg_get_player(potgo_value); + } +} + +void tablet_lightpen(int tx, int ty, int tmaxx, int tmaxy, int touch, int buttonmask, bool touchmode, int devid, int lpnum) +{ + struct vidbuf_description *vidinfo = &adisplays.gfxvidinfo; + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on) + goto end; + + if (vidinfo->outbuffer == NULL) + goto end; + + if (touch < 0) + goto end; + + int dw, dh, ax, ay, aw, ah; + float fx, fy; + float xmult, ymult; + + fx = (float)tx; + fy = (float)ty; + + desktop_coords (0, &dw, &dh, &ax, &ay, &aw, &ah); + + if (tmaxx < 0 || tmaxy < 0) { + tmaxx = dw; + tmaxy = dh; + } else if (tmaxx == 0 || tmaxy == 0) { + tmaxx = aw; + tmaxy = ah; + } + + if (!touchmode) { + dw = aw; + dh = ah; + ax = 0; + ay = 0; + } + + xmult = (float)tmaxx / dw; + ymult = (float)tmaxy / dh; + + fx = fx / xmult; + fy = fy / ymult; + + fx -= ax; + fy -= ay; + + float fdx, fdy, fmx, fmy; + getgfxoffset(0, &fdx, &fdy, &fmx, &fmy); + + int x = (int)(fx * fmx); + int y = (int)(fy * fmy); + x -= (int)(fdx * fmx) - 1; + y -= (int)(fdy * fmy) - 2; + + if (x < 0 || y < 0 || x >= aw || y >= ah) + goto end; + + if (lpnum < 0) { + lightpen_x[0] = x; + lightpen_y[0] = y; + lightpen_x[1] = x; + lightpen_y[1] = y; + } else { + lightpen_x[lpnum] = x; + lightpen_y[lpnum] = y; + } + + if (touch >= 0) + lightpen_active = true; + + if (touch > 0 && devid >= 0) { + setmousebuttonstate (devid, 0, 1); + } + + lightpen_enabled = true; + return; + +end: + if (lightpen_active) { + lightpen_active = false; + if (devid >= 0) + setmousebuttonstate (devid, 0, 0); + } + +} +#endif + +void inputdevice_tablet (int x, int y, int z, int pressure, uae_u32 buttonbits, int inproximity, int ax, int ay, int az, int devid) +{ + if (is_touch_lightpen()) { + + tablet_lightpen(x, y, tablet_maxx, tablet_maxy, inproximity ? 1 : -1, buttonbits, false, devid, -1); + + } else { + uae_u8 *p; + uae_u8 tmp[MH_END]; + + mousehack_enable (); + if (inputdevice_is_tablet () <= 0 || !mousehack_address) + return; + //write_log (_T("%d %d %d %d %08X %d %d %d %d\n"), x, y, z, pressure, buttonbits, inproximity, ax, ay, az); + p = mousehack_address; + + memcpy (tmp, p + MH_START, MH_END - MH_START); + + p[MH_X] = x >> 8; + p[MH_X + 1] = x; + p[MH_Y] = y >> 8; + p[MH_Y + 1] = y; + p[MH_Z] = z >> 8; + p[MH_Z + 1] = z; + + p[MH_AX] = ax >> 8; + p[MH_AX + 1] = ax; + p[MH_AY] = ay >> 8; + p[MH_AY + 1] = ay; + p[MH_AZ] = az >> 8; + p[MH_AZ + 1] = az; + + p[MH_PRESSURE] = pressure >> 8; + p[MH_PRESSURE + 1] = pressure; + + p[MH_BUTTONBITS + 0] = buttonbits >> 24; + p[MH_BUTTONBITS + 1] = buttonbits >> 16; + p[MH_BUTTONBITS + 2] = buttonbits >> 8; + p[MH_BUTTONBITS + 3] = buttonbits >> 0; + + if (inproximity < 0) { + p[MH_INPROXIMITY] = p[MH_INPROXIMITY + 1] = 0xff; + } else { + p[MH_INPROXIMITY] = 0; + p[MH_INPROXIMITY + 1] = inproximity ? 1 : 0; + } + + if (!memcmp (tmp, p + MH_START, MH_END - MH_START)) + return; + + //if (tablet_log & 1) { + // static int obuttonbits, oinproximity; + // if (inproximity != oinproximity || buttonbits != obuttonbits) { + // obuttonbits = buttonbits; + // oinproximity = inproximity; + // write_log (_T("TABLET: B=%08x P=%d\n"), buttonbits, inproximity); + // } + //} + //if (tablet_log & 2) { + // write_log (_T("TABLET: X=%d Y=%d Z=%d AX=%d AY=%d AZ=%d\n"), x, y, z, ax, ay, az); + //} + + p[MH_E] = 0xc0 | 2; + p[MH_CNT]++; + } +} + +void inputdevice_tablet_info (int maxx, int maxy, int maxz, int maxax, int maxay, int maxaz, int xres, int yres) +{ + tablet_maxx = maxx; + tablet_maxy = maxy; + tablet_maxz = maxz; + + tablet_resx = xres; + tablet_resy = yres; + tablet_maxax = maxax; + tablet_maxay = maxay; + tablet_maxaz = maxaz; + inputdevice_update_tablet_params(); +} + static void inputdevice_mh_abs (int x, int y, uae_u32 buttonbits) { - x -= mouseoffset_x + 1; - y -= mouseoffset_y + 2; + x -= mouseoffset_x + 1; + y -= mouseoffset_y + 2; - mousehack_enable (); + mousehack_enable (); if (mousehack_address) { - uae_u8 tmp1[4], tmp2[4]; + uae_u8 tmp1[4], tmp2[4]; uae_u8 *p = mousehack_address; - memcpy (tmp1, p + MH_ABSX, sizeof tmp1); - memcpy (tmp2, p + MH_BUTTONBITS, sizeof tmp2); + memcpy (tmp1, p + MH_ABSX, sizeof tmp1); + memcpy (tmp2, p + MH_BUTTONBITS, sizeof tmp2); - //write_log (_T("%04dx%04d %08x\n"), x, y, buttonbits); + //write_log (_T("%04dx%04d %08x\n"), x, y, buttonbits); - p[MH_ABSX] = x >> 8; - p[MH_ABSX + 1] = x; - p[MH_ABSY] = y >> 8; - p[MH_ABSY + 1] = y; + p[MH_ABSX] = x >> 8; + p[MH_ABSX + 1] = x; + p[MH_ABSY] = y >> 8; + p[MH_ABSY + 1] = y; - p[MH_BUTTONBITS + 0] = buttonbits >> 24; - p[MH_BUTTONBITS + 1] = buttonbits >> 16; - p[MH_BUTTONBITS + 2] = buttonbits >> 8; - p[MH_BUTTONBITS + 3] = buttonbits >> 0; + p[MH_BUTTONBITS + 0] = buttonbits >> 24; + p[MH_BUTTONBITS + 1] = buttonbits >> 16; + p[MH_BUTTONBITS + 2] = buttonbits >> 8; + p[MH_BUTTONBITS + 3] = buttonbits >> 0; - if (!memcmp (tmp1, p + MH_ABSX, sizeof tmp1) && !memcmp (tmp2, p + MH_BUTTONBITS, sizeof tmp2)) - return; - p[MH_E] = 0xc0 | 1; - p[MH_CNT]++; - tablet_data = 1; - } + if (!memcmp (tmp1, p + MH_ABSX, sizeof tmp1) && !memcmp (tmp2, p + MH_BUTTONBITS, sizeof tmp2)) + return; + p[MH_E] = 0xc0 | 1; + p[MH_CNT]++; + tablet_data = 1; + } } static void mousehack_helper (uae_u32 buttonmask) { - int x, y; + int x, y; + //write_log (_T("mousehack_helper %08X\n"), buttonmask); - if (currprefs.input_tablet < TABLET_MOUSEHACK) - return; - x = lastmx; - y = lastmy; + if (!(currprefs.input_mouse_untrap & MOUSEUNTRAP_MAGIC) && currprefs.input_tablet < TABLET_MOUSEHACK) + return; + + get_mouse_position(&x, &y, lastmx, lastmy); -#ifdef PICASSO96 - if (picasso_on) { - x -= picasso96_state.XOffset; - y -= picasso96_state.YOffset; - } else -#endif - { - x = coord_native_to_amiga_x (x); - y = coord_native_to_amiga_y (y) << 1; - } inputdevice_mh_abs (x, y, buttonmask); } +static int mouseedge_x, mouseedge_y, mouseedge_time; +#define MOUSEEDGE_RANGE 100 +#define MOUSEEDGE_TIME 2 + +static int mouseedge() +{ + struct amigadisplay *ad = &adisplays; + int x, y, dir; + uaecptr ib; + static int melast_x, melast_y; + static int isnonzero; + + if (!(currprefs.input_mouse_untrap & MOUSEUNTRAP_MAGIC) || currprefs.input_tablet > 0) + return 0; + if (magicmouse_ibase == 0xffffffff) + return 0; + if (joybutton[0] || joybutton[1]) + return 0; + dir = 0; + if (!mouseedge_time) { + isnonzero = 0; + goto end; + } + ib = get_intuitionbase (); + if (!ib) + return 0; + + if (get_word(ib + 20) < 31) // version < 31 + return 0; + x = get_word(ib + 70); + y = get_word(ib + 68); + + + //write_log("%dx%d\n", x, y); + + if (x || y) + isnonzero = 1; + if (!isnonzero) + return 0; + if (melast_x == x) { + if (mouseedge_x < -MOUSEEDGE_RANGE) { + mouseedge_x = 0; + dir |= 1; + goto end; + } + if (mouseedge_x > MOUSEEDGE_RANGE) { + mouseedge_x = 0; + dir |= 2; + goto end; + } + } else { + mouseedge_x = 0; + melast_x = x; + } + if (melast_y == y) { + if (mouseedge_y < -MOUSEEDGE_RANGE) { + mouseedge_y = 0; + dir |= 4; + goto end; + } + if (mouseedge_y > MOUSEEDGE_RANGE) { + mouseedge_y = 0; + dir |= 8; + goto end; + } + } else { + mouseedge_y = 0; + melast_y = y; + } + return 1; + +end: + mouseedge_time = 0; + if (dir) { + if (!ad->picasso_on) { + int aw = 0, ah = 0, dx, dy; + get_custom_mouse_limits (&aw, &ah, &dx, &dy, dimensioninfo_dbl); + x += dx; + y += dy; + } + //if (!dmaen (DMA_SPRITE)) + //setmouseactivexy(x, y, 0); + //else + // setmouseactivexy(x, y, dir); + } + return 1; +} + +int magicmouse_alive (void) +{ + return mouseedge_alive > 0; +} + +STATIC_INLINE int adjust (int val) +{ + if (val > 127) + return 127; + else if (val < -127) + return -127; + return val; +} + static int getbuttonstate (int joy, int button) { return (joybutton[joy] & (1 << button)) ? 1 : 0; } +static int pc_mouse_buttons[MAX_JPORTS]; + static int getvelocity (int num, int subnum, int pct) { int val; @@ -1846,6 +2630,8 @@ static int getvelocity (int num, int subnum, int pct) } if (!mouse_deltanoreset[num][subnum]) { mouse_delta[num][subnum] -= v; + //gui_gameport_axis_change (num, subnum * 2 + 0, 0, -1); + //gui_gameport_axis_change (num, subnum * 2 + 1, 0, -1); } return v; } @@ -1855,12 +2641,54 @@ static int getvelocity (int num, int subnum, int pct) static void mouseupdate (int pct, bool vsync) { int max = 120; + static int mxd, myd; + + if (vsync) { + if (mxd < 0) { + if (mouseedge_x > 0) + mouseedge_x = 0; + else + mouseedge_x += mxd; + mouseedge_time = MOUSEEDGE_TIME; + } + if (mxd > 0) { + if (mouseedge_x < 0) + mouseedge_x = 0; + else + mouseedge_x += mxd; + mouseedge_time = MOUSEEDGE_TIME; + } + if (myd < 0) { + if (mouseedge_y > 0) + mouseedge_y = 0; + else + mouseedge_y += myd; + mouseedge_time = MOUSEEDGE_TIME; + } + if (myd > 0) { + if (mouseedge_y < 0) + mouseedge_y = 0; + else + mouseedge_y += myd; + mouseedge_time = MOUSEEDGE_TIME; + } + if (mouseedge_time > 0) { + mouseedge_time--; + if (mouseedge_time == 0) { + mouseedge_x = 0; + mouseedge_y = 0; + } + } + mxd = 0; + myd = 0; + } for (int i = 0; i < 2; i++) { if (mouse_port[i]) { int v1 = getvelocity (i, 0, pct); + mxd += v1; mouse_x[i] += v1; if (mouse_x[i] < 0) { mouse_x[i] += MOUSEXY_MAX; @@ -1872,6 +2700,7 @@ static void mouseupdate (int pct, bool vsync) } int v2 = getvelocity (i, 1, pct); + myd += v2; mouse_y[i] += v2; if (mouse_y[i] < 0) { mouse_y[i] += MOUSEXY_MAX; @@ -1889,10 +2718,23 @@ static void mouseupdate (int pct, bool vsync) record_key (0x7a << 1); else if (v3 < 0) record_key (0x7b << 1); - if (!mouse_deltanoreset[i][2]) mouse_delta[i][2] = 0; - +#ifndef AMIBERRY + if (getbuttonstate(i, JOYBUTTON_1)) + pc_mouse_buttons[i] |= 1; + else + pc_mouse_buttons[i] &= ~1; + if (getbuttonstate(i, JOYBUTTON_2)) + pc_mouse_buttons[i] |= 2; + else + pc_mouse_buttons[i] &= ~2; + if (getbuttonstate(i, JOYBUTTON_3)) + pc_mouse_buttons[i] |= 4; + else + pc_mouse_buttons[i] &= ~4; + x86_mouse(i, v1, v2, v3, pc_mouse_buttons[i]); +#endif if (mouse_frame_x[i] - mouse_x[i] > max) { mouse_x[i] = mouse_frame_x[i] - max; mouse_x[i] &= MOUSEXY_MAX - 1; @@ -1914,10 +2756,25 @@ static void mouseupdate (int pct, bool vsync) } } +#ifndef AMIBERRY + for (int i = 0; i < 2; i++) { + if (lightpen_delta[i][0]) { + lightpen_x[i] += lightpen_delta[i][0]; + if (!lightpen_deltanoreset[i][0]) + lightpen_delta[i][0] = 0; + } + if (lightpen_delta[i][1]) { + lightpen_y[i] += lightpen_delta[i][1]; + if (!lightpen_deltanoreset[i][1]) + lightpen_delta[i][1] = 0; + } + } +#endif + } static int input_vpos, input_frame; - +extern int vpos; static void readinput (void) { uae_u32 totalvpos; @@ -1983,14 +2840,12 @@ static int inputread; static void inputdevice_read (void) { - for (;;) - { + for (;;) { int got = handle_msgpump(); if (!got) break; } - if (inputread <= 0) - { + if (inputread <= 0) { idev[IDTYPE_MOUSE].read(); idev[IDTYPE_JOYSTICK].read(); idev[IDTYPE_KEYBOARD].read(); @@ -2009,6 +2864,8 @@ static uae_u16 getjoystate (int joy) { uae_u16 v; + maybe_read_input(); + v = (uae_u8)mouse_x[joy] | (mouse_y[joy] << 8); return v; } @@ -2018,6 +2875,10 @@ uae_u16 JOY0DAT (void) uae_u16 v; readinput (); v = getjoystate (0); +#ifndef AMIBERRY + v = dongle_joydat (0, v); + v = alg_joydat(0, v); +#endif return v; } @@ -2026,6 +2887,17 @@ uae_u16 JOY1DAT (void) uae_u16 v; readinput (); v = getjoystate (1); +#ifndef AMIBERRY + v = dongle_joydat (1, v); + v = alg_joydat(1, v); + + if (inputrecord_debug & 2) { + if (input_record > 0) + inprec_recorddebug_cia (v, -1, m68k_getpc ()); + else if (input_play > 0) + inprec_playdebug_cia (v, -1, m68k_getpc ()); + } +#endif return v; } @@ -2033,6 +2905,9 @@ uae_u16 JOYGET (int num) { uae_u16 v; v = getjoystate (num); +#ifndef AMIBERRY + v = dongle_joydat (num, v); +#endif return v; } @@ -2058,9 +2933,11 @@ void JOYTEST (uae_u16 v) mouse_frame_y[0] = mouse_y[0]; mouse_frame_x[1] = mouse_x[1]; mouse_frame_y[1] = mouse_y[1]; +#ifndef AMIBERRY + dongle_joytest (v); +#endif } -#if !defined(INPUTDEVICE_SIMPLE) || defined(AMIBERRY) static uae_u8 parconvert (uae_u8 v, int jd, int shift) { if (jd & DIR_UP) @@ -2078,6 +2955,7 @@ static uae_u8 parconvert (uae_u8 v, int jd, int shift) uae_u8 handle_parport_joystick (int port, uae_u8 pra, uae_u8 dra) { uae_u8 v; + maybe_read_input(); switch (port) { case 0: @@ -2099,22 +2977,30 @@ uae_u8 handle_parport_joystick (int port, uae_u8 pra, uae_u8 dra) } return v; default: + abort (); return 0; } } -#endif -/* p5 is 1 or floating = cd32 2-button mode */ -static bool cd32padmode (uae_u16 p5dir, uae_u16 p5dat) +/* p5 (3rd button) is 1 or floating = cd32 2-button mode */ +static bool cd32padmode(int joy) { - return !(!(potgo_value & p5dir) || ((potgo_value & p5dat) && (potgo_value & p5dir))); + return pot_cap[joy][0] <= 100; } -#ifndef INPUTDEVICE_SIMPLE static bool is_joystick_pullup (int joy) { return joymodes[joy] == JSEM_MODE_GAMEPAD; } +static bool is_mouse_pullup (int joy) +{ + return mouse_pullup; +} + +static int lightpen_port_number(void) +{ + return currprefs.cs_dipagnus ? 0 : 1; +} static void charge_cap (int joy, int idx, int charge) { @@ -2126,7 +3012,6 @@ static void charge_cap (int joy, int idx, int charge) if (pot_cap[joy][idx] > 511) pot_cap[joy][idx] = 511; } -#endif static void cap_check (void) { @@ -2134,106 +3019,121 @@ static void cap_check (void) for (joy = 0; joy < 2; joy++) { for (i = 0; i < 2; i++) { -#ifndef INPUTDEVICE_SIMPLE - int charge = 0, joypot; -#endif + int charge = 0, dong, joypot; uae_u16 pdir = 0x0200 << (joy * 4 + i * 2); /* output enable */ uae_u16 pdat = 0x0100 << (joy * 4 + i * 2); /* data */ uae_u16 p5dir = 0x0200 << (joy * 4); uae_u16 p5dat = 0x0100 << (joy * 4); int isbutton = getbuttonstate (joy, i == 0 ? JOYBUTTON_3 : JOYBUTTON_2); - if (cd32_pad_enabled[joy]) { + if (cd32_pad_enabled[joy] && !cd32padmode(joy)) { // only red and blue can be read if CD32 pad and only if it is in normal pad mode isbutton |= getbuttonstate (joy, JOYBUTTON_CD32_BLUE); - // CD32 pad 3rd button line (P5) is always floating + // middle button line is floating if (i == 0) isbutton = 0; - if (cd32padmode (p5dir, p5dat)) - continue; + cd32_shifter[joy] = 8; } - -#ifndef INPUTDEVICE_SIMPLE +#ifndef AMIBERRY + // two lightpens use multiplexer chip + if (lightpen_enabled2 && lightpen_port_number() == joy) + continue; +#endif + //dong = dongle_analogjoy (joy, i); + //if (dong >= 0) { + // isbutton = 0; + // joypot = dong; + // if (pot_cap[joy][i] < joypot) + // charge = 1; // slow charge via dongle resistor + //} else { joypot = joydirpot[joy][i]; if (analog_port[joy][i] && pot_cap[joy][i] < joypot) charge = 1; // slow charge via pot variable resistor - if ((is_joystick_pullup (joy) && digital_port[joy][i]) || (mouse_port[joy])) + if ((is_joystick_pullup (joy) && digital_port[joy][i]) || (is_mouse_pullup (joy) && mouse_port[joy])) charge = 1; // slow charge via pull-up resistor -#endif + //} if (!(potgo_value & pdir)) { // input? if (pot_dat_act[joy][i]) pot_dat[joy][i]++; /* first 7 or 8 lines after potgo has been started = discharge cap */ if (pot_dat_act[joy][i] == 1) { if (pot_dat[joy][i] < (currprefs.ntscmode ? POTDAT_DELAY_NTSC : POTDAT_DELAY_PAL)) { -#ifndef INPUTDEVICE_SIMPLE charge = -2; /* fast discharge delay */ -#endif } else { pot_dat_act[joy][i] = 2; pot_dat[joy][i] = 0; } } -#ifndef INPUTDEVICE_SIMPLE + if (dong >= 0) { + if (pot_dat_act[joy][i] == 2 && pot_cap[joy][i] >= joypot) + pot_dat_act[joy][i] = 0; + } else { if (analog_port[joy][i] && pot_dat_act[joy][i] == 2 && pot_cap[joy][i] >= joypot) pot_dat_act[joy][i] = 0; -#endif if ((digital_port[joy][i] || mouse_port[joy]) && pot_dat_act[joy][i] == 2) { -#ifdef INPUTDEVICE_SIMPLE - if (!isbutton) -#else if (pot_cap[joy][i] >= 10 && !isbutton) -#endif pot_dat_act[joy][i] = 0; } + } } else { // output? -#ifndef INPUTDEVICE_SIMPLE charge = (potgo_value & pdat) ? 2 : -2; /* fast (dis)charge if output */ -#endif if (potgo_value & pdat) pot_dat_act[joy][i] = 0; // instant stop if output+high if (isbutton) pot_dat[joy][i]++; // "free running" if output+low } -#ifndef INPUTDEVICE_SIMPLE if (isbutton) charge = -2; // button press overrides everything + if (currprefs.cs_cdtvcd) { + /* CDTV P9 is not floating */ + if (!(potgo_value & pdir) && i == 1 && charge == 0) + charge = 2; + } + // CD32 pad in 2-button mode: blue button is not floating - if (cd32_pad_enabled[joy] && i == 1 && charge == 0) + if (cd32_pad_enabled[joy] && !cd32padmode(joy) && i == 1) { + if (charge == 0) charge = 2; + } + + if (dong < 0 && charge == 0) { + + if (lightpen_port[joy]) + charge = 2; /* official Commodore mouse has pull-up resistors in button lines * NOTE: 3rd party mice may not have pullups! */ - if ((mouse_port[joy] && digital_port[joy][i]) && charge == 0) + if (is_mouse_pullup (joy) && mouse_port[joy] && digital_port[joy][i]) charge = 2; + /* emulate pullup resistor if button mapped because there too many broken * programs that read second button in input-mode (and most 2+ button pads have * pullups) */ - if ((is_joystick_pullup (joy) && digital_port[joy][i]) && charge == 0) + if (is_joystick_pullup (joy) && digital_port[joy][i]) charge = 2; + } charge_cap (joy, i, charge); -#endif } } } + uae_u8 handle_joystick_buttons (uae_u8 pra, uae_u8 dra) { uae_u8 but = 0; int i; + maybe_read_input(); cap_check (); for (i = 0; i < 2; i++) { int mask = 0x40 << i; if (cd32_pad_enabled[i]) { - uae_u16 p5dir = 0x0200 << (i * 4); - uae_u16 p5dat = 0x0100 << (i * 4); but |= mask; - if (!cd32padmode (p5dir, p5dat)) { + if (!cd32padmode(i)) { if (getbuttonstate (i, JOYBUTTON_CD32_RED) || getbuttonstate (i, JOYBUTTON_1)) but &= ~mask; // always zero if output=1 and data=0 @@ -2244,6 +3144,11 @@ uae_u8 handle_joystick_buttons (uae_u8 pra, uae_u8 dra) } else { if (!getbuttonstate (i, JOYBUTTON_1)) but |= mask; + if (bouncy && cycles_in_range (bouncy_cycles)) { + but &= ~mask; + if (uaerand () & 1) + but |= mask; + } // always zero if output=1 and data=0 if ((dra & mask) && !(pra & mask)) { but &= ~mask; @@ -2260,12 +3165,11 @@ void handle_cd32_joystick_cia (uae_u8 pra, uae_u8 dra) static int oldstate[2]; int i; + maybe_read_input(); cap_check (); for (i = 0; i < 2; i++) { uae_u8 but = 0x40 << i; - uae_u16 p5dir = 0x0200 << (i * 4); /* output enable P5 */ - uae_u16 p5dat = 0x0100 << (i * 4); /* data P5 */ - if (cd32padmode (p5dir, p5dat)) { + if (cd32padmode(i)) { if ((dra & but) && (pra & but) != oldstate[i]) { if (!(pra & but)) { cd32_shifter[i]--; @@ -2290,39 +3194,52 @@ static uae_u16 handle_joystick_potgor (uae_u16 potgor) uae_u16 p5dir = 0x0200 << (i * 4); /* output enable P5 */ uae_u16 p5dat = 0x0100 << (i * 4); /* data P5 */ - if (cd32_pad_enabled[i] && cd32padmode (p5dir, p5dat)) { + if (cd32_pad_enabled[i] && cd32padmode(i)) { /* p5 is floating in input-mode */ potgor &= ~p5dat; - potgor |= potgo_value & p5dat; + if (pot_cap[i][0] > 100) + potgor |= p5dat; + if (!(potgo_value & p9dir)) potgor |= p9dat; - /* (P5 output and 1) or floating -> shift register is kept reset (Blue button) */ - if (!(potgo_value & p5dir) || ((potgo_value & p5dat) && (potgo_value & p5dir))) - cd32_shifter[i] = 8; + /* shift at 1 == return one, >1 = return button states */ if (cd32_shifter[i] == 0) potgor &= ~p9dat; /* shift at zero == return zero */ if (cd32_shifter[i] >= 2 && (joybutton[i] & ((1 << JOYBUTTON_CD32_PLAY) << (cd32_shifter[i] - 2)))) potgor &= ~p9dat; + + // normal second button pressed: always zero. Overrides CD32 mode. + if (getbuttonstate(i, JOYBUTTON_2)) + potgor &= ~p9dat; +#ifndef AMIBERRY + } else if (alg_flag) { + potgor = alg_potgor(potgo_value); + + } else if (lightpen_enabled2 && lightpen_port_number() == i) { + + int button; + + if (inputdevice_get_lightpen_id() == 1) + button = lightpen_trigger2; + else + button = getbuttonstate(i, JOYBUTTON_3); + + potgor |= 0x1000; + if (button) + potgor &= ~0x1000; +#endif } else { potgor &= ~p5dat; -#ifdef INPUTDEVICE_SIMPLE - if (getbuttonstate(i, JOYBUTTON_3) == 0) -#else if (pot_cap[i][0] > 100) -#endif potgor |= p5dat; - if (!cd32_pad_enabled[i] || !cd32padmode (p5dir, p5dat)) { + if (!cd32_pad_enabled[i] || !cd32padmode(i)) { potgor &= ~p9dat; -#ifdef INPUTDEVICE_SIMPLE - if(getbuttonstate(i, JOYBUTTON_2) == 0) -#else if (pot_cap[i][1] > 100) -#endif potgor |= p9dat; } @@ -2422,11 +3339,203 @@ static void inject_events (const TCHAR *str) } } +struct delayed_event +{ + TCHAR *event_string; + int delay; + int append; + struct delayed_event *next; +}; +static struct delayed_event *delayed_events; + +int handle_custom_event (const TCHAR *custom, int append) +{ + TCHAR *p, *buf, *nextp; + bool noquot = false; + bool first = true; + int adddelay = 0; + bool maybe_config_changed = false; + + if (custom == NULL) { + return 0; + } + //write_log (_T("%s\n"), custom); + + if (append) { + struct delayed_event *dee = delayed_events, *prev = NULL; + while (dee) { + if (dee->delay > 0 && dee->delay > adddelay && dee->append) { + adddelay = dee->delay; + } + prev = dee; + dee = dee->next; + } + } + + p = buf = my_strdup_trim (custom); + if (p[0] != '\"') + noquot = true; + while (p && *p) { + TCHAR *p2 = NULL; + if (!noquot) { + if (*p != '\"') + break; + p++; + p2 = p; + while (*p2 != '\"' && *p2 != 0) + p2++; + if (*p2 == '\"') { + *p2++ = 0; + nextp = p2 + 1; + while (*nextp == ' ') + nextp++; + } + } + //write_log (L"-> '%s'\n", p); + if (!_tcsnicmp (p, _T("delay "), 6) || !_tcsnicmp (p, _T("vdelay "), 7) || !_tcsnicmp (p, _T("hdelay "), 7) || adddelay) { + TCHAR *next = NULL; + int delay = -1; + if (!_tcsnicmp (p, _T("delay "), 6)) { + next = p + 7; + delay = _tstol(p + 6) * maxvpos_nom; + if (!delay) + delay = maxvpos_nom; + } else if (!_tcsnicmp (p, _T("vdelay "), 7)) { + next = p + 8; + delay = _tstol(p + 7) * maxvpos_nom; + if (!delay) + delay = maxvpos_nom; + } else if (!_tcsnicmp (p, _T("hdelay "), 7)) { + next = p + 8; + delay = _tstol(p + 7); + } + if (adddelay && delay < 0) { + delay = adddelay; + } else if (adddelay > 0 && delay >= 0) { + delay += adddelay; + } + if (delay >= 0) { + if (!p2) { + if (!next) + p2 = p; + else + p2 = _tcschr(next, ' '); + } + struct delayed_event *de = delayed_events; + while (de) { + if (de->delay < 0) { + de->delay = delay + 1; + de->event_string = p2 ? my_strdup (p2) : my_strdup(_T("")); + de->append = append; + break; + } + de = de->next; + } + if (!de) { + de = xcalloc (delayed_event, 1); + de->next = delayed_events; + delayed_events = de; + de->delay = delay + 1; + de->append = append; + de->event_string = p2 ? my_strdup (p2) : my_strdup(_T("")); + } + } + break; + } + if (first) { + first = false; + if (!append) + maybe_config_changed = true; + } + if (!_tcsicmp (p, _T("no_config_check"))) { + config_changed = 0; + maybe_config_changed = false; + } else if (!_tcsicmp (p, _T("do_config_check"))) { + set_config_changed (); +#ifndef AMIBERRY + } else if (!_tcsnicmp(p, _T("shellexec "), 10)) { + uae_ShellExecute(p + 10); + } else if (!_tcsnicmp(p, _T("dbg "), 4)) { + debug_parser(p + 4, NULL, -1); +#endif + } else if (!_tcsnicmp (p, _T("kbr "), 4)) { + inject_events (p + 4); + } else if (!_tcsnicmp (p, _T("evt "), 4)) { + TCHAR *pp = _tcschr (p + 4, ' '); + p += 4; + if (pp) + *pp++ = 0; + inputdevice_uaelib (p, pp); + } else if (!_tcsnicmp(p, _T("key_raw_up "), 11)) { + TCHAR *pp = _tcschr (p + 10, ' '); + if (pp) { + *pp++ = 0; + inputdevice_uaelib (p, pp); + } + } else if (!_tcsnicmp(p, _T("key_raw_down "), 13)) { + TCHAR *pp = _tcschr (p + 12, ' '); + if (pp) { + *pp++ = 0; + inputdevice_uaelib (p, pp); + } + } else { + cfgfile_parse_line (&changed_prefs, p, 0); + } + if (noquot) + break; + p = nextp; + } + if (maybe_config_changed) + set_config_changed(); + xfree (buf); + return 0; +} + void inputdevice_hsync(bool forceread) { - static int cnt; cap_check (); +#ifdef CATWEASEL + catweasel_hsync (); +#endif + + int cnt = 0; + struct delayed_event *de = delayed_events, *prev = NULL; + while (de) { + if (de->delay < 0) + cnt++; + if (de->delay > 0) + de->delay--; + if (de->delay == 0) { + de->delay = -1; + if (de->event_string) { + TCHAR *s = de->event_string; + de->event_string = NULL; + handle_custom_event (s, 0); + xfree (s); + } + } + prev = de; + de = de->next; + } + if (cnt > 4) { + // too many, delete some + struct delayed_event *de_prev = NULL; + de = delayed_events; + while (de) { + if (de->delay < 0 && de != delayed_events) { + struct delayed_event *next = de->next; + de_prev->next = next; + xfree(de->event_string); + xfree(de); + de = next; + } else { + de_prev = de; + de = de->next; + } + } + } + for (int i = 0; i < INPUT_QUEUE_SIZE; i++) { struct input_queue_struct *iq = &input_queue[i]; if (iq->linecnt > 0) { @@ -2436,22 +3545,39 @@ void inputdevice_hsync(bool forceread) iq->state = 0; else iq->state = iq->storedstate; + if (iq->custom) + handle_custom_event (iq->custom, 0); if (iq->evt) - handle_input_event (iq->evt, iq->state, iq->max, 0); + handle_input_event (iq->evt, iq->state, iq->max, HANDLE_IE_FLAG_PLAYBACKEVENT); iq->linecnt = iq->nextlinecnt; } } } - if (forceread) - { - inputread = maxvpos + 1; + if (bouncy && get_cycles () > bouncy_cycles) + bouncy = 0; +#ifndef AMIBERRY + if (input_record && input_record != INPREC_RECORD_PLAYING) { + if (vpos == 0) inputdevice_read(); } - else - { - maybe_read_input(); + if (input_play) { + inprec_playdiskchange (); + int nr, state, max, autofire; + while (inprec_playevent (&nr, &state, &max, &autofire)) + handle_input_event (nr, state, max, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_PLAYBACKEVENT); + if (vpos == 0) + handle_msgpump (); } + if (!input_record && !input_play) { + if (forceread) { + inputread = maxvpos + 1; + inputdevice_read(); + } else { +#endif + maybe_read_input(); + //} +//} } static uae_u16 POTDAT (int joy) @@ -2479,7 +3605,9 @@ uae_u16 POT1DAT (void) void POTGO (uae_u16 v) { int i, j; - +#ifndef AMIBERRY + dongle_potgo (v); +#endif potgo_value = potgo_value & 0x5500; /* keep state of data bits */ potgo_value |= v & 0xaa00; /* get new direction bits */ for (i = 0; i < 8; i += 2) { @@ -2490,14 +3618,6 @@ void POTGO (uae_u16 v) potgo_value |= v & data; } } - for (i = 0; i < 2; i++) { - if (cd32_pad_enabled[i]) { - uae_u16 p5dir = 0x0200 << (i * 4); /* output enable P5 */ - uae_u16 p5dat = 0x0100 << (i * 4); /* data P5 */ - if (!(potgo_value & p5dir) || ((potgo_value & p5dat) && (potgo_value & p5dir))) - cd32_shifter[i] = 8; - } - } if (v & 1) { for (i = 0; i < 2; i++) { for (j = 0; j < 2; j++) { @@ -2513,6 +3633,9 @@ uae_u16 POTGOR (void) uae_u16 v; v = handle_joystick_potgor (potgo_value) & 0x5500; +#ifndef AMIBERRY + v = dongle_potgor (v); +#endif return v; } @@ -2528,7 +3651,7 @@ static int check_input_queue (int evt) return -1; } -static void queue_input_event (int evt, int state, int max, int linecnt) +static void queue_input_event (int evt, const TCHAR *custom, int state, int max, int linecnt, int autofire) { struct input_queue_struct *iq; int idx; @@ -2544,7 +3667,7 @@ static void queue_input_event (int evt, int state, int max, int linecnt) if (iq->state == 0 && evt > 0) handle_input_event (evt, 0, 1, 0); } else if (state >= 0 && idx < 0) { - if (evt == 0) + if (evt == 0 && custom == NULL) return; for (idx = 0; idx < INPUT_QUEUE_SIZE; idx++) { iq = &input_queue[idx]; @@ -2555,11 +3678,15 @@ static void queue_input_event (int evt, int state, int max, int linecnt) write_log (_T("input queue overflow\n")); return; } + xfree (iq->custom); + iq->custom = NULL; + if (custom) + iq->custom = my_strdup (custom); iq->evt = evt; iq->state = iq->storedstate = state; iq->max = max; iq->linecnt = linecnt < 0 ? maxvpos + maxvpos / 2 : linecnt; - iq->nextlinecnt = linecnt; + iq->nextlinecnt = autofire > 0 ? linecnt : -1; } } @@ -2573,17 +3700,39 @@ struct inputcode }; static struct inputcode inputcode_pending[MAX_PENDING_EVENTS]; +#ifndef AMIBERRY +static bool inputdevice_handle_inputcode_immediate(int code, int state) +{ + if (!state) + return false; + switch(code) + { + case AKS_ENTERDEBUGGER: + activate_debugger (); + return true; + } + return false; +} +#endif + void inputdevice_add_inputcode (int code, int state, const TCHAR *s) { - for (auto & i : inputcode_pending) { - if (i.code == code && i.state == state) + for (int i = 0; i < MAX_PENDING_EVENTS; i++) { + if (inputcode_pending[i].code == code && inputcode_pending[i].state == state) return; } - for (auto & i : inputcode_pending) { - if (i.code == 0) { - i.code = code; - i.state = state; - i.s != nullptr ? i.s = my_strdup(s) : nullptr; + for (int i = 0; i < MAX_PENDING_EVENTS; i++) { + if (inputcode_pending[i].code == 0) { +#ifndef AMIBERRY + if (!inputdevice_handle_inputcode_immediate(code, state)) { +#endif + inputcode_pending[i].code = code; + inputcode_pending[i].state = state; + if(s == NULL) + inputcode_pending[i].s = NULL; + else + inputcode_pending[i].s = my_strdup(s); + //} return; } } @@ -2591,11 +3740,32 @@ void inputdevice_add_inputcode (int code, int state, const TCHAR *s) void inputdevice_do_keyboard (int code, int state) { +#ifdef CDTV + if (code >= 0x72 && code <= 0x77) { // CDTV keys + if (cdtv_front_panel (-1)) { + // front panel active + if (!state) + return; + cdtv_front_panel (code - 0x72); + return; + } + } +#endif if (code < 0x80) { uae_u8 key = code | (state ? 0x00 : 0x80); keybuf[key & 0x7f] = (key & 0x80) ? 0 : 1; - if (record_key ((uae_u8)((key << 1) | (key >> 7)))) { + if (key == AK_RESETWARNING) { + //resetwarning_do (0); + return; + } else if ((keybuf[AK_CTRL] || keybuf[AK_RCTRL]) && keybuf[AK_LAMI] && keybuf[AK_RAMI]) { + int r = keybuf[AK_LALT] | keybuf[AK_RALT]; + if (!r && currprefs.cs_resetwarning) + return; + memset (keybuf, 0, sizeof (keybuf)); + send_internalevent (INTERNALEVENT_KBRESET); + uae_reset (r, 1); } + record_key ((uae_u8)((key << 1) | (key >> 7))); return; } inputdevice_add_inputcode (code, state, NULL); @@ -2623,9 +3793,35 @@ int mousespeed; int i; int num_elements; +// these need cpu trace data +static bool needcputrace (int code) +{ + switch (code) + { + case AKS_ENTERGUI: + case AKS_STATECAPTURE: + case AKS_STATESAVEQUICK: + case AKS_STATESAVEQUICK1: + case AKS_STATESAVEQUICK2: + case AKS_STATESAVEQUICK3: + case AKS_STATESAVEQUICK4: + case AKS_STATESAVEQUICK5: + case AKS_STATESAVEQUICK6: + case AKS_STATESAVEQUICK7: + case AKS_STATESAVEQUICK8: + case AKS_STATESAVEQUICK9: + case AKS_STATESAVEDIALOG: + return true; + } + return false; +} + +void target_paste_to_keyboard(void); static bool inputdevice_handle_inputcode2(int code, int state, const TCHAR *s) { + static int swapperslot; + static int tracer_enable; int newstate, onoffstate; if (s != NULL && s[0] == 0) @@ -2633,6 +3829,17 @@ static bool inputdevice_handle_inputcode2(int code, int state, const TCHAR *s) if (code == 0) goto end; +#ifndef AMIBERRY + if (needcputrace (code) && can_cpu_tracer () == true && is_cpu_tracer () == false && !input_play && !input_record && !debugging) { + if (set_cpu_tracer (true)) { + tracer_enable = 1; + return true; // wait for next frame + } + } +#endif + + if (vpos != 0) + write_log (_T("inputcode=%d but vpos = %d"), code, vpos); onoffstate = state & ~SET_ONOFF_MASK_PRESS; @@ -2649,6 +3856,102 @@ static bool inputdevice_handle_inputcode2(int code, int state, const TCHAR *s) else newstate = 0; +#ifdef ARCADIA + switch (code) + { + case AKS_ARCADIADIAGNOSTICS: + arcadia_flag &= ~1; + arcadia_flag |= state ? 1 : 0; + break; + case AKS_ARCADIAPLY1: + arcadia_flag &= ~4; + arcadia_flag |= state ? 4 : 0; + break; + case AKS_ARCADIAPLY2: + arcadia_flag &= ~2; + arcadia_flag |= state ? 2 : 0; + break; + case AKS_ARCADIACOIN1: + if (state) + arcadia_coin[0]++; + break; + case AKS_ARCADIACOIN2: + if (state) + arcadia_coin[1]++; + break; + + case AKS_CUBOTOUCH: + if (state) + cubo_flag |= 0x80000000; + else + cubo_flag &= ~0x80000000; + cubo_flag &= ~0x40000000; + break; + case AKS_CUBOTEST: + if (state) + cubo_flag |= 0x00800000; + else + cubo_flag &= ~0x00800000; + break; + case AKS_CUBOCOIN1: + if (state) + cubo_function(0); + break; + case AKS_CUBOCOIN2: + if (state) + cubo_function(1); + break; + case AKS_CUBOCOIN3: + if (state) + cubo_function(2); + break; + case AKS_CUBOCOIN4: + if (state) + cubo_function(3); + break; + + case AKS_ALGSERVICE: + alg_flag &= ~2; + alg_flag |= state ? 2 : 0; + break; + case AKS_ALGLSTART: + alg_flag &= ~4; + alg_flag |= state ? 4 : 0; + break; + case AKS_ALGRSTART: + alg_flag &= ~8; + alg_flag |= state ? 8 : 0; + break; + case AKS_ALGLCOIN: + alg_flag &= ~16; + alg_flag |= state ? 16 : 0; + break; + case AKS_ALGRCOIN: + alg_flag &= ~32; + alg_flag |= state ? 32 : 0; + break; + case AKS_ALGLTRIGGER: + alg_flag &= ~64; + alg_flag |= state ? 64 : 0; + break; + case AKS_ALGRTRIGGER: + alg_flag &= ~128; + alg_flag |= state ? 128 : 0; + break; + case AKS_ALGLHOLSTER: + alg_flag &= ~256; + alg_flag |= state ? 256 : 0; + break; + case AKS_ALGRHOLSTER: + alg_flag &= ~512; + alg_flag |= state ? 512 : 0; + break; + } +#endif + if (!state) { + return false; + } + switch (code) { case AKS_ENTERGUI: @@ -2735,9 +4038,9 @@ static bool inputdevice_handle_inputcode2(int code, int state, const TCHAR *s) pausemode(0); autopause = 1; break; - //case AKS_WARP: - // warpmode(newstate); - // break; + case AKS_WARP: + warpmode(newstate); + break; //case AKS_INHIBITSCREEN: // toggle_inhibit_frame(monid, IHF_SCROLLLOCK); // break; @@ -2829,12 +4132,16 @@ static bool inputdevice_handle_inputcode2(int code, int state, const TCHAR *s) break; } end: +#ifndef AMIBERRY + if (tracer_enable) { + set_cpu_tracer (false); + tracer_enable = 0; + } +#endif return false; } - - -void inputdevice_handle_inputcode(void) +void inputdevice_handle_inputcode (void) { bool got = false; for (auto & i : inputcode_pending) { @@ -2878,19 +4185,22 @@ static uae_u64 isqual (int evt) return ID_FLAG_QUALIFIER1 << (num * 2); } -static int handle_input_event(int nr, int state, int max, int autofire) +static int handle_input_event2(int nr, int state, int max, int flags, int extra) { const struct inputevent *ie; int joy; - bool isaks; + bool isaks = false; + int autofire = (flags & HANDLE_IE_FLAG_AUTOFIRE) ? 1 : 0; if (nr <= 0 || nr == INPUTEVENT_SPC_CUSTOM_EVENT) return 0; #ifdef _WIN32 // ignore normal GUI event if forced gui key is in use - if (currprefs.win32_guikey >= 0 && nr == INPUTEVENT_SPC_ENTERGUI) + if (nr == INPUTEVENT_SPC_ENTERGUI) { + if (currprefs.win32_guikey > 0) return 0; + } #endif ie = &events[nr]; @@ -2902,12 +4212,92 @@ static int handle_input_event(int nr, int state, int max, int autofire) if (autofire) { if (state) - queue_input_event(nr, state, max, currprefs.input_autofire_linecnt); + queue_input_event (nr, NULL, state, max, currprefs.input_autofire_linecnt, 1); else - queue_input_event(nr, -1, 0, 0); + queue_input_event (nr, NULL, -1, 0, 0, 1); } switch (ie->unit) { +#ifndef AMIBERRY + case 5: /* lightpen/gun */ + case 6: /* lightpen/gun #2 */ + { + int unit = (ie->data & 1) ? 1 : 0; + int lpnum = ie->unit - 5; + if (lightpen_active <= 0) { + lightpen_x[0] = vidinfo->outbuffer->outwidth / 2; + lightpen_y[0] = vidinfo->outbuffer->outheight / 2; + lightpen_x[1] = -1; + lightpen_y[1] = -1; + } + lightpen_active = true; + lightpen_enabled = true; + if (flags & HANDLE_IE_FLAG_ABSOLUTE) { + lastmxy_abs[lpnum][unit] = extra; + if (!unit) + return 1; + int x = lastmxy_abs[lpnum][0]; + int y = lastmxy_abs[lpnum][1]; + if (x <= 0 || x >= 65535 || y <= 0 || y >= 65535) { + x = y = -1; + } + tablet_lightpen(x, y, 65535, 65535, 0, 0, false, -1, lpnum); + } else if (ie->type == 0) { + int delta = 0; + if (max == 0) { + delta = state * currprefs.input_mouse_speed / 100; + } else { + int deadzone = currprefs.input_joymouse_deadzone * max / 100; + if (state <= deadzone && state >= -deadzone) { + state = 0; + lightpen_deltanoreset[lpnum][unit] = 0; + } else if (state < 0) { + state += deadzone; + lightpen_deltanoreset[lpnum][unit] = 1; + } else { + state -= deadzone; + lightpen_deltanoreset[lpnum][unit] = 1; + } + max -= deadzone; + delta = state * currprefs.input_joymouse_multiplier / (10 * max); + } + if (ie->data) + lightpen_y[lpnum] += delta; + else + lightpen_x[lpnum] += delta; + if (max) + lightpen_delta[lpnum][unit] = delta; + else + lightpen_delta[lpnum][unit] += delta; + } else if (ie->type == 2) { + lightpen_trigger2 = state; + } else { + if (state) { + int delta = currprefs.input_joymouse_speed; + if (ie->data & DIR_LEFT) + lightpen_x[lpnum] -= delta; + if (ie->data & DIR_RIGHT) + lightpen_x[lpnum] += delta; + if (ie->data & DIR_UP) + lightpen_y[lpnum] -= delta; + if (ie->data & DIR_DOWN) + lightpen_y[lpnum] += delta; + } + } + if (lightpen_x[lpnum] < -10) + lightpen_x[lpnum] = -10; + if (lightpen_x[lpnum] >= vidinfo->drawbuffer.inwidth + 10) + lightpen_x[lpnum] = vidinfo->drawbuffer.inwidth + 10; + if (lightpen_y[lpnum] < -10) + lightpen_y[lpnum] = -10; + if (lightpen_y[lpnum] >= vidinfo->drawbuffer.inheight + 10) + lightpen_y[lpnum] = vidinfo->drawbuffer.inheight + 10; +#if 0 + write_log(_T("%d*%d\n"), lightpen_x[0], lightpen_y[0]); +#endif + } + break; +#endif case 1: /* ->JOY1 */ case 2: /* ->JOY2 */ case 3: /* ->Parallel port joystick adapter port #1 */ @@ -2918,13 +4308,22 @@ static int handle_input_event(int nr, int state, int max, int autofire) if (state) { joybutton[joy] |= 1 << ie->data; - } - else { + //gui_gameport_button_change (joy, ie->data, 1); + } else { joybutton[joy] &= ~(1 << ie->data); + //gui_gameport_button_change (joy, ie->data, 0); } +#ifndef AMIBERRY + if (ie->data == 0 && old != (joybutton[joy] & (1 << ie->data)) && currprefs.cpu_cycle_exact) { + if (!input_record && !input_play && currprefs.input_contact_bounce) { + // emulate contact bounce, 1st button only, others have capacitors + bouncy = 1; + bouncy_cycles = get_cycles () + CYCLE_UNIT * currprefs.input_contact_bounce; + } + } +#endif - } - else if (ie->type & 8) { + } else if (ie->type & 8) { /* real mouse / analog stick mouse emulation */ int delta; @@ -2935,27 +4334,30 @@ static int handle_input_event(int nr, int state, int max, int autofire) if (state <= deadzone && state >= -deadzone) { state = 0; mouse_deltanoreset[joy][unit] = 0; - } - else if (state < 0) { + } else if (state < 0) { state += deadzone; mouse_deltanoreset[joy][unit] = 1; - } - else { + } else { state -= deadzone; mouse_deltanoreset[joy][unit] = 1; } if (max > 0) { max -= deadzone; delta = state * currprefs.input_joymouse_multiplier / max; - } - else { + } else { delta = state; } - } - else { + } else { delta = state; mouse_deltanoreset[joy][unit] = 0; } + if (ie->data & IE_CDTV) { + delta = 0; + if (state > 0) + delta = JOYMOUSE_CDTV; + else if (state < 0) + delta = -JOYMOUSE_CDTV; + } if (ie->data & IE_INVERT) delta = -delta; @@ -2966,57 +4368,66 @@ static int handle_input_event(int nr, int state, int max, int autofire) mouse_delta[joy][unit] += delta; max = 32; - } - else if (ie->type & 32) { /* button mouse emulation vertical */ + //if (unit) { + // if (delta < 0) { + // gui_gameport_axis_change (joy, DIR_UP_BIT, abs (delta), max); + // gui_gameport_axis_change (joy, DIR_DOWN_BIT, 0, max); + // } + // if (delta > 0) { + // gui_gameport_axis_change (joy, DIR_DOWN_BIT, abs (delta), max); + // gui_gameport_axis_change (joy, DIR_UP_BIT, 0, max); + // } + //} else { + // if (delta < 0) { + // gui_gameport_axis_change (joy, DIR_LEFT_BIT, abs (delta), max); + // gui_gameport_axis_change (joy, DIR_RIGHT_BIT, 0, max); + // } + // if (delta > 0) { + // gui_gameport_axis_change (joy, DIR_RIGHT_BIT, abs (delta), max); + // gui_gameport_axis_change (joy, DIR_LEFT_BIT, 0, max); + // } + //} - int speed = currprefs.input_joymouse_speed; + } else if (ie->type & 32) { /* button mouse emulation vertical */ + + int speed = (ie->data & IE_CDTV) ? JOYMOUSE_CDTV : currprefs.input_joymouse_speed; if (state && (ie->data & DIR_UP)) { mouse_delta[joy][1] = -speed; mouse_deltanoreset[joy][1] = 1; - } - else if (state && (ie->data & DIR_DOWN)) { + } else if (state && (ie->data & DIR_DOWN)) { mouse_delta[joy][1] = speed; mouse_deltanoreset[joy][1] = 1; - } - else + } else mouse_deltanoreset[joy][1] = 0; - } - else if (ie->type & 64) { /* button mouse emulation horizontal */ + } else if (ie->type & 64) { /* button mouse emulation horizontal */ - int speed = currprefs.input_joymouse_speed; + int speed = (ie->data & IE_CDTV) ? JOYMOUSE_CDTV : currprefs.input_joymouse_speed; if (state && (ie->data & DIR_LEFT)) { mouse_delta[joy][0] = -speed; mouse_deltanoreset[joy][0] = 1; - } - else if (state && (ie->data & DIR_RIGHT)) { + } else if (state && (ie->data & DIR_RIGHT)) { mouse_delta[joy][0] = speed; mouse_deltanoreset[joy][0] = 1; - } - else + } else mouse_deltanoreset[joy][0] = 0; - } - else if (ie->type & 128) { /* analog joystick / paddle */ + } else if (ie->type & 128) { /* analog joystick / paddle */ -#ifndef INPUTDEVICE_SIMPLE int deadzone = currprefs.input_joymouse_deadzone * max / 100; int unit = ie->data & 0x7f; if (max) { if (state <= deadzone && state >= -deadzone) { state = 0; - } - else if (state < 0) { + } else if (state < 0) { state += deadzone; - } - else { + } else { state -= deadzone; } state = state * max / (max - deadzone); - } - else { + } else { max = 100; relativecount[joy][unit] += state; state = relativecount[joy][unit]; @@ -3030,6 +4441,18 @@ static int handle_input_event(int nr, int state, int max, int autofire) if (ie->data & IE_INVERT) state = -state; + //if (!unit) { + // if (state <= 0) + // gui_gameport_axis_change (joy, DIR_UP_BIT, abs (state), max); + // if (state >= 0) + // gui_gameport_axis_change (joy, DIR_DOWN_BIT, abs (state), max); + //} else { + // if (state <= 0) + // gui_gameport_axis_change (joy, DIR_LEFT_BIT, abs (state), max); + // if (state >= 0) + // gui_gameport_axis_change (joy, DIR_RIGHT_BIT, abs (state), max); + //} + state = state * currprefs.input_analog_joystick_mult / max; state += (128 * currprefs.input_analog_joystick_mult / 100) + currprefs.input_analog_joystick_offset; if (state < 0) @@ -3039,28 +4462,41 @@ static int handle_input_event(int nr, int state, int max, int autofire) joydirpot[joy][unit] = state; mouse_deltanoreset[joy][0] = 1; mouse_deltanoreset[joy][1] = 1; -#endif - } - else { + } else { int left = oleft[joy], right = oright[joy], top = otop[joy], bot = obot[joy]; if (ie->type & 16) { /* button to axis mapping */ if (ie->data & DIR_LEFT) { left = oleft[joy] = state ? 1 : 0; + if (horizclear[joy] && left) { + horizclear[joy] = 0; + right = oright[joy] = 0; + } } if (ie->data & DIR_RIGHT) { right = oright[joy] = state ? 1 : 0; + if (horizclear[joy] && right) { + horizclear[joy] = 0; + left = oleft[joy] = 0; + } } if (ie->data & DIR_UP) { top = otop[joy] = state ? 1 : 0; + if (vertclear[joy] && top) { + vertclear[joy] = 0; + bot = obot[joy] = 0; + } } if (ie->data & DIR_DOWN) { bot = obot[joy] = state ? 1 : 0; + if (vertclear[joy] && bot) { + vertclear[joy] = 0; + top = otop[joy] = 0; + } } - } - else { + } else { /* "normal" joystick axis */ int deadzone = currprefs.input_joystick_deadzone * max / 100; int neg, pos; @@ -3078,8 +4514,7 @@ static int handle_input_event(int nr, int state, int max, int autofire) if (cnt >(mmax + mextra)) cnt = (mmax + mextra); relativecount[joy][unit] = cnt; - } - else { + } else { if (state < deadzone && state > -deadzone) state = 0; neg = state < 0 ? 1 : 0; @@ -3087,15 +4522,31 @@ static int handle_input_event(int nr, int state, int max, int autofire) } if (ie->data & DIR_LEFT) { left = oleft[joy] = neg; + if (horizclear[joy] && left) { + horizclear[joy] = 0; + right = oright[joy] = 0; + } } if (ie->data & DIR_RIGHT) { right = oright[joy] = pos; + if (horizclear[joy] && right) { + horizclear[joy] = 0; + left = oleft[joy] = 0; + } } if (ie->data & DIR_UP) { top = otop[joy] = neg; + if (vertclear[joy] && top) { + vertclear[joy] = 0; + bot = obot[joy] = 0; + } } if (ie->data & DIR_DOWN) { bot = obot[joy] = pos; + if (vertclear[joy] && bot) { + vertclear[joy] = 0; + top = otop[joy] = 0; + } } } mouse_deltanoreset[joy][0] = 1; @@ -3111,6 +4562,11 @@ static int handle_input_event(int nr, int state, int max, int autofire) joydir[joy] |= DIR_DOWN; if (joy == 0 || joy == 1) joymousecounter(joy); + + //gui_gameport_axis_change (joy, DIR_LEFT_BIT, left, 0); + //gui_gameport_axis_change (joy, DIR_RIGHT_BIT, right, 0); + //gui_gameport_axis_change (joy, DIR_UP_BIT, top, 0); + //gui_gameport_axis_change (joy, DIR_DOWN_BIT, bot, 0); } break; case 0: /* ->KEY */ @@ -3120,12 +4576,29 @@ static int handle_input_event(int nr, int state, int max, int autofire) return 1; } +static int handle_input_event_extra(int nr, int state, int max, int flags, int extra) +{ + return handle_input_event2(nr, state, max, flags, extra); +} + +static int handle_input_event(int nr, int state, int max, int flags) +{ + return handle_input_event2(nr, state, max, flags, 0); +} + +int send_input_event (int nr, int state, int max, int autofire) +{ + check_enable(nr); + return handle_input_event(nr, state, max, autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0); +} + static void inputdevice_checkconfig (void) { bool changed = false; for (int i = 0; i < MAX_JPORTS; i++) { if (currprefs.jports[i].id != changed_prefs.jports[i].id || - currprefs.jports[i].mode != changed_prefs.jports[i].mode) + currprefs.jports[i].mode != changed_prefs.jports[i].mode || + _tcscmp(currprefs.jports_custom[i].custom, changed_prefs.jports_custom[i].custom)) changed = true; } @@ -3136,6 +4609,8 @@ static void inputdevice_checkconfig (void) currprefs.input_joystick_deadzone != changed_prefs.input_joystick_deadzone || currprefs.input_joymouse_speed != changed_prefs.input_joymouse_speed || currprefs.input_autofire_linecnt != changed_prefs.input_autofire_linecnt || + currprefs.input_autoswitch != changed_prefs.input_autoswitch || + currprefs.input_device_match_mask != changed_prefs.input_device_match_mask || currprefs.input_mouse_speed != changed_prefs.input_mouse_speed) { currprefs.input_selected_setting = changed_prefs.input_selected_setting; @@ -3145,9 +4620,17 @@ static void inputdevice_checkconfig (void) currprefs.input_joymouse_speed = changed_prefs.input_joymouse_speed; currprefs.input_autofire_linecnt = changed_prefs.input_autofire_linecnt; currprefs.input_mouse_speed = changed_prefs.input_mouse_speed; + currprefs.input_autoswitch = changed_prefs.input_autoswitch; + currprefs.input_device_match_mask = changed_prefs.input_device_match_mask; inputdevice_updateconfig (&changed_prefs, &currprefs); } +#ifndef AMIBERRY + if (currprefs.dongle != changed_prefs.dongle) { + currprefs.dongle = changed_prefs.dongle; + dongle_reset (); + } +#endif } void inputdevice_vsync (void) @@ -3164,12 +4647,20 @@ void inputdevice_vsync (void) inputread = -1; inputdevice_handle_inputcode (); + if (mouseedge_alive > 0) + mouseedge_alive--; + if (mouseedge()) + mouseedge_alive = 10; if (mousehack_alive_cnt > 0) { mousehack_alive_cnt--; + if (mousehack_alive_cnt == 0) + setmouseactive(-1); } else if (mousehack_alive_cnt < 0) { mousehack_alive_cnt++; if (mousehack_alive_cnt == 0) { mousehack_alive_cnt = 100; + setmouseactive(0); + setmouseactive(1); } } inputdevice_checkconfig (); @@ -3177,9 +4668,30 @@ void inputdevice_vsync (void) void inputdevice_reset(void) { + magicmouse_ibase = 0; + magicmouse_gfxbase = 0; mousehack_reset(); if (inputdevice_is_tablet()) mousehack_enable(); + bouncy = 0; + while (delayed_events) { + struct delayed_event *de = delayed_events; + delayed_events = de->next; + xfree (de->event_string); + xfree (de); + } + for (int i = 0; i < 2; i++) { + lastmxy_abs[i][0] = 0; + lastmxy_abs[i][1] = 0; + } + for (int i = 0; i < MAX_JPORTS; i++) { + pc_mouse_buttons[i] = 0; + } + lightpen_trigger2 = 0; + cubo_flag = 0; +#ifndef AMIBERRY + alg_flag &= 1; +#endif } static int getoldport (struct uae_input_device *id) @@ -3199,6 +4711,8 @@ static int getoldport (struct uae_input_device *id) return -1; } +static int inputdevice_joyport_config(struct uae_prefs *p, const TCHAR *value1, const TCHAR *value2, int portnum, int mode, int type, bool candefault); + static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) { int ismouse = 0; @@ -3208,9 +4722,12 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) const TCHAR *name = NULL, *fname = NULL; int otherbuttonpressed = 0; int acc = input_acquired; + const int *customswitch = NULL; if (num >= 4) return 0; + if (!currprefs.input_autoswitch) + return false; if (!target_can_autoswitchdevice()) return 0; @@ -3227,6 +4744,7 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) otherbuttonpressed = 1; } } + customswitch = custom_autoswitch_joy; } if (id == &mice[i]) { ismouse = 1; @@ -3234,6 +4752,7 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) fname = idev[IDTYPE_MOUSE].get_friendlyname (i); newport = num == 0 ? 0 : 1; flags = idev[IDTYPE_MOUSE].get_flags (i); + customswitch = custom_autoswitch_mouse; } } if (!name) { @@ -3259,6 +4778,15 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) return 0; } + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + if (customswitch && customswitch[i] >= 0) { + newslot = customswitch[i]; + name = currprefs.jports_custom[newslot].custom; + fname = name; + break; + } + } + #if 1 if (ismouse) { int nummouse = 0; // count number of non-supermouse mice @@ -3278,6 +4806,13 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) } #endif inputdevice_unacquire (); + //if (fname) { + // if (newslot >= 0) { + // statusline_add_message(STATUSTYPE_INPUT, _T("Port %d: Custom %d"), newport, newslot + 1); + // } else { + // statusline_add_message(STATUSTYPE_INPUT, _T("Port %d: %s"), newport, fname); + // } + //} if (currprefs.input_selected_setting != GAMEPORT_INPUT_SETTINGS && currprefs.jports[newport].id > JPORT_NONE) { // disable old device @@ -3328,8 +4863,8 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) } else { int oldport = getoldport (id); int k, evt; - const struct inputevent *ie, *ie2; + const struct inputevent *ie, *ie2; if (flags) return 0; if (oldport <= 0) { @@ -3384,6 +4919,8 @@ static int switchdevice (struct uae_input_device *id, int num, bool buttonmode) } write_log (_T("inputdevice input change '%s':%d->%d\n"), name, num, newport); inputdevice_unacquire (); + //if (fname) + // statusline_add_message(STATUSTYPE_INPUT, _T("Port %d: %s"), newport, fname); inputdevice_copyconfig (&currprefs, &changed_prefs); inputdevice_validate_jports (&changed_prefs, -1, NULL); inputdevice_copyconfig (&changed_prefs, &currprefs); @@ -3482,6 +5019,98 @@ static uae_u64 getqualmask (uae_u64 *qualmask, struct uae_input_device *id, int return mask; } + +static bool process_custom_event (struct uae_input_device *id, int offset, int state, uae_u64 *qualmask, int autofire, int sub) +{ + int idx, slotoffset, custompos; + TCHAR *custom; + uae_u64 flags, qual; + + if (!id) + return false; + + slotoffset = sub & ~3; + sub &= 3; + flags = id->flags[offset][slotoffset]; + qual = flags & ID_FLAG_QUALIFIER_MASK; + custom = id->custom[offset][slotoffset]; + + for (idx = 1; idx < 4; idx++) { + uae_u64 flags2 = id->flags[offset][slotoffset + idx]; + + // all slots must have same qualifier + if ((flags2 & ID_FLAG_QUALIFIER_MASK) != qual) + break; + // no slot must have autofire + if ((flags2 & ID_FLAG_AUTOFIRE_MASK) || (flags & ID_FLAG_AUTOFIRE_MASK)) + break; + } + // at least slot 0 and 2 must have custom + if (custom == NULL || id->custom[offset][slotoffset + 2] == NULL) + idx = -1; + + if (idx < 4) { + id->flags[offset][slotoffset] &= ~(ID_FLAG_CUSTOMEVENT_TOGGLED1 | ID_FLAG_CUSTOMEVENT_TOGGLED2); + int evt2 = id->eventid[offset][slotoffset + sub]; + uae_u64 flags2 = id->flags[offset][slotoffset + sub]; + if (checkqualifiers (evt2, flags2, qualmask, NULL)) { + custom = id->custom[offset][slotoffset + sub]; + if (state && custom) { + if (autofire) + queue_input_event (-1, custom, 1, 1, currprefs.input_autofire_linecnt, 1); + handle_custom_event (custom, 0); + return true; + } + } + return false; + } + + if (sub != 0) + return false; + + slotoffset = 0; + if (!checkqualifiers (id->eventid[offset][slotoffset], id->flags[offset][slotoffset], qualmask, NULL)) { + slotoffset = 4; + if (!checkqualifiers (id->eventid[offset][slotoffset], id->flags[offset][slotoffset], qualmask, NULL)) + return false; + } + + flags = id->flags[offset][slotoffset]; + custompos = (flags & ID_FLAG_CUSTOMEVENT_TOGGLED1) ? 1 : 0; + custompos |= (flags & ID_FLAG_CUSTOMEVENT_TOGGLED2) ? 2 : 0; + + if (state < 0) { + idx = 0; + custompos = 0; + } else { + if (state > 0) { + if (custompos & 1) + return false; // waiting for release + } else { + if (!(custompos & 1)) + return false; // waiting for press + } + idx = custompos; + custompos++; + } + + queue_input_event (-1, NULL, -1, 0, 0, 1); + + if ((id->flags[offset][slotoffset + idx] & ID_FLAG_QUALIFIER_MASK) == qual) { + custom = id->custom[offset][slotoffset + idx]; + if (autofire) + queue_input_event (-1, custom, 1, 1, currprefs.input_autofire_linecnt, 1); + if (custom) + handle_custom_event (custom, 0); + } + + id->flags[offset][slotoffset] &= ~(ID_FLAG_CUSTOMEVENT_TOGGLED1 | ID_FLAG_CUSTOMEVENT_TOGGLED2); + id->flags[offset][slotoffset] |= (custompos & 1) ? ID_FLAG_CUSTOMEVENT_TOGGLED1 : 0; + id->flags[offset][slotoffset] |= (custompos & 2) ? ID_FLAG_CUSTOMEVENT_TOGGLED2 : 0; + + return true; +} + static void setbuttonstateall (struct uae_input_device *id, struct uae_input_device2 *id2, int button, int buttonstate) { static frame_time_t switchdevice_timeout; @@ -3514,55 +5143,68 @@ static void setbuttonstateall (struct uae_input_device *id, struct uae_input_dev if (button >= ID_BUTTON_TOTAL) return; - if (doit) - { + if (currprefs.input_tablet == TABLET_REAL && mousehack_alive()) { + // mouse driver injects all buttons when tablet mode + if (id == &mice[0]) + doit = false; + } + + if (doit) { getqualmask(qualmask, id, ID_BUTTON_OFFSET + button, &qualonly); - for (i = 0; i < MAX_INPUT_SUB_EVENT; i++) - { + bool didcustom = false; + + for (i = 0; i < MAX_INPUT_SUB_EVENT; i++) { int sub = sublevdir[buttonstate == 0 ? 1 : 0][i]; uae_u64 *flagsp = &id->flags[ID_BUTTON_OFFSET + button][sub]; int evt = id->eventid[ID_BUTTON_OFFSET + button][sub]; + TCHAR *custom = id->custom[ID_BUTTON_OFFSET + button][sub]; uae_u64 flags = flagsp[0]; int autofire = (flags & ID_FLAG_AUTOFIRE) ? 1 : 0; int toggle = (flags & ID_FLAG_TOGGLE) ? 1 : 0; int inverttoggle = (flags & ID_FLAG_INVERTTOGGLE) ? 1 : 0; int invert = (flags & ID_FLAG_INVERT) ? 1 : 0; - int setmode = (flags & ID_FLAG_SET_ONOFF) ? 1 : 0; - int setval = (flags & ID_FLAG_SET_ONOFF_VAL) ? SET_ONOFF_ON_VALUE : SET_ONOFF_OFF_VALUE; + int setmode = (flags & ID_FLAG_SET_ONOFF) ? 1: 0; + int setvalval = (flags & (ID_FLAG_SET_ONOFF_VAL1 | ID_FLAG_SET_ONOFF_VAL2)); + int setval = setvalval == (ID_FLAG_SET_ONOFF_VAL1 | ID_FLAG_SET_ONOFF_VAL2) ? SET_ONOFF_PRESSREL_VALUE : + (setvalval == ID_FLAG_SET_ONOFF_VAL2 ? SET_ONOFF_PRESS_VALUE : (setvalval == ID_FLAG_SET_ONOFF_VAL1 ? SET_ONOFF_ON_VALUE : SET_ONOFF_OFF_VALUE)); int state; - if (buttonstate < 0) + if (buttonstate < 0) { state = buttonstate; - else if (invert) + } else if (invert) { state = buttonstate ? 0 : 1; - else + } else { state = buttonstate; - - if (setmode) - { + } + if (setmode) { if (state || setval == SET_ONOFF_PRESS_VALUE || setval == SET_ONOFF_PRESSREL_VALUE) state = setval | (buttonstate ? 1 : 0); } + if (!state) { + didcustom |= process_custom_event (id, ID_BUTTON_OFFSET + button, state, qualmask, autofire, i); + } + setqualifiers(evt, state > 0); if (qualonly) continue; -#ifndef INPUTDEVICE_SIMPLE if (state < 0) { if (!checkqualifiers (evt, flags, qualmask, NULL)) continue; - handle_input_event (evt, 1, 1, 0); + handle_input_event (evt, 1, 1, HANDLE_IE_FLAG_CANSTOPPLAYBACK); + didcustom |= process_custom_event (id, ID_BUTTON_OFFSET + button, state, qualmask, 0, i); } else if (inverttoggle) { /* pressed = firebutton, not pressed = autofire */ if (state) { - queue_input_event (evt, -1, 0, 0); - handle_input_event (evt, 2, 1, 0); + queue_input_event (evt, NULL, -1, 0, 0, 1); + handle_input_event (evt, 2, 1, HANDLE_IE_FLAG_CANSTOPPLAYBACK); } else { - handle_input_event (evt, 2, 1, autofire); + handle_input_event (evt, 2, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); } + didcustom |= process_custom_event (id, ID_BUTTON_OFFSET + button, state, qualmask, autofire, i); } else if (toggle) { if (!state) continue; @@ -3572,9 +5214,9 @@ static void setbuttonstateall (struct uae_input_device *id, struct uae_input_dev continue; *flagsp ^= ID_FLAG_TOGGLED; int toggled = (*flagsp & ID_FLAG_TOGGLED) ? 2 : 0; - handle_input_event (evt, toggled, 1, autofire); + handle_input_event (evt, toggled, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); + didcustom |= process_custom_event (id, ID_BUTTON_OFFSET + button, toggled, qualmask, autofire, i); } else { -#endif if (!checkqualifiers (evt, flags, qualmask, NULL)) { if (!state && !(flags & ID_FLAG_CANRELEASE)) { if (!invert) @@ -3588,14 +5230,15 @@ static void setbuttonstateall (struct uae_input_device *id, struct uae_input_dev else *flagsp |= ID_FLAG_CANRELEASE; if ((omask ^ nmask) & mask) { - handle_input_event (evt, state, 1, autofire); + handle_input_event (evt, state, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); + if (state) + didcustom |= process_custom_event (id, ID_BUTTON_OFFSET + button, state, qualmask, autofire, i); } -#ifndef INPUTDEVICE_SIMPLE } -#endif } - queue_input_event (-1, -1, 0, 0); + if (!didcustom) + queue_input_event (-1, NULL, -1, 0, 0, 1); } if (id2 && ((omask ^ nmask) & mask)) { @@ -3627,12 +5270,10 @@ static int iscd32 (int ei) static int isparport (int ei) { -#if !defined(INPUTDEVICE_SIMPLE) || defined(AMIBERRY) if (ei > INPUTEVENT_PAR_JOY1_START && ei < INPUTEVENT_PAR_JOY_END) { parport_joystick_enabled = 1; return 1; } -#endif return 0; } @@ -3651,7 +5292,6 @@ static int ismouse (int ei) static int isanalog (int ei) { -#ifndef INPUTDEVICE_SIMPLE if (ei == INPUTEVENT_JOY1_HORIZ_POT || ei == INPUTEVENT_JOY1_HORIZ_POT_INV) { analog_port[0][0] = 1; return 1; @@ -3668,7 +5308,6 @@ static int isanalog (int ei) analog_port[1][1] = 1; return 1; } -#endif return 0; } @@ -3692,7 +5331,22 @@ static int isdigitalbutton (int ei) } return 0; } - + +#ifndef AMIBERRY +static int islightpen (int ei) +{ + if (ei >= INPUTEVENT_LIGHTPEN_HORIZ2 && ei < INPUTEVENT_LIGHTPEN_DOWN2) { + lightpen_enabled2 = true; + } + if (ei >= INPUTEVENT_LIGHTPEN_FIRST && ei < INPUTEVENT_LIGHTPEN_LAST) { + lightpen_enabled = true; + lightpen_port[lightpen_port_number()] = 1; + return 1; + } + return 0; +} +#endif + static void isqualifier (int ei) { } @@ -3703,7 +5357,10 @@ static void check_enable(int ei) isparport(ei); ismouse(ei); isdigitalbutton(ei); +#ifndef AMIBERRY isqualifier(ei); + islightpen(ei); +#endif } static void scanevents (struct uae_prefs *p) @@ -3721,13 +5378,16 @@ static void scanevents (struct uae_prefs *p) for (i = 0; i < NORMAL_JPORTS; i++) { for (j = 0; j < 2; j++) { digital_port[i][j] = 0; -#ifndef INPUTDEVICE_SIMPLE analog_port[i][j] = 0; joydirpot[i][j] = 128 / (312 * 100 / currprefs.input_analog_joystick_mult) + (128 * currprefs.input_analog_joystick_mult / 100) + currprefs.input_analog_joystick_offset; -#endif } } - +#ifndef AMIBERRY + lightpen_enabled = false; + lightpen_enabled2 = false; + if (lightpen_active > 0) + lightpen_active = -1; +#endif for (i = 0; i < MAX_INPUT_DEVICES; i++) { use_joysticks[i] = 0; use_mice[i] = 0; @@ -3741,7 +5401,10 @@ static void scanevents (struct uae_prefs *p) isparport (ei); ismouse (ei); isdigitalbutton (ei); +#ifndef AMIBERRY isqualifier (ei); + islightpen (ei); +#endif if (joysticks[i].eventid[ID_BUTTON_OFFSET + j][k] > 0) use_joysticks[i] = 1; } @@ -3752,10 +5415,14 @@ static void scanevents (struct uae_prefs *p) isparport (ei); ismouse (ei); isdigitalbutton (ei); +#ifndef AMIBERRY isqualifier (ei); + islightpen (ei); +#endif if (mice[i].eventid[ID_BUTTON_OFFSET + j][k] > 0) use_mice[i] = 1; } + } for (j = 0; j < ID_AXIS_TOTAL; j++) { @@ -3767,7 +5434,10 @@ static void scanevents (struct uae_prefs *p) ismouse (ei); isanalog (ei); isdigitalbutton (ei); +#ifndef AMIBERRY isqualifier (ei); + islightpen (ei); +#endif if (ei > 0) use_joysticks[i] = 1; } @@ -3778,7 +5448,10 @@ static void scanevents (struct uae_prefs *p) ismouse (ei); isanalog (ei); isdigitalbutton (ei); +#ifndef AMIBERRY isqualifier (ei); + islightpen (ei); +#endif if (ei > 0) use_mice[i] = 1; } @@ -3798,7 +5471,10 @@ static void scanevents (struct uae_prefs *p) isparport (ei); ismouse (ei); isdigitalbutton (ei); +#ifndef AMIBERRY isqualifier (ei); + islightpen (ei); +#endif if (ei > 0) scancodeused[i][keyboards[i].extra[j]] = ei; } @@ -3817,10 +5493,16 @@ static const int axistable[] = { INPUTEVENT_JOY1_VERT, INPUTEVENT_JOY1_UP, INPUTEVENT_JOY1_DOWN, INPUTEVENT_JOY2_HORIZ, INPUTEVENT_JOY2_LEFT, INPUTEVENT_JOY2_RIGHT, INPUTEVENT_JOY2_VERT, INPUTEVENT_JOY2_UP, INPUTEVENT_JOY2_DOWN, +#ifndef AMIBERRY + INPUTEVENT_LIGHTPEN_HORIZ, INPUTEVENT_LIGHTPEN_LEFT, INPUTEVENT_LIGHTPEN_RIGHT, + INPUTEVENT_LIGHTPEN_VERT, INPUTEVENT_LIGHTPEN_UP, INPUTEVENT_LIGHTPEN_DOWN, +#endif INPUTEVENT_PAR_JOY1_HORIZ, INPUTEVENT_PAR_JOY1_LEFT, INPUTEVENT_PAR_JOY1_RIGHT, INPUTEVENT_PAR_JOY1_VERT, INPUTEVENT_PAR_JOY1_UP, INPUTEVENT_PAR_JOY1_DOWN, INPUTEVENT_PAR_JOY2_HORIZ, INPUTEVENT_PAR_JOY2_LEFT, INPUTEVENT_PAR_JOY2_RIGHT, INPUTEVENT_PAR_JOY2_VERT, INPUTEVENT_PAR_JOY2_UP, INPUTEVENT_PAR_JOY2_DOWN, + INPUTEVENT_MOUSE_CDTV_HORIZ, INPUTEVENT_MOUSE_CDTV_LEFT, INPUTEVENT_MOUSE_CDTV_RIGHT, + INPUTEVENT_MOUSE_CDTV_VERT, INPUTEVENT_MOUSE_CDTV_UP, INPUTEVENT_MOUSE_CDTV_DOWN, -1 }; @@ -3842,20 +5524,20 @@ int intputdevice_compa_get_eventtype (int evt, const int **axistablep) static const int rem_port1[] = { INPUTEVENT_MOUSE1_HORIZ, INPUTEVENT_MOUSE1_VERT, INPUTEVENT_JOY1_HORIZ, INPUTEVENT_JOY1_VERT, -#ifndef INPUTDEVICE_SIMPLE INPUTEVENT_JOY1_HORIZ_POT, INPUTEVENT_JOY1_VERT_POT, -#endif INPUTEVENT_JOY1_FIRE_BUTTON, INPUTEVENT_JOY1_2ND_BUTTON, INPUTEVENT_JOY1_3RD_BUTTON, INPUTEVENT_JOY1_CD32_RED, INPUTEVENT_JOY1_CD32_BLUE, INPUTEVENT_JOY1_CD32_GREEN, INPUTEVENT_JOY1_CD32_YELLOW, INPUTEVENT_JOY1_CD32_RWD, INPUTEVENT_JOY1_CD32_FFW, INPUTEVENT_JOY1_CD32_PLAY, + INPUTEVENT_MOUSE_CDTV_HORIZ, INPUTEVENT_MOUSE_CDTV_VERT, +#ifndef AMIBERRY + INPUTEVENT_LIGHTPEN_HORIZ, INPUTEVENT_LIGHTPEN_VERT, +#endif -1 }; static const int rem_port2[] = { INPUTEVENT_MOUSE2_HORIZ, INPUTEVENT_MOUSE2_VERT, INPUTEVENT_JOY2_HORIZ, INPUTEVENT_JOY2_VERT, -#ifndef INPUTDEVICE_SIMPLE INPUTEVENT_JOY2_HORIZ_POT, INPUTEVENT_JOY2_VERT_POT, -#endif INPUTEVENT_JOY2_FIRE_BUTTON, INPUTEVENT_JOY2_2ND_BUTTON, INPUTEVENT_JOY2_3RD_BUTTON, INPUTEVENT_JOY2_CD32_RED, INPUTEVENT_JOY2_CD32_BLUE, INPUTEVENT_JOY2_CD32_GREEN, INPUTEVENT_JOY2_CD32_YELLOW, INPUTEVENT_JOY2_CD32_RWD, INPUTEVENT_JOY2_CD32_FFW, INPUTEVENT_JOY2_CD32_PLAY, @@ -3937,6 +5619,32 @@ static const int ip_mouse2[] = { INPUTEVENT_JOY2_FIRE_BUTTON, INPUTEVENT_JOY2_2ND_BUTTON, -1 }; +static const int ip_mousecdtv[] = +{ + INPUTEVENT_MOUSE_CDTV_LEFT, INPUTEVENT_MOUSE_CDTV_RIGHT, INPUTEVENT_MOUSE_CDTV_UP, INPUTEVENT_MOUSE_CDTV_DOWN, + INPUTEVENT_JOY1_FIRE_BUTTON, INPUTEVENT_JOY1_2ND_BUTTON, + -1 +}; +static const int ip_mediacdtv[] = +{ + INPUTEVENT_KEY_CDTV_PLAYPAUSE, INPUTEVENT_KEY_CDTV_STOP, INPUTEVENT_KEY_CDTV_PREV, INPUTEVENT_KEY_CDTV_NEXT, + -1 +}; +static const int ip_arcadia[] = { + INPUTEVENT_SPC_ARCADIA_DIAGNOSTICS, INPUTEVENT_SPC_ARCADIA_PLAYER1, INPUTEVENT_SPC_ARCADIA_PLAYER2, + INPUTEVENT_SPC_ARCADIA_COIN1, INPUTEVENT_SPC_ARCADIA_COIN2, + -1 +}; +#ifndef AMIBERRY +static const int ip_lightpen1[] = { + INPUTEVENT_LIGHTPEN_HORIZ, INPUTEVENT_LIGHTPEN_VERT, INPUTEVENT_JOY1_3RD_BUTTON, + -1 +}; +static const int ip_lightpen2[] = { + INPUTEVENT_LIGHTPEN_HORIZ, INPUTEVENT_LIGHTPEN_VERT, INPUTEVENT_JOY2_3RD_BUTTON, + -1 +}; +#endif static const int ip_analog1[] = { INPUTEVENT_JOY1_HORIZ_POT, INPUTEVENT_JOY1_VERT_POT, INPUTEVENT_JOY1_LEFT, INPUTEVENT_JOY1_RIGHT, -1 @@ -3946,6 +5654,10 @@ static const int ip_analog2[] = { -1 }; +static const int ip_arcadiaxa[] = { + -1 +}; + static void checkcompakb (int *kb, const int *srcmap) { int found = 0, avail = 0; @@ -4058,7 +5770,7 @@ static void setcompakb (struct uae_prefs *p, int *kb, const int *srcmap, int ind if (m == 0 || uid->enabled) { for (int l = 0; l < MAX_INPUT_DEVICE_EVENTS; l++) { if (uid->extra[l] == id) { - setcompakbevent(p, uid, l, srcmap[k], index, af); + setcompakbevent(p, uid, l, srcmap[k], index, af, 0); break; } } @@ -4071,7 +5783,9 @@ static void setcompakb (struct uae_prefs *p, int *kb, const int *srcmap, int ind } } -int inputdevice_get_compatibility_input (struct uae_prefs *prefs, int index, int *typelist, int *inputlist, const int **at) +static int inputdevice_get_device_status (int devnum); + +static int inputdevice_get_compatibility_input (struct uae_prefs *prefs, int index, int *typelist, int *inputlist, const int **at) { if (index >= MAX_JPORTS || joymodes[index] < 0) return -1; @@ -4277,6 +5991,7 @@ void inputdevice_compa_prepare_custom (struct uae_prefs *prefs, int index, int n prefs->jports[index].mode = mode; if (removeold) { + prefs->jports_custom[JSEM_GETCUSTOMIDX(index, prefs)].custom[0] = 0; remove_compa_config (prefs, index); remove_custom_config (prefs, index); } @@ -4295,7 +6010,7 @@ static void cleardev (struct uae_input_device *uid, int num) inputdevice_sparecopy (&uid[num], i, 0); for (int j = 0; j < MAX_INPUT_SUB_EVENT; j++) { uid[num].eventid[i][j] = 0; - uid[num].flags[i][j] = 0; + uid[num].flags[i][j] &= ID_FLAG_AUTOFIRE_MASK; xfree (uid[num].custom[i][j]); uid[num].custom[i][j] = NULL; } @@ -4364,8 +6079,15 @@ static void setjoyinputs (struct uae_prefs *prefs, int port) case JSEM_MODE_MOUSE: joyinputs[port] = port ? ip_mouse2 : ip_mouse1; break; +#ifndef AMIBERRY + case JSEM_MODE_LIGHTPEN: + joyinputs[port] = port ? ip_lightpen2 : ip_lightpen1; + break; +#endif + case JSEM_MODE_MOUSE_CDTV: + joyinputs[port] = ip_mousecdtv; + break; } - //write_log (_T("joyinput %d = %p\n"), port, joyinputs[port]); } static void setautofire (struct uae_input_device *uid, int port, int af) @@ -4378,12 +6100,10 @@ static void setautofire (struct uae_input_device *uid, int port, int af) uid->flags[i][j] &= ~ID_FLAG_AUTOFIRE_MASK; if (af >= JPORT_AF_NORMAL) uid->flags[i][j] |= ID_FLAG_AUTOFIRE; -#ifndef INPUTDEVICE_SIMPLE if (af == JPORT_AF_TOGGLE) uid->flags[i][j] |= ID_FLAG_TOGGLE; if (af == JPORT_AF_ALWAYS) uid->flags[i][j] |= ID_FLAG_INVERTTOGGLE; -#endif } } } @@ -4392,6 +6112,13 @@ static void setautofire (struct uae_input_device *uid, int port, int af) static void setautofires (struct uae_prefs *prefs, int port, int af) { +#ifdef RETROPLATFORM + // don't override custom AF autofire mappings + if (rp_isactive ()) + return; +#endif + if (JSEM_ISCUSTOM(port, prefs)) + return; for (int l = 0; l < MAX_INPUT_DEVICES; l++) { setautofire (&joysticks[l], port, af); setautofire (&mice[l], port, af); @@ -4428,15 +6155,23 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) joymodes[i] = JSEM_MODE_WHEELMOUSE; joyinputs[i] = i ? ip_mouse2 : ip_mouse1; break; +#ifndef AMIBERRY + case JSEM_MODE_LIGHTPEN: + joymodes[i] = JSEM_MODE_LIGHTPEN; + joyinputs[i] = i ? ip_lightpen2 : ip_lightpen1; + break; +#endif + case JSEM_MODE_MOUSE_CDTV: + joymodes[i] = JSEM_MODE_MOUSE_CDTV; + joyinputs[i] = ip_mousecdtv; + break; } } else if (jsem_isjoy (i, prefs) >= 0) { switch (mode) { case JSEM_MODE_DEFAULT: case JSEM_MODE_JOYSTICK: -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_GAMEPAD: -#endif case JSEM_MODE_JOYSTICK_CD32: default: { @@ -4444,28 +6179,34 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) if (iscd32) { joymodes[i] = JSEM_MODE_JOYSTICK_CD32; joyinputs[i] = i ? ip_joycd322 : ip_joycd321; -#ifndef INPUTDEVICE_SIMPLE } else if (mode == JSEM_MODE_GAMEPAD) { joymodes[i] = JSEM_MODE_GAMEPAD; joyinputs[i] = i ? ip_joypad2 : ip_joypad1; -#endif } else { joymodes[i] = JSEM_MODE_JOYSTICK; joyinputs[i] = i ? ip_joy2 : ip_joy1; } break; } -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_JOYSTICK_ANALOG: joymodes[i] = JSEM_MODE_JOYSTICK_ANALOG; joyinputs[i] = i ? ip_analog2 : ip_analog1; break; -#endif case JSEM_MODE_MOUSE: case JSEM_MODE_WHEELMOUSE: joymodes[i] = JSEM_MODE_WHEELMOUSE; joyinputs[i] = i ? ip_mouse2 : ip_mouse1; break; +#ifndef AMIBERRY + case JSEM_MODE_LIGHTPEN: + joymodes[i] = JSEM_MODE_LIGHTPEN; + joyinputs[i] = i ? ip_lightpen2 : ip_lightpen1; + break; +#endif + case JSEM_MODE_MOUSE_CDTV: + joymodes[i] = JSEM_MODE_MOUSE_CDTV; + joyinputs[i] = ip_mousecdtv; + break; } } else if (prefs->jports[i].id >= 0) { joymodes[i] = i ? JSEM_MODE_JOYSTICK : JSEM_MODE_WHEELMOUSE; @@ -4474,7 +6215,6 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) } } -#ifndef INPUTDEVICE_SIMPLE for (i = 2; i < MAX_JPORTS; i++) { if (prefs->jports[i].id >= 0 && joymodes[i] <= 0) { if (jsem_isjoy (i, prefs) >= 0) { @@ -4486,7 +6226,6 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) } } } -#endif for (i = 0; i < 2; i++) { int af = prefs->jports[i].autofire; @@ -4504,21 +6243,25 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) input_get_default_mouse (mice, joy, i, af, !gameports, mode != JSEM_MODE_MOUSE, false); joymodes[i] = JSEM_MODE_WHEELMOUSE; break; + case JSEM_MODE_LIGHTPEN: + //input_get_default_lightpen (mice, joy, i, af, !gameports, false); + //joymodes[i] = JSEM_MODE_LIGHTPEN; + break; case JSEM_MODE_JOYSTICK: case JSEM_MODE_GAMEPAD: case JSEM_MODE_JOYSTICK_CD32: input_get_default_joystick (mice, joy, i, af, mode, !gameports, true); joymodes[i] = mode; break; -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_JOYSTICK_ANALOG: input_get_default_joystick_analog (mice, joy, i, af, !gameports, true); joymodes[i] = JSEM_MODE_JOYSTICK_ANALOG; break; -#endif } _tcsncpy (prefs->jports[i].idc.name, idev[IDTYPE_MOUSE].get_friendlyname (joy), MAX_JPORT_NAME - 1); - _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_MOUSE].get_uniquename (joy), MAX_JPORT_NAME - 1); + _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_MOUSE].get_uniquename (joy), MAX_JPORT_CONFIG - 1); + prefs->jports[i].idc.name[MAX_JPORT_NAME - 1] = 0; + prefs->jports[i].idc.configname[MAX_JPORT_CONFIG - 1] = 0; } } } @@ -4535,9 +6278,7 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) { case JSEM_MODE_DEFAULT: case JSEM_MODE_JOYSTICK: -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_GAMEPAD: -#endif case JSEM_MODE_JOYSTICK_CD32: default: { @@ -4545,28 +6286,35 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) input_get_default_joystick (joysticks, joy, i, af, mode, !gameports, false); if (iscd32) joymodes[i] = JSEM_MODE_JOYSTICK_CD32; -#ifndef INPUTDEVICE_SIMPLE else if (mode == JSEM_MODE_GAMEPAD) joymodes[i] = JSEM_MODE_GAMEPAD; -#endif else joymodes[i] = JSEM_MODE_JOYSTICK; break; } -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_JOYSTICK_ANALOG: input_get_default_joystick_analog (joysticks, joy, i, af, !gameports, false); joymodes[i] = JSEM_MODE_JOYSTICK_ANALOG; break; -#endif case JSEM_MODE_MOUSE: case JSEM_MODE_WHEELMOUSE: input_get_default_mouse (joysticks, joy, i, af, !gameports, mode == JSEM_MODE_WHEELMOUSE, true); joymodes[i] = JSEM_MODE_WHEELMOUSE; break; + case JSEM_MODE_LIGHTPEN: + //input_get_default_lightpen (joysticks, joy, i, af, !gameports, true); + //joymodes[i] = JSEM_MODE_LIGHTPEN; + break; + case JSEM_MODE_MOUSE_CDTV: + joymodes[i] = JSEM_MODE_MOUSE_CDTV; + input_get_default_joystick (joysticks, joy, i, af, mode, !gameports, false); + break; + } _tcsncpy (prefs->jports[i].idc.name, idev[IDTYPE_JOYSTICK].get_friendlyname (joy), MAX_JPORT_NAME - 1); - _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_JOYSTICK].get_uniquename (joy), MAX_JPORT_NAME - 1); + _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_JOYSTICK].get_uniquename (joy), MAX_JPORT_CONFIG - 1); + prefs->jports[i].idc.name[MAX_JPORT_NAME - 1] = 0; + prefs->jports[i].idc.configname[MAX_JPORT_CONFIG - 1] = 0; used[joy] = 1; } } @@ -4577,12 +6325,10 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) for (i = KBR_DEFAULT_MAP_FIRST; i <= KBR_DEFAULT_MAP_LAST; i++) { checkcompakb (keyboard_default_kbmaps[i], ip_joy2); checkcompakb (keyboard_default_kbmaps[i], ip_joy1); -#ifndef INPUTDEVICE_SIMPLE checkcompakb (keyboard_default_kbmaps[i], ip_joypad2); checkcompakb (keyboard_default_kbmaps[i], ip_joypad1); checkcompakb (keyboard_default_kbmaps[i], ip_parjoy2); checkcompakb (keyboard_default_kbmaps[i], ip_parjoy1); -#endif checkcompakb (keyboard_default_kbmaps[i], ip_mouse2); checkcompakb (keyboard_default_kbmaps[i], ip_mouse1); } @@ -4603,28 +6349,22 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) if (JSEM_ISNUMPAD (i, prefs)) { if (cd32) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_CD32_NP]; -#ifndef INPUTDEVICE_SIMPLE else if (mode == JSEM_MODE_GAMEPAD) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_NP3]; -#endif else kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_NP]; } else if (JSEM_ISCURSOR (i, prefs)) { if (cd32) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_CD32_CK]; -#ifndef INPUTDEVICE_SIMPLE else if (mode == JSEM_MODE_GAMEPAD) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_CK3]; -#endif else kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_CK]; } else if (JSEM_ISSOMEWHEREELSE (i, prefs)) { if (cd32) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_CD32_SE]; -#ifndef INPUTDEVICE_SIMPLE else if (mode == JSEM_MODE_GAMEPAD) kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_SE3]; -#endif else kb = keyboard_default_kbmaps[KBR_DEFAULT_MAP_SE]; } @@ -4632,19 +6372,15 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) switch (mode) { case JSEM_MODE_JOYSTICK: -#ifndef INPUTDEVICE_SIMPLE case JSEM_MODE_GAMEPAD: -#endif case JSEM_MODE_JOYSTICK_CD32: case JSEM_MODE_DEFAULT: if (cd32) { setcompakb (prefs, kb, i ? ip_joycd322 : ip_joycd321, i, af); joymodes[i] = JSEM_MODE_JOYSTICK_CD32; -#ifndef INPUTDEVICE_SIMPLE } else if (mode == JSEM_MODE_GAMEPAD) { setcompakb (prefs, kb, i ? ip_joypad2 : ip_joypad1, i, af); joymodes[i] = JSEM_MODE_GAMEPAD; -#endif } else { setcompakb (prefs, kb, i ? ip_joy2 : ip_joy1, i, af); joymodes[i] = JSEM_MODE_JOYSTICK; @@ -4661,8 +6397,15 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) } } } +#ifndef AMIBERRY + if (arcadia_bios) { + setcompakb (prefs, keyboard_default_kbmaps[KBR_DEFAULT_MAP_ARCADIA], ip_arcadia, 0, 0); + } +#endif + if (0 && currprefs.cs_cdtvcd) { + setcompakb (prefs, keyboard_default_kbmaps[KBR_DEFAULT_MAP_CDTV], ip_mediacdtv, 0, 0); + } -//#ifndef INPUTDEVICE_SIMPLE // parport for (i = 2; i < MAX_JPORTS; i++) { int af = prefs->jports[i].autofire; @@ -4673,7 +6416,9 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) cleardev (joysticks, joy); input_get_default_joystick (joysticks, joy, i, af, 0, !gameports, false); _tcsncpy (prefs->jports[i].idc.name, idev[IDTYPE_JOYSTICK].get_friendlyname (joy), MAX_JPORT_NAME - 1); - _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_JOYSTICK].get_uniquename (joy), MAX_JPORT_NAME - 1); + _tcsncpy (prefs->jports[i].idc.configname, idev[IDTYPE_JOYSTICK].get_uniquename (joy), MAX_JPORT_CONFIG - 1); + prefs->jports[i].idc.name[MAX_JPORT_NAME - 1] = 0; + prefs->jports[i].idc.configname[MAX_JPORT_CONFIG - 1] = 0; used[joy] = 1; joymodes[i] = JSEM_MODE_JOYSTICK; } @@ -4698,9 +6443,11 @@ static void compatibility_copy (struct uae_prefs *prefs, bool gameports) } } } -//#endif for (i = 0; i < MAX_JPORTS; i++) { + if (JSEM_ISCUSTOM(i, prefs)) { + inputdevice_parse_jport_custom(prefs, prefs->jports[i].id - JSEM_CUSTOM, i, NULL); + } if (gameports) setautofires (prefs, i, prefs->jports[i].autofire); } @@ -4730,9 +6477,10 @@ static void disableifempty (struct uae_prefs *prefs) if (!input_get_default_keyboard(l)) disableifempty2 (&keyboards[l]); } + prefs->internalevent_settings[0]->enabled = true; } -static void matchdevices (struct inputdevice_functions *inf, struct uae_input_device *uid) +static void matchdevices(struct uae_prefs *p, struct inputdevice_functions *inf, struct uae_input_device *uid, int match_mask) { int i, j; @@ -4750,8 +6498,16 @@ static void matchdevices (struct inputdevice_functions *inf, struct uae_input_de TCHAR *p1 ,*p2; TCHAR *bname1 = uid[j].name; - if (fullmatch && (!bname1 || aname1)) + if (fullmatch) { + if (!bname1 || aname1) + continue; + if (!(match_mask & INPUT_MATCH_BOTH)) + continue; + } else { + if (!(match_mask & INPUT_MATCH_CONFIG_NAME_ONLY)) continue; + } + _tcscpy (bname, uid[j].configname); _tcscpy (bname2, aname2); // strip possible local guid part @@ -4770,7 +6526,7 @@ static void matchdevices (struct inputdevice_functions *inf, struct uae_input_de if (bname[0] && !_tcscmp (bname2, bname)) matched = true; } - if (matched && fullmatch && _tcscmp(aname1, bname1) != 0) + if (matched && fullmatch && aname1 && bname1 && _tcscmp(aname1, bname1) != 0) matched = false; if (matched) { if (match >= 0) @@ -4787,7 +6543,7 @@ static void matchdevices (struct inputdevice_functions *inf, struct uae_input_de if (match == -2) { for (j = 0; j < MAX_INPUT_DEVICES; j++) { TCHAR *bname2 = uid[j].configname; - if (aname2 && bname2 && !_tcscmp (aname2, bname2)) { + if (aname2 && bname2 && (match_mask & INPUT_MATCH_CONFIG_NAME_ONLY) && !_tcscmp (aname2, bname2)) { match = j; break; } @@ -4797,7 +6553,7 @@ static void matchdevices (struct inputdevice_functions *inf, struct uae_input_de // no match, try friendly names only for (j = 0; j < MAX_INPUT_DEVICES; j++) { TCHAR *bname1 = uid[j].name; - if (aname1 && bname1 && !_tcscmp (aname1, bname1)) { + if (aname1 && bname1 && (match_mask & INPUT_MATCH_FRIENDLY_NAME_ONLY) && !_tcscmp (aname1, bname1)) { match = j; break; } @@ -4830,12 +6586,14 @@ static void matchdevices_all (struct uae_prefs *prefs) { int i; for (i = 0; i < MAX_INPUT_SETTINGS; i++) { - matchdevices (&idev[IDTYPE_MOUSE], prefs->mouse_settings[i]); - matchdevices (&idev[IDTYPE_JOYSTICK], prefs->joystick_settings[i]); - matchdevices (&idev[IDTYPE_KEYBOARD], prefs->keyboard_settings[i]); + matchdevices(prefs, &idev[IDTYPE_MOUSE], prefs->mouse_settings[i], prefs->input_device_match_mask); + matchdevices(prefs, &idev[IDTYPE_JOYSTICK], prefs->joystick_settings[i], prefs->input_device_match_mask); + matchdevices(prefs, &idev[IDTYPE_KEYBOARD], prefs->keyboard_settings[i], INPUT_MATCH_ALL); } } +static bool inputdevice_get_eventname (const struct inputevent *ie, TCHAR *out); + bool inputdevice_set_gameports_mapping (struct uae_prefs *prefs, int devnum, int num, int evtnum, uae_u64 flags, int port, int input_selected_setting) { TCHAR name[256]; @@ -4910,6 +6668,10 @@ static void resetinput (void) mouse_deltanoreset[i][2] = 0; mouse_delta[i][2] = 0; } + for (int i = 0; i < 2; i++) { + lightpen_delta[i][0] = lightpen_delta[i][1] = 0; + lightpen_deltanoreset[i][0] = lightpen_deltanoreset[i][1] = 0; + } memset (keybuf, 0, sizeof keybuf); for (int i = 0; i < INPUT_QUEUE_SIZE; i++) input_queue[i].linecnt = input_queue[i].nextlinecnt = -1; @@ -4918,16 +6680,26 @@ static void resetinput (void) sublevdir[0][i] = i; sublevdir[1][i] = MAX_INPUT_SUB_EVENT - i - 1; } + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + custom_autoswitch_joy[i] = -1; + custom_autoswitch_mouse[i] = -1; + } } -void inputdevice_copyjports(struct uae_prefs *srcprefs, struct uae_prefs *dstprefs) +static void inputdevice_copyjports(struct uae_prefs *srcprefs, struct uae_prefs *dstprefs) { for (int i = 0; i < MAX_JPORTS; i++) { copyjport(srcprefs, dstprefs, i); } + if (srcprefs) { + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + _tcscpy(dstprefs->jports_custom[i].custom, srcprefs->jports_custom[i].custom); + } + } + } -void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_prefs *dstprefs) +static void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_prefs *dstprefs) { keyboard_default = keyboard_default_table[currprefs.input_keyboard_type]; @@ -4937,6 +6709,7 @@ void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_p joysticks = dstprefs->joystick_settings[dstprefs->input_selected_setting]; mice = dstprefs->mouse_settings[dstprefs->input_selected_setting]; keyboards = dstprefs->keyboard_settings[dstprefs->input_selected_setting]; + internalevents = dstprefs->internalevent_settings[dstprefs->input_selected_setting]; matchdevices_all (dstprefs); @@ -4948,6 +6721,7 @@ void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_p joysticks = dstprefs->joystick_settings[GAMEPORT_INPUT_SETTINGS]; mice = dstprefs->mouse_settings[GAMEPORT_INPUT_SETTINGS]; keyboards = dstprefs->keyboard_settings[GAMEPORT_INPUT_SETTINGS]; + internalevents = dstprefs->internalevent_settings[GAMEPORT_INPUT_SETTINGS]; dstprefs->input_selected_setting = GAMEPORT_INPUT_SETTINGS; for (int i = 0; i < MAX_INPUT_SETTINGS; i++) { @@ -4955,6 +6729,10 @@ void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_p mice[i].enabled = 0; } + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + inputdevice_parse_jport_custom(dstprefs, i, -1, NULL); + } + compatibility_copy (dstprefs, true); dstprefs->input_selected_setting = input_selected_setting; @@ -4962,6 +6740,7 @@ void inputdevice_updateconfig_internal (struct uae_prefs *srcprefs, struct uae_p joysticks = dstprefs->joystick_settings[dstprefs->input_selected_setting]; mice = dstprefs->mouse_settings[dstprefs->input_selected_setting]; keyboards = dstprefs->keyboard_settings[dstprefs->input_selected_setting]; + internalevents = dstprefs->internalevent_settings[dstprefs->input_selected_setting]; if (dstprefs->input_selected_setting != GAMEPORT_INPUT_SETTINGS) { compatibility_copy (dstprefs, false); @@ -4986,14 +6765,24 @@ void inputdevice_updateconfig (struct uae_prefs *srcprefs, struct uae_prefs *dst for (int i = 0; i < MAX_JPORTS; i++) { inputdevice_store_used_device(&dstprefs->jports[i], i, false); } + +#ifdef RETROPLATFORM + rp_input_change (0); + rp_input_change (1); + rp_input_change (2); + rp_input_change (3); + for (int i = 0; i < MAX_JPORTS; i++) + rp_update_gameport (i, -1, 0); +#endif } -#ifndef INPUTDEVICE_SIMPLE +static int inputdevice_get_device_index (int devnum); + /* called when devices get inserted or removed * store old devices temporarily, enumerate all devices * restore old devices back (order may have changed) */ -void inputdevice_devicechange (struct uae_prefs *prefs) +bool inputdevice_devicechange (struct uae_prefs *prefs) { int acc = input_acquired; int i, idx; @@ -5002,6 +6791,7 @@ void inputdevice_devicechange (struct uae_prefs *prefs) int jportskb[MAX_JPORTS], jportscustom[MAX_JPORTS]; int jportsmode[MAX_JPORTS]; int jportid[MAX_JPORTS], jportaf[MAX_JPORTS]; + bool changed = false; for (i = 0; i < MAX_JPORTS; i++) { jportskb[i] = -1; @@ -5040,8 +6830,8 @@ void inputdevice_devicechange (struct uae_prefs *prefs) struct inputdevice_functions *inf = &idev[j]; dev_nums[j] = inf->get_num(); for (i = 0; i < dev_nums[j]; i++) { - TCHAR *un = inf->get_uniquename(i); - TCHAR *fn = inf->get_friendlyname(i); + const TCHAR *un = inf->get_uniquename(i); + const TCHAR *fn = inf->get_friendlyname(i); _tcscpy(devcfg[i][j].name, fn); _tcscpy(devcfg[i][j].configname, un); } @@ -5054,23 +6844,25 @@ void inputdevice_devicechange (struct uae_prefs *prefs) idev[IDTYPE_JOYSTICK].init (); idev[IDTYPE_MOUSE].init (); idev[IDTYPE_KEYBOARD].init (); - matchdevices (&idev[IDTYPE_MOUSE], mice); - matchdevices (&idev[IDTYPE_JOYSTICK], joysticks); - matchdevices (&idev[IDTYPE_KEYBOARD], keyboards); + matchdevices (prefs, &idev[IDTYPE_MOUSE], mice, prefs->input_device_match_mask); + matchdevices (prefs, &idev[IDTYPE_JOYSTICK], joysticks, prefs->input_device_match_mask); + matchdevices (prefs, &idev[IDTYPE_KEYBOARD], keyboards, INPUT_MATCH_ALL); + + write_log(_T("Checking for inserted/removed devices..\n")); // find out which one was removed or inserted for (int j = 0; j <= IDTYPE_KEYBOARD; j++) { struct inputdevice_functions *inf = &idev[j]; int num = inf->get_num(); - bool df[MAX_INPUT_DEVICES]; + bool df[MAX_INPUT_DEVICES] = { 0 }; for (i = 0; i < MAX_INPUT_DEVICES; i++) { TCHAR *fn2 = devcfg[i][j].name; TCHAR *un2 = devcfg[i][j].configname; - df[i] = false; if (fn2[0] && un2[0]) { for (int k = 0; k < num; k++) { - TCHAR *un = inf->get_uniquename(k); - TCHAR *fn = inf->get_friendlyname(k); + const TCHAR *un = inf->get_uniquename(k); + const TCHAR *fn = inf->get_friendlyname(k); + // device not removed or inserted if (!_tcscmp(fn2, fn) && !_tcscmp(un2, un)) { devcfg[i][j].name[0] = 0; devcfg[i][j].configname[0] = 0; @@ -5083,13 +6875,18 @@ void inputdevice_devicechange (struct uae_prefs *prefs) if (devcfg[i][j].name[0]) { write_log(_T("REMOVED: %s (%s)\n"), devcfg[i][j].name, devcfg[i][j].configname); inputdevice_store_unplugged_port(prefs, &devcfg[i][j]); + changed = true; } - if (i < num && df[i] == false) { + } + for (i = 0; i < num; i++) { + if (df[i] == false) { struct inputdevconfig idc; + struct stored_jport *sjp; _tcscpy(idc.configname, inf->get_uniquename(i)); _tcscpy(idc.name, inf->get_friendlyname(i)); write_log(_T("INSERTED: %s (%s)\n"), idc.name, idc.configname); - int portnum = inputdevice_get_unplugged_device(&idc); + changed = true; + int portnum = inputdevice_get_unplugged_device(&idc, &sjp); if (portnum >= 0) { write_log(_T("Inserting to port %d\n"), portnum); jportscustom[i] = -1; @@ -5097,6 +6894,8 @@ void inputdevice_devicechange (struct uae_prefs *prefs) xfree(jports_configname[portnum]); jports_name[portnum] = my_strdup(idc.name); jports_configname[portnum] = my_strdup(idc.configname); + jportaf[portnum] = sjp->jp.autofire; + jportsmode[portnum] = sjp->jp.mode; } else { write_log(_T("Not inserted to any port\n")); } @@ -5109,13 +6908,14 @@ void inputdevice_devicechange (struct uae_prefs *prefs) freejport (prefs, i); fixedports[i] = false; } + for (i = 0; i < MAX_JPORTS; i++) { bool found = true; if (jportscustom[i] >= 0) { TCHAR tmp[10]; _stprintf(tmp, _T("custom%d"), jportscustom[i]); found = inputdevice_joyport_config(prefs, tmp, NULL, i, jportsmode[i], 0, true) != 0; - } else if (jports_name[i][0] || jports_configname[i][0]) { + } else if ((jports_name[i] && jports_name[i][0]) || (jports_configname[i] && jports_configname[i][0])) { if (!inputdevice_joyport_config (prefs, jports_name[i], jports_configname[i], i, jportsmode[i], 1, true)) { found = inputdevice_joyport_config (prefs, jports_name[i], NULL, i, jportsmode[i], 1, true) != 0; } @@ -5135,13 +6935,22 @@ void inputdevice_devicechange (struct uae_prefs *prefs) inputdevice_validate_jports(prefs, i, fixedports); } + write_log(_T("Input remapping done. Changed=%d.\n"), changed); + + if (!changed) + return false; + if (prefs == &changed_prefs) inputdevice_copyconfig (&changed_prefs, &currprefs); if (acc) inputdevice_acquire (TRUE); - set_config_changed (); -} +#ifdef RETROPLATFORM + rp_enumdevices (); #endif + set_config_changed (); + return true; +} + // set default prefs to all input configuration settings void inputdevice_default_prefs(struct uae_prefs *p) @@ -5162,6 +6971,8 @@ void inputdevice_default_prefs(struct uae_prefs *p) p->input_mouse_speed = 100; p->input_autofire_linecnt = 0; //8 * 312; // Disable Autofire by default p->input_keyboard_type = 0; + p->input_autoswitch = true; + p->input_device_match_mask = -1; keyboard_default = keyboard_default_table[p->input_keyboard_type]; inputdevice_default_kb_all(p); } @@ -5181,6 +6992,29 @@ int inputdevice_iskeymapped (int keyboard, int scancode) return scancodeused[keyboard][scancode]; } +int inputdevice_synccapslock (int oldcaps, int *capstable) +{ + struct uae_input_device *na = &keyboards[0]; + int j, i; + + if (!keyboards) + return -1; + for (j = 0; na->extra[j]; j++) { + if (na->extra[j] == INPUTEVENT_KEY_CAPS_LOCK) { + for (i = 0; capstable[i]; i += 2) { + if (na->extra[j] == capstable[i]) { + if (oldcaps != capstable[i + 1]) { + oldcaps = capstable[i + 1]; + inputdevice_translatekeycode (0, capstable[i], oldcaps ? -1 : 0, false); + } + return i; + } + } + } + } + return -1; +} + static void rqualifiers (uae_u64 flags, bool release) { uae_u64 mask = ID_FLAG_QUALIFIER1 << 1; @@ -5214,11 +7048,12 @@ static void rqualifiers (uae_u64 flags, bool release) } } -static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keystate, bool qualifiercheckonly) +static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keystate, bool qualifiercheckonly, bool ignorecanrelease) { struct uae_input_device *na = &keyboards[keyboard]; int j, k; int handled = 0; + bool didcustom = false; if (!keyboards || scancode < 0) return handled; @@ -5241,7 +7076,9 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst int inverttoggle = (flags & ID_FLAG_INVERTTOGGLE) ? 1 : 0; int invert = (flags & ID_FLAG_INVERT) ? 1 : 0; int setmode = (flags & ID_FLAG_SET_ONOFF) ? 1: 0; - int setval = (flags & ID_FLAG_SET_ONOFF_VAL) ? SET_ONOFF_ON_VALUE : SET_ONOFF_OFF_VALUE; + int setvalval = (flags & (ID_FLAG_SET_ONOFF_VAL1 | ID_FLAG_SET_ONOFF_VAL2)); + int setval = setvalval == (ID_FLAG_SET_ONOFF_VAL1 | ID_FLAG_SET_ONOFF_VAL2) ? SET_ONOFF_PRESSREL_VALUE : + (setvalval == ID_FLAG_SET_ONOFF_VAL2 ? SET_ONOFF_PRESS_VALUE : (setvalval == ID_FLAG_SET_ONOFF_VAL1 ? SET_ONOFF_ON_VALUE : SET_ONOFF_OFF_VALUE)); int toggled; int state; @@ -5253,8 +7090,8 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst state = keystate; } if (setmode) { - if (state) - state = setval; + if (state || setval == SET_ONOFF_PRESS_VALUE || setval == SET_ONOFF_PRESSREL_VALUE) + state = setval | (keystate ? 1 : 0); } setqualifiers (evt, state > 0); @@ -5262,10 +7099,18 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst if (qualifiercheckonly) { if (!state && (flags & ID_FLAG_CANRELEASE)) { *flagsp &= ~ID_FLAG_CANRELEASE; - handle_input_event (evt, state, 1, autofire); + handle_input_event (evt, state, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); + if (k == 0) { + process_custom_event (na, j, state, qualmask, autofire, k); + } } continue; } + + if (!state) { + didcustom |= process_custom_event (na, j, state, qualmask, autofire, k); + } + // if evt == caps and scan == caps: sync with native caps led if (evt == INPUTEVENT_KEY_CAPS_LOCK) { int v; @@ -5276,21 +7121,20 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst continue; if (v > 0) toggle = 0; - } - else if (state < 0) { + } else if (state < 0) { // it was caps lock resync, ignore, not mapped to caps continue; } -#ifndef INPUTDEVICE_SIMPLE if (inverttoggle) { na->flags[j][sublevdir[state == 0 ? 1 : 0][k]] &= ~ID_FLAG_TOGGLED; if (state) { - queue_input_event (evt, -1, 0, 0); - handled |= handle_input_event (evt, 2, 1, 0); + queue_input_event (evt, NULL, -1, 0, 0, 1); + handled |= handle_input_event (evt, 2, 1, HANDLE_IE_FLAG_CANSTOPPLAYBACK); } else { - handled |= handle_input_event (evt, 2, 1, autofire); + handled |= handle_input_event (evt, 2, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); } + didcustom |= process_custom_event (na, j, state, qualmask, autofire, k); } else if (toggle) { if (!state) continue; @@ -5298,9 +7142,11 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst continue; *flagsp ^= ID_FLAG_TOGGLED; toggled = (*flagsp & ID_FLAG_TOGGLED) ? 2 : 0; - handled |= handle_input_event (evt, toggled, 1, autofire); + handled |= handle_input_event (evt, toggled, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); + if (k == 0) { + didcustom |= process_custom_event (na, j, state, qualmask, autofire, k); + } } else { -#endif rqualifiers (flags, state ? true : false); if (!checkqualifiers (evt, flags, qualmask, na->eventid[j])) { if (!state && !(flags & ID_FLAG_CANRELEASE)) { @@ -5315,16 +7161,18 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst if (!invert) *flagsp |= ID_FLAG_CANRELEASE; } else { + if (ignorecanrelease) + flags |= ID_FLAG_CANRELEASE; if (!(flags & ID_FLAG_CANRELEASE) && !invert) continue; *flagsp &= ~ID_FLAG_CANRELEASE; } - handled |= handle_input_event (evt, state, 1, autofire); -#ifndef INPUTDEVICE_SIMPLE + handled |= handle_input_event (evt, state, 1, (autofire ? HANDLE_IE_FLAG_AUTOFIRE : 0) | HANDLE_IE_FLAG_CANSTOPPLAYBACK); + didcustom |= process_custom_event (na, j, state, qualmask, autofire, k); } -#endif } - queue_input_event (-1, -1, 0, 0); + if (!didcustom) + queue_input_event (-1, NULL, -1, 0, 0, 1); return handled; } j++; @@ -5332,22 +7180,123 @@ static int inputdevice_translatekeycode_2 (int keyboard, int scancode, int keyst return handled; } +#define IECODE_UP_PREFIX 0x80 +#define RAW_STEALTH 0x68 +#define STEALTHF_E0KEY 0x08 +#define STEALTHF_UPSTROKE 0x04 +#define STEALTHF_SPECIAL 0x02 +#define STEALTHF_E1KEY 0x01 + +static void sendmmcodes (int code, int newstate) +{ + uae_u8 b; + + b = RAW_STEALTH | IECODE_UP_PREFIX; + record_key (((b << 1) | (b >> 7)) & 0xff); + b = IECODE_UP_PREFIX; + if ((code >> 8) == 0x01) + b |= STEALTHF_E0KEY; + if ((code >> 8) == 0x02) + b |= STEALTHF_E1KEY; + if (!newstate) + b |= STEALTHF_UPSTROKE; + record_key(((b << 1) | (b >> 7)) & 0xff); + b = ((code >> 4) & 0x0f) | IECODE_UP_PREFIX; + record_key(((b << 1) | (b >> 7)) & 0xff); + b = (code & 0x0f) | IECODE_UP_PREFIX; + record_key(((b << 1) | (b >> 7)) & 0xff); +} + // main keyboard press/release entry point -int inputdevice_translatekeycode (int keyboard, int scancode, int state) +int inputdevice_translatekeycode (int keyboard, int scancode, int state, bool alwaysrelease) { // if not default keyboard and all events are empty: use default keyboard if (!input_get_default_keyboard(keyboard) && isemptykey(keyboard, scancode)) { keyboard = input_get_default_keyboard(-1); } - if (inputdevice_translatekeycode_2 (keyboard, scancode, state, false)) + if (inputdevice_translatekeycode_2 (keyboard, scancode, state, false, alwaysrelease)) return 1; + if (currprefs.mmkeyboard && scancode > 0) { + sendmmcodes (scancode, state); + return 1; + } return 0; } void inputdevice_checkqualifierkeycode (int keyboard, int scancode, int state) { - inputdevice_translatekeycode_2 (keyboard, scancode, state, true); + inputdevice_translatekeycode_2 (keyboard, scancode, state, true, false); } +static const TCHAR *internaleventlabels[] = { + _T("CPU reset"), + _T("Keyboard reset"), + NULL +}; +static int init_int (void) +{ + return 1; +} +static void close_int (void) +{ +} +static int acquire_int (int num, int flags) +{ + return 1; +} +static void unacquire_int (int num) +{ +} +static void read_int (void) +{ +} +static int get_int_num (void) +{ + return 1; +} +static const TCHAR *get_int_friendlyname (int num) +{ + return my_strdup(_T("Internal events")); +} +static const TCHAR *get_int_uniquename (int num) +{ + return my_strdup(_T("INTERNALEVENTS1")); +} +static int get_int_widget_num (int num) +{ + int i; + for (i = 0; internaleventlabels[i]; i++); + return i; +} +static int get_int_widget_type (int kb, int num, TCHAR *name, uae_u32 *code) +{ + if (code) + *code = num; + if (name) + _tcscpy (name, internaleventlabels[num]); + return IDEV_WIDGET_BUTTON; +} +static int get_int_widget_first (int kb, int type) +{ + return 0; +} +static int get_int_flags (int num) +{ + return 0; +} +static struct inputdevice_functions inputdevicefunc_internalevent = { + init_int, close_int, acquire_int, unacquire_int, read_int, + get_int_num, get_int_friendlyname, get_int_uniquename, + get_int_widget_num, get_int_widget_type, + get_int_widget_first, + get_int_flags +}; + +void send_internalevent (int eventid) +{ + setbuttonstateall (&internalevents[0], NULL, eventid, -1); +} + + void inputdevice_init (void) { idev[IDTYPE_JOYSTICK] = inputdevicefunc_joystick; @@ -5356,6 +7305,8 @@ void inputdevice_init (void) idev[IDTYPE_MOUSE].init (); idev[IDTYPE_KEYBOARD] = inputdevicefunc_keyboard; idev[IDTYPE_KEYBOARD].init (); + idev[IDTYPE_INTERNALEVENT] = inputdevicefunc_internalevent; + idev[IDTYPE_INTERNALEVENT].init (); } void inputdevice_close (void) @@ -5363,6 +7314,10 @@ void inputdevice_close (void) idev[IDTYPE_JOYSTICK].close (); idev[IDTYPE_MOUSE].close (); idev[IDTYPE_KEYBOARD].close (); + idev[IDTYPE_INTERNALEVENT].close (); +#ifndef AMIBERRY + inprec_close (true); +#endif } static struct uae_input_device *get_uid (const struct inputdevice_functions *id, int devnum) @@ -5374,6 +7329,8 @@ static struct uae_input_device *get_uid (const struct inputdevice_functions *id, uid = &mice[devnum]; } else if (id == &idev[IDTYPE_KEYBOARD]) { uid = &keyboards[devnum]; + } else if (id == &idev[IDTYPE_INTERNALEVENT]) { + uid = &internalevents[devnum]; } return uid; } @@ -5455,6 +7412,7 @@ static int put_event_data (const struct inputdevice_functions *id, int devnum, i uid->flags[i][sub] = flags; uid->port[i][sub] = port; xfree (uid->custom[i][sub]); + uid->custom[i][sub] = custom && _tcslen (custom) > 0 ? stripstrdup (custom) : NULL; ret = i; } else if (type == IDEV_WIDGET_AXIS) { i = num - id->get_widget_first (devnum, type) + ID_AXIS_OFFSET; @@ -5462,6 +7420,7 @@ static int put_event_data (const struct inputdevice_functions *id, int devnum, i uid->flags[i][sub] = flags; uid->port[i][sub] = port; xfree (uid->custom[i][sub]); + uid->custom[i][sub] = custom && _tcslen (custom) > 0 ? stripstrdup (custom) : NULL; ret = i; } else if (type == IDEV_WIDGET_KEY) { i = num - id->get_widget_first (devnum, type); @@ -5469,6 +7428,7 @@ static int put_event_data (const struct inputdevice_functions *id, int devnum, i uid->flags[i][sub] = flags; uid->port[i][sub] = port; xfree (uid->custom[i][sub]); + uid->custom[i][sub] = custom && _tcslen (custom) > 0 ? stripstrdup (custom) : NULL; ret = i; } if (ret < 0) @@ -5495,7 +7455,7 @@ static int is_event_used (const struct inputdevice_functions *id, int devnum, in } // device based index from global device index -int inputdevice_get_device_index (int devnum) +static int inputdevice_get_device_index (int devnum) { int jcnt = idev[IDTYPE_JOYSTICK].get_num (); int mcnt = idev[IDTYPE_MOUSE].get_num (); @@ -5507,6 +7467,8 @@ int inputdevice_get_device_index (int devnum) return devnum - jcnt; else if (devnum < jcnt + mcnt + kcnt) return devnum - (jcnt + mcnt); + else if (devnum < jcnt + mcnt + kcnt + INTERNALEVENT_COUNT) + return devnum - (jcnt + mcnt + kcnt); return -1; } @@ -5565,7 +7527,7 @@ int inputdevice_get_widget_num (int devnum) } // return name of event, do not use ie->name directly -bool inputdevice_get_eventname (const struct inputevent *ie, TCHAR *out) +static bool inputdevice_get_eventname (const struct inputevent *ie, TCHAR *out) { if (!out) return false; @@ -5656,26 +7618,24 @@ int inputdevice_get_mapping (int devnum, int num, uae_u64 *pflags, int *pport, T _tcscpy (custom, customp); if (flag & ID_FLAG_AUTOFIRE) flags |= IDEV_MAPPED_AUTOFIRE_SET; -#ifndef INPUTDEVICE_SIMPLE if (flag & ID_FLAG_TOGGLE) flags |= IDEV_MAPPED_TOGGLE; if (flag & ID_FLAG_INVERTTOGGLE) flags |= IDEV_MAPPED_INVERTTOGGLE; -#endif if (flag & ID_FLAG_INVERT) flags |= IDEV_MAPPED_INVERT; if (flag & ID_FLAG_GAMEPORTSCUSTOM1) flags |= IDEV_MAPPED_GAMEPORTSCUSTOM1; -#ifndef INPUTDEVICE_SIMPLE if (flag & ID_FLAG_GAMEPORTSCUSTOM2) flags |= IDEV_MAPPED_GAMEPORTSCUSTOM2; -#endif if (flag & ID_FLAG_QUALIFIER_MASK) flags |= flag & ID_FLAG_QUALIFIER_MASK; if (flag & ID_FLAG_SET_ONOFF) flags |= IDEV_MAPPED_SET_ONOFF; - if (flag & ID_FLAG_SET_ONOFF_VAL) - flags |= IDEV_MAPPED_SET_ONOFF_VAL; + if (flag & ID_FLAG_SET_ONOFF_VAL1) + flags |= IDEV_MAPPED_SET_ONOFF_VAL1; + if (flag & ID_FLAG_SET_ONOFF_VAL2) + flags |= IDEV_MAPPED_SET_ONOFF_VAL2; if (pflags) *pflags = flags; if (pport) @@ -5725,21 +7685,18 @@ int inputdevice_set_mapping (int devnum, int num, const TCHAR *name, TCHAR *cust flag &= ~(ID_FLAG_AUTOFIRE_MASK | ID_FLAG_GAMEPORTSCUSTOM_MASK | IDEV_MAPPED_QUALIFIER_MASK | ID_FLAG_INVERT); if (amask & AM_AF) { flag |= (flags & IDEV_MAPPED_AUTOFIRE_SET) ? ID_FLAG_AUTOFIRE : 0; -#ifndef INPUTDEVICE_SIMPLE flag |= (flags & IDEV_MAPPED_TOGGLE) ? ID_FLAG_TOGGLE : 0; flag |= (flags & IDEV_MAPPED_INVERTTOGGLE) ? ID_FLAG_INVERTTOGGLE : 0; -#endif } flag |= (flags & IDEV_MAPPED_INVERT) ? ID_FLAG_INVERT : 0; flag |= (flags & IDEV_MAPPED_GAMEPORTSCUSTOM1) ? ID_FLAG_GAMEPORTSCUSTOM1 : 0; -#ifndef INPUTDEVICE_SIMPLE flag |= (flags & IDEV_MAPPED_GAMEPORTSCUSTOM2) ? ID_FLAG_GAMEPORTSCUSTOM2 : 0; -#endif flag |= flags & IDEV_MAPPED_QUALIFIER_MASK; - flag &= ~(IDEV_MAPPED_SET_ONOFF | IDEV_MAPPED_SET_ONOFF_VAL); + flag &= ~(IDEV_MAPPED_SET_ONOFF | IDEV_MAPPED_SET_ONOFF_VAL1 | IDEV_MAPPED_SET_ONOFF_VAL2); if (amask & AM_SETTOGGLE) { flag |= (flags & IDEV_MAPPED_SET_ONOFF) ? ID_FLAG_SET_ONOFF : 0; - flag |= (flags & IDEV_MAPPED_SET_ONOFF_VAL) ? ID_FLAG_SET_ONOFF_VAL : 0; + flag |= (flags & IDEV_MAPPED_SET_ONOFF_VAL1) ? ID_FLAG_SET_ONOFF_VAL1 : 0; + flag |= (flags & IDEV_MAPPED_SET_ONOFF_VAL2) ? ID_FLAG_SET_ONOFF_VAL2 : 0; } if (port >= 0) portp = port; @@ -5799,6 +7756,9 @@ void inputdevice_copyconfig(struct uae_prefs *src, struct uae_prefs *dst) for (int i = 0; i < MAX_JPORTS; i++) { copyjport(src, dst, i); } + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + _tcscpy(dst->jports_custom[i].custom, src->jports_custom[i].custom); + } for (int i = 0; i < MAX_INPUT_SETTINGS; i++) { for (int j = 0; j < MAX_INPUT_DEVICES; j++) { @@ -5977,12 +7937,27 @@ void inputdevice_copy_single_config (struct uae_prefs *p, int src, int dst, int } } +void inputdevice_releasebuttons(void) +{ + for (int i = 0; i < MAX_INPUT_DEVICES; i++) { + for (int j = 0; j < 32; j++) { + uae_u32 mask = 1 << j; + if (joysticks2[i].buttonmask & mask) { + setbuttonstateall(&joysticks[i], &joysticks2[i], j, 0); + } + if (mice2[i].buttonmask & mask) { + setbuttonstateall(&mice[i], &mice2[i], j, 0); + } + } + mice2[i].buttonmask = 0; + joysticks2[i].buttonmask = 0; + } +} + void inputdevice_acquire (int allmode) { int i; - //write_log (_T("inputdevice_acquire\n")); - for (i = 0; i < MAX_INPUT_DEVICES; i++) idev[IDTYPE_JOYSTICK].unacquire (i); for (i = 0; i < MAX_INPUT_DEVICES; i++) @@ -6010,17 +7985,18 @@ void inputdevice_acquire (int allmode) idev[IDTYPE_JOYSTICK].acquire (-1, 0); idev[IDTYPE_MOUSE].acquire (-1, 0); idev[IDTYPE_KEYBOARD].acquire (-1, 0); + + //target_inputdevice_acquire(); + // if (!input_acquired) // write_log (_T("input devices acquired (%s)\n"), allmode ? "all" : "selected only"); input_acquired = 1; } -void inputdevice_unacquire(bool emulationactive, int inputmask) +static void inputdevice_unacquire(bool emulationactive, int inputmask) { int i; - //write_log (_T("inputdevice_unacquire %d %d\n"), emulationactive, inputmask); - if (!emulationactive) inputmask = 0; @@ -6041,6 +8017,8 @@ void inputdevice_unacquire(bool emulationactive, int inputmask) if (!input_acquired) return; + //target_inputdevice_unacquire(); + input_acquired = 0; if (!(inputmask & 4)) idev[IDTYPE_JOYSTICK].unacquire (-1); @@ -6130,7 +8108,7 @@ void setjoystickstate (int joy, int axis, int state, int max) state2 = -state2; if (state2 != id2->states[axis][i]) { //write_log(_T("-> %d %d\n"), i, state2); - handle_input_event (id->eventid[ID_AXIS_OFFSET + axis][i], state2, max, flags & ID_FLAG_AUTOFIRE); + handle_input_event (id->eventid[ID_AXIS_OFFSET + axis][i], state2, max, ((flags & ID_FLAG_AUTOFIRE) ? HANDLE_IE_FLAG_AUTOFIRE : 0)); id2->states[axis][i] = state2; } } @@ -6144,6 +8122,7 @@ int getjoystickstate (int joy) void setmousestate (int mouse, int axis, int data, int isabs) { int i, v, diff; + int extraflags = 0, extrastate = 0; int *mouse_p, *oldm_p; float d; struct uae_input_device *id = &mice[mouse]; @@ -6165,24 +8144,29 @@ void setmousestate (int mouse, int axis, int data, int isabs) oldm_p = &oldm_axis[mouse][axis]; if (!isabs) { // eat relative movements while in mousehack mode - if (currprefs.input_tablet == TABLET_MOUSEHACK && mousehack_alive () && axis < 2) + if (currprefs.input_tablet == TABLET_MOUSEHACK && mousehack_alive () && axis < 2) { return; + } *oldm_p = *mouse_p; *mouse_p += data; d = (*mouse_p - *oldm_p) * currprefs.input_mouse_speed / 100.0f; } else { + extraflags |= HANDLE_IE_FLAG_ABSOLUTE; + extrastate = data; d = data - *oldm_p; *oldm_p = data; *mouse_p += d; - if (axis == 0) + if (axis == 0) { lastmx = data; - else + } else { lastmy = data; + } if (axis) mousehack_helper (mice2[mouse].buttonmask); - if (currprefs.input_tablet == TABLET_MOUSEHACK && mousehack_alive () && axis < 2) + if (currprefs.input_tablet == TABLET_MOUSEHACK && mousehack_alive () && axis < 2) { return; } + } v = (int)d; fract[mouse][axis] += d - v; diff = (int)fract[mouse][axis]; @@ -6192,7 +8176,8 @@ void setmousestate (int mouse, int axis, int data, int isabs) uae_u64 flags = id->flags[ID_AXIS_OFFSET + axis][i]; if (!isabs && (flags & ID_FLAG_INVERT)) v = -v; - handle_input_event (id->eventid[ID_AXIS_OFFSET + axis][i], v, 0, 0); + + handle_input_event_extra(id->eventid[ID_AXIS_OFFSET + axis][i], v, 0, HANDLE_IE_FLAG_CANSTOPPLAYBACK | extraflags, extrastate); } } @@ -6201,6 +8186,47 @@ int getmousestate (int joy) return mice[joy].enabled; } +void warpmode (int mode) +{ + int fr, fr2; + + fr = currprefs.gfx_framerate; + if (fr == 0) + fr = -1; + fr2 = currprefs.turbo_emulation; + if (fr2 == -1) + fr2 = 0; + + if (mode < 0) { + if (currprefs.turbo_emulation) { + changed_prefs.gfx_framerate = currprefs.gfx_framerate = fr2; + currprefs.turbo_emulation = 0; + } else { + currprefs.turbo_emulation = fr; + } + } else if (mode == 0 && currprefs.turbo_emulation) { + if (currprefs.turbo_emulation > 0) + changed_prefs.gfx_framerate = currprefs.gfx_framerate = fr2; + currprefs.turbo_emulation = 0; + } else if (mode > 0 && !currprefs.turbo_emulation) { + currprefs.turbo_emulation = fr; + } + if (currprefs.turbo_emulation) { + if (!currprefs.cpu_memory_cycle_exact && !currprefs.blitter_cycle_exact) + changed_prefs.gfx_framerate = currprefs.gfx_framerate = 10; + pause_sound (); + } else { + resume_sound (); + } + compute_vsynctime (); +#ifdef RETROPLATFORM + rp_turbo_cpu (currprefs.turbo_emulation); +#endif + changed_prefs.turbo_emulation = currprefs.turbo_emulation; + set_config_changed (); + setsystime (); +} + void pausemode(int mode) { if (mode < 0) @@ -6268,29 +8294,45 @@ static bool fixjport (struct jport *port, int add, bool always) if (vv >= JSEM_LASTKBD) vv = 0; vv += JSEM_KBDLAYOUT; + } else if (vv >= JSEM_CUSTOM && vv < JSEM_CUSTOM + MAX_JPORTS_CUSTOM) { + vv -= JSEM_CUSTOM; + vv += add; + if (vv >= MAX_JPORTS_CUSTOM) + vv = 0; + vv += JSEM_CUSTOM; } if (port->id != vv || always) { port->idc.shortid[0] = 0; port->idc.configname[0] = 0; port->idc.name[0] = 0; if (vv >= JSEM_JOYS && vv < JSEM_MICE) { - _tcscpy(port->idc.name, inputdevice_get_device_name (IDTYPE_JOYSTICK, vv - JSEM_JOYS)); - _tcscpy(port->idc.configname, inputdevice_get_device_unique_name (IDTYPE_JOYSTICK, vv - JSEM_JOYS)); + _tcsncpy(port->idc.name, inputdevice_get_device_name (IDTYPE_JOYSTICK, vv - JSEM_JOYS), MAX_JPORT_NAME - 1); + _tcsncpy(port->idc.configname, inputdevice_get_device_unique_name (IDTYPE_JOYSTICK, vv - JSEM_JOYS), MAX_JPORT_CONFIG - 1); } else if (vv >= JSEM_MICE && vv < JSEM_END) { - _tcscpy(port->idc.name, inputdevice_get_device_name (IDTYPE_MOUSE, vv - JSEM_MICE)); - _tcscpy(port->idc.configname, inputdevice_get_device_unique_name (IDTYPE_MOUSE, vv - JSEM_MICE)); + _tcsncpy(port->idc.name, inputdevice_get_device_name (IDTYPE_MOUSE, vv - JSEM_MICE), MAX_JPORT_NAME - 1); + _tcsncpy(port->idc.configname, inputdevice_get_device_unique_name (IDTYPE_MOUSE, vv - JSEM_MICE), MAX_JPORT_CONFIG - 1); } else if (vv >= JSEM_KBDLAYOUT && vv < JSEM_CUSTOM) { _stprintf(port->idc.shortid, _T("kbd%d"), vv - JSEM_KBDLAYOUT + 1); + } else if (vv >= JSEM_CUSTOM && vv < JSEM_JOYS) { + _stprintf(port->idc.shortid, _T("custom%d"), vv - JSEM_CUSTOM); } + port->idc.name[MAX_JPORT_NAME - 1] = 0; + port->idc.configname[MAX_JPORT_CONFIG - 1] = 0; wasinvalid = true; } port->id = vv; return wasinvalid; } -static void inputdevice_get_previous_joy(struct uae_prefs *p, int portnum) +static void inputdevice_get_previous_joy(struct uae_prefs *p, int portnum, bool userconfig) { struct jport *jpx = &p->jports[portnum]; + + if (!userconfig) { + // default.uae with unplugged device -> NONE + p->jports[portnum].id = JPORT_NONE; + return; + } bool found = false; int idx = 0; for (;;) { @@ -6397,6 +8439,7 @@ void inputdevice_joyport_config_store(struct uae_prefs *p, const TCHAR *value, i } if (mode >= 0) jp->mode = mode; + jp->changed = true; } int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const TCHAR *value2, int portnum, int mode, int type, bool candefault) @@ -6416,7 +8459,7 @@ int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const idnum = JSEM_JOYS; } idf = &idev[dtype]; - if (value1 && value2) { + if (value1 && value2 && (p->input_device_match_mask & INPUT_MATCH_BOTH)) { for (int i = 0; i < idf->get_num(); i++) { const TCHAR* name1 = idf->get_friendlyname(i); const TCHAR* name2 = idf->get_uniquename(i); @@ -6427,7 +8470,7 @@ int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const } } } - if (matched < 0 && value2) { + if (matched < 0 && value2 && (p->input_device_match_mask & INPUT_MATCH_CONFIG_NAME_ONLY)) { matched = -1; for (int i = 0; i < idf->get_num (); i++) { const TCHAR* name2 = idf->get_uniquename(i); @@ -6441,7 +8484,7 @@ int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const } } } - if (matched < 0 && value1) { + if (matched < 0 && value1 && (p->input_device_match_mask & INPUT_MATCH_FRIENDLY_NAME_ONLY)) { matched = -1; for (int i = 0; i < idf->get_num (); i++) { const TCHAR* name1 = idf->get_friendlyname(i); @@ -6504,6 +8547,16 @@ int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const max = idev[IDTYPE_MOUSE].get_num (); } else if (_tcscmp(value1, _T("none")) == 0) { got = 2; + } else if (_tcscmp (value1, _T("custom")) == 0) { + // obsolete custom + start = JSEM_CUSTOM + portnum; + got = 3; + } else if (_tcsncmp(value1, _T("custom"), 6) == 0) { + // new custom + start = JSEM_CUSTOM; + pp = value1 + 6; + got = 2; + max = MAX_JPORTS_CUSTOM; } if (got) { if (pp && max != 0) { @@ -6528,12 +8581,16 @@ int inputdevice_joyport_config (struct uae_prefs *p, const TCHAR *value1, const if (got == 2 && candefault) { inputdevice_store_used_device(&p->jports[portnum], portnum, false); } + if (got == 3) { + // mark for old custom handling + _tcscpy(p->jports_custom[portnum].custom, _T("#")); + } set_config_changed (); return 1; } // joystick not found, select previously used or default if (start == JSEM_JOYS && p->jports[portnum].id < JSEM_JOYS) { - inputdevice_get_previous_joy(p, portnum); + inputdevice_get_previous_joy(p, portnum, true); set_config_changed (); return 1; } @@ -6561,6 +8618,15 @@ int inputdevice_getjoyportdevice (int port, int val) if (idx >= inputdevice_get_device_total (IDTYPE_JOYSTICK)) idx = 0; idx += JSEM_LASTKBD; + } else if (val >= JSEM_CUSTOM) { + idx = val - JSEM_CUSTOM; + if (idx >= MAX_JPORTS_CUSTOM) + idx = 0; + if (port >= 2) { + idx += JSEM_LASTKBD + inputdevice_get_device_total(IDTYPE_JOYSTICK); + } else { + idx += JSEM_LASTKBD + inputdevice_get_device_total(IDTYPE_MOUSE) + inputdevice_get_device_total(IDTYPE_JOYSTICK); + } } else { idx = val - JSEM_KBDLAYOUT; } @@ -6570,18 +8636,33 @@ int inputdevice_getjoyportdevice (int port, int val) void inputdevice_fix_prefs(struct uae_prefs *p, bool userconfig) { struct jport jport_config_store[MAX_JPORTS]; + bool changed = false; for (int i = 0; i < MAX_JPORTS; i++) { memcpy(&jport_config_store[i], &p->jports[i], sizeof(struct jport)); + changed |= p->jports[i].changed; } - const bool defaultports = !userconfig; + if (!changed) + return; + + bool defaultports = userconfig == false; + // Convert old style custom mapping to new style + for (int i = 0; i < MAX_JPORTS_CUSTOM; i++) { + struct jport_custom *jpc = &p->jports_custom[i]; + if (!_tcscmp(jpc->custom, _T("#"))) { + TCHAR tmp[16]; + _stprintf(tmp, _T("custom%d"), i); + inputdevice_joyport_config(p, tmp, NULL, i, -1, 0, userconfig); + inputdevice_generate_jport_custom(p, i); + } + } bool matched[MAX_JPORTS]; // configname+friendlyname first for (int i = 0; i < MAX_JPORTS; i++) { struct jport *jp = &jport_config_store[i]; matched[i] = false; - if (jp->idc.configname[0] && jp->idc.name[0]) { + if (jp->idc.configname[0] && jp->idc.name[0] && (p->input_device_match_mask & INPUT_MATCH_BOTH)) { if (inputdevice_joyport_config(p, jp->idc.name, jp->idc.configname, i, jp->mode, 1, userconfig)) { inputdevice_validate_jports(p, i, matched); inputdevice_store_used_device(&p->jports[i], i, defaultports); @@ -6594,7 +8675,7 @@ void inputdevice_fix_prefs(struct uae_prefs *p, bool userconfig) for (int i = 0; i < MAX_JPORTS; i++) { if (!matched[i]) { struct jport *jp = &jport_config_store[i]; - if (jp->idc.configname[0]) { + if (jp->idc.configname[0] && (p->input_device_match_mask & INPUT_MATCH_CONFIG_NAME_ONLY)) { if (inputdevice_joyport_config(p, NULL, jp->idc.configname, i, jp->mode, 1, userconfig)) { inputdevice_validate_jports(p, i, matched); inputdevice_store_used_device(&p->jports[i], i, defaultports); @@ -6608,7 +8689,7 @@ void inputdevice_fix_prefs(struct uae_prefs *p, bool userconfig) for (int i = 0; i < MAX_JPORTS; i++) { if (!matched[i]) { struct jport *jp = &jport_config_store[i]; - if (jp->idc.name[0]) { + if (jp->idc.name[0] && (p->input_device_match_mask & INPUT_MATCH_FRIENDLY_NAME_ONLY)) { if (inputdevice_joyport_config(p, jp->idc.name, NULL, i, jp->mode, 1, userconfig)) { inputdevice_validate_jports(p, i, matched); inputdevice_store_used_device(&p->jports[i], i, defaultports); @@ -6632,13 +8713,13 @@ void inputdevice_fix_prefs(struct uae_prefs *p, bool userconfig) } if (!matched[i]) { if (jp->idc.configname[0] && jp->idc.name[0]) { - struct jport jpt = { }; + struct jport jpt = { 0 }; memcpy(&jpt.idc, &jp->idc, sizeof(struct inputdevconfig)); jpt.id = JPORT_UNPLUGGED; write_log(_T("Unplugged stored, port %d '%s' (%s)\n"), i, jp->idc.name, jp->idc.configname); inputdevice_store_used_device(&jpt, i, defaultports); freejport(p, i); - inputdevice_get_previous_joy(p, i); + inputdevice_get_previous_joy(p, i, userconfig); matched[i] = true; } } @@ -6649,7 +8730,7 @@ void inputdevice_fix_prefs(struct uae_prefs *p, bool userconfig) struct jport *jp = &jport_config_store[i]; freejport(p, i); if (jp->id != JPORT_NONE) { - inputdevice_get_previous_joy(p, i); + inputdevice_get_previous_joy(p, i, userconfig); write_log(_T("Port%d: ID=%d getting previous: %d\n"), i, jp->id, p->jports[i].id); } else { write_log(_T("Port%d: NONE\n"), i); diff --git a/src/inputevents.def b/src/inputevents.def index ff412924..9c6b2bc7 100644 --- a/src/inputevents.def +++ b/src/inputevents.def @@ -94,6 +94,24 @@ DEFEVENT2(JOY2_CD32_YELLOW,_T("Joy2 CD32 Yellow"),_T("CD32 Y"),AM_K,4,2,JOYBUTTO DEFEVENT2(JOY2_CD32_RED,_T("Joy2 CD32 Red"),_T("CD32 R"),AM_K,4,2,JOYBUTTON_CD32_RED,23) DEFEVENT2(JOY2_CD32_BLUE,_T("Joy2 CD32 Blue"),_T("CD32 B"),AM_K,4,2,JOYBUTTON_CD32_BLUE,24) +DEFEVENT(LIGHTPEN_FIRST, _T(""), AM_DUMMY, 0,0,0) + +DEFEVENT(LIGHTPEN_HORIZ,_T("Lightpen Horizontal"),AM_MOUSE_AXIS|AM_JOY_AXIS,0,5,0) +DEFEVENT(LIGHTPEN_VERT,_T("Lightpen Vertical"),AM_MOUSE_AXIS|AM_JOY_AXIS,0,5,1) +DEFEVENT(LIGHTPEN_LEFT,_T("Lightpen Left"),AM_K,1,5,DIR_LEFT) +DEFEVENT(LIGHTPEN_RIGHT,_T("Lightpen Right"),AM_K,1,5,DIR_RIGHT) +DEFEVENT(LIGHTPEN_UP,_T("Lightpen Up"),AM_K,1,5,DIR_UP) +DEFEVENT(LIGHTPEN_DOWN,_T("Lightpen Down"),AM_K,1,5,DIR_DOWN) +DEFEVENT(LIGHTPEN_HORIZ2,_T("Dual Lightpen Horizontal #2"),AM_MOUSE_AXIS|AM_JOY_AXIS,0,6,0) +DEFEVENT(LIGHTPEN_VERT2,_T("Dual Lightpen Vertical #2"),AM_MOUSE_AXIS|AM_JOY_AXIS,0,6,1) +DEFEVENT(LIGHTPEN_LEFT2,_T("Dual Lightpen Left #2"),AM_K,1,6,DIR_LEFT) +DEFEVENT(LIGHTPEN_RIGHT2,_T("Dual Lightpen Right #2"),AM_K,1,6,DIR_RIGHT) +DEFEVENT(LIGHTPEN_UP2,_T("Dual Lightpen Up #2"),AM_K,1,6,DIR_UP) +DEFEVENT(LIGHTPEN_DOWN2,_T("Dual Lightpen Down #2"),AM_K,1,6,DIR_DOWN) +DEFEVENT(LIGHTPEN_TRIGGER2,_T("Dual Lightpen Trigger"),AM_K,2,6,JOYBUTTON_LIGHTPEN2) + +DEFEVENT(LIGHTPEN_LAST, _T(""), AM_DUMMY, 0,0,0) + /* parallel port joystick adapter */ DEFEVENT(PAR_JOY1_START, _T("[Parallel port joystick adapter]"), AM_INFO, 0,3,0) diff --git a/src/jit/aarch64.h b/src/jit/aarch64.h new file mode 100644 index 00000000..f34e125f --- /dev/null +++ b/src/jit/aarch64.h @@ -0,0 +1,2127 @@ +/* Universal Disassembler Function Library + * https://gitlab.com/bztsrc/udisasm + * + * ----- GENERATED FILE, DO NOT EDIT! ----- + * + * Copyright (C) 2017 bzt (bztsrc@gitlab) + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, copy, + * modify, merge, publish, distribute, sublicense, and/or sell copies + * of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + * @brief Disassembler source generated from aarch64.txt + */ + +#ifdef __cplusplus +extern "C" { +#endif + +#define disasm_arch "aarch64" +enum { disasm_arg_NONE,disasm_arg_ofs,disasm_arg_ofe, disasm_arg_Xt, disasm_arg_labelij1, disasm_arg_RtS, disasm_arg_RnS, disasm_arg_i, disasm_arg_j12_opt, disasm_arg_Rn, disasm_arg_ib, disasm_arg_Rt, disasm_arg_j16_opt, disasm_arg_j, disasm_arg_Rm, disasm_arg_c, disasm_arg_labeli4, disasm_arg_i_opt, disasm_arg_pstate, disasm_arg_sh, disasm_arg_a0, disasm_arg_a1, disasm_arg_a2, disasm_arg_dc0, disasm_arg_dc1, disasm_arg_ZVA, disasm_arg_dc2, disasm_arg_ic, disasm_arg_Xt_opt, disasm_arg_tl0, disasm_arg_tl1, disasm_arg_tl2, disasm_arg_sysreg, disasm_arg_Cn, disasm_arg_Cm, disasm_arg_Xn, disasm_arg_b, disasm_arg_VtT, disasm_arg_Vt2T, disasm_arg_Vt3T, disasm_arg_Vt4T, disasm_arg_offs, disasm_arg_XnS, disasm_arg_offe, disasm_arg_Qi, disasm_arg_Xm, disasm_arg_Qi3, disasm_arg_Qi2, disasm_arg_Qi1, disasm_arg_VtB, disasm_arg_VtH, disasm_arg_VtS, disasm_arg_VtD, disasm_arg_i1, disasm_arg_i2, disasm_arg_i4, disasm_arg_i8, disasm_arg_Vt3B, disasm_arg_Vt3H, disasm_arg_Vt3S, disasm_arg_Vt3D, disasm_arg_i3, disasm_arg_i6, disasm_arg_i12, disasm_arg_i24, disasm_arg_Vt2B, disasm_arg_Vt2H, disasm_arg_Vt2S, disasm_arg_Vt2D, disasm_arg_i16, disasm_arg_Vt4B, disasm_arg_Vt4H, disasm_arg_Vt4S, disasm_arg_Vt4D, disasm_arg_i32, disasm_arg_z, disasm_arg_z3, disasm_arg_z2, disasm_arg_z4, disasm_arg_Rd, disasm_arg_Rd1, disasm_arg_Rt1, disasm_arg_Wd, disasm_arg_Wt, disasm_arg_FPt, disasm_arg_prf_op, disasm_arg_is4_opt, disasm_arg_FPm, disasm_arg_iz4_opt, disasm_arg_im4_opt, disasm_arg_nRt, disasm_arg_FPst, disasm_arg_j_opt, disasm_arg_Rom, disasm_arg_amountj, disasm_arg_amountz, disasm_arg_amountjs, disasm_arg_amountj2, disasm_arg_amountj3, disasm_arg_shiftj_opt, disasm_arg_Rsom, disasm_arg_exts, disasm_arg_Wn, disasm_arg_Wm, disasm_arg_Xd, disasm_arg_Vt16b, disasm_arg_Vn16b, disasm_arg_Qt, disasm_arg_Sn, disasm_arg_Vm4s, disasm_arg_Vt4s, disasm_arg_Vn4s, disasm_arg_Qn, disasm_arg_St, disasm_arg_FPjt, disasm_arg_Vnj, disasm_arg_FPidx, disasm_arg_Vtjq, disasm_arg_Ht, disasm_arg_Hn, disasm_arg_Hm, disasm_arg_FPn, disasm_arg_VtH1, disasm_arg_VnH1, disasm_arg_VmH1, disasm_arg_Vtzq, disasm_arg_Vnzq, disasm_arg_Vmzq, disasm_arg_simd0, disasm_arg_FPz2t, disasm_arg_FPz2n, disasm_arg_FPz2m, disasm_arg_VnT, disasm_arg_VmT, disasm_arg_FPz3t, disasm_arg_FPz3n, disasm_arg_FPz4n, disasm_arg_VnT3, disasm_arg_Vn2d, disasm_arg_Vn2h, disasm_arg_Vnz, disasm_arg_FPz4t, disasm_arg_Vtz, disasm_arg_FPz3m, disasm_arg_Dt, disasm_arg_Dn, disasm_arg_shrshift, disasm_arg_Vtj2, disasm_arg_Vnj2, disasm_arg_shlshift, disasm_arg_FPnj, disasm_arg_VnTa, disasm_arg_FPjt2, disasm_arg_FPjn2, disasm_arg_Vtz3, disasm_arg_VmTs, disasm_arg_VmHs, disasm_arg_VmTs2, disasm_arg_Vn116b, disasm_arg_Vn216b, disasm_arg_Vn316b, disasm_arg_Vn416b, disasm_arg_Vtj, disasm_arg_R2n, disasm_arg_FPidxk, disasm_arg_Vtzq2, disasm_arg_VnT2, disasm_arg_Vnz3, disasm_arg_Vnzq2, disasm_arg_shift8, disasm_arg_VtT3, disasm_arg_VmT3, disasm_arg_VtT4, disasm_arg_imm8, disasm_arg_amountk_opt, disasm_arg_amountk2_opt, disasm_arg_imm64, disasm_arg_Vt2d, disasm_arg_F16, disasm_arg_F32, disasm_arg_F64, disasm_arg_VmTs4b, disasm_arg_Vm2d, disasm_arg_Vm16b, disasm_arg_Vd16b, disasm_arg_Vd4s, disasm_arg_FPz5t, disasm_arg_fbits, disasm_arg_FPz5n, disasm_arg_Vn1d, disasm_arg_Vt1d, disasm_arg_FPk5t, disasm_arg_FPz5m, disasm_arg_jz, disasm_arg_FPz5d }; + +/*** private functions ***/ +const char *disasm_str(char*s,int n) {if(!s)return "?";while(n){s++;if(!*s){s++;n--;}}return *s?s:"?";} +const char *disasm_sysreg(uint8_t p,uint8_t k,uint8_t n,uint8_t m,uint8_t j) {char *t=NULL;switch(p){case 2: switch(k) {case 0: switch(n) {case 0: switch(m) {case 0: t="?\0?\0OSDTRRX_EL1\0"; break;case 2: t="MDCCINT_EL1\0?\0MDSCR_EL1\0"; break;case 3: t="?\0?\0OSDTRTX_EL1\0"; break;case 6: t="?\0?\0OSECCR_EL1\0"; break;default: { n=j; j=m; switch(n) {case 4: t="DBGBVR0_EL1\0DBGBVR1_EL1\0DBGBVR2_EL1\0DBGBVR3_EL1\0DBGBVR4_EL1\0DBGBVR5_EL1\0DBGBVR6_EL1\0DBGBVR7_EL1\0"; break;case 5: t="DBGBCR0_EL1\0DBGBCR1_EL1\0DBGBCR2_EL1\0DBGBCR3_EL1\0DBGBCR4_EL1\0DBGBCR5_EL1\0DBGBCR6_EL1\0DBGBCR7_EL1\0"; break;case 6: t="DBGWVR0_EL1\0DBGWVR1_EL1\0DBGWVR2_EL1\0DBGWVR3_EL1\0DBGWVR4_EL1\0DBGWVR5_EL1\0DBGWVR6_EL1\0DBGWVR7_EL1\0"; break;case 7: t="DBGWCR0_EL1\0DBGWCR1_EL1\0DBGWCR2_EL1\0DBGWCR3_EL1\0DBGWCR4_EL1\0DBGWCR5_EL1\0DBGWCR6_EL1\0DBGWCR7_EL1\0"; break;} break; }} break;case 1: if(m==0) t="MDRAR_EL1\0?\0?\0?\0OSLAR_EL1\0"; else if(j==4) { j=m; t="OSLSR_EL1\0?\0OSDLR_EL1\0DBGPRCR_EL1\0"; }break;case 7: if(j==6) { j=m; t="?\0?\0?\0?\0?\0?\0?\0?\0DBGCLAIMSET_EL1\0DBGCLAIMCLR_EL1\0?\0?\0?\0?\0DBGAUTHSTATUS_EL1\0"; }break;} break;case 3: if(n==0&&j==0) { j=m; t="?\0MDCCSR_EL0\0?\0?\0DBGDTR_EL0\0DBGDTRRX_EL0\0"; } break;case 4: if(n==0&&m==7) t="DBGVCR32_EL2\0"; break;} break;case 3: switch(k) {case 0: switch(n) {case 0: if(m==0) t="MIDR_EL1\0?\0?\0?\0?\0MPIDR_EL1\0REVIDR_EL1\0?\0ID_PFR0_EL1\0ID_PFR1_EL1\0ID_DFR0_EL1\0ID_AFR0_EL1\0ID_MMFR0_EL1\0ID_MMFR1_EL1\0ID_MMFR2_EL1\0ID_MMFR3_EL1\0ID_ISAR0_EL1\0ID_ISAR1_EL1\0ID_ISAR2_EL1\0ID_ISAR2_EL1\0ID_ISAR3_EL1\0ID_ISAR4_EL1\0ID_ISAR5_EL1\0ID_MMFR4_EL1\0?\0MVFR0_EL1\0MVFR1_EL1\0MVFR2_EL1\0?\0?\0?\0?\0?\0ID_A64PFR0_EL1\0ID_A64PFR1_EL1\0?\0?\0ID_A64ZFR0_EL1\0?\0?\0?\0ID_A64DFR0_EL1\0ID_A64DFR1_EL1\0?\0?\0ID_A64AFR0_EL1\0ID_A64AFR1_EL1\0?\0?\0ID_A64ISAR0_EL1\0ID_A64ISAR1_EL1\0?\0?\0?\0?\0?\0?\0ID_A64MMFR0_EL1\0ID_A64MMFR1_EL1\0ID_A64MMFR2_EL1\0"; break;case 1: switch(m) {case 0: t="SCTLR_EL1\0ACTLR_EL1\0CPACR_EL1\0"; break;case 2: t="ZCR_EL1\0"; break;} break;case 2: if(m==0) t="TTBR0_EL1\0TTBR1_EL1\0TCR_EL1\0"; break;case 4: switch(m) {case 0: t="SPSR_EL1\0ELR_EL1\0"; break;case 1: t="SP_EL0\0"; break;case 2: t="SPSel\0?\0CurrentEL\0PAN\0UAO\0"; break;case 6: t="ICC_PMR_EL1\0"; break;} break;case 5: switch(m) {case 1: t="AFSR0_EL1\0AFSR1_EL1\0"; break;case 2: t="ESR_EL1"; break;case 3: t="ERRIDR_EL1\0ERRSELR_EL1\0"; break;case 4: t="ERXFR_EL1\0ERXCTLR_EL1\0ERXSTATUS_EL1\0ERXADDR_EL1\0"; break;case 5: t="ERXMISC0_EL1\0ERXMISC1_EL1\0"; break;} break;case 6: if(m==0) t="FAR_EL1\0"; break;case 7: if(m==4) t="PAR_EL1\0"; break;case 9: switch(m) {case 9: t="PMSCR_EL1\0?\0PMSICR_EL1\0PMSIRR_EL1\0PMSFCR_EL1\0PMSEVFR_EL1\0PMSLATFR_EL1\0PMSIDR_EL1\0PMSIDR_EL1\0"; break;case 10: t="PMBLIMITR_EL1\0PMBPTR_EL1\0?\0PMBSR_EL1\0?\0?\0?\0PMBIDR_EL1\0"; break;case 14: t="?\0PMINTENSET_EL1\0PMINTENCLR_EL1\0"; break;} break;case 10: if(m==4) t="LORSA_EL1\0LOREA_EL1\0LORN_EL1\0LORC_EL1\0?\0?\0?\0LORID_EL1\0"; else if(m!=4&&j==0) { j=m; t="?\0?\0MAIR_EL1\0AMAIR_EL1\0"; }break;case 12: switch(m) {case 0: t="VBAR_EL1\0RVBAR_EL1\0RMR_EL1\0"; break;case 1: t="ISR_EL1\0DISR_EL1\0"; break;case 8: t="ICC_IAR0_EL1\0ICC_EOIR0_EL1\0ICC_HPPIR0_EL1\0ICC_BPR0_EL1\0ICC_AP0R0_EL1\0ICC_AP0R1_EL1\0ICC_AP0R2_EL1\0ICC_AP0R3_EL1\0"; break;case 9: t="ICC_AP1R0_EL1\0ICC_AP1R1_EL1\0ICC_AP1R2_EL1\0ICC_AP1R3_EL1\0"; break;case 11: t="?\0ICC_DIR_EL1\0?\0ICC_RPR_EL1\0?\0ICC_SGI1R_EL1\0ICC_ASGI1R_EL1\0ICC_SGI0R_EL1\0"; break;case 12: t="ICC_IAR1_EL1\0ICC_EOIR1_EL1\0ICC_HPPIR1_EL1\0ICC_BPR1_EL1\0ICC_CTLR_EL1\0ICC_SRE_EL1\0ICC_IGRPEN0_EL1\0ICC_IGRPEN1_EL1\0"; break;} break;case 13: if(m==0) t="?\0CONTEXTIDR_EL1\0?\0?\0TPIDR_EL1\0"; break;case 14: if(m==1) t="CNTKCTL_EL1\0"; break;} break;case 1: if(n==0&&m==0) t="CCSIDR_EL1\0CLIDR_EL1\0?\0?\0?\0?\0?\0AIDR_EL1\0"; break;case 2: if(n==0&&m==0) t="CSSELR_EL1\0"; break;case 3: switch(n) {case 0: if(m==0) t="?\0CTR_EL0\0?\0?\0?\0?\0?\0DCZID_EL0\0"; break;case 4: switch(m) {case 2: t="NZCV\0DAIF\0"; break;case 4: t="FPCR\0FPSR\0"; break;case 5: t="DSPSR_EL0\0DLR_EL0\0"; break;} break;case 9: switch(m) {case 12: t="PMCR_EL0\0PMCNTENSET_EL0\0PMCNTENCLR_EL0\0PMOVSCLR_EL0\0PMSWINC_EL0\0PMSELR_EL0\0PMCEID0_EL0\0PMCEID1_EL0\0"; break;case 13: t="PMCCNTR_EL0\0PMXEVTYPER_EL0\0PMXEVCNTR_EL0\0"; break;case 14: t="PMUSERENR_EL0\0?\0?\0PMOVSSET_EL0\0"; break;} break; +case 13: if(m==0) t="?\0?\0TPIDR_EL0\0TPIDRRO_EL0\0"; break;case 14: switch(m) {case 0: t="CNTFRQ_EL0\0CNTPCT_EL0\0CNTVCT_EL0\0"; break;case 2: t="CNTP_TVAL_EL0\0CNTP_CTL_EL0\0CNTP_CVAL_EL0\0"; break;case 3: t="CNTV_TVAL_EL0\0CNTV_CTL_EL0\0CNTV_CVAL_EL0\0"; break;} break;} break;case 4: switch(n) {case 0: if(m==0) t="VPIDR_EL2\0?\0?\0?\0?\0VMPIDR_EL2\0"; break;case 1: switch(m) {case 0: t="SCTLR_EL2\0ACTLR_EL2\0"; break;case 1: t="HCR_EL2\0MDCR_EL2\0CPTR_EL2\0HSTR_EL2\0?\0?\0?\0HACR_EL2\0"; break;case 2: t="ZCR_EL2\0"; break;} break;case 2: switch(m) {case 0: t="TTBR0_EL2\0?\0TCR_EL2\0"; break;case 1: t="VTTBR0_EL2\0?\0VTCR_EL2\0"; break;} break;case 3: if(m==0) t="DACR32_EL2\0"; break;case 4: switch(m) {case 0: t="SPSR_EL2\0ELR_EL2\0"; break;case 1: t="SP_EL1\0"; break;case 3: t="SPSR_irq\0SPSR_abt\0SPSR_und\0SPSR_fiq\0"; break;} break;case 5: switch(m) {case 0: t="?\0IFSR32_EL2\0"; break;case 1: t="AFSR0_EL2\0AFSR1_EL2\0"; break;case 2: t="ESR_EL2\0?\0?\0VSESR_EL2\0"; break;case 3: t="FPEXC32_EL2\0"; break;} break;case 6: if(m==0) t="FAR_EL2\0?\0?\0?\0HPFAR_EL2\0"; break;case 9: if(m==9) t="PMSCR_EL2\0"; break;case 10: switch(m) {case 2: t="MAIR_EL2\0"; break;case 3: t="AMAIR_EL2\0"; break;} break;case 12: switch(m) {case 0: t="VBAR_EL2\0RVBAR_EL2\0RMR_EL2\0"; break;case 1: t="?\0VDISR_EL2\0"; break;case 8: t="ICH_AP0R0_EL2\0ICH_AP0R1_EL2\0ICH_AP0R2_EL2\0ICH_AP0R3_EL2\0"; break;case 9: t="ICH_AP1R0_EL2\0ICH_AP1R1_EL2\0ICH_AP1R2_EL2\0ICH_AP1R3_EL2\0ICC_SRE_EL2\0"; break;case 11: t="ICH_HCR_EL2\0ICH_VTR_EL2\0ICH_MISR_EL2\0ICH_EISR_EL2\0?\0ICH_ELRSR_EL2\0?\0ICH_VMCR_EL2\0"; break;case 12: t="ICH_LR0_EL2\0ICH_LR1_EL2\0ICH_LR2_EL2\0ICH_LR3_EL2\0ICH_LR4_EL2\0ICH_LR5_EL2\0ICH_LR6_EL2\0ICH_LR7_EL2\0"; break;case 13: t="ICH_LR8_EL2\0ICH_LR9_EL2\0ICH_LR10_EL2\0ICH_LR11_EL2\0ICH_LR12_EL2\0ICH_LR13_EL2\0ICH_LR14_EL2\0ICH_LR15_EL2\0"; break;} break;case 13: if(m==0) t="?\0CONTEXTIDR_EL2\0TPIDR_EL2\0"; break;case 14: switch(m) {case 0: t="?\0?\0?\0CNTVOFF_EL2\0"; break;case 1: t="CNTHCTL_EL2\0"; break;case 2: t="CNTHP_TVAL_EL2\0CNTHP_CTL_EL2\0CNTHP_CVAL_EL2\0"; break;case 3: t="CNTHV_TVAL_EL2\0CNTHV_CTL_EL2\0CNTHV_CVAL_EL2\0"; break;} break;} break;case 5: if(n==4&&m==0) t="SPSR_EL12\0ELR_EL12\0"; break;case 6: if(n==4&&m==1) t="SP_EL2\0"; break;case 7: if(n==14&&m==2) t="CNTPS_TVAL_EL1\0CNTPS_CTL_EL1\0CNTPS_CVAL_EL1\0"; break;} break;}return t?disasm_str(t,j):NULL;} +uint64_t disasm_dbm(int k, int j, int i) {int e=(k<<6)|(~j&0x3F),l=6;uint64_t m,r;while(l>=0 && !(e&(1<>(64-(j+1));m=(m>>i)|(m<<(e-i));r=m;i=e;while(i<64){r|=(m<>20; ic32_15=ic32>>15; ic32_16=ic32>>16; ic32_5=ic32>>5; ic32_8=ic32>>8; ic32_22=ic32>>22; ic32_13=ic32>>13; ic32_14=ic32>>14; ic32_9=ic32>>9; ic32_10=ic32>>10; ic32_21=ic32>>21; ic32_4=ic32>>4; ic32_12=ic32>>12; ic32_24=ic32>>24; ic32_11=ic32>>11; ic32_18=ic32>>18; ic32_27=ic32>>27; ic32_28=ic32>>28; ic32_29=ic32>>29; ic32_25=ic32>>25; ic32_26=ic32>>26; ic32_23=ic32>>23; ic32_30=ic32>>30; ic32_19=ic32>>19; ic32_31=ic32>>31; + + /* handle multiple NOPs at once */ + if(ic32==0xd503201f) { + while(*((uint32_t*)addr)==ic32) { op++; addr+=4; } + if(str!=NULL) str+=sprintf(str," %d x nop",op); + *str=0; + return addr; + } + + /* decode instruction */ + if(((ic32_8)&0xff007c)==0x8007c) { + names="stxrb\0stlxrb\0?\0?\0?\0?\0?\0?\0?\0?\0casb\0caslb\0?\0?\0casab\0casalb\0"; + op=((ic32_20)&0xe)|((ic32_15)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Wt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffbffc)==0xe2168) { + names="fcvtn\0"; + z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtzq2; args[1]=disasm_arg_Vnz3; + } else + if(((ic32_8)&0xffbffc)==0xe21e8) { + names="fcvtl\0"; + z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_Vnzq2; + } else + if(((ic32_8)&0xff3ffc)==0xe2128) { + names="xtn\0"; + z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT2; + } else + if(((ic32_8)&0xff3ffc)==0xe2138) { + names="shll\0"; + z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_shift8; + } else + if(((ic32_8)&0xff209c)==0xe2090) { + names="sqdmlal\0sqdmlsl\0sqdmull\0"; + op=((ic32_13)&0x3); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xffc0b4)==0xf4020) { + names="smlal\0smlsl\0"; + op=((ic32_14)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=0; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0f4)==0xf40a0) { + names="smull\0"; + j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0b4)==0xf8020) { + names="smlal\0smlsl\0"; + op=((ic32_14)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=0; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0f4)==0xf80a0) { + names="smull\0"; + j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xfffffc)==0x1e6240) { + names="fcvt\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_St; args[1]=disasm_arg_Dn; + } else + if(((ic32_8)&0xff3e7c)==0x1e2240) { + names="fcvt\0"; + z=((ic32_22)&0x3); k=((ic32_15)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPk5t; args[1]=disasm_arg_FPz5n; + } else + if(((ic32_8)&0xff387c)==0x1e2040) { + names="fmov\0fabs\0fneg\0fsqrt\0?\0?\0?\0?\0frintn\0frintp\0frintm\0frintz\0frinta\0?\0frintx\0frinti\0"; + op=((ic32_15)&0xf); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_FPz5n; + } else + if((ic32&0xff20fc0f)==0x1e202000) { + names="fcmp\0fcmpe\0"; + op=((ic32_4)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); + args[0]=disasm_arg_FPz5n; args[1]=disasm_arg_FPz5m; + } else + if((ic32&0xff20fc0f)==0x1e202008) { + names="fcmp\0fcmpe\0"; + op=((ic32_4)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); + args[0]=disasm_arg_FPz5n; args[1]=disasm_arg_simd0; + } else + if((ic32&0xff201fe0)==0x1e201000) { + names="fmov\0"; + z=((ic32_22)&0x3); j=((ic32_13)&0xff); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_jz; + } else + if(((ic32_8)&0xff200c)==0x1e2004) { + names="ffcmp\0ffcmpe\0"; + op=((ic32_4)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); c=((ic32_12)&0xf); n=((ic32_5)&0x1f); j=((ic32)&0xf); + args[0]=disasm_arg_FPz5n; args[1]=disasm_arg_FPz5m; args[2]=disasm_arg_j; args[3]=disasm_arg_c; + } else + if(((ic32_8)&0xff200c)==0x1e2008) { + names="fmul\0fdiv\0fadd\0fsub\0fmax\0fmin\0fmaxnm\0fminmn\0fnmul\0"; + op=((ic32_12)&0xf); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_FPz5n; args[2]=disasm_arg_FPz5m; + } else + if(((ic32_8)&0xff200c)==0x1e200c) { + names="fcsel\0"; + z=((ic32_22)&0x3); m=((ic32_16)&0x1f); c=((ic32_12)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_FPz5n; args[2]=disasm_arg_FPz5m; args[3]=disasm_arg_c; + } else + if(((ic32_24)&0xff)==0x1f) { + names="fmadd\0fmsub\0fnmadd\0fnmsub\0"; + op=((ic32_20)&0x2)|((ic32_15)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); d=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_FPz5n; args[2]=disasm_arg_FPz5m; args[3]=disasm_arg_FPz5t; args[4]=disasm_arg_FPz5n; args[5]=disasm_arg_FPz5d; + } else + if(((ic32_8)&0xfff8fc)==0x2f00e4) { + names="movi\0"; + j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Dt; args[1]=disasm_arg_imm64; + } else + if(((ic32_8)&0xff200c)==0x382000) { + names="ldaddb\0ldclrb\0ldeorb\0ldsetb\0ldsmaxb\0ldsminb\0ldumaxb\0lduminb\0swpb\0?\0?\0?\0?\0?\0?\0?\0ldaddlb\0ldclrlb\0ldeorlb\0ldsetlb\0ldsmaxlb\0ldsminlb\0ldumaxlb\0lduminlb\0swplb\0?\0?\0?\0?\0?\0?\0?\0ldaddab\0ldclrab\0ldeorab\0ldsetab\0ldsmaxab\0ldsminab\0ldumaxab\0lduminab\0swpab\0?\0?\0?\0?\0?\0?\0?\0ldaddalb\0ldclralb\0ldeoralb\0ldsetalb\0ldsmaxalb\0ldsminalb\0ldumaxalb\0lduminalb\0swpalb\0"; + op=((ic32_18)&0x30)|((ic32_12)&0xf); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Wt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xdf3f9c)==0xe2108) { + names="?\0xtn\0sqxtn\0?\0?\0sqxtun\0uqxtn\0fcvtxn\0"; + op=((ic32_27)&0x4)|((ic32_13)&0x3); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT3; + } else + if(((ic32_8)&0xdf20dc)==0xe2010) { + names="saddw\0ssubw\0uaddw\0usubw\0"; + op=((ic32_28)&0x2)|((ic32_13)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT3; args[1]=disasm_arg_VnT3; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdf20dc)==0xe2040) { + names="addhn\0subhn\0raddhn\0rsubhn\0"; + op=((ic32_28)&0x2)|((ic32_13)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT3; args[2]=disasm_arg_VmT3; + } else + if(((ic32_8)&0xdf20fc)==0xe20e0) { + names="pmull\0umull\0"; + op=((ic32_29)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT4; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdf200c)==0xe2000) { + names="saddl\0saddw\0ssubl\0ssubw\0addhn\0sabal\0subhn\0sabdl\0smlal\0sqdmlal\0smlsl\0sqdmlsl\0?\0sqdmull\0pmull\0?\0uaddl\0uaddw\0usubl\0usubw\0raddhn\0uabal\0rsubhn\0uabdl\0umlal\0?\0umlsl\0?\0?\0?\0umull\0"; + op=((ic32_25)&0x10)|((ic32_12)&0xf); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_VtT3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdfc024)==0xf4020) { + names="smlal\0sqdmlal\0smlsl\0sqdmlsl\0smull\0sqdmull\0?\0?\0umlal\0?\0umlsl\0?\0umull\0"; + op=((ic32_26)&0x8)|((ic32_13)&0x6)|((ic32_12)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=0; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xdf80e4)==0xf0084) { + names="?\0rshrn\0sqshrn\0sqrshrn\0sqshrun\0sqrshrun\0uqshrn\0uqrshrn\0"; + op=((ic32_27)&0x4)|((ic32_11)&0x3); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_VnTa; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdf80fc)==0xf00a4) { + names="sshll\0usshll\0"; + op=((ic32_29)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=0; + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_VnTa; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0xdfc024)==0xf8020) { + names="smlal\0sqdmlal\0smlsl\0sqdmlsl\0smull\0sqdmull\0?\0?\0umlal\0?\0umlsl\0?\0umull\0"; + op=((ic32_26)&0x8)|((ic32_13)&0x6)|((ic32_12)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=0; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xff007c)==0x48007c) { + names="stxrh\0stlxrh\0?\0?\0?\0?\0?\0?\0?\0?\0cash\0caslh\0?\0?\0casah\0casalh\0"; + op=((ic32_20)&0xe)|((ic32_15)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Wt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffe0fc)==0x4e001c) { + names="ins\0"; + j=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj; args[1]=disasm_arg_offs; args[2]=disasm_arg_FPidx; args[3]=disasm_arg_offe; args[4]=disasm_arg_R2n; + } else + if(((ic32_8)&0xffffcc)==0x4e2848) { + names="aese\0aesd\0aesmc\0aesimc\0"; + op=((ic32_12)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt16b; args[1]=disasm_arg_Vn16b; + } else + if(((ic32_8)&0xffbffc)==0x4e2168) { + names="fcvtn2\0"; + z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtzq2; args[1]=disasm_arg_Vnz3; + } else + if(((ic32_8)&0xffbffc)==0x4e21e8) { + names="fcvtl2\0"; + z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_Vnzq2; + } else + if(((ic32_8)&0xff3ffc)==0x4e2128) { + names="xtn2\0"; + z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT2; + } else + if(((ic32_8)&0xff3ffc)==0x4e2138) { + names="shll2\0"; + z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_shift8; + } else + if(((ic32_8)&0xff209c)==0x4e2090) { + names="sqdmlal2\0sqdmlsl2\0sqdmull2\0"; + op=((ic32_13)&0x3); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xffc0b4)==0x4f4020) { + names="smlal2\0smlsl2\0"; + op=((ic32_14)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=1; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0f4)==0x4f40a0) { + names="smull2\0"; + j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0b4)==0x4f8020) { + names="smlal2\0smlsl2\0"; + op=((ic32_14)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=1; + args[0]=disasm_arg_Vtz3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc0f4)==0x4f80a0) { + names="smull2\0"; + j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if((ic32&0xff000010)==0x54000000) { + names="b.%s\0"; + i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); c=((ic32)&0xf); + args[0]=disasm_arg_labeli4; + } else + if(((ic32_8)&0xffe0fc)==0x5e0004) { + names="dup\0"; + j=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPjt; args[1]=disasm_arg_Vnj; args[2]=disasm_arg_offs; args[3]=disasm_arg_FPidx; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffe0fc)==0x5e0030) { + names="sha1su0\0"; + m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; args[2]=disasm_arg_Vm4s; + } else + if(((ic32_8)&0xffe0cc)==0x5e0000) { + names="sha1c\0sha1p\0sha1m\0sha1su0\0"; + op=((ic32_12)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Qt; args[1]=disasm_arg_Sn; args[2]=disasm_arg_Vm4s; + } else + if(((ic32_8)&0xffe0ec)==0x5e0040) { + names="sha256h\0sha256h2\0"; + op=((ic32_12)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Qt; args[1]=disasm_arg_Qn; args[2]=disasm_arg_Vm4s; + } else + if(((ic32_8)&0xffe0fc)==0x5e0060) { + names="sha256su1\0"; + m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; args[2]=disasm_arg_Vm4s; + } else + if(((ic32_8)&0xfffffc)==0x5e2808) { + names="sha1h\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_St; args[1]=disasm_arg_Sn; + } else + if(((ic32_8)&0xfffffc)==0x5e2818) { + names="sha1su1\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; + } else + if(((ic32_8)&0xfffffc)==0x5e2828) { + names="sha256su0\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; + } else + if(((ic32_8)&0xffe0fc)==0x5e401c) { + names="fmulx\0"; + m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xffe0fc)==0x5e4024) { + names="fcmeq\0"; + m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xffa0fc)==0x5e20dc) { + names="fmulx\0"; + z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xffa0fc)==0x5e20e4) { + names="fcmeq\0"; + z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xff7fcc)==0x5e30c8) { + names="fmaxnmp\0faddp\0?\0fmaxp\0fminnmp\0?\0?\0fminp\0"; + op=((ic32_21)&0x4)|((ic32_12)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Vn2h; + } else + if(((ic32_8)&0xff60fc)==0x5e403c) { + names="frecps\0frsqrts\0"; + op=((ic32_23)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xff3ffc)==0x5e31b8) { + names="addp\0"; + z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_Vn2d; + } else + if(((ic32_8)&0xff20fc)==0x5e20fc) { + names="frecps\0frsqrts\0"; + op=((ic32_23)&0x1); z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xff209c)==0x5e2090) { + names="sqdmlal\0sqdmlsl\0sqdmull\0"; + op=((ic32_13)&0x3); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz2n; args[2]=disasm_arg_FPz2m; + } else + if(((ic32_8)&0xffc0e4)==0x5f40c0) { + names="sqdmulh\0sqrdmulh\0"; + op=((ic32_12)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz4n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc034)==0x5f4030) { + names="sqdmlal\0sqdmlsl\0sqdmull\0"; + op=((ic32_14)&0x3); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xff80dc)==0x5f0054) { + names="shl\0sqshl\0"; + op=((ic32_13)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Dt; args[1]=disasm_arg_Dn; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0xffc0e4)==0x5f80c0) { + names="sqdmulh\0sqrdmulh\0"; + op=((ic32_12)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz4n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffc034)==0x5f8030) { + names="sqdmlal\0sqdmlsl\0sqdmull\0"; + op=((ic32_14)&0x3); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_16)&0xffc0)==0x68c0) { + names="ldpsw\0"; + i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_Xm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_im4_opt; + } else + if(((ic32_16)&0xff40)==0x6940) { + names="ldpsw\0"; + p=((ic32_23)&0x1); i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_Xm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_im4_opt; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xffe084)==0x6e0004) { + names="ins\0"; + j=((ic32_16)&0x1f); k=((ic32_11)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj; args[1]=disasm_arg_offs; args[2]=disasm_arg_FPidx; args[3]=disasm_arg_offe; args[4]=disasm_arg_Vnj; args[5]=disasm_arg_offs; args[6]=disasm_arg_FPidxk; args[7]=disasm_arg_offe; + } else + if(((ic32_8)&0xff3fcc)==0x6e30c8) { + names="fmaxnmv\0?\0?\0fmaxv\0fminnmv\0?\0?\0fminv\0"; + op=((ic32_21)&0x4)|((ic32_12)&0x3); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_Vn4s; + } else + if(((ic32_8)&0xfff8fc)==0x6f00e4) { + names="movi\0"; + j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2d; args[1]=disasm_arg_imm64; + } else + if(((ic32_8)&0xfff8fc)==0x6f00f4) { + names="fmov\0"; + j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2d; args[1]=disasm_arg_F64; + } else + if(((ic32_8)&0xff200c)==0x782000) { + names="ldaddh\0ldclrh\0ldeorh\0ldseth\0ldsmaxh\0ldsminh\0ldumaxh\0lduminh\0swph\0?\0?\0?\0?\0?\0?\0?\0ldaddlh\0ldclrlh\0ldeorlh\0ldsetlh\0ldsmaxlh\0ldsminlh\0ldumaxlh\0lduminlh\0swplh\0?\0?\0?\0?\0?\0?\0?\0ldaddah\0ldclrah\0ldeorah\0ldsetah\0ldsmaxah\0ldsminah\0ldumaxah\0lduminah\0swpah\0?\0?\0?\0?\0?\0?\0?\0ldaddalh\0ldclralh\0ldeoralh\0ldsetalh\0ldsmaxalh\0ldsminalh\0ldumaxalh\0lduminalh\0swpalh\0"; + op=((ic32_18)&0x30)|((ic32_12)&0xf); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Wt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffdffc)==0x7e10c8) { + names="fmaxnmp\0"; + z=((ic32_21)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_Vnz; + } else + if(((ic32_8)&0xffe0f4)==0x7e4024) { + names="fcmge\0facge\0"; + op=((ic32_11)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xffa0f4)==0x7e20e4) { + names="fcmge\0facge\0"; + op=((ic32_11)&0x1); z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xffe0fc)==0x7ec014) { + names="fabd\0"; + m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xffe0f4)==0x7ec024) { + names="fcmgt\0facgt\0"; + op=((ic32_11)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_Hm; + } else + if(((ic32_8)&0xffa0fc)==0x7ea0d4) { + names="fabd\0"; + z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xffa0f4)==0x7ea0e4) { + names="fcmgt\0facgt\0"; + op=((ic32_11)&0x1); z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_FPm; + } else + if(((ic32_8)&0xff20f4)==0x7e0084) { + names="sqrdmlah\0sqrdmlsh\0"; + op=((ic32_11)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz2t; args[1]=disasm_arg_FPz2n; args[2]=disasm_arg_FPz2m; + } else + if(((ic32_8)&0xff3fcc)==0x7e30c8) { + names="?\0faddp\0?\0fmaxp\0fminnmp\0?\0?\0fminp\0"; + op=((ic32_21)&0x4)|((ic32_12)&0x3); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_Vnz; + } else + if(((ic32_8)&0xffc0d4)==0x7f40d0) { + names="sqrdmlah\0sqrdmlsh\0"; + op=((ic32_13)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xff80fc)==0x7f0064) { + names="sqshlu\0"; + j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Dt; args[1]=disasm_arg_Dn; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0xff80fc)==0x7f0074) { + names="uqshl\0"; + j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPjt2; args[1]=disasm_arg_FPjn2; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0xffc0d4)==0x7f80d0) { + names="sqrdmlah\0sqrdmlsh\0"; + op=((ic32_13)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xdf3f9c)==0x4e2108) { + names="?\0xtn2\0sqxtn2\0?\0?\0sqxtun2\0uqxtn2\0fcvtxn2\0"; + op=((ic32_27)&0x4)|((ic32_13)&0x3); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT3; + } else + if(((ic32_8)&0xdf20dc)==0x4e2010) { + names="saddw2\0ssubw2\0uaddw2\0usubw2\0"; + op=((ic32_28)&0x2)|((ic32_13)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT3; args[1]=disasm_arg_VnT3; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdf20dc)==0x4e2040) { + names="addhn2\0subhn2\0raddhn2\0rsubhn2\0"; + op=((ic32_28)&0x2)|((ic32_13)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT3; args[2]=disasm_arg_VmT3; + } else + if(((ic32_8)&0xdf20fc)==0x4e20e0) { + names="pmull2\0umull2\0"; + op=((ic32_29)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT4; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdf200c)==0x4e2000) { + names="saddl2\0saddw2\0ssubl2\0ssubw2\0addhn2\0sabal2\0subhn2\0sabdl2\0smlal2\0sqdmlal2\0smlsl2\0sqdmlsl2\0?\0sqdmull2\0pmull2\0?\0uaddl2\0uaddw2\0usubl2\0usubw2\0raddhn2\0uabal2\0rsubhn2\0uabdl2\0umlal2\0?\0umlsl2\0?\0?\0?\0umull2\0"; + op=((ic32_25)&0x10)|((ic32_12)&0xf); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_VtT3; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xdfc024)==0x4f4020) { + names="smlal2\0sqdmlal2\0smlsl2\0sqdmlsl2\0smull2\0sqdmull2\0?\0?\0umlal2\0?\0umlsl2\0?\0umull2\0"; + op=((ic32_26)&0x8)|((ic32_13)&0x6)|((ic32_12)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1;q=1; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xdf80e4)==0x4f0084) { + names="?\0rshrn2\0sqshrn2\0sqrshrn2\0sqshrun2\0sqrshrun2\0uqshrn2\0uqrshrn2\0"; + op=((ic32_27)&0x4)|((ic32_11)&0x3); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_VnTa; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdf80fc)==0x4f00a4) { + names="sshll2\0usshll2\0"; + op=((ic32_29)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + q=1; + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_VnTa; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0xdfc024)==0x4f8020) { + names="smlal2\0sqdmlal2\0smlsl2\0sqdmlsl2\0smull2\0sqdmull2\0?\0?\0umlal2\0?\0umlsl2\0?\0umull2\0"; + op=((ic32_26)&0x8)|((ic32_13)&0x6)|((ic32_12)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2;q=1; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xdfffcc)==0x5ef8c8) { + names="fcmgt\0fcmeq\0fcmlt\0?\0fcmge\0fcmle\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0xdfbfcc)==0x5ea0c8) { + names="fcmgt\0fcmeq\0fcmlt\0?\0fcmge\0fcmle\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0xdf7f8c)==0x5e7988) { + names="?\0?\0fcvtns\0fcvtms\0fcvtas\0scvtf\0?\0?\0?\0?\0fcvtps\0fcvtzs\0?\0frecpe\0?\0frecpx\0?\0?\0fcvtnu\0fcvtmu\0fcvtau\0ucvtf\0?\0?\0?\0?\0fcvtpu\0fcvtzu\0?\0frsqrte\0"; + op=((ic32_25)&0x10)|((ic32_20)&0x8)|((ic32_12)&0x7); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; + } else + if(((ic32_8)&0xdf3fcc)==0x5e2088) { + names="cmgt\0cmeq\0cmlt\0abs\0cmge\0cmle\0?\0neg\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0xdf3f3c)==0x5e2038) { + names="suqadd\0sqabs\0abs\0?\0usqadd\0sqneg\0neg\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_FPz3n; + } else + if(((ic32_8)&0xdf3f9c)==0x5e2108) { + names="?\0?\0sqxtn\0?\0?\0sqxtun\0uqxtn\0fcvtxn\0"; + op=((ic32_27)&0x4)|((ic32_13)&0x3); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_FPz4n; + } else + if(((ic32_8)&0xdf3f8c)==0x5e2188) { + names="?\0?\0fcvtns\0fcvtms\0fcvtas\0scvtf\0?\0?\0?\0?\0fcvtps\0fcvtzs\0?\0frecpe\0?\0frecpx\0?\0?\0fcvtnu\0fcvtmu\0fcvtau\0ucvtf\0?\0?\0?\0?\0fcvtpu\0fcvtzu\0?\0frsqrte\0"; + op=((ic32_25)&0x10)|((ic32_20)&0x8)|((ic32_12)&0x7); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; + } else + if(((ic32_8)&0xdf2004)==0x5e2004) { + names="?\0sqadd\0?\0?\0?\0sqsub\0cmgt\0cmge\0sshl\0sqshl\0srshl\0sqrshl\0?\0?\0?\0?\0add\0cmtst\0?\0?\0?\0?\0sqdmulh\0?\0?\0?\0?\0?\0?\0?\0?\0?\0?\0uqadd\0?\0?\0?\0uqsub\0cmhi\0cmhs\0ushl\0uqshl\0urshl\0uqrshl\0?\0?\0?\0?\0sub\0cmeq\0?\0?\0?\0?\0sqrdmulh\0"; + op=((ic32_24)&0x20)|((ic32_11)&0x1f); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_FPz3n; args[2]=disasm_arg_FPz3m; + } else + if(((ic32_8)&0xdfc034)==0x5f0010) { + names="fmla\0fmls\0fmul\0?\0?\0?\0fmulx\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_9)&0x4)|((ic32_20)&0x3); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Hn; args[2]=disasm_arg_VmHs; + } else + if(((ic32_8)&0xdf808c)==0x5f0004) { + names="sshr\0ssra\0srshr\0srsra\0?\0shl\0?\0sqshl\0ushr\0usra\0urshr\0ursra\0sri\0sli\0sqshlu\0uqshl\0"; + op=((ic32_26)&0x8)|((ic32_12)&0x7); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Dt; args[1]=disasm_arg_Dn; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdf80e4)==0x5f0084) { + names="?\0?\0sqshrn\0sqrshrn\0sqshrun\0sqrshrun\0uqshrn\0uqrshrn\0"; + op=((ic32_27)&0x4)|((ic32_11)&0x3); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPjt; args[1]=disasm_arg_FPnj; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdf80fc)==0x5f00e4) { + names="scvtf\0ucvtf\0"; + op=((ic32_29)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPjt2; args[1]=disasm_arg_FPjn2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdf80fc)==0x5f00fc) { + names="fcvtzs\0fcvtzu\0"; + op=((ic32_29)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPjt; args[1]=disasm_arg_FPjn2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xdfc034)==0x5f8010) { + names="fmla\0fmls\0fmul\0sqrdmulh\0?\0?\0fmulx\0sqrdmlah\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_10)&0x2)|((ic32_21)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_VmTs2; + } else + if(((ic32_8)&0xdfe034)==0x5fc010) { + names="fmla\0fmls\0fmul\0?\0?\0?\0fmulx\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_11)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPn; args[2]=disasm_arg_VmTs2; + } else + if(((ic32_8)&0xbfa07c)==0x8207c) { + names="casp\0caspl\0caspa\0caspal\0"; + op=((ic32_21)&0x2)|((ic32_15)&0x1); s=((ic32_30)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rd; args[1]=disasm_arg_Rd1; args[2]=disasm_arg_Rt; args[3]=disasm_arg_Rt1; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; + } else + if(((ic32_8)&0xbf3f7c)==0x81f7c) { + names="?\0?\0ldxrb\0ldaxrb\0stllrb\0stlrb\0ldlarb\0ldarb\0?\0?\0ldxrh\0ldaxrh\0stllrh\0stlrh\0ldlarh\0ldarh\0"; + op=((ic32_27)&0x8)|((ic32_21)&0x6)|((ic32_15)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfd0)==0xc0000) { + names="st4\0st1\0ld4\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbff0)==0xc0070) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfd0)==0xc0040) { + names="st3\0st1\0ld3\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfd0)==0xc0080) { + names="st2\0st1\0ld2\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfd0)==0xc9f00) { + names="st4\0st1\0ld4\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; args[7]=disasm_arg_Qi; + } else + if(((ic32_8)&0xbfbff0)==0xc9f70) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Qi1; + } else + if(((ic32_8)&0xbfbfd0)==0xc9f40) { + names="st3\0st1\0ld3\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; args[6]=disasm_arg_Qi3; + } else + if(((ic32_8)&0xbfbfd0)==0xc9f80) { + names="st2\0st1\0ld2\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_Qi2; + } else + if(((ic32_8)&0xbfa0d0)==0xc8000) { + names="st4\0st1\0ld4\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; args[7]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0f0)==0xc8070) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0d0)==0xc8040) { + names="st3\0st1\0ld3\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; args[6]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0d0)==0xc8080) { + names="st2\0st1\0ld2\0ld1\0"; + op=((ic32_21)&0x2)|((ic32_13)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbffff0)==0xd40c0) { + names="ld1r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbffff0)==0xd40e0) { + names="ld3r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xbffff0)==0xd60c0) { + names="ld2r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbffff0)==0xd60e0) { + names="ld4r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd0000) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtB; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd0020) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd0040) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd0060) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbffc)==0xd0084) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtD; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfec)==0xd0080) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtS; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbffc)==0xd00a4) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfec)==0xd00a0) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd2000) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd2020) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd2040) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfe0)==0xd2060) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbffc)==0xd2084) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfec)==0xd2080) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbffc)==0xd20a4) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfbfec)==0xd20a0) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbffff0)==0xddfc0) { + names="ld1r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_z; + } else + if(((ic32_8)&0xbffff0)==0xddfe0) { + names="ld3r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; args[6]=disasm_arg_z3; + } else + if(((ic32_8)&0xbfe0f0)==0xdc0c0) { + names="ld1r\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfe0f0)==0xdc0e0) { + names="ld3r\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; args[6]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbffff0)==0xdffc0) { + names="ld2r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_z2; + } else + if(((ic32_8)&0xbffff0)==0xdffe0) { + names="ld4r\0"; + q=((ic32_30)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; args[7]=disasm_arg_z4; + } else + if(((ic32_8)&0xbfe0f0)==0xde0c0) { + names="ld2r\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfe0f0)==0xde0e0) { + names="ld4r\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vt2T; args[2]=disasm_arg_Vt3T; args[3]=disasm_arg_Vt4T; args[4]=disasm_arg_offs; args[5]=disasm_arg_XnS; args[6]=disasm_arg_offe; args[7]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfbfe0)==0xd9f00) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtB; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i1; + } else + if(((ic32_8)&0xbfbfe0)==0xd9f20) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i3; + } else + if(((ic32_8)&0xbfbfe0)==0xd9f40) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i2; + } else + if(((ic32_8)&0xbfbfe0)==0xd9f60) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i6; + } else + if(((ic32_8)&0xbfbffc)==0xd9f84) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtD; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i8; + } else + if(((ic32_8)&0xbfbfec)==0xd9f80) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtS; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i4; + } else + if(((ic32_8)&0xbfbffc)==0xd9fa4) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i24; + } else + if(((ic32_8)&0xbfbfec)==0xd9fa0) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i12; + } else + if(((ic32_8)&0xbfa0e0)==0xd8000) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtB; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xd8020) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xd8040) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xd8060) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0fc)==0xd8084) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtD; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0ec)==0xd8080) { + names="st1\0ld1\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtS; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0fc)==0xd80a4) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0ec)==0xd80a0) { + names="st3\0ld3\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt3S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfbfe0)==0xdbf00) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i2; + } else + if(((ic32_8)&0xbfbfe0)==0xdbf20) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i4; + } else + if(((ic32_8)&0xbfbfe0)==0xdbf40) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i4; + } else + if(((ic32_8)&0xbfbfe0)==0xdbf60) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i8; + } else + if(((ic32_8)&0xbfbffc)==0xdbf84) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i16; + } else + if(((ic32_8)&0xbfbfec)==0xdbf80) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i8; + } else + if(((ic32_8)&0xbfbffc)==0xdbfa4) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i32; + } else + if(((ic32_8)&0xbfbfec)==0xdbfa0) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i16; + } else + if(((ic32_8)&0xbfa0e0)==0xda000) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xda020) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4B; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xda040) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0e0)==0xda060) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); z=((ic32_10)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4H; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0fc)==0xda084) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0ec)==0xda080) { + names="st2\0ld2\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0fc)==0xda0a4) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4D; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfa0ec)==0xda0a0) { + names="st4\0ld4\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); s=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4S; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_Xm; + } else + if(((ic32_8)&0xbfe0fc)==0xe0004) { + names="dup\0"; + q=((ic32_30)&0x1); j=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtjq; args[1]=disasm_arg_Vnj; args[2]=disasm_arg_offs; args[3]=disasm_arg_FPidx; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfe0ec)==0xe0000) { + names="tbl\0tbx\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vn116b; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbfe0ec)==0xe0020) { + names="tbl\0tbx\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vn216b; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbfe0ec)==0xe002c) { + names="smov\0umov\0"; + op=((ic32_12)&0x1); s=((ic32_30)&0x1); j=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Vnj; args[2]=disasm_arg_offs; args[3]=disasm_arg_FPidx; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfe0ec)==0xe0040) { + names="tbl\0tbx\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vn316b; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbfe0ec)==0xe0060) { + names="tbl\0tbx\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vn416b; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbfe0fc)==0xe401c) { + names="fmulx\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbfe0fc)==0xe4024) { + names="fcmeq\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbfffec)==0xe7988) { + names="frintn\0frintm\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbffffc)==0xe79f8) { + names="fabs\0"; + q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbfa0fc)==0xe201c) { + names="fmulx\0"; + q=((ic32_30)&0x1); z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_Vmzq; + } else + if(((ic32_8)&0xbfffec)==0xef988) { + names="frintp\0frintz\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbf7fcc)==0xe30c8) { + names="fmaxnmv\0?\0?\0fmaxv\0fminnmv\0?\0?\0fminv\0"; + op=((ic32_21)&0x4)|((ic32_12)&0x3); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_Ht; args[1]=disasm_arg_Vnzq2; + } else + if(((ic32_8)&0xbf60fc)==0xe403c) { + names="frecps\0frsqrts\0"; + op=((ic32_23)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbf0080)==0xe0000) { + names="?\0?\0?\0?\0?\0?\0uzp1\0?\0?\0?\0trn1\0?\0?\0?\0zip1\0?\0?\0?\0?\0?\0?\0?\0uzp2\0?\0?\0?\0trn2\0?\0?\0?\0zip2\0?\0?\0shadd\0?\0sqadd\0?\0srhadd\0?\0?\0?\0?\0?\0sqsub\0?\0cmgt\0?\0cmge\0?\0sshl\0?\0sqshl\0?\0srshl\0?\0sqrshl\0?\0smax\0?\0smin\0?\0sabd\0?\0saba\0"; + op=((ic32_16)&0x20)|((ic32_10)&0x1f); q=((ic32_30)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbff8fc)==0xf00e4) { + names="movi\0"; + q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_imm8; + } else + if(((ic32_8)&0xbff8fc)==0xf00f4) { + names="fmov\0"; + q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_F32; + } else + if(((ic32_8)&0xbff8fc)==0xf00fc) { + names="fmov\0"; + q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_F16; + } else + if(((ic32_8)&0xbfc0a4)==0xf4080) { + names="mul\0?\0sqdmulh\0sqrdmulh\0"; + op=((ic32_13)&0x2)|((ic32_12)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); q=((ic32_30)&0x1); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xbf80cc)==0xf0004) { + names="sshr\0ssra\0srshr\0srsra\0"; + op=((ic32_12)&0x3); q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xbf80fc)==0xf00e4) { + names="scvtf\0"; + q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xbf80fc)==0xf00fc) { + names="fcvtzs\0"; + q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xbfc0a4)==0xf8080) { + names="mul\0fmul\0sqdmulh\0sqrdmulh\0"; + op=((ic32_13)&0x2)|((ic32_12)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_24)&0xbf)==0x18) { + names="ldr\0"; + s=((ic32_30)&0x1); i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_labeli4; + } else + if(((ic32_8)&0xbfe0fc)==0x1e000c) { + names="dup\0"; + q=((ic32_30)&0x1); j=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + s=q; + args[0]=disasm_arg_Vtjq; args[1]=disasm_arg_Rn; + } else + if(((ic32_8)&0xbfe084)==0x2e0000) { + names="ext\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); i=((ic32_14)&1?(0xffffffff<<4):0)|((ic32_11)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; args[3]=disasm_arg_i; + } else + if(((ic32_8)&0xbfe0f4)==0x2e4024) { + names="fcmge\0facge\0"; + op=((ic32_11)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbffffc)==0x2e7998) { + names="frintx\0"; + q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbfbffc)==0x2e2058) { + names="not\0rbit\0"; + op=((ic32_22)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbfe0fc)==0x2ec014) { + names="fabd\0"; + q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbfe0f4)==0x2ec024) { + names="fcmgt\0facgt\0"; + op=((ic32_11)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmH1; + } else + if(((ic32_8)&0xbffffc)==0x2ef8f8) { + names="fneg\0"; + q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbfffec)==0x2ef988) { + names="frinta\0frinti\0"; + op=((ic32_12)&0x1); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbffffc)==0x2ef9f8) { + names="fsqrt\0"; + q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0xbf2004)==0x2e2004) { + names="uhadd\0uqadd\0urhadd\0?\0uhsub\0uqsub\0cmhi\0cmhs\0ushl\0uqshl\0urshl\0uqrshl\0umax\0umin\0uabd\0uaba\0sub\0cmeq\0mls\0pmul\0umaxp\0uminp\0cqrdmulh\0"; + op=((ic32_11)&0x1f); q=((ic32_30)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0xbfc0d4)==0x2f40d0) { + names="sqrdmlah\0sqrdmlsh\0"; + op=((ic32_13)&0x1); j=((ic32_9)&0x4)|((ic32_20)&0x3); q=((ic32_30)&0x1); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xbf80fc)==0x2f00fc) { + names="fcvtzu\0"; + q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xbf800c)==0x2f0004) { + names="ushr\0usra\0urshr\0ursra\0sri\0sli\0sqshlu\0uqshl\0?\0?\0?\0?\0?\0?\0ucvtf\0"; + op=((ic32_12)&0xf); q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shrshift; + } else + if(((ic32_8)&0xbfc0d4)==0x2f80d0) { + names="sqrdmlah\0sqrdmlsh\0"; + op=((ic32_13)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_Vtz; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xbf00b4)==0x2f0000) { + names="mla\0mls\0"; + op=((ic32_14)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); q=((ic32_30)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xbfa00c)==0x380004) { + names="strb\0ldrb\0strh\0ldrh\0"; + op=((ic32_29)&0x2)|((ic32_22)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i_opt; + } else + if(((ic32_8)&0xbfa004)==0x380004) { + names="strb\0ldrb\0strh\0ldrh\0"; + op=((ic32_29)&0x2)|((ic32_22)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); p=((ic32_11)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa00c)==0x382008) { + names="strb\0ldrb\0strh\0ldrh\0"; + op=((ic32_29)&0x2)|((ic32_22)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountj; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa00c)==0x388004) { + names="ldrsb\0ldrsh\0"; + op=((ic32_30)&0x1); s=((ic32_22)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_nRt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i_opt; + } else + if(((ic32_8)&0xbfa004)==0x388000) { + names="ldursb\0?\0ldursh\0ldtrsh\0"; + op=((ic32_29)&0x2)|((ic32_11)&0x1); s=((ic32_22)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_nRt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa004)==0x388004) { + names="ldrsb\0ldrsh\0"; + op=((ic32_30)&0x1); s=((ic32_22)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); p=((ic32_11)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_nRt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa00c)==0x38a008) { + names="ldrsb\0ldrsh\0"; + op=((ic32_30)&0x1); s=((ic32_22)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_nRt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountj; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xbf2004)==0x380000) { + names="sturb\0sttrb\0ldurb\0ldtrb\0?\0ldtrsb\0?\0ldtrsb\0sturh\0sttrh\0ldurh\0ldtrh\0"; + op=((ic32_27)&0x8)|((ic32_21)&0x6)|((ic32_11)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0xbf80)==0x3900) { + names="strb\0ldrb\0strh\0ldrh\0"; + op=((ic32_29)&0x2)|((ic32_22)&0x1); j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0xbf80)==0x3980) { + names="ldrsb\0ldrsh\0"; + op=((ic32_30)&0x1); s=((ic32_22)&0x1); j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_nRt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0x9fffcc)==0xef8c8) { + names="fcmgt\0fcmeq\0fcmlt\0?\0fcmge\0fcmle\0?\0fneg\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0x9fbfcc)==0xea0c8) { + names="fcmgt\0fcmeq\0fcmlt\0?\0fcmge\0fcmle\0?\0fneg\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); q=((ic32_30)&0x1); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0x9f60c4)==0xe4004) { + names="fmaxnm\0fmla\0fadd\0fmulx\0fcmeq\0?\0fmax\0frecps\0fminnm\0fmls\0fsub\0?\0?\0?\0fmin\0frsqrts\0fmaxnmp\0?\0faddp\0fmul\0fcmge\0facge\0fmaxp\0fdiv\0fminnmp\0?\0fabd\0?\0fcmgt\0facgt\0fminp\0"; + op=((ic32_25)&0x10)|((ic32_20)&0x8)|((ic32_11)&0x7); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0x9f7f8c)==0xe7988) { + names="frintn\0frintm\0fcvtns\0fcvtms\0fcvtas\0scvtf\0?\0fabs\0frintp\0frintz\0fcvtps\0fcvtzs\0?\0frecpe\0?\0frecpx\0?\0frintx\0fcvtnu\0fcvtmu\0fcvtau\0ucvtf\0?\0?\0frinta\0frinti\0fcvtpu\0fcvtzu\0?\0frsqrte\0?\0fsqrt\0"; + op=((ic32_25)&0x10)|((ic32_20)&0x8)|((ic32_12)&0x7); q=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; + } else + if(((ic32_8)&0x9f20fc)==0xe0094) { + names="sdot\0udot\0"; + op=((ic32_29)&0x1); q=((ic32_30)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_Vmzq; + } else + if(((ic32_8)&0x9f3fbc)==0xe2028) { + names="saddlp\0sadalp\0uaddlp\0uadalp\0"; + op=((ic32_28)&0x2)|((ic32_14)&0x1); q=((ic32_30)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtzq2; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0x9f3fcc)==0xe2088) { + names="cmgt\0cmeq\0cmlt\0abs\0cmge\0cmle\0?\0neg\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); q=((ic32_30)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_simd0; + } else + if(((ic32_8)&0x9f3f0c)==0xe2008) { + names="rev64\0rev16\0saddlp\0suqadd\0cls\0cnt\0sadalp\0sqabs\0cmgt\0cmeq\0cmlt\0abs\0?\0?\0?\0?\0rev32\0?\0uaddlp\0usqadd\0clz\0?\0uadalp\0sqneg\0cmge\0cmle\0?\0neg\0"; + op=((ic32_25)&0x10)|((ic32_12)&0xf); q=((ic32_30)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0x9f3e8c)==0xe2088) { + names="?\0?\0?\0?\0?\0?\0?\0?\0frintn\0frintm\0fcvtns\0fcvtms\0fcvtas\0scvtf\0?\0fabs\0?\0?\0?\0?\0fcmgt\0fcmeq\0fcmlt\0?\0frintp\0frintz\0fcvtps\0fcvtzs\0urecpe\0frecpe\0?\0frecpx\0?\0?\0?\0?\0?\0?\0?\0?\0?\0frintx\0fcvtnu\0fcvtmu\0fcvtau\0ucvtf\0?\0?\0?\0?\0?\0?\0fcmge\0fcmle\0?\0fneg\0frinta\0frinti\0fcvtpu\0fcvtzu\0?\0frsqrte\0?\0fsqrt\0"; + op=((ic32_24)&0x20)|((ic32_19)&0x10)|((ic32_13)&0x8)|((ic32_12)&0x7); q=((ic32_30)&0x1); z=((ic32_22)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; + } else + if(((ic32_8)&0x9f3ffc)==0xe3038) { + names="saddlv\0uaddlv\0"; + op=((ic32_29)&0x1); q=((ic32_30)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz4t; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0x9f3eec)==0xe30a8) { + names="smaxv\0?\0sminv\0addv\0umaxv\0?\0uminv\0"; + op=((ic32_27)&0x4)|((ic32_15)&0x2)|((ic32_12)&0x1); q=((ic32_30)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz3t; args[1]=disasm_arg_VnT; + } else + if(((ic32_8)&0x9f20fc)==0xe201c) { + names="and\0bic\0orr\0orn\0eor\0bsl\0bit\0bif\0"; + op=((ic32_27)&0x4)|((ic32_22)&0x3); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0x9f20c4)==0xe20c4) { + names="fmaxnm\0fmla\0fadd\0?\0fcmeq\0?\0fmax\0frecps\0fminnm\0fmls\0fsub\0?\0?\0?\0fmin\0frsqrts\0fmaxnmp\0?\0faddp\0fmul\0fcmge\0facge\0fmaxp\0fdiv\0fminnmp\0?\0fabd\0?\0fcmgt\0facgt\0fminp\0"; + op=((ic32_25)&0x10)|((ic32_20)&0x8)|((ic32_11)&0x7); q=((ic32_30)&0x1); z=((ic32_22)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_Vmzq; + } else + if(((ic32_8)&0x9f00c4)==0xe0084) { + names="?\0?\0sdot\0?\0?\0?\0?\0?\0add\0cmtst\0mla\0mul\0smaxp\0sminp\0sqdmulh\0addp\0sqrdmlah\0sqrdmlsh\0udot\0?\0?\0?\0?\0?\0sub\0cmeq\0mls\0pmul\0umaxp\0uminp\0cqrdmulh\0"; + op=((ic32_25)&0x10)|((ic32_18)&0x8)|((ic32_11)&0x7); q=((ic32_30)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtT; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmT; + } else + if(((ic32_8)&0x9ff88c)==0xf0004) { + names="movi\0orr\0mvni\0bic\0"; + op=((ic32_28)&0x2)|((ic32_12)&0x1); q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); k=((ic32_13)&0x3); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_imm8; args[2]=disasm_arg_amountk_opt; + } else + if(((ic32_8)&0x9ff8cc)==0xf0084) { + names="movi\0orr\0mvni\0bic\0"; + op=((ic32_28)&0x2)|((ic32_12)&0x1); q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); k=((ic32_13)&0x1); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_imm8; args[2]=disasm_arg_amountk_opt; + } else + if(((ic32_8)&0x9ff8ec)==0xf00c4) { + names="movi\0mvni\0"; + op=((ic32_29)&0x1); q=((ic32_30)&0x1); j=((ic32_11)&0xe0)|((ic32_5)&0x1f); k=((ic32_12)&0x1); t=((ic32)&0x1f); + z=2; + args[0]=disasm_arg_VtT; args[1]=disasm_arg_imm8; args[2]=disasm_arg_amountk2_opt; + } else + if(((ic32_8)&0x9fc034)==0xf0010) { + names="fmla\0fmls\0fmul\0?\0?\0?\0fmulx\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_9)&0x4)|((ic32_20)&0x3); q=((ic32_30)&0x1); m=((ic32_16)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_VtH1; args[1]=disasm_arg_VnH1; args[2]=disasm_arg_VmHs; + } else + if(((ic32_8)&0x9f80cc)==0xf0044) { + names="?\0shl\0?\0sqshl\0sri\0sli\0sqshlu\0uqshl\0"; + op=((ic32_27)&0x4)|((ic32_12)&0x3); q=((ic32_30)&0x1); j=((ic32_16)&0x7f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vtj2; args[1]=disasm_arg_Vnj2; args[2]=disasm_arg_shlshift; + } else + if(((ic32_8)&0x9fc0f4)==0xf80e0) { + names="sdot\0udot\0"; + op=((ic32_29)&0x1); j=((ic32_10)&0x2)|((ic32_21)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_VnT; args[2]=disasm_arg_VmTs4b; + } else + if(((ic32_8)&0x9fc034)==0xf8010) { + names="fmla\0fmls\0fmul\0sqrdmulh\0?\0?\0fmulx\0sqrdmlah\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_10)&0x2)|((ic32_21)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_VmTs2; + } else + if(((ic32_8)&0x9fe034)==0xfc010) { + names="fmla\0fmls\0fmul\0?\0?\0?\0fmulx\0"; + op=((ic32_27)&0x4)|((ic32_14)&0x3); j=((ic32_11)&0x1); q=((ic32_30)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=1; + args[0]=disasm_arg_Vtzq; args[1]=disasm_arg_Vnzq; args[2]=disasm_arg_VmTs2; + } else + if(((ic32_8)&0xffe07c)==0x88007c) { + names="stxr\0stlxr\0"; + op=((ic32_15)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Wt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_24)&0xff)==0x98) { + names="ldrsw\0"; + i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_labeli4; + } else + if(((ic32_8)&0xff607c)==0x9b207c) { + names="smull\0smnegl\0umull\0umnegl\0"; + op=((ic32_22)&0x2)|((ic32_15)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_Wn; args[2]=disasm_arg_Wm; + } else + if(((ic32_16)&0xff60)==0x9b20) { + names="smaddl\0smsubl\0umaddl\0umsubl\0"; + op=((ic32_22)&0x2)|((ic32_15)&0x1); m=((ic32_16)&0x1f); d=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_Wn; args[2]=disasm_arg_Wm; args[3]=disasm_arg_Xd; + } else + if(((ic32_8)&0xff60fc)==0x9b407c) { + names="smulh\0umulh\0"; + op=((ic32_23)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_Xn; args[2]=disasm_arg_Xm; + } else + if(((ic32_8)&0xffe00c)==0xb88004) { + names="ldrsw\0"; + i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i_opt; + } else + if(((ic32_8)&0xffe004)==0xb88004) { + names="ldrsw\0"; + i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); p=((ic32_11)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffe00c)==0xb8a008) { + names="ldrsw\0"; + m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountj2; args[5]=disasm_arg_offe; + } else + if(((ic32_16)&0xffc0)==0xb980) { + names="ldrsw\0"; + j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffc080)==0xce0000) { + names="eor3\0bcax\0"; + op=((ic32_21)&0x1); m=((ic32_16)&0x1f); d=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt16b; args[1]=disasm_arg_Vn16b; args[2]=disasm_arg_Vm16b; args[3]=disasm_arg_Vd16b; + } else + if(((ic32_8)&0xffe080)==0xce4000) { + names="sm3ss1\0"; + m=((ic32_16)&0x1f); d=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; args[2]=disasm_arg_Vm4s; args[3]=disasm_arg_Vd4s; + } else + if(((ic32_8)&0xffe0c0)==0xce4080) { + names="sm3tt1a\0sm3tt1b\0sm3tt2a\0sm3tt2b\0"; + op=((ic32_10)&0x3); m=((ic32_16)&0x1f); j=((ic32_12)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + z=0; + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; args[2]=disasm_arg_VmTs; + } else + if(((ic32_8)&0xffe0f8)==0xce6080) { + names="sha512h\0sha512h2\0"; + op=((ic32_10)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Qt; args[1]=disasm_arg_Qn; args[2]=disasm_arg_Vm2d; + } else + if(((ic32_8)&0xffe0f8)==0xce6088) { + names="sha512su1\0rax1\0"; + op=((ic32_10)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2d; args[1]=disasm_arg_Vn2d; args[2]=disasm_arg_Vm2d; + } else + if(((ic32_8)&0xffe0f0)==0xce60c0) { + names="sm3partw1\0sm3partw2\0sm4ekey\0"; + op=((ic32_10)&0x3); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; args[2]=disasm_arg_Vm4s; + } else + if(((ic32_8)&0xfffffc)==0xcec080) { + names="sha512su0\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt2d; args[1]=disasm_arg_Vn2d; + } else + if(((ic32_8)&0xfffffc)==0xcec084) { + names="sm4e\0"; + n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt4s; args[1]=disasm_arg_Vn4s; + } else + if(((ic32_16)&0xffc0)==0xd400) { + names="?\0svc\0hvc\0smc\0brk\0"; + op=((ic32_19)&0x4)|((ic32)&0x3); i=((ic32_20)&1?(0xffffffff<<16):0)|((ic32_5)&0xffff); + args[0]=disasm_arg_i; + } else + if((ic32&0xffe00003)==0xd4400000) { + names="hlt\0"; + } else + if(((ic32_16)&0xffe0)==0xd4a0) { + names="?\0dcsp1\0dcps2\0dcps3\0"; + op=((ic32)&0x3); i=((ic32_20)&1?(0xffffffff<<16):0)|((ic32_5)&0xffff); + args[0]=disasm_arg_i_opt; + } else + if((ic32&0xfffffd1f)==0xd503201f) { + names="nop\0yield\0wfe\0wfi\0sev\0sevl\0?\0?\0esb\0psc\0"; + op=((ic32>>6)&0x8)|((ic32_5)&0x7); + } else + if((ic32&0xfffff0ff)==0xd503305f) { + names="clrex\0"; + i=((ic32_11)&1?(0xffffffff<<4):0)|((ic32_8)&0xf); + args[0]=disasm_arg_i_opt; + } else + if((ic32&0xfffff09f)==0xd503309f) { + names="dsb\0dmb\0?\0isb\0"; + op=((ic32_5)&0x3); j=((ic32_8)&0xf); + args[0]=disasm_arg_sh; + } else + if((ic32&0xfff8f01f)==0xd500401f) { + names="msr\0"; + i=((ic32_11)&1?(0xffffffff<<4):0)|((ic32_8)&0xf); p=((ic32_5)&0x7); + args[0]=disasm_arg_pstate; args[1]=disasm_arg_i; + } else + if((ic32&0xffffff80)==0xd5087600) { + names="dc\0"; + d=((ic32_5)&0x3); t=((ic32)&0x1f); + args[0]=disasm_arg_dc0; args[1]=disasm_arg_Xt; + } else + if((ic32&0xffffff80)==0xd5087800) { + names="at\0"; + a=((ic32_5)&0x3); t=((ic32)&0x1f); + args[0]=disasm_arg_a0; args[1]=disasm_arg_Xt; + } else + if(((ic32_8)&0xffffff)==0xd50879) { + names="at\0"; + a=((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_a1; args[1]=disasm_arg_Xt; + } else + if((ic32&0xfffffbe0)==0xd5087a40) { + names="dc\0"; + d=((ic32_10)&0x1); t=((ic32)&0x1f); + args[0]=disasm_arg_dc1; args[1]=disasm_arg_Xt; + } else + if((ic32&0xffffffe0)==0xd50b7420) { + names="dc\0"; + t=((ic32)&0x1f); + args[0]=disasm_arg_ZVA; args[1]=disasm_arg_Xt; + } else + if((ic32&0xfffffae0)==0xd50b7a20) { + names="dc\0"; + d=((ic32_9)&0x2)|((ic32_8)&0x1); t=((ic32)&0x1f); + args[0]=disasm_arg_dc2; args[1]=disasm_arg_Xt; + } else + if((ic32&0xfffcfbc0)==0xd5087100) { + names="ic\0"; + c=((ic32_15)&0x2)|((ic32_10)&0x1); t=((ic32)&0x1f); + args[0]=disasm_arg_ic; args[1]=disasm_arg_Xt_opt; + } else + if((ic32&0xfffffb60)==0xd50c8020) { + names="tlbi\0"; + n=((ic32_9)&0x2)|((ic32>>7)&0x1); t=((ic32)&0x1f); + args[0]=disasm_arg_tl1; args[1]=disasm_arg_Xt_opt; + } else + if((ic32&0xfffffb40)==0xd50e8300) { + names="tlbi\0"; + n=((ic32_8)&0x4)|((ic32>>6)&0x2)|((ic32_5)&0x1); t=((ic32)&0x1f); + args[0]=disasm_arg_tl2; args[1]=disasm_arg_Xt_opt; + } else + if(((ic32_8)&0xfffdff)==0xd50c78) { + names="at\0"; + a=((ic32_14)&0x8)|((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_a2; args[1]=disasm_arg_Xt; + } else + if(((ic32_8)&0xfffbfb)==0xd50883) { + names="tlbi\0"; + n=((ic32_14)&0x10)|((ic32>>7)&0x8)|((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_tl0; args[1]=disasm_arg_Xt_opt; + } else + if(((ic32_16)&0xffe0)==0xd500) { + names="msr\0"; + p=((ic32_19)&0x3); k=((ic32_16)&0x7); n=((ic32_12)&0xf); m=((ic32_8)&0xf); j=((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_sysreg; args[1]=disasm_arg_Xt; + } else + if(((ic32_16)&0xfff8)==0xd528) { + names="sysl\0"; + i=((ic32_18)&1?(0xffffffff<<3):0)|((ic32_16)&0x7); n=((ic32_12)&0xf); m=((ic32_8)&0xf); j=((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_i; args[2]=disasm_arg_Cn; args[3]=disasm_arg_Cm; args[4]=disasm_arg_j; + } else + if(((ic32_16)&0xffe0)==0xd520) { + names="mrs\0"; + p=((ic32_19)&0x3); k=((ic32_16)&0x7); n=((ic32_12)&0xf); m=((ic32_8)&0xf); j=((ic32_5)&0x7); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_sysreg; + } else + if((ic32&0xff9ffc1f)==0xd61f0000) { + names="br\0blr\0ret\0"; + op=((ic32_21)&0x3); n=((ic32_5)&0x1f); + args[0]=disasm_arg_Xn; + } else + if((ic32&0xffdfffff)==0xd69f03e0) { + names="eret\0drps\0"; + op=((ic32_21)&0x1); + } else + if(((ic32_24)&0xff)==0xd8) { + names="prfm\0"; + i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_prf_op; args[1]=disasm_arg_labeli4; + } else + if(((ic32_8)&0xffe00c)==0xf88000) { + names="prfum\0"; + i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_prf_op; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xffe00c)==0xf8a008) { + names="prfm\0"; + m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_prf_op; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountj3; args[5]=disasm_arg_offe; + } else + if(((ic32_16)&0xffc0)==0xf980) { + names="prfm\0"; + j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_prf_op; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0xbfe0)==0x8820) { + names="stxp\0stlxp\0"; + op=((ic32_15)&0x1); s=((ic32_30)&0x1); d=((ic32_16)&0x1f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Wd; args[1]=disasm_arg_Rt; args[2]=disasm_arg_Rm; args[3]=disasm_arg_offs; args[4]=disasm_arg_XnS; args[5]=disasm_arg_offe; + } else + if(((ic32_16)&0xbfff)==0x887f) { + names="ldxp\0ldaxp\0"; + op=((ic32_15)&0x1); s=((ic32_30)&0x1); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa07c)==0x88207c) { + names="cas\0casl\0casa\0casal\0"; + op=((ic32_21)&0x2)|((ic32_15)&0x1); s=((ic32_30)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rd; args[1]=disasm_arg_Rt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbf3f7c)==0x881f7c) { + names="?\0?\0ldxr\0ldaxr\0stllr\0stlr\0ldlar\0ldar\0"; + op=((ic32_21)&0x6)|((ic32_15)&0x1); s=((ic32_30)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa00c)==0xb80004) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); s=((ic32_30)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i_opt; + } else + if(((ic32_8)&0xbfa004)==0xb80000) { + names="stur\0sttr\0ldur\0ldtr\0"; + op=((ic32_21)&0x2)|((ic32_11)&0x1); s=((ic32_30)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa004)==0xb80004) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); s=((ic32_30)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); p=((ic32_11)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0xbfa00c)==0xb82008) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); s=((ic32_30)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountjs; args[5]=disasm_arg_offe; + } else + if(((ic32_8)&0xbf200c)==0xb82000) { + names="ldadd\0ldclr\0ldeor\0ldset\0ldsmax\0ldsmin\0ldumax\0ldumin\0swp\0?\0?\0?\0?\0?\0?\0?\0ldaddl\0ldclrl\0ldeorl\0ldsetl\0ldsmaxl\0ldsminl\0ldumaxl\0lduminl\0swpl\0?\0?\0?\0?\0?\0?\0?\0ldadda\0ldclra\0ldeora\0ldseta\0ldsmaxa\0ldsmina\0ldumaxa\0ldumina\0swpa\0?\0?\0?\0?\0?\0?\0?\0ldaddal\0ldclral\0ldeoral\0ldsetal\0ldsmaxal\0ldsminal\0ldumaxal\0lduminal\0swpal\0"; + op=((ic32_18)&0x30)|((ic32_12)&0xf); s=((ic32_30)&0x1); d=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rd; args[1]=disasm_arg_Rt; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0xbf80)==0xb900) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); s=((ic32_30)&0x1); j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0x7fa0)==0x1380) { + names="extr\0"; + s=((ic32_31)&0x1); m=((ic32_16)&0x1f); i=((ic32_15)&1?(0xffffffff<<6):0)|((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; args[3]=disasm_arg_i; + } else + if(((ic32_24)&0x7c)==0x14) { + names="b\0bl\0"; + op=((ic32_31)&0x1); i=((ic32_25)&1?(0xffffffff<<26):0)|((ic32)&0x3ffffff); + args[0]=disasm_arg_labeli4; + } else + if(((ic32_8)&0x7fe0fc)==0x1a0000) { + names="adc\0"; + s=((ic32_31)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; + } else + if(((ic32_8)&0x7fe080)==0x1ac000) { + names="?\0?\0udiv\0sdiv\0?\0?\0?\0?\0lslv\0lsrv\0asrv\0rorv\0?\0?\0?\0?\0crc32b\0crc32h\0crc32w\0crc32x\0crc32cb\0crc32ch\0crc32cw\0crc32cx\0"; + op=((ic32_10)&0x1f); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; + } else + if(((ic32_8)&0x7fe07c)==0x1b007c) { + names="mul\0mneg\0"; + op=((ic32_15)&0x1); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; + } else + if(((ic32_16)&0x7fe0)==0x1b00) { + names="madd\0msub\0"; + op=((ic32_15)&0x1); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); d=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; args[3]=disasm_arg_Rd; + } else + if(((ic32_8)&0x7ffffc)==0x1eae00) { + names="fmov\0"; + s=((ic32_31)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Vn1d; + } else + if(((ic32_8)&0x7ffffc)==0x1eaf00) { + names="fmov\0"; + s=((ic32_31)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Vt1d; args[1]=disasm_arg_Rn; + } else + if(((ic32_16)&0x7f3e)==0x1e02) { + names="scvtf\0ucvtf\0"; + op=((ic32_16)&0x1); s=((ic32_31)&0x1); z=((ic32_22)&0x3); j=((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_Rn; args[2]=disasm_arg_fbits; + } else + if(((ic32_16)&0x7f3e)==0x1e18) { + names="fcvtzs\0fcvtzu\0"; + op=((ic32_16)&0x1); s=((ic32_31)&0x1); z=((ic32_22)&0x3); j=((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_FPz5n; args[2]=disasm_arg_fbits; + } else + if(((ic32_8)&0x7f3afc)==0x1e2200) { + names="scvtf\0ucvtf\0fmov\0fmov\0"; + op=((ic32>>17)&0x2)|((ic32_16)&0x1); s=((ic32_31)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPz5t; args[1]=disasm_arg_Rn; + } else + if(((ic32_8)&0x7f30fc)==0x1e2000) { + names="fcvtns\0fcvtnu\0scvtf\0ucvtf\0fcvtas\0fcvtau\0fmov\0fmov\0fcvtns\0fcvtnu\0"; + op=((ic32_16)&0xf); s=((ic32_31)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_FPz5n; + } else + if(((ic32_8)&0x7f3efc)==0x1e3000) { + names="fcvtms\0fcvtmu\0"; + op=((ic32_16)&0x1); s=((ic32_31)&0x1); z=((ic32_22)&0x3); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_FPz5n; + } else + if(((ic32_16)&0x7f80)==0x2880) { + names="stp\0ldp\0"; + op=((ic32_22)&0x1); s=((ic32_31)&0x1); i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_is4_opt; + } else + if(((ic32_24)&0x7e)==0x28) { + names="stnp\0ldnp\0stp\0ldp\0"; + op=((ic32_23)&0x2)|((ic32_22)&0x1); s=((ic32_31)&0x1); p=((ic32_23)&0x1); i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_is4_opt; args[5]=disasm_arg_offe; + } else + if(((ic32_24)&0x7e)==0x34) { + names="cbz\0cbnz\0"; + op=((ic32_24)&0x1); s=((ic32_31)&0x1); i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_labeli4; + } else + if(((ic32_24)&0x7e)==0x36) { + names="tbz\0tbnz\0"; + op=((ic32_24)&0x1); b=((ic32_26)&0x20)|((ic32_19)&0x1f); i=((ic32_18)&1?(0xffffffff<<14):0)|((ic32_5)&0x3fff); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_b; args[2]=disasm_arg_labeli4; + } else + if(((ic32_8)&0x7fe004)==0x388000) { + names="?\0ldtrsb\0ldursw\0ldtrsw\0"; + op=((ic32_30)&0x2)|((ic32_11)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if((ic32&0x7fe0ffe0)==0x5a0003e0) { + names="ngc\0"; + s=((ic32_31)&0x1); m=((ic32_16)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rm; + } else + if(((ic32_8)&0x7ffff8)==0x5ac008) { + names="rev\0"; + s=((ic32_31)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; + } else + if(((ic32_8)&0x7fffe8)==0x5ac000) { + names="rbit\0rev16\0clz\0cls\0"; + op=((ic32_11)&0x2)|((ic32_10)&0x1); s=((ic32_31)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; + } else + if(((ic32_8)&0x3fe008)==0x1a8000) { + names="csel\0csinc\0csinv\0csneg\0"; + op=((ic32_29)&0x2)|((ic32_10)&0x1); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); c=((ic32_12)&0xf); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; args[3]=disasm_arg_c; + } else + if(((ic32_24)&0x3f)==0x1c) { + names="ldr\0"; + z=((ic32_30)&0x3); i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_labeli4; + } else + if((ic32&0x3fe0001f)==0x2b20001f) { + names="cmn\0cmp\0"; + op=((ic32_30)&0x1); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_10)&0x7); n=((ic32_5)&0x1f); + args[0]=disasm_arg_RnS; args[1]=disasm_arg_Rsom; args[2]=disasm_arg_exts; + } else + if(((ic32_16)&0x3f80)==0x2c80) { + names="stp\0ldp\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_offe; args[5]=disasm_arg_iz4_opt; + } else + if(((ic32_24)&0x3e)==0x2c) { + names="stnp\0ldnp\0stp\0ldp\0"; + op=((ic32_23)&0x2)|((ic32_22)&0x1); z=((ic32_30)&0x3); p=((ic32_23)&0x1); i=((ic32_21)&1?(0xffffffff<<7):0)|((ic32_15)&0x7f); m=((ic32_10)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPt; args[1]=disasm_arg_FPm; args[2]=disasm_arg_offs; args[3]=disasm_arg_XnS; args[4]=disasm_arg_iz4_opt; args[5]=disasm_arg_offe; + } else + if((ic32&0x3fe00c10)==0x3a400000) { + names="ccmn\0ccmp\0"; + op=((ic32_30)&0x1); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); c=((ic32_12)&0xf); n=((ic32_5)&0x1f); j=((ic32)&0xf); + args[0]=disasm_arg_Rn; args[1]=disasm_arg_Rm; args[2]=disasm_arg_j; args[3]=disasm_arg_c; + } else + if((ic32&0x3fe00c10)==0x3a400800) { + names="ccmn\0ccmp\0"; + op=((ic32_30)&0x1); s=((ic32_31)&0x1); b=((ic32_16)&0x1f); c=((ic32_12)&0xf); n=((ic32_5)&0x1f); j=((ic32)&0xf); + args[0]=disasm_arg_Rn; args[1]=disasm_arg_b; args[2]=disasm_arg_j; args[3]=disasm_arg_c; + } else + if(((ic32_8)&0x3f200c)==0x3c0000) { + names="stur\0ldur\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); s=((ic32_23)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPst; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0x3f200c)==0x3c0004) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); s=((ic32_23)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPst; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_offe; args[4]=disasm_arg_i_opt; + } else + if(((ic32_8)&0x3f2004)==0x3c0004) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); s=((ic32_23)&0x1); i=((ic32_20)&1?(0xffffffff<<9):0)|((ic32_12)&0x1ff); p=((ic32_11)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPst; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_i_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_8)&0x3f200c)==0x3c2008) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); s=((ic32_23)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_12)&0x1); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPst; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_Rom; args[4]=disasm_arg_amountz; args[5]=disasm_arg_offe; + } else + if(((ic32_24)&0x3f)==0x3d) { + names="str\0ldr\0"; + op=((ic32_22)&0x1); z=((ic32_30)&0x3); s=((ic32_23)&0x1); j=((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_FPst; args[1]=disasm_arg_offs; args[2]=disasm_arg_XnS; args[3]=disasm_arg_j_opt; args[4]=disasm_arg_offe; + } else + if(((ic32_16)&0x1fe0)==0xb20) { + names="add\0adds\0sub\0subs\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); o=((ic32_13)&0x7); j=((ic32_10)&0x7); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_RtS; args[1]=disasm_arg_RnS; args[2]=disasm_arg_Rsom; args[3]=disasm_arg_exts; + } else + if(((ic32_24)&0x1e)==0xa) { + names="and\0bic\0add\0?\0orr\0orn\0adds\0?\0eor\0eon\0sub\0?\0ands\0bics\0subs\0"; + op=((ic32_27)&0xc)|((ic32_23)&0x2)|((ic32_21)&0x1); s=((ic32_31)&0x1); z=((ic32_22)&0x3); m=((ic32_16)&0x1f); j=((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; args[3]=disasm_arg_shiftj_opt; + } else + if(((ic32_24)&0x1f)==0x10) { + names="adr\0adrp\0"; + op=((ic32_31)&0x1); j=((ic32_29)&0x3); i=((ic32_23)&1?(0xffffffff<<19):0)|((ic32_5)&0x7ffff); t=((ic32)&0x1f); + args[0]=disasm_arg_Xt; args[1]=disasm_arg_labelij1; + } else + if(((ic32_24)&0x1f)==0x11) { + names="add\0adds\0sub\0subs\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); j=((ic32_22)&0x3); i=((ic32_21)&1?(0xffffffff<<12):0)|((ic32_10)&0xfff); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_RtS; args[1]=disasm_arg_RnS; args[2]=disasm_arg_i; args[3]=disasm_arg_j12_opt; + } else + if(((ic32_16)&0x1f80)==0x1200) { + names="and\0orr\0eor\0ands\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); k=((ic32_22)&0x1); i=((ic32_21)&1?(0xffffffff<<6):0)|((ic32_16)&0x3f); j=((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_RtS; args[1]=disasm_arg_Rn; args[2]=disasm_arg_ib; + } else + if(((ic32_16)&0x1f80)==0x1280) { + names="movn\0?\0movz\0movk\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); j=((ic32_21)&0x3); i=((ic32_20)&1?(0xffffffff<<16):0)|((ic32_5)&0xffff); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_i; args[2]=disasm_arg_j16_opt; + } else + if(((ic32_16)&0x1f80)==0x1300) { + names="sbfm\0bfm\0ubfm\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); i=((ic32_21)&1?(0xffffffff<<6):0)|((ic32_16)&0x3f); j=((ic32_10)&0x3f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_i; args[3]=disasm_arg_j; + } else + if(((ic32_8)&0x1fe0fc)==0x1a0000) { + names="adc\0adcs\0sbc\0sbcs\0"; + op=((ic32_29)&0x3); s=((ic32_31)&0x1); m=((ic32_16)&0x1f); n=((ic32_5)&0x1f); t=((ic32)&0x1f); + args[0]=disasm_arg_Rt; args[1]=disasm_arg_Rn; args[2]=disasm_arg_Rm; + } else + names=NULL; + if(str!=NULL && names==NULL) { + sprintf(str,"0x%08x",ic32); + } + + if(str!=NULL && names!=NULL) { + str+=sprintf(str,disasm_str(names,op),disasm_str(conds,c)); + if(str-olds<10)om=10-(str-olds);else om=1;for(op=0;op>3)&3), ((t>>1)&3)+1, disasm_str(prf_pol,t&1)); break; + case disasm_arg_is4_opt: str+=sprintf(str,!i?"":"#0x%x", i<<(2+s)); break; + case disasm_arg_FPm: str+=sprintf(str,"%c%d", z==2?'q':(z==1?'d':'s'), m); break; + case disasm_arg_iz4_opt: str+=sprintf(str,!i?"":"#0x%x", i<<(2+z)); break; + case disasm_arg_im4_opt: str+=sprintf(str,!i?"":"#0x%x", i<<2); break; + case disasm_arg_nRt: str+=sprintf(str,t==31?"%czr":"%c%d", (s?'w':'x'), t); break; + case disasm_arg_FPst: str+=sprintf(str,"%c%d", s==1?'q':(z==3?'d':(z==2?'s':(z==1?'h':'b'))), t); break; + case disasm_arg_j_opt: str+=sprintf(str,!j?"":"#0x%x", j); break; + case disasm_arg_Rom: str+=sprintf(str,m==31?"%czr":"%c%d", (o&1?'x':'w'), m); break; + case disasm_arg_amountj: str+=sprintf(str,"%s #%d", disasm_str(extend64,o), j); break; + case disasm_arg_amountz: str+=sprintf(str,"%s #%d", disasm_str(extend64,o), j?(s?4:z):0); break; + case disasm_arg_amountjs: str+=sprintf(str,"%s #%d", disasm_str(extend64,o), j?(s?3:2):0); break; + case disasm_arg_amountj2: str+=sprintf(str,"%s #%d", disasm_str(extend64,o), j?2:0); break; + case disasm_arg_amountj3: str+=sprintf(str,"%s #%d", disasm_str(extend64,o), j?3:0); break; + case disasm_arg_shiftj_opt: str+=sprintf(str, !j?"":"%s #%d", disasm_str(shift,z), j); break; + case disasm_arg_Rsom: str+=sprintf(str,m==31?"%czr":"%c%d", (s&&(o&3)==3?'x':'w'), m); break; + case disasm_arg_exts: str+=sprintf(str,"%s #%d", s?disasm_str(extend64,o):disasm_str(extend32,o), j); break; + case disasm_arg_Wn: str+=sprintf(str,n==31?"wzr":"w%d", n); break; + case disasm_arg_Wm: str+=sprintf(str,m==31?"wzr":"w%d", m); break; + case disasm_arg_Xd: str+=sprintf(str,d==31?"xzr":"x%d", d); break; + case disasm_arg_Vt16b: str+=sprintf(str,"V%d.16b", t); break; + case disasm_arg_Vn16b: str+=sprintf(str,"V%d.16b", n); break; + case disasm_arg_Qt: str+=sprintf(str,"q%d", t); break; + case disasm_arg_Sn: str+=sprintf(str,"s%d", n); break; + case disasm_arg_Vm4s: str+=sprintf(str,"V%d.4s", m); break; + case disasm_arg_Vt4s: str+=sprintf(str,"V%d.4s", t); break; + case disasm_arg_Vn4s: str+=sprintf(str,"V%d.4s", n); break; + case disasm_arg_Qn: str+=sprintf(str,"q%d", n); break; + case disasm_arg_St: str+=sprintf(str,"s%d", t); break; + case disasm_arg_FPjt: str+=sprintf(str,"%c%d", j&1?'b':((j&3)==2?'h':((j&7)==4?'s':'d')), t); break; + case disasm_arg_Vnj: str+=sprintf(str,"V%d.%c", n, j&1?'b':((j&3)==2?'h':((j&7)==4?'s':'d'))); break; + case disasm_arg_FPidx: str+=sprintf(str,"%d", j>>(j&1?1:((j&3)==2?2:((j&7)==4?3:4))), t); break; + case disasm_arg_Vtjq: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,(j&1?0:((j&3)==2?2:(j&7)==4?4:6))+q)); break; + case disasm_arg_Ht: str+=sprintf(str,"h%d", t); break; + case disasm_arg_Hn: str+=sprintf(str,"h%d", n); break; + case disasm_arg_Hm: str+=sprintf(str,"h%d", m); break; + case disasm_arg_FPn: str+=sprintf(str,"%c%d", z==2?'q':(z==1?'d':'s'), n); break; + case disasm_arg_VtH1: str+=sprintf(str,"V%d.%dh", t, q?8:4); break; + case disasm_arg_VnH1: str+=sprintf(str,"V%d.%dh", n, q?8:4); break; + case disasm_arg_VmH1: str+=sprintf(str,"V%d.%dh", m, q?8:4); break; + case disasm_arg_Vtzq: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,4+(z*2)+q)); break; + case disasm_arg_Vnzq: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,4+(z*2)+q)); break; + case disasm_arg_Vmzq: str+=sprintf(str,"V%d.%s", m, disasm_str(quantum,4+(z*2)+q)); break; + case disasm_arg_simd0: str+=sprintf(str,"#0.0"); break; + case disasm_arg_FPz2t: str+=sprintf(str,"%c%d", z==1?'h':'s', t); break; + case disasm_arg_FPz2n: str+=sprintf(str,"%c%d", z==1?'h':'s', n); break; + case disasm_arg_FPz2m: str+=sprintf(str,"%c%d", z==1?'h':'s', m); break; + case disasm_arg_VnT: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,(z<<1)|q)); break; + case disasm_arg_VmT: str+=sprintf(str,"V%d.%s", m, disasm_str(quantum,(z<<1)|q)); break; + case disasm_arg_FPz3t: str+=sprintf(str,"%c%d", z==3?'d':(z==2?'s':(z==1?'h':'b')), t); break; + case disasm_arg_FPz3n: str+=sprintf(str,"%c%d", z==3?'d':(z==2?'s':(z==1?'h':'b')), n); break; + case disasm_arg_FPz4n: str+=sprintf(str,"%c%d", z==2?'d':(z==1?'s':'h'), n); break; + case disasm_arg_VnT3: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,(z<<1)+3)); break; + case disasm_arg_Vn2d: str+=sprintf(str,"V%d.2d", n); break; + case disasm_arg_Vn2h: str+=sprintf(str,"V%d.2h", n); break; + case disasm_arg_Vnz: str+=sprintf(str,"V%d.2%c", n, z?'d':'s'); break; + case disasm_arg_FPz4t: str+=sprintf(str,"%c%d", z==2?'d':(z==1?'s':'h'), t); break; + case disasm_arg_Vtz: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,4+(z*2))); break; + case disasm_arg_FPz3m: str+=sprintf(str,"%c%d", z==3?'d':(z==2?'s':(z==1?'h':'b')), m); break; + case disasm_arg_Dt: str+=sprintf(str,"d%d", t); break; + case disasm_arg_Dn: str+=sprintf(str,"d%d", n); break; + case disasm_arg_shrshift: str+=sprintf(str,"#%d", ((j>>3)==1?16:((j>>4)==1?32:((j>>5)==1?64:128)))-j); break; + case disasm_arg_Vtj2: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,((j>>3)==1?0:((j>>4)==1?2:((j>>5)==1?4:6)))|q)); break; + case disasm_arg_Vnj2: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,((j>>3)==1?0:((j>>4)==1?2:((j>>5)==1?4:6)))|q)); break; + case disasm_arg_shlshift: str+=sprintf(str,"#%d", j-((j>>3)==1?8:((j>>4)==1?16:((j>>5)==1?32:64)))); break; + case disasm_arg_FPnj: str+=sprintf(str,"%c%d", (j>>3)==1?'h':((j>>4)==1?'s':'d'), n); break; + case disasm_arg_VnTa: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,((j>>3)==1?3:((j>>4)==1?4:7)))); break; + case disasm_arg_FPjt2: str+=sprintf(str,"%c%d", (j>>3)==1?'b':((j>>4)==1?'h':((j>>5)==1?'s':'d')), t); break; + case disasm_arg_FPjn2: str+=sprintf(str,"%c%d", (j>>3)==1?'b':((j>>4)==1?'h':((j>>5)==1?'s':'d')), n); break; + case disasm_arg_Vtz3: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,(z<<1)+6)); break; + case disasm_arg_VmTs: str+=sprintf(str,"V%d.%c[%d]", m, z==1?'h':'s', j); break; + case disasm_arg_VmHs: str+=sprintf(str,"V%d.h[%d]", m, j); break; + case disasm_arg_VmTs2: str+=sprintf(str,"V%d.%c[%d]", m, z==1?'d':'s', j); break; + case disasm_arg_Vn116b: str+=sprintf(str,"{ V%d.16b }", n); break; + case disasm_arg_Vn216b: str+=sprintf(str,"{ V%d.16b, V%d.16b }", n, (n+1)&0x1f); break; + case disasm_arg_Vn316b: str+=sprintf(str,"{ V%d.16b, V%d.16b, V%d.16b }", n, (n+1)&0x1f, (n+2)&0x1f); break; + case disasm_arg_Vn416b: str+=sprintf(str,"{ V%d.16b, V%d.16b, V%d.16b, V%d.16b }", n, (n+1)&0x1f, (n+2)&0x1f, (n+3)&0x1f); break; + case disasm_arg_Vtj: str+=sprintf(str,"V%d.%c", t, j&1?'b':((j&3)==2?'h':((j&7)==4?'s':'d'))); break; + case disasm_arg_R2n: str+=sprintf(str,n==31?"%czr":"%c%d", ((j&15)==8?'x':'w'), n); break; + case disasm_arg_FPidxk: str+=sprintf(str,"%d", k>>(k&1?1:((k&3)==2?2:((k&7)==4?3:4))), t); break; + case disasm_arg_Vtzq2: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,2+(z*2)+q)); break; + case disasm_arg_VnT2: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,z+3)); break; + case disasm_arg_Vnz3: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,(z<<1)+6)); break; + case disasm_arg_Vnzq2: str+=sprintf(str,"V%d.%s", n, disasm_str(quantum,2+(z*2)+q)); break; + case disasm_arg_shift8: str+=sprintf(str,"#%d", 1<<(z+3)); break; + case disasm_arg_VtT3: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,(z<<1)+3)); break; + case disasm_arg_VmT3: str+=sprintf(str,"V%d.%s", m, disasm_str(quantum,(z<<1)+3)); break; + case disasm_arg_VtT4: str+=sprintf(str,"V%d.%s", t, disasm_str(quantum,z?8:3)); break; + case disasm_arg_imm8: str+=sprintf(str,"#%x", j); break; + case disasm_arg_amountk_opt: str+=sprintf(str,!k?"":"lsl #%d", 1<<(k*3)); break; + case disasm_arg_amountk2_opt: str+=sprintf(str,!k?"":"msl #%d", 1<<(k*3)); break; + case disasm_arg_imm64: str+=sprintf(str,"#0x%02x%02x%02x%02x%02x%02x%02x%02x", j&128?255:0,j&64?255:0,j&32?255:0,j&16?255:0,j&8?255:0,j&4?255:0,j&2?255:0,j&1?255:0); break; + case disasm_arg_Vt2d: str+=sprintf(str,"V%d.2d", t); break; + case disasm_arg_F16: str+=sprintf(str,"#0x02x%02x", (j&128)|(j&64?0:64)|(j&64?32:0)|(j&64?16:0)|((j>>2)&0xF), (j&3)<<6); break; + case disasm_arg_F32: str+=sprintf(str,"#0x02x%02x0000", (j&128)|(j&64?0:64)|(j&64?32:0)|(j&64?16:0)|(j&64?8:0)|(j&64?4:0)|(j&64?2:0)|(j&32?1:0), (j&0x1f)<<3); break; + case disasm_arg_F64: str+=sprintf(str,"#0x02x%02x%06x", (j&128)|(j&64?0:64)|(j&64?32:0)|(j&64?16:0)|(j&64?8:0)|(j&64?4:0)|(j&64?2:0)|(j&64?1:0), (j&64?128:0)|(j&64?64:0)|(j&0x3f), 0); break; + case disasm_arg_VmTs4b: str+=sprintf(str,"V%d.4b[%d]", m, j); break; + case disasm_arg_Vm2d: str+=sprintf(str,"V%d.2d", m); break; + case disasm_arg_Vm16b: str+=sprintf(str,"V%d.16b", m); break; + case disasm_arg_Vd16b: str+=sprintf(str,"V%d.16b", d); break; + case disasm_arg_Vd4s: str+=sprintf(str,"V%d.4s", d); break; + case disasm_arg_FPz5t: str+=sprintf(str,"%c%d", z==1?'d':(z==0?'s':'h'), t); break; + case disasm_arg_fbits: str+=sprintf(str,"#%d", 64-j); break; + case disasm_arg_FPz5n: str+=sprintf(str,"%c%d", z==1?'d':(z==0?'s':'h'), n); break; + case disasm_arg_Vn1d: str+=sprintf(str,"V%d.1d[n]", n); break; + case disasm_arg_Vt1d: str+=sprintf(str,"V%d.1d[1]", t); break; + case disasm_arg_FPk5t: str+=sprintf(str,"%c%d", k==1?'d':(k==0?'s':'h'), t); break; + case disasm_arg_FPz5m: str+=sprintf(str,"%c%d", z==1?'d':(z==0?'s':'h'), m); break; + case disasm_arg_jz: str+=sprintf(str,z==3?"#0x02x%02x":(z==0?"#0x02x%02x0000":"#0x02x%02x%06x"), z==3?(j&128)|(j&64?0:64)|(j&64?32:0)|(j&64?16:0)|((j>>2)&0xF):(j&128)|(j&64?0:64)|(j&64?32:0)|(j&64?16:0)|(j&64?8:0)|(j&64?4:0)|(j&64?2:0)|(j&(z==0?32:64)?1:0),z==3?(j&3)<<6:(z==0?(j&0x1f)<<3:(j&64?128:0)|(j&64?64:0)|(j&0x3f)), 0); break; + case disasm_arg_FPz5d: str+=sprintf(str,"%c%d", z==1?'d':(z==0?'s':'h'), d); break; + default: break; + } + if(*(str-2)==',')str-=2; + } + *str=0; + } + return addr+4; +} + +#ifdef __cplusplus +} +#endif + diff --git a/src/jit/codegen_arm.cpp.in b/src/jit/codegen_arm.cpp.in index 6db8370e..9dc7e943 100644 --- a/src/jit/codegen_arm.cpp.in +++ b/src/jit/codegen_arm.cpp.in @@ -2,6 +2,7 @@ * compiler/codegen_arm.cpp - ARM code generator * * Copyright (c) 2013 Jens Heitmann of ARAnyM dev team (see AUTHORS) + * Copyright (c) 2019 TomB * * Inspired by Christian Bauer's Basilisk II * @@ -28,15 +29,6 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * - * Current state: - * - Experimental - * - Still optimizable - * - Not clock cycle optimized - * - as a first step this compiler emulates x86 instruction to be compatible - * with gencomp. Better would be a specialized version of gencomp compiling - * 68k instructions to ARM compatible instructions. This is a step for the - * future - * */ #include "flags_arm.h" @@ -105,11 +97,16 @@ static const uae_u32 PRESERVE_MASK = ((1<> 16) + MOVT_ri16(r, val >> 16); +#else + uae_s32 offs = data_long_offs(val); + LDR_rRI(r, RPC_INDEX, offs); +#endif +} STATIC_INLINE void raw_push_regs_to_preserve(void) { PUSH_REGS(PRESERVE_MASK); @@ -180,8 +193,14 @@ STATIC_INLINE void raw_flags_evicted(int r) STATIC_INLINE void raw_flags_to_reg(int r) { + uintptr idx = (uintptr) &(regs.ccrflags.nzcv) - (uintptr) ®s; MRS_CPSR(r); - STR_rRI(r, R_REGSTRUCT, 16 * 4); // Flags are next to 8 Dregs and 8 Aregs in struct regstruct + if(flags_carry_inverted) { + EOR_rri(r, r, ARM_C_FLAG); + MSR_CPSRf_r(r); + flags_carry_inverted = false; + } + STR_rRI(r, R_REGSTRUCT, idx); raw_flags_evicted(r); } @@ -190,188 +209,93 @@ STATIC_INLINE void raw_reg_to_flags(int r) MSR_CPSRf_r(r); } + // // compuemu_support used raw calls // -LOWFUNC(WRITE,RMW,2,compemu_raw_add_l_mi,(IMM d, IMM s)) +LOWFUNC(WRITE,RMW,2,compemu_raw_inc_opcount,(IM16 op)) { + uintptr idx = (uintptr) &(regs.raw_cputbl_count) - (uintptr) ®s; + LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); #ifdef ARMV6T2 - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); - LDR_rR(REG_WORK2, REG_WORK1); - } - - if(CHECK32(s)) { - ADD_rri(REG_WORK2, REG_WORK2, s); - } else { - MOVW_ri16(REG_WORK3, s); - if(s >> 16) - MOVT_ri16(REG_WORK3, s >> 16); - ADD_rrr(REG_WORK2, REG_WORK2, REG_WORK3); - } - - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - STR_rR(REG_WORK2, REG_WORK1); - } + MOVW_ri16(REG_WORK3, op); #else - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); - LDR_rR(REG_WORK2, REG_WORK1); - - offs = data_long_offs(s); - LDR_rRI(REG_WORK3, RPC_INDEX, offs); - - ADD_rrr(REG_WORK2, REG_WORK2, REG_WORK3); - - STR_rR(REG_WORK2, REG_WORK1); + uae_s32 offs = data_long_offs(op); + LDR_rRI(REG_WORK3, RPC_INDEX, offs); #endif + LDR_rRr_LSLi(REG_WORK1, REG_WORK2, REG_WORK3, 2); + ADD_rri(REG_WORK1, REG_WORK1, 1); + STR_rRr_LSLi(REG_WORK1, REG_WORK2, REG_WORK3, 2); } -LENDFUNC(WRITE,RMW,2,compemu_raw_add_l_mi,(IMM d, IMM s)) +LENDFUNC(WRITE,RMW,1,compemu_raw_inc_opcount,(IM16 op)) -LOWFUNC(WRITE,READ,2,compemu_raw_cmp_l_mi,(MEMR d, IMM s)) +LOWFUNC(WRITE,READ,1,compemu_raw_cmp_pc,(IMPTR s)) { + /* s is always >= NATMEM_OFFSETX and < NATMEM_OFFSETX + max. Amiga mem */ clobber_flags(); - #ifdef ARMV6T2 - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - } else { - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); - LDR_rR(REG_WORK1, REG_WORK1); - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - } -#else - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - uae_s32 idx = d - (uae_u32) & regs; - LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); - } else { - data_check_end(8, 16); - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); - LDR_rR(REG_WORK1, REG_WORK1); - - offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - } -#endif + uintptr idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); + LOAD_U32(REG_WORK2, s); CMP_rr(REG_WORK1, REG_WORK2); } -LENDFUNC(WRITE,READ,2,compemu_raw_cmp_l_mi,(MEMR d, IMM s)) +LENDFUNC(WRITE,READ,1,compemu_raw_cmp_pc,(IMPTR s)) -LOWFUNC(NONE,NONE,3,compemu_raw_lea_l_brr,(W4 d, RR4 s, IMM offset)) +LOWFUNC(NONE,WRITE,1,compemu_raw_set_pc_m,(MEMR s)) { - if(CHECK32(offset)) { - ADD_rri(d, s, offset); + uintptr idx; + if(s >= (uintptr) ®s && s < ((uintptr) ®s) + sizeof(struct regstruct)) { + idx = s - (uintptr) & regs; + LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, offset); - if(offset >> 16) - MOVT_ri16(REG_WORK1, offset >> 16); -#else - uae_s32 offs = data_long_offs(offset); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - ADD_rrr(d, s, REG_WORK1); + LOAD_U32(REG_WORK1, s); + LDR_rR(REG_WORK1, REG_WORK1); } -} -LENDFUNC(NONE,NONE,3,compemu_raw_lea_l_brr,(W4 d, RR4 s, IMM offset)) -LOWFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IMM s)) -{ -#ifdef ARMV6T2 - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - uae_s32 idx = d - (uae_u32) & regs; - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - STR_rR(REG_WORK2, REG_WORK1); - } -#else - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - uae_s32 idx = d - (uae_u32) & regs; - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - data_check_end(8, 12); - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); - offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - STR_rR(REG_WORK2, REG_WORK1); - } -#endif + idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); } -LENDFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IMM s)) +LENDFUNC(NONE,WRITE,1,compemu_raw_set_pc_m,(MEMR s)) + +LOWFUNC(NONE,WRITE,1,compemu_raw_set_pc_i,(IMPTR s)) +{ + LOAD_U32(REG_WORK2, s); + uintptr idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + STR_rRI(REG_WORK2, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,1,compemu_raw_set_pc_i,(IMPTR s)) + +LOWFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IM32 s)) +{ + /* d points always to memory in regs struct */ + LOAD_U32(REG_WORK2, s); + uintptr idx = d - (uintptr) ®s; + STR_rRI(REG_WORK2, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IM32 s)) LOWFUNC(NONE,WRITE,2,compemu_raw_mov_l_mr,(MEMW d, RR4 s)) { - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - STR_rRI(s, R_REGSTRUCT, idx); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); -#else - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - STR_rR(s, REG_WORK1); - } + /* d points always to memory in regs struct */ + uintptr idx = d - (uintptr) ®s; + STR_rRI(s, R_REGSTRUCT, idx); } LENDFUNC(NONE,WRITE,2,compemu_raw_mov_l_mr,(MEMW d, RR4 s)) -LOWFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IMM s)) +LOWFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IM32 s)) { -#ifdef ARMV6T2 - MOVW_ri16(d, s); - if(s >> 16) - MOVT_ri16(d, s >> 16); -#else - uae_s32 offs = data_long_offs(s); - LDR_rRI(d, RPC_INDEX, offs); -#endif + LOAD_U32(d, s); } -LENDFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IMM s)) +LENDFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IM32 s)) LOWFUNC(NONE,READ,2,compemu_raw_mov_l_rm,(W4 d, MEMR s)) { - if(s >= (uae_u32) ®s && s < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = s - (uae_u32) & regs; + if(s >= (uintptr) ®s && s < ((uintptr) ®s) + sizeof(struct regstruct)) { + uintptr idx = s - (uintptr) ®s; LDR_rRI(d, R_REGSTRUCT, idx); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, s); - MOVT_ri16(REG_WORK1, s >> 16); -#else - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, s); LDR_rR(d, REG_WORK1); } } @@ -383,85 +307,21 @@ LOWFUNC(NONE,NONE,2,compemu_raw_mov_l_rr,(W4 d, RR4 s)) } LENDFUNC(NONE,NONE,2,compemu_raw_mov_l_rr,(W4 d, RR4 s)) -LOWFUNC(WRITE,RMW,2,compemu_raw_sub_l_mi,(MEMRW d, IMM s)) +LOWFUNC(WRITE,RMW,1,compemu_raw_dec_m,(MEMRW d)) { clobber_flags(); - if(CHECK32(s)) { - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); - SUBS_rri(REG_WORK2, REG_WORK2, s); - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); -#else - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - LDR_rR(REG_WORK2, REG_WORK1); - SUBS_rri(REG_WORK2, REG_WORK2, s); - STR_rR(REG_WORK2, REG_WORK1); - } - } else { - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) & regs; - LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); - -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, s); - if(s >> 16) - MOVT_ri16(REG_WORK1, s >> 16); -#else - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - - SUBS_rrr(REG_WORK2, REG_WORK2, REG_WORK1); - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); - LDR_rR(REG_WORK2, REG_WORK1); - - MOVW_ri16(REG_WORK3, s); - if(s >> 16) - MOVT_ri16(REG_WORK3, s >> 16); -#else - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); - LDR_rR(REG_WORK2, REG_WORK1); - - offs = data_long_offs(s); - LDR_rRI(REG_WORK3, RPC_INDEX, offs); -#endif - - SUBS_rrr(REG_WORK2, REG_WORK2, REG_WORK3); - STR_rR(REG_WORK2, REG_WORK1); - } - } + LOAD_U32(REG_WORK1, d); + LDR_rR(REG_WORK2, REG_WORK1); + SUBS_rri(REG_WORK2, REG_WORK2, 1); + STR_rR(REG_WORK2, REG_WORK1); } -LENDFUNC(WRITE,RMW,2,compemu_raw_sub_l_mi,(MEMRW d, IMM s)) +LENDFUNC(WRITE,RMW,1,compemu_raw_dec_m,(MEMRW ds)) -LOWFUNC(WRITE,NONE,2,compemu_raw_test_l_rr,(RR4 d, RR4 s)) +STATIC_INLINE void compemu_raw_call(uintptr t) { - clobber_flags(); - TST_rr(d, s); -} -LENDFUNC(WRITE,NONE,2,compemu_raw_test_l_rr,(RR4 d, RR4 s)) + LOAD_U32(REG_WORK1, t); -STATIC_INLINE void compemu_raw_call(uae_u32 t) -{ -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, t); - MOVT_ri16(REG_WORK1, t >> 16); -#else - uae_s32 offs = data_long_offs(t); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif PUSH(RLR_INDEX); BLX_r(REG_WORK1); POP(RLR_INDEX); @@ -476,6 +336,8 @@ STATIC_INLINE void compemu_raw_call_r(RR4 r) STATIC_INLINE void compemu_raw_jcc_l_oponly(int cc) { + FIX_INVERTED_CARRY + switch (cc) { case NATIVE_CC_HI: // HI BEQ_i(0); // beq no jump @@ -565,45 +427,20 @@ STATIC_INLINE void compemu_raw_jcc_l_oponly(int cc) // emit of target into last branch will be done by caller } -STATIC_INLINE void compemu_raw_handle_except(IMM cycles) +STATIC_INLINE void compemu_raw_handle_except(IM32 cycles) { uae_u32* branchadd; - int offs; clobber_flags(); -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); -#else - offs = data_long_offs((uae_u32)(&jit_exception)); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); -#endif - LDR_rR(REG_WORK1, REG_WORK2); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); TST_rr(REG_WORK1, REG_WORK1); - branchadd = (uae_u32*)get_target(); BEQ_i(0); // no exception, jump to next instruction - // countdown -= scaled_cycles(totcycles); - offs = (uae_u32)&countdown - (uae_u32)®s; - LDR_rRI(REG_WORK1, R_REGSTRUCT, offs); - if(CHECK32(cycles)) { - SUBS_rri(REG_WORK1, REG_WORK1, cycles); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, cycles); - if(cycles >> 16) - MOVT_ri16(REG_WORK2, cycles >> 16); -#else - int offs2 = data_long_offs(cycles); - LDR_rRI(REG_WORK2, RPC_INDEX, offs2); -#endif - SUBS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); - } - STR_rRI(REG_WORK1, R_REGSTRUCT, offs); - raw_pop_preserved_regs(); + LOAD_U32(REG_PAR1, cycles); LDR_rRI(RPC_INDEX, RPC_INDEX, -4); // emit_long((uintptr)execute_exception); @@ -611,7 +448,7 @@ STATIC_INLINE void compemu_raw_handle_except(IMM cycles) write_jmp_target(branchadd, (uintptr)get_target()); } -STATIC_INLINE void compemu_raw_maybe_recompile(uae_u32 t) +STATIC_INLINE void compemu_raw_maybe_recompile(uintptr t) { BGE_i(2); raw_pop_preserved_regs(); @@ -619,9 +456,9 @@ STATIC_INLINE void compemu_raw_maybe_recompile(uae_u32 t) emit_long(t); } -STATIC_INLINE void compemu_raw_jmp(uae_u32 t) +STATIC_INLINE void compemu_raw_jmp(uintptr t) { - if(t >= (uae_u32)popallspace && t < (uae_u32)(popallspace + POPALLSPACE_SIZE + MAX_JIT_CACHE * 1024)) { + if(t >= (uintptr)popallspace && t < (uintptr)(popallspace + POPALLSPACE_SIZE + MAX_JIT_CACHE * 1024)) { uae_u32* loc = (uae_u32*)get_target(); B_i(0); write_jmp_target(loc, t); @@ -631,23 +468,16 @@ STATIC_INLINE void compemu_raw_jmp(uae_u32 t) } } -STATIC_INLINE void compemu_raw_jmp_m_indexed(uae_u32 base, uae_u32 r, uae_u32 m) +STATIC_INLINE void compemu_raw_jmp_pc_tag(uintptr base) { - int shft; - switch(m) { - case 1: shft=0; break; - case 2: shft=1; break; - case 4: shft=2; break; - case 8: shft=3; break; - default: abort(); - } - - LDR_rR(REG_WORK1, RPC_INDEX); - LDR_rRR_LSLi(RPC_INDEX, REG_WORK1, r, shft); + uintptr idx = (uintptr)®s.pc_p - (uintptr)®s; + LDRH_rRI(REG_WORK1, R_REGSTRUCT, idx); + LDR_rR(REG_WORK2, RPC_INDEX); + LDR_rRR_LSLi(RPC_INDEX, REG_WORK2, REG_WORK1, 2); emit_long(base); } -STATIC_INLINE void compemu_raw_maybe_cachemiss(uae_u32 t) +STATIC_INLINE void compemu_raw_maybe_cachemiss(uintptr t) { BEQ_i(2); raw_pop_preserved_regs(); @@ -655,53 +485,62 @@ STATIC_INLINE void compemu_raw_maybe_cachemiss(uae_u32 t) emit_long(t); } -STATIC_INLINE void compemu_raw_jz_b_oponly(void) +STATIC_INLINE void compemu_raw_maybe_do_nothing(IM32 cycles, uintptr adr) { - BEQ_i(0); // Real distance set by caller + clobber_flags(); + + uintptr idx = (uintptr)®s.spcflags - (uintptr)®s; + LDR_rRI(REG_WORK1, R_REGSTRUCT, idx); + TST_rr(REG_WORK1, REG_WORK1); + uae_s8 *branchadd = (uae_s8 *)get_target(); + BEQ_i(0); // + + idx = (uintptr)&countdown - (uintptr) ®s; + LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); + if(CHECK32(cycles)) { + SUB_rri(REG_WORK2, REG_WORK2, cycles); + } else { + LOAD_U32(REG_WORK1, cycles); + SUB_rrr(REG_WORK2, REG_WORK2, REG_WORK1); + } + STR_rRI(REG_WORK2, R_REGSTRUCT, idx); + + raw_pop_preserved_regs(); + LDR_rRI(RPC_INDEX, RPC_INDEX, -4); + emit_long(adr); + + // + write_jmp_target((uae_u32*)branchadd, (uintptr)get_target()); } -STATIC_INLINE void compemu_raw_branch(IMM d) +STATIC_INLINE void compemu_raw_branch(IM32 d) { B_i((d >> 2) - 1); } -// Optimize access to struct regstruct with r11 and memory with r10 +// Optimize access to struct regstruct with and memory with fixed registers -LOWFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMM s)) +LOWFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMPTR s)) { -#ifdef ARMV6T2 - MOVW_ri16(R_REGSTRUCT, s); - MOVT_ri16(R_REGSTRUCT, s >> 16); -#else - uae_s32 offs = data_long_offs(s); - LDR_rRI(R_REGSTRUCT, RPC_INDEX, offs); -#endif - uae_s32 offsmem = (uae_u32)&NATMEM_OFFSETX - (uae_u32) ®s; + LOAD_U32(R_REGSTRUCT, s); + uintptr offsmem = (uintptr)&NATMEM_OFFSETX - (uintptr) ®s; LDR_rRI(R_MEMSTART, R_REGSTRUCT, offsmem); } -LENDFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMM s)) - +LENDFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMPTR s)) // Handle end of compiled block -LOWFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IMM cycles)) +LOWFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IM32 cycles)) { clobber_flags(); // countdown -= scaled_cycles(totcycles); - uae_s32 offs = (uae_u32)&countdown - (uae_u32)®s; + uintptr offs = (uintptr)&countdown - (uintptr)®s; LDR_rRI(REG_WORK1, R_REGSTRUCT, offs); if(CHECK32(cycles)) { SUBS_rri(REG_WORK1, REG_WORK1, cycles); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, cycles); - if(cycles >> 16) - MOVT_ri16(REG_WORK2, cycles >> 16); -#else - int offs2 = data_long_offs(cycles); - LDR_rRI(REG_WORK2, RPC_INDEX, offs2); -#endif + LOAD_U32(REG_WORK2, cycles); SUBS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); } STR_rRI(REG_WORK1, R_REGSTRUCT, offs); @@ -723,29 +562,21 @@ LOWFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IMM cycles)) emit_long((uintptr)cache_tags); emit_long((uintptr)do_nothing); } -LENDFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IMM cycles)) +LENDFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IM32 cycles)) - -//LOWFUNC(NONE,NONE,2,compemu_raw_endblock_pc_isconst,(IMM cycles, IMM v)) -STATIC_INLINE uae_u32* compemu_raw_endblock_pc_isconst(IMM cycles, IMM v) +STATIC_INLINE uae_u32* compemu_raw_endblock_pc_isconst(IM32 cycles, IMPTR v) { + /* v is always >= NATMEM_OFFSETX and < NATMEM_OFFSETX + max. Amiga mem */ uae_u32* tba; clobber_flags(); // countdown -= scaled_cycles(totcycles); - uae_s32 offs = (uae_u32)&countdown - (uae_u32)®s; + uintptr offs = (uintptr)&countdown - (uintptr)®s; LDR_rRI(REG_WORK1, R_REGSTRUCT, offs); if(CHECK32(cycles)) { SUBS_rri(REG_WORK1, REG_WORK1, cycles); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, cycles); - if(cycles >> 16) - MOVT_ri16(REG_WORK2, cycles >> 16); -#else - int offs2 = data_long_offs(cycles); - LDR_rRI(REG_WORK2, RPC_INDEX, offs2); -#endif + LOAD_U32(REG_WORK2, cycles); SUBS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); } STR_rRI(REG_WORK1, R_REGSTRUCT, offs); @@ -754,7 +585,7 @@ STATIC_INLINE uae_u32* compemu_raw_endblock_pc_isconst(IMM cycles, IMM v) CC_B_i(NATIVE_CC_MI^1, 0); // LDR_rRI(REG_WORK1, RPC_INDEX, 8); // - offs = (uae_u32)®s.pc_p - (uae_u32)®s; + offs = (uintptr)®s.pc_p - (uintptr)®s; STR_rRI(REG_WORK1, R_REGSTRUCT, offs); raw_pop_preserved_regs(); LDR_rRI(RPC_INDEX, RPC_INDEX, 0); // @@ -764,20 +595,13 @@ STATIC_INLINE uae_u32* compemu_raw_endblock_pc_isconst(IMM cycles, IMM v) return tba; } -//LENDFUNC(NONE,NONE,2,compemu_raw_endblock_pc_isconst,(IMM cycles, IMM v)) - - -LOWFUNC(NONE,READ,2,compemu_raw_tag_pc,(W4 d, MEMR s)) -{ - uae_s32 idx = (uae_u32)(s) - (uae_u32)®s; - LDRH_rRI(d, R_REGSTRUCT, idx); -} -LENDFUNC(NONE,READ,2,compemu_raw_tag_pc,(W4 d, MEMR s)) /************************************************************************* * FPU stuff * *************************************************************************/ +#ifdef USE_JIT_FPU + LOWFUNC(NONE,NONE,2,raw_fmov_rr,(FW d, FR s)) { VMOV64_dd(d, s); @@ -786,34 +610,21 @@ LENDFUNC(NONE,NONE,2,raw_fmov_rr,(FW d, FR s)) LOWFUNC(NONE,WRITE,2,compemu_raw_fmov_mr_drop,(MEMW mem, FR s)) { - if(mem >= (uae_u32) ®s && mem < (uae_u32) ®s + 1020 && ((mem - (uae_u32) ®s) & 0x3) == 0) { - VSTR64_dRi(s, R_REGSTRUCT, (mem - (uae_u32) ®s)); + if(mem >= (uintptr) ®s && mem < (uintptr) ®s + 1020 && ((mem - (uintptr) ®s) & 0x3) == 0) { + VSTR64_dRi(s, R_REGSTRUCT, (mem - (uintptr) ®s)); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, mem); - MOVT_ri16(REG_WORK1, mem >> 16); -#else - auto offs = data_long_offs(mem); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, mem); VSTR64_dRi(s, REG_WORK1, 0); } } LENDFUNC(NONE,WRITE,2,compemu_raw_fmov_mr_drop,(MEMW mem, FR s)) - LOWFUNC(NONE,READ,2,compemu_raw_fmov_rm,(FW d, MEMR mem)) { - if(mem >= (uae_u32) ®s && mem < (uae_u32) ®s + 1020 && ((mem - (uae_u32) ®s) & 0x3) == 0) { - VLDR64_dRi(d, R_REGSTRUCT, (mem - (uae_u32) ®s)); + if(mem >= (uintptr) ®s && mem < (uintptr) ®s + 1020 && ((mem - (uintptr) ®s) & 0x3) == 0) { + VLDR64_dRi(d, R_REGSTRUCT, (mem - (uintptr) ®s)); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, mem); - MOVT_ri16(REG_WORK1, mem >> 16); -#else - auto offs = data_long_offs(mem); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, mem); VLDR64_dRi(d, REG_WORK1, 0); } } @@ -835,7 +646,7 @@ LENDFUNC(NONE,NONE,2,raw_fmov_s_rr,(FW d, RR4 s)) LOWFUNC(NONE,NONE,2,raw_fmov_w_rr,(FW d, RR2 s)) { - SIGN_EXTEND_16_REG_2_REG(REG_WORK1, s); + SIGNED16_REG_2_REG(REG_WORK1, s); VMOVi_from_ARM_dr(SCRATCH_F64_1, REG_WORK1, 0); VCVTIto64_ds(d, SCRATCH_F32_1); } @@ -843,7 +654,7 @@ LENDFUNC(NONE,NONE,2,raw_fmov_w_rr,(FW d, RR2 s)) LOWFUNC(NONE,NONE,2,raw_fmov_b_rr,(FW d, RR1 s)) { - SIGN_EXTEND_8_REG_2_REG(REG_WORK1, s); + SIGNED8_REG_2_REG(REG_WORK1, s); VMOVi_from_ARM_dr(SCRATCH_F64_1, REG_WORK1, 0); VCVTIto64_ds(d, SCRATCH_F32_1); } @@ -928,26 +739,14 @@ LENDFUNC(NONE,NONE,1,raw_fmov_d_ri_10,(FW r)) LOWFUNC(NONE,READ,2,raw_fmov_d_rm,(FW r, MEMR m)) { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, m); - MOVT_ri16(REG_WORK1, m >> 16); -#else - auto offs = data_long_offs(m); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, m); VLDR64_dRi(r, REG_WORK1, 0); } LENDFUNC(NONE,READ,2,raw_fmov_d_rm,(FW r, MEMR m)) LOWFUNC(NONE,READ,2,raw_fmovs_rm,(FW r, MEMR m)) { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, m); - MOVT_ri16(REG_WORK1, m >> 16); -#else - auto offs = data_long_offs(m); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, m); VLDR32_sRi(SCRATCH_F32_1, REG_WORK1, 0); VCVT32to64_ds(r, SCRATCH_F32_1); } @@ -1079,13 +878,9 @@ LENDFUNC(NONE,NONE,2,raw_fmovs_rr,(FW d, FR s)) LOWFUNC(NONE,NONE,3,raw_ffunc_rr,(double (*func)(double), FW d, FR s)) { VMOV64_dd(0, s); -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, (uae_u32)func); - MOVT_ri16(REG_WORK1, ((uae_u32)func) >> 16); -#else - auto offs = data_long_offs(uae_u32(func)); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + + LOAD_U32(REG_WORK1, (uintptr)func); + PUSH(RLR_INDEX); BLX_r(REG_WORK1); POP(RLR_INDEX); @@ -1105,14 +900,8 @@ LOWFUNC(NONE,NONE,3,raw_fpowx_rr,(uae_u32 x, FW d, FR s)) } VMOV64_dd(1, s); - -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, (uae_u32)func); - MOVT_ri16(REG_WORK1, ((uae_u32)func) >> 16); -#else - auto offs = data_long_offs(uae_u32(func)); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + + LOAD_U32(REG_WORK1, (uintptr)func); PUSH(RLR_INDEX); BLX_r(REG_WORK1); @@ -1127,20 +916,15 @@ LOWFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) VMOVi_to_ARM_rd(REG_WORK1, s, 1); // get high part of double VCMP64_d0(s); VMRS_CPSR(); -#ifdef ARMV6T2 - BEQ_i(19); // iszero -#else - BEQ_i(20); -#endif + uae_u32* branchadd_iszero = (uae_u32*)get_target(); + BEQ_i(0); // iszero UBFX_rrii(REG_WORK2, REG_WORK1, 20, 11); // get exponent MOVW_ri16(REG_WORK3, 2047); CMP_rr(REG_WORK2, REG_WORK3); -#ifdef ARMV6T2 - BEQ_i(12); // isnan -#else - BEQ_i(13); -#endif + + uae_u32* branchadd_isnan = (uae_u32*)get_target(); + BEQ_i(0); // isnan MOVW_ri16(REG_WORK3, 15360); // diff of bias between double and long double ADD_rrr(REG_WORK2, REG_WORK2, REG_WORK3); // exponent done @@ -1158,19 +942,21 @@ LOWFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) ORR_rri(REG_WORK1, REG_WORK1, 0x80); // insert explicit 1 #ifdef ARMV6T2 STRD_rRI(REG_WORK1, REG_WORK3, 4); - B_i(8); // end_of_op #else STR_rRI(REG_WORK1, REG_WORK3, 4); STR_rRI(REG_WORK2, REG_WORK3, 8); - B_i(9); #endif + uae_u32* branchadd_end = (uae_u32*)get_target(); + B_i(0); // end_of_op // isnan + write_jmp_target(branchadd_isnan, (uintptr)get_target()); MOVW_ri16(REG_WORK1, 0x7fff); LSL_rri(REG_WORK1, REG_WORK1, 16); MVN_ri(REG_WORK2, 0); // iszero + write_jmp_target(branchadd_iszero, (uintptr)get_target()); CC_AND_rri(NATIVE_CC_EQ, REG_WORK1, REG_WORK1, 0x80000000); // extract sign CC_MOV_ri(NATIVE_CC_EQ, REG_WORK2, 0); @@ -1186,7 +972,7 @@ LOWFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) STR_rRI(REG_WORK2, REG_WORK3, 8); // end_of_op - + write_jmp_target(branchadd_end, (uintptr)get_target()); } LENDFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) @@ -1209,20 +995,27 @@ LOWFUNC(NONE,READ,2,raw_fp_to_exten_rm,(FW d, RR4 adr)) MOVW_ri16(REG_WORK2, 0x7fff); ANDS_rrr(REG_WORK2, REG_WORK2, REG_WORK1); - BNE_i(9); // not_zero + uae_u32* branchadd_notzero = (uae_u32*)get_target(); + BNE_i(0); // not_zero VCMP64_d0(d); VMRS_CPSR(); - BNE_i(6); // not zero + uae_u32* branchadd_notzero2 = (uae_u32*)get_target(); + BNE_i(0); // not zero + // zero VMOV_I64_dimmI(d, 0x00); TST_ri(REG_WORK1, 0x8000); // check sign - BEQ_i(12); // end_of_op + uae_u32* branchadd_end = (uae_u32*)get_target(); + BEQ_i(0); // end_of_op MOV_ri(REG_WORK1, 0x80000000); MOV_ri(REG_WORK2, 0); VMOV64_drr(d, REG_WORK2, REG_WORK1); - B_i(8); // end_of_op + uae_u32* branchadd_end2 = (uae_u32*)get_target(); + B_i(0); // end_of_op // not_zero + write_jmp_target(branchadd_notzero, (uintptr)get_target()); + write_jmp_target(branchadd_notzero2, (uintptr)get_target()); MOVW_ri16(REG_WORK3, 15360); // diff of bias between double and long double SUB_rrr(REG_WORK2, REG_WORK2, REG_WORK3); // exponent done, ToDo: check for carry -> result gets Inf in double UBFX_rrii(REG_WORK1, REG_WORK1, 15, 1); // extract sign @@ -1233,15 +1026,15 @@ LOWFUNC(NONE,READ,2,raw_fp_to_exten_rm,(FW d, RR4 adr)) VMOVi_from_ARM_dr(SCRATCH_F64_1, REG_WORK2, 1); VORR_ddd(d, d, SCRATCH_F64_1); // end_of_op - + write_jmp_target(branchadd_end, (uintptr)get_target()); + write_jmp_target(branchadd_end2, (uintptr)get_target()); } LENDFUNC(NONE,READ,2,raw_fp_to_exten_rm,(FW d, RR4 adr)) LOWFUNC(NONE,WRITE,2,raw_fp_from_double_mr,(RR4 adr, FR s)) { ADD_rrr(REG_WORK3, adr, R_MEMSTART); - - VREV64_8_dd(SCRATCH_F64_1, s); + VREV64_8_dd(SCRATCH_F64_1, s); VSTR64_dRi(SCRATCH_F64_1, REG_WORK3, 0); } LENDFUNC(NONE,WRITE,2,raw_fp_from_double_mr,(RR4 adr, FR s)) @@ -1249,7 +1042,6 @@ LENDFUNC(NONE,WRITE,2,raw_fp_from_double_mr,(RR4 adr, FR s)) LOWFUNC(NONE,READ,2,raw_fp_to_double_rm,(FW d, RR4 adr)) { ADD_rrr(REG_WORK3, adr, R_MEMSTART); - VLDR64_dRi(d, REG_WORK3, 0); VREV64_8_dd(d, d); } @@ -1371,12 +1163,14 @@ LOWFUNC(NONE,NONE,2,raw_fp_fscc_ri,(RW4 d, int cc)) } LENDFUNC(NONE,NONE,2,raw_fp_fscc_ri,(RW4 d, int cc)) -LOWFUNC(NONE,NONE,1,raw_roundingmode,(IMM mode)) +LOWFUNC(NONE,NONE,1,raw_roundingmode,(IM32 mode)) { VMRS_r(REG_WORK1); BIC_rri(REG_WORK1, REG_WORK1, 0x00c00000); ORR_rri(REG_WORK1, REG_WORK1, mode); VMSR_r(REG_WORK1); } -LENDFUNC(NONE,NONE,1,raw_roundingmode,(IMM mode)) +LENDFUNC(NONE,NONE,1,raw_roundingmode,(IM32 mode)) + +#endif // USE_JIT_FPU diff --git a/src/jit/codegen_arm.h b/src/jit/codegen_arm.h index 82d3350a..50c5bf59 100644 --- a/src/jit/codegen_arm.h +++ b/src/jit/codegen_arm.h @@ -1,5 +1,5 @@ /* - * compiler/codegen_arm.h - IA-32 and AMD64 code generator + * compiler/codegen_arm.h - ARM code generator * * Copyright (c) 2013 Jens Heitmann of ARAnyM dev team (see AUTHORS) * @@ -1327,8 +1327,7 @@ enum { #define SMULxy_rrr(Rd,Rn,Rm,x,y) CC_SMULxy_rrr(NATIVE_CC_AL,Rd,Rn,Rm,x,y) // ARMv6T2 -//#ifdef ARMV6T2 -#if 1 +#ifdef ARMV6T2 #define CC_BFI_rrii(cc,Rd,Rn,lsb,msb) _W(((cc) << 28) | (0x3e << 21) | ((msb) << 16) | ((Rd) << 12) | ((lsb) << 7) | (0x1 << 4) | (Rn)) #define BFI_rrii(Rd,Rn,lsb,msb) CC_BFI_rrii(NATIVE_CC_AL,Rd,Rn,lsb,msb) diff --git a/src/jit/codegen_armA64.cpp.in b/src/jit/codegen_armA64.cpp.in new file mode 100644 index 00000000..37c556cf --- /dev/null +++ b/src/jit/codegen_armA64.cpp.in @@ -0,0 +1,1138 @@ +/* + * compiler/codegen_arm.cpp - AARCH64 code generator + * + * Copyright (c) 2019 TomB + * + * This file is part of the UAE4ARM project. + * + * JIT compiler m68k -> ARMv8.0 + * + * Original 68040 JIT compiler for UAE, copyright 2000-2002 Bernd Meyer + * This file is derived from CCG, copyright 1999-2003 Ian Piumarta + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Note: JIT for aarch64 only works if memory for Amiga part (regs.natmen_offset + * to additional_mem + ADDITIONAL_MEMSIZE + BARRIER) is allocated in lower + * 32 bit address space. See alloc_AmigaMem() in generic_mem.cpp. + */ + +#include "flags_arm.h" +#include + +/************************************************************************* + * Some basic information about the the target CPU * + *************************************************************************/ + +#define R0_INDEX 0 +#define R1_INDEX 1 +#define R2_INDEX 2 +#define R3_INDEX 3 +#define R4_INDEX 4 +#define R5_INDEX 5 +#define R6_INDEX 6 +#define R7_INDEX 7 +#define R8_INDEX 8 +#define R9_INDEX 9 +#define R10_INDEX 10 +#define R11_INDEX 11 +#define R12_INDEX 12 +#define R13_INDEX 13 +#define R14_INDEX 14 +#define R15_INDEX 15 +#define R16_INDEX 16 +#define R17_INDEX 17 +#define R18_INDEX 18 +#define R27_INDEX 27 +#define R28_INDEX 28 + +#define RSP_INDEX 31 +#define RLR_INDEX 30 +#define RFP_INDEX 29 + +/* The register in which subroutines return an integer return value */ +#define REG_RESULT R0_INDEX + +/* The registers subroutines take their first and second argument in */ +#define REG_PAR1 R0_INDEX +#define REG_PAR2 R1_INDEX + +#define REG_WORK1 R2_INDEX +#define REG_WORK2 R3_INDEX +#define REG_WORK3 R4_INDEX +#define REG_WORK4 R5_INDEX + +#define REG_PC_TMP R1_INDEX /* Another register that is not the above */ + +#define R_MEMSTART 27 +#define R_REGSTRUCT 28 +uae_s8 always_used[] = {2,3,4,5,18,R_MEMSTART,R_REGSTRUCT,-1}; // r2-r5 are work register in emitted code, r18 special use reg + +uae_u8 call_saved[] = {0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,1, 1,1,1,1, 1,1,1,1, 1,0,0,0}; + +/* This *should* be the same as call_saved. But: + - We might not really know which registers are saved, and which aren't, + so we need to preserve some, but don't want to rely on everyone else + also saving those registers + - Special registers (such like the stack pointer) should not be "preserved" + by pushing, even though they are "saved" across function calls + - r19 - r26 not in use, so no need to preserve + - if you change need_to_preserve, modify raw_push_regs_to_preserve() and raw_pop_preserved_regs() +*/ +static const uae_u8 need_to_preserve[] = {0,0,0,0, 0,0,1,1, 1,1,1,1, 1,1,1,1, 1,1,1,0, 0,0,0,0, 0,0,0,1, 1,0,0,0}; + +#include "codegen_armA64.h" + +#define FIX_INVERTED_CARRY \ + if(flags_carry_inverted) { \ + MRS_NZCV_x(REG_WORK1); \ + EOR_xxCflag(REG_WORK1, REG_WORK1); \ + MSR_NZCV_x(REG_WORK1); \ + flags_carry_inverted = false; \ + } + + +STATIC_INLINE void SIGNED8_IMM_2_REG(W4 r, IM8 v) { + uae_s16 v16 = (uae_s16)(uae_s8)v; + if (v16 & 0x8000) { + MOVN_xi(r, (uae_u16) ~v16); + } else { + MOV_xi(r, (uae_u16) v16); + } +} + +STATIC_INLINE void UNSIGNED16_IMM_2_REG(W4 r, IM16 v) { + MOV_xi(r, v); +} + +STATIC_INLINE void SIGNED16_IMM_2_REG(W4 r, IM16 v) { + if (v & 0x8000) { + MOVN_xi(r, (uae_u16) ~v); + } else { + MOV_xi(r, (uae_u16) v); + } +} + +STATIC_INLINE void UNSIGNED8_REG_2_REG(W4 d, RR4 s) { + UXTB_xx(d, s); +} + +STATIC_INLINE void SIGNED8_REG_2_REG(W4 d, RR4 s) { + SXTB_xx(d, s); +} + +STATIC_INLINE void UNSIGNED16_REG_2_REG(W4 d, RR4 s) { + UXTH_xx(d, s); +} + +STATIC_INLINE void SIGNED16_REG_2_REG(W4 d, RR4 s) { + SXTH_xx(d, s); +} + +STATIC_INLINE void LOAD_U32(int r, uae_u32 val) +{ + if((val & 0xffff0000) == 0xffff0000) { + MOVN_xi(r, ~val); + } else { + MOV_xi(r, val); + if(val >> 16) + MOVK_xish(r, val >> 16, 16); + } +} + +STATIC_INLINE void LOAD_U64(int r, uae_u64 val) +{ + MOV_xi(r, val); + if((val >> 16) & 0xffff) + MOVK_xish(r, val >> 16, 16); + if((val >> 32) & 0xffff) + MOVK_xish(r, val >> 32, 32); + if(val >> 48) + MOVK_xish(r, val >> 48, 48); +} + + +#define NUM_PUSH_CMDS 1 +#define NUM_POP_CMDS 1 +STATIC_INLINE void raw_push_regs_to_preserve(void) { + STP_xxXpre(27, 28, RSP_INDEX, -16); +} + +STATIC_INLINE void raw_pop_preserved_regs(void) { + LDP_xxXpost(27, 28, RSP_INDEX, 16); +} + +STATIC_INLINE void raw_flags_evicted(int r) +{ + live.state[FLAGTMP].status = INMEM; + live.state[FLAGTMP].realreg = -1; + /* We just "evicted" FLAGTMP. */ + if (live.nat[r].nholds != 1) { + /* Huh? */ + abort(); + } + live.nat[r].nholds = 0; +} + +STATIC_INLINE void raw_flags_to_reg(int r) +{ + uintptr idx = (uintptr) &(regs.ccrflags.nzcv) - (uintptr) ®s; + MRS_NZCV_x(r); + if(flags_carry_inverted) { + EOR_xxCflag(r, r); + MSR_NZCV_x(r); + flags_carry_inverted = false; + } + STR_wXi(r, R_REGSTRUCT, idx); + raw_flags_evicted(r); +} + +STATIC_INLINE void raw_reg_to_flags(int r) +{ + MSR_NZCV_x(r); +} + + +// +// compuemu_support used raw calls +// +LOWFUNC(WRITE,RMW,2,compemu_raw_inc_opcount,(IM16 op)) +{ + uintptr idx = (uintptr) &(regs.raw_cputbl_count) - (uintptr) ®s; + LDR_xXi(REG_WORK2, R_REGSTRUCT, idx); + MOV_xi(REG_WORK3, op); + LDR_wXxLSLi(REG_WORK1, REG_WORK2, REG_WORK3, 1); + ADD_wwi(REG_WORK1, REG_WORK1, 1); + STR_wXxLSLi(REG_WORK1, REG_WORK2, REG_WORK3, 1); +} +LENDFUNC(WRITE,RMW,1,compemu_raw_inc_opcount,(IM16 op)) + +LOWFUNC(WRITE,READ,1,compemu_raw_cmp_pc,(IMPTR s)) +{ + /* s is always >= NATMEM_OFFSETX and < NATMEM_OFFSETX + max. Amiga mem */ + clobber_flags(); + + uintptr idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + LDR_xXi(REG_WORK1, R_REGSTRUCT, idx); // regs.pc_p is 64 bit + + LOAD_U64(REG_WORK2, s); + CMP_xx(REG_WORK1, REG_WORK2); +} +LENDFUNC(WRITE,READ,1,compemu_raw_cmp_pc,(IMPTR s)) + +LOWFUNC(NONE,WRITE,1,compemu_raw_set_pc_m,(MEMR s)) +{ + uintptr idx; + if(s >= (uintptr) ®s && s < ((uintptr) ®s) + sizeof(struct regstruct)) { + idx = s - (uintptr) ®s; + if(s == (uintptr) &(regs.pc_p)) + LDR_xXi(REG_WORK1, R_REGSTRUCT, idx); + else + LDR_wXi(REG_WORK1, R_REGSTRUCT, idx); + } else { + LOAD_U64(REG_WORK1, s); + LDR_xXi(REG_WORK1, REG_WORK1, 0); + } + + idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + STR_xXi(REG_WORK1, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,1,compemu_raw_set_pc_m,(MEMR s)) + +LOWFUNC(NONE,WRITE,1,compemu_raw_set_pc_i,(IMPTR s)) +{ + LOAD_U64(REG_WORK1, s); + uintptr idx = (uintptr) &(regs.pc_p) - (uintptr) ®s; + STR_xXi(REG_WORK1, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,1,compemu_raw_set_pc_i,(IMPTR s)) + +LOWFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IM32 s)) +{ + /* d points always to memory in regs struct */ + LOAD_U32(REG_WORK2, s); + uintptr idx = d - (uintptr) ®s; + if(d == (uintptr) &(regs.pc_p)) + STR_xXi(REG_WORK2, R_REGSTRUCT, idx); + else + STR_wXi(REG_WORK2, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,2,compemu_raw_mov_l_mi,(MEMW d, IM32 s)) + +LOWFUNC(NONE,WRITE,2,compemu_raw_mov_l_mr,(MEMW d, RR4 s)) +{ + /* d points always to memory in regs struct */ + uintptr idx = d - (uintptr) ®s; + if(d == (uintptr) &(regs.pc_p)) + STR_xXi(s, R_REGSTRUCT, idx); + else + STR_wXi(s, R_REGSTRUCT, idx); +} +LENDFUNC(NONE,WRITE,2,compemu_raw_mov_l_mr,(MEMW d, RR4 s)) + +LOWFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IM32 s)) +{ + LOAD_U32(d, s); +} +LENDFUNC(NONE,NONE,2,compemu_raw_mov_l_ri,(W4 d, IM32 s)) + +LOWFUNC(NONE,READ,2,compemu_raw_mov_l_rm,(W4 d, MEMR s)) +{ + if(s >= (uintptr) ®s && s < ((uintptr) ®s) + sizeof(struct regstruct)) { + uintptr idx = s - (uintptr) ®s; + if(s == (uintptr) &(regs.pc_p)) + LDR_xXi(d, R_REGSTRUCT, idx); + else + LDR_wXi(d, R_REGSTRUCT, idx); + } else { + LOAD_U64(REG_WORK1, s); + LDR_xXi(d, REG_WORK1, 0); + } +} +LENDFUNC(NONE,READ,2,compemu_raw_mov_l_rm,(W4 d, MEMR s)) + +LOWFUNC(NONE,NONE,2,compemu_raw_mov_l_rr,(W4 d, RR4 s)) +{ + MOV_xx(d, s); +} +LENDFUNC(NONE,NONE,2,compemu_raw_mov_l_rr,(W4 d, RR4 s)) + +LOWFUNC(WRITE,RMW,1,compemu_raw_dec_m,(MEMRW d)) +{ + clobber_flags(); + + LOAD_U64(REG_WORK1, d); + LDR_wXi(REG_WORK2, REG_WORK1, 0); + SUBS_wwi(REG_WORK2, REG_WORK2, 1); + STR_wXi(REG_WORK2, REG_WORK1, 0); +} +LENDFUNC(WRITE,RMW,1,compemu_raw_dec_m,(MEMRW ds)) + +STATIC_INLINE void compemu_raw_call(uintptr t) +{ + LOAD_U64(REG_WORK1, t); + + STR_xXpre(RLR_INDEX, RSP_INDEX, -16); + BLR_x(REG_WORK1); + LDR_xXpost(RLR_INDEX, RSP_INDEX, 16); +} + +STATIC_INLINE void compemu_raw_call_r(RR4 r) +{ + STR_xXpre(RLR_INDEX, RSP_INDEX, -16); + BLR_x(r); + LDR_xXpost(RLR_INDEX, RSP_INDEX, 16); +} + +STATIC_INLINE void compemu_raw_jcc_l_oponly(int cc) +{ + FIX_INVERTED_CARRY + + switch (cc) { + case NATIVE_CC_HI: // HI + BEQ_i(2); // beq no jump + BCC_i(0); // bcc jump + break; + + case NATIVE_CC_LS: // LS + BEQ_i(2); // beq jump + BCC_i(2); // bcc no jump + // jump + B_i(0); + // no jump + break; + + case NATIVE_CC_F_OGT: // Jump if valid and greater than + BVS_i(2); // do not jump if NaN + BGT_i(0); // jump if greater than + break; + + case NATIVE_CC_F_OGE: // Jump if valid and greater or equal + BVS_i(2); // do not jump if NaN + BCS_i(0); // jump if carry set + break; + + case NATIVE_CC_F_OLT: // Jump if vaild and less than + BVS_i(2); // do not jump if NaN + BCC_i(0); // jump if carry cleared + break; + + case NATIVE_CC_F_OLE: // Jump if valid and less or equal + BVS_i(2); // do not jump if NaN + BLE_i(0); // jump if less or equal + break; + + case NATIVE_CC_F_OGL: // Jump if valid and greator or less + BVS_i(2); // do not jump if NaN + BNE_i(0); // jump if not equal + break; + + case NATIVE_CC_F_OR: // Jump if valid + BVC_i(0); + break; + + case NATIVE_CC_F_UN: // Jump if NAN + BVS_i(0); + break; + + case NATIVE_CC_F_UEQ: // Jump if NAN or equal + BVS_i(2); // jump if NaN + BNE_i(2); // do not jump if greater or less + // jump + B_i(0); + break; + + case NATIVE_CC_F_UGT: // Jump if NAN or greater than + BVS_i(2); // jump if NaN + BLS_i(2); // do not jump if lower or same + // jump + B_i(0); + break; + + case NATIVE_CC_F_UGE: // Jump if NAN or greater or equal + BVS_i(2); // jump if NaN + BMI_i(2); // do not jump if lower + // jump + B_i(0); + break; + + case NATIVE_CC_F_ULT: // Jump if NAN or less than + BVS_i(2); // jump if NaN + BGE_i(2); // do not jump if greater or equal + // jump + B_i(0); + break; + + case NATIVE_CC_F_ULE: // Jump if NAN or less or equal + BVS_i(2); // jump if NaN + BGT_i(2); // do not jump if greater + // jump + B_i(0); + break; + + default: + CC_B_i(cc, 0); + break; + } + // emit of target into last branch will be done by caller +} + +STATIC_INLINE void compemu_raw_handle_except(IM32 cycles) +{ + uae_u32* branchadd; + + clobber_flags(); + + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + LDR_wXi(REG_WORK1, R_REGSTRUCT, idx); + branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // no exception, jump to next instruction + + raw_pop_preserved_regs(); + LOAD_U32(REG_PAR1, cycles); + LDR_xPCi(REG_WORK1, 8); // + BR_x(REG_WORK1); + emit_longlong((uintptr)execute_exception); + + // Write target of next instruction + write_jmp_target(branchadd, (uintptr)get_target()); +} + +STATIC_INLINE void compemu_raw_maybe_recompile(uintptr t) +{ + BGE_i(NUM_POP_CMDS + 5); + raw_pop_preserved_regs(); + LDR_xPCi(REG_WORK1, 8); + BR_x(REG_WORK1); + emit_longlong(t); +} + +STATIC_INLINE void compemu_raw_jmp(uintptr t) +{ + LDR_xPCi(REG_WORK1, 8); + BR_x(REG_WORK1); + emit_longlong(t); +} + +STATIC_INLINE void compemu_raw_jmp_pc_tag(uintptr base) +{ + uintptr idx = (uintptr)®s.pc_p - (uintptr)®s; + LDRH_wXi(REG_WORK1, R_REGSTRUCT, idx); + LDR_xPCi(REG_WORK2, 12); + LDR_xXxLSLi(REG_WORK1, REG_WORK2, REG_WORK1, 1); + BR_x(REG_WORK1); + emit_longlong(base); +} + +STATIC_INLINE void compemu_raw_maybe_cachemiss(uintptr t) +{ + BEQ_i(NUM_POP_CMDS + 5); + raw_pop_preserved_regs(); + LDR_xPCi(REG_WORK1, 8); + BR_x(REG_WORK1); + emit_longlong(t); +} + +STATIC_INLINE void compemu_raw_maybe_do_nothing(IM32 cycles, uintptr adr) +{ + uintptr idx = (uintptr)®s.spcflags - (uintptr) ®s; + LDR_wXi(REG_WORK1, R_REGSTRUCT, idx); + uae_s8 *branchadd = (uae_s8 *)get_target(); + CBZ_wi(REG_WORK1, 0); // + + idx = (uintptr)&countdown - (uintptr) ®s; + LDR_wXi(REG_WORK2, R_REGSTRUCT, idx); + if(cycles >= 0 && cycles <= 0xfff) { + SUB_wwi(REG_WORK2, REG_WORK2, cycles); + } else { + LOAD_U32(REG_WORK1, cycles); + SUB_www(REG_WORK2, REG_WORK2, REG_WORK1); + } + STR_wXi(REG_WORK2, R_REGSTRUCT, idx); + + raw_pop_preserved_regs(); + LDR_xPCi(REG_WORK1, 8); + BR_x(REG_WORK1); + emit_longlong(adr); + + // + write_jmp_target((uae_u32 *)branchadd, (uintptr)get_target()); +} + +// Optimize access to struct regstruct with and memory with fixed registers + +LOWFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMPTR s)) +{ + LOAD_U64(R_REGSTRUCT, s); + uintptr offsmem = (uintptr)&NATMEM_OFFSETX - (uintptr) ®s; + LDR_xXi(R_MEMSTART, R_REGSTRUCT, offsmem); +} +LENDFUNC(NONE,NONE,1,compemu_raw_init_r_regstruct,(IMPTR s)) + +// Handle end of compiled block +LOWFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IM32 cycles)) +{ + // countdown -= scaled_cycles(totcycles); + uintptr offs = (uintptr)&countdown - (uintptr)®s; + LDR_wXi(REG_WORK1, R_REGSTRUCT, offs); + if(cycles >= 0 && cycles <= 0xfff) { + SUB_wwi(REG_WORK1, REG_WORK1, cycles); + } else { + LOAD_U32(REG_WORK2, cycles); + SUB_www(REG_WORK1, REG_WORK1, REG_WORK2); + } + STR_wXi(REG_WORK1, R_REGSTRUCT, offs); + + TBNZ_xii(REG_WORK1, 31, 7); // test sign and branch if set (negative) + UBFIZ_xxii(rr_pc, rr_pc, 0, 16); // apply TAGMASK + LDR_xPCi(REG_WORK1, 12); // + LDR_xXxLSLi(REG_WORK1, REG_WORK1, rr_pc, 3); // cacheline holds pointer -> multiply with 8 + BR_x(REG_WORK1); + emit_longlong((uintptr)cache_tags); + + raw_pop_preserved_regs(); + LDR_xPCi(REG_WORK1, 8); // + BR_x(REG_WORK1); + + emit_longlong((uintptr)do_nothing); +} +LENDFUNC(NONE,NONE,2,compemu_raw_endblock_pc_inreg,(RR4 rr_pc, IM32 cycles)) + +STATIC_INLINE uae_u32* compemu_raw_endblock_pc_isconst(IM32 cycles, IMPTR v) +{ + /* v is always >= NATMEM_OFFSETX and < NATMEM_OFFSETX + max. Amiga mem */ + uae_u32* tba; + // countdown -= scaled_cycles(totcycles); + uintptr offs = (uintptr)&countdown - (uintptr)®s; + LDR_wXi(REG_WORK1, R_REGSTRUCT, offs); + if(cycles >= 0 && cycles <= 0xfff) { + SUB_wwi(REG_WORK1, REG_WORK1, cycles); + } else { + LOAD_U32(REG_WORK2, cycles); + SUB_www(REG_WORK1, REG_WORK1, REG_WORK2); + } + STR_wXi(REG_WORK1, R_REGSTRUCT, offs); + + TBNZ_xii(REG_WORK1, 31, 2); // test sign and branch if set (negative) + tba = (uae_u32*)get_target(); + B_i(0); // + + LDR_xPCi(REG_WORK1, 16 + 4 * NUM_POP_CMDS); // + offs = (uintptr)®s.pc_p - (uintptr)®s; + STR_xXi(REG_WORK1, R_REGSTRUCT, offs); + raw_pop_preserved_regs(); + LDR_xPCi(REG_WORK1, 16); // + BR_x(REG_WORK1); + + emit_longlong(v); + emit_longlong((uintptr)do_nothing); + + return tba; +} + +/************************************************************************* +* FPU stuff * +*************************************************************************/ + +#ifdef USE_JIT_FPU + +LOWFUNC(NONE,NONE,2,raw_fmov_rr,(FW d, FR s)) +{ + FMOV_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_fmov_rr,(FW d, FR s)) + +LOWFUNC(NONE,WRITE,2,compemu_raw_fmov_mr_drop,(MEMW mem, FR s)) +{ + if(mem >= (uintptr) ®s && mem < (uintptr) ®s + 32760 && ((mem - (uintptr) ®s) & 0x7) == 0) { + STR_dXi(s, R_REGSTRUCT, (mem - (uintptr) ®s)); + } else { + LOAD_U64(REG_WORK1, mem); + STR_dXi(s, REG_WORK1, 0); + } +} +LENDFUNC(NONE,WRITE,2,compemu_raw_fmov_mr_drop,(MEMW mem, FR s)) + +LOWFUNC(NONE,READ,2,compemu_raw_fmov_rm,(FW d, MEMR mem)) +{ + if(mem >= (uintptr) ®s && mem < (uintptr) ®s + 32760 && ((mem - (uintptr) ®s) & 0x7) == 0) { + LDR_dXi(d, R_REGSTRUCT, (mem - (uintptr) ®s)); + } else { + LOAD_U64(REG_WORK1, mem); + LDR_dXi(d, REG_WORK1, 0); + } +} +LENDFUNC(NONE,READ,2,compemu_raw_fmov_rm,(FW d, MEMW mem)) + +LOWFUNC(NONE,NONE,2,raw_fmov_l_rr,(FW d, RR4 s)) +{ + SCVTF_dw(d, s); +} +LENDFUNC(NONE,NONE,2,raw_fmov_l_rr,(FW d, RR4 s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_s_rr,(FW d, RR4 s)) +{ + FMOV_sw(SCRATCH_F64_1, s); + FCVT_ds(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_s_rr,(FW d, RR4 s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_w_rr,(FW d, RR2 s)) +{ + SIGNED16_REG_2_REG(REG_WORK1, s); + SCVTF_dw(d, REG_WORK1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_w_rr,(FW d, RR2 s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_b_rr,(FW d, RR1 s)) +{ + SIGNED8_REG_2_REG(REG_WORK1, s); + SCVTF_dw(d, REG_WORK1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_b_rr,(FW d, RR1 s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) +{ + BFI_xxii(s1, s2, 32, 32); + FMOV_dx(d, s1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) + +LOWFUNC(NONE,NONE,2,raw_fmov_to_l_rr,(W4 d, FR s)) +{ + FRINTI_dd(SCRATCH_F64_1, s); + FCVTAS_wd(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_to_l_rr,(W4 d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_to_s_rr,(W4 d, FR s)) +{ + FCVT_sd(SCRATCH_F64_1, s); + FMOV_ws(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fmov_to_s_rr,(W4 d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fmov_to_w_rr,(W4 d, FR s, int targetIsReg)) +{ + FRINTI_dd(SCRATCH_F64_1, s); + FCVTAS_wd(REG_WORK1, SCRATCH_F64_1); + + // maybe saturate... + TBZ_xii(REG_WORK1, 31, 6); // positive + CLS_ww(REG_WORK2, REG_WORK1); // negative: if 17 bits are 1 -> no saturate + SUB_wwi(REG_WORK2, REG_WORK2, 16); + TBZ_xii(REG_WORK2, 31, 7); // done + MOVK_wi(d, 0x8000); // max. negative value in 16 bit + B_i(6); + + // positive + CLZ_ww(REG_WORK2, REG_WORK1); // positive: if 17 bits are 0 -> no saturate + SUB_wwi(REG_WORK2, REG_WORK2, 17); + TBZ_xii(REG_WORK2, 31, 2); + MOV_wi(REG_WORK1, 0x7fff); // max. positive value in 16 bit + + // done + BFI_wwii(d, REG_WORK1, 0, 16); +} +LENDFUNC(NONE,NONE,2,raw_fmov_to_w_rr,(W4 d, FR s, int targetIsReg)) + +LOWFUNC(NONE,NONE,3,raw_fmov_to_b_rr,(W4 d, FR s, int targetIsReg)) +{ + FRINTI_dd(SCRATCH_F64_1, s); + FCVTAS_wd(REG_WORK1, SCRATCH_F64_1); + + // maybe saturate... + TBZ_xii(REG_WORK1, 31, 6); // positive + CLS_ww(REG_WORK2, REG_WORK1); // negative: if 25 bits are 1 -> no saturate + SUB_wwi(REG_WORK2, REG_WORK2, 24); + TBZ_xii(REG_WORK2, 31, 7); // done + MOV_wi(REG_WORK1, 0x80); // max. negative value in 8 bit + B_i(5); + + // positive + CLZ_ww(REG_WORK2, REG_WORK1); // positive: if 25 bits are 0 -> no saturate + SUB_wwi(REG_WORK2, REG_WORK2, 25); + TBZ_xii(REG_WORK2, 31, 2); + MOV_wi(REG_WORK1, 0x7f); // max. positive value in 8 bit + + // done + BFI_wwii(d, REG_WORK1, 0, 8); +} +LENDFUNC(NONE,NONE,3,raw_fmov_to_b_rr,(W4 d, FR s, int targetIsReg)) + +LOWFUNC(NONE,NONE,1,raw_fmov_d_ri_0,(FW r)) +{ + MOVI_di(r, 0); +} +LENDFUNC(NONE,NONE,1,raw_fmov_d_ri_0,(FW r)) + +LOWFUNC(NONE,NONE,1,raw_fmov_d_ri_1,(FW r)) +{ + FMOV_di(r, 0b01110000); +} +LENDFUNC(NONE,NONE,1,raw_fmov_d_ri_1,(FW r)) + +LOWFUNC(NONE,NONE,1,raw_fmov_d_ri_10,(FW r)) +{ + FMOV_di(r, 0b00100100); +} +LENDFUNC(NONE,NONE,1,raw_fmov_d_ri_10,(FW r)) + +LOWFUNC(NONE,NONE,1,raw_fmov_d_ri_100,(FW r)) +{ + MOV_wi(REG_WORK1, 100); + SCVTF_dw(r, REG_WORK1); +} +LENDFUNC(NONE,NONE,1,raw_fmov_d_ri_100,(FW r)) + +LOWFUNC(NONE,READ,2,raw_fmov_d_rm,(FW r, MEMR m)) +{ + LOAD_U64(REG_WORK1, m); + LDR_dXi(r, REG_WORK1, 0); +} +LENDFUNC(NONE,READ,2,raw_fmov_d_rm,(FW r, MEMR m)) + +LOWFUNC(NONE,READ,2,raw_fmovs_rm,(FW r, MEMR m)) +{ + LOAD_U64(REG_WORK1, m); + LDR_sXi(r, REG_WORK1, 0); + FCVT_ds(r, r); +} +LENDFUNC(NONE,READ,2,raw_fmovs_rm,(FW r, MEMR m)) + +LOWFUNC(NONE,NONE,3,raw_fmov_to_d_rrr,(W4 d1, W4 d2, FR s)) +{ + FMOV_xd(d1, s); + LSR_xxi(d2, d1, 32); +} +LENDFUNC(NONE,NONE,3,raw_fmov_to_d_rrr,(W4 d1, W4 d2, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fsqrt_rr,(FW d, FR s)) +{ + FSQRT_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_fsqrt_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fabs_rr,(FW d, FR s)) +{ + FABS_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_fabs_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fneg_rr,(FW d, FR s)) +{ + FNEG_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_fneg_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fdiv_rr,(FRW d, FR s)) +{ + FDIV_ddd(d, d, s); +} +LENDFUNC(NONE,NONE,2,raw_fdiv_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fadd_rr,(FRW d, FR s)) +{ + FADD_ddd(d, d, s); +} +LENDFUNC(NONE,NONE,2,raw_fadd_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fmul_rr,(FRW d, FR s)) +{ + FMUL_ddd(d, d, s); +} +LENDFUNC(NONE,NONE,2,raw_fmul_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fsub_rr,(FRW d, FR s)) +{ + FSUB_ddd(d, d, s); +} +LENDFUNC(NONE,NONE,2,raw_fsub_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_frndint_rr,(FW d, FR s)) +{ + FRINTI_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_frndint_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_frndintz_rr,(FW d, FR s)) +{ + FRINTZ_dd(d, s); +} +LENDFUNC(NONE,NONE,2,raw_frndintz_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fmod_rr,(FRW d, FR s)) +{ + FDIV_ddd(SCRATCH_F64_1, d, s); + FRINTZ_dd(SCRATCH_F64_1, SCRATCH_F64_1); + FMSUB_dddd(d, SCRATCH_F64_1, s, d); +} +LENDFUNC(NONE,NONE,2,raw_fmod_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fsgldiv_rr,(FRW d, FR s)) +{ + FCVT_sd(SCRATCH_F64_1, d); + FCVT_sd(SCRATCH_F64_2, s); + FDIV_sss(SCRATCH_F64_1, SCRATCH_F64_1, SCRATCH_F64_2); + FCVT_ds(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fsgldiv_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,1,raw_fcuts_r,(FRW r)) +{ + FCVT_sd(SCRATCH_F64_1, r); + FCVT_ds(r, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,1,raw_fcuts_r,(FRW r)) + +LOWFUNC(NONE,NONE,2,raw_frem1_rr,(FRW d, FR s)) +{ + FDIV_ddd(SCRATCH_F64_2, d, s); + FRINTA_dd(SCRATCH_F64_2, SCRATCH_F64_2); + FMSUB_dddd(d, SCRATCH_F64_2, s, d); +} +LENDFUNC(NONE,NONE,2,raw_frem1_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fsglmul_rr,(FRW d, FR s)) +{ + FCVT_sd(SCRATCH_F64_1, d); + FCVT_sd(SCRATCH_F64_2, s); + FMUL_sss(SCRATCH_F64_1, SCRATCH_F64_1, SCRATCH_F64_2); + FCVT_ds(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fsglmul_rr,(FRW d, FR s)) + +LOWFUNC(NONE,NONE,2,raw_fmovs_rr,(FW d, FR s)) +{ + FCVT_sd(SCRATCH_F64_1, s); + FCVT_ds(d, SCRATCH_F64_1); +} +LENDFUNC(NONE,NONE,2,raw_fmovs_rr,(FW d, FR s)) + +LOWFUNC(NONE,NONE,3,raw_ffunc_rr,(double (*func)(double), FW d, FR s)) +{ + FMOV_dd(0, s); + + LOAD_U64(REG_WORK1, (uintptr)func); + + STR_xXpre(RLR_INDEX, RSP_INDEX, -16); + BLR_x(REG_WORK1); + LDR_xXpost(RLR_INDEX, RSP_INDEX, 16); + + FMOV_dd(d, 0); +} +LENDFUNC(NONE,NONE,3,raw_ffunc_rr,(double (*func)(double), FW d, FR s)) + +LOWFUNC(NONE,NONE,3,raw_fpowx_rr,(uae_u32 x, FW d, FR s)) +{ + double (*func)(double,double) = pow; + + if(x == 2) { + FMOV_di(0, 0b00000000); // load imm #2 into first reg + } else { + FMOV_di(0, 0b00100100); // load imm #10 into first reg + } + + FMOV_dd(1, s); + + LOAD_U64(REG_WORK1, (uintptr)func); + + STR_xXpre(RLR_INDEX, RSP_INDEX, -16); + BLR_x(REG_WORK1); + LDR_xXpost(RLR_INDEX, RSP_INDEX, 16); + + FMOV_dd(d, 0); +} +LENDFUNC(NONE,NONE,3,raw_fpowx_rr,(uae_u32 x, FW d, FR s)) + +LOWFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) +{ + FMOV_xd(REG_WORK1, s); + FCMP_d0(s); + ADD_xxx(REG_WORK4, adr, R_MEMSTART); + + uae_u32* branchadd_iszero = (uae_u32*)get_target(); + BEQ_i(0); // iszero + + UBFX_xxii(REG_WORK2, REG_WORK1, 52, 11); // get exponent + CMP_xi(REG_WORK2, 2047); + + uae_u32* branchadd_isnan = (uae_u32*)get_target(); + BEQ_i(0); // isnan + + MOV_xi(REG_WORK3, 15360); // diff of bias between double and long double + ADD_xxx(REG_WORK2, REG_WORK2, REG_WORK3); // exponent done + UBFX_xxii(REG_WORK3, REG_WORK1, 63, 1); // extract sign + LSL_xxi(REG_WORK3, REG_WORK3, 31); + ORR_xxxLSLi(REG_WORK2, REG_WORK3, REG_WORK2, 16); // merge sign and exponent + + REV32_xx(REG_WORK2, REG_WORK2); + STRH_wXi(REG_WORK2, REG_WORK4, 0); // write exponent + ADD_xxi(REG_WORK4, REG_WORK4, 4); + + LSL_xxi(REG_WORK1, REG_WORK1, 11); // shift mantissa to correct position + REV_xx(REG_WORK1, REG_WORK1); + SET_xxbit(REG_WORK1, REG_WORK1, 7); // insert explicit 1 + STR_xXi(REG_WORK1, REG_WORK4, 0); + uae_u32* branchadd_end = (uae_u32*)get_target(); + B_i(0); // end_of_op + + // isnan + write_jmp_target(branchadd_isnan, (uintptr)get_target()); + MOV_xish(REG_WORK1, 0x7fff, 16); + MOVN_xi(REG_WORK2, 0); + B_i(4); + + // iszero + write_jmp_target(branchadd_iszero, (uintptr)get_target()); + UBFX_xxii(REG_WORK1, REG_WORK1, 63, 1); // extract sign + LSL_xxi(REG_WORK1, REG_WORK1, 31); + MOV_xi(REG_WORK2, 0); + + REV32_xx(REG_WORK1, REG_WORK1); + STR_wXi(REG_WORK1, REG_WORK4, 0); + STP_wwXi(REG_WORK2, REG_WORK2, REG_WORK4, 4); + + // end_of_op + write_jmp_target(branchadd_end, (uintptr)get_target()); +} +LENDFUNC(NONE,WRITE,2,raw_fp_from_exten_mr,(RR4 adr, FR s)) + +LOWFUNC(NONE,READ,2,raw_fp_to_exten_rm,(FW d, RR4 adr)) +{ + ADD_xxx(REG_WORK3, adr, R_MEMSTART); + + ADD_xxi(REG_WORK1, REG_WORK3, 4); + LDR_xXi(REG_WORK1, REG_WORK1, 0); + CLEAR_xxbit(REG_WORK1, REG_WORK1, 7); // clear explicit 1 + REV_xx(REG_WORK1, REG_WORK1); + + LDRH_wXi(REG_WORK4, REG_WORK3, 0); + REV16_xx(REG_WORK4, REG_WORK4); // exponent now in lower half + + ANDS_xx7fff(REG_WORK2, REG_WORK4); + uae_u32* branchadd_notzero = (uae_u32*)get_target(); + BNE_i(0); // not_zero + + uae_u32* branchadd_notzero2 = (uae_u32*)get_target(); + CBNZ_xi(REG_WORK1, 0); // not zero + + // zero + MOVI_di(d, 0); + uae_u32* branchadd_end = (uae_u32*)get_target(); + TBZ_xii(REG_WORK4, 15, 0); // end_of_op + MOV_xish(REG_WORK1, 0x8000, 48); + FMOV_dx(d, REG_WORK1); + uae_u32* branchadd_end2 = (uae_u32*)get_target(); + B_i(0); // end_of_op + + // not_zero + write_jmp_target(branchadd_notzero, (uintptr)get_target()); + write_jmp_target(branchadd_notzero2, (uintptr)get_target()); + MOV_xi(REG_WORK3, 15360); // diff of bias between double and long double + SUB_xxx(REG_WORK2, REG_WORK2, REG_WORK3); // exponent done, ToDo: check for carry -> result gets Inf in double + UBFX_xxii(REG_WORK4, REG_WORK4, 15, 1); // extract sign + BFI_xxii(REG_WORK2, REG_WORK4, 11, 1); // insert sign + LSR_xxi(REG_WORK1, REG_WORK1, 11); // shift mantissa to correct position + LSL_xxi(REG_WORK2, REG_WORK2, 52); + ORR_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + FMOV_dx(d, REG_WORK1); + + // end_of_op + write_jmp_target(branchadd_end, (uintptr)get_target()); + write_jmp_target(branchadd_end2, (uintptr)get_target()); +} +LENDFUNC(NONE,READ,2,raw_fp_to_exten_rm,(FW d, RR4 adr)) + +LOWFUNC(NONE,WRITE,2,raw_fp_from_double_mr,(RR4 adr, FR s)) +{ + REV64_dd(SCRATCH_F64_1, s); + STR_dXx(SCRATCH_F64_1, adr, R_MEMSTART); +} +LENDFUNC(NONE,WRITE,2,raw_fp_from_double_mr,(RR4 adr, FR s)) + +LOWFUNC(NONE,READ,2,raw_fp_to_double_rm,(FW d, RR4 adr)) +{ + LDR_dXx(d, adr, R_MEMSTART); + REV64_dd(d, d); +} +LENDFUNC(NONE,READ,2,raw_fp_to_double_rm,(FW d, RR4 adr)) + +STATIC_INLINE void raw_fflags_into_flags(int r) +{ + FCMP_d0(r); +} + +LOWFUNC(NONE,NONE,2,raw_fp_fscc_ri,(RW4 d, int cc)) +{ + switch (cc) { + case NATIVE_CC_F_NEVER: + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_NE: // Set if not equal + CSETM_wc(REG_WORK1, NATIVE_CC_NE); + BFXIL_xxii(d, REG_WORK1, 0, 8); + break; + + case NATIVE_CC_EQ: // Set if equal + CSETM_wc(REG_WORK1, NATIVE_CC_EQ); + BFXIL_xxii(d, REG_WORK1, 0, 8); + break; + + case NATIVE_CC_F_OGT: // Set if valid and greater than + BVS_i(4); // do not set if NaN + BLE_i(3); // do not set if less or equal + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_OGE: // Set if valid and greater or equal + BVS_i(4); // do not set if NaN + BCC_i(3); // do not set if carry cleared + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_OLT: // Set if vaild and less than + BVS_i(4); // do not set if NaN + BCS_i(3); // do not set if carry set + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_OLE: // Set if valid and less or equal + BVS_i(4); // do not set if NaN + BGT_i(3); // do not set if greater than + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_OGL: // Set if valid and greator or less + BVS_i(4); // do not set if NaN + BEQ_i(3); // do not set if equal + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_OR: // Set if valid + CSETM_wc(REG_WORK1, NATIVE_CC_VC); // do not set if NaN + BFXIL_xxii(d, REG_WORK1, 0, 8); + break; + + case NATIVE_CC_F_UN: // Set if NAN + CSETM_wc(REG_WORK1, NATIVE_CC_VS); // do not set if valid + BFXIL_xxii(d, REG_WORK1, 0, 8); + break; + + case NATIVE_CC_F_UEQ: // Set if NAN or equal + BVS_i(2); // set if NaN + BNE_i(3); // do not set if greater or less + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_UGT: // Set if NAN or greater than + BVS_i(2); // set if NaN + BLS_i(3); // do not set if lower or same + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_UGE: // Set if NAN or greater or equal + BVS_i(2); // set if NaN + BMI_i(3); // do not set if lower + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_ULT: // Set if NAN or less than + BVS_i(2); // set if NaN + BGE_i(3); // do not set if greater or equal + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + + case NATIVE_CC_F_ULE: // Set if NAN or less or equal + BVS_i(2); // set if NaN + BGT_i(3); // do not set if greater + SET_LOW8_xx(d, d); + B_i(2); + CLEAR_LOW8_xx(d, d); + break; + } +} +LENDFUNC(NONE,NONE,2,raw_fp_fscc_ri,(RW4 d, int cc)) + +LOWFUNC(NONE,NONE,1,raw_roundingmode,(IM32 mode)) +{ + MOV_xi(REG_WORK2, (mode >> 22)); + MRS_FPCR_x(REG_WORK1); + BFI_xxii(REG_WORK1, REG_WORK2, 22, 2); + MSR_FPCR_x(REG_WORK1); +} +LENDFUNC(NONE,NONE,1,raw_roundingmode,(IM32 mode)) + +#endif // USE_JIT_FPU + diff --git a/src/jit/codegen_armA64.h b/src/jit/codegen_armA64.h new file mode 100644 index 00000000..3763ec38 --- /dev/null +++ b/src/jit/codegen_armA64.h @@ -0,0 +1,482 @@ +/* + * compiler/codegen_armA64.h - AARCH64 code generator + * + * Copyright (c) 2019 TomB + * + * This file is part of the UAE4ARM project. + * + * JIT compiler m68k -> ARMv8.1 + * + * Original 68040 JIT compiler for UAE, copyright 2000-2002 Bernd Meyer + * This file is derived from CCG, copyright 1999-2003 Ian Piumarta + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#ifndef ARM_ASMA64_H +#define ARM_ASMA64_H + + +/* CPSR flags */ + +#define ARM_N_FLAG 0x80000000 +#define ARM_Z_FLAG 0x40000000 +#define ARM_C_FLAG 0x20000000 +#define ARM_V_FLAG 0x10000000 +#define ARM_CV_FLAGS (ARM_C_FLAG|ARM_V_FLAG) + + +#define _W(c) emit_long(c) + + +#define MIN_EL0 0b011 + +#define EX_UXTB 0b000 +#define EX_UXTH 0b001 +#define EX_UXTW 0b010 +#define EX_UXTX 0b011 +#define EX_SXTB 0b100 +#define EX_SXTH 0b101 +#define EX_SXTW 0b110 +#define EX_SXTX 0b111 + +#define immEncode(N,immr,imms) (N << 22) | (immr << 16) | (imms << 10) + + +/* read/write flags */ +// move from sysreg +#define MRS_NZCV_x(Xt) _W((0b1101010100111 << 19) | (MIN_EL0 << 16) | (0b0100 << 12) | (0b0010 << 8) | (0b000 << 5) | (Xt)) +#define MRS_FPCR_x(Xt) _W((0b1101010100111 << 19) | (MIN_EL0 << 16) | (0b0100 << 12) | (0b0100 << 8) | (0b000 << 5) | (Xt)) +// move to sysreg +#define MSR_NZCV_x(Xt) _W((0b1101010100011 << 19) | (MIN_EL0 << 16) | (0b0100 << 12) | (0b0010 << 8) | (0b000 << 5) | (Xt)) +#define MSR_FPCR_x(Xt) _W((0b1101010100011 << 19) | (MIN_EL0 << 16) | (0b0100 << 12) | (0b0100 << 8) | (0b000 << 5) | (Xt)) + + +/*---------------------------------------- + * branch instructions + *----------------------------------------*/ +// i is the number of instructions, i.e. 4 bytes +#define B_i(i) _W((0b000101 << 26) | ((i) & 0x03ffffff)) +#define BL_i(i) _W((0b100101 << 26) | ((i) & 0x03ffffff)) +#define BLR_x(Xn) _W((0b11010110001 << 21) | (0b11111 << 16) | (0 << 10) | ((Xn) << 5) | 0) +#define BR_x(Xn) _W((0b11010110000 << 21) | (0b11111 << 16) | (0 << 10) | ((Xn) << 5) | 0) + +#define CC_B_i(cc,i) _W((0b01010100 << 24) | (((i) & 0x0007ffff) << 5) | (cc)) +#define BEQ_i(i) CC_B_i(NATIVE_CC_EQ,i) +#define BNE_i(i) CC_B_i(NATIVE_CC_NE,i) +#define BCS_i(i) CC_B_i(NATIVE_CC_CS,i) +#define BCC_i(i) CC_B_i(NATIVE_CC_CC,i) +#define BMI_i(i) CC_B_i(NATIVE_CC_MI,i) +#define BPL_i(i) CC_B_i(NATIVE_CC_PL,i) +#define BVS_i(i) CC_B_i(NATIVE_CC_VS,i) +#define BVC_i(i) CC_B_i(NATIVE_CC_VC,i) +#define BHI_i(i) CC_B_i(NATIVE_CC_HI,i) +#define BLS_i(i) CC_B_i(NATIVE_CC_LS,i) +#define BGE_i(i) CC_B_i(NATIVE_CC_GE,i) +#define BLT_i(i) CC_B_i(NATIVE_CC_LT,i) +#define BGT_i(i) CC_B_i(NATIVE_CC_GT,i) +#define BLE_i(i) CC_B_i(NATIVE_CC_LE,i) + +#define RET _W((0b11010110010 << 21) | (0b11111 << 16) | (0 << 10) | ((30) << 5) | (0)) + +/* compare and branch */ +// these instructions do not affect condition flags +#define CBNZ_wi(Wt,i) _W((0b00110101 << 24) | (((i) & 0x0007ffff) << 5) | (Wt)) +#define CBNZ_xi(Xt,i) _W((0b10110101 << 24) | (((i) & 0x0007ffff) << 5) | (Xt)) +#define CBZ_wi(Wt,i) _W((0b00110100 << 24) | (((i) & 0x0007ffff) << 5) | (Wt)) +#define CBZ_xi(Xt,i) _W((0b10110100 << 24) | (((i) & 0x0007ffff) << 5) | (Xt)) + +/* test bit and branch */ +// these instructions do not affect condition flags +#define TBNZ_xii(Xt,bit,i) _W(((((bit) & 0x20) >> 5) << 31) | (0b0110111 << 24) | (((bit) & 0x1f) << 19) | ((((i)) % 0x3fff) << 5) | (Xt)) +#define TBNZ_wii(Wt,bit,i) _W((0 << 31) | (0b0110111 << 24) | (((bit) & 0x1f) << 19) | ((((i)) % 0x3fff) << 5) | (Wt)) +#define TBZ_xii(Xt,bit,i) _W(((((bit) & 0x20) >> 5) << 31) | (0b0110110 << 24) | (((bit) & 0x1f) << 19) | ((((i)) % 0x3fff) << 5) | (Xt)) +#define TBZ_wii(Wt,bit,i) _W((0 << 31) | (0b0110110 << 24) | (((bit) & 0x1f) << 19) | ((((i)) % 0x3fff) << 5) | (Wt)) + + +/*---------------------------------------- + * load/store registers + *---------------------------------------- */ +// i is number of bytes +#define LDP_wwXi(Wt1,Wt2,Xn,i) _W((0b0010100101 << 22) | ((((i)/4) & 0x7f) << 15) | ((Wt2) << 10) | ((Xn) << 5) | (Wt1)) +#define LDP_xxXi(Xt1,Xt2,Xn,i) _W((0b1010100101 << 22) | ((((i)/8) & 0x7f) << 15) | ((Xt2) << 10) | ((Xn) << 5) | (Xt1)) +#define LDP_xxXpost(Xt1,Xt2,Xn,i) _W((0b1010100011 << 22) | ((((i)/8) & 0x7f) << 15) | ((Xt2) << 10) | ((Xn) << 5) | (Xt1)) +#define LDR_wXi(Wt,Xn,i) _W((0b1011100101 << 22) | ((((i)/4) & 0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define LDR_xXi(Xt,Xn,i) _W((0b1111100101 << 22) | ((((i)/8) & 0xfff) << 10) | ((Xn) << 5) | (Xt)) +#define LDR_xXpost(Xt,Xn,i) _W((0b11111000010 << 21) | (((i) & 0x1ff) << 12) | (0b01 << 10) | ((Xn) << 5) | (Xt)) +#define LDR_wPCi(Wt,i) _W((0b00011000 << 24) | ((((i)/4) & 0x7ffff) << 5) | (Wt)) +#define LDR_xPCi(Xt,i) _W((0b01011000 << 24) | ((((i)/4) & 0x7ffff) << 5) | (Xt)) +#define LDR_wXx(Wt,Xn,Xm) _W((0b10111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define LDR_xXx(Xt,Xn,Xm) _W((0b11111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Xt)) +// i=0 no shift, i=1 LSL 2 (W) or LSL 3 (X) +#define LDR_wXxLSLi(Wt,Xn,Xm,i) _W((0b10111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (((i)&1) << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define LDR_xXxLSLi(Xt,Xn,Xm,i) _W((0b11111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (((i)&1) << 12) | (0b10 << 10) | ((Xn) << 5) | (Xt)) +#define LDRB_wXi(Wt,Xn,i) _W((0b0011100101 << 22) | (((i) & 0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define LDRB_wXx(Wt,Xn,Xm) _W((0b00111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define LDRH_wXi(Wt,Xn,i) _W((0b0111100101 << 22) | ((((i)/2) &0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define LDRH_wXx(Wt,Xn,Xm) _W((0b01111000011 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) + +#define STP_wwXi(Wt1,Wt2,Xn,i) _W((0b0010100100 << 22) | ((((i)/4) & 0x7f) << 15) | ((Wt2) << 10) | ((Xn) << 5) | (Wt1)) +#define STP_xxXi(Xt1,Xt2,Xn,i) _W((0b1010100100 << 22) | ((((i)/8) & 0x7f) << 15) | ((Xt2) << 10) | ((Xn) << 5) | (Xt1)) +#define STP_xxXpre(Xt1,Xt2,Xn,i) _W((0b1010100110 << 22) | ((((i)/8) & 0x7f) << 15) | ((Xt2) << 10) | ((Xn) << 5) | (Xt1)) +#define STR_wXi(Wt,Xn,i) _W((0b1011100100 << 22) | ((((i)/4) & 0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define STR_xXi(Xt,Xn,i) _W((0b1111100100 << 22) | ((((i)/8) & 0xfff) << 10) | ((Xn) << 5) | (Xt)) +#define STR_xXpre(Xt,Xn,i) _W((0b11111000000 << 21) | (((i) & 0x1ff) << 12) | (0b11 << 10) | ((Xn) << 5) | (Xt)) +#define STR_wXx(Wt,Xn,Xm) _W((0b10111000001 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define STR_xXx(Xt,Xn,Xm) _W((0b11111000001 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Xt)) +// i=0 no shift, i=1 LSL 2 (W) or LSL 3 (X) +#define STR_wXxLSLi(Wt,Xn,Xm,i) _W((0b10111000001 << 21) | ((Xm) << 16) | (0b011 << 13) | (((i)&1) << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define STRB_wXi(Wt,Xn,i) _W((0b0011100100 << 22) | (((i) & 0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define STRB_wXx(Wt,Xn,Xm) _W((0b00111000001 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) +#define STRH_wXi(Wt,Xn,i) _W((0b0111100100 << 22) | ((((i)/2) &0xfff) << 10) | ((Xn) << 5) | (Wt)) +#define STRH_wXx(Wt,Xn,Xm) _W((0b01111000001 << 21) | ((Xm) << 16) | (0b011 << 13) | (0 << 12) | (0b10 << 10) | ((Xn) << 5) | (Wt)) + + +/*---------------------------------------- + * move immediate/register + *----------------------------------------*/ +#define MOV_wi(Wd,i16) _W((0b01010010100 << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOV_xi(Xd,i16) _W((0b11010010100 << 21) | (((i16) & 0xffff) << 5) | (Xd)) +// sh in bits (multiple of 16) +#define MOV_wish(Wd,i16,sh) _W((0b010100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOV_xish(Xd,i16,sh) _W((0b110100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Xd)) +#define MOV_ww(Wd,Wm) _W((0b00101010000 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define MOV_xx(Xd,Xm) _W((0b10101010000 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) +#define MOVK_wi(Wd,i16) _W((0b01110010100 << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOVK_xi(Xd,i16) _W((0b11110010100 << 21) | (((i16) & 0xffff) << 5) | (Xd)) +#define MOVK_wish(Wd,i16,sh) _W((0b011100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOVK_xish(Xd,i16,sh) _W((0b111100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Xd)) +#define MOVN_wi(Wd,i16) _W((0b00010010100 << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOVN_xi(Xd,i16) _W((0b10010010100 << 21) | (((i16) & 0xffff) << 5) | (Xd)) +#define MOVN_wish(Wd,i16,sh) _W((0b000100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Wd)) +#define MOVN_xish(Xd,i16,sh) _W((0b100100101 << 23) | (((sh)/16) << 21) | (((i16) & 0xffff) << 5) | (Xd)) +#define MVN_ww(Wd,Wm) _W((0b00101010001 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define MVN_xx(Xd,Xm) _W((0b10101010001 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) + + +/*---------------------------------------- + * arithmetic + *----------------------------------------*/ +/* ADD */ +#define ADC_www(Wd,Wn,Wm) _W((0b00011010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ADC_xxx(Xd,Xn,Xm) _W((0b10011010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ADCS_www(Wd,Wn,Wm) _W((0b00111010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ADCS_xxx(Xd,Xn,Xm) _W((0b10111010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ADD_wwwEX(Wd,Wn,Wm,ex) _W((0b00001011001 << 21) | ((Wm) << 16) | ((ex) << 13) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ADD_xxwEX(Xd,Xn,Wm,ex) _W((0b10001011001 << 21) | ((Wm) << 16) | ((ex) << 13) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ADD_wwi(Wd,Wn,i12) _W((0b0001000100 << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (Wd)) +#define ADD_xxi(Xd,Xn,i12) _W((0b1001000100 << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (Xd)) +#define ADD_www(Wd,Wn,Wm) _W((0b00001011000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ADD_xxx(Xd,Xn,Xm) _W((0b10001011000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ADD_wwwLSLi(Wd,Wn,Wm,i) _W((0b00001011000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define ADD_xxxLSLi(Xd,Xn,Xm,i) _W((0b10001011000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define ADDS_wwi(Wd,Wn,i12) _W((0b0011000100 << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (Wd)) +#define ADDS_xxi(Xd,Xn,i12) _W((0b1011000100 << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (Xd)) +#define ADDS_www(Wd,Wn,Wm) _W((0b00101011000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ADDS_xxx(Xd,Xn,Xm) _W((0b10101011000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ADDS_wwwLSLi(Wd,Wn,Wm,i) _W((0b00101011000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define ADDS_xxxLSLi(Xd,Xn,Xm,i) _W((0b10101011000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) + +/* compare */ +#define CMP_wi(Wn,i12) _W((0b0111000100 << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (0b11111)) +#define CMP_xi(Xn,i12) _W((0b1111000100 << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (0b11111)) +#define CMP_ww(Wn,Wm) _W((0b01101011000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (0b11111)) +#define CMP_xx(Xn,Xm) _W((0b11101011000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (0b11111)) +#define CMP_wwLSLi(Wn,Wm,i) _W((0b01101011000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (0b11111)) +#define CMP_xxLSLi(Xn,Xm,i) _W((0b11101011000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (0b11111)) +#define CMP_wwEX(Wn,Wm,ex) _W((0b01101011001 << 21) | ((Wm) << 16) | ((ex) << 13) | (0 << 10) | ((Wn) << 5) | (0b11111)) + +/* MUL */ +#define MUL_www(Wd,Wn,Wm) _W((0b00011011000 << 21) | ((Wm) << 16) | (0b011111 << 10) | ((Wn) << 5) | (Wd)) +#define MUL_xxx(Xd,Xn,Xm) _W((0b10011011000 << 21) | ((Xm) << 16) | (0b011111 << 10) | ((Xn) << 5) | (Xd)) +// Xd = (Xn*Xm)[127...64] +#define SMULH_xxx(Xd,Xn,Xm) _W((0b10011011010 << 21) | ((Xm) << 16) | (0b011111 << 10) | ((Xn) << 5) | (Xd)) +#define UMULH_xxx(Xd,Xn,Xm) _W((0b10011011110 << 21) | ((Xm) << 16) | (0b011111 << 10) | ((Xn) << 5) | (Xd)) +// Xd = (Wn*Wm)[63...0] +#define SMULL_xww(Xd,Wn,Wm) _W((0b10011011001 << 21) | ((Wm) << 16) | (0b011111 << 10) | ((Wn) << 5) | (Xd)) +#define UMULL_xww(Xd,Wn,Wm) _W((0b10011011101 << 21) | ((Wm) << 16) | (0b011111 << 10) | ((Wn) << 5) | (Xd)) + +/* multiply sub */ +// Wd = Wa - (Wn * Wm) +#define MSUB_wwww(Wd,Wn,Wm,Wa) _W((0b00011011000 << 21) | ((Wm) << 16) | (1 << 15) | ((Wa) << 10) | ((Wn) << 5) | (Wd)) +#define MSUB_xxxx(Xd,Xn,Xm,Xa) _W((0b10011011000 << 21) | ((Xm) << 16) | (1 << 15) | ((Xa) << 10) | ((Xn) << 5) | (Xd)) + +/* DIV */ +// Wd = Wn / Wm +#define SDIV_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b000011 << 10) | ((Wn) << 5) | (Wd)) +#define SDIV_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b000011 << 10) | ((Xn) << 5) | (Xd)) +#define UDIV_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b000010 << 10) | ((Wn) << 5) | (Wd)) +#define UDIV_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b000010 << 10) | ((Xn) << 5) | (Xd)) + +/* NEG */ +#define NEG_ww(Wd,Wm) _W((0b01001011000 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define NEG_xx(Xd,Xm) _W((0b11001011000 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) +#define NEGS_ww(Wd,Wm) _W((0b01101011000 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define NEGS_xx(Xd,Xm) _W((0b11101011000 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) +#define NGC_ww(Wd,Wm) _W((0b01011010000 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define NGC_xx(Xd,Xm) _W((0b11011010000 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) +#define NGCS_ww(Wd,Wm) _W((0b01111010000 << 21) | ((Wm) << 16) | (0 << 10) | (0b11111 << 5) | (Wd)) +#define NGCS_xx(Xd,Xm) _W((0b11111010000 << 21) | ((Xm) << 16) | (0 << 10) | (0b11111 << 5) | (Xd)) + +/* SUB */ +// Wd = Wn - Wm +#define SBC_www(Wd,Wn,Wm) _W((0b01011010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define SBC_xxx(Xd,Xn,Xm) _W((0b11011010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define SBCS_www(Wd,Wn,Wm) _W((0b01111010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define SBCS_xxx(Xd,Xn,Xm) _W((0b11111010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define SUB_wwi(Wd,Wn,i12) _W((0b0101000100 << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (Wd)) +#define SUB_xxi(Xd,Xn,i12) _W((0b1101000100 << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (Xd)) +#define SUB_www(Wd,Wn,Wm) _W((0b01001011000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define SUB_xxx(Xd,Xn,Xm) _W((0b11001011000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define SUB_wwwEX(Wd,Wn,Wm,ex) _W((0b11001011001 << 21) | ((Wm) << 16) | ((ex) << 13) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define SUBS_wwi(Wd,Wn,i12) _W((0b0111000100 << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (Wd)) +#define SUBS_xxi(Xd,Xn,i12) _W((0b1111000100 << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (Xd)) +// sh: 0 - no shift, 1 - LSL 12 +#define SUBS_wwish(Wd,Wn,i12,sh) _W((0b011100010 << 23) | (((sh) & 1) << 22) | (((i12) & 0xfff) << 10) | ((Wn) << 5) | (Wd)) +#define SUBS_xxish(Xd,Xn,i12,sh) _W((0b111100010 << 23) | (((sh) & 1) << 22) | (((i12) & 0xfff) << 10) | ((Xn) << 5) | (Xd)) +#define SUBS_www(Wd,Wn,Wm) _W((0b01101011000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define SUBS_xxx(Xd,Xn,Xm) _W((0b11101011000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define SUBS_wwwLSLi(Wd,Wn,Wm,i) _W((0b01101011000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define SUBS_xxxLSLi(Xd,Xn,Xm,i) _W((0b11101011000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) + +/* signed extend */ +#define SBFM_wwii(Wd,Wn,immr,imms) _W((0b0001001100 << 22) | ((immr) << 16) | ((imms) << 10) | ((Wn) << 5) | (Wd)) +#define SBFM_xxii(Xd,Xn,immr,imms) _W((0b1001001101 << 22) | ((immr) << 16) | ((imms) << 10) | ((Xn) << 5) | (Xd)) +#define SXTB_ww(Wd,Wn) SBFM_wwii(Wd,Wn,0,7) +#define SXTB_xx(Xd,Xn) SBFM_xxii(Xd,Xn,0,7) +#define SXTH_ww(Wd,Wn) SBFM_wwii(Wd,Wn,0,15) +#define SXTH_xx(Xd,Xn) SBFM_xxii(Xd,Xn,0,15) +#define SXTW_xw(Xd,Wn) SBFM_xxii(Xd,Wn,0,31) + +/* unsigned extend */ +#define UBFM_wwii(Wd,Wn,immr,imms) _W((0b0101001100 << 22) | ((immr) << 16) | ((imms) << 10) | ((Wn) << 5) | (Wd)) +#define UBFM_xxii(Xd,Xn,immr,imms) _W((0b1101001101 << 22) | ((immr) << 16) | ((imms) << 10) | ((Xn) << 5) | (Xd)) +#define UXTB_ww(Wd,Wn) UBFM_wwii(Wd,Wn,0,7) +#define UXTB_xx(Xd,Xn) UBFM_xxii(Xd,Xn,0,7) +#define UXTH_ww(Wd,Wn) UBFM_wwii(Wd,Wn,0,15) +#define UXTH_xx(Xd,Xn) UBFM_xxii(Xd,Xn,0,15) + + +/*---------------------------------------- + * logical + *----------------------------------------*/ +/* AND */ +#define AND_www(Wd,Wn,Wm) _W((0b00001010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define AND_xxx(Xd,Xn,Xm) _W((0b10001010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define AND_ww3f(Wd,Wn) _W((0b000100100 << 23) | immEncode(0,0b000000,0b000101) | ((Wn) << 5) | (Wd)) +#define ANDS_www(Wd,Wn,Wm) _W((0b01101010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ANDS_xxx(Xd,Xn,Xm) _W((0b11101010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ANDS_xx7fff(Xd,Xn) _W((0b111100100 << 23) | immEncode(1,0b000000,0b001110) | ((Xn) << 5) | (Xd)) +#define ANDS_ww7f(Wd,Wn) _W((0b011100100 << 23) | immEncode(0,0b000000,0b000110) | ((Wn) << 5) | (Wd)) +#define ANDS_ww3f(Wd,Wn) _W((0b011100100 << 23) | immEncode(0,0b000000,0b000101) | ((Wn) << 5) | (Wd)) + +/* EOR */ +#define EOR_www(Wd,Wn,Wm) _W((0b01001010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define EOR_xxx(Xd,Xn,Xm) _W((0b11001010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define EOR_wwwLSLi(Wd,Wn,Wm,i) _W((0b01001010000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define EOR_xxxLSLi(Xd,Xn,Xm,i) _W((0b11001010000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) + +/* ORR */ +#define ORR_www(Wd,Wn,Wm) _W((0b00101010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define ORR_xxx(Xd,Xn,Xm) _W((0b10101010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) +#define ORR_wwwLSLi(Wd,Wn,Wm,i) _W((0b00101010000 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define ORR_xxxLSLi(Xd,Xn,Xm,i) _W((0b10101010000 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define ORR_wwwLSRi(Wd,Wn,Wm,i) _W((0b00101010010 << 21) | ((Wm) << 16) | (((i) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define ORR_xxxLSRi(Xd,Xn,Xm,i) _W((0b10101010010 << 21) | ((Xm) << 16) | (((i) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) + +/* TST */ +#define TST_ww(Wn,Wm) _W((0b01101010000 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (0b11111)) +#define TST_xx(Xn,Xm) _W((0b11101010000 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (0b11111)) + + +/*---------------------------------------- + * shift + *----------------------------------------*/ +#define ASR_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b001010 << 10) | ((Wn) << 5) | (Wd)) +#define ASR_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b001010 << 10) | ((Xn) << 5) | (Xd)) +#define ASR_wwi(Wd,Wn,i) _W((0b0001001100 << 22) | (((i) & 0x1f) << 16) | (0b011111 << 10) | ((Wn) << 5) | (Wd)) +#define ASR_xxi(Xd,Xn,i) _W((0b1001001101 << 22) | (((i) & 0x3f) << 16) | (0b111111 << 10) | ((Xn) << 5) | (Xd)) +#define LSL_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b001000 << 10) | ((Wn) << 5) | (Wd)) +#define LSL_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b001000 << 10) | ((Xn) << 5) | (Xd)) +#define LSL_wwi(Wd,Wn,i) _W((0b0101001100 << 22) | (((32-(i)) & 0x1f) << 16) | (((31-(i)) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define LSL_xxi(Xd,Xn,i) _W((0b1101001101 << 22) | (((64-(i)) & 0x3f) << 16) | (((63-(i)) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define LSR_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b001001 << 10) | ((Wn) << 5) | (Wd)) +#define LSR_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b001001 << 10) | ((Xn) << 5) | (Xd)) +#define LSR_wwi(Wd,Wn,i) _W((0b0101001100 << 22) | (((i) & 0x1f) << 16) | (0b011111 << 10) | ((Wn) << 5) | (Wd)) +#define LSR_xxi(Xd,Xn,i) _W((0b1101001101 << 22) | (((i) & 0x3f) << 16) | (0b111111 << 10) | ((Xn) << 5) | (Xd)) +#define ROR_wwi(Wd,Ws,i) _W((0b00010011100 << 21) | ((Ws) << 16) | (((i) & 0x1f) << 10) | ((Ws) << 5) | (Wd)) +#define ROR_xxi(Xd,Xs,i) _W((0b10010011110 << 21) | ((Xs) << 16) | (((i) & 0x3f) << 10) | ((Xs) << 5) | (Xd)) +#define ROR_www(Wd,Wn,Wm) _W((0b00011010110 << 21) | ((Wm) << 16) | (0b001011 << 10) | ((Wn) << 5) | (Wd)) +#define ROR_xxx(Xd,Xn,Xm) _W((0b10011010110 << 21) | ((Xm) << 16) | (0b001011 << 10) | ((Xn) << 5) | (Xd)) + + +/*---------------------------------------- + * bit ops + *----------------------------------------*/ +/* extract */ +// Wd[31...0] = Wn[31-lsb...0]Wm[31...lsb] +// Xd[63...0] = Xn[63-lsb...0]Xm[63...lsb] +#define EXTR_wwwi(Wd,Wn,Wm,lsb) _W((0b00010011100 << 21) | ((Wm) << 16) | (((lsb) & 0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define EXTR_xxxi(Xd,Xn,Xm,lsb) _W((0b10010011110 << 21) | ((Xm) << 16) | (((lsb) & 0x3f) << 10) | ((Xn) << 5) | (Xd)) + +/* bitfield */ +// dst[lsb+width-1...lsb] = src[width-1...0] +#define BFI_wwii(Wd,Wn,lsb,width) _W((0b0011001100 << 22) | (((32-(lsb))&0x1f) << 16) | ((((width)-1)&0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define BFI_xxii(Xd,Xn,lsb,width) _W((0b1011001101 << 22) | (((64-(lsb))&0x3f) << 16) | ((((width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define SBFIZ_wwii(Wd,Wn,lsb,width) _W((0b0001001100 << 22) | (((32-(lsb))&0x1f) << 16) | ((((width)-1)&0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define SBFIZ_xxii(Xd,Xn,lsb,width) _W((0b1001001101 << 22) | (((64-(lsb))&0x3f) << 16) | ((((width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define UBFIZ_wwii(Wd,Wn,lsb,width) _W((0b0101001100 << 22) | (((32-(lsb))&0x1f) << 16) | ((((width)-1)&0x1f) << 10) | ((Wn) << 5) | (Wd)) +#define UBFIZ_xxii(Xd,Xn,lsb,width) _W((0b1101001101 << 22) | (((64-(lsb))&0x3f) << 16) | ((((width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) + +// dst[width-1...0] = src[lsb+width-1...lsb] +#define BFXIL_wwii(Wd,Wn,lsb,width) _W((0b0011001100 << 22) | (((lsb)&0x1f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Wn) << 5) | (Wd)) +#define BFXIL_xxii(Xd,Xn,lsb,width) _W((0b1011001101 << 22) | (((lsb)&0x3f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define SBFX_wwii(Wd,Wn,lsb,width) _W((0b0001001100 << 22) | (((lsb)&0x1f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Wn) << 5) | (Wd)) +#define SBFX_xxii(Xd,Xn,lsb,width) _W((0b1001001101 << 22) | (((lsb)&0x3f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) +#define UBFX_wwii(Wd,Wn,lsb,width) _W((0b0101001100 << 22) | (((lsb)&0x1f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Wn) << 5) | (Wd)) +#define UBFX_xxii(Xd,Xn,lsb,width) _W((0b1101001101 << 22) | (((lsb)&0x3f) << 16) | ((((lsb)+(width)-1)&0x3f) << 10) | ((Xn) << 5) | (Xd)) + +#define BIC_www(Wd,Wn,Wm) _W((0b00001010001 << 21) | ((Wm) << 16) | (0 << 10) | ((Wn) << 5) | (Wd)) +#define BIC_xxx(Xd,Xn,Xm) _W((0b10001010001 << 21) | ((Xm) << 16) | (0 << 10) | ((Xn) << 5) | (Xd)) + +/* reverse */ +#define REV_ww(Wd,Wn) _W((0b01011010110 << 21) | (0b00000 << 16) | (0b000010 << 10) | ((Wn) << 5) | (Wd)) +#define REV_xx(Xd,Xn) _W((0b11011010110 << 21) | (0b00000 << 16) | (0b000011 << 10) | ((Xn) << 5) | (Xd)) +#define REV16_ww(Wd,Wn) _W((0b01011010110 << 21) | (0b00000 << 16) | (0b000001 << 10) | ((Wn) << 5) | (Wd)) +#define REV16_xx(Xd,Xn) _W((0b11011010110 << 21) | (0b00000 << 16) | (0b000001 << 10) | ((Xn) << 5) | (Xd)) +#define REV32_xx(Xd,Xn) _W((0b11011010110 << 21) | (0b00000 << 16) | (0b000010 << 10) | ((Xn) << 5) | (Xd)) + +#define CLS_ww(Wd,Wn) _W((0b01011010110 << 21) | (0b00000000101 << 10) | ((Wn) << 5) | (Wd)) +#define CLZ_ww(Wd,Wn) _W((0b01011010110 << 21) | (0b00000000100 << 10) | ((Wn) << 5) | (Wd)) + + +/*---------------------------------------- + * conditional ops + *----------------------------------------*/ +/* conditional compare */ +#define CCMP_wwfc(Wn,Wm,nzcv,cond) _W((0b01111010010 << 21) | ((Wm) << 16) | ((cond) << 12) | (0b00 << 10) | ((Wn) << 5) | (nzcv)) +#define CCMP_xxfc(Xn,Xm,nzcv,cond) _W((0b11111010010 << 21) | ((Xm) << 16) | ((cond) << 12) | (0b00 << 10) | ((Xn) << 5) | (nzcv)) + +/* conditional select */ +#define CSEL_wwwc(Wd,Wn,Wm,cond) _W((0b00011010100 << 21) | ((Wm) << 16) | ((cond) << 12) | (0b00 << 10) | ((Wn) << 5) | (Wd)) +#define CSEL_xxxc(Xd,Xn,Xm,cond) _W((0b10011010100 << 21) | ((Xm) << 16) | ((cond) << 12) | (0b00 << 10) | ((Xn) << 5) | (Xd)) + +/* conditional set */ +#define CSET_wc(Wd,cond) _W((0b00011010100 << 21) | (0b11111 << 16) | ((cond^1) << 12) | (0b01 << 10) | (0b11111 << 5) | (Wd)) +#define CSET_xc(Xd,cond) _W((0b10011010100 << 21) | (0b11111 << 16) | ((cond^1) << 12) | (0b01 << 10) | (0b11111 << 5) | (Xd)) + +/* conditional set mask */ +#define CSETM_wc(Wd,cond) _W((0b01011010100 << 21) | (0b11111 << 16) | ((cond^1) << 12) | (0b00 << 10) | (0b11111 << 5) | (Wd)) +#define CSETM_xc(Xd,cond) _W((0b11011010100 << 21) | (0b11111 << 16) | ((cond^1) << 12) | (0b00 << 10) | (0b11111 << 5) | (Xd)) + + +/*---------------------------------------- + * some special defines + *----------------------------------------*/ +// immediate encoding for flags: +// N N=1 immr=100001 imms=000000 +// Z N=1 immr=100010 imms=000000 +// C N=1 immr=100011 imms=000000 +// V N=1 immr=100100 imms=000000 +// ~N N=1 immr=100000 imms=111110 +// ~Z N=1 immr=100001 imms=111110 +// ~C N=1 immr=100010 imms=111110 +// ~V N=1 immr=100011 imms=111110 +#define immNflag immEncode(1, 0b100001, 0b000000) +#define immZflag immEncode(1, 0b100010, 0b000000) +#define immCflag immEncode(1, 0b100011, 0b000000) +#define immVflag immEncode(1, 0b100100, 0b000000) + +#define immNflagInv immEncode(1, 0b100000, 0b111110) +#define immZflagInv immEncode(1, 0b100001, 0b111110) +#define immCflagInv immEncode(1, 0b100010, 0b111110) +#define immVflagInv immEncode(1, 0b100011, 0b111110) + +#define immOP_EOR (0b110100100 << 23) +#define immOP_AND (0b100100100 << 23) +#define immOP_ORR (0b101100100 << 23) + +// R_MEMSTART is in 32bit address space and never 0, so CCMN(R_MEMSTART, #0, #0, #) will always clear NZCV +#define CLEAR_NZCV() _W((0b10111010010 << 21) | (0 << 16) | (NATIVE_CC_EQ << 12) | (0b10 << 10) | (R_MEMSTART << 5) | (0)) + +#define EOR_xxCflag(Xd,Xn) _W(immCflag | immOP_EOR | ((Xn) << 5) | (Xd)) +#define CLEAR_xxZflag(Xd,Xn) _W(immZflagInv | immOP_AND | ((Xn) << 5) | (Xd)) +#define CLEAR_xxCflag(Xd,Xn) _W(immCflagInv | immOP_AND | ((Xn) << 5) | (Xd)) +#define SET_xxZflag(Xd,Xn) _W(immZflag | immOP_ORR | ((Xn) << 5) | (Xd)) +#define SET_xxVflag(Xd,Xn) _W(immVflag | immOP_ORR | ((Xn) << 5) | (Xd)) +#define SET_xxCflag(Xd,Xn) _W(immCflag | immOP_ORR | ((Xn) << 5) | (Xd)) + +#define EOR_xxbit(Xd,Xn,bit) _W(immOP_EOR | immEncode(1, ((-(bit)) & 0x3f), 0b000000) | ((Xn) << 5) | (Xd)) +#define CLEAR_xxbit(Xd,Xn,bit) _W(immOP_AND | immEncode(1, ((-((bit)+1)) & 0x3f), 0b111110) | ((Xn) << 5) | (Xd)) +#define SET_xxbit(Xd,Xn,bit) _W(immOP_ORR | immEncode(1, ((-(bit)) & 0x3f), 0b000000) | ((Xn) << 5) | (Xd)) + +#define CLEAR_LOW4_xx(Xd,Xn) _W(immOP_AND | immEncode(1, 0b111100, 0b111011) | ((Xn) << 5) | (Xd)) +#define CLEAR_LOW8_xx(Xd,Xn) _W(immOP_AND | immEncode(1, 0b111000, 0b110111) | ((Xn) << 5) | (Xd)) +#define CLEAR_LOW16_xx(Xd,Xn) _W(immOP_AND | immEncode(1, 0b110000, 0b101111) | ((Xn) << 5) | (Xd)) + +#define SET_LOW8_xx(Xd,Xn) _W(immOP_ORR | immEncode(1, 0b000000, 0b000111) | ((Xn) << 5) | (Xd)) + +// Floatingpoint + +#define LDR_dXi(Dt,Xn,i) _W((0b1111110101 << 22) | (((i)/8) << 10) | ((Xn) << 5) | (Dt)) +#define LDR_sXi(St,Xn,i) _W((0b1011110101 << 22) | (((i)/4) << 10) | ((Xn) << 5) | (St)) +#define LDR_dXx(Dt,Xn,Xm) _W((0b11111100011 << 21) | ((Xm) << 16) | (0b011010 << 10) | ((Xn) << 5) | (Dt)) + +#define STR_dXi(Dt,Xn,i) _W((0b1111110100 << 22) | (((i)/8) << 10) | ((Xn) << 5) | (Dt)) +#define STR_sXi(St,Xn,i) _W((0b1011110100 << 22) | (((i)/4) << 10) | ((Xn) << 5) | (St)) +#define STR_dXx(Dt,Xn,Xm) _W((0b11111100001 << 21) | ((Xm) << 16) | (0b011010 << 10) | ((Xn) << 5) | (Dt)) +#define FMOV_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00000010000 << 10) | ((Dn) << 5) | (Dd)) +#define FMOV_ss(Sd,Sn) _W((0b00011110001 << 21) | (0b00000010000 << 10) | ((Sn) << 5) | (Sd)) +#define FMOV_dx(Dd,Xn) _W((0b10011110011 << 21) | (0b00111000000 << 10) | ((Xn) << 5) | (Dd)) +#define FMOV_xd(Xd,Dn) _W((0b10011110011 << 21) | (0b00110000000 << 10) | ((Dn) << 5) | (Xd)) +#define FMOV_sw(Sd,Wn) _W((0b00011110001 << 21) | (0b00111000000 << 10) | ((Wn) << 5) | (Sd)) +#define FMOV_ws(Wd,Sn) _W((0b00011110001 << 21) | (0b00110000000 << 10) | ((Sn) << 5) | (Wd)) +#define FMOV_di(Dd,i) _W((0b00011110011 << 21) | ((i) << 13) | (0b10000000 << 5) | (Dd)) +#define FMOV_si(Sd,i) _W((0b00011110001 << 21) | ((i) << 13) | (0b10000000 << 5) | (Sd)) +#define MOVI_di(Dd,i) _W((0b0010111100000 << 19) | ((((i) >> 5) & 0x7) << 16) | (0b111001 << 10) | (((i) & 0x1f) << 5) | (Dd)) +#define FCVT_ds(Dd,Sn) _W((0b00011110001 << 21) | (0b00010110000 << 10) | ((Sn) << 5) | (Dd)) +#define FCVT_sd(Sd,Dn) _W((0b00011110011 << 21) | (0b00010010000 << 10) | ((Dn) << 5) | (Sd)) +#define FRINTA_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00110010000 << 10) | ((Dn) << 5) | (Dd)) +#define FRINTI_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00111110000 << 10) | ((Dn) << 5) | (Dd)) +#define FRINTZ_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00101110000 << 10) | ((Dn) << 5) | (Dd)) +#define FCVTAS_wd(Wd,Dn) _W((0b00011110011 << 21) | (0b00100000000 << 10) | ((Dn) << 5) | (Wd)) +#define FCVTAS_xd(Xd,Dn) _W((0b10011110011 << 21) | (0b00100000000 << 10) | ((Dn) << 5) | (Xd)) +#define FCVTZS_xd(Xd,Dn) _W((0b10011110011 << 21) | (0b11000000000 << 10) | ((Dn) << 5) | (Xd)) +#define SCVTF_dw(Dd,Wn) _W((0b00011110011 << 21) | (0b00010000000 << 10) | ((Wn) << 5) | (Dd)) +#define SCVTF_sw(Sd,Wn) _W((0b00011110001 << 21) | (0b00010000000 << 10) | ((Wn) << 5) | (Sd)) +#define SCVTF_dx(Dd,Xn) _W((0b10011110011 << 21) | (0b00010000000 << 10) | ((Xn) << 5) | (Dd)) + +#define FABS_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00000110000 << 10) | ((Dn) << 5) | (Dd)) +#define FABS_ss(Sd,Sn) _W((0b00011110001 << 21) | (0b00000110000 << 10) | ((Sn) << 5) | (Sd)) +#define FADD_ddd(Dd,Dn,Dm) _W((0b00011110011 << 21) | ((Dm) << 16) | (0b001010 << 10) | ((Dn) << 5) | (Dd)) +#define FADD_sss(Sd,Sn,Sm) _W((0b00011110001 << 21) | ((Sm) << 16) | (0b001010 << 10) | ((Sn) << 5) | (Sd)) +#define FCMP_dd(Dn,Dm) _W((0b00011110011 << 21) | ((Dm) << 16) | (0b001000 << 10) | ((Dn) << 5) | (0b00000)) +#define FCMP_d0(Dn) _W((0b00011110011 << 21) | (0 << 16) | (0b001000 << 10) | ((Dn) << 5) | (0b01000)) +#define FCMP_ss(Sn,Sm) _W((0b00011110001 << 21) | ((Sm) << 16) | (0b001000 << 10) | ((Sn) << 5) | (0b00000)) +#define FDIV_ddd(Dd,Dn,Dm) _W((0b00011110011 << 21) | ((Dm) << 16) | (0b000110 << 10) | ((Dn) << 5) | (Dd)) +#define FDIV_sss(Sd,Sn,Sm) _W((0b00011110001 << 21) | ((Sm) << 16) | (0b000110 << 10) | ((Sn) << 5) | (Sd)) +#define FMUL_ddd(Dd,Dn,Dm) _W((0b00011110011 << 21) | ((Dm) << 16) | (0b000010 << 10) | ((Dn) << 5) | (Dd)) +#define FMUL_sss(Sd,Sn,Sm) _W((0b00011110001 << 21) | ((Sm) << 16) | (0b000010 << 10) | ((Sn) << 5) | (Sd)) +#define FMSUB_dddd(Dd,Dn,Dm,Da) _W((0b00011111010 << 21) | ((Dm) << 16) | (1 << 15) | ((Da) << 10) | ((Dn) << 5) | (Dd)) +#define FNEG_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00001010000 << 10) | ((Dn) << 5) | (Dd)) +#define FNEG_ss(Sd,Sn) _W((0b00011110001 << 21) | (0b00001010000 << 10) | ((Sn) << 5) | (Sd)) +#define FSQRT_dd(Dd,Dn) _W((0b00011110011 << 21) | (0b00001110000 << 10) | ((Dn) << 5) | (Dd)) +#define FSQRT_ss(Sd,Sn) _W((0b00011110001 << 21) | (0b00001110000 << 10) | ((Sn) << 5) | (Sd)) +#define FSUB_ddd(Dd,Dn,Dm) _W((0b00011110011 << 21) | ((Dm) << 16) | (0b001110 << 10) | ((Dn) << 5) | (Dd)) +#define FSUB_sss(Sd,Sn,Sm) _W((0b00011110001 << 21) | ((Sm) << 16) | (0b001110 << 10) | ((Sn) << 5) | (Sd)) + +#define REV64_dd(Vd,Vn) _W((0b0000111000 << 22) | (0b100000000010 << 10) | ((Vn) << 5) | (Vd)) + +#endif /* ARM_ASMA64_H */ diff --git a/src/jit/compemu.cpp b/src/jit/compemu.cpp index 69bd55ad..e7f08478 100644 --- a/src/jit/compemu.cpp +++ b/src/jit/compemu.cpp @@ -13512,7 +13512,7 @@ return 0; /* DIVL.L #.W,Dn */ uae_u32 REGPARAM2 op_4c40_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13545,7 +13545,7 @@ return 0; /* DIVL.L #.W,(An) */ uae_u32 REGPARAM2 op_4c50_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13580,7 +13580,7 @@ return 0; /* DIVL.L #.W,(An)+ */ uae_u32 REGPARAM2 op_4c58_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13616,7 +13616,7 @@ return 0; /* DIVL.L #.W,-(An) */ uae_u32 REGPARAM2 op_4c60_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13652,7 +13652,7 @@ return 0; /* DIVL.L #.W,(d16,An) */ uae_u32 REGPARAM2 op_4c68_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13688,7 +13688,7 @@ return 0; /* DIVL.L #.W,(d8,An,Xn) */ uae_u32 REGPARAM2 op_4c70_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13724,7 +13724,7 @@ return 0; /* DIVL.L #.W,(xxx).W */ uae_u32 REGPARAM2 op_4c78_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13759,7 +13759,7 @@ return 0; /* DIVL.L #.W,(xxx).L */ uae_u32 REGPARAM2 op_4c79_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13794,7 +13794,7 @@ return 0; /* DIVL.L #.W,(d16,PC) */ uae_u32 REGPARAM2 op_4c7a_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13832,7 +13832,7 @@ return 0; /* DIVL.L #.W,(d8,PC,Xn) */ uae_u32 REGPARAM2 op_4c7b_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -13871,7 +13871,7 @@ return 0; /* DIVL.L #.W,#.L */ uae_u32 REGPARAM2 op_4c7c_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -16015,7 +16015,7 @@ uae_u32 REGPARAM2 op_51c8_0_comp_ff(uae_u32 opcode) uae_u32 v2; uae_u32 v1=get_const(PC_P); v2=get_const(offs); - register_branch(v1, v2, 3); + register_branch(v1, v2, 2); if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); return 0; } @@ -18679,6 +18679,140 @@ uae_u32 REGPARAM2 op_67ff_0_comp_ff(uae_u32 opcode) return 0; } /* Bcc.W #.W */ +uae_u32 REGPARAM2 op_6800_0_comp_ff(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,(uae_s32)(uae_s16)comp_get_iword((m68k_pc_offset+=2)-2)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* BccQ.B # */ +uae_u32 REGPARAM2 op_6801_0_comp_ff(uae_u32 opcode) +{ + uae_s32 srcreg = (uae_s32)(uae_s8)(opcode & 255); + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,srcreg); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.L #.L */ +uae_u32 REGPARAM2 op_68ff_0_comp_ff(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,comp_get_ilong((m68k_pc_offset+=4)-4)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.W #.W */ +uae_u32 REGPARAM2 op_6900_0_comp_ff(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,(uae_s32)(uae_s16)comp_get_iword((m68k_pc_offset+=2)-2)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* BccQ.B # */ +uae_u32 REGPARAM2 op_6901_0_comp_ff(uae_u32 opcode) +{ + uae_s32 srcreg = (uae_s32)(uae_s8)(opcode & 255); + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,srcreg); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.L #.L */ +uae_u32 REGPARAM2 op_69ff_0_comp_ff(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,comp_get_ilong((m68k_pc_offset+=4)-4)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.W #.W */ uae_u32 REGPARAM2 op_6a00_0_comp_ff(uae_u32 opcode) { uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; @@ -19709,7 +19843,7 @@ return 0; /* DIVU.W Dn,Dn */ uae_u32 REGPARAM2 op_80c0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19731,7 +19865,7 @@ return 0; /* DIVU.W (An),Dn */ uae_u32 REGPARAM2 op_80d0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19755,7 +19889,7 @@ return 0; /* DIVU.W (An)+,Dn */ uae_u32 REGPARAM2 op_80d8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19780,7 +19914,7 @@ return 0; /* DIVU.W -(An),Dn */ uae_u32 REGPARAM2 op_80e0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19805,7 +19939,7 @@ return 0; /* DIVU.W (d16,An),Dn */ uae_u32 REGPARAM2 op_80e8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19830,7 +19964,7 @@ return 0; /* DIVU.W (d8,An,Xn),Dn */ uae_u32 REGPARAM2 op_80f0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19855,7 +19989,7 @@ return 0; /* DIVU.W (xxx).W,Dn */ uae_u32 REGPARAM2 op_80f8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19879,7 +20013,7 @@ return 0; /* DIVU.W (xxx).L,Dn */ uae_u32 REGPARAM2 op_80f9_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19903,7 +20037,7 @@ return 0; /* DIVU.W (d16,PC),Dn */ uae_u32 REGPARAM2 op_80fa_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19929,7 +20063,7 @@ return 0; /* DIVU.W (d8,PC,Xn),Dn */ uae_u32 REGPARAM2 op_80fb_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -19956,7 +20090,7 @@ return 0; /* DIVU.W #.W,Dn */ uae_u32 REGPARAM2 op_80fc_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20389,7 +20523,7 @@ return 0; /* DIVS.W Dn,Dn */ uae_u32 REGPARAM2 op_81c0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20411,7 +20545,7 @@ return 0; /* DIVS.W (An),Dn */ uae_u32 REGPARAM2 op_81d0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20435,7 +20569,7 @@ return 0; /* DIVS.W (An)+,Dn */ uae_u32 REGPARAM2 op_81d8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20460,7 +20594,7 @@ return 0; /* DIVS.W -(An),Dn */ uae_u32 REGPARAM2 op_81e0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20485,7 +20619,7 @@ return 0; /* DIVS.W (d16,An),Dn */ uae_u32 REGPARAM2 op_81e8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20510,7 +20644,7 @@ return 0; /* DIVS.W (d8,An,Xn),Dn */ uae_u32 REGPARAM2 op_81f0_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20535,7 +20669,7 @@ return 0; /* DIVS.W (xxx).W,Dn */ uae_u32 REGPARAM2 op_81f8_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20559,7 +20693,7 @@ return 0; /* DIVS.W (xxx).L,Dn */ uae_u32 REGPARAM2 op_81f9_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20583,7 +20717,7 @@ return 0; /* DIVS.W (d16,PC),Dn */ uae_u32 REGPARAM2 op_81fa_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20609,7 +20743,7 @@ return 0; /* DIVS.W (d8,PC,Xn),Dn */ uae_u32 REGPARAM2 op_81fb_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -20636,7 +20770,7 @@ return 0; /* DIVS.W #.W,Dn */ uae_u32 REGPARAM2 op_81fc_0_comp_ff(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41463,7 +41597,7 @@ return 0; /* DIVL.L #.W,Dn */ uae_u32 REGPARAM2 op_4c40_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41495,7 +41629,7 @@ return 0; /* DIVL.L #.W,(An) */ uae_u32 REGPARAM2 op_4c50_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41529,7 +41663,7 @@ return 0; /* DIVL.L #.W,(An)+ */ uae_u32 REGPARAM2 op_4c58_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41564,7 +41698,7 @@ return 0; /* DIVL.L #.W,-(An) */ uae_u32 REGPARAM2 op_4c60_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41599,7 +41733,7 @@ return 0; /* DIVL.L #.W,(d16,An) */ uae_u32 REGPARAM2 op_4c68_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41634,7 +41768,7 @@ return 0; /* DIVL.L #.W,(d8,An,Xn) */ uae_u32 REGPARAM2 op_4c70_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41669,7 +41803,7 @@ return 0; /* DIVL.L #.W,(xxx).W */ uae_u32 REGPARAM2 op_4c78_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41703,7 +41837,7 @@ return 0; /* DIVL.L #.W,(xxx).L */ uae_u32 REGPARAM2 op_4c79_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41737,7 +41871,7 @@ return 0; /* DIVL.L #.W,(d16,PC) */ uae_u32 REGPARAM2 op_4c7a_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41774,7 +41908,7 @@ return 0; /* DIVL.L #.W,(d8,PC,Xn) */ uae_u32 REGPARAM2 op_4c7b_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -41812,7 +41946,7 @@ return 0; /* DIVL.L #.W,#.L */ uae_u32 REGPARAM2 op_4c7c_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -43859,7 +43993,7 @@ uae_u32 REGPARAM2 op_51c8_0_comp_nf(uae_u32 opcode) uae_u32 v2; uae_u32 v1=get_const(PC_P); v2=get_const(offs); - register_branch(v1, v2, 3); + register_branch(v1, v2, 2); if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); return 0; } @@ -46523,6 +46657,140 @@ uae_u32 REGPARAM2 op_67ff_0_comp_nf(uae_u32 opcode) return 0; } /* Bcc.W #.W */ +uae_u32 REGPARAM2 op_6800_0_comp_nf(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,(uae_s32)(uae_s16)comp_get_iword((m68k_pc_offset+=2)-2)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* BccQ.B # */ +uae_u32 REGPARAM2 op_6801_0_comp_nf(uae_u32 opcode) +{ + uae_s32 srcreg = (uae_s32)(uae_s8)(opcode & 255); + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,srcreg); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.L #.L */ +uae_u32 REGPARAM2 op_68ff_0_comp_nf(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,comp_get_ilong((m68k_pc_offset+=4)-4)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 7); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.W #.W */ +uae_u32 REGPARAM2 op_6900_0_comp_nf(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,(uae_s32)(uae_s16)comp_get_iword((m68k_pc_offset+=2)-2)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* BccQ.B # */ +uae_u32 REGPARAM2 op_6901_0_comp_nf(uae_u32 opcode) +{ + uae_s32 srcreg = (uae_s32)(uae_s8)(opcode & 255); + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,srcreg); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.L #.L */ +uae_u32 REGPARAM2 op_69ff_0_comp_nf(uae_u32 opcode) +{ + uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; + m68k_pc_offset+=2; + uae_u8 scratchie=S1; + uae_u32 v1, v2; + int src = scratchie++; + mov_l_ri(src,comp_get_ilong((m68k_pc_offset+=4)-4)); + sub_l_ri(src, m68k_pc_offset - m68k_pc_offset_thisinst - 2); + arm_ADD_l_ri(src, (uintptr)comp_pc_p); + mov_l_ri(PC_P, (uintptr)comp_pc_p); + arm_ADD_l_ri(src, m68k_pc_offset); + arm_ADD_l_ri(PC_P, m68k_pc_offset); + m68k_pc_offset = 0; + v1 = get_const(PC_P); + v2 = get_const(src); + register_branch(v1, v2, 6); + make_flags_live(); + if (m68k_pc_offset>SYNC_PC_OFFSET) sync_m68k_pc(); +return 0; +} +/* Bcc.W #.W */ uae_u32 REGPARAM2 op_6a00_0_comp_nf(uae_u32 opcode) { uae_u32 m68k_pc_offset_thisinst=m68k_pc_offset; @@ -47519,7 +47787,7 @@ return 0; /* DIVU.W Dn,Dn */ uae_u32 REGPARAM2 op_80c0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47540,7 +47808,7 @@ return 0; /* DIVU.W (An),Dn */ uae_u32 REGPARAM2 op_80d0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47563,7 +47831,7 @@ return 0; /* DIVU.W (An)+,Dn */ uae_u32 REGPARAM2 op_80d8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47587,7 +47855,7 @@ return 0; /* DIVU.W -(An),Dn */ uae_u32 REGPARAM2 op_80e0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47611,7 +47879,7 @@ return 0; /* DIVU.W (d16,An),Dn */ uae_u32 REGPARAM2 op_80e8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47635,7 +47903,7 @@ return 0; /* DIVU.W (d8,An,Xn),Dn */ uae_u32 REGPARAM2 op_80f0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47659,7 +47927,7 @@ return 0; /* DIVU.W (xxx).W,Dn */ uae_u32 REGPARAM2 op_80f8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47682,7 +47950,7 @@ return 0; /* DIVU.W (xxx).L,Dn */ uae_u32 REGPARAM2 op_80f9_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47705,7 +47973,7 @@ return 0; /* DIVU.W (d16,PC),Dn */ uae_u32 REGPARAM2 op_80fa_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47730,7 +47998,7 @@ return 0; /* DIVU.W (d8,PC,Xn),Dn */ uae_u32 REGPARAM2 op_80fb_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -47756,7 +48024,7 @@ return 0; /* DIVU.W #.W,Dn */ uae_u32 REGPARAM2 op_80fc_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48167,7 +48435,7 @@ return 0; /* DIVS.W Dn,Dn */ uae_u32 REGPARAM2 op_81c0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48188,7 +48456,7 @@ return 0; /* DIVS.W (An),Dn */ uae_u32 REGPARAM2 op_81d0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48211,7 +48479,7 @@ return 0; /* DIVS.W (An)+,Dn */ uae_u32 REGPARAM2 op_81d8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48235,7 +48503,7 @@ return 0; /* DIVS.W -(An),Dn */ uae_u32 REGPARAM2 op_81e0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48259,7 +48527,7 @@ return 0; /* DIVS.W (d16,An),Dn */ uae_u32 REGPARAM2 op_81e8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48283,7 +48551,7 @@ return 0; /* DIVS.W (d8,An,Xn),Dn */ uae_u32 REGPARAM2 op_81f0_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48307,7 +48575,7 @@ return 0; /* DIVS.W (xxx).W,Dn */ uae_u32 REGPARAM2 op_81f8_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48330,7 +48598,7 @@ return 0; /* DIVS.W (xxx).L,Dn */ uae_u32 REGPARAM2 op_81f9_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48353,7 +48621,7 @@ return 0; /* DIVS.W (d16,PC),Dn */ uae_u32 REGPARAM2 op_81fa_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48378,7 +48646,7 @@ return 0; /* DIVS.W (d8,PC,Xn),Dn */ uae_u32 REGPARAM2 op_81fb_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else @@ -48404,7 +48672,7 @@ return 0; /* DIVS.W #.W,Dn */ uae_u32 REGPARAM2 op_81fc_0_comp_nf(uae_u32 opcode) { -#ifndef ARMV6T2 +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) FAIL(1); return 0; #else diff --git a/src/jit/compemu.h b/src/jit/compemu.h index 723bc1cd..1f7a2a25 100644 --- a/src/jit/compemu.h +++ b/src/jit/compemu.h @@ -32,17 +32,23 @@ #ifndef COMPEMU_H #define COMPEMU_H +#if defined(CPU_AARCH64) +typedef uae_u64 uintptr; +#else typedef uae_u32 uintptr; +#endif -/* Flags for Bernie during development/debugging. Should go away eventually */ -#define DISTRUST_CONSISTENT_MEM 0 /* Now that we do block chaining, and also have linked lists on each tag, TAGMASK can be much smaller and still do its job. Saves several megs of memory! */ #define TAGMASK 0x0000ffff #define TAGSIZE (TAGMASK+1) #define MAXRUN 1024 +#if defined(CPU_AARCH64) +#define cacheline(x) (((uae_u64)x)&TAGMASK) +#else #define cacheline(x) (((uae_u32)x)&TAGMASK) +#endif extern uae_u8* start_pc_p; extern uae_u32 start_pc; @@ -51,32 +57,14 @@ struct blockinfo_t; typedef struct { uae_u16* location; - uae_u8 cycles; uae_u8 specmem; } cpu_history; typedef union { - cpuop_func* handler; - struct blockinfo_t* bi; + cpuop_func* handler; + struct blockinfo_t* bi; } cacheline; -/* (gb) When on, this option can save save up to 30% compilation time - * when many lazy flushes occur (e.g. apps in MacOS 8.x). - */ -#define USE_SEPARATE_BIA 1 - -/* Use chain of checksum_info_t to compute the block checksum */ -#define USE_CHECKSUM_INFO 1 - -/* Use code inlining, aka follow-up of constant jumps */ -#define USE_INLINING 1 - -/* Inlining requires the chained checksuming information */ -#if USE_INLINING -#undef USE_CHECKSUM_INFO -#define USE_CHECKSUM_INFO 1 -#endif - #define COMP_DEBUG 0 #if COMP_DEBUG @@ -102,7 +90,6 @@ typedef union { #define MAX_HOLD_BI 3 /* One for the current block, and up to two for jump targets */ -#define INDIVIDUAL_INST 0 #if 1 // gb-- my format from readcpu.cpp is not the same #define FLAG_X 0x0010 @@ -121,22 +108,24 @@ typedef union { #define FLAG_ZNV (FLAG_Z | FLAG_N | FLAG_V) #if defined(CPU_arm) + //#define DEBUG_DATA_BUFFER -#define ALIGN_NOT_NEEDED + +#if defined(CPU_AARCH64) +#define N_REGS 18 /* really 32, but 29 to 31 are FP, LR, SP; 18 has special meaning; 27 holds memstart and 28 holds regs-struct */ +#else #define N_REGS 10 /* really 16, but 13 to 15 are SP, LR, PC; 12 is scratch reg, 10 holds memstart and 11 holds regs-struct */ +#endif + #else #define N_REGS 8 /* really only 7, but they are numbered 0,1,2,3,5,6,7 */ #endif + #define N_FREGS 16 // We use 10 regs: 6 - FP_RESULT, 7 - SCRATCH, 8-15 - Amiga regs FP0-FP7 /* Functions exposed to newcpu, or to what was moved from newcpu.c to * compemu_support.c */ extern void compiler_exit(void); -extern void init_comp(void); -extern void flush(int save_regs); -extern void small_flush(int save_regs); -extern void set_target(uae_u8* t); -extern void freescratch(void); extern void build_comp(void); extern void set_cache_state(int enabled); #ifdef JIT @@ -153,16 +142,12 @@ extern int check_for_cache_miss(void); extern void comp_fpp_opp (uae_u32 opcode, uae_u16 extra); extern void comp_fbcc_opp (uae_u32 opcode); extern void comp_fscc_opp (uae_u32 opcode, uae_u16 extra); -void comp_fdbcc_opp (uae_u32 opcode, uae_u16 extra); -void comp_ftrapcc_opp (uae_u32 opcode, uaecptr oldpc); -void comp_fsave_opp (uae_u32 opcode); -void comp_frestore_opp (uae_u32 opcode); extern uae_u32 needed_flags; extern uae_u8* comp_pc_p; extern void* pushall_call_handler; -#define VREGS 24 +#define VREGS 23 #define VFREGS 10 #define INMEM 1 @@ -177,7 +162,6 @@ typedef struct { uae_u8 status; uae_s8 realreg; /* gb-- realreg can hold -1 */ uae_u8 realind; /* The index in the holds[] array */ - uae_u8 validsize; } reg_status; typedef struct { @@ -188,10 +172,10 @@ typedef struct { } freg_status; typedef struct { - uae_u8 use_flags; - uae_u8 set_flags; - uae_u8 is_addx; - uae_u8 cflow; + uae_u8 use_flags; + uae_u8 set_flags; + uae_u8 is_addx; + uae_u8 cflow; } op_properties; extern op_properties prop[65536]; @@ -204,11 +188,11 @@ STATIC_INLINE int end_block(uae_u16 opcode) #define PC_P 16 #define FLAGX 17 #define FLAGTMP 18 +// Is S4 ever in use? #define S1 19 #define S2 20 #define S3 21 #define S4 22 -#define S5 23 #define FP_RESULT 8 #define FS1 9 @@ -233,28 +217,29 @@ typedef struct { } fn_status; /* For flag handling */ -#define NADA 1 #define TRASH 2 #define VALID 3 /* needflush values */ #define NF_SCRATCH 0 #define NF_TOMEM 1 -#define NF_HANDLER 2 typedef struct { - /* Integer part */ - reg_status state[VREGS]; - n_status nat[N_REGS]; - uae_u32 flags_on_stack; - uae_u32 flags_in_flags; - uae_u32 flags_are_important; - /* FPU part */ - freg_status fate[VFREGS]; - fn_status fat[N_FREGS]; + /* Integer part */ + reg_status state[VREGS]; + n_status nat[N_REGS]; + uae_u32 flags_on_stack; + uae_u32 flags_in_flags; + uae_u32 flags_are_important; + /* FPU part */ + freg_status fate[VFREGS]; + fn_status fat[N_FREGS]; } bigstate; -#define IMM uae_s32 +#define IM8 uae_s32 +#define IM16 uae_s32 +#define IM32 uae_s32 +#define IMPTR uintptr #define RR1 uae_u32 #define RR2 uae_u32 #define RR4 uae_u32 @@ -264,9 +249,9 @@ typedef struct { #define RW1 uae_u32 #define RW2 uae_u32 #define RW4 uae_u32 -#define MEMR uae_u32 -#define MEMW uae_u32 -#define MEMRW uae_u32 +#define MEMR uintptr +#define MEMW uintptr +#define MEMRW uintptr #define FW uae_u32 #define FR uae_u32 @@ -298,6 +283,7 @@ extern int failure; /* Convenience functions exposed to gencomp */ extern uae_u32 m68k_pc_offset; +/* address and dest are virtual register numbers */ extern void readbyte(int address, int dest); extern void readword(int address, int dest); extern void readlong(int address, int dest); @@ -336,40 +322,35 @@ typedef struct checksum_info_t { } checksum_info; typedef struct blockinfo_t { - uae_s32 count; - cpuop_func* direct_handler_to_use; - cpuop_func* handler_to_use; - /* The direct handler does not check for the correct address */ + uae_s32 count; + cpuop_func* direct_handler_to_use; + cpuop_func* handler_to_use; + /* The direct handler does not check for the correct address */ - cpuop_func* handler; - cpuop_func* direct_handler; + cpuop_func* handler; + cpuop_func* direct_handler; - cpuop_func* direct_pen; - cpuop_func* direct_pcc; + cpuop_func* direct_pen; + cpuop_func* direct_pcc; - uae_u8* nexthandler; - uae_u8* pc_p; + uae_u8* nexthandler; + uae_u8* pc_p; - uae_u32 c1; - uae_u32 c2; -#if USE_CHECKSUM_INFO - checksum_info *csi; -#else - uae_u32 len; - uae_u32 min_pcp; -#endif + uae_u32 c1; + uae_u32 c2; + checksum_info *csi; - struct blockinfo_t* next_same_cl; - struct blockinfo_t** prev_same_cl_p; - struct blockinfo_t* next; - struct blockinfo_t** prev_p; + struct blockinfo_t* next_same_cl; + struct blockinfo_t** prev_same_cl_p; + struct blockinfo_t* next; + struct blockinfo_t** prev_p; - uae_u8 optlevel; - uae_u8 needed_flags; - uae_u8 status; + uae_u8 optlevel; + uae_u8 needed_flags; + uae_u8 status; - dependency dep[2]; /* Holds things we depend on */ - dependency* deplist; /* List of things that depend on this */ + dependency dep[2]; /* Holds things we depend on */ + dependency* deplist; /* List of things that depend on this */ } blockinfo; #define BI_INVALID 0 @@ -380,7 +361,7 @@ typedef struct blockinfo_t { #define BI_COMPILING 5 #define BI_FINALIZING 6 -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) const int POPALLSPACE_SIZE = 2048; /* That should be enough space */ #else const int POPALLSPACE_SIZE = 512; /* That should be enough space */ @@ -389,14 +370,10 @@ const int POPALLSPACE_SIZE = 512; /* That should be enough space */ void execute_normal(void); void exec_nostats(void); void do_nothing(void); -void execute_exception(void); +void execute_exception(uae_u32 cycles); -/* ARAnyM uses fpu_register name, used in scratch_t */ -/* FIXME: check that no ARAnyM code assumes different floating point type */ typedef fptype fpu_register; void jit_abort(const TCHAR *format,...); -#define uae_p32(x) ((uae_u32)(x)) - #endif /* COMPEMU_H */ diff --git a/src/jit/compemu_fpp.cpp b/src/jit/compemu_fpp.cpp index 7a72adaa..fc98b8e8 100644 --- a/src/jit/compemu_fpp.cpp +++ b/src/jit/compemu_fpp.cpp @@ -8,8 +8,7 @@ * Modified 2005 Peter Keunecke */ -#include -#include +#include #include "sysdeps.h" @@ -27,179 +26,179 @@ static const int sz1[8] = { 4, 4, 12, 12, 2, 8, 1, 0 }; static const int sz2[8] = { 4, 4, 12, 12, 2, 8, 2, 0 }; /* return the required floating point precision or -1 for failure, 0=E, 1=S, 2=D */ -STATIC_INLINE int comp_fp_get(uae_u32 opcode, uae_u16 extra, int treg) +STATIC_INLINE int comp_fp_get (uae_u32 opcode, uae_u16 extra, int treg) { - const int reg = opcode & 7; - const int mode = (opcode >> 3) & 7; - const auto size = (extra >> 10) & 7; + int reg = opcode & 7; + int mode = (opcode >> 3) & 7; + int size = (extra >> 10) & 7; if (size == 3 || size == 7) /* 3 = packed decimal, 7 is not defined */ return -1; switch (mode) { - case 0: /* Dn */ - switch (size) { - case 0: /* Long */ - fmov_l_rr(treg, reg); - return 2; - case 1: /* Single */ - fmov_s_rr(treg, reg); - return 1; - case 4: /* Word */ - fmov_w_rr(treg, reg); - return 1; - case 6: /* Byte */ - fmov_b_rr(treg, reg); - return 1; - default: - return -1; - } - case 1: /* An, invalid mode */ - return -1; - case 2: /* (An) */ - mov_l_rr(S1, reg + 8); - break; - case 3: /* (An)+ */ - mov_l_rr(S1, reg + 8); - arm_ADD_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); - break; - case 4: /* -(An) */ - arm_SUB_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); - mov_l_rr(S1, reg + 8); - break; - case 5: /* (d16,An) */ - { - const uae_u32 off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_rr(S1, reg + 8); - lea_l_brr(S1, S1, off); - break; - } - case 6: /* (d8,An,Xn) or (bd,An,Xn) or ([bd,An,Xn],od) or ([bd,An],Xn,od) */ - { - const uae_u32 dp = comp_get_iword((m68k_pc_offset += 2) - 2); - calc_disp_ea_020(reg + 8, dp, S1); - break; - } - case 7: - switch (reg) { - case 0: /* (xxx).W */ + case 0: /* Dn */ + switch (size) { + case 0: /* Long */ + fmov_l_rr (treg, reg); + return 2; + case 1: /* Single */ + fmov_s_rr (treg, reg); + return 1; + case 4: /* Word */ + fmov_w_rr (treg, reg); + return 1; + case 6: /* Byte */ + fmov_b_rr (treg, reg); + return 1; + default: + return -1; + } + case 1: /* An, invalid mode */ + return -1; + case 2: /* (An) */ + mov_l_rr (S1, reg + 8); + break; + case 3: /* (An)+ */ + mov_l_rr (S1, reg + 8); + arm_ADD_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); + break; + case 4: /* -(An) */ + arm_SUB_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); + mov_l_rr (S1, reg + 8); + break; + case 5: /* (d16,An) */ { - const uae_u32 off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_ri(S1, off); + uae_u32 off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_rr (S1, reg + 8); + lea_l_brr (S1, S1, off); break; } - case 1: /* (xxx).L */ + case 6: /* (d8,An,Xn) or (bd,An,Xn) or ([bd,An,Xn],od) or ([bd,An],Xn,od) */ { - const auto off = comp_get_ilong((m68k_pc_offset += 4) - 4); - mov_l_ri(S1, off); + uae_u32 dp = comp_get_iword ((m68k_pc_offset += 2) - 2); + calc_disp_ea_020 (reg + 8, dp, S1); break; } - case 2: /* (d16,PC) */ - { - const auto address = start_pc + ((uae_char*)comp_pc_p - (uae_char*)start_pc_p) + m68k_pc_offset; - auto PC16off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_ri(S1, address + PC16off); - break; - } - case 3: /* (d8,PC,Xn) or (bd,PC,Xn) or ([bd,PC,Xn],od) or ([bd,PC],Xn,od) */ - return -1; /* rarely used, fallback to non-JIT */ - case 4: /* # < data >; Constants should be converted just once by the JIT */ - m68k_pc_offset += sz2[size]; - switch (size) { - case 0: - { - uae_s32 li = comp_get_ilong(m68k_pc_offset - 4); - auto si = float(li); - - if (li == int(si)) { - //write_log ("converted immediate LONG constant to SINGLE\n"); - fmov_s_ri(treg, *(uae_u32 *)&si); - return 1; - } - //write_log ("immediate LONG constant\n"); - fmov_l_ri(treg, *(uae_u32 *)&li); - return 2; - } - case 1: - //write_log (_T("immediate SINGLE constant\n")); - fmov_s_ri(treg, comp_get_ilong(m68k_pc_offset - 4)); - return 1; - case 2: - { - //write_log (_T("immediate LONG DOUBLE constant\n")); - uae_u32 wrd1, wrd2, wrd3; - fpdata tmp; - wrd3 = comp_get_ilong(m68k_pc_offset - 4); - wrd2 = comp_get_ilong(m68k_pc_offset - 8); - wrd1 = comp_get_iword(m68k_pc_offset - 12) << 16; - fpp_to_exten(&tmp, wrd1, wrd2, wrd3); - mov_l_ri(S1, ((uae_u32*)&tmp)[0]); - mov_l_ri(S2, ((uae_u32*)&tmp)[1]); - fmov_d_rrr(treg, S1, S2); - return 0; - } - case 4: - { - float si = float((uae_s16)comp_get_iword(m68k_pc_offset - 2)); - - //write_log (_T("converted immediate WORD constant %f to SINGLE\n"), si); - fmov_s_ri(treg, *(uae_u32 *)&si); - return 1; - } - case 5: - { - //write_log (_T("immediate DOUBLE constant\n")); - mov_l_ri(S1, comp_get_ilong(m68k_pc_offset - 4)); - mov_l_ri(S2, comp_get_ilong(m68k_pc_offset - 8)); - fmov_d_rrr(treg, S1, S2); - return 2; - } - case 6: - { - float si = float((uae_s8)comp_get_ibyte(m68k_pc_offset - 2)); - - //write_log (_T("converted immediate BYTE constant to SINGLE\n")); - fmov_s_ri(treg, *(uae_u32 *)&si); - return 1; - } - default: /* never reached */ - return -1; - } - default: /* never reached */ - return -1; - } - } - + case 7: + switch (reg) { + case 0: /* (xxx).W */ + { + uae_u32 off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_ri (S1, off); + break; + } + case 1: /* (xxx).L */ + { + uae_u32 off = comp_get_ilong ((m68k_pc_offset += 4) - 4); + mov_l_ri (S1, off); + break; + } + case 2: /* (d16,PC) */ + { + uae_u32 address = start_pc + ((uae_char*) comp_pc_p - (uae_char*) start_pc_p) + m68k_pc_offset; + uae_s32 PC16off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_ri (S1, address + PC16off); + break; + } + case 3: /* (d8,PC,Xn) or (bd,PC,Xn) or ([bd,PC,Xn],od) or ([bd,PC],Xn,od) */ + return -1; /* rarely used, fallback to non-JIT */ + case 4: /* # < data >; Constants should be converted just once by the JIT */ + m68k_pc_offset += sz2[size]; + switch (size) { + case 0: + { + uae_s32 li = comp_get_ilong(m68k_pc_offset - 4); + float si = (float)li; + + if (li == (int)si) { + //write_log ("converted immediate LONG constant to SINGLE\n"); + fmov_s_ri(treg, *(uae_u32 *)&si); + return 1; + } + //write_log ("immediate LONG constant\n"); + fmov_l_ri(treg, *(uae_u32 *)&li); + return 2; + } + case 1: + //write_log (_T("immediate SINGLE constant\n")); + fmov_s_ri(treg, comp_get_ilong(m68k_pc_offset - 4)); + return 1; + case 2: + { + //write_log (_T("immediate LONG DOUBLE constant\n")); + uae_u32 wrd1, wrd2, wrd3; + fpdata tmp; + wrd3 = comp_get_ilong(m68k_pc_offset - 4); + wrd2 = comp_get_ilong(m68k_pc_offset - 8); + wrd1 = comp_get_iword(m68k_pc_offset - 12) << 16; + fpp_to_exten(&tmp, wrd1, wrd2, wrd3); + mov_l_ri(S1, ((uae_u32*)&tmp)[0]); + mov_l_ri(S2, ((uae_u32*)&tmp)[1]); + fmov_d_rrr (treg, S1, S2); + return 0; + } + case 4: + { + float si = (float)(uae_s16)comp_get_iword(m68k_pc_offset-2); + + //write_log (_T("converted immediate WORD constant %f to SINGLE\n"), si); + fmov_s_ri(treg, *(uae_u32 *)&si); + return 1; + } + case 5: + { + //write_log (_T("immediate DOUBLE constant\n")); + mov_l_ri(S1, comp_get_ilong(m68k_pc_offset - 4)); + mov_l_ri(S2, comp_get_ilong(m68k_pc_offset - 8)); + fmov_d_rrr (treg, S1, S2); + return 2; + } + case 6: + { + float si = (float)(uae_s8)comp_get_ibyte(m68k_pc_offset - 2); + + //write_log (_T("converted immediate BYTE constant to SINGLE\n")); + fmov_s_ri(treg, *(uae_u32 *)&si); + return 1; + } + default: /* never reached */ + return -1; + } + default: /* never reached */ + return -1; + } + } + switch (size) { - case 0: /* Long */ - readlong(S1, S2); - fmov_l_rr(treg, S2); - return 2; - case 1: /* Single */ - readlong(S1, S2); - fmov_s_rr(treg, S2); - return 1; - case 2: /* Long Double */ - fp_to_exten_rm(treg, S1); - return 0; - case 4: /* Word */ - readword(S1, S2); - fmov_w_rr(treg, S2); - return 1; - case 5: /* Double */ - fp_to_double_rm(treg, S1); - return 2; - case 6: /* Byte */ - readbyte(S1, S2); - fmov_b_rr(treg, S2); - return 1; - default: - return -1; - } + case 0: /* Long */ + readlong (S1, S2); + fmov_l_rr (treg, S2); + return 2; + case 1: /* Single */ + readlong (S1, S2); + fmov_s_rr (treg, S2); + return 1; + case 2: /* Long Double */ + fp_to_exten_rm (treg, S1); + return 0; + case 4: /* Word */ + readword (S1, S2); + fmov_w_rr (treg, S2); + return 1; + case 5: /* Double */ + fp_to_double_rm (treg, S1); + return 2; + case 6: /* Byte */ + readbyte (S1, S2); + fmov_b_rr (treg, S2); + return 1; + default: + return -1; + } return -1; } /* return of -1 means failure, >=0 means OK */ -STATIC_INLINE int comp_fp_put(uae_u32 opcode, uae_u16 extra) +STATIC_INLINE int comp_fp_put (uae_u32 opcode, uae_u16 extra) { int reg = opcode & 7; int sreg = (extra >> 7) & 7; @@ -209,255 +208,253 @@ STATIC_INLINE int comp_fp_put(uae_u32 opcode, uae_u16 extra) if (size == 3 || size == 7) /* 3 = packed decimal, 7 is not defined */ return -1; switch (mode) { - case 0: /* Dn */ - switch (size) { - case 0: /* FMOVE.L FPx, Dn */ - fmov_to_l_rr(reg, sreg); - return 0; - case 1: /* FMOVE.S FPx, Dn */ - fmov_to_s_rr(reg, sreg); - return 0; - case 4: /* FMOVE.W FPx, Dn */ - fmov_to_w_rr(reg, sreg); - return 0; - case 6: /* FMOVE.B FPx, Dn */ - fmov_to_b_rr(reg, sreg); - return 0; - default: - return -1; - } - case 1: /* An, invalid mode */ - return -1; - case 2: /* (An) */ - mov_l_rr(S1, reg + 8); - break; - case 3: /* (An)+ */ - mov_l_rr(S1, reg + 8); - arm_ADD_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); - break; - case 4: /* -(An) */ - arm_SUB_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); - mov_l_rr(S1, reg + 8); - break; - case 5: /* (d16,An) */ - { - uae_u32 off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_rr(S1, reg + 8); - arm_ADD_l_ri(S1, off); - break; - } - case 6: /* (d8,An,Xn) or (bd,An,Xn) or ([bd,An,Xn],od) or ([bd,An],Xn,od) */ - { - uae_u32 dp = comp_get_iword((m68k_pc_offset += 2) - 2); - calc_disp_ea_020(reg + 8, dp, S1); - break; - } - case 7: - switch (reg) { - case 0: /* (xxx).W */ + case 0: /* Dn */ + switch (size) { + case 0: /* FMOVE.L FPx, Dn */ + fmov_to_l_rr(reg, sreg); + return 0; + case 1: /* FMOVE.S FPx, Dn */ + fmov_to_s_rr(reg, sreg); + return 0; + case 4: /* FMOVE.W FPx, Dn */ + fmov_to_w_rr(reg, sreg); + return 0; + case 6: /* FMOVE.B FPx, Dn */ + fmov_to_b_rr(reg, sreg); + return 0; + default: + return -1; + } + case 1: /* An, invalid mode */ + return -1; + case 2: /* (An) */ + mov_l_rr (S1, reg + 8); + break; + case 3: /* (An)+ */ + mov_l_rr (S1, reg + 8); + arm_ADD_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); + break; + case 4: /* -(An) */ + arm_SUB_l_ri8(reg + 8, (reg == 7 ? sz2[size] : sz1[size])); + mov_l_rr (S1, reg + 8); + break; + case 5: /* (d16,An) */ { - const uae_u32 off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_ri(S1, off); + uae_u32 off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_rr (S1, reg + 8); + arm_ADD_l_ri (S1, off); break; } - case 1: /* (xxx).L */ + case 6: /* (d8,An,Xn) or (bd,An,Xn) or ([bd,An,Xn],od) or ([bd,An],Xn,od) */ { - const auto off = comp_get_ilong((m68k_pc_offset += 4) - 4); - mov_l_ri(S1, off); + uae_u32 dp = comp_get_iword ((m68k_pc_offset += 2) - 2); + calc_disp_ea_020 (reg + 8, dp, S1); break; } - default: /* All other modes are not allowed for FPx to */ - write_log(_T("JIT FMOVE FPx, Mode is not allowed %04x %04x\n"), opcode, extra); - return -1; - } - } + case 7: + switch (reg) { + case 0: /* (xxx).W */ + { + uae_u32 off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_ri (S1, off); + break; + } + case 1: /* (xxx).L */ + { + uae_u32 off = comp_get_ilong ((m68k_pc_offset += 4) - 4); + mov_l_ri (S1, off); + break; + } + default: /* All other modes are not allowed for FPx to */ + write_log (_T ("JIT FMOVE FPx, Mode is not allowed %04x %04x\n"), opcode, extra); + return -1; + } + } switch (size) { - case 0: /* Long */ - fmov_to_l_rr(S2, sreg); - writelong_clobber(S1, S2); - return 0; - case 1: /* Single */ - fmov_to_s_rr(S2, sreg); - writelong_clobber(S1, S2); - return 0; - case 2:/* Long Double */ - fp_from_exten_mr(S1, sreg); - return 0; - case 4: /* Word */ - fmov_to_w_rr(S2, sreg); - writeword_clobber(S1, S2); - return 0; - case 5: /* Double */ - fp_from_double_mr(S1, sreg); - return 0; - case 6: /* Byte */ - fmov_to_b_rr(S2, sreg); - writebyte(S1, S2); - return 0; - default: - return -1; - } + case 0: /* Long */ + fmov_to_l_rr(S2, sreg); + writelong_clobber (S1, S2); + return 0; + case 1: /* Single */ + fmov_to_s_rr(S2, sreg); + writelong_clobber (S1, S2); + return 0; + case 2:/* Long Double */ + fp_from_exten_mr (S1, sreg); + return 0; + case 4: /* Word */ + fmov_to_w_rr(S2, sreg); + writeword_clobber (S1, S2); + return 0; + case 5: /* Double */ + fp_from_double_mr(S1, sreg); + return 0; + case 6: /* Byte */ + fmov_to_b_rr(S2, sreg); + writebyte (S1, S2); + return 0; + default: + return -1; + } return -1; } /* return -1 for failure, or register number for success */ -STATIC_INLINE int comp_fp_adr(uae_u32 opcode) +STATIC_INLINE int comp_fp_adr (uae_u32 opcode) { uae_s32 off; int mode = (opcode >> 3) & 7; int reg = opcode & 7; switch (mode) { - case 2: - case 3: - case 4: - mov_l_rr(S1, 8 + reg); - return S1; - case 5: - off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_rr(S1, 8 + reg); - arm_ADD_l_ri(S1, off); - return S1; - case 7: - switch (reg) { - case 0: - off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); - mov_l_ri(S1, off); - return S1; - case 1: - off = comp_get_ilong((m68k_pc_offset += 4) - 4); - mov_l_ri(S1, off); - return S1; - } - default: - return -1; + case 2: + case 3: + case 4: + mov_l_rr (S1, 8 + reg); + return S1; + case 5: + off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_rr (S1, 8 + reg); + arm_ADD_l_ri (S1, off); + return S1; + case 7: + switch (reg) { + case 0: + off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); + mov_l_ri (S1, off); + return S1; + case 1: + off = comp_get_ilong ((m68k_pc_offset += 4) - 4); + mov_l_ri (S1, off); + return S1; + } + default: + return -1; } } -void comp_fdbcc_opp(uae_u32 opcode, uae_u16 extra) +void comp_fscc_opp (uae_u32 opcode, uae_u16 extra) { - FAIL(1); - return; -} + int reg; -void comp_fscc_opp(uae_u32 opcode, uae_u16 extra) -{ if (!currprefs.compfpu) { - FAIL(1); + FAIL (1); return; } if (extra & 0x20) { /* only cc from 00 to 1f are defined */ - FAIL(1); - return; + FAIL (1); + return; } if ((opcode & 0x38) != 0) { /* We can only do to integer register */ - FAIL(1); + FAIL (1); return; } - fflags_into_flags(); - const int reg = (opcode & 7); + fflags_into_flags (); + reg = (opcode & 7); if (!(opcode & 0x38)) { - switch (extra & 0x0f) { /* according to fpp.c, the 0x10 bit is ignored */ - case 0: fp_fscc_ri(reg, NATIVE_CC_F_NEVER); break; - case 1: fp_fscc_ri(reg, NATIVE_CC_EQ); break; - case 2: fp_fscc_ri(reg, NATIVE_CC_F_OGT); break; - case 3: fp_fscc_ri(reg, NATIVE_CC_F_OGE); break; - case 4: fp_fscc_ri(reg, NATIVE_CC_F_OLT); break; - case 5: fp_fscc_ri(reg, NATIVE_CC_F_OLE); break; - case 6: fp_fscc_ri(reg, NATIVE_CC_F_OGL); break; - case 7: fp_fscc_ri(reg, NATIVE_CC_F_OR); break; - case 8: fp_fscc_ri(reg, NATIVE_CC_F_UN); break; - case 9: fp_fscc_ri(reg, NATIVE_CC_F_UEQ); break; - case 10: fp_fscc_ri(reg, NATIVE_CC_F_UGT); break; - case 11: fp_fscc_ri(reg, NATIVE_CC_F_UGE); break; - case 12: fp_fscc_ri(reg, NATIVE_CC_F_ULT); break; - case 13: fp_fscc_ri(reg, NATIVE_CC_F_ULE); break; - case 14: fp_fscc_ri(reg, NATIVE_CC_NE); break; - case 15: fp_fscc_ri(reg, NATIVE_CC_AL); break; - } - } + switch (extra & 0x0f) { /* according to fpp.c, the 0x10 bit is ignored */ + case 0: fp_fscc_ri(reg, NATIVE_CC_F_NEVER); break; + case 1: fp_fscc_ri(reg, NATIVE_CC_EQ); break; + case 2: fp_fscc_ri(reg, NATIVE_CC_F_OGT); break; + case 3: fp_fscc_ri(reg, NATIVE_CC_F_OGE); break; + case 4: fp_fscc_ri(reg, NATIVE_CC_F_OLT); break; + case 5: fp_fscc_ri(reg, NATIVE_CC_F_OLE); break; + case 6: fp_fscc_ri(reg, NATIVE_CC_F_OGL); break; + case 7: fp_fscc_ri(reg, NATIVE_CC_F_OR); break; + case 8: fp_fscc_ri(reg, NATIVE_CC_F_UN); break; + case 9: fp_fscc_ri(reg, NATIVE_CC_F_UEQ); break; + case 10: fp_fscc_ri(reg, NATIVE_CC_F_UGT); break; + case 11: fp_fscc_ri(reg, NATIVE_CC_F_UGE); break; + case 12: fp_fscc_ri(reg, NATIVE_CC_F_ULT); break; + case 13: fp_fscc_ri(reg, NATIVE_CC_F_ULE); break; + case 14: fp_fscc_ri(reg, NATIVE_CC_NE); break; + case 15: fp_fscc_ri(reg, NATIVE_CC_AL); break; + } + } } -void comp_fbcc_opp(uae_u32 opcode) +void comp_fbcc_opp (uae_u32 opcode) { - const auto start_68k_offset = m68k_pc_offset; - uae_u32 off; + uae_u32 start_68k_offset = m68k_pc_offset; + uae_u32 off, v1, v2; + int cc; if (!currprefs.compfpu) { - FAIL(1); + FAIL (1); return; } if (opcode & 0x20) { /* only cc from 00 to 1f are defined */ - FAIL(1); + FAIL (1); return; } if (!(opcode & 0x40)) { - off = uae_s32((uae_s16)comp_get_iword((m68k_pc_offset += 2) - 2)); + off = (uae_s32) (uae_s16) comp_get_iword ((m68k_pc_offset += 2) - 2); } else { - off = comp_get_ilong((m68k_pc_offset += 4) - 4); + off = comp_get_ilong ((m68k_pc_offset += 4) - 4); } /* according to fpp.c, the 0x10 bit is ignored (it handles exception handling, which we don't do, anyway ;-) */ - const int cc = opcode & 0x0f; - if (cc == 0) - return; /* jump never */ + cc = opcode & 0x0f; + if(cc == 0) + return; /* jump never */ - /* Note, "off" will sometimes be (unsigned) "negative", so the following - * uintptr can be > 0xffffffff, but the result will be correct due to - * wraparound when truncated to 32 bit in the call to mov_l_ri. */ - mov_l_ri(S1, uintptr(comp_pc_p + off - (m68k_pc_offset - start_68k_offset))); - mov_l_ri(PC_P, uintptr(comp_pc_p)); + /* Note, "off" will sometimes be (unsigned) "negative", so the following + * uintptr can be > 0xffffffff, but the result will be correct due to + * wraparound when truncated to 32 bit in the call to mov_l_ri. */ + mov_l_ri(S1, (uintptr) + (comp_pc_p + off - (m68k_pc_offset - start_68k_offset))); + mov_l_ri(PC_P, (uintptr) comp_pc_p); /* Now they are both constant. Might as well fold in m68k_pc_offset */ - arm_ADD_l_ri(S1, m68k_pc_offset); - arm_ADD_l_ri(PC_P, m68k_pc_offset); + arm_ADD_l_ri (S1, m68k_pc_offset); + arm_ADD_l_ri (PC_P, m68k_pc_offset); m68k_pc_offset = 0; - const auto v1 = get_const(PC_P); - const auto v2 = get_const(S1); - fflags_into_flags(); + v1 = get_const (PC_P); + v2 = get_const (S1); + fflags_into_flags (); switch (cc) { - case 1: register_branch(v1, v2, NATIVE_CC_EQ); break; - case 2: register_branch(v1, v2, NATIVE_CC_F_OGT); break; - case 3: register_branch(v1, v2, NATIVE_CC_F_OGE); break; - case 4: register_branch(v1, v2, NATIVE_CC_F_OLT); break; - case 5: register_branch(v1, v2, NATIVE_CC_F_OLE); break; - case 6: register_branch(v1, v2, NATIVE_CC_F_OGL); break; - case 7: register_branch(v1, v2, NATIVE_CC_F_OR); break; - case 8: register_branch(v1, v2, NATIVE_CC_F_UN); break; - case 9: register_branch(v1, v2, NATIVE_CC_F_UEQ); break; - case 10: register_branch(v1, v2, NATIVE_CC_F_UGT); break; - case 11: register_branch(v1, v2, NATIVE_CC_F_UGE); break; - case 12: register_branch(v1, v2, NATIVE_CC_F_ULT); break; - case 13: register_branch(v1, v2, NATIVE_CC_F_ULE); break; - case 14: register_branch(v1, v2, NATIVE_CC_NE); break; - case 15: register_branch(v2, v2, NATIVE_CC_AL); break; + case 1: register_branch (v1, v2, NATIVE_CC_EQ); break; + case 2: register_branch (v1, v2, NATIVE_CC_F_OGT); break; + case 3: register_branch (v1, v2, NATIVE_CC_F_OGE); break; + case 4: register_branch (v1, v2, NATIVE_CC_F_OLT); break; + case 5: register_branch (v1, v2, NATIVE_CC_F_OLE); break; + case 6: register_branch (v1, v2, NATIVE_CC_F_OGL); break; + case 7: register_branch (v1, v2, NATIVE_CC_F_OR); break; + case 8: register_branch (v1, v2, NATIVE_CC_F_UN); break; + case 9: register_branch (v1, v2, NATIVE_CC_F_UEQ); break; + case 10: register_branch (v1, v2, NATIVE_CC_F_UGT); break; + case 11: register_branch (v1, v2, NATIVE_CC_F_UGE); break; + case 12: register_branch (v1, v2, NATIVE_CC_F_ULT); break; + case 13: register_branch (v1, v2, NATIVE_CC_F_ULE); break; + case 14: register_branch (v1, v2, NATIVE_CC_NE); break; + case 15: register_branch (v2, v2, NATIVE_CC_AL); break; } } -static uae_u32 dhex_pi[] = { 0x54442D18, 0x400921FB }; -static uae_u32 dhex_exp_1[] = { 0x8B145769, 0x4005BF0A }; -static uae_u32 dhex_l2_e[] = { 0x652B82FE, 0x3FF71547 }; -static uae_u32 dhex_ln_2[] = { 0xFEFA39EF, 0x3FE62E42 }; -static uae_u32 dhex_ln_10[] = { 0xBBB55516, 0x40026BB1 }; -static uae_u32 dhex_l10_2[] = { 0x509F79FF, 0x3FD34413 }; -static uae_u32 dhex_l10_e[] = { 0x1526E50E, 0x3FDBCB7B }; -static uae_u32 dhex_1e16[] = { 0x37E08000, 0x4341C379 }; -static uae_u32 dhex_1e32[] = { 0xB5056E17, 0x4693B8B5 }; -static uae_u32 dhex_1e64[] = { 0xE93FF9F5, 0x4D384F03 }; -static uae_u32 dhex_1e128[] = { 0xF9301D32, 0x5A827748 }; -static uae_u32 dhex_1e256[] = { 0x7F73BF3C, 0x75154FDD }; +static uae_u32 dhex_pi[] ={0x54442D18, 0x400921FB}; +static uae_u32 dhex_exp_1[] ={0x8B145769, 0x4005BF0A}; +static uae_u32 dhex_l2_e[] ={0x652B82FE, 0x3FF71547}; +static uae_u32 dhex_ln_2[] ={0xFEFA39EF, 0x3FE62E42}; +static uae_u32 dhex_ln_10[] ={0xBBB55516, 0x40026BB1}; +static uae_u32 dhex_l10_2[] ={0x509F79FF, 0x3FD34413}; +static uae_u32 dhex_l10_e[] ={0x1526E50E, 0x3FDBCB7B}; +static uae_u32 dhex_1e16[] ={0x37E08000, 0x4341C379}; +static uae_u32 dhex_1e32[] ={0xB5056E17, 0x4693B8B5}; +static uae_u32 dhex_1e64[] ={0xE93FF9F5, 0x4D384F03}; +static uae_u32 dhex_1e128[] ={0xF9301D32, 0x5A827748}; +static uae_u32 dhex_1e256[] ={0x7F73BF3C, 0x75154FDD}; static double fp_1e8; -void comp_fpp_opp(uae_u32 opcode, uae_u16 extra) +void comp_fpp_opp (uae_u32 opcode, uae_u16 extra) { int reg; int sreg, prec = 0; @@ -465,493 +462,492 @@ void comp_fpp_opp(uae_u32 opcode, uae_u16 extra) int source = (extra >> 13) & 7; int opmode = extra & 0x7f; - if (special_mem) { - FAIL(1); - return; - } + if (special_mem) { + FAIL(1); + return; + } if (!currprefs.compfpu) { - FAIL(1); + FAIL (1); return; } switch (source) { - case 3: /* FMOVE FPx, */ - if (comp_fp_put(opcode, extra) < 0) - FAIL(1); - return; - case 4: /* FMOVE.L , ControlReg */ - if (!(opcode & 0x30)) { /* Dn or An */ - if (extra & 0x1000) { /* FPCR */ - mov_l_mr(uae_p32(®s.fpcr), opcode & 15); - return; - } - if (extra & 0x0800) { /* FPSR */ - FAIL(1); - return; - // set_fpsr(m68k_dreg (regs, opcode & 15)); - } - if (extra & 0x0400) { /* FPIAR */ - mov_l_mr(uae_p32(®s.fpiar), opcode & 15); return; - } - } - else if ((opcode & 0x3f) == 0x3c) { - if (extra & 0x1000) { /* FPCR */ - uae_u32 val = comp_get_ilong((m68k_pc_offset += 4) - 4); - mov_l_mi(uae_p32(®s.fpcr), val); - switch (val & 0x30) { - case 0x00: - // round to nearest - roundingmode(0x00000000); - break; - case 0x10: - // round toward minus infinity - roundingmode(0x00800000); - break; - case 0x01: - // round toward plus infinity - roundingmode(0x00400000); - break; - case 0x11: - default: - // round towards zero - roundingmode(0x00c00000); - break; - } - return; - } - if (extra & 0x0800) { /* FPSR */ - FAIL(1); - return; - } - if (extra & 0x0400) { /* FPIAR */ - uae_u32 val = comp_get_ilong((m68k_pc_offset += 4) - 4); - mov_l_mi(uae_p32(®s.fpiar), val); - return; - } - } - FAIL(1); - return; - case 5: /* FMOVE.L ControlReg, */ - if (!(opcode & 0x30)) { /* Dn or An */ - if (extra & 0x1000) { /* FPCR */ - mov_l_rm(opcode & 15, uae_p32(®s.fpcr)); return; - } - if (extra & 0x0800) { /* FPSR */ - FAIL(1); - return; - } - if (extra & 0x0400) { /* FPIAR */ - mov_l_rm(opcode & 15, uae_p32(®s.fpiar)); return; - } - } - FAIL(1); - return; - case 6: - case 7: - { - uae_u32 list = 0; - auto incr = 0; - if (extra & 0x2000) { - /* FMOVEM FPP->memory */ - switch ((extra >> 11) & 3) { /* Get out early if failure */ - case 0: - case 2: - break; - case 1: - case 3: - default: - FAIL(1); - return; - } - auto ad = comp_fp_adr(opcode); - if (ad < 0) { - m68k_setpc(m68k_getpc() - 4); - op_illg(opcode); - return; - } - switch ((extra >> 11) & 3) { - case 0: /* static pred */ - list = extra & 0xff; - incr = -1; - break; - case 2: /* static postinc */ - list = extra & 0xff; - incr = 1; - break; - case 1: /* dynamic pred */ - case 3: /* dynamic postinc */ - abort(); - } - if (incr < 0) { /* Predecrement */ - for (reg = 7; reg >= 0; reg--) { - if (list & 0x80) { - sub_l_ri(ad, 12); - fp_from_exten_mr(ad, reg); - } - list <<= 1; - } - } - else { /* Postincrement */ - for (reg = 0; reg <= 7; reg++) { - if (list & 0x80) { - fp_from_exten_mr(ad, reg); - arm_ADD_l_ri(ad, 12); - } - list <<= 1; - } - } - if ((opcode & 0x38) == 0x18) - mov_l_rr((opcode & 7) + 8, ad); - if ((opcode & 0x38) == 0x20) - mov_l_rr((opcode & 7) + 8, ad); - } - else { - /* FMOVEM memory->FPP */ + case 3: /* FMOVE FPx, */ + if (comp_fp_put (opcode, extra) < 0) + FAIL (1); + return; + case 4: /* FMOVE.L , ControlReg */ + if (!(opcode & 0x30)) { /* Dn or An */ + if (extra & 0x1000) { /* FPCR */ + mov_l_mr ((uintptr)®s.fpcr, opcode & 15); + return; + } + if (extra & 0x0800) { /* FPSR */ + FAIL (1); + return; + // set_fpsr(m68k_dreg (regs, opcode & 15)); + } + if (extra & 0x0400) { /* FPIAR */ + mov_l_mr ((uintptr)®s.fpiar, opcode & 15); + return; + } + } + else if ((opcode & 0x3f) == 0x3c) { + if (extra & 0x1000) { /* FPCR */ + uae_u32 val = comp_get_ilong ((m68k_pc_offset += 4) - 4); + mov_l_mi ((uintptr)®s.fpcr, val); + switch(val & 0x30) { + case 0x00: + // round to nearest + roundingmode(0x00000000); + break; + case 0x10: + // round toward minus infinity + roundingmode(0x00800000); + break; + case 0x01: + // round toward plus infinity + roundingmode(0x00400000); + break; + case 0x11: + default: + // round towards zero + roundingmode(0x00c00000); + break; + } + return; + } + if (extra & 0x0800) { /* FPSR */ + FAIL (1); + return; + } + if (extra & 0x0400) { /* FPIAR */ + uae_u32 val = comp_get_ilong ((m68k_pc_offset += 4) - 4); + mov_l_mi ((uintptr)®s.fpiar, val); + return; + } + } + FAIL (1); + return; + case 5: /* FMOVE.L ControlReg, */ + if (!(opcode & 0x30)) { /* Dn or An */ + if (extra & 0x1000) { /* FPCR */ + mov_l_rm (opcode & 15, (uintptr)®s.fpcr); return; + } + if (extra & 0x0800) { /* FPSR */ + FAIL (1); + return; + } + if (extra & 0x0400) { /* FPIAR */ + mov_l_rm (opcode & 15, (uintptr)®s.fpiar); return; + } + } + FAIL (1); + return; + case 6: + case 7: + { + uae_u32 list = 0; + int incr = 0; + if (extra & 0x2000) { + int ad; - int ad; - switch ((extra >> 11) & 3) { /* Get out early if failure */ - case 0: - case 2: - break; - case 1: - case 3: - default: - FAIL(1); - return; - } - ad = comp_fp_adr(opcode); - if (ad < 0) { - m68k_setpc(m68k_getpc() - 4); - op_illg(opcode); - return; - } - switch ((extra >> 11) & 3) { - case 0: /* static pred */ - list = extra & 0xff; - incr = -1; - break; - case 2: /* static postinc */ - list = extra & 0xff; - incr = 1; - break; - case 1: /* dynamic pred */ - case 3: /* dynamic postinc */ - abort(); - } + /* FMOVEM FPP->memory */ + switch ((extra >> 11) & 3) { /* Get out early if failure */ + case 0: + case 2: + break; + case 1: + case 3: + default: + FAIL (1); + return; + } + ad = comp_fp_adr (opcode); + if (ad < 0) { + m68k_setpc (m68k_getpc () - 4); + op_illg (opcode); + return; + } + switch ((extra >> 11) & 3) { + case 0: /* static pred */ + list = extra & 0xff; + incr = -1; + break; + case 2: /* static postinc */ + list = extra & 0xff; + incr = 1; + break; + case 1: /* dynamic pred */ + case 3: /* dynamic postinc */ + abort (); + } + if (incr < 0) { /* Predecrement */ + for (reg = 7; reg >= 0; reg--) { + if (list & 0x80) { + sub_l_ri (ad, 12); + fp_from_exten_mr (ad, reg); + } + list <<= 1; + } + } else { /* Postincrement */ + for (reg = 0; reg <= 7; reg++) { + if (list & 0x80) { + fp_from_exten_mr (ad, reg); + arm_ADD_l_ri (ad, 12); + } + list <<= 1; + } + } + if ((opcode & 0x38) == 0x18) + mov_l_rr ((opcode & 7) + 8, ad); + if ((opcode & 0x38) == 0x20) + mov_l_rr ((opcode & 7) + 8, ad); + } else { + /* FMOVEM memory->FPP */ + int ad; + switch ((extra >> 11) & 3) { /* Get out early if failure */ + case 0: + case 2: + break; + case 1: + case 3: + default: + FAIL (1); + return; + } + ad = comp_fp_adr (opcode); + if (ad < 0) { + m68k_setpc (m68k_getpc () - 4); + op_illg (opcode); + return; + } + switch ((extra >> 11) & 3) { + case 0: /* static pred */ + list = extra & 0xff; + incr = -1; + break; + case 2: /* static postinc */ + list = extra & 0xff; + incr = 1; + break; + case 1: /* dynamic pred */ + case 3: /* dynamic postinc */ + abort (); + } - if (incr < 0) { - // not reached - for (reg = 7; reg >= 0; reg--) { - if (list & 0x80) { - sub_l_ri(ad, 12); - fp_to_exten_rm(reg, ad); + if (incr < 0) { + // not reached + for (reg = 7; reg >= 0; reg--) { + if (list & 0x80) { + sub_l_ri (ad, 12); + fp_to_exten_rm(reg, ad); + } + list <<= 1; } - list <<= 1; - } - } - else { - for (reg = 0; reg <= 7; reg++) { - if (list & 0x80) { - fp_to_exten_rm(reg, ad); - arm_ADD_l_ri(ad, 12); + } else { + for (reg = 0; reg <= 7; reg++) { + if (list & 0x80) { + fp_to_exten_rm(reg, ad); + arm_ADD_l_ri (ad, 12); + } + list <<= 1; } - list <<= 1; } + if ((opcode & 0x38) == 0x18) + mov_l_rr ((opcode & 7) + 8, ad); + if ((opcode & 0x38) == 0x20) + mov_l_rr ((opcode & 7) + 8, ad); } - if ((opcode & 0x38) == 0x18) - mov_l_rr((opcode & 7) + 8, ad); - if ((opcode & 0x38) == 0x20) - mov_l_rr((opcode & 7) + 8, ad); } - } - return; - case 2: /* from to FPx */ - dont_care_fflags(); - if ((extra & 0xfc00) == 0x5c00) { /* FMOVECR */ - //write_log (_T("JIT FMOVECR %x\n"), opmode); - switch (opmode) { - case 0x00: - fmov_d_rm(dreg, uae_p32(&dhex_pi)); - break; - case 0x0b: - fmov_d_rm(dreg, uae_p32(&dhex_l10_2)); - break; - case 0x0c: - fmov_d_rm(dreg, uae_p32(&dhex_exp_1)); - break; - case 0x0d: - fmov_d_rm(dreg, uae_p32(&dhex_l2_e)); - break; - case 0x0e: - fmov_d_rm(dreg, uae_p32(&dhex_l10_e)); - break; - case 0x0f: - fmov_d_ri_0(dreg); - break; - case 0x30: - fmov_d_rm(dreg, uae_p32(&dhex_ln_2)); - break; - case 0x31: - fmov_d_rm(dreg, uae_p32(&dhex_ln_10)); - break; - case 0x32: - fmov_d_ri_1(dreg); - break; - case 0x33: - fmov_d_ri_10(dreg); - break; - case 0x34: - fmov_d_ri_100(dreg); - break; - case 0x35: - fmov_l_ri(dreg, 10000); - break; - case 0x36: - fmov_rm(dreg, uae_p32(&fp_1e8)); - break; - case 0x37: - fmov_d_rm(dreg, uae_p32(&dhex_1e16)); - break; - case 0x38: - fmov_d_rm(dreg, uae_p32(&dhex_1e32)); - break; - case 0x39: - fmov_d_rm(dreg, uae_p32(&dhex_1e64)); - break; - case 0x3a: - fmov_d_rm(dreg, uae_p32(&dhex_1e128)); - break; - case 0x3b: - fmov_d_rm(dreg, uae_p32(&dhex_1e256)); - break; - default: - FAIL(1); - return; - } - fmov_rr(FP_RESULT, dreg); - return; - } - if (opmode & 0x20) /* two operands, so we need a scratch reg */ - sreg = FS1; - else /* one operand only, thus we can load the argument into dreg */ - sreg = dreg; - if (opmode >= 0x30 && opmode <= 0x37) { - // get out early for unsupported ops - FAIL(1); - return; - } - if ((prec = comp_fp_get(opcode, extra, sreg)) < 0) { - FAIL(1); - return; - } - if (!opmode) { /* FMOVE ,FPx */ - fmov_rr(FP_RESULT, dreg); - return; - } - /* no break here for to dreg */ - case 0: /* directly from sreg to dreg */ - if (!source) { /* no */ - dont_care_fflags(); - sreg = (extra >> 10) & 7; - } - switch (opmode) { - case 0x00: /* FMOVE */ - fmov_rr(dreg, sreg); - break; - case 0x01: /* FINT */ - frndint_rr(dreg, sreg); - break; - case 0x02: /* FSINH */ - ffunc_rr(sinh, dreg, sreg); - break; - case 0x03: /* FINTRZ */ - frndintz_rr(dreg, sreg); - break; - case 0x04: /* FSQRT */ - fsqrt_rr(dreg, sreg); - break; - case 0x06: /* FLOGNP1 */ - ffunc_rr(log1p, dreg, sreg); - break; - case 0x08: /* FETOXM1 */ - ffunc_rr(expm1, dreg, sreg); - break; - case 0x09: /* FTANH */ - ffunc_rr(tanh, dreg, sreg); - break; - case 0x0a: /* FATAN */ - ffunc_rr(atan, dreg, sreg); - break; - case 0x0c: /* FASIN */ - ffunc_rr(asin, dreg, sreg); - break; - case 0x0d: /* FATANH */ - ffunc_rr(atanh, dreg, sreg); - break; - case 0x0e: /* FSIN */ - ffunc_rr(sin, dreg, sreg); - break; - case 0x0f: /* FTAN */ - ffunc_rr(tan, dreg, sreg); - break; - case 0x10: /* FETOX */ - ffunc_rr(exp, dreg, sreg); - break; - case 0x11: /* FTWOTOX */ - fpowx_rr(2, dreg, sreg); - break; - case 0x12: /* FTENTOX */ - fpowx_rr(10, dreg, sreg); - break; - case 0x14: /* FLOGN */ - ffunc_rr(log, dreg, sreg); - break; - case 0x15: /* FLOG10 */ - ffunc_rr(log10, dreg, sreg); - break; - case 0x16: /* FLOG2 */ - ffunc_rr(log2, dreg, sreg); - break; - case 0x18: /* FABS */ - fabs_rr(dreg, sreg); - break; - case 0x19: /* FCOSH */ - ffunc_rr(cosh, dreg, sreg); - break; - case 0x1a: /* FNEG */ - fneg_rr(dreg, sreg); - break; - case 0x1c: /* FACOS */ - ffunc_rr(acos, dreg, sreg); - break; - case 0x1d: /* FCOS */ - ffunc_rr(cos, dreg, sreg); - break; - case 0x20: /* FDIV */ - fdiv_rr(dreg, sreg); - break; - case 0x21: /* FMOD */ - fmod_rr(dreg, sreg); - break; - case 0x22: /* FADD */ - fadd_rr(dreg, sreg); - break; - case 0x23: /* FMUL */ - fmul_rr(dreg, sreg); - break; - case 0x24: /* FSGLDIV */ - fsgldiv_rr(dreg, sreg); - break; - case 0x60: /* FSDIV */ - fdiv_rr(dreg, sreg); - if (!currprefs.fpu_strict) /* faster, but less strict rounding */ - break; - fcuts_r(dreg); - break; - case 0x25: /* FREM */ - frem1_rr(dreg, sreg); - break; - case 0x27: /* FSGLMUL */ - fsglmul_rr(dreg, sreg); - break; - case 0x63: /* FSMUL */ - fmul_rr(dreg, sreg); - if (!currprefs.fpu_strict) /* faster, but less strict rounding */ - break; - fcuts_r(dreg); - break; - case 0x28: /* FSUB */ - fsub_rr(dreg, sreg); - break; - case 0x30: /* FSINCOS */ - case 0x31: - case 0x32: - case 0x33: - case 0x34: - case 0x35: - case 0x36: - case 0x37: - FAIL(1); - return; - case 0x38: /* FCMP */ - fmov_rr(FP_RESULT, dreg); - fsub_rr(FP_RESULT, sreg); - return; - case 0x3a: /* FTST */ - fmov_rr(FP_RESULT, sreg); - return; - case 0x40: /* FSMOVE */ - if (prec == 1 || !currprefs.fpu_strict) { - if (sreg != dreg) /* no */ - fmov_rr(dreg, sreg); - } - else { - fmovs_rr(dreg, sreg); - } - break; - case 0x44: /* FDMOVE */ - if (sreg != dreg) /* no */ - fmov_rr(dreg, sreg); - break; - case 0x41: /* FSSQRT */ - fsqrt_rr(dreg, sreg); - if (!currprefs.fpu_strict) /* faster, but less strict rounding */ - break; - fcuts_r(dreg); - break; - case 0x45: /* FDSQRT */ - fsqrt_rr(dreg, sreg); - break; - case 0x58: /* FSABS */ - fabs_rr(dreg, sreg); - if (prec != 1 && currprefs.fpu_strict) - fcuts_r(dreg); - break; - case 0x5a: /* FSNEG */ - fneg_rr(dreg, sreg); - if (prec != 1 && currprefs.fpu_strict) - fcuts_r(dreg); - break; - case 0x5c: /* FDABS */ - fabs_rr(dreg, sreg); - break; - case 0x5e: /* FDNEG */ - fneg_rr(dreg, sreg); - break; - case 0x62: /* FSADD */ - fadd_rr(dreg, sreg); - if (!currprefs.fpu_strict) /* faster, but less strict rounding */ - break; - fcuts_r(dreg); - break; - case 0x64: /* FDDIV */ - fdiv_rr(dreg, sreg); - break; - case 0x66: /* FDADD */ - fadd_rr(dreg, sreg); - break; - case 0x67: /* FDMUL */ - fmul_rr(dreg, sreg); - break; - case 0x68: /* FSSUB */ - fsub_rr(dreg, sreg); - if (!currprefs.fpu_strict) /* faster, but less strict rounding */ - break; - fcuts_r(dreg); - break; - case 0x6c: /* FDSUB */ - fsub_rr(dreg, sreg); - break; + return; + case 2: /* from to FPx */ + dont_care_fflags (); + if ((extra & 0xfc00) == 0x5c00) { /* FMOVECR */ + //write_log (_T("JIT FMOVECR %x\n"), opmode); + switch (opmode) { + case 0x00: + fmov_d_rm (dreg, (uintptr)&dhex_pi); + break; + case 0x0b: + fmov_d_rm (dreg, (uintptr)&dhex_l10_2); + break; + case 0x0c: + fmov_d_rm (dreg, (uintptr)&dhex_exp_1); + break; + case 0x0d: + fmov_d_rm (dreg, (uintptr)&dhex_l2_e); + break; + case 0x0e: + fmov_d_rm (dreg, (uintptr)&dhex_l10_e); + break; + case 0x0f: + fmov_d_ri_0 (dreg); + break; + case 0x30: + fmov_d_rm (dreg, (uintptr)&dhex_ln_2); + break; + case 0x31: + fmov_d_rm (dreg, (uintptr)&dhex_ln_10); + break; + case 0x32: + fmov_d_ri_1 (dreg); + break; + case 0x33: + fmov_d_ri_10 (dreg); + break; + case 0x34: + fmov_d_ri_100 (dreg); + break; + case 0x35: + fmov_l_ri (dreg, 10000); + break; + case 0x36: + fmov_rm (dreg, (uintptr)&fp_1e8); + break; + case 0x37: + fmov_d_rm (dreg, (uintptr)&dhex_1e16); + break; + case 0x38: + fmov_d_rm (dreg, (uintptr)&dhex_1e32); + break; + case 0x39: + fmov_d_rm (dreg, (uintptr)&dhex_1e64); + break; + case 0x3a: + fmov_d_rm (dreg, (uintptr)&dhex_1e128); + break; + case 0x3b: + fmov_d_rm (dreg, (uintptr)&dhex_1e256); + break; + default: + FAIL (1); + return; + } + fmov_rr (FP_RESULT, dreg); + return; + } + if (opmode & 0x20) /* two operands, so we need a scratch reg */ + sreg = FS1; + else /* one operand only, thus we can load the argument into dreg */ + sreg = dreg; + if(opmode >= 0x30 && opmode <= 0x37) { + // get out early for unsupported ops + FAIL (1); + return; + } + if ((prec = comp_fp_get (opcode, extra, sreg)) < 0) { + FAIL (1); + return; + } + if (!opmode) { /* FMOVE ,FPx */ + fmov_rr (FP_RESULT, dreg); + return; + } + /* no break here for to dreg */ + case 0: /* directly from sreg to dreg */ + if (!source) { /* no */ + dont_care_fflags (); + sreg = (extra >> 10) & 7; + } + switch (opmode) { + case 0x00: /* FMOVE */ + fmov_rr (dreg, sreg); + break; + case 0x01: /* FINT */ + frndint_rr (dreg, sreg); + break; + case 0x02: /* FSINH */ + ffunc_rr (sinh, dreg, sreg); + break; + case 0x03: /* FINTRZ */ + frndintz_rr (dreg, sreg); + break; + case 0x04: /* FSQRT */ + fsqrt_rr (dreg, sreg); + break; + case 0x06: /* FLOGNP1 */ + ffunc_rr (log1p, dreg, sreg); + break; + case 0x08: /* FETOXM1 */ + ffunc_rr (expm1, dreg, sreg); + break; + case 0x09: /* FTANH */ + ffunc_rr (tanh, dreg, sreg); + break; + case 0x0a: /* FATAN */ + ffunc_rr (atan, dreg, sreg); + break; + case 0x0c: /* FASIN */ + ffunc_rr (asin, dreg, sreg); + break; + case 0x0d: /* FATANH */ + ffunc_rr (atanh, dreg, sreg); + break; + case 0x0e: /* FSIN */ + ffunc_rr (sin, dreg, sreg); + break; + case 0x0f: /* FTAN */ + ffunc_rr (tan, dreg, sreg); + break; + case 0x10: /* FETOX */ + ffunc_rr (exp, dreg, sreg); + break; + case 0x11: /* FTWOTOX */ + fpowx_rr (2, dreg, sreg); + break; + case 0x12: /* FTENTOX */ + fpowx_rr (10, dreg, sreg); + break; + case 0x14: /* FLOGN */ + ffunc_rr (log, dreg, sreg); + break; + case 0x15: /* FLOG10 */ + ffunc_rr (log10, dreg, sreg); + break; + case 0x16: /* FLOG2 */ + ffunc_rr (log2, dreg, sreg); + break; + case 0x18: /* FABS */ + fabs_rr (dreg, sreg); + break; + case 0x19: /* FCOSH */ + ffunc_rr (cosh, dreg, sreg); + break; + case 0x1a: /* FNEG */ + fneg_rr (dreg, sreg); + break; + case 0x1c: /* FACOS */ + ffunc_rr (acos, dreg, sreg); + break; + case 0x1d: /* FCOS */ + ffunc_rr (cos, dreg, sreg); + break; + case 0x20: /* FDIV */ + fdiv_rr (dreg, sreg); + break; + case 0x21: /* FMOD */ + fmod_rr (dreg, sreg); + break; + case 0x22: /* FADD */ + fadd_rr (dreg, sreg); + break; + case 0x23: /* FMUL */ + fmul_rr (dreg, sreg); + break; + case 0x24: /* FSGLDIV */ + fsgldiv_rr (dreg, sreg); + break; + case 0x60: /* FSDIV */ + fdiv_rr (dreg, sreg); + if (!currprefs.fpu_strict) /* faster, but less strict rounding */ + break; + fcuts_r (dreg); + break; + case 0x25: /* FREM */ + frem1_rr (dreg, sreg); + break; + case 0x27: /* FSGLMUL */ + fsglmul_rr (dreg, sreg); + break; + case 0x63: /* FSMUL */ + fmul_rr (dreg, sreg); + if (!currprefs.fpu_strict) /* faster, but less strict rounding */ + break; + fcuts_r (dreg); + break; + case 0x28: /* FSUB */ + fsub_rr (dreg, sreg); + break; + case 0x30: /* FSINCOS */ + case 0x31: + case 0x32: + case 0x33: + case 0x34: + case 0x35: + case 0x36: + case 0x37: + FAIL (1); + return; + case 0x38: /* FCMP */ + fmov_rr (FP_RESULT, dreg); + fsub_rr (FP_RESULT, sreg); + return; + case 0x3a: /* FTST */ + fmov_rr (FP_RESULT, sreg); + return; + case 0x40: /* FSMOVE */ + if (prec == 1 || !currprefs.fpu_strict) { + if (sreg != dreg) /* no */ + fmov_rr (dreg, sreg); + } + else { + fmovs_rr (dreg, sreg); + } + break; + case 0x44: /* FDMOVE */ + if (sreg != dreg) /* no */ + fmov_rr (dreg, sreg); + break; + case 0x41: /* FSSQRT */ + fsqrt_rr (dreg, sreg); + if (!currprefs.fpu_strict) /* faster, but less strict rounding */ + break; + fcuts_r (dreg); + break; + case 0x45: /* FDSQRT */ + fsqrt_rr (dreg, sreg); + break; + case 0x58: /* FSABS */ + fabs_rr (dreg, sreg); + if (prec != 1 && currprefs.fpu_strict) + fcuts_r (dreg); + break; + case 0x5a: /* FSNEG */ + fneg_rr (dreg, sreg); + if (prec != 1 && currprefs.fpu_strict) + fcuts_r (dreg); + break; + case 0x5c: /* FDABS */ + fabs_rr (dreg, sreg); + break; + case 0x5e: /* FDNEG */ + fneg_rr (dreg, sreg); + break; + case 0x62: /* FSADD */ + fadd_rr (dreg, sreg); + if (!currprefs.fpu_strict) /* faster, but less strict rounding */ + break; + fcuts_r (dreg); + break; + case 0x64: /* FDDIV */ + fdiv_rr (dreg, sreg); + break; + case 0x66: /* FDADD */ + fadd_rr (dreg, sreg); + break; + case 0x67: /* FDMUL */ + fmul_rr (dreg, sreg); + break; + case 0x68: /* FSSUB */ + fsub_rr (dreg, sreg); + if (!currprefs.fpu_strict) /* faster, but less strict rounding */ + break; + fcuts_r (dreg); + break; + case 0x6c: /* FDSUB */ + fsub_rr (dreg, sreg); + break; + default: + FAIL (1); + return; + } + fmov_rr (FP_RESULT, dreg); + return; default: - FAIL(1); - return; - } - fmov_rr(FP_RESULT, dreg); - return; - default: - write_log(_T("Unsupported JIT-FPU instruction: 0x%04x %04x\n"), opcode, extra); - FAIL(1); - return; - } + write_log (_T ("Unsupported JIT-FPU instruction: 0x%04x %04x\n"), opcode, extra); + FAIL (1); + return; + } } #endif diff --git a/src/jit/compemu_midfunc_arm.cpp.in b/src/jit/compemu_midfunc_arm.cpp.in index fcec7332..4f101fcc 100644 --- a/src/jit/compemu_midfunc_arm.cpp.in +++ b/src/jit/compemu_midfunc_arm.cpp.in @@ -2,6 +2,7 @@ * compiler/compemu_midfunc_arm.cpp - Native MIDFUNCS for ARM * * Copyright (c) 2014 Jens Heitmann of ARAnyM dev team (see AUTHORS) + * Copyright (c) 2019 TomB * * Inspired by Christian Bauer's Basilisk II * @@ -162,45 +163,16 @@ MIDFUNC(0,make_flags_live,(void)) } MENDFUNC(0,make_flags_live,(void)) -MIDFUNC(2,mov_l_mi,(IMM d, IMM s)) +MIDFUNC(2,mov_l_mi,(IMPTR d, IM32 s)) { -#ifdef ARMV6T2 - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - uae_s32 idx = d - (uae_u32) ®s; - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - MOVW_ri16(REG_WORK1, d); - MOVT_ri16(REG_WORK1, d >> 16); - MOVW_ri16(REG_WORK2, s); - if(s >> 16) - MOVT_ri16(REG_WORK2, s >> 16); - STR_rR(REG_WORK2, REG_WORK1); - } -#else - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - uae_s32 idx = d - (uae_u32) & regs; - STR_rRI(REG_WORK2, R_REGSTRUCT, idx); - } else { - data_check_end(8, 12); - uae_s32 offs = data_long_offs(d); - - LDR_rRI(REG_WORK1, RPC_INDEX, offs); - - offs = data_long_offs(s); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); - - STR_rR(REG_WORK2, REG_WORK1); - } -#endif + /* d points always to memory in regs struct */ + LOAD_U32(REG_WORK2, s); + uintptr idx = d - (uintptr) ®s; + STR_rRI(REG_WORK2, R_REGSTRUCT, idx); } -MENDFUNC(2,mov_l_mi,(IMM d, IMM s)) +MENDFUNC(2,mov_l_mi,(IMPTR d, IM32 s)) -MIDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IMM shift, IMM extend)) +MIDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IM8 shift, IM8 extend)) { if(isconst(target) && isconst(reg)) { if(extend) @@ -223,9 +195,9 @@ MIDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IMM shift, IMM extend)) unlock2(target); unlock2(reg); } -MENDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IMM shift, IMM extend)) +MENDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IM8 shift, IM8 extend)) -MIDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IMM shift, IMM extend)) +MIDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IM8 shift, IM8 extend)) { if(isconst(reg)) { if(extend) @@ -248,7 +220,7 @@ MIDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IMM shift, IMM extend)) unlock2(target); unlock2(reg); } -MENDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IMM shift, IMM extend)) +MENDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IM8 shift, IM8 extend)) MIDFUNC(2,sign_extend_16_rr,(W4 d, RR2 s)) { @@ -272,7 +244,7 @@ MIDFUNC(2,sign_extend_16_rr,(W4 d, RR2 s)) } MENDFUNC(2,sign_extend_16_rr,(W4 d, RR2 s)) -MIDFUNC(3,lea_l_brr,(W4 d, RR4 s, IMM offset)) +MIDFUNC(3,lea_l_brr,(W4 d, RR4 s, IM32 offset)) { if (isconst(s)) { COMPCALL(mov_l_ri)(d, live.state[s].val+offset); @@ -290,31 +262,32 @@ MIDFUNC(3,lea_l_brr,(W4 d, RR4 s, IMM offset)) if(CHECK32(offset)) { ADD_rri(d, s, offset); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, offset); - if(offset >> 16) - MOVT_ri16(REG_WORK1, offset >> 16); -#else - uae_s32 offs = data_long_offs(offset); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, offset); ADD_rrr(d, s, REG_WORK1); } EXIT_REGS(d,s); } -MENDFUNC(3,lea_l_brr,(W4 d, RR4 s, IMM offset)) +MENDFUNC(3,lea_l_brr,(W4 d, RR4 s, IM32 offset)) -MIDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IMM factor, IMM offset)) +MIDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor, IM8 offset)) { if (!offset) { COMPCALL(lea_l_rr_indexed)(d, s, index, factor); return; } + if (isconst(s) && isconst(index)) { + set_const(d, live.state[s].val + (uae_s32)(uae_s8)offset + live.state[index].val * factor); + return; + } s = readreg(s); - index = readreg(index); - d = writereg(d); + if(d == index) { + d = index = rmw(d); + } else { + index = readreg(index); + d = writereg(d); + } int shft; switch(factor) { @@ -325,21 +298,34 @@ MIDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IMM factor, IMM offset)) default: abort(); } - SIGNED8_IMM_2_REG(REG_WORK1, offset); - ADD_rrr(REG_WORK1, s, REG_WORK1); + if(offset >= 0 && offset <= 127) { + ADD_rri(REG_WORK1, s, offset); + } else { + SUB_rri(REG_WORK1, s, -offset); + } ADD_rrrLSLi(d, REG_WORK1, index, shft); unlock2(d); - unlock2(index); + if(d != index) + unlock2(index); unlock2(s); } -MENDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IMM factor, IMM offset)) +MENDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor, IM8 offset)) -MIDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IMM factor)) +MIDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor)) { + if (isconst(s) && isconst(index)) { + set_const(d, live.state[s].val + live.state[index].val * factor); + return; + } + s = readreg(s); - index = readreg(index); - d = writereg(d); + if(d == index) { + d = index = rmw(d); + } else { + index = readreg(index); + d = writereg(d); + } int shft; switch(factor) { @@ -353,10 +339,11 @@ MIDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IMM factor)) ADD_rrrLSLi(d, s, index, shft); unlock2(d); - unlock2(index); + if(d != index) + unlock2(index); unlock2(s); } -MENDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IMM factor)) +MENDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor)) MIDFUNC(2,mov_l_rr,(W4 d, RR4 s)) { @@ -374,8 +361,7 @@ MIDFUNC(2,mov_l_rr,(W4 d, RR4 s)) s = readreg(s); live.state[d].realreg = s; live.state[d].realind = live.nat[s].nholds; - live.state[d].val = live.state[olds].val; - live.state[d].validsize = 4; + live.state[d].val = 0; set_status(d, DIRTY); live.nat[s].holds[live.nat[s].nholds] = d; @@ -384,8 +370,9 @@ MIDFUNC(2,mov_l_rr,(W4 d, RR4 s)) } MENDFUNC(2,mov_l_rr,(W4 d, RR4 s)) -MIDFUNC(2,mov_l_mr,(IMM d, RR4 s)) +MIDFUNC(2,mov_l_mr,(IMPTR d, RR4 s)) { + /* d points always to memory in regs struct */ if (isconst(s)) { COMPCALL(mov_l_mi)(d, live.state[s].val); return; @@ -393,55 +380,32 @@ MIDFUNC(2,mov_l_mr,(IMM d, RR4 s)) s = readreg(s); - if(d >= (uae_u32) ®s && d < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = d - (uae_u32) ®s; - STR_rRI(s, R_REGSTRUCT, idx); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, d); - if(d >> 16) - MOVT_ri16(REG_WORK1, d >> 16); -#else - uae_s32 offs = data_long_offs(d); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - STR_rR(s, REG_WORK1); - } + uintptr idx = d - (uintptr) ®s; + STR_rRI(s, R_REGSTRUCT, idx); unlock2(s); } -MENDFUNC(2,mov_l_mr,(IMM d, RR4 s)) +MENDFUNC(2,mov_l_mr,(IMPTR d, RR4 s)) -MIDFUNC(2,mov_l_rm,(W4 d, IMM s)) +MIDFUNC(2,mov_l_rm,(W4 d, IMPTR s)) { + /* s points always to memory in regs struct */ d = writereg(d); - if(s >= (uae_u32) ®s && s < ((uae_u32) ®s) + sizeof(struct regstruct)) { - uae_s32 idx = s - (uae_u32) & regs; - LDR_rRI(d, R_REGSTRUCT, idx); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, s); - if(s >> 16) - MOVT_ri16(REG_WORK1, s >> 16); -#else - uae_s32 offs = data_long_offs(s); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - LDR_rR(d, REG_WORK1); - } + uintptr idx = s - (uintptr) ®s; + LDR_rRI(d, R_REGSTRUCT, idx); unlock2(d); } -MENDFUNC(2,mov_l_rm,(W4 d, IMM s)) +MENDFUNC(2,mov_l_rm,(W4 d, IMPTR s)) -MIDFUNC(2,mov_l_ri,(W4 d, IMM s)) +MIDFUNC(2,mov_l_ri,(W4 d, IM32 s)) { set_const(d, s); } -MENDFUNC(2,mov_l_ri,(W4 d, IMM s)) +MENDFUNC(2,mov_l_ri,(W4 d, IM32 s)) -MIDFUNC(2,mov_b_ri,(W1 d, IMM s)) +MIDFUNC(2,mov_b_ri,(W1 d, IM8 s)) { if(d < 16) { if (isconst(d)) { @@ -458,9 +422,9 @@ MIDFUNC(2,mov_b_ri,(W1 d, IMM s)) set_const(d, s & 0xff); } } -MENDFUNC(2,mov_b_ri,(W1 d, IMM s)) +MENDFUNC(2,mov_b_ri,(W1 d, IM8 s)) -MIDFUNC(2,sub_l_ri,(RW4 d, IMM i)) +MIDFUNC(2,sub_l_ri,(RW4 d, IM8 i)) { if (!i) return; @@ -471,25 +435,13 @@ MIDFUNC(2,sub_l_ri,(RW4 d, IMM i)) d = rmw(d); - if(CHECK32(i)) { - SUB_rri(d, d, i); - } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, i); - if(i >> 16) - MOVT_ri16(REG_WORK1, i >> 16); -#else - uae_s32 offs = data_long_offs(i); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif - SUB_rrr(d, d, REG_WORK1); - } + SUB_rri(d, d, i); unlock2(d); } -MENDFUNC(2,sub_l_ri,(RW4 d, IMM i)) +MENDFUNC(2,sub_l_ri,(RW4 d, IM8 i)) -MIDFUNC(2,sub_w_ri,(RW2 d, IMM i)) +MIDFUNC(2,sub_w_ri,(RW2 d, IM8 i)) { // This function is only called with i = 1 // Caller needs flags... @@ -502,14 +454,9 @@ MIDFUNC(2,sub_w_ri,(RW2 d, IMM i)) SUBS_rri(REG_WORK2, REG_WORK2, (i & 0xff) << 16); PKHTB_rrrASRi(d, d, REG_WORK2, 16); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - unlock2(d); } -MENDFUNC(2,sub_w_ri,(RW2 d, IMM i)) - +MENDFUNC(2,sub_w_ri,(RW2 d, IM8 i)) /* forget_about() takes a mid-layer register */ MIDFUNC(1,forget_about,(W4 r)) @@ -522,8 +469,6 @@ MIDFUNC(1,forget_about,(W4 r)) MENDFUNC(1,forget_about,(W4 r)) -// ARM optimized functions - MIDFUNC(2,arm_ADD_l,(RW4 d, RR4 s)) { if (isconst(s)) { @@ -539,7 +484,7 @@ MIDFUNC(2,arm_ADD_l,(RW4 d, RR4 s)) } MENDFUNC(2,arm_ADD_l,(RW4 d, RR4 s)) -MIDFUNC(2,arm_ADD_l_ri,(RW4 d, IMM i)) +MIDFUNC(2,arm_ADD_l_ri,(RW4 d, IM32 i)) { if (!i) return; @@ -553,22 +498,15 @@ MIDFUNC(2,arm_ADD_l_ri,(RW4 d, IMM i)) if(CHECK32(i)) { ADD_rri(d, d, i); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, i); - if(i >> 16) - MOVT_ri16(REG_WORK1, i >> 16); -#else - uae_s32 offs = data_long_offs(i); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U32(REG_WORK1, i); ADD_rrr(d, d, REG_WORK1); } unlock2(d); } -MENDFUNC(2,arm_ADD_l_ri,(RW4 d, IMM i)) +MENDFUNC(2,arm_ADD_l_ri,(RW4 d, IM32 i)) -MIDFUNC(2,arm_ADD_l_ri8,(RW4 d, IMM i)) +MIDFUNC(2,arm_ADD_l_ri8,(RW4 d, IM8 i)) { if (!i) return; @@ -581,9 +519,9 @@ MIDFUNC(2,arm_ADD_l_ri8,(RW4 d, IMM i)) ADD_rri(d, d, i); unlock2(d); } -MENDFUNC(2,arm_ADD_l_ri8,(RW4 d, IMM i)) +MENDFUNC(2,arm_ADD_l_ri8,(RW4 d, IM8 i)) -MIDFUNC(2,arm_SUB_l_ri8,(RW4 d, IMM i)) +MIDFUNC(2,arm_SUB_l_ri8,(RW4 d, IM8 i)) { if (!i) return; @@ -596,10 +534,9 @@ MIDFUNC(2,arm_SUB_l_ri8,(RW4 d, IMM i)) SUB_rri(d, d, i); unlock2(d); } -MENDFUNC(2,arm_SUB_l_ri8,(RW4 d, IMM i)) +MENDFUNC(2,arm_SUB_l_ri8,(RW4 d, IM8 i)) -// Other STATIC_INLINE void flush_cpu_icache(void *start, void *stop) { register void *_beg __asm ("a1") = start; @@ -617,8 +554,10 @@ STATIC_INLINE void flush_cpu_icache(void *start, void *stop) #endif } -STATIC_INLINE void write_jmp_target(uae_u32* jmpaddr, uintptr a) { - uae_s32 off = ((uae_u32)a - (uae_u32)jmpaddr - 8) >> 2; + +STATIC_INLINE void write_jmp_target(uae_u32* jmpaddr, uintptr a) +{ + uintptr off = ((uintptr)a - (uintptr)jmpaddr - 8) >> 2; *(jmpaddr) = (*(jmpaddr) & 0xff000000) | (off & 0x00ffffff); flush_cpu_icache((void *)jmpaddr, (void *)&jmpaddr[1]); } @@ -709,7 +648,7 @@ MIDFUNC(3,fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) } MENDFUNC(3,fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) -MIDFUNC(2,fmov_l_ri,(FW d, IMM i)) +MIDFUNC(2,fmov_l_ri,(FW d, IM32 i)) { switch(i) { case 0: @@ -731,16 +670,16 @@ MIDFUNC(2,fmov_l_ri,(FW d, IMM i)) f_unlock(d); } } -MENDFUNC(2,fmov_l_ri,(FW d, IMM i)) +MENDFUNC(2,fmov_l_ri,(FW d, IM32 i)) -MIDFUNC(2,fmov_s_ri,(FW d, IMM i)) +MIDFUNC(2,fmov_s_ri,(FW d, IM32 i)) { d = f_writereg(d); compemu_raw_mov_l_ri(REG_WORK1, i); raw_fmov_s_rr(d, REG_WORK1); f_unlock(d); } -MENDFUNC(2,fmov_s_ri,(FW d, IMM i)) +MENDFUNC(2,fmov_s_ri,(FW d, IM32 i)) MIDFUNC(2,fmov_to_l_rr,(W4 d, FR s)) { @@ -1107,11 +1046,11 @@ MIDFUNC(2,fp_fscc_ri,(RW4 d, int cc)) } MENDFUNC(2,fp_fscc_ri,(RW4 d, int cc)) -MIDFUNC(1,roundingmode,(IMM mode)) +MIDFUNC(1,roundingmode,(IM32 mode)) { raw_roundingmode(mode); } -MENDFUNC(1,roundingmode,(IMM mode)) +MENDFUNC(1,roundingmode,(IM32 mode)) #endif // USE_JIT_FPU diff --git a/src/jit/compemu_midfunc_arm.h b/src/jit/compemu_midfunc_arm.h index 847587c1..2401f012 100644 --- a/src/jit/compemu_midfunc_arm.h +++ b/src/jit/compemu_midfunc_arm.h @@ -33,29 +33,28 @@ // Arm optimized midfunc DECLARE_MIDFUNC(arm_ADD_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(arm_ADD_l_ri(RW4 d, IMM i)); -DECLARE_MIDFUNC(arm_ADD_l_ri8(RW4 d, IMM i)); -DECLARE_MIDFUNC(arm_SUB_l_ri8(RW4 d, IMM i)); +DECLARE_MIDFUNC(arm_ADD_l_ri(RW4 d, IM32 i)); +DECLARE_MIDFUNC(arm_ADD_l_ri8(RW4 d, IM8 i)); +DECLARE_MIDFUNC(arm_SUB_l_ri8(RW4 d, IM8 i)); // Emulated midfunc -DECLARE_MIDFUNC(disp_ea20_target_add(RW4 target, RR4 reg, IMM shift, IMM extend)); -DECLARE_MIDFUNC(disp_ea20_target_mov(W4 target, RR4 reg, IMM shift, IMM extend)); +DECLARE_MIDFUNC(disp_ea20_target_add(RW4 target, RR4 reg, IM8 shift, IM8 extend)); +DECLARE_MIDFUNC(disp_ea20_target_mov(W4 target, RR4 reg, IM8 shift, IM8 extend)); -DECLARE_MIDFUNC(mov_l_mi(IMM d, IMM s)); +DECLARE_MIDFUNC(mov_l_mi(IMPTR d, IM32 s)); DECLARE_MIDFUNC(pop_l(W4 d)); DECLARE_MIDFUNC(push_l(RR4 s)); DECLARE_MIDFUNC(sign_extend_16_rr(W4 d, RR2 s)); -DECLARE_MIDFUNC(lea_l_brr(W4 d, RR4 s, IMM offset)); -DECLARE_MIDFUNC(lea_l_brr_indexed(W4 d, RR4 s, RR4 index, IMM factor, IMM offset)); -DECLARE_MIDFUNC(lea_l_rr_indexed(W4 d, RR4 s, RR4 index, IMM factor)); +DECLARE_MIDFUNC(lea_l_brr(W4 d, RR4 s, IM32 offset)); +DECLARE_MIDFUNC(lea_l_brr_indexed(W4 d, RR4 s, RR4 index, IM8 factor, IM8 offset)); +DECLARE_MIDFUNC(lea_l_rr_indexed(W4 d, RR4 s, RR4 index, IM8 factor)); DECLARE_MIDFUNC(mov_l_rr(W4 d, RR4 s)); -DECLARE_MIDFUNC(mov_l_mr(IMM d, RR4 s)); -DECLARE_MIDFUNC(mov_l_rm(W4 d, IMM s)); -DECLARE_MIDFUNC(mov_b_rm(W1 d, IMM s)); -DECLARE_MIDFUNC(mov_l_ri(W4 d, IMM s)); -DECLARE_MIDFUNC(mov_b_ri(W1 d, IMM s)); -DECLARE_MIDFUNC(sub_l_ri(RW4 d, IMM i)); -DECLARE_MIDFUNC(sub_w_ri(RW2 d, IMM i)); +DECLARE_MIDFUNC(mov_l_mr(IMPTR d, RR4 s)); +DECLARE_MIDFUNC(mov_l_rm(W4 d, IMPTR s)); +DECLARE_MIDFUNC(mov_l_ri(W4 d, IM32 s)); +DECLARE_MIDFUNC(mov_b_ri(W1 d, IM8 s)); +DECLARE_MIDFUNC(sub_l_ri(RW4 d, IM8 i)); +DECLARE_MIDFUNC(sub_w_ri(RW2 d, IM8 i)); DECLARE_MIDFUNC(live_flags(void)); DECLARE_MIDFUNC(dont_care_flags(void)); DECLARE_MIDFUNC(make_flags_live(void)); @@ -70,8 +69,8 @@ DECLARE_MIDFUNC(fmov_s_rr(FW d, RR4 s)); DECLARE_MIDFUNC(fmov_w_rr(FW d, RR2 s)); DECLARE_MIDFUNC(fmov_b_rr(FW d, RR1 s)); DECLARE_MIDFUNC(fmov_d_rrr(FW d, RR4 s1, RR4 s2)); -DECLARE_MIDFUNC(fmov_l_ri(FW d, IMM i)); -DECLARE_MIDFUNC(fmov_s_ri(FW d, IMM i)); +DECLARE_MIDFUNC(fmov_l_ri(FW d, IM32 i)); +DECLARE_MIDFUNC(fmov_s_ri(FW d, IM32 i)); DECLARE_MIDFUNC(fmov_to_l_rr(W4 d, FR s)); DECLARE_MIDFUNC(fmov_to_s_rr(W4 d, FR s)); DECLARE_MIDFUNC(fmov_to_w_rr(W4 d, FR s)); @@ -108,4 +107,4 @@ DECLARE_MIDFUNC(fp_to_exten_rm(FW d, RR4 adr)); DECLARE_MIDFUNC(fp_from_double_mr(RR4 adr, FR s)); DECLARE_MIDFUNC(fp_to_double_rm(FW d, RR4 adr)); DECLARE_MIDFUNC(fp_fscc_ri(RW4, int cc)); -DECLARE_MIDFUNC(roundingmode(IMM mode)); +DECLARE_MIDFUNC(roundingmode(IM32 mode)); diff --git a/src/jit/compemu_midfunc_arm2.cpp.in b/src/jit/compemu_midfunc_arm2.cpp.in index f93e9502..5a6580c6 100644 --- a/src/jit/compemu_midfunc_arm2.cpp.in +++ b/src/jit/compemu_midfunc_arm2.cpp.in @@ -2,6 +2,7 @@ * compiler/compemu_midfunc_arm.cpp - Native MIDFUNCS for ARM (JIT v2) * * Copyright (c) 2014 Jens Heitmann of ARAnyM dev team (see AUTHORS) + * Copyright (c) 2019 TomB * * Inspired by Christian Bauer's Basilisk II * @@ -52,28 +53,15 @@ const uae_u32 ARM_CCR_MAP[] = { 0, ARM_C_FLAG, // 1 C #define DUPLICACTE_CARRY \ if (needed_flags & FLAG_X) { \ int x = writereg(FLAGX); \ - MOV_ri(x, 0); \ - ADC_rri(x, x, 0); \ + MOV_ri(x, 0); \ + if (flags_carry_inverted) { \ + CC_MOV_ri(NATIVE_CC_CC, x, 1); \ + } else { \ + ADC_rri(x, x, 0); \ + } \ unlock2(x); \ } -#ifdef ARMV6T2 -#define DUPLICACTE_CARRY_FROM_REG(r) \ - if (needed_flags & FLAG_X) { \ - int x = writereg(FLAGX); \ - UBFX_rrii(x, r, 29, 1); \ - unlock2(x); \ - } -#else -#define DUPLICACTE_CARRY_FROM_REG(r) \ - if (needed_flags & FLAG_X) { \ - int x = writereg(FLAGX); \ - LSR_rri(x, r, 29); \ - AND_rri(x, x, 1); \ - unlock2(x); \ - } -#endif - /* * ADD * Operand Syntax: , Dn @@ -88,13 +76,8 @@ const uae_u32 ARM_CCR_MAP[] = { 0, ARM_C_FLAG, // 1 C * C Set if a carry is generated. Cleared otherwise. * */ -MIDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IMM v)) +MIDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IM8 v)) { - if (isconst(s)) { - set_const(d, live.state[s].val + v); - return; - } - int s_is_d = (s == d); if(s_is_d) { s = d = rmw(d); @@ -107,15 +90,10 @@ MIDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IMM v)) EXIT_REGS(d, s); } -MENDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IMM v)) +MENDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IM8 v)) -MIDFUNC(2,jnf_ADD_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jnf_ADD_b_imm,(RW1 d, IM8 v)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | (((live.state[d].val & 0xff) + (v & 0xff)) & 0x000000ff)); - return; - } - INIT_REG_b(d); if(targetIsReg) { @@ -133,7 +111,7 @@ MIDFUNC(2,jnf_ADD_b_imm,(RW1 d, IMM v)) unlock2(d); } -MENDFUNC(2,jnf_ADD_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jnf_ADD_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jnf_ADD_b,(RW1 d, RR1 s)) { @@ -161,20 +139,15 @@ MIDFUNC(2,jnf_ADD_b,(RW1 d, RR1 s)) } MENDFUNC(2,jnf_ADD_b,(RW1 d, RR1 s)) -MIDFUNC(2,jnf_ADD_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jnf_ADD_w_imm,(RW2 d, IM16 v)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | (((live.state[d].val & 0xffff) + (v & 0xffff)) & 0x0000ffff)); - return; - } - INIT_REG_w(d); if(targetIsReg) { if(CHECK32(v & 0xffff)) { ADD_rri(REG_WORK1, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); ADD_rrr(REG_WORK1, d, REG_WORK1); } PKHTB_rrr(d, d, REG_WORK1); @@ -182,14 +155,14 @@ MIDFUNC(2,jnf_ADD_w_imm,(RW2 d, IMM v)) if(CHECK32(v & 0xffff)) { ADD_rri(d, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); ADD_rrr(d, d, REG_WORK1); } } unlock2(d); } -MENDFUNC(2,jnf_ADD_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jnf_ADD_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jnf_ADD_w,(RW2 d, RR2 s)) { @@ -211,10 +184,10 @@ MIDFUNC(2,jnf_ADD_w,(RW2 d, RR2 s)) } MENDFUNC(2,jnf_ADD_w,(RW2 d, RR2 s)) -MIDFUNC(2,jnf_ADD_l_imm,(RW4 d, IMM v)) +MIDFUNC(2,jnf_ADD_l_imm,(RW4 d, IM32 v)) { if (isconst(d)) { - set_const(d, live.state[d].val + v); + live.state[d].val = live.state[d].val + v; return; } @@ -223,17 +196,22 @@ MIDFUNC(2,jnf_ADD_l_imm,(RW4 d, IMM v)) if(CHECK32(v)) { ADD_rri(d, d, v); } else { - compemu_raw_mov_l_ri(REG_WORK1, v); + // never reached... + LOAD_U32(REG_WORK1, v); ADD_rrr(d, d, REG_WORK1); } unlock2(d); } -MENDFUNC(2,jnf_ADD_l_imm,(RW4 d, IMM v)) +MENDFUNC(2,jnf_ADD_l_imm,(RW4 d, IM32 v)) MIDFUNC(2,jnf_ADD_l,(RW4 d, RR4 s)) { - if (isconst(s)) { + if (isconst(d) && isconst(s)) { + COMPCALL(jnf_ADD_l_imm)(d, live.state[s].val); + return; + } + if (isconst(s) && CHECK32(live.state[s].val)) { COMPCALL(jnf_ADD_l_imm)(d, live.state[s].val); return; } @@ -246,7 +224,7 @@ MIDFUNC(2,jnf_ADD_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_ADD_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_ADD_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jff_ADD_b_imm,(RW1 d, IM8 v)) { INIT_REG_b(d); @@ -259,11 +237,12 @@ MIDFUNC(2,jff_ADD_b_imm,(RW1 d, IMM v)) LSR_rri(d, REG_WORK1, 24); } + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); } -MENDFUNC(2,jff_ADD_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jff_ADD_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jff_ADD_b,(RW1 d, RR1 s)) { @@ -283,13 +262,14 @@ MIDFUNC(2,jff_ADD_b,(RW1 d, RR1 s)) LSR_rri(d, REG_WORK1, 24); } + flags_carry_inverted = false; DUPLICACTE_CARRY EXIT_REGS(d, s); } MENDFUNC(2,jff_ADD_b,(RW1 d, RR1 s)) -MIDFUNC(2,jff_ADD_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jff_ADD_w_imm,(RW2 d, IM16 v)) { INIT_REG_w(d); @@ -300,15 +280,16 @@ MIDFUNC(2,jff_ADD_w_imm,(RW2 d, IMM v)) uae_s32 offs = data_long_offs(v << 16); LDR_rRI(REG_WORK1, RPC_INDEX, offs); #endif - + ADDS_rrrLSLi(REG_WORK1, REG_WORK1, d, 16); PKHTB_rrrASRi(d, d, REG_WORK1, 16); + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); } -MENDFUNC(2,jff_ADD_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jff_ADD_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jff_ADD_w,(RW2 d, RR2 s)) { @@ -323,32 +304,35 @@ MIDFUNC(2,jff_ADD_w,(RW2 d, RR2 s)) ADDS_rrrLSLi(REG_WORK1, REG_WORK1, d, 16); PKHTB_rrrASRi(d, d, REG_WORK1, 16); + flags_carry_inverted = false; DUPLICACTE_CARRY EXIT_REGS(d, s); } MENDFUNC(2,jff_ADD_w,(RW2 d, RR2 s)) -MIDFUNC(2,jff_ADD_l_imm,(RW4 d, IMM v)) +MIDFUNC(2,jff_ADD_l_imm,(RW4 d, IM32 v)) { d = rmw(d); if(CHECK32(v)) { ADDS_rri(d, d, v); } else { - compemu_raw_mov_l_ri(REG_WORK2, v); + // never reached... + LOAD_U32(REG_WORK2, v); ADDS_rrr(d, d, REG_WORK2); } + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); } -MENDFUNC(2,jff_ADD_l_imm,(RW4 d, IMM v)) +MENDFUNC(2,jff_ADD_l_imm,(RW4 d, IM32 v)) MIDFUNC(2,jff_ADD_l,(RW4 d, RR4 s)) { - if (isconst(s)) { + if (isconst(s) && CHECK32(live.state[s].val)) { COMPCALL(jff_ADD_l_imm)(d, live.state[s].val); return; } @@ -357,6 +341,7 @@ MIDFUNC(2,jff_ADD_l,(RW4 d, RR4 s)) ADDS_rrr(d, d, s); + flags_carry_inverted = false; DUPLICACTE_CARRY EXIT_REGS(d, s); @@ -375,7 +360,22 @@ MENDFUNC(2,jff_ADD_l,(RW4 d, RR4 s)) MIDFUNC(2,jnf_ADDA_w,(RW4 d, RR2 s)) { if (isconst(d) && isconst(s)) { - set_const(d, live.state[d].val + (uae_s32)(uae_s16)(live.state[s].val & 0xffff)); + live.state[d].val = live.state[d].val + (uae_s32)(uae_s16)(live.state[s].val & 0xffff); + return; + } + if (isconst(s)) { + // no need to put virt. register s into a real host register via readreg() + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + if(CHECK32(tmp)) { + ADD_rri(d, d, tmp); + } else if (CHECK32(-tmp)) { + SUB_rri(d, d, -tmp); + } else { + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + ADD_rrr(d, d, REG_WORK1); + } + unlock2(d); return; } @@ -393,6 +393,13 @@ MIDFUNC(2,jnf_ADDA_l,(RW4 d, RR4 s)) set_const(d, live.state[d].val + live.state[s].val); return; } + if (isconst(s) && CHECK32((uae_s32)live.state[s].val)) { + uae_s32 tmp = (uae_s32)live.state[s].val; + d = rmw(d); + ADD_rri(d, d, tmp); + unlock2(d); + return; + } INIT_REGS_l(d, s); @@ -421,30 +428,22 @@ MENDFUNC(2,jnf_ADDA_l,(RW4 d, RR4 s)) MIDFUNC(2,jnf_ADDX_b,(RW1 d, RR1 s)) { int x = readreg(FLAGX); + INIT_REGS_b(d, s); - if(targetIsReg) { - if(s_is_d) { - ADD_rrrLSLi(REG_WORK1, x, d, 1); - } else { - ADD_rrr(REG_WORK1, d, s); - ADD_rrr(REG_WORK1, REG_WORK1, x); - } -#ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); -#else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); -#endif + if(s_is_d) { + ADD_rrrLSLi(REG_WORK1, x, d, 1); } else { - if(s_is_d) { - ADD_rrrLSLi(d, x, d, 1); - } else { - ADD_rrr(d, d, s); - ADD_rrr(d, d, x); - } + ADD_rrr(REG_WORK1, d, s); + ADD_rrr(REG_WORK1, REG_WORK1, x); } +#ifdef ARMV6T2 + BFI_rrii(d, REG_WORK1, 0, 7); +#else + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); +#endif EXIT_REGS(d, s); unlock2(x); @@ -454,24 +453,16 @@ MENDFUNC(2,jnf_ADDX_b,(RW1 d, RR1 s)) MIDFUNC(2,jnf_ADDX_w,(RW2 d, RR2 s)) { int x = readreg(FLAGX); + INIT_REGS_w(d, s); - if(targetIsReg) { - if(s_is_d) { - ADD_rrrLSLi(REG_WORK1, x, d, 1); - } else { - ADD_rrr(REG_WORK1, d, s); - ADD_rrr(REG_WORK1, REG_WORK1, x); - } - PKHTB_rrr(d, d, REG_WORK1); + if(s_is_d) { + ADD_rrrLSLi(REG_WORK1, x, d, 1); } else { - if(s_is_d) { - ADD_rrrLSLi(d, x, d, 1); - } else { - ADD_rrr(d, d, s); - ADD_rrr(d, d, x); - } + ADD_rrr(REG_WORK1, d, s); + ADD_rrr(REG_WORK1, REG_WORK1, x); } + PKHTB_rrr(d, d, REG_WORK1); EXIT_REGS(d, s); unlock2(x); @@ -481,6 +472,16 @@ MENDFUNC(2,jnf_ADDX_w,(RW2 d, RR2 s)) MIDFUNC(2,jnf_ADDX_l,(RW4 d, RR4 s)) { int x = readreg(FLAGX); + + if(s != d && isconst(s) && CHECK32(live.state[s].val)) { + d = rmw(d); + ADD_rri(d, d, live.state[s].val); + ADD_rrr(d, d, x); + unlock2(d); + unlock2(x); + return; + } + INIT_REGS_l(d, s); if(s_is_d) { @@ -504,8 +505,7 @@ MIDFUNC(2,jff_ADDX_b,(RW1 d, RR1 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore X to carry (don't care about other flags) - LSL_rri(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + SUBS_rri(REG_WORK3, x, 1); MVN_ri(REG_WORK1, 0); #ifdef ARMV6T2 @@ -515,23 +515,22 @@ MIDFUNC(2,jff_ADDX_b,(RW1 d, RR1 s)) ORR_rrrLSLi(REG_WORK1, REG_WORK1, s, 24); #endif ADCS_rrrLSLi(REG_WORK1, REG_WORK1, d, 24); - if(targetIsReg) { - BIC_rri(d, d, 0xff); - ORR_rrrLSRi(d, d, REG_WORK1, 24); - } else { - LSR_rri(d, REG_WORK1, 24); - } + BIC_rri(d, d, 0xff); + ORR_rrrLSRi(d, d, REG_WORK1, 24); MRS_CPSR(REG_WORK1); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) { #ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry #else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); #endif + } MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, s); } @@ -546,8 +545,7 @@ MIDFUNC(2,jff_ADDX_w,(RW2 d, RR2 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore X to carry (don't care about other flags) - LSL_rri(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + SUBS_rri(REG_WORK3, x, 1); MVN_ri(REG_WORK1, 0); #ifdef ARMV6T2 @@ -562,14 +560,17 @@ MIDFUNC(2,jff_ADDX_w,(RW2 d, RR2 s)) MRS_CPSR(REG_WORK1); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) { #ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry #else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); #endif + } MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, s); } @@ -584,21 +585,23 @@ MIDFUNC(2,jff_ADDX_l,(W4 d, RR4 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore X to carry (don't care about other flags) - LSL_rri(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + SUBS_rri(REG_WORK3, x, 1); ADCS_rrr(d, d, s); MRS_CPSR(REG_WORK1); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) { #ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry #else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); #endif + } MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, s); } @@ -617,9 +620,13 @@ MENDFUNC(2,jff_ADDX_l,(W4 d, RR4 s)) * C Cleared if bit 0 of immediate operand is zero. Unchanged otherwise. * */ -MIDFUNC(1,jff_ANDSR,(IMM s, IMM x)) +MIDFUNC(2,jff_ANDSR,(IM32 s, IM8 x)) { MRS_CPSR(REG_WORK1); + if(flags_carry_inverted) { + EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); + flags_carry_inverted = false; + } AND_rri(REG_WORK1, REG_WORK1, s); MSR_CPSRf_r(REG_WORK1); @@ -629,7 +636,7 @@ MIDFUNC(1,jff_ANDSR,(IMM s, IMM x)) unlock2(f); } } -MENDFUNC(1,jff_ANDSR,(IMM s)) +MENDFUNC(2,jff_ANDSR,(IM32 s, IM8 x)) /* * AND @@ -645,10 +652,10 @@ MENDFUNC(1,jff_ANDSR,(IMM s)) * C Always cleared. * */ -MIDFUNC(2,jnf_AND_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jnf_AND_b_imm,(RW1 d, IM8 v)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((live.state[d].val & v) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val & v) & 0x000000ff); return; } @@ -658,7 +665,7 @@ MIDFUNC(2,jnf_AND_b_imm,(RW1 d, IMM v)) unlock2(d); } -MENDFUNC(2,jnf_AND_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jnf_AND_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jnf_AND_b,(RW1 d, RR1 s)) { @@ -686,20 +693,15 @@ MIDFUNC(2,jnf_AND_b,(RW1 d, RR1 s)) } MENDFUNC(2,jnf_AND_b,(RW1 d, RR1 s)) -MIDFUNC(2,jnf_AND_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jnf_AND_w_imm,(RW2 d, IM16 v)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((live.state[d].val & v) & 0x0000ffff)); - return; - } - INIT_REG_w(d); if(targetIsReg) { if(CHECK32(v & 0xffff)) { AND_rri(REG_WORK1, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); AND_rrr(REG_WORK1, d, REG_WORK1); } PKHTB_rrr(d, d, REG_WORK1); @@ -707,14 +709,14 @@ MIDFUNC(2,jnf_AND_w_imm,(RW2 d, IMM v)) if(CHECK32(v & 0xffff)) { AND_rri(d, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); AND_rrr(d, d, REG_WORK1); } } unlock2(d); } -MENDFUNC(2,jnf_AND_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jnf_AND_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jnf_AND_w,(RW2 d, RR2 s)) { @@ -736,33 +738,8 @@ MIDFUNC(2,jnf_AND_w,(RW2 d, RR2 s)) } MENDFUNC(2,jnf_AND_w,(RW2 d, RR2 s)) -MIDFUNC(2,jnf_AND_l_imm,(RW4 d, IMM v)) -{ - if (isconst(d)) { - set_const(d, live.state[d].val & v); - return; - } - - d = rmw(d); - - if(CHECK32(v)) { - AND_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK1, v); - AND_rrr(d, d, REG_WORK1); - } - - unlock2(d); -} -MENDFUNC(2,jnf_AND_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jnf_AND_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jnf_AND_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); AND_rrr(d, d, s); @@ -771,7 +748,7 @@ MIDFUNC(2,jnf_AND_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_AND_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_AND_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jff_AND_b_imm,(RW1 d, IM8 v)) { INIT_REG_b(d); @@ -791,9 +768,10 @@ MIDFUNC(2,jff_AND_b_imm,(RW1 d, IMM v)) ANDS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_AND_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jff_AND_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jff_AND_b,(RW1 d, RR1 s)) { @@ -820,11 +798,12 @@ MIDFUNC(2,jff_AND_b,(RW1 d, RR1 s)) ANDS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_AND_b,(RW1 d, RR1 s)) -MIDFUNC(2,jff_AND_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jff_AND_w_imm,(RW2 d, IM16 v)) { INIT_REG_w(d); @@ -838,9 +817,10 @@ MIDFUNC(2,jff_AND_w_imm,(RW2 d, IMM v)) ANDS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_AND_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jff_AND_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jff_AND_w,(RW2 d, RR2 s)) { @@ -861,38 +841,19 @@ MIDFUNC(2,jff_AND_w,(RW2 d, RR2 s)) ANDS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_AND_w,(RW2 d, RR2 s)) -MIDFUNC(2,jff_AND_l_imm,(RW4 d, IMM v)) -{ - d = rmw(d); - - MSR_CPSRf_i(0); - if(CHECK32(v)) { - ANDS_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK2, v); - ANDS_rrr(d, d, REG_WORK2); - } - - unlock2(d); -} -MENDFUNC(2,jff_AND_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jff_AND_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jff_AND_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); MSR_CPSRf_i(0); ANDS_rrr(d, d, s); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_AND_l,(RW4 d, RR4 s)) @@ -914,7 +875,7 @@ MENDFUNC(2,jff_AND_l,(RW4 d, RR4 s)) * imm version only called with 1 <= i <= 8 * */ -MIDFUNC(2,jff_ASL_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_ASL_b_imm,(RW1 d, IM8 i)) { if(i) d = rmw(d); @@ -923,30 +884,33 @@ MIDFUNC(2,jff_ASL_b_imm,(RW1 d, IMM i)) LSL_rri(REG_WORK3, d, 24); if (i) { - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rri(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rri(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } LSLS_rri(REG_WORK3, REG_WORK3, i); BIC_rri(d, d, 0xff); ORR_rrrLSRi(d, d, REG_WORK3, 24); + flags_carry_inverted = false; DUPLICACTE_CARRY } else { MSR_CPSRf_i(0); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASL_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_ASL_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_ASL_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_ASL_w_imm,(RW2 d, IM8 i)) { if(i) d = rmw(d); @@ -955,29 +919,33 @@ MIDFUNC(2,jff_ASL_w_imm,(RW2 d, IMM i)) LSL_rri(REG_WORK3, d, 16); if (i) { - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rri(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rri(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } LSLS_rri(REG_WORK3, REG_WORK3, i); PKHTB_rrrASRi(d, d, REG_WORK3, 16); + + flags_carry_inverted = false; DUPLICACTE_CARRY } else { MSR_CPSRf_i(0); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASL_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_ASL_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_ASL_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_ASL_l_imm,(RW4 d, IM8 i)) { if(i) d = rmw(d); @@ -985,26 +953,29 @@ MIDFUNC(2,jff_ASL_l_imm,(RW4 d, IMM i)) d = readreg(d); if (i) { - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rri(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, d, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rri(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, d, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } LSLS_rri(d, d, i); + flags_carry_inverted = false; DUPLICACTE_CARRY } else { MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASL_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_ASL_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jff_ASL_b_reg,(RW1 d, RR4 i)) { @@ -1013,26 +984,33 @@ MIDFUNC(2,jff_ASL_b_reg,(RW1 d, RR4 i)) int x = writereg(FLAGX); LSL_rri(REG_WORK3, d, 24); - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rrr(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rrr(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } ANDS_rri(REG_WORK2, i, 63); - BEQ_i(5); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + LSLS_rrr(REG_WORK3, REG_WORK3, REG_WORK2); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); BIC_rri(d, d, 0xff); ORR_rrrLSRi(d, d, REG_WORK3, 24); B_i(0); + + // no shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1046,25 +1024,32 @@ MIDFUNC(2,jff_ASL_w_reg,(RW2 d, RR4 i)) int x = writereg(FLAGX); LSL_rri(REG_WORK3, d, 16); - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rrr(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rrr(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, REG_WORK3, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } ANDS_rri(REG_WORK2, i, 63); - BEQ_i(4); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + LSLS_rrr(REG_WORK3, REG_WORK3, REG_WORK2); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); PKHTB_rrrASRi(d, d, REG_WORK3, 16); B_i(0); + + // no shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1077,24 +1062,31 @@ MIDFUNC(2,jff_ASL_l_reg,(RW4 d, RR4 i)) d = rmw(d); int x = writereg(FLAGX); - // Calculate V Flag - MOV_ri8RORi(REG_WORK2, 0x80, 8); - ASR_rrr(REG_WORK2, REG_WORK2, i); - ANDS_rrr(REG_WORK1, d, REG_WORK2); - CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); - MOV_ri(REG_WORK1, 0); - CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); - - MSR_CPSRf_r(REG_WORK1); // store V flag + if (needed_flags & FLAG_V) { + // Calculate V Flag + MOV_ri8RORi(REG_WORK2, 0x80, 8); + ASR_rrr(REG_WORK2, REG_WORK2, i); + ANDS_rrr(REG_WORK1, d, REG_WORK2); + CC_TEQ_rr(NATIVE_CC_NE, REG_WORK1, REG_WORK2); + MOV_ri(REG_WORK1, 0); + CC_MOV_ri(NATIVE_CC_NE, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); // store V flag + } ANDS_rri(REG_WORK2, i, 63); - BEQ_i(3); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + LSLS_rrr(d, d, REG_WORK2); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); B_i(0); + + // no shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(d, d); + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1117,11 +1109,6 @@ MENDFUNC(2,jff_ASL_l_reg,(RW4 d, RR4 i)) */ MIDFUNC(1,jnf_ASLW,(RW2 d)) { - if (isconst(d)) { - set_const(d, (live.state[d].val << 1) & 0xffff); - return; - } - d = rmw(d); LSL_rri(d, d, 1); @@ -1137,15 +1124,18 @@ MIDFUNC(1,jff_ASLW,(RW2 d)) MSR_CPSRf_i(0); LSLS_rri(d, d, 17); - MRS_CPSR(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) - - // Calculate V flag - CC_ORR_rri(NATIVE_CC_MI, REG_WORK1, REG_WORK1, ARM_V_FLAG); - CC_EOR_rri(NATIVE_CC_CS, REG_WORK1, REG_WORK1, ARM_V_FLAG); - MSR_CPSRf_r(REG_WORK1); + if (needed_flags & FLAG_V) { + MRS_CPSR(REG_WORK1); + // Calculate V flag + CC_ORR_rri(NATIVE_CC_MI, REG_WORK1, REG_WORK1, ARM_V_FLAG); + CC_EOR_rri(NATIVE_CC_CS, REG_WORK1, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); + } ASR_rri(d, d, 16); + flags_carry_inverted = false; + DUPLICACTE_CARRY + unlock2(d); } MENDFUNC(1,jff_ASLW,(RW2 d)) @@ -1164,10 +1154,8 @@ MENDFUNC(1,jff_ASLW,(RW2 d)) * V Set if the most significant bit is changed at any time during the shift operation. Cleared otherwise. Shift right -> always 0 * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. * - * imm version only called with 1 <= i <= 8 - * */ -MIDFUNC(2,jnf_ASR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jnf_ASR_b_imm,(RW1 d, IM8 i)) { if(i) { d = rmw(d); @@ -1185,9 +1173,9 @@ MIDFUNC(2,jnf_ASR_b_imm,(RW1 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ASR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jnf_ASR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jnf_ASR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jnf_ASR_w_imm,(RW2 d, IM8 i)) { if(i) { d = rmw(d); @@ -1198,9 +1186,9 @@ MIDFUNC(2,jnf_ASR_w_imm,(RW2 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ASR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jnf_ASR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jnf_ASR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jnf_ASR_l_imm,(RW4 d, IM8 i)) { if(i) { d = rmw(d); @@ -1210,9 +1198,9 @@ MIDFUNC(2,jnf_ASR_l_imm,(RW4 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ASR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jnf_ASR_l_imm,(RW4 d, IM8 i)) -MIDFUNC(2,jff_ASR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_ASR_b_imm,(RW1 d, IM8 i)) { if(i) d = rmw(d); @@ -1230,16 +1218,18 @@ MIDFUNC(2,jff_ASR_b_imm,(RW1 d, IMM i)) BIC_rri(d, d, 0xff); ORR_rrr(d, d, REG_WORK1); #endif + flags_carry_inverted = false; DUPLICACTE_CARRY } else { TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_ASR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_ASR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_ASR_w_imm,(RW2 d, IM8 i)) { if(i) d = rmw(d); @@ -1251,16 +1241,18 @@ MIDFUNC(2,jff_ASR_w_imm,(RW2 d, IMM i)) if (i) { ASRS_rri(REG_WORK1, REG_WORK1, i); PKHTB_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; DUPLICACTE_CARRY } else { TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_ASR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_ASR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_ASR_l_imm,(RW4 d, IM8 i)) { if(i) d = rmw(d); @@ -1270,17 +1262,24 @@ MIDFUNC(2,jff_ASR_l_imm,(RW4 d, IMM i)) MSR_CPSRf_i(0); if (i) { ASRS_rri(d, d, i); + flags_carry_inverted = false; DUPLICACTE_CARRY } else { TST_rr(d, d); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_ASR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_ASR_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jnf_ASR_b_reg,(RW1 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jnf_ASR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); @@ -1302,6 +1301,11 @@ MENDFUNC(2,jnf_ASR_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jnf_ASR_w_reg,(RW2 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jnf_ASR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); @@ -1317,6 +1321,11 @@ MENDFUNC(2,jnf_ASR_w_reg,(RW2 d, RR4 i)) MIDFUNC(2,jnf_ASR_l_reg,(RW4 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jnf_ASR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); @@ -1330,6 +1339,11 @@ MENDFUNC(2,jnf_ASR_l_reg,(RW4 d, RR4 i)) MIDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_ASR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); int x = writereg(FLAGX); @@ -1338,10 +1352,13 @@ MIDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) MSR_CPSRf_i(0); ANDS_rri(REG_WORK2, i, 63); BEQ_i(3); // No shift -> X flag unchanged + + // shift count > 0 ASRS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); B_i(0); + TST_rr(REG_WORK1, REG_WORK1); #ifdef ARMV6T2 @@ -1352,6 +1369,7 @@ MIDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK1); #endif + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1360,6 +1378,11 @@ MENDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jff_ASR_w_reg,(RW2 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_ASR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); int x = writereg(FLAGX); @@ -1368,13 +1391,17 @@ MIDFUNC(2,jff_ASR_w_reg,(RW2 d, RR4 i)) MSR_CPSRf_i(0); ANDS_rri(REG_WORK2, i, 63); BEQ_i(4); // No shift -> X flag unchanged + + // shift count > 0 ASRS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); PKHTB_rrr(d, d, REG_WORK1); B_i(0); + TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1383,6 +1410,11 @@ MENDFUNC(2,jff_ASR_w_reg,(RW2 d, RR4 i)) MIDFUNC(2,jff_ASR_l_reg,(RW4 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_ASR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + i = readreg(i); d = rmw(d); int x = writereg(FLAGX); @@ -1390,12 +1422,16 @@ MIDFUNC(2,jff_ASR_l_reg,(RW4 d, RR4 i)) MSR_CPSRf_i(0); ANDS_rri(REG_WORK1, i, 63); BEQ_i(3); // No shift -> X flag unchanged + + // shift count > 0 ASRS_rrr(d, d, REG_WORK1); MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); B_i(0); + TST_rr(d, d); + flags_carry_inverted = false; unlock2(x); unlock2(d); unlock2(i); @@ -1431,9 +1467,11 @@ MIDFUNC(1,jff_ASRW,(RW2 d)) { d = rmw(d); - SIGNED16_REG_2_REG(d, d); + SIGNED16_REG_2_REG(REG_WORK1, d); MSR_CPSRf_i(0); - ASRS_rri(d, d, 1); + ASRS_rri(d, REG_WORK1, 1); + + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); @@ -1449,36 +1487,28 @@ MENDFUNC(1,jff_ASRW,(RW2 d)) * * X Not affected. * N Not affected. - * Z Set if the bit tested was zero. Cleared otherwise. + * Z Set if the bit changed was zero. Cleared otherwise. * V Not affected. * C Not affected. * */ /* BCHG.B: target is never a register */ /* BCHG.L: target is always a register */ -MIDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IM8 s)) { - if(isconst(d)) { - set_const(d, live.state[d].val ^ (1 << s)); - return; - } d = rmw(d); EOR_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IM8 s)) { - if(isconst(d)) { - set_const(d, live.state[d].val ^ (1 << s)); - return; - } d = rmw(d); EOR_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jnf_BCHG_b,(RW1 d, RR4 s)) { @@ -1486,6 +1516,7 @@ MIDFUNC(2,jnf_BCHG_b,(RW1 d, RR4 s)) COMPCALL(jnf_BCHG_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = rmw(d); @@ -1517,7 +1548,7 @@ MIDFUNC(2,jnf_BCHG_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_BCHG_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_BCHG_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jff_BCHG_b_imm,(RW1 d, IM8 s)) { d = rmw(d); @@ -1537,9 +1568,9 @@ MIDFUNC(2,jff_BCHG_b_imm,(RW1 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BCHG_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jff_BCHG_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jff_BCHG_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jff_BCHG_l_imm,(RW4 d, IM8 s)) { d = rmw(d); @@ -1559,7 +1590,7 @@ MIDFUNC(2,jff_BCHG_l_imm,(RW4 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BCHG_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jff_BCHG_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jff_BCHG_b,(RW1 d, RR4 s)) { @@ -1567,6 +1598,7 @@ MIDFUNC(2,jff_BCHG_b,(RW1 d, RR4 s)) COMPCALL(jff_BCHG_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = rmw(d); @@ -1619,36 +1651,32 @@ MENDFUNC(2,jff_BCHG_l,(RW4 d, RR4 s)) * * X Not affected. * N Not affected. - * Z Set if the bit tested was zero. Cleared otherwise. + * Z Set if the bit cleared was zero. Cleared otherwise. * V Not affected. * C Not affected. * */ /* BCLR.B: target is never a register */ /* BCLR.L: target is always a register */ -MIDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IM8 s)) { - if(isconst(d)) { - set_const(d, live.state[d].val & ~(1 << s)); - return; - } d = rmw(d); BIC_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IM8 s)) { if(isconst(d)) { - set_const(d, live.state[d].val & ~(1 << s)); + live.state[d].val = live.state[d].val & ~(1 << s); return; } d = rmw(d); BIC_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jnf_BCLR_b,(RW1 d, RR4 s)) { @@ -1687,7 +1715,7 @@ MIDFUNC(2,jnf_BCLR_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_BCLR_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_BCLR_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jff_BCLR_b_imm,(RW1 d, IM8 s)) { d = rmw(d); @@ -1701,9 +1729,9 @@ MIDFUNC(2,jff_BCLR_b_imm,(RW1 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BCLR_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jff_BCLR_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jff_BCLR_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jff_BCLR_l_imm,(RW4 d, IM8 s)) { d = rmw(d); @@ -1717,7 +1745,7 @@ MIDFUNC(2,jff_BCLR_l_imm,(RW4 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BCLR_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jff_BCLR_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jff_BCLR_b,(RW1 d, RR4 s)) { @@ -1725,6 +1753,7 @@ MIDFUNC(2,jff_BCLR_b,(RW1 d, RR4 s)) COMPCALL(jff_BCLR_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = rmw(d); @@ -1777,37 +1806,28 @@ MENDFUNC(2,jff_BCLR_l,(RW4 d, RR4 s)) * * X Not affected. * N Not affected. - * Z Set if the bit tested was zero. Cleared otherwise. + * Z Set if the bit set was zero. Cleared otherwise. * V Not affected. * C Not affected. * */ /* BSET.B: target is never a register */ /* BSET.L: target is always a register */ -MIDFUNC(2,jnf_BSET_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jnf_BSET_b_imm,(RW1 d, IM8 s)) { - if(isconst(d)) { - set_const(d, live.state[d].val | (1 << s)); - return; - } d = rmw(d); ORR_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BSET_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jnf_BSET_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jnf_BSET_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jnf_BSET_l_imm,(RW4 d, IM8 s)) { - if(isconst(d)) { - set_const(d, live.state[d].val | (1 << s)); - return; - } - d = rmw(d); ORR_rri(d, d, (1 << s)); unlock2(d); } -MENDFUNC(2,jnf_BSET_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jnf_BSET_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jnf_BSET_b,(RW1 d, RR4 s)) { @@ -1815,6 +1835,7 @@ MIDFUNC(2,jnf_BSET_b,(RW1 d, RR4 s)) COMPCALL(jnf_BSET_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = rmw(d); @@ -1846,7 +1867,7 @@ MIDFUNC(2,jnf_BSET_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_BSET_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_BSET_b_imm,(RW1 d, IMM s)) +MIDFUNC(2,jff_BSET_b_imm,(RW1 d, IM8 s)) { d = rmw(d); @@ -1860,9 +1881,9 @@ MIDFUNC(2,jff_BSET_b_imm,(RW1 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BSET_b_imm,(RW1 d, IMM s)) +MENDFUNC(2,jff_BSET_b_imm,(RW1 d, IM8 s)) -MIDFUNC(2,jff_BSET_l_imm,(RW4 d, IMM s)) +MIDFUNC(2,jff_BSET_l_imm,(RW4 d, IM8 s)) { d = rmw(d); @@ -1876,7 +1897,7 @@ MIDFUNC(2,jff_BSET_l_imm,(RW4 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BSET_l_imm,(RW4 d, IMM s)) +MENDFUNC(2,jff_BSET_l_imm,(RW4 d, IM8 s)) MIDFUNC(2,jff_BSET_b,(RW1 d, RR4 s)) { @@ -1884,6 +1905,7 @@ MIDFUNC(2,jff_BSET_b,(RW1 d, RR4 s)) COMPCALL(jff_BSET_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = rmw(d); @@ -1943,7 +1965,7 @@ MENDFUNC(2,jff_BSET_l,(RW4 d, RR4 s)) */ /* BTST.B: target is never a register */ /* BTST.L: target is always a register */ -MIDFUNC(2,jff_BTST_b_imm,(RR1 d, IMM s)) +MIDFUNC(2,jff_BTST_b_imm,(RR1 d, IM8 s)) { d = readreg(d); @@ -1955,9 +1977,9 @@ MIDFUNC(2,jff_BTST_b_imm,(RR1 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BTST_b_imm,(RR1 d, IMM s)) +MENDFUNC(2,jff_BTST_b_imm,(RR1 d, IM8 s)) -MIDFUNC(2,jff_BTST_l_imm,(RR4 d, IMM s)) +MIDFUNC(2,jff_BTST_l_imm,(RR4 d, IM8 s)) { d = readreg(d); @@ -1969,7 +1991,7 @@ MIDFUNC(2,jff_BTST_l_imm,(RR4 d, IMM s)) unlock2(d); } -MENDFUNC(2,jff_BTST_l_imm,(RR4 d, IMM s)) +MENDFUNC(2,jff_BTST_l_imm,(RR4 d, IM8 s)) MIDFUNC(2,jff_BTST_b,(RR1 d, RR4 s)) { @@ -1977,6 +1999,7 @@ MIDFUNC(2,jff_BTST_b,(RR1 d, RR4 s)) COMPCALL(jff_BTST_b_imm)(d, live.state[s].val & 7); return; } + s = readreg(s); d = readreg(d); @@ -2040,10 +2063,6 @@ MENDFUNC(2,jff_BTST_l,(RR4 d, RR4 s)) */ MIDFUNC(1,jnf_CLR_b,(W1 d)) { - if(isconst(d)) { - set_const(d, live.state[d].val & 0xffffff00); - return; - } if(d >= 16) { set_const(d, 0); return; @@ -2056,21 +2075,13 @@ MENDFUNC(1,jnf_CLR_b,(W1 d)) MIDFUNC(1,jnf_CLR_w,(W2 d)) { - if(isconst(d)) { - set_const(d, live.state[d].val & 0xffff0000); - return; - } if(d >= 16) { set_const(d, 0); return; } INIT_WREG_w(d); - if(targetIsReg) { - BIC_rri(d, d, 0x00ff); - BIC_rri(d, d, 0xff00); - } else { - MOV_ri(d, 0); - } + BIC_rri(d, d, 0x00ff); + BIC_rri(d, d, 0xff00); unlock2(d); } MENDFUNC(1,jnf_CLR_w,(W2 d)) @@ -2084,10 +2095,7 @@ MENDFUNC(1,jnf_CLR_l,(W4 d)) MIDFUNC(1,jff_CLR_b,(W1 d)) { MSR_CPSRf_i(ARM_Z_FLAG); - if(isconst(d)) { - set_const(d, live.state[d].val & 0xffffff00); - return; - } + flags_carry_inverted = false; if(d >= 16) { set_const(d, 0); return; @@ -2101,21 +2109,14 @@ MENDFUNC(1,jff_CLR_b,(W1 d)) MIDFUNC(1,jff_CLR_w,(W2 d)) { MSR_CPSRf_i(ARM_Z_FLAG); - if(isconst(d)) { - set_const(d, live.state[d].val & 0xffff0000); - return; - } + flags_carry_inverted = false; if(d >= 16) { set_const(d, 0); return; } INIT_WREG_w(d); - if(targetIsReg) { - BIC_rri(d, d, 0x00ff); - BIC_rri(d, d, 0xff00); - } else { - MOV_ri(d, 0); - } + BIC_rri(d, d, 0x00ff); + BIC_rri(d, d, 0xff00); unlock2(d); } MENDFUNC(1,jff_CLR_w,(W2 d)) @@ -2123,6 +2124,7 @@ MENDFUNC(1,jff_CLR_w,(W2 d)) MIDFUNC(1,jff_CLR_l,(W4 d)) { MSR_CPSRf_i(ARM_Z_FLAG); + flags_carry_inverted = false; set_const(d, 0); } MENDFUNC(1,jff_CLR_l,(W4 d)) @@ -2142,31 +2144,32 @@ MENDFUNC(1,jff_CLR_l,(W4 d)) */ MIDFUNC(2,jff_CMP_b,(RR1 d, RR1 s)) { - INIT_RREGS_b(d, s); - - LSL_rri(REG_WORK1, d, 24); - CMP_rrLSLi(REG_WORK1, s, 24); + INIT_RREGS_b(d, s); + + LSL_rri(REG_WORK1, d, 24); + CMP_rrLSLi(REG_WORK1, s, 24); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); + EXIT_REGS(d,s); - EXIT_REGS(d,s); + flags_carry_inverted = true; } MENDFUNC(2,jff_CMP_b,(RR1 d, RR1 s)) MIDFUNC(2,jff_CMP_w,(RR2 d, RR2 s)) { - INIT_RREGS_w(d, s); + if (isconst(d) && isconst(s)) { + SIGNED16_IMM_2_REG(REG_WORK1, live.state[d].val & 0xff); + SIGNED16_IMM_2_REG(REG_WORK2, live.state[s].val & 0xff); + CMP_rr(REG_WORK1, REG_WORK2); + } else { + INIT_RREGS_w(d, s); - LSL_rri(REG_WORK1, d, 16); - CMP_rrLSLi(REG_WORK1, s, 16); + LSL_rri(REG_WORK1, d, 16); + CMP_rrLSLi(REG_WORK1, s, 16); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - - EXIT_REGS(d,s); + EXIT_REGS(d,s); + } + flags_carry_inverted = true; } MENDFUNC(2,jff_CMP_w,(RR2 d, RR2 s)) @@ -2176,10 +2179,7 @@ MIDFUNC(2,jff_CMP_l,(RR4 d, RR4 s)) CMP_rr(d, s); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - + flags_carry_inverted = true; EXIT_REGS(d,s); } MENDFUNC(2,jff_CMP_l,(RR4 d, RR4 s)) @@ -2199,16 +2199,20 @@ MENDFUNC(2,jff_CMP_l,(RR4 d, RR4 s)) */ MIDFUNC(2,jff_CMPA_w,(RR2 d, RR2 s)) { - INIT_RREGS_w(d, s); + if (isconst(s)) { + uae_u16 tmp = (uae_u16)(live.state[s].val & 0xffff); + d = readreg(d); + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + CMP_rr(d, REG_WORK1); + unlock2(d); + } else { + INIT_RREGS_w(d, s); + SIGNED16_REG_2_REG(REG_WORK2, s); + CMP_rr(d, REG_WORK2); + EXIT_REGS(d,s); + } - SIGNED16_REG_2_REG(REG_WORK2, s); - CMP_rr(d, REG_WORK2); - - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - - EXIT_REGS(d,s); + flags_carry_inverted = true; } MENDFUNC(2,jff_CMPA_w,(RR2 d, RR2 s)) @@ -2218,10 +2222,7 @@ MIDFUNC(2,jff_CMPA_l,(RR4 d, RR4 s)) CMP_rr(d, s); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - + flags_carry_inverted = true; EXIT_REGS(d,s); } MENDFUNC(2,jff_CMPA_l,(RR4 d, RR4 s)) @@ -2230,10 +2231,12 @@ MENDFUNC(2,jff_CMPA_l,(RR4 d, RR4 s)) * DBCC * */ -MIDFUNC(2,jff_DBCC,(RW4 d, IMM cc)) +MIDFUNC(2,jff_DBCC,(RW4 d, IM8 cc)) { d = rmw(d); + FIX_INVERTED_CARRY + // If cc true -> no branch, so we have to clear ARM_C_FLAG MOV_ri(REG_WORK1, ARM_C_FLAG); switch(cc) { @@ -2265,7 +2268,7 @@ MIDFUNC(2,jff_DBCC,(RW4 d, IMM cc)) unlock2(d); } -MENDFUNC(2,jff_DBCC,(RW4 d, IMM cc)) +MENDFUNC(2,jff_DBCC,(RW4 d, IM8 cc)) /* * DIVU @@ -2281,32 +2284,23 @@ MENDFUNC(2,jff_DBCC,(RW4 d, IMM cc)) MIDFUNC(2,jnf_DIVU,(RW4 d, RR4 s)) { - if (isconst(d) && isconst(s) && live.state[s].val != 0) { - uae_u32 newv = (uae_u32)live.state[d].val / (uae_u32)(uae_u16)live.state[s].val; - uae_u32 rem = (uae_u32)live.state[d].val % (uae_u32)(uae_u16)live.state[s].val; - set_const(d, (newv & 0xffff) | ((uae_u32)rem << 16)); - return; - } INIT_REGS_l(d, s); UNSIGNED16_REG_2_REG(REG_WORK3, s); TST_rr(REG_WORK3, REG_WORK3); - BNE_i(4); // src is not 0 + BNE_i(2); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); -#ifdef ARM_HAS_DIV - B_i(4); // end_of_op + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV UDIV_rrr(REG_WORK1, d, REG_WORK3); #else - B_i(10); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, REG_WORK3, 0); VCVTIuto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2322,38 +2316,37 @@ MIDFUNC(2,jnf_DIVU,(RW4 d, RR4 s)) // Here we have to calc remainder MLS_rrrr(REG_WORK2, REG_WORK1, REG_WORK3, d); PKHBT_rrrLSLi(d, REG_WORK1, REG_WORK2, 16); -// end_of_op + // end_of_op + write_jmp_target(branchadd, (uintptr)get_target()); EXIT_REGS(d, s); } MENDFUNC(2,jnf_DIVU,(RW4 d, R4 s)) MIDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) { + uae_u32* branchadd; INIT_REGS_l(d, s); UNSIGNED16_REG_2_REG(REG_WORK3, s); TST_rr(REG_WORK3, REG_WORK3); - BNE_i(6); // src is not 0 + BNE_i(4); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); // simplified flag handling for div0: set Z and V (for signed DIV: Z only) MOV_ri(REG_WORK1, ARM_Z_FLAG | ARM_V_FLAG); MSR_CPSRf_r(REG_WORK1); -#ifdef ARM_HAS_DIV - B_i(11); // end_of_op + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV UDIV_rrr(REG_WORK1, d, REG_WORK3); #else - B_i(17); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, REG_WORK3, 0); VCVTIuto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2378,8 +2371,10 @@ MIDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) MLS_rrrr(REG_WORK2, REG_WORK1, REG_WORK3, d); PKHBT_rrrLSLi(d, REG_WORK1, REG_WORK2, 16); -// end_of_op - + + // end_of_op + flags_carry_inverted = false; + write_jmp_target(branchadd, (uintptr)get_target()); EXIT_REGS(d, s); } MENDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) @@ -2400,34 +2395,24 @@ MENDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) MIDFUNC(2,jnf_DIVS,(RW4 d, RR4 s)) { - if (isconst(d) && isconst(s) && live.state[s].val != 0) { - uae_s32 newv = (uae_s32)live.state[d].val / (uae_s32)(uae_s16)live.state[s].val; - uae_u16 rem = (uae_s32)live.state[d].val % (uae_s32)(uae_s16)live.state[s].val; - if (((uae_s16)rem < 0) != ((uae_s32)live.state[d].val < 0)) - rem = -rem; - set_const(d, (newv & 0xffff) | ((uae_u32)rem << 16)); - return; - } + uae_u32* branchadd; INIT_REGS_l(d, s); SIGNED16_REG_2_REG(REG_WORK3, s); TST_rr(REG_WORK3, REG_WORK3); - BNE_i(4); // src is not 0 + BNE_i(2); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); -#ifdef ARM_HAS_DIV - B_i(12); // end_of_op + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV SDIV_rrr(REG_WORK1, d, REG_WORK3); #else - B_i(18); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, REG_WORK3, 0); VCVTIto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2454,38 +2439,37 @@ MIDFUNC(2,jnf_DIVS,(RW4 d, RR4 s)) CC_RSB_rri(NATIVE_CC_MI, REG_WORK2, REG_WORK2, 0); PKHBT_rrrLSLi(d, REG_WORK1, REG_WORK2, 16); -// end_of_op + // end_of_op + write_jmp_target(branchadd, (uintptr)get_target()); EXIT_REGS(d, s); } MENDFUNC(2,jnf_DIVS,(RW4 d, RR4 s)) MIDFUNC(2,jff_DIVS,(RW4 d, RR4 s)) { + uae_u32* branchadd; INIT_REGS_l(d, s); SIGNED16_REG_2_REG(REG_WORK3, s); TST_rr(REG_WORK3, REG_WORK3); - BNE_i(6); // src is not 0 + BNE_i(4); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); // simplified flag handling for div0: set Z and V (for signed DIV: Z only) MOV_ri(REG_WORK1, ARM_Z_FLAG); MSR_CPSRf_r(REG_WORK1); -#ifdef ARM_HAS_DIV - B_i(19); // end_of_op + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV SDIV_rrr(REG_WORK1, d, REG_WORK3); #else - B_i(25); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, REG_WORK3, 0); VCVTIto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2524,8 +2508,9 @@ MIDFUNC(2,jff_DIVS,(RW4 d, RR4 s)) PKHBT_rrrLSLi(d, REG_WORK1, REG_WORK2, 16); -// end_of_op - + // end_of_op + flags_carry_inverted = false; + write_jmp_target(branchadd, (uintptr)get_target()); EXIT_REGS(d, s); } MENDFUNC(2,jff_DIVS,(RW4 d, RR4 s)) @@ -2537,22 +2522,19 @@ MIDFUNC(3,jnf_DIVLU32,(RW4 d, RR4 s1, W4 rem)) rem = writereg(rem); TST_rr(s1, s1); - BNE_i(4); // src is not 0 + BNE_i(2); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); -#ifdef ARM_HAS_DIV - B_i(3); // end_of_op + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV UDIV_rrr(REG_WORK1, d, s1); #else - B_i(9); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, s1, 0); VCVTIuto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2568,7 +2550,8 @@ MIDFUNC(3,jnf_DIVLU32,(RW4 d, RR4 s1, W4 rem)) MOV_rr(d, REG_WORK1); // end_of_op - + write_jmp_target(branchadd, (uintptr)get_target()); + unlock2(rem); unlock2(d); unlock2(s1); @@ -2582,26 +2565,23 @@ MIDFUNC(3,jff_DIVLU32,(RW4 d, RR4 s1, W4 rem)) rem = writereg(rem); TST_rr(s1, s1); - BNE_i(6); // src is not 0 + BNE_i(4); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); // simplified flag handling for div0: set Z and V (for signed DIV: Z only) MOV_ri(REG_WORK1, ARM_Z_FLAG); MSR_CPSRf_r(REG_WORK1); -#ifdef ARM_HAS_DIV - B_i(7); // end_of_op + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV UDIV_rrr(REG_WORK1, d, s1); #else - B_i(13); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, s1, 0); VCVTIuto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2621,8 +2601,10 @@ MIDFUNC(3,jff_DIVLU32,(RW4 d, RR4 s1, W4 rem)) SUB_rrr(rem, d, REG_WORK2); MOV_rr(d, REG_WORK1); -// end_of_op + // end_of_op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(rem); unlock2(d); unlock2(s1); @@ -2636,22 +2618,19 @@ MIDFUNC(3,jnf_DIVLS32,(RW4 d, RR4 s1, W4 rem)) rem = writereg(rem); TST_rr(s1, s1); - BNE_i(4); // src is not 0 + BNE_i(2); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); -#ifdef ARM_HAS_DIV - B_i(5); // end_of_op + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV SDIV_rrr(REG_WORK1, d, s1); #else - B_i(11); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, s1, 0); VCVTIto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2669,7 +2648,8 @@ MIDFUNC(3,jnf_DIVLS32,(RW4 d, RR4 s1, W4 rem)) CC_RSB_rri(NATIVE_CC_MI, rem, rem, 0); MOV_rr(d, REG_WORK1); -// end_of_op + // end_of_op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(rem); unlock2(d); @@ -2684,22 +2664,19 @@ MIDFUNC(3,jff_DIVLS32,(RW4 d, RR4 s1, W4 rem)) rem = writereg(rem); TST_rr(s1, s1); - BNE_i(4); // src is not 0 + BNE_i(2); // src is not 0 // Signal exception 5 MOV_ri(REG_WORK1, 5); - MOVW_ri16(REG_WORK2, (uae_u32)(&jit_exception)); - MOVT_ri16(REG_WORK2, ((uae_u32)(&jit_exception)) >> 16); - STR_rR(REG_WORK1, REG_WORK2); -#ifdef ARM_HAS_DIV - B_i(3); // end_of_op + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_rRI(REG_WORK1, R_REGSTRUCT, idx); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op // src is not 0 +#ifdef ARM_HAS_DIV SDIV_rrr(REG_WORK1, d, s1); #else - B_i(9); // end_of_op - - // src is not 0 VMOVi_from_ARM_dr(SCRATCH_F64_1, d, 0); VMOVi_from_ARM_dr(SCRATCH_F64_2, s1, 0); VCVTIto64_ds(SCRATCH_F64_1, SCRATCH_F32_1); @@ -2717,8 +2694,10 @@ MIDFUNC(3,jff_DIVLS32,(RW4 d, RR4 s1, W4 rem)) CC_RSB_rri(NATIVE_CC_MI, rem, rem, 0); MOV_rr(d, REG_WORK1); -// end_of_op + // end_of_op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(rem); unlock2(d); unlock2(s1); @@ -2740,20 +2719,15 @@ MENDFUNC(3,jff_DIVLS32,(RW4 d, RR4 s1, W4 rem)) * C Always cleared. * */ -MIDFUNC(2,jnf_EOR_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jnf_EOR_b_imm,(RW1 d, IM8 v)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((live.state[d].val ^ v) & 0x000000ff)); - return; - } - INIT_REG_b(d); EOR_rri(d, d, (v & 0xff)); unlock2(d); } -MENDFUNC(2,jnf_EOR_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jnf_EOR_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jnf_EOR_b,(RW1 d, RR1 s)) { @@ -2781,35 +2755,21 @@ MIDFUNC(2,jnf_EOR_b,(RW1 d, RR1 s)) } MENDFUNC(2,jnf_EOR_b,(RW1 d, RR1 s)) -MIDFUNC(2,jnf_EOR_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jnf_EOR_w_imm,(RW2 d, IM16 v)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((live.state[d].val ^ v) & 0x0000ffff)); - return; - } - INIT_REG_w(d); - if(targetIsReg) { - if(CHECK32(v & 0xffff)) { - EOR_rri(REG_WORK1, d, (v & 0xffff)); - } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); - EOR_rrr(REG_WORK1, d, REG_WORK1); - } - PKHTB_rrr(d, d, REG_WORK1); - } else{ - if(CHECK32(v & 0xffff)) { - EOR_rri(d, d, (v & 0xffff)); - } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); - EOR_rrr(d, d, REG_WORK1); - } - } + if(CHECK32(v & 0xffff)) { + EOR_rri(REG_WORK1, d, (v & 0xffff)); + } else { + LOAD_U16(REG_WORK1, v & 0xffff); + EOR_rrr(REG_WORK1, d, REG_WORK1); + } + PKHTB_rrr(d, d, REG_WORK1); unlock2(d); } -MENDFUNC(2,jnf_EOR_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jnf_EOR_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jnf_EOR_w,(RW2 d, RR2 s)) { @@ -2820,44 +2780,15 @@ MIDFUNC(2,jnf_EOR_w,(RW2 d, RR2 s)) INIT_REGS_w(d, s); - if(targetIsReg) { - EOR_rrr(REG_WORK1, d, s); - PKHTB_rrr(d, d, REG_WORK1); - } else { - EOR_rrr(d, d, s); - } + EOR_rrr(REG_WORK1, d, s); + PKHTB_rrr(d, d, REG_WORK1); EXIT_REGS(d, s); } MENDFUNC(2,jnf_EOR_w,(RW2 d, RR2 s)) -MIDFUNC(2,jnf_EOR_l_imm,(RW4 d, IMM v)) -{ - if (isconst(d)) { - set_const(d, live.state[d].val ^ v); - return; - } - - d = rmw(d); - - if(CHECK32(v)) { - EOR_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK1, v); - EOR_rrr(d, d, REG_WORK1); - } - - unlock2(d); -} -MENDFUNC(2,jnf_EOR_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jnf_EOR_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jnf_EOR_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); EOR_rrr(d, d, s); @@ -2866,7 +2797,7 @@ MIDFUNC(2,jnf_EOR_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_EOR_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_EOR_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jff_EOR_b_imm,(RW1 d, IM8 v)) { INIT_REG_b(d); @@ -2886,9 +2817,10 @@ MIDFUNC(2,jff_EOR_b_imm,(RW1 d, IMM v)) EORS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_EOR_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jff_EOR_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jff_EOR_b,(RW1 d, RR1 s)) { @@ -2915,11 +2847,12 @@ MIDFUNC(2,jff_EOR_b,(RW1 d, RR1 s)) EORS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_EOR_b,(RW1 d, RR1 s)) -MIDFUNC(2,jff_EOR_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jff_EOR_w_imm,(RW2 d, IM16 v)) { INIT_REG_w(d); @@ -2933,9 +2866,10 @@ MIDFUNC(2,jff_EOR_w_imm,(RW2 d, IMM v)) EORS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_EOR_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jff_EOR_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jff_EOR_w,(RW2 d, RR2 s)) { @@ -2956,38 +2890,19 @@ MIDFUNC(2,jff_EOR_w,(RW2 d, RR2 s)) EORS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_EOR_w,(RW2 d, RR2 s)) -MIDFUNC(2,jff_EOR_l_imm,(RW4 d, IMM v)) -{ - d = rmw(d); - - MSR_CPSRf_i(0); - if(CHECK32(v)) { - EORS_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK2, v); - EORS_rrr(d, d, REG_WORK2); - } - - unlock2(d); -} -MENDFUNC(2,jff_EOR_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jff_EOR_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jff_EOR_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); MSR_CPSRf_i(0); EORS_rrr(d, d, s); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_EOR_l,(RW4 d, RR4 s)) @@ -3005,9 +2920,13 @@ MENDFUNC(2,jff_EOR_l,(RW4 d, RR4 s)) * C — Changed if bit 0 of immediate operand is one; unchanged otherwise. * */ -MIDFUNC(1,jff_EORSR,(IMM s, IMM x)) +MIDFUNC(2,jff_EORSR,(IM32 s, IM8 x)) { MRS_CPSR(REG_WORK1); + if(flags_carry_inverted) { + EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG);; + flags_carry_inverted = false; + } EOR_rri(REG_WORK1, REG_WORK1, s); MSR_CPSRf_r(REG_WORK1); @@ -3017,7 +2936,7 @@ MIDFUNC(1,jff_EORSR,(IMM s, IMM x)) unlock2(f); } } -MENDFUNC(1,jff_EORSR,(IMM s)) +MENDFUNC(2,jff_EORSR,(IM32 s, IM8 x)) /* * EXT @@ -3035,7 +2954,7 @@ MENDFUNC(1,jff_EORSR,(IMM s)) MIDFUNC(1,jnf_EXT_b,(RW4 d)) { if (isconst(d)) { - set_const(d, (uae_s32)(uae_s8)live.state[d].val); + live.state[d].val = (uae_s32)(uae_s8)live.state[d].val; return; } @@ -3050,7 +2969,7 @@ MENDFUNC(1,jnf_EXT_b,(RW4 d)) MIDFUNC(1,jnf_EXT_w,(RW4 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | (((uae_s32)(uae_s8)live.state[d].val) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | (((uae_s32)(uae_s8)live.state[d].val) & 0x0000ffff); return; } @@ -3066,7 +2985,7 @@ MENDFUNC(1,jnf_EXT_w,(RW4 d)) MIDFUNC(1,jnf_EXT_l,(RW4 d)) { if (isconst(d)) { - set_const(d, (uae_s32)(uae_s16)live.state[d].val); + live.state[d].val = (uae_s32)(uae_s16)live.state[d].val; return; } @@ -3092,6 +3011,7 @@ MIDFUNC(1,jff_EXT_b,(RW4 d)) MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_EXT_b,(RW4 d)) @@ -3100,7 +3020,7 @@ MIDFUNC(1,jff_EXT_w,(RW4 d)) { if (isconst(d)) { uae_u8 tmp = (uae_u8)live.state[d].val; - d = rmw(d); + d = writereg(d); SIGNED8_IMM_2_REG(REG_WORK1, tmp); } else { d = rmw(d); @@ -3111,6 +3031,7 @@ MIDFUNC(1,jff_EXT_w,(RW4 d)) TST_rr(REG_WORK1, REG_WORK1); PKHTB_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_EXT_w,(RW4 d)) @@ -3128,6 +3049,7 @@ MIDFUNC(1,jff_EXT_l,(RW4 d)) MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_EXT_l,(RW4 d)) @@ -3146,16 +3068,15 @@ MENDFUNC(1,jff_EXT_l,(RW4 d)) * V Always cleared. * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. * - * imm version only called with 1 <= i <= 8 - * */ -MIDFUNC(2,jnf_LSL_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jnf_LSL_b_imm,(RW1 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((live.state[d].val << i) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val << i) & 0x000000ff); return; } + INIT_REG_b(d); LSL_rri(REG_WORK1, d, i); @@ -3170,15 +3091,16 @@ MIDFUNC(2,jnf_LSL_b_imm,(RW1 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSL_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jnf_LSL_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jnf_LSL_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jnf_LSL_w_imm,(RW2 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((live.state[d].val << i) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val << i) & 0x0000ffff); return; } + INIT_REG_w(d); LSL_rri(REG_WORK1, d, i); @@ -3187,15 +3109,16 @@ MIDFUNC(2,jnf_LSL_w_imm,(RW2 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSL_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jnf_LSL_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jnf_LSL_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jnf_LSL_l_imm,(RW4 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, live.state[d].val << i); + live.state[d].val = live.state[d].val << i; return; } + d = rmw(d); LSL_rri(d, d, i); @@ -3203,14 +3126,15 @@ MIDFUNC(2,jnf_LSL_l_imm,(RW4 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSL_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jnf_LSL_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jnf_LSL_b_reg,(RW1 d, RR4 i)) { if (isconst(i)) { - COMPCALL(jnf_LSL_b_imm)(d, live.state[i].val & 15); + COMPCALL(jnf_LSL_b_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_b(d, i); AND_rri(REG_WORK1, i, 63); @@ -3230,9 +3154,10 @@ MENDFUNC(2,jnf_LSL_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jnf_LSL_w_reg,(RW2 d, RR4 i)) { if (isconst(i)) { - COMPCALL(jnf_LSL_w_imm)(d, live.state[i].val & 31); + COMPCALL(jnf_LSL_w_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_w(d, i); AND_rri(REG_WORK1, i, 63); @@ -3249,9 +3174,10 @@ MIDFUNC(2,jnf_LSL_l_reg,(RW4 d, RR4 i)) if(i > 31) set_const(d, 0); else - COMPCALL(jnf_LSL_l_imm)(d, live.state[i].val & 31); + COMPCALL(jnf_LSL_l_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_l(d, i); AND_rri(REG_WORK1, i, 63); @@ -3261,128 +3187,183 @@ MIDFUNC(2,jnf_LSL_l_reg,(RW4 d, RR4 i)) } MENDFUNC(2,jnf_LSL_l_reg,(RW4 d, RR4 i)) -MIDFUNC(2,jff_LSL_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_LSL_b_imm,(RW1 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - - MSR_CPSRf_i(0); - if (i) { - LSLS_rri(REG_WORK3, d, i + 24); + d = rmw(d); + if(i > 8) { + MSR_CPSRf_i(ARM_Z_FLAG); + BIC_rri(d, d, 0xff); + } else { + MSR_CPSRf_i(0); + if(i == 8) { + LSL_rri(REG_WORK3, d, i); + LSLS_rri(REG_WORK3, REG_WORK3, 24); + } else + LSLS_rri(REG_WORK3, d, i + 24); + + BIC_rri(d, d, 0xff); + ORR_rrrLSRi(d, d, REG_WORK3, 24); + } + flags_carry_inverted = false; DUPLICACTE_CARRY - BIC_rri(d, d, 0xff); - ORR_rrrLSRi(d, d, REG_WORK3, 24); } else { + d = readreg(d); + MSR_CPSRf_i(0); LSL_rri(REG_WORK3, d, 24); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_LSL_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_LSL_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_LSL_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_LSL_w_imm,(RW2 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - - MSR_CPSRf_i(0); - if (i) { - LSLS_rri(REG_WORK3, d, i + 16); - PKHTB_rrrASRi(d, d, REG_WORK3, 16); + if(i > 16) { + MSR_CPSRf_i(ARM_Z_FLAG); + BIC_rri(d, d, 0x00ff); + BIC_rri(d, d, 0xff00); + } else { + MSR_CPSRf_i(0); + d = rmw(d); + if(i == 16) { + LSL_rri(REG_WORK3, d, i); + LSLS_rri(REG_WORK3, REG_WORK3, 16); + } else + LSLS_rri(REG_WORK3, d, i + 16); + PKHTB_rrrASRi(d, d, REG_WORK3, 16); + } + flags_carry_inverted = false; DUPLICACTE_CARRY } else { + d = readreg(d); + MSR_CPSRf_i(0); LSL_rri(REG_WORK3, d, 16); TST_rr(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_LSL_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_LSL_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_LSL_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_LSL_l_imm,(RW4 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - - MSR_CPSRf_i(0); if (i) { - LSLS_rri(d, d, i); + if(i > 32) { + MSR_CPSRf_i(ARM_Z_FLAG); + set_const(d, 0); + } else { + d = rmw(d); + MSR_CPSRf_i(0); + if(i == 32) { + LSL_rri(d, d, 16); + LSLS_rri(d, d, 16); + } else + LSLS_rri(d, d, i); + unlock2(d); + } + flags_carry_inverted = false; DUPLICACTE_CARRY } else { + d = readreg(d); + MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; + unlock2(d); } - - unlock2(d); } -MENDFUNC(2,jff_LSL_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_LSL_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jff_LSL_b_reg,(RW1 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSL_b_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_b(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); LSL_rri(REG_WORK3, d, 24); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(5); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + + // shift count > 0 LSLS_rrr(REG_WORK3, REG_WORK3, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); BIC_rri(d, d, 0xff); ORR_rrrLSRi(d, d, REG_WORK3, 24); + + flags_carry_inverted = false; + DUPLICACTE_CARRY B_i(0); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(REG_WORK3, REG_WORK3); - unlock2(x); EXIT_REGS(d, i); } MENDFUNC(2,jff_LSL_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jff_LSL_w_reg,(RW2 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSL_w_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_w(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); LSL_rri(REG_WORK3, d, 16); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(4); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + LSLS_rrr(REG_WORK3, REG_WORK3, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); PKHTB_rrrASRi(d, d, REG_WORK3, 16); + + flags_carry_inverted = false; + DUPLICACTE_CARRY B_i(0); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(REG_WORK3, REG_WORK3); - unlock2(x); EXIT_REGS(d, i); } MENDFUNC(2,jff_LSL_w_reg,(RW2 d, RR4 i)) MIDFUNC(2,jff_LSL_l_reg,(RW4 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSL_l_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_l(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(3); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + LSLS_rrr(d, d, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); + + flags_carry_inverted = false; + DUPLICACTE_CARRY B_i(0); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(d, d); - unlock2(x); EXIT_REGS(d, i); } MENDFUNC(2,jff_LSL_l_reg,(RW4 d, RR4 i)) @@ -3404,7 +3385,7 @@ MENDFUNC(2,jff_LSL_l_reg,(RW4 d, RR4 i)) MIDFUNC(1,jnf_LSLW,(RW2 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val << 1) & 0xffff); + live.state[d].val = (live.state[d].val << 1) & 0xffff; return; } @@ -3423,6 +3404,8 @@ MIDFUNC(1,jff_LSLW,(RW2 d)) MSR_CPSRf_i(0); LSLS_rri(d, d, 17); LSR_rri(d, d, 16); + + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); @@ -3443,16 +3426,15 @@ MENDFUNC(1,jff_LSLW,(RW2 d)) * V Always cleared. * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. * - * imm version only called with 1 <= i <= 8 - * */ -MIDFUNC(2,jnf_LSR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jnf_LSR_b_imm,(RW1 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((live.state[d].val >> i) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val & 0xff) >> i); return; } + INIT_REG_b(d); UNSIGNED8_REG_2_REG(REG_WORK1, d); @@ -3468,15 +3450,16 @@ MIDFUNC(2,jnf_LSR_b_imm,(RW1 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jnf_LSR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jnf_LSR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jnf_LSR_w_imm,(RW2 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((live.state[d].val >> i) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val & 0x0000ffff) >> i); return; } + INIT_REG_w(d); UNSIGNED16_REG_2_REG(REG_WORK1, d); @@ -3485,15 +3468,16 @@ MIDFUNC(2,jnf_LSR_w_imm,(RW2 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jnf_LSR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jnf_LSR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jnf_LSR_l_imm,(RW4 d, IM8 i)) { if(i) { if (isconst(d)) { - set_const(d, live.state[d].val >> i); + live.state[d].val = live.state[d].val >> i; return; } + d = rmw(d); LSR_rri(d, d, i); @@ -3501,81 +3485,104 @@ MIDFUNC(2,jnf_LSR_l_imm,(RW4 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_LSR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jnf_LSR_l_imm,(RW4 d, IM8 i)) -MIDFUNC(2,jff_LSR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_LSR_b_imm,(RW1 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - - UNSIGNED8_REG_2_REG(REG_WORK1, d); - MSR_CPSRf_i(0); if (i) { - LSRS_rri(REG_WORK1, REG_WORK1, i); + d = rmw(d); + if(i > 8) { + MSR_CPSRf_i(ARM_Z_FLAG); + BIC_rri(d, d, 0xff); + } else { + MSR_CPSRf_i(0); + UNSIGNED8_REG_2_REG(REG_WORK1, d); + LSRS_rri(REG_WORK1, REG_WORK1, i); #ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); + BFI_rrii(d, REG_WORK1, 0, 7); #else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); #endif + } + flags_carry_inverted = false; DUPLICACTE_CARRY } else { + d = readreg(d); + SIGNED8_REG_2_REG(REG_WORK1, d); + MSR_CPSRf_i(0); TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_LSR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_LSR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_LSR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_LSR_w_imm,(RW2 d, IM8 i)) { - if(i) + if (i) { d = rmw(d); - else - d = readreg(d); - - UNSIGNED16_REG_2_REG(REG_WORK1, d); - MSR_CPSRf_i(0); - if (i) { - LSRS_rri(REG_WORK1, REG_WORK1, i); - PKHTB_rrr(d, d, REG_WORK1); + if(i > 16) { + MSR_CPSRf_i(ARM_Z_FLAG); + BIC_rri(d, d, 0x00ff); + BIC_rri(d, d, 0xff00); + } else { + MSR_CPSRf_i(0); + UNSIGNED16_REG_2_REG(REG_WORK1, d); + LSRS_rri(REG_WORK1, REG_WORK1, i); + PKHTB_rrr(d, d, REG_WORK1); + } + flags_carry_inverted = false; DUPLICACTE_CARRY } else { + d = readreg(d); + SIGNED16_REG_2_REG(REG_WORK1, d); + MSR_CPSRf_i(0); TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } unlock2(d); } -MENDFUNC(2,jff_LSR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_LSR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_LSR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_LSR_l_imm,(RW4 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - - MSR_CPSRf_i(0); if (i) { - LSRS_rri(d, d, i); + if(i > 32) { + MSR_CPSRf_i(ARM_Z_FLAG); + set_const(d, 0); + } else { + d = rmw(d); + MSR_CPSRf_i(0); + if(i == 32) { + LSR_rri(d, d, 16); + LSRS_rri(d, d, 16); + } else + LSRS_rri(d, d, i); + unlock2(d); + } + flags_carry_inverted = false; DUPLICACTE_CARRY } else { + d = readreg(d); + MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; + unlock2(d); } - - unlock2(d); } -MENDFUNC(2,jff_LSR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_LSR_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jnf_LSR_b_reg,(RW1 d, RR4 i)) { if (isconst(i)) { - COMPCALL(jnf_LSR_b_imm)(d, live.state[i].val & 15); + COMPCALL(jnf_LSR_b_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_b(d, i); UNSIGNED8_REG_2_REG(REG_WORK1, d); @@ -3596,9 +3603,10 @@ MENDFUNC(2,jnf_LSR_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jnf_LSR_w_reg,(RW2 d, RR4 i)) { if (isconst(i)) { - COMPCALL(jnf_LSR_w_imm)(d, live.state[i].val & 31); + COMPCALL(jnf_LSR_w_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_w(d, i); UNSIGNED16_REG_2_REG(REG_WORK1, d); @@ -3616,9 +3624,10 @@ MIDFUNC(2,jnf_LSR_l_reg,(RW4 d, RR4 i)) if(i > 31) set_const(d, 0); else - COMPCALL(jnf_LSR_l_imm)(d, live.state[i].val & 31); + COMPCALL(jnf_LSR_l_imm)(d, live.state[i].val & 0x3f); return; } + INIT_REGS_l(d, i); AND_rri(REG_WORK1, i, 63); @@ -3630,20 +3639,20 @@ MENDFUNC(2,jnf_LSR_l_reg,(RW4 d, RR4 i)) MIDFUNC(2,jff_LSR_b_reg,(RW1 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_b(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(4); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + AND_rri(REG_WORK2, d, 0xff); // Shift count is not 0 -> unsigned required LSRS_rrr(REG_WORK2, REG_WORK2, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); - B_i(1); - SIGNED8_REG_2_REG(REG_WORK2, d); // Make sure, sign is in MSB if shift count is 0 (to get correct N flag) - TST_rr(REG_WORK2, REG_WORK2); - #ifdef ARMV6T2 BFI_rrii(d, REG_WORK2, 0, 7); #else @@ -3652,48 +3661,77 @@ MIDFUNC(2,jff_LSR_b_reg,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK2); #endif - unlock2(x); + flags_carry_inverted = false; + DUPLICACTE_CARRY + + B_i(1); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + SIGNED8_REG_2_REG(REG_WORK2, d); // Make sure, sign is in MSB if shift count is 0 (to get correct N flag) + TST_rr(REG_WORK2, REG_WORK2); + EXIT_REGS(d, i); } MENDFUNC(2,jff_LSR_b_reg,(RW1 d, RR4 i)) MIDFUNC(2,jff_LSR_w_reg,(RW2 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_w(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(5); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + UXTH_rr(REG_WORK2, d); // Shift count is not 0 -> unsigned required LSRS_rrr(REG_WORK2, REG_WORK2, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); PKHTB_rrr(d, d, REG_WORK2); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + B_i(1); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); SIGNED16_REG_2_REG(REG_WORK2, d); // Make sure, sign is in MSB if shift count is 0 (to get correct N flag) TST_rr(REG_WORK2, REG_WORK2); - unlock2(x); EXIT_REGS(d, i); } MENDFUNC(2,jff_LSR_w_reg,(RW2 d, RR4 i)) MIDFUNC(2,jff_LSR_l_reg,(RW4 d, RR4 i)) { + if (isconst(i)) { + COMPCALL(jff_LSR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + INIT_REGS_l(d, i); - int x = writereg(FLAGX); MSR_CPSRf_i(0); ANDS_rri(REG_WORK1, i, 63); - BEQ_i(3); // No shift -> X flag unchanged + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + LSRS_rrr(d, d, REG_WORK1); - MOV_ri(x, 1); - CC_MOV_ri(NATIVE_CC_CC, x, 0); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + B_i(0); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); TST_rr(d, d); - unlock2(x); EXIT_REGS(d, i); } MENDFUNC(2,jff_LSR_l_reg,(RW4 d, RR4 i)) @@ -3715,10 +3753,10 @@ MENDFUNC(2,jff_LSR_l_reg,(RW4 d, RR4 i)) MIDFUNC(1,jnf_LSRW,(RW2 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val >> 1) & 0xffff); + live.state[d].val = ((live.state[d].val & 0xffff) >> 1); return; } - + d = rmw(d); UNSIGNED16_REG_2_REG(d, d); @@ -3735,6 +3773,7 @@ MIDFUNC(1,jff_LSRW,(RW2 d)) UNSIGNED16_REG_2_REG(d, d); MSR_CPSRf_i(0); LSRS_rri(d, d, 1); + flags_carry_inverted = false; DUPLICACTE_CARRY unlock2(d); @@ -3754,12 +3793,13 @@ MENDFUNC(1,jff_LSRW,(RW2 d)) * C Always cleared. * */ -MIDFUNC(2,jnf_MOVE_b_imm,(W1 d, IMM s)) +MIDFUNC(2,jnf_MOVE_b_imm,(W1 d, IM8 s)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | (s & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | (s & 0x000000ff); return; } + d = rmw(d); MOV_ri(REG_WORK1, s & 0xff); @@ -3773,35 +3813,26 @@ MIDFUNC(2,jnf_MOVE_b_imm,(W1 d, IMM s)) unlock2(d); } -MENDFUNC(2,jnf_MOVE_b_imm,(W1 d, IMM s)) +MENDFUNC(2,jnf_MOVE_b_imm,(W1 d, IM8 s)) -MIDFUNC(2,jnf_MOVE_w_imm,(W2 d, IMM s)) +MIDFUNC(2,jnf_MOVE_w_imm,(W2 d, IM16 s)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | (s & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | (s & 0x0000ffff); return; } + d = rmw(d); - UNSIGNED16_IMM_2_REG(REG_WORK1, s & 0xffff); + LOAD_U16(REG_WORK1, s & 0xffff); PKHTB_rrr(d, d, REG_WORK1); unlock2(d); } -MENDFUNC(2,jnf_MOVE_w_imm,(W2 d, IMM s)) - -MIDFUNC(2,jnf_MOVE_l_imm,(W4 d, IMM s)) -{ - set_const(d, s); -} -MENDFUNC(2,jnf_MOVE_l_imm,(W4 d, IMM s)) +MENDFUNC(2,jnf_MOVE_w_imm,(W2 d, IM16 s)) MIDFUNC(2,jnf_MOVE_b,(W1 d, RR1 s)) { - if(d >= 16) { - mov_l_rr(d, s); - return; - } if(s == d) return; if (isconst(s)) { @@ -3825,10 +3856,6 @@ MENDFUNC(2,jnf_MOVE_b,(W1 d, RR1 s)) MIDFUNC(2,jnf_MOVE_w,(W2 d, RR2 s)) { - if(d >= 16) { - mov_l_rr(d, s); - return; - } if(s == d) return; if (isconst(s)) { @@ -3850,7 +3877,7 @@ MIDFUNC(2,jnf_MOVE_l,(W4 d, RR4 s)) } MENDFUNC(2,jnf_MOVE_l,(W4 d, RR4 s)) -MIDFUNC(2,jff_MOVE_b_imm,(W1 d, IMM s)) +MIDFUNC(2,jff_MOVE_b_imm,(W1 d, IM8 s)) { d = rmw(d); @@ -3868,11 +3895,12 @@ MIDFUNC(2,jff_MOVE_b_imm,(W1 d, IMM s)) ORR_rrr(d, d, REG_WORK2); #endif + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_MOVE_b_imm,(W1 d, IMM s)) +MENDFUNC(2,jff_MOVE_b_imm,(W1 d, IM8 s)) -MIDFUNC(2,jff_MOVE_w_imm,(W2 d, IMM s)) +MIDFUNC(2,jff_MOVE_w_imm,(W2 d, IM16 s)) { d = rmw(d); @@ -3881,21 +3909,23 @@ MIDFUNC(2,jff_MOVE_w_imm,(W2 d, IMM s)) TST_rr(REG_WORK1, REG_WORK1); PKHTB_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_MOVE_w_imm,(W2 d, IMM s)) +MENDFUNC(2,jff_MOVE_w_imm,(W2 d, IM16 s)) -MIDFUNC(2,jff_MOVE_l_imm,(W4 d, IMM s)) +MIDFUNC(2,jff_MOVE_l_imm,(W4 d, IM32 s)) { d = writereg(d); - compemu_raw_mov_l_ri(d, s); + LOAD_U32(d, s); MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_MOVE_l_imm,(W4 d, IMM s)) +MENDFUNC(2,jff_MOVE_l_imm,(W4 d, IM32 s)) MIDFUNC(2,jff_MOVE_b,(W1 d, RR1 s)) { @@ -3925,6 +3955,7 @@ MIDFUNC(2,jff_MOVE_b,(W1 d, RR1 s)) #endif } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MOVE_b,(W1 d, RR1 s)) @@ -3950,6 +3981,7 @@ MIDFUNC(2,jff_MOVE_w,(W2 d, RR2 s)) if(!s_is_d) PKHTB_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MOVE_w,(W2 d, RR2 s)) @@ -3963,15 +3995,16 @@ MIDFUNC(2,jff_MOVE_l,(W4 d, RR4 s)) int s_is_d = (s == d); s = readreg(s); - if(!s_is_d) - d = writereg(d); MSR_CPSRf_i(0); - if(!s_is_d) + if(!s_is_d) { + d = writereg(d); MOVS_rr(d, s); - else + } else { TST_rr(s, s); - + } + + flags_carry_inverted = false; if(!s_is_d) unlock2(d); unlock2(s); @@ -3984,7 +4017,7 @@ MENDFUNC(2,jff_MOVE_l,(W4 d, RR4 s)) * Flags: Not affected. * */ -MIDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IMM offset)) +MIDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IM8 offset)) { s = readreg(s); d = writereg(d); @@ -3996,9 +4029,9 @@ MIDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IMM offset)) unlock2(d); unlock2(s); } -MENDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IMM offset)) +MENDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IM8 offset)) -MIDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IMM offset)) +MIDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IM8 offset)) { s = readreg(s); d = writereg(d); @@ -4009,7 +4042,7 @@ MIDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IMM offset)) unlock2(d); unlock2(s); } -MENDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IMM offset)) +MENDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IM8 offset)) /* * MVMLE @@ -4017,7 +4050,7 @@ MENDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IMM offset)) * Flags: Not affected. * */ -MIDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IMM offset)) +MIDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IM8 offset)) { s = readreg(s); d = readreg(d); @@ -4031,9 +4064,9 @@ MIDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IMM offset)) unlock2(d); unlock2(s); } -MENDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IMM offset)) +MENDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IM8 offset)) -MIDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IMM offset)) +MIDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IM8 offset)) { s = readreg(s); d = readreg(d); @@ -4047,7 +4080,7 @@ MIDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IMM offset)) unlock2(d); unlock2(s); } -MENDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IMM offset)) +MENDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IM8 offset)) /* * MOVE16 @@ -4060,33 +4093,33 @@ MIDFUNC(2,jnf_MOVE16,(RR4 d, RR4 s)) s = readreg(s); d = readreg(d); - PUSH_REGS((1 << s) | (1 << d)); + PUSH_REGS((1 << d)); - BIC_rri(s, s, 0x0000000F); + BIC_rri(REG_WORK3, s, 0x0000000F); BIC_rri(d, d, 0x0000000F); - ADD_rrr(s, s, R_MEMSTART); + ADD_rrr(REG_WORK3, REG_WORK3, R_MEMSTART); ADD_rrr(d, d, R_MEMSTART); #ifdef ARMV6T2 - LDRD_rR(REG_WORK1, s); + LDRD_rR(REG_WORK1, REG_WORK3); STRD_rR(REG_WORK1, d); - LDRD_rRI(REG_WORK1, s, 8); + LDRD_rRI(REG_WORK1, REG_WORK3, 8); STRD_rRI(REG_WORK1, d, 8); #else - LDR_rR(REG_WORK1, s); - LDR_rRI(REG_WORK2, s, 4); + LDR_rR(REG_WORK1, REG_WORK3); + LDR_rRI(REG_WORK2, REG_WORK3, 4); STR_rR(REG_WORK1, d); STR_rRI(REG_WORK2, d, 4); - LDR_rRI(REG_WORK1, s, 8); - LDR_rRI(REG_WORK2, s, 12); + LDR_rRI(REG_WORK1, REG_WORK3, 8); + LDR_rRI(REG_WORK2, REG_WORK3, 12); STR_rRI(REG_WORK1, d, 8); STR_rRI(REG_WORK2, d, 12); #endif - POP_REGS((1 << s) | (1 << d)); + POP_REGS((1 << d)); unlock2(d); unlock2(s); @@ -4104,6 +4137,11 @@ MENDFUNC(2,jnf_MOVE16,(RR4 d, RR4 s)) */ MIDFUNC(2,jnf_MOVEA_w,(W4 d, RR2 s)) { + if (isconst(s)) { + set_const(d, (uae_s32)(uae_s16)live.state[s].val); + return; + } + INIT_REGS_l(d, s); SIGNED16_REG_2_REG(d, s); @@ -4145,12 +4183,13 @@ MIDFUNC(2,jff_MULS,(RW4 d, RR4 s)) { INIT_REGS_l(d, s); - SIGN_EXTEND_16_REG_2_REG(d, d); - SIGN_EXTEND_16_REG_2_REG(REG_WORK1, s); + SIGNED16_REG_2_REG(d, d); + SIGNED16_REG_2_REG(REG_WORK1, s); MSR_CPSRf_i(0); MULS_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MULS,(RW4 d, RR4 s)) @@ -4170,13 +4209,15 @@ MIDFUNC(2,jff_MULS32,(RW4 d, RR4 s)) INIT_REGS_l(d, s); MSR_CPSRf_i(0); - // L, H, SMULLS_rrrr(d, REG_WORK2, d, s); - MRS_CPSR(REG_WORK1); - TEQ_rrASRi(REG_WORK2, d, 31); - CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); - MSR_CPSRf_r(REG_WORK1); + if (needed_flags & FLAG_V) { + MRS_CPSR(REG_WORK1); + TEQ_rrASRi(REG_WORK2, d, 31); + CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); + } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MULS32,(RW4 d, RR4 s)) @@ -4186,7 +4227,6 @@ MIDFUNC(2,jnf_MULS64,(RW4 d, RW4 s)) s = rmw(s); d = rmw(d); - // L, H, SMULL_rrrr(d, s, d, s); unlock2(s); @@ -4200,13 +4240,16 @@ MIDFUNC(2,jff_MULS64,(RW4 d, RW4 s)) d = rmw(d); MSR_CPSRf_i(0); - // L, H, SMULLS_rrrr(d, s, d, s); - MRS_CPSR(REG_WORK1); - TEQ_rrASRi(s, d, 31); - CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); - MSR_CPSRf_r(REG_WORK1); + if (needed_flags & FLAG_V) { + MRS_CPSR(REG_WORK1); + TEQ_rrASRi(s, d, 31); + CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); + } + + flags_carry_inverted = false; unlock2(s); unlock2(d); } @@ -4227,11 +4270,20 @@ MENDFUNC(2,jff_MULS64,(RW4 d, RW4 s)) */ MIDFUNC(2,jnf_MULU,(RW4 d, RR4 s)) { + if (isconst(s)) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK1, tmp); + UNSIGNED16_REG_2_REG(d, d); + MUL_rrr(d, d, REG_WORK1); + unlock2(d); + return; + } + INIT_REGS_l(d, s); - ZERO_EXTEND_16_REG_2_REG(d, d); - ZERO_EXTEND_16_REG_2_REG(REG_WORK1, s); - + UNSIGNED16_REG_2_REG(d, d); + UNSIGNED16_REG_2_REG(REG_WORK1, s); MUL_rrr(d, d, REG_WORK1); EXIT_REGS(d, s); @@ -4240,14 +4292,26 @@ MENDFUNC(2,jnf_MULU,(RW4 d, RR4 s)) MIDFUNC(2,jff_MULU,(RW4 d, RR4 s)) { + if (isconst(s)) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK1, tmp); + UNSIGNED16_REG_2_REG(d, d); + MSR_CPSRf_i(0); + MULS_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; + unlock2(d); + return; + } + INIT_REGS_l(d, s); - ZERO_EXTEND_16_REG_2_REG(d, d); - ZERO_EXTEND_16_REG_2_REG(REG_WORK1, s); - + UNSIGNED16_REG_2_REG(d, d); + UNSIGNED16_REG_2_REG(REG_WORK1, s); MSR_CPSRf_i(0); MULS_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MULU,(RW4 d, RR4 s)) @@ -4266,14 +4330,17 @@ MIDFUNC(2,jff_MULU32,(RW4 d, RR4 s)) { INIT_REGS_l(d, s); - // L, H, MSR_CPSRf_i(0); UMULLS_rrrr(d, REG_WORK2, d, s); - MRS_CPSR(REG_WORK1); - TST_rr(REG_WORK2, REG_WORK2); - CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); - MSR_CPSRf_r(REG_WORK1); + if (needed_flags & FLAG_V) { + MRS_CPSR(REG_WORK1); + TST_rr(REG_WORK2, REG_WORK2); + CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); + } + + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_MULU32,(RW4 d, RR4 s)) @@ -4283,7 +4350,6 @@ MIDFUNC(2,jnf_MULU64,(RW4 d, RW4 s)) s = rmw(s); d = rmw(d); - // L, H, UMULL_rrrr(d, s, d, s); unlock2(s); @@ -4296,14 +4362,17 @@ MIDFUNC(2,jff_MULU64,(RW4 d, RW4 s)) s = rmw(s); d = rmw(d); - // L, H, MSR_CPSRf_i(0); UMULLS_rrrr(d, s, d, s); - MRS_CPSR(REG_WORK1); - TST_rr(s, s); - CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); - MSR_CPSRf_r(REG_WORK1); + if (needed_flags & FLAG_V) { + MRS_CPSR(REG_WORK1); + TST_rr(s, s); + CC_ORR_rri(NATIVE_CC_NE, REG_WORK1, REG_WORK1, ARM_V_FLAG); + MSR_CPSRf_r(REG_WORK1); + } + + flags_carry_inverted = false; unlock2(s); unlock2(d); } @@ -4319,31 +4388,22 @@ MENDFUNC(2,jff_MULU64,(RW4 d, RW4 s)) * N Set if the result is negative. Cleared otherwise. * Z Set if the result is zero. Cleared otherwise. * V Set if an overflow occurs. Cleared otherwise. - * C Cleared if the result is zero. Set otherwise. + * C Set if a borrow occurs. Cleared otherwise. * */ MIDFUNC(1,jnf_NEG_b,(RW1 d)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((0 - (uae_u8)live.state[d].val) & 0x000000ff)); - return; - } - INIT_REG_b(d); SIGNED8_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSB_rri(REG_WORK1, REG_WORK1, 0); + RSB_rri(REG_WORK1, REG_WORK1, 0); #ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); + BFI_rrii(d, REG_WORK1, 0, 7); #else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); #endif - } else { - RSB_rri(d, REG_WORK1, 0); - } unlock2(d); } @@ -4351,20 +4411,11 @@ MENDFUNC(1,jnf_NEG_b,(RW1 d)) MIDFUNC(1,jnf_NEG_w,(RW2 d)) { - if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((0 - (uae_u16)live.state[d].val) & 0x0000ffff)); - return; - } - INIT_REG_w(d); SIGNED16_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSB_rri(REG_WORK1, REG_WORK1, 0); - PKHTB_rrr(d, d, REG_WORK1); - } else { - RSB_rri(d, REG_WORK1, 0); - } + RSB_rri(REG_WORK1, REG_WORK1, 0); + PKHTB_rrr(d, d, REG_WORK1); unlock2(d); } @@ -4372,11 +4423,6 @@ MENDFUNC(1,jnf_NEG_w,(RW2 d)) MIDFUNC(1,jnf_NEG_l,(RW4 d)) { - if (isconst(d)) { - set_const(d, 0 - (uae_u32)live.state[d].val); - return; - } - d = rmw(d); RSB_rri(d, d, 0); @@ -4390,23 +4436,17 @@ MIDFUNC(1,jff_NEG_b,(RW1 d)) INIT_REG_b(d); SIGNED8_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSBS_rri(REG_WORK1, REG_WORK1, 0); + RSBS_rri(REG_WORK1, REG_WORK1, 0); #ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); + BFI_rrii(d, REG_WORK1, 0, 7); #else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); #endif - } else { - RSBS_rri(d, REG_WORK1, 0); - } - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY unlock2(d); } @@ -4417,17 +4457,11 @@ MIDFUNC(1,jff_NEG_w,(RW2 d)) INIT_REG_w(d); SIGNED16_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSBS_rri(REG_WORK1, REG_WORK1, 0); - PKHTB_rrr(d, d, REG_WORK1); - } else { - RSBS_rri(d, REG_WORK1, 0); - } + RSBS_rri(REG_WORK1, REG_WORK1, 0); + PKHTB_rrr(d, d, REG_WORK1); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY unlock2(d); } @@ -4439,10 +4473,8 @@ MIDFUNC(1,jff_NEG_l,(RW4 d)) RSBS_rri(d, d, 0); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY unlock2(d); } @@ -4458,7 +4490,7 @@ MENDFUNC(1,jff_NEG_l,(RW4 d)) * N Set if the result is negative. Cleared otherwise. * Z Cleared if the result is nonzero; unchanged otherwise. * V Set if an overflow occurs. Cleared otherwise. - * C Cleared if the result is zero. Set otherwise. + * C Set if a borrow occurs. Cleared otherwise. * * Attention: Z is cleared only if the result is nonzero. Unchanged otherwise * @@ -4470,22 +4502,17 @@ MIDFUNC(1,jnf_NEGX_b,(RW1 d)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SIGNED8_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSC_rri(REG_WORK1, REG_WORK1, 0); + RSC_rri(REG_WORK1, REG_WORK1, 0); #ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); + BFI_rrii(d, REG_WORK1, 0, 7); #else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); #endif - } else { - RSC_rri(d, REG_WORK1, 0); - } unlock2(d); unlock2(x); @@ -4500,16 +4527,11 @@ MIDFUNC(1,jnf_NEGX_w,(RW2 d)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SIGNED16_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSC_rri(REG_WORK1, REG_WORK1, 0); - PKHTB_rrr(d, d, REG_WORK1); - } else { - RSC_rri(d, REG_WORK1, 0); - } + RSC_rri(REG_WORK1, REG_WORK1, 0); + PKHTB_rrr(d, d, REG_WORK1); unlock2(d); unlock2(x); @@ -4524,8 +4546,7 @@ MIDFUNC(1,jnf_NEGX_l,(RW4 d)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); RSC_rri(d, d, 0); @@ -4543,33 +4564,31 @@ MIDFUNC(1,jff_NEGX_b,(RW1 d)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SIGNED8_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSCS_rri(REG_WORK1, REG_WORK1, 0); + RSCS_rri(REG_WORK1, REG_WORK1, 0); #ifdef ARMV6T2 - BFI_rrii(d, REG_WORK1, 0, 7); + BFI_rrii(d, REG_WORK1, 0, 7); #else - AND_rri(REG_WORK1, REG_WORK1, 0xff); - BIC_rri(d, d, 0xff); - ORR_rrr(d, d, REG_WORK1); + AND_rri(REG_WORK1, REG_WORK1, 0xff); + BIC_rri(d, d, 0xff); + ORR_rrr(d, d, REG_WORK1); #endif - } else { - RSCS_rri(d, REG_WORK1, 0); - } MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); unlock2(d); @@ -4585,27 +4604,25 @@ MIDFUNC(1,jff_NEGX_w,(RW2 d)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SIGNED16_REG_2_REG(REG_WORK1, d); - if(targetIsReg) { - RSCS_rri(REG_WORK1, REG_WORK1, 0); - PKHTB_rrr(d, d, REG_WORK1); - } else { - RSCS_rri(d, REG_WORK1, 0); - } + RSCS_rri(REG_WORK1, REG_WORK1, 0); + PKHTB_rrr(d, d, REG_WORK1); MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); unlock2(d); @@ -4621,21 +4638,23 @@ MIDFUNC(1,jff_NEGX_l,(RW4 d)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); RSCS_rri(d, d, 0); MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); unlock2(d); @@ -4658,7 +4677,7 @@ MENDFUNC(1,jff_NEGX_l,(RW4 d)) MIDFUNC(1,jnf_NOT_b,(RW1 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((~live.state[d].val) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | ((~live.state[d].val) & 0x000000ff); return; } @@ -4684,7 +4703,7 @@ MENDFUNC(1,jnf_NOT_b,(RW1 d)) MIDFUNC(1,jnf_NOT_w,(RW2 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((~live.state[d].val) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | ((~live.state[d].val) & 0x0000ffff); return; } @@ -4704,7 +4723,7 @@ MENDFUNC(1,jnf_NOT_w,(RW2 d)) MIDFUNC(1,jnf_NOT_l,(RW4 d)) { if (isconst(d)) { - set_const(d, ~live.state[d].val); + live.state[d].val = ~live.state[d].val; return; } @@ -4735,6 +4754,7 @@ MIDFUNC(1,jff_NOT_b,(RW1 d)) MVNS_rr(d, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_NOT_b,(RW1 d)) @@ -4752,6 +4772,7 @@ MIDFUNC(1,jff_NOT_w,(RW2 d)) MVNS_rr(d, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_NOT_w,(RW2 d)) @@ -4763,6 +4784,7 @@ MIDFUNC(1,jff_NOT_l,(RW4 d)) MSR_CPSRf_i(0); MVNS_rr(d, d); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_NOT_l,(RW4 d)) @@ -4781,10 +4803,10 @@ MENDFUNC(1,jff_NOT_l,(RW4 d)) * C Always cleared. * */ -MIDFUNC(2,jnf_OR_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jnf_OR_b_imm,(RW1 d, IM8 v)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | ((live.state[d].val | v) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val | v) & 0x000000ff); return; } @@ -4805,7 +4827,7 @@ MIDFUNC(2,jnf_OR_b_imm,(RW1 d, IMM v)) unlock2(d); } -MENDFUNC(2,jnf_OR_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jnf_OR_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jnf_OR_b,(RW1 d, RR1 s)) { @@ -4833,10 +4855,10 @@ MIDFUNC(2,jnf_OR_b,(RW1 d, RR1 s)) } MENDFUNC(2,jnf_OR_b,(RW1 d, RR1 s)) -MIDFUNC(2,jnf_OR_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jnf_OR_w_imm,(RW2 d, IM16 v)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | ((live.state[d].val | v) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val | v) & 0x0000ffff); return; } @@ -4846,7 +4868,7 @@ MIDFUNC(2,jnf_OR_w_imm,(RW2 d, IMM v)) if(CHECK32(v & 0xffff)) { ORR_rri(REG_WORK1, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); ORR_rrr(REG_WORK1, d, REG_WORK1); } PKHTB_rrr(d, d, REG_WORK1); @@ -4854,14 +4876,14 @@ MIDFUNC(2,jnf_OR_w_imm,(RW2 d, IMM v)) if(CHECK32(v & 0xffff)) { ORR_rri(d, d, (v & 0xffff)); } else { - compemu_raw_mov_l_ri(REG_WORK1, v & 0xffff); + LOAD_U16(REG_WORK1, v & 0xffff); ORR_rrr(d, d, REG_WORK1); } } unlock2(d); } -MENDFUNC(2,jnf_OR_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jnf_OR_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jnf_OR_w,(RW2 d, RR2 s)) { @@ -4883,30 +4905,10 @@ MIDFUNC(2,jnf_OR_w,(RW2 d, RR2 s)) } MENDFUNC(2,jnf_OR_w,(RW2 d, RR2 s)) -MIDFUNC(2,jnf_OR_l_imm,(RW4 d, IMM v)) -{ - if (isconst(d)) { - set_const(d, live.state[d].val | v); - return; - } - - d = rmw(d); - - if(CHECK32(v)) { - ORR_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK1, v); - ORR_rrr(d, d, REG_WORK1); - } - - unlock2(d); -} -MENDFUNC(2,jnf_OR_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jnf_OR_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jnf_OR_l_imm)(d, live.state[s].val); + if (isconst(d) && isconst(s)) { + live.state[d].val = live.state[d].val | live.state[s].val; return; } @@ -4918,7 +4920,7 @@ MIDFUNC(2,jnf_OR_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_OR_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_OR_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jff_OR_b_imm,(RW1 d, IM8 v)) { INIT_REG_b(d); @@ -4938,9 +4940,10 @@ MIDFUNC(2,jff_OR_b_imm,(RW1 d, IMM v)) ORRS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_OR_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jff_OR_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jff_OR_b,(RW1 d, RR1 s)) { @@ -4967,11 +4970,12 @@ MIDFUNC(2,jff_OR_b,(RW1 d, RR1 s)) ORRS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_OR_b,(RW1 d, RR1 s)) -MIDFUNC(2,jff_OR_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jff_OR_w_imm,(RW2 d, IM16 v)) { INIT_REG_w(d); @@ -4985,9 +4989,10 @@ MIDFUNC(2,jff_OR_w_imm,(RW2 d, IMM v)) ORRS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_OR_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jff_OR_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jff_OR_w,(RW2 d, RR2 s)) { @@ -5008,38 +5013,19 @@ MIDFUNC(2,jff_OR_w,(RW2 d, RR2 s)) ORRS_rrr(d, REG_WORK1, REG_WORK2); } + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_OR_w,(RW2 d, RR2 s)) -MIDFUNC(2,jff_OR_l_imm,(RW4 d, IMM v)) -{ - d = rmw(d); - - MSR_CPSRf_i(0); - if(CHECK32(v)) { - ORRS_rri(d, d, v); - } else { - compemu_raw_mov_l_ri(REG_WORK2, v); - ORRS_rrr(d, d, REG_WORK2); - } - - unlock2(d); -} -MENDFUNC(2,jff_OR_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jff_OR_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jff_OR_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); MSR_CPSRf_i(0); ORRS_rrr(d, d, s); + flags_carry_inverted = false; EXIT_REGS(d, s); } MENDFUNC(2,jff_OR_l,(RW4 d, RR4 s)) @@ -5057,9 +5043,13 @@ MENDFUNC(2,jff_OR_l,(RW4 d, RR4 s)) * C — Set if bit 0 of immediate operand is one; unchanged otherwise. * */ -MIDFUNC(1,jff_ORSR,(IMM s, IMM x)) +MIDFUNC(1,jff_ORSR,(IM32 s, IM8 x)) { MRS_CPSR(REG_WORK1); + if (flags_carry_inverted) { + EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); + flags_carry_inverted = false; + } ORR_rri(REG_WORK1, REG_WORK1, s); MSR_CPSRf_r(REG_WORK1); @@ -5069,7 +5059,7 @@ MIDFUNC(1,jff_ORSR,(IMM s, IMM x)) unlock2(f); } } -MENDFUNC(1,jff_ORSR,(IMM s)) +MENDFUNC(2,jff_ORSR,(IM32 s, IM8 x)) /* * ROL @@ -5086,7 +5076,7 @@ MENDFUNC(1,jff_ORSR,(IMM s)) * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. * */ -MIDFUNC(2,jnf_ROL_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jnf_ROL_b_imm,(RW1 d, IM8 i)) { if(i & 0x1f) { INIT_REG_b(d); @@ -5106,9 +5096,9 @@ MIDFUNC(2,jnf_ROL_b_imm,(RW1 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROL_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jnf_ROL_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jnf_ROL_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jnf_ROL_w_imm,(RW2 d, IM8 i)) { if(i & 0x1f) { INIT_REG_w(d); @@ -5120,11 +5110,17 @@ MIDFUNC(2,jnf_ROL_w_imm,(RW2 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROL_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jnf_ROL_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jnf_ROL_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jnf_ROL_l_imm,(RW4 d, IM8 i)) { if(i & 0x1f) { + if (isconst(d)) { + i = i & 31; + live.state[d].val = (live.state[d].val << i) | (live.state[d].val >> (32-i)); + return; + } + d = rmw(d); ROR_rri(d, d, (32 - (i & 0x1f))); @@ -5132,9 +5128,9 @@ MIDFUNC(2,jnf_ROL_l_imm,(RW4 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROL_l_imm,(RW4 d, RR4 s, IMM i)) +MENDFUNC(2,jnf_ROL_l_imm,(RW4 d, RR4 s, IM8 i)) -MIDFUNC(2,jff_ROL_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_ROL_b_imm,(RW1 d, IM8 i)) { if(i) d = rmw(d); @@ -5142,10 +5138,10 @@ MIDFUNC(2,jff_ROL_b_imm,(RW1 d, IMM i)) d = readreg(d); LSL_rri(REG_WORK1, d, 24); - ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); - ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); MSR_CPSRf_i(0); if (i) { + ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); if(i & 0x1f) RORS_rri(REG_WORK1, REG_WORK1, (32 - (i & 0x1f))); else @@ -5171,11 +5167,12 @@ MIDFUNC(2,jff_ROL_b_imm,(RW1 d, IMM i)) TST_rr(REG_WORK1, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROL_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_ROL_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_ROL_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_ROL_w_imm,(RW2 d, IM8 i)) { if(i) d = rmw(d); @@ -5204,23 +5201,22 @@ MIDFUNC(2,jff_ROL_w_imm,(RW2 d, IMM i)) TST_rr(REG_WORK1, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROL_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_ROL_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_ROL_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_ROL_l_imm,(RW4 d, IM8 i)) { - if(i) - d = rmw(d); - else - d = readreg(d); - MSR_CPSRf_i(0); if (i) { - if(i & 0x1f) + if(i & 0x1f) { + d = rmw(d); RORS_rri(d, d, (32 - (i & 0x1f))); - else + } else { + d = readreg(d); TST_rr(d, d); + } MRS_CPSR(REG_WORK2); #ifdef ARMV6T2 @@ -5232,12 +5228,14 @@ MIDFUNC(2,jff_ROL_l_imm,(RW4 d, IMM i)) #endif MSR_CPSRf_r(REG_WORK2); } else { + d = readreg(d); TST_rr(d, d); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROL_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_ROL_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jnf_ROL_b,(RW1 d, RR4 i)) { @@ -5245,6 +5243,7 @@ MIDFUNC(2,jnf_ROL_b,(RW1 d, RR4 i)) COMPCALL(jnf_ROL_b_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_b(d, i); AND_rri(REG_WORK1, i, 0x1f); @@ -5272,6 +5271,7 @@ MIDFUNC(2,jnf_ROL_w,(RW2 d, RR4 i)) COMPCALL(jnf_ROL_w_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_w(d, i); AND_rri(REG_WORK1, i, 0x1f); @@ -5291,6 +5291,7 @@ MIDFUNC(2,jnf_ROL_l,(RW4 d, RR4 i)) COMPCALL(jnf_ROL_l_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_l(d, i); AND_rri(REG_WORK1, i, 0x1f); @@ -5311,7 +5312,16 @@ MIDFUNC(2,jff_ROL_b,(RW1 d, RR4 i)) INIT_REGS_b(d, i); - AND_rri(REG_WORK1, i, 0x1f); + ANDS_rri(REG_WORK1, i, 0x1f); + BNE_i(3); + + // shift count is 0 + LSL_rri(REG_WORK3, d, 24); + MSR_CPSRf_i(0); + TST_rr(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + RSB_rri(REG_WORK1, REG_WORK1, 32); LSL_rri(REG_WORK2, d, 24); @@ -5337,6 +5347,10 @@ MIDFUNC(2,jff_ROL_b,(RW1 d, RR4 i)) #endif MSR_CPSRf_r(REG_WORK2); + // + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; EXIT_REGS(d, i); } MENDFUNC(2,jff_ROL_b,(RW1 d, RR4 i)) @@ -5350,7 +5364,16 @@ MIDFUNC(2,jff_ROL_w,(RW2 d, RR4 i)) INIT_REGS_w(d, i); - AND_rri(REG_WORK1, i, 0x1f); + ANDS_rri(REG_WORK1, i, 0x1f); + BNE_i(3); + + // shift count is 0 + LSL_rri(REG_WORK3, d, 16); + MSR_CPSRf_i(0); + TST_rr(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + RSB_rri(REG_WORK1, REG_WORK1, 32); PKHBT_rrrLSLi(REG_WORK2, d, d, 16); @@ -5368,6 +5391,10 @@ MIDFUNC(2,jff_ROL_w,(RW2 d, RR4 i)) #endif MSR_CPSRf_r(REG_WORK2); + // + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; EXIT_REGS(d, i); } MENDFUNC(2,jff_ROL_w,(RW2 d, RR4 i)) @@ -5397,6 +5424,7 @@ MIDFUNC(2,jff_ROL_l,(RW4 d, RR4 i)) #endif MSR_CPSRf_r(REG_WORK2); + flags_carry_inverted = false; unlock2(d); unlock2(i); } @@ -5445,6 +5473,7 @@ MIDFUNC(1,jff_ROLW,(RW2 d)) #endif MSR_CPSRf_r(REG_WORK2); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_ROLW,(RW2 d)) @@ -5478,11 +5507,8 @@ MIDFUNC(2,jnf_ROXL_b,(RW1 d, RR4 i)) CMP_ri(REG_WORK1, 8); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 9); TST_rr(REG_WORK1, REG_WORK1); -#ifdef ARMV6T2 - BEQ_i(8); // end of op -#else - BEQ_i(10); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op // need to rotate CMP_ri(REG_WORK1, 8); @@ -5503,7 +5529,8 @@ MIDFUNC(2,jnf_ROXL_b,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK2); #endif -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -5523,7 +5550,8 @@ MIDFUNC(2,jnf_ROXL_w,(RW2 d, RR4 i)) CMP_ri(REG_WORK1, 16); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 17); TST_rr(REG_WORK1, REG_WORK1); - BEQ_i(8); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op // need to rotate CMP_ri(REG_WORK1, 16); @@ -5538,7 +5566,8 @@ MIDFUNC(2,jnf_ROXL_w,(RW2 d, RR4 i)) ORR_rrrLSRr(REG_WORK2, REG_WORK2, REG_WORK1, REG_WORK3); PKHTB_rrr(d, d, REG_WORK2); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -5556,7 +5585,8 @@ MIDFUNC(2,jnf_ROXL_l,(RW4 d, RR4 i)) CMP_ri(REG_WORK1, 32); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 33); TST_rr(REG_WORK1, REG_WORK1); - BEQ_i(6); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op // need to rotate CMP_ri(REG_WORK1, 32); @@ -5569,7 +5599,8 @@ MIDFUNC(2,jnf_ROXL_l,(RW4 d, RR4 i)) RSB_rri(REG_WORK3, REG_WORK1, 33); ORR_rrrLSRr(d, REG_WORK2, d, REG_WORK3); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -5594,13 +5625,10 @@ MIDFUNC(2,jff_ROXL_b,(RW1 d, RR4 i)) MSR_CPSRf_i(0); AND_rri(REG_WORK1, d, 0xff); // make sure to clear carry MOVS_rrLSLi(REG_WORK1, REG_WORK1, 24); -#ifdef ARMV6T2 - B_i(13); // end of op -#else - B_i(16); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate CMP_ri(REG_WORK1, 8); CC_MOV_rrLSLr(NATIVE_CC_NE, REG_WORK2, d, REG_WORK1); CC_MOV_ri(NATIVE_CC_EQ, REG_WORK2, 0); @@ -5634,8 +5662,10 @@ MIDFUNC(2,jff_ROXL_b,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK2); #endif -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -5657,13 +5687,10 @@ MIDFUNC(2,jff_ROXL_w,(RW2 d, RR4 i)) MSR_CPSRf_i(0); BIC_rri(REG_WORK1, d, 0x00ff0000); // make sure to clear carry MOVS_rrLSLi(REG_WORK1, REG_WORK1, 16); -#ifdef ARMV6T2 - B_i(13); // end of op -#else - B_i(14); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate CMP_ri(REG_WORK1, 16); CC_MOV_rrLSLr(NATIVE_CC_NE, REG_WORK2, d, REG_WORK1); CC_MOV_ri(NATIVE_CC_EQ, REG_WORK2, 0); @@ -5691,8 +5718,10 @@ MIDFUNC(2,jff_ROXL_w,(RW2 d, RR4 i)) PKHTB_rrr(d, d, REG_WORK2); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -5711,9 +5740,10 @@ MIDFUNC(2,jff_ROXL_l,(RW4 d, RR4 i)) MSR_CPSRf_i(0); TST_rr(d, d); - B_i(9); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate CMP_ri(REG_WORK1, 32); CC_MOV_rrLSLr(NATIVE_CC_NE, REG_WORK2, d, REG_WORK1); CC_MOV_ri(NATIVE_CC_EQ, REG_WORK2, 0); @@ -5729,8 +5759,10 @@ MIDFUNC(2,jff_ROXL_l,(RW4 d, RR4 i)) MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -5751,7 +5783,7 @@ MENDFUNC(2,jff_ROXL_l,(RW4 d, RR4 i)) * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. * */ -MIDFUNC(2,jnf_ROR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jnf_ROR_b_imm,(RW1 d, IM8 i)) { if(i & 0x07) { INIT_REG_b(d); @@ -5771,9 +5803,9 @@ MIDFUNC(2,jnf_ROR_b_imm,(RW1 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jnf_ROR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jnf_ROR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jnf_ROR_w_imm,(RW2 d, IM8 i)) { if(i & 0x0f) { INIT_REG_w(d); @@ -5785,11 +5817,17 @@ MIDFUNC(2,jnf_ROR_w_imm,(RW2 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jnf_ROR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jnf_ROR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jnf_ROR_l_imm,(RW4 d, IM8 i)) { if(i & 0x1f) { + if (isconst(d)) { + i = i & 31; + live.state[d].val = (live.state[d].val >> i) | (live.state[d].val << (32-i)); + return; + } + d = rmw(d); ROR_rri(d, d, i & 31); @@ -5797,9 +5835,9 @@ MIDFUNC(2,jnf_ROR_l_imm,(RW4 d, IMM i)) unlock2(d); } } -MENDFUNC(2,jnf_ROR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jnf_ROR_l_imm,(RW4 d, IM8 i)) -MIDFUNC(2,jff_ROR_b_imm,(RW1 d, IMM i)) +MIDFUNC(2,jff_ROR_b_imm,(RW1 d, IM8 i)) { if(i) d = rmw(d); @@ -5807,10 +5845,10 @@ MIDFUNC(2,jff_ROR_b_imm,(RW1 d, IMM i)) d = readreg(d); LSL_rri(REG_WORK1, d, 24); - ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); - ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); MSR_CPSRf_i(0); if(i & 0x07) { + ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_rrrLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); RORS_rri(REG_WORK1, REG_WORK1, i & 0x07); #ifdef ARMV6T2 BFI_rrii(d, REG_WORK1, 0, 7); @@ -5829,11 +5867,12 @@ MIDFUNC(2,jff_ROR_b_imm,(RW1 d, IMM i)) TST_rr(REG_WORK1, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROR_b_imm,(RW1 d, IMM i)) +MENDFUNC(2,jff_ROR_b_imm,(RW1 d, IM8 i)) -MIDFUNC(2,jff_ROR_w_imm,(RW2 d, IMM i)) +MIDFUNC(2,jff_ROR_w_imm,(RW2 d, IM8 i)) { if(i) d = rmw(d); @@ -5855,11 +5894,12 @@ MIDFUNC(2,jff_ROR_w_imm,(RW2 d, IMM i)) TST_rr(REG_WORK1, REG_WORK1); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROR_w_imm,(RW2 d, IMM i)) +MENDFUNC(2,jff_ROR_w_imm,(RW2 d, IM8 i)) -MIDFUNC(2,jff_ROR_l_imm,(RW4 d, IMM i)) +MIDFUNC(2,jff_ROR_l_imm,(RW4 d, IM8 i)) { if(i) d = rmw(d); @@ -5870,18 +5910,19 @@ MIDFUNC(2,jff_ROR_l_imm,(RW4 d, IMM i)) if(i & 0x1f) { RORS_rri(d, d, i & 0x1f); } else if (i > 0x1f) { - TST_ri(d, d); + TST_rr(d, d); // We need to copy MSB to carry MRS_CPSR(REG_WORK1); // carry is cleared CC_ORR_rri(NATIVE_CC_MI, REG_WORK1, REG_WORK1, ARM_C_FLAG); MSR_CPSRf_r(REG_WORK1); } else { - TST_ri(d, d); + TST_rr(d, d); } + flags_carry_inverted = false; unlock2(d); } -MENDFUNC(2,jff_ROR_l_imm,(RW4 d, IMM i)) +MENDFUNC(2,jff_ROR_l_imm,(RW4 d, IM8 i)) MIDFUNC(2,jnf_ROR_b,(RW1 d, RR4 i)) { @@ -5889,6 +5930,7 @@ MIDFUNC(2,jnf_ROR_b,(RW1 d, RR4 i)) COMPCALL(jnf_ROR_b_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_b(d, i); LSL_rri(REG_WORK1, d, 24); @@ -5913,6 +5955,7 @@ MIDFUNC(2,jnf_ROR_w,(RW2 d, RR4 i)) COMPCALL(jnf_ROR_w_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_w(d, i); PKHBT_rrrLSLi(REG_WORK1, d, d, 16); @@ -5929,6 +5972,7 @@ MIDFUNC(2,jnf_ROR_l,(RW4 d, RR4 i)) COMPCALL(jnf_ROR_l_imm)(d, (uae_u8)live.state[i].val); return; } + INIT_REGS_l(d, i); ROR_rrr(d, d, i); @@ -5960,6 +6004,7 @@ MIDFUNC(2,jff_ROR_b,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK1); #endif + flags_carry_inverted = false; EXIT_REGS(d, i); } MENDFUNC(2,jff_ROR_b,(RW1 d, RR4 i)) @@ -5979,6 +6024,7 @@ MIDFUNC(2,jff_ROR_w,(RW2 d, RR4 i)) RORS_rrr(REG_WORK1, REG_WORK1, REG_WORK2); PKHTB_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; EXIT_REGS(d, i); } MENDFUNC(2,jff_ROR_w,(RW2 d, RR4 i)) @@ -5996,6 +6042,7 @@ MIDFUNC(2,jff_ROR_l,(RW4 d, RR4 i)) AND_rri(REG_WORK1, i, 63); RORS_rrr(d, d, REG_WORK1); + flags_carry_inverted = false; EXIT_REGS(d, i); } MENDFUNC(2,jff_ROR_l,(RW4 d, RR4 i)) @@ -6033,11 +6080,11 @@ MIDFUNC(1,jff_RORW,(RW2 d)) MSR_CPSRf_i(0); RORS_rri(d, d, 1); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_RORW,(RW2 d)) - /* * ROXR * Operand Syntax: Dx, Dy @@ -6067,13 +6114,10 @@ MIDFUNC(2,jnf_ROXR_b,(RW1 d, RR4 i)) CMP_ri(REG_WORK1, 8); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 9); TST_rr(REG_WORK1, REG_WORK1); -#ifdef ARMV6T2 - BEQ_i(4); // end of op -#else - BEQ_i(6); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op -// need to rotate + // need to rotate AND_rri(REG_WORK2, d, 0xff); // val = val & 0xff ORR_rrrLSLi(REG_WORK2, REG_WORK2, REG_WORK2, 9); // val = val | (val << 9) ORR_rrrLSLi(REG_WORK2, REG_WORK2, x, 8); // val = val | (x << 8) @@ -6087,7 +6131,8 @@ MIDFUNC(2,jnf_ROXR_b,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK2); #endif -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -6107,9 +6152,10 @@ MIDFUNC(2,jnf_ROXR_w,(RW2 d, RR4 i)) CMP_ri(REG_WORK1, 16); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 17); TST_rr(REG_WORK1, REG_WORK1); - BEQ_i(5); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op -// need to rotate + // need to rotate BIC_rri(REG_WORK2, d, 0xff000000); BIC_rri(REG_WORK2, REG_WORK2, 0x00ff0000); // val = val & 0xffff ORR_rrrLSLi(REG_WORK2, REG_WORK2, REG_WORK2, 17); // val = val | (val << 17) @@ -6118,7 +6164,8 @@ MIDFUNC(2,jnf_ROXR_w,(RW2 d, RR4 i)) PKHTB_rrr(d, d, REG_WORK2); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -6136,9 +6183,10 @@ MIDFUNC(2,jnf_ROXR_l,(RW4 d, RR4 i)) CMP_ri(REG_WORK1, 32); CC_SUB_rri(NATIVE_CC_GT, REG_WORK1, REG_WORK1, 33); TST_rr(REG_WORK1, REG_WORK1); - BEQ_i(6); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // end of op -// need to rotate + // need to rotate CMP_ri(REG_WORK1, 32); CC_MOV_rrLSRr(NATIVE_CC_NE, REG_WORK2, d, REG_WORK1); CC_MOV_ri(NATIVE_CC_EQ, REG_WORK2, 0); @@ -6149,7 +6197,8 @@ MIDFUNC(2,jnf_ROXR_l,(RW4 d, RR4 i)) ADD_rri(REG_WORK3, REG_WORK3, 1); ORR_rrrLSLr(d, REG_WORK2, d, REG_WORK3); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); unlock2(x); EXIT_REGS(d, i); @@ -6174,13 +6223,10 @@ MIDFUNC(2,jff_ROXR_b,(RW1 d, RR4 i)) MSR_CPSRf_i(0); BIC_rri(REG_WORK1, d, 0x0000ff00); // make sure to clear carry MOVS_rrLSLi(REG_WORK1, REG_WORK1, 24); -#ifdef ARMV6T2 - B_i(9); // end of op -#else - B_i(12); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate AND_rri(REG_WORK2, d, 0xff); // val = val & 0xff ORR_rrrLSLi(REG_WORK2, REG_WORK2, REG_WORK2, 9); // val = val | (val << 9) ORR_rrrLSLi(REG_WORK2, REG_WORK2, x, 8); // val = val | (x << 8) @@ -6208,8 +6254,10 @@ MIDFUNC(2,jff_ROXR_b,(RW1 d, RR4 i)) ORR_rrr(d, d, REG_WORK2); #endif -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -6231,13 +6279,10 @@ MIDFUNC(2,jff_ROXR_w,(RW2 d, RR4 i)) MSR_CPSRf_i(0); BIC_rri(REG_WORK1, d, 0x00ff0000); // make sure to clear carry MOVS_rrLSLi(REG_WORK1, REG_WORK1, 16); -#ifdef ARMV6T2 - B_i(10); // end of op -#else - B_i(11); // end of op -#endif + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate BIC_rri(REG_WORK2, d, 0xff000000); BIC_rri(REG_WORK2, REG_WORK2, 0x00ff0000); // val = val & 0xffff ORR_rrrLSLi(REG_WORK2, REG_WORK2, REG_WORK2, 17); // val = val | (val << 17) @@ -6260,8 +6305,10 @@ MIDFUNC(2,jff_ROXR_w,(RW2 d, RR4 i)) PKHTB_rrr(d, d, REG_WORK2); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -6280,19 +6327,20 @@ MIDFUNC(2,jff_ROXR_l,(RW4 d, RR4 i)) MSR_CPSRf_i(0); TST_rr(d, d); - B_i(13); // end of op + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op -// need to rotate + // need to rotate CMP_ri(REG_WORK1, 32); BNE_i(3); // rotate 1-31 -// rotate 32 + // rotate 32 MSR_CPSRf_i(0); LSLS_rri(d, d, 1); ORRS_rrr(d, d, x); B_i(5); // duplicate carry -// rotate 1-31 + // rotate 1-31 MSR_CPSRf_i(0); MOVS_rrLSRr(REG_WORK2, d, REG_WORK1); @@ -6306,8 +6354,10 @@ MIDFUNC(2,jff_ROXR_l,(RW4 d, RR4 i)) MOV_ri(x, 1); CC_MOV_ri(NATIVE_CC_CC, x, 0); -// end of op + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + flags_carry_inverted = false; unlock2(x); EXIT_REGS(d, i); } @@ -6317,8 +6367,10 @@ MENDFUNC(2,jff_ROXR_l,(RW4 d, RR4 i)) * SCC * */ -MIDFUNC(2,jnf_SCC,(W1 d, IMM cc)) +MIDFUNC(2,jnf_SCC,(W1 d, IM8 cc)) { + FIX_INVERTED_CARRY + INIT_WREG_b(d); switch (cc) { @@ -6342,7 +6394,7 @@ MIDFUNC(2,jnf_SCC,(W1 d, IMM cc)) unlock2(d); } -MENDFUNC(2,jnf_SCC,(W1 d, IMM cc)) +MENDFUNC(2,jnf_SCC,(W1 d, IM8 cc)) /* * SUB @@ -6358,10 +6410,10 @@ MENDFUNC(2,jnf_SCC,(W1 d, IMM cc)) * C Set if a carry is generated. Cleared otherwise. * */ -MIDFUNC(2,jnf_SUB_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jnf_SUB_b_imm,(RW1 d, IM8 v)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffffff00) | (((live.state[d].val & 0xff) - (v & 0xff)) & 0x000000ff)); + live.state[d].val = (live.state[d].val & 0xffffff00) | (((live.state[d].val & 0xff) - (v & 0xff)) & 0x000000ff); return; } @@ -6382,7 +6434,7 @@ MIDFUNC(2,jnf_SUB_b_imm,(RW1 d, IMM v)) unlock2(d); } -MENDFUNC(2,jnf_SUB_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jnf_SUB_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jnf_SUB_b,(RW1 d, RR1 s)) { @@ -6410,10 +6462,10 @@ MIDFUNC(2,jnf_SUB_b,(RW1 d, RR1 s)) } MENDFUNC(2,jnf_SUB_b,(RW1 d, RR1 s)) -MIDFUNC(2,jnf_SUB_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jnf_SUB_w_imm,(RW2 d, IM16 v)) { if (isconst(d)) { - set_const(d, (live.state[d].val & 0xffff0000) | (((live.state[d].val & 0xffff) - (v & 0xffff)) & 0x0000ffff)); + live.state[d].val = (live.state[d].val & 0xffff0000) | (((live.state[d].val & 0xffff) - (v & 0xffff)) & 0x0000ffff); return; } @@ -6429,7 +6481,7 @@ MIDFUNC(2,jnf_SUB_w_imm,(RW2 d, IMM v)) unlock2(d); } -MENDFUNC(2,jnf_SUB_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jnf_SUB_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jnf_SUB_w,(RW2 d, RR2 s)) { @@ -6451,26 +6503,10 @@ MIDFUNC(2,jnf_SUB_w,(RW2 d, RR2 s)) } MENDFUNC(2,jnf_SUB_w,(RW2 d, RR2 s)) -MIDFUNC(2,jnf_SUB_l_imm,(RW4 d, IMM v)) -{ - if (isconst(d)) { - set_const(d, live.state[d].val - v); - return; - } - - d = rmw(d); - - compemu_raw_mov_l_ri(REG_WORK1, v); - SUB_rrr(d, d, REG_WORK1); - - unlock2(d); -} -MENDFUNC(2,jnf_SUB_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jnf_SUB_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jnf_SUB_l_imm)(d, live.state[s].val); + if (isconst(d) && isconst(s)) { + live.state[d].val = live.state[d].val - live.state[s].val; return; } @@ -6482,7 +6518,7 @@ MIDFUNC(2,jnf_SUB_l,(RW4 d, RR4 s)) } MENDFUNC(2,jnf_SUB_l,(RW4 d, RR4 s)) -MIDFUNC(2,jff_SUB_b_imm,(RW1 d, IMM v)) +MIDFUNC(2,jff_SUB_b_imm,(RW1 d, IM8 v)) { INIT_REG_b(d); @@ -6495,14 +6531,12 @@ MIDFUNC(2,jff_SUB_b_imm,(RW1 d, IMM v)) LSR_rri(d, REG_WORK1, 24); } - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY unlock2(d); } -MENDFUNC(2,jff_SUB_b_imm,(RW1 d, IMM v)) +MENDFUNC(2,jff_SUB_b_imm,(RW1 d, IM8 v)) MIDFUNC(2,jff_SUB_b,(RW1 d, RR1 s)) { @@ -6522,41 +6556,32 @@ MIDFUNC(2,jff_SUB_b,(RW1 d, RR1 s)) LSR_rri(d, REG_WORK1, 24); } - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY EXIT_REGS(d, s); } MENDFUNC(2,jff_SUB_b,(RW1 d, RR1 s)) -MIDFUNC(2,jff_SUB_w_imm,(RW2 d, IMM v)) +MIDFUNC(2,jff_SUB_w_imm,(RW2 d, IM16 v)) { INIT_REG_w(d); if(CHECK32(v)) { MOV_ri(REG_WORK1, v); } else { -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK1, v); -#else - uae_s32 offs = data_word_offs(v); - LDR_rRI(REG_WORK1, RPC_INDEX, offs); -#endif + LOAD_U16(REG_WORK1, v); } LSL_rri(REG_WORK2, d, 16); SUBS_rrrLSLi(REG_WORK1, REG_WORK2, REG_WORK1, 16); PKHTB_rrrASRi(d, d, REG_WORK1, 16); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY unlock2(d); } -MENDFUNC(2,jff_SUB_w_imm,(RW2 d, IMM v)) +MENDFUNC(2,jff_SUB_w_imm,(RW2 d, IM16 v)) MIDFUNC(2,jff_SUB_w,(RW2 d, RR2 s)) { @@ -6571,46 +6596,21 @@ MIDFUNC(2,jff_SUB_w,(RW2 d, RR2 s)) SUBS_rrrLSLi(REG_WORK1, REG_WORK1, s, 16); PKHTB_rrrASRi(d, d, REG_WORK1, 16); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY EXIT_REGS(d, s); } MENDFUNC(2,jff_SUB_w,(RW2 d, RR2 s)) -MIDFUNC(2,jff_SUB_l_imm,(RW4 d, IMM v)) -{ - d = rmw(d); - - compemu_raw_mov_l_ri(REG_WORK2, v); - SUBS_rrr(d, d, REG_WORK2); - - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) - - unlock2(d); -} -MENDFUNC(2,jff_SUB_l_imm,(RW4 d, IMM v)) - MIDFUNC(2,jff_SUB_l,(RW4 d, RR4 s)) { - if (isconst(s)) { - COMPCALL(jff_SUB_l_imm)(d, live.state[s].val); - return; - } - INIT_REGS_l(d, s); SUBS_rrr(d, d, s); - MRS_CPSR(REG_WORK1); - EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); - MSR_CPSRf_r(REG_WORK1); - DUPLICACTE_CARRY_FROM_REG(REG_WORK1) + flags_carry_inverted = true; + DUPLICACTE_CARRY EXIT_REGS(d, s); } @@ -6671,17 +6671,12 @@ MIDFUNC(2,jnf_SUBX_b,(RW1 d, RR1 s)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); LSL_rri(REG_WORK1, d, 24); SBC_rrrLSLi(REG_WORK1, REG_WORK1, s, 24); - if(targetIsReg) { - BIC_rri(d, d, 0xff); - ORR_rrrLSRi(d, d, REG_WORK1, 24); - } else { - LSR_rri(d, REG_WORK1, 24); - } + BIC_rri(d, d, 0xff); + ORR_rrrLSRi(d, d, REG_WORK1, 24); unlock2(x); EXIT_REGS(d, s); @@ -6696,8 +6691,7 @@ MIDFUNC(2,jnf_SUBX_w,(RW2 d, RR2 s)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); LSL_rri(REG_WORK1, d, 16); SBC_rrrLSLi(REG_WORK1, REG_WORK1, s, 16); @@ -6716,8 +6710,7 @@ MIDFUNC(2,jnf_SUBX_l,(RW4 d, RR4 s)) clobber_flags(); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SBC_rrr(d, d, s); @@ -6735,28 +6728,26 @@ MIDFUNC(2,jff_SUBX_b,(RW1 d, RR1 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); LSL_rri(REG_WORK1, d, 24); SBCS_rrrLSLi(REG_WORK1, REG_WORK1, s, 24); - if(targetIsReg) { - BIC_rri(d, d, 0xff); - ORR_rrrLSRi(d, d, REG_WORK1, 24); - } else { - LSR_rri(d, REG_WORK1, 24); - } + BIC_rri(d, d, 0xff); + ORR_rrrLSRi(d, d, REG_WORK1, 24); MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); EXIT_REGS(d, s); @@ -6772,8 +6763,7 @@ MIDFUNC(2,jff_SUBX_w,(RW2 d, RR2 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); LSL_rri(REG_WORK1, d, 16); SBCS_rrrLSLi(REG_WORK1, REG_WORK1, s, 16); @@ -6782,13 +6772,16 @@ MIDFUNC(2,jff_SUBX_w,(RW2 d, RR2 s)) MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); EXIT_REGS(d, s); @@ -6804,21 +6797,23 @@ MIDFUNC(2,jff_SUBX_l,(RW4 d, RR4 s)) CC_MVN_ri(NATIVE_CC_NE, REG_WORK2, ARM_Z_FLAG); // Restore inverted X to carry (don't care about other flags) - MVN_rrLSLi(REG_WORK1, x, 29); - MSR_CPSRf_r(REG_WORK1); + RSBS_rri(REG_WORK1, x, 0); SBCS_rrr(d, d, s); MRS_CPSR(REG_WORK1); EOR_rri(REG_WORK1, REG_WORK1, ARM_C_FLAG); AND_rrr(REG_WORK1, REG_WORK1, REG_WORK2); -#ifdef ARMV6T2 - UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry -#else - LSR_rri(x, REG_WORK1, 29); - AND_rri(x, x, 1); -#endif MSR_CPSRf_r(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) { +#ifdef ARMV6T2 + UBFX_rrii(x, REG_WORK1, 29, 1); // Duplicate carry +#else + LSR_rri(x, REG_WORK1, 29); + AND_rri(x, x, 1); +#endif + } unlock2(x); EXIT_REGS(d, s); @@ -6841,7 +6836,7 @@ MENDFUNC(2,jff_SUBX_l,(RW4 d, RR4 s)) MIDFUNC(1,jnf_SWAP,(RW4 d)) { if (isconst(d)) { - set_const(d, (live.state[d].val >> 16) | (live.state[d].val << 16)); + live.state[d].val = (live.state[d].val >> 16) | (live.state[d].val << 16); return; } @@ -6861,6 +6856,7 @@ MIDFUNC(1,jff_SWAP,(RW4 d)) MSR_CPSRf_i(0); TST_rr(d, d); + flags_carry_inverted = false; unlock2(d); } MENDFUNC(1,jff_SWAP,(RW4 d)) @@ -6889,6 +6885,7 @@ MIDFUNC(1,jff_TST_b,(RR1 s)) } MSR_CPSRf_i(0); TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } MENDFUNC(1,jff_TST_b,(RR1 s)) @@ -6903,22 +6900,17 @@ MIDFUNC(1,jff_TST_w,(RR2 s)) } MSR_CPSRf_i(0); TST_rr(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; } MENDFUNC(1,jff_TST_w,(RR2 s)) MIDFUNC(1,jff_TST_l,(RR4 s)) { MSR_CPSRf_i(0); - - if (isconst(s)) { - compemu_raw_mov_l_ri(REG_WORK1, live.state[s].val); - TST_rr(REG_WORK1, REG_WORK1); - } - else { - s = readreg(s); - TST_rr(s, s); - unlock2(s); - } + s = readreg(s); + TST_rr(s, s); + unlock2(s); + flags_carry_inverted = false; } MENDFUNC(1,jff_TST_l,(RR4 s)) @@ -7116,7 +7108,7 @@ MIDFUNC(2,jnf_MEM_GETADR24_OFF,(W4 d, RR4 adr)) MENDFUNC(2,jnf_MEM_GETADR24_OFF,(W4 d, RR4 adr)) -MIDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IMM offset)) +MIDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IM8 offset)) { clobber_flags(); if (dest != adr) { @@ -7128,13 +7120,8 @@ MIDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IMM offset)) unlock2(adr); prepare_for_call_2(); -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, (uae_u32)mem_banks); - MOVT_ri16(REG_WORK2, (uae_u32)mem_banks >> 16); -#else - uae_s32 offs = data_long_offs((uae_u32)mem_banks); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); -#endif + uintptr idx = (uintptr)(®s.mem_banks) - (uintptr)(®s); + LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); LSR_rri(REG_WORK1, adr, 16); LDR_rRR_LSLi(REG_WORK3, REG_WORK2, REG_WORK1, 2); LDR_rRI(REG_WORK3, REG_WORK3, offset); @@ -7148,13 +7135,12 @@ MIDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IMM offset)) live.state[dest].realreg = REG_RESULT; live.state[dest].realind = 0; live.state[dest].val = 0; - live.state[dest].validsize = 4; set_status(dest, DIRTY); } -MENDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IMM offset)) +MENDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IM8 offset)) -MIDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IMM offset)) +MIDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IM8 offset)) { clobber_flags(); @@ -7165,18 +7151,13 @@ MIDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IMM offset)) unlock2(source); prepare_for_call_2(); -#ifdef ARMV6T2 - MOVW_ri16(REG_WORK2, (uae_u32)mem_banks); - MOVT_ri16(REG_WORK2, (uae_u32)mem_banks >> 16); -#else - uae_s32 offs = data_long_offs((uae_u32)mem_banks); - LDR_rRI(REG_WORK2, RPC_INDEX, offs); -#endif + uintptr idx = (uintptr)(®s.mem_banks) - (uintptr)(®s); + LDR_rRI(REG_WORK2, R_REGSTRUCT, idx); LSR_rri(REG_WORK1, adr, 16); LDR_rRR_LSLi(REG_WORK3, REG_WORK2, REG_WORK1, 2); LDR_rRI(REG_WORK3, REG_WORK3, offset); compemu_raw_call_r(REG_WORK3); } -MENDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IMM offset)) +MENDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IM8 offset)) diff --git a/src/jit/compemu_midfunc_arm2.h b/src/jit/compemu_midfunc_arm2.h index a901f7d2..59c73095 100644 --- a/src/jit/compemu_midfunc_arm2.h +++ b/src/jit/compemu_midfunc_arm2.h @@ -35,16 +35,16 @@ extern const uae_u32 ARM_CCR_MAP[]; // ADD -DECLARE_MIDFUNC(jnf_ADD_im8(W4 d, RR4 s, IMM v)); -DECLARE_MIDFUNC(jnf_ADD_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jnf_ADD_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jnf_ADD_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jnf_ADD_im8(W4 d, RR4 s, IM8 v)); +DECLARE_MIDFUNC(jnf_ADD_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jnf_ADD_w_imm(RW2 d, IM16 v)); +DECLARE_MIDFUNC(jnf_ADD_l_imm(RW4 d, IM32 v)); DECLARE_MIDFUNC(jnf_ADD_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jnf_ADD_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jnf_ADD_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_ADD_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jff_ADD_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jff_ADD_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jff_ADD_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jff_ADD_w_imm(RW2 d, IM16 v)); +DECLARE_MIDFUNC(jff_ADD_l_imm(RW4 d, IM32 v)); DECLARE_MIDFUNC(jff_ADD_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jff_ADD_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_ADD_l(RW4 d, RR4 s)); @@ -62,26 +62,24 @@ DECLARE_MIDFUNC(jff_ADDX_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_ADDX_l(RW4 d, RR4 s)); // ANDSR -DECLARE_MIDFUNC(jff_ANDSR(IMM s, IMM x)); +DECLARE_MIDFUNC(jff_ANDSR(IM32 s, IM8 x)); // AND -DECLARE_MIDFUNC(jnf_AND_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jnf_AND_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jnf_AND_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jnf_AND_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jnf_AND_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jnf_AND_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jnf_AND_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jnf_AND_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_AND_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jff_AND_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jff_AND_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jff_AND_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jff_AND_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jff_AND_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jff_AND_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_AND_l(RW4 d, RR4 s)); // ASL -DECLARE_MIDFUNC(jff_ASL_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jff_ASL_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jff_ASL_l_imm(RW4 d, IMM i)); +DECLARE_MIDFUNC(jff_ASL_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jff_ASL_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jff_ASL_l_imm(RW4 d, IM8 i)); DECLARE_MIDFUNC(jff_ASL_b_reg(RW1 d, RR4 i)); DECLARE_MIDFUNC(jff_ASL_w_reg(RW2 d, RR4 i)); DECLARE_MIDFUNC(jff_ASL_l_reg(RW4 d, RR4 i)); @@ -91,12 +89,12 @@ DECLARE_MIDFUNC(jff_ASLW(RW2 d)); DECLARE_MIDFUNC(jnf_ASLW(RW2 d)); // ASR -DECLARE_MIDFUNC(jnf_ASR_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jnf_ASR_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jnf_ASR_l_imm(RW4 d, IMM i)); -DECLARE_MIDFUNC(jff_ASR_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jff_ASR_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jff_ASR_l_imm(RW4 d, IMM i)); +DECLARE_MIDFUNC(jnf_ASR_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jnf_ASR_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jnf_ASR_l_imm(RW4 d, IM8 i)); +DECLARE_MIDFUNC(jff_ASR_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jff_ASR_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jff_ASR_l_imm(RW4 d, IM8 i)); DECLARE_MIDFUNC(jnf_ASR_b_reg(RW1 d, RR4 i)); DECLARE_MIDFUNC(jnf_ASR_w_reg(RW2 d, RR4 i)); DECLARE_MIDFUNC(jnf_ASR_l_reg(RW4 d, RR4 i)); @@ -109,38 +107,38 @@ DECLARE_MIDFUNC(jff_ASRW(RW2 d)); DECLARE_MIDFUNC(jnf_ASRW(RW2 d)); // BCHG -DECLARE_MIDFUNC(jnf_BCHG_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jnf_BCHG_l_imm(RW4 d, IMM s)); -DECLARE_MIDFUNC(jff_BCHG_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jff_BCHG_l_imm(RW4 d, IMM s)); +DECLARE_MIDFUNC(jnf_BCHG_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jnf_BCHG_l_imm(RW4 d, IM8 s)); +DECLARE_MIDFUNC(jff_BCHG_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jff_BCHG_l_imm(RW4 d, IM8 s)); DECLARE_MIDFUNC(jnf_BCHG_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jnf_BCHG_l(RW4 d, RR4 s)); DECLARE_MIDFUNC(jff_BCHG_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jff_BCHG_l(RW4 d, RR4 s)); // BCLR -DECLARE_MIDFUNC(jnf_BCLR_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jnf_BCLR_l_imm(RW4 d, IMM s)); +DECLARE_MIDFUNC(jnf_BCLR_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jnf_BCLR_l_imm(RW4 d, IM8 s)); DECLARE_MIDFUNC(jnf_BCLR_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jnf_BCLR_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_BCLR_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jff_BCLR_l_imm(RW4 d, IMM s)); +DECLARE_MIDFUNC(jff_BCLR_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jff_BCLR_l_imm(RW4 d, IM8 s)); DECLARE_MIDFUNC(jff_BCLR_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jff_BCLR_l(RW4 d, RR4 s)); // BSET -DECLARE_MIDFUNC(jnf_BSET_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jnf_BSET_l_imm(RW4 d, IMM s)); +DECLARE_MIDFUNC(jnf_BSET_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jnf_BSET_l_imm(RW4 d, IM8 s)); DECLARE_MIDFUNC(jnf_BSET_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jnf_BSET_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_BSET_b_imm(RW1 d, IMM s)); -DECLARE_MIDFUNC(jff_BSET_l_imm(RW4 d, IMM s)); +DECLARE_MIDFUNC(jff_BSET_b_imm(RW1 d, IM8 s)); +DECLARE_MIDFUNC(jff_BSET_l_imm(RW4 d, IM8 s)); DECLARE_MIDFUNC(jff_BSET_b(RW1 d, RR4 s)); DECLARE_MIDFUNC(jff_BSET_l(RW4 d, RR4 s)); // BTST -DECLARE_MIDFUNC(jff_BTST_b_imm(RR1 d, IMM s)); -DECLARE_MIDFUNC(jff_BTST_l_imm(RR4 d, IMM s)); +DECLARE_MIDFUNC(jff_BTST_b_imm(RR1 d, IM8 s)); +DECLARE_MIDFUNC(jff_BTST_l_imm(RR4 d, IM8 s)); DECLARE_MIDFUNC(jff_BTST_b(RR1 d, RR4 s)); DECLARE_MIDFUNC(jff_BTST_l(RR4 d, RR4 s)); @@ -162,7 +160,7 @@ DECLARE_MIDFUNC(jff_CMPA_w(RR2 d, RR2 s)); DECLARE_MIDFUNC(jff_CMPA_l(RR4 d, RR4 s)); // DBCC -DECLARE_MIDFUNC(jff_DBCC(RW4 d, IMM cc)); +DECLARE_MIDFUNC(jff_DBCC(RW4 d, IM8 cc)); // DIVU DECLARE_MIDFUNC(jnf_DIVU(RW4 d, RR4 s)); @@ -179,21 +177,19 @@ DECLARE_MIDFUNC(jnf_DIVLS32(RW4 d, RR4 s1, W4 rem)); DECLARE_MIDFUNC(jff_DIVLS32(RW4 d, RR4 s1, W4 rem)); // EOR -DECLARE_MIDFUNC(jnf_EOR_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jnf_EOR_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jnf_EOR_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jnf_EOR_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jnf_EOR_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jnf_EOR_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jnf_EOR_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jnf_EOR_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_EOR_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jff_EOR_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jff_EOR_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jff_EOR_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jff_EOR_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jff_EOR_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jff_EOR_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_EOR_l(RW4 d, RR4 s)); // EORSR -DECLARE_MIDFUNC(jff_EORSR(IMM s, IMM x)); +DECLARE_MIDFUNC(jff_EORSR(IM32 s, IM8 x)); // EXT DECLARE_MIDFUNC(jnf_EXT_b(RW4 d)); @@ -204,15 +200,15 @@ DECLARE_MIDFUNC(jff_EXT_w(RW4 d)); DECLARE_MIDFUNC(jff_EXT_l(RW4 d)); // LSL -DECLARE_MIDFUNC(jnf_LSL_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jnf_LSL_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jnf_LSL_l_imm(RW4 d, IMM i)); +DECLARE_MIDFUNC(jnf_LSL_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jnf_LSL_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jnf_LSL_l_imm(RW4 d, IM8 i)); DECLARE_MIDFUNC(jnf_LSL_b_reg(RW1 d, RR4 i)); DECLARE_MIDFUNC(jnf_LSL_w_reg(RW2 d, RR4 i)); DECLARE_MIDFUNC(jnf_LSL_l_reg(RW4 d, RR4 i)); -DECLARE_MIDFUNC(jff_LSL_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jff_LSL_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jff_LSL_l_imm(RW4 d, IMM i)); +DECLARE_MIDFUNC(jff_LSL_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jff_LSL_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jff_LSL_l_imm(RW4 d, IM8 i)); DECLARE_MIDFUNC(jff_LSL_b_reg(RW1 d, RR4 i)); DECLARE_MIDFUNC(jff_LSL_w_reg(RW2 d, RR4 i)); DECLARE_MIDFUNC(jff_LSL_l_reg(RW4 d, RR4 i)); @@ -222,12 +218,12 @@ DECLARE_MIDFUNC(jff_LSLW(RW2 d)); DECLARE_MIDFUNC(jnf_LSLW(RW2 d)); // LSR -DECLARE_MIDFUNC(jnf_LSR_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jnf_LSR_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jnf_LSR_l_imm(RW4 d, IMM i)); -DECLARE_MIDFUNC(jff_LSR_b_imm(RW1 d, IMM i)); -DECLARE_MIDFUNC(jff_LSR_w_imm(RW2 d, IMM i)); -DECLARE_MIDFUNC(jff_LSR_l_imm(RW4 d, IMM i)); +DECLARE_MIDFUNC(jnf_LSR_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jnf_LSR_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jnf_LSR_l_imm(RW4 d, IM8 i)); +DECLARE_MIDFUNC(jff_LSR_b_imm(RW1 d, IM8 i)); +DECLARE_MIDFUNC(jff_LSR_w_imm(RW2 d, IM8 i)); +DECLARE_MIDFUNC(jff_LSR_l_imm(RW4 d, IM8 i)); DECLARE_MIDFUNC(jnf_LSR_b_reg(RW1 d, RR4 i)); DECLARE_MIDFUNC(jnf_LSR_w_reg(RW2 d, RR4 i)); DECLARE_MIDFUNC(jnf_LSR_l_reg(RW4 d, RR4 i)); @@ -240,26 +236,25 @@ DECLARE_MIDFUNC(jff_LSRW(RW2 d)); DECLARE_MIDFUNC(jnf_LSRW(RW2 d)); // MOVE -DECLARE_MIDFUNC(jnf_MOVE_b_imm(W4 d, IMM i)); -DECLARE_MIDFUNC(jnf_MOVE_w_imm(W4 d, IMM i)); -DECLARE_MIDFUNC(jnf_MOVE_l_imm(W4 d, IMM i)); +DECLARE_MIDFUNC(jnf_MOVE_b_imm(W4 d, IM8 i)); +DECLARE_MIDFUNC(jnf_MOVE_w_imm(W4 d, IM16 i)); DECLARE_MIDFUNC(jnf_MOVE_b(W4 d, RR1 s)); DECLARE_MIDFUNC(jnf_MOVE_w(W4 d, RR2 s)); DECLARE_MIDFUNC(jnf_MOVE_l(W4 d, RR4 s)); -DECLARE_MIDFUNC(jff_MOVE_b_imm(W4 d, IMM i)); -DECLARE_MIDFUNC(jff_MOVE_w_imm(W4 d, IMM i)); -DECLARE_MIDFUNC(jff_MOVE_l_imm(W4 d, IMM i)); +DECLARE_MIDFUNC(jff_MOVE_b_imm(W4 d, IM8 i)); +DECLARE_MIDFUNC(jff_MOVE_w_imm(W4 d, IM16 i)); +DECLARE_MIDFUNC(jff_MOVE_l_imm(W4 d, IM32 i)); DECLARE_MIDFUNC(jff_MOVE_b(W4 d, RR1 s)); DECLARE_MIDFUNC(jff_MOVE_w(W4 d, RR2 s)); DECLARE_MIDFUNC(jff_MOVE_l(W4 d, RR4 s)); // MVMEL -DECLARE_MIDFUNC(jnf_MVMEL_w(W4 d, RR4 s, IMM offset)); -DECLARE_MIDFUNC(jnf_MVMEL_l(W4 d, RR4 s, IMM offset)); +DECLARE_MIDFUNC(jnf_MVMEL_w(W4 d, RR4 s, IM8 offset)); +DECLARE_MIDFUNC(jnf_MVMEL_l(W4 d, RR4 s, IM8 offset)); // MVMLE -DECLARE_MIDFUNC(jnf_MVMLE_w(RR4 d, RR4 s, IMM offset)); -DECLARE_MIDFUNC(jnf_MVMLE_l(RR4 d, RR4 s, IMM offset)); +DECLARE_MIDFUNC(jnf_MVMLE_w(RR4 d, RR4 s, IM8 offset)); +DECLARE_MIDFUNC(jnf_MVMLE_l(RR4 d, RR4 s, IM8 offset)); // MOVE16 DECLARE_MIDFUNC(jnf_MOVE16(RR4 d, RR4 s)); @@ -309,21 +304,19 @@ DECLARE_MIDFUNC(jff_NOT_w(RW2 d)); DECLARE_MIDFUNC(jff_NOT_l(RW4 d)); // OR -DECLARE_MIDFUNC(jnf_OR_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jnf_OR_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jnf_OR_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jnf_OR_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jnf_OR_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jnf_OR_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jnf_OR_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jnf_OR_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_OR_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jff_OR_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jff_OR_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jff_OR_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jff_OR_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jff_OR_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jff_OR_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_OR_l(RW4 d, RR4 s)); // ORSR -DECLARE_MIDFUNC(jff_ORSR(IMM s, IMM x)); +DECLARE_MIDFUNC(jff_ORSR(IM32 s, IM8 x)); // ROL DECLARE_MIDFUNC(jnf_ROL_b(RW1 d, RR4 i)); @@ -366,18 +359,16 @@ DECLARE_MIDFUNC(jff_ROXR_w(RW2 d, RR4 i)); DECLARE_MIDFUNC(jff_ROXR_l(RW4 d, RR4 i)); // Scc -DECLARE_MIDFUNC(jnf_SCC(W1 d, IMM cc)); +DECLARE_MIDFUNC(jnf_SCC(W1 d, IM8 cc)); // SUB -DECLARE_MIDFUNC(jnf_SUB_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jnf_SUB_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jnf_SUB_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jnf_SUB_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jnf_SUB_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jnf_SUB_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jnf_SUB_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jnf_SUB_l(RW4 d, RR4 s)); -DECLARE_MIDFUNC(jff_SUB_b_imm(RW1 d, IMM v)); -DECLARE_MIDFUNC(jff_SUB_w_imm(RW2 d, IMM v)); -DECLARE_MIDFUNC(jff_SUB_l_imm(RW4 d, IMM v)); +DECLARE_MIDFUNC(jff_SUB_b_imm(RW1 d, IM8 v)); +DECLARE_MIDFUNC(jff_SUB_w_imm(RW2 d, IM16 v)); DECLARE_MIDFUNC(jff_SUB_b(RW1 d, RR1 s)); DECLARE_MIDFUNC(jff_SUB_w(RW2 d, RR2 s)); DECLARE_MIDFUNC(jff_SUB_l(RW4 d, RR4 s)); @@ -421,5 +412,5 @@ DECLARE_MIDFUNC(jnf_MEM_READ24_OFF_l(W4 d, RR4 adr)); DECLARE_MIDFUNC(jnf_MEM_GETADR_OFF(W4 d, RR4 adr)); DECLARE_MIDFUNC(jnf_MEM_GETADR24_OFF(W4 d, RR4 adr)); -DECLARE_MIDFUNC(jnf_MEM_READMEMBANK(W4 dest, RR4 adr, IMM offset)); -DECLARE_MIDFUNC(jnf_MEM_WRITEMEMBANK(RR4 adr, RR4 source, IMM offset)); +DECLARE_MIDFUNC(jnf_MEM_READMEMBANK(W4 dest, RR4 adr, IM8 offset)); +DECLARE_MIDFUNC(jnf_MEM_WRITEMEMBANK(RR4 adr, RR4 source, IM8 offset)); diff --git a/src/jit/compemu_midfunc_armA64.cpp.in b/src/jit/compemu_midfunc_armA64.cpp.in new file mode 100644 index 00000000..57d7a4bd --- /dev/null +++ b/src/jit/compemu_midfunc_armA64.cpp.in @@ -0,0 +1,1105 @@ +/* + * compiler/compemu_midfunc_armA64.cpp - Native MIDFUNCS for AARCH64 + * + * Copyright (c) 2019 TomB + * + * Inspired by Christian Bauer's Basilisk II + * + * Original 68040 JIT compiler for UAE, copyright 2000-2002 Bernd Meyer + * + * Adaptation for Basilisk II and improvements, copyright 2000-2002 + * Gwenole Beauchesne + * + * Basilisk II (C) 1997-2002 Christian Bauer + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Note: + * File is included by compemu_support.cpp + * + */ + +/******************************************************************** + * CPU functions exposed to gencomp. Both CREATE and EMIT time * + ********************************************************************/ + +/* + * RULES FOR HANDLING REGISTERS: + * + * * In the function headers, order the parameters + * - 1st registers written to + * - 2nd read/modify/write registers + * - 3rd registers read from + * * Before calling raw_*, you must call readreg, writereg or rmw for + * each register + * * The order for this is + * - 1nd call readreg for all registers read without offset + * - 2rd call rmw for all rmw registers + * - 3th call writereg for all written-to registers + * - 4th call raw_* + * - 5th unlock2 all registers that were locked + */ + +#define INIT_REGS_b(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = rmw(d); \ + if(s_is_d) \ + s = d; + +#define INIT_RREGS_b(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = readreg(d); \ + if(s_is_d) \ + s = d; + +#define INIT_REG_b(d) \ + int targetIsReg = (d < 16); \ + d = rmw(d); + +#define INIT_RREG_b(d) \ + int targetIsReg = (d < 16); \ + d = readreg(d); + +#define INIT_WREG_b(d) \ + int targetIsReg = (d < 16); \ + if(targetIsReg) \ + d = rmw(d); \ + else \ + d = writereg(d); + +#define INIT_REGS_w(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = rmw(d); \ + if(s_is_d) \ + s = d; + +#define INIT_RREGS_w(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = readreg(d); \ + if(s_is_d) \ + s = d; + +#define INIT_REG_w(d) \ + int targetIsReg = (d < 16); \ + d = rmw(d); + +#define INIT_RREG_w(d) \ + int targetIsReg = (d < 16); \ + d = readreg(d); + +#define INIT_WREG_w(d) \ + int targetIsReg = (d < 16); \ + if(targetIsReg) \ + d = rmw(d); \ + else \ + d = writereg(d); + +#define INIT_REGS_l(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = rmw(d); \ + if(s_is_d) \ + s = d; + +#define INIT_RREGS_l(d,s) \ + int targetIsReg = (d < 16); \ + int s_is_d = (s == d); \ + if(!s_is_d) \ + s = readreg(s); \ + d = readreg(d); \ + if(s_is_d) \ + s = d; + +#define EXIT_REGS(d,s) \ + unlock2(d); \ + if(!s_is_d) \ + unlock2(s); + + +MIDFUNC(0,live_flags,(void)) +{ + live.flags_on_stack = TRASH; + live.flags_in_flags = VALID; + live.flags_are_important = 1; +} +MENDFUNC(0,live_flags,(void)) + +MIDFUNC(0,dont_care_flags,(void)) +{ + live.flags_are_important = 0; +} +MENDFUNC(0,dont_care_flags,(void)) + +MIDFUNC(0,make_flags_live,(void)) +{ + make_flags_live_internal(); +} +MENDFUNC(0,make_flags_live,(void)) + +MIDFUNC(2,mov_l_mi,(IMPTR d, IM32 s)) +{ + /* d points always to memory in regs struct */ + LOAD_U32(REG_WORK2, s); + uintptr idx = d - (uintptr) ®s; + if(d == (uintptr) &(regs.pc_p) || d == (uintptr) &(regs.pc_oldp)) + STR_xXi(REG_WORK2, R_REGSTRUCT, idx); + else + STR_wXi(REG_WORK2, R_REGSTRUCT, idx); +} +MENDFUNC(2,mov_l_mi,(IMPTR d, IM32 s)) + +MIDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IM8 shift, IM8 extend)) +{ + if(isconst(target) && isconst(reg)) { + if(extend) + set_const(target, live.state[target].val + (((uae_s32)(uae_s16)live.state[reg].val) << (shift & 0x1f))); + else + set_const(target, live.state[target].val + (live.state[reg].val << (shift & 0x1f))); + return; + } + + reg = readreg(reg); + target = rmw(target); + + if(extend) { + SIGNED16_REG_2_REG(REG_WORK1, reg); + ADD_wwwLSLi(target, target, REG_WORK1, shift & 0x1f); + } else { + ADD_wwwLSLi(target, target, reg, shift & 0x1f); + } + + unlock2(target); + unlock2(reg); +} +MENDFUNC(4,disp_ea20_target_add,(RW4 target, RR4 reg, IM8 shift, IM8 extend)) + +MIDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IM8 shift, IM8 extend)) +{ + if(isconst(reg)) { + if(extend) + set_const(target, ((uae_s32)(uae_s16)live.state[reg].val) << (shift & 0x1f)); + else + set_const(target, live.state[reg].val << (shift & 0x1f)); + return; + } + + reg = readreg(reg); + target = writereg(target); + + if(extend) { + SIGNED16_REG_2_REG(REG_WORK1, reg); + LSL_wwi(target, REG_WORK1, shift & 0x1f); + } else { + LSL_wwi(target, reg, shift & 0x1f); + } + + unlock2(target); + unlock2(reg); +} +MENDFUNC(4,disp_ea20_target_mov,(W4 target, RR4 reg, IM8 shift, IM8 extend)) + +MIDFUNC(2,sign_extend_16_rr,(W4 d, RR2 s)) +{ + // Only used in calc_disp_ea_020() -> flags not relevant and never modified + if (isconst(s)) { + set_const(d, (uae_s32)(uae_s16)live.state[s].val); + return; + } + + int s_is_d = (s == d); + if (!s_is_d) { + s = readreg(s); + d = writereg(d); + } else { + s = d = rmw(s); + } + SIGNED16_REG_2_REG(d, s); + if (!s_is_d) + unlock2(d); + unlock2(s); +} +MENDFUNC(2,sign_extend_16_rr,(W4 d, RR2 s)) + +MIDFUNC(3,lea_l_brr,(W4 d, RR4 s, IM32 offset)) +{ + if (isconst(s)) { + COMPCALL(mov_l_ri)(d, live.state[s].val+offset); + return; + } + + int s_is_d = (s == d); + if(s_is_d) { + s = d = rmw(d); + } else { + s = readreg(s); + d = writereg(d); + } + + if(offset >= 0 && offset <= 0xfff) { + ADD_wwi(d, s, offset); + } else if(offset >= -0xfff && offset < 0) { + SUB_wwi(d, s, -offset); + } else { + LOAD_U32(REG_WORK1, offset); + ADD_www(d, s, REG_WORK1); + } + + EXIT_REGS(d,s); +} +MENDFUNC(3,lea_l_brr,(W4 d, RR4 s, IM32 offset)) + +MIDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor, IM8 offset)) +{ + if (!offset) { + COMPCALL(lea_l_rr_indexed)(d, s, index, factor); + return; + } + if (isconst(s) && isconst(index)) { + set_const(d, live.state[s].val + (uae_s32)(uae_s8)offset + live.state[index].val * factor); + return; + } + + s = readreg(s); + if(d == index) { + d = index = rmw(d); + } else { + index = readreg(index); + d = writereg(d); + } + + int shft; + switch(factor) { + case 1: shft=0; break; + case 2: shft=1; break; + case 4: shft=2; break; + case 8: shft=3; break; + default: abort(); + } + + if(offset >= 0 && offset <= 127) { + ADD_wwi(REG_WORK1, s, offset); + } else { + SUB_wwi(REG_WORK1, s, -offset); + } + ADD_wwwLSLi(d, REG_WORK1, index, shft); + + unlock2(d); + if(d != index) + unlock2(index); + unlock2(s); +} +MENDFUNC(5,lea_l_brr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor, IM8 offset)) + +MIDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor)) +{ + if (isconst(s) && isconst(index)) { + set_const(d, live.state[s].val + live.state[index].val * factor); + return; + } + + s = readreg(s); + if(d == index) { + d = index = rmw(d); + } else { + index = readreg(index); + d = writereg(d); + } + + int shft; + switch(factor) { + case 1: shft=0; break; + case 2: shft=1; break; + case 4: shft=2; break; + case 8: shft=3; break; + default: abort(); + } + + ADD_wwwLSLi(d, s, index, shft); + + unlock2(d); + if(d != index) + unlock2(index); + unlock2(s); +} +MENDFUNC(4,lea_l_rr_indexed,(W4 d, RR4 s, RR4 index, IM8 factor)) + +MIDFUNC(2,mov_l_rr,(W4 d, RR4 s)) +{ + int olds; + + if (d == s) { /* How pointless! */ + return; + } + if (isconst(s)) { + COMPCALL(mov_l_ri)(d, live.state[s].val); + return; + } + olds = s; + disassociate(d); + s = readreg(s); + live.state[d].realreg = s; + live.state[d].realind = live.nat[s].nholds; + live.state[d].val = 0; + set_status(d, DIRTY); + + live.nat[s].holds[live.nat[s].nholds] = d; + live.nat[s].nholds++; + unlock2(s); +} +MENDFUNC(2,mov_l_rr,(W4 d, RR4 s)) + +MIDFUNC(2,mov_l_mr,(IMPTR d, RR4 s)) +{ + /* d points always to memory in regs struct */ + if (isconst(s)) { + COMPCALL(mov_l_mi)(d, live.state[s].val); + return; + } + + s = readreg(s); + + uintptr idx = d - (uintptr) ®s; + if(d == (uintptr)®s.pc_oldp || d == (uintptr)®s.pc_p) + STR_xXi(s, R_REGSTRUCT, idx); + else + STR_wXi(s, R_REGSTRUCT, idx); + + unlock2(s); +} +MENDFUNC(2,mov_l_mr,(IMPTR d, RR4 s)) + +MIDFUNC(2,mov_l_rm,(W4 d, IMPTR s)) +{ + /* s points always to memory in regs struct */ + d = writereg(d); + + uintptr idx = s - (uintptr) ®s; + LDR_wXi(d, R_REGSTRUCT, idx); + + unlock2(d); +} +MENDFUNC(2,mov_l_rm,(W4 d, IMPTR s)) + +MIDFUNC(2,mov_l_ri,(W4 d, IM32 s)) +{ + set_const(d, s); +} +MENDFUNC(2,mov_l_ri,(W4 d, IM32 s)) + +MIDFUNC(2,mov_b_ri,(W1 d, IM8 s)) +{ + if(d < 16) { + if (isconst(d)) { + set_const(d, (live.state[d].val & 0xffffff00) | (s & 0x000000ff)); + return; + } + d = rmw(d); + + MOV_xi(REG_WORK1, (s & 0xff)); + BFI_xxii(d, REG_WORK1, 0, 8); + + unlock2(d); + } else { + set_const(d, s & 0xff); + } +} +MENDFUNC(2,mov_b_ri,(W1 d, IM8 s)) + +MIDFUNC(2,sub_l_ri,(RW4 d, IM8 i)) +{ + if (!i) + return; + if (isconst(d)) { + live.state[d].val -= i; + return; + } + + d = rmw(d); + + SUB_xxi(d, d, i); + + unlock2(d); +} +MENDFUNC(2,sub_l_ri,(RW4 d, IM8 i)) + +MIDFUNC(2,sub_w_ri,(RW2 d, IM8 i)) +{ + // This function is only called with i = 1 + // Caller needs flags... + clobber_flags(); + + d = rmw(d); + + LSL_wwi(REG_WORK2, d, 16); + + SUBS_wwish(REG_WORK2, REG_WORK2, (i & 0xff) << 4, 1); + BFXIL_xxii(d, REG_WORK2, 16, 16); + + unlock2(d); +} +MENDFUNC(2,sub_w_ri,(RW2 d, IM8 i)) + +/* forget_about() takes a mid-layer register */ +MIDFUNC(1,forget_about,(W4 r)) +{ + if (isinreg(r)) + disassociate(r); + live.state[r].val = 0; + set_status(r, UNDEF); +} +MENDFUNC(1,forget_about,(W4 r)) + + +MIDFUNC(2,arm_ADD_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(arm_ADD_l_ri)(d,live.state[s].val); + return; + } + + s = readreg(s); + d = rmw(d); + ADD_www(d, d, s); + unlock2(d); + unlock2(s); +} +MENDFUNC(2,arm_ADD_l,(RW4 d, RR4 s)) + +MIDFUNC(2,arm_ADD_l_ri,(RW4 d, IM32 i)) +{ + if (!i) + return; + if (isconst(d)) { + live.state[d].val += i; + return; + } + + d = rmw(d); + + if(i >= 0 && i <= 0xfff) { + ADD_xxi(d, d, i); + } else { + if(i > -0x7fff && i < 0x7fff) { + SIGNED16_IMM_2_REG(REG_WORK1, i); + } else { + LOAD_U32(REG_WORK1, i); + SXTW_xw(REG_WORK1, REG_WORK1); + } + ADD_xxx(d, d, REG_WORK1); + } + + unlock2(d); +} +MENDFUNC(2,arm_ADD_l_ri,(RW4 d, IM32 i)) + +MIDFUNC(2,arm_ADD_l_ri8,(RW4 d, IM8 i)) +{ + if (!i) + return; + if (isconst(d)) { + live.state[d].val += i; + return; + } + + d = rmw(d); + ADD_xxi(d, d, i); + unlock2(d); +} +MENDFUNC(2,arm_ADD_l_ri8,(RW4 d, IM8 i)) + +MIDFUNC(2,arm_SUB_l_ri8,(RW4 d, IM8 i)) +{ + if (!i) + return; + if (isconst(d)) { + live.state[d].val -= i; + return; + } + + d = rmw(d); + SUB_xxi(d, d, i); + unlock2(d); +} +MENDFUNC(2,arm_SUB_l_ri8,(RW4 d, IM8 i)) + + +#ifdef JIT_DEBUG +#include "aarch64.h" + +void disam_range(void *start, void *stop) +{ + char disbuf[256]; + uint64_t disptr = (uint64_t)start; + while(disptr < (uint64_t)stop) { + disasm(disptr, disbuf); + write_log("%016llx %s\n", disptr, disbuf); + disptr += 4; + } +} + +#endif + +STATIC_INLINE void flush_cpu_icache(void *start, void *stop) +{ +#ifdef JIT_DEBUG + if((uae_u64)stop - (uae_u64)start > 4) { + if(disasm_this) { + char disbuf[256]; + uint64_t disptr = (uint64_t)start; + while(disptr < (uint64_t)stop) { + disasm(disptr, disbuf); + write_log("%016llx %s\n", disptr, disbuf); + disptr += 4; + } + disasm_this = false; + } + } +#endif + + //__builtin___clear_cache(start, stop); + __clear_cache(start, stop); +} + + +STATIC_INLINE void write_jmp_target(uae_u32* jmpaddr, uintptr a) +{ + uintptr off = (a - (uintptr)jmpaddr) >> 2; + if((*(jmpaddr) & 0xfc000000) == 0x14000000) { + /* branch always */ + off = off & 0x3ffffff; + *(jmpaddr) = (*(jmpaddr) & 0xfc000000) | off; + } else if((*(jmpaddr) & 0x7c000000) == 0x34000000) { + /* TBZ/TBNZ/CBZ/CBNZ */ + if((a > (uintptr)jmpaddr && off > 0x1fff) || (a < (uintptr)jmpaddr && (~off) > 0x1fff)) + write_log("JIT: TBZ/TBNZ branch to target too long.\n"); + off = off & 0x3fff; + *(jmpaddr) = (*(jmpaddr) & 0xfffc001f) | (off << 5); + } else { + /* conditional branch */ + if((a > (uintptr)jmpaddr && off > 0x3ffff) || (a < (uintptr)jmpaddr && (~off) > 0x3ffff)) + write_log("JIT: Branch to target too long.\n"); + off = off & 0x7ffff; + *(jmpaddr) = (*(jmpaddr) & 0xff00001f) | (off << 5); + } + + flush_cpu_icache((void *)jmpaddr, (void *)&jmpaddr[1]); +} + + +/************************************************************************* +* FPU stuff * +*************************************************************************/ + +#ifdef USE_JIT_FPU + +MIDFUNC(1,f_forget_about,(FW r)) +{ + if (f_isinreg(r)) + f_disassociate(r); + live.fate[r].status = UNDEF; +} +MENDFUNC(1,f_forget_about,(FW r)) + +MIDFUNC(0,dont_care_fflags,(void)) +{ + f_disassociate(FP_RESULT); +} +MENDFUNC(0,dont_care_fflags,(void)) + +MIDFUNC(2,fmov_rr,(FW d, FR s)) +{ + if (d == s) { /* How pointless! */ + return; + } + s = f_readreg(s); + d = f_writereg(d); + raw_fmov_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fmov_rr,(FW d, FR s)) + +MIDFUNC(2,fmov_l_rr,(FW d, RR4 s)) +{ + s = readreg(s); + d = f_writereg(d); + raw_fmov_l_rr(d, s); + f_unlock(d); + unlock2(s); +} +MENDFUNC(2,fmov_l_rr,(FW d, RR4 s)) + +MIDFUNC(2,fmov_s_rr,(FW d, RR4 s)) +{ + s = readreg(s); + d = f_writereg(d); + raw_fmov_s_rr(d, s); + f_unlock(d); + unlock2(s); +} +MENDFUNC(2,fmov_s_rr,(FW d, RR4 s)) + +MIDFUNC(2,fmov_w_rr,(FW d, RR2 s)) +{ + s = readreg(s); + d = f_writereg(d); + raw_fmov_w_rr(d, s); + f_unlock(d); + unlock2(s); +} +MENDFUNC(2,fmov_w_rr,(FW d, RR2 s)) + +MIDFUNC(2,fmov_b_rr,(FW d, RR1 s)) +{ + s = readreg(s); + d = f_writereg(d); + raw_fmov_b_rr(d, s); + f_unlock(d); + unlock2(s); +} +MENDFUNC(2,fmov_b_rr,(FW d, RR1 s)) + +MIDFUNC(3,fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) +{ + s1 = readreg(s1); + s2 = readreg(s2); + d = f_writereg(d); + raw_fmov_d_rrr(d, s1, s2); + f_unlock(d); + unlock2(s2); + unlock2(s1); +} +MENDFUNC(3,fmov_d_rrr,(FW d, RR4 s1, RR4 s2)) + +MIDFUNC(2,fmov_l_ri,(FW d, IM32 i)) +{ + switch(i) { + case 0: + fmov_d_ri_0(d); + break; + case 1: + fmov_d_ri_1(d); + break; + case 10: + fmov_d_ri_10(d); + break; + case 100: + fmov_d_ri_100(d); + break; + default: + d = f_writereg(d); + compemu_raw_mov_l_ri(REG_WORK1, i); + raw_fmov_l_rr(d, REG_WORK1); + f_unlock(d); + } +} +MENDFUNC(2,fmov_l_ri,(FW d, IM32 i)) + +MIDFUNC(2,fmov_s_ri,(FW d, IM32 i)) +{ + d = f_writereg(d); + compemu_raw_mov_l_ri(REG_WORK1, i); + raw_fmov_s_rr(d, REG_WORK1); + f_unlock(d); +} +MENDFUNC(2,fmov_s_ri,(FW d, IM32 i)) + +MIDFUNC(2,fmov_to_l_rr,(W4 d, FR s)) +{ + s = f_readreg(s); + d = writereg(d); + raw_fmov_to_l_rr(d, s); + unlock2(d); + f_unlock(s); +} +MENDFUNC(2,fmov_to_l_rr,(W4 d, FR s)) + +MIDFUNC(2,fmov_to_s_rr,(W4 d, FR s)) +{ + s = f_readreg(s); + d = writereg(d); + raw_fmov_to_s_rr(d, s); + unlock2(d); + f_unlock(s); +} +MENDFUNC(2,fmov_to_s_rr,(W4 d, FR s)) + +MIDFUNC(2,fmov_to_w_rr,(W4 d, FR s)) +{ + s = f_readreg(s); + INIT_WREG_w(d); + + raw_fmov_to_w_rr(d, s, targetIsReg); + unlock2(d); + f_unlock(s); +} +MENDFUNC(2,fmov_to_w_rr,(W4 d, FR s)) + +MIDFUNC(2,fmov_to_b_rr,(W4 d, FR s)) +{ + s = f_readreg(s); + INIT_WREG_b(d); + + raw_fmov_to_b_rr(d, s, targetIsReg); + unlock2(d); + f_unlock(s); +} +MENDFUNC(2,fmov_to_b_rr,(W4 d, FR s)) + +MIDFUNC(1,fmov_d_ri_0,(FW r)) +{ + r = f_writereg(r); + raw_fmov_d_ri_0(r); + f_unlock(r); +} +MENDFUNC(1,fmov_d_ri_0,(FW r)) + +MIDFUNC(1,fmov_d_ri_1,(FW r)) +{ + r = f_writereg(r); + raw_fmov_d_ri_1(r); + f_unlock(r); +} +MENDFUNC(1,fmov_d_ri_1,(FW r)) + +MIDFUNC(1,fmov_d_ri_10,(FW r)) +{ + r = f_writereg(r); + raw_fmov_d_ri_10(r); + f_unlock(r); +} +MENDFUNC(1,fmov_d_ri_10,(FW r)) + +MIDFUNC(1,fmov_d_ri_100,(FW r)) +{ + r = f_writereg(r); + raw_fmov_d_ri_100(r); + f_unlock(r); +} +MENDFUNC(1,fmov_d_ri_100,(FW r)) + +MIDFUNC(2,fmov_d_rm,(FW r, MEMR m)) +{ + r = f_writereg(r); + raw_fmov_d_rm(r, m); + f_unlock(r); +} +MENDFUNC(2,fmov_d_rm,(FW r, MEMR m)) + +MIDFUNC(2,fmovs_rm,(FW r, MEMR m)) +{ + r = f_writereg(r); + raw_fmovs_rm(r, m); + f_unlock(r); +} +MENDFUNC(2,fmovs_rm,(FW r, MEMR m)) + +MIDFUNC(2,fmov_rm,(FW r, MEMR m)) +{ + r = f_writereg(r); + raw_fmov_d_rm(r, m); + f_unlock(r); +} +MENDFUNC(2,fmov_rm,(FW r, MEMR m)) + +MIDFUNC(3,fmov_to_d_rrr,(W4 d1, W4 d2, FR s)) +{ + s = f_readreg(s); + d1 = writereg(d1); + d2 = writereg(d2); + raw_fmov_to_d_rrr(d1, d2, s); + unlock2(d2); + unlock2(d1); + f_unlock(s); +} +MENDFUNC(3,fmov_to_d_rrr,(W4 d1, W4 d2, FR s)) + +MIDFUNC(2,fsqrt_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_fsqrt_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fsqrt_rr,(FW d, FR s)) + +MIDFUNC(2,fabs_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_fabs_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fabs_rr,(FW d, FR s)) + +MIDFUNC(2,fneg_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_fneg_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fneg_rr,(FW d, FR s)) + +MIDFUNC(2,fdiv_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fdiv_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fdiv_rr,(FRW d, FR s)) + +MIDFUNC(2,fadd_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fadd_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fadd_rr,(FRW d, FR s)) + +MIDFUNC(2,fmul_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fmul_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fmul_rr,(FRW d, FR s)) + +MIDFUNC(2,fsub_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fsub_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fsub_rr,(FRW d, FR s)) + +MIDFUNC(2,frndint_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_frndint_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,frndint_rr,(FW d, FR s)) + +MIDFUNC(2,frndintz_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_frndintz_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,frndintz_rr,(FW d, FR s)) + +MIDFUNC(2,fmod_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fmod_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fmod_rr,(FRW d, FR s)) + +MIDFUNC(2,fsgldiv_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fsgldiv_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fsgldiv_rr,(FRW d, FR s)) + +MIDFUNC(1,fcuts_r,(FRW r)) +{ + r = f_rmw(r); + raw_fcuts_r(r); + f_unlock(r); +} +MENDFUNC(1,fcuts_r,(FRW r)) + +MIDFUNC(2,frem1_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_frem1_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,frem1_rr,(FRW d, FR s)) + +MIDFUNC(2,fsglmul_rr,(FRW d, FR s)) +{ + s = f_readreg(s); + d = f_rmw(d); + raw_fsglmul_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fsglmul_rr,(FRW d, FR s)) + +MIDFUNC(2,fmovs_rr,(FW d, FR s)) +{ + s = f_readreg(s); + d = f_writereg(d); + raw_fmovs_rr(d, s); + f_unlock(s); + f_unlock(d); +} +MENDFUNC(2,fmovs_rr,(FW d, FR s)) + +MIDFUNC(3,ffunc_rr,(double (*func)(double), FW d, FR s)) +{ + clobber_flags(); + + s = f_readreg(s); + int reald = f_writereg(d); + + prepare_for_call_1(); + + f_unlock(s); + f_unlock(reald); + + prepare_for_call_2(); + + raw_ffunc_rr(func, reald, s); + + live.fat[reald].holds = d; + live.fat[reald].nholds = 1; + + live.fate[d].realreg = reald; + live.fate[d].status = DIRTY; +} +MENDFUNC(3,ffunc_rr,(double (*func)(double), FW d, FR s)) + +MIDFUNC(3,fpowx_rr,(uae_u32 x, FW d, FR s)) +{ + clobber_flags(); + + s = f_readreg(s); + int reald = f_writereg(d); + + prepare_for_call_1(); + + f_unlock(s); + f_unlock(reald); + + prepare_for_call_2(); + + raw_fpowx_rr(x, reald, s); + + live.fat[reald].holds = d; + live.fat[reald].nholds = 1; + + live.fate[d].realreg = reald; + live.fate[d].status = DIRTY; +} +MENDFUNC(3,fpowx_rr,(uae_u32 x, FW d, FR s)) + +MIDFUNC(1,fflags_into_flags,()) +{ + clobber_flags(); + fflags_into_flags_internal(); +} +MENDFUNC(1,fflags_into_flags,()) + +MIDFUNC(2,fp_from_exten_mr,(RR4 adr, FR s)) +{ + clobber_flags(); + + adr = readreg(adr); + s = f_readreg(s); + raw_fp_from_exten_mr(adr, s); + f_unlock(s); + unlock2(adr); +} +MENDFUNC(2,fp_from_exten_mr,(RR4 adr, FR s)) + +MIDFUNC(2,fp_to_exten_rm,(FW d, RR4 adr)) +{ + clobber_flags(); + + adr = readreg(adr); + d = f_writereg(d); + raw_fp_to_exten_rm(d, adr); + unlock2(adr); + f_unlock(d); +} +MENDFUNC(2,fp_to_exten_rm,(FW d, RR4 adr)) + +MIDFUNC(2,fp_from_double_mr,(RR4 adr, FR s)) +{ + adr = readreg(adr); + s = f_readreg(s); + raw_fp_from_double_mr(adr, s); + f_unlock(s); + unlock2(adr); +} +MENDFUNC(2,fp_from_double_mr,(RR4 adr, FR s)) + +MIDFUNC(2,fp_to_double_rm,(FW d, RR4 adr)) +{ + adr = readreg(adr); + d = f_writereg(d); + raw_fp_to_double_rm(d, adr); + unlock2(adr); + f_unlock(d); +} +MENDFUNC(2,fp_to_double_rm,(FW d, RR4 adr)) + +MIDFUNC(2,fp_fscc_ri,(RW4 d, int cc)) +{ + d = rmw(d); + raw_fp_fscc_ri(d, cc); + unlock2(d); +} +MENDFUNC(2,fp_fscc_ri,(RW4 d, int cc)) + +MIDFUNC(1,roundingmode,(IM32 mode)) +{ + raw_roundingmode(mode); +} +MENDFUNC(1,roundingmode,(IM32 mode)) + + +#endif // USE_JIT_FPU diff --git a/src/jit/compemu_midfunc_armA64_2.cpp.in b/src/jit/compemu_midfunc_armA64_2.cpp.in new file mode 100644 index 00000000..5f94d736 --- /dev/null +++ b/src/jit/compemu_midfunc_armA64_2.cpp.in @@ -0,0 +1,6950 @@ +/* + * compiler/compemu_midfunc_arm.cpp - Native MIDFUNCS for AARCH64 (JIT v2) + * + * Copyright (c) 2019 TomB + * + * Inspired by Christian Bauer's Basilisk II + * + * Original 68040 JIT compiler for UAE, copyright 2000-2002 Bernd Meyer + * + * Adaptation for Basilisk II and improvements, copyright 2000-2002 + * Gwenole Beauchesne + * + * Basilisk II (C) 1997-2002 Christian Bauer + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Note: + * File is included by compemu_support.cpp + * + */ + +const uae_u32 ARM_CCR_MAP[] = { 0, ARM_C_FLAG, // 1 C + ARM_V_FLAG, // 2 V + ARM_C_FLAG | ARM_V_FLAG, // 3 VC + ARM_Z_FLAG, // 4 Z + ARM_Z_FLAG | ARM_C_FLAG, // 5 ZC + ARM_Z_FLAG | ARM_V_FLAG, // 6 ZV + ARM_Z_FLAG | ARM_C_FLAG | ARM_V_FLAG, // 7 ZVC + ARM_N_FLAG, // 8 N + ARM_N_FLAG | ARM_C_FLAG, // 9 NC + ARM_N_FLAG | ARM_V_FLAG, // 10 NV + ARM_N_FLAG | ARM_C_FLAG | ARM_V_FLAG, // 11 NVC + ARM_N_FLAG | ARM_Z_FLAG, // 12 NZ + ARM_N_FLAG | ARM_Z_FLAG | ARM_C_FLAG, // 13 NZC + ARM_N_FLAG | ARM_Z_FLAG | ARM_V_FLAG, // 14 NZV + ARM_N_FLAG | ARM_Z_FLAG | ARM_C_FLAG | ARM_V_FLAG, // 15 NZVC +}; + + +#define DUPLICACTE_CARRY \ + if (needed_flags & FLAG_X) { \ + int x = writereg(FLAGX); \ + if (flags_carry_inverted) \ + CSET_xc(x, NATIVE_CC_CC); \ + else \ + CSET_xc(x, NATIVE_CC_CS); \ + unlock2(x); \ + } + +/* + * ADD + * Operand Syntax: , Dn + * Dn, + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if an overflow is generated. Cleared otherwise. + * C Set if a carry is generated. Cleared otherwise. + * + */ +MIDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IM8 v)) +{ + int s_is_d = (s == d); + if(s_is_d) { + s = d = rmw(d); + } else { + s = readreg(s); + d = writereg(d); + } + + ADD_wwi(d, s, v & 0xff); + + EXIT_REGS(d, s); +} +MENDFUNC(3,jnf_ADD_im8,(W4 d, RR4 s, IM8 v)) + +MIDFUNC(2,jnf_ADD_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + if(targetIsReg) { + ADD_wwi(REG_WORK1, d, v & 0xff); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ADD_wwi(d, d, v & 0xff); + } + + unlock2(d); +} +MENDFUNC(2,jnf_ADD_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jnf_ADD_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_ADD_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + if(targetIsReg) { + ADD_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ADD_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_ADD_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_ADD_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + if(targetIsReg) { + if(v >= 0 && v <= 0xfff) { + ADD_wwi(REG_WORK1, d, v); + } else { + MOV_xi(REG_WORK1, v & 0xffff); + ADD_www(REG_WORK1, d, REG_WORK1); + } + BFI_xxii(d, REG_WORK1, 0, 16); + } else{ + if(v >= 0 && v <= 0xfff) { + ADD_wwi(d, d, v); + } else { + MOV_xi(REG_WORK1, v & 0xffff); + ADD_www(d, d, REG_WORK1); + } + } + + unlock2(d); +} +MENDFUNC(2,jnf_ADD_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jnf_ADD_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_ADD_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + if(targetIsReg) { + ADD_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ADD_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_ADD_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_ADD_l_imm,(RW4 d, IM32 v)) +{ + if (isconst(d)) { + live.state[d].val = live.state[d].val + v; + return; + } + + d = rmw(d); + + if(v >= 0 && v <= 0xfff) { + ADD_wwi(d, d, v); + } else { + // never reached... + LOAD_U32(REG_WORK1, v); + ADD_www(d, d, REG_WORK1); + } + + unlock2(d); +} +MENDFUNC(2,jnf_ADD_l_imm,(RW4 d, IM32 v)) + +MIDFUNC(2,jnf_ADD_l,(RW4 d, RR4 s)) +{ + if (isconst(d) && isconst(s)) { + COMPCALL(jnf_ADD_l_imm)(d, live.state[s].val); + return; + } + if (isconst(s) && (uae_s32)live.state[s].val >= 0 && (uae_s32)live.state[s].val <= 0xfff) { + COMPCALL(jnf_ADD_l_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_l(d, s); + + ADD_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_ADD_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_ADD_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + MOV_xish(REG_WORK2, (v & 0xff) << 8, 16); + ADDS_wwwLSLi(REG_WORK1, REG_WORK2, d, 24); + BFXIL_xxii(d, REG_WORK1, 24, 8); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(2,jff_ADD_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jff_ADD_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_ADD_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + LSL_wwi(REG_WORK2, s, 24); + ADDS_wwwLSLi(REG_WORK1, REG_WORK2, d, 24); + BFXIL_xxii(d, REG_WORK1, 24, 8); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADD_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_ADD_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + MOV_xish(REG_WORK1, v & 0xffff, 16); + ADDS_wwwLSLi(REG_WORK1, REG_WORK1, d, 16); + BFXIL_xxii(d, REG_WORK1, 16, 16); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(2,jff_ADD_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jff_ADD_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_ADD_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + LSL_wwi(REG_WORK1, s, 16); + ADDS_wwwLSLi(REG_WORK1, REG_WORK1, d, 16); + BFXIL_xxii(d, REG_WORK1, 16, 16); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADD_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_ADD_l_imm,(RW4 d, IM32 v)) +{ + d = rmw(d); + + if(v >= 0 && v <= 0xfff) { + ADDS_wwi(d, d, v); + } else { + // never reached... + LOAD_U32(REG_WORK2, v); + ADDS_www(d, d, REG_WORK2); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(2,jff_ADD_l_imm,(RW4 d, IM32 v)) + +MIDFUNC(2,jff_ADD_l,(RW4 d, RR4 s)) +{ + if (isconst(s) && (uae_s32)live.state[s].val >= 0 && (uae_s32)live.state[s].val <= 0xfff) { + COMPCALL(jff_ADD_l_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_l(d, s); + + ADDS_www(d, d, s); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADD_l,(RW4 d, RR4 s)) + +/* + * ADDA + * Operand Syntax: , An + * + * Operand Size: 16,32 + * + * Flags: Not affected. + * + */ +MIDFUNC(2,jnf_ADDA_w,(RW4 d, RR2 s)) +{ + if (isconst(d) && isconst(s)) { + live.state[d].val = live.state[d].val + (uae_s32)(uae_s16)(live.state[s].val & 0xffff); + return; + } + if (isconst(s)) { + // no need to put virt. register s into a real host register via readreg() + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + if(tmp >= 0 && tmp <= 0xfff) { + ADD_wwi(d, d, tmp); + } else if (tmp >= -0xfff && tmp < 0) { + SUB_wwi(d, d, -tmp); + } else { + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + ADD_www(d, d, REG_WORK1); + } + unlock2(d); + return; + } + + INIT_REGS_w(d, s); + + ADD_wwwEX(d, d, s, EX_SXTH); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_ADDA_w,(RW4 d, RR2 s)) + +MIDFUNC(2,jnf_ADDA_l,(RW4 d, RR4 s)) +{ + if (isconst(d) && isconst(s)) { + set_const(d, live.state[d].val + live.state[s].val); + return; + } + if (isconst(s) && (uae_s32)live.state[s].val >= 0 && (uae_s32)live.state[s].val <= 0xfff) { + uae_s32 tmp = (uae_s32)live.state[s].val; + d = rmw(d); + ADD_wwi(d, d, tmp); + unlock2(d); + return; + } + + INIT_REGS_l(d, s); + + ADD_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_ADDA_l,(RW4 d, RR4 s)) + +/* + * ADDX + * Operand Syntax: Dy, Dx + * -(Ay), -(Ax) + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Cleared if the result is nonzero; unchanged otherwise. + * V Set if an overflow is generated. Cleared otherwise. + * C Set if a carry is generated. Cleared otherwise. + * + * Attention: Z is cleared only if the result is nonzero. Unchanged otherwise + * + */ +MIDFUNC(2,jnf_ADDX_b,(RW1 d, RR1 s)) +{ + int x = readreg(FLAGX); + + INIT_REGS_b(d, s); + + if(s_is_d) { + ADD_wwwLSLi(REG_WORK1, x, d, 1); + } else { + ADD_www(REG_WORK1, d, s); + ADD_www(REG_WORK1, REG_WORK1, x); + } + BFI_xxii(d, REG_WORK1, 0, 8); + + EXIT_REGS(d, s); + unlock2(x); +} +MENDFUNC(2,jnf_ADDX_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_ADDX_w,(RW2 d, RR2 s)) +{ + int x = readreg(FLAGX); + + INIT_REGS_w(d, s); + + if(s_is_d) { + ADD_wwwLSLi(REG_WORK1, x, d, 1); + } else { + ADD_www(REG_WORK1, d, s); + ADD_www(REG_WORK1, REG_WORK1, x); + } + BFI_xxii(d, REG_WORK1, 0, 16); + + EXIT_REGS(d, s); + unlock2(x); +} +MENDFUNC(2,jnf_ADDX_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_ADDX_l,(RW4 d, RR4 s)) +{ + int x = readreg(FLAGX); + + if(s != d && isconst(s) && live.state[s].val >= 0 && live.state[s].val <= 0xfff) { + d = rmw(d); + ADD_wwi(d, d, live.state[s].val); + ADD_www(d, d, x); + unlock2(d); + unlock2(x); + return; + } + + INIT_REGS_l(d, s); + + if(s_is_d) { + ADD_wwwLSLi(d, x, d, 1); + } else { + ADD_www(d, d, s); + ADD_www(d, d, x); + } + + EXIT_REGS(d, s); + unlock2(x); +} +MENDFUNC(2,jnf_ADDX_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_ADDX_b,(RW1 d, RR1 s)) +{ + INIT_REGS_b(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK1, 0); + MOVN_xish(REG_WORK2, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK2, REG_WORK1, NATIVE_CC_NE); + + // Restore X to carry (don't care about other flags) + SUBS_wwi(REG_WORK3, x, 1); + + BFI_xxii(REG_WORK1, s, 24, 8); + LSL_wwi(REG_WORK3, d, 24); + ADCS_www(REG_WORK1, REG_WORK1, REG_WORK3); + BFXIL_xxii(d, REG_WORK1, 24, 8); + + MRS_NZCV_x(REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + MSR_NZCV_x(REG_WORK1); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADDX_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_ADDX_w,(RW2 d, RR2 s)) +{ + INIT_REGS_w(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK1, 0); + MOVN_xish(REG_WORK2, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK2, REG_WORK1, NATIVE_CC_NE); + + // Restore X to carry (don't care about other flags) + SUBS_wwi(REG_WORK3, x, 1); + + BFI_xxii(REG_WORK1, s, 16, 16); + LSL_wwi(REG_WORK3, d, 16); + ADCS_www(REG_WORK1, REG_WORK1, REG_WORK3); + BFXIL_xxii(d, REG_WORK1, 16, 16); + + MRS_NZCV_x(REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + MSR_NZCV_x(REG_WORK1); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADDX_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_ADDX_l,(W4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK1, 0); + MOVN_xish(REG_WORK2, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK2, REG_WORK1, NATIVE_CC_NE); + + // Restore X to carry (don't care about other flags) + SUBS_wwi(REG_WORK3, x, 1); + + ADCS_www(d, d, s); + + MRS_NZCV_x(REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + MSR_NZCV_x(REG_WORK1); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_ADDX_l,(W4 d, RR4 s)) + +/* + * ANDSR + * Operand Syntax: #, CCR + * + * Operand Size: 8 + * + * X Cleared if bit 4 of immediate operand is zero. Unchanged otherwise. + * N Cleared if bit 3 of immediate operand is zero. Unchanged otherwise. + * Z Cleared if bit 2 of immediate operand is zero. Unchanged otherwise. + * V Cleared if bit 1 of immediate operand is zero. Unchanged otherwise. + * C Cleared if bit 0 of immediate operand is zero. Unchanged otherwise. + * + */ +MIDFUNC(2,jff_ANDSR,(IM32 s, IM8 x)) +{ + MRS_NZCV_x(REG_WORK1); + if(flags_carry_inverted) { + EOR_xxCflag(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + MOV_xish(REG_WORK2, (s >> 16), 16); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + + if (!x) { + int f = writereg(FLAGX); + MOV_xi(f, 0); + unlock2(f); + } +} +MENDFUNC(2,jff_ANDSR,(IM32 s, IM8 x)) + +/* + * AND + * Operand Syntax: , Dn + * Dn, + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_AND_b_imm,(RW1 d, IM8 v)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val & v) & 0x000000ff); + return; + } + + INIT_REG_b(d); + + MOVN_xi(REG_WORK1, (~v) & 0xff); + AND_www(d, d, REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jnf_AND_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jnf_AND_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_AND_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + if(targetIsReg) { + AND_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + AND_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_AND_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_AND_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + MOVN_xi(REG_WORK1, (~v)); + AND_www(d, d, REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jnf_AND_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jnf_AND_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_AND_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + if(targetIsReg) { + AND_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + AND_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_AND_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_AND_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + AND_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_AND_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_AND_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + ANDS_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ANDS_www(d, REG_WORK1, REG_WORK2); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_AND_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jff_AND_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_AND_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + ANDS_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ANDS_www(d, REG_WORK1, REG_WORK2); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_AND_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_AND_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + ANDS_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ANDS_www(d, REG_WORK1, REG_WORK2); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_AND_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jff_AND_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_AND_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + ANDS_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ANDS_www(d, REG_WORK1, REG_WORK2); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_AND_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_AND_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + ANDS_www(d, d, s); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_AND_l,(RW4 d, RR4 s)) + +/* + * ASL + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if the most significant bit is changed at any time during the shift operation. Cleared otherwise. + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + * imm version only called with 1 <= i <= 8 + * + */ +MIDFUNC(2,jff_ASL_b_imm,(RW1 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + LSL_wwi(REG_WORK3, d, 24); + if (i) { + LSL_xxi(REG_WORK2, REG_WORK3, i); + BFXIL_xxii(d, REG_WORK2, 24, 8); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(REG_WORK2, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK1, REG_WORK3); + CMP_wi(REG_WORK1, i); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASL_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_ASL_w_imm,(RW2 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + LSL_wwi(REG_WORK3, d, 16); + if (i) { + LSL_xxi(REG_WORK2, REG_WORK3, i); + BFXIL_xxii(d, REG_WORK2, 16, 16); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(REG_WORK2, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK1, REG_WORK3); + CMP_wi(REG_WORK1, i); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASL_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_ASL_l_imm,(RW4 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + if (i) { + if (needed_flags & FLAG_V) + MOV_ww(REG_WORK3, d); + LSL_xxi(d, d, i); + TST_ww(d, d); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(d, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK1, REG_WORK3); + CMP_wi(REG_WORK1, i); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(d, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(d, d); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASL_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jff_ASL_b_reg,(RW1 d, RR4 i)) +{ + i = readreg(i); + d = rmw(d); + int x = writereg(FLAGX); + + LSL_wwi(REG_WORK3, d, 24); + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); + + // shift count is 0 + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + LSL_xxx(REG_WORK2, REG_WORK3, REG_WORK1); + BFXIL_xxii(d, REG_WORK2, 24, 8); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(REG_WORK2, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK2, REG_WORK3); + CMP_ww(REG_WORK2, REG_WORK1); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASL_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ASL_w_reg,(RW2 d, RR4 i)) +{ + i = readreg(i); + d = rmw(d); + int x = writereg(FLAGX); + + LSL_wwi(REG_WORK3, d, 16); + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); + + // shift count is 0 + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + LSL_xxx(REG_WORK2, REG_WORK3, REG_WORK1); + BFXIL_xxii(d, REG_WORK2, 16, 16); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(REG_WORK2, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK2, REG_WORK3); + CMP_ww(REG_WORK2, REG_WORK1); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASL_w_reg,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ASL_l_reg,(RW4 d, RR4 i)) +{ + i = readreg(i); + d = rmw(d); + int x = writereg(FLAGX); + + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); + + // shift count is 0 + TST_ww(d, d); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + if (needed_flags & FLAG_V) + MOV_ww(REG_WORK3, d); + LSL_xxx(d, d, REG_WORK1); + TST_ww(d, d); // NZ correct, VC cleared + + if (needed_flags & FLAG_V) { + // Calculate C Flag + MRS_NZCV_x(REG_WORK4); + TBZ_xii(d, 32, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V Flag + CLS_ww(REG_WORK2, REG_WORK3); + CMP_ww(REG_WORK2, REG_WORK1); + BGE_i(2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C Flag + TBZ_xii(d, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASL_l_reg,(RW4 d, RR4 i)) + +/* + * ASLW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Set according to the last bit shifted out of the operand. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if the most significant bit is changed at any time during the shift operation. Cleared otherwise. + * C Set according to the last bit shifted out of the operand. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_ASLW,(RW2 d)) +{ + d = rmw(d); + + LSL_wwi(d, d, 1); + + unlock2(d); +} +MENDFUNC(1,jnf_ASLW,(RW2 d)) + +MIDFUNC(1,jff_ASLW,(RW2 d)) +{ + d = rmw(d); + + LSL_wwi(REG_WORK1, d, 17); + TST_ww(REG_WORK1, REG_WORK1); + + if (needed_flags & FLAG_V) { + // Calculate C flag + MRS_NZCV_x(REG_WORK4); + TBZ_wii(d, 15, 2); + SET_xxCflag(REG_WORK4, REG_WORK4); + + // Calculate V flag + EOR_wwwLSLi(REG_WORK1, d, d, 1); // eor bit15 and bit14 of source + TBZ_wii(REG_WORK1, 15, 2); + SET_xxVflag(REG_WORK4, REG_WORK4); + + MSR_NZCV_x(REG_WORK4); + } else { + // Calculate C flag + TBZ_wii(d, 15, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + LSL_wwi(d, d, 1); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_ASLW,(RW2 d)) + +/* + * ASR + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if the most significant bit is changed at any time during the shift operation. Cleared otherwise. Shift right -> always 0 + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + */ +MIDFUNC(2,jnf_ASR_b_imm,(RW1 d, IM8 i)) +{ + if(i) { + d = rmw(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + ASR_wwi(REG_WORK1, REG_WORK1, i); + BFI_xxii(d, REG_WORK1, 0, 8); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ASR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jnf_ASR_w_imm,(RW2 d, IM8 i)) +{ + if(i) { + d = rmw(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + ASR_wwi(REG_WORK1, REG_WORK1, i); + BFI_xxii(d, REG_WORK1, 0, 16); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ASR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jnf_ASR_l_imm,(RW4 d, IM8 i)) +{ + if(i) { + d = rmw(d); + + ASR_wwi(d, d, i); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ASR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jff_ASR_b_imm,(RW1 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + if (i) { + ASR_wwi(REG_WORK2, REG_WORK1, i); + BFI_wwii(d, REG_WORK2, 0, 8); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C flag + TBZ_wii(REG_WORK1, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_ASR_w_imm,(RW2 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + if (i) { + ASR_wwi(REG_WORK2, REG_WORK1, i); + BFI_wwii(d, REG_WORK2, 0, 16); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C flag + TBZ_wii(REG_WORK1, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_ASR_l_imm,(RW4 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + if (i) { + MOV_ww(REG_WORK1, d); + ASR_wwi(d, d, i); + TST_ww(d, d); + + // Calculate C flag + if(i > 32) + i = 32; + TBZ_wii(REG_WORK1, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + TST_ww(d, d); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_ASR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jnf_ASR_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ASR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + AND_ww3f(REG_WORK2, i); + ASR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jnf_ASR_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_ASR_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ASR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + AND_ww3f(REG_WORK2, i); + ASR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 16); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jnf_ASR_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_ASR_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ASR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + AND_ww3f(REG_WORK1, i); + ASR_www(d, d, REG_WORK1); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jnf_ASR_l_reg,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ASR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + SIGNED8_REG_2_REG(REG_WORK3, d); + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); // No shift -> X flag unchanged + + // shift count is 0 + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + ASR_www(REG_WORK2, REG_WORK3, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 8); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + ASR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASR_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ASR_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ASR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + SIGNED16_REG_2_REG(REG_WORK3, d); + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); // No shift -> X flag unchanged + + // shift count is 0 + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + ASR_www(REG_WORK2, REG_WORK3, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 16); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + ASR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASR_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_ASR_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ASR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + i = readreg(i); + d = rmw(d); + + ANDS_ww3f(REG_WORK1, i); + BNE_i(3); // No shift -> X flag unchanged + + // shift count is 0 + TST_ww(d, d); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + // shift count > 0 + MOV_ww(REG_WORK3, d); + ASR_www(d, d, REG_WORK1); + TST_ww(d, d); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + ASR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ASR_l_reg,(RW4 d, RR4 i)) + +/* + * ASRW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Set according to the last bit shifted out of the operand. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if the most significant bit is changed at any time during the shift operation. Cleared otherwise. Shift right -> always 0 + * C Set according to the last bit shifted out of the operand. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_ASRW,(RW2 d)) +{ + d = rmw(d); + + SIGNED16_REG_2_REG(d, d); + ASR_wwi(d, d, 1); + + unlock2(d); +} +MENDFUNC(1,jnf_ASRW,(RW2 d)) + +MIDFUNC(1,jff_ASRW,(RW2 d)) +{ + d = rmw(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + ASR_wwi(d, REG_WORK1, 1); + TST_ww(d, d); + + // Calculate C flag + TBZ_wii(REG_WORK1, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_ASRW,(RW2 d)) + +/* + * BCHG + * Operand Syntax: Dn, + * #, + * + * Operand Size: 8,32 + * + * X Not affected. + * N Not affected. + * Z Set if the bit changed was zero. Cleared otherwise. + * V Not affected. + * C Not affected. + * + */ +/* BCHG.B: target is never a register */ +/* BCHG.L: target is always a register */ +MIDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + EOR_xxbit(d, d, s & 0x1f); + unlock2(d); +} +MENDFUNC(2,jnf_BCHG_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IM8 s)) +{ + d = rmw(d); + EOR_xxbit(d, d, s & 0x1f); + unlock2(d); +} +MENDFUNC(2,jnf_BCHG_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jnf_BCHG_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BCHG_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + EOR_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jnf_BCHG_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jnf_BCHG_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BCHG_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + EOR_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jnf_BCHG_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_BCHG_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + EOR_xxbit(d, d, s & 0x1f); + UBFX_xxii(REG_WORK2, d, s & 0x1f, 1); + BFI_xxii(REG_WORK1, REG_WORK2, 30, 1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jff_BCHG_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jff_BCHG_l_imm,(RW4 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + EOR_xxbit(d, d, s & 0x1f); + UBFX_xxii(REG_WORK2, d, s & 0x1f, 1); + BFI_xxii(REG_WORK1, REG_WORK2, 30, 1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jff_BCHG_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jff_BCHG_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BCHG_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d, REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + EOR_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jff_BCHG_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jff_BCHG_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BCHG_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d, REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + EOR_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jff_BCHG_l,(RW4 d, RR4 s)) + +/* + * BCLR + * Operand Syntax: Dn, + * #, + * + * Operand Size: 8,32 + * + * X Not affected. + * N Not affected. + * Z Set if the bit cleared was zero. Cleared otherwise. + * V Not affected. + * C Not affected. + * + */ +/* BCLR.B: target is never a register */ +/* BCLR.L: target is always a register */ +MIDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + CLEAR_xxbit(d, d, s); + unlock2(d); +} +MENDFUNC(2,jnf_BCLR_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IM8 s)) +{ + if(isconst(d)) { + live.state[d].val = live.state[d].val & ~(1 << s); + return; + } + d = rmw(d); + CLEAR_xxbit(d, d, s); + unlock2(d); +} +MENDFUNC(2,jnf_BCLR_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jnf_BCLR_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BCLR_b_imm)(d, live.state[s].val & 7); + return; + } + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + BIC_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jnf_BCLR_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jnf_BCLR_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BCLR_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + BIC_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jnf_BCLR_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_BCLR_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + CLEAR_xxbit(d, d, s); + + unlock2(d); +} +MENDFUNC(2,jff_BCLR_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jff_BCLR_l_imm,(RW4 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + CLEAR_xxbit(d, d, s); + + unlock2(d); +} +MENDFUNC(2,jff_BCLR_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jff_BCLR_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BCLR_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d,REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + BIC_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jff_BCLR_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jff_BCLR_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BCLR_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d,REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + BIC_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jff_BCLR_l,(RW4 d, RR4 s)) + +/* + * BSET + * Operand Syntax: Dn, + * #, + * + * Operand Size: 8,32 + * + * X Not affected. + * N Not affected. + * Z Set if the bit set was zero. Cleared otherwise. + * V Not affected. + * C Not affected. + * + */ +/* BSET.B: target is never a register */ +/* BSET.L: target is always a register */ +MIDFUNC(2,jnf_BSET_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + SET_xxbit(d, d, s & 0x1f); + unlock2(d); +} +MENDFUNC(2,jnf_BSET_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jnf_BSET_l_imm,(RW4 d, IM8 s)) +{ + d = rmw(d); + SET_xxbit(d, d, s & 0x1f); + unlock2(d); +} +MENDFUNC(2,jnf_BSET_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jnf_BSET_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BSET_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + ORR_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jnf_BSET_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jnf_BSET_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_BSET_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + ORR_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jnf_BSET_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_BSET_b_imm,(RW1 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + SET_xxbit(d, d, s & 0x1f); + + unlock2(d); +} +MENDFUNC(2,jff_BSET_b_imm,(RW1 d, IM8 s)) + +MIDFUNC(2,jff_BSET_l_imm,(RW4 d, IM8 s)) +{ + d = rmw(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + SET_xxbit(d, d, s & 0x1f); + + unlock2(d); +} +MENDFUNC(2,jff_BSET_l_imm,(RW4 d, IM8 s)) + +MIDFUNC(2,jff_BSET_b,(RW1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BSET_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = rmw(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d,REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + ORR_www(d, d, REG_WORK2); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jff_BSET_b,(RW1 d, RR4 s)) + +MIDFUNC(2,jff_BSET_l,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BSET_l_imm)(d, live.state[s].val & 31); + return; + } + + INIT_REGS_l(d,s); + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d,REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + ORR_www(d, d, REG_WORK2); + + EXIT_REGS(d,s); +} +MENDFUNC(2,jff_BSET_l,(RW4 d, RR4 s)) + +/* + * BTST + * Operand Syntax: Dn, + * #, + * + * Operand Size: 8,32 + * + * X Not affected + * N Not affected + * Z Set if the bit tested is zero. Cleared otherwise + * V Not affected + * C Not affected + * + */ +/* BTST.B: target is never a register */ +/* BTST.L: target is always a register */ +MIDFUNC(2,jff_BTST_b_imm,(RR1 d, IM8 s)) +{ + d = readreg(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); // skip next if bit is set + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jff_BTST_b_imm,(RR1 d, IM8 s)) + +MIDFUNC(2,jff_BTST_l_imm,(RR4 d, IM8 s)) +{ + d = readreg(d); + + MRS_NZCV_x(REG_WORK1); + CLEAR_xxZflag(REG_WORK1, REG_WORK1); + TBNZ_wii(d, s, 2); // skip next if bit is set + SET_xxZflag(REG_WORK1, REG_WORK1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jff_BTST_l_imm,(RR4 d, IM8 s)) + +MIDFUNC(2,jff_BTST_b,(RR1 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BTST_b_imm)(d, live.state[s].val & 7); + return; + } + + s = readreg(s); + d = readreg(d); + + UBFIZ_xxii(REG_WORK1, s, 0, 3); // REG_WORK1 = s & 7 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d, REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jff_BTST_b,(RR1 d, RR4 s)) + +MIDFUNC(2,jff_BTST_l,(RR4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_BTST_l_imm)(d, live.state[s].val & 31); + return; + } + + int s_is_d = (s == d); + d = readreg(d); + if(!s_is_d) + s = readreg(s); + else + s = d; + + UBFIZ_xxii(REG_WORK1, s, 0, 5); // REG_WORK1 = s & 31 + MOV_xi(REG_WORK2, 1); + LSL_www(REG_WORK2, REG_WORK2, REG_WORK1); + + MRS_NZCV_x(REG_WORK1); + TST_ww(d, REG_WORK2); + CSET_xc(REG_WORK3, NATIVE_CC_EQ); + BFI_xxii(REG_WORK1, REG_WORK3, 30, 1); + MSR_NZCV_x(REG_WORK1); + + unlock2(d); + if(!s_is_d) + unlock2(s); +} +MENDFUNC(2,jff_BTST_l,(RR4 d, RR4 s)) + +/* + * CLR + * Operand Syntax: + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Always cleared. + * Z Always set. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(1,jnf_CLR_b,(W1 d)) +{ + if(d >= 16) { + set_const(d, 0); + return; + } + INIT_WREG_b(d); + CLEAR_LOW8_xx(d, d); + unlock2(d); +} +MENDFUNC(1,jnf_CLR_b,(W1 d)) + +MIDFUNC(1,jnf_CLR_w,(W2 d)) +{ + if(d >= 16) { + set_const(d, 0); + return; + } + INIT_WREG_w(d); + CLEAR_LOW16_xx(d, d); + unlock2(d); +} +MENDFUNC(1,jnf_CLR_w,(W2 d)) + +MIDFUNC(1,jnf_CLR_l,(W4 d)) +{ + set_const(d, 0); +} +MENDFUNC(1,jnf_CLR_l,(W4 d)) + +MIDFUNC(1,jff_CLR_b,(W1 d)) +{ + MOV_xish(REG_WORK1, 0x4000, 16); // set Z flag + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + if(d >= 16) { + set_const(d, 0); + return; + } + INIT_WREG_b(d); + CLEAR_LOW8_xx(d, d); + unlock2(d); +} +MENDFUNC(1,jff_CLR_b,(W1 d)) + +MIDFUNC(1,jff_CLR_w,(W2 d)) +{ + MOV_xish(REG_WORK1, 0x4000, 16); // set Z flag + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + if(d >= 16) { + set_const(d, 0); + return; + } + INIT_WREG_w(d); + CLEAR_LOW16_xx(d, d); + unlock2(d); +} +MENDFUNC(1,jff_CLR_w,(W2 d)) + +MIDFUNC(1,jff_CLR_l,(W4 d)) +{ + MOV_xish(REG_WORK1, 0x4000, 16); // set Z flag + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + set_const(d, 0); +} +MENDFUNC(1,jff_CLR_l,(W4 d)) + +/* + * CMP + * Operand Syntax: , Dn + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if an overflow occurs. Cleared otherwise. + * C Set if a borrow occurs. Cleared otherwise. + * + */ +MIDFUNC(2,jff_CMP_b,(RR1 d, RR1 s)) +{ + if (isconst(d)) { + uae_u8 tmp = (uae_u8)(live.state[d].val & 0xff); + s = readreg(s); + MOV_wish(REG_WORK1, tmp << 8, 16); + CMP_wwLSLi(REG_WORK1, s, 24); + unlock2(s); + } else { + INIT_RREGS_b(d, s); + + LSL_wwi(REG_WORK1, d, 24); + CMP_wwLSLi(REG_WORK1, s, 24); + + EXIT_REGS(d,s); + } + flags_carry_inverted = true; +} +MENDFUNC(2,jff_CMP_b,(RR1 d, RR1 s)) + +MIDFUNC(2,jff_CMP_w,(RR2 d, RR2 s)) +{ + if (isconst(d) && isconst(s)) { + MOV_wish(REG_WORK1, (live.state[d].val & 0xffff), 16); + MOV_wish(REG_WORK2, (live.state[s].val & 0xffff), 16); + CMP_ww(REG_WORK1, REG_WORK2); + } else if (isconst(d)) { + uae_u16 tmp = (uae_u16)(live.state[d].val & 0xffff); + s = readreg(s); + MOV_wish(REG_WORK1, tmp, 16); + CMP_wwLSLi(REG_WORK1, s, 16); + unlock2(s); + } else { + INIT_RREGS_w(d, s); + + LSL_wwi(REG_WORK1, d, 16); + CMP_wwLSLi(REG_WORK1, s, 16); + + EXIT_REGS(d,s); + } + flags_carry_inverted = true; +} +MENDFUNC(2,jff_CMP_w,(RR2 d, RR2 s)) + +MIDFUNC(2,jff_CMP_l,(RR4 d, RR4 s)) +{ + INIT_RREGS_l(d, s); + + CMP_ww(d, s); + + flags_carry_inverted = true; + EXIT_REGS(d,s); +} +MENDFUNC(2,jff_CMP_l,(RR4 d, RR4 s)) + +/* + * CMPA + * Operand Syntax: , An + * + * Operand Size: 16,32 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if an overflow occurs. Cleared otherwise. + * C Set if a borrow occurs. Cleared otherwise. + * + */ +MIDFUNC(2,jff_CMPA_w,(RR2 d, RR2 s)) +{ + if (isconst(s)) { + uae_u16 tmp = (uae_u16)(live.state[s].val & 0xffff); + d = readreg(d); + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + CMP_ww(d, REG_WORK1); + unlock2(d); + } else { + INIT_RREGS_w(d, s); + CMP_wwEX(d, s, EX_SXTH); + EXIT_REGS(d,s); + } + + flags_carry_inverted = true; +} +MENDFUNC(2,jff_CMPA_w,(RR2 d, RR2 s)) + +MIDFUNC(2,jff_CMPA_l,(RR4 d, RR4 s)) +{ + INIT_RREGS_l(d, s); + + CMP_ww(d, s); + + flags_carry_inverted = true; + EXIT_REGS(d,s); +} +MENDFUNC(2,jff_CMPA_l,(RR4 d, RR4 s)) + +/* + * DBCC + * + */ +MIDFUNC(2,jff_DBCC,(RW4 d, IM8 cc)) +{ + d = rmw(d); + + FIX_INVERTED_CARRY + + // If cc true -> no branch, so we have to clear ARM_C_FLAG + MOV_xish(REG_WORK1, 0x2000, 16); // set C flag + MOV_xi(REG_WORK2, 0); + switch(cc) { + case 9: // LS + CSEL_xxxc(REG_WORK1, REG_WORK2, REG_WORK1, NATIVE_CC_EQ); + CSEL_xxxc(REG_WORK1, REG_WORK2, REG_WORK1, NATIVE_CC_CS); + break; + + case 8: // HI + MOV_xish(REG_WORK3, 0x2000, 16); + CSEL_xxxc(REG_WORK1, REG_WORK2, REG_WORK1, NATIVE_CC_CC); + CSEL_xxxc(REG_WORK1, REG_WORK3, REG_WORK1, NATIVE_CC_EQ); + break; + + default: + CSEL_xxxc(REG_WORK1, REG_WORK2, REG_WORK1, cc); + break; + } + clobber_flags(); + MSR_NZCV_x(REG_WORK1); + + BCC_i(4); // If cc true -> no sub + + // sub (d, 1) + LSL_wwi(REG_WORK2, d, 16); + SUBS_wwish(REG_WORK2, REG_WORK2, 0x10, 1); + BFXIL_xxii(d, REG_WORK2, 16, 16); + + // caller can now use register_branch(v1, v2, NATIVE_CC_CS); + + unlock2(d); +} +MENDFUNC(2,jff_DBCC,(RW4 d, IM8 cc)) + +/* + * DIVU + * + * X Not affected. + * N Set if the most significant bit of the result is set or overflow. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if overflow. Cleared otherwise. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_DIVU,(RW4 d, RR4 s)) +{ + int init_regs_used = 0; + int targetIsReg; + int s_is_d; + if (isconst(s) && (uae_u16)live.state[s].val != 0) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK3, tmp); + } else { + targetIsReg = (d < 16); + s_is_d = (s == d); + if(!s_is_d) + s = readreg(s); + d = rmw(d); + if(s_is_d) + s = d; + init_regs_used = 1; + + UNSIGNED16_REG_2_REG(REG_WORK3, s); + CBNZ_wi(REG_WORK3, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + B_i(7); // end_of_op + } + + // src is not 0 + UDIV_www(REG_WORK1, d, REG_WORK3); + + LSR_wwi(REG_WORK2, REG_WORK1, 16); // if result of this is not 0, DIVU overflows -> no result + CBNZ_wi(REG_WORK2, 4); + + // Here we have to calc remainder + MSUB_wwww(REG_WORK2, REG_WORK1, REG_WORK3, d); + LSL_wwi(d, REG_WORK2, 16); + BFI_wwii(d, REG_WORK1, 0, 16); + // end_of_op + + if (init_regs_used) { + EXIT_REGS(d, s); + } else { + unlock2(d); + } +} +MENDFUNC(2,jnf_DIVU,(RW4 d, R4 s)) + +MIDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) +{ + uae_u32* branchadd; + int init_regs_used = 0; + int targetIsReg; + int s_is_d; + if (isconst(s) && (uae_u16)live.state[s].val != 0) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK3, tmp); + } else { + targetIsReg = (d < 16); + s_is_d = (s == d); + if(!s_is_d) + s = readreg(s); + d = rmw(d); + if(s_is_d) + s = d; + init_regs_used = 1; + + UNSIGNED16_REG_2_REG(REG_WORK3, s); + uae_u32* branchadd_not0 = (uae_u32*)get_target(); + CBNZ_wi(REG_WORK3, 0); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + + // flag handling like divbyzero_special() + if (currprefs.cpu_model == 68020 || currprefs.cpu_model == 68030) { + MOV_wish(REG_WORK1, 0x5000, 16); // Set V and Z (if d >=0) + TBZ_wii(d, 31, 2); + MOV_wish(REG_WORK1, 0x9000, 16); // Set V and N (if d < 0) + } else if (currprefs.cpu_model >= 68040) { + MRS_NZCV_x(REG_WORK1); + CLEAR_xxCflag(REG_WORK1, REG_WORK1); + } else { + // 68000/010 + MOV_wish(REG_WORK1, 0x0000, 16); + } + MSR_NZCV_x(REG_WORK1); + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op + write_jmp_target(branchadd_not0, (uintptr)get_target()); + } + + // src is not 0 + UDIV_www(REG_WORK1, d, REG_WORK3); + + LSR_wwi(REG_WORK2, REG_WORK1, 16); // if result of this is not 0, DIVU overflows + CBZ_wi(REG_WORK2, 4); + // Here we handle overflow + MOV_wish(REG_WORK1, 0x9000, 16); // set V and N + MSR_NZCV_x(REG_WORK1); + B_i(6); + + // Here we have to calc flags and remainder + LSL_wwi(REG_WORK2, REG_WORK1, 16); + TST_ww(REG_WORK2, REG_WORK2); // N and Z ok, C and V cleared + + MSUB_wwww(REG_WORK2, REG_WORK1, REG_WORK3, d); + LSL_wwi(d, REG_WORK2, 16); + BFI_wwii(d, REG_WORK1, 0, 16); + + // end_of_op + flags_carry_inverted = false; + if (init_regs_used) { + write_jmp_target(branchadd, (uintptr)get_target()); + EXIT_REGS(d, s); + } else { + unlock2(d); + } +} +MENDFUNC(2,jff_DIVU,(RW4 d, RR4 s)) + +/* + * DIVS + * + * X Not affected. + * N Set if the most significant bit of the result is set or overflow. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if overflow. Cleared otherwise. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_DIVS,(RW4 d, RR4 s)) +{ + uae_u32* branchadd; + int init_regs_used = 0; + int targetIsReg; + int s_is_d; + if (isconst(s) && (uae_s16)live.state[s].val != 0) { + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + SIGNED16_IMM_2_REG(REG_WORK3, tmp); + } else { + targetIsReg = (d < 16); + s_is_d = (s == d); + if(!s_is_d) + s = readreg(s); + d = rmw(d); + if(s_is_d) + s = d; + init_regs_used = 1; + + SIGNED16_REG_2_REG(REG_WORK3, s); + CBNZ_wi(REG_WORK3, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op + } + + // src is not 0 + SDIV_www(REG_WORK1, d, REG_WORK3); + + // check for overflow + MOVN_wi(REG_WORK2, 0x7fff); // REG_WORK2 is now 0xffff8000 + ANDS_www(REG_WORK3, REG_WORK1, REG_WORK2); + BEQ_i(3); // positive result, no overflow + CMP_ww(REG_WORK3, REG_WORK2); + BNE_i(8); // overflow -> end_of_op + + // Here we have to calc remainder + SIGNED16_REG_2_REG(REG_WORK3, s); + MSUB_wwww(REG_WORK2, REG_WORK1, REG_WORK3, d); // REG_WORK2 contains remainder + + EOR_www(REG_WORK3, REG_WORK2, d); // If sign of remainder and first operand differs, change sign of remainder + TBZ_wii(REG_WORK3, 31, 2); + NEG_ww(REG_WORK2, REG_WORK2); + + LSL_wwi(d, REG_WORK2, 16); + BFI_wwii(d, REG_WORK1, 0, 16); + + // end_of_op + if (init_regs_used) { + write_jmp_target(branchadd, (uintptr)get_target()); + EXIT_REGS(d, s); + } else { + unlock2(d); + } +} +MENDFUNC(2,jnf_DIVS,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_DIVS,(RW4 d, RR4 s)) +{ + uae_u32* branchadd; + int init_regs_used = 0; + int targetIsReg; + int s_is_d; + if (isconst(s) && (uae_s16)live.state[s].val != 0) { + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + SIGNED16_IMM_2_REG(REG_WORK3, tmp); + } else { + targetIsReg = (d < 16); + s_is_d = (s == d); + if(!s_is_d) + s = readreg(s); + d = rmw(d); + if(s_is_d) + s = d; + init_regs_used = 1; + + SIGNED16_REG_2_REG(REG_WORK3, s); + uae_u32* branchadd_not0 = (uae_u32*)get_target(); + CBNZ_wi(REG_WORK3, 0); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + + // flag handling like divbyzero_special() + if (currprefs.cpu_model == 68020 || currprefs.cpu_model == 68030) { + MOV_wish(REG_WORK1, 0x4000, 16); // Set Z + } else if (currprefs.cpu_model >= 68040) { + MRS_NZCV_x(REG_WORK1); + CLEAR_xxCflag(REG_WORK1, REG_WORK1); + } else { + // 68000/010 + MOV_wish(REG_WORK1, 0x0000, 16); + } + + MSR_NZCV_x(REG_WORK1); + branchadd = (uae_u32*)get_target(); + B_i(0); // end_of_op + write_jmp_target(branchadd_not0, (uintptr)get_target()); + } + + // src is not 0 + SDIV_www(REG_WORK1, d, REG_WORK3); + + // check for overflow + MOVN_wi(REG_WORK2, 0x7fff); // REG_WORK2 is now 0xffff8000 + ANDS_www(REG_WORK3, REG_WORK1, REG_WORK2); + BEQ_i(6); // positive result, no overflow + CMP_ww(REG_WORK3, REG_WORK2); + BEQ_i(4); // no overflow + + // Here we handle overflow + MOV_wish(REG_WORK1, 0x9000, 16); // set V and N + MSR_NZCV_x(REG_WORK1); + B_i(10); + + // calc flags + LSL_wwi(REG_WORK2, REG_WORK1, 16); + TST_ww(REG_WORK2, REG_WORK2); // N and Z ok, C and V cleared + + // calc remainder + SIGNED16_REG_2_REG(REG_WORK3, s); + MSUB_wwww(REG_WORK2, REG_WORK1, REG_WORK3, d); // REG_WORK2 contains remainder + + EOR_www(REG_WORK3, REG_WORK2, d); // If sign of remainder and first operand differs, change sign of remainder + TBZ_wii(REG_WORK3, 31, 2); + NEG_ww(REG_WORK2, REG_WORK2); + + LSL_wwi(d, REG_WORK2, 16); + BFI_wwii(d, REG_WORK1, 0, 16); + + // end_of_op + flags_carry_inverted = false; + if (init_regs_used) { + write_jmp_target(branchadd, (uintptr)get_target()); + EXIT_REGS(d, s); + } else { + unlock2(d); + } +} +MENDFUNC(2,jff_DIVS,(RW4 d, RR4 s)) + +MIDFUNC(3,jnf_DIVLU32,(RW4 d, RR4 s1, W4 rem)) +{ + s1 = readreg(s1); + d = rmw(d); + rem = writereg(rem); + + CBNZ_wi(s1, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + B_i(4); // end_of_op + + // src is not 0 + UDIV_www(REG_WORK1, d, s1); + + // Here we have to calc remainder + MSUB_wwww(rem, s1, REG_WORK1, d); + MOV_ww(d, REG_WORK1); + +// end_of_op + + unlock2(rem); + unlock2(d); + unlock2(s1); +} +MENDFUNC(3,jnf_DIVLU32,(RW4 d, RR4 s1, W4 rem)) + +MIDFUNC(3,jff_DIVLU32,(RW4 d, RR4 s1, W4 rem)) +{ + s1 = readreg(s1); + d = rmw(d); + rem = writereg(rem); + + CBNZ_wi(s1, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + + B_i(5); // end_of_op + + // src is not 0 + UDIV_www(REG_WORK1, d, s1); + + // Here we have to calc flags and remainder + TST_ww(REG_WORK1, REG_WORK1); + + MSUB_wwww(rem, s1, REG_WORK1, d); + MOV_ww(d, REG_WORK1); + + // end_of_op + + flags_carry_inverted = false; + unlock2(rem); + unlock2(d); + unlock2(s1); +} +MENDFUNC(3,jff_DIVLU32,(RW4 d, RR4 s1, W4 rem)) + +MIDFUNC(3,jnf_DIVLS32,(RW4 d, RR4 s1, W4 rem)) +{ + s1 = readreg(s1); + d = rmw(d); + rem = writereg(rem); + + CBNZ_wi(s1, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + B_i(7); // end_of_op + + // src is not 0 + SDIV_www(REG_WORK1, d, s1); + + // Here we have to calc remainder + MSUB_wwww(rem, s1, REG_WORK1, d); + + EOR_www(REG_WORK3, rem, d); // If sign of remainder and first operand differs, change sign of remainder + TBZ_wii(REG_WORK3, 31, 2); + NEG_ww(rem, rem); + + MOV_ww(d, REG_WORK1); + + // end_of_op + + unlock2(rem); + unlock2(d); + unlock2(s1); +} +MENDFUNC(3,jnf_DIVLS32,(RW4 d, RR4 s1, W4 rem)) + +MIDFUNC(3,jff_DIVLS32,(RW4 d, RR4 s1, W4 rem)) +{ + s1 = readreg(s1); + d = rmw(d); + rem = writereg(rem); + + CBNZ_wi(s1, 4); // src is not 0 + + // Signal exception 5 + MOV_wi(REG_WORK1, 5); + uintptr idx = (uintptr)(®s.jit_exception) - (uintptr)(®s); + STR_wXi(REG_WORK1, R_REGSTRUCT, idx); + B_i(7); // end_of_op + + // src is not 0 + SDIV_www(REG_WORK1, d, s1); + + // Here we have to calc remainder + MSUB_wwww(rem, s1, REG_WORK1, d); + + EOR_www(REG_WORK3, rem, d); // If sign of remainder and first operand differs, change sign of remainder + TBZ_wii(REG_WORK3, 31, 2); + NEG_ww(REG_WORK2, REG_WORK2); + + MOV_ww(d, REG_WORK1); + + // end_of_op + + flags_carry_inverted = false; + unlock2(rem); + unlock2(d); + unlock2(s1); +} +MENDFUNC(3,jff_DIVLS32,(RW4 d, RR4 s1, W4 rem)) + +/* + * EOR + * Operand Syntax: Dn, + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_EOR_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + MOV_xi(REG_WORK1, (v & 0xff)); + EOR_www(d, d, REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jnf_EOR_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jnf_EOR_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_EOR_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + if(targetIsReg) { + EOR_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + EOR_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_EOR_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_EOR_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + MOV_xi(REG_WORK1, v & 0xffff); + EOR_www(d, d, REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jnf_EOR_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jnf_EOR_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_EOR_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + EOR_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 16); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_EOR_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_EOR_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + EOR_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_EOR_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_EOR_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + EOR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 8); + TST_ww(REG_WORK1, REG_WORK1); + } else { + EOR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_EOR_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jff_EOR_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_EOR_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + EOR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 8); + TST_ww(REG_WORK1, REG_WORK1); + } else { + EOR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_EOR_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_EOR_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + EOR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 16); + TST_ww(REG_WORK1, REG_WORK1); + } else { + EOR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_EOR_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jff_EOR_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_EOR_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + EOR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_xxii(d, REG_WORK1, 0, 16); + TST_ww(REG_WORK1, REG_WORK1); + } else { + EOR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_EOR_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_EOR_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + EOR_www(d, d, s); + TST_ww(d, d); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_EOR_l,(RW4 d, RR4 s)) + +/* + * EORSR + * Operand Syntax: #, CCR + * + * Operand Size: 8 + * + * X — Changed if bit 4 of immediate operand is one; unchanged otherwise. + * N — Changed if bit 3 of immediate operand is one; unchanged otherwise. + * Z — Changed if bit 2 of immediate operand is one; unchanged otherwise. + * V — Changed if bit 1 of immediate operand is one; unchanged otherwise. + * C — Changed if bit 0 of immediate operand is one; unchanged otherwise. + * + */ +MIDFUNC(2,jff_EORSR,(IM32 s, IM8 x)) +{ + MRS_NZCV_x(REG_WORK1); + if(flags_carry_inverted) { + EOR_xxCflag(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + MOV_xish(REG_WORK2, (s >> 16), 16); + EOR_www(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + + if (x) { + int f = rmw(FLAGX); + EOR_xxbit(f, f, 0); + unlock2(f); + } +} +MENDFUNC(2,jff_EORSR,(IM32 s, IM8 x)) + +/* + * EXT + * Operand Syntax: + * + * Operand Size: 16,32 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(1,jnf_EXT_b,(RW4 d)) +{ + if (isconst(d)) { + live.state[d].val = (uae_s32)(uae_s8)live.state[d].val; + return; + } + + d = rmw(d); + + SIGNED8_REG_2_REG(d, d); + + unlock2(d); +} +MENDFUNC(1,jnf_EXT_b,(RW4 d)) + +MIDFUNC(1,jnf_EXT_w,(RW4 d)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | (((uae_s32)(uae_s8)live.state[d].val) & 0x0000ffff); + return; + } + + d = rmw(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + BFI_xxii(d, REG_WORK1, 0, 16); + + unlock2(d); +} +MENDFUNC(1,jnf_EXT_w,(RW4 d)) + +MIDFUNC(1,jnf_EXT_l,(RW4 d)) +{ + if (isconst(d)) { + live.state[d].val = (uae_s32)(uae_s16)live.state[d].val; + return; + } + + d = rmw(d); + + SIGNED16_REG_2_REG(d, d); + + unlock2(d); +} +MENDFUNC(1,jnf_EXT_l,(RW4 d)) + +MIDFUNC(1,jff_EXT_b,(RW4 d)) +{ + if (isconst(d)) { + uae_u8 tmp = (uae_u8)live.state[d].val; + d = writereg(d); + SIGNED8_IMM_2_REG(d, tmp); + } else { + d = rmw(d); + SIGNED8_REG_2_REG(d, d); + } + + TST_ww(d, d); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_EXT_b,(RW4 d)) + +MIDFUNC(1,jff_EXT_w,(RW4 d)) +{ + if (isconst(d)) { + uae_u8 tmp = (uae_u8)live.state[d].val; + d = writereg(d); + SIGNED8_IMM_2_REG(REG_WORK1, tmp); + } else { + d = rmw(d); + SIGNED8_REG_2_REG(REG_WORK1, d); + } + + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_EXT_w,(RW4 d)) + +MIDFUNC(1,jff_EXT_l,(RW4 d)) +{ + if (isconst(d)) { + uae_u16 tmp = (uae_u8)live.state[d].val; + d = writereg(d); + SIGNED16_IMM_2_REG(d, tmp); + } else { + d = rmw(d); + SIGNED16_REG_2_REG(d, d); + } + TST_ww(d, d); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_EXT_l,(RW4 d)) + +/* + * LSL + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + */ +MIDFUNC(2,jnf_LSL_b_imm,(RW1 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val << i) & 0x000000ff); + return; + } + + INIT_REG_b(d); + + LSL_wwi(REG_WORK1, d, i); + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSL_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jnf_LSL_w_imm,(RW2 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val << i) & 0x0000ffff); + return; + } + + INIT_REG_w(d); + + LSL_wwi(REG_WORK1, d, i); + BFI_wwii(d, REG_WORK1, 0, 16); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSL_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jnf_LSL_l_imm,(RW4 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = live.state[d].val << i; + return; + } + + d = rmw(d); + + LSL_wwi(d, d, i); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSL_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jnf_LSL_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_LSL_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_b(d, i); + + AND_ww3f(REG_WORK1, i); + LSL_www(REG_WORK1, d, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 8); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSL_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_LSL_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_LSL_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_w(d, i); + + AND_ww3f(REG_WORK1, i); + LSL_www(REG_WORK1, d, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 16); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSL_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_LSL_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + if(i > 31) + set_const(d, 0); + else + COMPCALL(jnf_LSL_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_l(d, i); + + AND_ww3f(REG_WORK1, i); + LSL_www(d, d, REG_WORK1); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSL_l_reg,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_LSL_b_imm,(RW1 d, IM8 i)) +{ + if (i) { + d = rmw(d); + if(i >= 8) + MOV_wi(REG_WORK3, 0); + else + LSL_wwi(REG_WORK3, d, i + 24); + TST_ww(REG_WORK3, REG_WORK3); + + if(i <= 8) { + TBZ_wii(d, (8 - i), 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + flags_carry_inverted = false; + DUPLICACTE_CARRY + + BFXIL_xxii(d, REG_WORK3, 24, 8); + } else { + d = readreg(d); + LSL_wwi(REG_WORK3, d, 24); + TST_ww(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSL_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_LSL_w_imm,(RW2 d, IM8 i)) +{ + if (i) { + d = rmw(d); + if(i >= 16) + MOV_wi(REG_WORK3, 0); + else + LSL_wwi(REG_WORK3, d, i + 16); + TST_ww(REG_WORK3, REG_WORK3); + + if(i <= 16) { + TBZ_wii(d, (16 - i), 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + flags_carry_inverted = false; + DUPLICACTE_CARRY + + BFXIL_xxii(d, REG_WORK3, 16, 16); + } else { + d = readreg(d); + LSL_wwi(REG_WORK3, d, 16); + TST_ww(REG_WORK3, REG_WORK3); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSL_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_LSL_l_imm,(RW4 d, IM8 i)) +{ + if (i) { + d = rmw(d); + if(i >= 32) + MOV_wi(REG_WORK3, 0); + else + LSL_wwi(REG_WORK3, d, i); + TST_ww(REG_WORK3, REG_WORK3); + + if(i <= 32) { + TBZ_wii(d, (32 - i), 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + flags_carry_inverted = false; + DUPLICACTE_CARRY + MOV_ww(d, REG_WORK3); + } else { + d = readreg(d); + TST_ww(d, d); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSL_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jff_LSL_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSL_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_b(d, i); + + LSL_wwi(REG_WORK3, d, 24); + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + + // shift count > 0 + LSL_xxx(REG_WORK2, REG_WORK3, REG_WORK1); + BFXIL_xxii(d, REG_WORK2, 24, 8); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + B_i(2); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + TST_ww(REG_WORK3, REG_WORK3); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSL_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_LSL_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSL_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_w(d, i); + + LSL_wwi(REG_WORK3, d, 16); + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + + LSL_xxx(REG_WORK2, REG_WORK3, REG_WORK1); + BFXIL_xxii(d, REG_WORK2, 16, 16); // result is ready + TST_ww(REG_WORK2, REG_WORK2); // NZ correct, VC cleared + + // Calculate C Flag + TBZ_xii(REG_WORK2, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + B_i(2); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + TST_ww(REG_WORK3, REG_WORK3); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSL_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_LSL_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSL_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_l(d, i); + + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged, C cleared + + LSL_xxx(d, d, REG_WORK1); + TST_ww(d, d); // NZ correct, VC cleared + + // Calculate C Flag + TBZ_xii(d, 32, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + B_i(2); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + TST_ww(d, d); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSL_l_reg,(RW4 d, RR4 i)) + +/* + * LSLW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_LSLW,(RW2 d)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val << 1) & 0xffff; + return; + } + + d = rmw(d); + + LSL_wwi(d, d, 1); + + unlock2(d); +} +MENDFUNC(1,jnf_LSLW,(RW2 d)) + +MIDFUNC(1,jff_LSLW,(RW2 d)) +{ + d = rmw(d); + + LSL_wwi(REG_WORK1, d, 17); + TST_ww(REG_WORK1, REG_WORK1); + + // Calculate C flag + TBZ_wii(d, 15, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + LSL_wwi(d, d, 1); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_LSLW,(RW2 d)) + +/* + * LSR + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + */ +MIDFUNC(2,jnf_LSR_b_imm,(RW1 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val & 0xff) >> i); + return; + } + + INIT_REG_b(d); + + UNSIGNED8_REG_2_REG(REG_WORK1, d); + LSR_wwi(REG_WORK1, REG_WORK1, i); + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jnf_LSR_w_imm,(RW2 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val & 0x0000ffff) >> i); + return; + } + + INIT_REG_w(d); + + UNSIGNED16_REG_2_REG(REG_WORK1, d); + LSR_wwi(REG_WORK1, REG_WORK1, i); + BFI_wwii(d, REG_WORK1, 0, 16); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jnf_LSR_l_imm,(RW4 d, IM8 i)) +{ + if(i) { + if (isconst(d)) { + live.state[d].val = live.state[d].val >> i; + return; + } + + d = rmw(d); + + LSR_wwi(d, d, i); + + unlock2(d); + } +} +MENDFUNC(2,jnf_LSR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jff_LSR_b_imm,(RW1 d, IM8 i)) +{ + if (i) { + d = rmw(d); + if(i >= 8) + MOV_wi(REG_WORK1, 0); + else { + UNSIGNED8_REG_2_REG(REG_WORK1, d); + LSR_wwi(REG_WORK1, REG_WORK1, i); + } + TST_ww(REG_WORK1, REG_WORK1); + + if(i <= 8) { + TBZ_wii(d, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + BFI_wwii(d, REG_WORK1, 0, 8); + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + d = readreg(d); + SIGNED8_REG_2_REG(REG_WORK1, d); + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_LSR_w_imm,(RW2 d, IM8 i)) +{ + if (i) { + d = rmw(d); + if(i >= 16) + MOV_wi(REG_WORK1, 0); + else { + UNSIGNED16_REG_2_REG(REG_WORK1, d); + LSR_wwi(REG_WORK1, REG_WORK1, i); + } + TST_ww(REG_WORK1, REG_WORK1); + + if(i <= 16) { + TBZ_wii(d, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + BFI_wwii(d, REG_WORK1, 0, 16); + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + d = readreg(d); + SIGNED16_REG_2_REG(REG_WORK1, d); + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_LSR_l_imm,(RW4 d, IM8 i)) +{ + if (i) { + d = rmw(d); + MOV_ww(REG_WORK1, d); + LSR_wwi(d, d, i); + TST_ww(d, d); + + if(i <= 32) { + TBZ_wii(REG_WORK1, i-1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + flags_carry_inverted = false; + DUPLICACTE_CARRY + } else { + d = readreg(d); + TST_ww(d, d); + flags_carry_inverted = false; + } + + unlock2(d); +} +MENDFUNC(2,jff_LSR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jnf_LSR_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_LSR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_b(d, i); + + UNSIGNED8_REG_2_REG(REG_WORK1, d); + AND_ww3f(REG_WORK2, i); + LSR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 8); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSR_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_LSR_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_LSR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_w(d, i); + + UNSIGNED16_REG_2_REG(REG_WORK1, d); + AND_ww3f(REG_WORK2, i); + LSR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 16); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSR_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_LSR_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + if(i > 31) + set_const(d, 0); + else + COMPCALL(jnf_LSR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_l(d, i); + + AND_ww3f(REG_WORK1, i); + LSR_www(d, d, REG_WORK1); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_LSR_l_reg,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_LSR_b_reg,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSR_b_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_b(d, i); + + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + + UNSIGNED8_REG_2_REG(REG_WORK3, d); + LSR_www(REG_WORK2, REG_WORK3, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 8); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + LSR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + B_i(3); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + SIGNED8_REG_2_REG(REG_WORK2, d); // Make sure, sign is in MSB if shift count is 0 (to get correct N flag) + TST_ww(REG_WORK2, REG_WORK2); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSR_b_reg,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_LSR_w_reg,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSR_w_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_w(d, i); + + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + + UXTH_ww(REG_WORK3, d); // Shift count is not 0 -> unsigned required + LSR_www(REG_WORK2, REG_WORK3, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 16); + TST_ww(REG_WORK2, REG_WORK2); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + LSR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + B_i(3); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + SIGNED16_REG_2_REG(REG_WORK2, d); // Make sure, sign is in MSB if shift count is 0 (to get correct N flag) + TST_ww(REG_WORK2, REG_WORK2); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSR_w_reg,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_LSR_l_reg,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_LSR_l_imm)(d, live.state[i].val & 0x3f); + return; + } + + INIT_REGS_l(d, i); + + ANDS_ww3f(REG_WORK1, i); + uae_u32* branchadd = (uae_u32*)get_target(); + BEQ_i(0); // No shift -> X flag unchanged + + MOV_ww(REG_WORK3, d); + LSR_www(d, d, REG_WORK1); + TST_ww(d, d); + + // Calculate C Flag + SUB_wwi(REG_WORK2, REG_WORK1, 1); + LSR_www(REG_WORK2, REG_WORK3, REG_WORK2); + TBZ_wii(REG_WORK2, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + B_i(2); + + // No shift + write_jmp_target(branchadd, (uintptr)get_target()); + TST_ww(d, d); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_LSR_l_reg,(RW4 d, RR4 i)) + +/* + * LSRW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Set according to the last bit shifted out of the operand. Unaffected for a shift count of zero. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit shifted out of the operand. Cleared for a shift count of zero. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_LSRW,(RW2 d)) +{ + if (isconst(d)) { + live.state[d].val = ((live.state[d].val & 0xffff) >> 1); + return; + } + + d = rmw(d); + + UNSIGNED16_REG_2_REG(d, d); + LSR_wwi(d, d, 1); + + unlock2(d); +} +MENDFUNC(1,jnf_LSRW,(RW2 d)) + +MIDFUNC(1,jff_LSRW,(RW2 d)) +{ + d = rmw(d); + + UNSIGNED16_REG_2_REG(REG_WORK3, d); + LSR_wwi(d, REG_WORK3, 1); + TST_ww(d, d); + + // Calculate C Flag + TBZ_wii(REG_WORK3, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_LSRW,(RW2 d)) + +/* + * MOVE + * Operand Syntax: , + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_MOVE_b_imm,(W1 d, IM8 s)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | (s & 0x000000ff); + return; + } + + d = rmw(d); + + MOV_xi(REG_WORK1, s & 0xff); + BFI_xxii(d, REG_WORK1, 0, 8); + + unlock2(d); +} +MENDFUNC(2,jnf_MOVE_b_imm,(W1 d, IM8 s)) + +MIDFUNC(2,jnf_MOVE_w_imm,(W2 d, IM16 s)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | (s & 0x0000ffff); + return; + } + + d = rmw(d); + + MOVK_xi(d, s & 0xffff); + + unlock2(d); +} +MENDFUNC(2,jnf_MOVE_w_imm,(W2 d, IM16 s)) + +MIDFUNC(2,jnf_MOVE_b,(W1 d, RR1 s)) +{ + if(s == d) + return; + if (isconst(s)) { + COMPCALL(jnf_MOVE_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + BFI_xxii(d, s, 0, 8); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MOVE_b,(W1 d, RR1 s)) + +MIDFUNC(2,jnf_MOVE_w,(W2 d, RR2 s)) +{ + if(s == d) + return; + if (isconst(s)) { + COMPCALL(jnf_MOVE_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + BFI_xxii(d, s, 0, 16); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MOVE_w,(W2 d, RR2 s)) + +MIDFUNC(2,jnf_MOVE_l,(W4 d, RR4 s)) +{ + mov_l_rr(d, s); +} +MENDFUNC(2,jnf_MOVE_l,(W4 d, RR4 s)) + +MIDFUNC(2,jff_MOVE_b_imm,(W1 d, IM8 s)) +{ + d = rmw(d); + + if (s & 0x80) { + MOVN_wi(REG_WORK1, (uae_u8) ~s); + } else { + MOV_xi(REG_WORK1, (uae_u8) s); + } + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_MOVE_b_imm,(W1 d, IM8 s)) + +MIDFUNC(2,jff_MOVE_w_imm,(W2 d, IM16 s)) +{ + d = rmw(d); + + SIGNED16_IMM_2_REG(REG_WORK1, (uae_u16)s); + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_MOVE_w_imm,(W2 d, IM16 s)) + +MIDFUNC(2,jff_MOVE_l_imm,(W4 d, IM32 s)) +{ + d = writereg(d); + + LOAD_U32(d, s); + TST_ww(d, d); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_MOVE_l_imm,(W4 d, IM32 s)) + +MIDFUNC(2,jff_MOVE_b,(W1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_MOVE_b_imm)(d, live.state[s].val); + return; + } + + int s_is_d = (s == d); + if(!s_is_d) { + s = readreg(s); + d = rmw(d); + } else { + s = d = readreg(d); + } + + SIGNED8_REG_2_REG(REG_WORK1, s); + TST_ww(REG_WORK1, REG_WORK1); + if(!s_is_d) + BFI_xxii(d, REG_WORK1, 0, 8); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MOVE_b,(W1 d, RR1 s)) + +MIDFUNC(2,jff_MOVE_w,(W2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_MOVE_w_imm)(d, live.state[s].val); + return; + } + + int s_is_d = (s == d); + if(!s_is_d) { + s = readreg(s); + d = rmw(d); + } else { + s = d = readreg(d); + } + + SIGNED16_REG_2_REG(REG_WORK1, s); + TST_ww(REG_WORK1, REG_WORK1); + if(!s_is_d) + BFI_xxii(d, REG_WORK1, 0, 16); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MOVE_w,(W2 d, RR2 s)) + +MIDFUNC(2,jff_MOVE_l,(W4 d, RR4 s)) +{ + if (isconst(s)) { + COMPCALL(jff_MOVE_l_imm)(d, live.state[s].val); + return; + } + + int s_is_d = (s == d); + s = readreg(s); + + if(!s_is_d) { + d = writereg(d); + MOV_ww(d, s); + } + TST_ww(s, s); + + flags_carry_inverted = false; + if(!s_is_d) + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jff_MOVE_l,(W4 d, RR4 s)) + +/* + * MVMEL + * + * Flags: Not affected. + * + */ +MIDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IM8 offset)) +{ + s = readreg(s); + d = writereg(d); + + LDRH_wXi(REG_WORK1, s, offset); + REV16_ww(d, REG_WORK1); + SXTH_ww(d, d); + + unlock2(d); + unlock2(s); +} +MENDFUNC(3,jnf_MVMEL_w,(W4 d, RR4 s, IM8 offset)) + +MIDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IM8 offset)) +{ + s = readreg(s); + d = writereg(d); + + LDR_wXi(REG_WORK1, s, offset); + REV32_xx(d, REG_WORK1); + + unlock2(d); + unlock2(s); +} +MENDFUNC(3,jnf_MVMEL_l,(W4 d, RR4 s, IM8 offset)) + +/* + * MVMLE + * + * Flags: Not affected. + * + */ +MIDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IM8 offset)) +{ + s = readreg(s); + d = readreg(d); + + REV16_ww(REG_WORK1, s); + if (offset >= 0) + STRH_wXi(REG_WORK1, d, offset); + else { + SUB_wwi(REG_WORK2, d, -offset); + STRH_wXi(REG_WORK1, REG_WORK2, 0); + } + + unlock2(d); + unlock2(s); +} +MENDFUNC(3,jnf_MVMLE_w,(RR4 d, RR4 s, IM8 offset)) + +MIDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IM8 offset)) +{ + s = readreg(s); + d = readreg(d); + + REV32_xx(REG_WORK1, s); + if (offset >= 0) + STR_wXi(REG_WORK1, d, offset); + else { + SUB_wwi(REG_WORK2, d, -offset); + STR_wXi(REG_WORK1, REG_WORK2, 0); + } + + unlock2(d); + unlock2(s); +} +MENDFUNC(3,jnf_MVMLE_l,(RR4 d, RR4 s, IM8 offset)) + +/* + * MOVE16 + * + * Flags: Not affected. + * + */ +MIDFUNC(2,jnf_MOVE16,(RR4 d, RR4 s)) +{ + s = readreg(s); + d = readreg(d); + + CLEAR_LOW4_xx(REG_WORK3, s); + CLEAR_LOW4_xx(REG_WORK4, d); + + ADD_www(REG_WORK3, REG_WORK3, R_MEMSTART); + ADD_www(REG_WORK4, REG_WORK4, R_MEMSTART); + + LDP_xxXi(REG_WORK1, REG_WORK2, REG_WORK3, 0); + STP_xxXi(REG_WORK1, REG_WORK2, REG_WORK4, 0); + + unlock2(d); + unlock2(s); +} +MENDFUNC(2,jnf_MOVE16,(RR4 d, RR4 s)) + +/* + * MOVEA + * Operand Syntax: , An + * + * Operand Size: 16,32 + * + * Flags: Not affected. + * + */ +MIDFUNC(2,jnf_MOVEA_w,(W4 d, RR2 s)) +{ + if (isconst(s)) { + set_const(d, (uae_s32)(uae_s16)live.state[s].val); + return; + } + + INIT_REGS_l(d, s); + + SIGNED16_REG_2_REG(d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MOVEA_w,(W4 d, RR2 s)) + +MIDFUNC(2,jnf_MOVEA_l,(W4 d, RR4 s)) +{ + mov_l_rr(d, s); +} +MENDFUNC(2,jnf_MOVEA_l,(W4 d, RR4 s)) + +/* + * MULS + * Operand Syntax: , Dn + * + * Operand Size: 16 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if overflow. Cleared otherwise. (32 Bit multiply only) + * C Always cleared. + * + */ +MIDFUNC(2,jnf_MULS,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + SIGNED16_REG_2_REG(d, d); + SMULL_xww(d, d, REG_WORK1); + unlock2(d); + return; + } + + INIT_REGS_l(d, s); + + SIGNED16_REG_2_REG(d, d); + SIGNED16_REG_2_REG(REG_WORK1, s); + SMULL_xww(d, d, REG_WORK1); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MULS,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_MULS,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + SIGNED16_REG_2_REG(d, d); + SIGNED16_REG_2_REG(REG_WORK1, s); + SMULL_xww(d, d, REG_WORK1); + TST_ww(d, d); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MULS,(RW4 d, RR4 s)) + +MIDFUNC(2,jnf_MULS32,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + SMULL_xww(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MULS32,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_MULS32,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + SMULL_xww(d, d, s); + TST_ww(d, d); + + if (needed_flags & FLAG_V) { + LSR_xxi(REG_WORK1, d, 32); + CBZ_wi(REG_WORK1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxVflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MULS32,(RW4 d, RR4 s)) + +MIDFUNC(2,jnf_MULS64,(RW4 d, RW4 s)) +{ + s = rmw(s); + d = rmw(d); + + SMULL_xww(d, d, s); + LSR_xxi(s, d, 32); + + unlock2(s); + unlock2(d); +} +MENDFUNC(2,jnf_MULS64,(RW4 d, RW4 s)) + +MIDFUNC(2,jff_MULS64,(RW4 d, RW4 s)) +{ + s = rmw(s); + d = rmw(d); + + SXTW_xw(REG_WORK1, d); + SXTW_xw(REG_WORK2, s); + SMULL_xww(d, REG_WORK1, REG_WORK2); + TST_xx(d, d); + LSR_xxi(s, d, 32); + + if (needed_flags & FLAG_V) { + // check overflow: no overflow if high part is 0 or 0xffffffff + SMULH_xxx(REG_WORK3, REG_WORK1, REG_WORK2); + CBZ_xi(REG_WORK3, 6); + ADD_wwi(REG_WORK3, REG_WORK3, 1); + CBZ_xi(REG_WORK3, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxVflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + unlock2(s); + unlock2(d); +} +MENDFUNC(2,jff_MULS64,(RW4 d, RW4 s)) + +/* + * MULU + * Operand Syntax: , Dn + * + * Operand Size: 16 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if overflow. Cleared otherwise. (32 Bit multiply only) + * C Always cleared. + * + */ +MIDFUNC(2,jnf_MULU,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK1, tmp); + UNSIGNED16_REG_2_REG(d, d); + UMULL_xww(d, d, REG_WORK1); + unlock2(d); + return; + } + + INIT_REGS_l(d, s); + + UNSIGNED16_REG_2_REG(d, d); + UNSIGNED16_REG_2_REG(REG_WORK1, s); + UMULL_xww(d, d, REG_WORK1); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MULU,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_MULU,(RW4 d, RR4 s)) +{ + if (isconst(s)) { + uae_u16 tmp = (uae_u16)live.state[s].val; + d = rmw(d); + UNSIGNED16_IMM_2_REG(REG_WORK1, tmp); + UNSIGNED16_REG_2_REG(d, d); + UMULL_xww(d, d, REG_WORK1); + TST_ww(d, d); + flags_carry_inverted = false; + unlock2(d); + return; + } + + INIT_REGS_l(d, s); + + UNSIGNED16_REG_2_REG(d, d); + UNSIGNED16_REG_2_REG(REG_WORK1, s); + UMULL_xww(d, d, REG_WORK1); + TST_ww(d, d); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MULU,(RW4 d, RR4 s)) + +MIDFUNC(2,jnf_MULU32,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + UMULL_xww(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_MULU32,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_MULU32,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + UMULL_xww(d, d, s); + TST_ww(d, d); + + if (needed_flags & FLAG_V) { + LSR_xxi(REG_WORK1, d, 32); + CBZ_wi(REG_WORK1, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxVflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_MULU32,(RW4 d, RR4 s)) + +MIDFUNC(2,jnf_MULU64,(RW4 d, RW4 s)) +{ + s = rmw(s); + d = rmw(d); + + UMULL_xww(d, d, s); + LSR_xxi(s, d, 32); + + unlock2(s); + unlock2(d); +} +MENDFUNC(2,jnf_MULU64,(RW4 d, RW4 s)) + +MIDFUNC(2,jff_MULU64,(RW4 d, RW4 s)) +{ + s = rmw(s); + d = rmw(d); + + if (needed_flags & FLAG_V) { + MOV_ww(REG_WORK1, d); + MOV_ww(REG_WORK2, s); + UMULL_xww(d, REG_WORK1, REG_WORK2); + } else { + UMULL_xww(d, d, s); + } + TST_xx(d, d); + LSR_xxi(s, d, 32); + + if (needed_flags & FLAG_V) { + // check overflow: no overflow if high part is 0 + UMULH_xxx(REG_WORK3, REG_WORK1, REG_WORK2); + CBZ_xi(REG_WORK3, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxVflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + unlock2(s); + unlock2(d); +} +MENDFUNC(2,jff_MULU64,(RW4 d, RW4 s)) + +/* + * NEG + * Operand Syntax: + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if an overflow occurs. Cleared otherwise. + * C Set if a borrow occurs. Cleared otherwise. + * + */ +MIDFUNC(1,jnf_NEG_b,(RW1 d)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + NEG_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + + unlock2(d); +} +MENDFUNC(1,jnf_NEG_b,(RW1 d)) + +MIDFUNC(1,jnf_NEG_w,(RW2 d)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + NEG_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + + unlock2(d); +} +MENDFUNC(1,jnf_NEG_w,(RW2 d)) + +MIDFUNC(1,jnf_NEG_l,(RW4 d)) +{ + d = rmw(d); + + NEG_ww(d, d); + + unlock2(d); +} +MENDFUNC(1,jnf_NEG_l,(RW4 d)) + +MIDFUNC(1,jff_NEG_b,(RW1 d)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + NEGS_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_NEG_b,(RW1 d)) + +MIDFUNC(1,jff_NEG_w,(RW2 d)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + NEGS_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_NEG_w,(RW2 d)) + +MIDFUNC(1,jff_NEG_l,(RW4 d)) +{ + d = rmw(d); + + NEGS_ww(d, d); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(1,jff_NEG_l,(RW4 d)) + +/* + * NEGX + * Operand Syntax: + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Cleared if the result is nonzero; unchanged otherwise. + * V Set if an overflow occurs. Cleared otherwise. + * C Set if a borrow occurs. Cleared otherwise. + * + * Attention: Z is cleared only if the result is nonzero. Unchanged otherwise + * + */ +MIDFUNC(1,jnf_NEGX_b,(RW1 d)) +{ + int x = readreg(FLAGX); + INIT_REG_b(d); + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SIGNED8_REG_2_REG(REG_WORK1, d); + NGC_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + + unlock2(d); + unlock2(x); +} +MENDFUNC(1,jnf_NEGX_b,(RW1 d)) + +MIDFUNC(1,jnf_NEGX_w,(RW2 d)) +{ + int x = readreg(FLAGX); + INIT_REG_w(d); + + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SIGNED16_REG_2_REG(REG_WORK1, d); + NGC_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + + unlock2(d); + unlock2(x); +} +MENDFUNC(1,jnf_NEGX_w,(RW2 d)) + +MIDFUNC(1,jnf_NEGX_l,(RW4 d)) +{ + int x = readreg(FLAGX); + d = rmw(d); + + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + NGC_ww(d, d); + + unlock2(d); + unlock2(x); +} +MENDFUNC(1,jnf_NEGX_l,(RW4 d)) + +MIDFUNC(1,jff_NEGX_b,(RW1 d)) +{ + INIT_REG_b(d); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SIGNED8_REG_2_REG(REG_WORK1, d); + NGCS_ww(REG_WORK1, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 8); + + MRS_NZCV_x(REG_WORK4); + EOR_xxCflag(REG_WORK4, REG_WORK4); + AND_www(REG_WORK4, REG_WORK4, REG_WORK2); + MSR_NZCV_x(REG_WORK4); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_wwii(x, REG_WORK4, 29, 1); // Duplicate carry + + unlock2(x); + unlock2(d); +} +MENDFUNC(1,jff_NEGX_b,(RW1 d)) + +MIDFUNC(1,jff_NEGX_w,(RW2 d)) +{ + INIT_REG_w(d); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SIGNED16_REG_2_REG(REG_WORK1, d); + NGCS_ww(REG_WORK1, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 16); + + MRS_NZCV_x(REG_WORK4); + EOR_xxCflag(REG_WORK4, REG_WORK4); + AND_www(REG_WORK4, REG_WORK4, REG_WORK2); + MSR_NZCV_x(REG_WORK4); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_wwii(x, REG_WORK4, 29, 1); // Duplicate carry + + unlock2(x); + unlock2(d); +} +MENDFUNC(1,jff_NEGX_w,(RW2 d)) + +MIDFUNC(1,jff_NEGX_l,(RW4 d)) +{ + d = rmw(d); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + NGCS_ww(d, d); + + MRS_NZCV_x(REG_WORK4); + EOR_xxCflag(REG_WORK4, REG_WORK4); + AND_www(REG_WORK4, REG_WORK4, REG_WORK2); + MSR_NZCV_x(REG_WORK4); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_wwii(x, REG_WORK4, 29, 1); // Duplicate carry + + unlock2(x); + unlock2(d); +} +MENDFUNC(1,jff_NEGX_l,(RW4 d)) + +/* + * NOT + * Operand Syntax: + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(1,jnf_NOT_b,(RW1 d)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | ((~live.state[d].val) & 0x000000ff); + return; + } + + INIT_REG_b(d); + + if(targetIsReg) { + MVN_ww(REG_WORK1, d); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + MVN_ww(d, d); + } + + unlock2(d); +} +MENDFUNC(1,jnf_NOT_b,(RW1 d)) + +MIDFUNC(1,jnf_NOT_w,(RW2 d)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | ((~live.state[d].val) & 0x0000ffff); + return; + } + + INIT_REG_w(d); + + if(targetIsReg) { + MVN_ww(REG_WORK1, d); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + MVN_ww(d, d); + } + + unlock2(d); +} +MENDFUNC(1,jnf_NOT_w,(RW2 d)) + +MIDFUNC(1,jnf_NOT_l,(RW4 d)) +{ + if (isconst(d)) { + live.state[d].val = ~live.state[d].val; + return; + } + + d = rmw(d); + + MVN_ww(d, d); + + unlock2(d); +} +MENDFUNC(1,jnf_NOT_l,(RW4 d)) + +MIDFUNC(1,jff_NOT_b,(RW1 d)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + if(targetIsReg) { + MVN_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + TST_ww(REG_WORK1, REG_WORK1); + } else { + MVN_ww(d, REG_WORK1); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_NOT_b,(RW1 d)) + +MIDFUNC(1,jff_NOT_w,(RW2 d)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + if(targetIsReg) { + MVN_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + TST_ww(REG_WORK1, REG_WORK1); + } else { + MVN_ww(d, REG_WORK1); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_NOT_w,(RW2 d)) + +MIDFUNC(1,jff_NOT_l,(RW4 d)) +{ + d = rmw(d); + + MVN_ww(d, d); + TST_ww(d, d); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_NOT_l,(RW4 d)) + +/* + * OR + * Operand Syntax: , Dn + * Dn, + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(2,jnf_OR_b_imm,(RW1 d, IM8 v)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | ((live.state[d].val | v) & 0x000000ff); + return; + } + + INIT_REG_b(d); + + MOV_xi(REG_WORK2, v & 0xff); + ORR_www(d, d, REG_WORK2); + + unlock2(d); +} +MENDFUNC(2,jnf_OR_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jnf_OR_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_OR_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + if(targetIsReg) { + ORR_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ORR_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_OR_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_OR_w_imm,(RW2 d, IM16 v)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | ((live.state[d].val | v) & 0x0000ffff); + return; + } + + INIT_REG_w(d); + + MOV_xi(REG_WORK1, v & 0xffff); + ORR_www(d, d, REG_WORK1); + + unlock2(d); +} +MENDFUNC(2,jnf_OR_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jnf_OR_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_OR_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + if(targetIsReg) { + ORR_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ORR_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_OR_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_OR_l,(RW4 d, RR4 s)) +{ + if (isconst(d) && isconst(s)) { + live.state[d].val = live.state[d].val | live.state[s].val; + return; + } + + INIT_REGS_l(d, s); + + ORR_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_OR_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_OR_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ORR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_OR_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jff_OR_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_OR_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + SIGNED8_REG_2_REG(REG_WORK1, d); + SIGNED8_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + ORR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_OR_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_OR_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_IMM_2_REG(REG_WORK2, v); + if(targetIsReg) { + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ORR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_OR_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jff_OR_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_OR_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + SIGNED16_REG_2_REG(REG_WORK1, d); + SIGNED16_REG_2_REG(REG_WORK2, s); + if(targetIsReg) { + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + TST_ww(REG_WORK1, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + } else { + ORR_www(d, REG_WORK1, REG_WORK2); + TST_ww(d, d); + } + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_OR_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_OR_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + ORR_www(d, d, s); + TST_ww(d, d); + + flags_carry_inverted = false; + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_OR_l,(RW4 d, RR4 s)) + +/* + * ORSR + * Operand Syntax: #, CCR + * + * Operand Size: 8 + * + * X — Set if bit 4 of immediate operand is one; unchanged otherwise. + * N — Set if bit 3 of immediate operand is one; unchanged otherwise. + * Z — Set if bit 2 of immediate operand is one; unchanged otherwise. + * V — Set if bit 1 of immediate operand is one; unchanged otherwise. + * C — Set if bit 0 of immediate operand is one; unchanged otherwise. + * + */ +MIDFUNC(1,jff_ORSR,(IM32 s, IM8 x)) +{ + MRS_NZCV_x(REG_WORK1); + if (flags_carry_inverted) { + EOR_xxCflag(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; + } + MOV_xish(REG_WORK2, (s >> 16), 16); + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + + if (x) { + int f = writereg(FLAGX); + MOV_wi(f, 1); + unlock2(f); + } +} +MENDFUNC(2,jff_ORSR,(IM32 s, IM8 x)) + +/* + * ROL + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. + * + */ +MIDFUNC(2,jnf_ROL_b_imm,(RW1 d, IM8 i)) +{ + if(i & 0x1f) { + INIT_REG_b(d); + + LSL_wwi(REG_WORK1, d, 24); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + ROR_wwi(REG_WORK1, REG_WORK1, (32 - (i & 0x1f))); + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROL_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jnf_ROL_w_imm,(RW2 d, IM8 i)) +{ + if(i & 0x1f) { + INIT_REG_w(d); + + MOV_ww(REG_WORK1, d); + BFI_wwii(REG_WORK1, REG_WORK1, 16, 16); + ROR_wwi(REG_WORK1, REG_WORK1, (32 - (i & 0x1f))); + BFI_wwii(d, REG_WORK1, 0, 16); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROL_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jnf_ROL_l_imm,(RW4 d, IM8 i)) +{ + if(i & 0x1f) { + if (isconst(d)) { + i = i & 31; + live.state[d].val = (live.state[d].val << i) | (live.state[d].val >> (32-i)); + return; + } + + d = rmw(d); + + ROR_wwi(d, d, (32 - (i & 0x1f))); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROL_l_imm,(RW4 d, RR4 s, IM8 i)) + +MIDFUNC(2,jff_ROL_b_imm,(RW1 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + LSL_wwi(REG_WORK1, d, 24); + if (i) { + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + if(i & 0x1f) { + ROR_wwi(REG_WORK1, REG_WORK1, (32 - (i & 0x1f))); + } + TST_ww(REG_WORK1, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 8); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, REG_WORK1, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + } else { + TST_ww(REG_WORK1, REG_WORK1); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROL_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_ROL_w_imm,(RW2 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + MOV_ww(REG_WORK1, d); + BFI_wwii(REG_WORK1, REG_WORK1, 16, 16); + if (i) { + if(i & 0x1f) + ROR_wwi(REG_WORK1, REG_WORK1, (32 - (i & 0x1f))); + TST_ww(REG_WORK1, REG_WORK1); + BFI_wwii(d, REG_WORK1, 0, 16); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, REG_WORK1, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + } else { + TST_ww(REG_WORK1, REG_WORK1); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROL_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_ROL_l_imm,(RW4 d, IM8 i)) +{ + if (i) { + if(i & 0x1f) { + d = rmw(d); + ROR_wwi(d, d, (32 - (i & 0x1f))); + } else { + d = readreg(d); + } + TST_ww(d, d); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, d, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + } else { + d = readreg(d); + TST_ww(d, d); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROL_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jnf_ROL_b,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROL_b_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_b(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + LSL_wwi(REG_WORK2, d, 24); + ORR_wwwLSRi(REG_WORK2, REG_WORK2, REG_WORK2, 8); + ORR_wwwLSRi(REG_WORK2, REG_WORK2, REG_WORK2, 16); + ROR_www(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 8); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROL_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_ROL_w,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROL_w_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_w(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, REG_WORK2, 16, 16); + ROR_www(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 16); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROL_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_ROL_l,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROL_l_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_l(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + ROR_www(d, d, REG_WORK1); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROL_l,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ROL_b,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROL_b_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_b(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + CBNZ_wi(REG_WORK1, 4); + + // shift count is 0 + LSL_wwi(REG_WORK3, d, 24); + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + LSL_wwi(REG_WORK2, d, 24); + ORR_wwwLSRi(REG_WORK2, REG_WORK2, REG_WORK2, 8); + ORR_wwwLSRi(REG_WORK2, REG_WORK2, REG_WORK2, 16); + ROR_www(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 8); + TST_ww(REG_WORK2, REG_WORK2); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, d, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROL_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ROL_w,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROL_w_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_w(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + CBNZ_wi(REG_WORK1, 4); + + // shift count is 0 + LSL_wwi(REG_WORK3, d, 16); + TST_ww(REG_WORK3, REG_WORK3); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, REG_WORK2, 16, 16); + ROR_www(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 16); + TST_ww(REG_WORK2, REG_WORK2); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, d, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROL_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_ROL_l,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROL_l_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_l(d, i); + + UBFIZ_xxii(REG_WORK1, i, 0, 5); // AND_rri(REG_WORK1, i, 0x1f); + CBNZ_wi(REG_WORK1, 3); + + // shift count is 0 + TST_ww(d, d); // NZ correct, VC cleared + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // + + MOV_wi(REG_WORK2, 32); + SUB_www(REG_WORK1, REG_WORK2, REG_WORK1); + + ROR_www(d, d, REG_WORK1); + TST_ww(d, d); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, d, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + + // + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(d); + unlock2(i); +} +MENDFUNC(2,jff_ROL_l,(RW4 d, RR4 i)) + +/* + * ROLW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_ROLW,(RW2 d)) +{ + d = rmw(d); + + BFI_wwii(d, d, 16, 16); + ROR_wwi(d, d, (32 - 1)); + + unlock2(d); +} +MENDFUNC(1,jnf_ROLW,(RW2 d)) + +MIDFUNC(1,jff_ROLW,(RW2 d)) +{ + d = rmw(d); + + BFI_wwii(d, d, 16, 16); + ROR_wwi(d, d, (32 - 1)); + TST_ww(d, d); + + MRS_NZCV_x(REG_WORK4); + BFI_wwii(REG_WORK4, d, 29, 1); // Handle C flag + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_ROLW,(RW2 d)) + +/* + * ROXL + * Operand Syntax: Dx, Dy + * #, Dy + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit rotated out of the operand. Unchanged when the rotate count is zero. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. + * + */ +MIDFUNC(2,jnf_ROXL_b,(RW1 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_b(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 35); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 36); + CMP_wi(REG_WORK1, 17); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 18); + CMP_wi(REG_WORK1, 8); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 9); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 8, 1); // move x to left side of d + BFI_wwii(REG_WORK2, REG_WORK2, 9, 9); // duplicate 9 bits + + MOV_wi(REG_WORK3, 9); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_www(REG_WORK2, REG_WORK2, REG_WORK3); + + BFI_wwii(d, REG_WORK2, 0, 8); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXL_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_ROXL_w,(RW2 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_w(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 33); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 34); + CMP_wi(REG_WORK1, 16); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 17); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 16, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 17, 17); // duplicate 17 bits + + MOV_wi(REG_WORK3, 17); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_xxx(REG_WORK2, REG_WORK2, REG_WORK3); + + BFI_wwii(d, REG_WORK2, 0, 16); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXL_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_ROXL_l,(RW4 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_l(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 32); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 33); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_xxii(REG_WORK2, x, 32, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 33, 31); // duplicate 31 bits + + MOV_wi(REG_WORK3, 33); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_xxx(d, REG_WORK2, REG_WORK3); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXL_l,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ROXL_b,(RW1 d, RR4 i)) +{ + INIT_REGS_b(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 35); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 36); + CMP_wi(REG_WORK1, 17); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 18); + CMP_wi(REG_WORK1, 8); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 9); + CBNZ_wi(REG_WORK1, 4); // need to rotate + + LSL_wwi(REG_WORK1, d, 24); + TST_ww(REG_WORK1, REG_WORK1); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 8, 1); // move x to left side of d + BFI_wwii(REG_WORK2, REG_WORK2, 9, 9); // duplicate 9 bits + + MOV_wi(REG_WORK3, 9); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_www(REG_WORK2, REG_WORK2, REG_WORK3); + BFI_wwii(d, REG_WORK2, 0, 8); + + // Calculate NZ + LSL_wwi(REG_WORK1, REG_WORK2, 24); + TST_ww(REG_WORK1, REG_WORK1); + + // Calculate C: bit left of result + MRS_NZCV_x(REG_WORK4); + UBFX_wwii(x, REG_WORK2, 8, 1); + BFI_wwii(REG_WORK4, x, 29, 1); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXL_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ROXL_w,(RW2 d, RR4 i)) +{ + INIT_REGS_w(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 33); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 34); + CMP_wi(REG_WORK1, 16); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 17); + CBNZ_wi(REG_WORK1, 4); // need to rotate + + LSL_wwi(REG_WORK1, d, 16); + TST_ww(REG_WORK1, REG_WORK1); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 16, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 17, 17); // duplicate 17 bits + + MOV_wi(REG_WORK3, 17); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_xxx(REG_WORK2, REG_WORK2, REG_WORK3); + + BFI_wwii(d, REG_WORK2, 0, 16); + + // Calculate NZ + LSL_wwi(REG_WORK1, REG_WORK2, 16); + TST_ww(REG_WORK1, REG_WORK1); + + // Calculate C: bit left of result + MRS_NZCV_x(REG_WORK4); + UBFX_wwii(x, REG_WORK2, 16, 1); + BFI_wwii(REG_WORK4, x, 29, 1); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXL_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_ROXL_l,(RW4 d, RR4 i)) +{ + INIT_REGS_l(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 32); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 33); + CBNZ_wi(REG_WORK1, 3); // need to rotate + + TST_ww(d, d); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_xxii(REG_WORK2, x, 32, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 33, 31); // duplicate 31 bits + + MOV_wi(REG_WORK3, 33); + SUB_www(REG_WORK3, REG_WORK3, REG_WORK1); + LSR_xxx(d, REG_WORK2, REG_WORK3); + + // Calculate NZ + TST_ww(d, d); + + // Calculate C + MRS_NZCV_x(REG_WORK4); + SUB_wwi(REG_WORK3, REG_WORK3, 1); + LSR_xxx(REG_WORK2, REG_WORK2, REG_WORK3); + UBFX_wwii(x, REG_WORK2, 0, 1); + BFI_wwii(REG_WORK4, x, 29, 1); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXL_l,(RW4 d, RR4 i)) + +/* + * ROR + * Operand Syntax: Dx, Dy + * #, Dy + * + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. + * + */ +MIDFUNC(2,jnf_ROR_b_imm,(RW1 d, IM8 i)) +{ + if(i & 0x07) { + INIT_REG_b(d); + + MOV_ww(REG_WORK1, d); + BFI_wwii(REG_WORK1, REG_WORK1, 8, 8); + ROR_wwi(REG_WORK1, REG_WORK1, i & 0x07); + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jnf_ROR_w_imm,(RW2 d, IM8 i)) +{ + if(i & 0x0f) { + INIT_REG_w(d); + + MOV_ww(REG_WORK1, d); + BFI_wwii(REG_WORK1, REG_WORK1, 16, 16); + ROR_wwi(REG_WORK1, REG_WORK1, i & 0x0f); + BFI_wwii(d, REG_WORK1, 0, 16); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jnf_ROR_l_imm,(RW4 d, IM8 i)) +{ + if(i & 0x1f) { + if (isconst(d)) { + i = i & 31; + live.state[d].val = (live.state[d].val >> i) | (live.state[d].val << (32-i)); + return; + } + + d = rmw(d); + + ROR_wwi(d, d, i & 31); + + unlock2(d); + } +} +MENDFUNC(2,jnf_ROR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jff_ROR_b_imm,(RW1 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + LSL_wwi(REG_WORK1, d, 24); + if(i & 0x07) { + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + ROR_wwi(REG_WORK1, REG_WORK1, i & 0x07); + BFI_wwii(d, REG_WORK1, 0, 8); + } + TST_ww(REG_WORK1, REG_WORK1); + if(i) { + TBZ_wii(REG_WORK1, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROR_b_imm,(RW1 d, IM8 i)) + +MIDFUNC(2,jff_ROR_w_imm,(RW2 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + LSL_wwi(REG_WORK1, d, 16); + if(i & 0x0f) { + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + ROR_wwi(REG_WORK1, REG_WORK1, i & 0x0f); + BFI_wwii(d, REG_WORK1, 0, 16); + } + TST_ww(REG_WORK1, REG_WORK1); + if (i) { + TBZ_wii(REG_WORK1, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROR_w_imm,(RW2 d, IM8 i)) + +MIDFUNC(2,jff_ROR_l_imm,(RW4 d, IM8 i)) +{ + if(i) + d = rmw(d); + else + d = readreg(d); + + if(i & 0x1f) { + ROR_wwi(d, d, i & 0x1f); + } + TST_ww(d, d); + if (i) { + TBZ_wii(d, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + } + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(2,jff_ROR_l_imm,(RW4 d, IM8 i)) + +MIDFUNC(2,jnf_ROR_b,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROR_b_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_b(d, i); + + LSL_wwi(REG_WORK1, d, 24); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + ROR_www(REG_WORK1, REG_WORK1, i); + BFI_wwii(d, REG_WORK1, 0, 8); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROR_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_ROR_w,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROR_w_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_w(d, i); + + LSL_wwi(REG_WORK1, d, 16); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + ROR_www(REG_WORK1, REG_WORK1, i); + BFI_wwii(d, REG_WORK1, 0, 16); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROR_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_ROR_l,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jnf_ROR_l_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_l(d, i); + + ROR_www(d, d, i); + + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROR_l,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ROR_b,(RW1 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROR_b_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_b(d, i); + + LSL_wwi(REG_WORK1, d, 24); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 8); + ORR_wwwLSRi(REG_WORK1, REG_WORK1, REG_WORK1, 16); + AND_ww3f(REG_WORK2, i); + ROR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 8); + TST_ww(REG_WORK1, REG_WORK1); + + CBZ_wi(REG_WORK2, 5); // C cleared if no shift + TBZ_wii(REG_WORK1, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROR_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ROR_w,(RW2 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROR_w_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_w(d, i); + + LSL_wwi(REG_WORK1, d, 16); + BFXIL_wwii(REG_WORK1, REG_WORK1, 16, 16); + AND_ww3f(REG_WORK2, i); + ROR_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFI_wwii(d, REG_WORK1, 0, 16); + TST_ww(REG_WORK1, REG_WORK1); + + CBZ_wi(REG_WORK2, 5); // C cleared if no shift + TBZ_wii(REG_WORK1, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROR_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_ROR_l,(RW4 d, RR4 i)) +{ + if (isconst(i)) { + COMPCALL(jff_ROR_l_imm)(d, (uae_u8)live.state[i].val); + return; + } + + INIT_REGS_l(d, i); + + AND_ww3f(REG_WORK1, i); + ROR_www(d, d, REG_WORK1); + TST_ww(d, d); + + CBZ_wi(REG_WORK1, 5); // C cleared if no shift + TBZ_wii(d, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROR_l,(RW4 d, RR4 i)) + +/* + * RORW + * Operand Syntax: + * + * Operand Size: 16 + * + * X Not affected. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. + * + * Target is never a register. + */ +MIDFUNC(1,jnf_RORW,(RW2 d)) +{ + d = rmw(d); + + BFI_wwii(d, d, 16, 16); + ROR_wwi(d, d, 1); + + unlock2(d); +} +MENDFUNC(1,jnf_RORW,(RW2 d)) + +MIDFUNC(1,jff_RORW,(RW2 d)) +{ + d = rmw(d); + + BFI_wwii(d, d, 16, 16); + ROR_wwi(d, d, 1); + TST_ww(d, d); + + TBZ_wii(d, 31, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_RORW,(RW2 d)) + +/* + * ROXR + * Operand Syntax: Dx, Dy + * #, Dy + * + * Operand Size: 8,16,32 + * + * X Set according to the last bit rotated out of the operand. Unchanged when the rotate count is zero. + * N Set if the most significant bit of the result is set. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Always cleared. + * C Set according to the last bit rotated out of the operand. Cleared when the rotate count is zero. + * + */ +MIDFUNC(2,jnf_ROXR_b,(RW1 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_b(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 35); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 36); + CMP_wi(REG_WORK1, 17); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 18); + CMP_wi(REG_WORK1, 8); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 9); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 8, 1); // move x to left side of d + BFI_wwii(REG_WORK2, REG_WORK2, 9, 9); // duplicate 9 bits + + LSR_www(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 8); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXR_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jnf_ROXR_w,(RW2 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_w(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 33); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 34); + CMP_wi(REG_WORK1, 16); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 17); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 16, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 17, 17); // duplicate 17 bits + + LSR_xxx(REG_WORK2, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK2, 0, 16); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXR_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jnf_ROXR_l,(RW4 d, RR4 i)) +{ + int x = readreg(FLAGX); + INIT_REGS_l(d, i); + + clobber_flags(); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 32); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 33); + uae_u32* branchadd = (uae_u32*)get_target(); + CBZ_wi(REG_WORK1, 0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_xxii(REG_WORK2, x, 32, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 33, 31); // duplicate 31 bits + + LSR_xxx(d, REG_WORK2, REG_WORK1); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jnf_ROXR_l,(RW4 d, RR4 i)) + +MIDFUNC(2,jff_ROXR_b,(RW1 d, RR4 i)) +{ + INIT_REGS_b(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 35); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 36); + CMP_wi(REG_WORK1, 17); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 18); + CMP_wi(REG_WORK1, 8); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 9); + CBNZ_wi(REG_WORK1, 4); // need to rotate + + LSL_wwi(REG_WORK1, d, 24); + TST_ww(REG_WORK1, REG_WORK1); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 8, 1); // move x to left side of d + BFI_wwii(REG_WORK2, REG_WORK2, 9, 9); // duplicate 9 bits + + LSR_www(REG_WORK3, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK3, 0, 8); + + // calc N and Z + LSL_wwi(REG_WORK3, REG_WORK3, 24); + TST_ww(REG_WORK3, REG_WORK3); + + // calc C and X + SUB_wwi(REG_WORK1, REG_WORK1, 1); + LSR_www(REG_WORK3, REG_WORK2, REG_WORK1); + UBFIZ_wwii(x, REG_WORK3, 0, 1); + TBZ_wii(x, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXR_b,(RW1 d, RR4 i)) + +MIDFUNC(2,jff_ROXR_w,(RW2 d, RR4 i)) +{ + INIT_REGS_w(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 33); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 34); + CMP_wi(REG_WORK1, 16); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 17); + CBNZ_wi(REG_WORK1, 4); // need to rotate + + LSL_wwi(REG_WORK1, d, 16); + TST_ww(REG_WORK1, REG_WORK1); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_wwii(REG_WORK2, x, 16, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 17, 17); // duplicate 17 bits + + LSR_xxx(REG_WORK3, REG_WORK2, REG_WORK1); + BFI_wwii(d, REG_WORK3, 0, 16); + + // calc N and Z + LSL_wwi(REG_WORK3, REG_WORK3, 16); + TST_ww(REG_WORK3, REG_WORK3); + + // calc C and X + SUB_wwi(REG_WORK1, REG_WORK1, 1); + LSR_www(REG_WORK3, REG_WORK2, REG_WORK1); + UBFIZ_wwii(x, REG_WORK3, 0, 1); + TBZ_wii(x, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXR_w,(RW2 d, RR4 i)) + +MIDFUNC(2,jff_ROXR_l,(RW4 d, RR4 i)) +{ + INIT_REGS_l(d, i); + int x = rmw(FLAGX); + + AND_ww3f(REG_WORK1, i); + CMP_wi(REG_WORK1, 32); + BLE_i(2); + SUB_wwi(REG_WORK1, REG_WORK1, 33); + CBNZ_wi(REG_WORK1, 3); // need to rotate + + TST_ww(d, d); + uae_u32* branchadd = (uae_u32*)get_target(); + B_i(0); // end of op + + // need to rotate + MOV_ww(REG_WORK2, d); + BFI_xxii(REG_WORK2, x, 32, 1); // move x to left side of d + BFI_xxii(REG_WORK2, REG_WORK2, 33, 31); // duplicate 31 bits + + LSR_xxx(d, REG_WORK2, REG_WORK1); + + // Calculate NZ + TST_ww(d, d); + + // Calculate C + SUB_wwi(REG_WORK1, REG_WORK1, 1); + LSR_xxx(REG_WORK3, REG_WORK2, REG_WORK1); + UBFIZ_wwii(x, REG_WORK3, 0, 1); + TBZ_wii(x, 0, 4); + MRS_NZCV_x(REG_WORK4); + SET_xxCflag(REG_WORK4, REG_WORK4); + MSR_NZCV_x(REG_WORK4); + + // end of op + write_jmp_target(branchadd, (uintptr)get_target()); + + flags_carry_inverted = false; + unlock2(x); + EXIT_REGS(d, i); +} +MENDFUNC(2,jff_ROXR_l,(RW4 d, RR4 i)) + +/* + * SCC + * + */ +MIDFUNC(2,jnf_SCC,(W1 d, IM8 cc)) +{ + FIX_INVERTED_CARRY + + INIT_WREG_b(d); + + switch (cc) { + case 9: // LS + CSETM_wc(REG_WORK1, NATIVE_CC_CS); + CSETM_wc(REG_WORK2, NATIVE_CC_EQ); + ORR_www(REG_WORK1, REG_WORK1, REG_WORK2); + break; + + case 8: // HI + CSETM_wc(REG_WORK1, NATIVE_CC_CC); + CSETM_wc(REG_WORK2, NATIVE_CC_NE); + AND_www(REG_WORK1, REG_WORK1, REG_WORK2); + break; + + default: + CSETM_wc(REG_WORK1, cc); + break; + } + BFI_wwii(d, REG_WORK1, 0, 8); + + unlock2(d); +} +MENDFUNC(2,jnf_SCC,(W1 d, IM8 cc)) + +/* + * SUB + * Operand Syntax: , Dn + * Dn, + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Set if the result is zero. Cleared otherwise. + * V Set if an overflow is generated. Cleared otherwise. + * C Set if a carry is generated. Cleared otherwise. + * + */ +MIDFUNC(2,jnf_SUB_b_imm,(RW1 d, IM8 v)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffffff00) | (((live.state[d].val & 0xff) - (v & 0xff)) & 0x000000ff); + return; + } + + INIT_REG_b(d); + + if(targetIsReg) { + SUB_wwi(REG_WORK1, d, v & 0xff); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + SUB_wwi(d, d, v & 0xff); + } + + unlock2(d); +} +MENDFUNC(2,jnf_SUB_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jnf_SUB_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_SUB_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + if(targetIsReg) { + SUB_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 8); + } else { + SUB_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUB_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_SUB_w_imm,(RW2 d, IM16 v)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val & 0xffff0000) | (((live.state[d].val & 0xffff) - (v & 0xffff)) & 0x0000ffff); + return; + } + + INIT_REG_w(d); + + UNSIGNED16_IMM_2_REG(REG_WORK1, (uae_u16)v); + if(targetIsReg) { + SUB_www(REG_WORK1, d, REG_WORK1); + BFI_xxii(d, REG_WORK1, 0, 16); + } else{ + SUB_www(d, d, REG_WORK1); + } + + unlock2(d); +} +MENDFUNC(2,jnf_SUB_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jnf_SUB_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jnf_SUB_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + if(targetIsReg) { + SUB_www(REG_WORK1, d, s); + BFI_xxii(d, REG_WORK1, 0, 16); + } else{ + SUB_www(d, d, s); + } + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUB_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_SUB_l,(RW4 d, RR4 s)) +{ + if (isconst(d) && isconst(s)) { + live.state[d].val = live.state[d].val - live.state[s].val; + return; + } + + INIT_REGS_l(d, s); + + SUB_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUB_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_SUB_b_imm,(RW1 d, IM8 v)) +{ + INIT_REG_b(d); + + LSL_wwi(REG_WORK1, d, 24); + MOV_wish(REG_WORK2, (v & 0xff) << 8, 16); + SUBS_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFXIL_xxii(d, REG_WORK1, 24, 8); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(2,jff_SUB_b_imm,(RW1 d, IM8 v)) + +MIDFUNC(2,jff_SUB_b,(RW1 d, RR1 s)) +{ + if (isconst(s)) { + COMPCALL(jff_SUB_b_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_b(d, s); + + LSL_wwi(REG_WORK1, d, 24); + SUBS_wwwLSLi(REG_WORK1, REG_WORK1, s, 24); + BFXIL_xxii(d, REG_WORK1, 24, 8); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUB_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_SUB_w_imm,(RW2 d, IM16 v)) +{ + INIT_REG_w(d); + + MOV_xi(REG_WORK1, v); + LSL_wwi(REG_WORK2, d, 16); + SUBS_wwwLSLi(REG_WORK1, REG_WORK2, REG_WORK1, 16); + BFXIL_xxii(d, REG_WORK1, 16, 16); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + unlock2(d); +} +MENDFUNC(2,jff_SUB_w_imm,(RW2 d, IM16 v)) + +MIDFUNC(2,jff_SUB_w,(RW2 d, RR2 s)) +{ + if (isconst(s)) { + COMPCALL(jff_SUB_w_imm)(d, live.state[s].val); + return; + } + + INIT_REGS_w(d, s); + + LSL_wwi(REG_WORK1, d, 16); + SUBS_wwwLSLi(REG_WORK1, REG_WORK1, s, 16); + BFXIL_xxii(d, REG_WORK1, 16, 16); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUB_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_SUB_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + SUBS_www(d, d, s); + + flags_carry_inverted = true; + DUPLICACTE_CARRY + + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUB_l,(RW4 d, RR4 s)) + +/* + * SUBA + * + * Operand Syntax: , Dn + * + * Operand Size: 16,32 + * + * Flags: Not affected. + * + */ +MIDFUNC(2,jnf_SUBA_w,(RW4 d, RR2 s)) +{ + if (isconst(s)) { + // no need to put virt. register s into a real host register via readreg() + uae_s16 tmp = (uae_s16)live.state[s].val; + d = rmw(d); + SIGNED16_IMM_2_REG(REG_WORK1, tmp); + SUB_www(d, d, REG_WORK1); + unlock2(d); + return; + } + + INIT_REGS_w(d, s); + + SUB_wwwEX(d, d, s, EX_SXTH); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUBA_w,(RW4 d, RR2 s)) + +MIDFUNC(2,jnf_SUBA_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + + SUB_www(d, d, s); + + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUBA_l,(RW4 d, RR4 s)) + +/* + * SUBX + * Operand Syntax: Dy, Dx + * -(Ay), -(Ax) + * + * Operand Size: 8,16,32 + * + * X Set the same as the carry bit. + * N Set if the result is negative. Cleared otherwise. + * Z Cleared if the result is nonzero. Unchanged otherwise. + * V Set if an overflow is generated. Cleared otherwise. + * C Set if a carry is generated. Cleared otherwise. + * + * Attention: Z is cleared only if the result is nonzero. Unchanged otherwise + * + */ +MIDFUNC(2,jnf_SUBX_b,(RW1 d, RR1 s)) +{ + int x = readreg(FLAGX); + INIT_REGS_b(d, s); + + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + LSL_wwi(REG_WORK1, d, 24); + LSL_wwi(REG_WORK2, s, 24); + SBC_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFXIL_wwii(d, REG_WORK1, 24, 8); + + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUBX_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jnf_SUBX_w,(RW2 d, RR2 s)) +{ + int x = readreg(FLAGX); + INIT_REGS_w(d, s); + + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + LSL_wwi(REG_WORK1, d, 16); + LSL_wwi(REG_WORK2, s, 16); + SBC_www(REG_WORK1, REG_WORK1, REG_WORK2); + BFXIL_wwii(d, REG_WORK1, 16, 16); + + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jnf_SUBX_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jnf_SUBX_l,(RW4 d, RR4 s)) +{ + int x = readreg(FLAGX); + INIT_REGS_l(d, s); + + clobber_flags(); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SBC_www(d, d, s); + + EXIT_REGS(d, s); + unlock2(x); +} +MENDFUNC(2,jnf_SUBX_l,(RW4 d, RR4 s)) + +MIDFUNC(2,jff_SUBX_b,(RW1 d, RR1 s)) +{ + INIT_REGS_b(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + LSL_wwi(REG_WORK1, d, 24); + LSL_wwi(REG_WORK3, s, 24); + SBCS_www(REG_WORK1, REG_WORK1, REG_WORK3); + BFXIL_wwii(d, REG_WORK1, 24, 8); + + MRS_NZCV_x(REG_WORK1); + EOR_xxCflag(REG_WORK1, REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUBX_b,(RW1 d, RR1 s)) + +MIDFUNC(2,jff_SUBX_w,(RW2 d, RR2 s)) +{ + INIT_REGS_w(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + LSL_wwi(REG_WORK1, d, 16); + LSL_wwi(REG_WORK3, s, 16); + SBCS_www(REG_WORK1, REG_WORK1, REG_WORK3); + BFXIL_wwii(d, REG_WORK1, 16, 16); + + MRS_NZCV_x(REG_WORK1); + EOR_xxCflag(REG_WORK1, REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUBX_w,(RW2 d, RR2 s)) + +MIDFUNC(2,jff_SUBX_l,(RW4 d, RR4 s)) +{ + INIT_REGS_l(d, s); + int x = rmw(FLAGX); + + MOVN_xi(REG_WORK2, 0); + MOVN_xish(REG_WORK1, 0x4000, 16); // inverse Z flag + CSEL_xxxc(REG_WORK2, REG_WORK1, REG_WORK2, NATIVE_CC_NE); + + // Restore inverted X to carry (don't care about other flags) + NEGS_ww(REG_WORK1, x); + + SBCS_www(d, d, s); + + MRS_NZCV_x(REG_WORK1); + EOR_xxCflag(REG_WORK1, REG_WORK1); + AND_xxx(REG_WORK1, REG_WORK1, REG_WORK2); + MSR_NZCV_x(REG_WORK1); + flags_carry_inverted = false; + if (needed_flags & FLAG_X) + UBFX_xxii(x, REG_WORK1, 29, 1); // Duplicate carry + + unlock2(x); + EXIT_REGS(d, s); +} +MENDFUNC(2,jff_SUBX_l,(RW4 d, RR4 s)) + +/* + * SWAP + * Operand Syntax: Dn + * + * Operand Size: 16 + * + * X Not affected. + * N Set if the most significant bit of the 32-bit result is set. Cleared otherwise. + * Z Set if the 32-bit result is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(1,jnf_SWAP,(RW4 d)) +{ + if (isconst(d)) { + live.state[d].val = (live.state[d].val >> 16) | (live.state[d].val << 16); + return; + } + + d = rmw(d); + + ROR_wwi(d, d, 16); + + unlock2(d); +} +MENDFUNC(1,jnf_SWAP,(RW4 d)) + +MIDFUNC(1,jff_SWAP,(RW4 d)) +{ + d = rmw(d); + + ROR_wwi(d, d, 16); + TST_ww(d, d); + + flags_carry_inverted = false; + unlock2(d); +} +MENDFUNC(1,jff_SWAP,(RW4 d)) + +/* + * TST + * Operand Syntax: + * + * Operand Size: 8,16,32 + * + * X Not affected. + * N Set if the operand is negative. Cleared otherwise. + * Z Set if the operand is zero. Cleared otherwise. + * V Always cleared. + * C Always cleared. + * + */ +MIDFUNC(1,jff_TST_b,(RR1 s)) +{ + if (isconst(s)) { + SIGNED8_IMM_2_REG(REG_WORK1, (uae_u8)live.state[s].val); + } else { + s = readreg(s); + SIGNED8_REG_2_REG(REG_WORK1, s); + unlock2(s); + } + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; +} +MENDFUNC(1,jff_TST_b,(RR1 s)) + +MIDFUNC(1,jff_TST_w,(RR2 s)) +{ + if (isconst(s)) { + SIGNED16_IMM_2_REG(REG_WORK1, (uae_u16)live.state[s].val); + } else { + s = readreg(s); + SIGNED16_REG_2_REG(REG_WORK1, s); + unlock2(s); + } + TST_ww(REG_WORK1, REG_WORK1); + flags_carry_inverted = false; +} +MENDFUNC(1,jff_TST_w,(RR2 s)) + +MIDFUNC(1,jff_TST_l,(RR4 s)) +{ + s = readreg(s); + TST_ww(s, s); + unlock2(s); + flags_carry_inverted = false; +} +MENDFUNC(1,jff_TST_l,(RR4 s)) + +/* + * Memory access functions + * + * Two versions: full address range and 24 bit address range + * + */ +MIDFUNC(2,jnf_MEM_WRITE_OFF_b,(RR4 adr, RR4 b)) +{ + adr = readreg(adr); + b = readreg(b); + + STRB_wXx(b, adr, R_MEMSTART); + + unlock2(b); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE_OFF_b,(RR4 adr, RR4 b)) + +MIDFUNC(2,jnf_MEM_WRITE_OFF_w,(RR4 adr, RR4 w)) +{ + adr = readreg(adr); + w = readreg(w); + + REV16_ww(REG_WORK1, w); + STRH_wXx(REG_WORK1, adr, R_MEMSTART); + + unlock2(w); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE_OFF_w,(RR4 adr, RR4 w)) + +MIDFUNC(2,jnf_MEM_WRITE_OFF_l,(RR4 adr, RR4 l)) +{ + adr = readreg(adr); + l = readreg(l); + + REV32_xx(REG_WORK1, l); + STR_wXx(REG_WORK1, adr, R_MEMSTART); + + unlock2(l); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE_OFF_l,(RR4 adr, RR4 l)) + + +MIDFUNC(2,jnf_MEM_READ_OFF_b,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + LDRB_wXx(d, adr, R_MEMSTART); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ_OFF_b,(W4 d, RR4 adr)) + +MIDFUNC(2,jnf_MEM_READ_OFF_w,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + LDRH_wXx(REG_WORK1, adr, R_MEMSTART); + REV16_ww(d, REG_WORK1); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ_OFF_w,(W4 d, RR4 adr)) + +MIDFUNC(2,jnf_MEM_READ_OFF_l,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + LDR_wXx(REG_WORK1, adr, R_MEMSTART); + REV32_xx(d, REG_WORK1); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ_OFF_l,(W4 d, RR4 adr)) + + +MIDFUNC(2,jnf_MEM_WRITE24_OFF_b,(RR4 adr, RR4 b)) +{ + adr = readreg(adr); + b = readreg(b); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + STRB_wXx(b, REG_WORK1, R_MEMSTART); + + unlock2(b); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE24_OFF_b,(RR4 adr, RR4 b)) + +MIDFUNC(2,jnf_MEM_WRITE24_OFF_w,(RR4 adr, RR4 w)) +{ + adr = readreg(adr); + w = readreg(w); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + REV16_ww(REG_WORK3, w); + STRH_wXx(REG_WORK3, REG_WORK1, R_MEMSTART); + + unlock2(w); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE24_OFF_w,(RR4 adr, RR4 w)) + +MIDFUNC(2,jnf_MEM_WRITE24_OFF_l,(RR4 adr, RR4 l)) +{ + adr = readreg(adr); + l = readreg(l); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + REV32_xx(REG_WORK3, l); + STR_wXx(REG_WORK3, REG_WORK1, R_MEMSTART); + + unlock2(l); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_WRITE24_OFF_l,(RR4 adr, RR4 l)) + + +MIDFUNC(2,jnf_MEM_READ24_OFF_b,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + LDRB_wXx(d, REG_WORK1, R_MEMSTART); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ24_OFF_b,(W4 d, RR4 adr)) + +MIDFUNC(2,jnf_MEM_READ24_OFF_w,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + LDRH_wXx(REG_WORK1, REG_WORK1, R_MEMSTART); + REV16_ww(d, REG_WORK1); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ24_OFF_w,(W4 d, RR4 adr)) + +MIDFUNC(2,jnf_MEM_READ24_OFF_l,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + LDR_wXx(d, REG_WORK1, R_MEMSTART); + REV32_xx(d, d); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_READ24_OFF_l,(W4 d, RR4 adr)) + + +MIDFUNC(2,jnf_MEM_GETADR_OFF,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + ADD_www(d, adr, R_MEMSTART); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_GETADR_OFF,(W4 d, RR4 adr)) + +MIDFUNC(2,jnf_MEM_GETADR24_OFF,(W4 d, RR4 adr)) +{ + adr = readreg(adr); + d = writereg(d); + + UBFIZ_xxii(REG_WORK1, adr, 0, 24); + ADD_www(d, REG_WORK1, R_MEMSTART); + + unlock2(d); + unlock2(adr); +} +MENDFUNC(2,jnf_MEM_GETADR24_OFF,(W4 d, RR4 adr)) + + +MIDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IM8 offset)) +{ + clobber_flags(); + if (dest != adr) { + COMPCALL(forget_about)(dest); + } + + adr = readreg_specific(adr, REG_PAR1); + prepare_for_call_1(); + unlock2(adr); + prepare_for_call_2(); + + uintptr idx = (uintptr)(®s.mem_banks) - (uintptr)(®s); + LDR_xXi(REG_WORK2, R_REGSTRUCT, idx); + LSR_wwi(REG_WORK1, adr, 16); + LDR_xXxLSLi(REG_WORK3, REG_WORK2, REG_WORK1, 1); // 1 means shift by 3 + LDR_xXi(REG_WORK3, REG_WORK3, offset); + + compemu_raw_call_r(REG_WORK3); + + live.nat[REG_RESULT].holds[0] = dest; + live.nat[REG_RESULT].nholds = 1; + live.nat[REG_RESULT].touched = touchcnt++; + + live.state[dest].realreg = REG_RESULT; + live.state[dest].realind = 0; + live.state[dest].val = 0; + set_status(dest, DIRTY); +} +MENDFUNC(3,jnf_MEM_READMEMBANK,(W4 dest, RR4 adr, IM8 offset)) + + +MIDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IM8 offset)) +{ + clobber_flags(); + + adr = readreg_specific(adr, REG_PAR1); + source = readreg_specific(source, REG_PAR2); + prepare_for_call_1(); + unlock2(adr); + unlock2(source); + prepare_for_call_2(); + + uintptr idx = (uintptr)(®s.mem_banks) - (uintptr)(®s); + LDR_xXi(REG_WORK2, R_REGSTRUCT, idx); + LSR_wwi(REG_WORK1, adr, 16); + LDR_xXxLSLi(REG_WORK3, REG_WORK2, REG_WORK1, 1); // 1 means shift by 3 + LDR_xXi(REG_WORK3, REG_WORK3, offset); + + compemu_raw_call_r(REG_WORK3); +} +MENDFUNC(3,jnf_MEM_WRITEMEMBANK,(RR4 adr, RR4 source, IM8 offset)) + diff --git a/src/jit/compemu_support.cpp b/src/jit/compemu_support.cpp index 947da47d..03255252 100644 --- a/src/jit/compemu_support.cpp +++ b/src/jit/compemu_support.cpp @@ -66,7 +66,6 @@ #undef abort #define abort() do { \ fprintf(stderr, "Abort in file %s at line %d\n", __FILE__, __LINE__); \ - compiler_dumpstate(); \ SDL_Quit(); \ exit(EXIT_FAILURE); \ } while (0) @@ -99,11 +98,7 @@ static compop_func *nfcompfunctbl[65536]; uae_u8* comp_pc_p; // gb-- Extra data for Basilisk II/JIT -#if USE_INLINING #define follow_const_jumps (true) -#else -const int follow_const_jumps = 0; -#endif static uae_u32 cache_size = 0; // Size of total cache allocated for compiled blocks static uae_u32 current_cache_size = 0; // Cache grows upwards: how much has been consumed already @@ -112,12 +107,13 @@ static uae_u32 current_cache_size = 0; // Cache grows upwards: how much has bee #else #define avoid_fpu (true) #endif -static int optcount = 4; // How often a block has to be executed before it is translated +static const int optcount = 4; // How often a block has to be executed before it is translated op_properties prop[65536]; -uae_u32 jit_exception = 0; bool may_raise_exception = false; +static bool flags_carry_inverted = false; +static bool disasm_this = false; STATIC_INLINE bool is_const_jump(uae_u32 opcode) @@ -132,7 +128,6 @@ uae_u32 needed_flags; static uintptr next_pc_p; static uintptr taken_pc_p; static int branch_cc; -static int redo_current_block; uae_u8* current_compile_p = NULL; static uae_u8* max_compile_start; @@ -185,7 +180,7 @@ static bigstate live; static int writereg(int r); static void unlock2(int r); static void setlock(int r); -static int readreg_specific(int r, int spec); +static int readreg(int r); static void prepare_for_call_1(void); static void prepare_for_call_2(void); @@ -205,7 +200,7 @@ uae_u32 m68k_pc_offset; * case, we have to save them. * * We used to save them to the stack, but now store them back directly - * into the regflags.cznv of the traditional emulation. Thus some odd + * into the regflags.nzcv of the traditional emulation. Thus some odd * names. * * So flags can be in either of two places (used to be three; boy were @@ -483,28 +478,9 @@ void LazyBlockAllocator::release(T * const chunk) mChunks = chunk; } -template< class T > -class HardBlockAllocator -{ -public: - T * acquire() { - T * data = (T *)current_compile_p; - current_compile_p += sizeof(T); - return data; - } - void release(T * const chunk) { - // Deallocated on invalidation - } -}; - -#if USE_SEPARATE_BIA static LazyBlockAllocator BlockInfoAllocator; static LazyBlockAllocator ChecksumInfoAllocator; -#else -static HardBlockAllocator BlockInfoAllocator; -static HardBlockAllocator ChecksumInfoAllocator; -#endif STATIC_INLINE checksum_info *alloc_checksum_info(void) { @@ -531,18 +507,14 @@ STATIC_INLINE void free_checksum_info_chain(checksum_info *csi) STATIC_INLINE blockinfo *alloc_blockinfo(void) { blockinfo *bi = BlockInfoAllocator.acquire(); -#if USE_CHECKSUM_INFO bi->csi = NULL; -#endif return bi; } STATIC_INLINE void free_blockinfo(blockinfo *bi) { -#if USE_CHECKSUM_INFO free_checksum_info_chain(bi->csi); bi->csi = NULL; -#endif BlockInfoAllocator.release(bi); } @@ -592,12 +564,18 @@ static uae_u8* target; STATIC_INLINE void emit_long(uae_u32 x) { *((uae_u32*)target) = x; - target += 4; + target += 4; +} + +STATIC_INLINE void emit_longlong(uae_u64 x) +{ + *((uae_u64*)target) = x; + target += 8; } #define MAX_COMPILE_PTR max_compile_start -void set_target(uae_u8* t) +static void set_target(uae_u8* t) { target = t; } @@ -610,7 +588,7 @@ STATIC_INLINE uae_u8* get_target(void) /******************************************************************** * New version of data buffer: interleave data and code * ********************************************************************/ -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) #define DATA_BUFFER_SIZE 768 // Enlarge POPALLSPACE_SIZE if this value is greater than 768 #define DATA_BUFFER_MAXOFFSET (4096 - 32) // max range between emit of data and use of data @@ -621,7 +599,7 @@ static uae_u32 data_wasted = 0; static uae_u32 data_buffers_used = 0; #endif -STATIC_INLINE void compemu_raw_branch(IMM d); +STATIC_INLINE void compemu_raw_branch(IM32 d); STATIC_INLINE void data_check_end(uae_s32 n, uae_s32 codesize) { @@ -684,7 +662,9 @@ STATIC_INLINE void reset_data_buffer(void) ********************************************************************/ STATIC_INLINE void clobber_flags(void); -#if defined(CPU_arm) +#if defined(CPU_AARCH64) +#include "codegen_armA64.cpp.in" +#elif defined(CPU_arm) #include "codegen_arm.cpp.in" #endif #if defined(CPU_i386) || defined(CPU_x86_64) @@ -702,9 +682,10 @@ static void make_flags_live_internal(void) return; if (live.flags_on_stack == VALID) { int tmp; - tmp = readreg_specific(FLAGTMP, -1); + tmp = readreg(FLAGTMP); raw_reg_to_flags(tmp); unlock2(tmp); + flags_carry_inverted = false; live.flags_in_flags = VALID; return; @@ -715,10 +696,13 @@ static void make_flags_live_internal(void) static void flags_to_stack(void) { - if (live.flags_on_stack == VALID) + if (live.flags_on_stack == VALID) { + flags_carry_inverted = false; return; + } if (!live.flags_are_important) { live.flags_on_stack = VALID; + flags_carry_inverted = false; return; } { @@ -770,10 +754,8 @@ STATIC_INLINE int isinreg(int r) static void tomem(int r) { - int rr = live.state[r].realreg; - if (live.state[r].status == DIRTY) { - compemu_raw_mov_l_mr((uintptr)live.state[r].mem, rr); + compemu_raw_mov_l_mr((uintptr)live.state[r].mem, live.state[r].realreg); set_status(r, CLEAN); } } @@ -793,14 +775,12 @@ STATIC_INLINE void writeback_const(int r) set_status(r, INMEM); } -static void evict(int r) +static void evict(int r) { - int rr; - if (!isinreg(r)) return; tomem(r); - rr = live.state[r].realreg; + int rr = live.state[r].realreg; live.nat[rr].nholds--; if (live.nat[rr].nholds != live.state[r].realind) { /* Was not last */ @@ -832,7 +812,6 @@ STATIC_INLINE void isclean(int r) { if (!isinreg(r)) return; - live.state[r].validsize = 4; live.state[r].val = 0; set_status(r, CLEAN); } @@ -850,40 +829,33 @@ STATIC_INLINE void set_const(int r, uae_u32 val) set_status(r, ISCONST); } -static int alloc_reg_hinted(int r, int willclobber, int hint) +static int alloc_reg_hinted(int r, int willclobber, int hint) { - int bestreg; - uae_s32 when; + int bestreg = -1; + uae_s32 when = 2000000000; int i; - uae_s32 badness = 0; /* to shut up gcc */ - bestreg = -1; - when = 2000000000; for (i = N_REGS - 1; i >= 0; i--) { - badness = live.nat[i].touched; - if (live.nat[i].nholds == 0) - badness = 0; - if (i == hint) - badness -= 200000000; - if (!live.nat[i].locked && badness < when) { - bestreg = i; - when = badness; - if (live.nat[i].nholds == 0 && hint < 0) - break; - if (i == hint) - break; - } + if(!live.nat[i].locked) { + uae_s32 badness = live.nat[i].touched; + if (live.nat[i].nholds == 0) + badness = 0; + if (i == hint) + badness -= 200000000; + if (badness < when) { + bestreg = i; + when = badness; + if (live.nat[i].nholds == 0 && hint < 0) + break; + if (i == hint) + break; + } + } } if (live.nat[bestreg].nholds > 0) { free_nreg(bestreg); } - if (isinreg(r)) { - int rr = live.state[r].realreg; - /* This will happen if we read a partially dirty register at a - bigger size */ - evict(r); - } if (!willclobber) { if (live.state[r].status != UNDEF) { @@ -891,28 +863,24 @@ static int alloc_reg_hinted(int r, int willclobber, int hint) compemu_raw_mov_l_ri(bestreg, live.state[r].val); live.state[r].val = 0; set_status(r, DIRTY); - } - else { + } else { do_load_reg(bestreg, r); set_status(r, CLEAN); } - } - else { + } else { live.state[r].val = 0; set_status(r, CLEAN); } - live.state[r].validsize = 4; } else { /* this is the easiest way, but not optimal. */ - live.state[r].validsize = 4; live.state[r].val = 0; set_status(r, DIRTY); } live.state[r].realreg = bestreg; - live.state[r].realind = live.nat[bestreg].nholds; + live.state[r].realind = 0; live.nat[bestreg].touched = touchcnt++; - live.nat[bestreg].holds[live.nat[bestreg].nholds] = r; - live.nat[bestreg].nholds++; + live.nat[bestreg].holds[0] = r; + live.nat[bestreg].nholds = 1; return bestreg; } @@ -923,7 +891,7 @@ static void unlock2(int r) live.nat[r].locked--; } -static void setlock(int r) +static void setlock(int r) { live.nat[r].locked++; } @@ -931,18 +899,15 @@ static void setlock(int r) static void mov_nregs(int d, int s) { - int nd = live.nat[d].nholds; - int i; - if (s == d) return; - if (nd > 0) + if (live.nat[d].nholds > 0) free_nreg(d); compemu_raw_mov_l_rr(d, s); - for (i=0; i= 4) { - n = live.state[r].realreg; - - answer = n; - - if (answer < 0) - evict(r); - } - /* either the value was in memory to start with, or it was evicted and - is in memory now */ - if (answer < 0) { + if (isinreg(r)) { + answer = live.state[r].realreg; + } else { + /* the value is in memory to start with */ answer = alloc_reg_hinted(r, 0, spec); } @@ -1065,25 +997,15 @@ static int readreg_specific(int r, int spec) */ static int writereg(int r) { - int n; int answer = -1; - make_exclusive(r, 4); + make_exclusive(r, 0); if (isinreg(r)) { - n = live.state[r].realreg; - - live.state[r].validsize = 4; - answer = n; - - if (answer < 0) - evict(r); - } - /* either the value was in memory to start with, or it was evicted and - is in memory now */ - if (answer < 0) { + answer = live.state[r].realreg; + } else { + /* the value is in memory to start with */ answer = alloc_reg_hinted(r, 1, -1); } - live.state[r].validsize = 4; live.nat[answer].locked++; live.nat[answer].touched = touchcnt++; @@ -1094,28 +1016,20 @@ static int writereg(int r) static int rmw(int r) { - int n; int answer = -1; if (live.state[r].status == UNDEF) { jit_log("WARNING: Unexpected read of undefined register %d", r); } - make_exclusive(r, 0); + make_exclusive(r, 1); - if (isinreg(r) && live.state[r].validsize >= 4) { - n = live.state[r].realreg; - - answer = n; - if (answer < 0) - evict(r); - } - /* either the value was in memory to start with, or it was evicted and - is in memory now */ - if (answer < 0) { + if (isinreg(r)) { + answer = live.state[r].realreg; + } else { + /* the value is in memory to start with */ answer = alloc_reg_hinted(r, 0, -1); } - live.state[r].validsize = 4; set_status(r, DIRTY); live.nat[answer].locked++; @@ -1186,9 +1100,9 @@ static int f_alloc_reg(int r, int willclobber) if(r < 8) bestreg = r + 8; // map real Amiga reg to ARM VFP reg 8-15 (call save) else if(r == FP_RESULT) - bestreg = 6; // map FP_RESULT to ARM VFP reg 6 + bestreg = 6; // map FP_RESULT to ARM VFP reg 6 else // FS1 - bestreg = 7; // map FS1 to ARM VFP reg 7 + bestreg = 7; // map FS1 to ARM VFP reg 7 if (!willclobber) { if (live.fate[r].status == INMEM) { @@ -1216,11 +1130,10 @@ STATIC_INLINE int f_readreg(int r) if (f_isinreg(r)) { answer = live.fate[r].realreg; - } - /* either the value was in memory to start with, or it was evicted and - is in memory now */ - if (answer < 0) + } else { + /* the value is in memory to start with */ answer = f_alloc_reg(r,0); + } return answer; } @@ -1231,8 +1144,7 @@ STATIC_INLINE int f_writereg(int r) if (f_isinreg(r)) { answer = live.fate[r].realreg; - } - if (answer < 0) { + } else { answer = f_alloc_reg(r, 1); } live.fate[r].status = DIRTY; @@ -1245,9 +1157,9 @@ STATIC_INLINE int f_rmw(int r) if (f_isinreg(r)) { n = live.fate[r].realreg; - } - else + } else { n = f_alloc_reg(r, 0); + } live.fate[r].status = DIRTY; return n; } @@ -1264,7 +1176,10 @@ static void fflags_into_flags_internal(void) #endif -#if defined(CPU_arm) +#if defined(CPU_AARCH64) +#include "compemu_midfunc_armA64.cpp.in" +#include "compemu_midfunc_armA64_2.cpp.in" +#elif defined(CPU_arm) #include "compemu_midfunc_arm.cpp.in" #include "compemu_midfunc_arm2.cpp.in" #endif @@ -1292,17 +1207,6 @@ void sync_m68k_pc(void) } } -/******************************************************************** - * Scratch registers management * - ********************************************************************/ - -struct scratch_t { - uae_u32 regs[VREGS]; - fpu_register fregs[VFREGS]; -}; - -static scratch_t scratch; - /******************************************************************** * Support functions exposed to newcpu * ********************************************************************/ @@ -1359,7 +1263,7 @@ void compiler_exit(void) #endif } -void init_comp(void) +static void init_comp(void) { int i; uae_s8* au = always_used; @@ -1382,7 +1286,7 @@ void init_comp(void) set_status(i, INMEM); } else - live.state[i].mem = scratch.regs + i; + live.state[i].mem = ®s.scratchregs[i - 16]; } live.state[PC_P].mem = (uae_u32*)&(regs.pc_p); set_const(PC_P, (uintptr)comp_pc_p); @@ -1396,6 +1300,7 @@ void init_comp(void) live.state[FLAGTMP].mem = (uae_u32*)&(regs.ccrflags.cznv); #endif set_status(FLAGTMP, INMEM); + flags_carry_inverted = false; for (i = 0; i < VFREGS; i++) { if (i < 8) { /* First 8 registers map to 68k FPU registers */ @@ -1409,7 +1314,7 @@ void init_comp(void) live.fate[i].status = INMEM; } else - live.fate[i].mem = (uae_u32*)(&scratch.fregs[i]); + live.fate[i].mem = (uae_u32*)(®s.scratchfregs[i - 8]); } for (i = 0; i < N_REGS; i++) { @@ -1432,7 +1337,7 @@ void init_comp(void) live.flags_on_stack = VALID; live.flags_are_important = 1; - jit_exception = 0; + regs.jit_exception = 0; } /* Only do this if you really mean it! The next call should be to init!*/ @@ -1455,8 +1360,7 @@ void flush(int save_regs) switch(live.state[i].status) { case INMEM: if (live.state[i].val) { - compemu_raw_add_l_mi((uintptr)live.state[i].mem, live.state[i].val); - live.state[i].val = 0; + write_log("JIT: flush INMEM and val != 0!\n"); } break; case CLEAN: @@ -1481,11 +1385,13 @@ void flush(int save_regs) } } -void freescratch(void) +static void freescratch(void) { int i; for (i = 0; i < N_REGS; i++) -#if defined(CPU_arm) +#if defined(CPU_AARCH64) + if (live.nat[i].locked && i > 5 && i < 18) { +#elif defined(CPU_arm) if (live.nat[i].locked && i != 2 && i != 3 && i != 10 && i != 11 && i != 12) { #else if (live.nat[i].locked && i!=4 && i!= 12) { @@ -1507,8 +1413,8 @@ void freescratch(void) STATIC_INLINE int isinrom(uintptr addr) { - return (addr >= uae_p32(kickmem_bank.baseaddr) && - addr < uae_p32(kickmem_bank.baseaddr + 8 * 65536)); + return (addr >= (uintptr)kickmem_bank.baseaddr && + addr < (uintptr)(kickmem_bank.baseaddr + 8 * 65536)); } static void flush_all(void) @@ -1544,7 +1450,11 @@ static void prepare_for_call_2(void) int i; for (i = 0; i < N_REGS; i++) { +#if defined(CPU_AARCH64) + if (live.nat[i].nholds > 0) // in aarch64: first 18 regs not call saved +#else if (!call_saved[i] && live.nat[i].nholds > 0) +#endif free_nreg(i); } #ifdef USE_JIT_FPU @@ -1613,7 +1523,7 @@ STATIC_INLINE void writemem_special(int address, int source, int offset) void writebyte(int address, int source) { if (special_mem & S_WRITE) - writemem_special(address, source, 20); + writemem_special(address, source, SIZEOF_VOID_P * 5); else writemem_real(address, source, 1); } @@ -1621,7 +1531,7 @@ void writebyte(int address, int source) void writeword(int address, int source) { if (special_mem & S_WRITE) - writemem_special(address, source, 16); + writemem_special(address, source, SIZEOF_VOID_P * 4); else writemem_real(address, source, 2); } @@ -1629,7 +1539,7 @@ void writeword(int address, int source) void writelong(int address, int source) { if (special_mem & S_WRITE) - writemem_special(address, source, 12); + writemem_special(address, source, SIZEOF_VOID_P * 3); else writemem_real(address, source, 4); } @@ -1638,7 +1548,7 @@ void writelong(int address, int source) void writeword_clobber(int address, int source) { if (special_mem & S_WRITE) - writemem_special(address, source, 16); + writemem_special(address, source, SIZEOF_VOID_P * 4); else writemem_real(address, source, 2); forget_about(source); @@ -1647,7 +1557,7 @@ void writeword_clobber(int address, int source) void writelong_clobber(int address, int source) { if (special_mem & S_WRITE) - writemem_special(address, source, 12); + writemem_special(address, source, SIZEOF_VOID_P * 3); else writemem_real(address, source, 4); forget_about(source); @@ -1686,7 +1596,7 @@ STATIC_INLINE void readmem_special(int address, int dest, int offset) void readbyte(int address, int dest) { if (special_mem & S_READ) - readmem_special(address, dest, 8); + readmem_special(address, dest, SIZEOF_VOID_P * 2); else readmem_real(address, dest, 1); } @@ -1694,7 +1604,7 @@ void readbyte(int address, int dest) void readword(int address, int dest) { if (special_mem & S_READ) - readmem_special(address, dest, 4); + readmem_special(address, dest, SIZEOF_VOID_P * 1); else readmem_real(address, dest, 2); } @@ -1702,7 +1612,7 @@ void readword(int address, int dest) void readlong(int address, int dest) { if (special_mem & S_READ) - readmem_special(address, dest, 0); + readmem_special(address, dest, SIZEOF_VOID_P * 0); else readmem_real(address, dest, 4); } @@ -1710,7 +1620,7 @@ void readlong(int address, int dest) /* This one might appear a bit odd... */ STATIC_INLINE void get_n_addr_old(int address, int dest) { - readmem_special(address, dest, 24); + readmem_special(address, dest, SIZEOF_VOID_P * 6); } STATIC_INLINE void get_n_addr_real(int address, int dest) @@ -1818,15 +1728,15 @@ void alloc_cache(void) compiled_code = popallspace + POPALLSPACE_SIZE; if (compiled_code) { - write_log("Actual translation cache size : %d KB at %p-%p", cache_size, compiled_code, compiled_code + cache_size*1024); -#if defined(CPU_arm) && !defined(ARMV6T2) + write_log("Actual translation cache size : %d KB at %p-%p\n", cache_size, compiled_code, compiled_code + cache_size*1024); +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) max_compile_start = compiled_code + cache_size*1024 - BYTES_PER_INST - DATA_BUFFER_SIZE; #else max_compile_start = compiled_code + cache_size*1024 - BYTES_PER_INST; #endif current_compile_p = compiled_code; current_cache_size = 0; -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) reset_data_buffer(); #endif } @@ -1837,15 +1747,10 @@ static void calc_checksum(blockinfo* bi, uae_u32* c1, uae_u32* c2) uae_u32 k1 = 0; uae_u32 k2 = 0; -#if USE_CHECKSUM_INFO checksum_info *csi = bi->csi; while (csi) { uae_s32 len = csi->length; uintptr tmp = (uintptr)csi->start_p; -#else - uae_s32 len = bi->len; - uintptr tmp = (uintptr)bi->min_pcp; -#endif uae_u32* pos; len += (tmp & 3); @@ -1861,10 +1766,8 @@ static void calc_checksum(blockinfo* bi, uae_u32* c1, uae_u32* c2) } } -#if USE_CHECKSUM_INFO csi = csi->next; } -#endif *c1 = k1; *c2 = k2; @@ -2010,11 +1913,12 @@ STATIC_INLINE void create_popalls(void) return; } } + write_log("JIT popallspace: %p-%p\n", popallspace, popallspace + POPALLSPACE_SIZE); current_compile_p = popallspace; set_target(current_compile_p); -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) reset_data_buffer(); data_long(0, 0); // Make sure we emit the branch over the first buffer outside pushall_call_handler #endif @@ -2030,21 +1934,26 @@ STATIC_INLINE void create_popalls(void) current_compile_p = get_target(); pushall_call_handler = get_target(); raw_push_regs_to_preserve(); +#ifdef JIT_DEBUG + write_log("Address of regs: 0x%016x, regs.pc_p: 0x%016x\n", ®s, ®s.pc_p); + write_log("Address of natmem_offset: 0x%016x, natmem_offset = 0x%016x\n", ®s.natmem_offset, regs.natmem_offset); + write_log("Address of cache_tags: 0x%016x\n", cache_tags); +#endif compemu_raw_init_r_regstruct((uintptr)®s); - r = REG_PC_TMP; - compemu_raw_tag_pc(r, uae_p32(®s.pc_p)); - compemu_raw_jmp_m_indexed(uae_p32(cache_tags), r, SIZEOF_VOID_P); + compemu_raw_jmp_pc_tag((uintptr)cache_tags); /* now the exit points */ popall_execute_normal = get_target(); raw_pop_preserved_regs(); - compemu_raw_jmp(uae_p32(execute_normal)); + compemu_raw_jmp((uintptr)execute_normal); popall_check_checksum = get_target(); raw_pop_preserved_regs(); - compemu_raw_jmp(uae_p32(check_checksum)); + compemu_raw_jmp((uintptr)check_checksum); -#if defined(CPU_arm) && !defined(ARMV6T2) + flush_cpu_icache((void *)popallspace, (void *)target); + +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) reset_data_buffer(); #endif } @@ -2065,14 +1974,12 @@ static void prepare_block(blockinfo* bi) set_target(current_compile_p); bi->direct_pen = (cpuop_func *)get_target(); - compemu_raw_mov_l_rm(0, (uintptr)&(bi->pc_p)); - compemu_raw_mov_l_mr((uintptr)®s.pc_p, 0); + compemu_raw_set_pc_m((uintptr)&(bi->pc_p)); raw_pop_preserved_regs(); compemu_raw_jmp((uintptr)execute_normal); bi->direct_pcc = (cpuop_func *)get_target(); - compemu_raw_mov_l_rm(0, (uintptr)&(bi->pc_p)); - compemu_raw_mov_l_mr((uintptr)®s.pc_p, 0); + compemu_raw_set_pc_m((uintptr)&(bi->pc_p)); raw_pop_preserved_regs(); compemu_raw_jmp((uintptr)check_checksum); flush_cpu_icache((void *)current_compile_p, (void *)target); @@ -2106,6 +2013,11 @@ void build_comp(void) const struct comptbl* nftbl = op_smalltbl_0_comp_nf; int count; +#ifdef PROFILE_UNTRANSLATED_INSNS + regs.raw_cputbl_count = raw_cputbl_count; +#endif + regs.mem_banks = (uintptr)mem_banks; + for (opcode = 0; opcode < 65536; opcode++) { reset_compop(opcode); prop[opcode].use_flags = 0x1f; @@ -2211,7 +2123,7 @@ void flush_icache_hard(int n) if (!compiled_code) return; -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) reset_data_buffer(); #endif @@ -2283,16 +2195,10 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) int r; int was_comp = 0; uae_u8 liveflags[MAXRUN + 1]; -#if USE_CHECKSUM_INFO bool trace_in_rom = isinrom((uintptr)pc_hist[0].location) != 0; uintptr max_pcp = (uintptr)pc_hist[blocklen - 1].location; uintptr min_pcp = max_pcp; -#else - uintptr max_pcp = (uintptr)pc_hist[0].location; - uintptr min_pcp = max_pcp; -#endif uae_u32 cl = cacheline(pc_hist[0].location); - void* specflags = (void*)®s.spcflags; blockinfo* bi = NULL; blockinfo* bi2; @@ -2313,10 +2219,8 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) remove_deps(bi); /* We are about to create new code */ bi->optlevel = optlev; bi->pc_p = (uae_u8*)pc_hist[0].location; -#if USE_CHECKSUM_INFO free_checksum_info_chain(bi->csi); bi->csi = NULL; -#endif liveflags[blocklen] = 0x1f; /* All flags needed afterwards */ i = blocklen; @@ -2324,7 +2228,6 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) uae_u16* currpcp = pc_hist[i].location; uae_u32 op = DO_GET_OPCODE(currpcp); -#if USE_CHECKSUM_INFO trace_in_rom = trace_in_rom && isinrom((uintptr)currpcp); if (follow_const_jumps && is_const_jump(op)) { checksum_info *csi = alloc_checksum_info(); @@ -2335,25 +2238,17 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) max_pcp = (uintptr)currpcp; } min_pcp = (uintptr)currpcp; -#else - if ((uintptr)currpcp < min_pcp) - min_pcp = (uintptr)currpcp; - if ((uintptr)currpcp > max_pcp) - max_pcp = (uintptr)currpcp; -#endif liveflags[i] = ((liveflags[i + 1] & (~prop[op].set_flags)) | prop[op].use_flags); if (prop[op].is_addx && (liveflags[i + 1] & FLAG_Z) == 0) liveflags[i] &= ~FLAG_Z; } -#if USE_CHECKSUM_INFO checksum_info *csi = alloc_checksum_info(); csi->start_p = (uae_u8 *)min_pcp; csi->length = max_pcp - min_pcp + LONGEST_68K_INST; csi->next = bi->csi; bi->csi = csi; -#endif bi->needed_flags = liveflags[0]; @@ -2366,15 +2261,15 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) current_block_start_target = (uintptr)get_target(); if (bi->count >= 0) { /* Need to generate countdown code */ - compemu_raw_mov_l_mi((uintptr)®s.pc_p, (uintptr)pc_hist[0].location); - compemu_raw_sub_l_mi((uintptr)&(bi->count), 1); + compemu_raw_set_pc_i((uintptr)pc_hist[0].location); + compemu_raw_dec_m((uintptr)&(bi->count)); compemu_raw_maybe_recompile((uintptr)recompile_block); } if (optlev == 0) { /* No need to actually translate */ /* Execute normally without keeping stats */ - compemu_raw_mov_l_mi((uintptr)®s.pc_p, (uintptr)pc_hist[0].location); + compemu_raw_set_pc_i((uintptr)pc_hist[0].location); raw_pop_preserved_regs(); - compemu_raw_jmp(uae_p32(exec_nostats)); + compemu_raw_jmp((uintptr)exec_nostats); } else { next_pc_p = 0; @@ -2392,6 +2287,9 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) uae_u32 opcode = DO_GET_OPCODE(pc_hist[i].location); needed_flags = (liveflags[i + 1] & prop[opcode].set_flags); special_mem = pc_hist[i].specmem; +#ifdef JIT_DEBUG + write_log(" location=0x%016llx, opcode=0x%04x, target=0x%016llx, need_flags=%d\n", pc_hist[i].location, opcode, get_target(), needed_flags); +#endif if (!needed_flags) { cputbl = cpufunctbl; comptbl = nfcompfunctbl; @@ -2416,12 +2314,6 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) /* We can forget about flags */ dont_care_flags(); } -#if INDIVIDUAL_INST - flush(1); - nop(); - flush(1); - was_comp = 0; -#endif } if (failure) { @@ -2430,31 +2322,22 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) was_comp = 0; } compemu_raw_mov_l_ri(REG_PAR1, (uae_u32)opcode); - compemu_raw_mov_l_ri(REG_PAR2, (uae_u32)®s); - compemu_raw_mov_l_mi((uintptr)®s.pc_p, (uintptr)pc_hist[i].location); + compemu_raw_mov_l_rr(REG_PAR2, R_REGSTRUCT); + compemu_raw_set_pc_i((uintptr)pc_hist[i].location); compemu_raw_call((uintptr)cputbl[opcode]); #ifdef PROFILE_UNTRANSLATED_INSNS // raw_cputbl_count[] is indexed with plain opcode (in m68k order) - compemu_raw_add_l_mi((uintptr)&raw_cputbl_count[opcode], 1); + compemu_raw_inc_opcount(opcode); #endif if (i < blocklen - 1) { - uae_s8* branchadd; - - compemu_raw_mov_l_rm(0, (uintptr)specflags); - compemu_raw_test_l_rr(0, 0); -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(8, 64); #endif - compemu_raw_jz_b_oponly(); - branchadd = (uae_s8 *)get_target(); - compemu_raw_sub_l_mi(uae_p32(&countdown), scaled_cycles(totcycles)); - raw_pop_preserved_regs(); - compemu_raw_jmp((uintptr)do_nothing); - *(branchadd - 4) = (((uintptr)get_target() - (uintptr)branchadd) - 4) >> 2; + compemu_raw_maybe_do_nothing(scaled_cycles(totcycles), (uintptr)do_nothing); } } else if(may_raise_exception) { -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(8, 64); #endif compemu_raw_handle_except(scaled_cycles(totcycles)); @@ -2471,6 +2354,9 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) uae_u32* tba; bigstate tmp; blockinfo* tbi; +#ifdef JIT_DEBUG + write_log(" branch detected: t1=0x%016llx, t2=0x%016llx, cc=%d\n", t1, t2, cc); +#endif if (taken_pc_p < next_pc_p) { /* backward branch. Optimize for the "taken" case --- @@ -2485,16 +2371,16 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) } tmp = live; /* ouch! This is big... */ -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(8, 128); #endif compemu_raw_jcc_l_oponly(cc); // Last emitted opcode is branch to target branchadd = (uae_u32*)get_target() - 1; - + /* predicted outcome */ tbi = get_blockinfo_addr_new((void*)t1); match_states(tbi); - + tba = compemu_raw_endblock_pc_isconst(scaled_cycles(totcycles), t1); write_jmp_target(tba, get_handler(t1)); create_jmpdep(bi, 0, tba, t1); @@ -2518,7 +2404,7 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) /* Let's find out where next_handler is... */ if (was_comp && isinreg(PC_P)) { -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(4, 64); #endif r = live.state[PC_P].realreg; @@ -2532,7 +2418,7 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) tbi = get_blockinfo_addr_new((void*)v); match_states(tbi); -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(4, 64); #endif tba = compemu_raw_endblock_pc_isconst(scaled_cycles(totcycles), v); @@ -2542,7 +2428,7 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) else { r = REG_PC_TMP; compemu_raw_mov_l_rm(r, (uintptr)®s.pc_p); -#if defined(CPU_arm) && !defined(ARMV6T2) +#if defined(CPU_arm) && !defined(ARMV6T2) && !defined(CPU_AARCH64) data_check_end(4, 64); #endif compemu_raw_endblock_pc_inreg(r, scaled_cycles(totcycles)); @@ -2550,7 +2436,6 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) } } -#if USE_CHECKSUM_INFO remove_from_list(bi); if (trace_in_rom) { // No need to checksum that block trace on cache invalidation @@ -2562,32 +2447,13 @@ void compile_block(cpu_history* pc_hist, int blocklen, int totcycles) calc_checksum(bi, &(bi->c1), &(bi->c2)); add_to_active(bi); } -#else - if (next_pc_p >= max_pcp && next_pc_p < max_pcp + LONGEST_68K_INST) - max_pcp = next_pc_p; - else - max_pcp += LONGEST_68K_INST; - - bi->len = max_pcp - min_pcp; - bi->min_pcp = min_pcp; - - remove_from_list(bi); - if (isinrom(min_pcp) && isinrom(max_pcp)) { - add_to_dormant(bi); /* No need to checksum it on cache flush. - Please don't start changing ROMs in flight! */ - } - else { - calc_checksum(bi, &(bi->c1), &(bi->c2)); - add_to_active(bi); - } -#endif current_cache_size += get_target() - (uae_u8 *)current_compile_p; /* This is the non-direct handler */ bi->handler = bi->handler_to_use = (cpuop_func *)get_target(); - compemu_raw_cmp_l_mi((uintptr)®s.pc_p, (uintptr)pc_hist[0].location); + compemu_raw_cmp_pc((uintptr)pc_hist[0].location); compemu_raw_maybe_cachemiss((uintptr)cache_miss); comp_pc_p = (uae_u8*)pc_hist[0].location; diff --git a/src/jit/compstbl.cpp b/src/jit/compstbl.cpp index 52d80309..8858f5cf 100644 --- a/src/jit/compstbl.cpp +++ b/src/jit/compstbl.cpp @@ -1188,12 +1188,12 @@ extern const struct comptbl op_smalltbl_0_comp_ff[] = { { op_6700_0_comp_ff, 0x00000003, 26368 }, /* Bcc */ { op_6701_0_comp_ff, 0x00000001, 26369 }, /* Bcc */ { op_67ff_0_comp_ff, 0x00000003, 26623 }, /* Bcc */ -{ NULL, 0x00000003, 26624 }, /* Bcc */ -{ NULL, 0x00000001, 26625 }, /* Bcc */ -{ NULL, 0x00000003, 26879 }, /* Bcc */ -{ NULL, 0x00000003, 26880 }, /* Bcc */ -{ NULL, 0x00000001, 26881 }, /* Bcc */ -{ NULL, 0x00000003, 27135 }, /* Bcc */ +{ op_6800_0_comp_ff, 0x00000003, 26624 }, /* Bcc */ +{ op_6801_0_comp_ff, 0x00000001, 26625 }, /* Bcc */ +{ op_68ff_0_comp_ff, 0x00000003, 26879 }, /* Bcc */ +{ op_6900_0_comp_ff, 0x00000003, 26880 }, /* Bcc */ +{ op_6901_0_comp_ff, 0x00000001, 26881 }, /* Bcc */ +{ op_69ff_0_comp_ff, 0x00000003, 27135 }, /* Bcc */ { op_6a00_0_comp_ff, 0x00000003, 27136 }, /* Bcc */ { op_6a01_0_comp_ff, 0x00000001, 27137 }, /* Bcc */ { op_6aff_0_comp_ff, 0x00000003, 27391 }, /* Bcc */ @@ -3060,12 +3060,12 @@ extern const struct comptbl op_smalltbl_0_comp_nf[] = { { op_6700_0_comp_nf, 0x00000003, 26368 }, /* Bcc */ { op_6701_0_comp_nf, 0x00000001, 26369 }, /* Bcc */ { op_67ff_0_comp_nf, 0x00000003, 26623 }, /* Bcc */ -{ NULL, 0x00000003, 26624 }, /* Bcc */ -{ NULL, 0x00000001, 26625 }, /* Bcc */ -{ NULL, 0x00000003, 26879 }, /* Bcc */ -{ NULL, 0x00000003, 26880 }, /* Bcc */ -{ NULL, 0x00000001, 26881 }, /* Bcc */ -{ NULL, 0x00000003, 27135 }, /* Bcc */ +{ op_6800_0_comp_nf, 0x00000003, 26624 }, /* Bcc */ +{ op_6801_0_comp_nf, 0x00000001, 26625 }, /* Bcc */ +{ op_68ff_0_comp_nf, 0x00000003, 26879 }, /* Bcc */ +{ op_6900_0_comp_nf, 0x00000003, 26880 }, /* Bcc */ +{ op_6901_0_comp_nf, 0x00000001, 26881 }, /* Bcc */ +{ op_69ff_0_comp_nf, 0x00000003, 27135 }, /* Bcc */ { op_6a00_0_comp_nf, 0x00000003, 27136 }, /* Bcc */ { op_6a01_0_comp_nf, 0x00000001, 27137 }, /* Bcc */ { op_6aff_0_comp_nf, 0x00000003, 27391 }, /* Bcc */ diff --git a/src/jit/comptbl.h b/src/jit/comptbl.h index 05b5beb9..d6acbd95 100644 --- a/src/jit/comptbl.h +++ b/src/jit/comptbl.h @@ -965,6 +965,12 @@ extern compop_func op_66ff_0_comp_ff; extern compop_func op_6700_0_comp_ff; extern compop_func op_6701_0_comp_ff; extern compop_func op_67ff_0_comp_ff; +extern compop_func op_6800_0_comp_ff; +extern compop_func op_6801_0_comp_ff; +extern compop_func op_68ff_0_comp_ff; +extern compop_func op_6900_0_comp_ff; +extern compop_func op_6901_0_comp_ff; +extern compop_func op_69ff_0_comp_ff; extern compop_func op_6a00_0_comp_ff; extern compop_func op_6a01_0_comp_ff; extern compop_func op_6aff_0_comp_ff; @@ -2479,6 +2485,12 @@ extern compop_func op_66ff_0_comp_nf; extern compop_func op_6700_0_comp_nf; extern compop_func op_6701_0_comp_nf; extern compop_func op_67ff_0_comp_nf; +extern compop_func op_6800_0_comp_nf; +extern compop_func op_6801_0_comp_nf; +extern compop_func op_68ff_0_comp_nf; +extern compop_func op_6900_0_comp_nf; +extern compop_func op_6901_0_comp_nf; +extern compop_func op_69ff_0_comp_nf; extern compop_func op_6a00_0_comp_nf; extern compop_func op_6a01_0_comp_nf; extern compop_func op_6aff_0_comp_nf; diff --git a/src/machdep/m68k.h b/src/machdep/m68k.h index 7d801f2e..df64bb9b 100644 --- a/src/machdep/m68k.h +++ b/src/machdep/m68k.h @@ -124,7 +124,7 @@ STATIC_INLINE int cctrue (int cc) #endif /* REGS_DEFINED */ -#elif defined(CPU_arm) && defined(ARMV6_ASSEMBLY) +#elif defined(CPU_arm) #ifndef REGS_DEFINED diff --git a/src/machdep/maccess.h b/src/machdep/maccess.h index b0b84a2e..26de3c2f 100644 --- a/src/machdep/maccess.h +++ b/src/machdep/maccess.h @@ -1,4 +1,4 @@ - /* +/* * UAE - The Un*x Amiga Emulator * * Memory access functions @@ -9,44 +9,125 @@ #ifndef MACCESS_UAE_H #define MACCESS_UAE_H -static uae_u32 do_get_mem_long(uae_u32 *a) +#if defined(ARMV6_ASSEMBLY) +STATIC_INLINE uae_u32 do_get_mem_long(uae_u32* a) { - uae_u8 *b = (uae_u8 *)a; - - return (*b << 24) | (*(b + 1) << 16) | (*(b + 2) << 8) | (*(b + 3)); + uae_u32 v; + __asm__( + "ldr %[v], [%[a]] \n\t" + "rev %[v], %[v] \n\t" + : [v] "=r" (v) : [a] "r" (a)); + return v; } +#elif defined(CPU_AARCH64) +STATIC_INLINE uae_u32 do_get_mem_long(uae_u32 *a) +{ + uae_u32 v; + __asm__ ( + "ldr %w[v], [%x[a]] \n\t" + "rev %w[v], %w[v] \n\t" + : [v] "=r" (v) : [a] "r" (a) ); + return v; +} +#else +STATIC_INLINE uae_u32 do_get_mem_long(uae_u32 *_GCCRES_ a) +{ + uae_u8 *b = (uae_u8 *)a; + + return (*b << 24) | (*(b+1) << 16) | (*(b+2) << 8) | (*(b+3)); +} +#endif -static uae_u16 do_get_mem_word(uae_u16 *a) +#if defined(ARMV6_ASSEMBLY) + +STATIC_INLINE uae_u16 do_get_mem_word(uae_u16*_GCCRES_ a) +{ + uae_u16 v; + __asm__( + "ldrh %[v], [%[a]] \n\t" + "rev16 %[v], %[v] \n\t" + : [v] "=r" (v) : [a] "r" (a)); + return v; +} +#elif defined(CPU_AARCH64) +STATIC_INLINE uae_u16 do_get_mem_word(uae_u16 *_GCCRES_ a) +{ + uae_u16 v; + __asm__ ( + "ldrh %w[v], [%x[a]] \n\t" + "rev16 %w[v], %w[v] \n\t" + : [v] "=r" (v) : [a] "r" (a) ); + return v; +} +#else +STATIC_INLINE uae_u16 do_get_mem_word(uae_u16 *_GCCRES_ a) { uae_u8 *b = (uae_u8 *)a; return (*b << 8) | (*(b+1)); } +#endif -static uae_u8 do_get_mem_byte(uae_u8 *a) +STATIC_INLINE uae_u8 do_get_mem_byte(uae_u8 *_GCCRES_ a) { return *a; } -static void do_put_mem_long(uae_u32 *a, uae_u32 v) +#ifdef ARMV6_ASSEMBLY +STATIC_INLINE void do_put_mem_long(uae_u32*_GCCRES_ a, uae_u32 v) { - uae_u8 *b = (uae_u8 *)a; - - *b = v >> 24; - *(b + 1) = v >> 16; - *(b + 2) = v >> 8; - *(b + 3) = v; + __asm__( + "rev r2, %[v] \n\t" + "str r2, [%[a]] \n\t" + : : [v] "r" (v), [a] "r" (a) : "r2", "memory"); } +#elif defined(CPU_AARCH64) +STATIC_INLINE void do_put_mem_long(uae_u32 *_GCCRES_ a, uae_u32 v) +{ + __asm__ ( + "rev w2, %w[v] \n\t" + "str w2, [%x[a]] \n\t" + : : [v] "r" (v), [a] "r" (a) : "w2", "memory" ); +} +#else +STATIC_INLINE void do_put_mem_long(uae_u32 *_GCCRES_ a, uae_u32 v) +{ + uae_u8 *b = (uae_u8 *)a; + + *b = v >> 24; + *(b+1) = v >> 16; + *(b+2) = v >> 8; + *(b+3) = v; +} +#endif -static void do_put_mem_word(uae_u16 *a, uae_u16 v) +#ifdef ARMV6_ASSEMBLY +STATIC_INLINE void do_put_mem_word(uae_u16*_GCCRES_ a, uae_u16 v) +{ + __asm__( + "rev16 r2, %[v] \n\t" + "strh r2, [%[a]] \n\t" + : : [v] "r" (v), [a] "r" (a) : "r2", "memory"); +} +#elif defined(CPU_AARCH64) +STATIC_INLINE void do_put_mem_word(uae_u16 *_GCCRES_ a, uae_u16 v) +{ + __asm__ ( + "rev16 w2, %w[v] \n\t" + "strh w2, [%x[a]] \n\t" + : : [v] "r" (v), [a] "r" (a) : "w2", "memory" ); +} +#else +STATIC_INLINE void do_put_mem_word(uae_u16 *_GCCRES_ a, uae_u16 v) { uae_u8 *b = (uae_u8 *)a; *b = v >> 8; *(b+1) = v; } +#endif -static void do_put_mem_byte(uae_u8 *a, uae_u8 v) +STATIC_INLINE void do_put_mem_byte(uae_u8 *_GCCRES_ a, uae_u8 v) { *a = v; } diff --git a/src/machdep/support.cpp b/src/machdep/support.cpp index 59fc8010..d50e1175 100644 --- a/src/machdep/support.cpp +++ b/src/machdep/support.cpp @@ -3,22 +3,26 @@ #include "memory.h" #include "newcpu.h" #include "custom.h" +#include "xwin.h" extern int screen_is_picasso; int64_t g_uae_epoch = 0; -int machdep_init(void) + +int machdep_init (void) { - picasso_requested_on = 0; - picasso_on = 0; - screen_is_picasso = 0; + struct amigadisplay *ad = &adisplays; - // Initialize timebase - g_uae_epoch = read_processor_time(); - syncbase = 1000000; // Microseconds + ad->picasso_requested_on = 0; + ad->picasso_on = 0; + screen_is_picasso = 0; - return 1; + // Initialize timebase + g_uae_epoch = read_processor_time(); + syncbase = 1000000; // Microseconds + + return 1; } diff --git a/src/main.cpp b/src/main.cpp index b0bde388..ea0b7a7c 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,19 +1,19 @@ /* - * UAE - The Un*x Amiga Emulator - * - * Main program - * - * Copyright 1995 Ed Hanway - * Copyright 1995, 1996, 1997 Bernd Schmidt - */ +* UAE - The Un*x Amiga Emulator +* +* Main program +* +* Copyright 1995 Ed Hanway +* Copyright 1995, 1996, 1997 Bernd Schmidt +*/ #include #include #include - -#include #include +#include "sysconfig.h" #include "sysdeps.h" +#include #include "options.h" #include "threaddep/thread.h" @@ -33,9 +33,12 @@ #include "picasso96.h" #include "native2amiga.h" #include "savestate.h" +#include "filesys.h" #include "blkdev.h" #include "gfxboard.h" #include "devices.h" +#include "jit/compemu.h" +#include #ifdef USE_SDL2 SDL_Window* sdlWindow; @@ -59,7 +62,7 @@ bool kickstart_rom = true; struct gui_info gui_data; -TCHAR optionsfile[256]; +static TCHAR optionsfile[MAX_DPATH]; void my_trim(TCHAR *s) { @@ -124,7 +127,7 @@ static void fixup_prefs_dim2(struct wh *wh) void fixup_prefs_dimensions(struct uae_prefs *prefs) { - fixup_prefs_dim2(&prefs->gfx_size); + fixup_prefs_dim2(&prefs->gfx_monitor.gfx_size); } void fixup_cpu(struct uae_prefs *p) @@ -263,11 +266,11 @@ void fixup_prefs (struct uae_prefs *p, bool userconfig) p->chipmem_size = 0x200000; //err = 1; } - if (p->mbresmem_low_size > 0x01000000 || (p->mbresmem_low_size & 0xfffff)) { + if (p->mbresmem_low_size > 0x04000000 || (p->mbresmem_low_size & 0xfffff)) { p->mbresmem_low_size = 0; error_log(_T("Unsupported Mainboard RAM size")); } - if (p->mbresmem_high_size > 0x02000000 || (p->mbresmem_high_size & 0xfffff)) { + if (p->mbresmem_high_size > 0x08000000 || (p->mbresmem_high_size & 0xfffff)) { p->mbresmem_high_size = 0; error_log(_T("Unsupported CPU Board RAM size.")); } @@ -384,6 +387,7 @@ void fixup_prefs (struct uae_prefs *p, bool userconfig) blkdev_fix_prefs(p); inputdevice_fix_prefs(p, userconfig); target_fixup_options(p); + cfgfile_createconfigstore(p); } int quit_program = 0; @@ -464,7 +468,7 @@ static TCHAR *parsetextpath(const TCHAR *s) return s3; } -void print_usage() +void usage() { printf("\nUsage:\n"); printf(" -h Show this help.\n"); @@ -604,7 +608,7 @@ static void parse_cmdline(int argc, TCHAR **argv) } else if (_tcscmp(argv[i], _T("-h")) == 0 || _tcsncmp(argv[i], _T("--help"), 6) == 0) { - print_usage(); + usage(); } else if (argv[i][0] == '-' && argv[i][1] != '\0') { const TCHAR *arg = argv[i] + 2; @@ -613,7 +617,7 @@ static void parse_cmdline(int argc, TCHAR **argv) arg = i + 1 < argc ? argv[i + 1] : nullptr; const auto ret = parse_cmdline_option(&currprefs, argv[i][1], arg); if (ret == -1) - print_usage(); + usage(); if (ret && extra_arg) i++; } @@ -640,7 +644,7 @@ static void parse_cmdline(int argc, TCHAR **argv) else { printf("Unknown option %s\n", argv[i]); - print_usage(); + usage(); } } } @@ -671,7 +675,7 @@ static void parse_cmdline_and_init_file(int argc, TCHAR **argv) * of start_program() and leave_program() if you need to do anything special. * Add #ifdefs around these as appropriate. */ -void do_start_program(void) +static void do_start_program (void) { if (quit_program == -UAE_QUIT) return; @@ -682,7 +686,7 @@ void do_start_program(void) m68k_go(1); } -void start_program (void) +static void start_program (void) { char kbd_flags; // set capslock state based upon current "real" state @@ -695,7 +699,7 @@ void start_program (void) do_start_program (); } -void leave_program (void) +static void leave_program (void) { do_leave_program (); } @@ -752,7 +756,7 @@ static int real_main2 (int argc, TCHAR **argv) if (restart_config[0]) parse_cmdline_and_init_file(argc, argv); else - currprefs = changed_prefs; + copy_prefs(&changed_prefs, &currprefs); if (!graphics_setup()) { abort(); @@ -769,7 +773,8 @@ static int real_main2 (int argc, TCHAR **argv) } inputdevice_init(); - changed_prefs = currprefs; + copy_prefs(&currprefs, &changed_prefs); + no_gui = !currprefs.start_gui; if (restart_program == 2) no_gui = true; @@ -777,14 +782,13 @@ static int real_main2 (int argc, TCHAR **argv) no_gui = false; restart_program = 0; if (!no_gui) { - const int err = gui_init(); - currprefs = changed_prefs; + int err = gui_init (); + copy_prefs(&changed_prefs, &currprefs); set_config_changed(); if (err == -1) { write_log(_T("Failed to initialize the GUI\n")); return -1; - } - if (err == -2) { + } else if (err == -2) { return 1; } } @@ -803,12 +807,9 @@ static int real_main2 (int argc, TCHAR **argv) uae_restart(-1, nullptr); return 0; } -#ifdef PICASSO96 - picasso_reset(); -#endif fixup_prefs(&currprefs, true); - changed_prefs = currprefs; + copy_prefs(&currprefs, &changed_prefs); target_run(); /* force sound settings change */ currprefs.produce_sound = 0; @@ -853,7 +854,7 @@ void real_main(int argc, TCHAR **argv) default_config = 1; while (restart_program) { - changed_prefs = currprefs; + copy_prefs(&currprefs, &changed_prefs); real_main2(argc, argv); leave_program(); quit_program = 0; diff --git a/src/memory.cpp b/src/memory.cpp index ba464f22..a3d93c23 100644 --- a/src/memory.cpp +++ b/src/memory.cpp @@ -6,12 +6,12 @@ * (c) 1995 Bernd Schmidt */ -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "uae.h" -#include "include/memory.h" +#include "memory.h" #include "rommgr.h" #include "zfile.h" #include "custom.h" @@ -23,7 +23,6 @@ #include "gui.h" #include "akiko.h" #include "gayle.h" -#include "audio.h" #include "devices.h" #ifdef JIT @@ -34,11 +33,6 @@ static int mem_hardreset; static size_t bootrom_filepos, chip_filepos, bogo_filepos, a3000lmem_filepos, a3000hmem_filepos; -/* Set if we notice during initialization that settings changed, - and we must clear all memory to prevent bogus contents from confusing - the Kickstart. */ -static bool need_hardreset; - /* The address space setting used during the last reset. */ static bool last_address_space_24; @@ -47,8 +41,7 @@ addrbank *mem_banks[MEMORY_BANKS]; int addr_valid(const TCHAR *txt, uaecptr addr, uae_u32 len) { addrbank *ab = &get_mem_bank(addr); - if (ab == 0 || !(ab->flags & (ABFLAG_RAM | ABFLAG_ROM)) || addr < 0x100 || len > 16777215 || !valid_address(addr, len)) - { + if (ab == 0 || !(ab->flags & (ABFLAG_RAM | ABFLAG_ROM)) || addr < 0x100 || len > 16777215 || !valid_address(addr, len)) { write_log(_T("corrupt %s pointer %x (%d) detected!\n"), txt, addr, len); return 0; } @@ -112,23 +105,17 @@ uae_u32 dummy_get_safe(uaecptr addr, int size, bool inst, uae_u32 defvalue) return 0; if (currprefs.cs_unmapped_space == 2) return 0xffffffff & mask; - if ((currprefs.cpu_model <= 68010) || (currprefs.cpu_model == 68020 && (currprefs.chipset_mask & CSMASK_AGA) && currprefs.address_space_24)) - { - if (size == 4) - { + if ((currprefs.cpu_model <= 68010) || (currprefs.cpu_model == 68020 && (currprefs.chipset_mask & CSMASK_AGA) && currprefs.address_space_24)) { + if (size == 4) { v = regs.db & 0xffff; if (addr & 1) v = (v << 8) | (v >> 8); v = (v << 16) | v; - } - else if (size == 2) - { + } else if (size == 2) { v = regs.db & 0xffff; if (addr & 1) v = (v << 8) | (v >> 8); - } - else - { + } else { v = regs.db; v = (addr & 1) ? (v & 0xff) : ((v >> 8) & 0xff); } @@ -140,8 +127,7 @@ uae_u32 dummy_get(uaecptr addr, int size, bool inst, uae_u32 defvalue) { uae_u32 v = defvalue; - if (gary_nonrange(addr) || (size > 1 && gary_nonrange(addr + size - 1))) - { + if (gary_nonrange(addr) || (size > 1 && gary_nonrange(addr + size - 1))) { if (gary_toenb) exception2(addr, false, size, (regs.s ? 4 : 0) | (inst ? 0 : 1)); return v; @@ -154,10 +140,6 @@ static uae_u32 REGPARAM2 dummy_lget(uaecptr addr) { return dummy_get(addr, 4, false, nonexistingdata()); } -uae_u32 REGPARAM2 dummy_lgeti(uaecptr addr) -{ - return dummy_get(addr, 4, true, nonexistingdata()); -} static uae_u32 REGPARAM2 dummy_wget(uaecptr addr) { @@ -196,15 +178,12 @@ addrbank *get_sub_bank(uaecptr *paddr) struct addrbank_sub *sb = ab->sub_banks; if (!sb) return &dummy_bank; - for (i = 0; sb[i].bank; i++) - { + for (i = 0; sb[i].bank; i++) { int offset = addr & 65535; - if (offset < sb[i + 1].offset) - { + if (offset < sb[i + 1].offset) { uae_u32 mask = sb[i].mask; uae_u32 maskval = sb[i].maskval; - if ((offset & mask) == maskval) - { + if ((offset & mask) == maskval) { *paddr = addr - sb[i].suboffset; return sb[i].bank; } @@ -243,11 +222,6 @@ void REGPARAM3 sub_bank_bput(uaecptr addr, uae_u32 v) REGPARAM addrbank *ab = get_sub_bank(&addr); ab->bput(addr, v); } -uae_u32 REGPARAM3 sub_bank_lgeti(uaecptr addr) REGPARAM -{ - addrbank *ab = get_sub_bank(&addr); - return ab->lgeti(addr); -} uae_u32 REGPARAM3 sub_bank_wgeti(uaecptr addr) REGPARAM { addrbank *ab = get_sub_bank(&addr); @@ -269,9 +243,6 @@ uae_u8 *REGPARAM3 sub_bank_xlate(uaecptr addr) REGPARAM uae_u32 chipmem_full_mask; -static int REGPARAM3 chipmem_check (uaecptr addr, uae_u32 size) REGPARAM; -static uae_u8 *REGPARAM3 chipmem_xlate (uaecptr addr) REGPARAM; - static uae_u32 REGPARAM2 chipmem_lget(uaecptr addr) { uae_u32 *m; @@ -335,7 +306,7 @@ void REGPARAM2 chipmem_agnus_wput(uaecptr addr, uae_u32 w) static int REGPARAM2 chipmem_check(uaecptr addr, uae_u32 size) { addr &= chipmem_bank.mask; - return (addr + size) <= chipmem_bank.allocated_size; + return (addr + size) <= chipmem_bank.reserved_size; } static uae_u8 *REGPARAM2 chipmem_xlate(uaecptr addr) @@ -475,56 +446,64 @@ addrbank dummy_bank = { dummy_lget, dummy_wget, dummy_bget, dummy_lput, dummy_wput, dummy_bput, default_xlate, dummy_check, NULL, NULL, NULL, - dummy_lgeti, dummy_wgeti, - ABFLAG_NONE, S_READ, S_WRITE}; + dummy_wgeti, + ABFLAG_NONE, S_READ, S_WRITE +}; addrbank chipmem_bank = { chipmem_lget, chipmem_wget, chipmem_bget, chipmem_lput, chipmem_wput, chipmem_bput, chipmem_xlate, chipmem_check, NULL, _T("chip"), _T("Chip memory"), - chipmem_lget, chipmem_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE | ABFLAG_CHIPRAM, 0, 0}; + chipmem_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE | ABFLAG_CHIPRAM, 0, 0 +}; addrbank bogomem_bank = { bogomem_lget, bogomem_wget, bogomem_bget, bogomem_lput, bogomem_wput, bogomem_bput, bogomem_xlate, bogomem_check, NULL, _T("bogo"), _T("Slow memory"), - bogomem_lget, bogomem_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0}; + bogomem_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 +}; addrbank a3000lmem_bank = { a3000lmem_lget, a3000lmem_wget, a3000lmem_bget, a3000lmem_lput, a3000lmem_wput, a3000lmem_bput, a3000lmem_xlate, a3000lmem_check, NULL, _T("ramsey_low"), _T("RAMSEY memory (low)"), - a3000lmem_lget, a3000lmem_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0}; + a3000lmem_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 +}; addrbank a3000hmem_bank = { a3000hmem_lget, a3000hmem_wget, a3000hmem_bget, a3000hmem_lput, a3000hmem_wput, a3000hmem_bput, a3000hmem_xlate, a3000hmem_check, NULL, _T("ramsey_high"), _T("RAMSEY memory (high)"), - a3000hmem_lget, a3000hmem_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0}; + a3000hmem_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 +}; addrbank kickmem_bank = { kickmem_lget, kickmem_wget, kickmem_bget, kickmem_lput, kickmem_wput, kickmem_bput, kickmem_xlate, kickmem_check, NULL, _T("kick"), _T("Kickstart ROM"), - kickmem_lget, kickmem_wget, - ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE}; + kickmem_wget, + ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE +}; addrbank extendedkickmem_bank = { extendedkickmem_lget, extendedkickmem_wget, extendedkickmem_bget, extendedkickmem_lput, extendedkickmem_wput, extendedkickmem_bput, extendedkickmem_xlate, extendedkickmem_check, NULL, NULL, _T("Extended Kickstart ROM"), - extendedkickmem_lget, extendedkickmem_wget, - ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE}; + extendedkickmem_wget, + ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE +}; addrbank extendedkickmem2_bank = { extendedkickmem2_lget, extendedkickmem2_wget, extendedkickmem2_bget, extendedkickmem2_lput, extendedkickmem2_wput, extendedkickmem2_bput, extendedkickmem2_xlate, extendedkickmem2_check, NULL, _T("rom_a8"), _T("Extended 2nd Kickstart ROM"), - extendedkickmem2_lget, extendedkickmem2_wget, - ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE}; + extendedkickmem2_wget, + ABFLAG_ROM | ABFLAG_THREADSAFE, 0, S_WRITE +}; MEMORY_FUNCTIONS(custmem1); MEMORY_FUNCTIONS(custmem2); @@ -533,14 +512,48 @@ addrbank custmem1_bank = { custmem1_lget, custmem1_wget, custmem1_bget, custmem1_lput, custmem1_wput, custmem1_bput, custmem1_xlate, custmem1_check, NULL, _T("custmem1"), _T("Non-autoconfig RAM #1"), - custmem1_lget, custmem1_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0}; + custmem1_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 +}; addrbank custmem2_bank = { custmem2_lget, custmem2_wget, custmem2_bget, custmem2_lput, custmem2_wput, custmem2_bput, custmem2_xlate, custmem2_check, NULL, _T("custmem2"), _T("Non-autoconfig RAM #2"), - custmem2_lget, custmem2_wget, - ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0}; + custmem2_wget, + ABFLAG_RAM | ABFLAG_THREADSAFE, 0, 0 +}; + +static bool singlebit (uae_u32 v) +{ + while (v && !(v & 1)) + v >>= 1; + return (v & ~1) == 0; +} + +static void allocate_memory_custombanks(void) +{ + if (custmem1_bank.reserved_size != currprefs.custom_memory_sizes[0]) { + mapped_free (&custmem1_bank); + custmem1_bank.reserved_size = currprefs.custom_memory_sizes[0]; + // custmem1 and 2 can have non-power of 2 size so only set correct mask if size is power of 2. + custmem1_bank.mask = singlebit (custmem1_bank.reserved_size) ? custmem1_bank.reserved_size - 1 : -1; + custmem1_bank.start = currprefs.custom_memory_addrs[0]; + if (custmem1_bank.reserved_size) { + if (!mapped_malloc (&custmem1_bank)) + custmem1_bank.reserved_size = 0; + } + } + if (custmem2_bank.reserved_size != currprefs.custom_memory_sizes[1]) { + mapped_free (&custmem2_bank); + custmem2_bank.reserved_size = currprefs.custom_memory_sizes[1]; + custmem2_bank.mask = singlebit (custmem2_bank.reserved_size) ? custmem2_bank.reserved_size - 1 : -1; + custmem2_bank.start = currprefs.custom_memory_addrs[1]; + if (custmem2_bank.reserved_size) { + if (!mapped_malloc (&custmem2_bank)) + custmem2_bank.reserved_size = 0; + } + } +} static const uae_char *kickstring = "exec.library"; @@ -556,8 +569,8 @@ static int read_kickstart(struct zfile *f, uae_u8 *mem, int size, int dochecksum zfile_fseek(f, 0, SEEK_SET); } oldpos = zfile_ftell(f); - i = zfile_fread(buffer, 1, 11, f); - if (i < 11) + i = zfile_fread (buffer, 1, sizeof(buffer), f); + if (i < sizeof(buffer)) return 0; if (!memcmp(buffer, "KICK", 4)) { zfile_fseek(f, 512, SEEK_SET); @@ -671,59 +684,6 @@ static bool load_extendedkickstart(const TCHAR *romextfile, int type) return ret; } -/* disable incompatible drivers */ -static int patch_residents(uae_u8 *kickmemory, int size) -{ - int i, j, patched = 0; - const uae_char *residents[] = {"NCR scsi.device", NULL}; - // "scsi.device", "carddisk.device", "card.resource" }; - uaecptr base = size == ROM_SIZE_512 ? 0xf80000 : 0xfc0000; - - for (i = 0; i < size - 100; i++) - { - if (kickmemory[i] == 0x4a && kickmemory[i + 1] == 0xfc) - { - uaecptr addr; - addr = (kickmemory[i + 2] << 24) | (kickmemory[i + 3] << 16) | (kickmemory[i + 4] << 8) | (kickmemory[i + 5] << 0); - if (addr != i + base) - continue; - addr = (kickmemory[i + 14] << 24) | (kickmemory[i + 15] << 16) | (kickmemory[i + 16] << 8) | (kickmemory[i + 17] << 0); - if (addr >= base && addr < base + size) - { - j = 0; - while (residents[j]) - { - if (!memcmp(residents[j], kickmemory + addr - base, strlen(residents[j]) + 1)) - { - TCHAR *s = au(residents[j]); - write_log(_T("KSPatcher: '%s' at %08X disabled\n"), s, i + base); - xfree(s); - kickmemory[i] = 0x4b; /* destroy RTC_MATCHWORD */ - patched++; - break; - } - j++; - } - } - } - } - return patched; -} - -static void patch_kick(void) -{ - int patched = 0; - patched += patch_residents(kickmem_bank.baseaddr, kickmem_bank.allocated_size); - if (extendedkickmem_bank.baseaddr) - { - patched += patch_residents(extendedkickmem_bank.baseaddr, extendedkickmem_bank.allocated_size); - if (patched) - kickstart_fix_checksum(extendedkickmem_bank.baseaddr, extendedkickmem_bank.allocated_size); - } - if (patched) - kickstart_fix_checksum(kickmem_bank.baseaddr, kickmem_bank.allocated_size); -} - extern unsigned char arosrom[]; extern unsigned int arosrom_len; static bool load_kickstart_replacement(void) @@ -754,8 +714,7 @@ static bool load_kickstart_replacement(void) currprefs.fastmem[0].size == 0 && currprefs.z3fastmem[0].size == 0 && currprefs.mbresmem_high_size == 0 && - currprefs.mbresmem_low_size == 0) - { + currprefs.mbresmem_low_size == 0) { changed_prefs.custom_memory_addrs[0] = currprefs.custom_memory_addrs[0] = 0xa80000; changed_prefs.custom_memory_sizes[0] = currprefs.custom_memory_sizes[0] = 512 * 1024; @@ -763,11 +722,60 @@ static bool load_kickstart_replacement(void) changed_prefs.custom_memory_addrs[1] = currprefs.custom_memory_addrs[1] = 0xb00000; changed_prefs.custom_memory_sizes[1] = currprefs.custom_memory_sizes[1] = 512 * 1024; changed_prefs.custom_memory_mask[1] = currprefs.custom_memory_mask[1] = 0; + + allocate_memory_custombanks(); } return true; } +/* disable incompatible drivers */ +static int patch_residents (uae_u8 *kickmemory, int size) +{ + int i, j, patched = 0; + const uae_char *residents[] = { "NCR scsi.device", NULL }; + // "scsi.device", "carddisk.device", "card.resource" }; + uaecptr base = size == ROM_SIZE_512 ? 0xf80000 : 0xfc0000; + + for (i = 0; i < size - 100; i++) { + if (kickmemory[i] == 0x4a && kickmemory[i + 1] == 0xfc) { + uaecptr addr; + addr = (kickmemory[i + 2] << 24) | (kickmemory[i + 3] << 16) | (kickmemory[i + 4] << 8) | (kickmemory[i + 5] << 0); + if (addr != i + base) + continue; + addr = (kickmemory[i + 14] << 24) | (kickmemory[i + 15] << 16) | (kickmemory[i + 16] << 8) | (kickmemory[i + 17] << 0); + if (addr >= base && addr < base + size) { + j = 0; + while (residents[j]) { + if (!memcmp (residents[j], kickmemory + addr - base, strlen (residents[j]) + 1)) { + TCHAR *s = au (residents[j]); + write_log (_T("KSPatcher: '%s' at %08X disabled\n"), s, i + base); + xfree (s); + kickmemory[i] = 0x4b; /* destroy RTC_MATCHWORD */ + patched++; + break; + } + j++; + } + } + } + } + return patched; +} + +static void patch_kick(void) +{ + int patched = 0; + patched += patch_residents (kickmem_bank.baseaddr, kickmem_bank.allocated_size); + if (extendedkickmem_bank.baseaddr) { + patched += patch_residents (extendedkickmem_bank.baseaddr, extendedkickmem_bank.allocated_size); + if (patched) + kickstart_fix_checksum (extendedkickmem_bank.baseaddr, extendedkickmem_bank.allocated_size); + } + if (patched) + kickstart_fix_checksum (kickmem_bank.baseaddr, kickmem_bank.allocated_size); +} + static struct zfile *get_kickstart_filehandle(struct uae_prefs *p) { struct zfile *f; @@ -775,27 +783,25 @@ static struct zfile *get_kickstart_filehandle(struct uae_prefs *p) f = read_rom_name(p->romfile); _tcscpy(tmprom, p->romfile); - if (f == NULL) - { + _tcscpy(tmprom2, p->romfile); + if (f == NULL) { _stprintf(tmprom2, _T("%s%s"), start_path_data, p->romfile); f = rom_fopen(tmprom2, _T("rb"), ZFD_NORMAL); - if (f == NULL) - { - _stprintf(p->romfile, _T("%sroms/kick.rom"), start_path_data); - f = rom_fopen(p->romfile, _T("rb"), ZFD_NORMAL); - if (f == NULL) - { - _stprintf(p->romfile, _T("%skick.rom"), start_path_data); - f = rom_fopen(p->romfile, _T("rb"), ZFD_NORMAL); - if (f == NULL) - f = read_rom_name_guess(tmprom); + if (f == NULL) { + _stprintf (tmprom2, _T("%sroms/kick.rom"), start_path_data); + f = rom_fopen (tmprom2, _T("rb"), ZFD_NORMAL); + if (f == NULL) { + _stprintf (tmprom2, _T("%skick.rom"), start_path_data); + f = rom_fopen(tmprom2, _T("rb"), ZFD_NORMAL); + if (f == NULL) { + f = read_rom_name_guess (tmprom, tmprom2); } } - else - { - _tcscpy(p->romfile, tmprom2); } } + if (f) { + _tcscpy (p->romfile, tmprom2); + } return f; } @@ -896,21 +902,17 @@ static void init_mem_banks(void) mem_banks[i] = &dummy_bank; } -static bool singlebit (uae_u32 v) +static void map_banks_set(addrbank *bank, int start, int size, int realsize) { - while (v && !(v & 1)) - v >>= 1; - return (v & ~1) == 0; + map_banks(bank, start, size, realsize); } static void allocate_memory(void) { - if (chipmem_bank.reserved_size != currprefs.chipmem_size) - { + if (chipmem_bank.reserved_size != currprefs.chipmem_size) { int memsize; mapped_free(&chipmem_bank); - if (currprefs.chipmem_size > 2 * 1024 * 1024) - { + if (currprefs.chipmem_size > 2 * 1024 * 1024) { free_fastmemory(0); } @@ -925,23 +927,17 @@ static void allocate_memory(void) mapped_malloc(&chipmem_bank); chipmem_bank.reserved_size = currprefs.chipmem_size; chipmem_bank.allocated_size = currprefs.chipmem_size; - if (chipmem_bank.baseaddr == 0) - { + if (chipmem_bank.baseaddr == 0) { write_log(_T("Fatal error: out of memory for chipmem.\n")); chipmem_bank.reserved_size = 0; - } - else - { - need_hardreset = true; + } else { if (memsize > chipmem_bank.allocated_size) memset(chipmem_bank.baseaddr + chipmem_bank.allocated_size, 0xff, memsize - chipmem_bank.allocated_size); } currprefs.chipset_mask = changed_prefs.chipset_mask; chipmem_full_mask = chipmem_bank.allocated_size - 1; - if (!currprefs.cachesize) - { - if (currprefs.chipset_mask & CSMASK_ECS_AGNUS) - { + if (!currprefs.cachesize) { + if (currprefs.chipset_mask & CSMASK_ECS_AGNUS) { if (chipmem_bank.allocated_size < 0x100000) chipmem_full_mask = 0x100000 - 1; if (chipmem_bank.allocated_size > 0x100000 && chipmem_bank.allocated_size < 0x200000) @@ -950,14 +946,13 @@ static void allocate_memory(void) } } - if (bogomem_bank.reserved_size != currprefs.bogomem_size) - { + if (bogomem_bank.reserved_size != currprefs.bogomem_size) { mapped_free(&bogomem_bank); bogomem_bank.reserved_size = 0; if (currprefs.bogomem_size > 0x1c0000) currprefs.bogomem_size = 0x1c0000; - if (currprefs.bogomem_size > 0x180000 && ((changed_prefs.chipset_mask & CSMASK_AGA) || (currprefs.cpu_model >= 68020))) + if (currprefs.bogomem_size > 0x180000 && ((currprefs.chipset_mask & CSMASK_AGA) || (currprefs.cpu_model >= 68020))) currprefs.bogomem_size = 0x180000; bogomem_bank.reserved_size = currprefs.bogomem_size; @@ -966,80 +961,44 @@ static void allocate_memory(void) bogomem_bank.mask = bogomem_bank.reserved_size - 1; bogomem_bank.start = bogomem_start_addr; - if (bogomem_bank.reserved_size) - { - if (!mapped_malloc(&bogomem_bank)) - { + if (bogomem_bank.reserved_size) { + if (!mapped_malloc (&bogomem_bank)) { write_log(_T("Out of memory for bogomem.\n")); bogomem_bank.reserved_size = 0; } } - need_hardreset = true; } - if (a3000lmem_bank.reserved_size != currprefs.mbresmem_low_size) - { + if (a3000lmem_bank.reserved_size != currprefs.mbresmem_low_size) { mapped_free(&a3000lmem_bank); a3000lmem_bank.reserved_size = currprefs.mbresmem_low_size; a3000lmem_bank.mask = a3000lmem_bank.reserved_size - 1; a3000lmem_bank.start = 0x08000000 - a3000lmem_bank.reserved_size; - if (a3000lmem_bank.reserved_size) - { - if (!mapped_malloc(&a3000lmem_bank)) - { + if (a3000lmem_bank.reserved_size) { + if (!mapped_malloc (&a3000lmem_bank)) { write_log(_T("Out of memory for a3000lowmem.\n")); a3000lmem_bank.reserved_size = 0; } } - need_hardreset = true; } - if (a3000hmem_bank.reserved_size != currprefs.mbresmem_high_size) - { + if (a3000hmem_bank.reserved_size != currprefs.mbresmem_high_size) { mapped_free(&a3000hmem_bank); a3000hmem_bank.reserved_size = currprefs.mbresmem_high_size; a3000hmem_bank.mask = a3000hmem_bank.reserved_size - 1; a3000hmem_bank.start = 0x08000000; - if (a3000hmem_bank.reserved_size) - { - if (!mapped_malloc(&a3000hmem_bank)) - { + if (a3000hmem_bank.reserved_size) { + if (!mapped_malloc (&a3000hmem_bank)) { write_log(_T("Out of memory for a3000highmem.\n")); a3000hmem_bank.reserved_size = 0; } } - need_hardreset = true; - } - if (custmem1_bank.reserved_size != currprefs.custom_memory_sizes[0]) - { - mapped_free(&custmem1_bank); - custmem1_bank.reserved_size = currprefs.custom_memory_sizes[0]; - // custmem1 and 2 can have non-power of 2 size so only set correct mask if size is power of 2. - custmem1_bank.mask = singlebit(custmem1_bank.reserved_size) ? custmem1_bank.reserved_size - 1 : -1; - custmem1_bank.start = currprefs.custom_memory_addrs[0]; - if (custmem1_bank.reserved_size) - { - if (!mapped_malloc(&custmem1_bank)) - custmem1_bank.reserved_size = 0; - } - } - if (custmem2_bank.reserved_size != currprefs.custom_memory_sizes[1]) - { - mapped_free(&custmem2_bank); - custmem2_bank.reserved_size = currprefs.custom_memory_sizes[1]; - custmem2_bank.mask = singlebit(custmem2_bank.reserved_size) ? custmem2_bank.reserved_size - 1 : -1; - custmem2_bank.start = currprefs.custom_memory_addrs[1]; - if (custmem2_bank.reserved_size) - { - if (!mapped_malloc(&custmem2_bank)) - custmem2_bank.reserved_size = 0; - } } - if (savestate_state == STATE_RESTORE) - { - if (bootrom_filepos) - { + allocate_memory_custombanks(); + + if (savestate_state == STATE_RESTORE) { + if (bootrom_filepos) { protect_roms(false); restore_ram(bootrom_filepos, rtarea_bank.baseaddr); protect_roms(true); @@ -1067,13 +1026,10 @@ void map_overlay(int chip) size = chipmem_bank.allocated_size >= 0x180000 ? (chipmem_bank.allocated_size >> 16) : 32; cb = &chipmem_bank; - if (chip) - { + if (chip) { map_banks(&dummy_bank, 0, size, 0); map_banks(cb, 0, size, chipmem_bank.allocated_size); - } - else - { + } else { addrbank *rb = NULL; if (size < 32) size = 32; @@ -1091,11 +1047,6 @@ void map_overlay(int chip) m68k_setpc_normal(currPC); } -static void map_banks_set(addrbank *bank, int start, int size, int realsize) -{ - map_banks(bank, start, size, realsize); -} - void memory_clear(void) { mem_hardreset = 0; @@ -1120,7 +1071,6 @@ static void restore_roms(void) memcpy(currprefs.romfile, changed_prefs.romfile, sizeof currprefs.romfile); memcpy(currprefs.romextfile, changed_prefs.romextfile, sizeof currprefs.romextfile); - need_hardreset = true; mapped_free(&extendedkickmem_bank); mapped_free(&extendedkickmem2_bank); extendedkickmem_bank.reserved_size = 0; @@ -1199,8 +1149,7 @@ bool read_kickstart_version(struct uae_prefs *p) read_kickstart(z, mem, sizeof mem, 0, 0); zfile_fclose(z); kickstart_version = (mem[12] << 8) | mem[13]; - if (kickstart_version == 0xffff) - { + if (kickstart_version == 0xffff) { // 1.0-1.1 and older kickstart_version = (mem[16] << 8) | mem[17]; if (kickstart_version > 33) @@ -1210,15 +1159,14 @@ bool read_kickstart_version(struct uae_prefs *p) return true; } +static void memory_init (void); + void memory_reset(void) { int bnk, bnk_end; bool gayleorfatgary; - need_hardreset = false; /* Use changed_prefs, as m68k_reset is called later. */ - if (last_address_space_24 != changed_prefs.address_space_24) - need_hardreset = true; last_address_space_24 = changed_prefs.address_space_24; if (mem_hardreset > 2) @@ -1242,7 +1190,9 @@ void memory_reset(void) init_mem_banks(); allocate_memory(); - if (mem_hardreset > 1 || _tcscmp(currprefs.romfile, changed_prefs.romfile) != 0 || _tcscmp(currprefs.romextfile, changed_prefs.romextfile) != 0) + if (mem_hardreset > 1 + || _tcscmp (currprefs.romfile, changed_prefs.romfile) != 0 + || _tcscmp (currprefs.romextfile, changed_prefs.romextfile) != 0) { restore_roms(); } @@ -1259,24 +1209,20 @@ void memory_reset(void) bnk = 0x20 + (currprefs.fastmem[0].size >> 16); bnk_end = currprefs.cs_cd32cd ? 0xBE : (gayleorfatgary ? 0xBF : 0xA0); map_banks(&dummy_bank, bnk, bnk_end - bnk, 0); - if (gayleorfatgary) - { + if (gayleorfatgary) { // a4000 = custom chips from 0xc0 to 0xd0 if (currprefs.cs_ide == IDE_A4000) map_banks(&dummy_bank, 0xd0, 8, 0); else map_banks(&dummy_bank, 0xc0, 0xd8 - 0xc0, 0); - } - else if (currprefs.cs_cd32cd) - { + } else if (currprefs.cs_cd32cd) { // CD32: 0xc0 to 0xd0 map_banks(&dummy_bank, 0xd0, 8, 0); // strange 64k custom mirror map_banks(&custom_bank, 0xb9, 1, 0); } - if (bogomem_bank.baseaddr) - { + if (bogomem_bank.baseaddr) { int t = currprefs.bogomem_size >> 16; if (t > 0x1C) t = 0x1C; @@ -1308,8 +1254,7 @@ void memory_reset(void) if (currprefs.cs_fatgaryrev >= 0 || currprefs.cs_ramseyrev >= 0) map_banks(&mbres_bank, 0xDE, 1, 0); #ifdef CD32 - if (currprefs.cs_cd32c2p || currprefs.cs_cd32cd || currprefs.cs_cd32nvram) - { + if (currprefs.cs_cd32c2p || currprefs.cs_cd32cd || currprefs.cs_cd32nvram) { map_banks(&akiko_bank, AKIKO_BASE >> 16, 1, 0); map_banks(&gayle2_bank, 0xDD, 2, 0); } @@ -1320,8 +1265,7 @@ void memory_reset(void) map_banks(&a3000hmem_bank, a3000hmem_bank.start >> 16, a3000hmem_bank.allocated_size >> 16, 0); map_banks_set(&kickmem_bank, 0xF8, 8, 0); /* map beta Kickstarts at 0x200000/0xC00000/0xF00000 */ - if (kickmem_bank.baseaddr[0] == 0x11 && kickmem_bank.baseaddr[2] == 0x4e && kickmem_bank.baseaddr[3] == 0xf9 && kickmem_bank.baseaddr[4] == 0x00) - { + if (kickmem_bank.baseaddr[0] == 0x11 && kickmem_bank.baseaddr[2] == 0x4e && kickmem_bank.baseaddr[3] == 0xf9 && kickmem_bank.baseaddr[4] == 0x00) { uae_u32 addr = kickmem_bank.baseaddr[5]; if (addr == 0x20 && currprefs.chipmem_size <= 0x200000 && currprefs.fastmem[0].size == 0) map_banks_set(&kickmem_bank, addr, 8, 0); @@ -1338,8 +1282,7 @@ void memory_reset(void) /* Map the chipmem into all of the lower 8MB */ map_overlay(1); - switch (extendedkickmem_type) - { + switch (extendedkickmem_type) { case EXTENDED_ROM_KS: map_banks_set(&extendedkickmem_bank, 0xE0, 8, 0); break; @@ -1355,21 +1298,15 @@ void memory_reset(void) map_banks_set(&rtarea_bank, rtarea_base >> 16, 1, 0); #endif - if ((cloanto_rom || currprefs.cs_ksmirror_e0) && !extendedkickmem_type) - { + if ((cloanto_rom || currprefs.cs_ksmirror_e0) && !extendedkickmem_type) { map_banks(&kickmem_bank, 0xE0, 8, 0); } - if (currprefs.cs_ksmirror_a8) - { - if (extendedkickmem2_bank.allocated_size) - { - map_banks_set(&extendedkickmem2_bank, 0xa8, 16, 0); - } - else - { + if (currprefs.cs_ksmirror_a8) { + if (extendedkickmem2_bank.allocated_size) { + map_banks_set(&extendedkickmem2_bank, extendedkickmem2_bank.start >> 16, extendedkickmem2_bank.allocated_size >> 16, 0); + } else { struct romdata *rd = getromdatabypath(currprefs.cartfile); - if (!rd || rd->id != 63) - { + if (!rd || rd->id != 63) { if (extendedkickmem_type == EXTENDED_ROM_CD32 || extendedkickmem_type == EXTENDED_ROM_KS) map_banks(&extendedkickmem_bank, 0xb0, 8, 0); else @@ -1377,37 +1314,34 @@ void memory_reset(void) map_banks(&kickmem_bank, 0xa8, 8, 0); } } + } else if (extendedkickmem2_bank.allocated_size && extendedkickmem2_bank.baseaddr) { + map_banks_set(&extendedkickmem2_bank, extendedkickmem2_bank.start >> 16, extendedkickmem2_bank.allocated_size >> 16, 0); } #ifdef ACTION_REPLAY action_replay_memory_reset(); #endif - for (int i = 0; i < 2; i++) - { - if (currprefs.custom_memory_sizes[i]) - { + for (int i = 0; i < 2; i++) { + if (currprefs.custom_memory_sizes[i]) { map_banks(i == 0 ? &custmem1_bank : &custmem2_bank, currprefs.custom_memory_addrs[i] >> 16, currprefs.custom_memory_sizes[i] >> 16, 0); - if (currprefs.custom_memory_mask[i]) - { - for (int j = currprefs.custom_memory_addrs[i]; j & currprefs.custom_memory_mask[i]; j += currprefs.custom_memory_sizes[i]) - { + if (currprefs.custom_memory_mask[i]) { + for (int j = currprefs.custom_memory_addrs[i]; j & currprefs.custom_memory_mask[i]; j += currprefs.custom_memory_sizes[i]) { map_banks(i == 0 ? &custmem1_bank : &custmem2_bank, j >> 16, currprefs.custom_memory_sizes[i] >> 16, 0); } } } } - if (mem_hardreset) - { + if (mem_hardreset) { memory_clear(); } write_log (_T("memory init end\n")); } -void memory_init(void) +static void memory_init (void) { init_mem_banks(); virtualdevice_init(); @@ -1475,8 +1409,7 @@ void memory_hardreset (int mode) // do not map if it conflicts with custom banks void map_banks_cond(addrbank *bank, int start, int size, int realsize) { - for (int i = 0; i < MAX_CUSTOM_MEMORY_ADDRS; i++) - { + for (int i = 0; i < MAX_CUSTOM_MEMORY_ADDRS; i++) { int cstart = currprefs.custom_memory_addrs[i] >> 16; if (!cstart) continue; @@ -1491,7 +1424,7 @@ void map_banks_cond(addrbank *bank, int start, int size, int realsize) map_banks(bank, start, size, realsize); } -static void map_banks2(addrbank *bank, int start, int size, int realsize, int quick) +static void map_banks2 (addrbank *bank, int start, int size, int realsize) { int bnr; unsigned long int hioffs = 0, endhioffs = 0x100; @@ -1502,17 +1435,14 @@ static void map_banks2(addrbank *bank, int start, int size, int realsize, int qu if (!realsize) realsize = size << 16; - if ((size << 16) < realsize) - { + if ((size << 16) < realsize) { write_log(_T("Broken mapping, size=%x, realsize=%x\nStart is %x\n"), size, realsize, start); } #ifndef ADDRESS_SPACE_24BIT - if (start >= 0x100) - { - for (bnr = start; bnr < start + size; bnr++) - { + if (start >= 0x100) { + for (bnr = start; bnr < start + size; bnr++) { mem_banks[bnr] = bank; } return; @@ -1523,10 +1453,8 @@ static void map_banks2(addrbank *bank, int start, int size, int realsize, int qu #ifdef ADDRESS_SPACE_24BIT endhioffs = 0x100; #endif - for (hioffs = 0; hioffs < endhioffs; hioffs += 0x100) - { - for (bnr = start; bnr < start + size; bnr++) - { + for (hioffs = 0; hioffs < endhioffs; hioffs += 0x100) { + for (bnr = start; bnr < start + size; bnr++) { mem_banks[bnr + hioffs] = bank; } } @@ -1536,32 +1464,27 @@ void map_banks(addrbank *bank, int start, int size, int realsize) { if (start == 0xffffffff) return; - if (start >= 0x100) - { + if (start >= 0x100) { if (currprefs.address_space_24) return; } - map_banks2(bank, start, size, realsize, 0); + map_banks2 (bank, start, size, realsize); } -bool validate_banks_z3(addrbank *bank, int start, int size) +static bool validate_banks_z3(addrbank *bank, int start, int size) { - if (start < 0x1000 || size <= 0) - { + if (start < 0x1000 || size <= 0) { error_log(_T("Z3 invalid map_banks(%s) start=%08x size=%08x\n"), bank->name, start << 16, size << 16); cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); return false; } - if (size > 0x4000 || start + size > 0xf000) - { + if (size > 0x4000 || start + size > 0xf000) { error_log(_T("Z3 invalid map_banks(%s) start=%08x size=%08x\n"), bank->name, start << 16, size << 16); return false; } - for (int i = start; i < start + size; i++) - { + for (int i = start; i < start + size; i++) { addrbank *ab = &get_mem_bank(start << 16); - if (ab != &dummy_bank && ab != bank) - { + if (ab != &dummy_bank && ab != bank) { error_log(_T("Z3 map_banks(%s) attempting to override existing memory bank '%s' at %08x!\n"), bank->name, ab->name, i << 16); return false; } @@ -1578,41 +1501,32 @@ void map_banks_z3(addrbank *bank, int start, int size) bool validate_banks_z2(addrbank *bank, int start, int size) { - if (start < 0x20 || (start >= 0xa0 && start < 0xe9) || start >= 0xf0) - { + if (start < 0x20 || (start >= 0xa0 && start < 0xe9) || start >= 0xf0) { error_log(_T("Z2 map_banks(%s) with invalid start address %08X\n"), bank->name, start << 16); cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); return false; } - if (start >= 0xe9) - { - if (start + size > 0xf0) - { + if (start >= 0xe9) { + if (start + size > 0xf0) { + error_log(_T("Z2 map_banks(%s) with invalid region %08x - %08X\n"), bank->name, start << 16, (start + size) << 16); + cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); + return false; + } + } else { + if (start + size > 0xa0) { error_log(_T("Z2 map_banks(%s) with invalid region %08x - %08X\n"), bank->name, start << 16, (start + size) << 16); cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); return false; } } - else - { - if (start + size > 0xa0) - { - error_log(_T("Z2 map_banks(%s) with invalid region %08x - %08X\n"), bank->name, start << 16, (start + size) << 16); - cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); - return false; - } - } - if (size <= 0 || size > 0x80) - { + if (size <= 0 || size > 0x80) { error_log(_T("Z2 map_banks(%s) with invalid size %08x\n"), bank->name, size); cpu_halt(CPU_HALT_AUTOCONFIG_CONFLICT); return false; } - for (int i = start; i < start + size; i++) - { + for (int i = start; i < start + size; i++) { addrbank *ab = &get_mem_bank(start << 16); - if (ab != &dummy_bank) - { + if (ab != &dummy_bank) { error_log(_T("Z2 map_banks(%s) attempting to override existing memory bank '%s' at %08x!\n"), bank->name, ab->name, i << 16); return false; } @@ -1620,6 +1534,7 @@ bool validate_banks_z2(addrbank *bank, int start, int size) return true; } + void map_banks_z2(addrbank *bank, int start, int size) { if (!validate_banks_z2(bank, start, size)) @@ -1627,11 +1542,6 @@ void map_banks_z2(addrbank *bank, int start, int size) map_banks(bank, start, size, 0); } -void map_banks_quick(addrbank *bank, int start, int size, int realsize) -{ - map_banks2(bank, start, size, realsize, 1); -} - #ifdef SAVESTATE /* memory save/restore code */ @@ -1711,12 +1621,9 @@ uae_u8 *restore_rom(uae_u8 *src) crc32 = restore_u32(); romn = restore_string(); crcdet = 0; - for (i = 0; i < romlist_count(); i++) - { - if (rl[i].rd->crc32 == crc32 && crc32) - { - if (zfile_exists(rl[i].path)) - { + for (i = 0; i < romlist_count (); i++) { + if (rl[i].rd->crc32 == crc32 && crc32) { + if (zfile_exists (rl[i].path)) { switch (mem_type) { case 0: @@ -1728,19 +1635,15 @@ uae_u8 *restore_rom(uae_u8 *src) } write_log(_T("ROM '%s' = '%s'\n"), romn, rl[i].path); crcdet = 1; - } - else - { + } else { write_log(_T("ROM '%s' = '%s' invalid rom scanner path!"), romn, rl[i].path); } break; } } s = restore_string(); - if (!crcdet) - { - if (zfile_exists(s)) - { + if (!crcdet) { + if(zfile_exists (s)) { switch (mem_type) { case 0: @@ -1777,30 +1680,26 @@ uae_u8 *save_rom(int first, int *len, uae_u8 *dstptr) saverom = 0; if (first) count = 0; - for (;;) - { + for (;;) { mem_type = count; mem_size = 0; - switch (count) - { + switch (count) { case 0: /* Kickstart ROM */ mem_start = 0xf80000; mem_real_start = kickmem_bank.baseaddr; mem_size = kickmem_bank.allocated_size; path = currprefs.romfile; /* 256KB or 512KB ROM? */ - for (i = 0; i < mem_size / 2 - 4; i++) - { - if (longget(i + mem_start) != longget(i + mem_start + mem_size / 2)) + for (i = 0; i < mem_size / 2 - 4; i++) { + if (get_long (i + mem_start) != get_long (i + mem_start + mem_size / 2)) break; } - if (i == mem_size / 2 - 4) - { + if (i == mem_size / 2 - 4) { mem_size /= 2; mem_start += ROM_SIZE_256; } - version = longget(mem_start + 12); /* version+revision */ - _stprintf(tmpname, _T("Kickstart %d.%d"), wordget(mem_start + 12), wordget(mem_start + 14)); + version = get_long (mem_start + 12); /* version+revision */ + _stprintf (tmpname, _T("Kickstart %d.%d"), get_word (mem_start + 12), get_word (mem_start + 14)); break; case 1: /* Extended ROM */ if (!extendedkickmem_type) @@ -1809,9 +1708,9 @@ uae_u8 *save_rom(int first, int *len, uae_u8 *dstptr) mem_real_start = extendedkickmem_bank.baseaddr; mem_size = extendedkickmem_bank.allocated_size; path = currprefs.romextfile; - version = longget(mem_start + 12); /* version+revision */ + version = get_long (mem_start + 12); /* version+revision */ if (version == 0xffffffff) - version = longget(mem_start + 16); + version = get_long (mem_start + 16); _stprintf(tmpname, _T("Extended")); break; default: @@ -1832,10 +1731,9 @@ uae_u8 *save_rom(int first, int *len, uae_u8 *dstptr) save_u32(get_crc32(mem_real_start, mem_size)); save_string(tmpname); save_string(path); - if (saverom) - { + if (saverom) { for (i = 0; i < mem_size; i++) - *dst++ = byteget(mem_start + i); + *dst++ = get_byte (mem_start + i); } *len = dst - dstbak; return dstbak; @@ -1857,42 +1755,11 @@ void memcpyha(uaecptr dst, const uae_u8 *src, int size) while (size--) put_byte(dst++, *src++); } -void memcpyah_safe(uae_u8 *dst, uaecptr src, int size) -{ - if (!addr_valid(_T("memcpyah"), src, size)) - return; - while (size--) - *dst++ = get_byte(src++); -} -void memcpyah(uae_u8 *dst, uaecptr src, int size) -{ - while (size--) - *dst++ = get_byte(src++); -} -uae_char *strcpyah_safe(uae_char *dst, uaecptr src, int maxsize) -{ - uae_char *res = dst; - uae_u8 b; - dst[0] = 0; - do - { - if (!addr_valid(_T("_tcscpyah"), src, 1)) - return res; - b = get_byte(src++); - *dst++ = b; - *dst = 0; - maxsize--; - if (maxsize <= 1) - break; - } while (b); - return res; -} uaecptr strcpyha_safe(uaecptr dst, const uae_char *src) { uaecptr res = dst; uae_u8 b; - do - { + do { if (!addr_valid(_T("_tcscpyha"), dst, 1)) return res; b = *src++; diff --git a/src/newcpu.cpp b/src/newcpu.cpp index 65b37b0c..f75969ef 100644 --- a/src/newcpu.cpp +++ b/src/newcpu.cpp @@ -5,11 +5,6 @@ * * (c) 1995 Bernd Schmidt */ -#include -#include -#include -#include -#include #include "sysdeps.h" @@ -24,6 +19,7 @@ #include "savestate.h" #include "blitter.h" #include "ar.h" +#include "inputdevice.h" #include "audio.h" #include "threaddep/thread.h" #include "bsdsocket.h" @@ -37,7 +33,7 @@ bool check_prefs_changed_comp (bool checkonly) { return false; } #endif /* Opcode of faulting instruction */ -static uae_u16 last_op_for_exception_3; +static uae_u32 last_op_for_exception_3; /* PC at fault time */ static uaecptr last_addr_for_exception_3; /* Address that generated the exception */ @@ -56,14 +52,14 @@ int m68k_pc_indirect; static int cpu_prefs_changed_flag; -const int areg_byteinc[] = {1, 1, 1, 1, 1, 1, 1, 2}; -const int imm8_table[] = {8, 1, 2, 3, 4, 5, 6, 7}; +const int areg_byteinc[] = { 1,1,1,1,1,1,1,2 }; +const int imm8_table[] = { 8,1,2,3,4,5,6,7 }; int movem_index1[256]; int movem_index2[256]; int movem_next[256]; -cpuop_func* cpufunctbl[65536]; +cpuop_func *cpufunctbl[65536]; struct cputbl_data { @@ -71,7 +67,6 @@ struct cputbl_data uae_s8 disp020[2]; uae_u8 branch; }; - static struct cputbl_data cpudatatbl[65536]; struct mmufixup mmufixup[1]; @@ -83,26 +78,26 @@ static uae_u32 fake_tt0_030, fake_tt1_030, fake_tc_030; static uae_u16 fake_mmusr_030; #if COUNT_INSTRS -static unsigned long int instrcount[65536]; +static uae_u32 instrcount[65536]; static uae_u16 opcodenums[65536]; -static int compfn(const void *el1, const void *el2) +static int compfn (const void *el1, const void *el2) { return instrcount[*(const uae_u16 *)el1] < instrcount[*(const uae_u16 *)el2]; } -static TCHAR *icountfilename(void) +static TCHAR *icountfilename (void) { - TCHAR *name = getenv("INSNCOUNT"); + TCHAR *name = getenv ("INSNCOUNT"); if (name) return name; return (TCHAR *)(COUNT_INSTRS == 2 ? _T("frequent.68k") : _T("insncount")); } -void dump_counts(void) +void dump_counts (void) { - FILE *f = fopen(icountfilename(), "w"); - unsigned long int total; + FILE *f = fopen (icountfilename (), "w"); + uae_u32 total; int i; write_log(_T("Writing instruction count file...\n")); @@ -110,33 +105,32 @@ void dump_counts(void) opcodenums[i] = i; total += instrcount[i]; } - qsort(opcodenums, 65536, sizeof(uae_u16), compfn); + qsort (opcodenums, 65536, sizeof (uae_u16), compfn); - fprintf(f, "Total: %lu\n", total); - for (i = 0; i < 65536; i++) { - unsigned long int cnt = instrcount[opcodenums[i]]; + fprintf (f, "Total: %lu\n", total); + for (i=0; i < 65536; i++) { + uae_u32 cnt = instrcount[opcodenums[i]]; struct instr *dp; struct mnemolookup *lookup; if (!cnt) break; dp = table68k + opcodenums[i]; - for (lookup = lookuptab; lookup->mnemo != dp->mnemo; lookup++) + for (lookup = lookuptab;lookup->mnemo != dp->mnemo; lookup++) ; - fprintf(f, "%04x: %8lu %s\n", opcodenums[i], cnt, lookup->name); + fprintf (f, "%04x: %8lu %s\n", opcodenums[i], cnt, lookup->name); } - fclose(f); + fclose (f); } -STATIC_INLINE void count_instr(unsigned int opcode) +STATIC_INLINE void count_instr (unsigned int opcode) { - instrcount[opcode]++; + instrcount[opcode]++; } #else -void dump_counts(void) +void dump_counts (void) { } - -STATIC_INLINE void count_instr(unsigned int opcode) +STATIC_INLINE void count_instr (unsigned int opcode) { } #endif @@ -144,19 +138,24 @@ STATIC_INLINE void count_instr(unsigned int opcode) uae_u32 (*x_get_long)(uaecptr); uae_u32 (*x_get_word)(uaecptr); uae_u32 (*x_get_byte)(uaecptr); -void (*x_put_long)(uaecptr, uae_u32); -void (*x_put_word)(uaecptr, uae_u32); -void (*x_put_byte)(uaecptr, uae_u32); +void (*x_put_long)(uaecptr,uae_u32); +void (*x_put_word)(uaecptr,uae_u32); +void (*x_put_byte)(uaecptr,uae_u32); // indirect memory access functions -static void set_x_funcs(void) +static void set_x_funcs (void) { - if (currprefs.cpu_model < 68020) - { + if (currprefs.cpu_model < 68020) { // 68000/010 - if (currprefs.cpu_compatible) - { + if (currprefs.cpu_compatible) { // cpu_compatible only + x_put_long = put_long_compatible; + x_put_word = put_word_compatible; + x_put_byte = put_byte_compatible; + x_get_long = get_long_compatible; + x_get_word = get_word_compatible; + x_get_byte = get_byte_compatible; + } else { x_put_long = put_long; x_put_word = put_word; x_put_byte = put_byte; @@ -164,54 +163,37 @@ static void set_x_funcs(void) x_get_word = get_word; x_get_byte = get_byte; } - else - { - x_put_long = put_long; - x_put_word = put_word; - x_put_byte = put_byte; - x_get_long = get_long; - x_get_word = get_word; - x_get_byte = get_byte; - } - } - else - { + } else { // 68020+ no ce - if (currprefs.cachesize) - { - x_put_long = put_long_jit; - x_put_word = put_word_jit; - x_put_byte = put_byte_jit; - x_get_long = get_long_jit; - x_get_word = get_word_jit; - x_get_byte = get_byte_jit; - } - else - { - x_put_long = put_long; - x_put_word = put_word; - x_put_byte = put_byte; - x_get_long = get_long; - x_get_word = get_word; - x_get_byte = get_byte; - } - } + if (currprefs.cachesize) { + x_put_long = put_long_jit; + x_put_word = put_word_jit; + x_put_byte = put_byte_jit; + x_get_long = get_long_jit; + x_get_word = get_word_jit; + x_get_byte = get_byte_jit; + } else { + x_put_long = put_long; + x_put_word = put_word; + x_put_byte = put_byte; + x_get_long = get_long; + x_get_word = get_word; + x_get_byte = get_byte; + } + } } -void flush_cpu_caches(bool force) +static void flush_cpu_caches(bool force) { - if (currprefs.cpu_model == 68020) - { + if (currprefs.cpu_model == 68020) { regs.cacr &= ~0x08; regs.cacr &= ~0x04; - } - else if (currprefs.cpu_model == 68030) - { + } else if (currprefs.cpu_model == 68030) { regs.cacr &= ~0x08; regs.cacr &= ~0x04; regs.cacr &= ~0x800; regs.cacr &= ~0x400; - } + } } void flush_cpu_caches_040(uae_u16 opcode) @@ -220,18 +202,12 @@ void flush_cpu_caches_040(uae_u16 opcode) int cache = (opcode >> 6) & 3; int scope = (opcode >> 3) & 3; - for (int k = 0; k < 2; k++) - { - if (cache & (1 << k)) - { - if (scope == 3) - { + for (int k = 0; k < 2; k++) { + if (cache & (1 << k)) { + if (scope == 3) { // all - if (!k) - { - } - else - { + if (!k) { + } else { // instruction flush_cpu_caches(true); } @@ -240,70 +216,59 @@ void flush_cpu_caches_040(uae_u16 opcode) } } -void set_cpu_caches(bool flush) +void set_cpu_caches (bool flush) { #ifdef JIT - if (currprefs.cachesize) - { - if (currprefs.cpu_model < 68040) - { - set_cache_state(regs.cacr & 1); - if (regs.cacr & 0x08) - { - flush_icache(3); + if (currprefs.cachesize) { + if (currprefs.cpu_model < 68040) { + set_cache_state (regs.cacr & 1); + if (regs.cacr & 0x08) { + flush_icache (3); } - } - else - { - set_cache_state((regs.cacr & 0x8000) ? 1 : 0); + } else { + set_cache_state ((regs.cacr & 0x8000) ? 1 : 0); } } #endif flush_cpu_caches(flush); } -static uae_u32 REGPARAM2 op_illg_1(uae_u32 opcode) +static uae_u32 REGPARAM2 op_illg_1 (uae_u32 opcode) { - op_illg(opcode); + op_illg (opcode); return 4; } // generic+direct, generic+direct+jit, more compatible -static const struct cputbl* cputbls[5][3] = +static const struct cputbl *cputbls[5][3] = { // 68000 {op_smalltbl_5_ff, op_smalltbl_45_ff, op_smalltbl_12_ff}, // 68010 {op_smalltbl_4_ff, op_smalltbl_44_ff, op_smalltbl_11_ff}, // 68020 - {op_smalltbl_3_ff, op_smalltbl_43_ff, nullptr}, + { op_smalltbl_3_ff, op_smalltbl_43_ff, NULL }, // 68030 - {op_smalltbl_2_ff, op_smalltbl_42_ff, nullptr}, + { op_smalltbl_2_ff, op_smalltbl_42_ff, NULL }, // 68040 - {op_smalltbl_1_ff, op_smalltbl_41_ff, nullptr}, + { op_smalltbl_1_ff, op_smalltbl_41_ff, NULL }, }; -static void build_cpufunctbl(void) +static void build_cpufunctbl (void) { - int i; - unsigned long opcode; - const struct cputbl* tbl = nullptr; + int i; + uae_u32 opcode; + const struct cputbl *tbl = NULL; int lvl, mode; - if (!currprefs.cachesize) - { - if (currprefs.cpu_compatible && currprefs.cpu_model < 68020) - { + if (!currprefs.cachesize) { + if (currprefs.cpu_compatible && currprefs.cpu_model < 68020) { mode = 2; - } - else - { + } else { mode = 0; } m68k_pc_indirect = mode != 0 ? 1 : 0; - } - else - { + } else { mode = 1; m68k_pc_indirect = 0; } @@ -312,161 +277,138 @@ static void build_cpufunctbl(void) lvl = 4; tbl = cputbls[lvl][mode]; - if (tbl == nullptr) - { - write_log(_T("no CPU emulation cores available CPU=%d!"), currprefs.cpu_model); - abort(); - } + if (tbl == NULL) { + write_log (_T("no CPU emulation cores available CPU=%d!"), currprefs.cpu_model); + abort (); + } - for (opcode = 0; opcode < 65536; opcode++) - cpufunctbl[opcode] = op_illg_1; - for (i = 0; tbl[i].handler != nullptr; i++) - { - opcode = tbl[i].opcode; - cpufunctbl[opcode] = tbl[i].handler; + for (opcode = 0; opcode < 65536; opcode++) + cpufunctbl[opcode] = op_illg_1; + for (i = 0; tbl[i].handler != NULL; i++) { + opcode = tbl[i].opcode; + cpufunctbl[opcode] = tbl[i].handler; cpudatatbl[opcode].length = tbl[i].length; cpudatatbl[opcode].disp020[0] = tbl[i].disp020[0]; cpudatatbl[opcode].disp020[1] = tbl[i].disp020[1]; cpudatatbl[opcode].branch = tbl[i].branch; - } + } - /* hack fpu to 68000/68010 mode */ - if (currprefs.fpu_model && currprefs.cpu_model < 68020) - { - tbl = op_smalltbl_3_ff; - for (i = 0; tbl[i].handler != nullptr; i++) - { - if ((tbl[i].opcode & 0xfe00) == 0xf200) - { - cpufunctbl[tbl[i].opcode] = tbl[i].handler; + /* hack fpu to 68000/68010 mode */ + if (currprefs.fpu_model && currprefs.cpu_model < 68020) { + tbl = op_smalltbl_3_ff; + for (i = 0; tbl[i].handler != NULL; i++) { + if ((tbl[i].opcode & 0xfe00) == 0xf200) { + cpufunctbl[tbl[i].opcode] = tbl[i].handler; cpudatatbl[tbl[i].opcode].length = tbl[i].length; cpudatatbl[tbl[i].opcode].disp020[0] = tbl[i].disp020[0]; cpudatatbl[tbl[i].opcode].disp020[1] = tbl[i].disp020[1]; cpudatatbl[tbl[i].opcode].branch = tbl[i].branch; - } - } - } + } + } + } - for (opcode = 0; opcode < 65536; opcode++) - { - cpuop_func* f; - instr* table = &table68k[opcode]; + for (opcode = 0; opcode < 65536; opcode++) { + cpuop_func *f; + struct instr *table = &table68k[opcode]; if (table->mnemo == i_ILLG) - continue; + continue; /* unimplemented opcode? */ - if (table->unimpclev > 0 && lvl >= table->unimpclev) - { + if (table->unimpclev > 0 && lvl >= table->unimpclev) { cpufunctbl[opcode] = op_illg_1; continue; } - if (currprefs.fpu_model && currprefs.cpu_model < 68020) - { - /* more hack fpu to 68000/68010 mode */ - if (table->clev > lvl && (opcode & 0xfe00) != 0xf200) - continue; - } - else if (table->clev > lvl) - { - continue; - } + if (currprefs.fpu_model && currprefs.cpu_model < 68020) { + /* more hack fpu to 68000/68010 mode */ + if (table->clev > lvl && (opcode & 0xfe00) != 0xf200) + continue; + } else if (table->clev > lvl) { + continue; + } - if (table->handler != -1) - { - int idx = table->handler; - f = cpufunctbl[idx]; - if (f == op_illg_1) - abort(); - cpufunctbl[opcode] = f; + if (table->handler != -1) { + int idx = table->handler; + f = cpufunctbl[idx]; + if (f == op_illg_1) + abort(); + cpufunctbl[opcode] = f; memcpy(&cpudatatbl[opcode], &cpudatatbl[idx], sizeof(struct cputbl_data)); - } - } + } + } #ifdef JIT - write_log(_T("JIT: &countdown = %p\n"), &countdown); - write_log(_T("JIT: &build_comp = %p\n"), &build_comp); - build_comp(); + build_comp (); #endif write_log(_T("CPU=%d, FPU=%d%s, JIT%s=%d."), currprefs.cpu_model, currprefs.fpu_model, currprefs.fpu_model ? _T(" (host)") : _T(""), currprefs.cachesize ? (currprefs.compfpu ? _T("=CPU/FPU") : _T("=CPU")) : _T(""), - currprefs.cachesize); + currprefs.cachesize); - regs.address_space_mask = 0xffffffff; - if (currprefs.cpu_compatible) - { - if (currprefs.address_space_24 && currprefs.cpu_model >= 68040) - currprefs.address_space_24 = false; - } + regs.address_space_mask = 0xffffffff; + if (currprefs.cpu_compatible) { + if (currprefs.address_space_24 && currprefs.cpu_model >= 68040) + currprefs.address_space_24 = false; + } - if (currprefs.cpu_compatible) - { - write_log(_T(" prefetch")); - } + if (currprefs.cpu_compatible) { + write_log (_T(" prefetch")); + } if (currprefs.m68k_speed < 0) - write_log(_T(" fast")); - if (currprefs.fpu_no_unimplemented && currprefs.fpu_model) - { + write_log(_T(" fast")); + if (currprefs.fpu_no_unimplemented && currprefs.fpu_model) { write_log(_T(" no unimplemented floating point instructions")); } - if (currprefs.address_space_24) - { - regs.address_space_mask = 0x00ffffff; - write_log(_T(" 24-bit")); - } - write_log(_T("\n")); + if (currprefs.address_space_24) { + regs.address_space_mask = 0x00ffffff; + write_log (_T(" 24-bit")); + } + write_log (_T("\n")); - set_cpu_caches(true); + set_cpu_caches (true); } -static unsigned long cycles_shift; -static unsigned long cycles_shift_2; +static uae_u32 cycles_shift; +static uae_u32 cycles_shift_2; -static void update_68k_cycles(void) +static void update_68k_cycles (void) { - cycles_shift = 0; - cycles_shift_2 = 0; - if (currprefs.m68k_speed >= 0) - { - if (currprefs.m68k_speed == M68K_SPEED_14MHZ_CYCLES) - cycles_shift = 1; - else if (currprefs.m68k_speed == M68K_SPEED_25MHZ_CYCLES) - { - if (currprefs.cpu_model >= 68040) - { - cycles_shift = 4; - } - else - { - cycles_shift = 2; - cycles_shift_2 = 5; - } - } - } + cycles_shift = 0; + cycles_shift_2 = 0; + if(currprefs.m68k_speed >= 0) { + if(currprefs.m68k_speed == M68K_SPEED_14MHZ_CYCLES) + cycles_shift = 1; + else if(currprefs.m68k_speed == M68K_SPEED_25MHZ_CYCLES) { + if(currprefs.cpu_model >= 68040) { + cycles_shift = 4; + } else { + cycles_shift = 2; + cycles_shift_2 = 5; + } + } + } - if (currprefs.m68k_speed < 0 || currprefs.cachesize > 0) - do_cycles = do_cycles_cpu_fastest; - else - do_cycles = do_cycles_cpu_norm; + if(currprefs.m68k_speed < 0 || currprefs.cachesize > 0) + do_cycles = do_cycles_cpu_fastest; + else + do_cycles = do_cycles_cpu_norm; - set_config_changed(); + set_config_changed (); } -static void prefs_changed_cpu(void) +static void prefs_changed_cpu (void) { - fixup_cpu(&changed_prefs); + fixup_cpu (&changed_prefs); check_prefs_changed_comp(false); - currprefs.cpu_model = changed_prefs.cpu_model; - currprefs.fpu_model = changed_prefs.fpu_model; - if (currprefs.cpu_compatible != changed_prefs.cpu_compatible) - { - currprefs.cpu_compatible = changed_prefs.cpu_compatible; + currprefs.cpu_model = changed_prefs.cpu_model; + currprefs.fpu_model = changed_prefs.fpu_model; + if (currprefs.cpu_compatible != changed_prefs.cpu_compatible) { + currprefs.cpu_compatible = changed_prefs.cpu_compatible; flush_cpu_caches(true); } - currprefs.address_space_24 = changed_prefs.address_space_24; + currprefs.address_space_24 = changed_prefs.address_space_24; currprefs.fpu_no_unimplemented = changed_prefs.fpu_no_unimplemented; } @@ -477,19 +419,17 @@ static int check_prefs_changed_cpu2(void) #ifdef JIT changed = check_prefs_changed_comp(true) ? 1 : 0; #endif - if (changed - || currprefs.cpu_model != changed_prefs.cpu_model - || currprefs.fpu_model != changed_prefs.fpu_model - || currprefs.fpu_no_unimplemented != changed_prefs.fpu_no_unimplemented - || currprefs.cpu_compatible != changed_prefs.cpu_compatible) - { - cpu_prefs_changed_flag |= 1; - } - if (changed - || currprefs.m68k_speed != changed_prefs.m68k_speed) - { - cpu_prefs_changed_flag |= 2; - } + if (changed + || currprefs.cpu_model != changed_prefs.cpu_model + || currprefs.fpu_model != changed_prefs.fpu_model + || currprefs.fpu_no_unimplemented != changed_prefs.fpu_no_unimplemented + || currprefs.cpu_compatible != changed_prefs.cpu_compatible) { + cpu_prefs_changed_flag |= 1; + } + if (changed + || currprefs.m68k_speed != changed_prefs.m68k_speed) { + cpu_prefs_changed_flag |= 2; + } return cpu_prefs_changed_flag; } @@ -498,65 +438,57 @@ void check_prefs_changed_cpu(void) if (!config_changed) return; - if (check_prefs_changed_cpu2()) - { - set_special(SPCFLAG_MODE_CHANGE); - reset_frame_rate_hack(); + if (check_prefs_changed_cpu2()) { + set_special (SPCFLAG_MODE_CHANGE); + reset_frame_rate_hack (); } } -void init_m68k(void) +void init_m68k (void) { - prefs_changed_cpu(); - update_68k_cycles(); + prefs_changed_cpu (); + update_68k_cycles (); - for (int i = 0; i < 256; i++) - { - int j; - for (j = 0; j < 8; j++) - { - if (i & (1 << j)) break; - } - movem_index1[i] = j; - movem_index2[i] = 7 - j; - movem_next[i] = i & (~(1 << j)); - } + for (int i = 0 ; i < 256 ; i++) { + int j; + for (j = 0 ; j < 8 ; j++) { + if (i & (1 << j)) break; + } + movem_index1[i] = j; + movem_index2[i] = 7-j; + movem_next[i] = i & (~(1 << j)); + } #if COUNT_INSTRS - memset(instrcount, 0, sizeof instrcount); + memset (instrcount, 0, sizeof instrcount); #endif - read_table68k(); - do_merges(); + read_table68k (); + do_merges (); - build_cpufunctbl(); - set_x_funcs(); - set_speedup_values(); + build_cpufunctbl (); + set_x_funcs (); + set_speedup_values(); } struct regstruct regs; -int get_cpu_model(void) +STATIC_INLINE int in_rom (uaecptr pc) { - return currprefs.cpu_model; + return (munge24 (pc) & 0xFFF80000) == 0xF80000; } -STATIC_INLINE int in_rom(uaecptr pc) +STATIC_INLINE int in_rtarea (uaecptr pc) { - return (munge24(pc) & 0xFFF80000) == 0xF80000; + return (munge24 (pc) & 0xFFFF0000) == rtarea_base && (uae_boot_rom_type || currprefs.uaeboard > 0); } -STATIC_INLINE int in_rtarea(uaecptr pc) +STATIC_INLINE uae_u32 adjust_cycles(uae_u32 cycles) { - return (munge24(pc) & 0xFFFF0000) == rtarea_base && (uae_boot_rom_type || currprefs.uaeboard > 0); -} - -STATIC_INLINE unsigned long adjust_cycles(unsigned long cycles) -{ - unsigned long res = cycles >> cycles_shift; - if (cycles_shift_2) - return res + (cycles >> cycles_shift_2); - return res; + uae_u32 res = cycles >> cycles_shift; + if(cycles_shift_2) + return res + (cycles >> cycles_shift_2); + return res; } static void m68k_set_stop(void) @@ -575,8 +507,8 @@ static void m68k_unset_stop(void) static void activate_trace(void) { - unset_special(SPCFLAG_TRACE); - set_special(SPCFLAG_DOTRACE); + unset_special (SPCFLAG_TRACE); + set_special (SPCFLAG_DOTRACE); } // make sure interrupt is checked immediately after current instruction @@ -587,103 +519,84 @@ static void doint_imm(void) set_special(SPCFLAG_INT); } -void REGPARAM2 MakeSR(void) +void REGPARAM2 MakeSR (void) { - regs.sr = ((regs.t1 << 15) | (regs.t0 << 14) - | (regs.s << 13) | (regs.m << 12) | (regs.intmask << 8) - | (GET_XFLG() << 4) | (GET_NFLG() << 3) - | (GET_ZFLG() << 2) | (GET_VFLG() << 1) - | GET_CFLG()); + regs.sr = ((regs.t1 << 15) | (regs.t0 << 14) + | (regs.s << 13) | (regs.m << 12) | (regs.intmask << 8) + | (GET_XFLG() << 4) | (GET_NFLG() << 3) + | (GET_ZFLG() << 2) | (GET_VFLG() << 1) + | GET_CFLG()); } STATIC_INLINE void MakeFromSR_x(int t0trace) { - int oldm = regs.m; - int olds = regs.s; + int oldm = regs.m; + int olds = regs.s; int oldt0 = regs.t0; int oldt1 = regs.t1; - SET_XFLG((regs.sr >> 4) & 1); - SET_NFLG((regs.sr >> 3) & 1); - SET_ZFLG((regs.sr >> 2) & 1); - SET_VFLG((regs.sr >> 1) & 1); - SET_CFLG(regs.sr & 1); - if (regs.t1 == ((regs.sr >> 15) & 1) && - regs.t0 == ((regs.sr >> 14) & 1) && - regs.s == ((regs.sr >> 13) & 1) && - regs.m == ((regs.sr >> 12) & 1) && - regs.intmask == ((regs.sr >> 8) & 7)) - return; - regs.t1 = (regs.sr >> 15) & 1; - regs.t0 = (regs.sr >> 14) & 1; - regs.s = (regs.sr >> 13) & 1; - regs.m = (regs.sr >> 12) & 1; - regs.intmask = (regs.sr >> 8) & 7; - if (currprefs.cpu_model >= 68020) - { - if (olds != regs.s) - { - if (olds) - { - if (oldm) - regs.msp = m68k_areg(regs, 7); - else - regs.isp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.usp; - } - else - { - regs.usp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.m ? regs.msp : regs.isp; - } - } - else if (olds && oldm != regs.m) - { - if (oldm) - { - regs.msp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.isp; - } - else - { - regs.isp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.msp; - } - } - } - else - { - regs.t0 = regs.m = 0; - if (olds != regs.s) - { - if (olds) - { - regs.isp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.usp; - } - else - { - regs.usp = m68k_areg(regs, 7); - m68k_areg(regs, 7) = regs.isp; - } - } - } + SET_XFLG ((regs.sr >> 4) & 1); + SET_NFLG ((regs.sr >> 3) & 1); + SET_ZFLG ((regs.sr >> 2) & 1); + SET_VFLG ((regs.sr >> 1) & 1); + SET_CFLG (regs.sr & 1); + if (regs.t1 == ((regs.sr >> 15) & 1) && + regs.t0 == ((regs.sr >> 14) & 1) && + regs.s == ((regs.sr >> 13) & 1) && + regs.m == ((regs.sr >> 12) & 1) && + regs.intmask == ((regs.sr >> 8) & 7)) + return; + regs.t1 = (regs.sr >> 15) & 1; + regs.t0 = (regs.sr >> 14) & 1; + regs.s = (regs.sr >> 13) & 1; + regs.m = (regs.sr >> 12) & 1; + regs.intmask = (regs.sr >> 8) & 7; + + if (currprefs.cpu_model >= 68020) { + if (olds != regs.s) { + if (olds) { + if (oldm) + regs.msp = m68k_areg(regs, 7); + else + regs.isp = m68k_areg(regs, 7); + m68k_areg(regs, 7) = regs.usp; + } else { + regs.usp = m68k_areg(regs, 7); + m68k_areg(regs, 7) = regs.m ? regs.msp : regs.isp; + } + } else if (olds && oldm != regs.m) { + if (oldm) { + regs.msp = m68k_areg (regs, 7); + m68k_areg (regs, 7) = regs.isp; + } else { + regs.isp = m68k_areg (regs, 7); + m68k_areg (regs, 7) = regs.msp; + } + } + } else { + regs.t0 = regs.m = 0; + if (olds != regs.s) { + if (olds) { + regs.isp = m68k_areg (regs, 7); + m68k_areg (regs, 7) = regs.usp; + } else { + regs.usp = m68k_areg (regs, 7); + m68k_areg (regs, 7) = regs.isp; + } + } + } - doint_imm(); - if (regs.t1 || regs.t0) - { - set_special(SPCFLAG_TRACE); - } - else - { - /* Keep SPCFLAG_DOTRACE, we still want a trace exception for -SR-modifying instructions (including STOP). */ - unset_special(SPCFLAG_TRACE); - } + doint_imm(); + if (regs.t1 || regs.t0) { + set_special (SPCFLAG_TRACE); + } else { + /* Keep SPCFLAG_DOTRACE, we still want a trace exception for + SR-modifying instructions (including STOP). */ + unset_special (SPCFLAG_TRACE); + } // Stop SR-modification does not generate T0 // If this SR modification set Tx bit, no trace until next instruction. - if ((oldt0 && t0trace && currprefs.cpu_model >= 68020) || oldt1) - { + if ((oldt0 && t0trace && currprefs.cpu_model >= 68020) || oldt1) { // Always trace if Tx bits were already set, even if this SR modification cleared them. activate_trace(); } @@ -693,24 +606,22 @@ void REGPARAM2 MakeFromSR_T0(void) { MakeFromSR_x(1); } - void REGPARAM2 MakeFromSR(void) { MakeFromSR_x(0); } -static void exception_check_trace(int nr) +static void exception_check_trace (int nr) { - unset_special(SPCFLAG_TRACE | SPCFLAG_DOTRACE); - if (regs.t1 && !regs.t0) - { - /* trace stays pending if exception is div by zero, chk, -* trapv or trap #x -*/ - if (nr == 5 || nr == 6 || nr == 7 || (nr >= 32 && nr <= 47)) - set_special(SPCFLAG_DOTRACE); - } - regs.t1 = regs.t0 = 0; + unset_special (SPCFLAG_TRACE | SPCFLAG_DOTRACE); + if (regs.t1 && !regs.t0) { + /* trace stays pending if exception is div by zero, chk, + * trapv or trap #x + */ + if (nr == 5 || nr == 6 || nr == 7 || (nr >= 32 && nr <= 47)) + set_special (SPCFLAG_DOTRACE); + } + regs.t1 = regs.t0 = 0; } static int iack_cycle(int nr) @@ -722,179 +633,68 @@ static int iack_cycle(int nr) return vector; } -static uae_u32 exception_pc(int nr) -{ - // bus error, address error, illegal instruction, privilege violation, a-line, f-line - if (nr == 2 || nr == 3 || nr == 4 || nr == 8 || nr == 10 || nr == 11) - return regs.instruction_pc; - return m68k_getpc(); -} - static void add_approximate_exception_cycles(int nr) { int cycles; - if (currprefs.cpu_model > 68000) - { - // 68020 exceptions - if (nr >= 24 && nr <= 31) - { - /* Interrupts */ - cycles = 26 * CYCLE_UNIT / 2; - } - else if (nr >= 32 && nr <= 47) - { - /* Trap */ - cycles = 20 * CYCLE_UNIT / 2; - } - else - { - switch (nr) - { - case 2: cycles = 43 * CYCLE_UNIT / 2; - break; /* Bus error */ - case 3: cycles = 43 * CYCLE_UNIT / 2; - break; /* Address error ??? */ - case 4: cycles = 20 * CYCLE_UNIT / 2; - break; /* Illegal instruction */ - case 5: cycles = 32 * CYCLE_UNIT / 2; - break; /* Division by zero */ - case 6: cycles = 32 * CYCLE_UNIT / 2; - break; /* CHK */ - case 7: cycles = 32 * CYCLE_UNIT / 2; - break; /* TRAPV */ - case 8: cycles = 20 * CYCLE_UNIT / 2; - break; /* Privilege violation */ - case 9: cycles = 25 * CYCLE_UNIT / 2; - break; /* Trace */ - case 10: cycles = 20 * CYCLE_UNIT / 2; - break; /* Line-A */ - case 11: cycles = 20 * CYCLE_UNIT / 2; - break; /* Line-F */ - default: - cycles = 4 * CYCLE_UNIT / 2; - break; - } - } - } - else - { - // 68000 exceptions - if (nr >= 24 && nr <= 31) - { - /* Interrupts */ - cycles = (44 + 4) * CYCLE_UNIT / 2; - } - else if (nr >= 32 && nr <= 47) - { - /* Trap (total is 34, but cpuemux.c already adds 4) */ - cycles = (34 - 4) * CYCLE_UNIT / 2; - } - else - { - switch (nr) - { - case 2: cycles = 50 * CYCLE_UNIT / 2; - break; /* Bus error */ - case 3: cycles = 50 * CYCLE_UNIT / 2; - break; /* Address error */ - case 4: cycles = 34 * CYCLE_UNIT / 2; - break; /* Illegal instruction */ - case 5: cycles = 38 * CYCLE_UNIT / 2; - break; /* Division by zero */ - case 6: cycles = 40 * CYCLE_UNIT / 2; - break; /* CHK */ - case 7: cycles = 34 * CYCLE_UNIT / 2; - break; /* TRAPV */ - case 8: cycles = 34 * CYCLE_UNIT / 2; - break; /* Privilege violation */ - case 9: cycles = 34 * CYCLE_UNIT / 2; - break; /* Trace */ - case 10: cycles = 34 * CYCLE_UNIT / 2; - break; /* Line-A */ - case 11: cycles = 34 * CYCLE_UNIT / 2; - break; /* Line-F */ - default: - cycles = 4 * CYCLE_UNIT / 2; - break; - } - } - } + if (currprefs.cpu_model > 68000) { + // 68020 exceptions + if (nr >= 24 && nr <= 31) { + /* Interrupts */ + cycles = 26 * CYCLE_UNIT / 2; + } else if (nr >= 32 && nr <= 47) { + /* Trap */ + cycles = 20 * CYCLE_UNIT / 2; + } else { + switch (nr) + { + case 2: cycles = 43 * CYCLE_UNIT / 2; break; /* Bus error */ + case 3: cycles = 43 * CYCLE_UNIT / 2; break; /* Address error ??? */ + case 4: cycles = 20 * CYCLE_UNIT / 2; break; /* Illegal instruction */ + case 5: cycles = 32 * CYCLE_UNIT / 2; break; /* Division by zero */ + case 6: cycles = 32 * CYCLE_UNIT / 2; break; /* CHK */ + case 7: cycles = 32 * CYCLE_UNIT / 2; break; /* TRAPV */ + case 8: cycles = 20 * CYCLE_UNIT / 2; break; /* Privilege violation */ + case 9: cycles = 25 * CYCLE_UNIT / 2; break; /* Trace */ + case 10: cycles = 20 * CYCLE_UNIT / 2; break; /* Line-A */ + case 11: cycles = 20 * CYCLE_UNIT / 2; break; /* Line-F */ + default: + cycles = 4 * CYCLE_UNIT / 2; + break; + } + } + } else { + // 68000 exceptions + if (nr >= 24 && nr <= 31) { + /* Interrupts */ + cycles = (44 + 4) * CYCLE_UNIT / 2; + } else if (nr >= 32 && nr <= 47) { + /* Trap (total is 34, but cpuemux.c already adds 4) */ + cycles = (34 - 4) * CYCLE_UNIT / 2; + } else { + switch (nr) + { + case 2: cycles = 50 * CYCLE_UNIT / 2; break; /* Bus error */ + case 3: cycles = 50 * CYCLE_UNIT / 2; break; /* Address error */ + case 4: cycles = 34 * CYCLE_UNIT / 2; break; /* Illegal instruction */ + case 5: cycles = 38 * CYCLE_UNIT / 2; break; /* Division by zero */ + case 6: cycles = 40 * CYCLE_UNIT / 2; break; /* CHK */ + case 7: cycles = 34 * CYCLE_UNIT / 2; break; /* TRAPV */ + case 8: cycles = 34 * CYCLE_UNIT / 2; break; /* Privilege violation */ + case 9: cycles = 34 * CYCLE_UNIT / 2; break; /* Trace */ + case 10: cycles = 34 * CYCLE_UNIT / 2; break; /* Line-A */ + case 11: cycles = 34 * CYCLE_UNIT / 2; break; /* Line-F */ + default: + cycles = 4 * CYCLE_UNIT / 2; + break; + } + } + } cycles = adjust_cycles(cycles); x_do_cycles(cycles); } -static void Exception_build_stack_frame(uae_u32 oldpc, uae_u32 currpc, uae_u32 ssw, int nr, int format) -{ - switch (format) - { - case 0x0: // four word stack frame - break; - case 0x2: // six word stack frame - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), oldpc); - break; - case 0x3: // floating point post-instruction stack frame (68040) - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), regs.fp_ea); - break; - case 0x4: // floating point unimplemented stack frame (68LC040, 68EC040) - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), ssw); - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), oldpc); - break; - default: - write_log(_T("Unknown exception stack frame format: %X\n"), format); - return; - } - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), (format << 12) | (nr * 4)); - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), currpc); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), regs.sr); -} - -static void Exception_build_stack_frame_common(uae_u32 oldpc, uae_u32 currpc, int nr) -{ - if (nr == 5 || nr == 6 || nr == 7 || nr == 9) - { - Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x2); - } - else if (nr == 60 || nr == 61) - { - Exception_build_stack_frame(oldpc, regs.instruction_pc, 0, nr, 0x0); - } - else if (nr >= 48 && nr <= 55) - { - if (regs.fpu_exp_pre) - { - Exception_build_stack_frame(oldpc, regs.instruction_pc, 0, nr, 0x0); - } - else - { - /* post-instruction */ - Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x3); - } - } - else if (nr == 11 && regs.fp_unimp_ins) - { - regs.fp_unimp_ins = false; - if (currprefs.cpu_model == 68040 && currprefs.fpu_model == 0) - { - Exception_build_stack_frame(regs.fp_ea, currpc, regs.instruction_pc, nr, 0x4); - } - else - { - Exception_build_stack_frame(regs.fp_ea, currpc, 0, nr, 0x2); - } - } - else - { - Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x0); - } -} +static void exception3_notinstruction(uae_u32 opcode, uaecptr addr); void Exception(int nr) { @@ -917,41 +717,33 @@ void Exception(int nr) MakeSR(); - if (!regs.s) - { + if (!regs.s) { regs.usp = m68k_areg(regs, 7); - if (currprefs.cpu_model >= 68020) - { + if (currprefs.cpu_model >= 68020) { m68k_areg(regs, 7) = regs.m ? regs.msp : regs.isp; - } - else - { + } else { m68k_areg(regs, 7) = regs.isp; } regs.s = 1; } - if ((m68k_areg(regs, 7) & 1) && currprefs.cpu_model < 68020) - { + if ((m68k_areg(regs, 7) & 1) && currprefs.cpu_model < 68020) { if (nr == 2 || nr == 3) cpu_halt(CPU_HALT_DOUBLE_FAULT); else exception3_notinstruction(regs.ir, m68k_areg(regs, 7)); return; } - if ((nr == 2 || nr == 3) && exception_in_exception < 0) - { + if ((nr == 2 || nr == 3) && exception_in_exception < 0) { cpu_halt(CPU_HALT_DOUBLE_FAULT); return; } - if (!currprefs.cpu_compatible) - { + if (!currprefs.cpu_compatible) { addrbank* ab = &get_mem_bank(m68k_areg(regs, 7) - 4); // Not plain RAM check because some CPU type tests that // don't need to return set stack to ROM.. - if (!ab || ab == &dummy_bank || (ab->flags & ABFLAG_IO)) - { + if (!ab || ab == &dummy_bank || (ab->flags & ABFLAG_IO)) { cpu_halt(CPU_HALT_SSP_IN_NON_EXISTING_ADDRESS); return; } @@ -960,20 +752,15 @@ void Exception(int nr) bool used_exception_build_stack_frame = false; add_approximate_exception_cycles(nr); - if (currprefs.cpu_model > 68000) - { + if (currprefs.cpu_model > 68000) { uae_u32 oldpc = regs.instruction_pc; nextpc = exception_pc(nr); - if (nr == 2 || nr == 3) - { + if (nr == 2 || nr == 3) { int i; - if (currprefs.cpu_model >= 68040) - { - if (nr == 2) - { + if (currprefs.cpu_model >= 68040) { + if (nr == 2) { // 68040 bus error (not really, some garbage?) - for (i = 0; i < 18; i++) - { + for (i = 0 ; i < 18 ; i++) { m68k_areg(regs, 7) -= 2; x_put_word(m68k_areg(regs, 7), 0); } @@ -996,40 +783,28 @@ void Exception(int nr) m68k_areg(regs, 7) -= 2; x_put_word(m68k_areg(regs, 7), regs.sr); goto kludge_me_do; - } - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), last_fault_for_exception_3); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0x2000 + vector_nr * 4); + + } else { + // 68040/060 odd PC address error + Exception_build_stack_frame(last_fault_for_exception_3, currpc, 0, nr, 0x02); + used_exception_build_stack_frame = true; } - else - { - // 68020 address error + } else if (currprefs.cpu_model >= 68020) { + // 68020/030 odd PC address error (partially implemented only) uae_u16 ssw = (sv ? 4 : 0) | (last_instructionaccess_for_exception_3 ? 2 : 1); ssw |= last_writeaccess_for_exception_3 ? 0 : 0x40; ssw |= 0x20; - for (i = 0; i < 36; i++) - { - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0); - } - m68k_areg(regs, 7) -= 4; - x_put_long(m68k_areg(regs, 7), last_fault_for_exception_3); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), ssw); - m68k_areg(regs, 7) -= 2; - x_put_word(m68k_areg(regs, 7), 0xb000 + vector_nr * 4); - } + Exception_build_stack_frame(oldpc, currpc, ssw, nr, 0x0a); + used_exception_build_stack_frame = true; + } else { + // 68010 address error (partially implemented only) + uae_u16 ssw = (sv ? 4 : 0) | (last_instructionaccess_for_exception_3 ? 2 : 1); + ssw |= last_writeaccess_for_exception_3 ? 0 : 0x100; + ssw |= last_instructionaccess_for_exception_3 ? 0 : 0x2000; + Exception_build_stack_frame(oldpc, currpc, ssw, nr, 0x08); + used_exception_build_stack_frame = true; } - else if (regs.m && interrupt) - { - /* M + Interrupt */ + } else if (regs.m && interrupt) { /* M + Interrupt */ m68k_areg(regs, 7) -= 2; x_put_word(m68k_areg(regs, 7), vector_nr * 4); m68k_areg(regs, 7) -= 4; @@ -1042,36 +817,27 @@ void Exception(int nr) m68k_areg(regs, 7) = regs.isp; m68k_areg(regs, 7) -= 2; x_put_word(m68k_areg(regs, 7), 0x1000 + vector_nr * 4); - } - else - { + } else { Exception_build_stack_frame_common(oldpc, currpc, nr); used_exception_build_stack_frame = true; } - } - else - { + } else { nextpc = m68k_getpc(); - if (nr == 2 || nr == 3) - { - // 68000 address error + if (nr == 2 || nr == 3) { + // 68000 bus error/address error uae_u16 mode = (sv ? 4 : 0) | (last_instructionaccess_for_exception_3 ? 2 : 1); mode |= last_writeaccess_for_exception_3 ? 0 : 16; mode |= last_notinstruction_for_exception_3 ? 8 : 0; - // undocumented bits seem to contain opcode - mode |= last_op_for_exception_3 & ~31; - m68k_areg(regs, 7) -= 14; + uae_u16 statusormask = (last_op_for_exception_3 >> 16) & 0xff; + uae_u16 statusandmask = (last_op_for_exception_3 >> 24) & 0xff; + mode |= statusormask; + mode &= ~statusandmask; exception_in_exception = -1; - x_put_word(m68k_areg(regs, 7) + 0, mode); - x_put_long(m68k_areg(regs, 7) + 2, last_fault_for_exception_3); - x_put_word(m68k_areg(regs, 7) + 6, last_op_for_exception_3); - x_put_word(m68k_areg(regs, 7) + 8, regs.sr); - x_put_long(m68k_areg(regs, 7) + 10, last_addr_for_exception_3); + Exception_build_68000_address_error_stack_frame(mode, last_op_for_exception_3, last_fault_for_exception_3, last_addr_for_exception_3); goto kludge_me_do; } } - if (!used_exception_build_stack_frame) - { + if (!used_exception_build_stack_frame) { m68k_areg(regs, 7) -= 4; x_put_long(m68k_areg(regs, 7), nextpc); m68k_areg(regs, 7) -= 2; @@ -1080,8 +846,7 @@ void Exception(int nr) kludge_me_do: newpc = x_get_long(regs.vbr + 4 * vector_nr); exception_in_exception = 0; - if (newpc & 1) - { + if (newpc & 1) { if (nr == 2 || nr == 3) cpu_halt(CPU_HALT_DOUBLE_FAULT); else @@ -1103,30 +868,25 @@ void REGPARAM2 Exception_cpu(int nr) bool t0 = currprefs.cpu_model >= 68020 && regs.t0; Exception(nr); // check T0 trace - if (t0) - { + if (t0) { activate_trace(); } } static void bus_error(void) { - TRY(prb2) - { + TRY (prb2) { Exception(2); - } CATCH(prb2) - { + } CATCH (prb2) { cpu_halt(CPU_HALT_BUS_ERROR_DOUBLE_FAULT); - } - ENDTRY + } ENDTRY } static void do_interrupt(int nr) { m68k_unset_stop(); - for (;;) - { + for (;;) { Exception(nr + 24); if (!currprefs.cpu_compatible) break; @@ -1176,13 +936,13 @@ static void m68k_reset(bool hardreset) regs.spcflags = 0; #ifdef SAVESTATE - if (isrestore()) - { + if (isrestore ()) { m68k_reset_sr(); m68k_setpc_normal(regs.pc); return; - } + } else { set_special(SPCFLAG_CHECK); + } #endif regs.s = 1; v = get_long(4); @@ -1207,29 +967,27 @@ static void m68k_reset(bool hardreset) regs.caar = regs.cacr = 0; regs.itt0 = regs.itt1 = regs.dtt0 = regs.dtt1 = 0; regs.tcr = regs.mmusr = regs.urp = regs.srp = regs.buscr = 0; - if (currprefs.cpu_model == 68020) - { + if (currprefs.cpu_model == 68020) { regs.cacr |= 8; set_cpu_caches(false); } mmufixup[0].reg = -1; - if (currprefs.cpu_model >= 68040) - { + if (currprefs.cpu_model >= 68040) { set_cpu_caches(false); } /* only (E)nable bit is zeroed when CPU is reset, A3000 SuperKickstart expects this */ fake_tc_030 &= ~0x80000000; fake_tt0_030 &= ~0x80000000; fake_tt1_030 &= ~0x80000000; - if (hardreset || regs.halted) - { + if (hardreset || regs.halted) { fake_srp_030 = fake_crp_030 = 0; fake_tt0_030 = fake_tt1_030 = fake_tc_030 = 0; } fake_mmusr_030 = 0; regs.pcr = 0; + fill_prefetch(); } @@ -1239,42 +997,36 @@ uae_u32 REGPARAM2 op_illg(uae_u32 opcode) int inrom = in_rom(pc); int inrt = in_rtarea(pc); - if ((opcode == 0x4afc || opcode == 0xfc4a) && !valid_address(pc, 4) && valid_address(pc - 4, 4)) - { + if ((opcode == 0x4afc || opcode == 0xfc4a) && !valid_address(pc, 4) && valid_address(pc - 4, 4)) { // PC fell off the end of RAM bus_error(); return 4; } - if (cloanto_rom && (opcode & 0xF100) == 0x7100) - { + if (cloanto_rom && (opcode & 0xF100) == 0x7100) { m68k_dreg(regs, (opcode >> 9) & 7) = (uae_s8)(opcode & 0xFF); m68k_incpc_normal(2); fill_prefetch(); return 4; } - if (opcode == 0x4E7B && inrom) - { - if (get_long(0x10) == 0) - { + if (opcode == 0x4E7B && inrom) { + if (get_long (0x10) == 0) { notify_user(NUMSG_KS68020); - uae_restart(-1, nullptr); + uae_restart (-1, NULL); m68k_setstopped(); return 4; } } #ifdef AUTOCONFIG - if (opcode == 0xFF0D && inrt) - { + if (opcode == 0xFF0D && inrt) { /* User-mode STOP replacement */ m68k_setstopped(); return 4; } - if ((opcode & 0xF000) == 0xA000 && inrt) - { + if ((opcode & 0xF000) == 0xA000 && inrt) { /* Calltrap. */ m68k_incpc_normal(2); m68k_handle_trap(opcode & 0xFFF); @@ -1283,13 +1035,11 @@ uae_u32 REGPARAM2 op_illg(uae_u32 opcode) } #endif - if ((opcode & 0xF000) == 0xF000) - { + if ((opcode & 0xF000) == 0xF000) { Exception(0xB); return 4; } - if ((opcode & 0xF000) == 0xA000) - { + if ((opcode & 0xF000) == 0xA000) { Exception(0xA); return 4; } @@ -1306,7 +1056,7 @@ static bool mmu_op30_invea(uae_u32 opcode) int rreg = opcode & 7; // Dn, An, (An)+, -(An), immediate and PC-relative not allowed - if (eamode == 0 || eamode == 1 || eamode == 3 || eamode == 4 || eamode == 6 || (eamode == 7 && rreg > 1)) + if (eamode == 0 || eamode == 1 || eamode == 3 || eamode == 4 || (eamode == 7 && rreg > 1)) return true; return false; } @@ -1317,7 +1067,7 @@ static bool mmu_op30fake_pmove(uaecptr pc, uae_u32 opcode, uae_u16 next, uaecptr int rw = (next >> 9) & 1; int fd = (next >> 8) & 1; int unused = (next & 0xff); - const TCHAR* reg = nullptr; + const TCHAR *reg = NULL; uae_u32 otc = fake_tc_030; int siz; @@ -1343,13 +1093,10 @@ static bool mmu_op30fake_pmove(uaecptr pc, uae_u32 opcode, uae_u16 next, uaecptr case 0x12: // SRP reg = _T("SRP"); siz = 8; - if (rw) - { + if (rw) { x_put_long(extra, fake_srp_030 >> 32); x_put_long(extra + 4, (uae_u32)fake_srp_030); - } - else - { + } else { fake_srp_030 = (uae_u64)x_get_long(extra) << 32; fake_srp_030 |= x_get_long(extra + 4); } @@ -1357,20 +1104,16 @@ static bool mmu_op30fake_pmove(uaecptr pc, uae_u32 opcode, uae_u16 next, uaecptr case 0x13: // CRP reg = _T("CRP"); siz = 8; - if (rw) - { + if (rw) { x_put_long(extra, fake_crp_030 >> 32); x_put_long(extra + 4, (uae_u32)fake_crp_030); - } - else - { + } else { fake_crp_030 = (uae_u64)x_get_long(extra) << 32; fake_crp_030 |= x_get_long(extra + 4); } break; case 0x18: // MMUSR - if (fd) - { + if (fd) { // FD must be always zero when MMUSR read or write return true; } @@ -1475,8 +1218,7 @@ bool mmu_op30(uaecptr pc, uae_u32 opcode, uae_u16 extra, uaecptr extraa) fline = mmu_op30fake_ptest(pc, opcode, extra, extraa); break; } - if (fline) - { + if (fline) { m68k_setpc(pc); op_illg(opcode); } @@ -1486,20 +1228,16 @@ bool mmu_op30(uaecptr pc, uae_u32 opcode, uae_u16 extra, uaecptr extraa) /* check if an address matches a ttr */ static int fake_mmu_do_match_ttr(uae_u32 ttr, uaecptr addr, bool super) { - if (ttr & MMU_TTR_BIT_ENABLED) - { - /* TTR enabled */ + if (ttr & MMU_TTR_BIT_ENABLED) { /* TTR enabled */ uae_u8 msb, mask; msb = ((addr ^ ttr) & MMU_TTR_LOGICAL_BASE) >> 24; mask = (ttr & MMU_TTR_LOGICAL_MASK) >> 16; - if (!(msb & ~mask)) - { - if ((ttr & MMU_TTR_BIT_SFIELD_ENABLED) == 0) - { - if (((ttr & MMU_TTR_BIT_SFIELD_SUPER) == 0) != (super == 0)) - { + if (!(msb & ~mask)) { + + if ((ttr & MMU_TTR_BIT_SFIELD_ENABLED) == 0) { + if (((ttr & MMU_TTR_BIT_SFIELD_SUPER) == 0) != (super == 0)) { return TTR_NO_MATCH; } } @@ -1514,14 +1252,11 @@ static int fake_mmu_match_ttr(uaecptr addr, bool super, bool data) { int res; - if (data) - { + if (data) { res = fake_mmu_do_match_ttr(regs.dtt0, addr, super); if (res == TTR_NO_MATCH) res = fake_mmu_do_match_ttr(regs.dtt1, addr, super); - } - else - { + } else { res = fake_mmu_do_match_ttr(regs.itt0, addr, super); if (res == TTR_NO_MATCH) res = fake_mmu_do_match_ttr(regs.itt1, addr, super); @@ -1532,14 +1267,11 @@ static int fake_mmu_match_ttr(uaecptr addr, bool super, bool data) // 68040+ MMU instructions only void mmu_op(uae_u32 opcode, uae_u32 extra) { - if ((opcode & 0xFE0) == 0x0500) - { + if ((opcode & 0xFE0) == 0x0500) { /* PFLUSH */ regs.mmusr = 0; return; - } - if ((opcode & 0x0FD8) == 0x0548) - { + } else if ((opcode & 0x0FD8) == 0x0548) { /* PTEST */ int regno = opcode & 7; uae_u32 addr = m68k_areg(regs, regno); @@ -1548,8 +1280,7 @@ void mmu_op(uae_u32 opcode, uae_u32 extra) bool data = (regs.dfc & 3) != 2; regs.mmusr = 0; - if (fake_mmu_match_ttr(addr, super, data) != TTR_NO_MATCH) - { + if (fake_mmu_match_ttr(addr, super, data) != TTR_NO_MATCH) { regs.mmusr = MMU_MMUSR_T | MMU_MMUSR_R; } regs.mmusr |= addr & 0xfffff000; @@ -1563,38 +1294,31 @@ void mmu_op(uae_u32 opcode, uae_u32 extra) static void do_trace(void) { - if (regs.t0 && currprefs.cpu_model >= 68020) - { + if (regs.t0 && currprefs.cpu_model >= 68020) { // this is obsolete return; } - if (regs.t1) - { + if (regs.t1) { activate_trace(); } } static void check_uae_int_request(void) { - if (uae_int_requested) - { + if (uae_int_requested) { bool irq = false; - if (uae_int_requested & 0x00ff) - { + if (uae_int_requested & 0x00ff) { INTREQ_f(0x8000 | 0x0008); irq = true; } - if (uae_int_requested & 0xff00) - { + if (uae_int_requested & 0xff00) { INTREQ_f(0x8000 | 0x2000); irq = true; } - if (uae_int_requested & 0xff0000) - { + if (uae_int_requested & 0xff0000) { atomic_and(&uae_int_requested, ~0x010000); } - if (irq) - { + if (irq) { doint(); } } @@ -1607,11 +1331,9 @@ void cpu_sleep_millis(int ms) static bool haltloop(void) { - while (regs.halted) - { + while (regs.halted) { static int prevvpos; - if (vpos == 0 && prevvpos) - { + if (vpos == 0 && prevvpos) { prevvpos = 0; cpu_sleep_millis(8); } @@ -1622,8 +1344,7 @@ static bool haltloop(void) if (regs.spcflags & SPCFLAG_COPPER) do_copper(); - if (regs.spcflags) - { + if (regs.spcflags) { if ((regs.spcflags & (SPCFLAG_BRK | SPCFLAG_MODE_CHANGE))) return true; } @@ -1640,15 +1361,15 @@ void doint(void) set_special(SPCFLAG_DOINT); } +static void m68k_resumestopped (void); + static int do_specialties(int cycles) { if (regs.spcflags & SPCFLAG_MODE_CHANGE) return 1; - if (regs.spcflags & SPCFLAG_CHECK) - { - if (regs.halted) - { + if (regs.spcflags & SPCFLAG_CHECK) { + if (regs.halted) { unset_special(SPCFLAG_CHECK); if (haltloop()) return 1; @@ -1658,8 +1379,7 @@ static int do_specialties(int cycles) #ifdef ACTION_REPLAY #ifdef ACTION_REPLAY_HRTMON - if ((regs.spcflags & SPCFLAG_ACTION_REPLAY) && hrtmon_flag != ACTION_REPLAY_INACTIVE) - { + if ((regs.spcflags & SPCFLAG_ACTION_REPLAY) && hrtmon_flag != ACTION_REPLAY_INACTIVE) { int isinhrt = (m68k_getpc() >= hrtmem_start && m68k_getpc() < hrtmem_start + hrtmem_size); /* exit from HRTMon? */ if (hrtmon_flag == ACTION_REPLAY_ACTIVE && !isinhrt) @@ -1668,24 +1388,19 @@ static int do_specialties(int cycles) hrtmon_enter(); } #endif - if ((regs.spcflags & SPCFLAG_ACTION_REPLAY) && action_replay_flag != ACTION_REPLAY_INACTIVE) - { + if ((regs.spcflags & SPCFLAG_ACTION_REPLAY) && action_replay_flag != ACTION_REPLAY_INACTIVE) { /*if (action_replay_flag == ACTION_REPLAY_ACTIVE && !is_ar_pc_in_rom ())*/ /* write_log (_T("PC:%p\n"), m68k_getpc ());*/ if (action_replay_flag == ACTION_REPLAY_ACTIVATE || action_replay_flag == ACTION_REPLAY_DORESET) action_replay_enter(); - if ((action_replay_flag == ACTION_REPLAY_HIDE || action_replay_flag == ACTION_REPLAY_ACTIVE) && ! - is_ar_pc_in_rom()) - { + if ((action_replay_flag == ACTION_REPLAY_HIDE || action_replay_flag == ACTION_REPLAY_ACTIVE) && !is_ar_pc_in_rom ()) { action_replay_hide(); unset_special(SPCFLAG_ACTION_REPLAY); } - if (action_replay_flag == ACTION_REPLAY_WAIT_PC) - { + if (action_replay_flag == ACTION_REPLAY_WAIT_PC) { /*write_log (_T("Waiting for PC: %p, current PC= %p\n"), wait_for_pc, m68k_getpc ());*/ - if (m68k_getpc() == wait_for_pc) - { + if (m68k_getpc () == wait_for_pc) { action_replay_flag = ACTION_REPLAY_ACTIVATE; /* Activate after next instruction. */ } } @@ -1699,17 +1414,13 @@ static int do_specialties(int cycles) unset_special(SPCFLAG_END_COMPILE); /* has done its job */ #endif - while ((regs.spcflags & SPCFLAG_BLTNASTY) && dmaen(DMA_BLITTER) && cycles > 0) - { + while ((regs.spcflags & SPCFLAG_BLTNASTY) && dmaen (DMA_BLITTER) && cycles > 0) { int c = blitnasty(); - if (c > 0) - { + if (c > 0) { cycles -= c * CYCLE_UNIT * 2; if (cycles < CYCLE_UNIT) cycles = 0; - } - else - { + } else { c = 4; } x_do_cycles(c * CYCLE_UNIT); @@ -1720,8 +1431,7 @@ static int do_specialties(int cycles) if (regs.spcflags & SPCFLAG_DOTRACE) Exception(9); - if ((regs.spcflags & SPCFLAG_STOP) && regs.s == 0 && currprefs.cpu_model <= 68010) - { + if ((regs.spcflags & SPCFLAG_STOP) && regs.s == 0 && currprefs.cpu_model <= 68010) { // 68000/68010 undocumented special case: // if STOP clears S-bit and T was not set: // cause privilege violation exception, PC pointing to following instruction. @@ -1731,13 +1441,8 @@ static int do_specialties(int cycles) } bool first = true; - while ((regs.spcflags & SPCFLAG_STOP) && !(regs.spcflags & SPCFLAG_BRK)) - { + while ((regs.spcflags & SPCFLAG_STOP) && !(regs.spcflags & SPCFLAG_BRK)) { check_uae_int_request(); - { - if (bsd_int_requested) - bsdsock_fake_int_handler(); - } if (!first) x_do_cycles(4 * CYCLE_UNIT); @@ -1745,16 +1450,14 @@ static int do_specialties(int cycles) if (regs.spcflags & SPCFLAG_COPPER) do_copper(); - if (regs.spcflags & (SPCFLAG_INT | SPCFLAG_DOINT)) - { + if (regs.spcflags & (SPCFLAG_INT | SPCFLAG_DOINT)) { int intr = intlev(); unset_special(SPCFLAG_INT | SPCFLAG_DOINT); if (intr > 0 && intr > regs.intmask) do_interrupt(intr); } - if (regs.spcflags & SPCFLAG_MODE_CHANGE) - { + if (regs.spcflags & SPCFLAG_MODE_CHANGE) { m68k_resumestopped(); return 1; } @@ -1763,22 +1466,19 @@ static int do_specialties(int cycles) if (regs.spcflags & SPCFLAG_TRACE) do_trace(); - if (regs.spcflags & SPCFLAG_INT) - { + if (regs.spcflags & SPCFLAG_INT) { int intr = intlev(); unset_special(SPCFLAG_INT | SPCFLAG_DOINT); if (intr > 0 && (intr > regs.intmask || intr == 7)) do_interrupt(intr); } - if (regs.spcflags & SPCFLAG_DOINT) - { + if (regs.spcflags & SPCFLAG_DOINT) { unset_special(SPCFLAG_DOINT); set_special(SPCFLAG_INT); } - if (regs.spcflags & SPCFLAG_BRK) - { + if (regs.spcflags & SPCFLAG_BRK) { unset_special(SPCFLAG_BRK); } @@ -1793,12 +1493,9 @@ static void m68k_run_1(void) struct regstruct* r = ®s; bool exit = false; - while (!exit) - { - TRY(prb) - { - while (!exit) - { + while (!exit) { + TRY (prb) { + while (!exit) { r->opcode = r->ir; #if defined (CPU_arm) && defined(USE_ARMNEON) @@ -1813,35 +1510,30 @@ static void m68k_run_1(void) r->instruction_pc = m68k_getpc(); cpu_cycles = (*cpufunctbl[r->opcode])(r->opcode); cpu_cycles = adjust_cycles(cpu_cycles); - if (r->spcflags) - { + if (r->spcflags) { if (do_specialties(cpu_cycles)) exit = true; } if (!currprefs.cpu_compatible) exit = true; } - } CATCH(prb) - { + } CATCH (prb) { bus_error(); - if (r->spcflags) - { + if (r->spcflags) { if (do_specialties(cpu_cycles)) exit = true; } - } - ENDTRY + } ENDTRY } } #ifdef JIT /* Completely different run_2 replacement */ -extern uae_u32 jit_exception; - -void execute_exception(void) +void execute_exception(uae_u32 cycles) { - Exception_cpu(jit_exception); - jit_exception = 0; + countdown -= cycles; + Exception_cpu(regs.jit_exception); + regs.jit_exception = 0; cpu_cycles = adjust_cycles(4 * CYCLE_UNIT / 2); do_cycles(cpu_cycles); // after leaving this function, we fall back to execute_normal() @@ -1885,13 +1577,12 @@ void execute_normal(void) blocklen = 0; start_pc_p = r->pc_oldp; start_pc = r->pc; - for (;;) - { + for (;;) { /* Take note: This is the do-it-normal loop */ regs.instruction_pc = m68k_getpc(); r->opcode = get_diword(0); - special_mem = DISTRUST_CONSISTENT_MEM; + special_mem = 0; pc_hist[blocklen].location = (uae_u16*)r->pc_p; cpu_cycles = (*cpufunctbl[r->opcode])(r->opcode); @@ -1900,8 +1591,7 @@ void execute_normal(void) total_cycles += cpu_cycles; pc_hist[blocklen].specmem = special_mem; blocklen++; - if (end_block(r->opcode) || blocklen >= MAXRUN || r->spcflags || uae_int_requested) - { + if (end_block(r->opcode) || blocklen >= MAXRUN || r->spcflags || uae_int_requested) { compile_block(pc_hist, blocklen, total_cycles); return; /* We will deal with the spcflags in the caller */ } @@ -1914,15 +1604,12 @@ typedef void compiled_handler(void); static void m68k_run_jit(void) { - for (;;) - { - ((compiled_handler*)pushall_call_handler)(); + for (;;) { + ((compiled_handler*)(pushall_call_handler))(); /* Whenever we return from that, we should check spcflags */ check_uae_int_request(); - if (regs.spcflags) - { - if (do_specialties(0)) - { + if (regs.spcflags) { + if (do_specialties (0)) { return; } } @@ -1933,8 +1620,7 @@ static void m68k_run_jit(void) void cpu_halt(int id) { // id > 0: emulation halted. - if (!regs.halted) - { + if (!regs.halted) { write_log(_T("CPU halted: reason = %d PC=%08x\n"), id, M68K_GETPC); regs.halted = id; gui_data.cpu_halted = id; @@ -1952,12 +1638,9 @@ static void m68k_run_2(void) struct regstruct* r = ®s; bool exit = false; - while (!exit) - { - TRY(prb) - { - while (!exit) - { + while (!exit) { + TRY(prb) { + while (!exit) { r->instruction_pc = m68k_getpc(); r->opcode = get_diword(0); @@ -1974,22 +1657,18 @@ static void m68k_run_2(void) cpu_cycles = (*cpufunctbl[r->opcode])(r->opcode); cpu_cycles = adjust_cycles(cpu_cycles); - if (r->spcflags) - { + if (r->spcflags) { if (do_specialties(cpu_cycles)) exit = true; } } - } CATCH(prb) - { + } CATCH(prb) { bus_error(); - if (r->spcflags) - { + if (r->spcflags) { if (do_specialties(cpu_cycles)) exit = true; } - } - ENDTRY + } ENDTRY } } @@ -1998,7 +1677,7 @@ static int in_m68k_go = 0; static bool cpu_hardreset; #ifdef USE_JIT_FPU -static uae_u8 fp_buffer[8 * 8]; +static uae_u8 fp_buffer[9 * 16]; #endif void m68k_go(int may_quit) @@ -2006,15 +1685,14 @@ void m68k_go(int may_quit) int hardboot = 1; int startup = 1; - if (in_m68k_go || !may_quit) - { + if (in_m68k_go || !may_quit) { write_log(_T("Bug! m68k_go is not reentrant.\n")); abort(); } #ifdef USE_JIT_FPU - __asm__ volatile("vstmia %[fp_buffer]!, {d7-d15}"::[fp_buffer] "r" (fp_buffer)); - //save_host_fp_regs((uae_u8 *)(&fp_buffer[0])); + //__asm__ volatile("vstmia %[fp_buffer]!, {d7-d15}"::[fp_buffer] "r" (fp_buffer)); + save_host_fp_regs(fp_buffer); #endif reset_frame_rate_hack(); @@ -2022,13 +1700,11 @@ void m68k_go(int may_quit) cpu_prefs_changed_flag = 0; in_m68k_go++; - for (;;) - { + for (;;) { + int restored = 0; void (*run_func)(void); - if (quit_program > 0) - { - int restored = 0; + if (quit_program > 0) { bool cpu_keyboardreset = quit_program == UAE_RESET_KEYBOARD; cpu_hardreset = ((quit_program == UAE_RESET_HARD ? 1 : 0) | hardboot) != 0; @@ -2051,23 +1727,21 @@ void m68k_go(int may_quit) set_cycles(0); custom_reset(cpu_hardreset != 0, cpu_keyboardreset); m68k_reset(cpu_hardreset != 0); - if (cpu_hardreset) - { + if (cpu_hardreset) { memory_clear(); write_log(_T("hardreset, memory cleared\n")); } cpu_hardreset = false; #ifdef SAVESTATE /* We may have been restoring state, but we're done now. */ - if (isrestore()) - { + if (isrestore ()) { savestate_restore_finish(); startup = 1; restored = 1; } #endif if (currprefs.produce_sound == 0) - eventtab[ev_audio].active = false; + eventtab[ev_audio].active = 0; m68k_setpc_normal(regs.pc); check_prefs_changed_audio(); @@ -2076,19 +1750,17 @@ void m68k_go(int may_quit) statusline_clear(); } - if (regs.spcflags & SPCFLAG_MODE_CHANGE) - { - if (cpu_prefs_changed_flag & 1) - { + if (regs.spcflags & SPCFLAG_MODE_CHANGE) { + if (cpu_prefs_changed_flag & 1) { uaecptr pc = m68k_getpc(); prefs_changed_cpu(); + custom_cpuchange(); build_cpufunctbl(); m68k_setpc_normal(pc); fill_prefetch(); update_68k_cycles(); } - if (cpu_prefs_changed_flag & 2) - { + if (cpu_prefs_changed_flag & 2) { fixup_cpu(&changed_prefs); currprefs.m68k_speed = changed_prefs.m68k_speed; update_68k_cycles(); @@ -2098,42 +1770,35 @@ void m68k_go(int may_quit) } set_x_funcs(); - if (startup) - { + if (startup) { custom_prepare(); protect_roms(true); } startup = 0; unset_special(SPCFLAG_MODE_CHANGE); - if (!regs.halted) - { +#ifdef SAVESTATE + if (restored) { + restored = 0; + } +#endif + + if (!regs.halted) { // check that PC points to something that looks like memory. uaecptr pc = m68k_getpc(); addrbank* ab = &get_mem_bank(pc); - if (ab == nullptr || ab == &dummy_bank || (!currprefs.cpu_compatible && !valid_address(pc, 2)) || (pc & 1)) - { + if (ab == NULL || ab == &dummy_bank || (!currprefs.cpu_compatible && !valid_address(pc, 2)) || (pc & 1)) { cpu_halt(CPU_HALT_INVALID_START_ADDRESS); } } - if (regs.halted) - { + if (regs.halted) { cpu_halt(regs.halted); - if (regs.halted < 0) - { - haltloop(); - continue; - } } run_func = - currprefs.cpu_compatible && currprefs.cpu_model <= 68010 - ? m68k_run_1 - : + currprefs.cpu_compatible && currprefs.cpu_model <= 68010 ? m68k_run_1 : #ifdef JIT - currprefs.cpu_model >= 68020 && currprefs.cachesize - ? m68k_run_jit - : + currprefs.cpu_model >= 68020 && currprefs.cachesize ? m68k_run_jit : #endif m68k_run_2; run_func(); @@ -2142,12 +1807,12 @@ void m68k_go(int may_quit) // Prepare for a restart: reset pc regs.pc = 0; - regs.pc_p = nullptr; - regs.pc_oldp = nullptr; + regs.pc_p = NULL; + regs.pc_oldp = NULL; #ifdef USE_JIT_FPU - __asm__ volatile("vldmia %[fp_buffer]!, {d7-d15}"::[fp_buffer] "r" (fp_buffer)); - //restore_host_fp_regs(fp_buffer); + //__asm__ volatile("vldmia %[fp_buffer]!, {d7-d15}"::[fp_buffer] "r" (fp_buffer)); + restore_host_fp_regs(fp_buffer); #endif in_m68k_go--; @@ -2167,9 +1832,9 @@ uae_u8* restore_cpu(uae_u8* src) currprefs.cpu_model = changed_prefs.cpu_model = model = restore_u32(); flags = restore_u32(); - changed_prefs.address_space_24 = false; + changed_prefs.address_space_24 = 0; if (flags & CPUTYPE_EC) - changed_prefs.address_space_24 = true; + changed_prefs.address_space_24 = 1; currprefs.address_space_24 = changed_prefs.address_space_24; currprefs.cpu_compatible = changed_prefs.cpu_compatible; for (int i = 0; i < 15; i++) @@ -2181,28 +1846,22 @@ uae_u8* restore_cpu(uae_u8* src) regs.isp = restore_u32(); regs.sr = restore_u16(); l = restore_u32(); - if (l & CPUMODE_HALT) - { + if (l & CPUMODE_HALT) { regs.stopped = 1; - } - else - { + } else { regs.stopped = 0; } - if (model >= 68010) - { + if (model >= 68010) { regs.dfc = restore_u32(); regs.sfc = restore_u32(); regs.vbr = restore_u32(); } - if (model >= 68020) - { + if (model >= 68020) { regs.caar = restore_u32(); regs.cacr = restore_u32(); regs.msp = restore_u32(); } - if (model >= 68030) - { + if (model >= 68030) { fake_crp_030 = restore_u64(); fake_srp_030 = restore_u64(); fake_tt0_030 = restore_u32(); @@ -2210,8 +1869,7 @@ uae_u8* restore_cpu(uae_u8* src) fake_tc_030 = restore_u32(); fake_mmusr_030 = restore_u16(); } - if (model >= 68040) - { + if (model >= 68040) { regs.itt0 = restore_u32(); regs.itt1 = restore_u32(); regs.dtt0 = restore_u32(); @@ -2220,8 +1878,7 @@ uae_u8* restore_cpu(uae_u8* src) regs.urp = restore_u32(); regs.srp = restore_u32(); } - if (flags & 0x80000000) - { + if (flags & 0x80000000) { int khz = restore_u32(); restore_u32(); if (khz > 0 && khz < 800000) @@ -2239,8 +1896,7 @@ uae_u8* restore_cpu(uae_u8* src) static void fill_prefetch_quick(void) { - if (currprefs.cpu_model >= 68020) - { + if (currprefs.cpu_model >= 68020) { fill_prefetch(); return; } @@ -2324,20 +1980,17 @@ uae_u8* save_cpu(int* len, uae_u8* dstptr) save_u32(regs.s ? regs.regs[15] : regs.isp); /* ISP */ save_u16(regs.sr); /* SR/CCR */ save_u32(regs.stopped ? CPUMODE_HALT : 0); /* flags */ - if (model >= 68010) - { + if(model >= 68010) { save_u32(regs.dfc); /* DFC */ save_u32(regs.sfc); /* SFC */ save_u32(regs.vbr); /* VBR */ } - if (model >= 68020) - { + if(model >= 68020) { save_u32(regs.caar); /* CAAR */ save_u32(regs.cacr); /* CACR */ save_u32(regs.msp); /* MSP */ } - if (model >= 68030) - { + if(model >= 68030) { save_u64(fake_crp_030); /* CRP */ save_u64(fake_srp_030); /* SRP */ save_u32(fake_tt0_030); /* TT0/AC0 */ @@ -2345,8 +1998,7 @@ uae_u8* save_cpu(int* len, uae_u8* dstptr) save_u32(fake_tc_030); /* TCR */ save_u16(fake_mmusr_030); /* MMUSR/ACUSR */ } - if (model >= 68040) - { + if(model >= 68040) { save_u32(regs.itt0); /* ITT0 */ save_u32(regs.itt1); /* ITT1 */ save_u32(regs.dtt0); /* DTT0 */ @@ -2356,8 +2008,7 @@ uae_u8* save_cpu(int* len, uae_u8* dstptr) save_u32(regs.srp); /* SRP */ } khz = -1; - if (currprefs.m68k_speed == 0) - { + if (currprefs.m68k_speed == 0) { khz = currprefs.ntscmode ? 715909 : 709379; if (currprefs.cpu_model >= 68020) khz *= 2; @@ -2370,26 +2021,20 @@ uae_u8* save_cpu(int* len, uae_u8* dstptr) #endif /* SAVESTATE */ -static void exception3f(uae_u32 opcode, uaecptr addr, bool writeaccess, bool instructionaccess, bool notinstruction, - uaecptr pc, bool plus2) +static void exception3f (uae_u32 opcode, uaecptr addr, bool writeaccess, bool instructionaccess, bool notinstruction, uaecptr pc, bool plus2) { if (currprefs.cpu_model >= 68040) addr &= ~1; - if (currprefs.cpu_model >= 68020) - { + if (currprefs.cpu_model >= 68020) { if (pc == 0xffffffff) last_addr_for_exception_3 = regs.instruction_pc; else last_addr_for_exception_3 = pc; - } - else if (pc == 0xffffffff) - { + } else if (pc == 0xffffffff) { last_addr_for_exception_3 = m68k_getpc(); if (plus2) last_addr_for_exception_3 += 2; - } - else - { + } else { last_addr_for_exception_3 = pc; } last_fault_for_exception_3 = addr; @@ -2400,32 +2045,28 @@ static void exception3f(uae_u32 opcode, uaecptr addr, bool writeaccess, bool ins Exception(3); } -void exception3_notinstruction(uae_u32 opcode, uaecptr addr) +static void exception3_notinstruction(uae_u32 opcode, uaecptr addr) { exception3f(opcode, addr, true, false, true, 0xffffffff, false); } - void exception3_read(uae_u32 opcode, uaecptr addr) { - exception3f(opcode, addr, false, false, false, 0xffffffff, false); + exception3f (opcode, addr, false, 0, false, 0xffffffff, false); } - void exception3_write(uae_u32 opcode, uaecptr addr) { - exception3f(opcode, addr, true, false, false, 0xffffffff, false); + exception3f (opcode, addr, true, 0, false, 0xffffffff, false); } - void exception3i(uae_u32 opcode, uaecptr addr) { - exception3f(opcode, addr, false, true, false, 0xffffffff, true); + exception3f (opcode, addr, 0, 1, false, 0xffffffff, true); } - void exception3b(uae_u32 opcode, uaecptr addr, bool w, bool i, uaecptr pc) { exception3f(opcode, addr, w, i, false, pc, true); } -void exception2(uaecptr addr, bool read, int size, uae_u32 fc) +void exception2_setup(uaecptr addr, bool read, int size, uae_u32 fc) { last_addr_for_exception_3 = m68k_getpc(); last_fault_for_exception_3 = addr; @@ -2433,6 +2074,11 @@ void exception2(uaecptr addr, bool read, int size, uae_u32 fc) last_instructionaccess_for_exception_3 = (fc & 1) == 0; last_op_for_exception_3 = regs.opcode; last_notinstruction_for_exception_3 = exception_in_exception != 0; +} + +void exception2 (uaecptr addr, bool read, int size, uae_u32 fc) +{ + exception2_setup(addr, read, size, fc); THROW(2); } @@ -2445,15 +2091,14 @@ void cpureset(void) addrbank* ab; set_special(SPCFLAG_CHECK); - if (currprefs.cpu_compatible && currprefs.cpu_model <= 68020) - { + send_internalevent(INTERNALEVENT_CPURESET); + if (currprefs.cpu_compatible && currprefs.cpu_model <= 68020) { custom_reset(false, false); return; } pc = m68k_getpc() + 2; ab = &get_mem_bank(pc); - if (ab->check(pc, 2)) - { + if (ab->check (pc, 2)) { write_log(_T("CPU reset PC=%x (%s)..\n"), pc - 2, ab->name); ins = get_word(pc); custom_reset(false, false); @@ -2461,8 +2106,7 @@ void cpureset(void) if (ab == &get_mem_bank(pc)) return; // it did - if ((ins & ~7) == 0x4ed0) - { + if ((ins & ~7) == 0x4ed0) { int reg = ins & 7; uae_u32 addr = m68k_areg(regs, reg); if (addr < 0x80000) @@ -2483,17 +2127,14 @@ void m68k_setstopped(void) { /* A traced STOP instruction drops through immediately without actually stopping. */ - if ((regs.spcflags & SPCFLAG_DOTRACE) == 0) - { + if ((regs.spcflags & SPCFLAG_DOTRACE) == 0) { m68k_set_stop(); - } - else - { + } else { m68k_resumestopped(); } } -void m68k_resumestopped(void) +static void m68k_resumestopped (void) { if (!regs.stopped) return; @@ -2503,8 +2144,7 @@ void m68k_resumestopped(void) void check_t0_trace(void) { - if (regs.t0 && currprefs.cpu_model >= 68020) - { + if (regs.t0 && currprefs.cpu_model >= 68020) { unset_special(SPCFLAG_TRACE); set_special(SPCFLAG_DOTRACE); } diff --git a/src/newcpu_common.cpp b/src/newcpu_common.cpp index 38d07af4..e5f8d7f0 100644 --- a/src/newcpu_common.cpp +++ b/src/newcpu_common.cpp @@ -1,223 +1,141 @@ -#include -#include - #include "sysdeps.h" #include "options.h" #include "memory.h" #include "newcpu.h" -int movec_illg(int regno) +int get_cpu_model(void) { - int regno2 = regno & 0x7ff; + return currprefs.cpu_model; +} - if (currprefs.cpu_model == 68010) - { - if (regno2 < 2) - return 0; - return 1; - } - else if (currprefs.cpu_model == 68020) - { +static int movec_illg (int regno) +{ + int regno2 = regno & 0x7ff; + + if (currprefs.cpu_model == 68010) { + if (regno2 < 2) + return 0; + return 1; + } else if (currprefs.cpu_model == 68020) { if (regno == 3) return 1; /* 68040/060 only */ - /* 4 is >=68040, but 0x804 is in 68020 */ - if (regno2 < 4 || regno == 0x804) - return 0; - return 1; - } - else if (currprefs.cpu_model == 68030) - { + /* 4 is >=68040, but 0x804 is in 68020 */ + if (regno2 < 4 || regno == 0x804) + return 0; + return 1; + } else if (currprefs.cpu_model == 68030) { if (regno2 <= 2) return 0; - if (regno == 0x803 || regno == 0x804) - return 0; - return 1; - } - else if (currprefs.cpu_model == 68040) - { + if (regno == 0x803 || regno == 0x804) + return 0; + return 1; + } else if (currprefs.cpu_model == 68040) { if (regno == 0x802) return 1; /* 68020/030 only */ - if (regno2 < 8) - return 0; - return 1; - } - return 1; + if (regno2 < 8) return 0; + return 1; + } + return 1; } -int m68k_move2c(int regno, uae_u32 *regp) +int m68k_move2c (int regno, uae_u32 *regp) { - if (movec_illg(regno)) - { - op_illg(0x4E7B); + if (movec_illg (regno)) { + op_illg (0x4E7B); return 0; - } - else - { - switch (regno) - { - case 0: - regs.sfc = *regp & 7; - break; - case 1: - regs.dfc = *regp & 7; - break; - case 2: - { - uae_u32 cacr_mask = 0; - if (currprefs.cpu_model == 68020) - cacr_mask = 0x0000000f; - else if (currprefs.cpu_model == 68030) - cacr_mask = 0x00003f1f; - else if (currprefs.cpu_model == 68040) - cacr_mask = 0x80008000; - regs.cacr = *regp & cacr_mask; - set_cpu_caches(false); - } - break; - /* 68040/060 only */ - case 3: - regs.tcr = *regp & 0xc000; - break; + } else { + switch (regno) { + case 0: regs.sfc = *regp & 7; break; + case 1: regs.dfc = *regp & 7; break; + case 2: + { + uae_u32 cacr_mask = 0; + if (currprefs.cpu_model == 68020) + cacr_mask = 0x0000000f; + else if (currprefs.cpu_model == 68030) + cacr_mask = 0x00003f1f; + else if (currprefs.cpu_model == 68040) + cacr_mask = 0x80008000; + regs.cacr = *regp & cacr_mask; + set_cpu_caches(false); + } + break; + /* 68040/060 only */ + case 3: + regs.tcr = *regp & 0xc000; + break; - /* no differences between 68040 and 68060 */ - case 4: - regs.itt0 = *regp & 0xffffe364; - break; - case 5: - regs.itt1 = *regp & 0xffffe364; - break; - case 6: - regs.dtt0 = *regp & 0xffffe364; - break; - case 7: - regs.dtt1 = *regp & 0xffffe364; - break; + /* no differences between 68040 and 68060 */ + case 4: regs.itt0 = *regp & 0xffffe364; break; + case 5: regs.itt1 = *regp & 0xffffe364; break; + case 6: regs.dtt0 = *regp & 0xffffe364; break; + case 7: regs.dtt1 = *regp & 0xffffe364; break; /* 68060 only */ - case 8: - regs.buscr = *regp & 0xf0000000; - break; + case 8: regs.buscr = *regp & 0xf0000000; break; - case 0x800: - regs.usp = *regp; - break; - case 0x801: - regs.vbr = *regp; - break; - case 0x802: - regs.caar = *regp; - break; - case 0x803: - regs.msp = *regp; - if (regs.m == 1) - m68k_areg(regs, 7) = regs.msp; - break; - case 0x804: - regs.isp = *regp; - if (regs.m == 0) - m68k_areg(regs, 7) = regs.isp; - break; - /* 68040 only */ - case 0x805: - regs.mmusr = *regp; - break; - /* 68040 stores all bits, 68060 zeroes low 9 bits */ - case 0x806: - regs.urp = *regp; - break; - case 0x807: - regs.srp = *regp; - break; - default: - op_illg(0x4E7B); + case 0x800: regs.usp = *regp; break; + case 0x801: regs.vbr = *regp; break; + case 0x802: regs.caar = *regp; break; + case 0x803: regs.msp = *regp; if (regs.m == 1) m68k_areg(regs, 7) = regs.msp; break; + case 0x804: regs.isp = *regp; if (regs.m == 0) m68k_areg(regs, 7) = regs.isp; break; + /* 68040 only */ + case 0x805: regs.mmusr = *regp; break; + /* 68040 stores all bits, 68060 zeroes low 9 bits */ + case 0x806: regs.urp = *regp; break; + case 0x807: regs.srp = *regp; break; + default: + op_illg (0x4E7B); return 0; - } - } + } + } return 1; } -int m68k_movec2(int regno, uae_u32 *regp) +int m68k_movec2 (int regno, uae_u32 *regp) { - if (movec_illg(regno)) - { - op_illg(0x4E7A); + if (movec_illg (regno)) { + op_illg (0x4E7A); return 0; - } - else - { - switch (regno) - { - case 0: - *regp = regs.sfc; - break; - case 1: - *regp = regs.dfc; - break; - case 2: - { - uae_u32 v = regs.cacr; - uae_u32 cacr_mask = 0; - if (currprefs.cpu_model == 68020) - cacr_mask = 0x00000003; - else if (currprefs.cpu_model == 68030) - cacr_mask = 0x00003313; - else if (currprefs.cpu_model == 68040) - cacr_mask = 0x80008000; - *regp = v & cacr_mask; - } - break; - case 3: - *regp = regs.tcr; - break; - case 4: - *regp = regs.itt0; - break; - case 5: - *regp = regs.itt1; - break; - case 6: - *regp = regs.dtt0; - break; - case 7: - *regp = regs.dtt1; - break; - case 8: - *regp = regs.buscr; - break; + } else { + switch (regno) { + case 0: *regp = regs.sfc; break; + case 1: *regp = regs.dfc; break; + case 2: + { + uae_u32 v = regs.cacr; + uae_u32 cacr_mask = 0; + if (currprefs.cpu_model == 68020) + cacr_mask = 0x00000003; + else if (currprefs.cpu_model == 68030) + cacr_mask = 0x00003313; + else if (currprefs.cpu_model == 68040) + cacr_mask = 0x80008000; + *regp = v & cacr_mask; + } + break; + case 3: *regp = regs.tcr; break; + case 4: *regp = regs.itt0; break; + case 5: *regp = regs.itt1; break; + case 6: *regp = regs.dtt0; break; + case 7: *regp = regs.dtt1; break; + case 8: *regp = regs.buscr; break; - case 0x800: - *regp = regs.usp; - break; - case 0x801: - *regp = regs.vbr; - break; - case 0x802: - *regp = regs.caar; - break; - case 0x803: - *regp = regs.m == 1 ? m68k_areg(regs, 7) : regs.msp; - break; - case 0x804: - *regp = regs.m == 0 ? m68k_areg(regs, 7) : regs.isp; - break; - case 0x805: - *regp = regs.mmusr; - break; - case 0x806: - *regp = regs.urp; - break; - case 0x807: - *regp = regs.srp; - break; - case 0x808: - *regp = regs.pcr; - break; + case 0x800: *regp = regs.usp; break; + case 0x801: *regp = regs.vbr; break; + case 0x802: *regp = regs.caar; break; + case 0x803: *regp = regs.m == 1 ? m68k_areg(regs, 7) : regs.msp; break; + case 0x804: *regp = regs.m == 0 ? m68k_areg(regs, 7) : regs.isp; break; + case 0x805: *regp = regs.mmusr; break; + case 0x806: *regp = regs.urp; break; + case 0x807: *regp = regs.srp; break; + case 0x808: *regp = regs.pcr; break; - default: - op_illg(0x4E7A); + default: + op_illg (0x4E7A); return 0; - } - } + } + } return 1; } @@ -225,48 +143,47 @@ int m68k_movec2(int regno, uae_u32 *regp) * extract bitfield data from memory and return it in the MSBs * bdata caches the unmodified data for put_bitfield() */ -uae_u32 REGPARAM2 get_bitfield(uae_u32 src, uae_u32 bdata[2], uae_s32 offset, int width) +uae_u32 REGPARAM2 get_bitfield (uae_u32 src, uae_u32 bdata[2], uae_s32 offset, int width) { uae_u32 tmp, res, mask; offset &= 7; mask = 0xffffffffu << (32 - width); - switch ((offset + width + 7) >> 3) - { + switch ((offset + width + 7) >> 3) { case 1: - tmp = get_byte(src); + tmp = get_byte (src); res = tmp << (24 + offset); bdata[0] = tmp & ~(mask >> (24 + offset)); break; case 2: - tmp = get_word(src); + tmp = get_word (src); res = tmp << (16 + offset); bdata[0] = tmp & ~(mask >> (16 + offset)); break; case 3: - tmp = get_word(src); + tmp = get_word (src); res = tmp << (16 + offset); bdata[0] = tmp & ~(mask >> (16 + offset)); - tmp = get_byte(src + 2); + tmp = get_byte (src + 2); res |= tmp << (8 + offset); bdata[1] = tmp & ~(mask >> (8 + offset)); break; case 4: - tmp = get_long(src); + tmp = get_long (src); res = tmp << offset; bdata[0] = tmp & ~(mask >> offset); break; case 5: - tmp = get_long(src); + tmp = get_long (src); res = tmp << offset; bdata[0] = tmp & ~(mask >> offset); - tmp = get_byte(src + 4); + tmp = get_byte (src + 4); res |= tmp >> (8 - offset); bdata[1] = tmp & ~(mask << (8 - offset)); break; default: /* Panic? */ - write_log(_T("get_bitfield() can't happen %d\n"), (offset + width + 7) >> 3); + write_log (_T("get_bitfield() can't happen %d\n"), (offset + width + 7) >> 3); res = 0; break; } @@ -276,73 +193,68 @@ uae_u32 REGPARAM2 get_bitfield(uae_u32 src, uae_u32 bdata[2], uae_s32 offset, in * write bitfield data (in the LSBs) back to memory, upper bits * must be cleared already. */ -void REGPARAM2 put_bitfield(uae_u32 dst, uae_u32 bdata[2], uae_u32 val, uae_s32 offset, int width) +void REGPARAM2 put_bitfield (uae_u32 dst, uae_u32 bdata[2], uae_u32 val, uae_s32 offset, int width) { offset = (offset & 7) + width; - switch ((offset + 7) >> 3) - { + switch ((offset + 7) >> 3) { case 1: - put_byte(dst, bdata[0] | (val << (8 - offset))); + put_byte (dst, bdata[0] | (val << (8 - offset))); break; case 2: - put_word(dst, bdata[0] | (val << (16 - offset))); + put_word (dst, bdata[0] | (val << (16 - offset))); break; case 3: - put_word(dst, bdata[0] | (val >> (offset - 16))); - put_byte(dst + 2, bdata[1] | (val << (24 - offset))); + put_word (dst, bdata[0] | (val >> (offset - 16))); + put_byte (dst + 2, bdata[1] | (val << (24 - offset))); break; case 4: - put_long(dst, bdata[0] | (val << (32 - offset))); + put_long (dst, bdata[0] | (val << (32 - offset))); break; case 5: - put_long(dst, bdata[0] | (val >> (offset - 32))); - put_byte(dst + 4, bdata[1] | (val << (40 - offset))); + put_long (dst, bdata[0] | (val >> (offset - 32))); + put_byte (dst + 4, bdata[1] | (val << (40 - offset))); break; default: - write_log(_T("put_bitfield() can't happen %d\n"), (offset + 7) >> 3); + write_log (_T("put_bitfield() can't happen %d\n"), (offset + 7) >> 3); break; } } -uae_u32 REGPARAM2 _get_disp_ea_020(uae_u32 base) +uae_u32 REGPARAM2 _get_disp_ea_020 (uae_u32 base) { - uae_u16 dp = next_diword(); - int reg = (dp >> 12) & 15; - uae_s32 regd = regs.regs[reg]; - if ((dp & 0x800) == 0) - regd = (uae_s32)(uae_s16)regd; - regd <<= (dp >> 9) & 3; - if (dp & 0x100) - { - uae_s32 outer = 0; - if (dp & 0x80) - base = 0; - if (dp & 0x40) - regd = 0; + uae_u16 dp = next_diword (); + int reg = (dp >> 12) & 15; + uae_s32 regd = regs.regs[reg]; + if ((dp & 0x800) == 0) + regd = (uae_s32)(uae_s16)regd; + regd <<= (dp >> 9) & 3; + if (dp & 0x100) { - if ((dp & 0x30) == 0x20) - base += (uae_s32)(uae_s16)next_diword(); - if ((dp & 0x30) == 0x30) - base += next_dilong(); + uae_s32 outer = 0; + if (dp & 0x80) base = 0; + if (dp & 0x40) regd = 0; - if ((dp & 0x3) == 0x2) - outer = (uae_s32)(uae_s16)next_diword(); - if ((dp & 0x3) == 0x3) - outer = next_dilong(); + if ((dp & 0x30) == 0x20) + base += (uae_s32)(uae_s16) next_diword (); + if ((dp & 0x30) == 0x30) + base += next_dilong (); - if ((dp & 0x4) == 0) - base += regd; - if (dp & 0x3) - base = get_long(base); - if (dp & 0x4) - base += regd; + if ((dp & 0x3) == 0x2) + outer = (uae_s32)(uae_s16) next_diword (); + if ((dp & 0x3) == 0x3) + outer = next_dilong (); - return base + outer; - } - else - { - return base + (uae_s32)((uae_s8)dp) + regd; - } + if ((dp & 0x4) == 0) + base += regd; + if (dp & 0x3) + base = get_long (base); + if (dp & 0x4) + base += regd; + + return base + outer; + } else { + return base + (uae_s32)((uae_s8)dp) + regd; + } } /* @@ -403,37 +315,34 @@ uae_u32 REGPARAM2 _get_disp_ea_020(uae_u32 base) */ -int getDivu68kCycles(uae_u32 dividend, uae_u16 divisor) +int getDivu68kCycles (uae_u32 dividend, uae_u16 divisor) { int mcycles; uae_u32 hdivisor; int i; - if (divisor == 0) + if(divisor == 0) return 0; // Overflow - if ((dividend >> 16) >= divisor) + if((dividend >> 16) >= divisor) return (mcycles = 5) * 2; mcycles = 38; hdivisor = divisor << 16; - for (i = 0; i < 15; i++) - { + for( i = 0; i < 15; i++) { uae_u32 temp; temp = dividend; dividend <<= 1; // If carry from shift - if ((uae_s32)temp < 0) + if((uae_s32)temp < 0) dividend -= hdivisor; - else - { + else { mcycles += 2; - if (dividend >= hdivisor) - { + if(dividend >= hdivisor) { dividend -= hdivisor; mcycles--; } @@ -442,32 +351,31 @@ int getDivu68kCycles(uae_u32 dividend, uae_u16 divisor) return mcycles * 2; } -int getDivs68kCycles(uae_s32 dividend, uae_s16 divisor) +int getDivs68kCycles (uae_s32 dividend, uae_s16 divisor) { int mcycles; uae_u32 aquot; int i; - if (divisor == 0) + if(divisor == 0) return 0; mcycles = 6; - if (dividend < 0) + if( dividend < 0) mcycles++; // Check for absolute overflow - if (((uae_u32)abs(dividend) >> 16) >= (uae_u16)abs(divisor)) + if(((uae_u32)abs(dividend) >> 16) >= (uae_u16)abs(divisor)) return (mcycles + 2) * 2; // Absolute quotient - aquot = (uae_u32)abs(dividend) / (uae_u16)abs(divisor); + aquot = (uae_u32) abs(dividend) / (uae_u16)abs(divisor); mcycles += 55; - if (divisor >= 0) - { - if (dividend >= 0) + if(divisor >= 0) { + if(dividend >= 0) mcycles--; else mcycles++; @@ -475,9 +383,8 @@ int getDivs68kCycles(uae_s32 dividend, uae_s16 divisor) // Count 15 msbits in absolute of quotient - for (i = 0; i < 15; i++) - { - if ((uae_s16)aquot >= 0) + for( i = 0; i < 15; i++) { + if((uae_s16)aquot >= 0) mcycles++; aquot <<= 1; } @@ -485,35 +392,41 @@ int getDivs68kCycles(uae_s32 dividend, uae_s16 divisor) return mcycles * 2; } -/* 68000 Z=1. NVC=0 - * 68020 and 68030: Signed: Z=1 NVC=0. Unsigned: V=1, N>16)<0 Z=(dst>>16)==0 + * 68020 and 68030: Signed: Z=1 NC=0. V=? (sometimes random!) Unsigned: V=1, N=(dst>>16)<0 Z=(dst>>16)==0, C=0. * 68040/68060 C=0. + * */ -void divbyzero_special(bool issigned, uae_s32 dst) +void divbyzero_special (bool issigned, uae_s32 dst) { - if (currprefs.cpu_model == 68020 || currprefs.cpu_model == 68030) - { - CLEAR_CZNV(); - if (issigned == false) - { - if (dst < 0) - SET_NFLG(1); - SET_ZFLG(!GET_NFLG()); - SET_VFLG(1); - } - else - { + if (currprefs.cpu_model == 68020 || currprefs.cpu_model == 68030) { + CLEAR_CZNV (); + if (issigned) { SET_ZFLG(1); + } else { + uae_s16 d = dst >> 16; + if (d < 0) + SET_NFLG (1); + else if (d == 0) + SET_ZFLG(1); + SET_VFLG (1); } - } - else if (currprefs.cpu_model >= 68040) - { - SET_CFLG(0); - } - else - { + } else if (currprefs.cpu_model >= 68040) { + SET_CFLG (0); + } else { // 68000/010 - CLEAR_CZNV(); + CLEAR_CZNV (); + if (issigned) { + SET_ZFLG(1); + } else { + uae_s16 d = dst >> 16; + if (d < 0) + SET_NFLG(1); + else if (d == 0) + SET_ZFLG(1); + } } } @@ -530,18 +443,13 @@ void divbyzero_special(bool issigned, uae_s32 dst) void setdivuoverflowflags(uae_u32 dividend, uae_u16 divisor) { - if (currprefs.cpu_model >= 68040) - { + if (currprefs.cpu_model >= 68040) { SET_VFLG(1); - } - else if (currprefs.cpu_model >= 68020) - { + } else if (currprefs.cpu_model >= 68020) { SET_VFLG(1); if ((uae_s32)dividend < 0) SET_NFLG(1); - } - else - { + } else { SET_VFLG(1); SET_NFLG(1); } @@ -562,12 +470,9 @@ void setdivuoverflowflags(uae_u32 dividend, uae_u16 divisor) void setdivsoverflowflags(uae_s32 dividend, uae_s16 divisor) { - if (currprefs.cpu_model >= 68040) - { + if (currprefs.cpu_model >= 68040) { SET_VFLG(1); - } - else if (currprefs.cpu_model >= 68020) - { + } else if (currprefs.cpu_model >= 68020) { SET_VFLG(1); // absolute overflow? if (((uae_u32)abs(dividend) >> 16) >= (uae_u16)abs(divisor)) @@ -577,34 +482,93 @@ void setdivsoverflowflags(uae_s32 dividend, uae_s16 divisor) SET_ZFLG(1); if ((uae_s8)aquot < 0) SET_NFLG(1); - } - else - { + } else { SET_VFLG(1); SET_NFLG(1); } } +/* + * CHK.W undefined flags + * + * 68000: CV=0. Z: dst==0. N: dst < 0. !N: dst > src. + * 68020: Z: dst==0. N: dst < 0. V: src-dst overflow. C: if dst < 0: (dst > src || src >= 0), if dst > src: (src >= 0). + * + */ +void setchkundefinedflags(uae_s32 src, uae_s32 dst, int size) +{ + CLEAR_CZNV(); + if (currprefs.cpu_model < 68020) { + if (dst == 0) + SET_ZFLG(1); + if (dst < 0) + SET_NFLG(1); + else if (dst > src) + SET_NFLG(0); + } else if (currprefs.cpu_model == 68020 || currprefs.cpu_model == 68030) { + if (dst == 0) + SET_ZFLG(1); + SET_NFLG(dst < 0); + if (dst < 0 || dst > src) { + if (size == sz_word) { + int flgs = ((uae_s16)(dst)) < 0; + int flgo = ((uae_s16)(src)) < 0; + uae_s16 val = (uae_s16)src - (uae_s16)dst; + int flgn = val < 0; + SET_VFLG((flgs ^ flgo) & (flgn ^ flgo)); + } else { + int flgs = dst < 0; + int flgo = src < 0; + uae_s32 val = src - dst; + int flgn = val < 0; + SET_VFLG((flgs ^ flgo) & (flgn ^ flgo)); + } + if (dst < 0) { + SET_CFLG(dst > src || src >= 0); + } else { + SET_CFLG(src >= 0); + } + } + } +} + +void setchk2undefinedflags(uae_u32 lower, uae_u32 upper, uae_u32 val, int size) +{ + uae_u32 nmask; + if (size == sz_byte) + nmask = 0x80; + else if (size == sz_word) + nmask = 0x8000; + else + nmask = 0x80000000; + + SET_NFLG(0); + if ((upper & nmask) && val > upper) { + SET_NFLG(1); + } else if (!(upper & nmask) && val > upper && val < nmask) { + SET_NFLG(1); + } else if (val < lower) { + SET_NFLG(1); + } + SET_VFLG(0); +} + #if !defined (uae_s64) STATIC_INLINE int div_unsigned(uae_u32 src_hi, uae_u32 src_lo, uae_u32 div, uae_u32 *quot, uae_u32 *rem) { uae_u32 q = 0, cbit = 0; int i; - if (div <= src_hi) - { - return 1; + if (div <= src_hi) { + return 1; } - for (i = 0; i < 32; i++) - { + for (i = 0 ; i < 32 ; i++) { cbit = src_hi & 0x80000000ul; src_hi <<= 1; - if (src_lo & 0x80000000ul) - src_hi++; + if (src_lo & 0x80000000ul) src_hi++; src_lo <<= 1; q = q << 1; - if (cbit || div <= src_hi) - { + if (cbit || div <= src_hi) { q |= 1; src_hi -= div; } @@ -615,6 +579,14 @@ STATIC_INLINE int div_unsigned(uae_u32 src_hi, uae_u32 src_lo, uae_u32 div, uae_ } #endif +static void divl_overflow(void) +{ + SET_VFLG(1); + SET_NFLG(1); + SET_CFLG(0); + SET_ZFLG(0); +} + void m68k_divl (uae_u32 opcode, uae_u32 src, uae_u16 extra) { // Done in caller @@ -634,18 +606,14 @@ void m68k_divl (uae_u32 opcode, uae_u32 src, uae_u16 extra) } if ((uae_u64)a == 0x8000000000000000UL && src == ~0u) { - SET_VFLG (1); - SET_NFLG (1); - SET_CFLG (0); + divl_overflow(); } else { rem = a % (uae_s64)(uae_s32)src; quot = a / (uae_s64)(uae_s32)src; if ((quot & UVAL64(0xffffffff80000000)) != 0 && (quot & UVAL64(0xffffffff80000000)) != UVAL64(0xffffffff80000000)) { - SET_VFLG (1); - SET_NFLG (1); - SET_CFLG (0); + divl_overflow(); } else { if (((uae_s32)rem < 0) != ((uae_s64)a < 0)) rem = -rem; SET_VFLG (0); @@ -668,9 +636,7 @@ void m68k_divl (uae_u32 opcode, uae_u32 src, uae_u16 extra) rem = a % (uae_u64)src; quot = a / (uae_u64)src; if (quot > 0xffffffffu) { - SET_VFLG (1); - SET_NFLG (1); - SET_CFLG (0); + divl_overflow(); } else { SET_VFLG (0); SET_CFLG (0); @@ -702,9 +668,7 @@ void m68k_divl (uae_u32 opcode, uae_u32 src, uae_u16 extra) if ((uae_s32)src < 0) src = -src; if (div_unsigned(hi, lo, src, ", &rem) || (sign & 0x80000000) ? quot > 0x80000000 : quot > 0x7fffffff) { - SET_VFLG (1); - SET_NFLG (1); - SET_CFLG (0); + divl_overflow(); } else { if (sign & 0x80000000) quot = -quot; if (((uae_s32)rem < 0) != (save_high < 0)) rem = -rem; @@ -725,9 +689,7 @@ void m68k_divl (uae_u32 opcode, uae_u32 src, uae_u16 extra) hi = (uae_u32)m68k_dreg(regs, extra & 7); } if (div_unsigned(hi, lo, src, ", &rem)) { - SET_VFLG (1); - SET_NFLG (1); - SET_CFLG (0); + divl_overflow(); } else { SET_VFLG (0); SET_CFLG (0); @@ -750,12 +712,10 @@ STATIC_INLINE void mul_unsigned(uae_u32 src1, uae_u32 src2, uae_u32 *dst_hi, uae uae_u32 lo; lo = r0 + ((r1 << 16) & 0xffff0000ul); - if (lo < r0) - r3++; + if (lo < r0) r3++; r0 = lo; lo = r0 + ((r2 << 16) & 0xffff0000ul); - if (lo < r0) - r3++; + if (lo < r0) r3++; r3 += ((r1 >> 16) & 0xffff) + ((r2 >> 16) & 0xffff); *dst_lo = lo; *dst_hi = r3; @@ -766,22 +726,28 @@ void m68k_mull (uae_u32 opcode, uae_u32 src, uae_u16 extra) { #if defined(uae_s64) if (extra & 0x800) { - /* signed variant */ + /* signed */ uae_s64 a = (uae_s64)(uae_s32)m68k_dreg(regs, (extra >> 12) & 7); a *= (uae_s64)(uae_s32)src; SET_VFLG (0); SET_CFLG (0); - SET_ZFLG (a == 0); - SET_NFLG (a < 0); if (extra & 0x400) { + // 32 * 32 = 64 + m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; m68k_dreg(regs, extra & 7) = (uae_u32)(a >> 32); - } else if ((a & UVAL64 (0xffffffff80000000)) != 0 - && (a & UVAL64(0xffffffff80000000)) != UVAL64(0xffffffff80000000)) - { - SET_VFLG (1); + SET_ZFLG (a == 0); + SET_NFLG (a < 0); + } else { + // 32 * 32 = 32 + uae_s32 b = (uae_s32)a; + m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; + if ((a & UVAL64 (0xffffffff80000000)) != 0 && (a & UVAL64(0xffffffff80000000)) != UVAL64(0xffffffff80000000)) { + SET_VFLG (1); + } + SET_ZFLG(b == 0); + SET_NFLG(b < 0); } - m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; } else { /* unsigned */ uae_u64 a = (uae_u64)(uae_u32)m68k_dreg(regs, (extra >> 12) & 7); @@ -789,18 +755,26 @@ void m68k_mull (uae_u32 opcode, uae_u32 src, uae_u16 extra) a *= (uae_u64)src; SET_VFLG (0); SET_CFLG (0); - SET_ZFLG (a == 0); - SET_NFLG (((uae_s64)a) < 0); if (extra & 0x400) { + // 32 * 32 = 64 + m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; m68k_dreg(regs, extra & 7) = (uae_u32)(a >> 32); - } else if ((a & UVAL64 (0xffffffff00000000)) != 0) { - SET_VFLG (1); + SET_ZFLG (a == 0); + SET_NFLG (((uae_s64)a) < 0); + } else { + // 32 * 32 = 32 + uae_s32 b = (uae_s32)a; + m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; + if ((a & UVAL64(0xffffffff00000000)) != 0) { + SET_VFLG (1); + } + SET_ZFLG(b == 0); + SET_NFLG(b < 0); } - m68k_dreg(regs, (extra >> 12) & 7) = (uae_u32)a; } #else if (extra & 0x800) { - /* signed variant */ + /* signed */ uae_s32 src1,src2; uae_u32 dst_lo,dst_hi; uae_u32 sign; @@ -818,15 +792,16 @@ void m68k_mull (uae_u32 opcode, uae_u32 src, uae_u16 extra) } SET_VFLG (0); SET_CFLG (0); + if (extra & 0x400) { + m68k_dreg(regs, extra & 7) = dst_hi; SET_ZFLG (dst_hi == 0 && dst_lo == 0); SET_NFLG (((uae_s32)dst_hi) < 0); - if (extra & 0x400) - m68k_dreg(regs, extra & 7) = dst_hi; - else if ((dst_hi != 0 || (dst_lo & 0x80000000) != 0) - && ((dst_hi & 0xffffffff) != 0xffffffff - || (dst_lo & 0x80000000) != 0x80000000)) - { - SET_VFLG (1); + } else { + if ((dst_hi != 0 || (dst_lo & 0x80000000) != 0) && ((dst_hi & 0xffffffff) != 0xffffffff || (dst_lo & 0x80000000) != 0x80000000)) { + SET_VFLG (1); + } + SET_ZFLG(dst_lo == 0); + SET_NFLG(((uae_s32)dst_lo) < 0); } m68k_dreg(regs, (extra >> 12) & 7) = dst_lo; } else { @@ -837,14 +812,188 @@ void m68k_mull (uae_u32 opcode, uae_u32 src, uae_u16 extra) SET_VFLG (0); SET_CFLG (0); - SET_ZFLG (dst_hi == 0 && dst_lo == 0); - SET_NFLG (((uae_s32)dst_hi) < 0); - if (extra & 0x400) - m68k_dreg(regs, extra & 7) = dst_hi; - else if (dst_hi != 0) { - SET_VFLG (1); + if (extra & 0x400) { + m68k_dreg(regs, extra & 7) = dst_hi; + SET_ZFLG (dst_hi == 0 && dst_lo == 0); + SET_NFLG (((uae_s32)dst_hi) < 0); + } else { + if (dst_hi != 0) { + SET_VFLG (1); + } + SET_ZFLG(dst_lo == 0); + SET_NFLG(((uae_s32)dst_lo) < 0); } m68k_dreg(regs, (extra >> 12) & 7) = dst_lo; } #endif } + +uae_u32 exception_pc(int nr) +{ + // bus error, address error, illegal instruction, privilege violation, a-line, f-line + if (nr == 2 || nr == 3 || nr == 4 || nr == 8 || nr == 10 || nr == 11) + return regs.instruction_pc; + return m68k_getpc (); +} + +void Exception_build_stack_frame(uae_u32 oldpc, uae_u32 currpc, uae_u32 ssw, int nr, int format) +{ + switch (format) { + case 0x0: // four word stack frame + case 0x1: // throwaway four word stack frame + break; + case 0x2: // six word stack frame + m68k_areg (regs, 7) -= 4; + x_put_long (m68k_areg (regs, 7), oldpc); + break; + case 0x3: // floating point post-instruction stack frame (68040) + m68k_areg (regs, 7) -= 4; + x_put_long (m68k_areg (regs, 7), regs.fp_ea); + break; + case 0x4: // floating point unimplemented stack frame (68LC040, 68EC040) + m68k_areg (regs, 7) -= 4; + x_put_long (m68k_areg (regs, 7), ssw); + m68k_areg (regs, 7) -= 4; + x_put_long (m68k_areg (regs, 7), oldpc); + break; + case 0x8: // address error (68010) + for (int i = 0; i < 15; i++) { + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); + } + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // version + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), regs.opcode); // instruction input buffer + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // unused + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // data input buffer + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // unused + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // data output buffer + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // unused + m68k_areg(regs, 7) -= 4; + x_put_long(m68k_areg(regs, 7), 0); // fault addr + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), ssw); // ssw + break; + case 0xA: + // short bus cycle fault stack frame (68020, 68030) + // used when instruction's last write causes bus fault + m68k_areg(regs, 7) -= 4; + x_put_long(m68k_areg(regs, 7), 0); + m68k_areg(regs, 7) -= 4; + // Data output buffer = value that was going to be written + x_put_long(m68k_areg(regs, 7), 0); + m68k_areg(regs, 7) -= 4; + x_put_long(m68k_areg(regs, 7), regs.irc); // Internal register (opcode storage) + m68k_areg(regs, 7) -= 4; + x_put_long(m68k_areg(regs, 7), 0); // data cycle fault address + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // Instr. pipe stage B + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // Instr. pipe stage C + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), ssw); + m68k_areg(regs, 7) -= 2; + x_put_word(m68k_areg(regs, 7), 0); // = mmu030_state[1]); + break; + default: + write_log(_T("Unknown exception stack frame format: %X\n"), format); + return; + } + m68k_areg (regs, 7) -= 2; + x_put_word (m68k_areg (regs, 7), (format << 12) | (nr * 4)); + m68k_areg (regs, 7) -= 4; + x_put_long (m68k_areg (regs, 7), currpc); + m68k_areg (regs, 7) -= 2; + x_put_word (m68k_areg (regs, 7), regs.sr); +} + +void Exception_build_stack_frame_common(uae_u32 oldpc, uae_u32 currpc, int nr) +{ + if (nr == 5 || nr == 6 || nr == 7 || nr == 9) { + if (currprefs.cpu_model <= 68010) + Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x0); + else + Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x2); + } else if (nr == 60 || nr == 61) { + Exception_build_stack_frame(oldpc, regs.instruction_pc, 0, nr, 0x0); + } else if (nr >= 48 && nr <= 55) { + if (regs.fpu_exp_pre) { + Exception_build_stack_frame(oldpc, regs.instruction_pc, 0, nr, 0x0); + } else { /* post-instruction */ + Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x3); + } + } else if (nr == 11 && regs.fp_unimp_ins) { + regs.fp_unimp_ins = false; + if (currprefs.cpu_model == 68040 && currprefs.fpu_model == 0) { + Exception_build_stack_frame(regs.fp_ea, currpc, regs.instruction_pc, nr, 0x4); + } else { + Exception_build_stack_frame(regs.fp_ea, currpc, 0, nr, 0x2); + } + } else { + Exception_build_stack_frame(oldpc, currpc, 0, nr, 0x0); + } +} + +void Exception_build_68000_address_error_stack_frame(uae_u16 mode, uae_u16 opcode, uaecptr fault_addr, uaecptr pc) +{ + // undocumented bits seem to contain opcode + mode |= opcode & ~31; + m68k_areg(regs, 7) -= 14; + x_put_word(m68k_areg(regs, 7) + 0, mode); + x_put_long(m68k_areg(regs, 7) + 2, fault_addr); + x_put_word(m68k_areg(regs, 7) + 6, opcode); + x_put_word(m68k_areg(regs, 7) + 8, regs.sr); + x_put_long(m68k_areg(regs, 7) + 10, pc); +} + +// Low word: Z and N +void ccr_68000_long_move_ae_LZN(uae_s32 src) +{ + CLEAR_CZNV(); + uae_s16 vsrc = (uae_s16)(src & 0xffff); + SET_ZFLG(vsrc == 0); + SET_NFLG(vsrc < 0); +} + +// Low word: N only +void ccr_68000_long_move_ae_LN(uae_s32 src) +{ + CLEAR_CZNV(); + uae_s16 vsrc = (uae_s16)(src & 0xffff); + SET_NFLG(vsrc < 0); +} + +// High word: N and Z clear. +void ccr_68000_long_move_ae_HNZ(uae_s32 src) +{ + uae_s16 vsrc = (uae_s16)(src >> 16); + if(vsrc < 0) { + SET_NFLG(1); + SET_ZFLG(0); + } else if (vsrc) { + SET_NFLG(0); + SET_ZFLG(0); + } else { + SET_NFLG(0); + } +} + +// Set normally. +void ccr_68000_long_move_ae_normal(uae_s32 src) +{ + CLEAR_CZNV(); + SET_ZFLG(src == 0); + SET_NFLG(src < 0); +} +void ccr_68000_word_move_ae_normal(uae_s16 src) +{ + CLEAR_CZNV(); + SET_ZFLG(src == 0); + SET_NFLG(src < 0); +} diff --git a/src/osdep/aarch64_helper.s b/src/osdep/aarch64_helper.s new file mode 100644 index 00000000..93322b6f --- /dev/null +++ b/src/osdep/aarch64_helper.s @@ -0,0 +1,1014 @@ +// Some functions and tests to increase performance in drawing.cpp and custom.cpp + +//.arm + +.global save_host_fp_regs +.global restore_host_fp_regs +.global copy_screen_8bit +.global copy_screen_16bit_swap +.global copy_screen_32bit_to_16bit +.global ARM_doline_n1 +.global NEON_doline_n2 +.global NEON_doline_n3 +.global NEON_doline_n4 +.global NEON_doline_n5 +.global NEON_doline_n6 +.global NEON_doline_n7 +.global NEON_doline_n8 + +.text + +.align 8 + +//---------------------------------------------------------------- +// save_host_fp_regs +//---------------------------------------------------------------- +save_host_fp_regs: + st4 {v7.2D-v10.2D}, [x0], #64 + st4 {v11.2D-v14.2D}, [x0], #64 + st1 {v15.2D}, [x0], #16 + ret + +//---------------------------------------------------------------- +// restore_host_fp_regs +//---------------------------------------------------------------- +restore_host_fp_regs: + ld4 {v7.2D-v10.2D}, [x0], #64 + ld4 {v11.2D-v14.2D}, [x0], #64 + ld1 {v15.2D}, [x0], #16 + ret + + +//---------------------------------------------------------------- +// copy_screen_8bit +// +// x0: uae_u8 *dst +// x1: uae_u8 *src +// x2: int bytes always a multiple of 64: even number of lines, number of pixel per line is multiple of 32 (320, 640, 800, 1024, 1152, 1280) +// x3: uae_u32 *clut +// +// void copy_screen_8bit(uae_u8 *dst, uae_u8 *src, int bytes, uae_u32 *clut); +// +//---------------------------------------------------------------- +copy_screen_8bit: + mov x7, #64 +copy_screen_8bit_loop: + ldrsw x4, [x1], #4 + ubfx x5, x4, #0, #8 + ldrsw x6, [x3, x5, lsl #2] + ubfx x5, x4, #8, #8 + strh w6, [x0], #2 + ldrsw x6, [x3, x5, lsl #2] + ubfx x5, x4, #16, #8 + strh w6, [x0], #2 + ldrsw x6, [x3, x5, lsl #2] + ubfx x5, x4, #24, #8 + strh w6, [x0], #2 + ldrsw x6, [x3, x5, lsl #2] + subs x7, x7, #4 + strh w6, [x0], #2 + bgt copy_screen_8bit_loop + subs x2, x2, #64 + bgt copy_screen_8bit + ret + + +//---------------------------------------------------------------- +// copy_screen_16bit_swap +// +// x0: uae_u8 *dst +// x1: uae_u8 *src +// x2: int bytes always a multiple of 128: even number of lines, 2 bytes per pixel, number of pixel per line is multiple of 32 (320, 640, 800, 1024, 1152, 1280) +// +// void copy_screen_16bit_swap(uae_u8 *dst, uae_u8 *src, int bytes); +// +//---------------------------------------------------------------- +copy_screen_16bit_swap: + ld4 {v0.2D-v3.2D}, [x1], #64 + rev16 v0.16b, v0.16b + rev16 v1.16b, v1.16b + rev16 v2.16b, v2.16b + rev16 v3.16b, v3.16b + subs w2, w2, #64 + st4 {v0.2D-v3.2D}, [x0], #64 + bne copy_screen_16bit_swap + ret + + +//---------------------------------------------------------------- +// copy_screen_32bit_to_16bit +// +// x0: uae_u8 *dst - Format (bits): rrrr rggg gggb bbbb +// x1: uae_u8 *src - Format (bytes) in memory rgba +// x2: int bytes +// +// void copy_screen_32bit_to_16bit(uae_u8 *dst, uae_u8 *src, int bytes); +// +//---------------------------------------------------------------- +copy_screen_32bit_to_16bit: + ldr x3, =Masks_rgb + ld2r {v0.4S-v1.4S}, [x3] +copy_screen_32bit_to_16bit_loop: + ld1 {v3.4S}, [x1], #16 + rev64 v3.16B, v3.16B + ushr v4.4S, v3.4S, #16 + ushr v5.4S, v3.4S, #13 + ushr v3.4S, v3.4S, #11 + bit v3.16B, v4.16B, v0.16B + bit v3.16B, v5.16B, v1.16B + xtn v3.4H, v3.4S + rev32 v3.4H, v3.4H + subs w2, w2, #16 + st1 {v3.4H}, [x0], #8 + bne copy_screen_32bit_to_16bit_loop + ret + + +//---------------------------------------------------------------- +// ARM_doline_n1 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void ARM_doline_n1(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +ARM_doline_n1: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x3, x3, x2 // real_bplpt[0] + + ldr x10, =Lookup_doline_n1 + +ARM_doline_n1_loop: + ldr w2, [x3], #4 + + ubfx x5, x2, #28, #4 + ldr w6, [x10, x5, lsl #2] + + ubfx x5, x2, #24, #4 + ldr w7, [x10, x5, lsl #2] + + ubfx x5, x2, #20, #4 + ldr w8, [x10, x5, lsl #2] + + ubfx x5, x2, #16, #4 + ldr w9, [x10, x5, lsl #2] + stp w6, w7, [x0], #8 + stp w8, w9, [x0], #8 + + ubfx x5, x2, #12, #4 + ldr w6, [x10, x5, lsl #2] + + ubfx x5, x2, #8, #4 + ldr w7, [x10, x5, lsl #2] + + ubfx x5, x2, #4, #4 + ldr w8, [x10, x5, lsl #2] + + ubfx x5, x2, #0, #4 + ldr w9, [x10, x5, lsl #2] + stp w6, w7, [x0], #8 + stp w8, w9, [x0], #8 + + subs x1, x1, #1 + bgt ARM_doline_n1_loop + + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n2 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n2(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n2: + + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + +// Load masks to registers + movi v16.8b, #0x55 + movi v17.16b, #0x03 + movi v18.8b, #1 + +NEON_doline_n2_loop: + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + + ushr v2.8b, v0.8b, #1 // tmpb = b >> shift + ushl v3.8b, v1.8b, v18.8b // tmpa = a << shift + bit v1.8b, v2.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v3.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + zip2 v4.8b, v1.8b, v0.8b + zip1 v5.8b, v1.8b, v0.8b + + zip1 v5.2d, v4.2d, v5.2d + + ushr v0.16b, v5.16b, #6 + ushr v1.16b, v5.16b, #4 + ushr v2.16b, v5.16b, #2 + + and v1.16b, v1.16b, v17.16b + and v2.16b, v2.16b, v17.16b + and v5.16b, v5.16b, v17.16b + + zip2 v21.8h, v0.8h, v1.8h + zip1 v23.8h, v0.8h, v1.8h + + zip2 v20.8h, v2.8h, v5.8h + zip1 v22.8h, v2.8h, v5.8h + + zip2 v1.4s, v21.4s, v20.4s + zip1 v3.4s, v21.4s, v20.4s + + uzp2 v0.2d, v1.2d, v1.2d + uzp2 v2.2d, v3.2d, v3.2d + + st4 { v0.d, v1.d, v2.d, v3.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n2_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v23.4s, v22.4s + zip1 v7.4s, v23.4s, v22.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n2_loop + +NEON_doline_n2_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n3 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n3(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n3: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n3_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + movi v3.8b, #0 + + ushr v4.8b, v0.8b, #1 // tmpb = b >> shift + ushl v5.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v4.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v5.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v4.8b, v2.8b, #1 // tmpb = b >> shift + bif v2.8b, v3.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v3.8b, v4.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v4.8b, v0.8b, #2 // tmpb = b >> shift + ushl v5.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v4.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v5.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v4.8b, v1.8b, #2 // tmpb = b >> shift + ushl v5.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v4.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v5.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + zip2 v4.8b, v3.8b, v2.8b + zip1 v5.8b, v3.8b, v2.8b + zip2 v6.8b, v1.8b, v0.8b + zip1 v7.8b, v1.8b, v0.8b + + zip1 v20.8h, v4.8h, v6.8h + zip1 v21.8h, v5.8h, v7.8h + + ushr v0.16b, v20.16b, #4 + ushr v1.16b, v21.16b, #4 + + and v20.16b, v20.16b, v18.16b + and v21.16b, v21.16b, v18.16b + + zip2 v5.4s, v1.4s, v21.4s + zip1 v7.4s, v1.4s, v21.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n3_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v20.4s + zip1 v7.4s, v0.4s, v20.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n3_loop + +NEON_doline_n3_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n4 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n4(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n4: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + add x5, x4, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n4_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + ld1 {v3.8b}, [x5], #8 + + ushr v4.8b, v0.8b, #1 // tmpb = b >> shift + ushl v5.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v4.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v5.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v4.8b, v2.8b, #1 // tmpb = b >> shift + ushl v5.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v4.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v2.8b, v5.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v4.8b, v0.8b, #2 // tmpb = b >> shift + ushl v5.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v4.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v5.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v4.8b, v1.8b, #2 // tmpb = b >> shift + ushl v5.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v4.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v5.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + zip2 v4.8b, v3.8b, v2.8b + zip1 v5.8b, v3.8b, v2.8b + zip2 v6.8b, v1.8b, v0.8b + zip1 v7.8b, v1.8b, v0.8b + + zip1 v20.8h, v4.8h, v6.8h + zip1 v21.8h, v5.8h, v7.8h + + ushr v0.16b, v20.16b, #4 + ushr v1.16b, v21.16b, #4 + + and v20.16b, v20.16b, v18.16b + and v21.16b, v21.16b, v18.16b + + zip2 v5.4s, v1.4s, v21.4s + zip1 v7.4s, v1.4s, v21.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n4_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v20.4s + zip1 v7.4s, v0.4s, v20.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n4_loop + +NEON_doline_n4_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n5 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n5(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n5: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + add x5, x4, #200 + add x6, x5, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n5_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + ld1 {v3.8b}, [x5], #8 + ld1 {v4.8b}, [x6], #8 + movi v5.8b, #0 + movi v6.8b, #0 + movi v7.8b, #0 + + ushr v20.8b, v0.8b, #1 // tmpb = b >> shift + ushl v21.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v2.8b, #1 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v2.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #1 // tmpb = b >> shift + bif v4.8b, v5.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v5.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v20.8b, v0.8b, #2 // tmpb = b >> shift + ushl v21.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v1.8b, #2 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #2 // tmpb = b >> shift + bif v4.8b, v6.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v6.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + + ushr v20.8b, v5.8b, #2 // tmpb = b >> shift + bif v5.8b, v7.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v7.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + + add v19.8b, v19.8b, v19.8b // now each element contains 4 + + ushr v20.8b, v3.8b, #4 + ushl v21.8b, v7.8b, v19.8b + bit v7.8b, v20.8b, v18.8b + bif v3.8b, v21.8b, v18.8b + + ushr v20.8b, v2.8b, #4 + ushl v21.8b, v6.8b, v19.8b + bit v6.8b, v20.8b, v18.8b + bif v2.8b, v21.8b, v18.8b + + ushr v20.8b, v1.8b, #4 + ushl v21.8b, v5.8b, v19.8b + bit v5.8b, v20.8b, v18.8b + bif v1.8b, v21.8b, v18.8b + + ushr v20.8b, v0.8b, #4 + ushl v21.8b, v4.8b, v19.8b + bit v4.8b, v20.8b, v18.8b + bif v0.8b, v21.8b, v18.8b + + zip1 v20.16b, v7.16b, v6.16b + zip1 v21.16b, v5.16b, v4.16b + zip1 v22.16b, v3.16b, v2.16b + zip1 v23.16b, v1.16b, v0.16b + + zip2 v0.8h, v20.8h, v21.8h + zip1 v1.8h, v20.8h, v21.8h + zip2 v2.8h, v22.8h, v23.8h + zip1 v3.8h, v22.8h, v23.8h + + zip2 v5.4s, v1.4s, v3.4s + zip1 v7.4s, v1.4s, v3.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n5_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v2.4s + zip1 v7.4s, v0.4s, v2.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n5_loop + +NEON_doline_n5_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n6 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n6(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n6: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + add x5, x4, #200 + add x6, x5, #200 + add x7, x6, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n6_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + ld1 {v3.8b}, [x5], #8 + ld1 {v4.8b}, [x6], #8 + ld1 {v5.8b}, [x7], #8 + movi v6.8b, #0 + movi v7.8b, #0 + + ushr v20.8b, v0.8b, #1 // tmpb = b >> shift + ushl v21.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v2.8b, #1 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v2.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #1 // tmpb = b >> shift + ushl v21.8b, v5.8b, v19.8b // tmpa = a << shift + bit v5.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v4.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v20.8b, v0.8b, #2 // tmpb = b >> shift + ushl v21.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v1.8b, #2 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #2 // tmpb = b >> shift + bif v4.8b, v6.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v6.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + + ushr v20.8b, v5.8b, #2 // tmpb = b >> shift + bif v5.8b, v7.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + bit v7.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + + add v19.8b, v19.8b, v19.8b // now each element contains 4 + + ushr v20.8b, v3.8b, #4 + ushl v21.8b, v7.8b, v19.8b + bit v7.8b, v20.8b, v18.8b + bif v3.8b, v21.8b, v18.8b + + ushr v20.8b, v2.8b, #4 + ushl v21.8b, v6.8b, v19.8b + bit v6.8b, v20.8b, v18.8b + bif v2.8b, v21.8b, v18.8b + + ushr v20.8b, v1.8b, #4 + ushl v21.8b, v5.8b, v19.8b + bit v5.8b, v20.8b, v18.8b + bif v1.8b, v21.8b, v18.8b + + ushr v20.8b, v0.8b, #4 + ushl v21.8b, v4.8b, v19.8b + bit v4.8b, v20.8b, v18.8b + bif v0.8b, v21.8b, v18.8b + + zip1 v20.16b, v7.16b, v6.16b + zip1 v21.16b, v5.16b, v4.16b + zip1 v22.16b, v3.16b, v2.16b + zip1 v23.16b, v1.16b, v0.16b + + zip2 v0.8h, v20.8h, v21.8h + zip1 v1.8h, v20.8h, v21.8h + zip2 v2.8h, v22.8h, v23.8h + zip1 v3.8h, v22.8h, v23.8h + + zip2 v5.4s, v1.4s, v3.4s + zip1 v7.4s, v1.4s, v3.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n6_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v2.4s + zip1 v7.4s, v0.4s, v2.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n6_loop + +NEON_doline_n6_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n7 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n7(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n7: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + add x5, x4, #200 + add x6, x5, #200 + add x7, x6, #200 + add x8, x7, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n7_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + ld1 {v3.8b}, [x5], #8 + ld1 {v4.8b}, [x6], #8 + ld1 {v5.8b}, [x7], #8 + ld1 {v6.8b}, [x8], #8 + movi v7.8b, #0 + + ushr v20.8b, v0.8b, #1 // tmpb = b >> shift + ushl v21.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v2.8b, #1 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v2.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #1 // tmpb = b >> shift + ushl v21.8b, v5.8b, v19.8b // tmpa = a << shift + bit v5.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v4.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v6.8b, #1 // tmpb = b >> shift + bif v6.8b, v7.8b, v16.8b // b = b anh bit set from tmpa if mask (0x55) is false + bit v7.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v20.8b, v0.8b, #2 // tmpb = b >> shift + ushl v21.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v1.8b, #2 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #2 // tmpb = b >> shift + ushl v21.8b, v6.8b, v19.8b // tmpa = a << shift + bit v6.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v4.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v5.8b, #2 // tmpb = b >> shift + ushl v21.8b, v7.8b, v19.8b // tmpa = a << shift + bit v7.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v5.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + add v19.8b, v19.8b, v19.8b // now each element contains 4 + + ushr v20.8b, v3.8b, #4 + ushl v21.8b, v7.8b, v19.8b + bit v7.8b, v20.8b, v18.8b + bif v3.8b, v21.8b, v18.8b + + ushr v20.8b, v2.8b, #4 + ushl v21.8b, v6.8b, v19.8b + bit v6.8b, v20.8b, v18.8b + bif v2.8b, v21.8b, v18.8b + + ushr v20.8b, v1.8b, #4 + ushl v21.8b, v5.8b, v19.8b + bit v5.8b, v20.8b, v18.8b + bif v1.8b, v21.8b, v18.8b + + ushr v20.8b, v0.8b, #4 + ushl v21.8b, v4.8b, v19.8b + bit v4.8b, v20.8b, v18.8b + bif v0.8b, v21.8b, v18.8b + + zip1 v20.16b, v7.16b, v6.16b + zip1 v21.16b, v5.16b, v4.16b + zip1 v22.16b, v3.16b, v2.16b + zip1 v23.16b, v1.16b, v0.16b + + zip2 v0.8h, v20.8h, v21.8h + zip1 v1.8h, v20.8h, v21.8h + zip2 v2.8h, v22.8h, v23.8h + zip1 v3.8h, v22.8h, v23.8h + + zip2 v5.4s, v1.4s, v3.4s + zip1 v7.4s, v1.4s, v3.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n7_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v2.4s + zip1 v7.4s, v0.4s, v2.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n7_loop + +NEON_doline_n7_exit: + ret + + +.align 8 + +//---------------------------------------------------------------- +// NEON_doline_n8 +// +// x0: uae_u32 *pixels +// x1: int wordcount +// x2: int lineno +// +// void NEON_doline_n8(uae_u32 *pixels, int wordcount, int lineno); +// +//---------------------------------------------------------------- +NEON_doline_n8: + mov x3, #1600 + mul x2, x2, x3 + ldr x3, =line_data + add x2, x3, x2 // real_bplpt[0] + add x3, x2, #200 + add x4, x3, #200 + add x5, x4, #200 + add x6, x5, #200 + add x7, x6, #200 + add x8, x7, #200 + add x9, x8, #200 + + // Load masks to registers + movi v16.8b, #0x55 + movi v17.8b, #0x33 + movi v18.16b, #0x0f + +NEON_doline_n8_loop: + movi v19.8b, #1 + + ld1 {v0.8b}, [x2], #8 + ld1 {v1.8b}, [x3], #8 + ld1 {v2.8b}, [x4], #8 + ld1 {v3.8b}, [x5], #8 + ld1 {v4.8b}, [x6], #8 + ld1 {v5.8b}, [x7], #8 + ld1 {v6.8b}, [x8], #8 + ld1 {v7.8b}, [x9], #8 + + ushr v20.8b, v0.8b, #1 // tmpb = b >> shift + ushl v21.8b, v1.8b, v19.8b // tmpa = a << shift + bit v1.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v2.8b, #1 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v2.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #1 // tmpb = b >> shift + ushl v21.8b, v5.8b, v19.8b // tmpa = a << shift + bit v5.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v4.8b, v21.8b, v16.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v6.8b, #1 // tmpb = b >> shift + ushl v21.8b, v7.8b, v19.8b // tmpa = a << shift + bit v7.8b, v20.8b, v16.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v6.8b, v21.8b, v16.8b // b = b anh bit set from tmpa if mask (0x55) is false + + add v19.8b, v19.8b, v19.8b // now each element contains 2 + + ushr v20.8b, v0.8b, #2 // tmpb = b >> shift + ushl v21.8b, v2.8b, v19.8b // tmpa = a << shift + bit v2.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v0.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v1.8b, #2 // tmpb = b >> shift + ushl v21.8b, v3.8b, v19.8b // tmpa = a << shift + bit v3.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v1.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v4.8b, #2 // tmpb = b >> shift + ushl v21.8b, v6.8b, v19.8b // tmpa = a << shift + bit v6.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v4.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + ushr v20.8b, v5.8b, #2 // tmpb = b >> shift + ushl v21.8b, v7.8b, v19.8b // tmpa = a << shift + bit v7.8b, v20.8b, v17.8b // a = a and bit set from tmpb if mask (0x55) is true + bif v5.8b, v21.8b, v17.8b // b = b and bit set from tmpa if mask (0x55) is false + + add v19.8b, v19.8b, v19.8b // now each element contains 4 + + ushr v20.8b, v3.8b, #4 + ushl v21.8b, v7.8b, v19.8b + bit v7.8b, v20.8b, v18.8b + bif v3.8b, v21.8b, v18.8b + + ushr v20.8b, v2.8b, #4 + ushl v21.8b, v6.8b, v19.8b + bit v6.8b, v20.8b, v18.8b + bif v2.8b, v21.8b, v18.8b + + ushr v20.8b, v1.8b, #4 + ushl v21.8b, v5.8b, v19.8b + bit v5.8b, v20.8b, v18.8b + bif v1.8b, v21.8b, v18.8b + + ushr v20.8b, v0.8b, #4 + ushl v21.8b, v4.8b, v19.8b + bit v4.8b, v20.8b, v18.8b + bif v0.8b, v21.8b, v18.8b + + zip1 v20.16b, v7.16b, v6.16b + zip1 v21.16b, v5.16b, v4.16b + zip1 v22.16b, v3.16b, v2.16b + zip1 v23.16b, v1.16b, v0.16b + + zip2 v0.8h, v20.8h, v21.8h + zip1 v1.8h, v20.8h, v21.8h + zip2 v2.8h, v22.8h, v23.8h + zip1 v3.8h, v22.8h, v23.8h + + zip2 v5.4s, v1.4s, v3.4s + zip1 v7.4s, v1.4s, v3.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + cmp x1, #1 // Exit from here if odd number of words + beq NEON_doline_n8_exit + + subs x1, x1, #2 // We handle 2 words (64 bit) per loop: wordcount -= 2 + + zip2 v5.4s, v0.4s, v2.4s + zip1 v7.4s, v0.4s, v2.4s + + uzp2 v4.2d, v5.2d, v5.2d + uzp2 v6.2d, v7.2d, v7.2d + + st4 { v4.d, v5.d, v6.d, v7.d }[0], [x0], #32 + + bgt NEON_doline_n8_loop + +NEON_doline_n8_exit: + ret + + + +.align 8 + +Masks_rgb: + .long 0x0000f800, 0x000007e0 + +Lookup_doline_n1: + .long 0x00000000, 0x01000000, 0x00010000, 0x01010000 + .long 0x00000100, 0x01000100, 0x00010100, 0x01010100 + .long 0x00000001, 0x01000001, 0x00010001, 0x01010001 + .long 0x00000101, 0x01000101, 0x00010101, 0x01010101 diff --git a/src/osdep/amiberry.cpp b/src/osdep/amiberry.cpp index 43434cd4..dfb0305e 100644 --- a/src/osdep/amiberry.cpp +++ b/src/osdep/amiberry.cpp @@ -4,7 +4,7 @@ * Amiberry interface * */ -#include + #include #include #include @@ -295,6 +295,13 @@ void fixtrailing(TCHAR *p) _tcscat(p, "/"); } +bool samepath(const TCHAR *p1, const TCHAR *p2) +{ + if (!_tcsicmp(p1, p2)) + return true; + return false; +} + void getpathpart(TCHAR *outpath, int size, const TCHAR *inpath) { _tcscpy(outpath, inpath); @@ -371,11 +378,11 @@ void target_fixup_options(struct uae_prefs* p) } p->picasso96_modeflags = RGBFF_CLUT | RGBFF_R5G6B5PC | RGBFF_R8G8B8A8; - if (p->gfx_size.width == 0) - p->gfx_size.width = 640; - if (p->gfx_size.height == 0) - p->gfx_size.height = 256; - p->gfx_resolution = p->gfx_size.width > 600 ? 1 : 0; + if (p->gfx_monitor.gfx_size.width == 0) + p->gfx_monitor.gfx_size.width = 640; + if (p->gfx_monitor.gfx_size.height == 0) + p->gfx_monitor.gfx_size.height = 256; + p->gfx_resolution = p->gfx_monitor.gfx_size.width > 600 ? 1 : 0; if (p->gfx_vresolution && !can_have_linedouble) // If there's not enough vertical space, cancel Line Doubling/Scanlines p->gfx_vresolution = 0; @@ -719,7 +726,7 @@ int target_cfgfile_load(struct uae_prefs* p, const char* filename, int type, int { for (auto i = 0; i < p->nr_floppies; ++i) { - if (!DISK_validate_filename(p, p->floppyslots[i].df, 0, nullptr, nullptr, nullptr)) + if (!DISK_validate_filename(p, p->floppyslots[i].df, nullptr, 0, nullptr, nullptr, nullptr)) p->floppyslots[i].df[0] = 0; disk_insert(i, p->floppyslots[i].df); if (strlen(p->floppyslots[i].df) > 0) @@ -986,7 +993,7 @@ void load_amiberry_settings(void) { trimwsa(linea); if (strlen(linea) > 0) { - if (!cfgfile_separate_linea(path, linea, option, value)) + if (!cfgfile_separate_linea (path, linea, option, value)) continue; if (cfgfile_string(option, value, "ROMName", romName, sizeof romName) @@ -1063,6 +1070,13 @@ void rename_old_adfdir() write_log("Error while trying to rename old adfdir.conf file to amiberry.conf!"); } +void target_getdate(int *y, int *m, int *d) +{ + *y = GETBDY(AMIBERRYDATE); + *m = GETBDM(AMIBERRYDATE); + *d = GETBDD(AMIBERRYDATE); +} + void target_addtorecent(const TCHAR *name, int t) { } @@ -1099,6 +1113,11 @@ void target_shutdown(void) system("sudo poweroff"); } +bool target_isrelativemode(void) +{ + return true; +} + int main(int argc, char* argv[]) { struct sigaction action{}; @@ -1295,11 +1314,11 @@ int handle_msgpump() // Handle all other keys #ifdef USE_SDL1 if (keyboard_type == KEYCODE_UNK) - inputdevice_translatekeycode(0, rEvent.key.keysym.sym, 1); + inputdevice_translatekeycode(0, rEvent.key.keysym.sym, 1, false); else - inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 1); + inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 1, false); #elif USE_SDL2 - inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 1); + inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 1, false); } #endif break; @@ -1310,11 +1329,11 @@ int handle_msgpump() #endif #ifdef USE_SDL1 if (keyboard_type == KEYCODE_UNK) - inputdevice_translatekeycode(0, rEvent.key.keysym.sym, 0); + inputdevice_translatekeycode(0, rEvent.key.keysym.sym, 0, true); else - inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 0); + inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 0, true); #elif USE_SDL2 - inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 0); + inputdevice_translatekeycode(0, rEvent.key.keysym.scancode, 0, true); } #endif break; diff --git a/src/osdep/amiberry_filesys.cpp b/src/osdep/amiberry_filesys.cpp index d838dbf1..656d3651 100644 --- a/src/osdep/amiberry_filesys.cpp +++ b/src/osdep/amiberry_filesys.cpp @@ -89,28 +89,28 @@ int my_readdir(struct my_opendir_s* mod, char* name) struct my_openfile_s { - void* h; + int h; }; void my_close(struct my_openfile_s* mos) { if (mos) - close(int(mos->h)); + close(mos->h); xfree (mos); } uae_s64 my_lseek(struct my_openfile_s* mos,const uae_s64 offset, const int pos) { - return lseek(int(mos->h), offset, pos); + return lseek(mos->h, offset, pos); } uae_s64 my_fsize(struct my_openfile_s* mos) { - uae_s64 pos = lseek(int(mos->h), 0, SEEK_CUR); - uae_s64 size = lseek(int(mos->h), 0, SEEK_END); + uae_s64 pos = lseek(mos->h, 0, SEEK_CUR); + uae_s64 size = lseek(mos->h, 0, SEEK_END); lseek(int(mos->h), pos, SEEK_SET); return size; } @@ -118,13 +118,13 @@ uae_s64 my_fsize(struct my_openfile_s* mos) unsigned int my_read(struct my_openfile_s* mos, void* b, unsigned int size) { - return read(int(mos->h), b, size); + return read(mos->h, b, size); } unsigned int my_write(struct my_openfile_s* mos, void* b, unsigned int size) { - return write(int(mos->h), b, size); + return write(mos->h, b, size); } @@ -161,9 +161,9 @@ struct my_openfile_s* my_open(const TCHAR* name, const int flags) if (!mos) return nullptr; if (flags & O_CREAT) - mos->h = reinterpret_cast(open(name, flags, 0660)); + mos->h = open(name, flags, 0660); else - mos->h = reinterpret_cast(open(name, flags)); + mos->h = open(name, flags); if (!mos->h) { xfree (mos); diff --git a/src/osdep/amiberry_gfx.cpp b/src/osdep/amiberry_gfx.cpp index 80db21cc..43dd3433 100644 --- a/src/osdep/amiberry_gfx.cpp +++ b/src/osdep/amiberry_gfx.cpp @@ -16,6 +16,7 @@ #include "amiberry_gfx.h" #include +#include "inputdevice.h" #ifdef USE_SDL1 #include #include @@ -432,11 +433,12 @@ static void wait_for_display_thread(void) void InitAmigaVidMode(struct uae_prefs* p) { /* Initialize structure for Amiga video modes */ - gfxvidinfo.drawbuffer.pixbytes = screen->format->BytesPerPixel; - gfxvidinfo.drawbuffer.bufmem = static_cast(screen->pixels); - gfxvidinfo.drawbuffer.outwidth = p->gfx_size.width; - gfxvidinfo.drawbuffer.outheight = p->gfx_size.height << p->gfx_vresolution; - gfxvidinfo.drawbuffer.rowbytes = screen->pitch; + struct amigadisplay *ad = &adisplays; + ad->gfxvidinfo.drawbuffer.pixbytes = screen->format->BytesPerPixel; + ad->gfxvidinfo.drawbuffer.bufmem = static_cast(screen->pixels); + ad->gfxvidinfo.drawbuffer.outwidth = p->gfx_monitor.gfx_size.width; + ad->gfxvidinfo.drawbuffer.outheight = p->gfx_monitor.gfx_size.height << p->gfx_vresolution; + ad->gfxvidinfo.drawbuffer.rowbytes = screen->pitch; } void graphics_subshutdown() @@ -566,9 +568,9 @@ static void open_screen(struct uae_prefs* p) } else { - p->gfx_resolution = p->gfx_size.width ? (p->gfx_size.width > 600 ? 1 : 0) : 1; - display_width = p->gfx_size.width ? p->gfx_size.width : 640; - display_height = (p->gfx_size.height ? p->gfx_size.height : 256) << p->gfx_vresolution; + p->gfx_resolution = p->gfx_monitor.gfx_size.width ? (p->gfx_monitor.gfx_size.width > 600 ? 1 : 0) : 1; + display_width = p->gfx_monitor.gfx_size.width ? p->gfx_monitor.gfx_size.width : 640; + display_height = (p->gfx_monitor.gfx_size.height ? p->gfx_monitor.gfx_size.height : 256) << p->gfx_vresolution; #ifdef USE_SDL2 if (p->scaling_method == -1) @@ -671,20 +673,21 @@ static void open_screen(struct uae_prefs* p) void update_display(struct uae_prefs* p) { + struct amigadisplay *ad = &adisplays; open_screen(p); #ifdef USE_SDL2 SDL_SetRelativeMouseMode(SDL_TRUE); #endif SDL_ShowCursor(SDL_DISABLE); - framecnt = 1; // Don't draw frame before reset done + ad->framecnt = 1; // Don't draw frame before reset done } int check_prefs_changed_gfx() { auto changed = 0; - if (currprefs.gfx_size.height != changed_prefs.gfx_size.height || - currprefs.gfx_size.width != changed_prefs.gfx_size.width || + if (currprefs.gfx_monitor.gfx_size.height != changed_prefs.gfx_monitor.gfx_size.height || + currprefs.gfx_monitor.gfx_size.width != changed_prefs.gfx_monitor.gfx_size.width || currprefs.gfx_resolution != changed_prefs.gfx_resolution || currprefs.gfx_vresolution != changed_prefs.gfx_vresolution || currprefs.gfx_iscanlines != changed_prefs.gfx_iscanlines || @@ -693,9 +696,8 @@ int check_prefs_changed_gfx() currprefs.gfx_lores_mode != changed_prefs.gfx_lores_mode || currprefs.gfx_scandoubler != changed_prefs.gfx_scandoubler) { - cfgfile_configuration_change(1); - currprefs.gfx_size.height = changed_prefs.gfx_size.height; - currprefs.gfx_size.width = changed_prefs.gfx_size.width; + currprefs.gfx_monitor.gfx_size.height = changed_prefs.gfx_monitor.gfx_size.height; + currprefs.gfx_monitor.gfx_size.width = changed_prefs.gfx_monitor.gfx_size.width; currprefs.gfx_resolution = changed_prefs.gfx_resolution; currprefs.gfx_vresolution = changed_prefs.gfx_vresolution; currprefs.gfx_iscanlines = changed_prefs.gfx_iscanlines; @@ -989,11 +991,13 @@ int GetSurfacePixelFormat() int graphics_init(bool mousecapture) { + inputdevice_unacquire(); graphics_subinit(); if (!init_colors()) return 0; + inputdevice_acquire(TRUE); return 1; } @@ -1164,7 +1168,8 @@ static int save_thumb(char* path) static int currVSyncRate = 0; bool vsync_switchmode(int hz) { - auto changed_height = changed_prefs.gfx_size.height; + struct amigadisplay* ad = &adisplays; + auto changed_height = changed_prefs.gfx_monitor.gfx_size.height; if (hz >= 55) hz = 60; @@ -1217,8 +1222,8 @@ bool vsync_switchmode(int hz) vsync_modulo = 5; // Amiga draws 5 frames while host has 6 vsyncs -> sync every 5th Amiga frame } - if (!picasso_on && !picasso_requested_on) - changed_prefs.gfx_size.height = changed_height; + if (!ad->picasso_on && !ad->picasso_requested_on) + changed_prefs.gfx_monitor.gfx_size.height = changed_height; return true; } @@ -1227,7 +1232,7 @@ bool target_graphics_buffer_update() { auto rate_changed = false; - if (currprefs.gfx_size.height != changed_prefs.gfx_size.height) + if (currprefs.gfx_monitor.gfx_size.height != changed_prefs.gfx_monitor.gfx_size.height) { update_display(&changed_prefs); rate_changed = true; @@ -1247,22 +1252,21 @@ bool target_graphics_buffer_update() #ifdef PICASSO96 -int picasso_palette(struct MyCLUTEntry *clut) +int picasso_palette(struct MyCLUTEntry *CLUT, uae_u32 *clut) { - auto changed = 0; - for (auto i = 0; i < 256; i++) - { - int r = clut[i].Red; - int g = clut[i].Green; - int b = clut[i].Blue; - //auto v = CONVERT_RGB(r << 16 | g << 8 | b); - uae_u32 v = (doMask256(r, red_bits, red_shift) - | doMask256(g, green_bits, green_shift) - | doMask256(b, blue_bits, blue_shift)) - | doMask256(0xff, alpha_bits, alpha_shift); - if (v != picasso_vidinfo.clut[i]) - { - picasso_vidinfo.clut[i] = v; + int changed = 0; + + for (int i = 0; i < 256; i++) { + int r = CLUT[i].Red; + int g = CLUT[i].Green; + int b = CLUT[i].Blue; + uae_u32 v = (doMask256 (r, red_bits, red_shift) + | doMask256 (g, green_bits, green_shift) + | doMask256 (b, blue_bits, blue_shift)) + | doMask256 (0xff, alpha_bits, alpha_shift); + if (v != clut[i]) { + //write_log (_T("%d:%08x\n"), i, v); + clut[i] = v; changed = 1; } } @@ -1413,7 +1417,7 @@ void gfx_set_picasso_modeinfo(uae_u32 w, uae_u32 h, uae_u32 depth, RGBFTYPE rgbf void gfx_set_picasso_colors(RGBFTYPE rgbfmt) { - alloc_colors_picasso(red_bits, green_bits, blue_bits, red_shift, green_shift, blue_shift, rgbfmt); + alloc_colors_picasso(red_bits, green_bits, blue_bits, red_shift, green_shift, blue_shift, rgbfmt, p96_rgbx16); } uae_u8* gfx_lock_picasso() diff --git a/src/osdep/amiberry_gui.cpp b/src/osdep/amiberry_gui.cpp index 056b2e82..b8d64f2d 100644 --- a/src/osdep/amiberry_gui.cpp +++ b/src/osdep/amiberry_gui.cpp @@ -58,6 +58,8 @@ struct gui_msg gui_msglist[] = { { NUMSG_ROMNEED, "One of the following system ROMs is required:\n\n%s\n\nCheck the System ROM path in the Paths panel and click Rescan ROMs." }, { NUMSG_EXPROMNEED, "One of the following expansion boot ROMs is required:\n\n%s\n\nCheck the System ROM path in the Paths panel and click Rescan ROMs." }, { NUMSG_NOMEMORY, "Out of memory or too much Z3 autoconfig space configured." }, + { NUMSG_NOCAPS, "capsimg.so not found. CAPS/IPF support not available." }, + { NUMSG_OLDCAPS, "Old version of capsimg.so found." }, { -1, "" } }; @@ -197,20 +199,6 @@ static struct romdata* scan_single_rom_2(struct zfile* f) return rd; } -static struct romdata* scan_single_rom(char* path) -{ - char tmp[MAX_DPATH]; - - strncpy (tmp, path, MAX_DPATH - 1); - auto rd = getromdatabypath(path); - if (rd && rd->crc32 == 0xffffffff) - return rd; - const auto z = zfile_fopen(path, "rb", ZFD_NORMAL); - if (!z) - return nullptr; - return scan_single_rom_2(z); -} - static int isromext(char* path) { if (!path) @@ -339,7 +327,13 @@ void ReadConfigFileList(void) removeFileExtension(tmp->Name); // If the user has many (thousands) of configs, this will take a long time if (read_config_descriptions) - cfgfile_get_description(tmp->FullPath, tmp->Description); + { + struct uae_prefs *p = cfgfile_open(tmp->FullPath, NULL); + if (p) { + cfgfile_get_description(p, NULL, tmp->Description, NULL); + cfgfile_close(p); + } + } ConfigFilesList.emplace_back(tmp); } } @@ -354,23 +348,55 @@ ConfigFileInfo* SearchConfigInList(const char* name) return nullptr; } - -static void prefs_to_gui() +static void clearallkeys (void) { + inputdevice_updateconfig (&changed_prefs, &currprefs); +} + +void setmouseactive(int active) +{ + if (active) { + inputdevice_acquire(TRUE); + } else { + inputdevice_acquire (FALSE); + inputdevice_releasebuttons(); + } +} + +static void prefs_to_gui(struct uae_prefs *p) +{ + default_prefs(&workprefs, false, 0); + copy_prefs(p, &workprefs); /* filesys hack */ changed_prefs.mountitems = currprefs.mountitems; memcpy(&changed_prefs.mountconfig, &currprefs.mountconfig, MOUNT_CONFIG_SIZE * sizeof(struct uaedev_config_info)); + set_config_changed (); } static void gui_to_prefs(void) { + /* Always copy our prefs to changed_prefs, ... */ + copy_prefs(&workprefs, &changed_prefs); /* filesys hack */ currprefs.mountitems = changed_prefs.mountitems; memcpy(&currprefs.mountconfig, &changed_prefs.mountconfig, MOUNT_CONFIG_SIZE * sizeof(struct uaedev_config_info)); fixup_prefs(&changed_prefs, true); } +static void get_settings(void) +{ + memset (&workprefs, 0, sizeof (struct uae_prefs)); + prefs_to_gui(&changed_prefs); + + run_gui(); + gui_to_prefs(); + + if(quit_program) + screen_is_picasso = 0; + + update_display(&changed_prefs); +} static void after_leave_gui() { @@ -402,16 +428,15 @@ int gui_init() if (lstAvailableROMs.empty()) RescanROMs(); - prefs_to_gui(); - run_gui(); - gui_to_prefs(); + get_settings(); + if (quit_program < 0) quit_program = -quit_program; if (quit_program == UAE_QUIT) ret = -2; // Quit without start of emulator - update_display(&changed_prefs); - + inputdevice_acquire (TRUE); + after_leave_gui(); emulating = 1; return ret; @@ -498,26 +523,22 @@ void gui_display(int shortcut) graphics_subshutdown(); - prefs_to_gui(); - run_gui(); - gui_to_prefs(); - - if (quit_program) - screen_is_picasso = 0; + get_settings(); black_screen_now(); - update_display(&changed_prefs); - - reset_sound(); - resume_sound(); - blkdev_exitgui(); - - after_leave_gui(); - - gui_update(); - + gui_update (); gui_purge_events(); + + reset_sound(); + after_leave_gui(); + clearallkeys (); + blkdev_exitgui(); + resume_sound(); + + inputdevice_acquire (TRUE); + setmouseactive(1); + fpscounter_reset(); pause_emulation = 0; } @@ -609,7 +630,7 @@ void gui_fps(int fps, int idle, int color) gui_led(LED_SND, (gui_data.sndbuf_status > 1 || gui_data.sndbuf_status < 0) ? 0 : 1, -1); } -void gui_led(int led, int on) +void gui_led(int led, int on, int brightness) { unsigned char kbd_led_status; @@ -764,7 +785,7 @@ bool DevicenameExists(const char* name) auto uci = &changed_prefs.mountconfig[i]; const auto ci = &uci->ci; - if (ci->devname[0]) + if (ci->devname && ci->devname[0]) { if (!strcmp(ci->devname, name)) return true; diff --git a/src/osdep/amiberry_hardfile.cpp b/src/osdep/amiberry_hardfile.cpp index 147f8559..a1c7d795 100644 --- a/src/osdep/amiberry_hardfile.cpp +++ b/src/osdep/amiberry_hardfile.cpp @@ -1,7 +1,6 @@ -#include -#include -#include -#include +#include "stdlib.h" +#include "stdio.h" +#include #include "sysdeps.h" diff --git a/src/osdep/amiberry_input.cpp b/src/osdep/amiberry_input.cpp index 0d74ff95..685771b3 100644 --- a/src/osdep/amiberry_input.cpp +++ b/src/osdep/amiberry_input.cpp @@ -1,6 +1,6 @@ -#include -#include -#include +#include "stdio.h" +#include "string.h" +#include #include "sysdeps.h" #include "options.h" diff --git a/src/osdep/amiberry_mem.cpp b/src/osdep/amiberry_mem.cpp index 3393c905..c28ceeaa 100644 --- a/src/osdep/amiberry_mem.cpp +++ b/src/osdep/amiberry_mem.cpp @@ -1,6 +1,5 @@ -#include -#include -#include +#include +#include "string.h" #include "sysdeps.h" #include "options.h" @@ -88,9 +87,14 @@ void alloc_AmigaMem(void) // Allocation successful -> we can use natmem_offset for entire memory access at real address changed_prefs.z3autoconfig_start = currprefs.z3autoconfig_start = Z3BASE_REAL; z3_base_adr = Z3BASE_REAL; +#if defined(CPU_AARCH64) + write_log("Allocated 16 MB for 24-bit area (0x%016lx) and %d MB for Z3 and RTG at real address (0x%016lx - 0x%016lx)\n", + regs.natmem_offset, ADDITIONAL_MEMSIZE / (1024 * 1024), additional_mem, additional_mem + ADDITIONAL_MEMSIZE + BARRIER); +#else write_log("Allocated 16 MB for 24-bit area (0x%08x) and %d MB for Z3 and RTG at real address (0x%08x - 0x%08x)\n", regs.natmem_offset, ADDITIONAL_MEMSIZE / (1024 * 1024), additional_mem, additional_mem + ADDITIONAL_MEMSIZE + BARRIER ); +#endif set_expamem_z3_hack_mode(Z3MAPPING_REAL); return; } @@ -102,9 +106,13 @@ void alloc_AmigaMem(void) // Allocation successful -> we can use natmem_offset for entire memory access at fake address changed_prefs.z3autoconfig_start = currprefs.z3autoconfig_start = Z3BASE_UAE; z3_base_adr = Z3BASE_UAE; - write_log("Allocated 16 MB for 24-bit area (0x%08x) and %d MB for Z3 and RTG at fake address (0x%08x - 0x%08x)\n", - regs.natmem_offset, ADDITIONAL_MEMSIZE / (1024 * 1024), additional_mem, additional_mem + ADDITIONAL_MEMSIZE + BARRIER - ); +#if defined(CPU_AARCH64) + write_log("Allocated 16 MB for 24-bit area (0x%016lx) and %d MB for Z3 and RTG at fake address (0x%016lx - 0x%016lx)\n", + regs.natmem_offset, ADDITIONAL_MEMSIZE / (1024 * 1024), additional_mem, additional_mem + ADDITIONAL_MEMSIZE + BARRIER); +#else + write_log("Allocated 16 MB for 24-bit area (0x%08x) and %d MB for Z3 and RTG at fake address (0x%08x - 0x%08x)\n", + regs.natmem_offset, ADDITIONAL_MEMSIZE / (1024 * 1024), additional_mem, additional_mem + ADDITIONAL_MEMSIZE + BARRIER); +#endif set_expamem_z3_hack_mode(Z3MAPPING_UAE); return; } @@ -123,6 +131,10 @@ void alloc_AmigaMem(void) changed_prefs.z3autoconfig_start = currprefs.z3autoconfig_start = Z3BASE_UAE; z3_base_adr = Z3BASE_UAE; write_log("Allocated %d MB for entire memory\n", natmem_size / (1024 * 1024)); +#if defined(CPU_AARCH64) + if(((uae_u64)(regs.natmem_offset + natmem_size + BARRIER) & 0xffffffff00000000) != 0) + write_log("Memory address is higher than 32 bit. JIT will crash\n"); +#endif return; } @@ -142,6 +154,10 @@ void alloc_AmigaMem(void) write_log("Reserved: %p-%p (0x%08x %dM)\n", regs.natmem_offset, (uae_u8*)regs.natmem_offset + natmem_size, natmem_size, natmem_size >> 20); +#if defined(CPU_AARCH64) + if(((uae_u64)(regs.natmem_offset + natmem_size + BARRIER) & 0xffffffff00000000) != 0) + write_log("Memory address is higher than 32 bit. JIT will crash\n"); +#endif } @@ -566,3 +582,10 @@ bool init_shm(void) memory_hardreset(2); return true; } + +void free_shm (void) +{ + for (int i = 0; i < MAX_RAM_BOARDS; i++) { + ortgmem_type[i] = -1; + } +} diff --git a/src/osdep/amiberry_rp9.cpp b/src/osdep/amiberry_rp9.cpp index 218a32f8..f3e29e9d 100644 --- a/src/osdep/amiberry_rp9.cpp +++ b/src/osdep/amiberry_rp9.cpp @@ -1,19 +1,25 @@ -#include +#include #include -#include #include #include "sysdeps.h" +#include "config.h" +#include "uae.h" #include "options.h" +#include "gui.h" #include "disk.h" #include "fsdb.h" #include "memory.h" #include "newcpu.h" #include "custom.h" #include "filesys.h" +#include "autoconf.h" #include "zfile.h" #include "archivers/zip/unzip.h" #include +#include +#include + #define RP9_MANIFEST _T("rp9-manifest.xml") #define MAX_MANIFEST_ENTRY 256 @@ -202,17 +208,17 @@ static void parse_clip(struct uae_prefs* p, xmlNode* node) else width = width / 4; // Use Lores in OCS/ECS if (width <= 320) - p->gfx_size.width = 320; + p->gfx_monitor.gfx_size.width = 320; else if (width <= 352) - p->gfx_size.width = 352; + p->gfx_monitor.gfx_size.width = 352; else if (width <= 384) - p->gfx_size.width = 384; + p->gfx_monitor.gfx_size.width = 384; else if (width <= 640) - p->gfx_size.width = 640; + p->gfx_monitor.gfx_size.width = 640; else if (width <= 704) - p->gfx_size.width = 704; + p->gfx_monitor.gfx_size.width = 704; else - p->gfx_size.width = 768; + p->gfx_monitor.gfx_size.width = 768; xmlFree(attr); } attr = xmlGetProp(curr_node, reinterpret_cast("height")); @@ -220,17 +226,17 @@ static void parse_clip(struct uae_prefs* p, xmlNode* node) { height = atoi(reinterpret_cast(attr)) / 2; if (height <= 200) - p->gfx_size.height = 200; + p->gfx_monitor.gfx_size.height = 200; else if (height <= 216) - p->gfx_size.height = 216; + p->gfx_monitor.gfx_size.height = 216; else if (height <= 240) - p->gfx_size.height = 240; + p->gfx_monitor.gfx_size.height = 240; else if (height <= 256) - p->gfx_size.height = 256; + p->gfx_monitor.gfx_size.height = 256; else if (height <= 262) - p->gfx_size.height = 262; + p->gfx_monitor.gfx_size.height = 262; else - p->gfx_size.height = 270; + p->gfx_monitor.gfx_size.height = 270; xmlFree(attr); } break; diff --git a/src/osdep/arm_helper.s b/src/osdep/arm_helper.s index 8e45c390..622e81c3 100644 --- a/src/osdep/arm_helper.s +++ b/src/osdep/arm_helper.s @@ -2,14 +2,31 @@ .arm +.global save_host_fp_regs +.global restore_host_fp_regs .global copy_screen_8bit -.global copy_screen_16bit_swap_arm -.global copy_screen_32bit_to_16bit_arm +.global copy_screen_16bit_swap +.global copy_screen_32bit_to_16bit .text .align 8 +@---------------------------------------------------------------- +@ save_host_fp_regs +@---------------------------------------------------------------- +save_host_fp_regs: + vstmia r0!, {d7-d15} + bx lr + +@---------------------------------------------------------------- +@ restore_host_fp_regs +@---------------------------------------------------------------- +restore_host_fp_regs: + vldmia r0!, {d7-d15} + bx lr + + @---------------------------------------------------------------- @ copy_screen_8bit @ @@ -50,35 +67,35 @@ copy_screen_8bit_loop_2: @---------------------------------------------------------------- -@ copy_screen_16bit_swap_arm +@ copy_screen_16bit_swap @ @ r0: uae_u8 *dst @ r1: uae_u8 *src @ r2: int bytes always a multiple of 128: even number of lines, 2 bytes per pixel, number of pixel per line is multiple of 32 (320, 640, 800, 1024, 1152, 1280) @ -@ void copy_screen_16bit_swap_arm(uae_u8 *dst, uae_u8 *src, int bytes); +@ void copy_screen_16bit_swap(uae_u8 *dst, uae_u8 *src, int bytes); @ @---------------------------------------------------------------- -copy_screen_16bit_swap_arm: +copy_screen_16bit_swap: ldr r3, [r1], #4 rev16 r3, r3 str r3, [r0], #4 subs r2, r2, #4 -bne copy_screen_16bit_swap_arm +bne copy_screen_16bit_swap bx lr @---------------------------------------------------------------- -@ copy_screen_32bit_to_16bit_arm +@ copy_screen_32bit_to_16bit @ @ r0: uae_u8 *dst - Format (bits): rrrr rggg gggb bbbb @ r1: uae_u8 *src - Format (bytes) in memory rgba @ r2: int bytes @ -@ void copy_screen_32bit_to_16bit_arm(uae_u8 *dst, uae_u8 *src, int bytes); +@ void copy_screen_32bit_to_16bit(uae_u8 *dst, uae_u8 *src, int bytes); @ @---------------------------------------------------------------- -copy_screen_32bit_to_16bit_arm: +copy_screen_32bit_to_16bit: stmdb sp!, {r4-r6, lr} copy_screen_32bit_to_16bit_loop: ldr r3, [r1], #4 diff --git a/src/osdep/bsdsocket_host.cpp b/src/osdep/bsdsocket_host.cpp index 99af447d..bd61a866 100644 --- a/src/osdep/bsdsocket_host.cpp +++ b/src/osdep/bsdsocket_host.cpp @@ -21,20 +21,6 @@ * along with this program; if not, write to the Free Software Foundation, * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include #include "sysdeps.h" @@ -45,32 +31,20 @@ #include "bsdsocket.h" #include "native2amiga.h" -#ifndef BSDSOCKET - -volatile int bsd_int_requested; - -void bsdsock_fake_int_handler(void) -{ -} - -#else - +#include +#include #include #include #ifdef HAVE_SYS_FILIO_H # include #endif +#include +#include #include #include #include - -//#define DEBUG_BSDSOCKET -#ifdef DEBUG_BSDSOCKET -#define DEBUG_LOG write_log -#else -#define DEBUG_LOG(...) do ; while(0) -#endif +#include #define WAITSIGNAL waitsig (ctx, sb) #ifdef ANDROID @@ -80,7 +54,6 @@ void bsdsock_fake_int_handler(void) /* Sigqueue is unsafe on SMP machines. * Temporary work-around. */ -//#define SETSIGNAL addtosigqueue (sb, 0) #define SETSIGNAL \ do { \ uae_Signal (sb->ownertask, sb->sigstosend | ((uae_u32) 1) << sb->signal); \ @@ -100,15 +73,8 @@ void bsdsock_fake_int_handler(void) #define S_GL_result(res) sb->resultval = (res) -uae_u32 bsdthr_Accept_2 (SB); -uae_u32 bsdthr_Recv_2 (SB); -uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB); -uae_u32 bsdthr_SendRecvAcceptConnect (uae_u32 (*tryfunc)(SB), SB); -uae_u32 bsdthr_Send_2 (SB); -uae_u32 bsdthr_Connect_2 (SB); -uae_u32 bsdthr_WaitSelect (SB); -uae_u32 bsdthr_Wait (SB); -void clearsockabort (SB); +static uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB); +static void clearsockabort (SB); static uae_sem_t sem_queue = 0; @@ -193,7 +159,6 @@ static int mapsockoptlevel (int level) case 98: return IPPROTO_ENCAP; default: - DEBUG_LOG ("Unknown sockopt level %d\n", level); return level; } } @@ -249,8 +214,6 @@ static int mapsockoptname (int level, int optname) return SO_TYPE; default: - DEBUG_LOG("Invalid setsockopt option 0x%x for level %d\n", - optname, level); return -1; } break; @@ -281,8 +244,6 @@ static int mapsockoptname (int level, int optname) return IP_ADD_MEMBERSHIP; default: - DEBUG_LOG ("Invalid setsockopt option 0x%x for level %d\n", - optname, level); return -1; } break; @@ -295,14 +256,11 @@ static int mapsockoptname (int level, int optname) return TCP_MAXSEG; default: - DEBUG_LOG ("Invalid setsockopt option 0x%x for level %d\n", - optname, level); return -1; } break; default: - DEBUG_LOG ("Unknown level %d\n", level); return -1; } } @@ -342,8 +300,7 @@ static void mapsockoptreturn(TrapContext *ctx, int level, int optname, uae_u32 o break; case SO_ERROR: - DEBUG_LOG("New errno is %d\n", mapErrno(*(int *)buf)); - trap_put_long (ctx, optval, mapErrno(*static_cast(buf))); + trap_put_long (ctx, optval, mapErrno(*static_cast(buf))); break; default: break; @@ -493,17 +450,6 @@ STATIC_INLINE void bsd_amigaside_FD_SET (TrapContext *ctx, int n, uae_u32 set) trap_put_long(ctx, set, trap_get_long(ctx, set) | (1 << (n % 32))); } -#ifdef DEBUG_BSDSOCKET -static void printSockAddr (struct sockaddr_in *in) -{ - DEBUG_LOG ("Family %d, ", in->sin_family); - DEBUG_LOG ("Port %d,", ntohs (in->sin_port)); - DEBUG_LOG ("Address %s,", inet_ntoa (in->sin_addr)); -} -#else -#define printSockAddr(sockAddr) -#endif - /* * Copy a sockaddr object from amiga space to native space */ @@ -590,7 +536,6 @@ static void copyHostent (const struct hostent *hostent, SB) trap_put_long (sb->context, sb->hostent, aptr); addstr (sb->context, &aptr, hostent->h_name); - BSDTRACE (("OK (%s)\n",hostent->h_name)); bsdsocklib_seterrno (sb->context, sb, 0); } @@ -642,7 +587,7 @@ static void copyProtoent (TrapContext *ctx, SB, const struct protoent *p) -uae_u32 bsdthr_WaitSelect (SB) +static uae_u32 bsdthr_WaitSelect (SB) { fd_set sets [3]; int i, s, set, a_s, max; @@ -650,11 +595,6 @@ uae_u32 bsdthr_WaitSelect (SB) struct timeval tv; int r; - DEBUG_LOG ("WaitSelect: %d 0x%x 0x%x 0x%x 0x%x 0x%x\n", sb->nfds, sb->sets [0], sb->sets [1], sb->sets [2], sb->timeout, sb->sigmp); - - if (sb->timeout) - DEBUG_LOG ("WaitSelect: timeout %d %d\n", trap_get_long (sb->context, sb->timeout), trap_get_long (sb->context, sb->timeout + 4)); - FD_ZERO (&sets [0]); FD_ZERO (&sets [1]); FD_ZERO (&sets [2]); @@ -670,7 +610,6 @@ uae_u32 bsdthr_WaitSelect (SB) for (i = 0; i < sb->nfds; i++) { if (bsd_amigaside_FD_ISSET (sb->context, i, a_set)) { s = getsock (sb->context, sb, i + 1); - DEBUG_LOG ("WaitSelect: AmigaSide %d set. NativeSide %d.\n", i, s); if (s == -1) { write_log ("BSDSOCK: WaitSelect() called with invalid descriptor %d in set %d.\n", i, set); } else { @@ -689,14 +628,11 @@ uae_u32 bsdthr_WaitSelect (SB) tv.tv_usec = trap_get_long (sb->context, sb->timeout + 4); } - DEBUG_LOG("Select going to select\n"); r = select (max, &sets [0], &sets [1], &sets [2], (sb->timeout == 0) ? NULL : &tv); - DEBUG_LOG("Select returns %d, errno is %d\n", r, errno); if( r > 0 ) { /* Socket told us to abort */ if (FD_ISSET (sb->sockabort[0], &sets[0])) { /* read from the pipe to reset it */ - DEBUG_LOG ("WaitSelect aborted from signal\n"); r = 0; for (set = 0; set < 3; set++) if (sb->sets [set] != 0) @@ -713,8 +649,6 @@ uae_u32 bsdthr_WaitSelect (SB) a_s = getsock (sb->context, sb, i + 1); if (a_s != -1) { if (FD_ISSET (a_s, &sets [set])) { - DEBUG_LOG ("WaitSelect: NativeSide %d set. AmigaSide %d.\n", a_s, i); - bsd_amigaside_FD_SET (sb->context, i, a_set); } } @@ -726,14 +660,13 @@ uae_u32 bsdthr_WaitSelect (SB) if (sb->sets [set] != 0) bsd_amigaside_FD_ZERO (sb->context, sb->sets [set]); } - DEBUG_LOG ("WaitSelect: r=%d errno=%d\n", r, errno); return r; } -uae_u32 bsdthr_Accept_2 (SB) +static uae_u32 bsdthr_Accept_2 (SB) { int foo, s, s2; - long flags; + uae_s32 flags; struct sockaddr_in addr; socklen_t hlen = sizeof (struct sockaddr_in); @@ -743,8 +676,6 @@ uae_u32 bsdthr_Accept_2 (SB) fcntl (s, F_SETFL, flags & ~O_NONBLOCK); /* @@@ Don't do this if it's supposed to stay nonblocking... */ s2 = getsd (sb->context, sb, s); sb->ftable[s2-1] = sb->ftable[sb->len]; /* new socket inherits the old socket's properties */ - DEBUG_LOG ("Accept: AmigaSide %d, NativeSide %d, len %d(%d)", sb->resultval, s, hlen, trap_get_long (sb->context, sb->a_addrlen)); - printSockAddr (&addr); foo = trap_get_long (sb->context, sb->a_addrlen); if (foo > 16) trap_put_long (sb->context, sb->a_addrlen, 16); @@ -755,19 +686,17 @@ uae_u32 bsdthr_Accept_2 (SB) } } -uae_u32 bsdthr_Recv_2 (SB) +static uae_u32 bsdthr_Recv_2 (SB) { int foo; if (sb->from == 0) { foo = recv (sb->s, sb->buf, sb->len, sb->flags /*| MSG_NOSIGNAL*/); - DEBUG_LOG ("recv2, recv returns %d, errno is %d\n", foo, errno); } else { struct sockaddr_in addr; socklen_t l = sizeof (struct sockaddr_in); int i = trap_get_long (sb->context, sb->fromlen); copysockaddr_a2n (sb->context, &addr, sb->from, i); foo = recvfrom (sb->s, sb->buf, sb->len, sb->flags | MSG_NOSIGNAL, (struct sockaddr *)&addr, &l); - DEBUG_LOG ("recv2, recvfrom returns %d, errno is %d\n", foo, errno); if (foo >= 0) { copysockaddr_n2a (sb->context, sb->from, &addr, l); trap_put_long (sb->context, sb->fromlen, l); @@ -776,7 +705,7 @@ uae_u32 bsdthr_Recv_2 (SB) return foo; } -uae_u32 bsdthr_Send_2 (SB) +static uae_u32 bsdthr_Send_2 (SB) { if (sb->to == 0) { return send (sb->s, sb->buf, sb->len, sb->flags | MSG_NOSIGNAL); @@ -788,7 +717,7 @@ uae_u32 bsdthr_Send_2 (SB) } } -uae_u32 bsdthr_Connect_2 (SB) +static uae_u32 bsdthr_Connect_2 (SB) { if (sb->action == 1) { struct sockaddr_in addr; @@ -796,7 +725,6 @@ uae_u32 bsdthr_Connect_2 (SB) int retval; copysockaddr_a2n (sb->context, &addr, sb->a_addr, sb->a_addrlen); retval = connect (sb->s, reinterpret_cast(&addr), len); - DEBUG_LOG ("Connect returns %d, errno is %d\n", retval, errno); /* Hack: I need to set the action to something other than * 1 but I know action == 2 does the correct thing */ @@ -811,22 +739,21 @@ uae_u32 bsdthr_Connect_2 (SB) bar = sizeof (foo); if (getsockopt (sb->s, SOL_SOCKET, SO_ERROR, &foo, &bar) == 0) { errno = foo; - DEBUG_LOG("Connect status is %d\n", foo); return (foo == 0) ? 0 : -1; } return -1; } } -uae_u32 bsdthr_SendRecvAcceptConnect (uae_u32 (*tryfunc)(SB), SB) +static uae_u32 bsdthr_SendRecvAcceptConnect (uae_u32 (*tryfunc)(SB), SB) { return bsdthr_blockingstuff (tryfunc, sb); } -uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB) +static uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB) { int done = 0, foo; - long flags; + uae_s32 flags; int nonblock; if ((flags = fcntl (sb->s, F_GETFL)) == -1) flags = 0; @@ -853,7 +780,6 @@ uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB) num = select (maxfd + 1, &readset, &writeset, &exceptset, NULL); if (num == -1) { - DEBUG_LOG ("Blocking select(%d) returns -1,errno is %d\n", sb->sockabort[0],errno); fcntl (sb->s, F_SETFL, flags); return -1; } @@ -861,10 +787,7 @@ uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB) if (FD_ISSET (sb->sockabort[0], &readset) || FD_ISSET (sb->sockabort[0], &writeset)) { /* reset sock abort pipe */ /* read from the pipe to reset it */ - DEBUG_LOG ("select aborted from signal\n"); - clearsockabort (sb); - DEBUG_LOG ("Done read\n"); errno = EINTR; done = 1; } else { @@ -879,23 +802,18 @@ uae_u32 bsdthr_blockingstuff (uae_u32 (*tryfunc)(SB), SB) } -static void *bsdlib_threadfunc (void *arg) +static int bsdlib_threadfunc (void *arg) { struct socketbase *sb = static_cast(arg); - DEBUG_LOG ("THREAD_START\n"); - while (1) { uae_sem_wait (&sb->sem); TrapContext *ctx = sb->context; - DEBUG_LOG ("Socket thread got action %d (sb=0x%08x)\n", sb->action, sb); - switch (sb->action) { case 0: /* kill thread (CloseLibrary) */ - DEBUG_LOG ("THREAD_END\n"); - uae_sem_destroy (&sb->sem); - return NULL; + uae_sem_destroy (&sb->sem); + return 0; case 1: /* Connect */ sb->resultval = bsdthr_SendRecvAcceptConnect (bsdthr_Connect_2, sb); @@ -947,7 +865,7 @@ static void *bsdlib_threadfunc (void *arg) SETSIGNAL; } - return NULL; /* Just to keep GCC happy.. */ + return 0; /* Just to keep GCC happy.. */ } @@ -997,9 +915,6 @@ void host_recvfrom (TrapContext *ctx, SB, uae_u32 sd, uae_u32 msg, uae_u8* hmsg, { int s = getsock (ctx, sb, sd + 1); - DEBUG_LOG ("Recv[from](%p, %x, %x, %d, %x, %x, %u)\n", - sb, sd, msg, len, flags, addr, addrlen); - if (s == -1) { sb->resultval = -1; bsdsocklib_seterrno (ctx, sb, 9); /* EBADF */ @@ -1046,10 +961,6 @@ void host_setsockopt (SB, uae_u32 sd, uae_u32 level, uae_u32 optname, uae_u32 op if (buf) free(buf); SETERRNO; - - DEBUG_LOG ("setsockopt: sock %d, level %d, 'name' %d(%d), len %d -> %d, %d\n", - s, level, optname, nativeoptname, optlen, - sb->resultval, errno); } uae_u32 host_getsockname (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u32 namelen) @@ -1058,17 +969,13 @@ uae_u32 host_getsockname (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u3 socklen_t len = sizeof (struct sockaddr_in); struct sockaddr_in addr; - DEBUG_LOG ("getsockname(%u, 0x%x, %u) -> ", sd, name, len); - s = getsock (ctx, sb, sd + 1); if (s != -1) { if (getsockname (s, (struct sockaddr *)&addr, &len)) { SETERRNO; - DEBUG_LOG ("failed (%d)\n", sb->sb_errno); } else { int a_nl; - DEBUG_LOG ("okay\n"); a_nl = trap_get_long (ctx, namelen); if (!trap_valid_address(ctx, name, a_nl)) return -1; @@ -1088,17 +995,13 @@ uae_u32 host_getpeername (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u3 socklen_t len = sizeof (struct sockaddr_in); struct sockaddr_in addr; - DEBUG_LOG ("getpeername(%u, 0x%x, %u) -> ", sd, name, len); - s = getsock (ctx, sb, sd + 1); if (s != -1) { if (getpeername (s, (struct sockaddr *)&addr, &len)) { SETERRNO; - DEBUG_LOG ("failed (%d)\n", sb->sb_errno); } else { int a_nl; - DEBUG_LOG ("okay\n"); a_nl = trap_get_long (ctx, namelen); if (!trap_valid_address(ctx, name, a_nl)) return -1; @@ -1139,7 +1042,6 @@ void host_WaitSelect (TrapContext *ctx, SB, uae_u32 nfds, uae_u32 readfds, uae_u trap_call_add_dreg (ctx, 1, wssigs); sigs = trap_call_lib (ctx, trap_get_long (ctx, 4), -0x132) & wssigs; // SetSignal() if (sigs) { - DEBUG_LOG ("WaitSelect preempted by signals 0x%08x\n", sigs & wssigs); trap_put_long (ctx, sigmp, sigs); // Check for zero address -> otherwise WinUAE crashes if (readfds) fd_zero (ctx, readfds, nfds); @@ -1185,8 +1087,6 @@ void host_WaitSelect (TrapContext *ctx, SB, uae_u32 nfds, uae_u32 readfds, uae_u if (sigs & wssigs) { /* Received the signals we were waiting on */ - DEBUG_LOG ("WaitSelect: got signal(s) %x\n", sigs); - if (!(sigs & (((uae_u32)1) << sb->signal))) { sockabort (sb); WAITSIGNAL; @@ -1200,8 +1100,6 @@ void host_WaitSelect (TrapContext *ctx, SB, uae_u32 nfds, uae_u32 readfds, uae_u bsdsocklib_seterrno (ctx, sb, 0); } else if (sigs & sb->eintrsigs) { /* Wait select was interrupted */ - DEBUG_LOG ("WaitSelect: interrupted\n"); - if (!(sigs & (((uae_u32)1) << sb->signal))) { sockabort (sb); WAITSIGNAL; @@ -1229,7 +1127,6 @@ void host_accept (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u32 namele return; } - DEBUG_LOG ("accept(%d, %x, %x)\n", sb->s, name, namelen); sb->a_addr = name; sb->a_addrlen = namelen; sb->action = 6; @@ -1239,7 +1136,6 @@ void host_accept (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u32 namele uae_sem_post (&sb->sem); WAITSIGNAL; - DEBUG_LOG ("Accept returns %d\n", sb->resultval); } int host_socket (TrapContext *ctx, SB, int af, int type, int protocol) @@ -1247,13 +1143,8 @@ int host_socket (TrapContext *ctx, SB, int af, int type, int protocol) int sd; int s; - DEBUG_LOG ("socket(%s,%s,%d) -> ",af == AF_INET ? "AF_INET" : "AF_other", - type == SOCK_STREAM ? "SOCK_STREAM" : type == SOCK_DGRAM ? - "SOCK_DGRAM " : "SOCK_RAW", protocol); - if ((s = socket (af, type, protocol)) == -1) { SETERRNO; - DEBUG_LOG ("failed (%d)\n", sb->sb_errno); return -1; } else { int arg = 1; @@ -1262,7 +1153,6 @@ int host_socket (TrapContext *ctx, SB, int af, int type, int protocol) } sb->ftable[sd-1] = SF_BLOCKING; - DEBUG_LOG ("socket returns Amiga %d, NativeSide %d\n", sd - 1, s); return sd - 1; } @@ -1280,14 +1170,9 @@ uae_u32 host_bind (TrapContext *ctx, SB, uae_u32 sd, uae_u32 name, uae_u32 namel return -1; } - DEBUG_LOG ("bind(%u[%d], 0x%x, %u) -> ", sd, s, name, namelen); copysockaddr_a2n (ctx, &addr, name, namelen); - printSockAddr (&addr); - if ((success = bind (s, reinterpret_cast(&addr), len)) != 0) { + if ((success = ::bind (s, reinterpret_cast(&addr), len)) != 0) { SETERRNO; - DEBUG_LOG ("failed (%d)\n",sb->sb_errno); - } else { - DEBUG_LOG ("OK\n"); } return success; } @@ -1297,7 +1182,6 @@ uae_u32 host_listen (TrapContext *ctx, SB, uae_u32 sd, uae_u32 backlog) int s; uae_u32 success = -1; - DEBUG_LOG ("listen(%d,%d) -> ", sd, backlog); s = getsock (ctx, sb, sd + 1); if (s == -1) { @@ -1307,9 +1191,6 @@ uae_u32 host_listen (TrapContext *ctx, SB, uae_u32 sd, uae_u32 backlog) if ((success = listen (s, backlog)) != 0) { SETERRNO; - DEBUG_LOG ("failed (%d)\n", sb->sb_errno); - } else { - DEBUG_LOG ("OK\n"); } return success; } @@ -1318,21 +1199,17 @@ void host_getprotobyname (TrapContext *ctx, SB, uae_u32 name) { struct protoent *p = getprotobyname (reinterpret_cast(get_real_address(name))); - DEBUG_LOG ("Getprotobyname(%s) = %p\n", get_real_address (name), p); - if (p == NULL) { SETERRNO; return; } copyProtoent (ctx, sb, p); - BSDTRACE (("OK (%s, %d)\n", p->p_name, p->p_proto)); } void host_getprotobynumber (TrapContext *ctx, SB, uae_u32 number) { struct protoent *p = getprotobynumber(number); - DEBUG_LOG("getprotobynumber(%d) = %p\n", number, p); if (p == NULL) { SETERRNO; @@ -1340,7 +1217,6 @@ void host_getprotobynumber (TrapContext *ctx, SB, uae_u32 number) } copyProtoent (ctx, sb, p); - BSDTRACE (("OK (%s, %d)\n", p->p_name, p->p_proto)); } void host_getservbynameport (TrapContext *ctx, SB, uae_u32 name, uae_u32 proto, uae_u32 type) @@ -1366,12 +1242,6 @@ void host_getservbynameport (TrapContext *ctx, SB, uae_u32 name, uae_u32 proto, uae_u32 aptr; int i; - if (type) { - DEBUG_LOG("Getservbyport(%d, %s) = %p\n", name, protobuf, s); - } else { - DEBUG_LOG("Getservbyname(%s, %s) = %p\n", namebuf, protobuf, s); - } - if (s == NULL) { SETERRNO; return; @@ -1416,7 +1286,6 @@ void host_getservbynameport (TrapContext *ctx, SB, uae_u32 name, uae_u32 proto, trap_put_long (ctx, sb->servent + 12, aptr); addstr (ctx, &aptr, s->s_proto); - BSDTRACE (("OK (%s, %d)\n", s->s_name, (unsigned short)htons (s->s_port))); bsdsocklib_seterrno (ctx, sb,0); } @@ -1493,19 +1362,14 @@ uae_u32 host_Inet_NtoA (TrapContext *ctx, SB, uae_u32 in) *reinterpret_cast(&ina) = htonl (in); - BSDTRACE (("Inet_NtoA(%x) -> ", in)); - if ((addr = inet_ntoa(ina)) != NULL) { buf = trap_get_areg(ctx, 6) + offsetof (struct UAEBSDBase, scratchbuf); strncpyha(ctx, buf, addr, SCRATCHBUFSIZE); - BSDTRACE (("%s\n", addr)); return buf; } else SETERRNO; - BSDTRACE (("failed (%d)\n", sb->sb_errno)); - - return 0; + return 0; } uae_u32 host_inet_addr (TrapContext *ctx, uae_u32 cp) @@ -1519,7 +1383,6 @@ uae_u32 host_inet_addr (TrapContext *ctx, uae_u32 cp) addr = htonl (inet_addr (cp_rp)); - BSDTRACE (("inet_addr(%s) -> 0x%08x\n", cp_rp, addr)); xfree(cp_rp); return addr; @@ -1530,15 +1393,12 @@ uae_u32 host_shutdown (SB, uae_u32 sd, uae_u32 how) TrapContext *ctx = NULL; SOCKET s; - BSDTRACE (("shutdown(%d,%d) -> ", sd, how)); s = getsock (ctx, sb, sd + 1); if (s != -1) { if (shutdown (s, how)) { SETERRNO; - BSDTRACE (("failed (%d)\n", sb->sb_errno)); } else { - BSDTRACE (("OK\n")); return 0; } } @@ -1550,14 +1410,12 @@ int host_dup2socket (TrapContext *ctx, SB, int fd1, int fd2) { int s1, s2; - BSDTRACE (("dup2socket(%d,%d) -> ", fd1, fd2)); fd1++; s1 = getsock (ctx, sb, fd1); if (s1 != -1) { if (fd2 != -1) { if (static_cast(fd2) >= static_cast(sb->dtablesize)) { - BSDTRACE (("Bad file descriptor (%d)\n", fd2)); bsdsocklib_seterrno (ctx, sb, 9); /* EBADF */ } fd2++; @@ -1566,21 +1424,17 @@ int host_dup2socket (TrapContext *ctx, SB, int fd1, int fd2) close (s2); } setsd (ctx, sb, fd2, dup (s1)); - BSDTRACE (("0(%d)\n", getsock (ctx, sb, fd2))); return 0; } else { fd2 = getsd (ctx, sb, 1); if (fd2 != -1) { setsd (ctx, sb, fd2, dup (s1)); - BSDTRACE (("%d(%d)\n", fd2, getsock (ctx, sb, fd2))); return (fd2 - 1); } else { - BSDTRACE(("-1\n")); return -1; } } } - BSDTRACE (("-1\n")); return -1; } @@ -1615,8 +1469,6 @@ uae_u32 host_getsockopt (TrapContext *ctx, SB, uae_u32 sd, uae_u32 level, uae_u3 trap_put_long (ctx, optlen, len); SETERRNO; - DEBUG_LOG ("getsockopt: sock AmigaSide %d NativeSide %d, level %d, 'name' %x(%d), len %d -> %d, %d\n", - sd, s, level, optname, nativeoptname, len, r, errno); if (optval) { if (r == 0) { @@ -1633,7 +1485,7 @@ uae_u32 host_IoctlSocket (TrapContext *ctx, SB, uae_u32 sd, uae_u32 request, uae { int sock = getsock (ctx, sb, sd + 1); int r, argval = trap_get_long (ctx, arg); - long flags; + uae_s32 flags; if (sock == -1) { sb->resultval = -1; @@ -1646,8 +1498,6 @@ uae_u32 host_IoctlSocket (TrapContext *ctx, SB, uae_u32 sd, uae_u32 request, uae return -1; } - DEBUG_LOG ("Ioctl code is %x, flags are %ld\n", request, flags); - switch (request) { case 0x8004667B: /* FIOGETOWN */ sb->ownertask = trap_get_long (ctx, arg); @@ -1669,10 +1519,8 @@ uae_u32 host_IoctlSocket (TrapContext *ctx, SB, uae_u32 sd, uae_u32 request, uae r = fcntl (sock, F_SETFL, argval ? flags | O_NONBLOCK : flags & ~O_NONBLOCK); if (argval) { - DEBUG_LOG ("nonblocking\n"); sb->ftable[sd] &= ~SF_BLOCKING; } else { - DEBUG_LOG ("blocking\n"); sb->ftable[sd] |= SF_BLOCKING; } return r; @@ -1705,7 +1553,6 @@ int host_CloseSocket (TrapContext *ctx, SB, int sd) return 0; } */ - DEBUG_LOG ("CloseSocket Amiga: %d, NativeSide %d\n", sd, s); retval = close (s); SETERRNO; releasesock (ctx, sb, sd + 1); @@ -1743,7 +1590,6 @@ int init_socket_layer(void) if (currprefs.socket_emu) { if (uae_sem_init(&sem_queue, 0, 1) < 0) { - DEBUG_LOG("Can't create sem %d\n", errno); return 0; } result = 1; @@ -1752,20 +1598,18 @@ int init_socket_layer(void) return result; } -void clearsockabort (SB) +static void clearsockabort (SB) { int chr; int num; while ((num = read (sb->sockabort[0], &chr, sizeof(chr))) >= 0) { - DEBUG_LOG ("Sockabort got %d bytes\n", num); } } void sockabort (SB) { int chr = 1; - DEBUG_LOG ("Sock abort!!\n"); write (sb->sockabort[1], &chr, sizeof (chr)); } @@ -1778,5 +1622,3 @@ void unlocksigqueue (void) { uae_sem_post(&sem_queue); } - -#endif diff --git a/src/osdep/cda_play.cpp b/src/osdep/cda_play.cpp index c7ef6b65..7da13eee 100644 --- a/src/osdep/cda_play.cpp +++ b/src/osdep/cda_play.cpp @@ -1,7 +1,3 @@ -#include -#include -#include - #include "sysdeps.h" #include "audio.h" @@ -9,68 +5,69 @@ #include "cda_play.h" #include "sounddep/sound.h" -cda_audio::~cda_audio() +cda_audio::~cda_audio() { - cdaudio_active = false; - wait(0); - wait(1); - for (int i = 0; i < 2; i++) { - xfree(buffers[i]); - buffers[i] = NULL; - } + cdaudio_active = false; + if (active) { + wait(0); + wait(1); + } + for (int i = 0; i < 2; i++) { + xfree (buffers[i]); + buffers[i] = NULL; + } } cda_audio::cda_audio(int num_sectors, int sectorsize, int samplerate) { - active = false; - playing = false; - volume[0] = volume[1] = 0; - currBuf = 1; + active = false; + playing = false; + volume[0] = volume[1] = 0; + currBuf = 1; - bufsize = num_sectors * sectorsize; + bufsize = num_sectors * sectorsize; this->sectorsize = sectorsize; - for (int i = 0; i < 2; i++) { - buffers[i] = xcalloc(uae_u8, num_sectors * ((bufsize + 4095) & ~4095)); - } - this->num_sectors = num_sectors; - active = true; - playing = true; - cdaudio_active = true; + for (int i = 0; i < 2; i++) { + buffers[i] = xcalloc (uae_u8, num_sectors * ((bufsize + 4095) & ~4095)); + } + this->num_sectors = num_sectors; + active = true; + playing = true; + cdaudio_active = true; } -void cda_audio::setvolume(int left, int right) +void cda_audio::setvolume(int left, int right) { - for (int j = 0; j < 2; j++) { - volume[j] = j == 0 ? left : right; + for (int j = 0; j < 2; j++) { + volume[j] = j == 0 ? left : right; volume[j] = sound_cd_volume[j] * volume[j] / 32768; - if (volume[j]) - volume[j]++; - if (volume[j] >= 32768) - volume[j] = 32768; - } + if (volume[j]) + volume[j]++; + if (volume[j] >= 32768) + volume[j] = 32768; + } } -bool cda_audio::play(int bufnum) +bool cda_audio::play(int bufnum) { - if (!active) { - return false; - } + if (!active) { + return false; + } - currBuf = bufnum; - uae_s16 *p = (uae_s16*)(buffers[bufnum]); - for (int i = 0; i < num_sectors * sectorsize / 4; i++) { - PUT_CDAUDIO_WORD_STEREO(p[i * 2 + 0] * volume[0] / 32768, p[i * 2 + 1] * volume[1] / 32768); - check_cdaudio_buffers(); - } + currBuf = bufnum; + uae_s16 *p = (uae_s16*)(buffers[bufnum]); + for (int i = 0; i < num_sectors * sectorsize / 4; i++) { + PUT_CDAUDIO_WORD_STEREO(p[i * 2 + 0] * volume[0] / 32768, p[i * 2 + 1] * volume[1] / 32768); + check_cdaudio_buffers(); + } - return cdaudio_catchup(); + return cdaudio_catchup(); } -void cda_audio::wait(int bufnum) +void cda_audio::wait(int bufnum) { - if (!active || !playing) { - return; - } + if (!active || !playing) + return; } bool cda_audio::isplaying(int bufnum) diff --git a/src/osdep/cda_play.h b/src/osdep/cda_play.h index 4759b830..20c5cb78 100644 --- a/src/osdep/cda_play.h +++ b/src/osdep/cda_play.h @@ -5,22 +5,22 @@ extern volatile bool cd_audio_mode_changed; class cda_audio { private: - int bufsize; + int bufsize; int sectorsize; - int volume[2]{}; - bool playing; - bool active; + int volume[2]; + bool playing; + bool active; + int currBuf; + int num_sectors; public: - uae_u8 *buffers[2]{}; - int currBuf; - int num_sectors; + uae_u8 *buffers[2]; cda_audio(int num_sectors, int sectorsize, int samplerate); - ~cda_audio(); - void setvolume(int left, int right); - bool play(int bufnum); - void wait(void); - void wait(int bufnum); + ~cda_audio(); + void setvolume(int left, int right); + bool play(int bufnum); + void wait(void); + void wait(int bufnum); bool isplaying(int bufnum); }; diff --git a/src/osdep/charset.cpp b/src/osdep/charset.cpp index 929d1193..0c678514 100644 --- a/src/osdep/charset.cpp +++ b/src/osdep/charset.cpp @@ -71,16 +71,16 @@ char *ua_fs(const TCHAR *s, int defchar) TCHAR *au_fs_copy(TCHAR *dst, int maxlen, const char *src) { - dst[0] = 0; - strncpy(dst, src, maxlen); - return dst; + dst[0] = 0; + strncpy(dst, src, maxlen - 1); + return dst; } char *ua_fs_copy(char *dst, int maxlen, const TCHAR *src, int defchar) { - dst[0] = 0; - strncpy(dst, src, maxlen); - return dst; + dst[0] = 0; + strncpy(dst, src, maxlen - 1); + return dst; } void to_lower(TCHAR *s, int len) diff --git a/src/osdep/gui/CreateFilesysHardfile.cpp b/src/osdep/gui/CreateFilesysHardfile.cpp index ca1a8bd9..50faf0ff 100644 --- a/src/osdep/gui/CreateFilesysHardfile.cpp +++ b/src/osdep/gui/CreateFilesysHardfile.cpp @@ -404,7 +404,7 @@ bool CreateFilesysHardfile() ci.controller_media_type = 0; ci.unit_feature_level = 1; ci.readonly = false; - const auto uci = add_filesys_config(&changed_prefs, -1, &ci); + const auto uci = add_filesys_config(&workprefs, -1, &ci); if (uci) { const auto hfd = get_hardfile_data(uci->configoffset); diff --git a/src/osdep/gui/EditFilesysHardfile.cpp b/src/osdep/gui/EditFilesysHardfile.cpp index c2f7125e..02f103be 100644 --- a/src/osdep/gui/EditFilesysHardfile.cpp +++ b/src/osdep/gui/EditFilesysHardfile.cpp @@ -529,9 +529,9 @@ bool EditFilesysHardfile(const int unit_no) if (unit_no >= 0) { - uci = &changed_prefs.mountconfig[unit_no]; + uci = &workprefs.mountconfig[unit_no]; const auto ci = &uci->ci; - get_filesys_unitconfig(&changed_prefs, unit_no, &mi); + get_filesys_unitconfig(&workprefs, unit_no, &mi); strdevname.assign(ci->devname); txtDevice->setText(strdevname); @@ -614,7 +614,7 @@ bool EditFilesysHardfile(const int unit_no) ci.bootpri = bp; ci.physical_geometry = hardfile_testrdb(ci.rootdir); - uci = add_filesys_config(&changed_prefs, unit_no, &ci); + uci = add_filesys_config(&workprefs, unit_no, &ci); if (uci) { const auto hfd = get_hardfile_data(uci->configoffset); diff --git a/src/osdep/gui/EditFilesysVirtual.cpp b/src/osdep/gui/EditFilesysVirtual.cpp index 74b57527..78cb12b5 100644 --- a/src/osdep/gui/EditFilesysVirtual.cpp +++ b/src/osdep/gui/EditFilesysVirtual.cpp @@ -357,9 +357,9 @@ bool EditFilesysVirtual(const int unit_no) if (unit_no >= 0) { - uci = &changed_prefs.mountconfig[unit_no]; + uci = &workprefs.mountconfig[unit_no]; const auto ci = &uci->ci; - get_filesys_unitconfig(&changed_prefs, unit_no, &mi); + get_filesys_unitconfig(&workprefs, unit_no, &mi); strdevname.assign(ci->devname); txtDevice->setText(strdevname); @@ -407,7 +407,7 @@ bool EditFilesysVirtual(const int unit_no) ci.readonly = !chkReadWrite->isSelected(); ci.bootpri = bp; - uci = add_filesys_config(&changed_prefs, unit_no, &ci); + uci = add_filesys_config(&workprefs, unit_no, &ci); if (uci) { filesys_media_change (ci.rootdir, 1, uci); diff --git a/src/osdep/gui/PanelCPU.cpp b/src/osdep/gui/PanelCPU.cpp index 82bc0cd4..520f2184 100644 --- a/src/osdep/gui/PanelCPU.cpp +++ b/src/osdep/gui/PanelCPU.cpp @@ -51,45 +51,45 @@ public: { if (actionEvent.getSource() == optCPU68000) { - changed_prefs.cpu_model = 68000; - changed_prefs.fpu_model = 0; - changed_prefs.address_space_24 = true; - changed_prefs.z3fastmem[0].size = 0; - changed_prefs.rtgboards[0].rtgmem_size = 0; - changed_prefs.cachesize = 0; - changed_prefs.compfpu = false; + workprefs.cpu_model = 68000; + workprefs.fpu_model = 0; + workprefs.address_space_24 = true; + workprefs.z3fastmem[0].size = 0; + workprefs.rtgboards[0].rtgmem_size = 0; + workprefs.cachesize = 0; + workprefs.compfpu = false; } else if (actionEvent.getSource() == optCPU68010) { - changed_prefs.cpu_model = 68010; - changed_prefs.fpu_model = 0; - changed_prefs.address_space_24 = true; - changed_prefs.z3fastmem[0].size = 0; - changed_prefs.rtgboards[0].rtgmem_size = 0; - changed_prefs.cachesize = 0; - changed_prefs.compfpu = false; + workprefs.cpu_model = 68010; + workprefs.fpu_model = 0; + workprefs.address_space_24 = true; + workprefs.z3fastmem[0].size = 0; + workprefs.rtgboards[0].rtgmem_size = 0; + workprefs.cachesize = 0; + workprefs.compfpu = false; } else if (actionEvent.getSource() == optCPU68020) { - changed_prefs.cpu_model = 68020; - if (changed_prefs.fpu_model == 68040) - changed_prefs.fpu_model = 68881; - changed_prefs.cpu_compatible = false; + workprefs.cpu_model = 68020; + if (workprefs.fpu_model == 68040) + workprefs.fpu_model = 68881; + workprefs.cpu_compatible = false; } else if (actionEvent.getSource() == optCPU68030) { - changed_prefs.cpu_model = 68030; - if (changed_prefs.fpu_model == 68040) - changed_prefs.fpu_model = 68881; - changed_prefs.address_space_24 = false; - changed_prefs.cpu_compatible = false; + workprefs.cpu_model = 68030; + if (workprefs.fpu_model == 68040) + workprefs.fpu_model = 68881; + workprefs.address_space_24 = false; + workprefs.cpu_compatible = false; } else if (actionEvent.getSource() == optCPU68040) { - changed_prefs.cpu_model = 68040; - changed_prefs.fpu_model = 68040; - changed_prefs.address_space_24 = false; - changed_prefs.cpu_compatible = false; + workprefs.cpu_model = 68040; + workprefs.fpu_model = 68040; + workprefs.address_space_24 = false; + workprefs.cpu_compatible = false; } RefreshPanelCPU(); RefreshPanelRAM(); @@ -105,19 +105,19 @@ public: { if (actionEvent.getSource() == optFPUnone) { - changed_prefs.fpu_model = 0; + workprefs.fpu_model = 0; } else if (actionEvent.getSource() == optFPU68881) { - changed_prefs.fpu_model = 68881; + workprefs.fpu_model = 68881; } else if (actionEvent.getSource() == optFPU68882) { - changed_prefs.fpu_model = 68882; + workprefs.fpu_model = 68882; } else if (actionEvent.getSource() == optFPUinternal) { - changed_prefs.fpu_model = 68040; + workprefs.fpu_model = 68040; } RefreshPanelCPU(); RefreshPanelRAM(); @@ -133,15 +133,15 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == opt7Mhz) - changed_prefs.m68k_speed = M68K_SPEED_7MHZ_CYCLES; + workprefs.m68k_speed = M68K_SPEED_7MHZ_CYCLES; else if (actionEvent.getSource() == opt14Mhz) - changed_prefs.m68k_speed = M68K_SPEED_14MHZ_CYCLES; + workprefs.m68k_speed = M68K_SPEED_14MHZ_CYCLES; else if (actionEvent.getSource() == opt28Mhz) - changed_prefs.m68k_speed = M68K_SPEED_25MHZ_CYCLES; + workprefs.m68k_speed = M68K_SPEED_25MHZ_CYCLES; else if (actionEvent.getSource() == optFastest) - changed_prefs.m68k_speed = -1; + workprefs.m68k_speed = -1; else if (actionEvent.getSource() == optTurbo) - changed_prefs.m68k_speed = -30; + workprefs.m68k_speed = -30; } }; @@ -153,7 +153,7 @@ class CPU24BitActionListener : public gcn::ActionListener public: void action(const gcn::ActionEvent& actionEvent) override { - changed_prefs.address_space_24 = chk24Bit->isSelected(); + workprefs.address_space_24 = chk24Bit->isSelected(); RefreshPanelCPU(); } }; @@ -167,12 +167,12 @@ public: { if (chkCPUCompatible->isSelected()) { - changed_prefs.cpu_compatible = true; - changed_prefs.cachesize = 0; + workprefs.cpu_compatible = true; + workprefs.cachesize = 0; } else { - changed_prefs.cpu_compatible = false; + workprefs.cpu_compatible = false; } RefreshPanelCPU(); } @@ -190,19 +190,19 @@ public: { if (chkJIT->isSelected()) { - changed_prefs.cpu_compatible = false; - changed_prefs.cachesize = MAX_JIT_CACHE; - changed_prefs.compfpu = true; + workprefs.cpu_compatible = false; + workprefs.cachesize = MAX_JIT_CACHE; + workprefs.compfpu = true; } else { - changed_prefs.cachesize = 0; - changed_prefs.compfpu = false; + workprefs.cachesize = 0; + workprefs.compfpu = false; } } else if (actionEvent.getSource() == chkFPUJIT) { - changed_prefs.compfpu = chkFPUJIT->isSelected(); + workprefs.compfpu = chkFPUJIT->isSelected(); } RefreshPanelCPU(); } @@ -216,7 +216,7 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == chkFPUstrict) { - changed_prefs.fpu_strict = chkFPUstrict->isSelected(); + workprefs.fpu_strict = chkFPUstrict->isSelected(); } RefreshPanelCPU(); @@ -380,25 +380,25 @@ void ExitPanelCPU() void RefreshPanelCPU() { - if (changed_prefs.cpu_model == 68000) + if (workprefs.cpu_model == 68000) optCPU68000->setSelected(true); - else if (changed_prefs.cpu_model == 68010) + else if (workprefs.cpu_model == 68010) optCPU68010->setSelected(true); - else if (changed_prefs.cpu_model == 68020) + else if (workprefs.cpu_model == 68020) optCPU68020->setSelected(true); - else if (changed_prefs.cpu_model == 68030) + else if (workprefs.cpu_model == 68030) optCPU68030->setSelected(true); - else if (changed_prefs.cpu_model == 68040) + else if (workprefs.cpu_model == 68040) optCPU68040->setSelected(true); - chk24Bit->setSelected(changed_prefs.address_space_24); - chk24Bit->setEnabled(changed_prefs.cpu_model == 68020); - chkCPUCompatible->setSelected(changed_prefs.cpu_compatible > 0); - chkCPUCompatible->setEnabled(changed_prefs.cpu_model <= 68010); - chkJIT->setEnabled(changed_prefs.cpu_model > 68010); - chkJIT->setSelected(changed_prefs.cachesize > 0); + chk24Bit->setSelected(workprefs.address_space_24); + chk24Bit->setEnabled(workprefs.cpu_model == 68020); + chkCPUCompatible->setSelected(workprefs.cpu_compatible > 0); + chkCPUCompatible->setEnabled(workprefs.cpu_model <= 68010); + chkJIT->setEnabled(workprefs.cpu_model > 68010); + chkJIT->setSelected(workprefs.cachesize > 0); - switch (changed_prefs.fpu_model) + switch (workprefs.fpu_model) { case 68881: optFPU68881->setSelected(true); @@ -413,29 +413,29 @@ void RefreshPanelCPU() optFPUnone->setSelected(true); break; } - optFPU68881->setEnabled(changed_prefs.cpu_model >= 68020 && changed_prefs.cpu_model < 68040); - optFPU68882->setEnabled(changed_prefs.cpu_model >= 68020 && changed_prefs.cpu_model < 68040); - optFPUinternal->setEnabled(changed_prefs.cpu_model == 68040); + optFPU68881->setEnabled(workprefs.cpu_model >= 68020 && workprefs.cpu_model < 68040); + optFPU68882->setEnabled(workprefs.cpu_model >= 68020 && workprefs.cpu_model < 68040); + optFPUinternal->setEnabled(workprefs.cpu_model == 68040); - chkFPUstrict->setSelected(changed_prefs.fpu_strict); + chkFPUstrict->setSelected(workprefs.fpu_strict); #ifdef USE_JIT_FPU - chkFPUJIT->setEnabled(changed_prefs.cachesize > 0); - chkFPUJIT->setSelected(changed_prefs.compfpu); + chkFPUJIT->setEnabled(workprefs.cachesize > 0); + chkFPUJIT->setSelected(workprefs.compfpu); #else chkFPUJIT->setSelected(false); chkFPUJIT->setEnabled(false); #endif - if (changed_prefs.m68k_speed == M68K_SPEED_7MHZ_CYCLES) + if (workprefs.m68k_speed == M68K_SPEED_7MHZ_CYCLES) opt7Mhz->setSelected(true); - else if (changed_prefs.m68k_speed == M68K_SPEED_14MHZ_CYCLES) + else if (workprefs.m68k_speed == M68K_SPEED_14MHZ_CYCLES) opt14Mhz->setSelected(true); - else if (changed_prefs.m68k_speed == M68K_SPEED_25MHZ_CYCLES) + else if (workprefs.m68k_speed == M68K_SPEED_25MHZ_CYCLES) opt28Mhz->setSelected(true); - else if (changed_prefs.m68k_speed == -1) + else if (workprefs.m68k_speed == -1) optFastest->setSelected(true); - else if (changed_prefs.m68k_speed == -30) + else if (workprefs.m68k_speed == -30) optTurbo->setSelected(true); } diff --git a/src/osdep/gui/PanelChipset.cpp b/src/osdep/gui/PanelChipset.cpp index 0d99bda1..78ebe4a6 100644 --- a/src/osdep/gui/PanelChipset.cpp +++ b/src/osdep/gui/PanelChipset.cpp @@ -101,9 +101,9 @@ public: // Chipset selected //--------------------------------------- const auto cs = chipsets[cboChipset->getSelected()].compatible; - if (changed_prefs.cs_compatible != cs) { - changed_prefs.cs_compatible = cs; - built_in_chipset_prefs(&changed_prefs); + if (workprefs.cs_compatible != cs) { + workprefs.cs_compatible = cs; + built_in_chipset_prefs(&workprefs); RefreshPanelChipset(); } } @@ -118,13 +118,13 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == optOCS) - changed_prefs.chipset_mask = 0; + workprefs.chipset_mask = 0; else if (actionEvent.getSource() == optECSAgnus) - changed_prefs.chipset_mask = CSMASK_ECS_AGNUS; + workprefs.chipset_mask = CSMASK_ECS_AGNUS; else if (actionEvent.getSource() == optECS) - changed_prefs.chipset_mask = CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE; + workprefs.chipset_mask = CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE; else - changed_prefs.chipset_mask = CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE | CSMASK_AGA; + workprefs.chipset_mask = CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE | CSMASK_AGA; } }; @@ -138,13 +138,13 @@ public: { if (chkNTSC->isSelected()) { - changed_prefs.ntscmode = true; - changed_prefs.chipset_refreshrate = 60; + workprefs.ntscmode = true; + workprefs.chipset_refreshrate = 60; } else { - changed_prefs.ntscmode = false; - changed_prefs.chipset_refreshrate = 50; + workprefs.ntscmode = false; + workprefs.chipset_refreshrate = 50; } RefreshPanelQuickstart(); } @@ -158,7 +158,7 @@ class FastCopperActionListener : public gcn::ActionListener public: void action(const gcn::ActionEvent& actionEvent) override { - changed_prefs.fast_copper = chkFastCopper->isSelected(); + workprefs.fast_copper = chkFastCopper->isSelected(); } }; static FastCopperActionListener* fastCopperActionListener; @@ -169,8 +169,8 @@ class BlitterButtonActionListener : public gcn::ActionListener public: void action(const gcn::ActionEvent& actionEvent) override { - changed_prefs.immediate_blits = optBlitImmed->isSelected(); - changed_prefs.waiting_blits = optBlitWait->isSelected(); + workprefs.immediate_blits = optBlitImmed->isSelected(); + workprefs.waiting_blits = optBlitWait->isSelected(); } }; @@ -183,13 +183,13 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == optCollNone) - changed_prefs.collision_level = 0; + workprefs.collision_level = 0; else if (actionEvent.getSource() == optCollSprites) - changed_prefs.collision_level = 1; + workprefs.collision_level = 1; else if (actionEvent.getSource() == optCollPlayfield) - changed_prefs.collision_level = 2; + workprefs.collision_level = 2; else - changed_prefs.collision_level = 3; + workprefs.collision_level = 3; } }; @@ -350,7 +350,7 @@ void RefreshPanelChipset() bIgnoreListChange = true; auto idx = 0; for (auto i = 0; isetSelected(idx); bIgnoreListChange = false; - if (changed_prefs.chipset_mask == 0) + if (workprefs.chipset_mask == 0) optOCS->setSelected(true); - else if (changed_prefs.chipset_mask == CSMASK_ECS_AGNUS) + else if (workprefs.chipset_mask == CSMASK_ECS_AGNUS) optECSAgnus->setSelected(true); - else if (changed_prefs.chipset_mask == (CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE)) + else if (workprefs.chipset_mask == (CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE)) optECS->setSelected(true); - else if (changed_prefs.chipset_mask == (CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE | CSMASK_AGA)) + else if (workprefs.chipset_mask == (CSMASK_ECS_AGNUS | CSMASK_ECS_DENISE | CSMASK_AGA)) optAGA->setSelected(true); - chkNTSC->setSelected(changed_prefs.ntscmode); + chkNTSC->setSelected(workprefs.ntscmode); - if (changed_prefs.immediate_blits) + if (workprefs.immediate_blits) optBlitImmed->setSelected(true); - else if (changed_prefs.waiting_blits) + else if (workprefs.waiting_blits) optBlitWait->setSelected(true); else optBlitNormal->setSelected(true); - chkFastCopper->setSelected(changed_prefs.fast_copper); + chkFastCopper->setSelected(workprefs.fast_copper); - if (changed_prefs.collision_level == 0) + if (workprefs.collision_level == 0) optCollNone->setSelected(true); - else if (changed_prefs.collision_level == 1) + else if (workprefs.collision_level == 1) optCollSprites->setSelected(true); - else if (changed_prefs.collision_level == 2) + else if (workprefs.collision_level == 2) optCollPlayfield->setSelected(true); else optCollFull->setSelected(true); diff --git a/src/osdep/gui/PanelConfig.cpp b/src/osdep/gui/PanelConfig.cpp index 19f91fbf..179e01a0 100644 --- a/src/osdep/gui/PanelConfig.cpp +++ b/src/osdep/gui/PanelConfig.cpp @@ -48,7 +48,7 @@ bool LoadConfigByName(const char *name) { txtName->setText(config->Name); txtDesc->setText(config->Description); - target_cfgfile_load(&changed_prefs, config->FullPath, 0, 0); + target_cfgfile_load(&workprefs, config->FullPath, 0, 0); strncpy(last_active_config, config->Name, MAX_DPATH); DisableResume(); RefreshAllPanels(); @@ -121,13 +121,13 @@ public: if (emulating) { DisableResume(); - target_cfgfile_load(&changed_prefs, ConfigFilesList[i]->FullPath, 0, 0); + target_cfgfile_load(&workprefs, ConfigFilesList[i]->FullPath, 0, 0); strncpy(last_active_config, ConfigFilesList[i]->Name, MAX_DPATH); RefreshAllPanels(); } else { - target_cfgfile_load(&changed_prefs, ConfigFilesList[i]->FullPath, 0, 0); + target_cfgfile_load(&workprefs, ConfigFilesList[i]->FullPath, 0, 0); strncpy(last_active_config, ConfigFilesList[i]->Name, MAX_DPATH); RefreshAllPanels(); } @@ -143,8 +143,8 @@ public: fetch_configurationpath(filename, MAX_DPATH); strncat(filename, txtName->getText().c_str(), MAX_DPATH - 1); strncat(filename, ".uae", MAX_DPATH - 1); - strncpy(changed_prefs.description, txtDesc->getText().c_str(), 256); - if (cfgfile_save(&changed_prefs, filename, 0)) + strncpy(workprefs.description, txtDesc->getText().c_str(), 256); + if (cfgfile_save(&workprefs, filename, 0)) RefreshPanelConfig(); } } @@ -198,7 +198,7 @@ public: //----------------------------------------------- // Second click on selected config -> Load it and start emulation // ---------------------------------------------- - target_cfgfile_load(&changed_prefs, ConfigFilesList[selected_item]->FullPath, 0, 0); + target_cfgfile_load(&workprefs, ConfigFilesList[selected_item]->FullPath, 0, 0); strncpy(last_active_config, ConfigFilesList[selected_item]->Name, MAX_DPATH); if (emulating) @@ -303,7 +303,7 @@ void InitPanelConfig(const struct _ConfigCategory& category) } } txtName->setText(last_active_config); - txtDesc->setText(changed_prefs.description); + txtDesc->setText(workprefs.description); ensureVisible = -1; RefreshPanelConfig(); } diff --git a/src/osdep/gui/PanelCustom.cpp b/src/osdep/gui/PanelCustom.cpp index e6313dd4..e4442a6b 100644 --- a/src/osdep/gui/PanelCustom.cpp +++ b/src/osdep/gui/PanelCustom.cpp @@ -178,7 +178,7 @@ public: SelectedFunction = 3; else if (actionEvent.getSource() == chkAnalogRemap) - changed_prefs.input_analog_remap = chkAnalogRemap->isSelected(); + workprefs.input_analog_remap = chkAnalogRemap->isSelected(); RefreshPanelCustom(); } @@ -199,16 +199,16 @@ public: switch (SelectedFunction) { case 0: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_none; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_none; break; case 1: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_hotkey; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_hotkey; break; case 2: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_left_trigger; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_left_trigger; break; case 3: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_right_trigger; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_right_trigger; break; default: break; @@ -297,16 +297,16 @@ public: switch (SelectedFunction) { case 0: - changed_prefs.jports[SelectedPort].amiberry_custom_none = tempmap; + workprefs.jports[SelectedPort].amiberry_custom_none = tempmap; break; case 1: - changed_prefs.jports[SelectedPort].amiberry_custom_hotkey = tempmap; + workprefs.jports[SelectedPort].amiberry_custom_hotkey = tempmap; break; case 2: - changed_prefs.jports[SelectedPort].amiberry_custom_left_trigger = tempmap; + workprefs.jports[SelectedPort].amiberry_custom_left_trigger = tempmap; break; case 3: - changed_prefs.jports[SelectedPort].amiberry_custom_right_trigger = tempmap; + workprefs.jports[SelectedPort].amiberry_custom_right_trigger = tempmap; break; default: break; @@ -315,7 +315,7 @@ public: // and here, we will scroll through the custom-map and // push it into the currprefs config file - inputdevice_updateconfig(nullptr, &changed_prefs); + inputdevice_updateconfig(nullptr, &workprefs); RefreshPanelCustom(); } } @@ -516,7 +516,7 @@ void RefreshPanelCustom(void) // optMultiLeft->setSelected(SelectedFunction == 2); // optMultiRight->setSelected(SelectedFunction == 3); - chkAnalogRemap->setSelected(changed_prefs.input_analog_remap); + chkAnalogRemap->setSelected(workprefs.input_analog_remap); // you'll want to refresh the drop-down section here // get map @@ -524,16 +524,16 @@ void RefreshPanelCustom(void) switch (SelectedFunction) { case 0: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_none; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_none; break; case 1: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_hotkey; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_hotkey; break; case 2: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_left_trigger; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_left_trigger; break; case 3: - tempmap = changed_prefs.jports[SelectedPort].amiberry_custom_right_trigger; + tempmap = workprefs.jports[SelectedPort].amiberry_custom_right_trigger; break; default: break; @@ -543,9 +543,9 @@ void RefreshPanelCustom(void) // update the joystick port , and disable those which are not available char tmp[255]; - if (changed_prefs.jports[SelectedPort].id > JSEM_JOYS && changed_prefs.jports[SelectedPort].id < JSEM_MICE - 1) + if (workprefs.jports[SelectedPort].id > JSEM_JOYS && workprefs.jports[SelectedPort].id < JSEM_MICE - 1) { - const auto hostjoyid = changed_prefs.jports[SelectedPort].id - JSEM_JOYS - 1; + const auto hostjoyid = workprefs.jports[SelectedPort].id - JSEM_JOYS - 1; #ifdef USE_SDL1 strncpy(tmp, SDL_JoystickName(hostjoyid), 255); #elif USE_SDL2 @@ -644,7 +644,7 @@ void RefreshPanelCustom(void) } else if (temp_button == host_input_buttons[hostjoyid].quit_button && temp_button != -1 && SelectedFunction == 1 && - changed_prefs.use_retroarch_quit) + workprefs.use_retroarch_quit) { cboCustomAction[n]->setListModel(&CustomEventList_Quit); cboCustomAction[n]->setEnabled(false); @@ -652,7 +652,7 @@ void RefreshPanelCustom(void) } else if (temp_button == host_input_buttons[hostjoyid].menu_button && temp_button != -1 && SelectedFunction == 1 && - changed_prefs.use_retroarch_menu) + workprefs.use_retroarch_menu) { cboCustomAction[n]->setListModel(&CustomEventList_Menu); cboCustomAction[n]->setEnabled(false); @@ -660,7 +660,7 @@ void RefreshPanelCustom(void) } else if (temp_button == host_input_buttons[hostjoyid].reset_button && temp_button != -1 && SelectedFunction == 1 && - changed_prefs.use_retroarch_reset) + workprefs.use_retroarch_reset) { cboCustomAction[n]->setListModel(&CustomEventList_Reset); cboCustomAction[n]->setEnabled(false); @@ -673,7 +673,7 @@ void RefreshPanelCustom(void) } } - if (host_input_buttons[hostjoyid].number_of_hats > 0 || changed_prefs.input_analog_remap == true) + if (host_input_buttons[hostjoyid].number_of_hats > 0 || workprefs.input_analog_remap == true) { cboCustomAction[ 0]->setEnabled(true); cboCustomAction[ 1]->setEnabled(true); diff --git a/src/osdep/gui/PanelDisplay.cpp b/src/osdep/gui/PanelDisplay.cpp index eaec7a21..d67b4940 100644 --- a/src/osdep/gui/PanelDisplay.cpp +++ b/src/osdep/gui/PanelDisplay.cpp @@ -58,45 +58,45 @@ public: { if (actionEvent.getSource() == sldAmigaWidth) { - if (changed_prefs.gfx_size.width != amigawidth_values[int(sldAmigaWidth->getValue())]) + if (workprefs.gfx_monitor.gfx_size.width != amigawidth_values[int(sldAmigaWidth->getValue())]) { - changed_prefs.gfx_size.width = amigawidth_values[int(sldAmigaWidth->getValue())]; + workprefs.gfx_monitor.gfx_size.width = amigawidth_values[int(sldAmigaWidth->getValue())]; RefreshPanelDisplay(); } } else if (actionEvent.getSource() == sldAmigaHeight) { - if (changed_prefs.gfx_size.height != amigaheight_values[int(sldAmigaHeight->getValue())]) + if (workprefs.gfx_monitor.gfx_size.height != amigaheight_values[int(sldAmigaHeight->getValue())]) { - changed_prefs.gfx_size.height = amigaheight_values[int(sldAmigaHeight->getValue())]; + workprefs.gfx_monitor.gfx_size.height = amigaheight_values[int(sldAmigaHeight->getValue())]; RefreshPanelDisplay(); } } else if (actionEvent.getSource() == sldVertPos) { - if (changed_prefs.vertical_offset != int(sldVertPos->getValue()) + OFFSET_Y_ADJUST) + if (workprefs.vertical_offset != int(sldVertPos->getValue()) + OFFSET_Y_ADJUST) { - changed_prefs.vertical_offset = int(sldVertPos->getValue()) + OFFSET_Y_ADJUST; + workprefs.vertical_offset = int(sldVertPos->getValue()) + OFFSET_Y_ADJUST; RefreshPanelDisplay(); } } else if (actionEvent.getSource() == chkFrameskip) - changed_prefs.gfx_framerate = chkFrameskip->isSelected() ? 1 : 0; + workprefs.gfx_framerate = chkFrameskip->isSelected() ? 1 : 0; else if (actionEvent.getSource() == chkAspect) - changed_prefs.gfx_correct_aspect = chkAspect->isSelected(); + workprefs.gfx_correct_aspect = chkAspect->isSelected(); else if (actionEvent.getSource() == chkFullscreen) { - if (changed_prefs.gfx_apmode[0].gfx_fullscreen == GFX_FULLSCREEN) + if (workprefs.gfx_apmode[0].gfx_fullscreen == GFX_FULLSCREEN) { - changed_prefs.gfx_apmode[0].gfx_fullscreen = GFX_WINDOW; - changed_prefs.gfx_apmode[1].gfx_fullscreen = GFX_WINDOW; + workprefs.gfx_apmode[0].gfx_fullscreen = GFX_WINDOW; + workprefs.gfx_apmode[1].gfx_fullscreen = GFX_WINDOW; } else { - changed_prefs.gfx_apmode[0].gfx_fullscreen = GFX_FULLSCREEN; - changed_prefs.gfx_apmode[1].gfx_fullscreen = GFX_FULLSCREEN; + workprefs.gfx_apmode[0].gfx_fullscreen = GFX_FULLSCREEN; + workprefs.gfx_apmode[1].gfx_fullscreen = GFX_FULLSCREEN; } } } @@ -111,11 +111,11 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == optAuto) - changed_prefs.scaling_method = -1; + workprefs.scaling_method = -1; else if (actionEvent.getSource() == optNearest) - changed_prefs.scaling_method = 0; + workprefs.scaling_method = 0; else if (actionEvent.getSource() == optLinear) - changed_prefs.scaling_method = 1; + workprefs.scaling_method = 1; } }; @@ -129,18 +129,18 @@ public: { if (action_event.getSource() == optSingle) { - changed_prefs.gfx_vresolution = VRES_NONDOUBLE; - changed_prefs.gfx_pscanlines = 0; + workprefs.gfx_vresolution = VRES_NONDOUBLE; + workprefs.gfx_pscanlines = 0; } else if (action_event.getSource() == optDouble) { - changed_prefs.gfx_vresolution = VRES_DOUBLE; - changed_prefs.gfx_pscanlines = 0; + workprefs.gfx_vresolution = VRES_DOUBLE; + workprefs.gfx_pscanlines = 0; } else if (action_event.getSource() == optScanlines) { - changed_prefs.gfx_vresolution = VRES_DOUBLE; - changed_prefs.gfx_pscanlines = 1; + workprefs.gfx_vresolution = VRES_DOUBLE; + workprefs.gfx_pscanlines = 1; } } }; @@ -320,17 +320,17 @@ void ExitPanelDisplay() void RefreshPanelDisplay() { - chkFrameskip->setSelected(changed_prefs.gfx_framerate); + chkFrameskip->setSelected(workprefs.gfx_framerate); int i; char tmp[32]; for (i = 0; i<6; ++i) { - if (changed_prefs.gfx_size.width == amigawidth_values[i]) + if (workprefs.gfx_monitor.gfx_size.width == amigawidth_values[i]) { sldAmigaWidth->setValue(i); - snprintf(tmp, 32, "%d", changed_prefs.gfx_size.width); + snprintf(tmp, 32, "%d", workprefs.gfx_monitor.gfx_size.width); lblAmigaWidthInfo->setCaption(tmp); break; } @@ -338,36 +338,36 @@ void RefreshPanelDisplay() for (i = 0; i<6; ++i) { - if (changed_prefs.gfx_size.height == amigaheight_values[i]) + if (workprefs.gfx_monitor.gfx_size.height == amigaheight_values[i]) { sldAmigaHeight->setValue(i); - snprintf(tmp, 32, "%d", changed_prefs.gfx_size.height); + snprintf(tmp, 32, "%d", workprefs.gfx_monitor.gfx_size.height); lblAmigaHeightInfo->setCaption(tmp); break; } } - chkAspect->setSelected(changed_prefs.gfx_correct_aspect); - chkFullscreen->setSelected(changed_prefs.gfx_apmode[0].gfx_fullscreen == GFX_FULLSCREEN); + chkAspect->setSelected(workprefs.gfx_correct_aspect); + chkFullscreen->setSelected(workprefs.gfx_apmode[0].gfx_fullscreen == GFX_FULLSCREEN); #ifdef USE_SDL2 - if (changed_prefs.scaling_method == -1) + if (workprefs.scaling_method == -1) optAuto->setSelected(true); - else if (changed_prefs.scaling_method == 0) + else if (workprefs.scaling_method == 0) optNearest->setSelected(true); - else if (changed_prefs.scaling_method == 1) + else if (workprefs.scaling_method == 1) optLinear->setSelected(true); #endif - if (changed_prefs.gfx_vresolution == VRES_NONDOUBLE && changed_prefs.gfx_pscanlines == 0) + if (workprefs.gfx_vresolution == VRES_NONDOUBLE && workprefs.gfx_pscanlines == 0) optSingle->setSelected(true); - else if (changed_prefs.gfx_vresolution == VRES_DOUBLE && changed_prefs.gfx_pscanlines == 0) + else if (workprefs.gfx_vresolution == VRES_DOUBLE && workprefs.gfx_pscanlines == 0) optDouble->setSelected(true); - else if (changed_prefs.gfx_vresolution == VRES_DOUBLE && changed_prefs.gfx_pscanlines == 1) + else if (workprefs.gfx_vresolution == VRES_DOUBLE && workprefs.gfx_pscanlines == 1) optScanlines->setSelected(true); - sldVertPos->setValue(changed_prefs.vertical_offset - OFFSET_Y_ADJUST); - snprintf(tmp, 32, "%d", changed_prefs.vertical_offset - OFFSET_Y_ADJUST); + sldVertPos->setValue(workprefs.vertical_offset - OFFSET_Y_ADJUST); + snprintf(tmp, 32, "%d", workprefs.vertical_offset - OFFSET_Y_ADJUST); lblVertPosInfo->setCaption(tmp); } diff --git a/src/osdep/gui/PanelFloppy.cpp b/src/osdep/gui/PanelFloppy.cpp index 4560138e..b412bdff 100644 --- a/src/osdep/gui/PanelFloppy.cpp +++ b/src/osdep/gui/PanelFloppy.cpp @@ -108,7 +108,7 @@ public: for (auto i = 0; i < 4; ++i) { if (actionEvent.getSource() == cboDFxType[i]) - changed_prefs.floppyslots[i].dfxtype = cboDFxType[i]->getSelected() - 1; + workprefs.floppyslots[i].dfxtype = cboDFxType[i]->getSelected() - 1; } RefreshPanelFloppy(); RefreshPanelQuickstart(); @@ -134,17 +134,17 @@ public: // Drive enabled/disabled //--------------------------------------- if (chkDFx[i]->isSelected()) - changed_prefs.floppyslots[i].dfxtype = DRV_35_DD; + workprefs.floppyslots[i].dfxtype = DRV_35_DD; else - changed_prefs.floppyslots[i].dfxtype = DRV_NONE; + workprefs.floppyslots[i].dfxtype = DRV_NONE; } else if (actionEvent.getSource() == chkDFxWriteProtect[i]) { //--------------------------------------- // Write-protect changed //--------------------------------------- - disk_setwriteprotect(&changed_prefs, i, changed_prefs.floppyslots[i].df, chkDFxWriteProtect[i]->isSelected()); - if (disk_getwriteprotect(&changed_prefs, changed_prefs.floppyslots[i].df) != chkDFxWriteProtect[i]->isSelected()) { + disk_setwriteprotect(&workprefs, i, workprefs.floppyslots[i].df, chkDFxWriteProtect[i]->isSelected()); + if (disk_getwriteprotect(&workprefs, workprefs.floppyslots[i].df) != chkDFxWriteProtect[i]->isSelected()) { // Failed to change write protection -> maybe filesystem doesn't support this chkDFxWriteProtect[i]->setSelected(!chkDFxWriteProtect[i]->isSelected()); ShowMessage("Set/Clear write protect", "Failed to change write permission.", "Maybe underlying filesystem doesn't support this.", "Ok", ""); @@ -174,7 +174,7 @@ public: //--------------------------------------- // Show info about current disk-image //--------------------------------------- - //if (changed_prefs.floppyslots[i].dfxtype != DRV_NONE && strlen(changed_prefs.floppyslots[i].df) > 0) + //if (workprefs.floppyslots[i].dfxtype != DRV_NONE && strlen(workprefs.floppyslots[i].df) > 0) //ToDo: Show info dialog } else if (actionEvent.getSource() == cmdDFxEject[i]) @@ -183,7 +183,7 @@ public: // Eject disk from drive //--------------------------------------- disk_eject(i); - strncpy(changed_prefs.floppyslots[i].df, "", MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, "", MAX_DPATH); AdjustDropDownControls(); } else if (actionEvent.getSource() == cmdDFxSelect[i]) @@ -193,15 +193,15 @@ public: //--------------------------------------- char tmp[MAX_DPATH]; - if (strlen(changed_prefs.floppyslots[i].df) > 0) - strncpy(tmp, changed_prefs.floppyslots[i].df, MAX_DPATH); + if (strlen(workprefs.floppyslots[i].df) > 0) + strncpy(tmp, workprefs.floppyslots[i].df, MAX_DPATH); else strncpy(tmp, currentDir, MAX_DPATH); if (SelectFile("Select disk image file", tmp, diskfile_filter)) { - if(strncmp(changed_prefs.floppyslots[i].df, tmp, MAX_DPATH) != 0) + if(strncmp(workprefs.floppyslots[i].df, tmp, MAX_DPATH) != 0) { - strncpy(changed_prefs.floppyslots[i].df, tmp, MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, tmp, MAX_DPATH); disk_insert(i, tmp); AddFileToDiskList(tmp, 1); extractPath(tmp, currentDir); @@ -209,7 +209,7 @@ public: if (i == 0 && chkLoadConfig->isSelected()) { // Search for config of disk - extractFileName(changed_prefs.floppyslots[i].df, tmp); + extractFileName(workprefs.floppyslots[i].df, tmp); removeFileExtension(tmp); LoadConfigByName(tmp); } @@ -246,17 +246,17 @@ public: if (idx < 0) { disk_eject(i); - strncpy(changed_prefs.floppyslots[i].df, "", MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, "", MAX_DPATH); AdjustDropDownControls(); } else { - if (diskfileList.getElementAt(idx) != changed_prefs.floppyslots[i].df) + if (diskfileList.getElementAt(idx) != workprefs.floppyslots[i].df) { - strncpy(changed_prefs.floppyslots[i].df, diskfileList.getElementAt(idx).c_str(), MAX_DPATH); - disk_insert(i, changed_prefs.floppyslots[i].df); + strncpy(workprefs.floppyslots[i].df, diskfileList.getElementAt(idx).c_str(), MAX_DPATH); + disk_insert(i, workprefs.floppyslots[i].df); lstMRUDiskList.erase(lstMRUDiskList.begin() + idx); - lstMRUDiskList.insert(lstMRUDiskList.begin(), changed_prefs.floppyslots[i].df); + lstMRUDiskList.insert(lstMRUDiskList.begin(), workprefs.floppyslots[i].df); bIgnoreListChange = true; cboDFxFile[i]->setSelected(0); bIgnoreListChange = false; @@ -266,7 +266,7 @@ public: // Search for config of disk char tmp[MAX_DPATH]; - extractFileName(changed_prefs.floppyslots[i].df, tmp); + extractFileName(workprefs.floppyslots[i].df, tmp); removeFileExtension(tmp); LoadConfigByName(tmp); } @@ -288,7 +288,7 @@ class DriveSpeedSliderActionListener : public gcn::ActionListener public: void action(const gcn::ActionEvent& actionEvent) override { - changed_prefs.floppy_speed = drivespeedvalues[int(sldDriveSpeed->getValue())]; + workprefs.floppy_speed = drivespeedvalues[int(sldDriveSpeed->getValue())]; RefreshPanelFloppy(); } }; @@ -304,20 +304,20 @@ public: //--------------------------------------- // Save configuration for current disk //--------------------------------------- - if (strlen(changed_prefs.floppyslots[0].df) > 0) + if (strlen(workprefs.floppyslots[0].df) > 0) { char filename[MAX_DPATH]; char diskname[MAX_DPATH]; - extractFileName(changed_prefs.floppyslots[0].df, diskname); + extractFileName(workprefs.floppyslots[0].df, diskname); removeFileExtension(diskname); fetch_configurationpath(filename, MAX_DPATH); strncat(filename, diskname, MAX_DPATH - 1); strncat(filename, ".uae", MAX_DPATH - 1); - snprintf(changed_prefs.description, 256, "Configuration for disk '%s'", diskname); - if (cfgfile_save(&changed_prefs, filename, 0)) + snprintf(workprefs.description, 256, "Configuration for disk '%s'", diskname); + if (cfgfile_save(&workprefs, filename, 0)) RefreshPanelConfig(); } } @@ -342,7 +342,7 @@ public: extractFileName(tmp, diskname); removeFileExtension(diskname); diskname[31] = '\0'; - disk_creatediskfile(&changed_prefs, tmp, 0, DRV_35_DD, -1, diskname, false, false, nullptr); + disk_creatediskfile(&workprefs, tmp, 0, DRV_35_DD, -1, diskname, false, false, nullptr); AddFileToDiskList(tmp, 1); extractPath(tmp, currentDir); } @@ -359,7 +359,7 @@ public: extractFileName(tmp, diskname); removeFileExtension(diskname); diskname[31] = '\0'; - disk_creatediskfile(&changed_prefs, tmp, 0, DRV_35_HD, -1, diskname, false, false, nullptr); + disk_creatediskfile(&workprefs, tmp, 0, DRV_35_HD, -1, diskname, false, false, nullptr); AddFileToDiskList(tmp, 1); extractPath(tmp, currentDir); } @@ -548,11 +548,11 @@ static void AdjustDropDownControls() { cboDFxFile[i]->clearSelected(); - if (changed_prefs.floppyslots[i].dfxtype != DRV_NONE && strlen(changed_prefs.floppyslots[i].df) > 0) + if (workprefs.floppyslots[i].dfxtype != DRV_NONE && strlen(workprefs.floppyslots[i].df) > 0) { for (unsigned int j = 0; j < lstMRUDiskList.size(); ++j) { - if (strcmp(lstMRUDiskList[j].c_str(), changed_prefs.floppyslots[i].df) == 0) + if (strcmp(lstMRUDiskList[j].c_str(), workprefs.floppyslots[i].df) == 0) { cboDFxFile[i]->setSelected(j); break; @@ -572,17 +572,17 @@ void RefreshPanelFloppy() AdjustDropDownControls(); - changed_prefs.nr_floppies = 0; + workprefs.nr_floppies = 0; for (i = 0; i < 4; ++i) { - const auto driveEnabled = changed_prefs.floppyslots[i].dfxtype != DRV_NONE; + const auto driveEnabled = workprefs.floppyslots[i].dfxtype != DRV_NONE; chkDFx[i]->setSelected(driveEnabled); - cboDFxType[i]->setSelected(changed_prefs.floppyslots[i].dfxtype + 1); - chkDFxWriteProtect[i]->setSelected(disk_getwriteprotect(&changed_prefs, changed_prefs.floppyslots[i].df)); + cboDFxType[i]->setSelected(workprefs.floppyslots[i].dfxtype + 1); + chkDFxWriteProtect[i]->setSelected(disk_getwriteprotect(&workprefs, workprefs.floppyslots[i].df)); chkDFx[i]->setEnabled(prevAvailable); cboDFxType[i]->setEnabled(prevAvailable); - chkDFxWriteProtect[i]->setEnabled(driveEnabled && !changed_prefs.floppy_read_only); + chkDFxWriteProtect[i]->setEnabled(driveEnabled && !workprefs.floppy_read_only); cmdDFxInfo[i]->setEnabled(driveEnabled); cmdDFxEject[i]->setEnabled(driveEnabled); cmdDFxSelect[i]->setEnabled(driveEnabled); @@ -590,14 +590,14 @@ void RefreshPanelFloppy() prevAvailable = driveEnabled; if (driveEnabled) - changed_prefs.nr_floppies = i + 1; + workprefs.nr_floppies = i + 1; } chkLoadConfig->setSelected(bLoadConfigForDisk); for (i = 0; i < 4; ++i) { - if (changed_prefs.floppy_speed == drivespeedvalues[i]) + if (workprefs.floppy_speed == drivespeedvalues[i]) { sldDriveSpeed->setValue(i); lblDriveSpeedInfo->setCaption(drivespeedlist[i]); diff --git a/src/osdep/gui/PanelHD.cpp b/src/osdep/gui/PanelHD.cpp index 56eff1f3..f2ead4ed 100644 --- a/src/osdep/gui/PanelHD.cpp +++ b/src/osdep/gui/PanelHD.cpp @@ -72,10 +72,10 @@ static int GetHDType(const int index) { struct mountedinfo mi{}; - auto type = get_filesys_unitconfig(&changed_prefs, index, &mi); + auto type = get_filesys_unitconfig(&workprefs, index, &mi); if (type < 0) { - const auto uci = &changed_prefs.mountconfig[index]; + const auto uci = &workprefs.mountconfig[index]; type = uci->ci.type == UAEDEV_DIR ? FILESYS_VIRTUAL : FILESYS_HARDFILE; } return type; @@ -113,7 +113,7 @@ public: { if (actionEvent.getSource() == listCmdDelete[i]) { - kill_filesys_unitconfig(&changed_prefs, i); + kill_filesys_unitconfig(&workprefs, i); gui_force_rtarea_hdchange(); break; } @@ -217,15 +217,15 @@ public: { if (actionEvent.getSource() == chkCD) { - if (changed_prefs.cdslots[0].inuse) + if (workprefs.cdslots[0].inuse) { - changed_prefs.cdslots[0].inuse = false; - changed_prefs.cdslots[0].type = SCSI_UNIT_DISABLED; + workprefs.cdslots[0].inuse = false; + workprefs.cdslots[0].type = SCSI_UNIT_DISABLED; } else { - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; } RefreshPanelHD(); RefreshPanelQuickstart(); @@ -246,25 +246,25 @@ public: //--------------------------------------- // Eject CD from drive //--------------------------------------- - strncpy(changed_prefs.cdslots[0].name, "", MAX_DPATH); + strncpy(workprefs.cdslots[0].name, "", MAX_DPATH); AdjustDropDownControls(); } else if (actionEvent.getSource() == cmdCDSelect) { char tmp[MAX_DPATH]; - if (strlen(changed_prefs.cdslots[0].name) > 0) - strncpy(tmp, changed_prefs.cdslots[0].name, MAX_DPATH); + if (strlen(workprefs.cdslots[0].name) > 0) + strncpy(tmp, workprefs.cdslots[0].name, MAX_DPATH); else strcpy(tmp, currentDir); if (SelectFile("Select CD image file", tmp, cdfile_filter)) { - if (strncmp(changed_prefs.cdslots[0].name, tmp, MAX_DPATH) != 0) + if (strncmp(workprefs.cdslots[0].name, tmp, MAX_DPATH) != 0) { - strncpy(changed_prefs.cdslots[0].name, tmp, sizeof(changed_prefs.cdslots[0].name)); - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; + strncpy(workprefs.cdslots[0].name, tmp, sizeof(workprefs.cdslots[0].name)); + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; AddFileToCDList(tmp, 1); extractPath(tmp, currentDir); @@ -289,15 +289,15 @@ public: if (actionEvent.getSource() == sldCDVol) { const auto newvol = 100 - int(sldCDVol->getValue()); - if (changed_prefs.sound_volume_cd != newvol) + if (workprefs.sound_volume_cd != newvol) { - changed_prefs.sound_volume_cd = newvol; + workprefs.sound_volume_cd = newvol; RefreshPanelHD(); } } else if (actionEvent.getSource() == chkHDReadOnly) { - changed_prefs.harddrive_read_only = chkHDReadOnly->isSelected(); + workprefs.harddrive_read_only = chkHDReadOnly->isSelected(); } } }; @@ -321,18 +321,18 @@ public: if (idx < 0) { - strncpy(changed_prefs.cdslots[0].name, "", MAX_DPATH); + strncpy(workprefs.cdslots[0].name, "", MAX_DPATH); AdjustDropDownControls(); } else { - if (cdfileList.getElementAt(idx) != changed_prefs.cdslots[0].name) + if (cdfileList.getElementAt(idx) != workprefs.cdslots[0].name) { - strncpy(changed_prefs.cdslots[0].name, cdfileList.getElementAt(idx).c_str(), sizeof changed_prefs.cdslots[0].name); - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; + strncpy(workprefs.cdslots[0].name, cdfileList.getElementAt(idx).c_str(), sizeof workprefs.cdslots[0].name); + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; lstMRUCDList.erase(lstMRUCDList.begin() + idx); - lstMRUCDList.insert(lstMRUCDList.begin(), changed_prefs.cdslots[0].name); + lstMRUCDList.insert(lstMRUCDList.begin(), workprefs.cdslots[0].name); bIgnoreListChange = true; cboCDFile->setSelected(0); bIgnoreListChange = false; @@ -551,11 +551,11 @@ void ExitPanelHD() static void AdjustDropDownControls() { cboCDFile->clearSelected(); - if (changed_prefs.cdslots[0].inuse && strlen(changed_prefs.cdslots[0].name) > 0) + if (workprefs.cdslots[0].inuse && strlen(workprefs.cdslots[0].name) > 0) { for (unsigned int i = 0; i < lstMRUCDList.size(); ++i) { - if (strcmp(lstMRUCDList[i].c_str(), changed_prefs.cdslots[0].name) == 0) + if (strcmp(lstMRUCDList[i].c_str(), workprefs.cdslots[0].name) == 0) { cboCDFile->setSelected(i); break; @@ -574,11 +574,11 @@ void RefreshPanelHD() for (auto row = 0; row < MAX_HD_DEVICES; ++row) { - if (row < changed_prefs.mountitems) + if (row < workprefs.mountitems) { - auto uci = &changed_prefs.mountconfig[row]; + auto uci = &workprefs.mountconfig[row]; const auto ci = &uci->ci; - auto type = get_filesys_unitconfig(&changed_prefs, row, &mi); + auto type = get_filesys_unitconfig(&workprefs, row, &mi); if (type < 0) { type = uci->ci.type == UAEDEV_DIR ? FILESYS_VIRTUAL : FILESYS_HARDFILE; @@ -632,16 +632,16 @@ void RefreshPanelHD() } } - chkHDReadOnly->setSelected(changed_prefs.harddrive_read_only); + chkHDReadOnly->setSelected(workprefs.harddrive_read_only); - chkCD->setSelected(changed_prefs.cdslots[0].inuse); - cmdCDEject->setEnabled(changed_prefs.cdslots[0].inuse); - cmdCDSelect->setEnabled(changed_prefs.cdslots[0].inuse); - cboCDFile->setEnabled(changed_prefs.cdslots[0].inuse); - sldCDVol->setEnabled(changed_prefs.cdslots[0].inuse); + chkCD->setSelected(workprefs.cdslots[0].inuse); + cmdCDEject->setEnabled(workprefs.cdslots[0].inuse); + cmdCDSelect->setEnabled(workprefs.cdslots[0].inuse); + cboCDFile->setEnabled(workprefs.cdslots[0].inuse); + sldCDVol->setEnabled(workprefs.cdslots[0].inuse); - sldCDVol->setValue(100 - changed_prefs.sound_volume_cd); - snprintf(tmp, 32, "%d %%", 100 - changed_prefs.sound_volume_cd); + sldCDVol->setValue(100 - workprefs.sound_volume_cd); + snprintf(tmp, 32, "%d %%", 100 - workprefs.sound_volume_cd); lblCDVolInfo->setCaption(tmp); } diff --git a/src/osdep/gui/PanelInput.cpp b/src/osdep/gui/PanelInput.cpp index ee3cdd84..81cb082a 100644 --- a/src/osdep/gui/PanelInput.cpp +++ b/src/osdep/gui/PanelInput.cpp @@ -104,26 +104,26 @@ public: { if (i == current_port) continue; - if (changed_prefs.jports[i].id == portListIDs[sel]) + if (workprefs.jports[i].id == portListIDs[sel]) { - changed_prefs.jports[i].id = JPORT_NONE; - changed_prefs.jports[i].idc.configname[0] = 0; - changed_prefs.jports[i].idc.name[0] = 0; - changed_prefs.jports[i].idc.shortid[0] = 0; + workprefs.jports[i].id = JPORT_NONE; + workprefs.jports[i].idc.configname[0] = 0; + workprefs.jports[i].idc.name[0] = 0; + workprefs.jports[i].idc.shortid[0] = 0; } } } static void set_port(const int sel, const int current_port) { - changed_prefs.jports[current_port].id = portListIDs[sel]; - if (changed_prefs.jports[current_port].id == JPORT_NONE) + workprefs.jports[current_port].id = portListIDs[sel]; + if (workprefs.jports[current_port].id == JPORT_NONE) { - changed_prefs.jports[current_port].idc.configname[0] = 0; - changed_prefs.jports[current_port].idc.name[0] = 0; - changed_prefs.jports[current_port].idc.shortid[0] = 0; + workprefs.jports[current_port].idc.configname[0] = 0; + workprefs.jports[current_port].idc.name[0] = 0; + workprefs.jports[current_port].idc.shortid[0] = 0; } - inputdevice_updateconfig(nullptr, &changed_prefs); + inputdevice_updateconfig(nullptr, &workprefs); RefreshPanelInput(); RefreshPanelCustom(); } @@ -185,30 +185,30 @@ public: else if (actionEvent.getSource() == cboPort0mode) { if (cboPort0mode->getSelected() == 0) - changed_prefs.jports[0].mode = JSEM_MODE_MOUSE; + workprefs.jports[0].mode = JSEM_MODE_MOUSE; else if (cboPort0mode->getSelected() == 1) - changed_prefs.jports[0].mode = JSEM_MODE_JOYSTICK; + workprefs.jports[0].mode = JSEM_MODE_JOYSTICK; else if (cboPort0mode->getSelected() == 2) - changed_prefs.jports[0].mode = JSEM_MODE_JOYSTICK_CD32; + workprefs.jports[0].mode = JSEM_MODE_JOYSTICK_CD32; else - changed_prefs.jports[0].mode = JSEM_MODE_DEFAULT; + workprefs.jports[0].mode = JSEM_MODE_DEFAULT; - inputdevice_updateconfig(nullptr, &changed_prefs); + inputdevice_updateconfig(nullptr, &workprefs); RefreshPanelInput(); RefreshPanelCustom(); } else if (actionEvent.getSource() == cboPort1mode) { if (cboPort1mode->getSelected() == 0) - changed_prefs.jports[1].mode = JSEM_MODE_MOUSE; + workprefs.jports[1].mode = JSEM_MODE_MOUSE; else if (cboPort1mode->getSelected() == 1) - changed_prefs.jports[1].mode = JSEM_MODE_JOYSTICK; + workprefs.jports[1].mode = JSEM_MODE_JOYSTICK; else if (cboPort1mode->getSelected() == 2) - changed_prefs.jports[1].mode = JSEM_MODE_JOYSTICK_CD32; + workprefs.jports[1].mode = JSEM_MODE_JOYSTICK_CD32; else - changed_prefs.jports[1].mode = JSEM_MODE_DEFAULT; + workprefs.jports[1].mode = JSEM_MODE_DEFAULT; - inputdevice_updateconfig(nullptr, &changed_prefs); + inputdevice_updateconfig(nullptr, &workprefs); RefreshPanelInput(); RefreshPanelCustom(); } @@ -216,30 +216,30 @@ public: // mousemap drop-down change else if (actionEvent.getSource() == cboPort0mousemode) { - changed_prefs.jports[0].mousemap = cboPort0mousemode->getSelected(); - inputdevice_updateconfig(nullptr, &changed_prefs); + workprefs.jports[0].mousemap = cboPort0mousemode->getSelected(); + inputdevice_updateconfig(nullptr, &workprefs); } else if (actionEvent.getSource() == cboPort1mousemode) { - changed_prefs.jports[1].mousemap = cboPort1mousemode->getSelected(); - inputdevice_updateconfig(nullptr, &changed_prefs); + workprefs.jports[1].mousemap = cboPort1mousemode->getSelected(); + inputdevice_updateconfig(nullptr, &workprefs); } else if (actionEvent.getSource() == cboAutofire) { if (cboAutofire->getSelected() == 0) - changed_prefs.input_autofire_linecnt = 0; + workprefs.input_autofire_linecnt = 0; else if (cboAutofire->getSelected() == 1) - changed_prefs.input_autofire_linecnt = 12 * 312; + workprefs.input_autofire_linecnt = 12 * 312; else if (cboAutofire->getSelected() == 2) - changed_prefs.input_autofire_linecnt = 8 * 312; + workprefs.input_autofire_linecnt = 8 * 312; else - changed_prefs.input_autofire_linecnt = 4 * 312; + workprefs.input_autofire_linecnt = 4 * 312; } else if (actionEvent.getSource() == sldMouseSpeed) { - changed_prefs.input_joymouse_multiplier = mousespeed_values[int(sldMouseSpeed->getValue())]; + workprefs.input_joymouse_multiplier = mousespeed_values[int(sldMouseSpeed->getValue())]; RefreshPanelInput(); } @@ -251,7 +251,7 @@ public: else SDL_ANDROID_SetMouseEmulationMode(1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1); #endif - changed_prefs.input_tablet = chkMouseHack->isSelected() ? TABLET_MOUSEHACK : TABLET_OFF; + workprefs.input_tablet = chkMouseHack->isSelected() ? TABLET_MOUSEHACK : TABLET_OFF; } } }; @@ -461,7 +461,7 @@ void RefreshPanelInput() auto idx = 0; for (auto i = 0; i < ctrlPortList.getNumberOfElements(); ++i) { - if (changed_prefs.jports[0].id == portListIDs[i]) + if (workprefs.jports[0].id == portListIDs[i]) { idx = i; break; @@ -473,7 +473,7 @@ void RefreshPanelInput() idx = 0; for (auto i = 0; i < ctrlPortList.getNumberOfElements(); ++i) { - if (changed_prefs.jports[1].id == portListIDs[i]) + if (workprefs.jports[1].id == portListIDs[i]) { idx = i; break; @@ -485,7 +485,7 @@ void RefreshPanelInput() idx = 0; for (auto i = 0; i < ctrlPortList.getNumberOfElements(); ++i) { - if (changed_prefs.jports[2].id == portListIDs[i]) + if (workprefs.jports[2].id == portListIDs[i]) { idx = i; break; @@ -497,7 +497,7 @@ void RefreshPanelInput() idx = 0; for (auto i = 0; i < ctrlPortList.getNumberOfElements(); ++i) { - if (changed_prefs.jports[3].id == portListIDs[i]) + if (workprefs.jports[3].id == portListIDs[i]) { idx = i; break; @@ -505,38 +505,38 @@ void RefreshPanelInput() } cboPort3->setSelected(idx); - if (changed_prefs.input_autofire_linecnt == 0) + if (workprefs.input_autofire_linecnt == 0) cboAutofire->setSelected(0); - else if (changed_prefs.input_autofire_linecnt > 10 * 312) + else if (workprefs.input_autofire_linecnt > 10 * 312) cboAutofire->setSelected(1); - else if (changed_prefs.input_autofire_linecnt > 6 * 312) + else if (workprefs.input_autofire_linecnt > 6 * 312) cboAutofire->setSelected(2); else cboAutofire->setSelected(3); - if (changed_prefs.jports[0].mode == JSEM_MODE_MOUSE) + if (workprefs.jports[0].mode == JSEM_MODE_MOUSE) cboPort0mode->setSelected(0); - else if (changed_prefs.jports[0].mode == JSEM_MODE_JOYSTICK) + else if (workprefs.jports[0].mode == JSEM_MODE_JOYSTICK) cboPort0mode->setSelected(1); - else if (changed_prefs.jports[0].mode == JSEM_MODE_JOYSTICK_CD32) + else if (workprefs.jports[0].mode == JSEM_MODE_JOYSTICK_CD32) cboPort0mode->setSelected(2); else cboPort0mode->setSelected(3); - if (changed_prefs.jports[1].mode == JSEM_MODE_MOUSE) + if (workprefs.jports[1].mode == JSEM_MODE_MOUSE) cboPort1mode->setSelected(0); - else if (changed_prefs.jports[1].mode == JSEM_MODE_JOYSTICK) + else if (workprefs.jports[1].mode == JSEM_MODE_JOYSTICK) cboPort1mode->setSelected(1); - else if (changed_prefs.jports[1].mode == JSEM_MODE_JOYSTICK_CD32) + else if (workprefs.jports[1].mode == JSEM_MODE_JOYSTICK_CD32) cboPort1mode->setSelected(2); else cboPort1mode->setSelected(3); // changed mouse map - cboPort0mousemode->setSelected(changed_prefs.jports[0].mousemap); - cboPort1mousemode->setSelected(changed_prefs.jports[1].mousemap); + cboPort0mousemode->setSelected(workprefs.jports[0].mousemap); + cboPort1mousemode->setSelected(workprefs.jports[1].mousemap); if (cboPort0mode->getSelected() == 0) { @@ -558,7 +558,7 @@ void RefreshPanelInput() for (auto i = 0; i < 5; ++i) { - if (changed_prefs.input_joymouse_multiplier == mousespeed_values[i]) + if (workprefs.input_joymouse_multiplier == mousespeed_values[i]) { sldMouseSpeed->setValue(i); lblMouseSpeedInfo->setCaption(mousespeed_list[i]); @@ -566,7 +566,7 @@ void RefreshPanelInput() } } - chkMouseHack->setSelected(changed_prefs.input_tablet == TABLET_MOUSEHACK); + chkMouseHack->setSelected(workprefs.input_tablet == TABLET_MOUSEHACK); } bool HelpPanelInput(std::vector &helptext) diff --git a/src/osdep/gui/PanelMisc.cpp b/src/osdep/gui/PanelMisc.cpp index 97a56cba..08d16fef 100644 --- a/src/osdep/gui/PanelMisc.cpp +++ b/src/osdep/gui/PanelMisc.cpp @@ -85,49 +85,49 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == chkStatusLine) - changed_prefs.leds_on_screen = chkStatusLine->isSelected(); + workprefs.leds_on_screen = chkStatusLine->isSelected(); else if (actionEvent.getSource() == chkHideIdleLed) - changed_prefs.hide_idle_led = chkHideIdleLed->isSelected(); + workprefs.hide_idle_led = chkHideIdleLed->isSelected(); else if (actionEvent.getSource() == chkShowGUI) - changed_prefs.start_gui = chkShowGUI->isSelected(); + workprefs.start_gui = chkShowGUI->isSelected(); else if (actionEvent.getSource() == chkRetroArchQuit) { - changed_prefs.use_retroarch_quit = chkRetroArchQuit->isSelected(); + workprefs.use_retroarch_quit = chkRetroArchQuit->isSelected(); RefreshPanelCustom(); } else if (actionEvent.getSource() == chkRetroArchMenu) { - changed_prefs.use_retroarch_menu = chkRetroArchMenu->isSelected(); + workprefs.use_retroarch_menu = chkRetroArchMenu->isSelected(); RefreshPanelCustom(); } else if (actionEvent.getSource() == chkRetroArchReset) { - changed_prefs.use_retroarch_reset = chkRetroArchReset->isSelected(); + workprefs.use_retroarch_reset = chkRetroArchReset->isSelected(); RefreshPanelCustom(); } // else if (actionEvent.getSource() == chkRetroArchSavestate) - // changed_prefs.amiberry_use_retroarch_savestatebuttons = chkRetroArchSavestate->isSelected(); + // workprefs.amiberry_use_retroarch_savestatebuttons = chkRetroArchSavestate->isSelected(); else if (actionEvent.getSource() == chkBSDSocket) - changed_prefs.socket_emu = chkBSDSocket->isSelected(); + workprefs.socket_emu = chkBSDSocket->isSelected(); else if (actionEvent.getSource() == chkMasterWP) { - changed_prefs.floppy_read_only = chkMasterWP->isSelected(); + workprefs.floppy_read_only = chkMasterWP->isSelected(); RefreshPanelQuickstart(); RefreshPanelFloppy(); } else if (actionEvent.getSource() == cboKBDLed_num) - changed_prefs.kbd_led_num = cboKBDLed_num->getSelected(); + workprefs.kbd_led_num = cboKBDLed_num->getSelected(); else if (actionEvent.getSource() == cboKBDLed_scr) - changed_prefs.kbd_led_scr = cboKBDLed_scr->getSelected(); + workprefs.kbd_led_scr = cboKBDLed_scr->getSelected(); else if (actionEvent.getSource() == cmdOpenGUI) { @@ -135,7 +135,7 @@ public: if (key != nullptr) { txtOpenGUI->setText(key); - strcpy(changed_prefs.open_gui, key); + strcpy(workprefs.open_gui, key); } } @@ -145,7 +145,7 @@ public: if (key != nullptr) { txtKeyForQuit->setText(key); - strcpy(changed_prefs.quit_amiberry, key); + strcpy(workprefs.quit_amiberry, key); } } @@ -155,7 +155,7 @@ public: if (key != nullptr) { txtKeyActionReplay->setText(key); - strcpy(changed_prefs.action_replay, key); + strcpy(workprefs.action_replay, key); } } @@ -165,7 +165,7 @@ public: if (key != nullptr) { txtKeyFullScreen->setText(key); - strcpy(changed_prefs.fullscreen_toggle, key); + strcpy(workprefs.fullscreen_toggle, key); } } } @@ -372,25 +372,25 @@ void ExitPanelMisc() void RefreshPanelMisc() { - chkStatusLine->setSelected(changed_prefs.leds_on_screen); - chkHideIdleLed->setSelected(changed_prefs.hide_idle_led); - chkShowGUI->setSelected(changed_prefs.start_gui); + chkStatusLine->setSelected(workprefs.leds_on_screen); + chkHideIdleLed->setSelected(workprefs.hide_idle_led); + chkShowGUI->setSelected(workprefs.start_gui); - chkRetroArchQuit->setSelected(changed_prefs.use_retroarch_quit); - chkRetroArchMenu->setSelected(changed_prefs.use_retroarch_menu); - chkRetroArchReset->setSelected(changed_prefs.use_retroarch_reset); - //chkRetroArchSavestate->setSelected(changed_prefs.use_retroarch_statebuttons); + chkRetroArchQuit->setSelected(workprefs.use_retroarch_quit); + chkRetroArchMenu->setSelected(workprefs.use_retroarch_menu); + chkRetroArchReset->setSelected(workprefs.use_retroarch_reset); + //chkRetroArchSavestate->setSelected(workprefs.use_retroarch_statebuttons); - chkBSDSocket->setSelected(changed_prefs.socket_emu); - chkMasterWP->setSelected(changed_prefs.floppy_read_only); + chkBSDSocket->setSelected(workprefs.socket_emu); + chkMasterWP->setSelected(workprefs.floppy_read_only); - cboKBDLed_num->setSelected(changed_prefs.kbd_led_num); - cboKBDLed_scr->setSelected(changed_prefs.kbd_led_scr); + cboKBDLed_num->setSelected(workprefs.kbd_led_num); + cboKBDLed_scr->setSelected(workprefs.kbd_led_scr); - txtOpenGUI->setText(strncmp(changed_prefs.open_gui, "", 1) != 0 ? changed_prefs.open_gui : "Click to map"); - txtKeyForQuit->setText(strncmp(changed_prefs.quit_amiberry, "", 1) != 0 ? changed_prefs.quit_amiberry : "Click to map"); - txtKeyActionReplay->setText(strncmp(changed_prefs.action_replay, "", 1) != 0 ? changed_prefs.action_replay : "Click to map"); - txtKeyFullScreen->setText(strncmp(changed_prefs.fullscreen_toggle, "", 1) != 0 ? changed_prefs.fullscreen_toggle : "Click to map"); + txtOpenGUI->setText(strncmp(workprefs.open_gui, "", 1) != 0 ? workprefs.open_gui : "Click to map"); + txtKeyForQuit->setText(strncmp(workprefs.quit_amiberry, "", 1) != 0 ? workprefs.quit_amiberry : "Click to map"); + txtKeyActionReplay->setText(strncmp(workprefs.action_replay, "", 1) != 0 ? workprefs.action_replay : "Click to map"); + txtKeyFullScreen->setText(strncmp(workprefs.fullscreen_toggle, "", 1) != 0 ? workprefs.fullscreen_toggle : "Click to map"); } bool HelpPanelMisc(std::vector &helptext) diff --git a/src/osdep/gui/PanelQuickstart.cpp b/src/osdep/gui/PanelQuickstart.cpp index 40357a72..a958463e 100644 --- a/src/osdep/gui/PanelQuickstart.cpp +++ b/src/osdep/gui/PanelQuickstart.cpp @@ -184,7 +184,7 @@ static void SetControlState(const int model) break; } - chkDFxWriteProtect[0]->setEnabled(df0Editable && !changed_prefs.floppy_read_only); + chkDFxWriteProtect[0]->setEnabled(df0Editable && !workprefs.floppy_read_only); cmdDFxInfo[0]->setEnabled(df0Editable); cmdDFxEject[0]->setEnabled(df0Editable); cmdDFxSelect[0]->setEnabled(df0Editable); @@ -206,9 +206,9 @@ static void SetControlState(const int model) static void AdjustPrefs(void) { - //const auto old_cs = changed_prefs.cs_compatible; + //const auto old_cs = workprefs.cs_compatible; - built_in_prefs(&changed_prefs, quickstart_model, quickstart_conf, 0, 0); + built_in_prefs(&workprefs, quickstart_model, quickstart_conf, 0, 0); switch (quickstart_model) { case 0: // A500 @@ -220,22 +220,22 @@ static void AdjustPrefs(void) case 6: // A4000 case 7: // A4000T // df0 always active - changed_prefs.floppyslots[0].dfxtype = DRV_35_DD; + workprefs.floppyslots[0].dfxtype = DRV_35_DD; // No CD available - changed_prefs.cdslots[0].inuse = false; - changed_prefs.cdslots[0].type = SCSI_UNIT_DISABLED; + workprefs.cdslots[0].inuse = false; + workprefs.cdslots[0].type = SCSI_UNIT_DISABLED; break; case 8: // CD32 case 9: // CDTV // No floppy drive available, CD available - changed_prefs.floppyslots[0].dfxtype = DRV_NONE; - changed_prefs.floppyslots[1].dfxtype = DRV_NONE; - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; - changed_prefs.gfx_size.width = 768; - changed_prefs.gfx_size.height = 270; + workprefs.floppyslots[0].dfxtype = DRV_NONE; + workprefs.floppyslots[1].dfxtype = DRV_NONE; + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; + workprefs.gfx_monitor.gfx_size.width = 768; + workprefs.gfx_monitor.gfx_size.height = 270; break; default: break; @@ -341,25 +341,25 @@ public: //--------------------------------------- // Eject CD from drive //--------------------------------------- - strncpy(changed_prefs.cdslots[0].name, "", MAX_DPATH); + strncpy(workprefs.cdslots[0].name, "", MAX_DPATH); AdjustDropDownControls(); } else if (actionEvent.getSource() == cmdCDSelect) { char tmp[MAX_DPATH]; - if (strlen(changed_prefs.cdslots[0].name) > 0) - strncpy(tmp, changed_prefs.cdslots[0].name, MAX_DPATH); + if (strlen(workprefs.cdslots[0].name) > 0) + strncpy(tmp, workprefs.cdslots[0].name, MAX_DPATH); else strncpy(tmp, currentDir, MAX_DPATH); if (SelectFile("Select CD image file", tmp, cdfile_filter)) { - if (strncmp(changed_prefs.cdslots[0].name, tmp, MAX_DPATH) != 0) + if (strncmp(workprefs.cdslots[0].name, tmp, MAX_DPATH) != 0) { - strncpy(changed_prefs.cdslots[0].name, tmp, MAX_DPATH); - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; + strncpy(workprefs.cdslots[0].name, tmp, MAX_DPATH); + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; AddFileToCDList(tmp, 1); extractPath(tmp, currentDir); @@ -393,18 +393,18 @@ public: if (idx < 0) { - strncpy(changed_prefs.cdslots[0].name, "", MAX_DPATH); + strncpy(workprefs.cdslots[0].name, "", MAX_DPATH); AdjustDropDownControls(); } else { - if (cdfileList.getElementAt(idx) != changed_prefs.cdslots[0].name) + if (cdfileList.getElementAt(idx) != workprefs.cdslots[0].name) { - strncpy(changed_prefs.cdslots[0].name, cdfileList.getElementAt(idx).c_str(), MAX_DPATH); - changed_prefs.cdslots[0].inuse = true; - changed_prefs.cdslots[0].type = SCSI_UNIT_IMAGE; + strncpy(workprefs.cdslots[0].name, cdfileList.getElementAt(idx).c_str(), MAX_DPATH); + workprefs.cdslots[0].inuse = true; + workprefs.cdslots[0].type = SCSI_UNIT_IMAGE; lstMRUCDList.erase(lstMRUCDList.begin() + idx); - lstMRUCDList.insert(lstMRUCDList.begin(), changed_prefs.cdslots[0].name); + lstMRUCDList.insert(lstMRUCDList.begin(), workprefs.cdslots[0].name); bIgnoreListChange = true; cboCDFile->setSelected(0); bIgnoreListChange = false; @@ -474,13 +474,13 @@ public: { if (chkNTSC->isSelected()) { - changed_prefs.ntscmode = true; - changed_prefs.chipset_refreshrate = 60; + workprefs.ntscmode = true; + workprefs.chipset_refreshrate = 60; } else { - changed_prefs.ntscmode = false; - changed_prefs.chipset_refreshrate = 50; + workprefs.ntscmode = false; + workprefs.chipset_refreshrate = 50; } RefreshPanelChipset(); } @@ -502,18 +502,18 @@ public: // Drive enabled/disabled //--------------------------------------- if (chkDFx[i]->isSelected()) - changed_prefs.floppyslots[i].dfxtype = DRV_35_DD; + workprefs.floppyslots[i].dfxtype = DRV_35_DD; else - changed_prefs.floppyslots[i].dfxtype = DRV_NONE; + workprefs.floppyslots[i].dfxtype = DRV_NONE; } else if (actionEvent.getSource() == chkDFxWriteProtect[i]) { //--------------------------------------- // Write-protect changed //--------------------------------------- - disk_setwriteprotect(&changed_prefs, i, changed_prefs.floppyslots[i].df, + disk_setwriteprotect(&workprefs, i, workprefs.floppyslots[i].df, chkDFxWriteProtect[i]->isSelected()); - if (disk_getwriteprotect(&changed_prefs, changed_prefs.floppyslots[i].df) != chkDFxWriteProtect[i]-> + if (disk_getwriteprotect(&workprefs, workprefs.floppyslots[i].df) != chkDFxWriteProtect[i]-> isSelected()) { // Failed to change write protection -> maybe filesystem doesn't support this @@ -545,7 +545,7 @@ public: //--------------------------------------- // Show info about current disk-image //--------------------------------------- - //if (changed_prefs.floppyslots[i].dfxtype != DRV_NONE && strlen(changed_prefs.floppyslots[i].df) > 0); + //if (workprefs.floppyslots[i].dfxtype != DRV_NONE && strlen(workprefs.floppyslots[i].df) > 0); // ToDo: Show info dialog } else if (actionEvent.getSource() == cmdDFxEject[i]) @@ -554,7 +554,7 @@ public: // Eject disk from drive //--------------------------------------- disk_eject(i); - strncpy(changed_prefs.floppyslots[i].df, "", MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, "", MAX_DPATH); AdjustDropDownControls(); } else if (actionEvent.getSource() == cmdDFxSelect[i]) @@ -564,15 +564,15 @@ public: //--------------------------------------- char tmp[MAX_DPATH]; - if (strlen(changed_prefs.floppyslots[i].df) > 0) - strncpy(tmp, changed_prefs.floppyslots[i].df, MAX_DPATH); + if (strlen(workprefs.floppyslots[i].df) > 0) + strncpy(tmp, workprefs.floppyslots[i].df, MAX_DPATH); else strncpy(tmp, currentDir, MAX_DPATH); if (SelectFile("Select disk image file", tmp, diskfile_filter)) { - if (strncmp(changed_prefs.floppyslots[i].df, tmp, MAX_DPATH) != 0) + if (strncmp(workprefs.floppyslots[i].df, tmp, MAX_DPATH) != 0) { - strncpy(changed_prefs.floppyslots[i].df, tmp, MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, tmp, MAX_DPATH); disk_insert(i, tmp); AddFileToDiskList(tmp, 1); extractPath(tmp, currentDir); @@ -611,17 +611,17 @@ public: if (idx < 0) { disk_eject(i); - strncpy(changed_prefs.floppyslots[i].df, "", MAX_DPATH); + strncpy(workprefs.floppyslots[i].df, "", MAX_DPATH); AdjustDropDownControls(); } else { - if (diskfileList.getElementAt(idx) != changed_prefs.floppyslots[i].df) + if (diskfileList.getElementAt(idx) != workprefs.floppyslots[i].df) { - strncpy(changed_prefs.floppyslots[i].df, diskfileList.getElementAt(idx).c_str(), MAX_DPATH); - disk_insert(i, changed_prefs.floppyslots[i].df); + strncpy(workprefs.floppyslots[i].df, diskfileList.getElementAt(idx).c_str(), MAX_DPATH); + disk_insert(i, workprefs.floppyslots[i].df); lstMRUDiskList.erase(lstMRUDiskList.begin() + idx); - lstMRUDiskList.insert(lstMRUDiskList.begin(), changed_prefs.floppyslots[i].df); + lstMRUDiskList.insert(lstMRUDiskList.begin(), workprefs.floppyslots[i].df); bIgnoreListChange = true; cboDFxFile[i]->setSelected(0); bIgnoreListChange = false; @@ -862,11 +862,11 @@ static void AdjustDropDownControls(void) { cboDFxFile[i]->clearSelected(); - if (changed_prefs.floppyslots[i].dfxtype != DRV_NONE && strlen(changed_prefs.floppyslots[i].df) > 0) + if (workprefs.floppyslots[i].dfxtype != DRV_NONE && strlen(workprefs.floppyslots[i].df) > 0) { for (unsigned int j = 0; j < lstMRUDiskList.size(); ++j) { - if (strcmp(lstMRUDiskList[j].c_str(), changed_prefs.floppyslots[i].df) == 0) + if (strcmp(lstMRUDiskList[j].c_str(), workprefs.floppyslots[i].df) == 0) { cboDFxFile[i]->setSelected(j); break; @@ -876,11 +876,11 @@ static void AdjustDropDownControls(void) } cboCDFile->clearSelected(); - if (changed_prefs.cdslots[0].inuse && strlen(changed_prefs.cdslots[0].name) > 0) + if (workprefs.cdslots[0].inuse && strlen(workprefs.cdslots[0].name) > 0) { for (unsigned int i = 0; i < lstMRUCDList.size(); ++i) { - if (lstMRUCDList[i].c_str() != changed_prefs.cdslots[0].name) + if (lstMRUCDList[i].c_str() != workprefs.cdslots[0].name) { cboCDFile->setSelected(i); break; @@ -896,38 +896,38 @@ void RefreshPanelQuickstart(void) { auto prevAvailable = true; - chkNTSC->setSelected(changed_prefs.ntscmode); + chkNTSC->setSelected(workprefs.ntscmode); AdjustDropDownControls(); - changed_prefs.nr_floppies = 0; + workprefs.nr_floppies = 0; for (auto i = 0; i < 4; ++i) { - const auto driveEnabled = changed_prefs.floppyslots[i].dfxtype != DRV_NONE; + const auto driveEnabled = workprefs.floppyslots[i].dfxtype != DRV_NONE; if (i < 2) { chkDFx[i]->setSelected(driveEnabled); - chkDFxWriteProtect[i]->setSelected(disk_getwriteprotect(&changed_prefs, changed_prefs.floppyslots[i].df)); + chkDFxWriteProtect[i]->setSelected(disk_getwriteprotect(&workprefs, workprefs.floppyslots[i].df)); if (i == 0) chkDFx[i]->setEnabled(false); else chkDFx[i]->setEnabled(prevAvailable); cmdDFxInfo[i]->setEnabled(driveEnabled); - chkDFxWriteProtect[i]->setEnabled(driveEnabled && !changed_prefs.floppy_read_only); + chkDFxWriteProtect[i]->setEnabled(driveEnabled && !workprefs.floppy_read_only); cmdDFxEject[i]->setEnabled(driveEnabled); cmdDFxSelect[i]->setEnabled(driveEnabled); cboDFxFile[i]->setEnabled(driveEnabled); } prevAvailable = driveEnabled; if (driveEnabled) - changed_prefs.nr_floppies = i + 1; + workprefs.nr_floppies = i + 1; } - chkCD->setSelected(changed_prefs.cdslots[0].inuse); - cmdCDEject->setEnabled(changed_prefs.cdslots[0].inuse); - cmdCDSelect->setEnabled(changed_prefs.cdslots[0].inuse); - cboCDFile->setEnabled(changed_prefs.cdslots[0].inuse); + chkCD->setSelected(workprefs.cdslots[0].inuse); + cmdCDEject->setEnabled(workprefs.cdslots[0].inuse); + cmdCDSelect->setEnabled(workprefs.cdslots[0].inuse); + cboCDFile->setEnabled(workprefs.cdslots[0].inuse); chkQuickstartMode->setSelected(quickstart_start); } diff --git a/src/osdep/gui/PanelRAM.cpp b/src/osdep/gui/PanelRAM.cpp index 00946fad..dc06c43c 100644 --- a/src/osdep/gui/PanelRAM.cpp +++ b/src/osdep/gui/PanelRAM.cpp @@ -61,47 +61,47 @@ public: { if (actionEvent.getSource() == sldChipmem) { - changed_prefs.chipmem_size = ChipMem_values[int(sldChipmem->getValue())]; - if ((changed_prefs.chipmem_size > 0x200000) && (changed_prefs.fastmem[0].size > 0)) - changed_prefs.fastmem[0].size = 0; + workprefs.chipmem_size = ChipMem_values[int(sldChipmem->getValue())]; + if ((workprefs.chipmem_size > 0x200000) && (workprefs.fastmem[0].size > 0)) + workprefs.fastmem[0].size = 0; } if (actionEvent.getSource() == sldSlowmem) { - changed_prefs.bogomem_size = SlowMem_values[int(sldSlowmem->getValue())]; + workprefs.bogomem_size = SlowMem_values[int(sldSlowmem->getValue())]; } if (actionEvent.getSource() == sldFastmem) { - changed_prefs.fastmem[0].size = FastMem_values[int(sldFastmem->getValue())]; - if (changed_prefs.fastmem[0].size > 0 && changed_prefs.chipmem_size > 0x200000) - changed_prefs.chipmem_size = 0x200000; + workprefs.fastmem[0].size = FastMem_values[int(sldFastmem->getValue())]; + if (workprefs.fastmem[0].size > 0 && workprefs.chipmem_size > 0x200000) + workprefs.chipmem_size = 0x200000; } if (actionEvent.getSource() == sldZ3mem) { - changed_prefs.z3fastmem[0].size = FastMem_values[int(sldZ3mem->getValue())]; - if (changed_prefs.z3fastmem[0].size > max_z3fastmem) - changed_prefs.z3fastmem[0].size = max_z3fastmem; + workprefs.z3fastmem[0].size = FastMem_values[int(sldZ3mem->getValue())]; + if (workprefs.z3fastmem[0].size > max_z3fastmem) + workprefs.z3fastmem[0].size = max_z3fastmem; } if (actionEvent.getSource() == sldGfxmem) { - changed_prefs.rtgboards[0].rtgmem_size = FastMem_values[int(sldGfxmem->getValue())]; - changed_prefs.rtgboards[0].rtgmem_type = GFXBOARD_UAE_Z3; + workprefs.rtgboards[0].rtgmem_size = FastMem_values[int(sldGfxmem->getValue())]; + workprefs.rtgboards[0].rtgmem_type = GFXBOARD_UAE_Z3; } if (actionEvent.getSource() == sldA3000Lowmem) { - changed_prefs.mbresmem_low_size = A3000LowMem_values[int(sldA3000Lowmem->getValue())]; - if (currprefs.mbresmem_low_size != changed_prefs.mbresmem_low_size) + workprefs.mbresmem_low_size = A3000LowMem_values[int(sldA3000Lowmem->getValue())]; + if (currprefs.mbresmem_low_size != workprefs.mbresmem_low_size) DisableResume(); } if (actionEvent.getSource() == sldA3000Highmem) { - changed_prefs.mbresmem_high_size = A3000HighMem_values[int(sldA3000Highmem->getValue())]; - if (currprefs.mbresmem_high_size != changed_prefs.mbresmem_high_size) + workprefs.mbresmem_high_size = A3000HighMem_values[int(sldA3000Highmem->getValue())]; + if (currprefs.mbresmem_high_size != workprefs.mbresmem_high_size) DisableResume(); } @@ -278,7 +278,7 @@ void RefreshPanelRAM() for (i = 0; i < 5; ++i) { - if (changed_prefs.chipmem_size == ChipMem_values[i]) + if (workprefs.chipmem_size == ChipMem_values[i]) { sldChipmem->setValue(i); lblChipsize->setCaption(ChipMem_list[i]); @@ -288,7 +288,7 @@ void RefreshPanelRAM() for (i = 0; i < 5; ++i) { - if (changed_prefs.bogomem_size == SlowMem_values[i]) + if (workprefs.bogomem_size == SlowMem_values[i]) { sldSlowmem->setValue(i); lblSlowsize->setCaption(SlowMem_list[i]); @@ -298,7 +298,7 @@ void RefreshPanelRAM() for (i = 0; i < 5; ++i) { - if (changed_prefs.fastmem[0].size == FastMem_values[i]) + if (workprefs.fastmem[0].size == FastMem_values[i]) { sldFastmem->setValue(i); lblFastsize->setCaption(FastMem_list[i]); @@ -308,29 +308,29 @@ void RefreshPanelRAM() for (i = 0; i < 9; ++i) { - if (changed_prefs.z3fastmem[0].size == FastMem_values[i]) + if (workprefs.z3fastmem[0].size == FastMem_values[i]) { sldZ3mem->setValue(i); lblZ3size->setCaption(FastMem_list[i]); break; } } - sldZ3mem->setEnabled(!changed_prefs.address_space_24); + sldZ3mem->setEnabled(!workprefs.address_space_24); for (i = 0; i < 9; ++i) { - if (changed_prefs.rtgboards[0].rtgmem_size == FastMem_values[i]) + if (workprefs.rtgboards[0].rtgmem_size == FastMem_values[i]) { sldGfxmem->setValue(i); lblGfxsize->setCaption(FastMem_list[i]); break; } } - sldGfxmem->setEnabled(!changed_prefs.address_space_24); + sldGfxmem->setEnabled(!workprefs.address_space_24); for (i = 0; i < 3; ++i) { - if (changed_prefs.mbresmem_low_size == A3000LowMem_values[i]) + if (workprefs.mbresmem_low_size == A3000LowMem_values[i]) { sldA3000Lowmem->setValue(i); lblA3000Lowsize->setCaption(A3000LowMem_list[i]); @@ -340,7 +340,7 @@ void RefreshPanelRAM() for (i = 0; i < 4; ++i) { - if (changed_prefs.mbresmem_high_size == A3000HighMem_values[i]) + if (workprefs.mbresmem_high_size == A3000HighMem_values[i]) { sldA3000Highmem->setValue(i); lblA3000Highsize->setCaption(A3000HighMem_list[i]); diff --git a/src/osdep/gui/PanelROM.cpp b/src/osdep/gui/PanelROM.cpp index 03a9970c..28379044 100644 --- a/src/osdep/gui/PanelROM.cpp +++ b/src/osdep/gui/PanelROM.cpp @@ -99,7 +99,7 @@ public: { const auto rom = mainROMList->getROMat(cboMainROM->getSelected()); if (rom != nullptr) - strncpy(changed_prefs.romfile, rom->Path, sizeof(changed_prefs.romfile)); + strncpy(workprefs.romfile, rom->Path, sizeof(workprefs.romfile)); } }; @@ -113,9 +113,9 @@ public: { const auto rom = extROMList->getROMat(cboExtROM->getSelected()); if (rom != nullptr) - strncpy(changed_prefs.romextfile, rom->Path, sizeof(changed_prefs.romextfile)); + strncpy(workprefs.romextfile, rom->Path, sizeof(workprefs.romextfile)); else - strncpy(changed_prefs.romextfile, "", sizeof(changed_prefs.romextfile)); + strncpy(workprefs.romextfile, "", sizeof(workprefs.romextfile)); } }; @@ -128,9 +128,9 @@ public: { const auto rom = cartROMList->getROMat(cboCartROM->getSelected()); if (rom != nullptr) - strncpy(changed_prefs.cartfile, rom->Path, sizeof changed_prefs.cartfile); + strncpy(workprefs.cartfile, rom->Path, sizeof workprefs.cartfile); else - strncpy(changed_prefs.cartfile, "", sizeof changed_prefs.cartfile); + strncpy(workprefs.cartfile, "", sizeof workprefs.cartfile); } }; static CartROMActionListener* cartROMActionListener; @@ -154,7 +154,7 @@ public: strncpy(newrom->Path, tmp, MAX_DPATH); newrom->ROMType = ROMTYPE_KICK; lstAvailableROMs.push_back(newrom); - strncpy(changed_prefs.romfile, tmp, sizeof(changed_prefs.romfile)); + strncpy(workprefs.romfile, tmp, sizeof(workprefs.romfile)); RefreshPanelROM(); } cmdMainROM->requestFocus(); @@ -170,7 +170,7 @@ public: strncpy(newrom->Path, tmp, MAX_DPATH); newrom->ROMType = ROMTYPE_EXTCDTV; lstAvailableROMs.push_back(newrom); - strncpy(changed_prefs.romextfile, tmp, sizeof(changed_prefs.romextfile)); + strncpy(workprefs.romextfile, tmp, sizeof(workprefs.romextfile)); RefreshPanelROM(); } cmdExtROM->requestFocus(); @@ -186,7 +186,7 @@ public: strncpy(newrom->Path, tmp, MAX_DPATH); newrom->ROMType = ROMTYPE_CD32CART; lstAvailableROMs.push_back(newrom); - strncpy(changed_prefs.romextfile, tmp, sizeof(changed_prefs.romextfile)); + strncpy(workprefs.romextfile, tmp, sizeof(workprefs.romextfile)); RefreshPanelROM(); } cmdCartROM->requestFocus(); @@ -297,13 +297,13 @@ void ExitPanelROM() void RefreshPanelROM() { - auto idx = mainROMList->InitROMList(changed_prefs.romfile); + auto idx = mainROMList->InitROMList(workprefs.romfile); cboMainROM->setSelected(idx); - idx = extROMList->InitROMList(changed_prefs.romextfile); + idx = extROMList->InitROMList(workprefs.romextfile); cboExtROM->setSelected(idx); - idx = cartROMList->InitROMList(changed_prefs.cartfile); + idx = cartROMList->InitROMList(workprefs.cartfile); cboCartROM->setSelected(idx); } diff --git a/src/osdep/gui/PanelSavestate.cpp b/src/osdep/gui/PanelSavestate.cpp index a4ef608c..5a057a22 100644 --- a/src/osdep/gui/PanelSavestate.cpp +++ b/src/osdep/gui/PanelSavestate.cpp @@ -66,7 +66,7 @@ public: if (f) { fclose(f); - savestate_initsave(savestate_fname, 2, 0, false); + savestate_initsave(savestate_fname); savestate_state = STATE_DORESTORE; gui_running = false; } @@ -86,7 +86,7 @@ public: //------------------------------------------ if (emulating) { - savestate_initsave(savestate_fname, 2, 0, false); + savestate_initsave(savestate_fname); save_state(savestate_fname, "..."); savestate_state = STATE_DOSAVE; // Just to create the screenshot delay_savestate_frame = 2; diff --git a/src/osdep/gui/PanelSound.cpp b/src/osdep/gui/PanelSound.cpp index e3bcc630..53f0726a 100644 --- a/src/osdep/gui/PanelSound.cpp +++ b/src/osdep/gui/PanelSound.cpp @@ -141,34 +141,34 @@ public: void action(const gcn::ActionEvent& actionEvent) override { if (actionEvent.getSource() == optSoundDisabled) - changed_prefs.produce_sound = 0; + workprefs.produce_sound = 0; else if (actionEvent.getSource() == optSoundDisabledEmu) - changed_prefs.produce_sound = 1; + workprefs.produce_sound = 1; else if (actionEvent.getSource() == optSoundEmulated) - changed_prefs.produce_sound = 2; + workprefs.produce_sound = 2; else if (actionEvent.getSource() == optSoundEmulatedBest) - changed_prefs.produce_sound = 3; + workprefs.produce_sound = 3; else if (actionEvent.getSource() == optMono) - changed_prefs.sound_stereo = 0; + workprefs.sound_stereo = 0; else if (actionEvent.getSource() == optStereo) - changed_prefs.sound_stereo = 1; + workprefs.sound_stereo = 1; else if (actionEvent.getSource() == cboFrequency) { switch (cboFrequency->getSelected()) { case 0: - changed_prefs.sound_freq = 11025; + workprefs.sound_freq = 11025; break; case 1: - changed_prefs.sound_freq = 22050; + workprefs.sound_freq = 22050; break; case 2: - changed_prefs.sound_freq = 32000; + workprefs.sound_freq = 32000; break; case 3: - changed_prefs.sound_freq = 44100; + workprefs.sound_freq = 44100; break; default: break; @@ -176,30 +176,30 @@ public: } else if (actionEvent.getSource() == cboInterpolation) - changed_prefs.sound_interpol = cboInterpolation->getSelected(); + workprefs.sound_interpol = cboInterpolation->getSelected(); else if (actionEvent.getSource() == cboFilter) { switch (cboFilter->getSelected()) { case 0: - changed_prefs.sound_filter = FILTER_SOUND_OFF; + workprefs.sound_filter = FILTER_SOUND_OFF; break; case 1: - changed_prefs.sound_filter = FILTER_SOUND_EMUL; - changed_prefs.sound_filter_type = 0; + workprefs.sound_filter = FILTER_SOUND_EMUL; + workprefs.sound_filter_type = 0; break; case 2: - changed_prefs.sound_filter = FILTER_SOUND_EMUL; - changed_prefs.sound_filter_type = 1; + workprefs.sound_filter = FILTER_SOUND_EMUL; + workprefs.sound_filter_type = 1; break; case 3: - changed_prefs.sound_filter = FILTER_SOUND_ON; - changed_prefs.sound_filter_type = 0; + workprefs.sound_filter = FILTER_SOUND_ON; + workprefs.sound_filter_type = 0; break; case 4: - changed_prefs.sound_filter = FILTER_SOUND_ON; - changed_prefs.sound_filter_type = 1; + workprefs.sound_filter = FILTER_SOUND_ON; + workprefs.sound_filter_type = 1; break; default: break; @@ -209,23 +209,23 @@ public: else if (actionEvent.getSource() == sldSeparation) { if (curr_separation_idx != int(sldSeparation->getValue()) - && changed_prefs.sound_stereo > 0) + && workprefs.sound_stereo > 0) { curr_separation_idx = int(sldSeparation->getValue()); - changed_prefs.sound_stereo_separation = 10 - curr_separation_idx; + workprefs.sound_stereo_separation = 10 - curr_separation_idx; } } else if (actionEvent.getSource() == sldStereoDelay) { if (curr_stereodelay_idx != int(sldStereoDelay->getValue()) - && changed_prefs.sound_stereo > 0) + && workprefs.sound_stereo > 0) { curr_stereodelay_idx = int(sldStereoDelay->getValue()); if (curr_stereodelay_idx > 0) - changed_prefs.sound_mixed_stereo_delay = curr_stereodelay_idx; + workprefs.sound_mixed_stereo_delay = curr_stereodelay_idx; else - changed_prefs.sound_mixed_stereo_delay = -1; + workprefs.sound_mixed_stereo_delay = -1; } } @@ -383,7 +383,7 @@ void RefreshPanelSound() { char tmp[10]; - switch (changed_prefs.produce_sound) + switch (workprefs.produce_sound) { case 0: optSoundDisabled->setSelected(true); @@ -401,12 +401,12 @@ void RefreshPanelSound() break; } - if (changed_prefs.sound_stereo == 0) + if (workprefs.sound_stereo == 0) optMono->setSelected(true); - else if (changed_prefs.sound_stereo == 1) + else if (workprefs.sound_stereo == 1) optStereo->setSelected(true); - switch (changed_prefs.sound_freq) + switch (workprefs.sound_freq) { case 11025: cboFrequency->setSelected(0); @@ -422,43 +422,43 @@ void RefreshPanelSound() break; } - cboInterpolation->setSelected(changed_prefs.sound_interpol); + cboInterpolation->setSelected(workprefs.sound_interpol); auto i = 0; - switch (changed_prefs.sound_filter) + switch (workprefs.sound_filter) { case 0: i = 0; break; case 1: - i = changed_prefs.sound_filter_type ? 2 : 1; + i = workprefs.sound_filter_type ? 2 : 1; break; case 2: - i = changed_prefs.sound_filter_type ? 4 : 3; + i = workprefs.sound_filter_type ? 4 : 3; break; default: break; } cboFilter->setSelected(i); - if (changed_prefs.sound_stereo == 0) + if (workprefs.sound_stereo == 0) { curr_separation_idx = 0; curr_stereodelay_idx = 0; } else { - curr_separation_idx = 10 - changed_prefs.sound_stereo_separation; - curr_stereodelay_idx = changed_prefs.sound_mixed_stereo_delay > 0 ? changed_prefs.sound_mixed_stereo_delay : 0; + curr_separation_idx = 10 - workprefs.sound_stereo_separation; + curr_stereodelay_idx = workprefs.sound_mixed_stereo_delay > 0 ? workprefs.sound_mixed_stereo_delay : 0; } sldSeparation->setValue(curr_separation_idx); - sldSeparation->setEnabled(changed_prefs.sound_stereo >= 1); + sldSeparation->setEnabled(workprefs.sound_stereo >= 1); snprintf(tmp, 10, "%d%%", 100 - 10 * curr_separation_idx); lblSeparationInfo->setCaption(tmp); sldStereoDelay->setValue(curr_stereodelay_idx); - sldStereoDelay->setEnabled(changed_prefs.sound_stereo >= 1); + sldStereoDelay->setEnabled(workprefs.sound_stereo >= 1); if (curr_stereodelay_idx <= 0) lblStereoDelayInfo->setCaption("-"); else diff --git a/src/osdep/gui/gui_handling.h b/src/osdep/gui/gui_handling.h index 54375d45..d45f4184 100644 --- a/src/osdep/gui/gui_handling.h +++ b/src/osdep/gui/gui_handling.h @@ -1,6 +1,8 @@ #ifndef GUI_HANDLING_H #define GUI_HANDLING_H +extern struct uae_prefs workprefs; + #define GUI_WIDTH 800 #define GUI_HEIGHT 480 #define DISTANCE_BORDER 15 diff --git a/src/osdep/neon_helper.s b/src/osdep/neon_helper.s index 007ce0c9..5fb3ce24 100644 --- a/src/osdep/neon_helper.s +++ b/src/osdep/neon_helper.s @@ -2,20 +2,39 @@ .arm +.global save_host_fp_regs +.global restore_host_fp_regs .global copy_screen_8bit .global copy_screen_16bit_swap -.global copy_screen_32bit_to_16bit_neon +.global copy_screen_32bit_to_16bit .global ARM_doline_n1 .global NEON_doline_n2 .global NEON_doline_n3 .global NEON_doline_n4 +.global NEON_doline_n5 .global NEON_doline_n6 +.global NEON_doline_n7 .global NEON_doline_n8 .text .align 8 +@---------------------------------------------------------------- +@ save_host_fp_regs +@---------------------------------------------------------------- +save_host_fp_regs: + vstmia r0!, {d7-d15} + bx lr + +@---------------------------------------------------------------- +@ restore_host_fp_regs +@---------------------------------------------------------------- +restore_host_fp_regs: + vldmia r0!, {d7-d15} + bx lr + + @---------------------------------------------------------------- @ copy_screen_8bit @ @@ -87,16 +106,16 @@ copy_screen_16bit_swap: @---------------------------------------------------------------- -@ copy_screen_32bit_to_16bit_neon +@ copy_screen_32bit_to_16bit @ @ r0: uae_u8 *dst - Format (bits): rrrr rggg gggb bbbb @ r1: uae_u8 *src - Format (bytes) in memory rgba @ r2: int bytes @ -@ void copy_screen_32bit_to_16bit_neon(uae_u8 *dst, uae_u8 *src, int bytes); +@ void copy_screen_32bit_to_16bit(uae_u8 *dst, uae_u8 *src, int bytes); @ @---------------------------------------------------------------- -copy_screen_32bit_to_16bit_neon: +copy_screen_32bit_to_16bit: pld [r1, #192] vld4.8 {d18-d21}, [r1]! vld4.8 {d22-d25}, [r1]! @@ -110,7 +129,7 @@ copy_screen_32bit_to_16bit_neon: subs r2, r2, #64 @ processd 4 (bytes per pixel) * 16 (pixel) vst2.8 {d16-d17}, [r0]! vst2.8 {d18-d19}, [r0]! - bne copy_screen_32bit_to_16bit_neon + bne copy_screen_32bit_to_16bit bx lr @@ -479,6 +498,134 @@ NEON_doline_n4_exit: ldmia sp!, {r4, pc} +.align 8 + +@---------------------------------------------------------------- +@ NEON_doline_n5 +@ +@ r0: uae_u32 *pixels +@ r1: int wordcount +@ r2: int lineno +@ +@ void NEON_doline_n5(uae_u32 *pixels, int wordcount, int lineno); +@ +@---------------------------------------------------------------- +NEON_doline_n5: + stmdb sp!, {r4-r5, lr} + + mov r3, #1600 + mul r2, r2, r3 + ldr r3, =line_data + add r2, r3, r2 @ real_bplpt[0] + add r3, r2, #200 + add r4, r3, #200 + add r5, r4, #200 + add lr, r5, #200 + +@ Load masks to registers + vmov.u8 d18, #0x55 + vmov.u8 d19, #0x33 + vmov.u8 d20, #0x0f + +NEON_doline_n5_loop: + @ Load data as early as possible + vldmia lr!, {d5} + vmov.u8 d7, #0 + + @ Load data as early as possible + vldmia r4!, {d0} +@ MERGE (b2, b3, 0x55555555, 1); + vshr.u8 d16, d5, #1 @ tmpb = b >> shift + vshl.u8 d17, d7, #1 @ tmpa = a << shift + @ Load data as early as possible + vldmia r5!, {d2} + vbit.u8 d7, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d5, d17, d18 @ b = b and bit set from tmpa if mask is false + @ Load data as early as possible + vldmia r2!, {d4} +@ MERGE (b4, b5, 0x55555555, 1); + vshr.u8 d16, d0, #1 @ tmpb = b >> shift + vshl.u8 d17, d2, #1 @ tmpa = a << shift + @ Load data as early as possible + vldmia r3!, {d6} + vbit.u8 d2, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d0, d17, d18 @ b = b and bit set from tmpa if mask is false +@ MERGE (b6, b7, 0x55555555, 1); + vshr.u8 d16, d4, #1 @ tmpb = b >> shift + vshl.u8 d17, d6, #1 @ tmpa = a << shift + vbit.u8 d6, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d18 @ b = b and bit set from tmpa if mask is false + +@ MERGE_0(b0, b2, 0x33333333, 2); + vshr.u8 d16, d7, #2 @ tmp = b >> shift + vand.8 d3, d16, d19 @ a = tmp & mask + vand.8 d7, d7, d19 @ b = b & mask +@ MERGE_0(b1, b3, 0x33333333, 2); + vshr.u8 d16, d5, #2 @ tmp = b >> shift + vand.8 d1, d16, d19 @ a = tmp & mask + vand.8 d5, d5, d19 @ b = b & mask +@ MERGE (b4, b6, 0x33333333, 2); + vshr.u8 d16, d6, #2 @ tmpb = b >> shift + vshl.u8 d17, d2, #2 @ tmpa = a << shift + vbit.u8 d2, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d6, d17, d19 @ b = b and bit set from tmpa if mask is false +@ MERGE (b5, b7, 0x33333333, 2); + vshr.u8 d16, d4, #2 @ tmpb = b >> shift + vshl.u8 d17, d0, #2 @ tmpa = a << shift + vbit.u8 d0, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d19 @ b = b and bit set from tmpa if mask is false + +@ MERGE (b0, b4, 0x0f0f0f0f, 4); + vshr.u8 d16, d2, #4 @ tmpb = b >> shift + vshl.u8 d17, d3, #4 @ tmpa = a << shift + vbit.u8 d3, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d2, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b1, b5, 0x0f0f0f0f, 4); + vshr.u8 d16, d0, #4 @ tmpb = b >> shift + vshl.u8 d17, d1, #4 @ tmpa = a << shift + vbit.u8 d1, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d0, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b2, b6, 0x0f0f0f0f, 4); + vshr.u8 d16, d6, #4 @ tmpb = b >> shift + vshl.u8 d17, d7, #4 @ tmpa = a << shift + vbit.u8 d7, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d6, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b3, b7, 0x0f0f0f0f, 4); + vshr.u8 d16, d4, #4 @ tmpb = b >> shift + vshl.u8 d17, d5, #4 @ tmpa = a << shift + vbit.u8 d5, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d20 @ b = b and bit set from tmpa if mask is false + + vzip.8 d3, d7 + vzip.8 d1, d5 + vzip.8 d2, d6 + vzip.8 d0, d4 + + vzip.8 d3, d1 + vzip.8 d2, d0 + vzip.32 d3, d2 + vzip.32 d1, d0 + + vst1.8 {d0, d1, d2, d3}, [r0]! + + cmp r1, #1 @ Exit from here if odd number of words + ldmeqia sp!, {r4-r5, pc} + + subs r1, r1, #2 @ We handle 2 words (64 bit) per loop: wordcount -= 2 + + vzip.8 d7, d5 + vzip.8 d6, d4 + vzip.32 d7, d6 + vzip.32 d5, d4 + + vst1.8 {d4, d5, d6, d7}, [r0]! + + bgt NEON_doline_n5_loop + +NEON_doline_n5_exit: + ldmia sp!, {r4-r5, pc} + + .align 8 @---------------------------------------------------------------- @@ -608,6 +755,153 @@ NEON_doline_n6_exit: ldmia sp!, {r4-r6, pc} +.align 8 + +@---------------------------------------------------------------- +@ NEON_doline_n7 +@ +@ r0: uae_u32 *pixels +@ r1: int wordcount +@ r2: int lineno +@ +@ void NEON_doline_n7(uae_u32 *pixels, int wordcount, int lineno); +@ +@---------------------------------------------------------------- +NEON_doline_n7: + stmdb sp!, {r4-r7, lr} + + mov r3, #1600 + mul r2, r2, r3 + ldr r3, =line_data + add r2, r3, r2 @ real_bplpt[0] + add r3, r2, #200 + add r4, r3, #200 + add r5, r4, #200 + add r6, r5, #200 + add r7, r6, #200 + add lr, r7, #200 + + @ Load data as early as possible + vldmia lr!, {d1} + vmov.u8 d3, #0 + +@ Load masks to registers + vmov.u8 d18, #0x55 + vmov.u8 d19, #0x33 + vmov.u8 d20, #0x0f + +NEON_doline_n7_loop: + @ Load data as early as possible + vldmia r6!, {d5} +@ MERGE (b0, b1, 0x55555555, 1); + vshr.u8 d16, d1, #1 @ tmpb = b >> shift + @ Load data as early as possible + vldmia r7!, {d7} + vbif.u8 d1, d3, d18 @ b = b and bit set from tmpa if mask is false + vbit.u8 d3, d16, d18 @ a = a and bit set from tmpb if mask is true + @ Load data as early as possible + vldmia r4!, {d0} +@ MERGE (b2, b3, 0x55555555, 1); + vshr.u8 d16, d5, #1 @ tmpb = b >> shift + vshl.u8 d17, d7, #1 @ tmpa = a << shift + @ Load data as early as possible + vldmia r5!, {d2} + vbit.u8 d7, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d5, d17, d18 @ b = b and bit set from tmpa if mask is false + @ Load data as early as possible + vldmia r2!, {d4} +@ MERGE (b4, b5, 0x55555555, 1); + vshr.u8 d16, d0, #1 @ tmpb = b >> shift + vshl.u8 d17, d2, #1 @ tmpa = a << shift + @ Load data as early as possible + vldmia r3!, {d6} + vbit.u8 d2, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d0, d17, d18 @ b = b and bit set from tmpa if mask is false +@ MERGE (b6, b7, 0x55555555, 1); + vshr.u8 d16, d4, #1 @ tmpb = b >> shift + vshl.u8 d17, d6, #1 @ tmpa = a << shift + vbit.u8 d6, d16, d18 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d18 @ b = b and bit set from tmpa if mask is false + +@ MERGE (b0, b2, 0x33333333, 2); + vshr.u8 d16, d7, #2 @ tmpb = b >> shift + vshl.u8 d17, d3, #2 @ tmpa = a << shift + vbit.u8 d3, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d7, d17, d19 @ b = b and bit set from tmpa if mask is false +@ MERGE (b1, b3, 0x33333333, 2); + vshr.u8 d16, d5, #2 @ tmpb = b >> shift + vshl.u8 d17, d1, #2 @ tmpa = a << shift + vbit.u8 d1, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d5, d17, d19 @ b = b and bit set from tmpa if mask is false +@ MERGE (b4, b6, 0x33333333, 2); + vshr.u8 d16, d6, #2 @ tmpb = b >> shift + vshl.u8 d17, d2, #2 @ tmpa = a << shift + vbit.u8 d2, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d6, d17, d19 @ b = b and bit set from tmpa if mask is false +@ MERGE (b5, b7, 0x33333333, 2); + vshr.u8 d16, d4, #2 @ tmpb = b >> shift + vshl.u8 d17, d0, #2 @ tmpa = a << shift + vbit.u8 d0, d16, d19 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d19 @ b = b and bit set from tmpa if mask is false + +@ MERGE (b0, b4, 0x0f0f0f0f, 4); + vshr.u8 d16, d2, #4 @ tmpb = b >> shift + vshl.u8 d17, d3, #4 @ tmpa = a << shift + vbit.u8 d3, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d2, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b1, b5, 0x0f0f0f0f, 4); + vshr.u8 d16, d0, #4 @ tmpb = b >> shift + vshl.u8 d17, d1, #4 @ tmpa = a << shift + vbit.u8 d1, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d0, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b2, b6, 0x0f0f0f0f, 4); + vshr.u8 d16, d6, #4 @ tmpb = b >> shift + vshl.u8 d17, d7, #4 @ tmpa = a << shift + vbit.u8 d7, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d6, d17, d20 @ b = b and bit set from tmpa if mask is false +@ MERGE (b3, b7, 0x0f0f0f0f, 4); + vshr.u8 d16, d4, #4 @ tmpb = b >> shift + vshl.u8 d17, d5, #4 @ tmpa = a << shift + vbit.u8 d5, d16, d20 @ a = a and bit set from tmpb if mask is true + vbif.u8 d4, d17, d20 @ b = b and bit set from tmpa if mask is false + + vzip.8 d3, d7 + vzip.8 d1, d5 + vzip.8 d2, d6 + vzip.8 d0, d4 + + vzip.8 d3, d1 + vzip.8 d2, d0 + vzip.32 d3, d2 + vzip.32 d1, d0 + + vst1.8 {d0, d1, d2, d3}, [r0]! + + cmp r1, #1 @ Exit from here if odd number of words + ldmeqia sp!, {r4-r7, pc} + + subs r1, r1, #2 @ We handle 2 words (64 bit) per loop: wordcount -= 2 + + @ Load data as early as possible + vldmiagt lr!, {d1} + + vzip.8 d7, d5 + vzip.8 d6, d4 + + @ Load data as early as possible + vmov.u8 d3, #0 + + vzip.32 d7, d6 + vzip.32 d5, d4 + + vst1.8 {d4, d5, d6, d7}, [r0]! + + bgt NEON_doline_n7_loop + +NEON_doline_n7_exit: + ldmia sp!, {r4-r7, pc} + + .align 8 @---------------------------------------------------------------- diff --git a/src/osdep/picasso96.cpp b/src/osdep/picasso96.cpp index 2a7e6a19..e4991d1f 100644 --- a/src/osdep/picasso96.cpp +++ b/src/osdep/picasso96.cpp @@ -30,21 +30,8 @@ * programs started from a Picasso workbench. */ -/* - * Note: This is the Pandora specific version of Picasso96: - * - only 16 bit color mode is available (R5G6B5) in hardware - * - we simulate R8G8B8A8 on Amiga side and use Neon-code to convert to R5G6B5 - * - we have no hardware sprite for mouse pointer - * I removed some code which handled unsupported modes and formats to make code - * easier to read. - */ -#include -#include -#include -#include - +#include "sysconfig.h" #include "sysdeps.h" -#include "gfxboard.h" #if defined(PICASSO96) @@ -53,16 +40,19 @@ #include "config.h" #include "options.h" #include "threaddep/thread.h" -#include "include/memory.h" +#include "memory.h" #include "custom.h" #include "newcpu.h" #include "xwin.h" #include "savestate.h" #include "autoconf.h" #include "traps.h" -#include "native2amiga.h" +#ifdef RETROPLATFORM +#include "rp.h" +#endif #include "picasso96.h" -#include +#include "gfxboard.h" +#include "devices.h" #define NOBLITTER 0 #define NOBLITTER_BLIT 0 @@ -70,18 +60,11 @@ static const int defaultHz = 60; -//TODO use the amigadisplay struct eventually -#ifdef AMIBERRY -bool pending_render; -#endif - static int picasso96_BT = BT_uaegfx; static int picasso96_GCT = GCT_Unknown; static int picasso96_PCT = PCT_Unknown; -int p96refresh_active; -bool have_done_picasso = true; /* For the JIT compiler */ -static int p96syncrate; +static bool picasso_flushpixels(uae_u8 *src, int offset); static smp_comm_pipe* render_pipe; static volatile int render_thread_state; @@ -91,7 +74,6 @@ static volatile int render_thread_state; #define PICASSO_STATE_SETGC 4 #define PICASSO_STATE_SETDAC 8 #define PICASSO_STATE_SETSWITCH 16 -static uae_atomic picasso_state_change; #ifdef PICASSO96 @@ -99,7 +81,7 @@ static uae_u8 all_ones_bitmap, all_zeros_bitmap; /* yuk */ struct picasso96_state_struct picasso96_state; struct picasso_vidbuf_description picasso_vidinfo; -static struct PicassoResolution* newmodes = nullptr; +static struct PicassoResolution *newmodes; /* These are the maximum resolutions... They are filled in by GetSupportedResolutions() have to fill this in, otherwise problems occur on the Amiga side P96 s/w which expects @@ -115,7 +97,6 @@ uae_u32 p96rc[256], p96gc[256], p96bc[256]; static uaecptr boardinfo, ABI_interrupt; static int interrupt_enabled; -double p96vblank; static int uaegfx_old, uaegfx_active; static uae_u32 reserved_gfxmem; @@ -145,7 +126,7 @@ typedef enum { BLIT_SWAP = 30 } BLIT_OPCODE; -static void init_picasso_screen(void); +static void init_picasso_screen(); static uae_u32 p2ctab[256][2]; static int set_gc_called = 0, init_picasso_screen_called = 0; //fastscreen @@ -160,18 +141,10 @@ STATIC_INLINE void endianswap(uae_u32* vp, int bpp) switch (bpp) { case 2: -#ifdef AMIBERRY *vp = bswap_16(v); -#else - *vp = (((v >> 8) & 0x00ff) | (v << 8)) & 0xffff; -#endif break; case 4: -#ifdef AMIBERRY *vp = bswap_32(v); -#else - *vp = ((v >> 24) & 0x000000ff) | ((v >> 8) & 0x0000ff00) | ((v << 8) & 0x00ff0000) | ((v << 24) & 0xff000000); -#endif break; } } @@ -181,6 +154,7 @@ static uae_u8 GetBytesPerPixel(uae_u32 RGBfmt) switch (RGBfmt) { case RGBFB_CLUT: + case RGBFB_Y4U1V1: return 1; case RGBFB_A8R8G8B8: @@ -199,6 +173,7 @@ static uae_u8 GetBytesPerPixel(uae_u32 RGBfmt) case RGBFB_R5G5B5PC: case RGBFB_B5G6R5PC: case RGBFB_B5G5R5PC: + case RGBFB_Y4U2V2: return 2; } return 0; @@ -264,8 +239,7 @@ static int CopyRenderInfoStructureA2U(TrapContext* ctx, uaecptr amigamemptr, str static int CopyPatternStructureA2U(TrapContext* ctx, uaecptr amigamemptr, struct Pattern* pattern) { - if (trap_valid_address(ctx, amigamemptr, PSSO_Pattern_sizeof)) - { + if (trap_valid_address(ctx, amigamemptr, PSSO_Pattern_sizeof)) { struct trapmd md[] = { { TRAPCMD_GET_LONG, { amigamemptr + PSSO_Pattern_Memory } }, @@ -324,7 +298,6 @@ static int CopyBitMapStructureA2U(TrapContext* ctx, uaecptr amigamemptr, struct for (i = 0; i < bm->Depth; i++) { uaecptr plane = md[4 + i].params[0]; - bm->APlanes[i] = plane; switch (plane) { case 0: bm->Planes[i] = &all_zeros_bitmap; @@ -371,31 +344,6 @@ static int CopyTemplateStructureA2U(TrapContext* ctx, uaecptr amigamemptr, struc return 0; } -static int CopyLineStructureA2U(TrapContext *ctx, uaecptr amigamemptr, struct Line *line) -{ - if (trap_valid_address(ctx, amigamemptr, sizeof(struct Line))) { - line->X = trap_get_word(ctx, amigamemptr + PSSO_Line_X); - line->Y = trap_get_word(ctx, amigamemptr + PSSO_Line_Y); - line->Length = trap_get_word(ctx, amigamemptr + PSSO_Line_Length); - line->dX = trap_get_word(ctx, amigamemptr + PSSO_Line_dX); - line->dY = trap_get_word(ctx, amigamemptr + PSSO_Line_dY); - line->lDelta = trap_get_word(ctx, amigamemptr + PSSO_Line_lDelta); - line->sDelta = trap_get_word(ctx, amigamemptr + PSSO_Line_sDelta); - line->twoSDminusLD = trap_get_word(ctx, amigamemptr + PSSO_Line_twoSDminusLD); - line->LinePtrn = trap_get_word(ctx, amigamemptr + PSSO_Line_LinePtrn); - line->PatternShift = trap_get_word(ctx, amigamemptr + PSSO_Line_PatternShift); - line->FgPen = trap_get_long(ctx, amigamemptr + PSSO_Line_FgPen); - line->BgPen = trap_get_long(ctx, amigamemptr + PSSO_Line_BgPen); - line->Horizontal = trap_get_word(ctx, amigamemptr + PSSO_Line_Horizontal); - line->DrawMode = trap_get_byte(ctx, amigamemptr + PSSO_Line_DrawMode); - line->Xorigin = trap_get_word(ctx, amigamemptr + PSSO_Line_Xorigin); - line->Yorigin = trap_get_word(ctx, amigamemptr + PSSO_Line_Yorigin); - return 1; - } - write_log (_T("ERROR - Invalid Line structure...\n")); - return 0; -} - /* list is Amiga address of list, in correct endian format for UAE * node is Amiga address of node, in correct endian format for UAE */ static void AmigaListAddTail(TrapContext *ctx, uaecptr l, uaecptr n) @@ -425,43 +373,91 @@ static void do_fillrect_frame_buffer(struct RenderInfo *ri, int X, int Y, int Wi } break; case 2: + { Pen |= Pen << 16; for (int lines = 0; lines < Height; lines++, dst += bpr) { - uae_u16* dst16 = (uae_u16 *)dst; - int tmpwidth = Width; - if ((uintptr_t)dst16 & 3) { - *dst16++ = (uae_u16)Pen; - tmpwidth--; - } - uae_u32* p = (uae_u32*)dst16; - for (cols = 0; cols < tmpwidth >> 1; cols++) + uae_u32 *p = (uae_u32*)dst; + for (cols = 0; cols < (Width & ~15); cols += 16) { *p++ = Pen; - if (tmpwidth & 1) - ((uae_u16*)p)[0] = (uae_u16)Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + } + while (cols < (Width & ~1)) { + *p++ = Pen; + cols += 2; + } + if (Width & 1) { + ((uae_u16*)p)[0] = Pen; + } + } } break; case 3: + { + uae_u16 Pen1 = Pen & 0xffff; + uae_u16 Pen2 = (Pen << 8) | ((Pen >> 16) & 0xff); + uae_u16 Pen3 = Pen >> 8; + bool same = (Pen & 0xff) == ((Pen >> 8) & 0xff) && (Pen & 0xff) == ((Pen >> 16) & 0xff); for (int lines = 0; lines < Height; lines++, dst += bpr) { - uae_u8* p = (uae_u8*)dst; - for (cols = 0; cols < Width; cols++) { - *p++ = Pen >> 0; - *p++ = Pen >> 8; - *p++ = Pen >> 16; + uae_u16 *p = (uae_u16*)dst; + if (same) { + memset(p, Pen & 0xff, Width * 3); + } else { + for (cols = 0; cols < (Width & ~7); cols += 8) { + *p++ = Pen1; + *p++ = Pen2; + *p++ = Pen3; + *p++ = Pen1; + *p++ = Pen2; + *p++ = Pen3; + *p++ = Pen1; + *p++ = Pen2; + *p++ = Pen3; + *p++ = Pen1; + *p++ = Pen2; + *p++ = Pen3; + } + uae_u8 *p8 = (uae_u8*)p; + while (cols < Width) { + *p8++ = Pen >> 0; + *p8++ = Pen >> 8; + *p8++ = Pen >> 16; + cols++; + } + } } } break; case 4: + { for (int lines = 0; lines < Height; lines++, dst += bpr) { uae_u32* p = (uae_u32*)dst; - for (cols = 0; cols < Width; cols++) + for (cols = 0; cols < (Width & ~7); cols += 8) { + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; + *p++ = Pen; *p++ = Pen; } + while (cols < Width) { + *p++ = Pen; + cols++; + } + } + } break; } } static int p96_framecnt; -int p96skipmode = -1; static int doskip (void) { if (p96_framecnt > currprefs.gfx_framerate) @@ -469,7 +465,7 @@ static int doskip (void) return p96_framecnt > 0; } -void picasso_trigger_vblank(void) +static void picasso_trigger_vblank (void) { TrapContext* ctx = nullptr; if (!ABI_interrupt || !uaegfx_base || !interrupt_enabled) @@ -480,50 +476,23 @@ void picasso_trigger_vblank(void) static bool is_uaegfx_active(void) { - if (currprefs.rtgboards[0].rtgmem_type >= GFXBOARD_HARDWARE || !currprefs.rtgboards[0].rtgmem_size) + if (!currprefs.rtgboards[0].rtgmem_size) return false; return true; } -static void rtg_render(void) +static bool rtg_render (void) { + bool flushed = false; bool uaegfx_active = is_uaegfx_active(); - int uaegfx_index = 0; - if (doskip()) - { - return; - } - //bool full = picasso_vidinfo.full_refresh > 0; - if (uaegfx_active) - { - if (!currprefs.rtg_multithread) - { - picasso_flushpixels(gfxmem_banks[0]->start + regs.natmem_offset, - picasso96_state.XYOffset - gfxmem_banks[0]->start); - } - } - else - { - if (picasso_vidinfo.full_refresh < 0) - picasso_vidinfo.full_refresh = 0; - if (picasso_vidinfo.full_refresh > 0) - picasso_vidinfo.full_refresh--; - } - //gfxboard_vsync_handler(full, true); - if (currprefs.rtg_multithread && uaegfx_active) - { - if (pending_render) - { - pending_render = false; - gfx_unlock_picasso(true); - } - write_comm_pipe_int(render_pipe, uaegfx_index, 0); - } -} + struct picasso96_state_struct* state = &picasso96_state; -static void rtg_clear(void) -{ - picasso_vidinfo.rtg_clear_flag = 4; + if (uaegfx_active) { + if (!doskip ()) + flushed = picasso_flushpixels (gfxmem_banks[0]->start + regs.natmem_offset, state->XYOffset - gfxmem_banks[0]->start); + } + + return flushed; } enum @@ -542,6 +511,8 @@ enum RGBFB_B5G6R5PC_32, RGBFB_B5G5R5PC_32, RGBFB_CLUT_RGBFB_32, + RGBFB_Y4U2V2_32, + RGBFB_Y4U1V1_32, /* DEST = RGBFB_R5G6B5PC,16 */ RGBFB_A8R8G8B8_16, @@ -557,12 +528,14 @@ enum RGBFB_B5G6R5PC_16, RGBFB_B5G5R5PC_16, RGBFB_CLUT_RGBFB_16, + RGBFB_Y4U2V2_16, + RGBFB_Y4U1V1_16, /* DEST = RGBFB_CLUT,8 */ RGBFB_CLUT_8 }; -static int getconvert(int rgbformat, int pixbytes) +static int getconvert (int rgbformat, int pixbytes) { int v = 0; int d = pixbytes; @@ -652,35 +625,43 @@ static int getconvert(int rgbformat, int pixbytes) else if (d == 4) v = RGBFB_R8G8B8A8_32; break; + + case RGBFB_Y4U2V2: + if (d == 4) + v = RGBFB_Y4U2V2_32; + else + v = RGBFB_Y4U2V2_16; + break; + case RGBFB_Y4U1V1: + if (d == 4) + v = RGBFB_Y4U1V1_32; + else + v = RGBFB_Y4U1V1_16; + break; + } return v; } -static void setconvert(void) +static void setconvert() { - picasso_vidinfo.picasso_convert = getconvert(picasso96_state.RGBFormat, picasso_vidinfo.pixbytes); - picasso_vidinfo.host_mode = GetSurfacePixelFormat(); + struct picasso_vidbuf_description* vidinfo = &picasso_vidinfo; + struct picasso96_state_struct* state = &picasso96_state; + + vidinfo->picasso_convert = getconvert (state->RGBFormat, picasso_vidinfo.pixbytes); + vidinfo->host_mode = GetSurfacePixelFormat(); if (picasso_vidinfo.pixbytes == 4) alloc_colors_rgb(8, 8, 8, 16, 8, 0, 0, 0, 0, 0, p96rc, p96gc, p96bc); else alloc_colors_rgb(5, 6, 5, 11, 5, 0, 0, 0, 0, 0, p96rc, p96gc, p96bc); - gfx_set_picasso_colors(picasso96_state.RGBFormat); - picasso_palette(picasso96_state.CLUT); - if (picasso_vidinfo.host_mode != picasso_vidinfo.ohost_mode || picasso96_state.RGBFormat != picasso_vidinfo. - orgbformat) - { + gfx_set_picasso_colors(state->RGBFormat); + picasso_palette(state->CLUT, vidinfo->clut); + if (vidinfo->host_mode != vidinfo->ohost_mode || state->RGBFormat != vidinfo->orgbformat) { write_log(_T("RTG conversion: Depth=%d HostRGBF=%d P96RGBF=%d Mode=%d\n"), - picasso_vidinfo.pixbytes, picasso_vidinfo.host_mode, picasso96_state.RGBFormat, picasso_vidinfo. - picasso_convert); - picasso_vidinfo.ohost_mode = picasso_vidinfo.host_mode; - picasso_vidinfo.orgbformat = picasso96_state.RGBFormat; + picasso_vidinfo.pixbytes, vidinfo->host_mode, state->RGBFormat, vidinfo->picasso_convert); + vidinfo->ohost_mode = vidinfo->host_mode; + vidinfo->orgbformat = state->RGBFormat; } - picasso_vidinfo.full_refresh = 1; -} - -bool picasso_is_active(void) -{ - return picasso_vidinfo.picasso_active; } /* Clear our screen, since we've got a new Picasso screen-mode, and refresh with the proper contents @@ -689,25 +670,24 @@ bool picasso_is_active(void) * 2. Picasso-->Picasso transition, via SetPanning(). * 3. whenever the graphics code notifies us that the screen contents have been lost. */ -void picasso_refresh(void) +void picasso_refresh() { struct RenderInfo ri; + struct amigadisplay* ad = &adisplays; + struct picasso96_state_struct* state = &picasso96_state; - if (!picasso_on) + if (!ad->picasso_on) return; - picasso_vidinfo.full_refresh = 1; setconvert(); - rtg_clear(); /* Make sure that the first time we show a Picasso video mode, we don't blit any crap. * We can do this by checking if we have an Address yet. */ - if (picasso96_state.Address) - { + if (state->Address) { /* blit the stuff from our static frame-buffer to the gfx-card */ - ri.Memory = gfxmem_bank.baseaddr + (picasso96_state.Address - gfxmem_bank.start); - ri.BytesPerRow = picasso96_state.BytesPerRow; - ri.RGBFormat = (RGBFTYPE)picasso96_state.RGBFormat; + ri.Memory = gfxmem_bank.baseaddr + (state->Address - gfxmem_bank.start); + ri.BytesPerRow = state->BytesPerRow; + ri.RGBFormat = state->RGBFormat; } else { @@ -715,146 +695,61 @@ void picasso_refresh(void) } } -static void picasso_handle_vsync2() +bool picasso_rendered = false; +void picasso_handle_vsync(void) { - //static int vsynccnt; - int thisisvsync = 1; - //int vsync = isvsync_rtg(); - //int mult; - //bool rendered = false; - bool uaegfx = currprefs.rtgboards[0].rtgmem_type < GFXBOARD_HARDWARE; - //bool uaegfx_active = is_uaegfx_active(); + struct amigadisplay* ad = &adisplays; + struct picasso_vidbuf_description* vidinfo = &picasso_vidinfo; - int state = picasso_state_change; - if (state & PICASSO_STATE_SETDAC) - { - atomic_and(&picasso_state_change, ~PICASSO_STATE_SETDAC); - rtg_clear(); + if (currprefs.rtgboards[0].rtgmem_size == 0) + return; + + if (!ad->picasso_on) { + picasso_trigger_vblank (); + return; } - if (state & PICASSO_STATE_SETGC) - { - atomic_and(&picasso_state_change, ~PICASSO_STATE_SETGC); + + int state = vidinfo->picasso_state_change; + if (state & PICASSO_STATE_SETDAC) { + atomic_and(&vidinfo->picasso_state_change, ~PICASSO_STATE_SETDAC); + } + if (state & PICASSO_STATE_SETGC) { + atomic_and(&vidinfo->picasso_state_change, ~PICASSO_STATE_SETGC); set_gc_called = 1; - picasso_vidinfo.picasso_changed = true; + vidinfo->picasso_changed = true; init_picasso_screen(); - init_hz_p96(); } - if (state & PICASSO_STATE_SETSWITCH) - { - atomic_and(&picasso_state_change, ~PICASSO_STATE_SETSWITCH); + if (state & PICASSO_STATE_SETSWITCH) { + atomic_and(&vidinfo->picasso_state_change, ~PICASSO_STATE_SETSWITCH); /* Do not switch immediately. Tell the custom chip emulation about the * desired state, and wait for custom.c to call picasso_enablescreen * whenever it is ready to change the screen state. */ - if (picasso_on == picasso_requested_on && picasso_requested_on && picasso_vidinfo.picasso_changed) - { - picasso_requested_forced_on = true; + if (ad->picasso_on == ad->picasso_requested_on && ad->picasso_requested_on && vidinfo->picasso_changed) { + ad->picasso_requested_forced_on = true; } - picasso_vidinfo.picasso_changed = false; - picasso_vidinfo.picasso_active = picasso_requested_on; + vidinfo->picasso_changed = false; + vidinfo->picasso_active = ad->picasso_requested_on; } - if (state & PICASSO_STATE_SETPANNING) - { - atomic_and(&picasso_state_change, ~PICASSO_STATE_SETPANNING); - picasso_vidinfo.full_refresh = 1; - picasso_vidinfo.set_panning_called = 1; + if (state & PICASSO_STATE_SETPANNING) { + atomic_and(&vidinfo->picasso_state_change, ~PICASSO_STATE_SETPANNING); + vidinfo->set_panning_called = 1; init_picasso_screen(); - picasso_vidinfo.set_panning_called = 0; + vidinfo->set_panning_called = 0; } - if (state & PICASSO_STATE_SETDISPLAY) - { - atomic_and(&picasso_vidinfo.picasso_state_change, ~PICASSO_STATE_SETDISPLAY); + if (state & PICASSO_STATE_SETDISPLAY) { + atomic_and(&vidinfo->picasso_state_change, ~PICASSO_STATE_SETDISPLAY); // do nothing } p96_framecnt++; - if (!uaegfx && !picasso_on) - { - rtg_render(); - return; - } - - if (!picasso_on) + if (!ad->picasso_on) return; - if (thisisvsync) - { - rtg_render(); - } + picasso_rendered = rtg_render(); - if (uaegfx) - { - if (thisisvsync) - picasso_trigger_vblank(); - } -} - -static int p96hsync; - -void picasso_handle_vsync(void) -{ - bool uaegfx = currprefs.rtgboards[0].rtgmem_type < GFXBOARD_HARDWARE; - //bool uaegfx_active = is_uaegfx_active(); - - if (currprefs.rtgboards[0].rtgmem_size == 0) - return; - - if (!picasso_on && uaegfx) - { - picasso_trigger_vblank(); - return; - } - - //int vsync = isvsync_rtg(); - //if (vsync < 0) { - p96hsync = 0; - picasso_handle_vsync2(); - //} -} - -void picasso_handle_hsync(void) -{ - bool uaegfx = currprefs.rtgboards[0].rtgmem_type < GFXBOARD_HARDWARE; - //bool uaegfx_active = is_uaegfx_active(); - - if (currprefs.rtgboards[0].rtgmem_size == 0) - return; - - if (pending_render) - { - pending_render = false; - gfx_unlock_picasso(true); - } - - //int vsync = isvsync_rtg(); - //if (vsync < 0) { - //p96hsync++; - if (p96hsync >= p96syncrate * 3) - { - p96hsync = 0; - // kickstart vblank vsync_busywait stuff - picasso_handle_vsync(); - } - //return; - //} - - p96hsync++; - if (p96hsync >= p96syncrate) - { - if (picasso_on) - { - if (uaegfx) - { picasso_trigger_vblank(); } - } - else - { - picasso_handle_vsync2(); - } - p96hsync = 0; - } -} #define BLT_SIZE 4 #define BLT_MULT 1 @@ -1229,8 +1124,6 @@ d7: RGBFTYPE RGBFormat */ static uae_u32 REGPARAM2 picasso_SetSpritePosition(TrapContext* ctx) { - uaecptr bi = trap_get_areg(ctx, 0); - boardinfo = bi; return 0; } @@ -1249,9 +1142,7 @@ This function changes one of the possible three colors of the hardware sprite. */ static uae_u32 REGPARAM2 picasso_SetSpriteColor(TrapContext* ctx) { - uaecptr bi = trap_get_areg(ctx, 0); - boardinfo = bi; - return 0; + return 0; } /* @@ -1279,11 +1170,9 @@ planes for one image line respectively. You have to double each pixel horizontal used in this case already assume a zoomed sprite, only the sprite data is not zoomed yet. You will have to compensate for this when accounting for hotspot offsets and sprite dimensions. */ -static uae_u32 REGPARAM2 picasso_SetSpriteImage(TrapContext* ctx) +static uae_u32 REGPARAM2 picasso_SetSpriteImage(TrapContext *ctx) { - uaecptr bi = trap_get_areg(ctx, 0); - boardinfo = bi; - return 0; + return 0; } /* @@ -1295,13 +1184,13 @@ d7: RGBFTYPE RGBFormat This function activates or deactivates the hardware sprite. */ -static uae_u32 REGPARAM2 picasso_SetSprite(TrapContext* ctx) +static uae_u32 REGPARAM2 picasso_SetSprite (TrapContext *ctx) { - return 0; + return 0; } /* -* BOOL FindCard(struct BoardInfo *bi); and +* BOOL FindCard(struct BoardInfo *bi); and * * FindCard is called in the first stage of the board initialisation and * configuration and is used to look if there is a free and unconfigured @@ -1315,37 +1204,31 @@ static uae_u32 REGPARAM2 picasso_SetSprite(TrapContext* ctx) * BoardInfo struct supplied by the caller, the rtg.library, for example * the MemoryBase, MemorySize and RegisterBase fields. */ -static void picasso96_alloc2(TrapContext* ctx); - -static uae_u32 REGPARAM2 picasso_FindCard(TrapContext* ctx) +static void picasso96_alloc2 (TrapContext *ctx); +static uae_u32 REGPARAM2 picasso_FindCard (TrapContext *ctx) { uaecptr AmigaBoardInfo = trap_get_areg(ctx, 0); + struct picasso96_state_struct *state = &picasso96_state; /* NOTES: See BoardInfo struct definition in Picasso96 dev info */ if (!uaegfx_active || !gfxmem_bank.start) return 0; - if (uaegfx_base) - { + if (uaegfx_base) { trap_put_long(ctx, uaegfx_base + CARD_BOARDINFO, AmigaBoardInfo); - } - else if (uaegfx_old) - { - picasso96_alloc2(ctx); + } else if (uaegfx_old) { + picasso96_alloc2 (ctx); } boardinfo = AmigaBoardInfo; - - if (gfxmem_bank.allocated_size && !picasso96_state.CardFound) - { + if (gfxmem_bank.allocated_size && !state->CardFound) { /* Fill in MemoryBase, MemorySize */ trap_put_long(ctx, AmigaBoardInfo + PSSO_BoardInfo_MemoryBase, gfxmem_bank.start); trap_put_long(ctx, AmigaBoardInfo + PSSO_BoardInfo_MemorySize, gfxmem_bank.allocated_size - reserved_gfxmem); - picasso96_state.CardFound = 1; /* mark our "card" as being found */ + state->CardFound = 1; /* mark our "card" as being found */ return -1; - } - return 0; + } else + return 0; } -static void FillBoardInfo(TrapContext* ctx, uaecptr amigamemptr, struct LibResolution* res, int width, int height, - int depth) +static void FillBoardInfo(TrapContext *ctx, uaecptr amigamemptr, struct LibResolution *res, int width, int height, int depth) { switch (depth) { @@ -1385,17 +1268,13 @@ static void FillBoardInfo(TrapContext* ctx, uaecptr amigamemptr, struct LibResol trap_put_byte(ctx, amigamemptr + PSSO_ModeInfo_second_union, 14); trap_put_long(ctx, amigamemptr + PSSO_ModeInfo_PixelClock, - width * height * (currprefs.gfx_apmode[1].gfx_refreshrate - ? abs(currprefs.gfx_apmode[1].gfx_refreshrate) - : defaultHz)); + width * height * defaultHz); } -struct modeids -{ +struct modeids { int width, height; int id; }; - static struct modeids mi[] = { /* "original" modes */ @@ -1407,10 +1286,10 @@ static struct modeids mi[] = 800, 600, 4, 1024, 768, 5, 1152, 864, 6, - 1280, 1024, 7, - 1600, 1280, 8, + 1280,1024, 7, + 1600,1280, 8, 320, 256, 9, - 640, 512, 10, + 640, 512,10, /* new modes */ @@ -1435,53 +1314,49 @@ static struct modeids mi[] = 1366, 768, 147, 1440, 900, 148, 1440, 960, 149, - 1600, 1200, 150, - 1680, 1050, 151, - 1920, 1080, 152, - 1920, 1200, 153, - 2048, 1152, 154, - 2048, 1536, 155, - 2560, 1600, 156, - 2560, 2048, 157, + 1600,1200, 150, + 1680,1050, 151, + 1920,1080, 152, + 1920,1200, 153, + 2048,1152, 154, + 2048,1536, 155, + 2560,1600, 156, + 2560,2048, 157, 400, 300, 158, 512, 384, 159, 640, 432, 160, 1360, 768, 161, - 1360, 1024, 162, - 1400, 1050, 163, - 1792, 1344, 164, - 1800, 1440, 165, - 1856, 1392, 166, - 1920, 1440, 167, + 1360,1024, 162, + 1400,1050, 163, + 1792,1344, 164, + 1800,1440, 165, + 1856,1392, 166, + 1920,1440, 167, 480, 360, 168, 640, 350, 169, 1600, 900, 170, 960, 600, 171, 1088, 612, 172, 1152, 648, 173, - 1776, 1000, 174, - 2560, 1440, 175, - -1, -1, 0 + 1776,1000, 174, + 2560,1440, 175, + -1,-1,0 }; -static int AssignModeID(int w, int h, int* unkcnt) +static int AssignModeID (int w, int h, int *unkcnt) { int i; - for (i = 0; mi[i].width > 0; i++) - { + for (i = 0; mi[i].width > 0; i++) { if (w == mi[i].width && h == mi[i].height) return 0x50001000 | (mi[i].id * 0x10000); } (*unkcnt)++; - write_log(_T("P96: Non-unique mode %dx%d"), w, h); - if (256 - (*unkcnt) == mi[i - 1].id + 1) - { + write_log (_T("P96: Non-unique mode %dx%d"), w, h); + if (i > 0 && 256 - (*unkcnt) == mi[i - 1].id + 1) { (*unkcnt) = 256 - 127; write_log(_T(" (Skipped reserved)")); - } - else if (256 - (*unkcnt) == 11) - { + } else if (256 - (*unkcnt) == 11) { (*unkcnt) = 511; write_log(_T(" (Using extra)")); } @@ -1492,40 +1367,38 @@ static int AssignModeID(int w, int h, int* unkcnt) static uaecptr picasso96_amem, picasso96_amemend; -static void CopyLibResolutionStructureU2A(TrapContext* ctx, struct LibResolution* libres, uaecptr amigamemptr) +static void CopyLibResolutionStructureU2A(TrapContext *ctx, struct LibResolution *libres, uaecptr amigamemptr) { + int i; + trap_set_bytes(ctx, amigamemptr, 0, PSSO_LibResolution_sizeof); - for (unsigned int i = 0; i < strlen(libres->P96ID); i++) + for (i = 0; i < strlen (libres->P96ID); i++) trap_put_byte(ctx, amigamemptr + PSSO_LibResolution_P96ID + i, libres->P96ID[i]); trap_put_long(ctx, amigamemptr + PSSO_LibResolution_DisplayID, libres->DisplayID); trap_put_word(ctx, amigamemptr + PSSO_LibResolution_Width, libres->Width); trap_put_word(ctx, amigamemptr + PSSO_LibResolution_Height, libres->Height); trap_put_word(ctx, amigamemptr + PSSO_LibResolution_Flags, libres->Flags); - for (int i = 0; i < MAXMODES; i++) + for (i = 0; i < MAXMODES; i++) trap_put_long(ctx, amigamemptr + PSSO_LibResolution_Modes + i * 4, libres->Modes[i]); trap_put_long(ctx, amigamemptr + 10, amigamemptr + PSSO_LibResolution_P96ID); trap_put_long(ctx, amigamemptr + PSSO_LibResolution_BoardInfo, libres->BoardInfo); } -static void init_alloc(TrapContext* ctx, int size) +static void init_alloc (TrapContext *ctx, int size) { picasso96_amem = picasso96_amemend = 0; - if (uaegfx_base) - { + if (uaegfx_base) { int size = trap_get_long(ctx, uaegfx_base + CARD_RESLISTSIZE); picasso96_amem = trap_get_long(ctx, uaegfx_base + CARD_RESLIST); - } - else if (uaegfx_active) - { + } else if (uaegfx_active) { reserved_gfxmem = size; picasso96_amem = gfxmem_bank.start + gfxmem_bank.allocated_size - size; } picasso96_amemend = picasso96_amem + size; - write_log(_T("P96 RESINFO: %08X-%08X (%d,%d)\n"), picasso96_amem, picasso96_amemend, size / PSSO_ModeInfo_sizeof, - size); + write_log (_T("P96 RESINFO: %08X-%08X (%d,%d)\n"), picasso96_amem, picasso96_amemend, size / PSSO_ModeInfo_sizeof, size); } -static int p96depth(int depth) +static int p96depth (int depth) { uae_u32 f = currprefs.picasso96_modeflags; int ok = 0; @@ -1543,10 +1416,10 @@ static int p96depth(int depth) return ok; } -static int resolution_compare(const void* a, const void* b) +static int resolution_compare (const void *a, const void *b) { - struct PicassoResolution* ma = (struct PicassoResolution *)a; - struct PicassoResolution* mb = (struct PicassoResolution *)b; + struct PicassoResolution *ma = (struct PicassoResolution *)a; + struct PicassoResolution *mb = (struct PicassoResolution *)b; if (ma->res.width < mb->res.width) return -1; if (ma->res.width > mb->res.width) @@ -1558,43 +1431,40 @@ static int resolution_compare(const void* a, const void* b) return ma->depth - mb->depth; } -static int missmodes[] = {640, 400, 640, 480, 800, 480, -1}; +static int missmodes[] = { 320, 200, 320, 240, 320, 256, 640, 400, 640, 480, 640, 512, 800, 600, 1024, 768, 1280, 1024, -1 }; -static uaecptr uaegfx_card_install(TrapContext* ctx, uae_u32 size); +static uaecptr uaegfx_card_install (TrapContext *ctx, uae_u32 size); -static void picasso96_alloc2(TrapContext* ctx) +static void picasso96_alloc2 (TrapContext *ctx) { int i, j, size, cnt; int misscnt, depths; - xfree(newmodes); - newmodes = nullptr; + xfree (newmodes); + newmodes = NULL; picasso96_amem = picasso96_amemend = 0; if (gfxmem_bank.allocated_size == 0) return; misscnt = 0; - newmodes = xmalloc(struct PicassoResolution, MAX_PICASSO_MODES); + newmodes = xmalloc (struct PicassoResolution, MAX_PICASSO_MODES); size = 0; depths = 0; - if (p96depth(8)) + if (p96depth (8)) depths++; - if (p96depth(15)) + if (p96depth (15)) depths++; - if (p96depth(16)) + if (p96depth (16)) depths++; - if (p96depth(24)) + if (p96depth (24)) depths++; - if (p96depth(32)) + if (p96depth (32)) depths++; i = 0; - while (DisplayModes[i].depth >= 0) - { - for (j = 0; missmodes[j * 2] >= 0; j++) - { - if (DisplayModes[i].res.width == missmodes[j * 2 + 0] && DisplayModes[i].res.height == missmodes[j * 2 + 1]) - { + while (DisplayModes[i].depth >= 0) { + for (j = 0; missmodes[j * 2] >= 0; j++) { + if (DisplayModes[i].res.width == missmodes[j * 2 + 0] && DisplayModes[i].res.height == missmodes[j * 2 + 1]) { missmodes[j * 2 + 0] = 0; missmodes[j * 2 + 1] = 0; } @@ -1604,51 +1474,44 @@ static void picasso96_alloc2(TrapContext* ctx) cnt = 0; i = 0; - while (DisplayModes[i].depth >= 0) - { + while (DisplayModes[i].depth >= 0) { // Not even 256 color mode fits in VRAM? Ignore it completely. - if (DisplayModes[i].res.width * DisplayModes[i].res.height > gfxmem_bank.allocated_size - 256) - { + if (DisplayModes[i].res.width * DisplayModes[i].res.height > gfxmem_bank.allocated_size - 256) { i++; continue; } - //j = i; + j = i; size += PSSO_LibResolution_sizeof; while (missmodes[misscnt * 2] == 0) misscnt++; - if (missmodes[misscnt * 2] >= 0) - { + if (missmodes[misscnt * 2] >= 0) { int w = DisplayModes[i].res.width; int h = DisplayModes[i].res.height; - if (w > missmodes[misscnt * 2 + 0] || (w == missmodes[misscnt * 2 + 0] && h > missmodes[misscnt * 2 + 1])) - { - struct PicassoResolution* pr = &newmodes[cnt]; - memcpy(pr, &DisplayModes[i], sizeof(struct PicassoResolution)); + if (w > missmodes[misscnt * 2 + 0] || (w == missmodes[misscnt * 2 + 0] && h > missmodes[misscnt * 2 + 1])) { + struct PicassoResolution *pr = &newmodes[cnt]; + memcpy (pr, &DisplayModes[i], sizeof (struct PicassoResolution)); pr->res.width = missmodes[misscnt * 2 + 0]; pr->res.height = missmodes[misscnt * 2 + 1]; - _stprintf(pr->name, _T("%dx%d FAKE"), pr->res.width, pr->res.height); + _stprintf (pr->name, _T("%dx%d FAKE"), pr->res.width, pr->res.height); size += PSSO_ModeInfo_sizeof * depths; cnt++; misscnt++; continue; } } - memcpy(&newmodes[cnt], &DisplayModes[i], sizeof(struct PicassoResolution)); - size += PSSO_ModeInfo_sizeof * depths; - cnt++; + memcpy (&newmodes[cnt], &DisplayModes[i], sizeof (struct PicassoResolution)); + size += PSSO_ModeInfo_sizeof * depths; + cnt++; i++; } - qsort(newmodes, cnt, sizeof(struct PicassoResolution), resolution_compare); + qsort (newmodes, cnt, sizeof (struct PicassoResolution), resolution_compare); newmodes[cnt].depth = -1; - for (i = 0; i < cnt; i++) - { + for (i = 0; i < cnt; i++) { int depth; - for (depth = 1; depth <= 4; depth++) - { - switch (depth) - { + for (depth = 1; depth <= 4; depth++) { + switch (depth) { case 1: if (newmodes[i].res.width > chunky.width) chunky.width = newmodes[i].res.width; @@ -1676,26 +1539,24 @@ static void picasso96_alloc2(TrapContext* ctx) } } } - - uaegfx_card_install(ctx, size); - init_alloc(ctx, size); + uaegfx_card_install (ctx, size); + init_alloc (ctx, size); } -void picasso96_alloc(TrapContext* ctx) +void picasso96_alloc (TrapContext *ctx) { + uaegfx_resname = ds (_T("uaegfx.card")); if (uaegfx_old) return; - uaegfx_resname = ds(_T("uaegfx.card")); - picasso96_alloc2(ctx); + picasso96_alloc2 (ctx); } -static void inituaegfxfuncs(TrapContext* ctx, uaecptr start, uaecptr ABI); - -static void inituaegfx(TrapContext* ctx, uaecptr ABI) +static void inituaegfxfuncs (TrapContext *ctx, uaecptr start, uaecptr ABI); +static void inituaegfx(TrapContext *ctx, uaecptr ABI) { uae_u32 flags; - write_log(_T("RTG mode mask: %x\n"), currprefs.picasso96_modeflags); + write_log (_T("RTG mode mask: %x BI=%08x\n"), currprefs.picasso96_modeflags, ABI); trap_put_word(ctx, ABI + PSSO_BoardInfo_BitsPerCannon, 8); trap_put_word(ctx, ABI + PSSO_BoardInfo_RGBFormats, currprefs.picasso96_modeflags); trap_put_long(ctx, ABI + PSSO_BoardInfo_BoardType, picasso96_BT); @@ -1728,21 +1589,18 @@ static void inituaegfx(TrapContext* ctx, uaecptr ABI) flags = trap_get_long(ctx, ABI + PSSO_BoardInfo_Flags); flags &= 0xffff0000; if (flags & BIF_NOBLITTER) - write_log(_T("P96: Blitter disabled in devs:monitors/uaegfx!\n")); - if (NOBLITTER_ALL) - { + write_log (_T("P96: Blitter disabled in devs:monitors/uaegfx!\n")); + if (NOBLITTER_ALL) { flags |= BIF_NOBLITTER; flags &= ~BIF_BLITTER; + } else { + flags |= BIF_BLITTER; } - flags |= BIF_BLITTER; flags |= BIF_NOMEMORYMODEMIX; - flags &= ~BIF_HARDWARESPRITE; - if (!uaegfx_old) flags |= BIF_VBLANKINTERRUPT; - if (!(flags & BIF_INDISPLAYCHAIN)) - { - write_log(_T("P96: BIF_INDISPLAYCHAIN force-enabled!\n")); + if (!(flags & BIF_INDISPLAYCHAIN)) { + write_log (_T("P96: BIF_INDISPLAYCHAIN force-enabled!\n")); flags |= BIF_INDISPLAYCHAIN; } trap_put_long(ctx, ABI + PSSO_BoardInfo_Flags, flags); @@ -1761,18 +1619,14 @@ static void inituaegfx(TrapContext* ctx, uaecptr ABI) inituaegfxfuncs(ctx, uaegfx_rom, ABI); } -static bool addmode(TrapContext* ctx, uaecptr AmigaBoardInfo, uaecptr* amem, struct LibResolution* res, int w, int h, - const TCHAR* name, int display, int* unkcnt) +static bool addmode(TrapContext *ctx, uaecptr AmigaBoardInfo, uaecptr *amem, struct LibResolution *res, int w, int h, const TCHAR *name, int display, int *unkcnt) { int depth; bool added = false; - if (display > 0) - { + if (display > 0) { res->DisplayID = 0x51000000 + display * 0x100000; - } - else - { + } else { res->DisplayID = AssignModeID(w, h, unkcnt); } res->BoardInfo = AmigaBoardInfo; @@ -1780,23 +1634,18 @@ static bool addmode(TrapContext* ctx, uaecptr AmigaBoardInfo, uaecptr* amem, str res->Height = h; res->Flags = P96F_PUBLIC; memcpy(res->P96ID, "P96-0:", 6); - if (name) - { + if (name) { char* n2 = ua(name); - strncpy(res->Name, n2, MAXRESOLUTIONNAMELENGTH); + strcpy (res->Name, n2); xfree (n2); - } - else - { + } else { sprintf(res->Name, "UAE:%4dx%4d", w, h); } - for (depth = 8; depth <= 32; depth++) - { + for (depth = 8; depth <= 32; depth++) { if (!p96depth(depth)) continue; - if (gfxmem_bank.allocated_size >= w * h * ((depth + 7) / 8)) - { + if(gfxmem_bank.allocated_size >= w * h * ((depth + 7) / 8)) { FillBoardInfo(ctx, *amem, res, w, h, depth); *amem += PSSO_ModeInfo_sizeof; added = true; @@ -1818,8 +1667,7 @@ static uae_u32 REGPARAM2 picasso_InitCard(TrapContext* ctx) uaecptr amem; uaecptr AmigaBoardInfo = trap_get_areg(ctx, 0); - if (!picasso96_amem) - { + if (!picasso96_amem) { write_log (_T("P96: InitCard() but no resolution memory!\n")); return 0; } @@ -1829,13 +1677,10 @@ static uae_u32 REGPARAM2 picasso_InitCard(TrapContext* ctx) i = 0; unkcnt = cnt = 0; - while (newmodes[i].depth >= 0) - { + while (newmodes[i].depth >= 0) { struct LibResolution res = {0}; int j = i; - if (addmode(ctx, AmigaBoardInfo, &amem, &res, newmodes[i].res.width, newmodes[i].res.height, nullptr, 0, - &unkcnt)) - { + if (addmode(ctx, AmigaBoardInfo, &amem, &res, newmodes[i].res.width, newmodes[i].res.height, NULL, 0, &unkcnt)) { TCHAR* s; s = au(res.Name); write_log (_T("%2d: %08X %4dx%4d %s\n"), ++cnt, res.DisplayID, res.Width, res.Height, s); @@ -1877,19 +1722,22 @@ static uae_u32 REGPARAM2 picasso_InitCard(TrapContext* ctx) */ static uae_u32 REGPARAM2 picasso_SetSwitch(TrapContext* ctx) { + struct picasso96_state_struct *state = &picasso96_state; + struct amigadisplay *ad = &adisplays; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u16 flag = trap_get_dreg(ctx, 0) & 0xFFFF; - atomic_or(&picasso_state_change, PICASSO_STATE_SETSWITCH); - picasso_requested_on = flag != 0; + atomic_or(&vidinfo->picasso_state_change, PICASSO_STATE_SETSWITCH); + ad->picasso_requested_on = flag != 0; set_config_changed(); TCHAR p96text[100]; p96text[0] = 0; if (flag) _stprintf(p96text, _T("Picasso96 %dx%dx%d (%dx%dx%d)"), - picasso96_state.Width, picasso96_state.Height, picasso96_state.BytesPerPixel * 8, - picasso_vidinfo.width, picasso_vidinfo.height, picasso_vidinfo.pixbytes * 8); - write_log(_T("SetSwitch() - %s\n"), flag ? p96text : _T("amiga")); + state->Width, state->Height, state->BytesPerPixel * 8, + vidinfo->width, vidinfo->height, vidinfo->pixbytes * 8); + write_log (_T("SetSwitch() - %s.\n"), flag ? p96text : _T("amiga")); /* Put old switch-state in D0 */ return !flag; @@ -1898,21 +1746,21 @@ static uae_u32 REGPARAM2 picasso_SetSwitch(TrapContext* ctx) void picasso_enablescreen(int on) { - bool uaegfx = currprefs.rtgboards[0].rtgmem_type < GFXBOARD_HARDWARE && currprefs.rtgboards[0].rtgmem_size; + bool uaegfx = currprefs.rtgboards[0].rtgmem_size; bool uaegfx_active = is_uaegfx_active(); - if (uaegfx_active && uaegfx) + if (uaegfx_active && uaegfx) { if (!init_picasso_screen_called) init_picasso_screen(); - + } setconvert(); picasso_refresh(); } -static void resetpalette(void) +static void resetpalette(struct picasso96_state_struct *state) { for (int i = 0; i < 256; i++) - picasso96_state.CLUT[i].Pad = 0xff; + state->CLUT[i].Pad = 0xff; } /* @@ -1929,6 +1777,8 @@ static void resetpalette(void) */ static int updateclut(TrapContext* ctx, uaecptr clut, int start, int count) { + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u8 clutbuf[256 * 3]; int i, changed = 0; clut += start * 3; @@ -1937,35 +1787,32 @@ static int updateclut(TrapContext* ctx, uaecptr clut, int start, int count) int r = clutbuf[i * 3 + 0]; int g = clutbuf[i * 3 + 1]; int b = clutbuf[i * 3 + 2]; - - changed |= picasso96_state.CLUT[i].Red != r - || picasso96_state.CLUT[i].Green != g - || picasso96_state.CLUT[i].Blue != b; - if (picasso96_state.CLUT[i].Pad) - { + changed |= state->CLUT[i].Red != r + || state->CLUT[i].Green != g + || state->CLUT[i].Blue != b; + if (state->CLUT[i].Pad) { changed = 1; - picasso96_state.CLUT[i].Pad = 0; + state->CLUT[i].Pad = 0; } - picasso96_state.CLUT[i].Red = r; - picasso96_state.CLUT[i].Green = g; - picasso96_state.CLUT[i].Blue = b; - } - changed |= picasso_palette(picasso96_state.CLUT); - return changed; + state->CLUT[i].Red = r; + state->CLUT[i].Green = g; + state->CLUT[i].Blue = b; } + changed |= picasso_palette(state->CLUT, vidinfo->clut); + return changed; +} static uae_u32 REGPARAM2 picasso_SetColorArray(TrapContext* ctx) { /* Fill in some static UAE related structure about this new CLUT setting -* We need this for CLUT-based displays, and for mapping CLUT to hi/true colour */ + * We need this for CLUT-based displays, and for mapping CLUT to hi/true colour */ uae_u16 start = trap_get_dreg(ctx, 0); uae_u16 count = trap_get_dreg(ctx, 1); uaecptr boardinfo = trap_get_areg(ctx, 0); uaecptr clut = boardinfo + PSSO_BoardInfo_CLUT; if (start > 256 || count > 256 || start + count > 256) return 0; - if (updateclut(ctx, clut, start, count)) - picasso_vidinfo.full_refresh = 1; + updateclut(ctx, clut, start, count); return 1; } @@ -1979,30 +1826,29 @@ static uae_u32 REGPARAM2 picasso_SetColorArray(TrapContext* ctx) */ static uae_u32 REGPARAM2 picasso_SetDAC(TrapContext* ctx) { + struct picasso_vidbuf_description* vidinfo = &picasso_vidinfo; /* Fill in some static UAE related structure about this new DAC setting -* Lets us keep track of what pixel format the Amiga is thinking about in our frame-buffer */ + * Lets us keep track of what pixel format the Amiga is thinking about in our frame-buffer */ - atomic_or(&picasso_vidinfo.picasso_state_change, PICASSO_STATE_SETDAC); + atomic_or(&vidinfo->picasso_state_change, PICASSO_STATE_SETDAC); return 1; } -static void init_picasso_screen(void) +static void init_picasso_screen() { - if (picasso_vidinfo.set_panning_called) - { - picasso96_state.Extent = picasso96_state.Address + picasso96_state.BytesPerRow * - picasso96_state.VirtualHeight; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + struct picasso96_state_struct *state = &picasso96_state; + if(vidinfo->set_panning_called) { + state->Extent = state->Address + state->BytesPerRow * state->VirtualHeight; } - if (set_gc_called) - { - gfx_set_picasso_modeinfo(picasso96_state.Width, picasso96_state.Height, - picasso96_state.GC_Depth, (RGBFTYPE)picasso96_state.RGBFormat); + if (set_gc_called) { + gfx_set_picasso_modeinfo(state->Width, state->Height, state->GC_Depth, state->RGBFormat); set_gc_called = 0; } - if ((picasso_vidinfo.width == picasso96_state.Width) && - (picasso_vidinfo.height == picasso96_state.Height) && - (picasso_vidinfo.depth == (picasso96_state.GC_Depth >> 3)) && - (picasso_vidinfo.selected_rgbformat == picasso96_state.RGBFormat)) + if((vidinfo->width == state->Width) && + (vidinfo->height == state->Height) && + (vidinfo->depth == (state->GC_Depth >> 3)) && + (vidinfo->selected_rgbformat == state->RGBFormat)) { picasso_refresh(); } @@ -2022,6 +1868,8 @@ static void init_picasso_screen(void) */ static uae_u32 REGPARAM2 picasso_SetGC(TrapContext* ctx) { + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; /* Fill in some static UAE related structure about this new ModeInfo setting */ uaecptr AmigaBoardInfo = trap_get_areg(ctx, 0); uae_u32 border = trap_get_dreg(ctx, 0); @@ -2030,19 +1878,18 @@ static uae_u32 REGPARAM2 picasso_SetGC(TrapContext* ctx) trap_put_long(ctx, AmigaBoardInfo + PSSO_BoardInfo_ModeInfo, modeinfo); trap_put_word(ctx, AmigaBoardInfo + PSSO_BoardInfo_Border, border); - picasso96_state.Width = trap_get_word(ctx, modeinfo + PSSO_ModeInfo_Width); - picasso96_state.VirtualWidth = picasso96_state.Width; /* in case SetPanning doesn't get called */ + state->Width = trap_get_word(ctx, modeinfo + PSSO_ModeInfo_Width); + state->VirtualWidth = state->Width; /* in case SetPanning doesn't get called */ - picasso96_state.Height = trap_get_word(ctx, modeinfo + PSSO_ModeInfo_Height); - picasso96_state.VirtualHeight = picasso96_state.Height; /* in case SetPanning doesn't get called */ + state->Height = trap_get_word(ctx, modeinfo + PSSO_ModeInfo_Height); + state->VirtualHeight = state->Height; /* in case SetPanning doesn't get called */ - picasso96_state.GC_Depth = trap_get_byte(ctx, modeinfo + PSSO_ModeInfo_Depth); - picasso96_state.GC_Flags = trap_get_byte(ctx, modeinfo + PSSO_ModeInfo_Flags); + state->GC_Depth = trap_get_byte(ctx, modeinfo + PSSO_ModeInfo_Depth); + state->GC_Flags = trap_get_byte(ctx, modeinfo + PSSO_ModeInfo_Flags); - picasso96_state.HostAddress = nullptr; - - atomic_or(&picasso_state_change, PICASSO_STATE_SETGC); + state->HostAddress = NULL; + atomic_or(&vidinfo->picasso_state_change, PICASSO_STATE_SETGC); return 1; } @@ -2069,85 +1916,55 @@ static uae_u32 REGPARAM2 picasso_SetGC(TrapContext* ctx) * because SetSwitch() is not called for subsequent Picasso screens. */ -static void picasso_SetPanningInit(void) +static void picasso_SetPanningInit (struct picasso96_state_struct *state) { - picasso96_state.XYOffset = picasso96_state.Address + (picasso96_state.XOffset * - picasso96_state.BytesPerPixel) - + (picasso96_state.YOffset * picasso96_state.BytesPerRow); - if (picasso96_state.VirtualWidth > picasso96_state.Width || picasso96_state.VirtualHeight > picasso96_state.Height) - picasso96_state.BigAssBitmap = 1; - else - picasso96_state.BigAssBitmap = 0; + state->XYOffset = state->Address + (state->XOffset * state->BytesPerPixel) + + (state->YOffset * state->BytesPerRow); } static uae_u32 REGPARAM2 picasso_SetPanning(TrapContext* ctx) { + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u16 Width = trap_get_dreg(ctx, 0); uaecptr start_of_screen = trap_get_areg(ctx, 1); uaecptr bi = trap_get_areg(ctx, 0); uaecptr bmeptr = trap_get_long(ctx, bi + PSSO_BoardInfo_BitMapExtra); /* Get our BoardInfo ptr's BitMapExtra ptr */ uae_u16 bme_width, bme_height; - //int changed = 0; RGBFTYPE rgbf; if (oldscr == 0) { oldscr = start_of_screen; - //changed = 1; } if (oldscr != start_of_screen) { oldscr = start_of_screen; - //changed = 1; } bme_width = trap_get_word(ctx, bmeptr + PSSO_BitMapExtra_Width); bme_height = trap_get_word(ctx, bmeptr + PSSO_BitMapExtra_Height); - rgbf = picasso96_state.RGBFormat; + rgbf = state->RGBFormat; - picasso96_state.Address = start_of_screen; /* Amiga-side address */ - picasso96_state.XOffset = (uae_s16)(trap_get_dreg(ctx, 1) & 0xFFFF); - picasso96_state.YOffset = (uae_s16)(trap_get_dreg(ctx, 2) & 0xFFFF); - trap_put_word(ctx, bi + PSSO_BoardInfo_XOffset, picasso96_state.XOffset); - trap_put_word(ctx, bi + PSSO_BoardInfo_YOffset, picasso96_state.YOffset); - picasso96_state.VirtualWidth = bme_width; - picasso96_state.VirtualHeight = bme_height; - picasso96_state.RGBFormat = (RGBFTYPE)trap_get_dreg(ctx, 7); - picasso96_state.BytesPerPixel = GetBytesPerPixel(picasso96_state.RGBFormat); - picasso96_state.BytesPerRow = picasso96_state.VirtualWidth * picasso96_state.BytesPerPixel; - picasso_SetPanningInit(); + state->Address = start_of_screen; /* Amiga-side address */ + state->XOffset = (uae_s16)(trap_get_dreg(ctx, 1) & 0xFFFF); + state->YOffset = (uae_s16)(trap_get_dreg(ctx, 2) & 0xFFFF); + trap_put_word(ctx, bi + PSSO_BoardInfo_XOffset, state->XOffset); + trap_put_word(ctx, bi + PSSO_BoardInfo_YOffset, state->YOffset); + state->VirtualWidth = bme_width; + state->VirtualHeight = bme_height; + state->RGBFormat = (RGBFTYPE)trap_get_dreg(ctx, 7); + state->BytesPerPixel = GetBytesPerPixel (state->RGBFormat); + state->BytesPerRow = state->VirtualWidth * state->BytesPerPixel; + picasso_SetPanningInit(state); - if (rgbf != picasso96_state.RGBFormat) - { + if (rgbf != state->RGBFormat) { setconvert(); } - atomic_or(&picasso_state_change, PICASSO_STATE_SETPANNING); + atomic_or(&vidinfo->picasso_state_change, PICASSO_STATE_SETPANNING); return 1; } -#ifdef CPU_64_BIT -static void do_xor8 (uae_u8 *p, int w, uae_u32 v) -{ - while (ALIGN_POINTER_TO32 (p) != 7 && w) { - *p ^= v; - p++; - w--; - } - uae_u64 vv = v | ((uae_u64)v << 32); - while (w >= 2 * 8) { - *((uae_u64*)p) ^= vv; - p += 8; - *((uae_u64*)p) ^= vv; - p += 8; - w -= 2 * 8; - } - while (w) { - *p ^= v; - p++; - w--; - } -} -#else static void do_xor8 (uae_u8 *p, int w, uae_u32 v) { while (ALIGN_POINTER_TO32 (p) != 3 && w) { @@ -2168,7 +1985,7 @@ static void do_xor8 (uae_u8 *p, int w, uae_u32 v) w--; } } -#endif + /* * InvertRect: * @@ -2204,8 +2021,7 @@ static uae_u32 REGPARAM2 picasso_InvertRect (TrapContext *ctx) if (NOBLITTER) return 0; - if (CopyRenderInfoStructureA2U(ctx, renderinfo, &ri)) - { + if (CopyRenderInfoStructureA2U(ctx, renderinfo, &ri)) { if (!validatecoords(ctx, &ri, &X, &Y, &Width, &Height)) return 1; @@ -2254,7 +2070,7 @@ static uae_u32 REGPARAM2 picasso_FillRect(TrapContext* ctx) if (NOBLITTER) return 0; - if (CopyRenderInfoStructureA2U(ctx, renderinfo, &ri)) { + if (CopyRenderInfoStructureA2U (ctx, renderinfo, &ri) && Y != 0xFFFF) { if (!validatecoords(ctx, &ri, &X, &Y, &Width, &Height)) return 1; @@ -2564,8 +2380,7 @@ static uae_u32 REGPARAM2 picasso_BlitPattern (TrapContext *ctx) if (pattern.Size >= 16) result = 0; - if (result) - { + if (result) { uae_u32 fgpen, bgpen; ysize_mask = (1 << pattern.Size) - 1; @@ -2576,8 +2391,7 @@ static uae_u32 REGPARAM2 picasso_BlitPattern (TrapContext *ctx) bgpen = pattern.BgPen; endianswap(&bgpen, Bpp); - for (rows = 0; rows < H; rows++, uae_mem += ri.BytesPerRow) - { + for (rows = 0; rows < H; rows++, uae_mem += ri.BytesPerRow) { unsigned long prow = (rows + pattern.YOffset) & ysize_mask; unsigned int d; uae_u8* uae_mem2 = uae_mem; @@ -2863,22 +2677,14 @@ static uae_u32 REGPARAM2 picasso_CalculateBytesPerRow (TrapContext *ctx) */ static uae_u32 REGPARAM2 picasso_SetDisplay(TrapContext* ctx) { + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u32 setstate = trap_get_dreg(ctx, 0); - resetpalette(); - atomic_or(&picasso_vidinfo.picasso_state_change, PICASSO_STATE_SETDISPLAY); + resetpalette(state); + atomic_or(&vidinfo->picasso_state_change, PICASSO_STATE_SETDISPLAY); return !setstate; } -void init_hz_p96(void) -{ - p96vblank = vblank_hz; - if (p96vblank <= 0) - p96vblank = 60; - if (p96vblank >= 300) - p96vblank = 300; - p96syncrate = maxvpos_nom * vblank_hz / p96vblank; -} - /* NOTE: Watch for those planeptrs of 0x00000000 and 0xFFFFFFFF for all zero / all one bitmaps !!!! */ static void PlanarToChunky(TrapContext* ctx, struct RenderInfo* ri, struct BitMap* bm, unsigned long srcx, unsigned long srcy, @@ -2939,14 +2745,13 @@ static void PlanarToChunky(TrapContext* ctx, struct RenderInfo* ri, struct BitMa do_put_mem_long((uae_u32 *)(image + cols), a); do_put_mem_long((uae_u32 *)(image + cols + 4), b); } - for (j = 0; j < Depth; j++) - { + for (j = 0; j < Depth; j++) { if (PLANAR[j] != &all_zeros_bitmap && PLANAR[j] != &all_ones_bitmap) { PLANAR[j] += eol_offset; } - } } } +} /* * BlitPlanar2Chunky: @@ -3005,10 +2810,12 @@ static void PlanarToDirect(TrapContext* ctx, struct RenderInfo* ri, struct BitMa int j; int bpp = GetBytesPerPixel(ri->RGBFormat); uae_u8* PLANAR[8]; + uaecptr APLANAR[8]; uae_u8* image = ri->Memory + dstx * bpp + dsty * ri->BytesPerRow; int Depth = bm->Depth; unsigned long rows; long eol_offset; + //bool indirect = trap_is_indirect(); int maxc = -1; uae_u32 cim[256]; @@ -3016,8 +2823,7 @@ static void PlanarToDirect(TrapContext* ctx, struct RenderInfo* ri, struct BitMa return; /* Set up our bm->Planes[] pointers to the right horizontal offset */ - for (j = 0; j < Depth; j++) - { + for (j = 0; j < Depth; j++) { uae_u8 *p = bm->Planes[j]; if (p != &all_zeros_bitmap && p != &all_ones_bitmap) p += srcx / 8 + srcy * bm->BytesPerRow; @@ -3026,15 +2832,14 @@ static void PlanarToDirect(TrapContext* ctx, struct RenderInfo* ri, struct BitMa PLANAR[j] = &all_zeros_bitmap; } - eol_offset = (long)bm->BytesPerRow - (long)((width + (srcx & 7)) >> 3); + eol_offset = (uae_s32) bm->BytesPerRow - (uae_s32) ((width + (srcx & 7)) >> 3); for (rows = 0; rows < height; rows++, image += ri->BytesPerRow) { unsigned long cols; uae_u8 *image2 = image; unsigned int bitoffs = 7 - (srcx & 7); int i; - for (cols = 0; cols < width; cols++) - { + for (cols = 0; cols < width; cols ++) { int v = 0, k; for (k = 0; k < Depth; k++) { if (PLANAR[k] == &all_ones_bitmap) @@ -3067,7 +2872,6 @@ static void PlanarToDirect(TrapContext* ctx, struct RenderInfo* ri, struct BitMa maxc = vc; } - switch (bpp) { case 2: @@ -3165,44 +2969,43 @@ static uae_u32 REGPARAM2 picasso_BlitPlanar2Direct (TrapContext *ctx) } #include "statusline.h" - -static void picasso_statusline(uae_u8* dst) +void picasso_statusline( uae_u8 *dst) { + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + struct picasso96_state_struct *state = &picasso96_state; int y; int dst_height, dst_width, pitch; - dst_height = picasso96_state.Height; - if (dst_height > picasso_vidinfo.height) - dst_height = picasso_vidinfo.height; - dst_width = picasso96_state.Width; - if (dst_width > picasso_vidinfo.width) - dst_width = picasso_vidinfo.width; - pitch = picasso_vidinfo.rowbytes; + dst_height = state->Height; + if (dst_height > vidinfo->height) + dst_height = vidinfo->height; + dst_width = state->Width; + if (dst_width > vidinfo->width) + dst_width = vidinfo->width; + pitch = vidinfo->rowbytes; for (y = 0; y < TD_TOTAL_HEIGHT; y++) { int line = dst_height - TD_TOTAL_HEIGHT + y; uae_u8* buf = dst + line * pitch; - draw_status_line_single(buf, picasso_vidinfo.pixbytes, y, dst_width, p96rc, p96gc, p96bc, nullptr); + draw_status_line_single(buf, vidinfo->pixbytes, y, dst_width, p96rc, p96gc, p96bc, nullptr); } } -static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcbytesperrow, int srcpixbytes, int dy, - int dstbytesperrow, int dstpixbytes, bool direct, int convert_mode) +static void copyrow (uae_u8 *src, uae_u8 *dst, int x, int y, int width, int srcbytesperrow, int srcpixbytes, int dx, int dy, int dstbytesperrow, int dstpixbytes, bool direct, int convert_mode, uae_u32 *p96_rgbx16p) { + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u8* src2 = src + y * srcbytesperrow; uae_u8* dst2 = dst + dy * dstbytesperrow; int endx = x + width, endx4; int dstpix = dstpixbytes; int srcpix = srcpixbytes; - if (direct) - { + if (direct) { memcpy(dst2 + x * dstpix, src2 + x * srcpix, width * dstpix); return; } // native match? - if (currprefs.gfx_api) - { + if (currprefs.gfx_api) { switch (convert_mode) { #ifdef WORDS_BIGENDIAN @@ -3212,12 +3015,10 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby case RGBFB_B8G8R8A8_32: case RGBFB_R5G6B5PC_16: #endif - memcpy(dst2 + x * dstpix, src2 + x * srcpix, width * dstpix); + memcpy (dst2 + dx * dstpix, src2 + x * srcpix, width * dstpix); return; } - } - else - { + } else { switch (convert_mode) { #ifdef WORDS_BIGENDIAN @@ -3227,7 +3028,7 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby case RGBFB_B8G8R8A8_32: case RGBFB_R5G6B5PC_16: #endif - memcpy(dst2 + x * dstpix, src2 + x * srcpix, width * dstpix); + memcpy (dst2 + dx * dstpix, src2 + x * srcpix, width * dstpix); return; } } @@ -3238,40 +3039,40 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby { /* 24bit->32bit */ case RGBFB_R8G8B8_32: - while (x < endx) - { - ((uae_u32*)dst2)[x] = (src2[x * 3 + 0] << 16) | (src2[x * 3 + 1] << 8) | (src2[x * 3 + 2] << 0); + while (x < endx) { + ((uae_u32*)dst2)[dx] = (src2[x * 3 + 0] << 16) | (src2[x * 3 + 1] << 8) | (src2[x * 3 + 2] << 0); x++; + dx++; } break; case RGBFB_B8G8R8_32: - while (x < endx) - { - ((uae_u32*)dst2)[x] = ((uae_u32*)(src2 + x * 3))[0] & 0x00ffffff; + while (x < endx) { + ((uae_u32*)dst2)[dx] = ((uae_u32*)(src2 + x * 3))[0] & 0x00ffffff; x++; + dx++; } break; /* 32bit->32bit */ case RGBFB_R8G8B8A8_32: - while (x < endx) - { - ((uae_u32*)dst2)[x] = (src2[x * 4 + 0] << 16) | (src2[x * 4 + 1] << 8) | (src2[x * 4 + 2] << 0); + while (x < endx) { + ((uae_u32*)dst2)[dx] = (src2[x * 4 + 0] << 16) | (src2[x * 4 + 1] << 8) | (src2[x * 4 + 2] << 0); x++; + dx++; } break; case RGBFB_A8R8G8B8_32: - while (x < endx) - { - ((uae_u32*)dst2)[x] = (src2[x * 4 + 1] << 16) | (src2[x * 4 + 2] << 8) | (src2[x * 4 + 3] << 0); + while (x < endx) { + ((uae_u32*)dst2)[dx] = (src2[x * 4 + 1] << 16) | (src2[x * 4 + 2] << 8) | (src2[x * 4 + 3] << 0); x++; + dx++; } break; case RGBFB_A8B8G8R8_32: - while (x < endx) - { - ((uae_u32*)dst2)[x] = ((uae_u32*)src2)[x] >> 8; + while (x < endx) { + ((uae_u32*)dst2)[dx] = ((uae_u32*)src2)[x] >> 8; x++; + dx++; } break; @@ -3283,26 +3084,29 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby case RGBFB_B5G6R5PC_32: case RGBFB_B5G5R5PC_32: { - while ((x & 3) && x < endx) - { - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + while ((x & 3) && x < endx) { + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } - while (x < endx4) - { - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + while (x < endx4) { + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } - while (x < endx) - { - ((uae_u32*)dst2)[x] = p96_rgbx16[((uae_u16*)src2)[x]]; + while (x < endx) { + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } } break; @@ -3315,119 +3119,119 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby case RGBFB_B5G6R5PC_16: case RGBFB_R5G6B5PC_16: { - while ((x & 3) && x < endx) - { - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + while ((x & 3) && x < endx) { + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } - while (x < endx4) - { - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + while (x < endx4) { + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + dx++; + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } - while (x < endx) - { - ((uae_u16*)dst2)[x] = (uae_u16)p96_rgbx16[((uae_u16*)src2)[x]]; + while (x < endx) { + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; x++; + dx++; } } break; /* 24bit->16bit */ case RGBFB_R8G8B8_16: - while (x < endx) - { + while (x < endx) { uae_u8 r, g, b; r = src2[x * 3 + 0]; g = src2[x * 3 + 1]; b = src2[x * 3 + 2]; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((r >> 3) & 0x1f) << 11) | (((g >> 2) & 0x3f) << 5) | (((b >> 3) & 0x1f) - << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((r >> 3) & 0x1f) << 11) | (((g >> 2) & 0x3f) << 5) | (((b >> 3) & 0x1f) << 0)]; x++; + dx++; } break; case RGBFB_B8G8R8_16: - while (x < endx) - { + while (x < endx) { uae_u32 v; v = ((uae_u32*)(&src2[x * 3]))[0] >> 8; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((v >> (8 + 3)) & 0x1f) << 11) | (((v >> (0 + 2)) & 0x3f) << 5) | (((v >> - (16 + 3)) & 0x1f) << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((v >> (8 + 3)) & 0x1f) << 11) | (((v >> (0 + 2)) & 0x3f) << 5) | (((v >> (16 + 3)) & 0x1f) << 0)]; x++; + dx++; } break; /* 32bit->16bit */ case RGBFB_R8G8B8A8_16: - while (x < endx) - { + while (x < endx) { uae_u32 v; v = ((uae_u32*)src2)[x]; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((v >> (0 + 3)) & 0x1f) << 11) | (((v >> (8 + 2)) & 0x3f) << 5) | (((v >> - (16 + 3)) & 0x1f) << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((v >> (0 + 3)) & 0x1f) << 11) | (((v >> (8 + 2)) & 0x3f) << 5) | (((v >> (16 + 3)) & 0x1f) << 0)]; x++; + dx++; } break; case RGBFB_A8R8G8B8_16: - while (x < endx) - { + while (x < endx) { uae_u32 v; v = ((uae_u32*)src2)[x]; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((v >> (8 + 3)) & 0x1f) << 11) | (((v >> (16 + 2)) & 0x3f) << 5) | (((v >> - (24 + 3)) & 0x1f) << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((v >> (8 + 3)) & 0x1f) << 11) | (((v >> (16 + 2)) & 0x3f) << 5) | (((v >> (24 + 3)) & 0x1f) << 0)]; x++; + dx++; } break; case RGBFB_A8B8G8R8_16: - while (x < endx) - { + while (x < endx) { uae_u32 v; v = ((uae_u32*)src2)[x]; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((v >> (24 + 3)) & 0x1f) << 11) | (((v >> (16 + 2)) & 0x3f) << 5) | (((v - >> (8 + 3)) & 0x1f) << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((v >> (24 + 3)) & 0x1f) << 11) | (((v >> (16 + 2)) & 0x3f) << 5) | (((v >> (8 + 3)) & 0x1f) << 0)]; x++; + dx++; } break; case RGBFB_B8G8R8A8_16: - while (x < endx) - { + while (x < endx) { uae_u32 v; v = ((uae_u32*)src2)[x]; - ((uae_u16*)dst2)[x] = p96_rgbx16[(((v >> (16 + 3)) & 0x1f) << 11) | (((v >> (8 + 2)) & 0x3f) << 5) | (((v >> - (0 + 3)) & 0x1f) << 0)]; + ((uae_u16*)dst2)[dx] = p96_rgbx16p[(((v >> (16 + 3)) & 0x1f) << 11) | (((v >> (8 + 2)) & 0x3f) << 5) | (((v >> (0 + 3)) & 0x1f) << 0)]; x++; + dx++; } break; /* 8bit->32bit */ case RGBFB_CLUT_RGBFB_32: { - while ((x & 3) && x < endx) - { - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while ((x & 3) && x < endx) { + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } - while (x < endx4) - { - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while (x < endx4) { + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } - while (x < endx) - { - ((uae_u32*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while (x < endx) { + ((uae_u32*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } } break; @@ -3435,39 +3239,590 @@ static void copyrow(uae_u8* src, uae_u8* dst, int x, int y, int width, int srcby /* 8bit->16bit */ case RGBFB_CLUT_RGBFB_16: { - while ((x & 3) && x < endx) - { - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while ((x & 3) && x < endx) { + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } - while (x < endx4) - { - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while (x < endx4) { + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + dx++; + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } - while (x < endx) - { - ((uae_u16*)dst2)[x] = picasso_vidinfo.clut[src2[x]]; + while (x < endx) { + ((uae_u16*)dst2)[dx] = vidinfo->clut[src2[x]]; x++; + dx++; } } break; } } -static void copyall(uae_u8* src, uae_u8* dst, int pwidth, int pheight, int srcbytesperrow, int srcpixbytes, - int dstbytesperrow, int dstpixbytes, bool direct, int mode_convert) +static uae_u16 yuvtorgb(uae_u8 yx, uae_u8 ux, uae_u8 vx) { + int y = yx - 16; + int u = ux - 128; + int v = vx - 128; + int r = (298 * y + 409 * v + 128) >> (8 + 3); + int g = (298 * y - 100 * u - 208 * v + 128) >> (8 + 3); + int b = (298 * y + 516 * u + 128) >> (8 + 3); + if (r < 0) + r = 0; + if (r > 31) + r = 31; + if (g < 0) + g = 0; + if (g > 31) + g = 31; + if (b < 0) + b = 0; + if (b > 31) + b = 31; + return (r << 10) | (g << 5) | b; +} + +#define CKCHECK if (!ck \ + || (screenpixbytes == 4 && colorkey == ((uae_u32*)srcs)[dx]) \ + || (screenpixbytes == 2 && (uae_u16)colorkey == ((uae_u16*)srcs)[dx]) \ + || (screenpixbytes == 1 && (uae_u8)colorkey == ((uae_u8*)srcs)[dx]) \ + || (screenpixbytes == 3 && ckbytes[0] == srcs[dx * 3 + 0] && ckbytes[1] == srcs[dx * 3 + 1] && ckbytes[2] == srcs[dx * 3 + 2])) + +void copyrow_scale(uae_u8 *src, uae_u8 *src_screen, uae_u8 *dst, + int sx, int sy, int sxadd, int width, int srcbytesperrow, int srcpixbytes, + int screenbytesperrow, int screenpixbytes, + int dx, int dy, int dstwidth, int dstheight, int dstbytesperrow, int dstpixbytes, + bool ck, uae_u32 colorkey, + int convert_mode, uae_u32 *p96_rgbx16p, uae_u32 *clut, bool yuv_swap) +{ + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + uae_u8 *src2 = src + sy * srcbytesperrow; + uae_u8 *dst2 = dst + dy * dstbytesperrow; + uae_u8 *srcs = src_screen + dy * screenbytesperrow; + int endx, endx4; + int dstpix = dstpixbytes; + int srcpix = srcpixbytes; + int x; + uae_u8 ckbytes[3]; + + if (dx < 0 || dx >= dstwidth) + return; + if (dy < 0 || dy >= dstheight) + return; + + if (dx + (width * 256) / sxadd > dstwidth) { + width = ((dstwidth - dx) * sxadd) / 256; + if (width <= 0) + return; + } + + endx = (sx + width) << 8; + + switch (convert_mode) + { + case RGBFB_Y4U2V2_32: + case RGBFB_Y4U2V2_16: + endx /= 2; + sxadd /= 2; + break; + case RGBFB_Y4U1V1_32: + case RGBFB_Y4U1V1_16: + endx /= 4; + sxadd /= 4; + break; + } + + endx4 = endx & ~(3 << 8); + + ckbytes[0] = colorkey >> 16; + ckbytes[1] = colorkey >> 8; + ckbytes[2] = colorkey >> 0; + + switch (convert_mode) + { + /* 24bit->32bit */ + case RGBFB_R8G8B8_32: + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = (src2[x * 3 + 0] << 16) | (src2[x * 3 + 1] << 8) | (src2[x * 3 + 2] << 0); + dx++; + } + break; + case RGBFB_B8G8R8_32: + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = ((uae_u32*)(src2 + x * 3))[0] & 0x00ffffff; + dx++; + } + break; + + /* 32bit->32bit */ + case RGBFB_R8G8B8A8_32: + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = (src2[x * 4 + 0] << 16) | (src2[x * 4 + 1] << 8) | (src2[x * 4 + 2] << 0); + dx++; + } + break; + case RGBFB_A8R8G8B8_32: + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = (src2[x * 4 + 1] << 16) | (src2[x * 4 + 2] << 8) | (src2[x * 4 + 3] << 0); + dx++; + } + break; + case RGBFB_A8B8G8R8_32: + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = ((uae_u32*)src2)[x] >> 8; + dx++; + } + break; + + /* 15/16bit->32bit */ + case RGBFB_R5G6B5PC_32: + case RGBFB_R5G5B5PC_32: + case RGBFB_R5G6B5_32: + case RGBFB_R5G5B5_32: + case RGBFB_B5G6R5PC_32: + case RGBFB_B5G5R5PC_32: + { + while ((sx & (3 << 8)) && sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + while (sx < endx4) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + } + break; + + case RGBFB_Y4U2V2_32: + { + uae_u32 outval1, outval2; + uae_u8 y0, y1, u, v; + bool docalc1 = false; + bool docalc2 = false; + int oldsx = -1; + uae_u32 val = ((uae_u32*)src2)[sx >> 8]; + uae_u32 oldval = val ^ 1; + while (sx < endx) { + x = sx >> 8; + if (oldsx != x) { + uae_u32 val = ((uae_u32*)src2)[x]; + if (val != oldval) { + oldval = val; + if (yuv_swap) + val = ((val & 0xff00ff00) >> 8) | ((val & 0x00ff00ff) << 8); + y0 = val >> 8; + y1 = val >> 24; + u = val >> 0; + v = val >> 16; + if (y0 == y1) { + uae_u16 out = yuvtorgb(y0, u, v); + outval1 = p96_rgbx16p[out]; + outval2 = outval1; + } else { + docalc1 = true; + docalc2 = true; + } + } + oldsx = x; + } + if ((sx & 255) < 128) { + CKCHECK + { + if (docalc1) { + uae_u16 out = yuvtorgb(y0, u, v); + outval1 = p96_rgbx16p[out]; + docalc1 = false; + } + ((uae_u32*)dst2)[dx] = outval1; + } + } else { + CKCHECK + { + if (docalc2) { + uae_u16 out = yuvtorgb(y1, u, v); + outval2 = p96_rgbx16p[out]; + docalc2 = false; + } + ((uae_u32*)dst2)[dx] = outval2; + } + } + sx += sxadd; + dx++; + } + } + break; + + case RGBFB_Y4U1V1_32: + { + while (sx < endx) { + x = sx >> 8; + uae_u32 val = ((uae_u32*)src2)[x]; + uae_u8 y0 = ((val >> 12) & 31) * 8; + uae_u8 y1 = ((val >> 17) & 31) * 8; + uae_u8 y2 = ((val >> 22) & 31) * 8; + uae_u8 y3 = ((val >> 27) & 31) * 8; + uae_s8 u = ((val >> 0) & 63) * 4; + uae_s8 v = ((val >> 6) & 63) * 4; + int fr = sx & 255; + if (fr >= 192) { + CKCHECK + { + uae_u16 out = yuvtorgb(y3, u, v); + ((uae_u32*)dst2)[dx] = p96_rgbx16p[out]; + } + } else if (fr >= 128) { + CKCHECK + { + uae_u16 out = yuvtorgb(y2, u, v); + ((uae_u32*)dst2)[dx] = p96_rgbx16p[out]; + } + } else if (fr >= 64) { + CKCHECK + { + uae_u16 out = yuvtorgb(y1, u, v); + ((uae_u32*)dst2)[dx] = p96_rgbx16p[out]; + } + } else { + CKCHECK + { + uae_u16 out = yuvtorgb(y0, u, v); + ((uae_u32*)dst2)[dx] = p96_rgbx16p[out]; + } + } + sx += sxadd; + dx++; + } + } + break; + + /* 16/15bit->16bit */ + case RGBFB_R5G5B5PC_16: + case RGBFB_R5G6B5_16: + case RGBFB_R5G5B5_16: + case RGBFB_B5G5R5PC_16: + case RGBFB_B5G6R5PC_16: + case RGBFB_R5G6B5PC_16: + { + while ((sx & (3 << 8)) && sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + while (sx < endx4) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = (uae_u16)p96_rgbx16p[((uae_u16*)src2)[x]]; + dx++; + } + } + break; + + /* 8bit->16bit */ + case RGBFB_CLUT_RGBFB_16: + { + while ((sx & (3 << 8)) && sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + } + while (sx < endx4) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + } + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u16*)dst2)[dx] = clut[src2[x]]; + dx++; + } + } + break; + + /* 8bit->32bit */ + case RGBFB_CLUT_RGBFB_32: + { + while ((sx & (3 << 8)) && sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + } + while (sx < endx4) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + } + while (sx < endx) { + x = sx >> 8; + sx += sxadd; + CKCHECK + ((uae_u32*)dst2)[dx] = clut[src2[x]]; + dx++; + } + } + break; + + case RGBFB_Y4U2V2_16: + { + uae_u16 outval1, outval2; + uae_u8 y0, y1, u, v; + bool docalc1 = false; + bool docalc2 = false; + int oldsx = -1; + uae_u32 val = ((uae_u32*)src2)[sx >> 8]; + uae_u32 oldval = val ^ 1; + while (sx < endx) { + x = sx >> 8; + if (x != oldsx) { + val = ((uae_u32*)src2)[x]; + if (val != oldval) { + oldval = val; + if (yuv_swap) + val = ((val & 0xff00ff00) >> 8) | ((val & 0x00ff00ff) << 8); + y0 = val >> 8; + y1 = val >> 24; + u = val >> 0; + v = val >> 16; + if (y0 == y1) { + uae_u16 out = yuvtorgb(y0, u, v); + outval1 = p96_rgbx16p[out]; + outval2 = outval1; + } else { + docalc1 = true; + docalc2 = true; + } + } + oldsx = x; + } + if ((sx & 255) < 128) { + CKCHECK + { + if (docalc1) { + uae_u16 out = yuvtorgb(y0, u, v); + outval1 = p96_rgbx16p[out]; + docalc1 = false; + } + ((uae_u16*)dst2)[dx] = outval1; + } + CKCHECK + { + if (docalc2) { + uae_u16 out = yuvtorgb(y1, u, v); + outval2 = p96_rgbx16p[out]; + docalc2 = false; + } + ((uae_u16*)dst2)[dx] = outval2; + } + } + sx += sxadd; + dx++; + } + } + break; + + case RGBFB_Y4U1V1_16: + { + while (sx < endx) { + x = sx >> 8; + uae_u32 val = ((uae_u32*)src2)[x]; + uae_u8 y0 = ((val >> 12) & 31) * 8; + uae_u8 y1 = ((val >> 17) & 31) * 8; + uae_u8 y2 = ((val >> 22) & 31) * 8; + uae_u8 y3 = ((val >> 27) & 31) * 8; + uae_s8 u = ((val >> 0) & 63) * 4; + uae_s8 v = ((val >> 6) & 63) * 4; + int fr = sx & 255; + if (fr >= 192) { + CKCHECK + { + uae_u16 out = yuvtorgb(y3, u, v); + ((uae_u16*)dst2)[dx] = p96_rgbx16p[out]; + } + } else if (fr >= 128) { + CKCHECK + { + uae_u16 out = yuvtorgb(y2, u, v); + ((uae_u16*)dst2)[dx] = p96_rgbx16p[out]; + } + } else if (fr >= 64) { + CKCHECK + { + uae_u16 out = yuvtorgb(y1, u, v); + ((uae_u16*)dst2)[dx] = p96_rgbx16p[out]; + } + } else { + CKCHECK + { + uae_u16 out = yuvtorgb(y0, u, v); + ((uae_u16*)dst2)[dx] = p96_rgbx16p[out]; + } + } + sx += sxadd; + dx++; + } + } + break; + + } +} + +void fb_copyrow(uae_u8 *src, uae_u8 *dst, int x, int y, int width, int srcpixbytes, int dy) +{ + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + struct picasso96_state_struct *state = &picasso96_state; + copyrow(src, dst, x, y, width, 0, srcpixbytes, + x, dy, picasso_vidinfo.rowbytes, picasso_vidinfo.pixbytes, + state->RGBFormat == vidinfo->host_mode, vidinfo->picasso_convert, p96_rgbx16); +} + +static void copyallinvert(uae_u8 *src, uae_u8 *dst, int pwidth, int pheight, int srcbytesperrow, int srcpixbytes, int dstbytesperrow, int dstpixbytes, bool direct, int mode_convert) +{ + int x, y, w; + + w = pwidth * dstpixbytes; + if (direct) { + for (y = 0; y < pheight; y++) { + for (x = 0; x < w; x++) + dst[x] = src[x] ^ 0xff; + dst += dstbytesperrow; + src += srcbytesperrow; + } + } else { + uae_u8 *src2 = src; + for (y = 0; y < pheight; y++) { + for (x = 0; x < w; x++) + src2[x] ^= 0xff; + copyrow(src, dst, 0, y, pwidth, srcbytesperrow, srcpixbytes, 0, y, dstbytesperrow, dstpixbytes, direct, mode_convert, p96_rgbx16); + for (x = 0; x < w; x++) + src2[x] ^= 0xff; + src2 += srcbytesperrow; + } + } +} + +static void copyall (uae_u8 *src, uae_u8 *dst, int pwidth, int pheight, int srcbytesperrow, int srcpixbytes, int dstbytesperrow, int dstpixbytes, bool direct, int mode_convert) +{ + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; int y, bytes; if (direct) { - auto w = pwidth * picasso_vidinfo.pixbytes; + auto w = pwidth * vidinfo->pixbytes; for (y = 0; y < pheight; y++) { memcpy(dst, src, w); @@ -3478,86 +3833,109 @@ static void copyall(uae_u8* src, uae_u8* dst, int pwidth, int pheight, int srcby else { for (y = 0; y < pheight; y++) - copyrow(src, dst, 0, y, pwidth, srcbytesperrow, srcpixbytes, y, dstbytesperrow, dstpixbytes, direct, - mode_convert); + copyrow (src, dst, 0, y, pwidth, srcbytesperrow, srcpixbytes, 0, y, dstbytesperrow, dstpixbytes, direct, mode_convert, p96_rgbx16); } - - //else if (picasso96_state.RGBFormat == RGBFB_R5G6B5 - // || picasso96_state.RGBFormat == RGBFB_R5G6B5PC) { - // bytes = picasso96_state.Width * picasso96_state.Height * 2; - // for (auto i = 0; i < bytes; i += 4) { - // *reinterpret_cast(dst + i) = - // bswap_16(*reinterpret_cast(src + i + 2)) << 16 | - // bswap_16(*reinterpret_cast(src + i)); - // } - //} - //else if (picasso96_state.RGBFormat == RGBFB_CLUT) - //{ - // bytes = picasso96_state.Width * picasso96_state.Height; - // for (auto i = 0; i < bytes; ++i) { - // *reinterpret_cast(dst + (i << 1)) = - // picasso96_state.CLUT[(*static_cast(src + i))].Red >> 3 << 11 | - // picasso96_state.CLUT[(*static_cast(src + i))].Green >> 2 << 5 | - // picasso96_state.CLUT[(*static_cast(src + i))].Blue >> 3; - // } - //} } -bool picasso_flushpixels(uae_u8* src, int off) +uae_u8 *getrtgbuffer(int *widthp, int *heightp, int *pitch, int *depth, uae_u8 *palette) { + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + struct picasso96_state_struct *state = &picasso96_state; + uae_u8 *src = gfxmem_bank.start + regs.natmem_offset; + int off = state->XYOffset - gfxmem_bank.start; + int width, height, pixbytes; + uae_u8 *dst; + int convert; + int hmode; + + if (!vidinfo->extra_mem) + return NULL; + + width = state->VirtualWidth; + height = state->VirtualHeight; + pixbytes = state->BytesPerPixel == 1 && palette ? 1 : 4; + if (!width || !height || !pixbytes) + return NULL; + + dst = xmalloc (uae_u8, width * height * pixbytes); + if (!dst) + return NULL; + hmode = pixbytes == 1 ? RGBFB_CLUT : RGBFB_B8G8R8A8; + convert = getconvert (state->RGBFormat, pixbytes); + alloc_colors_picasso(8, 8, 8, 16, 8, 0, state->RGBFormat, p96_rgbx16); + + if (pixbytes > 1 && hmode != convert) { + copyall (src + off, dst, width, height, state->BytesPerRow, state->BytesPerPixel, width * pixbytes, pixbytes, false, convert); + } else { + uae_u8 *dstp = dst; + uae_u8 *srcp = src; + for (int y = 0; y < height; y++) { + memcpy (dstp, srcp, width * pixbytes); + dstp += width * pixbytes; + srcp += state->BytesPerRow; + } + } + if (pixbytes == 1) { + for (int i = 0; i < 256; i++) { + palette[i * 3 + 0] = state->CLUT[i].Red; + palette[i * 3 + 1] = state->CLUT[i].Green; + palette[i * 3 + 2] = state->CLUT[i].Blue; + } + } + + gfx_set_picasso_colors(state->RGBFormat); + + *widthp = width; + *heightp = height; + *pitch = width * pixbytes; + *depth = pixbytes * 8; + + return dst; +} +void freertgbuffer(uae_u8 *dst) +{ + xfree (dst); +} + +void picasso_invalidate(int x, int y, int w, int h) +{ + +} + +static bool picasso_flushpixels (uae_u8 *src, int off) +{ + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + struct picasso96_state_struct *state = &picasso96_state; uae_u8* src_start; uae_u8* src_end; uae_u8* dst = nullptr; - int pwidth = picasso96_state.Width > picasso96_state.VirtualWidth - ? picasso96_state.VirtualWidth - : picasso96_state.Width; - int pheight = picasso96_state.Height > picasso96_state.VirtualHeight - ? picasso96_state.VirtualHeight - : picasso96_state.Height; + int pwidth = state->Width > state->VirtualWidth ? state->VirtualWidth : state->Width; + int pheight = state->Height > state->VirtualHeight ? state->VirtualHeight : state->Height; src_start = src + off; - src_end = src + off + picasso96_state.BytesPerRow * pheight - 1; - if (!picasso_vidinfo.extra_mem || src_start >= src_end) - { + src_end = src + off + state->BytesPerRow * pheight - 1; + if (!vidinfo->extra_mem || src_start >= src_end) { return false; } - if (picasso_vidinfo.full_refresh || picasso_vidinfo.rtg_clear_flag) - picasso_vidinfo.full_refresh = -1; + dst = gfx_lock_picasso(); + if (dst == nullptr) + return false; - for (;;) - { - if (doskip()) - break; + copyall(src + off, dst, pwidth, pheight, + state->BytesPerRow, state->BytesPerPixel, + vidinfo->rowbytes, vidinfo->pixbytes, + state->RGBFormat == vidinfo->host_mode, vidinfo->picasso_convert); - dst = gfx_lock_picasso(); - if (dst == nullptr) - return false; - - if (doskip()) - break; - - //copyall(src + off, dst); - copyall(src + off, dst, pwidth, pheight, - picasso96_state.BytesPerRow, picasso96_state.BytesPerPixel, - picasso_vidinfo.rowbytes, picasso_vidinfo.pixbytes, - picasso96_state.RGBFormat == picasso_vidinfo.host_mode, picasso_vidinfo.picasso_convert); - break; - } if (currprefs.leds_on_screen) picasso_statusline(dst); gfx_unlock_picasso(true); - if (dst) - { - picasso_vidinfo.full_refresh = 0; - } - return true; } -static void* render_thread(void* v) +static int render_thread(void* v) { render_thread_state = 1; for (;;) { @@ -3565,33 +3943,27 @@ static void* render_thread(void* v) if (idx == -1) break; idx &= 0xff; - //int monid = currprefs.rtgboards[idx].monitor_id; - //struct amigadisplay *ad = &adisplays[monid]; - if (picasso_on && picasso_requested_on) - { - //lockrtg(); - if (picasso_requested_on) - { - //struct picasso96_state_struct *state = &picasso96_state[monid]; - picasso_flushpixels(gfxmem_banks[idx]->start + regs.natmem_offset, - picasso96_state.XYOffset - gfxmem_banks[idx]->start); - pending_render = true; + + struct amigadisplay *ad = &adisplays; + if (ad->picasso_on && ad->picasso_requested_on) { + if (ad->picasso_requested_on) { + struct picasso96_state_struct *state = &picasso96_state; + picasso_flushpixels(gfxmem_banks[idx]->start + regs.natmem_offset, state->XYOffset - gfxmem_banks[idx]->start); + ad->pending_render = true; } - //unlockrtg(); } } render_thread_state = -1; - return nullptr; + return 0; } extern addrbank gfxmem_bank; MEMORY_FUNCTIONS(gfxmem); - addrbank gfxmem_bank = { gfxmem_lget, gfxmem_wget, gfxmem_bget, gfxmem_lput, gfxmem_wput, gfxmem_bput, gfxmem_xlate, gfxmem_check, nullptr, nullptr, _T("RTG RAM"), - dummy_lgeti, dummy_wgeti, + dummy_wgeti, ABFLAG_RAM | ABFLAG_RTG, 0, 0 }; addrbank* gfxmem_banks[MAX_RTG_BOARDS]; @@ -3599,14 +3971,17 @@ addrbank* gfxmem_banks[MAX_RTG_BOARDS]; /* Call this function first, near the beginning of code flow * Place in InitGraphics() which seems reasonable... * Also put it in reset_drawing() for safe-keeping. */ -void InitPicasso96(void) +void InitPicasso96() { + struct picasso96_state_struct *state = &picasso96_state; + int i; + gfxmem_banks[0] = &gfxmem_bank; //fastscreen oldscr = 0; //fastscreen - memset(&picasso96_state, 0, sizeof(struct picasso96_state_struct)); + memset (state, 0, sizeof (struct picasso96_state_struct)); for (int i = 0; i < 256; i++) { @@ -3699,7 +4074,7 @@ static uae_u32 REGPARAM2 picasso_SetMemoryMode(TrapContext* ctx) #define PUTABI(func) \ if (ABI) \ - trap_put_long(ctx, ABI + func, here ()); + trap_put_long(ctx, ABI + func, here ()); #define RTGCALL(func,funcdef,call) \ PUTABI (func); \ @@ -3723,15 +4098,9 @@ static uae_u32 REGPARAM2 picasso_SetMemoryMode(TrapContext* ctx) dw (funcdef); \ dw (RTS); -#define RTGCALLONLYDEFAULT(func,funcdef,unused) \ - PUTABI (func); \ - dw (0x2f28); \ - dw (funcdef); \ - dw (RTS); - #define RTGNONE(func) \ if (ABI) \ - trap_put_long(ctx, ABI + func, start); + trap_put_long(ctx, ABI + func, start); static void inituaegfxfuncs(TrapContext* ctx, uaecptr start, uaecptr ABI) { @@ -3779,7 +4148,7 @@ rts */ PUTABI(PSSO_BoardInfo_GetCompatibleFormats); dw(0x203c); - dl(RGBMASK_8BIT | RGBMASK_15BIT | RGBMASK_16BIT | RGBMASK_24BIT | RGBMASK_32BIT); + dl (RGBMASK_8BIT | RGBMASK_15BIT | RGBMASK_16BIT | RGBMASK_24BIT | RGBMASK_32BIT); dw(RTS); /* CalculateBytesPerRow (optimized) */ @@ -3847,18 +4216,18 @@ rts RTGCALL2(PSSO_BoardInfo_SetInterrupt, picasso_SetInterrupt); - write_log(_T("uaegfx.card magic code: %08X-%08X ABI=%08X\n"), start, here(), ABI); + write_log (_T("uaegfx.card magic code: %08X-%08X BI=%08X\n"), start, here (), ABI); if (ABI) initvblankABI(ctx, uaegfx_base, ABI); } -void picasso_reset(void) +static void picasso_reset(int hardreset) { - if (currprefs.rtg_multithread) - { - if (!render_pipe) - { + struct picasso96_state_struct *state = &picasso96_state; + if (currprefs.rtg_multithread) { + if (!render_pipe) { + //InitializeCriticalSection(&render_cs); render_pipe = xmalloc(smp_comm_pipe, 1); init_comm_pipe(render_pipe, 10, 1); } @@ -3869,18 +4238,29 @@ void picasso_reset(void) } } - if (savestate_state != STATE_RESTORE) - { + if (savestate_state != STATE_RESTORE) { uaegfx_base = 0; uaegfx_old = 0; uaegfx_active = 0; interrupt_enabled = 0; reserved_gfxmem = 0; - resetpalette(); + resetpalette(state); InitPicasso96(); } - picasso_requested_on = false; + struct amigadisplay *ad = &adisplays; + ad->picasso_requested_on = false; +} + +static void picasso_free(void) +{ + if (render_thread_state > 0) { + write_comm_pipe_int(render_pipe, -1, 0); + while (render_thread_state >= 0) { + Sleep(10); + } + render_thread_state = 0; + } } void uaegfx_install_code(uaecptr start) @@ -3888,10 +4268,13 @@ void uaegfx_install_code(uaecptr start) uaegfx_rom = start; org(start); inituaegfxfuncs(nullptr, start, 0); + + device_add_reset(picasso_reset); + device_add_exit(picasso_free); } #define UAEGFX_VERSION 3 -#define UAEGFX_REVISION 3 +#define UAEGFX_REVISION 4 static uae_u32 REGPARAM2 gfx_open(TrapContext* ctx) { @@ -3920,7 +4303,7 @@ static uaecptr uaegfx_card_install(TrapContext* ctx, uae_u32 extrasize) if (uaegfx_old || !gfxmem_bank.start) return 0; - uaegfx_resid = ds(_T("UAE Graphics Card 3.3")); + uaegfx_resid = ds (_T("UAE Graphics Card 3.4")); uaegfx_vblankname = ds(_T("UAE Graphics Card VBLANK")); uaegfx_portsname = ds(_T("UAE Graphics Card PORTS")); @@ -4055,32 +4438,28 @@ uae_u32 picasso_demux(uae_u32 arg, TrapContext* ctx) return 0; } -void picasso_free(void) -{ - if (render_thread_state > 0) { - write_comm_pipe_int(render_pipe, -1, 0); - while (render_thread_state >= 0) { - Sleep(10); - } - render_thread_state = 0; - } -} - static uae_u32 p96_restored_flags; void restore_p96_finish(void) { - init_alloc(nullptr, 0); + struct amigadisplay *ad = &adisplays; + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; + + init_alloc (NULL, 0); if (uaegfx_rom && boardinfo) { - inituaegfxfuncs(nullptr, uaegfx_rom, boardinfo); - picasso_requested_on = !!(p96_restored_flags & 1); - picasso_vidinfo.picasso_active = picasso_requested_on; + inituaegfxfuncs(NULL, uaegfx_rom, boardinfo); + ad->picasso_requested_on = !!(p96_restored_flags & 1); + vidinfo->picasso_active = ad->picasso_requested_on; set_config_changed(); } } uae_u8* restore_p96(uae_u8* src) { + struct amigadisplay *ad = &adisplays; + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u32 flags; int i; @@ -4088,44 +4467,44 @@ uae_u8* restore_p96(uae_u8* src) return src; InitPicasso96(); p96_restored_flags = flags = restore_u32(); - picasso_requested_on = !!(flags & 1); init_picasso_screen_called = 0; set_gc_called = !!(flags & 2); - picasso_vidinfo.set_panning_called = !!(flags & 4); + vidinfo->set_panning_called = !!(flags & 4); interrupt_enabled = !!(flags & 32); changed_prefs.rtgboards[0].rtgmem_size = restore_u32(); - picasso96_state.Address = restore_u32(); - picasso96_state.RGBFormat = (RGBFTYPE)restore_u32(); - picasso96_state.Width = restore_u16(); - picasso96_state.Height = restore_u16(); - picasso96_state.VirtualWidth = restore_u16(); - picasso96_state.VirtualHeight = restore_u16(); - picasso96_state.XOffset = restore_u16(); - picasso96_state.YOffset = restore_u16(); - picasso96_state.GC_Depth = restore_u8(); - picasso96_state.GC_Flags = restore_u8(); - picasso96_state.BytesPerRow = restore_u16(); - picasso96_state.BytesPerPixel = restore_u8(); + state->Address = restore_u32 (); + state->RGBFormat = (RGBFTYPE)restore_u32 (); + state->Width = restore_u16 (); + state->Height = restore_u16 (); + state->VirtualWidth = restore_u16 (); + state->VirtualHeight = restore_u16 (); + state->XOffset = restore_u16 (); + state->YOffset = restore_u16 (); + state->GC_Depth = restore_u8 (); + state->GC_Flags = restore_u8 (); + state->BytesPerRow = restore_u16 (); + state->BytesPerPixel = restore_u8 (); uaegfx_base = restore_u32(); uaegfx_rom = restore_u32(); boardinfo = restore_u32(); - if (flags & 64) - { - for (i = 0; i < 256; i++) - { - picasso96_state.CLUT[i].Red = restore_u8(); - picasso96_state.CLUT[i].Green = restore_u8(); - picasso96_state.CLUT[i].Blue = restore_u8(); + if (flags & 64) { + for (i = 0; i < 256; i++) { + state->CLUT[i].Red = restore_u8 (); + state->CLUT[i].Green = restore_u8 (); + state->CLUT[i].Blue = restore_u8 (); } } - picasso96_state.HostAddress = nullptr; - picasso_SetPanningInit(); - picasso96_state.Extent = picasso96_state.Address + picasso96_state.BytesPerRow * picasso96_state.VirtualHeight; + state->HostAddress = NULL; + picasso_SetPanningInit(state); + state->Extent = state->Address + state->BytesPerRow * state->VirtualHeight; return src; } uae_u8* save_p96(int* len, uae_u8* dstptr) { + struct amigadisplay *ad = &adisplays; + struct picasso96_state_struct *state = &picasso96_state; + struct picasso_vidbuf_description *vidinfo = &picasso_vidinfo; uae_u8 *dstbak, *dst; int i; @@ -4134,31 +4513,30 @@ uae_u8* save_p96(int* len, uae_u8* dstptr) if (dstptr) dstbak = dst = dstptr; else - dstbak = dst = xmalloc(uae_u8, 1000); + dstbak = dst = xmalloc (uae_u8, 1000); save_u32(2); - save_u32((picasso_on ? 1 : 0) | (set_gc_called ? 2 : 0) | (picasso_vidinfo.set_panning_called ? 4 : 0) | - (interrupt_enabled ? 32 : 0) | 64); + save_u32 ((ad->picasso_on ? 1 : 0) | (set_gc_called ? 2 : 0) | (vidinfo->set_panning_called ? 4 : 0) | + (interrupt_enabled ? 32 : 0) | 64); save_u32(currprefs.rtgboards[0].rtgmem_size); - save_u32(picasso96_state.Address); - save_u32(picasso96_state.RGBFormat); - save_u16(picasso96_state.Width); - save_u16(picasso96_state.Height); - save_u16(picasso96_state.VirtualWidth); - save_u16(picasso96_state.VirtualHeight); - save_u16(picasso96_state.XOffset); - save_u16(picasso96_state.YOffset); - save_u8(picasso96_state.GC_Depth); - save_u8(picasso96_state.GC_Flags); - save_u16(picasso96_state.BytesPerRow); - save_u8(picasso96_state.BytesPerPixel); + save_u32 (state->Address); + save_u32 (state->RGBFormat); + save_u16 (state->Width); + save_u16 (state->Height); + save_u16 (state->VirtualWidth); + save_u16 (state->VirtualHeight); + save_u16 (state->XOffset); + save_u16 (state->YOffset); + save_u8 (state->GC_Depth); + save_u8 (state->GC_Flags); + save_u16 (state->BytesPerRow); + save_u8 (state->BytesPerPixel); save_u32(uaegfx_base); save_u32(uaegfx_rom); save_u32(boardinfo); - for (i = 0; i < 256; i++) - { - save_u8(picasso96_state.CLUT[i].Red); - save_u8(picasso96_state.CLUT[i].Green); - save_u8(picasso96_state.CLUT[i].Blue); + for (i = 0; i < 256; i++) { + save_u8 (state->CLUT[i].Red); + save_u8 (state->CLUT[i].Green); + save_u8 (state->CLUT[i].Blue); } *len = dst - dstbak; return dstbak; diff --git a/src/osdep/picasso96.h b/src/osdep/picasso96.h index e69603e4..d3af0ab9 100644 --- a/src/osdep/picasso96.h +++ b/src/osdep/picasso96.h @@ -171,31 +171,16 @@ struct CLUTEntry { struct BitMap { - uae_u16 BytesPerRow; - uae_u16 Rows; - uae_u8 Flags; - uae_u8 Depth; - uae_u16 pad; - uae_u8 *Planes[8]; - uaecptr APlanes[8]; + uae_u16 BytesPerRow; + uae_u16 Rows; + uae_u8 Flags; + uae_u8 Depth; + uae_u16 pad; + uae_u8* Planes[8]; }; /************************************************************************/ -#define SETTINGSNAMEMAXCHARS 30 -#define BOARDNAMEMAXCHARS 30 - -struct Settings { - uae_u32 BoardType; - /* a value describing assignment to nth board local to boardtype - * to be used for reassignment when boards are added or removed. */ - uae_u16 LocalOrdering; - uae_s16 LastSelected; - char NameField[SETTINGSNAMEMAXCHARS]; - /* neu! */ - char *BoardName; -}; - #define MAXRESOLUTIONNAMELENGTH 22 /******************************** @@ -348,6 +333,82 @@ struct Line { #define PSSO_BitMapExtra_CompanionMaster 50 #define PSSO_BitMapExtra_Last 54 +enum { + SFT_INVALID, SFT_FLICKERFIXER, SFT_VIDEOCAPTURE, SFT_VIDEOWINDOW, SFT_MEMORYWINDOW +}; + +#ifndef TAG_USER +#define TAG_USER 0x80000000 +#endif +#define FA_Restore (TAG_USER+0) +#define FA_Onboard (TAG_USER+1) +#define FA_Active (TAG_USER+2) +#define FA_Left (TAG_USER+3) +#define FA_Top (TAG_USER+4) +#define FA_Width (TAG_USER+5) +#define FA_Height (TAG_USER+6) +#define FA_Format (TAG_USER+7) +#define FA_Color (TAG_USER+8) +#define FA_Occlusion (TAG_USER+9) +#define FA_SourceWidth (TAG_USER+10) +#define FA_SourceHeight (TAG_USER+11) +#define FA_MinWidth (TAG_USER+12) +#define FA_MinHeight (TAG_USER+13) +#define FA_MaxWidth (TAG_USER+14) +#define FA_MaxHeight (TAG_USER+15) +#define FA_Interlace (TAG_USER+16) +#define FA_PAL (TAG_USER+17) +#define FA_BitMap (TAG_USER+18) +#define FA_Brightness (TAG_USER+19) +#define FA_ModeInfo (TAG_USER+20) +#define FA_ModeFormat (TAG_USER+21) +#define FA_Colors (TAG_USER+22) +#define FA_Colors32 (TAG_USER+23) +#define FA_NoMemory (TAG_USER+24) +#define FA_RenderFunc (TAG_USER+25) +#define FA_SaveFunc (TAG_USER+26) +#define FA_UserData (TAG_USER+27) +#define FA_Alignment (TAG_USER+28) +#define FA_ConstantBytesPerRow (TAG_USER+29) +#define FA_DoubleBuffer (TAG_USER+30) +#define FA_Pen (TAG_USER+31) +#define FA_ModeMemorySize (TAG_USER+32) +#define FA_ClipLeft (TAG_USER+33) +#define FA_ClipTop (TAG_USER+34) +#define FA_ClipWidth (TAG_USER+35) +#define FA_ClipHeight (TAG_USER+36) +#define FA_ConstantByteSwapping (TAG_USER+37) + +#define GBMA_MEMORY (TAG_USER+0) +#define GBMA_BASEMEMORY (TAG_USER+1) +#define GBMA_BYTESPERROW (TAG_USER+2) +#define GBMA_BYTESPERPIXEL (TAG_USER+3) +#define GBMA_BITSPERPIXEL (TAG_USER+4) +#define GBMA_RGBFORMAT (TAG_USER+6) +#define GBMA_WIDTH (TAG_USER+7) +#define GBMA_HEIGHT (TAG_USER+8) +#define GBMA_DEPTH (TAG_USER+9) + +#define ABMA_Friend (TAG_USER+0) +#define ABMA_Depth (TAG_USER+1) +#define ABMA_RGBFormat (TAG_USER+2) +#define ABMA_Clear (TAG_USER+3) +#define ABMA_Displayable (TAG_USER+4) +#define ABMA_Visible (TAG_USER+5) +#define ABMA_NoMemory (TAG_USER+6) +#define ABMA_NoSprite (TAG_USER+7) +#define ABMA_Colors (TAG_USER+8) +#define ABMA_Colors32 (TAG_USER+9) +#define ABMA_ModeWidth (TAG_USER+10) +#define ABMA_ModeHeight (TAG_USER+11) +#define ABMA_RenderFunc (TAG_USER+12) +#define ABMA_SaveFunc (TAG_USER+13) +#define ABMA_UserData (TAG_USER+14) +#define ABMA_Alignment (TAG_USER+15) +#define ABMA_ConstantBytesPerRow (TAG_USER+16) +#define ABMA_UserPrivate (TAG_USER+17) +#define ABMA_ConstantByteSwapping (TAG_USER+18) + #define PSSO_BoardInfo_RegisterBase 0 #define PSSO_BoardInfo_MemoryBase PSSO_BoardInfo_RegisterBase + 4 #define PSSO_BoardInfo_MemoryIOBase PSSO_BoardInfo_MemoryBase + 4 @@ -507,53 +568,57 @@ struct Line { /* BoardInfo flags */ /* 0-15: hardware flags */ /* 16-31: user flags */ -#define BIB_HARDWARESPRITE 0 /* board has hardware sprite */ -#define BIB_NOMEMORYMODEMIX 1 /* board does not support modifying planar bitmaps while displaying chunky and vice versa */ -#define BIB_NEEDSALIGNMENT 2 /* bitmaps have to be aligned (not yet supported!) */ -#define BIB_CACHEMODECHANGE 3 /* board memory may be set to Imprecise (060) or Nonserialised (040) */ -#define BIB_VBLANKINTERRUPT 4 /* board can cause a hardware interrupt on a vertical retrace */ +#define BIB_HARDWARESPRITE 0 /* board has hardware sprite */ +#define BIB_NOMEMORYMODEMIX 1 /* board does not support modifying planar bitmaps while displaying chunky and vice versa */ +#define BIB_NEEDSALIGNMENT 2 /* bitmaps have to be aligned (not yet supported!) */ +#define BIB_CACHEMODECHANGE 3 /* board memory may be set to Imprecise (060) or Nonserialised (040) */ +#define BIB_VBLANKINTERRUPT 4 /* board can cause a hardware interrupt on a vertical retrace */ #define BIB_DBLSCANDBLSPRITEY 8 /* hardware sprite y position is doubled on doublescan display modes */ #define BIB_ILACEHALFSPRITEY 9 /* hardware sprite y position is halved on interlace display modes */ #define BIB_ILACEDBLROWOFFSET 10 /* doubled row offset in interlaced display modes needs additional horizontal bit */ -#define BIB_FLICKERFIXER 12 /* board can flicker fix Amiga RGB signal */ -#define BIB_VIDEOCAPTURE 13 /* board can capture video data to a memory area */ -#define BIB_VIDEOWINDOW 14 /* board can display a second mem area as a pip */ -#define BIB_BLITTER 15 /* board has blitter */ -#define BIB_HIRESSPRITE 16 /* mouse sprite has double resolution */ -#define BIB_BIGSPRITE 17 /* user wants big mouse sprite */ -#define BIB_BORDEROVERRIDE 18 /* user wants to override system overscan border prefs */ -#define BIB_BORDERBLANK 19 /* user wants border blanking */ -#define BIB_INDISPLAYCHAIN 20 /* board switches Amiga signal */ -#define BIB_QUIET 21 /* not yet implemented */ -#define BIB_NOMASKBLITS 22 /* perform blits without taking care of mask */ -#define BIB_NOC2PBLITS 23 /* use CPU for planar to chunky conversions */ -#define BIB_NOBLITTER 24 /* disable all blitter functions */ -#define BIB_OVERCLOCK 31 /* enable overclocking for some boards */ +#define BIB_FLICKERFIXER 12 /* board can flicker fix Amiga RGB signal */ +#define BIB_VIDEOCAPTURE 13 /* board can capture video data to a memory area */ +#define BIB_VIDEOWINDOW 14 /* board can display a second mem area as a pip */ +#define BIB_BLITTER 15 /* board has blitter */ +#define BIB_HIRESSPRITE 16 /* mouse sprite has double resolution */ +#define BIB_BIGSPRITE 17 /* user wants big mouse sprite */ +#define BIB_BORDEROVERRIDE 18 /* user wants to override system overscan border prefs */ +#define BIB_BORDERBLANK 19 /* user wants border blanking */ +#define BIB_INDISPLAYCHAIN 20 /* board switches Amiga signal */ +#define BIB_QUIET 21 /* not yet implemented */ +#define BIB_NOMASKBLITS 22 /* perform blits without taking care of mask */ +#define BIB_NOC2PBLITS 23 /* use CPU for planar to chunky conversions */ +#define BIB_NOBLITTER 24 /* disable all blitter functions */ +#define BIB_SYSTEM2SCREENBLITS 25 /* allow data to be written to screen memory for cpu as blitter source */ +#define BIB_GRANTDIRECTACCESS 26 /* all data on the board can be accessed at any time without bi->SetMemoryMode() */ +#define BIB_OVERCLOCK 31 /* enable overclocking for some boards */ #define BIB_IGNOREMASK BIB_NOMASKBLITS -#define BIF_HARDWARESPRITE (1 << BIB_HARDWARESPRITE) -#define BIF_NOMEMORYMODEMIX (1 << BIB_NOMEMORYMODEMIX) -#define BIF_NEEDSALIGNMENT (1 << BIB_NEEDSALIGNMENT) -#define BIF_CACHEMODECHANGE (1 << BIB_CACHEMODECHANGE) -#define BIF_VBLANKINTERRUPT (1 << BIB_VBLANKINTERRUPT) +#define BIF_HARDWARESPRITE (1 << BIB_HARDWARESPRITE) +#define BIF_NOMEMORYMODEMIX (1 << BIB_NOMEMORYMODEMIX) +#define BIF_NEEDSALIGNMENT (1 << BIB_NEEDSALIGNMENT) +#define BIF_CACHEMODECHANGE (1 << BIB_CACHEMODECHANGE) +#define BIF_VBLANKINTERRUPT (1 << BIB_VBLANKINTERRUPT) #define BIF_DBLSCANDBLSPRITEY (1 << BIB_DBLSCANDBLSPRITEY) #define BIF_ILACEHALFSPRITEY (1 << BIB_ILACEHALFSPRITEY) #define BIF_ILACEDBLROWOFFSET (1 << BIB_ILACEDBLROWOFFSET) -#define BIF_FLICKERFIXER (1 << BIB_FLICKERFIXER) -#define BIF_VIDEOCAPTURE (1 << BIB_VIDEOCAPTURE) -#define BIF_VIDEOWINDOW (1 << BIB_VIDEOWINDOW) -#define BIF_BLITTER (1 << BIB_BLITTER) -#define BIF_HIRESSPRITE (1 << BIB_HIRESSPRITE) -#define BIF_BIGSPRITE (1 << BIB_BIGSPRITE) -#define BIF_BORDEROVERRIDE (1 << BIB_BORDEROVERRIDE) -#define BIF_BORDERBLANK (1 << BIB_BORDERBLANK) -#define BIF_INDISPLAYCHAIN (1 << BIB_INDISPLAYCHAIN) -#define BIF_QUIET (1 << BIB_QUIET) -#define BIF_NOMASKBLITS (1 << BIB_NOMASKBLITS) -#define BIF_NOC2PBLITS (1 << BIB_NOC2PBLITS) -#define BIF_NOBLITTER (1 << BIB_NOBLITTER) -#define BIF_OVERCLOCK (1 << BIB_OVERCLOCK) +#define BIF_FLICKERFIXER (1 << BIB_FLICKERFIXER) +#define BIF_VIDEOCAPTURE (1 << BIB_VIDEOCAPTURE) +#define BIF_VIDEOWINDOW (1 << BIB_VIDEOWINDOW) +#define BIF_BLITTER (1 << BIB_BLITTER) +#define BIF_HIRESSPRITE (1 << BIB_HIRESSPRITE) +#define BIF_BIGSPRITE (1 << BIB_BIGSPRITE) +#define BIF_BORDEROVERRIDE (1 << BIB_BORDEROVERRIDE) +#define BIF_BORDERBLANK (1 << BIB_BORDERBLANK) +#define BIF_INDISPLAYCHAIN (1 << BIB_INDISPLAYCHAIN) +#define BIF_QUIET (1 << BIB_QUIET) +#define BIF_NOMASKBLITS (1 << BIB_NOMASKBLITS) +#define BIF_NOC2PBLITS (1 << BIB_NOC2PBLITS) +#define BIF_NOBLITTER (1 << BIB_NOBLITTER) +#define BIF_SYSTEM2SCREENBLITS (1 << BIB_SYSTEM2SCREENBLITS) +#define BIF_GRANTDIRECTACCESS (1 << BIB_GRANTDIRECTACCESS) +#define BIF_OVERCLOCK (1 << BIB_OVERCLOCK) #define BIF_IGNOREMASK BIF_NOMASKBLITS @@ -589,22 +654,14 @@ struct picasso96_state_struct extern void InitPicasso96 (void); -extern int uaegfx_card_found; extern bool picasso_rendered; extern struct picasso96_state_struct picasso96_state; extern void picasso_enablescreen (int on); extern void picasso_refresh (void); -extern void init_hz_p96 (void); -extern void picasso_handle_hsync(void); extern void picasso_handle_vsync (void); -extern void picasso_trigger_vblank (void); -extern void picasso_reset (void); -extern bool picasso_is_active (void); -extern int picasso_palette (struct MyCLUTEntry *CLUT); -extern bool picasso_flushpixels (uae_u8 *src, int offset); -extern void picasso_free(void); +extern int picasso_palette (struct MyCLUTEntry *CLUT, uae_u32 *clut); /* This structure describes the UAE-side framebuffer for the Picasso * screen. */ @@ -629,13 +686,10 @@ extern struct picasso_vidbuf_description picasso_vidinfo; extern void gfx_set_picasso_modeinfo (uae_u32 w, uae_u32 h, uae_u32 d, RGBFTYPE rgbfmt); extern void gfx_set_picasso_colors(RGBFTYPE rgbfmt); -extern void gfx_set_picasso_baseaddr (uaecptr); extern void gfx_set_picasso_state (int on); extern uae_u8 *gfx_lock_picasso (void); extern void gfx_unlock_picasso (bool); -extern int p96refresh_active; - #define LIB_SIZE 34 #define CARD_FLAGS LIB_SIZE #define CARD_EXECBASE (CARD_FLAGS + 2) @@ -658,14 +712,9 @@ extern int p96refresh_active; #ifdef __cplusplus extern "C" { #endif -void copy_screen_8bit(uae_u8 *dst, uae_u8 *src, int bytes, uae_u32 *clut); -#ifdef USE_ARMNEON -void copy_screen_16bit_swap(uae_u8 *dst, uae_u8 *src, int bytes); -void copy_screen_32bit_to_16bit_neon(uae_u8 *dst, uae_u8 *src, int bytes); -#else -void copy_screen_16bit_swap_arm(uae_u8 *dst, uae_u8 *src, int bytes); -void copy_screen_32bit_to_16bit_arm(uae_u8 *dst, uae_u8 *src, int bytes); -#endif + void copy_screen_8bit(uae_u8 *dst, uae_u8 *src, int bytes, uae_u32 *clut); + void copy_screen_16bit_swap(uae_u8 *dst, uae_u8 *src, int bytes); + void copy_screen_32bit_to_16bit(uae_u8 *dst, uae_u8 *src, int bytes); #ifdef __cplusplus } #endif diff --git a/src/osdep/sigsegv_handler.cpp b/src/osdep/sigsegv_handler.cpp index 7f8663d2..8946b1ef 100644 --- a/src/osdep/sigsegv_handler.cpp +++ b/src/osdep/sigsegv_handler.cpp @@ -23,92 +23,452 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * */ -#include -#include #include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "include/memory.h" #include "newcpu.h" +#include "custom.h" +#ifdef JIT +#include "jit/comptbl.h" #include "jit/compemu.h" +#endif #include "uae.h" #include -#include +#include #include -#ifndef ANDROID #include -#else -int backtrace(void**,int){ return 0; } -char** backtrace_symbols(void* const*,int){return NULL; } -void backtrace_symbols_fd(void* const*,int,int){} -#endif +#include +#ifdef JIT extern uae_u8* current_compile_p; extern uae_u8* compiled_code; -extern uae_u8* popallspace; +extern uae_u8 *popallspace; extern blockinfo* active; extern blockinfo* dormant; extern void invalidate_block(blockinfo* bi); extern void raise_in_cl_list(blockinfo* bi); -extern bool write_logfile; +#endif + #define SHOW_DETAILS 2 +#ifdef WITH_LOGGING #define output_log write_log +#else +#define output_log +#endif -enum transfer_type_t -{ + +enum transfer_type_t { TYPE_UNKNOWN, TYPE_LOAD, TYPE_STORE }; -enum type_size_t -{ +enum type_size_t { SIZE_UNKNOWN, SIZE_BYTE, SIZE_WORD, SIZE_INT }; -enum style_type_t -{ - STYLE_SIGNED, - STYLE_UNSIGNED +enum style_type_t { + STYLE_SIGNED, + STYLE_UNSIGNED }; +#define HANDLE_EXCEPTION_NONE 0 +#define HANDLE_EXCEPTION_OK 1 +#define HANDLE_EXCEPTION_A4000RAM 2 + static int in_handler = 0; -static int max_signals = 200; +static int max_signals = 200; void init_max_signals(void) { - if (write_logfile) - max_signals = 20; - else - max_signals = 200; +#ifdef WITH_LOGGING + max_signals = 20; +#else + max_signals = 200; +#endif } -enum +#if defined(CPU_AARCH64) + +#ifdef JIT +static int delete_trigger(blockinfo *bi, void *pc) { - ARM_REG_PC = 15, - ARM_REG_CPSR = 16 + while (bi) { + if (bi->handler && (uae_u8*)bi->direct_handler <= pc && (uae_u8*)bi->nexthandler > pc) { + output_log(_T("JIT: Deleted trigger (0x%016x < 0x%016x < 0x%016x) 0x%016x\n"), + bi->handler, pc, bi->nexthandler, bi->pc_p); + invalidate_block(bi); + raise_in_cl_list(bi); + countdown = 0; + set_special(0); + return 1; + } + bi = bi->next; + } + return 0; +} +#endif + + +typedef uae_u64 uintptr; + +static int handle_exception(mcontext_t *sigcont, long fault_addr) +{ + int handled = HANDLE_EXCEPTION_NONE; + uintptr fault_pc = (uintptr)sigcont->pc; + + if (fault_pc == 0) { + output_log(_T("PC is NULL.\n")); + return HANDLE_EXCEPTION_NONE; + } + + // Check for exception in handler + if (in_handler > 0) { + output_log(_T("Segmentation fault in handler.\n")); + return HANDLE_EXCEPTION_NONE; + } + ++in_handler; + +#ifdef JIT + for(;;) { + // We analyse only exceptions from JIT + if(currprefs.cachesize == 0) { + output_log(_T("JIT not in use.\n")); + break; + } + + // Did the error happens in compiled code? + if (fault_pc >= (uintptr)compiled_code && fault_pc < (uintptr)current_compile_p) + output_log(_T("Error in compiled code.\n")); + else if(fault_pc >= (uintptr)popallspace && fault_pc < (uintptr)(popallspace + POPALLSPACE_SIZE)) + output_log(_T("Error in popallspace code.\n")); + else { + output_log(_T("Error not in JIT code.\n")); + break; + } + + // Get Amiga address of illegal memory address + long amiga_addr = (long) fault_addr - (long) regs.natmem_offset; + + // Check for stupid RAM detection of kickstart + if(a3000lmem_bank.allocated_size > 0 && amiga_addr >= a3000lmem_bank.start - 0x00100000 && amiga_addr < a3000lmem_bank.start - 0x00100000 + 8) { + output_log(_T(" Stupid kickstart detection for size of ramsey_low at 0x%08x.\n"), amiga_addr); + sigcont->pc += 4; + handled = HANDLE_EXCEPTION_A4000RAM; + break; + } + + // Check for stupid RAM detection of kickstart + if(a3000hmem_bank.allocated_size > 0 && amiga_addr >= a3000hmem_bank.start + a3000hmem_bank.allocated_size && amiga_addr < a3000hmem_bank.start + a3000hmem_bank.allocated_size + 8) { + output_log(_T(" Stupid kickstart detection for size of ramsey_high at 0x%08x.\n"), amiga_addr); + sigcont->pc += 4; + handled = HANDLE_EXCEPTION_A4000RAM; + break; + } + + // Get memory bank of address + addrbank *ab = &get_mem_bank(amiga_addr); + if (ab) + output_log(_T("JIT: Address bank: %s, address %08x\n"), ab->name ? ab->name : _T("NONE"), amiga_addr); + + // Analyse AARCH64 instruction + const unsigned int opcode = ((uae_u32*)fault_pc)[0]; + output_log(_T("JIT: AARCH64 opcode = 0x%08x\n"), opcode); +#ifdef JIT_DEBUG +extern void disam_range(void *start, void *stop); + disam_range((void*)(fault_pc - 128), (void*)(fault_pc + 32)); +#endif + transfer_type_t transfer_type = TYPE_UNKNOWN; + int transfer_size = SIZE_UNKNOWN; + + unsigned int masked_op = opcode & 0xfffffc00; + switch(masked_op) { + case 0x383b6800: // STRB_wXx + transfer_size = SIZE_BYTE; + transfer_type = TYPE_STORE; + break; + + case 0x783b6800: // STRH_wXx + transfer_size = SIZE_WORD; + transfer_type = TYPE_STORE; + break; + + case 0xb83b6800: // STR_wXx + transfer_size = SIZE_INT; + transfer_type = TYPE_STORE; + break; + + case 0x387b6800: // LDRB_wXx + transfer_size = SIZE_BYTE; + transfer_type = TYPE_LOAD; + break; + + case 0x787b6800: // LDRH_wXx + transfer_size = SIZE_WORD; + transfer_type = TYPE_LOAD; + break; + + case 0xb87b6800: // LDR_wXx + transfer_size = SIZE_INT; + transfer_type = TYPE_LOAD; + break; + + default: + output_log(_T("AARCH64: Handling of instruction 0x%08x not supported.\n"), opcode); + } + + if (transfer_size != SIZE_UNKNOWN) { + // Get AARCH64 register + int rd = opcode & 0x1f; + + output_log(_T("%s %s register x%d\n"), + transfer_size == SIZE_BYTE ? _T("byte") : transfer_size == SIZE_WORD ? _T("word") : transfer_size == SIZE_INT ? _T("long") : _T("unknown"), + transfer_type == TYPE_LOAD ? _T("load to") : _T("store from"), + rd); + + if (transfer_type == TYPE_LOAD) { + // Perform load via indirect memory call + uae_u32 oldval = sigcont->regs[rd]; + switch(transfer_size) { + case SIZE_BYTE: + sigcont->regs[rd] = (uae_u8)get_byte(amiga_addr); + break; + + case SIZE_WORD: + sigcont->regs[rd] = do_byteswap_16((uae_u16)get_word(amiga_addr)); + break; + + case SIZE_INT: + sigcont->regs[rd] = do_byteswap_32(get_long(amiga_addr)); + break; + } + output_log(_T("New value in x%d: 0x%08x (old: 0x%08x)\n"), rd, sigcont->regs[rd], oldval); + } else { + // Perform store via indirect memory call + switch(transfer_size) { + case SIZE_BYTE: { + put_byte(amiga_addr, sigcont->regs[rd]); + break; + } + case SIZE_WORD: { + put_word(amiga_addr, do_byteswap_16(sigcont->regs[rd])); + break; + } + case SIZE_INT: { + put_long(amiga_addr, do_byteswap_32(sigcont->regs[rd])); + break; + } + } + output_log(_T("Stored value from x%d to 0x%08x\n"), rd, amiga_addr); + } + + // Go to next instruction + sigcont->pc += 4; + handled = HANDLE_EXCEPTION_OK; + + if (!delete_trigger(active, (void*)fault_pc)) { + /* Not found in the active list. Might be a rom routine that + * is in the dormant list */ + delete_trigger(dormant, (void*)fault_pc); + } + } + + break; + } +#endif + + in_handler--; + return handled; +} + +void signal_segv(int signum, siginfo_t* info, void*ptr) +{ + int handled = HANDLE_EXCEPTION_NONE; + ucontext_t *ucontext = (ucontext_t*)ptr; + Dl_info dlinfo; + + output_log(_T("--- New exception ---\n")); + +#ifdef TRACER + trace_end(); +#endif + + mcontext_t *context = &(ucontext->uc_mcontext); + + unsigned long long *regs = context->regs; + uintptr addr = (uintptr)info->si_addr; + + handled = handle_exception(context, addr); + +#if SHOW_DETAILS + if(handled != HANDLE_EXCEPTION_A4000RAM) { + if(signum == 4) + output_log(_T("Illegal Instruction\n")); + else + output_log(_T("Segmentation Fault\n")); + + output_log(_T("info.si_signo = %d\n"), signum); + output_log(_T("info.si_errno = %d\n"), info->si_errno); + output_log(_T("info.si_code = %d\n"), info->si_code); + output_log(_T("info.si_addr = %08x\n"), info->si_addr); + if(signum == 4) + output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); + + for(int i=0; i < 31; ++i) + output_log(_T("x%02d = 0x%016lx\n"), i, ucontext->uc_mcontext.regs[i]); + output_log(_T("SP = 0x%016lx\n"), ucontext->uc_mcontext.sp); + output_log(_T("PC = 0x%016lx\n"), ucontext->uc_mcontext.pc); + output_log(_T("Fault Address = 0x%016lx\n"), ucontext->uc_mcontext.fault_address); + output_log(_T("pstate = 0x%016lx\n"), ucontext->uc_mcontext.pstate); + + void *getaddr = (void *)ucontext->uc_mcontext.regs[30]; + if(dladdr(getaddr, &dlinfo)) + output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); + else + output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); + } +#endif + +#if SHOW_DETAILS > 1 + if(handled != HANDLE_EXCEPTION_A4000RAM) { + output_log(_T("Stack trace:\n")); + + #define MAX_BACKTRACE 20 + + void *array[MAX_BACKTRACE]; + int size = backtrace(array, MAX_BACKTRACE); + for(int i=0; i (%s)\n"), array[i], symname, + (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + } + } + + output_log(_T("Stack trace (non-dedicated):\n")); + char **strings; + void *bt[100]; + int sz = backtrace(bt, 100); + strings = backtrace_symbols(bt, sz); + for(int i = 0; i < sz; ++i) + output_log(_T("%s\n"), strings[i]); + output_log(_T("End of stack trace.\n")); + } +#endif + + output_log(_T("--- end exception ---\n")); + + if (handled != HANDLE_EXCEPTION_A4000RAM) { + --max_signals; + if(max_signals <= 0) { + target_startup_msg(_T("Exception"), _T("Too many access violations. Please turn off JIT.")); + uae_restart(1, NULL); + return; + } + } + + if (handled != HANDLE_EXCEPTION_NONE) + return; + + SDL_Quit(); + exit(1); +} + + +void signal_buserror(int signum, siginfo_t* info, void*ptr) +{ + ucontext_t *ucontext = (ucontext_t*)ptr; + Dl_info dlinfo; + + output_log(_T("--- New exception ---\n")); + +#ifdef TRACER + trace_end(); +#endif + + mcontext_t *context = &(ucontext->uc_mcontext); + + unsigned long long *regs = context->regs; + uintptr_t addr = (uintptr_t)info->si_addr; + + output_log(_T("info.si_signo = %d\n"), signum); + output_log(_T("info.si_errno = %d\n"), info->si_errno); + output_log(_T("info.si_code = %d\n"), info->si_code); + output_log(_T("info.si_addr = %08x\n"), info->si_addr); + if(signum == 4) + output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); + + for(int i=0; i < 31; ++i) + output_log(_T("x%02d = 0x%016lx\n"), i, ucontext->uc_mcontext.regs[i]); + output_log(_T("SP = 0x%016lx\n"), ucontext->uc_mcontext.sp); + output_log(_T("PC = 0x%016lx\n"), ucontext->uc_mcontext.pc); + output_log(_T("Fault Address = 0x%016lx\n"), ucontext->uc_mcontext.fault_address); + output_log(_T("pstate = 0x%016lx\n"), ucontext->uc_mcontext.pstate); + + void *getaddr = (void *)ucontext->uc_mcontext.regs[30]; + if(dladdr(getaddr, &dlinfo)) + output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); + else + output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); + + output_log(_T("Stack trace:\n")); + + #define MAX_BACKTRACE 20 + + void *array[MAX_BACKTRACE]; + int size = backtrace(array, MAX_BACKTRACE); + for(int i=0; i (%s)\n"), array[i], symname, + (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + } + } + + output_log(_T("Stack trace (non-dedicated):\n")); + char **strings; + void *bt[100]; + int sz = backtrace(bt, 100); + strings = backtrace_symbols(bt, sz); + for(int i = 0; i < sz; ++i) + output_log(_T("%s\n"), strings[i]); + output_log(_T("End of stack trace.\n")); + + output_log(_T("--- end exception ---\n")); + + SDL_Quit(); + exit(1); +} + +#else + +enum { + ARM_REG_PC = 15, + ARM_REG_CPSR = 16 }; -static const char* reg_names[] = { +static const char * reg_names[] = { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10/sl", "r11/fp", "r12/ip", "r13/sp", "r14/lr", "r15/pc" }; -static int delete_trigger(blockinfo* bi, void* pc) +#ifdef JIT +static int delete_trigger(blockinfo *bi, void *pc) { - while (bi) - { - if (bi->handler && (uae_u8*)bi->direct_handler <= pc && (uae_u8*)bi->nexthandler > pc) - { + while (bi) { + if (bi->handler && (uae_u8*)bi->direct_handler <= pc && (uae_u8*)bi->nexthandler > pc) { output_log(_T("JIT: Deleted trigger (0x%08x < 0x%08x < 0x%08x) 0x%08x\n"), bi->handler, pc, bi->nexthandler, bi->pc_p); invalidate_block(bi); @@ -121,449 +481,415 @@ static int delete_trigger(blockinfo* bi, void* pc) } return 0; } +#endif -#define HANDLE_EXCEPTION_NONE 0 -#define HANDLE_EXCEPTION_OK 1 -#define HANDLE_EXCEPTION_A4000RAM 2 - - -static int handle_exception(unsigned long* pregs, uintptr fault_addr) +static int handle_exception(unsigned long *pregs, long fault_addr) { - int handled = HANDLE_EXCEPTION_NONE; - unsigned int* fault_pc = (unsigned int *)pregs[ARM_REG_PC]; - - if (fault_pc == nullptr) - { - output_log(_T("PC is NULL.\n")); - return HANDLE_EXCEPTION_NONE; - } + int handled = HANDLE_EXCEPTION_NONE; + unsigned int *fault_pc = (unsigned int *)pregs[ARM_REG_PC]; + + if (fault_pc == 0) { + output_log(_T("PC is NULL.\n")); + return HANDLE_EXCEPTION_NONE; + } // Check for exception in handler - if (in_handler > 0) - { - output_log(_T("Segmentation fault in handler.\n")); - return HANDLE_EXCEPTION_NONE; - } - ++in_handler; + if (in_handler > 0) { + output_log(_T("Segmentation fault in handler.\n")); + return HANDLE_EXCEPTION_NONE; + } + ++in_handler; - for (;;) - { - // We analyse only exceptions from JIT - if (currprefs.cachesize == 0) - { - output_log(_T("JIT not in use.\n")); - break; - } +#ifdef JIT + for(;;) { + // We analyse only exceptions from JIT + if(currprefs.cachesize == 0) { + output_log(_T("JIT not in use.\n")); + break; + } - // Did the error happens in compiled code? - if ((uae_u8*)fault_pc >= compiled_code && (uae_u8*)fault_pc < current_compile_p) - output_log(_T("Error in compiled code.\n")); - else if ((uae_u8*)fault_pc >= popallspace && (uae_u8*)fault_pc < popallspace + POPALLSPACE_SIZE) - output_log(_T("Error in popallspace code.\n")); - else - { - output_log(_T("Error not in JIT code.\n")); - break; - } + // Did the error happens in compiled code? + if ((uae_u8*)fault_pc >= compiled_code && (uae_u8*)fault_pc < current_compile_p) + output_log(_T("Error in compiled code.\n")); + else if((uae_u8*)fault_pc >= popallspace && (uae_u8*)fault_pc < popallspace + POPALLSPACE_SIZE) + output_log(_T("Error in popallspace code.\n")); + else { + output_log(_T("Error not in JIT code.\n")); + break; + } - // Get Amiga address of illegal memory address - auto amiga_addr = uae_u32(fault_addr) - uae_u32(regs.natmem_offset); - - // Check for stupid RAM detection of kickstart - if (a3000lmem_bank.allocated_size > 0 && amiga_addr >= a3000lmem_bank.start - 0x00100000 && amiga_addr < - a3000lmem_bank.start - 0x00100000 + 8) - { - output_log(_T(" Stupid kickstart detection for size of ramsey_low at 0x%08x.\n"), amiga_addr); - pregs[ARM_REG_PC] += 4; - handled = HANDLE_EXCEPTION_A4000RAM; - break; - } - - // Check for stupid RAM detection of kickstart - if (a3000hmem_bank.allocated_size > 0 && amiga_addr >= a3000hmem_bank.start + a3000hmem_bank.allocated_size && - amiga_addr < a3000hmem_bank.start + a3000hmem_bank.allocated_size + 8) - { - output_log(_T(" Stupid kickstart detection for size of ramsey_high at 0x%08x.\n"), amiga_addr); - pregs[ARM_REG_PC] += 4; - handled = HANDLE_EXCEPTION_A4000RAM; - break; - } - - // Get memory bank of address - const auto ab = &get_mem_bank(amiga_addr); - if (ab) - output_log(_T("JIT: Address bank: %s, address %08x\n"), ab->name ? ab->name : _T("NONE"), amiga_addr); - - // Analyse ARM instruction - const auto opcode = fault_pc[0]; - auto transfer_type = TYPE_UNKNOWN; - int transfer_size = SIZE_UNKNOWN; - int style = STYLE_UNSIGNED; + // Get Amiga address of illegal memory address + long amiga_addr = (long) fault_addr - (long) regs.natmem_offset; + + // Check for stupid RAM detection of kickstart + if(a3000lmem_bank.allocated_size > 0 && amiga_addr >= a3000lmem_bank.start - 0x00100000 && amiga_addr < a3000lmem_bank.start - 0x00100000 + 8) { + output_log(_T(" Stupid kickstart detection for size of ramsey_low at 0x%08x.\n"), amiga_addr); + pregs[ARM_REG_PC] += 4; + handled = HANDLE_EXCEPTION_A4000RAM; + break; + } + + // Check for stupid RAM detection of kickstart + if(a3000hmem_bank.allocated_size > 0 && amiga_addr >= a3000hmem_bank.start + a3000hmem_bank.allocated_size && amiga_addr < a3000hmem_bank.start + a3000hmem_bank.allocated_size + 8) { + output_log(_T(" Stupid kickstart detection for size of ramsey_high at 0x%08x.\n"), amiga_addr); + pregs[ARM_REG_PC] += 4; + handled = HANDLE_EXCEPTION_A4000RAM; + break; + } + + // Get memory bank of address + addrbank *ab = &get_mem_bank(amiga_addr); + if (ab) + output_log(_T("JIT: Address bank: %s, address %08x\n"), ab->name ? ab->name : _T("NONE"), amiga_addr); + + // Analyse ARM instruction + const unsigned int opcode = fault_pc[0]; + transfer_type_t transfer_type = TYPE_UNKNOWN; + int transfer_size = SIZE_UNKNOWN; + int style = STYLE_UNSIGNED; output_log(_T("JIT: ARM opcode = 0x%08x\n"), opcode); + + // Handle load/store instructions only + switch ((opcode >> 25) & 7) { + case 0: // Halfword and Signed Data Transfer (LDRH, STRH, LDRSB, LDRSH) + // Determine transfer size (S/H bits) + switch ((opcode >> 5) & 3) { + case 0: // SWP instruction + output_log(_T("ARM: SWP Instruction, not supported (0x%08x)\n"), opcode); + break; + case 1: // Unsigned halfwords + transfer_size = SIZE_WORD; + break; + case 3: // Signed halfwords + style = STYLE_SIGNED; + transfer_size = SIZE_WORD; + break; + case 2: // Signed byte + style = STYLE_SIGNED; + transfer_size = SIZE_BYTE; + break; + } + break; - // Handle load/store instructions only - switch ((opcode >> 25) & 7) - { - case 0: // Halfword and Signed Data Transfer (LDRH, STRH, LDRSB, LDRSH) - // Determine transfer size (S/H bits) - switch ((opcode >> 5) & 3) - { - case 0: // SWP instruction - output_log(_T("ARM: SWP Instruction, not supported (0x%08x)\n"), opcode); - break; - case 1: // Unsigned halfwords - transfer_size = SIZE_WORD; - break; - case 3: // Signed halfwords - style = STYLE_SIGNED; - transfer_size = SIZE_WORD; - break; - case 2: // Signed byte - style = STYLE_SIGNED; - transfer_size = SIZE_BYTE; - break; - } - break; + case 2: + case 3: // Single Data Transfer (LDR, STR) + style = STYLE_UNSIGNED; + // Determine transfer size (B bit) + if (((opcode >> 22) & 1) == 1) + transfer_size = SIZE_BYTE; + else + transfer_size = SIZE_INT; + break; - case 2: - case 3: // Single Data Transfer (LDR, STR) - style = STYLE_UNSIGNED; - // Determine transfer size (B bit) - if (((opcode >> 22) & 1) == 1) - transfer_size = SIZE_BYTE; - else - transfer_size = SIZE_INT; - break; + default: + output_log(_T("ARM: Handling of instruction 0x%08x not supported.\n"), opcode); + } - default: - output_log(_T("ARM: Handling of instruction 0x%08x not supported.\n"), opcode); - } + // Determine transfer type (L bit) + if (((opcode >> 20) & 1) == 1) + transfer_type = TYPE_LOAD; + else + transfer_type = TYPE_STORE; - // Determine transfer type (L bit) - if (((opcode >> 20) & 1) == 1) - transfer_type = TYPE_LOAD; - else - transfer_type = TYPE_STORE; + // Get ARM register + int rd = (opcode >> 12) & 0xf; - // Get ARM register - int rd = (opcode >> 12) & 0xf; + output_log(_T("%s %s register %s\n"), + transfer_size == SIZE_BYTE ? _T("byte") : transfer_size == SIZE_WORD ? _T("word") : transfer_size == SIZE_INT ? _T("long") : _T("unknown"), + transfer_type == TYPE_LOAD ? _T("load to") : _T("store from"), + reg_names[rd]); + + if (transfer_size != SIZE_UNKNOWN) { + if (transfer_type == TYPE_LOAD) { + // Perform load via indirect memory call + uae_u32 oldval = pregs[rd]; + switch(transfer_size) { + case SIZE_BYTE: + pregs[rd] = style == STYLE_SIGNED ? (uae_s8)get_byte(amiga_addr) : (uae_u8)get_byte(amiga_addr); + break; - output_log(_T("%s %s register %s\n"), - transfer_size == SIZE_BYTE - ? _T("byte") - : transfer_size == SIZE_WORD - ? _T("word") - : transfer_size == SIZE_INT - ? _T("long") - : _T("unknown"), - transfer_type == TYPE_LOAD ? _T("load to") : _T("store from"), - reg_names[rd]); + case SIZE_WORD: + pregs[rd] = do_byteswap_16(style == STYLE_SIGNED ? (uae_s16)get_word(amiga_addr) : (uae_u16)get_word(amiga_addr)); + break; - if (transfer_size != SIZE_UNKNOWN) - { - if (transfer_type == TYPE_LOAD) - { - // Perform load via indirect memory call - uae_u32 oldval = pregs[rd]; - switch (transfer_size) - { - case SIZE_BYTE: - pregs[rd] = style == STYLE_SIGNED ? (uae_s8)get_byte(amiga_addr) : uae_u8(get_byte(amiga_addr)); - break; + case SIZE_INT: + pregs[rd] = do_byteswap_32(get_long(amiga_addr)); + break; + } + output_log(_T("New value in %s: 0x%08x (old: 0x%08x)\n"), reg_names[rd], pregs[rd], oldval); + } else { + // Perform store via indirect memory call + switch(transfer_size) { + case SIZE_BYTE: { + put_byte(amiga_addr, pregs[rd]); + break; + } + case SIZE_WORD: { + put_word(amiga_addr, do_byteswap_16(pregs[rd])); + break; + } + case SIZE_INT: { + put_long(amiga_addr, do_byteswap_32(pregs[rd])); + break; + } + } + output_log(_T("Stored value from %s to 0x%08x\n"), reg_names[rd], amiga_addr); + } + + // Go to next instruction + pregs[ARM_REG_PC] += 4; + handled = HANDLE_EXCEPTION_OK; + + if (!delete_trigger(active, fault_pc)) { + /* Not found in the active list. Might be a rom routine that + * is in the dormant list */ + delete_trigger(dormant, fault_pc); + } + } + + break; + } +#endif - case SIZE_WORD: - pregs[rd] = bswap_16(style == STYLE_SIGNED ? (uae_s16)get_word(amiga_addr) : uae_u16(get_word(amiga_addr))); - break; - - case SIZE_INT: - pregs[rd] = bswap_32(get_long(amiga_addr)); - break; - } - output_log(_T("New value in %s: 0x%08x (old: 0x%08x)\n"), reg_names[rd], pregs[rd], oldval); - } - else - { - // Perform store via indirect memory call - switch (transfer_size) - { - case SIZE_BYTE: - { - put_byte(amiga_addr, pregs[rd]); - break; - } - case SIZE_WORD: - { - put_word(amiga_addr, bswap_16(pregs[rd])); - break; - } - case SIZE_INT: - { - put_long(amiga_addr, bswap_32(pregs[rd])); - break; - } - } - output_log(_T("Stored value from %s to 0x%08x\n"), reg_names[rd], amiga_addr); - } - - // Go to next instruction - pregs[ARM_REG_PC] += 4; - handled = HANDLE_EXCEPTION_OK; - - if (!delete_trigger(active, fault_pc)) - { - /* Not found in the active list. Might be a rom routine that - * is in the dormant list */ - delete_trigger(dormant, fault_pc); - } - } - - break; - } - - in_handler--; + in_handler--; return handled; -} +} -void signal_segv(int signum, siginfo_t* info, void* ptr) +void signal_segv(int signum, siginfo_t* info, void*ptr) { - auto ucontext = (ucontext_t*)ptr; - Dl_info dlinfo; + int handled = HANDLE_EXCEPTION_NONE; + ucontext_t *ucontext = (ucontext_t*)ptr; + Dl_info dlinfo; - output_log(_T("--- New exception ---\n")); + output_log(_T("--- New exception ---\n")); #ifdef TRACER trace_end(); #endif - auto context = &(ucontext->uc_mcontext); - const auto regs = &context->arm_r0; - const auto addr = uintptr(info->si_addr); + mcontext_t *context = &(ucontext->uc_mcontext); - const auto handled = handle_exception(regs, addr); + unsigned long *regs = &context->arm_r0; + uintptr addr = (uintptr)info->si_addr; + + handled = handle_exception(regs, addr); #if SHOW_DETAILS - if (handled != HANDLE_EXCEPTION_A4000RAM) - { - if (signum == 4) - output_log(_T("Illegal Instruction\n")); - else - output_log(_T("Segmentation Fault\n")); - - output_log(_T("info.si_signo = %d\n"), signum); - output_log(_T("info.si_errno = %d\n"), info->si_errno); - output_log(_T("info.si_code = %d\n"), info->si_code); - output_log(_T("info.si_addr = %08x\n"), info->si_addr); - if (signum == 4) - output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); - output_log(_T("r0 = 0x%08x\n"), ucontext->uc_mcontext.arm_r0); - output_log(_T("r1 = 0x%08x\n"), ucontext->uc_mcontext.arm_r1); - output_log(_T("r2 = 0x%08x\n"), ucontext->uc_mcontext.arm_r2); - output_log(_T("r3 = 0x%08x\n"), ucontext->uc_mcontext.arm_r3); - output_log(_T("r4 = 0x%08x\n"), ucontext->uc_mcontext.arm_r4); - output_log(_T("r5 = 0x%08x\n"), ucontext->uc_mcontext.arm_r5); - output_log(_T("r6 = 0x%08x\n"), ucontext->uc_mcontext.arm_r6); - output_log(_T("r7 = 0x%08x\n"), ucontext->uc_mcontext.arm_r7); - output_log(_T("r8 = 0x%08x\n"), ucontext->uc_mcontext.arm_r8); - output_log(_T("r9 = 0x%08x\n"), ucontext->uc_mcontext.arm_r9); - output_log(_T("r10 = 0x%08x\n"), ucontext->uc_mcontext.arm_r10); - output_log(_T("FP = 0x%08x\n"), ucontext->uc_mcontext.arm_fp); - output_log(_T("IP = 0x%08x\n"), ucontext->uc_mcontext.arm_ip); - output_log(_T("SP = 0x%08x\n"), ucontext->uc_mcontext.arm_sp); - output_log(_T("LR = 0x%08x\n"), ucontext->uc_mcontext.arm_lr); - output_log(_T("PC = 0x%08x\n"), ucontext->uc_mcontext.arm_pc); - output_log(_T("CPSR = 0x%08x\n"), ucontext->uc_mcontext.arm_cpsr); - output_log(_T("Fault Address = 0x%08x\n"), ucontext->uc_mcontext.fault_address); - output_log(_T("Trap no = 0x%08x\n"), ucontext->uc_mcontext.trap_no); - output_log(_T("Err Code = 0x%08x\n"), ucontext->uc_mcontext.error_code); - output_log(_T("Old Mask = 0x%08x\n"), ucontext->uc_mcontext.oldmask); - - auto getaddr = (void *)ucontext->uc_mcontext.arm_lr; - if (dladdr(getaddr, &dlinfo)) - output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); - else - output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); - } + if(handled != HANDLE_EXCEPTION_A4000RAM) { + if(signum == 4) + output_log(_T("Illegal Instruction\n")); + else + output_log(_T("Segmentation Fault\n")); + + output_log(_T("info.si_signo = %d\n"), signum); + output_log(_T("info.si_errno = %d\n"), info->si_errno); + output_log(_T("info.si_code = %d\n"), info->si_code); + output_log(_T("info.si_addr = %08x\n"), info->si_addr); + if(signum == 4) + output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); + output_log(_T("r0 = 0x%08x\n"), ucontext->uc_mcontext.arm_r0); + output_log(_T("r1 = 0x%08x\n"), ucontext->uc_mcontext.arm_r1); + output_log(_T("r2 = 0x%08x\n"), ucontext->uc_mcontext.arm_r2); + output_log(_T("r3 = 0x%08x\n"), ucontext->uc_mcontext.arm_r3); + output_log(_T("r4 = 0x%08x\n"), ucontext->uc_mcontext.arm_r4); + output_log(_T("r5 = 0x%08x\n"), ucontext->uc_mcontext.arm_r5); + output_log(_T("r6 = 0x%08x\n"), ucontext->uc_mcontext.arm_r6); + output_log(_T("r7 = 0x%08x\n"), ucontext->uc_mcontext.arm_r7); + output_log(_T("r8 = 0x%08x\n"), ucontext->uc_mcontext.arm_r8); + output_log(_T("r9 = 0x%08x\n"), ucontext->uc_mcontext.arm_r9); + output_log(_T("r10 = 0x%08x\n"), ucontext->uc_mcontext.arm_r10); + output_log(_T("FP = 0x%08x\n"), ucontext->uc_mcontext.arm_fp); + output_log(_T("IP = 0x%08x\n"), ucontext->uc_mcontext.arm_ip); + output_log(_T("SP = 0x%08x\n"), ucontext->uc_mcontext.arm_sp); + output_log(_T("LR = 0x%08x\n"), ucontext->uc_mcontext.arm_lr); + output_log(_T("PC = 0x%08x\n"), ucontext->uc_mcontext.arm_pc); + output_log(_T("CPSR = 0x%08x\n"), ucontext->uc_mcontext.arm_cpsr); + output_log(_T("Fault Address = 0x%08x\n"), ucontext->uc_mcontext.fault_address); + output_log(_T("Trap no = 0x%08x\n"), ucontext->uc_mcontext.trap_no); + output_log(_T("Err Code = 0x%08x\n"), ucontext->uc_mcontext.error_code); + output_log(_T("Old Mask = 0x%08x\n"), ucontext->uc_mcontext.oldmask); + + void *getaddr = (void *)ucontext->uc_mcontext.arm_lr; + if(dladdr(getaddr, &dlinfo)) + output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); + else + output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); + } #endif #if SHOW_DETAILS > 1 - if (handled != HANDLE_EXCEPTION_A4000RAM) - { - output_log(_T("Stack trace:\n")); - -#define MAX_BACKTRACE 20 - - void* array[MAX_BACKTRACE]; - auto size = backtrace(array, MAX_BACKTRACE); - for (auto i = 0; i < size; ++i) - { - if (dladdr(array[i], &dlinfo)) - { - auto symname = dlinfo.dli_sname; - output_log(_T("0x%08x <%s + 0x%08x> (%s)\n"), array[i], symname, - (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); - } - } - - auto ip = (void*)ucontext->uc_mcontext.arm_r10; - auto bp = (void**)ucontext->uc_mcontext.arm_r10; - auto f = 0; - while (bp && ip) - { - if (!dladdr(ip, &dlinfo)) - { - output_log(_T("IP out of range\n")); - break; - } - const char* symname = dlinfo.dli_sname; - output_log(_T("%02d: 0x%08x <%s + 0x%08x> (%s)\n"), ++f, ip, symname, - (unsigned long)ip - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); - if (dlinfo.dli_sname && !strcmp(dlinfo.dli_sname, "main")) - break; - ip = bp[1]; - bp = (void**)bp[0]; - } - - output_log(_T("Stack trace (non-dedicated):\n")); - char** strings; - void* bt[100]; - auto sz = backtrace(bt, 100); - strings = backtrace_symbols(bt, sz); - for (auto i = 0; i < sz; ++i) - output_log(_T("%s\n"), strings[i]); - output_log(_T("End of stack trace.\n")); - } + if(handled != HANDLE_EXCEPTION_A4000RAM) { + output_log(_T("Stack trace:\n")); + + #define MAX_BACKTRACE 20 + + void *array[MAX_BACKTRACE]; + int size = backtrace(array, MAX_BACKTRACE); + for(int i=0; i (%s)\n"), array[i], symname, + (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + } + } + + void *ip = (void*)ucontext->uc_mcontext.arm_r10; + void **bp = (void**)ucontext->uc_mcontext.arm_r10; + int f = 0; + while(bp && ip) { + if (!dladdr(ip, &dlinfo)) { + output_log(_T("IP out of range\n")); + break; + } + const char *symname = dlinfo.dli_sname; + output_log(_T("%02d: 0x%08x <%s + 0x%08x> (%s)\n"), ++f, ip, symname, + (unsigned long)ip - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + if(dlinfo.dli_sname && !strcmp(dlinfo.dli_sname, "main")) + break; + ip = bp[1]; + bp = (void**)bp[0]; + } + + output_log(_T("Stack trace (non-dedicated):\n")); + char **strings; + void *bt[100]; + int sz = backtrace(bt, 100); + strings = backtrace_symbols(bt, sz); + for(int i = 0; i < sz; ++i) + output_log(_T("%s\n"), strings[i]); + output_log(_T("End of stack trace.\n")); + } #endif - output_log(_T("--- end exception ---\n")); + output_log(_T("--- end exception ---\n")); - if (handled != HANDLE_EXCEPTION_A4000RAM) - { - --max_signals; - if (max_signals <= 0) - { - target_startup_msg(_T("Exception"), _T("Too many access violations. Please turn off JIT.")); - uae_restart(1, nullptr); - return; - } - } + if (handled != HANDLE_EXCEPTION_A4000RAM) { + --max_signals; + if(max_signals <= 0) { + target_startup_msg(_T("Exception"), _T("Too many access violations. Please turn off JIT.")); + uae_restart(1, NULL); + return; + } + } if (handled != HANDLE_EXCEPTION_NONE) - return; + return; - SDL_Quit(); - exit(1); + SDL_Quit(); + exit(1); } -void signal_buserror(int signum, siginfo_t* info, void* ptr) +void signal_buserror(int signum, siginfo_t* info, void*ptr) { - auto ucontext = (ucontext_t*)ptr; - Dl_info dlinfo; + ucontext_t *ucontext = (ucontext_t*)ptr; + Dl_info dlinfo; - output_log(_T("--- New exception ---\n")); + output_log(_T("--- New exception ---\n")); #ifdef TRACER trace_end(); #endif - auto context = &(ucontext->uc_mcontext); - auto regs = &context->arm_r0; - auto addr = uintptr(info->si_addr); + mcontext_t *context = &(ucontext->uc_mcontext); - output_log(_T("info.si_signo = %d\n"), signum); - output_log(_T("info.si_errno = %d\n"), info->si_errno); - output_log(_T("info.si_code = %d\n"), info->si_code); - output_log(_T("info.si_addr = %08x\n"), info->si_addr); - if (signum == 4) - output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); - output_log(_T("r0 = 0x%08x\n"), ucontext->uc_mcontext.arm_r0); - output_log(_T("r1 = 0x%08x\n"), ucontext->uc_mcontext.arm_r1); - output_log(_T("r2 = 0x%08x\n"), ucontext->uc_mcontext.arm_r2); - output_log(_T("r3 = 0x%08x\n"), ucontext->uc_mcontext.arm_r3); - output_log(_T("r4 = 0x%08x\n"), ucontext->uc_mcontext.arm_r4); - output_log(_T("r5 = 0x%08x\n"), ucontext->uc_mcontext.arm_r5); - output_log(_T("r6 = 0x%08x\n"), ucontext->uc_mcontext.arm_r6); - output_log(_T("r7 = 0x%08x\n"), ucontext->uc_mcontext.arm_r7); - output_log(_T("r8 = 0x%08x\n"), ucontext->uc_mcontext.arm_r8); - output_log(_T("r9 = 0x%08x\n"), ucontext->uc_mcontext.arm_r9); - output_log(_T("r10 = 0x%08x\n"), ucontext->uc_mcontext.arm_r10); - output_log(_T("FP = 0x%08x\n"), ucontext->uc_mcontext.arm_fp); - output_log(_T("IP = 0x%08x\n"), ucontext->uc_mcontext.arm_ip); - output_log(_T("SP = 0x%08x\n"), ucontext->uc_mcontext.arm_sp); - output_log(_T("LR = 0x%08x\n"), ucontext->uc_mcontext.arm_lr); - output_log(_T("PC = 0x%08x\n"), ucontext->uc_mcontext.arm_pc); - output_log(_T("CPSR = 0x%08x\n"), ucontext->uc_mcontext.arm_cpsr); - output_log(_T("Fault Address = 0x%08x\n"), ucontext->uc_mcontext.fault_address); - output_log(_T("Trap no = 0x%08x\n"), ucontext->uc_mcontext.trap_no); - output_log(_T("Err Code = 0x%08x\n"), ucontext->uc_mcontext.error_code); - output_log(_T("Old Mask = 0x%08x\n"), ucontext->uc_mcontext.oldmask); + unsigned long *regs = &context->arm_r0; + uintptr_t addr = (uintptr_t)info->si_addr; - auto getaddr = (void *)ucontext->uc_mcontext.arm_lr; - if (dladdr(getaddr, &dlinfo)) - output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); - else - output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); + output_log(_T("info.si_signo = %d\n"), signum); + output_log(_T("info.si_errno = %d\n"), info->si_errno); + output_log(_T("info.si_code = %d\n"), info->si_code); + output_log(_T("info.si_addr = %08x\n"), info->si_addr); + if(signum == 4) + output_log(_T(" value = 0x%08x\n"), *((uae_u32*)(info->si_addr))); + output_log(_T("r0 = 0x%08x\n"), ucontext->uc_mcontext.arm_r0); + output_log(_T("r1 = 0x%08x\n"), ucontext->uc_mcontext.arm_r1); + output_log(_T("r2 = 0x%08x\n"), ucontext->uc_mcontext.arm_r2); + output_log(_T("r3 = 0x%08x\n"), ucontext->uc_mcontext.arm_r3); + output_log(_T("r4 = 0x%08x\n"), ucontext->uc_mcontext.arm_r4); + output_log(_T("r5 = 0x%08x\n"), ucontext->uc_mcontext.arm_r5); + output_log(_T("r6 = 0x%08x\n"), ucontext->uc_mcontext.arm_r6); + output_log(_T("r7 = 0x%08x\n"), ucontext->uc_mcontext.arm_r7); + output_log(_T("r8 = 0x%08x\n"), ucontext->uc_mcontext.arm_r8); + output_log(_T("r9 = 0x%08x\n"), ucontext->uc_mcontext.arm_r9); + output_log(_T("r10 = 0x%08x\n"), ucontext->uc_mcontext.arm_r10); + output_log(_T("FP = 0x%08x\n"), ucontext->uc_mcontext.arm_fp); + output_log(_T("IP = 0x%08x\n"), ucontext->uc_mcontext.arm_ip); + output_log(_T("SP = 0x%08x\n"), ucontext->uc_mcontext.arm_sp); + output_log(_T("LR = 0x%08x\n"), ucontext->uc_mcontext.arm_lr); + output_log(_T("PC = 0x%08x\n"), ucontext->uc_mcontext.arm_pc); + output_log(_T("CPSR = 0x%08x\n"), ucontext->uc_mcontext.arm_cpsr); + output_log(_T("Trap no = 0x%08x\n"), ucontext->uc_mcontext.trap_no); + output_log(_T("Err Code = 0x%08x\n"), ucontext->uc_mcontext.error_code); + output_log(_T("Old Mask = 0x%08x\n"), ucontext->uc_mcontext.oldmask); + output_log(_T("Fault Address = 0x%08x\n"), ucontext->uc_mcontext.fault_address); + + void *getaddr = (void *)ucontext->uc_mcontext.arm_lr; + if(dladdr(getaddr, &dlinfo)) + output_log(_T("LR - 0x%08X: <%s> (%s)\n"), getaddr, dlinfo.dli_sname, dlinfo.dli_fname); + else + output_log(_T("LR - 0x%08X: symbol not found\n"), getaddr); output_log(_T("Stack trace:\n")); -#define MAX_BACKTRACE 20 + #define MAX_BACKTRACE 20 + + void *array[MAX_BACKTRACE]; + int size = backtrace(array, MAX_BACKTRACE); + for(int i=0; i (%s)\n"), array[i], symname, + (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + } + } - void* array[MAX_BACKTRACE]; - auto size = backtrace(array, MAX_BACKTRACE); - for (auto i = 0; i < size; ++i) - { - if (dladdr(array[i], &dlinfo)) - { - auto symname = dlinfo.dli_sname; - output_log(_T("0x%08x <%s + 0x%08x> (%s)\n"), array[i], symname, - (unsigned long)array[i] - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); - } - } - - auto ip = (void*)ucontext->uc_mcontext.arm_r10; - auto bp = (void**)ucontext->uc_mcontext.arm_r10; - auto f = 0; - while (bp && ip) - { - if (!dladdr(ip, &dlinfo)) - { - output_log(_T("IP out of range\n")); - break; - } - auto symname = dlinfo.dli_sname; - output_log(_T("%02d: 0x%08x <%s + 0x%08x> (%s)\n"), ++f, ip, symname, - (unsigned long)ip - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); - if (dlinfo.dli_sname && !strcmp(dlinfo.dli_sname, "main")) - break; - ip = bp[1]; - bp = (void**)bp[0]; - } + void *ip = (void*)ucontext->uc_mcontext.arm_r10; + void **bp = (void**)ucontext->uc_mcontext.arm_r10; + int f = 0; + while(bp && ip) { + if (!dladdr(ip, &dlinfo)) { + output_log(_T("IP out of range\n")); + break; + } + const char *symname = dlinfo.dli_sname; + output_log(_T("%02d: 0x%08x <%s + 0x%08x> (%s)\n"), ++f, ip, symname, + (unsigned long)ip - (unsigned long)dlinfo.dli_saddr, dlinfo.dli_fname); + if(dlinfo.dli_sname && !strcmp(dlinfo.dli_sname, "main")) + break; + ip = bp[1]; + bp = (void**)bp[0]; + } output_log(_T("Stack trace (non-dedicated):\n")); - char** strings; - void* bt[100]; - auto sz = backtrace(bt, 100); - strings = backtrace_symbols(bt, sz); - for (int i = 0; i < sz; ++i) - output_log(_T("%s\n"), strings[i]); + char **strings; + void *bt[100]; + int sz = backtrace(bt, 100); + strings = backtrace_symbols(bt, sz); + for(int i = 0; i < sz; ++i) + output_log(_T("%s\n"), strings[i]); output_log(_T("End of stack trace.\n")); - output_log(_T("--- end exception ---\n")); + output_log(_T("--- end exception ---\n")); - SDL_Quit(); - exit(1); + SDL_Quit(); + exit(1); } +#endif -void signal_term(int signum, siginfo_t* info, void* ptr) + +void signal_term(int signum, siginfo_t* info, void*ptr) { - output_log(_T("--- SIGTERM ---\n")); + output_log(_T("--- SIGTERM ---\n")); #ifdef TRACER trace_end(); #endif - SDL_Quit(); - exit(1); + SDL_Quit(); + exit(1); } diff --git a/src/osdep/sysconfig.h b/src/osdep/sysconfig.h index dcda3bf6..ea762899 100644 --- a/src/osdep/sysconfig.h +++ b/src/osdep/sysconfig.h @@ -18,9 +18,8 @@ #define FILESYS /* filesys emulation */ #define UAE_FILESYS_THREADS #define AUTOCONFIG /* autoconfig support, fast ram, harddrives etc.. */ - -#ifdef ARMV6T2 #define JIT /* JIT compiler support */ +#if defined(ARMV6T2) || defined(CPU_AARCH64) #define USE_JIT_FPU #endif /* #define NATMEM_OFFSET regs.natmem_offset */ @@ -60,7 +59,7 @@ #define PICASSO96 /* Picasso96 display card emulation */ #define UAEGFX_INTERNAL /* built-in libs:picasso96/uaegfx.card */ #define BSDSOCKET /* bsdsocket.library emulation */ -#define CAPS /* CAPS-image support */ +#define CAPS /* CAPS-image support */ /* #define SCP */ /* SuperCardPro */ #define FDI2RAW /* FDI 1.0 and 2.x image support */ /* #define AVIOUTPUT */ /* Avioutput support */ @@ -93,7 +92,6 @@ /* #define CUSTOM_SIMPLE */ /* simplified custom chipset emulation */ /* #define CPUEMU_68000_ONLY */ /* drop 68010+ commands from CPUEMU_0 */ /* #define ADDRESS_SPACE_24BIT */ -#define INPUTDEVICE_SIMPLE /* simplified inputdevice for faster emulation */ /* #define WITH_SCSI_IOCTL */ /* #define WITH_SCSI_SPTI */ @@ -115,13 +113,17 @@ #include +#ifdef CPU_AARCH64 +#define SIZEOF_VOID_P 8 +#else #define SIZEOF_VOID_P 4 +#endif #if !defined(AHI) #undef ENFORCER #endif -typedef long uae_atomic; +typedef int32_t uae_atomic; /* src/sysconfig.h. Generated automatically by configure. */ /* src/sysconfig.h.in. Generated automatically from configure.in by autoheader. */ @@ -258,7 +260,11 @@ typedef long uae_atomic; #define SIZEOF_INT 4 /* The number of bytes in a long. */ +#ifdef CPU_AARCH64 +#define SIZEOF_LONG 8 +#else #define SIZEOF_LONG 4 +#endif /* The number of bytes in a long long. */ #define SIZEOF_LONG_LONG 8 @@ -529,7 +535,7 @@ typedef long uae_atomic; #define M68K_SPEED_25MHZ_CYCLES 128 typedef unsigned int WPARAM; -typedef long LPARAM; +typedef int LPARAM; typedef int SOCKET; #define INVALID_SOCKET -1 diff --git a/src/osdep/target.h b/src/osdep/target.h index 15495ad7..3453f1e3 100644 --- a/src/osdep/target.h +++ b/src/osdep/target.h @@ -13,6 +13,18 @@ #define OPTIONSFILENAME "uaeconfig" +#if !defined(ARMV6T2) && !defined(CPU_AARCH64) +#undef USE_JIT_FPU +#endif + +#define MAKEBD(x,y,z) ((((x) - 2000) * 10000 + (y)) * 100 + (z)) +#define GETBDY(x) ((x) / 1000000 + 2000) +#define GETBDM(x) (((x) - ((x / 10000) * 10000)) / 100) +#define GETBDD(x) ((x) % 100) + + +#define AMIBERRYDATE MAKEBD(2019, 5, 17) + STATIC_INLINE FILE *uae_tfopen(const TCHAR *path, const TCHAR *mode) { return fopen(path, mode); @@ -114,29 +126,69 @@ STATIC_INLINE int max(int x, int y) return x > y ? x : y; } +#if defined(CPU_AARCH64) + STATIC_INLINE void atomic_and(volatile uae_atomic *p, uae_u32 v) { - __sync_and_and_fetch(p, v); + __atomic_and_fetch(p, v, __ATOMIC_ACQ_REL); } STATIC_INLINE void atomic_or(volatile uae_atomic *p, uae_u32 v) { - __sync_or_and_fetch(p, v); + __atomic_or_fetch(p, v, __ATOMIC_ACQ_REL); } -STATIC_INLINE uae_atomic atomic_inc(volatile uae_atomic *p) +STATIC_INLINE void atomic_inc(volatile uae_atomic *p) { - return __sync_add_and_fetch(p, 1); -} -STATIC_INLINE uae_atomic atomic_dec(volatile uae_atomic *p) -{ - return __sync_sub_and_fetch(p, 1); + __atomic_add_fetch(p, 1, __ATOMIC_ACQ_REL); } STATIC_INLINE uae_u32 atomic_bit_test_and_reset(volatile uae_atomic *p, uae_u32 v) { - long mask = (1 << v); - uae_u32 res = __sync_fetch_and_and(p, ~mask); - return (res && mask); + uae_u32 mask = (1 << v); + uae_u32 res = __atomic_fetch_and(p, ~mask, __ATOMIC_ACQ_REL); + return (res & mask); } STATIC_INLINE void atomic_set(volatile uae_atomic *p, uae_u32 v) +{ + __atomic_store_n(p, v, __ATOMIC_ACQ_REL); +} + +#else + +STATIC_INLINE uae_u32 atomic_fetch(volatile uae_atomic * p) +{ + return *p; +} +STATIC_INLINE void atomic_and(volatile uae_atomic * p, uae_u32 v) +{ + __sync_and_and_fetch(p, v); +} +STATIC_INLINE void atomic_or(volatile uae_atomic * p, uae_u32 v) +{ + __sync_or_and_fetch(p, v); +} +STATIC_INLINE void atomic_inc(volatile uae_atomic *p) +{ + __sync_add_and_fetch(p, 1); +} +STATIC_INLINE uae_u32 atomic_bit_test_and_reset(volatile uae_atomic * p, uae_u32 v) +{ + uae_u32 mask = (1 << v); + uae_u32 res = __sync_fetch_and_and(p, ~mask); + return (res & mask); +} +STATIC_INLINE void atomic_set(volatile uae_atomic * p, uae_u32 v) { __sync_lock_test_and_set(p, v); -} \ No newline at end of file +} + +#endif + +#ifdef USE_JIT_FPU +#ifdef __cplusplus + extern "C" { +#endif + void save_host_fp_regs(void* buf); + void restore_host_fp_regs(void* buf); +#ifdef __cplusplus + } +#endif +#endif diff --git a/src/readcpu.cpp b/src/readcpu.cpp index 915373dc..6558ecc0 100644 --- a/src/readcpu.cpp +++ b/src/readcpu.cpp @@ -5,7 +5,6 @@ * * Copyright 1995,1996 Bernd Schmidt */ -#include #include "sysdeps.h" #include "readcpu.h" @@ -123,7 +122,6 @@ struct mnemolookup lookuptab[] = { { i_FScc, _T("FScc") }, { i_FTRAPcc, _T("FTRAPcc") }, { i_FBcc, _T("FBcc") }, - { i_FBcc, _T("FBcc") }, { i_FSAVE, _T("FSAVE") }, { i_FRESTORE, _T("FRESTORE") }, @@ -196,7 +194,7 @@ STATIC_INLINE amodes mode_from_mr (int mode, int reg) return (amodes)0; } -static void build_insn(int insn) +static void build_insn (int insn) { int find = -1; int variants; @@ -205,90 +203,61 @@ static void build_insn(int insn) int i, n; int flaglive = 0, flagdead = 0; - int cflow = 0; + int cflow = 0; - // Mask of flags set/used - unsigned char flags_set = 0; - unsigned char flags_used = 0; + // Mask of flags set/used + unsigned char flags_set = 0; + unsigned char flags_used = 0; id = defs68k[insn]; - // Control flow information - cflow = id.cflow; + // Control flow information + cflow = id.cflow; - for (i = 0, n = 4; i < 5; i++, n--) - { - switch (id.flaginfo[i].flagset) - { - case fa_unset: - case fa_isjmp: - break; - default: - flags_set |= (1 << n); - } + for (i = 0, n = 4; i < 5; i++, n--) { + switch (id.flaginfo[i].flagset) { + case fa_unset: + case fa_isjmp: + break; + default: + flags_set |= (1 << n); + } - switch (id.flaginfo[i].flaguse) - { - case fu_unused: - case fu_isjmp: - break; - default: - flags_used |= (1 << n); - } - } + switch (id.flaginfo[i].flaguse) { + case fu_unused: + case fu_isjmp: + break; + default: + flags_used |= (1 << n); + } + } - for (i = 0; i < 5; i++) - { - switch (id.flaginfo[i].flagset) - { - case fa_unset: - break; - case fa_isjmp: - break; - case fa_zero: - flagdead |= 1 << i; - break; - case fa_one: - flagdead |= 1 << i; - break; - case fa_dontcare: - flagdead |= 1 << i; - break; - case fa_unknown: - flagdead = -1; - goto out1; - case fa_set: - flagdead |= 1 << i; - break; + for (i = 0; i < 5; i++) { + switch (id.flaginfo[i].flagset){ + case fa_unset: break; + case fa_isjmp: break; + case fa_zero: flagdead |= 1 << i; break; + case fa_one: flagdead |= 1 << i; break; + case fa_dontcare: flagdead |= 1 << i; break; + case fa_unknown: flagdead = -1; goto out1; + case fa_set: flagdead |= 1 << i; break; } } out1: - for (i = 0; i < 5; i++) - { - switch (id.flaginfo[i].flaguse) - { - case fu_unused: - break; - case fu_isjmp: - flaglive |= 1 << i; - break; - case fu_maybecc: - flaglive |= 1 << i; - break; - case fu_unknown: - flaglive = -1; - goto out2; - case fu_used: - flaglive |= 1 << i; - break; + for (i = 0; i < 5; i++) { + switch (id.flaginfo[i].flaguse) { + case fu_unused: break; + case fu_isjmp: flaglive |= 1 << i; break; + case fu_maybecc: flaglive |= 1 << i; break; + case fu_unknown: flaglive = -1; goto out2; + case fu_used: flaglive |= 1 << i; break; } } out2: opcstr = id.opcstr; - for (variants = 0; variants < (1 << id.n_variable); variants++) - { + for (variants = 0; variants < (1 << id.n_variable); variants++) { int bitcnt[lastbit]; int bitval[lastbit]; int bitpos[lastbit]; @@ -307,19 +276,19 @@ out2: int usesrc = 0, usedst = 0; int srctype = 0; int srcpos = -1, dstpos = -1; + int usecc = 0; amodes srcmode = am_unknown, destmode = am_unknown; int srcreg = -1, destreg = -1; - for (i = 0; i < lastbit; i++) + for (i = 0; i < lastbit; i++) { bitcnt[i] = bitval[i] = 0; + } vmsk = 1 << id.n_variable; - for (i = 0, msk = 0x8000; i < 16; i++, msk >>= 1) - { - if (!(msk & id.mask)) - { + for (i = 0, msk = 0x8000; i < 16; i++, msk >>= 1) { + if (!(msk & id.mask)) { int currbit = id.bitpos[bitno++]; int bit_set; vmsk >>= 1; @@ -330,11 +299,12 @@ out2: bitcnt[currbit]++; bitval[currbit] <<= 1; bitval[currbit] |= bit_set; + if (currbit == bitC || currbit == bitc) + usecc = 1; } } - if (bitval[bitj] == 0) - bitval[bitj] = 8; + if (bitval[bitj] == 0) bitval[bitj] = 8; /* first check whether this one does not match after all */ if (bitval[bitz] == 3 || bitval[bitC] == 1) continue; @@ -345,69 +315,40 @@ out2: continue; /* bitI and bitC get copied to biti and bitc */ - if (bitcnt[bitI]) - { - bitval[biti] = bitval[bitI]; - bitpos[biti] = bitpos[bitI]; + if (bitcnt[bitI]) { + bitval[biti] = bitval[bitI]; bitpos[biti] = bitpos[bitI]; } if (bitcnt[bitC]) bitval[bitc] = bitval[bitC]; pos = 0; - while (opcstr[pos] && !_istspace(opcstr[pos])) - { - if (opcstr[pos] == '.') - { + while (opcstr[pos] && !_istspace(opcstr[pos])) { + if (opcstr[pos] == '.') { pos++; unsized = 0; - switch (opcstr[pos]) - { + switch (opcstr[pos]) { - case 'B': - sz = sz_byte; - break; - case 'W': - sz = sz_word; - break; - case 'L': - sz = sz_long; - break; + case 'B': sz = sz_byte; break; + case 'W': sz = sz_word; break; + case 'L': sz = sz_long; break; case 'z': - switch (bitval[bitz]) - { - case 0: - sz = sz_byte; - break; - case 1: - sz = sz_word; - break; - case 2: - sz = sz_long; - break; - default: - abort(); + switch (bitval[bitz]) { + case 0: sz = sz_byte; break; + case 1: sz = sz_word; break; + case 2: sz = sz_long; break; + default: abort(); } break; - default: - abort(); + default: abort(); } - } - else - { + } else { mnemonic[mnp] = opcstr[pos]; - if (mnemonic[mnp] == 'f') - { + if (mnemonic[mnp] == 'f') { find = -1; - switch (bitval[bitf]) - { - case 0: - mnemonic[mnp] = 'R'; - break; - case 1: - mnemonic[mnp] = 'L'; - break; - default: - abort(); + switch (bitval[bitf]) { + case 0: mnemonic[mnp] = 'R'; break; + case 1: mnemonic[mnp] = 'L'; break; + default: abort(); } } mnp++; @@ -426,209 +367,136 @@ out2: /* parse the source address */ usesrc = 1; - switch (opcstr[pos++]) - { + switch (opcstr[pos++]) { case 'D': srcmode = Dreg; - switch (opcstr[pos++]) - { - case 'r': - srcreg = bitval[bitr]; - srcgather = 1; - srcpos = bitpos[bitr]; - break; - case 'R': - srcreg = bitval[bitR]; - srcgather = 1; - srcpos = bitpos[bitR]; - break; - default: - abort(); + switch (opcstr[pos++]) { + case 'r': srcreg = bitval[bitr]; srcgather = 1; srcpos = bitpos[bitr]; break; + case 'R': srcreg = bitval[bitR]; srcgather = 1; srcpos = bitpos[bitR]; break; + default: abort(); } break; case 'A': srcmode = Areg; - switch (opcstr[pos++]) - { - case 'l': - srcmode = absl; - break; - case 'r': - srcreg = bitval[bitr]; - srcgather = 1; - srcpos = bitpos[bitr]; - break; - case 'R': - srcreg = bitval[bitR]; - srcgather = 1; - srcpos = bitpos[bitR]; - break; - default: - abort(); + switch (opcstr[pos++]) { + case 'l': srcmode = absl; break; + case 'r': srcreg = bitval[bitr]; srcgather = 1; srcpos = bitpos[bitr]; break; + case 'R': srcreg = bitval[bitR]; srcgather = 1; srcpos = bitpos[bitR]; break; + default: abort(); } - switch (opcstr[pos]) - { - case 'p': - srcmode = Apdi; - pos++; - break; - case 'P': - srcmode = Aipi; - pos++; - break; - case 'a': - srcmode = Aind; - pos++; - break; + switch (opcstr[pos]) { + case 'p': srcmode = Apdi; pos++; break; + case 'P': srcmode = Aipi; pos++; break; + case 'a': srcmode = Aind; pos++; break; } break; case 'L': srcmode = absl; break; case '#': - switch (opcstr[pos++]) - { - case 'z': - srcmode = imm; - break; - case '0': - srcmode = imm0; - break; - case '1': - srcmode = imm1; - break; - case '2': - srcmode = imm2; - break; - case 'i': - srcmode = immi; - srcreg = (uae_s32)(uae_s8)bitval[biti]; - if (CPU_EMU_SIZE < 4) - { + switch (opcstr[pos++]) { + case 'z': srcmode = imm; break; + case '0': srcmode = imm0; break; + case '1': srcmode = imm1; break; + case '2': srcmode = imm2; break; + case 'i': srcmode = immi; srcreg = (uae_s32)(uae_s8)bitval[biti]; + if (CPU_EMU_SIZE < 4) { /* Used for branch instructions */ srctype = 1; srcgather = 1; srcpos = bitpos[biti]; } break; - case 'j': - srcmode = immi; - srcreg = bitval[bitj]; - if (CPU_EMU_SIZE < 3) - { + case 'j': srcmode = immi; srcreg = bitval[bitj]; + if (CPU_EMU_SIZE < 3) { /* 1..8 for ADDQ/SUBQ and rotshi insns */ srcgather = 1; srctype = 3; srcpos = bitpos[bitj]; } break; - case 'J': - srcmode = immi; - srcreg = bitval[bitJ]; - if (CPU_EMU_SIZE < 5) - { + case 'J': srcmode = immi; srcreg = bitval[bitJ]; + if (CPU_EMU_SIZE < 5) { /* 0..15 */ srcgather = 1; srctype = 2; srcpos = bitpos[bitJ]; } break; - case 'k': - srcmode = immi; - srcreg = bitval[bitk]; - if (CPU_EMU_SIZE < 3) - { + case 'k': srcmode = immi; srcreg = bitval[bitk]; + if (CPU_EMU_SIZE < 3) { srcgather = 1; srctype = 4; srcpos = bitpos[bitk]; } break; - case 'K': - srcmode = immi; - srcreg = bitval[bitK]; - if (CPU_EMU_SIZE < 5) - { + case 'K': srcmode = immi; srcreg = bitval[bitK]; + if (CPU_EMU_SIZE < 5) { /* 0..15 */ srcgather = 1; srctype = 5; srcpos = bitpos[bitK]; } break; - case 'E': - srcmode = immi; - srcreg = bitval[bitE]; - if (CPU_EMU_SIZE < 5) - { - /* 1..255 */ - srcgather = 1; - srctype = 6; - srcpos = bitpos[bitE]; - } - break; - case 'p': - srcmode = immi; - srcreg = bitval[bitp]; - if (CPU_EMU_SIZE < 5) - { + case 'E': srcmode = immi; srcreg = bitval[bitE]; + if (CPU_EMU_SIZE < 5) { + /* 1..255 */ + srcgather = 1; + srctype = 6; + srcpos = bitpos[bitE]; + } + break; + case 'p': srcmode = immi; srcreg = bitval[bitp]; + if (CPU_EMU_SIZE < 5) { /* 0..3 */ srcgather = 1; srctype = 7; srcpos = bitpos[bitp]; } break; - default: - abort(); + default: abort(); } break; case 'd': srcreg = bitval[bitD]; - srcmode = mode_from_mr(bitval[bitd], bitval[bitD]); + srcmode = mode_from_mr(bitval[bitd],bitval[bitD]); if (srcmode == am_illg) continue; if (CPU_EMU_SIZE < 2 && - (srcmode == Areg || srcmode == Dreg || srcmode == Aind || srcmode == Ad16 || srcmode == Ad8r || srcmode == Aipi || srcmode == Apdi)) + (srcmode == Areg || srcmode == Dreg || srcmode == Aind + || srcmode == Ad16 || srcmode == Ad8r || srcmode == Aipi + || srcmode == Apdi)) { - srcgather = 1; - srcpos = bitpos[bitD]; + srcgather = 1; srcpos = bitpos[bitD]; } - if (opcstr[pos] == '[') - { + if (opcstr[pos] == '[') { pos++; - if (opcstr[pos] == '!') - { + if (opcstr[pos] == '!') { /* exclusion */ - do - { + do { pos++; - if (mode_from_str(opcstr + pos) == srcmode) + if (mode_from_str(opcstr+pos) == srcmode) goto nomatch; pos += 4; } while (opcstr[pos] == ','); pos++; - } - else - { - if (opcstr[pos + 4] == '-') - { + } else { + if (opcstr[pos+4] == '-') { /* replacement */ - if (mode_from_str(opcstr + pos) == srcmode) - srcmode = mode_from_str(opcstr + pos + 5); + if (mode_from_str(opcstr+pos) == srcmode) + srcmode = mode_from_str(opcstr+pos+5); else goto nomatch; pos += 10; - } - else - { + } else { /* normal */ - while (mode_from_str(opcstr + pos) != srcmode) - { + while(mode_from_str(opcstr+pos) != srcmode) { pos += 4; if (opcstr[pos] == ']') goto nomatch; pos++; } - while (opcstr[pos] != ']') - pos++; + while(opcstr[pos] != ']') pos++; pos++; break; } @@ -640,64 +508,56 @@ out2: break; case 's': srcreg = bitval[bitS]; - srcmode = mode_from_mr(bitval[bits], bitval[bitS]); + srcmode = mode_from_mr(bitval[bits],bitval[bitS]); if (srcmode == am_illg) continue; if (CPU_EMU_SIZE < 2 && - (srcmode == Areg || srcmode == Dreg || srcmode == Aind || srcmode == Ad16 || srcmode == Ad8r || srcmode == Aipi || srcmode == Apdi)) + (srcmode == Areg || srcmode == Dreg || srcmode == Aind + || srcmode == Ad16 || srcmode == Ad8r || srcmode == Aipi + || srcmode == Apdi)) { - srcgather = 1; - srcpos = bitpos[bitS]; + srcgather = 1; srcpos = bitpos[bitS]; } - if (opcstr[pos] == '[') - { + if (opcstr[pos] == '[') { pos++; - if (opcstr[pos] == '!') - { + if (opcstr[pos] == '!') { /* exclusion */ - do - { + do { pos++; - if (mode_from_str(opcstr + pos) == srcmode) + if (mode_from_str(opcstr+pos) == srcmode) goto nomatch; pos += 4; } while (opcstr[pos] == ','); pos++; - } - else - { - if (opcstr[pos + 4] == '-') - { + } else { + if (opcstr[pos+4] == '-') { /* replacement */ - if (mode_from_str(opcstr + pos) == srcmode) - srcmode = mode_from_str(opcstr + pos + 5); + if (mode_from_str(opcstr+pos) == srcmode) + srcmode = mode_from_str(opcstr+pos+5); else goto nomatch; pos += 10; - } - else - { + } else { /* normal */ - while (mode_from_str(opcstr + pos) != srcmode) - { + while(mode_from_str(opcstr+pos) != srcmode) { pos += 4; if (opcstr[pos] == ']') goto nomatch; pos++; } - while (opcstr[pos] != ']') - pos++; + while(opcstr[pos] != ']') pos++; pos++; } } } break; - default: - abort(); + default: abort(); } /* safety check - might have changed */ - if (srcmode != Areg && srcmode != Dreg && srcmode != Aind && srcmode != Ad16 && srcmode != Ad8r && srcmode != Aipi && srcmode != Apdi && srcmode != immi) + if (srcmode != Areg && srcmode != Dreg && srcmode != Aind + && srcmode != Ad16 && srcmode != Ad8r && srcmode != Aipi + && srcmode != Apdi && srcmode != immi) { srcgather = 0; } @@ -710,159 +570,91 @@ out2: /* parse the destination address */ usedst = 1; - switch (opcstr[pos++]) - { + switch (opcstr[pos++]) { case 'D': destmode = Dreg; - switch (opcstr[pos++]) - { - case 'r': - destreg = bitval[bitr]; - dstgather = 1; - dstpos = bitpos[bitr]; - break; - case 'R': - destreg = bitval[bitR]; - dstgather = 1; - dstpos = bitpos[bitR]; - break; - default: - abort(); + switch (opcstr[pos++]) { + case 'r': destreg = bitval[bitr]; dstgather = 1; dstpos = bitpos[bitr]; break; + case 'R': destreg = bitval[bitR]; dstgather = 1; dstpos = bitpos[bitR]; break; + default: abort(); } if (dstpos < 0 || dstpos >= 32) - abort(); + abort (); break; case 'A': destmode = Areg; - switch (opcstr[pos++]) - { - case 'l': - destmode = absl; - break; - case 'r': - destreg = bitval[bitr]; - dstgather = 1; - dstpos = bitpos[bitr]; - break; - case 'R': - destreg = bitval[bitR]; - dstgather = 1; - dstpos = bitpos[bitR]; - break; - case 'x': - destreg = 0; - dstgather = 0; - dstpos = 0; - break; - default: - abort(); + switch (opcstr[pos++]) { + case 'l': destmode = absl; break; + case 'r': destreg = bitval[bitr]; dstgather = 1; dstpos = bitpos[bitr]; break; + case 'R': destreg = bitval[bitR]; dstgather = 1; dstpos = bitpos[bitR]; break; + case 'x': destreg = 0; dstgather = 0; dstpos = 0; break; + default: abort(); } - if (destmode != absl && (dstpos < 0 || dstpos >= 32)) - abort(); - switch (opcstr[pos]) - { - case 'p': - destmode = Apdi; - pos++; - break; - case 'P': - destmode = Aipi; - pos++; - break; + if (destmode != absl && (dstpos < 0 || dstpos >= 32)) + abort (); + switch (opcstr[pos]) { + case 'p': destmode = Apdi; pos++; break; + case 'P': destmode = Aipi; pos++; break; } break; case 'L': destmode = absl; break; case '#': - switch (opcstr[pos++]) - { - case 'z': - destmode = imm; - break; - case '0': - destmode = imm0; - break; - case '1': - destmode = imm1; - break; - case '2': - destmode = imm2; - break; - case 'i': - destmode = immi; - destreg = (uae_s32)(uae_s8)bitval[biti]; - break; - case 'j': - destmode = immi; - destreg = bitval[bitj]; - break; - case 'J': - destmode = immi; - destreg = bitval[bitJ]; - break; - case 'k': - destmode = immi; - destreg = bitval[bitk]; - break; - case 'K': - destmode = immi; - destreg = bitval[bitK]; - break; - default: - abort(); + switch (opcstr[pos++]) { + case 'z': destmode = imm; break; + case '0': destmode = imm0; break; + case '1': destmode = imm1; break; + case '2': destmode = imm2; break; + case 'i': destmode = immi; destreg = (uae_s32)(uae_s8)bitval[biti]; break; + case 'j': destmode = immi; destreg = bitval[bitj]; break; + case 'J': destmode = immi; destreg = bitval[bitJ]; break; + case 'k': destmode = immi; destreg = bitval[bitk]; break; + case 'K': destmode = immi; destreg = bitval[bitK]; break; + default: abort(); } break; case 'd': destreg = bitval[bitD]; - destmode = mode_from_mr(bitval[bitd], bitval[bitD]); + destmode = mode_from_mr(bitval[bitd],bitval[bitD]); if (destmode == am_illg) continue; if (CPU_EMU_SIZE < 1 && - (destmode == Areg || destmode == Dreg || destmode == Aind || destmode == Ad16 || destmode == Ad8r || destmode == Aipi || destmode == Apdi)) + (destmode == Areg || destmode == Dreg || destmode == Aind + || destmode == Ad16 || destmode == Ad8r || destmode == Aipi + || destmode == Apdi)) { - dstgather = 1; - dstpos = bitpos[bitD]; + dstgather = 1; dstpos = bitpos[bitD]; } - if (opcstr[pos] == '[') - { + if (opcstr[pos] == '[') { pos++; - if (opcstr[pos] == '!') - { + if (opcstr[pos] == '!') { /* exclusion */ - do - { + do { pos++; - if (mode_from_str(opcstr + pos) == destmode) + if (mode_from_str(opcstr+pos) == destmode) goto nomatch; pos += 4; } while (opcstr[pos] == ','); pos++; - } - else - { - if (opcstr[pos + 4] == '-') - { + } else { + if (opcstr[pos+4] == '-') { /* replacement */ - if (mode_from_str(opcstr + pos) == destmode) - destmode = mode_from_str(opcstr + pos + 5); + if (mode_from_str(opcstr+pos) == destmode) + destmode = mode_from_str(opcstr+pos+5); else goto nomatch; pos += 10; - } - else - { + } else { /* normal */ - while (mode_from_str(opcstr + pos) != destmode) - { + while(mode_from_str(opcstr+pos) != destmode) { pos += 4; if (opcstr[pos] == ']') goto nomatch; pos++; } - while (opcstr[pos] != ']') - pos++; + while(opcstr[pos] != ']') pos++; pos++; break; } @@ -874,101 +666,93 @@ out2: break; case 's': destreg = bitval[bitS]; - destmode = mode_from_mr(bitval[bits], bitval[bitS]); + destmode = mode_from_mr(bitval[bits],bitval[bitS]); if (destmode == am_illg) continue; if (CPU_EMU_SIZE < 1 && - (destmode == Areg || destmode == Dreg || destmode == Aind || destmode == Ad16 || destmode == Ad8r || destmode == Aipi || destmode == Apdi)) + (destmode == Areg || destmode == Dreg || destmode == Aind + || destmode == Ad16 || destmode == Ad8r || destmode == Aipi + || destmode == Apdi)) { - dstgather = 1; - dstpos = bitpos[bitS]; + dstgather = 1; dstpos = bitpos[bitS]; } - if (opcstr[pos] == '[') - { + if (opcstr[pos] == '[') { pos++; - if (opcstr[pos] == '!') - { + if (opcstr[pos] == '!') { /* exclusion */ - do - { + do { pos++; - if (mode_from_str(opcstr + pos) == destmode) + if (mode_from_str(opcstr+pos) == destmode) goto nomatch; pos += 4; } while (opcstr[pos] == ','); pos++; - } - else - { - if (opcstr[pos + 4] == '-') - { + } else { + if (opcstr[pos+4] == '-') { /* replacement */ - if (mode_from_str(opcstr + pos) == destmode) - destmode = mode_from_str(opcstr + pos + 5); + if (mode_from_str(opcstr+pos) == destmode) + destmode = mode_from_str(opcstr+pos+5); else goto nomatch; pos += 10; - } - else - { + } else { /* normal */ - while (mode_from_str(opcstr + pos) != destmode) - { + while(mode_from_str(opcstr+pos) != destmode) { pos += 4; if (opcstr[pos] == ']') goto nomatch; pos++; } - while (opcstr[pos] != ']') - pos++; + while(opcstr[pos] != ']') pos++; pos++; } } } break; - default: - abort(); + default: abort(); } /* safety check - might have changed */ - if (destmode != Areg && destmode != Dreg && destmode != Aind && destmode != Ad16 && destmode != Ad8r && destmode != Aipi && destmode != Apdi) + if (destmode != Areg && destmode != Dreg && destmode != Aind + && destmode != Ad16 && destmode != Ad8r && destmode != Aipi + && destmode != Apdi) { dstgather = 0; } if (destmode == Areg && sz == sz_byte) goto nomatch; - endofline: +endofline: /* now, we have a match */ if (table68k[opc].mnemo != i_ILLG) - ; //write_log (_T("Double match: %x: %s\n"), opc, opcstr); - if (find == -1) - { - for (find = 0;; find++) - { - if (_tcscmp(mnemonic, lookuptab[find].name) == 0) - { + ;//write_log (_T("Double match: %x: %s\n"), opc, opcstr); + if (find == -1) { + for (find = 0;; find++) { + if (_tcscmp (mnemonic, lookuptab[find].name) == 0) { table68k[opc].mnemo = lookuptab[find].mnemo; break; } - if (_tcslen(lookuptab[find].name) == 0) + if (_tcslen (lookuptab[find].name) == 0) abort(); } } - else - { + else { table68k[opc].mnemo = lookuptab[find].mnemo; } table68k[opc].cc = bitval[bitc]; + table68k[opc].ccuse = usecc != 0; + mnemo = table68k[opc].mnemo; - if (mnemo == i_BTST || mnemo == i_BSET || mnemo == i_BCLR || mnemo == i_BCHG) + if (mnemo == i_BTST + || mnemo == i_BSET + || mnemo == i_BCLR + || mnemo == i_BCHG) { sz = destmode == Dreg ? sz_long : sz_byte; unsized = 0; } - if (mnemo == i_JSR || mnemo == i_JMP) - { + if (mnemo == i_JSR || mnemo == i_JMP) { unsized = 1; } @@ -992,167 +776,108 @@ out2: table68k[opc].clocks = id.clocks; table68k[opc].fetchmode = id.fetchmode; - // Fix flags used information for Scc, Bcc, TRAPcc, DBcc instructions - if (table68k[opc].mnemo == i_Scc || table68k[opc].mnemo == i_Bcc || table68k[opc].mnemo == i_DBcc || table68k[opc].mnemo == i_TRAPcc) - { - switch (table68k[opc].cc) - { - // CC mask: XNZVC - // 8421 - case 0: - flags_used = 0x00; - break; /* T */ - case 1: - flags_used = 0x00; - break; /* F */ - case 2: - flags_used = 0x05; - break; /* HI */ - case 3: - flags_used = 0x05; - break; /* LS */ - case 4: - flags_used = 0x01; - break; /* CC */ - case 5: - flags_used = 0x01; - break; /* CS */ - case 6: - flags_used = 0x04; - break; /* NE */ - case 7: - flags_used = 0x04; - break; /* EQ */ - case 8: - flags_used = 0x02; - break; /* VC */ - case 9: - flags_used = 0x02; - break; /* VS */ - case 10: - flags_used = 0x08; - break; /* PL */ - case 11: - flags_used = 0x08; - break; /* MI */ - case 12: - flags_used = 0x0A; - break; /* GE */ - case 13: - flags_used = 0x0A; - break; /* LT */ - case 14: - flags_used = 0x0E; - break; /* GT */ - case 15: - flags_used = 0x0E; - break; /* LE */ - } + // Fix flags used information for Scc, Bcc, TRAPcc, DBcc instructions + if ( table68k[opc].mnemo == i_Scc + || table68k[opc].mnemo == i_Bcc + || table68k[opc].mnemo == i_DBcc + || table68k[opc].mnemo == i_TRAPcc + ) { + switch (table68k[opc].cc) { + // CC mask: XNZVC + // 8421 + case 0: flags_used = 0x00; break; /* T */ + case 1: flags_used = 0x00; break; /* F */ + case 2: flags_used = 0x05; break; /* HI */ + case 3: flags_used = 0x05; break; /* LS */ + case 4: flags_used = 0x01; break; /* CC */ + case 5: flags_used = 0x01; break; /* CS */ + case 6: flags_used = 0x04; break; /* NE */ + case 7: flags_used = 0x04; break; /* EQ */ + case 8: flags_used = 0x02; break; /* VC */ + case 9: flags_used = 0x02; break; /* VS */ + case 10:flags_used = 0x08; break; /* PL */ + case 11:flags_used = 0x08; break; /* MI */ + case 12:flags_used = 0x0A; break; /* GE */ + case 13:flags_used = 0x0A; break; /* LT */ + case 14:flags_used = 0x0E; break; /* GT */ + case 15:flags_used = 0x0E; break; /* LE */ } + } #if 1 - /* gb-- flagdead and flaglive would not have correct information */ - table68k[opc].flagdead = flags_set; - table68k[opc].flaglive = flags_used; + /* gb-- flagdead and flaglive would not have correct information */ + table68k[opc].flagdead = flags_set; + table68k[opc].flaglive = flags_used; #else table68k[opc].flagdead = flagdead; table68k[opc].flaglive = flaglive; #endif - table68k[opc].cflow = cflow; - nomatch: + table68k[opc].cflow = cflow; +nomatch: /* FOO! */; } } -void read_table68k(void) + +void read_table68k (void) { int i; - free(table68k); - table68k = xmalloc(struct instr, 65536); - for (i = 0; i < 65536; i++) - { + free (table68k); + table68k = xmalloc (struct instr, 65536); + for (i = 0; i < 65536; i++) { table68k[i].mnemo = i_ILLG; table68k[i].handler = -1; } - for (i = 0; i < n_defs68k; i++) - { - build_insn(i); + for (i = 0; i < n_defs68k; i++) { + build_insn (i); } } static int imismatch; -static void handle_merges(long int opcode) +static void handle_merges (long int opcode) { uae_u16 smsk; uae_u16 dmsk; int sbitdst, dstend; int srcreg, dstreg; - if (table68k[opcode].spos == -1) - { - sbitdst = 1; - smsk = 0; - } - else - { - switch (table68k[opcode].stype) - { + if (table68k[opcode].spos == -1) { + sbitdst = 1; smsk = 0; + } else { + switch (table68k[opcode].stype) { case 0: - smsk = 7; - sbitdst = 8; - break; + smsk = 7; sbitdst = 8; break; case 1: - smsk = 255; - sbitdst = 256; - break; + smsk = 255; sbitdst = 256; break; case 2: - smsk = 15; - sbitdst = 16; - break; + smsk = 15; sbitdst = 16; break; case 3: - smsk = 7; - sbitdst = 8; - break; + smsk = 7; sbitdst = 8; break; case 4: - smsk = 7; - sbitdst = 8; - break; + smsk = 7; sbitdst = 8; break; case 5: - smsk = 63; - sbitdst = 64; - break; - case 6: - smsk = 255; - sbitdst = 256; - break; + smsk = 63; sbitdst = 64; break; + case 6: + smsk = 255; sbitdst = 256; break; case 7: - smsk = 3; - sbitdst = 4; - break; + smsk = 3; sbitdst = 4; break; default: - smsk = 0; - sbitdst = 0; + smsk = 0; sbitdst = 0; abort(); break; } smsk <<= table68k[opcode].spos; } - if (table68k[opcode].dpos == -1) - { - dstend = 1; - dmsk = 0; - } - else - { + if (table68k[opcode].dpos == -1) { + dstend = 1; dmsk = 0; + } else { dmsk = 7 << table68k[opcode].dpos; dstend = 8; } - for (srcreg = 0; srcreg < sbitdst; srcreg++) - { - for (dstreg = 0; dstreg < dstend; dstreg++) - { + for (srcreg=0; srcreg < sbitdst; srcreg++) { + for (dstreg=0; dstreg < dstend; dstreg++) { uae_u16 code = (uae_u16)opcode; code = (code & ~smsk) | (srcreg << table68k[opcode].spos); @@ -1161,20 +886,25 @@ static void handle_merges(long int opcode) /* Check whether this is in fact the same instruction. * The instructions should never differ, except for the * Bcc.(BW) case. */ - if (table68k[code].mnemo != table68k[opcode].mnemo || table68k[code].size != table68k[opcode].size || table68k[code].suse != table68k[opcode].suse || table68k[code].duse != table68k[opcode].duse) + if (table68k[code].mnemo != table68k[opcode].mnemo + || table68k[code].size != table68k[opcode].size + || table68k[code].suse != table68k[opcode].suse + || table68k[code].duse != table68k[opcode].duse) { - imismatch++; - continue; + imismatch++; continue; } - if (table68k[opcode].suse && (table68k[opcode].spos != table68k[code].spos || table68k[opcode].smode != table68k[code].smode || table68k[opcode].stype != table68k[code].stype)) + if (table68k[opcode].suse + && (table68k[opcode].spos != table68k[code].spos + || table68k[opcode].smode != table68k[code].smode + || table68k[opcode].stype != table68k[code].stype)) { - imismatch++; - continue; + imismatch++; continue; } - if (table68k[opcode].duse && (table68k[opcode].dpos != table68k[code].dpos || table68k[opcode].dmode != table68k[code].dmode)) + if (table68k[opcode].duse + && (table68k[opcode].dpos != table68k[code].dpos + || table68k[opcode].dmode != table68k[code].dmode)) { - imismatch++; - continue; + imismatch++; continue; } if (code != opcode) @@ -1183,22 +913,21 @@ static void handle_merges(long int opcode) } } -void do_merges(void) +void do_merges (void) { long int opcode; int nr = 0; imismatch = 0; - for (opcode = 0; opcode < 65536; opcode++) - { + for (opcode = 0; opcode < 65536; opcode++) { if (table68k[opcode].handler != -1 || table68k[opcode].mnemo == i_ILLG) continue; nr++; - handle_merges(opcode); + handle_merges (opcode); } nr_cpuop_funcs = nr; } -int get_no_mismatches(void) +int get_no_mismatches (void) { return imismatch; } diff --git a/src/rommgr.cpp b/src/rommgr.cpp index 997aa8ce..bf772d59 100644 --- a/src/rommgr.cpp +++ b/src/rommgr.cpp @@ -21,8 +21,6 @@ #include "autoconf.h" #include "filesys.h" -#define SAVE_ROM 0 - static struct romlist *rl; static int romlist_cnt; @@ -101,7 +99,7 @@ struct romdata *getromdatabypath(const TCHAR *path) return NULL; } -#define NEXT_ROM_ID 251 +#define NEXT_ROM_ID 255 #define ALTROM(id,grp,num,size,flags,crc32,a,b,c,d,e) \ { _T("X"), 0, 0, 0, 0, 0, size, id, 0, 0, flags, (grp << 16) | num, 0, NULL, crc32, a, b, c, d, e }, @@ -920,12 +918,6 @@ static void romlist_cleanup (void) } i++; } -#if 0 - for (i = 0; i < romlist_cnt; i++) { - struct romlist *rll = &rl[i]; - write_log (_T("%d: %08x %s (%s)\n"), rll->rd->id, rll->rd->group, rll->rd->name, rll->path); - } -#endif } struct romlist **getromlistbyident (int ver, int rev, int subver, int subrev, const TCHAR *model, int romflags, bool all) @@ -1206,7 +1198,7 @@ int load_keyring (struct uae_prefs *p, const TCHAR *path) break; case 1: if (p) { - _tcscpy (tmp, p->path_rom); + _tcscpy (tmp, p->path_rom.path[0]); _tcscat (tmp, _T("rom.key")); } break; @@ -1437,9 +1429,7 @@ int decode_rom (uae_u8 *mem, int size, int mode, int real_size) { if (mode == 1) { if (!decode_cloanto_rom_do (mem, size, real_size)) { -#ifndef SINGLEFILE notify_user (NUMSG_NOROMKEY); -#endif return 0; } return 1; @@ -1465,16 +1455,6 @@ struct romdata *getromdatabydata (uae_u8 *rom, int size) rom = tmpbuf; size = tmpsize; } -#if 0 - if (size > 0x6c + 524288 && !memcmp (rom, "AMIG", 4)) { - uae_u8 *tmpbuf = (uae_u8*)xmalloc (uae_u8, size); - int tmpsize = size - 0x6c; - memcpy (tmpbuf, rom + 0x6c, tmpsize); - decode_rom (tmpbuf, tmpsize, 2, tmpsize); - rom = tmpbuf; - size = tmpsize; - } -#endif get_sha1 (rom, size, sha1); ret = checkromdata(sha1, size, -1); if (!ret) { @@ -1532,6 +1512,8 @@ void getromname (const struct romdata *rd, TCHAR *name) _stprintf (name + _tcslen (name), _T(" [%s]"), rd->partnumber); } +static struct romlist *getromlistbyids (const int *ids, const TCHAR *romname); + struct romlist *getromlistbyromdata (const struct romdata *rd) { int ids[2]; @@ -1541,7 +1523,7 @@ struct romlist *getromlistbyromdata (const struct romdata *rd) return getromlistbyids(ids, NULL); } -struct romlist *getromlistbyromtype(uae_u32 romtype, const TCHAR *romname) +static struct romlist *getromlistbyromtype(uae_u32 romtype, const TCHAR *romname) { int i = 0; while (roms[i].name) { @@ -1563,7 +1545,7 @@ struct romlist *getromlistbyromtype(uae_u32 romtype, const TCHAR *romname) return NULL; } -struct romlist *getromlistbyids (const int *ids, const TCHAR *romname) +static struct romlist *getromlistbyids (const int *ids, const TCHAR *romname) { struct romdata *rd; int i, j; @@ -1666,7 +1648,6 @@ void romwarning (const int *ids) gui_message (tmp3, tmp2); } - static void byteswap (uae_u8 *buf, int size) { int i; @@ -1702,14 +1683,6 @@ static void mergecd32 (uae_u8 *dst, uae_u8 *src, int size) dst[k + 2] = src[j + 1]; k += 4; } -#if 0 - { - struct zfile *f; - f = zfile_fopen ("c:\\d\\1.rom","wb", ZFD_NORMAL); - zfile_fwrite (dst, 1, size, f); - zfile_fclose(f); - } -#endif } static void descramble (const struct romdata *rd, uae_u8 *data, int size, int odd) @@ -1744,17 +1717,7 @@ static int read_rom_file (uae_u8 *buf, const struct romdata *rd) return 1; } -#if SAVE_ROM -static void save_rom(uae_u8 *rom, int size) -{ - struct zfile *f; - f = zfile_fopen (_T("c:\\temp\\1.rom"), _T("wb")); - zfile_fwrite (rom, 1, size, f); - zfile_fclose(f); -} -#endif - -struct zfile *read_rom (struct romdata *prd) +static struct zfile *read_rom (struct romdata *prd) { struct romdata *rd2 = prd; struct romdata *rd = prd; @@ -1865,10 +1828,6 @@ struct zfile *read_rom (struct romdata *prd) add = 2; } -#if SAVE_ROM - save_rom(buf, size); -#endif - if (notcrc32(crc32) || get_crc32(buf, size) == crc32) { ok = 1; } @@ -2019,7 +1978,7 @@ struct zfile *read_rom_name (const TCHAR *filename) return f; } -struct zfile *read_rom_name_guess (const TCHAR *filename) +struct zfile *read_rom_name_guess (const TCHAR *filename, TCHAR *out) { int i, j; struct zfile *f; @@ -2046,6 +2005,7 @@ struct zfile *read_rom_name_guess (const TCHAR *filename) f = read_rom (rd); if (f) { write_log (_T("ROM %s not found, using %s\n"), filename, rl[i].path); + _tcscpy(out, rl[i].path); return f; } } @@ -2079,9 +2039,7 @@ void kickstart_fix_checksum (uae_u8 *mem, int size) int kickstart_checksum (uae_u8 *mem, int size) { if (!kickstart_checksum_do (mem, size)) { -#ifndef SINGLEFILE notify_user (NUMSG_KSROMCRCERROR); -#endif return 0; } return 1; @@ -2319,7 +2277,7 @@ static bool isspecialrom(const TCHAR *name) return false; } -struct zfile *read_device_from_romconfig(struct romconfig *rc, uae_u32 romtype) +static struct zfile *read_device_from_romconfig(struct romconfig *rc, uae_u32 romtype) { struct zfile *z = NULL; if (isspecialrom(rc->romfile)) diff --git a/src/rtc.cpp b/src/rtc.cpp index b0f17076..15fa7f15 100644 --- a/src/rtc.cpp +++ b/src/rtc.cpp @@ -10,7 +10,7 @@ uae_u8 get_clock_msm(struct rtc_msm_data *data, int addr, struct tm *ct) { - uae_u8 v; + uae_u8 v = 0; int year; if (!ct) { @@ -72,9 +72,6 @@ uae_u8 get_clock_ricoh(struct rtc_ricoh_data *data, int addr, struct tm *ct) /* alarm */ if (bank == 1 && addr < 0x0d) { v = data->rtc_alarm[addr]; -#if CLOCK_DEBUG - write_log (_T("CLOCK ALARM R %X: %X\n"), addr, v); -#endif return v; } if (!ct) { diff --git a/src/savestate.cpp b/src/savestate.cpp index 230b5127..19b0537e 100644 --- a/src/savestate.cpp +++ b/src/savestate.cpp @@ -1,54 +1,57 @@ - /* - * UAE - The Un*x Amiga Emulator - * - * Save/restore emulator state - * - * (c) 1999-2001 Toni Wilen - * - * see below for ASF-structure - */ +/* +* UAE - The Un*x Amiga Emulator +* +* Save/restore emulator state +* +* (c) 1999-2001 Toni Wilen +* +* see below for ASF-structure +*/ - /* Features: - * - * - full CPU state (68000/68010/68020/68030/68040/68060) - * - FPU (68881/68882/68040/68060) - * - full CIA-A and CIA-B state (with all internal registers) - * - saves all custom registers and audio internal state. - * - Chip, Bogo, Fast, Z3 and Picasso96 RAM supported - * - disk drive type, imagefile, track and motor state - * - Kickstart ROM version, address and size is saved. This data is not used during restore yet. - * - Action Replay state is saved - */ +/* Features: +* +* - full CPU state (68000/68010/68020/68030/68040/68060) +* - FPU (68881/68882/68040/68060) +* - full CIA-A and CIA-B state (with all internal registers) +* - saves all custom registers and audio internal state. +* - Chip, Bogo, Fast, Z3 and Picasso96 RAM supported +* - disk drive type, imagefile, track and motor state +* - Kickstart ROM version, address and size is saved. This data is not used during restore yet. +* - Action Replay state is saved +*/ - /* Notes: - * - * - blitter state is not saved, blitter is forced to finish immediately if it - * was active - * - disk DMA state is completely saved - * - does not ask for statefile name and description. Currently uses DF0's disk - * image name (".adf" is replaced with ".asf") - * - only Amiga state is restored, harddisk support, autoconfig, expansion boards etc.. - * are not saved/restored (and probably never will). - * - use this for saving games that can't be saved to disk - */ +/* Notes: +* +* - blitter state is not saved, blitter is forced to finish immediately if it +* was active +* - disk DMA state is completely saved +* - does not ask for statefile name and description. Currently uses DF0's disk +* image name (".adf" is replaced with ".asf") +* - only Amiga state is restored, harddisk support, autoconfig, expansion boards etc.. +* are not saved/restored (and probably never will). +* - use this for saving games that can't be saved to disk +*/ + +/* Usage : +* +* save: +* +* set savestate_state = STATE_DOSAVE, savestate_filename = "..." +* +* restore: +* +* set savestate_state = STATE_DORESTORE, savestate_filename = "..." +* +*/ - /* Usage : - * - * save: - * - * set savestate_state = STATE_DOSAVE, savestate_filename = "..." - * - * restore: - * - * set savestate_state = STATE_DORESTORE, savestate_filename = "..." - * - */ #include #include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" +#include "memory.h" #include "zfile.h" #include "autoconf.h" #include "custom.h" @@ -58,13 +61,11 @@ #include "audio.h" #include "filesys.h" #include "devices.h" +#include "fsdb.h" int savestate_state = 0; -static bool new_blitter = false; - struct zfile *savestate_file; -static int savestate_docompress, savestate_nodialogs; TCHAR savestate_fname[MAX_DPATH]; @@ -134,6 +135,15 @@ void save_path_func (uae_u8 **dstp, const TCHAR *from, int type) { save_string_func (dstp, from); } +void save_path_full_func(uae_u8 **dstp, const TCHAR *spath, int type) +{ + TCHAR path[MAX_DPATH]; + save_u32_func(dstp, type); + _tcscpy(path, spath ? spath : _T("")); + save_string_func(dstp, path); + _tcscpy(path, spath ? spath : _T("")); + save_string_func(dstp, path); +} uae_u32 restore_u32_func (uae_u8 **dstp) { @@ -187,50 +197,101 @@ TCHAR *restore_string_func (uae_u8 **dstp) xfree (to); return s; } -TCHAR *restore_path_func (uae_u8 **dstp, int type) + +static bool state_path_exists(const TCHAR *path, int type) +{ + if (type == SAVESTATE_PATH_VDIR) + return my_existsdir(path); + return my_existsfile(path); +} + +static TCHAR *state_resolve_path(TCHAR *s, int type, bool newmode) { TCHAR *newpath; - TCHAR *s; TCHAR tmp[MAX_DPATH], tmp2[MAX_DPATH]; - s = restore_string_func(dstp); if (s[0] == 0) return s; - if (zfile_exists (s)) + if (!newmode && state_path_exists(s, type)) return s; if (type == SAVESTATE_PATH_HD) return s; + if (newmode) { + _tcscpy(tmp, s); + if (state_path_exists(tmp, type)) { + xfree(s); + return my_strdup(tmp); + } + getfilepart(tmp, sizeof tmp / sizeof(TCHAR), s); + } else { getfilepart (tmp, sizeof tmp / sizeof (TCHAR), s); - if (zfile_exists (tmp)) { - xfree (s); - return my_strdup (tmp); - } - - newpath = NULL; - if (type == SAVESTATE_PATH_FLOPPY) - newpath = currprefs.path_floppy; - else if (type == SAVESTATE_PATH_VDIR || type == SAVESTATE_PATH_HDF) - newpath = currprefs.path_hardfile; - else if (type == SAVESTATE_PATH_CD) - newpath = currprefs.path_cd; - if (newpath != NULL && newpath[0] != 0) { + if (state_path_exists(tmp, type)) { + xfree (s); + return my_strdup (tmp); + } + } + for (int i = 0; i < MAX_PATHS; i++) { + newpath = NULL; + if (type == SAVESTATE_PATH_FLOPPY) + newpath = currprefs.path_floppy.path[i]; + else if (type == SAVESTATE_PATH_VDIR || type == SAVESTATE_PATH_HDF) + newpath = currprefs.path_hardfile.path[i]; + else if (type == SAVESTATE_PATH_CD) + newpath = currprefs.path_cd.path[i]; + if (newpath == NULL || newpath[0] == 0) + break; _tcscpy (tmp2, newpath); fixtrailing (tmp2); _tcscat (tmp2, tmp); - if (zfile_exists (tmp2)) { + if (state_path_exists(tmp2, type)) { xfree (s); return my_strdup (tmp2); } } getpathpart (tmp2, sizeof tmp2 / sizeof (TCHAR), savestate_fname); _tcscat (tmp2, tmp); - if (zfile_exists (tmp2)) { + if (state_path_exists(tmp2, type)) { xfree (s); return my_strdup (tmp2); } return s; } +TCHAR *restore_path_func (uae_u8 **dstp, int type) +{ + TCHAR *s = restore_string_func(dstp); + return state_resolve_path(s, type, false); +} + +TCHAR *restore_path_full_func(uae_u8 **dstp) +{ + int type = restore_u32_func(dstp); + TCHAR *a = restore_string_func(dstp); + TCHAR *r = restore_string_func(dstp); + if (target_isrelativemode()) { + xfree(a); + return state_resolve_path(r, type, true); + } else { + TCHAR tmp[MAX_DPATH]; + _tcscpy(tmp, a); + if (state_path_exists(tmp, type)) { + xfree(r); + xfree(a); + return my_strdup(tmp); + } + _tcscpy(tmp, r); + if (state_path_exists(tmp, type)) { + xfree(r); + xfree(a); + return my_strdup(tmp); + } + xfree(r); + return state_resolve_path(a, type, true); + } + return NULL; +} + + /* read and write IFF-style hunks */ static void save_chunk (struct zfile *f, uae_u8 *chunk, unsigned int len, const TCHAR *name, int compress) @@ -570,6 +631,8 @@ void restore_state (const TCHAR *filename) end = restore_hrtmon (chunk); #endif #ifdef FILESYS + else if (!_tcscmp(name, _T("FSYP"))) + end = restore_filesys_paths(chunk); else if (!_tcscmp (name, _T("FSYS"))) end = restore_filesys (chunk); else if (!_tcscmp (name, _T("FSYC"))) @@ -585,8 +648,8 @@ void restore_state (const TCHAR *filename) end = restore_gayle_ide (chunk); else if (!_tcsncmp (name, _T("CDU"), 3)) end = restore_cd (name[3] - '0', chunk); - else if (!_tcsncmp (name, _T("EXPI"), 4)) - end = restore_expansion_info(chunk); + else if (!_tcsncmp (name, _T("EXPB"), 4)) + end = restore_expansion_boards(chunk); else { end = chunk + len; @@ -614,39 +677,39 @@ error: zfile_fclose (f); } -void savestate_restore_finish (void) +bool savestate_restore_finish(void) { if (!isrestore ()) - return; - zfile_fclose (savestate_file); - savestate_file = 0; - restore_cpu_finish(); + return false; + zfile_fclose (savestate_file); + savestate_file = 0; + restore_cpu_finish (); restore_audio_finish (); restore_disk_finish (); restore_blitter_finish (); + restore_expansion_finish(); restore_akiko_finish (); #ifdef PICASSO96 restore_p96_finish (); #endif restore_cia_finish (); +#ifdef ACTION_REPLAY + restore_ar_finish(); +#endif savestate_state = 0; init_hz_normal(); - audio_activate (); + audio_activate(); + return true; } /* 1=compressed,2=not compressed */ -void savestate_initsave (const TCHAR *filename, int mode, int nodialogs, bool save) +void savestate_initsave (const TCHAR *filename) { if (filename == NULL) { savestate_fname[0] = 0; - savestate_docompress = 0; - savestate_nodialogs = 0; return; } _tcscpy (savestate_fname, filename); - savestate_docompress = (mode == 1) ? 1 : 0; - savestate_nodialogs = nodialogs; - new_blitter = false; } static void save_rams (struct zfile *f, int comp) @@ -748,19 +811,19 @@ static int save_state_internal (struct zfile *f, const TCHAR *description, int c dst = save_blitter_new (&len, 0); save_chunk (f, dst, len, _T("BLTX"), 0); xfree (dst); - if (new_blitter == false) { - dst = save_blitter (&len, 0); - save_chunk (f, dst, len, _T("BLIT"), 0); - xfree (dst); - } + dst = save_blitter (&len, 0); + save_chunk (f, dst, len, _T("BLIT"), 0); + xfree (dst); dst = save_input (&len, 0); save_chunk (f, dst, len, _T("CINP"), 0); xfree (dst); dst = save_custom_agacolors (&len, 0); - save_chunk (f, dst, len, _T("AGAC"), 0); - xfree (dst); + if (dst) { + save_chunk (f, dst, len, _T("AGAC"), 0); + xfree (dst); + } _tcscpy (name, _T("SPRx")); for (i = 0; i < 8; i++) { @@ -791,8 +854,16 @@ static int save_state_internal (struct zfile *f, const TCHAR *description, int c xfree (dst); #ifdef AUTOCONFIG - dst = save_expansion_info(&len, 0); - save_chunk(f, dst, len, _T("EXPI"), 0); + // new + i = 0; + for (;;) { + dst = save_expansion_boards(&len, 0, i); + if (!dst) + break; + save_chunk(f, dst, len, _T("EXPB"), 0); + xfree (dst); + i++; + } dst = save_expansion (&len, 0); save_chunk (f, dst, len, _T("EXPA"), 0); xfree (dst); @@ -827,6 +898,11 @@ static int save_state_internal (struct zfile *f, const TCHAR *description, int c if (dst) { save_chunk (f, dst, len, _T("FSYC"), 0); for (i = 0; i < nr_units (); i++) { + dst = save_filesys_paths(i, &len); + if (dst) { + save_chunk(f, dst, len, _T("FSYP"), 0); + xfree(dst); + } dst = save_filesys (i, &len); if (dst) { save_chunk (f, dst, len, _T("FSYS"), 0); @@ -864,22 +940,17 @@ static int save_state_internal (struct zfile *f, const TCHAR *description, int c int save_state (const TCHAR *filename, const TCHAR *description) { struct zfile *f; - int comp = savestate_docompress; - if (!savestate_nodialogs) { - state_incompatible_warn(); - if (!save_filesys_cando()) { - gui_message (_T("Filesystem active. Try again later.")); - return -1; - } - } - new_blitter = false; - savestate_nodialogs = 0; + state_incompatible_warn(); + if (!save_filesys_cando()) { + gui_message (_T("Filesystem active. Try again later.")); + return -1; + } custom_prepare_savestate (); f = zfile_fopen (filename, _T("w+b"), 0); if (!f) return 0; - int v = save_state_internal (f, description, comp, true); + int v = save_state_internal (f, description, false, true); if (v) write_log (_T("Save of '%s' complete\n"), filename); zfile_fclose (f); diff --git a/src/scsi.cpp b/src/scsi.cpp index 7893563a..6333a5a7 100644 --- a/src/scsi.cpp +++ b/src/scsi.cpp @@ -6,18 +6,19 @@ * Copyright 2007-2015 Toni Wilen * */ -#include +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" #include "filesys.h" #include "scsi.h" -static const int outcmd[] = { 0x04, 0x0a, 0x0c, 0x11, 0x2a, 0xaa, 0x15, 0x55, 0x0f, -1 }; -static const int incmd[] = { 0x01, 0x03, 0x08, 0x0e, 0x12, 0x1a, 0x5a, 0x25, 0x28, 0x34, 0x37, 0x42, 0x43, 0xa8, 0x51, 0x52, 0xb9, 0xbd, 0xd8, 0xd9, 0xbe, -1 }; -static const int nonecmd[] = { 0x00, 0x05, 0x06, 0x07, 0x09, 0x0b, 0x10, 0x16, 0x17, 0x19, 0x1b, 0x1d, 0x1e, 0x2b, 0x35, 0x45, 0x47, 0x48, 0x49, 0x4b, 0x4e, 0xa5, 0xa9, 0xba, 0xbc, 0xe0, 0xe3, 0xe4, -1 }; -static const int scsicmdsizes[] = { 6, 10, 10, 12, 16, 12, 10, 6 }; +static const uae_s16 outcmd[] = { 0x04, 0x0a, 0x0c, 0x11, 0x2a, 0xaa, 0x15, 0x55, 0x0f, -1 }; +static const uae_s16 incmd[] = { 0x01, 0x03, 0x08, 0x0e, 0x12, 0x1a, 0x5a, 0x25, 0x28, 0x34, 0x37, 0x42, 0x43, 0xa8, 0x51, 0x52, 0xb9, 0xbd, 0xd8, 0xd9, 0xbe, -1 }; +static const uae_s16 nonecmd[] = { 0x00, 0x05, 0x06, 0x07, 0x09, 0x0b, 0x10, 0x16, 0x17, 0x19, 0x1b, 0x1d, 0x1e, 0x2b, 0x35, 0x45, 0x47, 0x48, 0x49, 0x4b, 0x4e, 0xa5, 0xa9, 0xba, 0xbc, 0xe0, 0xe3, 0xe4, -1 }; +static const uae_s16 safescsi[] = { 0x00, 0x01, 0x03, 0x08, 0x0e, 0x0f, 0x12, 0x1a, 0x1b, 0x25, 0x28, 0x35, 0x5a, -1 }; +static const uae_s16 scsicmdsizes[] = { 6, 10, 10, 12, 16, 12, 10, 6 }; static void scsi_illegal_command(struct scsi_data *sd) { @@ -163,6 +164,9 @@ bool scsi_emulate_analyze (struct scsi_data *sd) sd->data_len = data_len; } sd->direction = scsi_data_dir (sd); + if (sd->direction > 0 && sd->data_len == 0) { + sd->direction = 0; + } return true; nocmd: sd->status = SCSI_STATUS_CHECK_CONDITION; @@ -171,7 +175,7 @@ nocmd: return false; } -void scsi_clear_sense(struct scsi_data *sd) +static void scsi_clear_sense(struct scsi_data *sd) { memset (sd->sense, 0, sizeof (sd->sense)); memset (sd->reply, 0, sizeof (sd->reply)); @@ -253,6 +257,17 @@ static bool handle_ca(struct scsi_data *sd) return true; } +bool scsi_cmd_is_safe(uae_u8 cmd) +{ + for (int i = 0; safescsi[i] >= 0; i++) { + if (safescsi[i] == cmd) { + return true; + } + } + return false; +} + + void scsi_emulate_cmd(struct scsi_data *sd) { sd->status = 0; @@ -264,6 +279,7 @@ void scsi_emulate_cmd(struct scsi_data *sd) sd->cmd[1] |= lun << 5; } if (sd->device_type == UAEDEV_HDF) { + uae_u32 ua = 0; ua = scsi_hd_emulate(sd->hfd, sd->hdhfd, NULL, 0, 0, 0, 0, 0, 0, 0); if (ua) @@ -278,8 +294,34 @@ void scsi_emulate_cmd(struct scsi_data *sd) copyreply(sd); } } + + } else if (sd->device_type == UAEDEV_DIR) { + + uae_u32 ua = 0; + ua = scsi_hd_emulate(sd->hfd, sd->hdhfd, NULL, 0, 0, 0, 0, 0, 0, 0); + if (ua) + sd->unit_attention = ua; + if (handle_ca(sd)) { + if (scsi_cmd_is_safe(sd->cmd[0])) { + if (sd->cmd[0] == 0x03) { /* REQUEST SENSE */ + scsi_hd_emulate(sd->hfd, sd->hdhfd, sd->cmd, 0, 0, 0, 0, 0, sd->sense, &sd->sense_len); + copysense(sd); + } else { + sd->status = scsi_hd_emulate(sd->hfd, sd->hdhfd, + sd->cmd, sd->cmd_len, sd->buffer, &sd->data_len, sd->reply, &sd->reply_len, sd->sense, &sd->sense_len); + copyreply(sd); + } + } else { + sd->sense[0] = 0x70; + sd->sense[2] = 5; /* Illegal Request */ + sd->sense[12] = 0x20; /* Invalid/unsupported command code */ + sd->sense_len = 18; + sd->status = 2; + copyreply(sd); + } + } + } - sd->offset = 0; } static void allocscsibuf(struct scsi_data *sd) @@ -288,13 +330,14 @@ static void allocscsibuf(struct scsi_data *sd) sd->buffer = xcalloc(uae_u8, sd->buffer_size); } -struct scsi_data *scsi_alloc_generic(struct hardfiledata *hfd, int type) +struct scsi_data *scsi_alloc_generic(struct hardfiledata *hfd, int type, int uae_unitnum) { struct scsi_data *sd = xcalloc(struct scsi_data, 1); sd->hfd = hfd; sd->id = -1; sd->blocksize = hfd->ci.blocksize; sd->device_type = type; + sd->uae_unitnum = uae_unitnum; allocscsibuf(sd); return sd; } @@ -306,8 +349,3 @@ void scsi_free(struct scsi_data *sd) xfree(sd->buffer); xfree(sd); } - -void scsi_start_transfer(struct scsi_data *sd) -{ - sd->offset = 0; -} diff --git a/src/statusline.cpp b/src/statusline.cpp index 84e75873..ff868afe 100644 --- a/src/statusline.cpp +++ b/src/statusline.cpp @@ -1,6 +1,5 @@ -#include -#include -#include +#include +#include #include "sysdeps.h" @@ -52,6 +51,7 @@ static void write_tdnumber(uae_u8 *buf, int bpp, int x, int y, int num, uae_u32 void draw_status_line_single(uae_u8 *buf, int bpp, int y, int totalwidth, uae_u32 *rc, uae_u32 *gc, uae_u32 *bc, uae_u32 *alpha) { + struct amigadisplay *ad = &adisplays; int x_start, j, led, border; uae_u32 c1, c2, cb; @@ -71,7 +71,7 @@ void draw_status_line_single(uae_u8 *buf, int bpp, int y, int totalwidth, uae_u3 xcolnr on_rgb = 0, on_rgb2 = 0, off_rgb = 0, pen_rgb = 0; int half = 0; - if (!(currprefs.leds_on_screen_mask[picasso_on ? 1 : 0] & (1 << led))) + if (!(currprefs.leds_on_screen_mask[ad->picasso_on ? 1 : 0] & (1 << led))) continue; pen_rgb = c1; diff --git a/src/threaddep/thread.h b/src/threaddep/thread.h index 60f22006..c6e65d56 100644 --- a/src/threaddep/thread.h +++ b/src/threaddep/thread.h @@ -1,23 +1,23 @@ -/* -* UAE - The Un*x Amiga Emulator -* -* Threading support, using SDL -* -* Copyright 1997, 2001 Bernd Schmidt -*/ + /* + * UAE - The Un*x Amiga Emulator + * + * Threading support, using SDL + * + * Copyright 1997, 2001 Bernd Schmidt + */ #pragma once #include #include /* Sempahores. We use POSIX semaphores; if you are porting this to a machine -* with different ones, make them look like POSIX semaphores. */ + * with different ones, make them look like POSIX semaphores. */ typedef SDL_sem *uae_sem_t; STATIC_INLINE int uae_sem_init(uae_sem_t *sem, int dummy, int init) { - *sem = SDL_CreateSemaphore(init); - return (*sem == nullptr); + *sem = SDL_CreateSemaphore (init); + return (*sem == 0); } #define uae_sem_destroy(PSEM) SDL_DestroySemaphore (*PSEM) @@ -31,51 +31,41 @@ STATIC_INLINE int uae_sem_init(uae_sem_t *sem, int dummy, int init) typedef SDL_Thread *uae_thread_id; #define BAD_THREAD 0 -STATIC_INLINE void uae_set_thread_priority(uae_thread_id *id, int pri) +STATIC_INLINE void uae_set_thread_priority (uae_thread_id *id, int pri) { } -STATIC_INLINE void uae_end_thread(uae_thread_id *tid) +STATIC_INLINE void uae_end_thread (uae_thread_id *tid) { } -#ifdef USE_SDL1 -STATIC_INLINE int uae_start_thread(const TCHAR *name, void *(*f) (void *), void *arg, uae_thread_id *foo) +STATIC_INLINE long uae_start_thread (const TCHAR *name, int(*f) (void *), void *arg, uae_thread_id *foo) { - auto id = SDL_CreateThread(reinterpret_cast(f), arg); - if (foo != nullptr) - *foo = id; - return int(id); -} - -STATIC_INLINE int uae_start_thread_fast(void *(*f) (void *), void *arg, uae_thread_id *foo) -{ - auto id = SDL_CreateThread(reinterpret_cast(f), arg); - if (foo != nullptr) - *foo = id; - return int(id); -} -#elif USE_SDL2 -STATIC_INLINE uae_thread_id uae_start_thread(const TCHAR* name, void*(*f)(void*), void* arg, uae_thread_id* foo) -{ - uae_thread_id id = SDL_CreateThread(reinterpret_cast(f), "StartThread", arg); - if (foo != NULL) - *foo = id; - return id; -} - -STATIC_INLINE uae_thread_id uae_start_thread_fast(void*(*f)(void*), void* arg, uae_thread_id* foo) -{ - uae_thread_id id = SDL_CreateThread(reinterpret_cast(f), "StartThreadFast", arg); - if (foo != NULL) - *foo = id; - return id; -} +#ifdef USE_SDL2 + uae_thread_id id = SDL_CreateThread (f, "StartThread", arg); +#else + uae_thread_id id = SDL_CreateThread (f, arg); #endif + if(foo != NULL) + *foo = id; + return (long)id; +} -STATIC_INLINE void uae_wait_thread(uae_thread_id thread) +STATIC_INLINE long uae_start_thread_fast (void *(*f) (void *), void *arg, uae_thread_id *foo) { - SDL_WaitThread(thread, static_cast(nullptr)); +#ifdef USE_SDL2 + uae_thread_id id = SDL_CreateThread ((int (*)(void *))f, "StartThreadFast", arg); +#else + uae_thread_id id = SDL_CreateThread ((int (*)(void *))f, arg); +#endif + if(foo != NULL) + *foo = id; + return (long)id; +} + +STATIC_INLINE void uae_wait_thread (uae_thread_id thread) +{ + SDL_WaitThread (thread, (int*)0); } /* Do nothing; thread exits if thread function returns. */ diff --git a/src/traps.cpp b/src/traps.cpp index 99a9c330..17f01ae2 100644 --- a/src/traps.cpp +++ b/src/traps.cpp @@ -1,72 +1,73 @@ - /* - * E-UAE - The portable Amiga Emulator - * - * Support for traps - * - * Copyright Richard Drummond 2005 - * - * Inspired by code from UAE: - * Copyright 1995, 1996 Bernd Schmidt - * Copyright 1996 Ed Hanway - */ -#include -#include +/* +* E-UAE - The portable Amiga Emulator +* +* Support for traps +* +* Copyright Richard Drummond 2005 +* +* Inspired by code from UAE: +* Copyright 1995, 1996 Bernd Schmidt +* Copyright 1996 Ed Hanway +*/ +#include "sysconfig.h" #include "sysdeps.h" #include "options.h" -#include "include/memory.h" +#include "memory.h" +#include "custom.h" #include "newcpu.h" #include "threaddep/thread.h" #include "autoconf.h" +#include "traps.h" #include "uae.h" /* - * Traps are the mechanism via which 68k code can call emulator code - * (and for that emulator code in turn to call 68k code). They are - * thus the basis for much of the cool stuff that E-UAE can do. - * - * Emulator traps take advantage of the illegal 68k opwords 0xA000 to - * 0xAFFF. Normally these would generate an A-line exception. However, - * when encountered in the RTAREA section of memory, these opwords - * instead invoke a corresponding emulator trap, allowing a host - * function to be called. - * - * Two types of emulator trap are available - a simple trap and an - * extended trap. A simple trap may not call 68k code; an extended - * trap can. - * - * Extended traps are rather complex beasts (to implement, not - * necessarily to use). This is because for the trap handler function - * to be able to call 68k code, we must somehow allow the emulator's - * 68k interpreter to resume execution of 68k code in the middle of - * the trap handler function. - * - * In UAE of old this used to be implemented via a stack-swap mechanism. - * While this worked, it was definitely in the realm of black magic and - * horribly non-portable, requiring assembly language glue specific to - * the host ABI and compiler to actually perform the swap. - * - * In this implementation, in essence we do something similar - but the - * new stack is provided by a new thread. No voodoo required, just a - * working thread layer. - * - * The complexity in this approach arises in synchronizing the trap - * threads with the emulator thread. This implementation errs on the side - * of paranoia when it comes to thread synchronization. Once all the - * bugs are knocked out of the bsdsocket emulation, a simpler scheme may - * suffice. - */ +* Traps are the mechanism via which 68k code can call emulator code +* (and for that emulator code in turn to call 68k code). They are +* thus the basis for much of the cool stuff that E-UAE can do. +* +* Emulator traps take advantage of the illegal 68k opwords 0xA000 to +* 0xAFFF. Normally these would generate an A-line exception. However, +* when encountered in the RTAREA section of memory, these opwords +* instead invoke a corresponding emulator trap, allowing a host +* function to be called. +* +* Two types of emulator trap are available - a simple trap and an +* extended trap. A simple trap may not call 68k code; an extended +* trap can. +* +* Extended traps are rather complex beasts (to implement, not +* necessarily to use). This is because for the trap handler function +* to be able to call 68k code, we must somehow allow the emulator's +* 68k interpreter to resume execution of 68k code in the middle of +* the trap handler function. +* +* In UAE of old this used to be implemented via a stack-swap mechanism. +* While this worked, it was definitely in the realm of black magic and +* horribly non-portable, requiring assembly language glue specific to +* the host ABI and compiler to actually perform the swap. +* +* In this implementation, in essence we do something similar - but the +* new stack is provided by a new thread. No voodoo required, just a +* working thread layer. +* +* The complexity in this approach arises in synchronizing the trap +* threads with the emulator thread. This implementation errs on the side +* of paranoia when it comes to thread synchronization. Once all the +* bugs are knocked out of the bsdsocket emulation, a simpler scheme may +* suffice. +*/ /* - * Record of a defined trap (that is, a trap allocated to a host function) - */ +* Record of a defined trap (that is, a trap allocated to a host function) +*/ struct Trap { - TrapHandler handler; /* Handler function to be invoked for this trap. */ - int flags; /* Trap attributes. */ - const TCHAR *name; /* For debugging purposes. */ - uaecptr addr; + TrapHandler handler; /* Handler function to be invoked for this trap. */ + int flags; /* Trap attributes. */ + const TCHAR *name; /* For debugging purposes. */ + uaecptr addr; }; #define MAX_TRAPS 4096 @@ -79,26 +80,26 @@ static void trap_HandleExtendedTrap (TrapHandler, int has_retval); uaecptr find_trap (const TCHAR *name) { - int i; + int i; - for (i = 0; i < trap_count; i++) { - struct Trap *trap = &traps[i]; - if ((trap->flags & TRAPFLAG_UAERES) && trap->name && !_tcscmp (trap->name, name)) - return trap->addr; - } - return 0; + for (i = 0; i < trap_count; i++) { + struct Trap *trap = &traps[i]; + if ((trap->flags & TRAPFLAG_UAERES) && trap->name && !_tcscmp (trap->name, name)) + return trap->addr; + } + return 0; } /* - * Define an emulator trap - * - * handler_func = host function that will be invoked to handle this trap - * flags = trap attributes - * name = name for debugging purposes - * - * returns trap number of defined trap - */ +* Define an emulator trap +* +* handler_func = host function that will be invoked to handle this trap +* flags = trap attributes +* name = name for debugging purposes +* +* returns trap number of defined trap +*/ unsigned int define_trap (TrapHandler handler_func, int flags, const TCHAR *name) { if (trap_count == MAX_TRAPS) { @@ -112,30 +113,30 @@ unsigned int define_trap (TrapHandler handler_func, int flags, const TCHAR *name struct Trap *trap; uaecptr addr = here (); - for (i = 0; i < trap_count; i++) { - if (addr == traps[i].addr) - return i; - } + for (i = 0; i < trap_count; i++) { + if (addr == traps[i].addr) + return i; + } - trap_num = trap_count++; - trap = &traps[trap_num]; + trap_num = trap_count++; + trap = &traps[trap_num]; - trap->handler = handler_func; - trap->flags = flags; - trap->name = name; - trap->addr = addr; + trap->handler = handler_func; + trap->flags = flags; + trap->name = name; + trap->addr = addr; - return trap_num; - } + return trap_num; + } } /* - * This function is called by the 68k interpreter to handle an emulator trap. - * - * trap_num = number of trap to invoke - * regs = current 68k state - */ +* This function is called by the 68k interpreter to handle an emulator trap. +* +* trap_num = number of trap to invoke +* regs = current 68k state +*/ void REGPARAM2 m68k_handle_trap (unsigned int trap_num) { struct Trap *trap = &traps[trap_num]; @@ -144,35 +145,35 @@ void REGPARAM2 m68k_handle_trap (unsigned int trap_num) int has_retval = (trap->flags & TRAPFLAG_NO_RETVAL) == 0; int implicit_rts = (trap->flags & TRAPFLAG_DORET) != 0; - if (trap_num < trap_count) { - if (trap->flags & TRAPFLAG_EXTRA_STACK) { - /* Handle an extended trap. - * Note: the return value of this trap is passed back to 68k - * space via a separate, dedicated simple trap which the trap - * handler causes to be invoked when it is done. - */ - trap_HandleExtendedTrap (trap->handler, has_retval); - } else { - /* Handle simple trap */ - retval = (trap->handler) (NULL); + if (trap_num < trap_count) { + if (trap->flags & TRAPFLAG_EXTRA_STACK) { + /* Handle an extended trap. + * Note: the return value of this trap is passed back to 68k + * space via a separate, dedicated simple trap which the trap + * handler causes to be invoked when it is done. + */ + trap_HandleExtendedTrap (trap->handler, has_retval); + } else { + /* Handle simple trap */ + retval = (trap->handler) (NULL); - if (has_retval) - m68k_dreg (regs, 0) = retval; + if (has_retval) + m68k_dreg (regs, 0) = retval; - if (implicit_rts) { - m68k_do_rts (); - fill_prefetch (); - } - } - } else + if (implicit_rts) { + m68k_do_rts (); + fill_prefetch (); + } + } + } else write_log (_T("Illegal emulator trap\n")); } /* - * Implementation of extended traps - */ +* Implementation of extended traps +*/ struct TrapCPUContext { @@ -183,32 +184,33 @@ struct TrapCPUContext struct TrapContext { - /* Trap's working copy of 68k state. This is what the trap handler should - * access to get arguments from 68k space. */ + /* Trap's working copy of 68k state. This is what the trap handler should + * access to get arguments from 68k space. */ - /* Trap handler function that gets called on the trap context */ - TrapHandler trap_handler; - /* Should the handler return a value to 68k space in D0? */ - int trap_has_retval; - /* Return value from trap handler */ - uae_u32 trap_retval; + /* Trap handler function that gets called on the trap context */ + TrapHandler trap_handler; + /* Should the handler return a value to 68k space in D0? */ + int trap_has_retval; + /* Return value from trap handler */ + uae_u32 trap_retval; - /* Copy of 68k state at trap entry. */ + /* Copy of 68k state at trap entry. */ struct TrapCPUContext saved_regs; - /* Thread which effects the trap context. */ - uae_thread_id thread; - /* For IPC between the main emulator. */ - uae_sem_t switch_to_emu_sem; - /* context and the trap context. */ - uae_sem_t switch_to_trap_sem; + /* Thread which effects the trap context. */ + uae_thread_id thread; + /* For IPC between the main emulator. */ + uae_sem_t switch_to_emu_sem; + /* context and the trap context. */ + uae_sem_t switch_to_trap_sem; - /* When calling a 68k function from a trap handler, this is set to the - * address of the function to call. */ - uaecptr call68k_func_addr; - /* And this gets set to the return value of the 68k call. */ - uae_u32 call68k_retval; + /* When calling a 68k function from a trap handler, this is set to the + * address of the function to call. */ + uaecptr call68k_func_addr; + /* And this gets set to the return value of the 68k call. */ + uae_u32 call68k_retval; + /* do not ack automatically */ uae_u32 calllib_regs[16]; uae_u8 calllib_reg_inuse[16]; }; @@ -238,244 +240,244 @@ static TrapContext *current_context; /* - * Thread body for trap context - */ +* Thread body for trap context +*/ static void *trap_thread (void *arg) { - TrapContext *context = (TrapContext *) arg; + TrapContext *context = (TrapContext *) arg; - /* Wait until main thread is ready to switch to the - * this trap context. */ - uae_sem_wait (&context->switch_to_trap_sem); + /* Wait until main thread is ready to switch to the + * this trap context. */ + uae_sem_wait (&context->switch_to_trap_sem); - /* Execute trap handler function. */ - context->trap_retval = context->trap_handler (context); + /* Execute trap handler function. */ + context->trap_retval = context->trap_handler (context); - /* Trap handler is done - we still need to tidy up - * and make sure the handler's return value is propagated - * to the calling 68k thread. - * - * We do this by causing our exit handler to be executed on the 68k context. - */ + /* Trap handler is done - we still need to tidy up + * and make sure the handler's return value is propagated + * to the calling 68k thread. + * + * We do this by causing our exit handler to be executed on the 68k context. + */ - /* Enter critical section - only one trap at a time, please! */ - uae_sem_wait (&trap_mutex); + /* Enter critical section - only one trap at a time, please! */ + uae_sem_wait (&trap_mutex); //regs = context->saved_regs; /* Set PC to address of the exit handler, so that it will be called * when the 68k context resumes. */ copyfromcpucontext (&context->saved_regs, exit_trap_trapaddr); - /* Don't allow an interrupt and thus potentially another - * trap to be invoked while we hold the above mutex. - * This is probably just being paranoid. */ - regs.intmask = 7; + /* Don't allow an interrupt and thus potentially another + * trap to be invoked while we hold the above mutex. + * This is probably just being paranoid. */ + regs.intmask = 7; //m68k_setpc (exit_trap_trapaddr); - current_context = context; + current_context = context; - /* Switch back to 68k context */ - uae_sem_post (&context->switch_to_emu_sem); + /* Switch back to 68k context */ + uae_sem_post (&context->switch_to_emu_sem); - /* Good bye, cruel world... */ + /* Good bye, cruel world... */ - /* dummy return value */ - return 0; + /* dummy return value */ + return 0; } /* - * Set up extended trap context and call handler function - */ -static void trap_HandleExtendedTrap (TrapHandler handler_func, int has_retval) +* Set up extended trap context and call handler function +*/ +static void trap_HandleExtendedTrap(TrapHandler handler_func, int has_retval) { - struct TrapContext *context = xcalloc (TrapContext, 1); + struct TrapContext *context = xcalloc(TrapContext, 1); - if (context) { - uae_sem_init (&context->switch_to_trap_sem, 0, 0); - uae_sem_init (&context->switch_to_emu_sem, 0, 0); + if (context) { + uae_sem_init(&context->switch_to_trap_sem, 0, 0); + uae_sem_init(&context->switch_to_emu_sem, 0, 0); - context->trap_handler = handler_func; - context->trap_has_retval = has_retval; + context->trap_handler = handler_func; + context->trap_has_retval = has_retval; //context->saved_regs = regs; - copytocpucontext (&context->saved_regs); + copytocpucontext(&context->saved_regs); - /* Start thread to handle new trap context. */ - uae_start_thread_fast (trap_thread, (void *)context, &context->thread); + /* Start thread to handle new trap context. */ + uae_start_thread_fast(trap_thread, (void *)context, &context->thread); - /* Switch to trap context to begin execution of - * trap handler function. - */ - uae_sem_post (&context->switch_to_trap_sem); + /* Switch to trap context to begin execution of + * trap handler function. + */ + uae_sem_post(&context->switch_to_trap_sem); - /* Wait for trap context to switch back to us. - * - * It'll do this when the trap handler is done - or when - * the handler wants to call 68k code. */ - uae_sem_wait (&context->switch_to_emu_sem); - } + /* Wait for trap context to switch back to us. + * + * It'll do this when the trap handler is done - or when + * the handler wants to call 68k code. */ + uae_sem_wait(&context->switch_to_emu_sem); + } } /* - * Call m68k function from an extended trap handler - * - * This function is to be called from the trap context. - */ +* Call m68k function from an extended trap handler +* +* This function is to be called from the trap context. +*/ static uae_u32 trap_Call68k (TrapContext *ctx, uaecptr func_addr) { - /* Enter critical section - only one trap at a time, please! */ - uae_sem_wait (&trap_mutex); - current_context = ctx; + /* Enter critical section - only one trap at a time, please! */ + uae_sem_wait(&trap_mutex); + current_context = ctx; - /* Don't allow an interrupt and thus potentially another - * trap to be invoked while we hold the above mutex. - * This is probably just being paranoid. */ - regs.intmask = 7; + /* Don't allow an interrupt and thus potentially another + * trap to be invoked while we hold the above mutex. + * This is probably just being paranoid. */ + regs.intmask = 7; - /* Set up function call address. */ - ctx->call68k_func_addr = func_addr; + /* Set up function call address. */ + ctx->call68k_func_addr = func_addr; - /* Set PC to address of 68k call trap, so that it will be - * executed when emulator context resumes. */ - m68k_setpc (m68k_call_trapaddr); - fill_prefetch (); + /* Set PC to address of 68k call trap, so that it will be + * executed when emulator context resumes. */ + m68k_setpc(m68k_call_trapaddr); + fill_prefetch(); - /* Switch to emulator context. */ - uae_sem_post (&ctx->switch_to_emu_sem); + /* Switch to emulator context. */ + uae_sem_post(&ctx->switch_to_emu_sem); - /* Wait for 68k call return handler to switch back to us. */ - uae_sem_wait (&ctx->switch_to_trap_sem); + /* Wait for 68k call return handler to switch back to us. */ + uae_sem_wait(&ctx->switch_to_trap_sem); - /* End critical section. */ - uae_sem_post (&trap_mutex); + /* End critical section. */ + uae_sem_post(&trap_mutex); - /* Get return value from 68k function called. */ - return ctx->call68k_retval; + /* Get return value from 68k function called. */ + return ctx->call68k_retval; } /* - * Handles the emulator's side of a 68k call (from an extended trap) - */ -static uae_u32 REGPARAM2 m68k_call_handler (TrapContext *dummy_ctx) +* Handles the emulator's side of a 68k call (from an extended trap) +*/ +static uae_u32 REGPARAM2 m68k_call_handler(TrapContext *dummy_ctx) { - TrapContext *context = current_context; + TrapContext *context = current_context; - uae_u32 sp; + uae_u32 sp; - sp = m68k_areg (regs, 7); + sp = m68k_areg(regs, 7); - /* Push address of trap context on 68k stack. This is - * so the return trap can find this context. */ - sp -= sizeof (void *); - put_pointer (sp, context); + /* Push address of trap context on 68k stack. This is + * so the return trap can find this context. */ + sp -= sizeof(void *); + put_pointer(sp, context); - /* Push addr to return handler trap on 68k stack. - * When the called m68k function does an RTS, the CPU will pull this - * address off the stack and so call the return handler. */ - sp -= 4; - put_long (sp, m68k_return_trapaddr); + /* Push addr to return handler trap on 68k stack. + * When the called m68k function does an RTS, the CPU will pull this + * address off the stack and so call the return handler. */ + sp -= 4; + put_long(sp, m68k_return_trapaddr); - m68k_areg (regs, 7) = sp; + m68k_areg(regs, 7) = sp; - /* Set PC to address of 68k function to call. */ - m68k_setpc (context->call68k_func_addr); - fill_prefetch (); + /* Set PC to address of 68k function to call. */ + m68k_setpc(context->call68k_func_addr); + fill_prefetch(); - /* End critical section: allow other traps run. */ - uae_sem_post (&trap_mutex); + /* End critical section: allow other traps run. */ + uae_sem_post(&trap_mutex); - /* Restore interrupts. */ - regs.intmask = context->saved_regs.intmask; + /* Restore interrupts. */ + regs.intmask = context->saved_regs.intmask; - /* Dummy return value. */ - return 0; + /* Dummy return value. */ + return 0; } /* - * Handles the return from a 68k call at the emulator's side. - */ -static uae_u32 REGPARAM2 m68k_return_handler (TrapContext *dummy_ctx) +* Handles the return from a 68k call at the emulator's side. +*/ +static uae_u32 REGPARAM2 m68k_return_handler(TrapContext *dummy_ctx) { - TrapContext *context; - uae_u32 sp; + TrapContext *context; + uae_u32 sp; - /* One trap returning at a time, please! */ - uae_sem_wait (&trap_mutex); + /* One trap returning at a time, please! */ + uae_sem_wait(&trap_mutex); - /* Get trap context from 68k stack. */ - sp = m68k_areg (regs, 7); - context = (TrapContext *) get_pointer(sp); - sp += sizeof (void *); - m68k_areg (regs, 7) = sp; + /* Get trap context from 68k stack. */ + sp = m68k_areg(regs, 7); + context = (TrapContext *)get_pointer(sp); + sp += sizeof(void *); + m68k_areg(regs, 7) = sp; - /* Get return value from the 68k call. */ - context->call68k_retval = m68k_dreg (regs, 0); + /* Get return value from the 68k call. */ + context->call68k_retval = m68k_dreg(regs, 0); - /* Switch back to trap context. */ - uae_sem_post (&context->switch_to_trap_sem); + /* Switch back to trap context. */ + uae_sem_post(&context->switch_to_trap_sem); - /* Wait for trap context to switch back to us. - * - * It'll do this when the trap handler is done - or when - * the handler wants to call another 68k function. */ - uae_sem_wait (&context->switch_to_emu_sem); + /* Wait for trap context to switch back to us. + * + * It'll do this when the trap handler is done - or when + * the handler wants to call another 68k function. */ + uae_sem_wait(&context->switch_to_emu_sem); - /* Dummy return value. */ - return 0; + /* Dummy return value. */ + return 0; } /* - * Handles completion of an extended trap and passes - * return value from trap function to 68k space. - */ -static uae_u32 REGPARAM2 exit_trap_handler (TrapContext *dummy_ctx) +* Handles completion of an extended trap and passes +* return value from trap function to 68k space. +*/ +static uae_u32 REGPARAM2 exit_trap_handler(TrapContext *dummy_ctx) { - TrapContext *context = current_context; + TrapContext *context = current_context; - /* Wait for trap context thread to exit. */ - uae_wait_thread (context->thread); + /* Wait for trap context thread to exit. */ + uae_wait_thread(context->thread); - /* Restore 68k state saved at trap entry. */ + /* Restore 68k state saved at trap entry. */ //regs = context->saved_regs; - copyfromcpucontext (&context->saved_regs, context->saved_regs.pc); - - /* If trap is supposed to return a value, then store - * return value in D0. */ - if (context->trap_has_retval) - m68k_dreg (regs, 0) = context->trap_retval; + copyfromcpucontext(&context->saved_regs, context->saved_regs.pc); - uae_sem_destroy (&context->switch_to_trap_sem); - uae_sem_destroy (&context->switch_to_emu_sem); + /* If trap is supposed to return a value, then store + * return value in D0. */ + if (context->trap_has_retval) + m68k_dreg(regs, 0) = context->trap_retval; - xfree (context); + uae_sem_destroy(&context->switch_to_trap_sem); + uae_sem_destroy(&context->switch_to_emu_sem); - /* End critical section */ - uae_sem_post (&trap_mutex); + xfree(context); - /* Dummy return value. */ - return 0; + /* End critical section */ + uae_sem_post(&trap_mutex); + + /* Dummy return value. */ + return 0; } /* - * Call a 68k library function from extended trap. - */ -uae_u32 CallLib (TrapContext *ctx, uaecptr base, uae_s16 offset) +* Call a 68k library function from extended trap. +*/ +uae_u32 CallLib(TrapContext *ctx, uaecptr base, uae_s16 offset) { - uae_u32 retval; + uae_u32 retval; uaecptr olda6 = trap_get_areg(ctx, 6); trap_set_areg(ctx, 6, base); - retval = trap_Call68k (ctx, base + offset); + retval = trap_Call68k(ctx, base + offset); trap_set_areg(ctx, 6, olda6); - return retval; + return retval; } /* - * Call 68k function from extended trap. - */ +* Call 68k function from extended trap. +*/ uae_u32 CallFunc(TrapContext *ctx, uaecptr func) { return trap_Call68k(ctx, func); @@ -491,8 +493,8 @@ void init_traps (void) } /* - * Initialize the extended trap mechanism. - */ +* Initialize the extended trap mechanism. +*/ void init_extended_traps (void) { m68k_call_trapaddr = here (); @@ -734,18 +736,6 @@ uae_char *trap_get_alloc_string(TrapContext *ctx, uaecptr addr, int maxlen) return buf; } -int trap_get_bstr(TrapContext *ctx, uae_u8 *haddr, uaecptr addr, int maxlen) -{ - int len = 0; - uae_u8 cnt = get_byte(addr); - while (cnt-- != 0 && maxlen-- > 0) { - addr++; - *haddr++ = get_byte(addr); - } - *haddr = 0; - return len; -} - void trap_set_longs(TrapContext *ctx, uaecptr addr, uae_u32 v, int cnt) { if (cnt <= 0) @@ -840,16 +830,3 @@ void trap_multi(TrapContext *ctx, struct trapmd *data, int items) } } } - -void trap_memcpyha_safe(TrapContext *ctx, uaecptr dst, const uae_u8 *src, int size) -{ - if (size <= 0) - return; - memcpyha_safe(dst, src, size); -} -void trap_memcpyah_safe(TrapContext *ctx, uae_u8 *dst, uaecptr src, int size) -{ - if (size <= 0) - return; - memcpyah_safe(dst, src, size); -} diff --git a/src/uaelib.cpp b/src/uaelib.cpp index c2ebcd56..f8de419f 100644 --- a/src/uaelib.cpp +++ b/src/uaelib.cpp @@ -13,7 +13,6 @@ #include "options.h" #include "uae.h" #include "memory.h" -//#include "newcpu.h" #include "autoconf.h" #include "disk.h" #include "gensound.h" @@ -23,42 +22,42 @@ /* * Returns UAE Version */ -static uae_u32 emulib_GetVersion(void) +static uae_u32 emulib_GetVersion (void) { - return version; + return version; } /* * Resets your amiga */ -static uae_u32 emulib_HardReset(void) +static uae_u32 emulib_HardReset (void) { uae_reset(1, 1); - return 0; + return 0; } -static uae_u32 emulib_Reset(void) +static uae_u32 emulib_Reset (void) { uae_reset(0, 0); - return 0; + return 0; } /* * Enables SOUND */ -static uae_u32 emulib_EnableSound(uae_u32 val) +static uae_u32 emulib_EnableSound (uae_u32 val) { - if (!sound_available || currprefs.produce_sound == 2) - return 0; + if (!sound_available || currprefs.produce_sound == 2) + return 0; - currprefs.produce_sound = val; - return 1; + currprefs.produce_sound = val; + return 1; } /* * Enables FAKE JOYSTICK */ -static uae_u32 emulib_EnableJoystick(uae_u32 val) +static uae_u32 emulib_EnableJoystick (uae_u32 val) { currprefs.jports[0].id = val & 255; currprefs.jports[1].id = (val >> 8) & 255; @@ -68,50 +67,53 @@ static uae_u32 emulib_EnableJoystick(uae_u32 val) /* * Sets the framerate */ -static uae_u32 emulib_SetFrameRate(uae_u32 val) +static uae_u32 emulib_SetFrameRate (uae_u32 val) { - if (val == 0) - return 0; - if (val > 20) - return 0; - currprefs.gfx_framerate = val; - return 1; + if (val == 0) + return 0; + else if (val > 20) + return 0; + else { + currprefs.gfx_framerate = val; + return 1; + } } /* * Changes keyboard language settings */ -static uae_u32 emulib_ChangeLanguage(uae_u32 which) +static uae_u32 emulib_ChangeLanguage (uae_u32 which) { if (which > 6) - return 0; - switch (which) - { - case 0: - currprefs.keyboard_lang = KBD_LANG_US; - break; - case 1: - currprefs.keyboard_lang = KBD_LANG_DK; - break; - case 2: - currprefs.keyboard_lang = KBD_LANG_DE; - break; - case 3: - currprefs.keyboard_lang = KBD_LANG_SE; - break; - case 4: - currprefs.keyboard_lang = KBD_LANG_FR; - break; - case 5: - currprefs.keyboard_lang = KBD_LANG_IT; - break; - case 6: - currprefs.keyboard_lang = KBD_LANG_ES; - break; - default: - break; - } - return 1; + return 0; + else { + switch (which) { + case 0: + currprefs.keyboard_lang = KBD_LANG_US; + break; + case 1: + currprefs.keyboard_lang = KBD_LANG_DK; + break; + case 2: + currprefs.keyboard_lang = KBD_LANG_DE; + break; + case 3: + currprefs.keyboard_lang = KBD_LANG_SE; + break; + case 4: + currprefs.keyboard_lang = KBD_LANG_FR; + break; + case 5: + currprefs.keyboard_lang = KBD_LANG_IT; + break; + case 6: + currprefs.keyboard_lang = KBD_LANG_ES; + break; + default: + break; + } + return 1; + } } /* The following ones don't work as we never realloc the arrays... */ @@ -119,83 +121,80 @@ static uae_u32 emulib_ChangeLanguage(uae_u32 which) * Changes chip memory size * (reboots) */ -static uae_u32 REGPARAM2 emulib_ChgCMemSize(TrapContext* ctx, uae_u32 memsize) +static uae_u32 REGPARAM2 emulib_ChgCMemSize(TrapContext *ctx, uae_u32 memsize) { - if (memsize != 0x80000 && memsize != 0x100000 && - memsize != 0x200000) - { - memsize = 0x200000; - write_log (_T("Unsupported chipmem size!\n")); - } - trap_set_dreg(ctx, 0, 0); + if (memsize != 0x80000 && memsize != 0x100000 && + memsize != 0x200000) { + memsize = 0x200000; + write_log (_T("Unsupported chipmem size!\n")); + } + trap_set_dreg(ctx, 0, 0); - changed_prefs.chipmem_size = memsize; + changed_prefs.chipmem_size = memsize; uae_reset(1, 1); - return 1; + return 1; } /* * Changes slow memory size * (reboots) */ -static uae_u32 REGPARAM2 emulib_ChgSMemSize(TrapContext* ctx, uae_u32 memsize) +static uae_u32 REGPARAM2 emulib_ChgSMemSize(TrapContext *ctx, uae_u32 memsize) { - if (memsize != 0x80000 && memsize != 0x100000 && - memsize != 0x180000 && memsize != 0x1C0000) - { - memsize = 0; - write_log (_T("Unsupported bogomem size!\n")); - } + if (memsize != 0x80000 && memsize != 0x100000 && + memsize != 0x180000 && memsize != 0x1C0000) { + memsize = 0; + write_log (_T("Unsupported bogomem size!\n")); + } trap_set_dreg(ctx, 0, 0); - changed_prefs.bogomem_size = memsize; - uae_reset(1, 1); - return 1; + changed_prefs.bogomem_size = memsize; + uae_reset (1, 1); + return 1; } /* * Changes fast memory size * (reboots) */ -static uae_u32 REGPARAM2 emulib_ChgFMemSize(TrapContext* ctx, uae_u32 memsize) +static uae_u32 REGPARAM2 emulib_ChgFMemSize(TrapContext *ctx, uae_u32 memsize) { - if (memsize != 0x100000 && memsize != 0x200000 && - memsize != 0x400000 && memsize != 0x800000) - { - memsize = 0; - write_log (_T("Unsupported fastmem size!\n")); - } + if (memsize != 0x100000 && memsize != 0x200000 && + memsize != 0x400000 && memsize != 0x800000) { + memsize = 0; + write_log (_T("Unsupported fastmem size!\n")); + } trap_set_dreg(ctx, 0, 0); - changed_prefs.fastmem[0].size = memsize; - uae_reset(1, 1); - return 0; + changed_prefs.fastmem[0].size = memsize; + uae_reset (1, 1); + return 0; } /* * Inserts a disk */ -static uae_u32 emulib_InsertDisk(TrapContext* ctx, uaecptr name, uae_u32 drive) +static uae_u32 emulib_InsertDisk(TrapContext *ctx, uaecptr name, uae_u32 drive) { - char real_name[256]; - TCHAR* s; + char real_name[256]; + TCHAR *s; - if (drive > 3) - return 0; + if (drive > 3) + return 0; if (trap_get_string(ctx, real_name, name, sizeof real_name) >= sizeof real_name) - return 0; /* ENAMETOOLONG */ + return 0; /* ENAMETOOLONG */ - s = au(real_name); - _tcscpy(changed_prefs.floppyslots[drive].df, s); + s = au (real_name); + _tcscpy (changed_prefs.floppyslots[drive].df, s); xfree (s); - return 1; + return 1; } /* * Exits the emulator */ -static uae_u32 emulib_ExitEmu(void) +static uae_u32 emulib_ExitEmu (void) { uae_quit(); return 1; @@ -204,7 +203,7 @@ static uae_u32 emulib_ExitEmu(void) /* * Gets UAE Configuration */ -static uae_u32 emulib_GetUaeConfig(TrapContext* ctx, uaecptr place) +static uae_u32 emulib_GetUaeConfig(TrapContext *ctx, uaecptr place) { trap_put_long(ctx, place, version); trap_put_long(ctx, place + 4, chipmem_bank.allocated_size); @@ -214,30 +213,29 @@ static uae_u32 emulib_GetUaeConfig(TrapContext* ctx, uaecptr place) trap_put_long(ctx, place + 20, currprefs.produce_sound); trap_put_long(ctx, place + 24, currprefs.jports[0].id | (currprefs.jports[1].id << 8)); trap_put_long(ctx, place + 28, currprefs.keyboard_lang); - if (disk_empty(0)) + if (disk_empty (0)) trap_put_byte(ctx, place + 32, 0); - else + else trap_put_byte(ctx, place + 32, 1); - if (disk_empty(1)) + if (disk_empty (1)) trap_put_byte(ctx, place + 33, 0); - else + else trap_put_byte(ctx, place + 33, 1); - if (disk_empty(2)) + if (disk_empty(2)) trap_put_byte(ctx, place + 34, 0); - else + else trap_put_byte(ctx, place + 34, 1); - if (disk_empty(3)) + if (disk_empty(3)) trap_put_byte(ctx, place + 35, 0); - else + else trap_put_byte(ctx, place + 35, 1); - for (int i = 0; i < 4; i++) - { - char* s = ua(currprefs.floppyslots[i].df); + for (int i = 0; i < 4; i++) { + char *s = ua (currprefs.floppyslots[i].df); trap_put_string(ctx, s, place + 36 + i * 256, 256); xfree (s); - } - return 1; + } + return 1; } /* @@ -245,109 +243,99 @@ static uae_u32 emulib_GetUaeConfig(TrapContext* ctx, uaecptr place) * * NOT IMPLEMENTED YET */ -static uae_u32 emulib_SetUaeConfig(uaecptr place) +static uae_u32 emulib_SetUaeConfig (uaecptr place) { - return 1; + return 1; } /* * Gets the name of the disk in the given drive */ -static uae_u32 emulib_GetDisk(TrapContext* ctx, uae_u32 drive, uaecptr name) +static uae_u32 emulib_GetDisk(TrapContext *ctx, uae_u32 drive, uaecptr name) { - if (drive > 3) - return 0; + if (drive > 3) + return 0; - char* n = ua(currprefs.floppyslots[drive].df); + char *n = ua(currprefs.floppyslots[drive].df); trap_put_string(ctx, (uae_u8*)n, name, 256); xfree(n); - return 1; + return 1; } -#define CREATE_NATIVE_FUNC_PTR uae_u32 (* native_func)( uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, \ - uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32) -#define SET_NATIVE_FUNC(x) native_func = (uae_u32 (*)(uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32))(x) -#define CALL_NATIVE_FUNC( d1,d2,d3,d4,d5,d6,d7,a1,a2,a3,a4,a5,a6) if(native_func) native_func( d1,d2,d3,d4,d5,d6,d7,a1,a2,a3,a4,a5,a6 ) -/* A0 - Contains a ptr to the native .obj data. This ptr is Amiga-based. */ -/* We simply find the first function in this .obj data, and execute it. */ - -static int native_dos_op(TrapContext* ctx, uae_u32 mode, uae_u32 p1, uae_u32 p2, uae_u32 p3) +static int native_dos_op(TrapContext *ctx, uae_u32 mode, uae_u32 p1, uae_u32 p2, uae_u32 p3) { - TCHAR tmp[MAX_DPATH]; - char* s; + TCHAR tmp[MAX_DPATH]; + char *s; int v; - if (mode) - return -1; - /* receive native path from lock - * p1 = dos.library:Lock, p2 = buffer, p3 = max buffer size - */ + if (mode) + return -1; + /* receive native path from lock + * p1 = dos.library:Lock, p2 = buffer, p3 = max buffer size + */ v = get_native_path(ctx, p1, tmp); - if (v) - return v; - s = ua(tmp); + if (v) + return v; + s = ua (tmp); trap_put_string(ctx, (uae_u8*)s, p2, p3); xfree (s); - return 0; + return 0; } -static uae_u32 uaelib_demux_common(TrapContext* ctx, uae_u32 ARG0, uae_u32 ARG1, uae_u32 ARG2, uae_u32 ARG3, - uae_u32 ARG4, uae_u32 ARG5) +static uae_u32 uaelib_demux_common(TrapContext *ctx, uae_u32 ARG0, uae_u32 ARG1, uae_u32 ARG2, uae_u32 ARG3, uae_u32 ARG4, uae_u32 ARG5) { - switch (ARG0) - { - case 0: return emulib_GetVersion(); - case 1: return emulib_GetUaeConfig(ctx, ARG1); - case 2: return emulib_SetUaeConfig(ARG1); - case 3: return emulib_HardReset(); - case 4: return emulib_Reset(); - case 5: return emulib_InsertDisk(ctx, ARG1, ARG2); - case 6: return emulib_EnableSound(ARG1); - case 7: return emulib_EnableJoystick(ARG1); - case 8: return emulib_SetFrameRate(ARG1); - case 9: return emulib_ChgCMemSize(ctx, ARG1); - case 10: return emulib_ChgSMemSize(ctx, ARG1); - case 11: return emulib_ChgFMemSize(ctx, ARG1); - case 12: return emulib_ChangeLanguage(ARG1); - /* The next call brings bad luck */ - case 13: return emulib_ExitEmu(); - case 14: return emulib_GetDisk(ctx, ARG1, ARG2); - case 15: return 0; + switch (ARG0) { + case 0: return emulib_GetVersion (); + case 1: return emulib_GetUaeConfig(ctx, ARG1); + case 2: return emulib_SetUaeConfig (ARG1); + case 3: return emulib_HardReset (); + case 4: return emulib_Reset (); + case 5: return emulib_InsertDisk(ctx, ARG1, ARG2); + case 6: return emulib_EnableSound (ARG1); + case 7: return emulib_EnableJoystick (ARG1); + case 8: return emulib_SetFrameRate (ARG1); + case 9: return emulib_ChgCMemSize(ctx, ARG1); + case 10: return emulib_ChgSMemSize(ctx, ARG1); + case 11: return emulib_ChgFMemSize(ctx, ARG1); + case 12: return emulib_ChangeLanguage (ARG1); + /* The next call brings bad luck */ + case 13: return emulib_ExitEmu (); + case 14: return emulib_GetDisk(ctx, ARG1, ARG2); + case 15: return 0; - case 68: return 0; - case 69: return 0; + case 68: return 0; + case 69: return 0; - case 70: return 0; /* RESERVED. Something uses this.. */ + case 70: return 0; /* RESERVED. Something uses this.. */ - case 80: - return 0xffffffff; - case 81: return cfgfile_uaelib(ctx, ARG1, ARG2, ARG3, ARG4); - case 82: return cfgfile_uaelib_modify(ctx, ARG1, ARG2, ARG3, ARG4, ARG5); - case 83: return 0; - case 85: return native_dos_op(ctx, ARG1, ARG2, ARG3, ARG4); - case 86: - if (valid_address(ARG1, 1)) - { - uae_char tmp[MAX_DPATH]; - trap_get_string(ctx, tmp, ARG1, sizeof tmp); - TCHAR* s = au(tmp); - write_log (_T("DBG: %s\n"), s); - xfree (s); - return 1; - } - return 0; - case 87: - { - uae_u32 d0, d1; - d0 = emulib_target_getcpurate(ARG1, &d1); - trap_set_dreg(ctx, 1, d1); - return d0; - } - } - return 0; + case 80: + return 0xffffffff; + case 81: return cfgfile_uaelib(ctx, ARG1, ARG2, ARG3, ARG4); + case 82: return cfgfile_uaelib_modify(ctx, ARG1, ARG2, ARG3, ARG4, ARG5); + case 83: return 0; + case 85: return native_dos_op(ctx, ARG1, ARG2, ARG3, ARG4); + case 86: + if (valid_address(ARG1, 1)) { + uae_char tmp[MAX_DPATH]; + trap_get_string(ctx, tmp, ARG1, sizeof tmp); + TCHAR *s = au(tmp); + write_log (_T("DBG: %s\n"), s); + xfree (s); + return 1; + } + return 0; + case 87: + { + uae_u32 d0, d1; + d0 = emulib_target_getcpurate (ARG1, &d1); + trap_set_dreg(ctx, 1, d1); + return d0; + } + } + return 0; } -static uae_u32 REGPARAM2 uaelib_demux2(TrapContext* ctx) +static uae_u32 REGPARAM2 uaelib_demux2 (TrapContext *ctx) { #define ARG0 (trap_get_long(ctx, trap_get_areg(ctx, 7) + 4)) #define ARG1 (trap_get_long(ctx, trap_get_areg(ctx, 7) + 8)) @@ -363,25 +351,25 @@ static uae_u32 REGPARAM2 uaelib_demux2(TrapContext* ctx) return uaelib_demux_common(ctx, ARG0, ARG1, ARG2, ARG3, ARG4, ARG5); } -static uae_u32 REGPARAM2 uaelib_demux(TrapContext* ctx) +static uae_u32 REGPARAM2 uaelib_demux (TrapContext *ctx) { - uae_u32 v; + uae_u32 v; - v = uaelib_demux2(ctx); - return v; + v = uaelib_demux2 (ctx); + return v; } /* * Installs the UAE LIBRARY */ -void emulib_install(void) +void emulib_install (void) { - uaecptr a; + uaecptr a; if (!uae_boot_rom_type && !currprefs.uaeboard) - return; - a = here(); - org(rtarea_base + 0xFF60); - calltrap(deftrapres (uaelib_demux, 0, _T("uaelib_demux"))); - dw(RTS); - org(a); + return; + a = here (); + org (rtarea_base + 0xFF60); + calltrap (deftrapres (uaelib_demux, 0, _T("uaelib_demux"))); + dw (RTS); + org (a); } diff --git a/src/zfile.cpp b/src/zfile.cpp index b14b895f..a7684453 100644 --- a/src/zfile.cpp +++ b/src/zfile.cpp @@ -75,10 +75,6 @@ static struct zcache *cache_get (const TCHAR *name) return NULL; } -static void zcache_flush (void) -{ -} - static void zcache_free_data (struct zcache *zc) { int i; @@ -115,17 +111,6 @@ static void zcache_free (struct zcache *zc) pl->next = nxt; } -static void zcache_close (void) -{ - struct zcache *zc = zcachedata; - while (zc) { - struct zcache *n = zc->next; - zcache_free_data (zc); - xfree (n); - zc = n; - } -} - static void zcache_check (void) { int cnt = 0; @@ -186,15 +171,10 @@ static void zfile_free (struct zfile *f) { if (f->f) fclose (f->f); - if (f->deleteafterclose) { - _wunlink (f->name); - write_log (_T("deleted temporary file '%s'\n"), f->name); - } xfree (f->name); xfree (f->originalname); xfree (f->data); xfree (f->mode); - xfree (f->userdata); xfree (f); } @@ -310,6 +290,8 @@ int zfile_gettype (struct zfile *z) zfile_fseek (z, -8, SEEK_CUR); if (!memcmp (buf, exeheader, sizeof(buf))) return ZFILE_DISKIMAGE; + if (!memcmp (buf, "CAPS", 4)) + return ZFILE_DISKIMAGE; if (!memcmp (buf, "UAE--ADF", 8)) return ZFILE_DISKIMAGE; if (!memcmp (buf, "UAE-1ADF", 8)) @@ -403,6 +385,7 @@ static struct zfile *zfile_gunzip (struct zfile *z, int *retcode) zs.next_out = z2->data; zs.avail_out = size; first = 1; + ret = Z_STREAM_ERROR; do { zs.next_in = buffer; zs.avail_in = zfile_fread (buffer, 1, sizeof (buffer), z); @@ -680,6 +663,143 @@ end: return NULL; } +#ifdef CAPS +#include "uae/caps.h" +static struct zfile *ipf (struct zfile *z, int index, int *retcode) +{ + int i, j, r; + struct zfile *zo; + TCHAR *orgname = zfile_getname (z); + TCHAR *ext = _tcsrchr (orgname, '.'); + TCHAR newname[MAX_DPATH]; + uae_u16 *amigamfmbuffer; + uae_u8 writebuffer_ok[32]; + int tracks, len; + int outsize; + int startpos = 0; + uae_u8 *outbuf; + uae_u8 tmp[12]; + struct zcache *zc; + + if (checkwrite (z, retcode)) + return NULL; + + if (index > 2) + return NULL; + + zc = cache_get (z->name); + if (!zc) { + uae_u16 *mfm; + struct zdiskimage *zd; + if (!caps_loadimage (z, 0, &tracks)) + return NULL; + mfm = xcalloc (uae_u16, 32000 / 2); + zd = xcalloc (struct zdiskimage, 1); + zd->tracks = tracks; + for (i = 0; i < tracks; i++) { + uae_u8 *buf, *p; + int mrev, gapo; + caps_loadtrack (mfm, NULL, 0, i, &len, &mrev, &gapo, NULL, true); + //write_log (_T("%d: %d %d %d\n"), i, mrev, gapo, len); + len /= 8; + buf = p = xmalloc (uae_u8, len); + for (j = 0; j < len / 2; j++) { + uae_u16 v = mfm[j]; + *p++ = v >> 8; + *p++ = v; + } + zd->zdisktracks[i].data = buf; + zd->zdisktracks[i].len = len; + } + caps_unloadimage (0); + zc = zcache_put (z->name, zd); + } + + outbuf = xcalloc (uae_u8, 16384); + amigamfmbuffer = xcalloc (uae_u16, 32000 / 2); + if (ext) { + _tcscpy (newname, orgname); + _tcscpy (newname + _tcslen (newname) - _tcslen (ext), _T(".adf")); + } else { + _tcscat (newname, _T(".adf")); + } + if (index == 1) + _tcscpy (newname + _tcslen (newname) - 4, _T(".ima")); + if (index == 2) + _tcscpy (newname + _tcslen (newname) - 4, _T(".ext.adf")); + + zo = zfile_fopen_empty (z, newname, 0); + if (!zo) + goto end; + + if (retcode) + *retcode = 1; + + tracks = zc->zd->tracks; + + if (index > 1) { + zfile_fwrite ("UAE-1ADF", 8, 1, zo); + tmp[0] = 0; tmp[1] = 0; /* flags (reserved) */ + tmp[2] = 0; tmp[3] = tracks; /* number of tracks */ + zfile_fwrite (tmp, 4, 1, zo); + memset (tmp, 0, sizeof tmp); + tmp[2] = 0; tmp[3] = 1; /* track type */ + startpos = zfile_ftell (zo); + for (i = 0; i < tracks; i++) + zfile_fwrite (tmp, sizeof tmp, 1, zo); + } + + outsize = 0; + for (i = 0; i < tracks; i++) { + uae_u8 *p = (uae_u8*)zc->zd->zdisktracks[i].data; + len = zc->zd->zdisktracks[i].len; + memset (writebuffer_ok, 0, sizeof writebuffer_ok); + memset (outbuf, 0, 16384); + if (index == 0) { + r = isamigatrack (amigamfmbuffer, p, len, outbuf, writebuffer_ok, i, &outsize); + if (r < 0 && i == 0) { + zfile_seterror (_T("'%s' is not AmigaDOS formatted"), orgname); + goto end; + } + zfile_fwrite (outbuf, 1, outsize, zo); + } else if (index == 1) { + r = ispctrack (amigamfmbuffer, p, len, outbuf, writebuffer_ok, i, &outsize); + if (r < 0 && i == 0) { + zfile_seterror (_T("'%s' is not PC formatted"), orgname); + goto end; + } + zfile_fwrite (outbuf, outsize, 1, zo); + } else { + int pos = zfile_ftell (zo); + int maxlen = len > 12798 ? len : 12798; + int lenb = len * 8; + + if (maxlen & 1) + maxlen++; + zfile_fseek (zo, startpos + i * 12 + 4, SEEK_SET); + tmp[4] = 0; tmp[5] = 0; tmp[6] = maxlen >> 8; tmp[7] = maxlen; + tmp[8] = lenb >> 24; tmp[9] = lenb >> 16; tmp[10] = lenb >> 8; tmp[11] = lenb; + zfile_fwrite (tmp + 4, 2, 4, zo); + zfile_fseek (zo, pos, SEEK_SET); + zfile_fwrite (p, 1, len, zo); + if (maxlen > len) + zfile_fwrite (outbuf, 1, maxlen - len, zo); + } + } + zfile_fclose (z); + xfree (amigamfmbuffer); + xfree (outbuf); + if (index == 0) + truncate880k (zo); + return zo; +end: + zfile_fclose (zo); + xfree (amigamfmbuffer); + xfree (outbuf); + return NULL; +} +#endif + #ifdef A_LZX static struct zfile *dsq (struct zfile *z, int lzx, int *retcode) { @@ -943,9 +1063,9 @@ end: } #endif -const TCHAR *uae_ignoreextensions[] = +static const TCHAR *uae_ignoreextensions[] = { _T(".gif"), _T(".jpg"), _T(".png"), _T(".xml"), _T(".pdf"), _T(".txt"), 0 }; -const TCHAR *uae_diskimageextensions[] = +static const TCHAR *uae_diskimageextensions[] = { _T(".adf"), _T(".adz"), _T(".ipf"), _T(".scp"), _T(".fdi"), _T(".exe"), _T(".dms"), _T(".wrp"), _T(".dsq"), 0 }; int zfile_is_ignore_ext(const TCHAR *name) @@ -1138,6 +1258,10 @@ struct zfile *zuncompress (struct znode *parent, struct zfile *z, int dodefault, #endif } if (mask & ZFD_RAWDISK) { +#ifdef CAPS + if (stricmp (ext, _T("ipf")) == 0) + return ipf (z, index, retcode); +#endif if (stricmp(ext, _T("fdi")) == 0) return fdi (z, index, retcode); if (mask & (ZFD_RAWDISK_PC | ZFD_RAWDISK_AMIGA)) @@ -1175,6 +1299,10 @@ struct zfile *zuncompress (struct znode *parent, struct zfile *z, int dodefault, #endif } if (mask & ZFD_RAWDISK) { +#ifdef CAPS + if (header[0] == 'C' && header[1] == 'A' && header[2] == 'P' && header[3] == 'S') + return ipf (z, index, retcode); +#endif if (!memcmp (header, "Formatte", 8)) return fdi (z, index, retcode); if (!memcmp (header, "UAE-1ADF", 8)) @@ -1300,7 +1428,6 @@ static struct zfile *zfile_fopen_2 (const TCHAR *name, const TCHAR *mode, int ma l->zfdmask = mask; if (!_tcsicmp (mode, _T("r"))) { f = my_opentext (l->name); - l->textmode = 1; } else { f = uae_tfopen (l->name, mode); } @@ -1512,9 +1639,7 @@ static struct zfile *zfile_fopenx2 (const TCHAR *name, const TCHAR *mode, int ma static struct zfile *zfile_fopenx (const TCHAR *name, const TCHAR *mode, int mask, int index) { struct zfile *zf; - //write_log (_T("zfile_fopen('%s','%s',%08x,%d)\n"), name, mode, mask, index); zf = zfile_fopenx2 (name, mode, mask, index); - //write_log (_T("=%p\n"), zf); return zf; } @@ -1538,11 +1663,7 @@ struct zfile *zfile_dup (struct zfile *zf) return NULL; if (zf->archiveparent) checkarchiveparent (zf); - if (zf->userdata) - return NULL; - if (!zf->data && zf->dataseek) { - nzf = zfile_create (zf, NULL); - } else if (zf->data) { + if (zf->data) { nzf = zfile_create (zf, NULL); nzf->data = xmalloc (uae_u8, zf->size); if (!nzf->data) { @@ -1673,23 +1794,6 @@ struct zfile *zfile_fopen_data (const TCHAR *name, uae_u64 size, const uae_u8 *d return l; } -uae_u8 *zfile_load_data (const TCHAR *name, const uae_u8 *data,int datalen, int *outlen) -{ - struct zfile *zf, *f; - int size; - uae_u8 *out; - - zf = zfile_fopen_data (name, datalen, data); - f = zfile_gunzip (zf); - size = f->datasize; - zfile_fseek (f, 0, SEEK_SET); - out = xmalloc (uae_u8, size); - zfile_fread (out, 1, size, f); - zfile_fclose (f); - *outlen = size; - return out; -} - uae_u8 *zfile_load_file(const TCHAR *name, int *outlen) { struct zfile *zf; @@ -1732,16 +1836,14 @@ uae_s64 zfile_size (struct zfile *z) uae_s64 zfile_ftell (struct zfile *z) { - if (z->data || z->dataseek || z->parent) + if (z->data || z->parent) return z->seek; return _ftelli64 (z->f); } uae_s64 zfile_fseek (struct zfile *z, uae_s64 offset, int mode) { - if (z->zfileseek) - return z->zfileseek (z, offset, mode); - if (z->data || z->dataseek || (z->parent && z->useparent)) { + if (z->data || (z->parent && z->useparent)) { int ret = 0; switch (mode) { @@ -1772,8 +1874,6 @@ uae_s64 zfile_fseek (struct zfile *z, uae_s64 offset, int mode) size_t zfile_fread (void *b, size_t l1, size_t l2, struct zfile *z) { - if (z->zfileread) - return z->zfileread (b, l1, l2, z); if (z->data) { if (z->datasize < z->size && z->seek + l1 * l2 > z->datasize) { if (z->archiveparent) { @@ -1820,8 +1920,6 @@ size_t zfile_fwrite (const void *b, size_t l1, size_t l2, struct zfile *z) { if (z->archiveparent) return 0; - if (z->zfilewrite) - return z->zfilewrite (b, l1, l2, z); if (z->parent && z->useparent) return 0; if (z->data) { @@ -1848,15 +1946,6 @@ size_t zfile_fwrite (const void *b, size_t l1, size_t l2, struct zfile *z) return fwrite (b, l1, l2, z->f); } -size_t zfile_fputs (struct zfile *z, const TCHAR *s) -{ - char *s2 = ua (s); - size_t t; - t = zfile_fwrite (s2, strlen (s2), 1, z); - xfree (s2); - return t; -} - char *zfile_fgetsa(char *s, int size, struct zfile *z) { checkarchiveparent (z); @@ -2142,22 +2231,6 @@ static struct znode *znode_alloc_child(struct znode *parent, const TCHAR *name) return zn; } -static struct znode *znode_alloc_sibling(struct znode *sibling, const TCHAR *name) -{ - struct znode *zn = znode_alloc(sibling->parent, name); - - if (!sibling->sibling) { - sibling->sibling = zn; - } else { - struct znode *pn = sibling->sibling; - while (pn->sibling) - pn = pn->sibling; - pn->sibling = zn; - } - zn->parent = sibling->parent; - return zn; -} - static void zvolume_addtolist(struct zvolume *zv) { if (!zv) @@ -2217,12 +2290,7 @@ struct zvolume *zvolume_alloc (struct zfile *z, unsigned int id, void *handle, c return zvolume_alloc_2 (zfile_getname (z), z, id, handle, volumename); } -static struct zvolume *zvolume_alloc_nofile (const TCHAR *name, unsigned int id, void *handle, const TCHAR *volumename) -{ - return zvolume_alloc_2 (name, NULL, id, handle, volumename); -} - -struct zvolume *zvolume_alloc_empty (struct zvolume *prev, const TCHAR *name) +static struct zvolume *zvolume_alloc_empty (struct zvolume *prev, const TCHAR *name) { struct zvolume *zv = zvolume_alloc_2(name, 0, 0, 0, NULL); if (!zv) @@ -2414,40 +2482,11 @@ static struct zvolume *prepare_recursive_volume (struct zvolume *zv, const TCHAR goto end; zvnew = zfile_fopen_archive_ext (zv->parentz, zf, flags); if (!zvnew && !(flags & ZFD_NORECURSE)) { -#if 1 zvnew = archive_directory_plain (zf); if (zvnew) { zfile_fopen_archive_recurse (zvnew, flags); done = 1; } -#else - int rc; - int index; - struct zfile *zf2, *zf3; - TCHAR oldname[MAX_DPATH]; - _tcscpy (oldname, zf->name); - index = 0; - for (;;) { - zf3 = zfile_dup (zf); - if (!zf3) - break; - zf2 = zuncompress (&zv->root, zf3, 0, ZFD_ALL, &rc, index); - if (zf2) { - zvnew = archive_directory_plain (zf2); - if (zvnew) { - zvnew->parent = zv->parent; - zfile_fopen_archive_recurse (zvnew); - done = 1; - } - } else { - zfile_fclose (zf3); - if (rc <= 0) - break; - } - index++; - break; // TODO - } -#endif } else if (zvnew) { zvnew->parent = zv->parent; zfile_fopen_archive_recurse (zvnew, flags); @@ -2532,7 +2571,7 @@ static bool valid_zi(struct zarchive_info *zai) return true; } -struct znode *znode_adddir(struct znode *parent, const TCHAR *name, struct zarchive_info *zai) +static struct znode *znode_adddir(struct znode *parent, const TCHAR *name, struct zarchive_info *zai) { struct znode *zn; TCHAR path[MAX_DPATH]; @@ -2619,47 +2658,7 @@ struct znode *zvolume_addfile_abs(struct zvolume *zv, struct zarchive_info *zai) return zn; } -static struct zvolume *zfile_fopen_directory (const TCHAR *dirname) -{ - struct zvolume *zv = NULL; - struct my_opendir_s *dir; - TCHAR fname[MAX_DPATH]; - - dir = my_opendir (dirname); - if (!dir) - return NULL; - zv = zvolume_alloc_nofile (dirname, ArchiveFormatDIR, NULL, NULL); - while (my_readdir (dir, fname)) { - TCHAR fullname[MAX_DPATH]; - struct mystat statbuf; - struct zarchive_info zai = { 0 }; - if (!_tcscmp (fname, _T(".")) || !_tcscmp (fname, _T(".."))) - continue; - _tcscpy (fullname, dirname); - _tcscat (fullname, FSDB_DIR_SEPARATOR_S); - _tcscat (fullname, fname); - if (!my_stat (fullname, &statbuf)) - continue; - zai.name = fname; - zai.size = statbuf.size; - zai.tv.tv_sec = statbuf.mtime.tv_sec; - zai.tv.tv_usec = statbuf.mtime.tv_usec; - if (statbuf.mode & FILEFLAG_DIR) { - zvolume_adddir_abs (zv, &zai); - } else { - struct znode *zn; - zn = zvolume_addfile_abs (zv, &zai); - //zfile_fopen_archive_recurse2 (zv, zn); - } - } - my_closedir (dir); - // zfile_fopen_archive_recurse (zv); - if (zv) - zvolume_addtolist (zv); - return zv; -} - -struct zvolume *zfile_fopen_archive (const TCHAR *filename, int flags) +static struct zvolume *zfile_fopen_archive (const TCHAR *filename, int flags) { struct zvolume *zv = NULL; struct zfile *zf = zfile_fopen_nozip (filename, _T("rb")); @@ -2691,37 +2690,6 @@ struct zvolume *zfile_fopen_archive (const TCHAR *filename) return zfile_fopen_archive (filename, ZFD_ALL); } -struct zvolume *zfile_fopen_archive_root (const TCHAR *filename, int flags) -{ - TCHAR path[MAX_DPATH], *p1, *p2, *lastp; - struct zvolume *zv = NULL; - //int last = 0; - int num, i; - - if (my_existsdir (filename)) - return zfile_fopen_directory (filename); - - num = 1; - lastp = NULL; - for (;;) { - _tcscpy (path, filename); - p1 = p2 = path; - for (i = 0; i < num; i++) { - while (*p1 != FSDB_DIR_SEPARATOR && *p1 != 0) - p1++; - if (*p1 == 0 && p1 == lastp) - return NULL; - if (i + 1 < num) - p1++; - } - *p1 = 0; - lastp = p1; - if (my_existsfile (p2)) - return zfile_fopen_archive (p2, flags); - num++; - } -} - void zfile_fclose_archive(struct zvolume *zv) { struct znode *zn; @@ -2771,7 +2739,7 @@ struct zdirectory { TCHAR **filenames; }; -struct zdirectory *zfile_opendir_archive (const TCHAR *path, int flags) +static struct zdirectory *zfile_opendir_archive (const TCHAR *path, int flags) { struct zvolume *zv = get_zvolume(path); bool created = false; @@ -2818,7 +2786,7 @@ void zfile_closedir_archive(struct zdirectory *zd) xfree (zd->filenames); xfree(zd); } -int zfile_readdir_archive (struct zdirectory *zd, TCHAR *out, bool fullpath) +static int zfile_readdir_archive (struct zdirectory *zd, TCHAR *out, bool fullpath) { if (out) out[0] = 0; @@ -2865,21 +2833,6 @@ int zfile_readdir_archive (struct zdirectory *zd, TCHAR *out) return zfile_readdir_archive (zd, out, false); } -struct zfile *zfile_readdir_archive_open (struct zdirectory *zd, const TCHAR *mode) -{ - TCHAR path[MAX_DPATH]; - if (!zfile_readdir_archive (zd, path, true)) - return NULL; - return zfile_fopen (path, mode, ZFD_ARCHIVE | ZFD_NORECURSE); -} - - -void zfile_resetdir_archive (struct zdirectory *zd) -{ - zd->offset = 0; - zd->n = zd->first; -} - int zfile_fill_file_attrs_archive(const TCHAR *path, int *isdir, int *flags, TCHAR **comment) { struct zvolume *zv = get_zvolume(path); @@ -2981,35 +2934,6 @@ int zfile_exists_archive (const TCHAR *path, const TCHAR *rel) return zn ? 1 : 0; } -int zfile_convertimage (const TCHAR *src, const TCHAR *dst) -{ - struct zfile *s, *d; - int ret = 0; - - s = zfile_fopen (src, _T("rb"), ZFD_NORMAL); - if (s) { - uae_u8 *b; - int size; - zfile_fseek (s, 0, SEEK_END); - size = zfile_ftell (s); - zfile_fseek (s, 0, SEEK_SET); - b = xcalloc (uae_u8, size); - if (b) { - if (zfile_fread (b, size, 1, s) == 1) { - d = zfile_fopen (dst, _T("wb"), 0); - if (d) { - if (zfile_fwrite (b, size, 1, d) == 1) - ret = 1; - zfile_fclose (d); - } - } - xfree (b); - } - zfile_fclose (s); - } - return ret; -} - #ifdef _CONSOLE static TCHAR *zerror; #define WRITE_LOG_BUF_SIZE 4096 @@ -3025,10 +2949,6 @@ void zfile_seterror (const TCHAR *format, ...) va_end (parms); } } -TCHAR *zfile_geterror (void) -{ - return zerror; -} #else void zfile_seterror (const TCHAR *format, ...) { diff --git a/src/zfile_archive.cpp b/src/zfile_archive.cpp index 35332d06..7e7177b4 100644 --- a/src/zfile_archive.cpp +++ b/src/zfile_archive.cpp @@ -22,9 +22,6 @@ #include "zarchive.h" #include "disk.h" -#define unpack_log write_log -#undef unpack_log -#define unpack_log(fmt, ...) static time_t fromdostime (uae_u32 dd) { @@ -138,10 +135,6 @@ struct zfile *archive_access_select (struct znode *parent, struct zfile *zf, uns diskimg = zfile_is_diskimage (zn->fullname); if (isok) { if (tmphist[0]) { -#ifndef _CONSOLE - if (diskimg >= 0 && canhistory) - DISK_history_add (tmphist, -1, diskimg, 1); -#endif tmphist[0] = 0; first = 0; } @@ -150,10 +143,6 @@ struct zfile *archive_access_select (struct znode *parent, struct zfile *zf, uns _tcscpy (tmphist, zn->fullname); } else { _tcscpy (tmphist, zn->fullname); -#ifndef _CONSOLE - if (diskimg >= 0 && canhistory) - DISK_history_add (tmphist, -1, diskimg, 1); -#endif tmphist[0] = 0; } select = 0; @@ -206,8 +195,6 @@ struct zfile *archive_access_select (struct znode *parent, struct zfile *zf, uns } #ifndef _CONSOLE diskimg = zfile_is_diskimage (zfile_getname (zf)); - if (diskimg >= 0 && first && tmphist[0] && canhistory) - DISK_history_add (zfile_getname (zf), -1, diskimg, 1); #endif zfile_fclose_archive (zv); if (z) { @@ -327,7 +314,7 @@ struct zvolume *archive_directory_tar (struct zfile *z) return zv; } -struct zfile *archive_access_tar (struct znode *zn) +static struct zfile *archive_access_tar (struct znode *zn) { return zfile_fopen_parent (zn->volume->archive, zn->fullname, zn->offset, zn->size); } @@ -440,22 +427,16 @@ static struct zfile *archive_do_zip (struct znode *zn, struct zfile *z, int flag if (z) { int err = -1; if (!(flags & FILE_DELAYEDOPEN) || z->size <= PEEK_BYTES) { - unpack_log (_T("ZIP: unpacking %s, flags=%d\n"), name, flags); err = unzReadCurrentFile (uz, z->data, z->datasize); - unpack_log (_T("ZIP: unpacked, code=%d\n"), err); } else { z->archiveparent = zfile_dup (zn->volume->archive); if (z->archiveparent) { - unpack_log (_T("ZIP: delayed open '%s'\n"), name); xfree (z->archiveparent->name); z->archiveparent->name = my_strdup (tmp); z->datasize = PEEK_BYTES; err = unzReadCurrentFile (uz, z->data, z->datasize); - unpack_log (_T("ZIP: unpacked, code=%d\n"), err); } else { - unpack_log (_T("ZIP: unpacking %s (failed DELAYEDOPEN)\n"), name); err = unzReadCurrentFile (uz, z->data, z->datasize); - unpack_log (_T("ZIP: unpacked, code=%d\n"), err); } } } @@ -710,7 +691,7 @@ static int canrar (void) return israr < 0 ? 0 : 1; } -static int CALLBACK RARCallbackProc (UINT msg, LONG UserData, LONG P1, LONG P2) +static int CALLBACK RARCallbackProc (UINT msg, LPARAM UserData, LPARAM P1, LPARAM P2) { if (msg == UCM_PROCESSDATA) { zfile_fwrite ((uae_u8*)P1, 1, P2, rarunpackzf); @@ -734,9 +715,6 @@ static void archive_close_rar (void *ctx) struct zvolume *archive_directory_rar (struct zfile *z) { -#ifdef WIN64 - return archive_directory_arcacc (z, ArchiveFormatRAR); -#else struct zvolume *zv; struct RARContext *rc; struct zfile *zftmp; @@ -776,12 +754,10 @@ struct zvolume *archive_directory_rar (struct zfile *z) zv->archive = zftmp; zv->method = ArchiveFormatRAR; return zv; -#endif } static struct zfile *archive_access_rar (struct znode *zn) { -#ifndef WIN64 struct RARContext *rc = (struct RARContext*)zn->volume->handle; int i; struct zfile *zf = NULL; @@ -812,12 +788,9 @@ static struct zfile *archive_access_rar (struct znode *zn) end: pRARCloseArchive(rc->hArcData); return zf; -#else - return NULL; -#endif } -#endif +#endif /* ArchiveAccess */ @@ -986,7 +959,7 @@ struct zvolume *archive_directory_arcacc (struct zfile *z, unsigned int id) static struct zfile *archive_access_arcacc (struct znode *zn) { - struct zfile *zf; + struct zfile *zf = NULL; struct zfile *z = zn->volume->archive; int status, id_r, id_w; aaHandle ah; @@ -1180,27 +1153,6 @@ static const int secs_per_day = 24 * 60 * 60; static const int diff = (8 * 365 + 2) * (24 * 60 * 60); static const int diff2 = (-8 * 365 - 2) * (24 * 60 * 60); -static time_t put_time (long days, long mins, long ticks) -{ - time_t t; - - if (days < 0) - days = 0; - if (days > 9900 * 365) - days = 9900 * 365; // in future far enough? - if (mins < 0 || mins >= 24 * 60) - mins = 0; - if (ticks < 0 || ticks >= 60 * 50) - ticks = 0; - - t = ticks / 50; - t += mins * 60; - t += ((uae_u64)days) * secs_per_day; - t += diff; - - return t; -} - static int adf_read_block (struct adfhandle *adf, int block) { memset (adf->block, 0, adf->blocksize); @@ -2123,7 +2075,6 @@ struct zfile *archive_unpackzfile (struct zfile *zf) struct zfile *zout = NULL; if (!zf->archiveparent) return NULL; - unpack_log (_T("delayed unpack '%s'\n"), zf->name); zf->datasize = zf->size; switch (zf->archiveid) {