Update to v106r66 release.

byuu says:

Changelog:

  - moved to GCC 8.2 and C++17
  - fixed compilation under FreeBSD 12.0
  - don't read beyond the file size in
    SuperFamicom::Cartridge::loadMemory
  - add missing I/O cycle HuC6280::instructionImmediate
  - serialize Mega Drive's Game Genie state
  - serialize SPC7110::Thread information
  - enable 30-bit color depth support under the GLX/OpenGL 2.0 driver
    (doesn't work with OpenGL 3.2 yet)

The 30-bit color depth option isn't super useful, but why not? I need to
update ruby to detect that the display is actually capable of it before
exposing an option that can result in the driver failing to initialize,
however.
This commit is contained in:
Tim Allen 2018-12-20 11:55:47 +11:00
parent 0b44399c0a
commit 4c4e79aa0e
15 changed files with 65 additions and 26 deletions

View File

@ -28,7 +28,7 @@ using namespace nall;
namespace Emulator { namespace Emulator {
static const string Name = "higan"; static const string Name = "higan";
static const string Version = "106.65"; static const string Version = "106.66";
static const string Author = "byuu"; static const string Author = "byuu";
static const string License = "GPLv3"; static const string License = "GPLv3";
static const string Website = "https://byuu.org/"; static const string Website = "https://byuu.org/";

View File

@ -3,5 +3,11 @@ auto Cartridge::serialize(serializer& s) -> void {
s.integer(ramEnable); s.integer(ramEnable);
s.integer(ramWritable); s.integer(ramWritable);
s.array(romBank); s.array(romBank);
s.boolean(gameGenie.enable);
for(auto& code : gameGenie.codes) {
s.boolean(code.enable);
s.integer(code.address);
s.integer(code.data);
}
if(slot) slot->serialize(s); if(slot) slot->serialize(s);
} }

View File

@ -139,7 +139,8 @@ L io();
} }
auto HuC6280::instructionImmediate(fp alu, uint8& data) -> void { auto HuC6280::instructionImmediate(fp alu, uint8& data) -> void {
L data = ALU(operand()); L io();
data = ALU(operand());
} }
auto HuC6280::instructionImplied(fp alu, uint8& data) -> void { auto HuC6280::instructionImplied(fp alu, uint8& data) -> void {

View File

@ -125,7 +125,7 @@ auto Cartridge::loadMemory(Memory& ram, Markup::Node node, bool required) -> voi
if(memory->type == "RAM" && !memory->nonVolatile) return; if(memory->type == "RAM" && !memory->nonVolatile) return;
if(memory->type == "RTC" && !memory->nonVolatile) return; if(memory->type == "RTC" && !memory->nonVolatile) return;
if(auto fp = platform->open(pathID(), memory->name(), File::Read, required)) { if(auto fp = platform->open(pathID(), memory->name(), File::Read, required)) {
fp->read(ram.data(), ram.size()); fp->read(ram.data(), min(fp->size(), ram.size()));
} }
} }
} }

View File

@ -1,4 +1,5 @@
auto SPC7110::serialize(serializer& s) -> void { auto SPC7110::serialize(serializer& s) -> void {
Thread::serialize(s);
s.array(ram.data(), ram.size()); s.array(ram.data(), ram.size());
s.integer(r4801); s.integer(r4801);

View File

@ -224,6 +224,9 @@ auto Presentation::clearViewport() -> void {
if(!emulator->loaded()) viewportLayout.setPadding(); if(!emulator->loaded()) viewportLayout.setPadding();
if(!visible() || !video) return; if(!visible() || !video) return;
uint32_t opaqueBlack = 0xff000000;
if(settings.video.format == "RGB30") opaqueBlack = 0xc0000000;
uint32_t* output; uint32_t* output;
uint length; uint length;
uint width = 16; uint width = 16;
@ -231,7 +234,7 @@ auto Presentation::clearViewport() -> void {
if(video.acquire(output, length, width, height)) { if(video.acquire(output, length, width, height)) {
for(uint y : range(height)) { for(uint y : range(height)) {
auto line = output + y * (length >> 2); auto line = output + y * (length >> 2);
for(uint x : range(width)) *line++ = 0xff000000; for(uint x : range(width)) *line++ = opaqueBlack;
} }
video.release(); video.release();
video.output(); video.output();

View File

@ -50,6 +50,8 @@ auto Program::updateVideoFormat() -> void {
settings.video.format = video.format(); settings.video.format = video.format();
} }
video.setFormat(settings.video.format); video.setFormat(settings.video.format);
Emulator::video.setDepth(settings.video.format == "RGB30" ? 30 : 24);
Emulator::video.setPalette();
} }
auto Program::updateVideoShader() -> void { auto Program::updateVideoShader() -> void {

View File

@ -153,12 +153,13 @@ auto DriverSettings::videoFormatChanged() -> void {
} }
//videoFormatOption.setEnabled(video.hasFormat()); //videoFormatOption.setEnabled(video.hasFormat());
layout.setGeometry(layout.geometry()); layout.setGeometry(layout.geometry());
videoFormatChange();
} }
auto DriverSettings::videoFormatChange() -> void { auto DriverSettings::videoFormatChange() -> void {
auto item = videoFormatOption.selected(); auto item = videoFormatOption.selected();
settings.video.format = item.text(); settings.video.format = item.text();
video.setFormat(item.text()); program.updateVideoFormat();
} }
// //

View File

@ -60,11 +60,17 @@ auto Video::setPalette() -> void {
b = uclamp<16>(b * luminance); b = uclamp<16>(b * luminance);
} }
//convert color from 16-bits/channel to 8-bits/channel; force alpha to 1.0 switch(depth) {
palette[index] = a.byte(1) << 24 | r.byte(1) << 16 | g.byte(1) << 8 | b.byte(1) << 0; case 24: palette[index] = r >> 8 << 16 | g >> 8 << 8 | b >> 8 << 0; break;
case 30: palette[index] = r >> 6 << 20 | g >> 6 << 10 | b >> 6 << 0; break;
}
} }
} }
auto Video::setDepth(uint depth) -> void {
this->depth = depth;
}
auto Video::setSaturation(double saturation) -> void { auto Video::setSaturation(double saturation) -> void {
this->saturation = saturation; this->saturation = saturation;
} }
@ -130,21 +136,23 @@ auto Video::refresh(uint32* input, uint pitch, uint width, uint height) -> void
*target++ = color; *target++ = color;
} }
} else { } else {
uint32 mask = depth == 30 ? 0x40100401 : 0x01010101;
for(uint x : range(width)) { for(uint x : range(width)) {
auto a = *target; auto a = *target;
auto b = palette[*source++]; auto b = palette[*source++];
*target++ = (a + b - ((a ^ b) & 0x01010101)) >> 1; *target++ = (a + b - ((a ^ b) & mask)) >> 1;
} }
} }
} }
if(effects.colorBleed) { if(effects.colorBleed) {
uint32 mask = depth == 30 ? 0x40100401 : 0x01010101;
for(uint y : range(height)) { for(uint y : range(height)) {
auto target = output + y * width; auto target = output + y * width;
for(uint x : range(width)) { for(uint x : range(width)) {
auto a = target[x]; auto a = target[x];
auto b = target[x + (x != width - 1)]; auto b = target[x + (x != width - 1)];
target[x] = (a + b - ((a ^ b) & 0x01010101)) >> 1; target[x] = (a + b - ((a ^ b) & mask)) >> 1;
} }
} }
} }
@ -164,6 +172,7 @@ auto Video::refresh(uint32* input, uint pitch, uint width, uint height) -> void
for(auto& sprite : sprites) { for(auto& sprite : sprites) {
if(!sprite->visible) continue; if(!sprite->visible) continue;
uint32 opaqueAlpha = depth == 30 ? 0xc0000000 : 0xff000000;
for(int y : range(sprite->height)) { for(int y : range(sprite->height)) {
for(int x : range(sprite->width)) { for(int x : range(sprite->width)) {
int pixelY = sprite->y + y; int pixelY = sprite->y + y;
@ -173,7 +182,7 @@ auto Video::refresh(uint32* input, uint pitch, uint width, uint height) -> void
if(pixelX < 0 || pixelX >= width) continue; if(pixelX < 0 || pixelX >= width) continue;
auto pixel = sprite->pixels[y * sprite->width + x]; auto pixel = sprite->pixels[y * sprite->width + x];
if(pixel) output[pixelY * width + pixelX] = 0xff000000 | pixel; if(pixel) output[pixelY * width + pixelX] = opaqueAlpha | pixel;
} }
} }
} }

View File

@ -17,6 +17,7 @@ struct Video {
auto reset(Interface* interface) -> void; auto reset(Interface* interface) -> void;
auto setPalette() -> void; auto setPalette() -> void;
auto setDepth(uint depth) -> void;
auto setSaturation(double saturation) -> void; auto setSaturation(double saturation) -> void;
auto setGamma(double gamma) -> void; auto setGamma(double gamma) -> void;
auto setLuminance(double luminance) -> void; auto setLuminance(double luminance) -> void;
@ -40,6 +41,7 @@ private:
uint height = 0; uint height = 0;
uint colors = 0; uint colors = 0;
uint depth = 24;
double saturation = 1.0; double saturation = 1.0;
double gamma = 1.0; double gamma = 1.0;
double luminance = 1.0; double luminance = 1.0;

View File

@ -40,28 +40,28 @@ ifeq ($(platform),)
endif endif
compiler.c = $(compiler) -x c -std=c11 compiler.c = $(compiler) -x c -std=c11
compiler.cpp = $(compiler) -x c++ -std=c++14 compiler.cpp = $(compiler) -x c++ -std=c++17
compiler.objc = $(compiler) -x objective-c -std=c11 compiler.objc = $(compiler) -x objective-c -std=c11
compiler.objcpp = $(compiler) -x objective-c++ -std=c++14 compiler.objcpp = $(compiler) -x objective-c++ -std=c++17
flags.c = -x c -std=c11 flags.c = -x c -std=c11
flags.cpp = -x c++ -std=c++14 flags.cpp = -x c++ -std=c++17
flags.objc = -x objective-c -std=c11 flags.objc = -x objective-c -std=c11
flags.objcpp = -x objective-c++ -std=c++14 flags.objcpp = -x objective-c++ -std=c++17
flags.deps = -MMD -MP -MF $(@:.o=.d) flags.deps = -MMD -MP -MF $(@:.o=.d)
# compiler detection # compiler detection
ifeq ($(compiler),) ifeq ($(compiler),)
ifeq ($(platform),windows) ifeq ($(platform),windows)
compiler := g++ compiler := g++
compiler.cpp = $(compiler) -x c++ -std=gnu++14 compiler.cpp = $(compiler) -x c++ -std=gnu++17
flags.cpp = -x c++ -std=gnu++14 flags.cpp = -x c++ -std=gnu++17
else ifeq ($(platform),macos) else ifeq ($(platform),macos)
compiler := clang++ compiler := clang++
else ifeq ($(platform),linux) else ifeq ($(platform),linux)
compiler := g++ compiler := g++
else ifeq ($(platform),bsd) else ifeq ($(platform),bsd)
compiler := g++49 compiler := g++8
else else
compiler := g++ compiler := g++
endif endif
@ -126,7 +126,8 @@ endif
ifeq ($(platform),bsd) ifeq ($(platform),bsd)
flags += -I/usr/local/include flags += -I/usr/local/include
options += -Wl,-rpath=/usr/local/lib options += -Wl,-rpath=/usr/local/lib
options += -Wl,-rpath=/usr/local/lib/gcc49 options += -Wl,-rpath=/usr/local/lib/gcc8
options += -lstdc++ -lm
endif endif
# threading support # threading support

View File

@ -15,6 +15,11 @@
#include <sys/types.h> #include <sys/types.h>
#endif #endif
#if !defined(MAP_NORESERVE)
//not supported on FreeBSD; flag removed in 11.0
#define MAP_NORESERVE 0
#endif
namespace nall { namespace nall {
struct file_map { struct file_map {
@ -39,7 +44,7 @@ struct file_map {
//auto close() -> void; //auto close() -> void;
private: private:
bool _open = false; bool _open = false; //zero-byte files return _data = nullptr, _size = 0
uint8_t* _data = nullptr; uint8_t* _data = nullptr;
uint64_t _size = 0; uint64_t _size = 0;
@ -66,6 +71,9 @@ public:
} }
auto open(const string& filename, uint mode_) -> bool { auto open(const string& filename, uint mode_) -> bool {
close();
if(file::exists(filename) && file::size(filename) == 0) return _open = true;
int desiredAccess, creationDisposition, protection, mapAccess; int desiredAccess, creationDisposition, protection, mapAccess;
switch(mode_) { switch(mode_) {
@ -111,7 +119,7 @@ public:
} }
_data = (uint8_t*)MapViewOfFile(_map, mapAccess, 0, 0, _size); _data = (uint8_t*)MapViewOfFile(_map, mapAccess, 0, 0, _size);
return _open = _data; return _open = true;
} }
auto close() -> void { auto close() -> void {
@ -154,6 +162,8 @@ public:
auto open(const string& filename, uint mode_) -> bool { auto open(const string& filename, uint mode_) -> bool {
close(); close();
if(file::exists(filename) && file::size(filename) == 0) return _open = true;
int openFlags = 0; int openFlags = 0;
int mmapFlags = 0; int mmapFlags = 0;
@ -192,7 +202,7 @@ public:
return false; return false;
} }
return _open = _data; return _open = true;
} }
auto close() -> void { auto close() -> void {

View File

@ -7,7 +7,7 @@ namespace nall {
enum class Platform : uint { Windows, MacOS, Linux, BSD, Unknown }; enum class Platform : uint { Windows, MacOS, Linux, BSD, Unknown };
enum class API : uint { Windows, Posix, Unknown }; enum class API : uint { Windows, Posix, Unknown };
enum class DisplayServer : uint { Windows, Quartz, Xorg, Unknown }; enum class DisplayServer : uint { Windows, Quartz, Xorg, Unknown };
enum class Architecture : uint { x86, amd64, ARM, PPC32, PPC64, Unknown }; enum class Architecture : uint { x86, amd64, ARM32, ARM64, PPC32, PPC64, Unknown };
enum class Endian : uint { LSB, MSB, Unknown }; enum class Endian : uint { LSB, MSB, Unknown };
enum class Build : uint { Debug, Stable, Size, Release, Performance }; enum class Build : uint { Debug, Stable, Size, Release, Performance };
@ -123,9 +123,12 @@ namespace nall {
#elif defined(__amd64__) || defined(_M_AMD64) #elif defined(__amd64__) || defined(_M_AMD64)
#define ARCHITECTURE_AMD64 #define ARCHITECTURE_AMD64
constexpr auto architecture() -> Architecture { return Architecture::amd64; } constexpr auto architecture() -> Architecture { return Architecture::amd64; }
#elif defined(__aarch64__)
#define ARCHITECTURE_ARM64
constexpr auto architecture() -> Architecture { return Architecture::ARM64; }
#elif defined(__arm__) #elif defined(__arm__)
#define ARCHITECTURE_ARM #define ARCHITECTURE_ARM32
constexpr auto architecture() -> Architecture { return Architecture::ARM; } constexpr auto architecture() -> Architecture { return Architecture::ARM32; }
#elif defined(__ppc64__) || defined(_ARCH_PPC64) #elif defined(__ppc64__) || defined(_ARCH_PPC64)
#define ARCHITECTURE_PPC64 #define ARCHITECTURE_PPC64
constexpr auto architecture() -> Architecture { return Architecture::PPC64; } constexpr auto architecture() -> Architecture { return Architecture::PPC64; }

View File

@ -26,7 +26,7 @@ struct VideoGLX : VideoDriver, OpenGL {
auto hasShader() -> bool override { return true; } auto hasShader() -> bool override { return true; }
auto hasFormats() -> vector<string> override { auto hasFormats() -> vector<string> override {
return {"RGB24"}; //"RGB30" return {"RGB24"}; //"RGB30" is currently broken; use OpenGL 2.0 driver instead
} }
auto setContext(uintptr context) -> bool override { auto setContext(uintptr context) -> bool override {

View File

@ -37,7 +37,7 @@ struct VideoGLX2 : VideoDriver {
auto hasContext() -> bool override { return true; } auto hasContext() -> bool override { return true; }
auto hasBlocking() -> bool override { return true; } auto hasBlocking() -> bool override { return true; }
auto hasFlush() -> bool override { return true; } auto hasFlush() -> bool override { return true; }
auto hasFormats() -> vector<string> override { return {"RGB24"}; } auto hasFormats() -> vector<string> override { return {"RGB24", "RGB30"}; }
auto hasShader() -> bool override { return true; } auto hasShader() -> bool override { return true; }
auto setContext(uintptr context) -> bool override { auto setContext(uintptr context) -> bool override {