sysclk: code cleanup and fan speed
also fix incompatibility with nx fancontrol
This commit is contained in:
260
Source/sys-clk/common/include/battery.h
Normal file
260
Source/sys-clk/common/include/battery.h
Normal file
@@ -0,0 +1,260 @@
|
||||
/*
|
||||
* Battery Info Driver for Nintendo Switch
|
||||
* Single-header library for accessing battery information
|
||||
*
|
||||
* Usage:
|
||||
* #define BATTERY_INFO_IMPLEMENTATION
|
||||
* #include "battery_info.h"
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include <switch.h>
|
||||
#include <inttypes.h>
|
||||
#include <string.h>
|
||||
// Battery charging flags
|
||||
typedef enum {
|
||||
BatteryFlag_NoHub = BIT(0), // Hub is disconnected
|
||||
BatteryFlag_Rail = BIT(8), // At least one Joy-con is charging from rail
|
||||
BatteryFlag_SPDSRC = BIT(12), // OTG
|
||||
BatteryFlag_ACC = BIT(16) // Accessory
|
||||
} BatteryChargeFlags;
|
||||
|
||||
// Power Delivery Controller State (BM92T series)
|
||||
typedef enum {
|
||||
PDState_NewPDO = 1, // Received new Power Data Object
|
||||
PDState_NoPD = 2, // No Power Delivery source is detected
|
||||
PDState_AcceptedRDO = 3 // Received and accepted Request Data Object
|
||||
} BatteryPDControllerState;
|
||||
|
||||
// Charger type detection
|
||||
typedef enum {
|
||||
ChargerType_None = 0,
|
||||
ChargerType_PD = 1,
|
||||
ChargerType_TypeC_1500mA = 2,
|
||||
ChargerType_TypeC_3000mA = 3,
|
||||
ChargerType_DCP = 4, // Dedicated Charging Port
|
||||
ChargerType_CDP = 5, // Charging Downstream Port
|
||||
ChargerType_SDP = 6, // Standard Downstream Port
|
||||
ChargerType_Apple_500mA = 7,
|
||||
ChargerType_Apple_1000mA = 8,
|
||||
ChargerType_Apple_2000mA = 9
|
||||
} BatteryChargerType;
|
||||
|
||||
// Power role (USB Power Delivery)
|
||||
typedef enum {
|
||||
PowerRole_Sink = 1, // Device is receiving power
|
||||
PowerRole_Source = 2 // Device is providing power
|
||||
} BatteryPowerRole;
|
||||
|
||||
// Complete battery charge information structure
|
||||
typedef struct {
|
||||
int32_t InputCurrentLimit; // Input (Sink) current limit in mA
|
||||
int32_t VBUSCurrentLimit; // Output (Source/VBUS/OTG) current limit in mA
|
||||
int32_t ChargeCurrentLimit; // Battery charging current limit in mA
|
||||
int32_t ChargeVoltageLimit; // Battery charging voltage limit in mV
|
||||
int32_t unk_x10; // Unknown field (possibly enum)
|
||||
int32_t unk_x14; // Unknown field (possibly flags)
|
||||
BatteryPDControllerState PDControllerState; // PD Controller State
|
||||
int32_t BatteryTemperature; // Battery temperature in milli-Celsius
|
||||
int32_t RawBatteryCharge; // Battery charge in per cent-mille (100% = 100000)
|
||||
int32_t VoltageAvg; // Average voltage in mV
|
||||
int32_t BatteryAge; // Battery health (capacity full/design) in pcm
|
||||
BatteryPowerRole PowerRole; // Current power role
|
||||
BatteryChargerType ChargerType; // Type of charger connected
|
||||
int32_t ChargerVoltageLimit; // Charger voltage limit in mV
|
||||
int32_t ChargerCurrentLimit; // Charger current limit in mA
|
||||
BatteryChargeFlags Flags; // Various status flags
|
||||
} BatteryChargeInfo;
|
||||
|
||||
// Helper macro to check if battery charging is enabled
|
||||
#define IS_BATTERY_CHARGING_ENABLED(info) (((info)->unk_x14 >> 8) & 1)
|
||||
|
||||
// Initialize the battery info driver
|
||||
Result batteryInfoInitialize(void);
|
||||
|
||||
// Cleanup the battery info driver
|
||||
void batteryInfoExit(void);
|
||||
|
||||
// Get complete battery charge information
|
||||
Result batteryInfoGetChargeInfo(BatteryChargeInfo *out);
|
||||
|
||||
// Get battery charge percentage (0-100)
|
||||
Result batteryInfoGetChargePercentage(u32 *out);
|
||||
|
||||
// Check if enough power is being supplied
|
||||
Result batteryInfoIsEnoughPowerSupplied(bool *out);
|
||||
|
||||
// Battery charge control functions
|
||||
Result batteryInfoEnableCharging(void);
|
||||
Result batteryInfoDisableCharging(void);
|
||||
Result batteryInfoEnableFastCharging(void);
|
||||
Result batteryInfoDisableFastCharging(void);
|
||||
|
||||
// Helper functions to get human-readable strings
|
||||
const char* batteryInfoGetChargerTypeString(BatteryChargerType type);
|
||||
const char* batteryInfoGetPowerRoleString(BatteryPowerRole role);
|
||||
const char* batteryInfoGetPDStateString(BatteryPDControllerState state);
|
||||
|
||||
// Convenience functions for common values
|
||||
static inline int batteryInfoGetTemperatureMiliCelsius(BatteryChargeInfo *info) {
|
||||
return info->BatteryTemperature;
|
||||
}
|
||||
|
||||
static inline float batteryInfoGetChargePercent(BatteryChargeInfo *info) {
|
||||
return (float)info->RawBatteryCharge / 1000.0f;
|
||||
}
|
||||
|
||||
static inline float batteryInfoGetBatteryHealthPercent(BatteryChargeInfo *info) {
|
||||
return (float)info->BatteryAge / 1000.0f;
|
||||
}
|
||||
|
||||
static inline bool batteryInfoIsCharging(BatteryChargeInfo *info) {
|
||||
return IS_BATTERY_CHARGING_ENABLED(info);
|
||||
}
|
||||
|
||||
// String lookup tables
|
||||
static const char* s_chargerTypeStrings[] = {
|
||||
"None",
|
||||
"Power Delivery",
|
||||
"USB-C @ 1.5A",
|
||||
"USB-C @ 3.0A",
|
||||
"USB-DCP",
|
||||
"USB-CDP",
|
||||
"USB-SDP",
|
||||
"Apple @ 0.5A",
|
||||
"Apple @ 1.0A",
|
||||
"Apple @ 2.0A",
|
||||
};
|
||||
|
||||
static const char* s_powerRoleStrings[] = {
|
||||
"Unknown",
|
||||
"Sink",
|
||||
"Source",
|
||||
};
|
||||
|
||||
static const char* s_pdStateStrings[] = {
|
||||
"Unknown",
|
||||
"New PDO Received",
|
||||
"No PD Source",
|
||||
"RDO Accepted"
|
||||
};
|
||||
|
||||
// Internal PSM service handle
|
||||
static Service g_psmService = {0};
|
||||
static bool g_batteryInfoInitialized = false;
|
||||
|
||||
// Internal PSM command implementations
|
||||
static Result psmGetBatteryChargeInfoFields(BatteryChargeInfo *out) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return serviceDispatchOut(&g_psmService, 17, *out);
|
||||
}
|
||||
|
||||
static Result psmEnableBatteryCharging_internal(void) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return serviceDispatch(&g_psmService, 2);
|
||||
}
|
||||
|
||||
static Result psmDisableBatteryCharging_internal(void) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return serviceDispatch(&g_psmService, 3);
|
||||
}
|
||||
|
||||
static Result psmEnableFastBatteryCharging_internal(void) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return serviceDispatch(&g_psmService, 10);
|
||||
}
|
||||
|
||||
static Result psmDisableFastBatteryCharging_internal(void) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return serviceDispatch(&g_psmService, 11);
|
||||
}
|
||||
|
||||
// Public API implementations
|
||||
Result batteryInfoInitialize(void) {
|
||||
if (g_batteryInfoInitialized)
|
||||
return 0;
|
||||
|
||||
Result rc = psmInitialize();
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
memcpy(&g_psmService, psmGetServiceSession(), sizeof(Service));
|
||||
g_batteryInfoInitialized = true;
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
void batteryInfoExit(void) {
|
||||
if (g_batteryInfoInitialized) {
|
||||
psmExit();
|
||||
memset(&g_psmService, 0, sizeof(Service));
|
||||
g_batteryInfoInitialized = false;
|
||||
}
|
||||
}
|
||||
|
||||
Result batteryInfoGetChargeInfo(BatteryChargeInfo *out) {
|
||||
if (!out)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_BadInput);
|
||||
|
||||
return psmGetBatteryChargeInfoFields(out);
|
||||
}
|
||||
|
||||
Result batteryInfoGetChargePercentage(u32 *out) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return psmGetBatteryChargePercentage(out);
|
||||
}
|
||||
|
||||
Result batteryInfoIsEnoughPowerSupplied(bool *out) {
|
||||
if (!g_batteryInfoInitialized)
|
||||
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
|
||||
|
||||
return psmIsEnoughPowerSupplied(out);
|
||||
}
|
||||
|
||||
Result batteryInfoEnableCharging(void) {
|
||||
return psmEnableBatteryCharging_internal();
|
||||
}
|
||||
|
||||
Result batteryInfoDisableCharging(void) {
|
||||
return psmDisableBatteryCharging_internal();
|
||||
}
|
||||
|
||||
Result batteryInfoEnableFastCharging(void) {
|
||||
return psmEnableFastBatteryCharging_internal();
|
||||
}
|
||||
|
||||
Result batteryInfoDisableFastCharging(void) {
|
||||
return psmDisableFastBatteryCharging_internal();
|
||||
}
|
||||
|
||||
const char* batteryInfoGetChargerTypeString(BatteryChargerType type) {
|
||||
if (type < 0 || type > ChargerType_Apple_2000mA)
|
||||
return "Unknown";
|
||||
|
||||
return s_chargerTypeStrings[type];
|
||||
}
|
||||
|
||||
const char* batteryInfoGetPowerRoleString(BatteryPowerRole role) {
|
||||
if (role < PowerRole_Sink || role > PowerRole_Source)
|
||||
return s_powerRoleStrings[0];
|
||||
|
||||
return s_powerRoleStrings[role];
|
||||
}
|
||||
|
||||
const char* batteryInfoGetPDStateString(BatteryPDControllerState state) {
|
||||
if (state < PDState_NewPDO || state > PDState_AcceptedRDO)
|
||||
return s_pdStateStrings[0];
|
||||
|
||||
return s_pdStateStrings[state];
|
||||
}
|
||||
57
Source/sys-clk/common/include/i2c.h
Normal file
57
Source/sys-clk/common/include/i2c.h
Normal file
@@ -0,0 +1,57 @@
|
||||
#pragma once
|
||||
|
||||
#include <switch.h>
|
||||
|
||||
// To use i2c service, sm and i2c should be intialized via smInitialize() and i2cInitialize().
|
||||
|
||||
Result I2cSet_U8(I2cDevice dev, u8 reg, u8 val);
|
||||
|
||||
Result I2cRead_OutU8(I2cDevice dev, u8 reg, u8 *out);
|
||||
Result I2cRead_OutU16(I2cDevice dev, u8 reg, u16 *out);
|
||||
|
||||
// Max17050 fuel gauge
|
||||
float I2c_Max17050_GetBatteryCurrent();
|
||||
|
||||
const u8 MAX17050_CURRENT_REG = 0x0A;
|
||||
|
||||
// Buck Converter
|
||||
typedef enum I2c_BuckConverter_Reg {
|
||||
I2c_Max77620_SD1VOLT_REG = 0x17, // Used for Erista DDR VDDQ+VDD2 / Mariko VDD2
|
||||
I2c_Max77621_VOLT_REG = 0x00,
|
||||
I2c_Max77812_CPUVOLT_REG = 0x26,
|
||||
I2c_Max77812_GPUVOLT_REG = 0x23,
|
||||
I2c_Max77812_MEMVOLT_REG = 0x25, // Master 3 (GPU 1 + 2, DRAM 3, CPU 4), used for Mariko VDDQ
|
||||
} I2c_BuckConverter_Reg;
|
||||
|
||||
typedef struct I2c_BuckConverter_Domain {
|
||||
I2cDevice device;
|
||||
I2c_BuckConverter_Reg reg;
|
||||
u8 volt_mask;
|
||||
u32 uv_step;
|
||||
u32 uv_min;
|
||||
u32 uv_max;
|
||||
u8 por_val;
|
||||
} I2c_BuckConverter_Domain;
|
||||
|
||||
const I2c_BuckConverter_Domain I2c_Erista_CPU = { I2cDevice_Max77621Cpu, I2c_Max77621_VOLT_REG, 0x7F, 6250, 606250, 1400000, };
|
||||
const I2c_BuckConverter_Domain I2c_Erista_GPU = { I2cDevice_Max77621Gpu, I2c_Max77621_VOLT_REG, 0x7F, 6250, 606250, 1400000, };
|
||||
const I2c_BuckConverter_Domain I2c_Erista_DRAM = { I2cDevice_Max77620Pmic, I2c_Max77620_SD1VOLT_REG, 0x7F, 12500, 600000, 1250000, };
|
||||
const I2c_BuckConverter_Domain I2c_Mariko_CPU = { I2cDevice_Max77812_2, I2c_Max77812_CPUVOLT_REG, 0xFF, 5000, 250000, 1525000, 0x78 };
|
||||
const I2c_BuckConverter_Domain I2c_Mariko_GPU = { I2cDevice_Max77812_2, I2c_Max77812_GPUVOLT_REG, 0xFF, 5000, 250000, 1525000, 0x78 };
|
||||
const I2c_BuckConverter_Domain I2c_Mariko_DRAM_VDDQ = { I2cDevice_Max77812_2, I2c_Max77812_MEMVOLT_REG, 0xFF, 5000, 250000, 700000, 0x78 };
|
||||
const I2c_BuckConverter_Domain I2c_Mariko_DRAM_VDD2 = { I2cDevice_Max77620Pmic, I2c_Max77620_SD1VOLT_REG, 0x7F, 12500, 600000, 1250000, };
|
||||
|
||||
u32 I2c_BuckConverter_GetMvOut(const I2c_BuckConverter_Domain* domain);
|
||||
Result I2c_BuckConverter_SetMvOut(const I2c_BuckConverter_Domain* domain, u32 mvolt);
|
||||
|
||||
// Bq24193 Battery management
|
||||
u32 I2c_Bq24193_Convert_Raw_mA(u8 raw);
|
||||
u8 I2c_Bq24193_Convert_mA_Raw(u32 ma);
|
||||
|
||||
Result I2c_Bq24193_GetFastChargeCurrentLimit(u32 *ma);
|
||||
Result I2c_Bq24193_SetFastChargeCurrentLimit(u32 ma);
|
||||
|
||||
const u32 MA_RANGE_MIN = 512;
|
||||
const u32 MA_RANGE_MAX = 4544;
|
||||
|
||||
const u8 BQ24193_CHARGE_CURRENT_CONTROL_REG = 0x2;
|
||||
27
Source/sys-clk/common/include/notification.h
Normal file
27
Source/sys-clk/common/include/notification.h
Normal file
@@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <ctime>
|
||||
#include <cstdio>
|
||||
|
||||
static void writeNotification(const std::string& message) {
|
||||
const char* flagPath = "sdmc:/config/ultrahand/flags/NOTIFICATIONS.flag";
|
||||
|
||||
FILE* flagFile = fopen(flagPath, "r");
|
||||
if (!flagFile) {
|
||||
return;
|
||||
}
|
||||
fclose(flagFile);
|
||||
|
||||
std::string filename = "Horizon OC -" + std::to_string(std::time(nullptr)) + ".notify";
|
||||
std::string fullPath = "sdmc:/config/ultrahand/notifications/" + filename;
|
||||
|
||||
FILE* file = fopen(fullPath.c_str(), "w");
|
||||
if (file) {
|
||||
fprintf(file, "{\n");
|
||||
fprintf(file, " \"text\": \"%s\",\n", message.c_str());
|
||||
fprintf(file, " \"fontSize\": 28\n");
|
||||
fprintf(file, "}\n");
|
||||
fclose(file);
|
||||
}
|
||||
}
|
||||
95
Source/sys-clk/common/include/pcv_types.h
Normal file
95
Source/sys-clk/common/include/pcv_types.h
Normal file
@@ -0,0 +1,95 @@
|
||||
#pragma once
|
||||
/*
|
||||
* SDx actual min is 625 mV. Multipliers 0/1 reserved.
|
||||
* SD0 max is 1400 mV
|
||||
* SD1 max is 1550 mV
|
||||
* SD2 max is 3787.5 mV
|
||||
* SD3 max is 3787.5 mV
|
||||
*/
|
||||
|
||||
/*
|
||||
* Switch Power domains (max77620):
|
||||
* Name | Usage | uV step | uV min | uV default | uV max | Init
|
||||
*-------+---------------+---------+--------+------------+---------+------------------
|
||||
* sd0 | SoC | 12500 | 600000 | 625000 | 1400000 | 1.125V (pkg1.1)
|
||||
* sd1 | SDRAM | 12500 | 600000 | 1125000 | 1125000 | 1.1V (pkg1.1)
|
||||
* sd2 | ldo{0-1, 7-8} | 12500 | 600000 | 1325000 | 1350000 | 1.325V (pcv)
|
||||
* sd3 | 1.8V general | 12500 | 600000 | 1800000 | 1800000 |
|
||||
* ldo0 | Display Panel | 25000 | 800000 | 1200000 | 1200000 | 1.2V (pkg1.1)
|
||||
* ldo1 | XUSB, PCIE | 25000 | 800000 | 1050000 | 1050000 | 1.05V (pcv)
|
||||
* ldo2 | SDMMC1 | 50000 | 800000 | 1800000 | 3300000 |
|
||||
* ldo3 | GC ASIC | 50000 | 800000 | 3100000 | 3100000 | 3.1V (pcv)
|
||||
* ldo4 | RTC | 12500 | 800000 | 850000 | 850000 | 0.85V (AO, pcv)
|
||||
* ldo5 | GC Card | 50000 | 800000 | 1800000 | 1800000 | 1.8V (pcv)
|
||||
* ldo6 | Touch, ALS | 50000 | 800000 | 2900000 | 2900000 | 2.9V (pcv)
|
||||
* ldo7 | XUSB | 50000 | 800000 | 1050000 | 1050000 | 1.05V (pcv)
|
||||
* ldo8 | XUSB, DP, MCU | 50000 | 800000 | 1050000 | 2800000 | 1.05V/2.8V (pcv)
|
||||
*/
|
||||
|
||||
|
||||
// GPIOs T210: 3: 3.3V, 5: CPU PMIC, 6: GPU PMIC, 7: DSI/VI 1.2V powered by ldo0.
|
||||
|
||||
/*
|
||||
* OTP: T210 - T210B01:
|
||||
* SD0: 1.0V 1.05V - SoC. EN Based on FPSSRC.
|
||||
* SD1: 1.15V 1.1V - DRAM for T210. EN Based on FPSSRC.
|
||||
* SD2: 1.35V 1.35V
|
||||
* SD3: 1.8V 1.8V
|
||||
* All powered off?
|
||||
* LDO0: -- -- - Display
|
||||
* LDO1: 1.05V 1.05V
|
||||
* LDO2: -- -- - SD
|
||||
* LDO3: 3.1V 3.1V - GC ASIC
|
||||
* LDO4: 1.0V 0.8V - Needed for RTC domain on T210.
|
||||
* LDO5: 3.1V 3.1V
|
||||
* LDO6: 2.8V 2.9V - Touch.
|
||||
* LDO7: 1.05V 1.0V
|
||||
* LDO8: 1.05V 1.0V
|
||||
*/
|
||||
|
||||
/*
|
||||
* MAX77620_AME_GPIO: control GPIO modes (bits 0 - 7 correspond to GPIO0 - GPIO7); 0 -> GPIO, 1 -> alt-mode
|
||||
* MAX77620_REG_GPIOx: 0x9 sets output and enable
|
||||
*/
|
||||
|
||||
typedef enum {
|
||||
PcvPowerDomain_Max77620_Sd0 = 0,
|
||||
PcvPowerDomain_Max77620_Sd1 = 1,
|
||||
PcvPowerDomain_Max77620_Sd2 = 2,
|
||||
PcvPowerDomain_Max77620_Sd3 = 3,
|
||||
PcvPowerDomain_Max77620_Ldo0 = 4,
|
||||
PcvPowerDomain_Max77620_Ldo1 = 5,
|
||||
PcvPowerDomain_Max77620_Ldo2 = 6,
|
||||
PcvPowerDomain_Max77620_Ldo3 = 7,
|
||||
PcvPowerDomain_Max77620_Ldo4 = 8,
|
||||
PcvPowerDomain_Max77620_Ldo5 = 9,
|
||||
PcvPowerDomain_Max77620_Ldo6 = 10,
|
||||
PcvPowerDomain_Max77620_Ldo7 = 11,
|
||||
PcvPowerDomain_Max77620_Ldo8 = 12,
|
||||
PcvPowerDomain_Max77621_Cpu = 13,
|
||||
PcvPowerDomain_Max77621_Gpu = 14,
|
||||
PcvPowerDomain_Max77812_Cpu = 15,
|
||||
PcvPowerDomain_Max77812_Gpu = 16,
|
||||
PcvPowerDomain_Max77812_Dram = 17,
|
||||
} PowerDomain;
|
||||
|
||||
typedef enum {
|
||||
PcvPowerDomainId_Max77620_Sd0 = 0x3A000080,
|
||||
PcvPowerDomainId_Max77620_Sd1 = 0x3A000081, // vdd2
|
||||
PcvPowerDomainId_Max77620_Sd2 = 0x3A000082,
|
||||
PcvPowerDomainId_Max77620_Sd3 = 0x3A000083,
|
||||
PcvPowerDomainId_Max77620_Ldo0 = 0x3A0000A0,
|
||||
PcvPowerDomainId_Max77620_Ldo1 = 0x3A0000A1,
|
||||
PcvPowerDomainId_Max77620_Ldo2 = 0x3A0000A2,
|
||||
PcvPowerDomainId_Max77620_Ldo3 = 0x3A0000A3,
|
||||
PcvPowerDomainId_Max77620_Ldo4 = 0x3A0000A4,
|
||||
PcvPowerDomainId_Max77620_Ldo5 = 0x3A0000A5,
|
||||
PcvPowerDomainId_Max77620_Ldo6 = 0x3A0000A6,
|
||||
PcvPowerDomainId_Max77620_Ldo7 = 0x3A0000A7,
|
||||
PcvPowerDomainId_Max77620_Ldo8 = 0x3A0000A8,
|
||||
PcvPowerDomainId_Max77621_Cpu = 0x3A000003,
|
||||
PcvPowerDomainId_Max77621_Gpu = 0x3A000004,
|
||||
PcvPowerDomainId_Max77812_Cpu = 0x3A000003,
|
||||
PcvPowerDomainId_Max77812_Gpu = 0x3A000004,
|
||||
PcvPowerDomainId_Max77812_Dram = 0x3A000005, // vddq
|
||||
} PowerDomainId;
|
||||
22
Source/sys-clk/common/include/pwm.h
Normal file
22
Source/sys-clk/common/include/pwm.h
Normal file
@@ -0,0 +1,22 @@
|
||||
#pragma once
|
||||
|
||||
#include <switch.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct {
|
||||
Service s;
|
||||
} PwmChannelSession;
|
||||
|
||||
Result pwmInitialize(void);
|
||||
void pwmExit(void);
|
||||
Service* pwmGetServiceSession(void);
|
||||
Result pwmOpenSession2(PwmChannelSession *out, u32 device_code);
|
||||
Result pwmChannelSessionGetDutyCycle(PwmChannelSession *c, double* out);
|
||||
void pwmChannelSessionClose(PwmChannelSession *c);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif
|
||||
19
Source/sys-clk/common/include/rgltr.h
Normal file
19
Source/sys-clk/common/include/rgltr.h
Normal file
@@ -0,0 +1,19 @@
|
||||
#pragma once
|
||||
#include <switch.h>
|
||||
#include "pcv_types.h"
|
||||
|
||||
typedef struct {
|
||||
Service s;
|
||||
} RgltrSession;
|
||||
|
||||
Result rgltrInitialize(void);
|
||||
|
||||
void rgltrExit(void);
|
||||
|
||||
Service* rgltrGetServiceSession(void);
|
||||
|
||||
Result rgltrOpenSession(RgltrSession* session_out, PowerDomainId module_id);
|
||||
void rgltrCloseSession(RgltrSession* session);
|
||||
Result rgltrGetVoltage(RgltrSession* session, u32 *out_volt);
|
||||
Result rgltrGetPowerModuleNumLimit(u32 *out);
|
||||
Result rgltrGetVoltageEnabled(RgltrSession* session, u32 *out);
|
||||
15
Source/sys-clk/common/include/rgltr_services.h
Normal file
15
Source/sys-clk/common/include/rgltr_services.h
Normal file
@@ -0,0 +1,15 @@
|
||||
#pragma once
|
||||
|
||||
#include <switch.h> // for Service, Result, hosversionBefore(), smGetService(), serviceClose(), etc.
|
||||
#include "rgltr.h" // for RgltrSession, PowerDomainId, etc.
|
||||
|
||||
extern Service g_rgltrSrv;
|
||||
|
||||
Result rgltrInitialize(void);
|
||||
void rgltrExit(void);
|
||||
|
||||
Result rgltrOpenSession(RgltrSession* session_out, PowerDomainId module_id);
|
||||
|
||||
Result rgltrGetVoltage(RgltrSession* session, u32* out_volt);
|
||||
|
||||
void rgltrCloseSession(RgltrSession* session);
|
||||
65
Source/sys-clk/common/include/service_guard.h
Normal file
65
Source/sys-clk/common/include/service_guard.h
Normal file
@@ -0,0 +1,65 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <switch/types.h>
|
||||
#include <switch/result.h>
|
||||
#include <switch/kernel/mutex.h>
|
||||
#include <switch/sf/service.h>
|
||||
#include <switch/services/sm.h>
|
||||
|
||||
typedef struct ServiceGuard {
|
||||
Mutex mutex;
|
||||
u32 refCount;
|
||||
} ServiceGuard;
|
||||
|
||||
NX_INLINE bool serviceGuardBeginInit(ServiceGuard* g)
|
||||
{
|
||||
mutexLock(&g->mutex);
|
||||
return (g->refCount++) == 0;
|
||||
}
|
||||
|
||||
NX_INLINE Result serviceGuardEndInit(ServiceGuard* g, Result rc, void (*cleanupFunc)(void))
|
||||
{
|
||||
if (R_FAILED(rc)) {
|
||||
cleanupFunc();
|
||||
--g->refCount;
|
||||
}
|
||||
mutexUnlock(&g->mutex);
|
||||
return rc;
|
||||
}
|
||||
|
||||
NX_INLINE void serviceGuardExit(ServiceGuard* g, void (*cleanupFunc)(void))
|
||||
{
|
||||
mutexLock(&g->mutex);
|
||||
if (g->refCount && (--g->refCount) == 0)
|
||||
cleanupFunc();
|
||||
mutexUnlock(&g->mutex);
|
||||
}
|
||||
|
||||
#define NX_GENERATE_SERVICE_GUARD_PARAMS(name, _paramdecl, _parampass) \
|
||||
\
|
||||
static ServiceGuard g_##name##Guard; \
|
||||
NX_INLINE Result _##name##Initialize _paramdecl; \
|
||||
static void _##name##Cleanup(void); \
|
||||
\
|
||||
Result name##Initialize _paramdecl \
|
||||
{ \
|
||||
Result rc = 0; \
|
||||
if (serviceGuardBeginInit(&g_##name##Guard)) \
|
||||
rc = _##name##Initialize _parampass; \
|
||||
return serviceGuardEndInit(&g_##name##Guard, rc, _##name##Cleanup); \
|
||||
} \
|
||||
\
|
||||
void name##Exit(void) \
|
||||
{ \
|
||||
serviceGuardExit(&g_##name##Guard, _##name##Cleanup); \
|
||||
}
|
||||
|
||||
#define NX_GENERATE_SERVICE_GUARD(name) NX_GENERATE_SERVICE_GUARD_PARAMS(name, (void), ())
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
@@ -103,6 +103,7 @@ typedef enum
|
||||
HocClkPartLoad_GPU,
|
||||
HocClkPartLoad_CPUAvg,
|
||||
HocClkPartLoad_BAT,
|
||||
HocClkPartLoad_FAN,
|
||||
SysClkPartLoad_EnumMax
|
||||
} SysClkPartLoad;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user