bsnes/nall/array.hpp

90 lines
2.1 KiB
C++
Raw Normal View History

Update to v101r07 release. byuu says: Added VDP sprite rendering. Can't get any games far enough in to see if it actually works. So in other words, it doesn't work at all and is 100% completely broken. Also added 68K exceptions and interrupts. So far only the VDP interrupt is present. It definitely seems to be firing in commercial games, so that's promising. But the implementation is almost certainly completely wrong. There is fuck all of nothing for documentation on how interrupts actually work. I had to find out the interrupt vector numbers from reading the comments from the Sonic the Hedgehog disassembly. I have literally no fucking clue what I0-I2 (3-bit integer priority value in the status register) is supposed to do. I know that Vblank=6, Hblank=4, Ext(gamepad)=2. I know that at reset, SR.I=7. I don't know if I'm supposed to block interrupts when I is >, >=, <, <= to the interrupt level. I don't know what level CPU exceptions are supposed to be. Also implemented VDP regular DMA. No idea if it works correctly since none of the commercial games run far enough to use it. So again, it's horribly broken for usre. Also improved VDP fill mode. But I don't understand how it takes byte-lengths when the bus is 16-bit. The transfer times indicate it's actually transferring at the same speed as the 68K->VDP copy, strongly suggesting it's actually doing 16-bit transfers at a time. In which case, what happens when you set an odd transfer length? Also, both DMA modes can now target VRAM, VSRAM, CRAM. Supposedly there's all kinds of weird shit going on when you target VSRAM, CRAM with VDP fill/copy modes, but whatever. Get to that later. Also implemented a very lazy preliminary wait mechanism to to stall out a processor while another processor exerts control over the bus. This one's going to be a major work in progress. For one, it totally breaks the model I use to do save states with libco. For another, I don't know if a 68K->VDP DMA instantly locks the CPU, or if it the CPU could actually keep running if it was executing out of RAM when it started the DMA transfer from ROM (eg it's a bus busy stall, not a hard chip stall.) That'll greatly change how I handle the waiting. Also, the OSS driver now supports Audio::Latency. Sound should be even lower latency now. On FreeBSD when set to 0ms, it's absolutely incredible. Cannot detect latency whatsoever. The Mario jump sound seems to happen at the very instant I hear my cherry blue keyswitch activate.
2016-08-15 04:56:38 +00:00
#pragma once
#include <nall/array-span.hpp>
#include <nall/array-view.hpp>
Update to v101r07 release. byuu says: Added VDP sprite rendering. Can't get any games far enough in to see if it actually works. So in other words, it doesn't work at all and is 100% completely broken. Also added 68K exceptions and interrupts. So far only the VDP interrupt is present. It definitely seems to be firing in commercial games, so that's promising. But the implementation is almost certainly completely wrong. There is fuck all of nothing for documentation on how interrupts actually work. I had to find out the interrupt vector numbers from reading the comments from the Sonic the Hedgehog disassembly. I have literally no fucking clue what I0-I2 (3-bit integer priority value in the status register) is supposed to do. I know that Vblank=6, Hblank=4, Ext(gamepad)=2. I know that at reset, SR.I=7. I don't know if I'm supposed to block interrupts when I is >, >=, <, <= to the interrupt level. I don't know what level CPU exceptions are supposed to be. Also implemented VDP regular DMA. No idea if it works correctly since none of the commercial games run far enough to use it. So again, it's horribly broken for usre. Also improved VDP fill mode. But I don't understand how it takes byte-lengths when the bus is 16-bit. The transfer times indicate it's actually transferring at the same speed as the 68K->VDP copy, strongly suggesting it's actually doing 16-bit transfers at a time. In which case, what happens when you set an odd transfer length? Also, both DMA modes can now target VRAM, VSRAM, CRAM. Supposedly there's all kinds of weird shit going on when you target VSRAM, CRAM with VDP fill/copy modes, but whatever. Get to that later. Also implemented a very lazy preliminary wait mechanism to to stall out a processor while another processor exerts control over the bus. This one's going to be a major work in progress. For one, it totally breaks the model I use to do save states with libco. For another, I don't know if a 68K->VDP DMA instantly locks the CPU, or if it the CPU could actually keep running if it was executing out of RAM when it started the DMA transfer from ROM (eg it's a bus busy stall, not a hard chip stall.) That'll greatly change how I handle the waiting. Also, the OSS driver now supports Audio::Latency. Sound should be even lower latency now. On FreeBSD when set to 0ms, it's absolutely incredible. Cannot detect latency whatsoever. The Mario jump sound seems to happen at the very instant I hear my cherry blue keyswitch activate.
2016-08-15 04:56:38 +00:00
#include <nall/range.hpp>
#include <nall/view.hpp>
Update to v101r07 release. byuu says: Added VDP sprite rendering. Can't get any games far enough in to see if it actually works. So in other words, it doesn't work at all and is 100% completely broken. Also added 68K exceptions and interrupts. So far only the VDP interrupt is present. It definitely seems to be firing in commercial games, so that's promising. But the implementation is almost certainly completely wrong. There is fuck all of nothing for documentation on how interrupts actually work. I had to find out the interrupt vector numbers from reading the comments from the Sonic the Hedgehog disassembly. I have literally no fucking clue what I0-I2 (3-bit integer priority value in the status register) is supposed to do. I know that Vblank=6, Hblank=4, Ext(gamepad)=2. I know that at reset, SR.I=7. I don't know if I'm supposed to block interrupts when I is >, >=, <, <= to the interrupt level. I don't know what level CPU exceptions are supposed to be. Also implemented VDP regular DMA. No idea if it works correctly since none of the commercial games run far enough to use it. So again, it's horribly broken for usre. Also improved VDP fill mode. But I don't understand how it takes byte-lengths when the bus is 16-bit. The transfer times indicate it's actually transferring at the same speed as the 68K->VDP copy, strongly suggesting it's actually doing 16-bit transfers at a time. In which case, what happens when you set an odd transfer length? Also, both DMA modes can now target VRAM, VSRAM, CRAM. Supposedly there's all kinds of weird shit going on when you target VSRAM, CRAM with VDP fill/copy modes, but whatever. Get to that later. Also implemented a very lazy preliminary wait mechanism to to stall out a processor while another processor exerts control over the bus. This one's going to be a major work in progress. For one, it totally breaks the model I use to do save states with libco. For another, I don't know if a 68K->VDP DMA instantly locks the CPU, or if it the CPU could actually keep running if it was executing out of RAM when it started the DMA transfer from ROM (eg it's a bus busy stall, not a hard chip stall.) That'll greatly change how I handle the waiting. Also, the OSS driver now supports Audio::Latency. Sound should be even lower latency now. On FreeBSD when set to 0ms, it's absolutely incredible. Cannot detect latency whatsoever. The Mario jump sound seems to happen at the very instant I hear my cherry blue keyswitch activate.
2016-08-15 04:56:38 +00:00
namespace nall {
template<typename T> struct array;
Update to v101r07 release. byuu says: Added VDP sprite rendering. Can't get any games far enough in to see if it actually works. So in other words, it doesn't work at all and is 100% completely broken. Also added 68K exceptions and interrupts. So far only the VDP interrupt is present. It definitely seems to be firing in commercial games, so that's promising. But the implementation is almost certainly completely wrong. There is fuck all of nothing for documentation on how interrupts actually work. I had to find out the interrupt vector numbers from reading the comments from the Sonic the Hedgehog disassembly. I have literally no fucking clue what I0-I2 (3-bit integer priority value in the status register) is supposed to do. I know that Vblank=6, Hblank=4, Ext(gamepad)=2. I know that at reset, SR.I=7. I don't know if I'm supposed to block interrupts when I is >, >=, <, <= to the interrupt level. I don't know what level CPU exceptions are supposed to be. Also implemented VDP regular DMA. No idea if it works correctly since none of the commercial games run far enough to use it. So again, it's horribly broken for usre. Also improved VDP fill mode. But I don't understand how it takes byte-lengths when the bus is 16-bit. The transfer times indicate it's actually transferring at the same speed as the 68K->VDP copy, strongly suggesting it's actually doing 16-bit transfers at a time. In which case, what happens when you set an odd transfer length? Also, both DMA modes can now target VRAM, VSRAM, CRAM. Supposedly there's all kinds of weird shit going on when you target VSRAM, CRAM with VDP fill/copy modes, but whatever. Get to that later. Also implemented a very lazy preliminary wait mechanism to to stall out a processor while another processor exerts control over the bus. This one's going to be a major work in progress. For one, it totally breaks the model I use to do save states with libco. For another, I don't know if a 68K->VDP DMA instantly locks the CPU, or if it the CPU could actually keep running if it was executing out of RAM when it started the DMA transfer from ROM (eg it's a bus busy stall, not a hard chip stall.) That'll greatly change how I handle the waiting. Also, the OSS driver now supports Audio::Latency. Sound should be even lower latency now. On FreeBSD when set to 0ms, it's absolutely incredible. Cannot detect latency whatsoever. The Mario jump sound seems to happen at the very instant I hear my cherry blue keyswitch activate.
2016-08-15 04:56:38 +00:00
//usage: int x[256] => array<int[256]> x
template<typename T, uint Size> struct array<T[Size]> {
array() = default;
array(const initializer_list<T>& source) {
uint index = 0;
for(auto& value : source) {
operator[](index++) = value;
}
}
operator array_span<T>() {
return {data(), size()};
}
operator array_view<T>() const {
return {data(), size()};
}
alwaysinline auto operator[](uint index) -> T& {
#ifdef DEBUG
struct out_of_bounds {};
if(index >= Size) throw out_of_bounds{};
#endif
return values[index];
}
alwaysinline auto operator[](uint index) const -> const T& {
#ifdef DEBUG
struct out_of_bounds {};
if(index >= Size) throw out_of_bounds{};
#endif
return values[index];
}
alwaysinline auto operator()(uint index, const T& fallback = {}) const -> const T& {
if(index >= Size) return fallback;
return values[index];
}
auto fill(const T& fill = {}) -> array& {
for(auto& value : values) value = fill;
return *this;
}
auto data() -> T* { return values; }
auto data() const -> const T* { return values; }
auto size() const -> uint { return Size; }
auto begin() -> T* { return &values[0]; }
auto end() -> T* { return &values[Size]; }
auto begin() const -> const T* { return &values[0]; }
auto end() const -> const T* { return &values[Size]; }
private:
T values[Size];
};
Update to v106r83 release. byuu says: Changelog: - reverted nall/inline-if.hpp usage for now, since the nall/primitives.hpp math operators still cast to (u)int64_t - improved nall/primitives.hpp more; integer8 x = -128; print(-x) will now print 128 (unary operator+ and - cast to (u)int64_t) - renamed processor/lr35902 to processor/sm83; after the Sharp SM83 CPU core [gekkio discovered the name] - a few bugfixes to the TLCS900H CPU core - completed the disassembler for the TLCS900H core As a result of reverting most of the inline if stuff, I guess the testing priority has been reduced. Which is probably a good thing, considering I seem to have a smaller pool of testers these days. Indeed, the TLCS900H core has ended up at 131KiB compared to the M68000 core at 128KiB. So it's now the largest CPU core in all of higan. It's even more ridiculous because the M68000 core would ordinarily be quite a bit smaller, had I not gone overboard with the extreme templating to reduce instruction decoding overhead (you kind of have to do this for RISC CPUs, and the inverted design of the TLCS900H kind of makes it infeasible to do the same there.) This CPU core is bound to have dozens of extremely difficult CPU bugs, and there's no easy way for me to test them. I would greatly appreciate any help in looking over the core for bugs. A fresh pair of eyes to spot a mistake could save me up to several days of tedious debugging work. The core still isn't ready to actually be tested: I have to hook up cartridge loading, a memory bus, interrupts, timers, and the micro DMA controller before it's likely that anything happens at all.
2019-01-19 01:34:17 +00:00
template<typename T, T... p> auto from_array(uint index) -> T {
static const array<T[sizeof...(p)]> table{p...};
struct out_of_bounds {};
#if defined(DEBUG)
if(index >= sizeof...(p)) throw out_of_bounds{};
#endif
return table[index];
}
template<int64_t... p> auto from_array(uint index) -> int64_t {
static const array<int64_t[sizeof...(p)]> table{p...};
struct out_of_bounds {};
#if defined(DEBUG)
if(index >= sizeof...(p)) throw out_of_bounds{};
#endif
return table[index];
}
Update to v101r07 release. byuu says: Added VDP sprite rendering. Can't get any games far enough in to see if it actually works. So in other words, it doesn't work at all and is 100% completely broken. Also added 68K exceptions and interrupts. So far only the VDP interrupt is present. It definitely seems to be firing in commercial games, so that's promising. But the implementation is almost certainly completely wrong. There is fuck all of nothing for documentation on how interrupts actually work. I had to find out the interrupt vector numbers from reading the comments from the Sonic the Hedgehog disassembly. I have literally no fucking clue what I0-I2 (3-bit integer priority value in the status register) is supposed to do. I know that Vblank=6, Hblank=4, Ext(gamepad)=2. I know that at reset, SR.I=7. I don't know if I'm supposed to block interrupts when I is >, >=, <, <= to the interrupt level. I don't know what level CPU exceptions are supposed to be. Also implemented VDP regular DMA. No idea if it works correctly since none of the commercial games run far enough to use it. So again, it's horribly broken for usre. Also improved VDP fill mode. But I don't understand how it takes byte-lengths when the bus is 16-bit. The transfer times indicate it's actually transferring at the same speed as the 68K->VDP copy, strongly suggesting it's actually doing 16-bit transfers at a time. In which case, what happens when you set an odd transfer length? Also, both DMA modes can now target VRAM, VSRAM, CRAM. Supposedly there's all kinds of weird shit going on when you target VSRAM, CRAM with VDP fill/copy modes, but whatever. Get to that later. Also implemented a very lazy preliminary wait mechanism to to stall out a processor while another processor exerts control over the bus. This one's going to be a major work in progress. For one, it totally breaks the model I use to do save states with libco. For another, I don't know if a 68K->VDP DMA instantly locks the CPU, or if it the CPU could actually keep running if it was executing out of RAM when it started the DMA transfer from ROM (eg it's a bus busy stall, not a hard chip stall.) That'll greatly change how I handle the waiting. Also, the OSS driver now supports Audio::Latency. Sound should be even lower latency now. On FreeBSD when set to 0ms, it's absolutely incredible. Cannot detect latency whatsoever. The Mario jump sound seems to happen at the very instant I hear my cherry blue keyswitch activate.
2016-08-15 04:56:38 +00:00
}