Merge branch 'master' into timerz

This commit is contained in:
wheremyfoodat 2023-08-21 18:57:18 +03:00
commit 1d601e41ba
63 changed files with 871 additions and 262282 deletions

View file

@ -9,6 +9,13 @@ struct EmulatorConfig {
bool discordRpcEnabled = false;
RendererType rendererType = RendererType::OpenGL;
bool sdCardInserted = true;
bool sdWriteProtected = false;
bool chargerPlugged = true;
// Default to 3% battery to make users suffer
int batteryPercentage = 3;
EmulatorConfig(const std::filesystem::path& path);
void load(const std::filesystem::path& path);
void save(const std::filesystem::path& path);

View file

@ -105,6 +105,7 @@ namespace Crypto {
AESEngine() {}
void loadKeys(const std::filesystem::path& path);
bool haveKeys() { return keysLoaded; }
bool haveGenerator() { return m_generator.has_value(); }
constexpr bool hasKeyX(std::size_t slotId) {
if (slotId >= AesKeySlotCount) {

View file

@ -19,24 +19,26 @@ namespace KernelHandles {
CECD, // More Streetpass stuff?
CFG_U, // CFG service (Console & region info)
CFG_I,
DLP_SRVR, // Download Play: Server. Used for network play.
DSP, // DSP service (Used for audio decoding and output)
HID, // HID service (Handles input-related things including gyro. Does NOT handle New3DS controls or CirclePadPro)
HTTP, // HTTP service (Handles HTTP requests)
IR_USER, // One of 3 infrared communication services
FRD, // Friend service (Miiverse friend service)
FS, // Filesystem service
GPU, // GPU service
LCD, // LCD service (Used for configuring the displays)
LDR_RO, // Loader service. Used for loading CROs.
MIC, // MIC service (Controls the microphone)
NFC, // NFC (Duh), used for Amiibo
NIM, // Updates, DLC, etc
NDM, // ?????
PTM, // PTM service (Used for accessing various console info, such as battery, shell and pedometer state)
SOC, // Socket service
SSL, // SSL service (Totally didn't expect that)
Y2R, // Also does camera stuff
DLP_SRVR, // Download Play: Server. Used for network play.
DSP, // DSP service (Used for audio decoding and output)
HID, // HID service (Handles input-related things including gyro. Does NOT handle New3DS controls or CirclePadPro)
HTTP, // HTTP service (Handles HTTP requests)
IR_USER, // One of 3 infrared communication services
FRD, // Friend service (Miiverse friend service)
FS, // Filesystem service
GPU, // GPU service
LCD, // LCD service (Used for configuring the displays)
LDR_RO, // Loader service. Used for loading CROs.
MCU_HWC, // Used for various MCU hardware-related things like battery control
MIC, // MIC service (Controls the microphone)
NFC, // NFC (Duh), used for Amiibo
NIM, // Updates, DLC, etc
NDM, // ?????
NEWS_U, // This service literally has 1 command (AddNotification) and I don't even understand what it does
PTM, // PTM service (Used for accessing various console info, such as battery, shell and pedometer state)
SOC, // Socket service
SSL, // SSL service (Totally didn't expect that)
Y2R, // Also does camera stuff
MinServiceHandle = AC,
MaxServiceHandle = Y2R,
@ -81,8 +83,10 @@ namespace KernelHandles {
case GPU: return "GSP::GPU";
case LCD: return "GSP::LCD";
case LDR_RO: return "LDR:RO";
case MCU_HWC: return "MCU::HWC";
case MIC: return "MIC";
case NDM: return "NDM";
case NEWS_U: return "NEWS_U";
case NFC: return "NFC";
case NIM: return "NIM";
case PTM: return "PTM";

View file

@ -6,6 +6,7 @@
#include <string>
#include <vector>
#include "config.hpp"
#include "helpers.hpp"
#include "kernel_types.hpp"
#include "logger.hpp"
@ -61,7 +62,7 @@ class Kernel {
Handle makeProcess(u32 id);
Handle makePort(const char* name);
Handle makeSession(Handle port);
Handle makeThread(u32 entrypoint, u32 initialSP, u32 priority, s32 id, u32 arg,ThreadStatus status = ThreadStatus::Dormant);
Handle makeThread(u32 entrypoint, u32 initialSP, u32 priority, ProcessorID id, u32 arg,ThreadStatus status = ThreadStatus::Dormant);
Handle makeMemoryBlock(u32 addr, u32 size, u32 myPermission, u32 otherPermission);
public:
@ -129,6 +130,7 @@ private:
void exitThread();
void mapMemoryBlock();
void queryMemory();
void getCurrentProcessorNumber();
void getProcessID();
void getProcessInfo();
void getResourceLimit();
@ -137,6 +139,7 @@ private:
void getSystemInfo();
void getSystemTick();
void getThreadID();
void getThreadIdealProcessor();
void getThreadPriority();
void sendSyncRequest();
void setThreadPriority();
@ -175,7 +178,7 @@ private:
void readDirectory(u32 messagePointer, Handle directory);
public:
Kernel(CPU& cpu, Memory& mem, GPU& gpu);
Kernel(CPU& cpu, Memory& mem, GPU& gpu, const EmulatorConfig& config);
void initializeFS() { return serviceManager.initializeFS(); }
void setVersion(u8 major, u8 minor);
void serviceSVC(u32 svc);

View file

@ -34,6 +34,16 @@ enum class ArbitrationType {
DecrementAndWaitIfLessTimeout = 4
};
enum class ProcessorID : s32 {
AllCPUs = -1,
Default = -2,
AppCore = 0,
Syscore = 1,
New3DSExtra1 = 2,
New3DSExtra2 = 3
};
struct AddressArbiter {};
struct ResourceLimits {
@ -95,7 +105,7 @@ struct Thread {
u32 entrypoint; // Initial r15 value
u32 priority;
u32 arg;
s32 processorID;
ProcessorID processorID;
ThreadStatus status;
Handle handle; // OS handle for this thread
int index; // Index of the thread. 0 for the first thread, 1 for the second, and so on

View file

@ -48,7 +48,9 @@ namespace Log {
static Logger<false> gspGPULogger;
static Logger<false> gspLCDLogger;
static Logger<false> ldrLogger;
static Logger<false> mcuLogger;
static Logger<false> micLogger;
static Logger<false> newsLogger;
static Logger<false> nfcLogger;
static Logger<false> nimLogger;
static Logger<false> ndmLogger;

View file

@ -5,12 +5,13 @@
#include <fstream>
#include <optional>
#include <vector>
#include "config.hpp"
#include "crypto/aes_engine.hpp"
#include "helpers.hpp"
#include "handles.hpp"
#include "helpers.hpp"
#include "loader/ncsd.hpp"
#include "services/region_codes.hpp"
#include "services/shared_font.hpp"
namespace PhysicalAddrs {
enum : u32 {
@ -111,7 +112,7 @@ class Memory {
std::vector<KernelMemoryTypes::MemoryInfo> memoryInfo;
std::array<SharedMemoryBlock, 3> sharedMemBlocks = {
SharedMemoryBlock(0, u32(_shared_font_len), KernelHandles::FontSharedMemHandle), // Shared memory for the system font
SharedMemoryBlock(0, 0, KernelHandles::FontSharedMemHandle), // Shared memory for the system font (size is 0 because we read the size from the cmrc filesystem
SharedMemoryBlock(0, 0x1000, KernelHandles::GSPSharedMemHandle), // GSP shared memory
SharedMemoryBlock(0, 0x1000, KernelHandles::HIDSharedMemHandle) // HID shared memory
};
@ -154,13 +155,14 @@ private:
static constexpr FirmwareInfo firm{.unk = 0, .revision = 0, .minor = 0x34, .major = 2, .syscoreVer = 2, .sdkVer = 0x0000F297};
// Adjusted upon loading a ROM based on the ROM header. Used by CFG::SecureInfoGetArea to get past region locks
Regions region = Regions::USA;
const EmulatorConfig& config;
public:
u16 kernelVersion = 0;
u32 usedUserMemory = u32(0_MB); // How much of the APPLICATION FCRAM range is used (allocated to the appcore)
u32 usedSystemMemory = u32(0_MB); // Similar for the SYSTEM range (reserved for the syscore)
Memory(u64& cpuTicks);
Memory(u64& cpuTicks, const EmulatorConfig& config);
void reset();
void* getReadPointer(u32 address);
void* getWritePointer(u32 address);
@ -265,4 +267,5 @@ public:
void setVRAM(u8* pointer) { vram = pointer; }
bool allocateMainThreadStack(u32 size);
Regions getConsoleRegion();
void copySharedFont(u8* ptr);
};

View file

@ -55,6 +55,7 @@ class RendererGL final : public Renderer {
OpenGL::Texture screenTexture;
GLuint lightLUTTextureArray;
OpenGL::Framebuffer screenFramebuffer;
OpenGL::Texture blankTexture;
OpenGL::Framebuffer getColourFBO();
OpenGL::Texture getTexture(Texture& tex);

View file

@ -11,7 +11,11 @@ class ACService {
MAKE_LOG_FUNCTION(log, acLogger)
// Service commands
void cancelConnectAsync(u32 messagePointer);
void closeAsync(u32 messagePointer);
void createDefaultConfig(u32 messagePointer);
void getLastErrorCode(u32 messagePointer);
void registerDisconnectEvent(u32 messagePointer);
void setClientVersion(u32 messagePointer);
public:

View file

@ -12,6 +12,7 @@ class AMService {
// Service commands
void getDLCTitleInfo(u32 messagePointer);
void getPatchTitleInfo(u32 messagePointer);
void listTitleInfo(u32 messagePointer);
public:

View file

@ -13,15 +13,22 @@ class BOSSService {
// Service commands
void cancelTask(u32 messagePointer);
void initializeSession(u32 messagePointer);
void getNsDataIdList(u32 messagePointer);
void getErrorCode(u32 messagePointer);
void getNsDataIdList(u32 messagePointer, u32 commandWord);
void getOptoutFlag(u32 messagePointer);
void getStorageEntryInfo(u32 messagePointer); // Unknown what this is, name taken from Citra
void getTaskIdList(u32 messagePointer);
void getTaskInfo(u32 messagePointer);
void getTaskServiceStatus(u32 messagePointer);
void getTaskState(u32 messagePointer);
void getTaskStatus(u32 messagePointer);
void getTaskStorageInfo(u32 messagePointer);
void receiveProperty(u32 messagePointer);
void registerNewArrivalEvent(u32 messagePointer);
void registerStorageEntry(u32 messagePointer);
void registerTask(u32 messagePointer);
void sendProperty(u32 messagePointer);
void startTask(u32 messagePointer);
void unregisterStorage(u32 messagePointer);
void unregisterTask(u32 messagePointer);

View file

@ -1,21 +1,33 @@
#pragma once
#include <array>
#include <optional>
#include "helpers.hpp"
#include "kernel_types.hpp"
#include "logger.hpp"
#include "memory.hpp"
#include "result/result.hpp"
// Yay, circular dependencies!
class Kernel;
class CAMService {
Handle handle = KernelHandles::CAM;
Memory& mem;
Kernel& kernel;
MAKE_LOG_FUNCTION(log, camLogger)
using Event = std::optional<Handle>;
static constexpr size_t portCount = 4; // PORT_NONE, PORT_CAM1, PORT_CAM2, PORT_BOTH
std::array<Event, portCount> bufferErrorInterruptEvents;
// Service commands
void driverInitialize(u32 messagePointer);
void getMaxLines(u32 messagePointer);
void getBufferErrorInterruptEvent(u32 messagePointer);
public:
CAMService(Memory& mem) : mem(mem) {}
public:
CAMService(Memory& mem, Kernel& kernel) : mem(mem), kernel(kernel) {}
void reset();
void handleSyncRequest(u32 messagePointer);
};

View file

@ -18,6 +18,7 @@ class CECDService {
// Service commands
void getInfoEventHandle(u32 messagePointer);
void openAndRead(u32 messagePointer);
public:
CECDService(Memory& mem, Kernel& kernel) : mem(mem), kernel(kernel) {}

View file

@ -19,6 +19,8 @@ class FRDService {
Memory& mem;
MAKE_LOG_FUNCTION(log, frdLogger)
bool loggedIn = false;
// Service commands
void attachToEventNotification(u32 messagePointer);
void getFriendKeyList(u32 messagePointer);
@ -27,8 +29,11 @@ class FRDService {
void getMyPresence(u32 messagePointer);
void getMyProfile(u32 messagePointer);
void getMyScreenName(u32 messsagePointer);
void hasLoggedIn(u32 messagePointer);
void logout(u32 messagePointer);
void setClientSDKVersion(u32 messagePointer);
void setNotificationMask(u32 messagePointer);
void updateGameModeDescription(u32 messagePointer);
public:
FRDService(Memory& mem) : mem(mem) {}

View file

@ -37,9 +37,11 @@ class FSService {
// Service commands
void createDirectory(u32 messagePointer);
void createExtSaveData(u32 messagePointer);
void createFile(u32 messagePointer);
void closeArchive(u32 messagePointer);
void controlArchive(u32 messagePointer);
void deleteExtSaveData(u32 messagePointer);
void deleteFile(u32 messagePointer);
void formatSaveData(u32 messagePointer);
void formatThisUserSaveData(u32 messagePointer);

View file

@ -71,6 +71,7 @@ class HIDService {
void getGyroscopeLowCalibrateParam(u32 messagePointer);
void getGyroscopeCoefficient(u32 messagePointer);
void getIPCHandles(u32 messagePointer);
void getSoundVolume(u32 messagePointer);
// Don't call these prior to initializing shared mem pls
template <typename T>
@ -141,4 +142,6 @@ class HIDService {
void releaseTouchScreen() {
touchScreenPressed = false;
}
bool isTouchScreenPressed() { return touchScreenPressed; }
};

View file

@ -0,0 +1,24 @@
#pragma once
#include "config.hpp"
#include "helpers.hpp"
#include "kernel_types.hpp"
#include "logger.hpp"
#include "memory.hpp"
namespace MCU {
class HWCService {
Handle handle = KernelHandles::MCU_HWC;
Memory& mem;
MAKE_LOG_FUNCTION(log, mcuLogger)
const EmulatorConfig& config;
// Service commands
void getBatteryLevel(u32 messagePointer);
public:
HWCService(Memory& mem, const EmulatorConfig& config) : mem(mem), config(config) {}
void reset();
void handleSyncRequest(u32 messagePointer);
};
} // namespace MCU

View file

@ -18,11 +18,13 @@ class MICService {
void setIirFilter(u32 messagePointer);
void setPower(u32 messagePointer);
void startSampling(u32 messagePointer);
void stopSampling(u32 messagePointer);
void theCaptainToadFunction(u32 messagePointer);
u8 gain = 0; // How loud our microphone input signal is
bool micEnabled = false;
bool shouldClamp = false;
bool isSampling = false;
public:
MICService(Memory& mem) : mem(mem) {}

View file

@ -11,6 +11,7 @@ class NDMService {
MAKE_LOG_FUNCTION(log, ndmLogger)
// Service commands
void clearHalfAwakeMacFilter(u32 messagePointer);
void overrideDefaultDaemons(u32 messagePointer);
void resumeDaemons(u32 messagePointer);
void resumeScheduler(u32 messagePointer);

View file

@ -0,0 +1,18 @@
#pragma once
#include "helpers.hpp"
#include "kernel_types.hpp"
#include "logger.hpp"
#include "memory.hpp"
class NewsUService {
Handle handle = KernelHandles::NEWS_U;
Memory& mem;
MAKE_LOG_FUNCTION(log, newsLogger)
// Service commands
public:
NewsUService(Memory& mem) : mem(mem) {}
void reset();
void handleSyncRequest(u32 messagePointer);
};

View file

@ -14,13 +14,38 @@ class NFCService {
Kernel& kernel;
MAKE_LOG_FUNCTION(log, nfcLogger)
enum class Old3DSAdapterStatus : u32 {
Idle = 0,
AttemptingToInitialize = 1,
InitializationComplete = 2,
Active = 3,
};
enum class TagStatus : u8 {
NotInitialized = 0,
Initialized = 1,
Scanning = 2,
InRange = 3,
OutOfRange = 4,
Loaded = 5,
};
// Kernel events signaled when an NFC tag goes in and out of range respectively
std::optional<Handle> tagInRangeEvent, tagOutOfRangeEvent;
Old3DSAdapterStatus adapterStatus;
TagStatus tagStatus;
bool initialized = false;
// Service commands
void communicationGetResult(u32 messagePointer);
void communicationGetStatus(u32 messagePointer);
void initialize(u32 messagePointer);
void getTagInRangeEvent(u32 messagePointer);
void getTagOutOfRangeEvent(u32 messagePointer);
void getTagState(u32 messagePointer);
void startCommunication(u32 messagePointer);
void stopCommunication(u32 messagePointer);
public:
NFCService(Memory& mem, Kernel& kernel) : mem(mem), kernel(kernel) {}

View file

@ -1,4 +1,5 @@
#pragma once
#include "config.hpp"
#include "helpers.hpp"
#include "kernel_types.hpp"
#include "logger.hpp"
@ -10,6 +11,8 @@ class PTMService {
Memory& mem;
MAKE_LOG_FUNCTION(log, ptmLogger)
const EmulatorConfig& config;
// Service commands
void configureNew3DSCPU(u32 messagePointer);
void getAdapterState(u32 messagePointer);
@ -18,7 +21,7 @@ class PTMService {
void getTotalStepCount(u32 messagePointer);
public:
PTMService(Memory& mem) : mem(mem) {}
PTMService(Memory& mem, const EmulatorConfig& config) : mem(mem), config(config) {}
void reset();
void handleSyncRequest(u32 messagePointer);

View file

@ -24,8 +24,10 @@
#include "services/http.hpp"
#include "services/ir_user.hpp"
#include "services/ldr_ro.hpp"
#include "services/mcu/mcu_hwc.hpp"
#include "services/mic.hpp"
#include "services/ndm.hpp"
#include "services/news_u.hpp"
#include "services/nfc.hpp"
#include "services/nim.hpp"
#include "services/ptm.hpp"
@ -33,6 +35,7 @@
#include "services/ssl.hpp"
#include "services/y2r.hpp"
struct EmulatorConfig;
// More circular dependencies!!
class Kernel;
@ -64,14 +67,17 @@ class ServiceManager {
LCDService gsp_lcd;
LDRService ldr;
MICService mic;
NDMService ndm;
NewsUService news_u;
NFCService nfc;
NIMService nim;
NDMService ndm;
PTMService ptm;
SOCService soc;
SSLService ssl;
Y2RService y2r;
MCU::HWCService mcu_hwc;
// "srv:" commands
void enableNotification(u32 messagePointer);
void getServiceHandle(u32 messagePointer);
@ -80,7 +86,7 @@ class ServiceManager {
void subscribe(u32 messagePointer);
public:
ServiceManager(std::span<u32, 16> regs, Memory& mem, GPU& gpu, u32& currentPID, Kernel& kernel);
ServiceManager(std::span<u32, 16> regs, Memory& mem, GPU& gpu, u32& currentPID, Kernel& kernel, const EmulatorConfig& config);
void reset();
void initializeFS() { fs.initializeFilesystem(); }
void handleSyncRequest(u32 messagePointer);

View file

@ -1,5 +0,0 @@
#pragma once
#include <cstddef>
extern unsigned char _shared_font_bin[];
extern size_t _shared_font_len;

View file

@ -75,6 +75,7 @@ class Y2RService {
void setInputLineWidth(u32 messagePointer);
void setInputLines(u32 messagePointer);
void setOutputFormat(u32 messagePointer);
void setPackageParameter(u32 messagePointer);
void setReceiving(u32 messagePointer);
void setRotation(u32 messagePointer);
void setSendingY(u32 messagePointer);