#include <3ds/ipc.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
-#include <3ds/linear.h>
-#include <3ds/vram.h>
#include <3ds/os.h>
#include <3ds/synchronization.h>
#include <3ds/gfx.h>
#include <3ds/console.h>
#include <3ds/util/utf.h>
+#include <3ds/allocator/linear.h>
+#include <3ds/allocator/mappable.h>
+#include <3ds/allocator/vram.h>
+
#include <3ds/services/ac.h>
#include <3ds/services/am.h>
#include <3ds/services/apt.h>
#include <3ds/services/csnd.h>
#include <3ds/services/dsp.h>
#include <3ds/services/fs.h>
-#include <3ds/services/gsp.h>
+#include <3ds/services/gspgpu.h>
+#include <3ds/services/gsplcd.h>
#include <3ds/services/hid.h>
#include <3ds/services/irrst.h>
#include <3ds/services/httpc.h>
#include <3ds/services/ns.h>
#include <3ds/services/pm.h>
#include <3ds/services/ps.h>
-#include <3ds/services/ptm.h>
+#include <3ds/services/ptmu.h>
+#include <3ds/services/ptmsysm.h>
#include <3ds/services/soc.h>
#include <3ds/services/mic.h>
#include <3ds/services/mvd.h>
#pragma once
#include <3ds/types.h>
-#include <3ds/services/gsp.h>
+#include <3ds/services/gspgpu.h>
/// Converts red, green, and blue components to packed RGB565.
#define RGB565(r,g,b) (((b)&0x1f)|(((g)&0x3f)<<5)|(((r)&0x1f)<<11))
* @note Even if the double buffering is disabled, it will allocate two buffer per screen.
* @note You should always call @ref gfxExit once done to free the memory and services
*/
-void gfxInit(GSP_FramebufferFormats topFormat, GSP_FramebufferFormats bottomFormat, bool vrambuffers);
+void gfxInit(GSPGPU_FramebufferFormats topFormat, GSPGPU_FramebufferFormats bottomFormat, bool vrambuffers);
/**
* @brief Closes the gsp service and frees the framebuffers.
* @param screen The screen of which format should be changed
* @param format One of the gsp pixel formats.
*/
-void gfxSetScreenFormat(gfxScreen_t screen, GSP_FramebufferFormats format);
+void gfxSetScreenFormat(gfxScreen_t screen, GSPGPU_FramebufferFormats format);
/**
* @brief Gets a screen pixel format.
* @param screen Screen to get the pixel format of.
* @return the pixel format of the chosen screen set by ctrulib.
*/
-GSP_FramebufferFormats gfxGetScreenFormat(gfxScreen_t screen);
+GSPGPU_FramebufferFormats gfxGetScreenFormat(gfxScreen_t screen);
/**
* @brief Sets whether to use ctrulib's double buffering
/**
* @brief Supported transfer pixel formats.
- * @sa GSP_FramebufferFormats
+ * @sa GSPGPU_FramebufferFormats
*/
typedef enum
{
};
/// Interpolation types.
-enum
+typedef enum
{
NDSP_INTERP_POLYPHASE = 0, ///< Polyphase interpolation
NDSP_INTERP_LINEAR = 1, ///< Linear interpolation
NDSP_INTERP_NONE = 2, ///< No interpolation
-};
+} ndspInterpType;
///@}
///@{
/**
* @brief Sets the format of a channel.
- * @sa NDSP_Encoding
* @param id ID of the channel (0..23).
* @param format Format to use.
*/
* @param id ID of the channel (0..23).
* @param type Interpolation type to use.
*/
-void ndspChnSetInterp(int id, int type);
+void ndspChnSetInterp(int id, ndspInterpType type);
/**
* @brief Sets the sample rate of a channel.
///@name Data types
///@{
/// Sound output modes.
-enum
+typedef enum
{
NDSP_OUTPUT_MONO = 0, ///< Mono sound
NDSP_OUTPUT_STEREO = 1, ///< Stereo sound
NDSP_OUTPUT_SURROUND = 2, ///< 3D Surround sound
-};
+} ndspOutputMode;
// Clipping modes.
-enum
+typedef enum
{
NDSP_CLIP_NORMAL = 0, ///< "Normal" clipping mode (?)
NDSP_CLIP_SOFT = 1, ///< "Soft" clipping mode (?)
-};
+} ndspClippingMode;
// Surround speaker positions.
-enum
+typedef enum
{
NDSP_SPKPOS_SQUARE = 0, ///<?
NDSP_SPKPOS_WIDE = 1, ///<?
NDSP_SPKPOS_NUM = 2, ///<?
-};
+} ndspSpeakerPos;
/// ADPCM data.
typedef struct
* @brief Sets the output mode.
* @param mode Output mode to set. Defaults to NDSP_OUTPUT_STEREO.
*/
-void ndspSetOutputMode(int mode);
+void ndspSetOutputMode(ndspOutputMode mode);
/**
* @brief Sets the clipping mode.
* @param mode Clipping mode to set. Defaults to NDSP_CLIP_SOFT.
*/
-void ndspSetClippingMode(int mode);
+void ndspSetClippingMode(ndspClippingMode mode);
/**
* @brief Sets the output count.
* @brief Sets the surround sound position.
* @param pos Position to set. Defaults to NDSP_SPKPOS_SQUARE.
*/
-void ndspSurroundSetPos(u16 pos);
+void ndspSurroundSetPos(ndspSpeakerPos pos);
/**
* @brief Sets the surround sound rear ratio.
/// Exits AC.
void acExit(void);
+/// Waits for the system to connect to the internet.
+Result acWaitInternetConnection(void);
+
/**
* @brief Gets the current Wifi status.
* @param out Pointer to output the current Wifi status to. (0 = not connected, 1 = O3DS Internet, 2 = N3DS Internet)
*/
Result ACU_GetWifiStatus(u32 *out);
-
-/// Waits for the system to connect to the internet.
-Result ACU_WaitInternetConnection(void);
*
* Retrieved from http://3dbrew.org/wiki/NS_and_APT_Services#AppIDs
*/
-typedef enum{
+typedef enum {
APPID_HOMEMENU = 0x101, ///< Home Menu
APPID_CAMERA = 0x110, ///< Camera applet
APPID_FRIENDS_LIST = 0x112, ///< Friends List applet
APPID_MINT = 0x407, ///< mint
APPID_EXTRAPAD = 0x408, ///< extrapad
APPID_MEMOLIB = 0x409, ///< memolib
-}NS_APPID;
+} NS_APPID;
/// App status values.
-typedef enum{
+typedef enum {
APP_NOTINITIALIZED, ///< App not initialized.
APP_RUNNING, ///< App running.
APP_SUSPENDED, ///< App suspended.
APP_PREPARE_SLEEPMODE, ///< App preparing to enter sleep mode.
APP_APPLETSTARTED, ///< Applet started.
APP_APPLETCLOSED ///< Applet closed.
-}APP_STATUS;
+} APT_AppStatus;
/// APT signals.
-enum {
+typedef enum {
APTSIGNAL_HOMEBUTTON = 1, ///< Home button pressed.
// 2: sleep-mode related?
APTSIGNAL_PREPARESLEEP = 3, ///< Prepare to enter sleep mode.
APTSIGNAL_UTILITY = 9, ///< Utility called.
APTSIGNAL_SLEEPSYSTEM = 10, ///< System sleeping.
APTSIGNAL_ERROR = 11 ///< Error occurred.
-};
+} APT_Signal;
/// APT hook types.
-enum {
+typedef enum {
APTHOOK_ONSUSPEND = 0, ///< App suspended.
APTHOOK_ONRESTORE, ///< App restored.
APTHOOK_ONSLEEP, ///< App sleeping.
APTHOOK_ONEXIT, ///< App exiting.
APTHOOK_COUNT, ///< Number of APT hook types.
-};
+} APT_HookType;
/// APT hook function.
-typedef void (*aptHookFn)(int hook, void* param);
+typedef void (*aptHookFn)(APT_HookType hook, void* param);
/// APT hook cookie.
typedef struct tag_aptHookCookie
* @brief Sets the app's status.
* @param status Status to set.
*/
-void aptSetStatus(APP_STATUS status);
+void aptSetStatus(APT_AppStatus status);
/**
* @brief Gets the app's status.
* @return The app's status.
*/
-APP_STATUS aptGetStatus(void);
+APT_AppStatus aptGetStatus(void);
/**
* @brief Gets the app's power status.
* @param appID ID of the application.
* @param signalType Pointer to output the signal type to.
*/
-Result APT_InquireNotification(u32 appID, u8* signalType);
+Result APT_InquireNotification(u32 appID, APT_Signal* signalType);
/**
* @brief Notifies an application to wait.
#include <3ds/types.h>
/// Camera connection target ports.
-typedef enum {
+enum {
PORT_NONE = 0x0, ///< No port.
PORT_CAM1 = BIT(0), ///< CAM1 port.
PORT_CAM2 = BIT(1), ///< CAM2 port.
// Port combinations.
PORT_BOTH = PORT_CAM1 | PORT_CAM2, ///< Both ports.
-} CAMU_Port;
+};
/// Camera combinations.
-typedef enum {
+enum {
SELECT_NONE = 0x0, ///< No camera.
SELECT_OUT1 = BIT(0), ///< Outer camera 1.
SELECT_IN1 = BIT(1), ///< Inner camera 1.
SELECT_OUT1_OUT2 = SELECT_OUT1 | SELECT_OUT2, ///< Both outer cameras.
SELECT_IN1_OUT2 = SELECT_IN1 | SELECT_OUT2, ///< Inner camera 1 and outer camera 2.
SELECT_ALL = SELECT_OUT1 | SELECT_IN1 | SELECT_OUT2, ///< All cameras.
-} CAMU_CameraSelect;
+};
/// Camera contexts.
typedef enum {
/// Batch camera configuration for use without a context.
typedef struct {
- u8 camera; ///< #CAMU_CameraSelect Selected camera.
+ u8 camera; ///< Selected camera.
s8 exposure; ///< Camera exposure.
u8 whiteBalance; ///< #CAMU_WhiteBalance Camera white balance.
s8 sharpness; ///< Camera sharpness.
/// Batch camera configuration for use with a context.
typedef struct {
- u8 camera; ///< #CAMU_CameraSelect Selected camera.
+ u8 camera; ///< Selected camera.
u8 context; ///< #CAMU_Context Selected context.
u8 flip; ///< #CAMU_Flip Camera image flip mode.
u8 effect; ///< #CAMU_Effect Camera image special effects.
/// Batch camera configuration for use with a context and with detailed size information.
typedef struct {
- u8 camera; ///< #CAMU_CameraSelect Selected camera.
+ u8 camera; ///< Selected camera.
u8 context; ///< #CAMU_Context Selected context.
u8 flip; ///< #CAMU_Flip Camera image flip mode.
u8 effect; ///< #CAMU_Effect Camera image special effects.
* Begins capture on the specified camera port.
* @param port Port to begin capture on.
*/
-Result CAMU_StartCapture(CAMU_Port port);
+Result CAMU_StartCapture(u32 port);
/**
* Terminates capture on the specified camera port.
* @param port Port to terminate capture on.
*/
-Result CAMU_StopCapture(CAMU_Port port);
+Result CAMU_StopCapture(u32 port);
/**
* @brief Gets whether the specified camera port is busy.
* @param busy Pointer to output the busy state to.
* @param port Port to check.
*/
-Result CAMU_IsBusy(bool* busy, CAMU_Port port);
+Result CAMU_IsBusy(bool* busy, u32 port);
/**
* @brief Clears the buffer and error flags of the specified camera port.
* @param port Port to clear.
*/
-Result CAMU_ClearBuffer(CAMU_Port port);
+Result CAMU_ClearBuffer(u32 port);
/**
* @brief Gets a handle to the event signaled on vsync interrupts.
* @param event Pointer to output the event handle to.
* @param port Port to use.
*/
-Result CAMU_GetVsyncInterruptEvent(Handle* event, CAMU_Port port);
+Result CAMU_GetVsyncInterruptEvent(Handle* event, u32 port);
/**
* @brief Gets a handle to the event signaled on camera buffer errors.
* @param event Pointer to output the event handle to.
* @param port Port to use.
*/
-Result CAMU_GetBufferErrorInterruptEvent(Handle* event, CAMU_Port port);
+Result CAMU_GetBufferErrorInterruptEvent(Handle* event, u32 port);
/**
* @brief Initiates the process of receiving a camera frame.
* @param imageSize Size of the image to receive.
* @param transferUnit Transfer unit to use when receiving.
*/
-Result CAMU_SetReceiving(Handle* event, void* dst, CAMU_Port port, u32 imageSize, s16 transferUnit);
+Result CAMU_SetReceiving(Handle* event, void* dst, u32 port, u32 imageSize, s16 transferUnit);
/**
* @brief Gets whether the specified camera port has finished receiving image data.
* @param finishedReceiving Pointer to output the receiving status to.
* @param port Port to check.
*/
-Result CAMU_IsFinishedReceiving(bool* finishedReceiving, CAMU_Port port);
+Result CAMU_IsFinishedReceiving(bool* finishedReceiving, u32 port);
/**
* @brief Sets the number of lines to transfer into an image buffer.
* @param width Width of the image.
* @param height Height of the image.
*/
-Result CAMU_SetTransferLines(CAMU_Port port, s16 lines, s16 width, s16 height);
+Result CAMU_SetTransferLines(u32 port, s16 lines, s16 width, s16 height);
/**
* @brief Gets the maximum number of lines that can be saved to an image buffer.
* @param width Width of the image.
* @param height Height of the image.
*/
-Result CAMU_SetTransferBytes(CAMU_Port port, u32 bytes, s16 width, s16 height);
+Result CAMU_SetTransferBytes(u32 port, u32 bytes, s16 width, s16 height);
/**
* @brief Gets the number of bytes to transfer into an image buffer.
* @param transferBytes Pointer to write the number of bytes to.
* @param port Port to use.
*/
-Result CAMU_GetTransferBytes(u32* transferBytes, CAMU_Port port);
+Result CAMU_GetTransferBytes(u32* transferBytes, u32 port);
/**
* @brief Gets the maximum number of bytes that can be saved to an image buffer.
* @param port Port to use.
* @param trimming Whether image trimming is enabled.
*/
-Result CAMU_SetTrimming(CAMU_Port port, bool trimming);
+Result CAMU_SetTrimming(u32 port, bool trimming);
/**
* @brief Gets whether image trimming is enabled.
* @param trimming Pointer to output the trim state to.
* @param port Port to use.
*/
-Result CAMU_IsTrimming(bool* trimming, CAMU_Port port);
+Result CAMU_IsTrimming(bool* trimming, u32 port);
/**
* @brief Sets the parameters used for trimming images.
* @param xEnd End X coordinate.
* @param yEnd End Y coordinate.
*/
-Result CAMU_SetTrimmingParams(CAMU_Port port, s16 xStart, s16 yStart, s16 xEnd, s16 yEnd);
+Result CAMU_SetTrimmingParams(u32 port, s16 xStart, s16 yStart, s16 xEnd, s16 yEnd);
/**
* @brief Gets the parameters used for trimming images.
* @param yEnd Pointer to write the end Y coordinate to.
* @param port Port to use.
*/
-Result CAMU_GetTrimmingParams(s16* xStart, s16* yStart, s16* xEnd, s16* yEnd, CAMU_Port port);
+Result CAMU_GetTrimmingParams(s16* xStart, s16* yStart, s16* xEnd, s16* yEnd, u32 port);
/**
* @brief Sets the parameters used for trimming images, relative to the center of the image.
* @param camWidth Camera width.
* @param camHeight Camera height.
*/
-Result CAMU_SetTrimmingParamsCenter(CAMU_Port port, s16 trimWidth, s16 trimHeight, s16 camWidth, s16 camHeight);
+Result CAMU_SetTrimmingParamsCenter(u32 port, s16 trimWidth, s16 trimHeight, s16 camWidth, s16 camHeight);
/**
* @brief Activates the specified camera.
* @param select Camera to use.
*/
-Result CAMU_Activate(CAMU_CameraSelect select);
+Result CAMU_Activate(u32 select);
/**
* @brief Switches the specified camera's active context.
* @param select Camera to use.
* @param context Context to use.
*/
-Result CAMU_SwitchContext(CAMU_CameraSelect select, CAMU_Context context);
+Result CAMU_SwitchContext(u32 select, CAMU_Context context);
/**
* @brief Sets the exposure value of the specified camera.
* @param select Camera to use.
* @param exposure Exposure value to use.
*/
-Result CAMU_SetExposure(CAMU_CameraSelect select, s8 exposure);
+Result CAMU_SetExposure(u32 select, s8 exposure);
/**
* @brief Sets the white balance mode of the specified camera.
* @param select Camera to use.
* @param whiteBalance White balance mode to use.
*/
-Result CAMU_SetWhiteBalance(CAMU_CameraSelect select, CAMU_WhiteBalance whiteBalance);
+Result CAMU_SetWhiteBalance(u32 select, CAMU_WhiteBalance whiteBalance);
/**
* @brief Sets the white balance mode of the specified camera.
* @param select Camera to use.
* @param whiteBalance White balance mode to use.
*/
-Result CAMU_SetWhiteBalanceWithoutBaseUp(CAMU_CameraSelect select, CAMU_WhiteBalance whiteBalance);
+Result CAMU_SetWhiteBalanceWithoutBaseUp(u32 select, CAMU_WhiteBalance whiteBalance);
/**
* @brief Sets the sharpness of the specified camera.
* @param select Camera to use.
* @param sharpness Sharpness to use.
*/
-Result CAMU_SetSharpness(CAMU_CameraSelect select, s8 sharpness);
+Result CAMU_SetSharpness(u32 select, s8 sharpness);
/**
* @brief Sets whether auto exposure is enabled on the specified camera.
* @param select Camera to use.
* @param autoWhiteBalance Whether auto exposure is enabled.
*/
-Result CAMU_SetAutoExposure(CAMU_CameraSelect select, bool autoExposure);
+Result CAMU_SetAutoExposure(u32 select, bool autoExposure);
/**
* @brief Gets whether auto exposure is enabled on the specified camera.
* @param autoExposure Pointer to output the auto exposure state to.
* @param select Camera to use.
*/
-Result CAMU_IsAutoExposure(bool* autoExposure, CAMU_CameraSelect select);
+Result CAMU_IsAutoExposure(bool* autoExposure, u32 select);
/**
* @brief Sets whether auto white balance is enabled on the specified camera.
* @param select Camera to use.
* @param autoWhiteBalance Whether auto white balance is enabled.
*/
-Result CAMU_SetAutoWhiteBalance(CAMU_CameraSelect select, bool autoWhiteBalance);
+Result CAMU_SetAutoWhiteBalance(u32 select, bool autoWhiteBalance);
/**
* @brief Gets whether auto white balance is enabled on the specified camera.
* @param autoWhiteBalance Pointer to output the auto white balance state to.
* @param select Camera to use.
*/
-Result CAMU_IsAutoWhiteBalance(bool* autoWhiteBalance, CAMU_CameraSelect select);
+Result CAMU_IsAutoWhiteBalance(bool* autoWhiteBalance, u32 select);
/**
* @brief Flips the image of the specified camera in the specified context.
* @param flip Flip mode to use.
* @param context Context to use.
*/
-Result CAMU_FlipImage(CAMU_CameraSelect select, CAMU_Flip flip, CAMU_Context context);
+Result CAMU_FlipImage(u32 select, CAMU_Flip flip, CAMU_Context context);
/**
* @brief Sets the image resolution of the given camera in the given context, in detail.
* @param cropY1 Second crop point Y.
* @param context Context to use.
*/
-Result CAMU_SetDetailSize(CAMU_CameraSelect select, s16 width, s16 height, s16 cropX0, s16 cropY0, s16 cropX1, s16 cropY1, CAMU_Context context);
+Result CAMU_SetDetailSize(u32 select, s16 width, s16 height, s16 cropX0, s16 cropY0, s16 cropX1, s16 cropY1, CAMU_Context context);
/**
* @brief Sets the image resolution of the given camera in the given context.
* @param size Size to use.
* @param context Context to use.
*/
-Result CAMU_SetSize(CAMU_CameraSelect select, CAMU_Size size, CAMU_Context context);
+Result CAMU_SetSize(u32 select, CAMU_Size size, CAMU_Context context);
/**
* @brief Sets the frame rate of the given camera.
* @param select Camera to use.
* @param frameRate Frame rate to use.
*/
-Result CAMU_SetFrameRate(CAMU_CameraSelect select, CAMU_FrameRate frameRate);
+Result CAMU_SetFrameRate(u32 select, CAMU_FrameRate frameRate);
/**
* @brief Sets the photo mode of the given camera.
* @param select Camera to use.
* @param photoMode Photo mode to use.
*/
-Result CAMU_SetPhotoMode(CAMU_CameraSelect select, CAMU_PhotoMode photoMode);
+Result CAMU_SetPhotoMode(u32 select, CAMU_PhotoMode photoMode);
/**
* @brief Sets the special effects of the given camera in the given context.
* @param effect Effect to use.
* @param context Context to use.
*/
-Result CAMU_SetEffect(CAMU_CameraSelect select, CAMU_Effect effect, CAMU_Context context);
+Result CAMU_SetEffect(u32 select, CAMU_Effect effect, CAMU_Context context);
/**
* @brief Sets the contrast mode of the given camera.
* @param select Camera to use.
* @param contrast Contrast mode to use.
*/
-Result CAMU_SetContrast(CAMU_CameraSelect select, CAMU_Contrast contrast);
+Result CAMU_SetContrast(u32 select, CAMU_Contrast contrast);
/**
* @brief Sets the lens correction mode of the given camera.
* @param select Camera to use.
* @param lensCorrection Lens correction mode to use.
*/
-Result CAMU_SetLensCorrection(CAMU_CameraSelect select, CAMU_LensCorrection lensCorrection);
+Result CAMU_SetLensCorrection(u32 select, CAMU_LensCorrection lensCorrection);
/**
* @brief Sets the output format of the given camera in the given context.
* @param format Format to output.
* @param context Context to use.
*/
-Result CAMU_SetOutputFormat(CAMU_CameraSelect select, CAMU_OutputFormat format, CAMU_Context context);
+Result CAMU_SetOutputFormat(u32 select, CAMU_OutputFormat format, CAMU_Context context);
/**
* @brief Sets the region to base auto exposure off of for the specified camera.
* @param width Width of the region.
* @param height Height of the region.
*/
-Result CAMU_SetAutoExposureWindow(CAMU_CameraSelect select, s16 x, s16 y, s16 width, s16 height);
+Result CAMU_SetAutoExposureWindow(u32 select, s16 x, s16 y, s16 width, s16 height);
/**
* @brief Sets the region to base auto white balance off of for the specified camera.
* @param width Width of the region.
* @param height Height of the region.
*/
-Result CAMU_SetAutoWhiteBalanceWindow(CAMU_CameraSelect select, s16 x, s16 y, s16 width, s16 height);
+Result CAMU_SetAutoWhiteBalanceWindow(u32 select, s16 x, s16 y, s16 width, s16 height);
/**
* @brief Sets whether the specified camera's noise filter is enabled.
* @param select Camera to use.
* @param noiseFilter Whether the noise filter is enabled.
*/
-Result CAMU_SetNoiseFilter(CAMU_CameraSelect select, bool noiseFilter);
+Result CAMU_SetNoiseFilter(u32 select, bool noiseFilter);
/**
* @brief Synchronizes the specified cameras' vsync timing.
* @param select1 First camera.
* @param select2 Second camera.
*/
-Result CAMU_SynchronizeVsyncTiming(CAMU_CameraSelect select1, CAMU_CameraSelect select2);
+Result CAMU_SynchronizeVsyncTiming(u32 select1, u32 select2);
/**
* @brief Gets the vsync timing record of the specified camera for the specified number of signals.
* @param port Port to use.
* @param past Number of past timings to retrieve.
*/
-Result CAMU_GetLatestVsyncTiming(s64* timing, CAMU_Port port, u32 past);
+Result CAMU_GetLatestVsyncTiming(s64* timing, u32 port, u32 past);
/**
* @brief Gets the specified camera's stereo camera calibration data.
* @param addr Address to write to.
* @param data Data to write.
*/
-Result CAMU_WriteRegisterI2c(CAMU_CameraSelect select, u16 addr, u16 data);
+Result CAMU_WriteRegisterI2c(u32 select, u16 addr, u16 data);
/**
* @brief Writes to the specified MCU variable of the specified camera.
* @param addr Address to write to.
* @param data Data to write.
*/
-Result CAMU_WriteMcuVariableI2c(CAMU_CameraSelect select, u16 addr, u16 data);
+Result CAMU_WriteMcuVariableI2c(u32 select, u16 addr, u16 data);
/**
* @brief Reads the specified I2C register of the specified camera.
* @param select Camera to read from.
* @param addr Address to read.
*/
-Result CAMU_ReadRegisterI2cExclusive(u16* data, CAMU_CameraSelect select, u16 addr);
+Result CAMU_ReadRegisterI2cExclusive(u16* data, u32 select, u16 addr);
/**
* @brief Reads the specified MCU variable of the specified camera.
* @param select Camera to read from.
* @param addr Address to read.
*/
-Result CAMU_ReadMcuVariableI2cExclusive(u16* data, CAMU_CameraSelect select, u16 addr);
+Result CAMU_ReadMcuVariableI2cExclusive(u16* data, u32 select, u16 addr);
/**
* @brief Sets the specified camera's image quality calibration data.
* @brief Gets the Y2R coefficient applied to image data by the camera.
* @param coefficient Pointer to output the Y2R coefficient to.
*/
-Result CAMU_GetSuitableY2rStandardCoefficient(Y2R_StandardCoefficient* coefficient);
+Result CAMU_GetSuitableY2rStandardCoefficient(Y2RU_StandardCoefficient* coefficient);
/**
* @brief Plays the specified shutter sound.
* @brief Gets the current activated camera.
* @param select Pointer to output the current activated camera to.
*/
-Result CAMU_GetActivatedCamera(CAMU_CameraSelect* select);
+Result CAMU_GetActivatedCamera(u32* select);
/**
* @brief Gets the current sleep camera.
* @param select Pointer to output the current sleep camera to.
*/
-Result CAMU_GetSleepCamera(CAMU_CameraSelect* select);
+Result CAMU_GetSleepCamera(u32* select);
/**
* @brief Sets the current sleep camera.
* @param select Camera to set.
*/
-Result CAMU_SetSleepCamera(CAMU_CameraSelect select);
+Result CAMU_SetSleepCamera(u32 select);
/**
* @brief Sets whether to enable synchronization of left and right camera brightnesses.
* @brief Initializes CFGNOR.
* @param value Unknown, usually 1.
*/
+Result cfgnorInit(u8 value);
+
+/// Exits CFGNOR
+void cfgnorExit(void);
+
+/**
+ * @brief Dumps the NOR flash.
+ * @param buf Buffer to dump to.
+ * @param size Size of the buffer.
+ */
+Result cfgnorDumpFlash(u32 *buf, u32 size);
+
+/**
+ * @brief Writes the NOR flash.
+ * @param buf Buffer to write from.
+ * @param size Size of the buffer.
+ */
+Result cfgnorWriteFlash(u32 *buf, u32 size);
+
+/**
+ * @brief Initializes the CFGNOR session.
+ * @param value Unknown, usually 1.
+ */
Result CFGNOR_Initialize(u8 value);
-/// Shuts down CFGNOR.
+/// Shuts down the CFGNOR session.
Result CFGNOR_Shutdown(void);
/**
* @param size Size of the buffer.
*/
Result CFGNOR_WriteData(u32 offset, u32 *buf, u32 size);
-
-/**
- * @brief Dumps the NOR flash.
- * @param buf Buffer to dump to.
- * @param size Size of the buffer.
- */
-Result CFGNOR_DumpFlash(u32 *buf, u32 size);
-
-/**
- * @brief Writes the NOR flash.
- * @param buf Buffer to write from.
- * @param size Size of the buffer.
- */
-Result CFGNOR_WriteFlash(u32 *buf, u32 size);
CFG_LANGUAGE_PT = 9, ///< Portugese
CFG_LANGUAGE_RU = 10, ///< Russian
CFG_LANGUAGE_TW = 11, ///< Traditional Chinese
-} CFG_Langage;
+} CFG_Language;
/// Initializes CFGU.
Result cfguInit(void);
/**
* @brief Gets the system's language.
- * @param language Pointer to write the language to. (see @ref CFG_Langage)
+ * @param language Pointer to write the language to. (see @ref CFG_Language)
*/
Result CFGU_GetSystemLanguage(u8* language);
};
/// Duty cycles for a PSG channel.
-enum
+typedef enum
{
DutyCycle_0 = 7, ///< 0.0% duty cycle
DutyCycle_12 = 0, ///< 12.5% duty cycle
DutyCycle_62 = 4, ///< 62.5% duty cycle
DutyCycle_75 = 5, ///< 75.0% duty cycle
DutyCycle_87 = 6 ///< 87.5% duty cycle
-};
+} CSND_DutyCycle;
/// Channel info.
typedef union
*/
Result CSND_ReleaseCapUnit(u32 capUnit);
+/**
+ * @brief Flushes the data cache of a memory region.
+ * @param adr Address of the memory region.
+ * @param size Size of the memory region.
+ */
+Result CSND_FlushDataCache(const void* adr, u32 size);
+
+/**
+ * @brief Stores the data cache of a memory region.
+ * @param adr Address of the memory region.
+ * @param size Size of the memory region.
+ */
+Result CSND_StoreDataCache(const void* adr, u32 size);
+
+/**
+ * @brief Invalidates the data cache of a memory region.
+ * @param adr Address of the memory region.
+ * @param size Size of the memory region.
+ */
+Result CSND_InvalidateDataCache(const void* adr, u32 size);
+
/**
* @brief Resets CSND.
* Note: Currently breaks sound, don't use for now!
* @param channel Channel to use.
* @param duty Duty to set.
*/
-void CSND_SetDuty(u32 channel, u32 duty);
+void CSND_SetDuty(u32 channel, CSND_DutyCycle duty);
/**
* @brief Sets a channel's timer.
* @param capVolumes Capture volume data.
* @param duty Duty value to set.
*/
-void CSND_SetChnRegsPSG(u32 flags, u32 chnVolumes, u32 capVolumes, u32 duty);
+void CSND_SetChnRegsPSG(u32 flags, u32 chnVolumes, u32 capVolumes, CSND_DutyCycle duty);
/**
* @brief Sets CSND's noise channel registers.
* @param data0 First block of sound data.
* @param data1 Second block of sound data. This is the block that will be looped over.
* @param size Size of the sound data.
- *
+ *
* In this implementation if the loop mode is used, data1 must be in the range [data0 ; data0 + size]. Sound will be played once from data0 to data0 + size and then loop between data1 and data0+size.
*/
Result csndPlaySound(int chn, u32 flags, u32 sampleRate, float vol, float pan, void* data0, void* data1, u32 size);
// 0x00
u16 name[0x106]; ///< UTF-16 encoded name
// 0x20C
- u8 shortName[0x09]; ///< 8.3 File name
- // 0x215
- u8 unknown1; ///< ???
+ u8 shortName[0x0A]; ///< 8.3 File name
// 0x216
u8 shortExt[0x04]; ///< 8.3 File extension (set to spaces for directories)
// 0x21A
* @param path Path to use.
* @return The created FS_path instance.
*/
-FS_path FS_makePath(FS_pathType type, const char *path);
+FS_path fsMakePath(FS_pathType type, const char *path);
/**
* @brief Initializes FSUSER.
/**
- * @file gsp.h
- * @brief GSP service.
+ * @file gspgpu.h
+ * @brief GSPGPU service.
*/
#pragma once
-#define GSP_REBASE_REG(r) ((r)-0x1EB00000)
+#define GSPGPU_REBASE_REG(r) ((r)-0x1EB00000)
/// Framebuffer information.
typedef struct
u32 format; ///< Framebuffer format, this u16 is written to the low u16 for LCD register 0x1EF00X70.
u32 framebuf_dispselect; ///< Value for 0x1EF00X78, controls which framebuffer is displayed.
u32 unk; ///< Unknown.
-} GSP_FramebufferInfo;
+} GSPGPU_FramebufferInfo;
/// Framebuffer format.
typedef enum
GSP_RGB565_OES=2, ///< RGB565. (2 bytes)
GSP_RGB5_A1_OES=3, ///< RGB5A1. (2 bytes)
GSP_RGBA4_OES=4 ///< RGBA4. (2 bytes)
-}GSP_FramebufferFormats;
+} GSPGPU_FramebufferFormats;
/// Capture info entry.
typedef struct
u32 *framebuf1_vaddr; ///< Right framebuffer.
u32 format; ///< Framebuffer format.
u32 framebuf_widthbytesize; ///< Framebuffer pitch.
-} GSP_CaptureInfoEntry;
+} GSPGPU_CaptureInfoEntry;
/// Capture info.
typedef struct
{
- GSP_CaptureInfoEntry screencapture[2]; ///< Capture info entries, one for each screen.
-} GSP_CaptureInfo;
+ GSPGPU_CaptureInfoEntry screencapture[2]; ///< Capture info entries, one for each screen.
+} GSPGPU_CaptureInfo;
-/// GSP events.
+/// GSPGPU events.
typedef enum
{
- GSPEVENT_PSC0 = 0, ///< Memory fill completed.
- GSPEVENT_PSC1, ///< TODO
- GSPEVENT_VBlank0, ///< TODO
- GSPEVENT_VBlank1, ///< TODO
- GSPEVENT_PPF, ///< Display transfer finished.
- GSPEVENT_P3D, ///< Command list processing finished.
- GSPEVENT_DMA, ///< TODO
-
- GSPEVENT_MAX, ///< Used to know how many events there are.
-} GSP_Event;
-
-/// LCD screens.
-typedef enum
-{
- GSPLCD_TOP = BIT(0), ///< Top screen.
- GSPLCD_BOTTOM = BIT(1), ///< Bottom screen.
- GSPLCD_BOTH = GSPLCD_TOP | GSPLCD_BOTTOM, ///< Both screens.
-}GSPLCD_Screens;
-
-/// Initializes GSP.
+ GSPGPU_EVENT_PSC0 = 0, ///< Memory fill completed.
+ GSPGPU_EVENT_PSC1, ///< TODO
+ GSPGPU_EVENT_VBlank0, ///< TODO
+ GSPGPU_EVENT_VBlank1, ///< TODO
+ GSPGPU_EVENT_PPF, ///< Display transfer finished.
+ GSPGPU_EVENT_P3D, ///< Command list processing finished.
+ GSPGPU_EVENT_DMA, ///< TODO
+
+ GSPGPU_EVENT_MAX, ///< Used to know how many events there are.
+} GSPGPU_Event;
+
+/// Initializes GSPGPU.
Result gspInit(void);
-/// Exits GSP.
+/// Exits GSPGPU.
void gspExit(void);
-/// Initializes GSPLCD.
-Result gspLcdInit(void);
-
-/// Exits GSPLCD.
-void gspLcdExit(void);
-
/**
- * @brief Initializes the GSP event handler.
+ * @brief Initializes the GSPGPU event handler.
* @param gspEvent Event handle to use.
* @param gspSharedMem GSP shared memory.
* @param gspThreadId ID of the GSP thread.
*/
Result gspInitEventHandler(Handle gspEvent, vu8* gspSharedMem, u8 gspThreadId);
-/// Exits the GSP event handler.
+/// Exits the GSPGPU event handler.
void gspExitEventHandler(void);
/**
- * @brief Waits for a GSP event to occur.
+ * @brief Waits for a GSPGPU event to occur.
* @param id ID of the event.
* @param Whether to discard the current event and wait for the next event.
*/
-void gspWaitForEvent(GSP_Event id, bool nextEvent);
+void gspWaitForEvent(GSPGPU_Event id, bool nextEvent);
/// Waits for PSC0
-#define gspWaitForPSC0() gspWaitForEvent(GSPEVENT_PSC0, false)
+#define gspWaitForPSC0() gspWaitForEvent(GSPGPU_EVENT_PSC0, false)
/// Waits for PSC1
-#define gspWaitForPSC1() gspWaitForEvent(GSPEVENT_PSC1, false)
+#define gspWaitForPSC1() gspWaitForEvent(GSPGPU_EVENT_PSC1, false)
/// Waits for VBlank.
#define gspWaitForVBlank() gspWaitForVBlank0()
/// Waits for VBlank0.
-#define gspWaitForVBlank0() gspWaitForEvent(GSPEVENT_VBlank0, true)
+#define gspWaitForVBlank0() gspWaitForEvent(GSPGPU_EVENT_VBlank0, true)
/// Waits for VBlank1.
-#define gspWaitForVBlank1() gspWaitForEvent(GSPEVENT_VBlank1, true)
+#define gspWaitForVBlank1() gspWaitForEvent(GSPGPU_EVENT_VBlank1, true)
/// Waits for PPF.
-#define gspWaitForPPF() gspWaitForEvent(GSPEVENT_PPF, false)
+#define gspWaitForPPF() gspWaitForEvent(GSPGPU_EVENT_PPF, false)
/// Waits for P3D.
-#define gspWaitForP3D() gspWaitForEvent(GSPEVENT_P3D, false)
+#define gspWaitForP3D() gspWaitForEvent(GSPGPU_EVENT_P3D, false)
/// Waits for DMA.
-#define gspWaitForDMA() gspWaitForEvent(GSPEVENT_DMA, false)
+#define gspWaitForDMA() gspWaitForEvent(GSPGPU_EVENT_DMA, false)
+
+/**
+ * @brief Submits a GX command.
+ * @param sharedGspCmdBuf Command buffer to use.
+ * @param gxCommand GX command to execute.
+ */
+Result gspSubmitGxCommand(u32* sharedGspCmdBuf, u32 gxCommand[0x8]);
/**
* @brief Acquires GPU rights.
* @brief Retrieves display capture info.
* @param captureinfo Pointer to output capture info to.
*/
-Result GSPGPU_ImportDisplayCaptureInfo(GSP_CaptureInfo *captureinfo);
+Result GSPGPU_ImportDisplayCaptureInfo(GSPGPU_CaptureInfo*captureinfo);
/// Sames the VRAM sys area.
Result GSPGPU_SaveVramSysArea(void);
* @param screenid ID of the screen to update.
* @param framebufinfo Framebuffer information to update with.
*/
-Result GSPGPU_SetBufferSwap(u32 screenid, GSP_FramebufferInfo *framebufinfo);
+Result GSPGPU_SetBufferSwap(u32 screenid, GSPGPU_FramebufferInfo*framebufinfo);
/**
* @brief Flushes memory from the data cache.
/// Triggers a handling of commands written to shared memory.
Result GSPGPU_TriggerCmdReqQueue(void);
-/**
- * @brief Submits a GX command.
- * @param sharedGspCmdBuf Command buffer to use.
- * @param gxCommand GX command to execute.
- */
-Result GSPGPU_SubmitGxCommand(u32* sharedGspCmdBuf, u32 gxCommand[0x8]);
-
-/**
- * @brief Powers off the backlight.
- * @param screen Screen to power off.
- */
-Result GSPLCD_PowerOffBacklight(GSPLCD_Screens screen);
-
-/**
- * @brief Powers on the backlight.
- * @param screen Screen to power on.
- */
-Result GSPLCD_PowerOnBacklight(GSPLCD_Screens screen);
--- /dev/null
+/**
+ * @file gsplcd.h
+ * @brief GSPLCD service.
+ */
+#pragma once
+#include <3ds/gfx.h> // For gfxScreen_t
+
+/// LCD screens.
+enum
+{
+ GSPLCD_SCREEN_TOP = BIT(GFX_TOP), ///< Top screen.
+ GSPLCD_SCREEN_BOTTOM = BIT(GFX_BOTTOM), ///< Bottom screen.
+ GSPLCD_SCREEN_BOTH = GSPLCD_SCREEN_TOP | GSPLCD_SCREEN_BOTTOM, ///< Both screens.
+};
+
+/// Initializes GSPLCD.
+Result gspLcdInit(void);
+
+/// Exits GSPLCD.
+void gspLcdExit(void);
+
+/**
+ * @brief Powers on the backlight.
+ * @param screen Screen to power on.
+ */
+Result GSPLCD_PowerOnBacklight(u32 screen);
+
+/**
+ * @brief Powers off the backlight.
+ * @param screen Screen to power off.
+ */
+Result GSPLCD_PowerOffBacklight(u32 screen);
+
//See also: http://3dbrew.org/wiki/HID_Services http://3dbrew.org/wiki/HID_Shared_Memory
/// Key values.
-typedef enum
+enum
{
KEY_A = BIT(0), ///< A
KEY_B = BIT(1), ///< B
KEY_DOWN = KEY_DDOWN | KEY_CPAD_DOWN, ///< D-Pad Down or Circle Pad Down
KEY_LEFT = KEY_DLEFT | KEY_CPAD_LEFT, ///< D-Pad Left or Circle Pad Left
KEY_RIGHT = KEY_DRIGHT | KEY_CPAD_RIGHT, ///< D-Pad Right or Circle Pad Right
-} PAD_KEY;
+};
/// Touch position.
typedef struct
/// HTTP request status.
typedef enum {
- HTTPCREQSTAT_INPROGRESS_REQSENT = 0x5, ///< Request in progress.
- HTTPCREQSTAT_DLREADY = 0x7 ///< Download ready.
-} httpcReqStatus;
+ HTTPC_STATUS_REQUEST_IN_PROGRESS = 0x5, ///< Request in progress.
+ HTTPC_STATUS_DOWNLOAD_READY = 0x7 ///< Download ready.
+} HTTPC_RequestStatus;
/// Result code returned when a download is pending.
#define HTTPC_RESULTCODE_DOWNLOADPENDING 0xd840a02b
* @param context Context to use.
* @param out Pointer to output the HTTP request state to.
*/
-Result httpcGetRequestState(httpcContext *context, httpcReqStatus* out);
+Result httpcGetRequestState(httpcContext *context, HTTPC_RequestStatus* out);
/**
* @brief Gets the download size state of a HTTP context.
* @param contextHandle HTTP context handle to use.
* @param out Pointer to output the request state to.
*/
-Result HTTPC_GetRequestState(Handle handle, Handle contextHandle, httpcReqStatus* out);
+Result HTTPC_GetRequestState(Handle handle, Handle contextHandle, HTTPC_RequestStatus* out);
/**
* @brief Gets the download size state of a HTTP context.
* @param buf Buffer to receive data to.
* @param size Size of the buffer.
* @param flag Flags to receive data with.
- * @param transfercount Pointer to write the bytes read to.
+ * @param transfercount Pointer to output the number of bytes read to.
* @param wait Whether to wait for the data to be received.
*/
Result iruRecvData(u8 *buf, u32 size, u8 flag, u32 *transfercount, bool wait);
+/// Initializes the IR session.
+Result IRU_Initialize(void);
+
+/// Shuts down the IR session.
+Result IRU_Shutdown(void);
+
+/**
+ * @brief Begins sending data.
+ * @param buf Buffer to send.
+ * @param size Size of the buffer.
+ */
+Result IRU_StartSendTransfer(u8 *buf, u32 size);
+
+/// Waits for a send operation to complete.
+Result IRU_WaitSendTransfer(void);
+
+/**
+ * @brief Begins receiving data.
+ * @param size Size of the data to receive.
+ * @param flag Flags to use when receiving.
+ */
+Result IRU_StartRecvTransfer(u32 size, u8 flag);
+
+/**
+ * @brief Waits for a receive operation to complete.
+ * @param transfercount Pointer to output the number of bytes read to.
+ */
+Result IRU_WaitRecvTransfer(u32 *transfercount);
+
/**
* @brief Sets the IR bit rate.
* @param value Bit rate to set.
typedef enum {
MVDMODE_COLORFORMATCONV, ///< Converting color formats.
MVDMODE_VIDEOPROCESSING ///< Processing video.
-} mvdstdMode;
+} MVDSTD_Mode;
/// Input format.
typedef enum {
- MVDTYPEIN_YUYV422 = 0x00010001, ///< YUYV422
- MVDTYPEIN_H264 = 0x00020001 ///< H264
-} mvdstdTypeInput;
+ MVD_INPUT_YUYV422 = 0x00010001, ///< YUYV422
+ MVD_INPUT_H264 = 0x00020001 ///< H264
+} MVDSTD_InputFormat;
/// Output format.
typedef enum {
- MVDTYPEOUT_RGB565 = 0x00040002 ///< RGB565
-} mvdstdTypeOutput;
+ MVD_OUTPUT_RGB565 = 0x00040002 ///< RGB565
+} MVDSTD_OutputFormat;
/// Processing configuration.
typedef struct {
- mvdstdTypeInput input_type; ///< Input type.
+ MVDSTD_InputFormat input_type; ///< Input type.
u32 unk_x04; ///< Unknown.
u32 unk_x08; ///< Unknown.
u32 inwidth; ///< Input width.
u32 outheight0; ///< First output width. Only set for H.264.
u32 outwidth0; ///< First output height. Only set for H.264.
u32 unk_x54; ///< Unknown.
- mvdstdTypeOutput output_type; ///< Output type.
+ MVDSTD_OutputFormat output_type; ///< Output type.
u32 outwidth1; ///< Second output width.
u32 outheight1; ///< Second output height.
u32 physaddr_outdata0; ///< Physical address of output data.
u32 physaddr_outdata1_colorconv; ///< Physical address of color conversion output data.
u32 unk_x6c[0xb0>>2]; ///< Unknown.
-} mvdstdConfig;
-
-/**
- * @brief Generates a default MVDSTD configuration.
- * @param config Pointer to output the generated config to.
- * @param input_width Input width.
- * @param input_height Input height.
- * @param output_width Output width.
- * @param output_height Output height.
- * @param vaddr_colorconv_indata Virtual address of the color conversion input data.
- * @param vaddr_outdata0 Virtual address of the output data.
- * @param vaddr_outdata1_colorconv Virtual address of the color conversion output data.
- */
-void mvdstdGenerateDefaultConfig(mvdstdConfig *config, u32 input_width, u32 input_height, u32 output_width, u32 output_height, u32 *vaddr_colorconv_indata, u32 *vaddr_outdata0, u32 *vaddr_outdata1_colorconv);
+} MVDSTD_Config;
/**
* @brief Initializes MVDSTD. Video processing / H.264 currently isn't supported.
* @param output_type Type of output to produce.
* @param size Size of data to process. Not used when type == MVDTYPE_COLORFORMATCONV.
*/
-Result mvdstdInit(mvdstdMode mode, mvdstdTypeInput input_type, mvdstdTypeOutput output_type, u32 size);
+Result mvdstdInit(MVDSTD_Mode mode, MVDSTD_InputFormat input_type, MVDSTD_OutputFormat output_type, u32 size);
/// Shuts down MVDSTD.
void mvdstdExit(void);
/**
- * @brief Sets the current configuration of MVDSTD.
- * @param config Pointer to the configuration to set.
+ * @brief Generates a default MVDSTD configuration.
+ * @param config Pointer to output the generated config to.
+ * @param input_width Input width.
+ * @param input_height Input height.
+ * @param output_width Output width.
+ * @param output_height Output height.
+ * @param vaddr_colorconv_indata Virtual address of the color conversion input data.
+ * @param vaddr_outdata0 Virtual address of the output data.
+ * @param vaddr_outdata1_colorconv Virtual address of the color conversion output data.
*/
-Result mvdstdSetConfig(mvdstdConfig *config);
+void mvdstdGenerateDefaultConfig(MVDSTD_Config*config, u32 input_width, u32 input_height, u32 output_width, u32 output_height, u32 *vaddr_colorconv_indata, u32 *vaddr_outdata0, u32 *vaddr_outdata1_colorconv);
/**
* @brief Processes a frame.
* @param h264_inframesize Size of the input frame.
* @param h264_frameid ID of the input frame.
*/
-Result mvdstdProcessFrame(mvdstdConfig *config, u32 *h264_vaddr_inframe, u32 h264_inframesize, u32 h264_frameid);
+Result mvdstdProcessFrame(MVDSTD_Config*config, u32 *h264_vaddr_inframe, u32 h264_inframesize, u32 h264_frameid);
+
+/**
+ * @brief Sets the current configuration of MVDSTD.
+ * @param config Pointer to the configuration to set.
+ */
+Result MVDSTD_SetConfig(MVDSTD_Config* config);
/// PS AES algorithms.
typedef enum
{
- ps_CBC_ENC, ///< CBC encoding.
- ps_CBC_DEC, ///< CBC decoding.
- ps_CTR_ENC, ///< CTR encoding.
- ps_CTR_DEC, ///< CTR decoding.
- ps_CCM_ENC, ///< CCM encoding.
- ps_CCM_DEC, ///< CCM decoding.
-} ps_aes_algo;
+ PS_ALGORITHM_CBC_ENC, ///< CBC encoding.
+ PS_ALGORITHM_CBC_DEC, ///< CBC decoding.
+ PS_ALGORITHM_CTR_ENC, ///< CTR encoding.
+ PS_ALGORITHM_CTR_DEC, ///< CTR decoding.
+ PS_ALGORITHM_CCM_ENC, ///< CCM encoding.
+ PS_ALGORITHM_CCM_DEC, ///< CCM decoding.
+} PS_AESAlgorithm;
/// PS key slots.
typedef enum
{
- ps_KEYSLOT_0D, ///< Key slot 0x0D.
- ps_KEYSLOT_2D, ///< Key slot 0x2D.
- ps_KEYSLOT_31, ///< Key slot 0x31.
- ps_KEYSLOT_38, ///< Key slot 0x38.
- ps_KEYSLOT_32, ///< Key slot 0x32.
- ps_KEYSLOT_39_DLP, ///< Key slot 0x39. (DLP)
- ps_KEYSLOT_2E, ///< Key slot 0x2E.
- ps_KEYSLOT_INVALID, ///< Invalid key slot.
- ps_KEYSLOT_36, ///< Key slot 0x36.
- ps_KEYSLOT_39_NFC ///< Key slot 0x39. (NFC)
-} ps_aes_keytypes;
+ PS_KEYSLOT_0D, ///< Key slot 0x0D.
+ PS_KEYSLOT_2D, ///< Key slot 0x2D.
+ PS_KEYSLOT_31, ///< Key slot 0x31.
+ PS_KEYSLOT_38, ///< Key slot 0x38.
+ PS_KEYSLOT_32, ///< Key slot 0x32.
+ PS_KEYSLOT_39_DLP, ///< Key slot 0x39. (DLP)
+ PS_KEYSLOT_2E, ///< Key slot 0x2E.
+ PS_KEYSLOT_INVALID, ///< Invalid key slot.
+ PS_KEYSLOT_36, ///< Key slot 0x36.
+ PS_KEYSLOT_39_NFC ///< Key slot 0x39. (NFC)
+} PS_AESKeyType;
/// Initializes PS.
Result psInit(void);
* @param key_type Key type to use.
* @param iv Pointer to the CTR/IV.
*/
-Result PS_EncryptDecryptAes(u32 size, u8* in, u8* out, u32 aes_algo, u32 key_type, u8* iv);
+Result PS_EncryptDecryptAes(u32 size, u8* in, u8* out, PS_AESAlgorithm aes_algo, PS_AESKeyType key_type, u8* iv);
/**
* @brief Encrypts/Decrypts signed AES CCM data.
* @param key_type Key type to use.
* @param nonce Pointer to the nonce.
*/
-Result PS_EncryptSignDecryptVerifyAesCcm(u8* in, u32 in_size, u8* out, u32 out_size, u32 data_len, u32 mac_data_len, u32 mac_len, u32 aes_algo, u32 key_type, u8* nonce);
+Result PS_EncryptSignDecryptVerifyAesCcm(u8* in, u32 in_size, u8* out, u32 out_size, u32 data_len, u32 mac_data_len, u32 mac_len, PS_AESAlgorithm aes_algo, PS_AESKeyType key_type, u8* nonce);
/**
* @brief Gets the 64-bit console friend code seed.
--- /dev/null
+/**
+ * @file ptmsysm.h
+ * @brief PTMSYSM service.
+ */
+#pragma once
+
+/// Initializes ptm:sysm.
+Result ptmSysmInit(void);
+
+/// Exits ptm:sysm.
+void ptmSysmExit(void);
+
+/**
+ * @brief Configures the New 3DS' CPU clock speed and L2 cache.
+ * @param value Bit0: enable higher clock, Bit1: enable L2 cache.
+ */
+Result PTMSYSM_ConfigureNew3DSCPU(u8 value);
+
/**
- * @file ptm.h
- * @brief PTM service.
+ * @file ptmu.h
+ * @brief PTMU service.
*/
#pragma once
-/// Initializes PTM.
-Result ptmInit(void);
+/// Initializes PTMU.
+Result ptmuInit(void);
-/// Exits PTM.
-void ptmExit(void);
-
-/// Initializes ptm:sysm.
-Result ptmSysmInit(void);
-
-/// Exits ptm:sysm.
-void ptmSysmExit(void);
+/// Exits PTMU.
+void ptmuExit(void);
/**
* @brief Gets the system's current shell state.
*/
Result PTMU_GetTotalStepCount(u32 *steps);
-/**
- * @brief Configures the New 3DS' CPU clock speed and L2 cache.
- * @param value Bit0: enable higher clock, Bit1: enable L2 cache.
- */
-Result PTMSYSM_ConfigureNew3DSCPU(u8 value);
typedef struct {
float x; ///< X coordinate.
float y; ///< Y coordinate.
-} qtmHeadtrackingInfoCoord;
+} QTM_HeadTrackingInfoCoord;
/// Head tracking info.
typedef struct {
u8 flags[5]; ///< Flags.
u8 padding[3]; ///< Padding.
float floatdata_x08; ///< Unknown. Not used by System_Settings.
- qtmHeadtrackingInfoCoord coords0[4]; ///< Head coordinates.
+ QTM_HeadTrackingInfoCoord coords0[4]; ///< Head coordinates.
u32 unk_x2c[5]; ///< Unknown. Not used by System_Settings.
-} qtmHeadtrackingInfo;
+} QTM_HeadTrackingInfo;
/// Initializes QTM.
Result qtmInit(void);
*/
bool qtmCheckInitialized(void);
-/**
- * @brief Gets the current head tracking info.
- * @param val Normally 0.
- * @param out Pointer to write head tracking info to.
- */
-Result qtmGetHeadtrackingInfo(u64 val, qtmHeadtrackingInfo *out);
-
/**
* @brief Checks whether a head is fully detected.
* @param info Tracking info to check.
*/
-bool qtmCheckHeadFullyDetected(qtmHeadtrackingInfo *info);
+bool qtmCheckHeadFullyDetected(QTM_HeadTrackingInfo *info);
/**
* @brief Converts QTM coordinates to screen coordinates.
* @param x Pointer to output the screen X coordinate to.
* @param y Pointer to output the screen Y coordinate to.
*/
-Result qtmConvertCoordToScreen(qtmHeadtrackingInfoCoord *coord, float *screen_width, float *screen_height, u32 *x, u32 *y);
+Result qtmConvertCoordToScreen(QTM_HeadTrackingInfoCoord *coord, float *screen_width, float *screen_height, u32 *x, u32 *y);
+/**
+ * @brief Gets the current head tracking info.
+ * @param val Normally 0.
+ * @param out Pointer to write head tracking info to.
+ */
+Result QTM_GetHeadTrackingInfo(u64 val, QTM_HeadTrackingInfo* out);
* @param context_size Size of the buffer, a multiple of 0x1000.
* @note The specified context buffer can no longer be accessed by the process which called this function, since the userland permissions for this block are set to no-access.
*/
-Result SOC_Initialize(u32 *context_addr, u32 context_size);
+Result socInit(u32 *context_addr, u32 context_size);
/**
* @brief Closes the soc service.
* @note You need to call this in order to be able to use the buffer again.
*/
-Result SOC_Shutdown(void);
+Result socExit(void);
// this is supposed to be in unistd.h but newlib only puts it for cygwin
/**
--- /dev/null
+/**
+ * @file srvpm.h
+ * @brief srv:pm service.
+ */
+#pragma once
+
+/// Initializes srv:pm.
+Result srvPmInit(void);
+
+/// Exits srv:pm.
+void srvPmExit(void);
+
+/**
+ * @brief Publishes a notification to a process.
+ * @param notificationId ID of the notification.
+ * @param process Process to publish to.
+ */
+Result SRVPM_PublishToProcess(u32 notificationId, Handle process);
+
+/**
+ * @brief Publishes a notification to all processes.
+ * @param notificationId ID of the notification.
+ */
+Result SRVPM_PublishToAll(u32 notificationId);
+
+/**
+ * @brief Registers a process with SRV.
+ * @param procid ID of the process.
+ * @param count Number of services within the service access control data.
+ * @param serviceaccesscontrol Service Access Control list.
+ */
+Result SRVPM_RegisterProcess(u32 procid, u32 count, void* serviceaccesscontrol);
+
+/**
+ * @brief Unregisters a process with SRV.
+ * @param procid ID of the process.
+ */
+Result SRVPM_UnregisterProcess(u32 procid);
+
INPUT_YUV422_INDIV_16 = 0x2, ///< 16-bit per component, planar YUV 4:2:2, 32bpp, (1 Cr & Cb sample per 2x1 Y samples).\n Usually named YUV422P16.
INPUT_YUV420_INDIV_16 = 0x3, ///< 16-bit per component, planar YUV 4:2:0, 24bpp, (1 Cr & Cb sample per 2x2 Y samples).\n Usually named YUV420P16.
INPUT_YUV422_BATCH = 0x4, ///< 8-bit per component, packed YUV 4:2:2, 16bpp, (Y0 Cb Y1 Cr).\n Usually named YUYV422.
-} Y2R_InputFormat;
+} Y2RU_InputFormat;
/**
* @brief Output color formats
OUTPUT_RGB_24 = 0x1,
OUTPUT_RGB_16_555 = 0x2, ///< The alpha bit is the 7th bit of the alpha value set by @ref Y2RU_SetAlpha
OUTPUT_RGB_16_565 = 0x3,
-} Y2R_OutputFormat;
+} Y2RU_OutputFormat;
/**
* @brief Rotation to be applied to the output
ROTATION_CLOCKWISE_90 = 0x1,
ROTATION_CLOCKWISE_180 = 0x2,
ROTATION_CLOCKWISE_270 = 0x3,
-} Y2R_Rotation;
+} Y2RU_Rotation;
/**
* @brief Block alignment of output
{
BLOCK_LINE = 0x0, ///< The result buffer will be laid out in linear format, the usual way.
BLOCK_8_BY_8 = 0x1, ///< The result will be stored as 8x8 blocks in Z-order.\n Useful for textures since it is the format used by the PICA200.
-} Y2R_BlockAlignment;
+} Y2RU_BlockAlignment;
/**
* @brief Coefficients of the YUV->RGB conversion formula.
u16 r_offset;
u16 g_offset;
u16 b_offset;
-} Y2R_ColorCoefficients;
+} Y2RU_ColorCoefficients;
/**
* @brief Preset conversion coefficients based on ITU standards for the YUV->RGB formula.
*
- * For more details refer to @ref Y2R_ColorCoefficients
+ * For more details refer to @ref Y2RU_ColorCoefficients
*/
typedef enum
{
COEFFICIENT_ITU_R_BT_709 = 0x1, ///< Coefficients from the ITU-R BT.709 standard with PC ranges.
COEFFICIENT_ITU_R_BT_601_SCALING = 0x2, ///< Coefficients from the ITU-R BT.601 standard with TV ranges.
COEFFICIENT_ITU_R_BT_709_SCALING = 0x3, ///< Coefficients from the ITU-R BT.709 standard with TV ranges.
-} Y2R_StandardCoefficient;
+} Y2RU_StandardCoefficient;
/**
* @brief Structure used to configure all parameters at once.
*/
typedef struct
{
- Y2R_InputFormat input_format : 8; ///< Value passed to @ref Y2RU_SetInputFormat
- Y2R_OutputFormat output_format : 8; ///< Value passed to @ref Y2RU_SetOutputFormat
- Y2R_Rotation rotation : 8; ///< Value passed to @ref Y2RU_SetRotation
- Y2R_BlockAlignment block_alignment : 8; ///< Value passed to @ref Y2RU_SetBlockAlignment
+ Y2RU_InputFormat input_format : 8; ///< Value passed to @ref Y2RU_SetInputFormat
+ Y2RU_OutputFormat output_format : 8; ///< Value passed to @ref Y2RU_SetOutputFormat
+ Y2RU_Rotation rotation : 8; ///< Value passed to @ref Y2RU_SetRotation
+ Y2RU_BlockAlignment block_alignment : 8; ///< Value passed to @ref Y2RU_SetBlockAlignment
s16 input_line_width; ///< Value passed to @ref Y2RU_SetInputLineWidth
s16 input_lines; ///< Value passed to @ref Y2RU_SetInputLines
- Y2R_StandardCoefficient standard_coefficient : 8; ///< Value passed to @ref Y2RU_SetStandardCoefficient
+ Y2RU_StandardCoefficient standard_coefficient : 8; ///< Value passed to @ref Y2RU_SetStandardCoefficient
u8 unused;
u16 alpha; ///< Value passed to @ref Y2RU_SetAlpha
-} Y2R_ConversionParams;
+} Y2RU_ConversionParams;
/**
* @brief Dithering weights
u16 w3_xOdd_yEven;
u16 w3_xEven_yOdd;
u16 w3_xOdd_yOdd;
-} Y2R_DitheringWeightParams;
-
-
+} Y2RU_DitheringWeightParams;
/**
* @brief Initializes the y2r service.
*/
Result y2rInit(void);
-
/**
* @brief Closes the y2r service.
*
*/
void y2rExit(void);
-
/**
* @brief Used to configure the input format.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetInputFormat(Y2R_InputFormat format);
+Result Y2RU_SetInputFormat(Y2RU_InputFormat format);
-Result Y2RU_GetInputFormat(Y2R_InputFormat* format);
+Result Y2RU_GetInputFormat(Y2RU_InputFormat* format);
/**
* @brief Used to configure the output format.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetOutputFormat(Y2R_OutputFormat format);
+Result Y2RU_SetOutputFormat(Y2RU_OutputFormat format);
-Result Y2RU_GetOutputFormat(Y2R_OutputFormat* format);
+Result Y2RU_GetOutputFormat(Y2RU_OutputFormat* format);
/**
* @brief Used to configure the rotation of the output.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetRotation(Y2R_Rotation rotation);
+Result Y2RU_SetRotation(Y2RU_Rotation rotation);
-Result Y2RU_GetRotation(Y2R_Rotation* rotation);
+Result Y2RU_GetRotation(Y2RU_Rotation* rotation);
/**
* @brief Used to configure the alignment of the output buffer.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetBlockAlignment(Y2R_BlockAlignment alignment);
+Result Y2RU_SetBlockAlignment(Y2RU_BlockAlignment alignment);
-Result Y2RU_GetBlockAlignment(Y2R_BlockAlignment* alignment);
+Result Y2RU_GetBlockAlignment(Y2RU_BlockAlignment* alignment);
///Sets the usage of spacial dithering
Result Y2RU_SetSpacialDithering(bool enable);
/**
* @brief Used to configure the color conversion formula.
*
- * See @ref Y2R_ColorCoefficients for more information about the coefficients.
+ * See @ref Y2RU_ColorCoefficients for more information about the coefficients.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetCoefficients(const Y2R_ColorCoefficients* coefficients);
+Result Y2RU_SetCoefficients(const Y2RU_ColorCoefficients* coefficients);
-Result Y2RU_GetCoefficients(Y2R_ColorCoefficients* coefficients);
+Result Y2RU_GetCoefficients(Y2RU_ColorCoefficients* coefficients);
/**
* @brief Used to configure the color conversion formula with ITU stantards coefficients.
*
- * See @ref Y2R_ColorCoefficients for more information about the coefficients.
+ * See @ref Y2RU_ColorCoefficients for more information about the coefficients.
*
* @note Prefer using @ref Y2RU_SetConversionParams if you have to set multiple parameters.
*/
-Result Y2RU_SetStandardCoefficient(Y2R_StandardCoefficient coefficient);
+Result Y2RU_SetStandardCoefficient(Y2RU_StandardCoefficient coefficient);
///Retrieves the coeeficients associated to the given standard
-Result Y2RU_GetStandardCoefficient(Y2R_ColorCoefficients* coefficients, Y2R_StandardCoefficient standardCoeff);
+Result Y2RU_GetStandardCoefficient(Y2RU_ColorCoefficients* coefficients, Y2RU_StandardCoefficient standardCoeff);
/**
* @brief Used to configure the alpha value of the output.
Result Y2RU_IsDoneReceiving(bool* is_done);
/// Sets the dithering weights
-Result Y2RU_SetDitheringWeightParams(const Y2R_DitheringWeightParams* params);
+Result Y2RU_SetDitheringWeightParams(const Y2RU_DitheringWeightParams* params);
/// Retrieves the dithering weights
-Result Y2RU_GetDitheringWeightParams(Y2R_DitheringWeightParams* params);
+Result Y2RU_GetDitheringWeightParams(Y2RU_DitheringWeightParams* params);
/**
- * @brief Sets all the parameters of Y2R_ConversionParams at once.
+ * @brief Sets all the parameters of Y2RU_ConversionParams at once.
*
* Faster than calling the individual value through Y2R_Set* because only one system call is made.
*/
-Result Y2RU_SetConversionParams(const Y2R_ConversionParams* params);
+Result Y2RU_SetConversionParams(const Y2RU_ConversionParams* params);
/// Starts the conversion process
Result Y2RU_StartConversion(void);
*/
Handle *srvGetSessionHandle(void);
-/// Registers the current process as a client to the service API.
-Result srvRegisterClient(void);
-
/**
- * @brief Retrieves a service handle, bypassing the handle list.
+ * @brief Retrieves a service handle, retrieving from the launcher handle list if possible.
* @param out Pointer to write the handle to.
* @param name Name of the service.
*/
-Result srvGetServiceHandleDirect(Handle* out, const char* name);
+Result srvGetServiceHandle(Handle* out, const char* name);
+
+/// Registers the current process as a client to the service API.
+Result srvRegisterClient(void);
/**
- * @brief Retrieves a service handle.
- * @param out Pointer to write the handle to.
- * @param name Name of the service.
+ * @brief Enables service notificatios, returning a notification semaphore.
+ * @param semaphoreOut Pointer to output the notification semaphore to.
*/
-Result srvGetServiceHandle(Handle* out, const char* name);
+Result srvEnableNotification(Handle* semaphoreOut);
/**
* @brief Registers the current process as a service.
*/
Result srvUnregisterService(const char* name);
-/// Initializes the srv:pm port.
-Result srvPmInit(void);
+/**
+ * @brief Retrieves a service handle.
+ * @param out Pointer to output the handle to.
+ * @param name Name of the service.
+ */
+Result srvGetServiceHandleDirect(Handle* out, const char* name);
+
+/**
+ * @brief Registers a port.
+ * @param name Name of the port.
+ * @param clientHandle Client handle of the port.
+ */
+Result srvRegisterPort(const char* name, Handle clientHandle);
+
+/**
+ * @brief Unregisters a port.
+ * @param name Name of the port.
+ */
+Result srvUnregisterPort(const char* name);
+
+/**
+ * @brief Retrieves a port handle.
+ * @param out Pointer to output the handle to.
+ * @param name Name of the port.
+ */
+Result srvGetPort(Handle* out, const char* name);
+
+/**
+ * @brief Subscribes to a notification.
+ * @param notificationId ID of the notification.
+ */
+Result srvSubscribe(u32 notificationId);
+
+/**
+ * @brief Unsubscribes from a notification.
+ * @param notificationId ID of the notification.
+ */
+Result srvUnsubscribe(u32 notificationId);
+
+/**
+ * @brief Receives a notification.
+ * @param notificationIdOut Pointer to output the ID of the received notification to.
+ */
+Result srvReceiveNotification(u32* notificationIdOut);
+
+/**
+ * @brief Publishes a notification to subscribers.
+ * @param notificationId ID of the notification.
+ * @param flags Flags to publish with. (bit 0 = only fire if not fired, bit 1 = report errors)
+ */
+Result srvPublishToSubscriber(u32 notificationId, u32 flags);
/**
- * @brief Registers a process with srv:pm.
- * @param procid ID of the process to register.
- * @param count Number of services to register access to.
- * @param serviceaccesscontrol Service access permissions of the process.
+ * @brief Publishes a notification to subscribers and retrieves a list of all processes that were notified.
+ * @param processIdCountOut Pointer to output the number of process IDs to.
+ * @param processIdsOut Pointer to output the process IDs to. Should have size "60 * sizeof(u32)".
+ * @param notificationId ID of the notification.
*/
-Result srvRegisterProcess(u32 procid, u32 count, void *serviceaccesscontrol);
+Result srvPublishAndGetSubscriber(u32* processIdCountOut, u32* processIdsOut, u32 notificationId);
/**
- * @brief Unregisters a process with srv:pm.
- * @param procid ID of the process to unregister.
+ * @brief Checks whether a service is registered.
+ * @param registeredOut Pointer to output the registration status to.
+ * @param name Name of the service to check.
*/
-Result srvUnregisterProcess(u32 procid);
+Result srvIsServiceRegistered(bool* registeredOut, const char* name);
extern "C"
{
#include <3ds/types.h>
- #include <3ds/linear.h>
+ #include <3ds/allocator/linear.h>
#include <3ds/util/rbtree.h>
}
extern "C"
{
#include <3ds/types.h>
- #include <3ds/mappable.h>
+ #include <3ds/allocator/mappable.h>
#include <3ds/util/rbtree.h>
}
extern "C"
{
#include <3ds/types.h>
- #include <3ds/vram.h>
+ #include <3ds/allocator/vram.h>
#include <3ds/util/rbtree.h>
}
#include <stdlib.h>
#include <stdio.h>
-#include <string.h>
#include <3ds/types.h>
#include <3ds/gfx.h>
#include <3ds/svc.h>
-#include <3ds/linear.h>
-#include <3ds/mappable.h>
-#include <3ds/vram.h>
+#include <3ds/allocator/linear.h>
+#include <3ds/allocator/mappable.h>
+#include <3ds/allocator/vram.h>
#include <3ds/gpu/gx.h>
-GSP_FramebufferInfo topFramebufferInfo, bottomFramebufferInfo;
+GSPGPU_FramebufferInfo topFramebufferInfo, bottomFramebufferInfo;
u8 gfxThreadID;
u8* gfxSharedMemory;
Handle gspEvent, gspSharedMemHandle;
-static GSP_FramebufferFormats topFormat = GSP_BGR8_OES;
-static GSP_FramebufferFormats botFormat = GSP_BGR8_OES;
+static GSPGPU_FramebufferFormats topFormat = GSP_BGR8_OES;
+static GSPGPU_FramebufferFormats botFormat = GSP_BGR8_OES;
void gfxSet3D(bool enable)
{
enable3d=enable;
}
-void gfxSetScreenFormat(gfxScreen_t screen, GSP_FramebufferFormats format) {
+void gfxSetScreenFormat(gfxScreen_t screen, GSPGPU_FramebufferFormats format) {
if(screen==GFX_TOP)
topFormat = format;
else
botFormat = format;
}
-GSP_FramebufferFormats gfxGetScreenFormat(gfxScreen_t screen) {
+GSPGPU_FramebufferFormats gfxGetScreenFormat(gfxScreen_t screen) {
if(screen==GFX_TOP)
return topFormat;
else
doubleBuf[screen] = doubleBuffering ? 1 : 0; // make sure they're the integer values '1' and '0'
}
-static u32 __get_bytes_per_pixel(GSP_FramebufferFormats format) {
+static u32 __get_bytes_per_pixel(GSPGPU_FramebufferFormats format) {
switch(format) {
case GSP_RGBA8_OES:
return 4;
{
u8* framebufferInfoHeader=gfxSharedMemory+0x200+gfxThreadID*0x80;
if(screen==GFX_BOTTOM)framebufferInfoHeader+=0x40;
- GSP_FramebufferInfo* framebufferInfo=(GSP_FramebufferInfo*)&framebufferInfoHeader[0x4];
+ GSPGPU_FramebufferInfo* framebufferInfo=(GSPGPU_FramebufferInfo*)&framebufferInfoHeader[0x4];
framebufferInfoHeader[0x0]^=doubleBuf[screen];
framebufferInfo[framebufferInfoHeader[0x0]]=(screen==GFX_TOP)?(topFramebufferInfo):(bottomFramebufferInfo);
framebufferInfoHeader[0x1]=1;
static void (*screenFree)(void *) = NULL;
-void gfxInit(GSP_FramebufferFormats topFormat, GSP_FramebufferFormats bottomFormat, bool vrambuffers)
+void gfxInit(GSPGPU_FramebufferFormats topFormat, GSPGPU_FramebufferFormats bottomFormat, bool vrambuffers)
{
void *(*screenAlloc)(size_t);
currentBuffer[1]=0;
// Initialize event handler and wait for VBlank
- gspInitEventHandler(gspEvent, (vu8*)gfxSharedMemory, gfxThreadID);
+ gspInitEventHandler(gspEvent, (vu8*) gfxSharedMemory, gfxThreadID);
gspWaitForVBlank();
GSPGPU_SetLcdForceBlack(0x0);
#include <3ds/svc.h>
#include <3ds/srv.h>
#include <3ds/gpu/gx.h>
-#include <3ds/services/gsp.h>
+#include <3ds/services/gspgpu.h>
u32* gxCmdBuf;
gxCommand[3]=length; //size
gxCommand[4]=gxCommand[5]=gxCommand[6]=gxCommand[7]=0x0;
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
Result GX_ProcessCommandList(u32* buf0a, u32 buf0s, u8 flags)
gxCommand[4]=gxCommand[5]=gxCommand[6]=0x0;
gxCommand[7]=(flags>>1)&1; //when non-zero, call svcFlushProcessDataCache() with the specified buffer
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
Result GX_MemoryFill(u32* buf0a, u32 buf0v, u32* buf0e, u16 control0, u32* buf1a, u32 buf1v, u32* buf1e, u16 control1)
gxCommand[6]=(u32)buf1e; //buf1 end addr
gxCommand[7]=(control0)|(control1<<16);
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
// Flags, for applications this is 0x1001000 for the main screen, and 0x1000 for the sub screen.
gxCommand[5]=flags;
gxCommand[6]=gxCommand[7]=0x0;
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
Result GX_TextureCopy(u32* inadr, u32 indim, u32* outadr, u32 outdim, u32 size, u32 flags)
gxCommand[6]=flags;
gxCommand[7]=0x0;
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
Result GX_FlushCacheRegions(u32* buf0a, u32 buf0s, u32* buf1a, u32 buf1s, u32* buf2a, u32 buf2s)
gxCommand[6]=(u32)buf2s; //buf2 size
gxCommand[7]=0x0;
- return GSPGPU_SubmitGxCommand(gxCmdBuf, gxCommand);
+ return gspSubmitGxCommand(gxCmdBuf, gxCommand);
}
ndspChn[id].format = format;
}
-void ndspChnSetInterp(int id, int type)
+void ndspChnSetInterp(int id, ndspInterpType type)
{
ndspChnSt* chn = &ndspChn[id];
LightLock_Lock(&chn->lock);
LightLock_Unlock(&ndspMutex);
}
-static void ndspAptHook(int hook, void* param)
+static void ndspAptHook(APT_HookType hook, void* param)
{
switch (hook)
{
bSleeping = true;
ndspFinalize(true);
break;
+
+ default:
+ break;
}
}
LightLock_Unlock(&ndspMaster.lock);
}
-void ndspSetOutputMode(int mode)
+void ndspSetOutputMode(ndspOutputMode mode)
{
LightLock_Lock(&ndspMaster.lock);
ndspMaster.outputMode = mode;
LightLock_Unlock(&ndspMaster.lock);
}
-void ndspSetClippingMode(int mode)
+void ndspSetClippingMode(ndspClippingMode mode)
{
LightLock_Lock(&ndspMaster.lock);
ndspMaster.clippingMode = mode;
LightLock_Unlock(&ndspMaster.lock);
}
-void ndspSurroundSetPos(u16 pos)
+void ndspSurroundSetPos(ndspSpeakerPos pos)
{
LightLock_Lock(&ndspMaster.lock);
ndspMaster.surround.pos = pos;
#include <3ds/result.h>
#include <3ds/os.h>
#include <3ds/svc.h>
-#include <3ds/services/ptm.h>
+#include <3ds/services/ptmsysm.h>
#include <sys/time.h>
#include <reent.h>
svcCloseHandle(acHandle);
}
-// ptr=0x200-byte outbuf
-Result ACU_CreateDefaultConfig(u32 *ptr)
+Result acWaitInternetConnection(void)
{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
- u32 *staticbufs = getThreadStaticBuffers();
-
- u32 savedValue0 = staticbufs[0];
- u32 savedValue1 = staticbufs[1];
-
- cmdbuf[0] = IPC_MakeHeader(0x1,0,0); // 0x00010000
- staticbufs[0] = IPC_Desc_StaticBuffer(0x200,0);
- staticbufs[1] = (u32)ptr;
-
- if(R_FAILED(ret = svcSendSyncRequest(acHandle)))return ret;
-
- staticbufs[0] = savedValue0;
- staticbufs[1] = savedValue1;
-
- return (Result)cmdbuf[1];
-}
-
-// Unknown what this cmd does at the time of writing. (ptr=0x200-byte inbuf/outbuf)
-Result ACU_cmd26(u32 *ptr, u8 val)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
- u32 *staticbufs = getThreadStaticBuffers();
-
- u32 savedValue0 = staticbufs[0];
- u32 savedValue1 = staticbufs[1];
-
- cmdbuf[0] = IPC_MakeHeader(0x26,1,2); // 0x00260042
- cmdbuf[1] = (u32)val;
- staticbufs[0] = IPC_Desc_StaticBuffer(0x200,0);
- staticbufs[1] = (u32)ptr;
- cmdbuf[2] = IPC_Desc_StaticBuffer(0x200,0);
- cmdbuf[3] = (u32)ptr;
-
- if(R_FAILED(ret = svcSendSyncRequest(acHandle)))return ret;
-
- staticbufs[0] = savedValue0;
- staticbufs[1] = savedValue1;
-
- return (Result)cmdbuf[1];
+ Result ret = 0;
+ u32 status = 0;
+ while(R_SUCCEEDED(ret = ACU_GetWifiStatus(&status)) && status == 0);
+ return ret;
}
Result ACU_GetWifiStatus(u32 *out)
return (Result)cmdbuf[1];
}
-
-Result ACU_WaitInternetConnection(void)
-{
- Result ret=0;
- u32 outval=0;
-
- if(R_FAILED(ret = acInit()))return ret;
-
- while(1)
- {
- ret = ACU_GetWifiStatus(&outval);
- if(R_SUCCEEDED(ret) && outval!=0)break;
- }
-
- acExit();
-
- return ret;
-}
#include <3ds/srv.h>
#include <3ds/synchronization.h>
#include <3ds/services/apt.h>
-#include <3ds/services/gsp.h>
+#include <3ds/services/gspgpu.h>
#include <3ds/ipc.h>
LightLock aptStatusMutex;
Handle aptStatusEvent;
-APP_STATUS aptStatus = APP_NOTINITIALIZED;
-APP_STATUS aptStatusBeforeSleep = APP_NOTINITIALIZED;
+APT_AppStatus aptStatus = APP_NOTINITIALIZED;
+APT_AppStatus aptStatusBeforeSleep = APP_NOTINITIALIZED;
u32 aptStatusPower;
Handle aptSleepSync;
static aptHookCookie aptFirstHook;
-static void aptCallHook(int hookType)
+static void aptCallHook(APT_HookType hookType)
{
aptHookCookie* c;
for (c = &aptFirstHook; c && c->callback; c = c->next)
{
u32 tmp=0;
u32 main_pixsz, sub_pixsz;
- GSP_CaptureInfo gspcapinfo;
+ GSPGPU_CaptureInfo gspcapinfo;
- memset(&gspcapinfo, 0, sizeof(GSP_CaptureInfo));
+ memset(&gspcapinfo, 0, sizeof(GSPGPU_CaptureInfo));
// Get display-capture info from GSP.
GSPGPU_ImportDisplayCaptureInfo(&gspcapinfo);
}
static void __handle_notification(void) {
- u8 type;
+ APT_Signal type;
Result ret=0;
// Get notification type.
aptSetStatus(aptStatusBeforeSleep);
}
break;
+
+ default:
+ break;
}
}
}
}
-APP_STATUS aptGetStatus(void)
+APT_AppStatus aptGetStatus(void)
{
- APP_STATUS ret;
+ APT_AppStatus ret;
LightLock_Lock(&aptStatusMutex);
ret = aptStatus;
LightLock_Unlock(&aptStatusMutex);
return ret;
}
-void aptSetStatus(APP_STATUS status)
+void aptSetStatus(APT_AppStatus status)
{
LightLock_Lock(&aptStatusMutex);
return cmdbuf[1];
}
-Result APT_InquireNotification(u32 appID, u8* signalType)
+Result APT_InquireNotification(u32 appID, APT_Signal* signalType)
{
u32* cmdbuf=getThreadCommandBuffer();
cmdbuf[0]=IPC_MakeHeader(0xB,1,0); // 0xB0040
if(out)
{
*out = 0;
- if(ret==0)*out=cmdbuf[2];
+ if(ret==0)*out=cmdbuf[2] & 0xFF;
}
return ret;
if(out)
{
*out = 0;
- if(ret==0)*out=cmdbuf[2];
+ if(ret==0)*out=cmdbuf[2] & 0xFF;
}
return ret;
#include <3ds/synchronization.h>
#include <3ds/types.h>
#include <3ds/result.h>
+#include <3ds/ipc.h>
Handle camHandle;
static int camRefCount;
svcCloseHandle(camHandle);
}
-Result CAMU_StartCapture(CAMU_Port port) {
+Result CAMU_StartCapture(u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00010040;
+ cmdbuf[0] = IPC_MakeHeader(0x1,1,0); // 0x10040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_StopCapture(CAMU_Port port) {
+Result CAMU_StopCapture(u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00020040;
+ cmdbuf[0] = IPC_MakeHeader(0x2,1,0); // 0x20040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_IsBusy(bool* busy, CAMU_Port port) {
+Result CAMU_IsBusy(bool* busy, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00030040;
+ cmdbuf[0] = IPC_MakeHeader(0x3,1,0); // 0x30040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *busy = (bool) cmdbuf[2];
+ *busy = (bool) cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-Result CAMU_ClearBuffer(CAMU_Port port) {
+Result CAMU_ClearBuffer(u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00040040;
+ cmdbuf[0] = IPC_MakeHeader(0x4,1,0); // 0x40040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_GetVsyncInterruptEvent(Handle* event, CAMU_Port port) {
+Result CAMU_GetVsyncInterruptEvent(Handle* event, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00050040;
+ cmdbuf[0] = IPC_MakeHeader(0x5,1,0); // 0x50040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_GetBufferErrorInterruptEvent(Handle* event, CAMU_Port port) {
+Result CAMU_GetBufferErrorInterruptEvent(Handle* event, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00060040;
+ cmdbuf[0] = IPC_MakeHeader(0x6,1,0); // 0x60040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_SetReceiving(Handle* event, void* dst, CAMU_Port port, u32 imageSize, s16 transferUnit) {
+Result CAMU_SetReceiving(Handle* event, void* dst, u32 port, u32 imageSize, s16 transferUnit) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00070102;
+ cmdbuf[0] = IPC_MakeHeader(0x7,4,2); // 0x70102
cmdbuf[1] = (u32) dst;
cmdbuf[2] = port;
cmdbuf[3] = imageSize;
cmdbuf[4] = transferUnit;
- cmdbuf[5] = 0;
- cmdbuf[6] = 0xFFFF8001;
+ cmdbuf[5] = IPC_Desc_SharedHandles(1);
+ cmdbuf[6] = CUR_PROCESS_HANDLE;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
*event = cmdbuf[3];
return cmdbuf[1];
}
-Result CAMU_IsFinishedReceiving(bool* finishedReceiving, CAMU_Port port) {
+Result CAMU_IsFinishedReceiving(bool* finishedReceiving, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00080040;
+ cmdbuf[0] = IPC_MakeHeader(0x8,1,0); // 0x80040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *finishedReceiving = (bool) cmdbuf[2];
+ *finishedReceiving = (bool) cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-Result CAMU_SetTransferLines(CAMU_Port port, s16 lines, s16 width, s16 height) {
+Result CAMU_SetTransferLines(u32 port, s16 lines, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00090100;
+ cmdbuf[0] = IPC_MakeHeader(0x9,4,0); // 0x90100
cmdbuf[1] = port;
cmdbuf[2] = lines;
cmdbuf[3] = width;
Result CAMU_GetMaxLines(s16* maxLines, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000A0080;
+ cmdbuf[0] = IPC_MakeHeader(0xA,2,0); // 0xA0080
cmdbuf[1] = width;
cmdbuf[2] = height;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *maxLines = (s16) cmdbuf[2];
+ *maxLines = (s16) cmdbuf[2] & 0xFFFF;
return cmdbuf[1];
}
-Result CAMU_SetTransferBytes(CAMU_Port port, u32 bytes, s16 width, s16 height) {
+Result CAMU_SetTransferBytes(u32 port, u32 bytes, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000B0100;
+ cmdbuf[0] = IPC_MakeHeader(0xB,4,0); // 0xB0100
cmdbuf[1] = port;
cmdbuf[2] = bytes;
cmdbuf[3] = width;
return cmdbuf[1];
}
-Result CAMU_GetTransferBytes(u32* transferBytes, CAMU_Port port) {
+Result CAMU_GetTransferBytes(u32* transferBytes, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000C0040;
+ cmdbuf[0] = IPC_MakeHeader(0xC,1,0); // 0xC0040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_GetMaxBytes(u32* maxBytes, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000D0080;
+ cmdbuf[0] = IPC_MakeHeader(0xD,2,0); // 0xD0080
cmdbuf[1] = width;
cmdbuf[2] = height;
return cmdbuf[1];
}
-Result CAMU_SetTrimming(CAMU_Port port, bool trimming) {
+Result CAMU_SetTrimming(u32 port, bool trimming) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000E0080;
+ cmdbuf[0] = IPC_MakeHeader(0xE,2,0); // 0xE0080
cmdbuf[1] = port;
cmdbuf[2] = trimming;
return cmdbuf[1];
}
-Result CAMU_IsTrimming(bool* trimming, CAMU_Port port) {
+Result CAMU_IsTrimming(bool* trimming, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x000F0040;
+ cmdbuf[0] = IPC_MakeHeader(0xF,1,0); // 0xF0040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *trimming = (bool) cmdbuf[2];
+ *trimming = (bool) cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-Result CAMU_SetTrimmingParams(CAMU_Port port, s16 xStart, s16 yStart, s16 xEnd, s16 yEnd) {
+Result CAMU_SetTrimmingParams(u32 port, s16 xStart, s16 yStart, s16 xEnd, s16 yEnd) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00100140;
+ cmdbuf[0] = IPC_MakeHeader(0x10,5,0); // 0x100140
cmdbuf[1] = port;
cmdbuf[2] = xStart;
cmdbuf[3] = yStart;
return cmdbuf[1];
}
-Result CAMU_GetTrimmingParams(s16* xStart, s16* yStart, s16* xEnd, s16* yEnd, CAMU_Port port) {
+Result CAMU_GetTrimmingParams(s16* xStart, s16* yStart, s16* xEnd, s16* yEnd, u32 port) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00110040;
+ cmdbuf[0] = IPC_MakeHeader(0x11,1,0); // 0x110040
cmdbuf[1] = port;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *xStart = (s16) cmdbuf[2];
- *yStart = (s16) cmdbuf[3];
- *xEnd = (s16) cmdbuf[4];
- *yEnd = (s16) cmdbuf[5];
+ *xStart = (s16) cmdbuf[2] & 0xFFFF;
+ *yStart = (s16) cmdbuf[3] & 0xFFFF;
+ *xEnd = (s16) cmdbuf[4] & 0xFFFF;
+ *yEnd = (s16) cmdbuf[5] & 0xFFFF;
return cmdbuf[1];
}
-Result CAMU_SetTrimmingParamsCenter(CAMU_Port port, s16 trimWidth, s16 trimHeight, s16 camWidth, s16 camHeight) {
+Result CAMU_SetTrimmingParamsCenter(u32 port, s16 trimWidth, s16 trimHeight, s16 camWidth, s16 camHeight) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00120140;
+ cmdbuf[0] = IPC_MakeHeader(0x12,5,0); // 0x120140
cmdbuf[1] = port;
cmdbuf[2] = trimWidth;
cmdbuf[3] = trimHeight;
return cmdbuf[1];
}
-Result CAMU_Activate(CAMU_CameraSelect select) {
+Result CAMU_Activate(u32 select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00130040;
+ cmdbuf[0] = IPC_MakeHeader(0x13,1,0); // 0x130040
cmdbuf[1] = select;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_SwitchContext(CAMU_CameraSelect select, CAMU_Context context) {
+Result CAMU_SwitchContext(u32 select, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00140080;
+ cmdbuf[0] = IPC_MakeHeader(0x14,2,0); // 0x140080
cmdbuf[1] = select;
cmdbuf[2] = context;
return cmdbuf[1];
}
-Result CAMU_SetExposure(CAMU_CameraSelect select, s8 exposure) {
+Result CAMU_SetExposure(u32 select, s8 exposure) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00150080;
+ cmdbuf[0] = IPC_MakeHeader(0x15,2,0); // 0x150080
cmdbuf[1] = select;
cmdbuf[2] = exposure;
return cmdbuf[1];
}
-Result CAMU_SetWhiteBalance(CAMU_CameraSelect select, CAMU_WhiteBalance whiteBalance) {
+Result CAMU_SetWhiteBalance(u32 select, CAMU_WhiteBalance whiteBalance) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00160080;
+ cmdbuf[0] = IPC_MakeHeader(0x16,2,0); // 0x160080
cmdbuf[1] = select;
cmdbuf[2] = whiteBalance;
return cmdbuf[1];
}
-Result CAMU_SetWhiteBalanceWithoutBaseUp(CAMU_CameraSelect select, CAMU_WhiteBalance whiteBalance) {
+Result CAMU_SetWhiteBalanceWithoutBaseUp(u32 select, CAMU_WhiteBalance whiteBalance) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00170080;
+ cmdbuf[0] = IPC_MakeHeader(0x17,2,0); // 0x170080
cmdbuf[1] = select;
cmdbuf[2] = whiteBalance;
return cmdbuf[1];
}
-Result CAMU_SetSharpness(CAMU_CameraSelect select, s8 sharpness) {
+Result CAMU_SetSharpness(u32 select, s8 sharpness) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00180080;
+ cmdbuf[0] = IPC_MakeHeader(0x18,2,0); // 0x180080
cmdbuf[1] = select;
cmdbuf[2] = sharpness;
return cmdbuf[1];
}
-Result CAMU_SetAutoExposure(CAMU_CameraSelect select, bool autoExposure) {
+Result CAMU_SetAutoExposure(u32 select, bool autoExposure) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00190080;
+ cmdbuf[0] = IPC_MakeHeader(0x19,2,0); // 0x190080
cmdbuf[1] = select;
cmdbuf[2] = autoExposure;
return cmdbuf[1];
}
-Result CAMU_IsAutoExposure(bool* autoExposure, CAMU_CameraSelect select) {
+Result CAMU_IsAutoExposure(bool* autoExposure, u32 select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001A0040;
+ cmdbuf[0] = IPC_MakeHeader(0x1A,1,0); // 0x1A0040
cmdbuf[1] = select;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *autoExposure = (bool) cmdbuf[2];
+ *autoExposure = (bool) cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-Result CAMU_SetAutoWhiteBalance(CAMU_CameraSelect select, bool autoWhiteBalance) {
+Result CAMU_SetAutoWhiteBalance(u32 select, bool autoWhiteBalance) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001B0080;
+ cmdbuf[0] = IPC_MakeHeader(0x1B,2,0); // 0x1B0080
cmdbuf[1] = select;
cmdbuf[2] = autoWhiteBalance;
return cmdbuf[1];
}
-Result CAMU_IsAutoWhiteBalance(bool* autoWhiteBalance, CAMU_CameraSelect select) {
+Result CAMU_IsAutoWhiteBalance(bool* autoWhiteBalance, u32 select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001C0040;
+ cmdbuf[0] = IPC_MakeHeader(0x1C,1,0); // 0x1C0040
cmdbuf[1] = select;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *autoWhiteBalance = (bool) cmdbuf[2];
+ *autoWhiteBalance = (bool) cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-Result CAMU_FlipImage(CAMU_CameraSelect select, CAMU_Flip flip, CAMU_Context context) {
+Result CAMU_FlipImage(u32 select, CAMU_Flip flip, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001D00C0;
+ cmdbuf[0] = IPC_MakeHeader(0x1D,3,0); // 0x1D00C0
cmdbuf[1] = select;
cmdbuf[2] = flip;
cmdbuf[3] = context;
return cmdbuf[1];
}
-Result CAMU_SetDetailSize(CAMU_CameraSelect select, s16 width, s16 height, s16 cropX0, s16 cropY0, s16 cropX1, s16 cropY1, CAMU_Context context) {
+Result CAMU_SetDetailSize(u32 select, s16 width, s16 height, s16 cropX0, s16 cropY0, s16 cropX1, s16 cropY1, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001E0200;
+ cmdbuf[0] = IPC_MakeHeader(0x1E,8,0); // 0x1E0200
cmdbuf[1] = select;
cmdbuf[2] = width;
cmdbuf[3] = height;
return cmdbuf[1];
}
-Result CAMU_SetSize(CAMU_CameraSelect select, CAMU_Size size, CAMU_Context context) {
+Result CAMU_SetSize(u32 select, CAMU_Size size, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x001F00C0;
+ cmdbuf[0] = IPC_MakeHeader(0x1F,3,0); // 0x1F00C0
cmdbuf[1] = select;
cmdbuf[2] = size;
cmdbuf[3] = context;
return cmdbuf[1];
}
-Result CAMU_SetFrameRate(CAMU_CameraSelect select, CAMU_FrameRate frameRate) {
+Result CAMU_SetFrameRate(u32 select, CAMU_FrameRate frameRate) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00200080;
+ cmdbuf[0] = IPC_MakeHeader(0x20,2,0); // 0x200080
cmdbuf[1] = select;
cmdbuf[2] = frameRate;
return cmdbuf[1];
}
-Result CAMU_SetPhotoMode(CAMU_CameraSelect select, CAMU_PhotoMode photoMode) {
+Result CAMU_SetPhotoMode(u32 select, CAMU_PhotoMode photoMode) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00210080;
+ cmdbuf[0] = IPC_MakeHeader(0x21,2,0); // 0x210080
cmdbuf[1] = select;
cmdbuf[2] = photoMode;
return cmdbuf[1];
}
-Result CAMU_SetEffect(CAMU_CameraSelect select, CAMU_Effect effect, CAMU_Context context) {
+Result CAMU_SetEffect(u32 select, CAMU_Effect effect, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002200C0;
+ cmdbuf[0] = IPC_MakeHeader(0x22,3,0); // 0x2200C0
cmdbuf[1] = select;
cmdbuf[2] = effect;
cmdbuf[3] = context;
return cmdbuf[1];
}
-Result CAMU_SetContrast(CAMU_CameraSelect select, CAMU_Contrast contrast) {
+Result CAMU_SetContrast(u32 select, CAMU_Contrast contrast) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00230080;
+ cmdbuf[0] = IPC_MakeHeader(0x23,2,0); // 0x230080
cmdbuf[1] = select;
cmdbuf[2] = contrast;
return cmdbuf[1];
}
-Result CAMU_SetLensCorrection(CAMU_CameraSelect select, CAMU_LensCorrection lensCorrection) {
+Result CAMU_SetLensCorrection(u32 select, CAMU_LensCorrection lensCorrection) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00240080;
+ cmdbuf[0] = IPC_MakeHeader(0x24,2,0); // 0x240080
cmdbuf[1] = select;
cmdbuf[2] = lensCorrection;
return cmdbuf[1];
}
-Result CAMU_SetOutputFormat(CAMU_CameraSelect select, CAMU_OutputFormat format, CAMU_Context context) {
+Result CAMU_SetOutputFormat(u32 select, CAMU_OutputFormat format, CAMU_Context context) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002500C0;
+ cmdbuf[0] = IPC_MakeHeader(0x25,2,0); // 0x2500C0
cmdbuf[1] = select;
cmdbuf[2] = format;
cmdbuf[3] = context;
return cmdbuf[1];
}
-Result CAMU_SetAutoExposureWindow(CAMU_CameraSelect select, s16 x, s16 y, s16 width, s16 height) {
+Result CAMU_SetAutoExposureWindow(u32 select, s16 x, s16 y, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00260140;
+ cmdbuf[0] = IPC_MakeHeader(0x26,5,0); // 0x260140
cmdbuf[1] = select;
cmdbuf[2] = x;
cmdbuf[3] = y;
return cmdbuf[1];
}
-Result CAMU_SetAutoWhiteBalanceWindow(CAMU_CameraSelect select, s16 x, s16 y, s16 width, s16 height) {
+Result CAMU_SetAutoWhiteBalanceWindow(u32 select, s16 x, s16 y, s16 width, s16 height) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00270140;
+ cmdbuf[0] = IPC_MakeHeader(0x27,5,0); // 0x270140
cmdbuf[1] = select;
cmdbuf[2] = x;
cmdbuf[3] = y;
return cmdbuf[1];
}
-Result CAMU_SetNoiseFilter(CAMU_CameraSelect select, bool noiseFilter) {
+Result CAMU_SetNoiseFilter(u32 select, bool noiseFilter) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00280080;
+ cmdbuf[0] = IPC_MakeHeader(0x28,2,0); // 0x280080
cmdbuf[1] = select;
cmdbuf[2] = noiseFilter;
return cmdbuf[1];
}
-Result CAMU_SynchronizeVsyncTiming(CAMU_CameraSelect select1, CAMU_CameraSelect select2) {
+Result CAMU_SynchronizeVsyncTiming(u32 select1, u32 select2) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00290080;
+ cmdbuf[0] = IPC_MakeHeader(0x29,2,0); // 0x290080
cmdbuf[1] = select1;
cmdbuf[2] = select2;
return cmdbuf[1];
}
-Result CAMU_GetLatestVsyncTiming(s64* timing, CAMU_Port port, u32 past) {
+Result CAMU_GetLatestVsyncTiming(s64* timing, u32 port, u32 past) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002A0080;
+ cmdbuf[0] = IPC_MakeHeader(0x2A,2,0); // 0x2A0080
cmdbuf[1] = port;
cmdbuf[2] = past;
cmdbuf[49] = (past << 17) | 2;
Result CAMU_GetStereoCameraCalibrationData(CAMU_StereoCameraCalibrationData* data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002B0000;
+ cmdbuf[0] = IPC_MakeHeader(0x2B,0,0); // 0x2B0000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
*data = *(CAMU_StereoCameraCalibrationData*) cmdbuf[2];
Result CAMU_SetStereoCameraCalibrationData(CAMU_StereoCameraCalibrationData data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002C0400;
+ cmdbuf[0] = IPC_MakeHeader(0x2C,16,0); // 0x2C0400
*(CAMU_StereoCameraCalibrationData*) cmdbuf[1] = data;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_WriteRegisterI2c(CAMU_CameraSelect select, u16 addr, u16 data) {
+Result CAMU_WriteRegisterI2c(u32 select, u16 addr, u16 data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002D00C0;
+ cmdbuf[0] = IPC_MakeHeader(0x2D,3,0); // 0x2D00C0
cmdbuf[1] = select;
cmdbuf[2] = addr;
cmdbuf[3] = data;
return cmdbuf[1];
}
-Result CAMU_WriteMcuVariableI2c(CAMU_CameraSelect select, u16 addr, u16 data) {
+Result CAMU_WriteMcuVariableI2c(u32 select, u16 addr, u16 data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002E00C0;
+ cmdbuf[0] = IPC_MakeHeader(0x2E,3,0); // 0x2E00C0
cmdbuf[1] = select;
cmdbuf[2] = addr;
cmdbuf[3] = data;
return cmdbuf[1];
}
-Result CAMU_ReadRegisterI2cExclusive(u16* data, CAMU_CameraSelect select, u16 addr) {
+Result CAMU_ReadRegisterI2cExclusive(u16* data, u32 select, u16 addr) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x002F0080;
+ cmdbuf[0] = IPC_MakeHeader(0x2F,2,0); // 0x2F0080
cmdbuf[1] = select;
cmdbuf[2] = addr;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *data = (u16) cmdbuf[2];
+ *data = (u16) cmdbuf[2] & 0xFFFF;
return cmdbuf[1];
}
-Result CAMU_ReadMcuVariableI2cExclusive(u16* data, CAMU_CameraSelect select, u16 addr) {
+Result CAMU_ReadMcuVariableI2cExclusive(u16* data, u32 select, u16 addr) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00300080;
+ cmdbuf[0] = IPC_MakeHeader(0x30,2,0); // 0x300080
cmdbuf[1] = select;
cmdbuf[2] = addr;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *data = (u16) cmdbuf[2];
+ *data = (u16) cmdbuf[2] & 0xFFFF;
return cmdbuf[1];
}
Result CAMU_SetImageQualityCalibrationData(CAMU_ImageQualityCalibrationData data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00310180;
+ cmdbuf[0] = IPC_MakeHeader(0x31,6,0); // 0x310180
*(CAMU_ImageQualityCalibrationData*) cmdbuf[1] = data;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_GetImageQualityCalibrationData(CAMU_ImageQualityCalibrationData* data) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00320000;
+ cmdbuf[0] = IPC_MakeHeader(0x32,0,0); // 0x320000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
*data = *(CAMU_ImageQualityCalibrationData*) cmdbuf[2];
Result CAMU_SetPackageParameterWithoutContext(CAMU_PackageParameterCameraSelect param) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003302C0;
+ cmdbuf[0] = IPC_MakeHeader(0x33,11,0); // 0x3302C0
*(CAMU_PackageParameterCameraSelect*) cmdbuf[1] = param;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_SetPackageParameterWithContext(CAMU_PackageParameterContext param) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00340140;
+ cmdbuf[0] = IPC_MakeHeader(0x34,5,0); // 0x340140
*(CAMU_PackageParameterContext*) cmdbuf[1] = param;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_SetPackageParameterWithContextDetail(CAMU_PackageParameterContextDetail param) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003501C0;
+ cmdbuf[0] = IPC_MakeHeader(0x35,7,0); // 0x3501C0
*(CAMU_PackageParameterContextDetail*) cmdbuf[1] = param;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_GetSuitableY2rStandardCoefficient(Y2R_StandardCoefficient* coefficient) {
+Result CAMU_GetSuitableY2rStandardCoefficient(Y2RU_StandardCoefficient* coefficient) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00360000;
+ cmdbuf[0] = IPC_MakeHeader(0x36,0,0); // 0x360000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *coefficient = (Y2R_StandardCoefficient) cmdbuf[2];
+ *coefficient = (Y2RU_StandardCoefficient) cmdbuf[2];
return cmdbuf[1];
}
Result CAMU_PlayShutterSound(CAMU_ShutterSoundType sound) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00380040;
+ cmdbuf[0] = IPC_MakeHeader(0x38,1,0); // 0x380040
cmdbuf[1] = sound;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_DriverInitialize(void) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00390000;
+ cmdbuf[0] = IPC_MakeHeader(0x39,0,0); // 0x390000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
Result CAMU_DriverFinalize(void) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003A0000;
+ cmdbuf[0] = IPC_MakeHeader(0x3A,0,0); // 0x3A0000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
return cmdbuf[1];
}
-Result CAMU_GetActivatedCamera(CAMU_CameraSelect* select) {
+Result CAMU_GetActivatedCamera(u32* select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003B0000;
+ cmdbuf[0] = IPC_MakeHeader(0x3B,0,0); // 0x3B0000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *select = (CAMU_CameraSelect) cmdbuf[2];
+ *select = (u32) cmdbuf[2];
return cmdbuf[1];
}
-Result CAMU_GetSleepCamera(CAMU_CameraSelect* select) {
+Result CAMU_GetSleepCamera(u32* select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003C0000;
+ cmdbuf[0] = IPC_MakeHeader(0x3C,0,0); // 0x3C0000
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
- *select = (CAMU_CameraSelect) cmdbuf[2];
+ *select = (u32) cmdbuf[2];
return cmdbuf[1];
}
-Result CAMU_SetSleepCamera(CAMU_CameraSelect select) {
+Result CAMU_SetSleepCamera(u32 select) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003D0040;
+ cmdbuf[0] = IPC_MakeHeader(0x3D,0,0); // 0x3D0040
cmdbuf[1] = select;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
Result CAMU_SetBrightnessSynchronization(bool brightnessSynchronization) {
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x003E0040;
+ cmdbuf[0] = IPC_MakeHeader(0x3E,1,0); // 0x3E0040
cmdbuf[1] = brightnessSynchronization;
if (R_FAILED(ret = svcSendSyncRequest(camHandle))) return ret;
#include <3ds/services/cfgnor.h>
#include <3ds/ipc.h>
-Handle CFGNOR_handle;
+Handle cfgnorHandle;
+
+Result cfgnorInit(u8 value)
+{
+ Result ret = 0;
+ if(R_FAILED(ret = srvGetServiceHandle(&cfgnorHandle, "cfg:nor")))return ret;
+ if(R_FAILED(ret = CFGNOR_Initialize(value))) svcCloseHandle(cfgnorHandle);
+ return ret;
+}
+
+void cfgnorExit(void)
+{
+ if(cfgnorHandle != 0)
+ {
+ CFGNOR_Shutdown();
+ svcCloseHandle(cfgnorHandle);
+ cfgnorHandle = 0;
+ }
+}
+
+Result cfgnorDumpFlash(u32 *buf, u32 size)
+{
+ Result ret = 0;
+ u32 pos=0;
+ u32 chunksize = 0x100;
+
+ for(pos=0; pos<size; pos+=chunksize)
+ {
+ if(size-pos < chunksize)chunksize = size-pos;
+
+ ret = CFGNOR_ReadData(pos, &buf[pos>>2], chunksize);
+ if(R_FAILED(ret))break;
+ }
+
+ return ret;
+}
+
+Result cfgnorWriteFlash(u32 *buf, u32 size)
+{
+ Result ret = 0;
+ u32 pos=0;
+ u32 chunksize = 0x100;
+
+ for(pos=0; pos<size; pos+=chunksize)
+ {
+ if(size-pos < chunksize)chunksize = size-pos;
+
+ ret = CFGNOR_WriteData(pos, &buf[pos>>2], chunksize);
+ if(ret!=0)break;
+ }
+
+ return ret;
+}
Result CFGNOR_Initialize(u8 value)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
- ret = srvGetServiceHandle(&CFGNOR_handle, "cfg:nor");
- if(R_FAILED(ret))return ret;
-
cmdbuf[0] = IPC_MakeHeader(0x1,1,0); // 0x10040
cmdbuf[1] = (u32)value;
- if(R_FAILED(ret = svcSendSyncRequest(CFGNOR_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfgnorHandle)))return ret;
- ret = (Result)cmdbuf[1];
- return ret;
+ return cmdbuf[1];
}
Result CFGNOR_Shutdown(void)
cmdbuf[0] = IPC_MakeHeader(0x2,0,0); // 0x20000
- if(R_FAILED(ret = svcSendSyncRequest(CFGNOR_handle)))return ret;
- ret = (Result)cmdbuf[1];
-
- svcCloseHandle(CFGNOR_handle);
- CFGNOR_handle = 0;
+ if(R_FAILED(ret = svcSendSyncRequest(cfgnorHandle)))return ret;
- return ret;
+ return cmdbuf[1];
}
Result CFGNOR_ReadData(u32 offset, u32 *buf, u32 size)
cmdbuf[3] = IPC_Desc_Buffer(size,IPC_BUFFER_W);
cmdbuf[4] = (u32)buf;
- if(R_FAILED(ret = svcSendSyncRequest(CFGNOR_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfgnorHandle)))return ret;
- ret = (Result)cmdbuf[1];
- return ret;
+ return cmdbuf[1];
}
Result CFGNOR_WriteData(u32 offset, u32 *buf, u32 size)
cmdbuf[3] = IPC_Desc_Buffer(size,IPC_BUFFER_R);
cmdbuf[4] = (u32)buf;
- if(R_FAILED(ret = svcSendSyncRequest(CFGNOR_handle)))return ret;
-
- ret = (Result)cmdbuf[1];
- return ret;
-}
-
-Result CFGNOR_DumpFlash(u32 *buf, u32 size)
-{
- Result ret = 0;
- u32 pos=0;
- u32 chunksize = 0x100;
-
- for(pos=0; pos<size; pos+=chunksize)
- {
- if(size-pos < chunksize)chunksize = size-pos;
-
- ret = CFGNOR_ReadData(pos, &buf[pos>>2], chunksize);
- if(R_FAILED(ret))break;
- }
-
- return ret;
-}
-
-Result CFGNOR_WriteFlash(u32 *buf, u32 size)
-{
- Result ret = 0;
- u32 pos=0;
- u32 chunksize = 0x100;
-
- for(pos=0; pos<size; pos+=chunksize)
- {
- if(size-pos < chunksize)chunksize = size-pos;
+ if(R_FAILED(ret = svcSendSyncRequest(cfgnorHandle)))return ret;
- ret = CFGNOR_WriteData(pos, &buf[pos>>2], chunksize);
- if(ret!=0)break;
- }
-
- return ret;
+ return cmdbuf[1];
}
#include <3ds/services/cfgu.h>
#include <3ds/ipc.h>
-static Handle CFGU_handle;
-static int CFGU_refCount;
+static Handle cfguHandle;
+static int cfguRefCount;
Result cfguInit(void)
{
Result ret;
- if (AtomicPostIncrement(&CFGU_refCount)) return 0;
+ if (AtomicPostIncrement(&cfguRefCount)) return 0;
// cfg:i has the most commands, then cfg:s, then cfg:u
- ret = srvGetServiceHandle(&CFGU_handle, "cfg:i");
- if(R_FAILED(ret)) ret = srvGetServiceHandle(&CFGU_handle, "cfg:s");
- if(R_FAILED(ret)) ret = srvGetServiceHandle(&CFGU_handle, "cfg:u");
- if(R_FAILED(ret)) AtomicDecrement(&CFGU_refCount);
+ ret = srvGetServiceHandle(&cfguHandle, "cfg:i");
+ if(R_FAILED(ret)) ret = srvGetServiceHandle(&cfguHandle, "cfg:s");
+ if(R_FAILED(ret)) ret = srvGetServiceHandle(&cfguHandle, "cfg:u");
+ if(R_FAILED(ret)) AtomicDecrement(&cfguRefCount);
return ret;
}
void cfguExit(void)
{
- if (AtomicDecrement(&CFGU_refCount)) return;
- svcCloseHandle(CFGU_handle);
+ if (AtomicDecrement(&cfguRefCount)) return;
+ svcCloseHandle(cfguHandle);
}
Result CFGU_SecureInfoGetRegion(u8* region)
cmdbuf[0] = IPC_MakeHeader(0x2,0,0); // 0x20000
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *region = (u8)cmdbuf[2];
+ *region = (u8)cmdbuf[2] & 0xFF;
return (Result)cmdbuf[1];
}
cmdbuf[0] = IPC_MakeHeader(0x3,1,0); // 0x30040
cmdbuf[1] = appIDSalt;
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
*hash = (u64)cmdbuf[2];
*hash |= ((u64)cmdbuf[3])<<32;
cmdbuf[0] = IPC_MakeHeader(0x4,0,0); // 0x40000
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *value = (u8)cmdbuf[2];
+ *value = (u8)cmdbuf[2] & 0xFF;
return (Result)cmdbuf[1];
}
cmdbuf[0] = IPC_MakeHeader(0x5,0,0); // 0x50000
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *model = (u8)cmdbuf[2];
+ *model = (u8)cmdbuf[2] & 0xFF;
return (Result)cmdbuf[1];
}
cmdbuf[0] = IPC_MakeHeader(0x6,0,0); // 0x60000
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *value = (u8)cmdbuf[2];
+ *value = (u8)cmdbuf[2] & 0xFF;
return (Result)cmdbuf[1];
}
cmdbuf[0] = IPC_MakeHeader(0x9,1,0); // 0x90040
cmdbuf[1] = (u32)code;
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *string = (u16)cmdbuf[2];
+ *string = (u16)cmdbuf[2] & 0xFFFF;
return (Result)cmdbuf[1];
}
cmdbuf[0] = IPC_MakeHeader(0xA,1,0); // 0xA0040
cmdbuf[1] = (u32)string;
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
- *code = (u16)cmdbuf[2];
+ *code = (u16)cmdbuf[2] & 0xFFFF;
return (Result)cmdbuf[1];
}
cmdbuf[3] = IPC_Desc_Buffer(size,IPC_BUFFER_W);
cmdbuf[4] = (u32)outData;
- if(R_FAILED(ret = svcSendSyncRequest(CFGU_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(cfguHandle)))return ret;
return (Result)cmdbuf[1];
}
#include <3ds/result.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
-#include <3ds/mappable.h>
+#include <3ds/allocator/mappable.h>
#include <3ds/os.h>
#include <3ds/services/csnd.h>
#include <3ds/ipc.h>
static u32 csndCmdStartOff;
static u32 csndCmdCurOff;
-static Result CSND_Initialize(void)
+static Result CSND_Initialize(Handle* mutex, Handle* sharedMem, u32 sharedMemSize, u32* offsets)
{
Result ret=0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1,5,0); // 0x10140
- cmdbuf[1] = csndSharedMemSize;
- memcpy(&cmdbuf[2], &csndOffsets[0], 4*sizeof(u32));
+ cmdbuf[1] = sharedMemSize;
+ memcpy(&cmdbuf[2], &offsets[0], 4*sizeof(u32));
if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
- csndMutex = cmdbuf[3];
- csndSharedMemBlock = cmdbuf[4];
+ if(mutex) *mutex = cmdbuf[3];
+ if(sharedMem) *sharedMem = cmdbuf[4];
return (Result)cmdbuf[1];
}
return (Result)cmdbuf[1];
}
+static Result CSND_ExecuteCommands(u32 offset)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x3,1,0); // 0x30040
+ cmdbuf[1] = offset;
+
+ if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
+
+ return (Result)cmdbuf[1];
+}
+
static Result CSND_AcquireSoundChannels(u32* channelMask)
{
Result ret=0;
return (Result)cmdbuf[1];
}
+Result CSND_FlushDataCache(const void* adr, u32 size)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x9,2,2); // 0x90082
+ cmdbuf[1] = (u32)adr;
+ cmdbuf[2] = size;
+ cmdbuf[3] = IPC_Desc_SharedHandles(1);
+ cmdbuf[4] = CUR_PROCESS_HANDLE;
+
+ if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
+
+ return cmdbuf[1];
+}
+
+Result CSND_StoreDataCache(const void* adr, u32 size)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xA,2,2); // 0xA0082
+ cmdbuf[1] = (u32)adr;
+ cmdbuf[2] = size;
+ cmdbuf[3] = IPC_Desc_SharedHandles(1);
+ cmdbuf[4] = CUR_PROCESS_HANDLE;
+
+ if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
+
+ return cmdbuf[1];
+}
+
+Result CSND_InvalidateDataCache(const void* adr, u32 size)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xB,2,2); // 0xB0082
+ cmdbuf[1] = (u32)adr;
+ cmdbuf[2] = size;
+ cmdbuf[3] = IPC_Desc_SharedHandles(1);
+ cmdbuf[4] = CUR_PROCESS_HANDLE;
+
+ if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
+
+ return cmdbuf[1];
+}
+
Result CSND_Reset(void)
{
Result ret=0;
csndOffsets[3] = csndOffsets[2] + 2*8; // Offset to the input of command 0x00040080
csndSharedMemSize = csndOffsets[3] + 0x3C; // Total size of the CSND shared memory
- ret = CSND_Initialize();
+ ret = CSND_Initialize(&csndMutex, &csndSharedMemBlock, csndSharedMemSize, csndOffsets);
if (R_FAILED(ret)) goto cleanup1;
csndSharedMem = (vu32*)mappableAlloc(csndSharedMemSize);
}
}
-static Result CSND_ExecuteCommands(u32 offset)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x3,1,0); // 0x30040
- cmdbuf[1] = offset;
-
- if(R_FAILED(ret = svcSendSyncRequest(csndHandle)))return ret;
-
- return (Result)cmdbuf[1];
-}
-
u32* csndAddCmd(int cmdid)
{
vu16* ptr;
cmdparams[1] = interp ? 1 : 0;
}
-void CSND_SetDuty(u32 channel, u32 duty)
+void CSND_SetDuty(u32 channel, CSND_DutyCycle duty)
{
u32* cmdparams = csndAddCmd(0x007);
cmdparams[5] = totalbytesize;
}
-void CSND_SetChnRegsPSG(u32 flags, u32 chnVolumes, u32 capVolumes, u32 duty)
+void CSND_SetChnRegsPSG(u32 flags, u32 chnVolumes, u32 capVolumes, CSND_DutyCycle duty)
{
u32* cmdparams = csndAddCmd(0x00F);
#include <3ds/services/fs.h>
#include <3ds/ipc.h>
-/*! @internal
- *
- * @file fs.c
- *
- * Filesystem Services
- */
-
-/*! FSUSER handle */
static Handle fsuHandle;
+static int fsuRefCount;
// used to determine whether or not we should do FSUSER_Initialize on fsuHandle
Handle __get_handle_from_list(char* name);
-/*! Create an FS_path from a type and data pointer.
- *
- * @param[in] type Path type.
- * @param[in] path Pointer to path data.
- *
- * @returns FS_path
- *
- * @sa FS_pathType
- */
-FS_path
-FS_makePath(FS_pathType type,
- const char *path)
-{
- return (FS_path){type, strlen(path)+1, (const u8*)path};
-}
-
-static int fsRefCount;
-
-/*! Initialize FS service
- *
- * @returns error
- */
Result fsInit(void)
{
Result ret = 0;
- if (AtomicPostIncrement(&fsRefCount)) return 0;
+ if (AtomicPostIncrement(&fsuRefCount)) return 0;
ret = srvGetServiceHandle(&fsuHandle, "fs:USER");
if (R_SUCCEEDED(ret) && __get_handle_from_list("fs:USER")==0)
ret = FSUSER_Initialize(fsuHandle);
if (R_FAILED(ret)) svcCloseHandle(fsuHandle);
}
- if (R_FAILED(ret)) AtomicDecrement(&fsRefCount);
+
+ if (R_FAILED(ret)) AtomicDecrement(&fsuRefCount);
return ret;
}
-/// Deinitialize FS service
void fsExit(void)
{
- if (AtomicDecrement(&fsRefCount)) return;
+ if (AtomicDecrement(&fsuRefCount)) return;
svcCloseHandle(fsuHandle);
}
-/*! Gets the fsuser service session handle.
-*
-* @returns Handle
-*/
Handle *fsGetSessionHandle(void)
{
return &fsuHandle;
}
-/*! Initialize FS service handle
- *
- * @returns error
- *
- * @param[in] handle fs:USER service handle
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08010002]
- * 1 | 0x20 (ProcessID header)
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_Initialize(Handle handle)
+FS_path fsMakePath(FS_pathType type, const char *path)
+{
+ return (FS_path){type, strlen(path)+1, (const u8*)path};
+}
+
+Result FSUSER_Initialize(Handle handle)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[1] = IPC_Desc_CurProcessHandle();
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
return cmdbuf[1];
}
-/*! Open a file
- *
- * @param[out] out Output handle
- * @param[in] archive Open archive
- * @param[in] fileLowPath File path
- * @param[in] openFlags Open flags
- * @param[in] attributes Create attributes
- *
- * @note This requires @a archive to have been opened
- *
- * @returns error
- *
- * @sa fs_open_flags
- * @sa fs_create_attributes
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080201C2]
- * 1 | Transaction (usually 0)
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | fileLowPath.type
- * 5 | fileLowPath.size
- * 6 | openFlags
- * 7 | attributes
- * 8 | (fileLowPath.size << 14) \| 0x2
- * 9 | fileLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | ???
- * 3 | File handle
- */
-Result
-FSUSER_OpenFile(Handle *out,
- FS_archive archive,
- FS_path fileLowPath,
- u32 openFlags,
- u32 attributes)
+Result FSUSER_OpenFile(Handle *out, FS_archive archive, FS_path fileLowPath, u32 openFlags, u32 attributes)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[9] = (u32)fileLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(out)
- *out = cmdbuf[3];
+ if(out) *out = cmdbuf[3];
return cmdbuf[1];
}
-/*! Open a file
- *
- * @param[out] out Output handle
- * @param[in] archive Open archive
- * @param[in] fileLowPath File path
- * @param[in] openFlags Open flags
- * @param[in] attributes Create attributes
- *
- * @note This does not require @a archive to have been opened
- *
- * @returns error
- *
- * @sa fs_open_flags
- * @sa fs_create_attributes
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08030204]
- * 1 | Transaction (usually 0)
- * 2 | archive.id
- * 3 | archive.lowPath.type
- * 4 | archive.lowPath.Size
- * 5 | fileLowPath.type
- * 6 | fileLowPath.size
- * 7 | openFlags
- * 8 | attributes
- * 9 | (archive.lowPath.size << 14 \| 0x802
- * 10 | archive.lowPath.data
- * 11 | (fileLowPath.size << 14) \| 0x2
- * 12 | fileLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | ???
- * 3 | File handle
- */
-Result
-FSUSER_OpenFileDirectly(Handle *out,
- FS_archive archive,
- FS_path fileLowPath,
- u32 openFlags,
- u32 attributes)
+Result FSUSER_OpenFileDirectly(Handle *out, FS_archive archive, FS_path fileLowPath, u32 openFlags, u32 attributes)
{
u32 *cmdbuf = getThreadCommandBuffer();
- cmdbuf[ 0] = IPC_MakeHeader(0x803,8,4); // 0x8030204
- cmdbuf[ 1] = 0;
- cmdbuf[ 2] = archive.id;
- cmdbuf[ 3] = archive.lowPath.type;
- cmdbuf[ 4] = archive.lowPath.size;
- cmdbuf[ 5] = fileLowPath.type;
- cmdbuf[ 6] = fileLowPath.size;
- cmdbuf[ 7] = openFlags;
- cmdbuf[ 8] = attributes;
- cmdbuf[ 9] = IPC_Desc_StaticBuffer(archive.lowPath.size,2);
+ cmdbuf[0] = IPC_MakeHeader(0x803,8,4); // 0x8030204
+ cmdbuf[1] = 0;
+ cmdbuf[2] = archive.id;
+ cmdbuf[3] = archive.lowPath.type;
+ cmdbuf[4] = archive.lowPath.size;
+ cmdbuf[5] = fileLowPath.type;
+ cmdbuf[6] = fileLowPath.size;
+ cmdbuf[7] = openFlags;
+ cmdbuf[8] = attributes;
+ cmdbuf[9] = IPC_Desc_StaticBuffer(archive.lowPath.size,2);
cmdbuf[10] = (u32)archive.lowPath.data;
cmdbuf[11] = IPC_Desc_StaticBuffer(fileLowPath.size,0);
cmdbuf[12] = (u32)fileLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(out)
- *out = cmdbuf[3];
+ if(out) *out = cmdbuf[3];
return cmdbuf[1];
}
-/*! Delete a file
- *
- * @param[in] archive Open archive
- * @param[in] fileLowPath File path
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08040142]
- * 1 | 0
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | fileLowPath.type
- * 5 | fileLowPath.size
- * 6 | (fileLowPath.size << 14) \| 0x2
- * 7 | fileLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_DeleteFile(FS_archive archive,
- FS_path fileLowPath)
+Result FSUSER_DeleteFile(FS_archive archive, FS_path fileLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[7] = (u32)fileLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Renames or moves a file.
- *
- * @param[in] srcArchive Open archive of source
- * @param[in] srcFileLowPath File path to source
- * @param[in] destArchive Open archive of destination
- * @param[in] destFileLowPath File path to destination
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08050244]
- * 1 | 0
- * 2 | srcArchive.handleLow
- * 3 | srcArchive.handleHigh
- * 4 | srcFileLowPath.type
- * 5 | srcFileLowPath.size
- * 6 | destArchive.handleLow
- * 7 | destArchive.handleHigh
- * 8 | destFileLowPath.type
- * 9 | destFileLowPath.size
- * 10 | (srcFileLowPath.size << 14) \| 0x402
- * 11 | srcFileLowPath.data
- * 12 | (destFileLowPath.size << 14) \| 0x802
- * 13 | destFileLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_RenameFile(FS_archive srcArchive,
- FS_path srcFileLowPath,
- FS_archive destArchive,
- FS_path destFileLowPath)
+Result FSUSER_RenameFile(FS_archive srcArchive, FS_path srcFileLowPath, FS_archive destArchive, FS_path destFileLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[13] = (u32)destFileLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Delete a directory
- *
- * @param[in] archive Open archive
- * @param[in] dirLowPath Directory path
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08060142]
- * 1 | 0
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | dirLowPath.type
- * 5 | dirLowPath.size
- * 6 | (dirLowPath.size << 14) \| 0x2
- * 7 | dirLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_DeleteDirectory(FS_archive archive,
- FS_path dirLowPath)
+Result FSUSER_DeleteDirectory(FS_archive archive, FS_path dirLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[7] = (u32)dirLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Delete a directory and all sub directories/files recursively
- *
- * @param[in] archive Open archive
- * @param[in] dirLowPath Directory path
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08070142]
- * 1 | 0
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | dirLowPath.type
- * 5 | dirLowPath.size
- * 6 | (dirLowPath.size << 14) \| 0x2
- * 7 | dirLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_DeleteDirectoryRecursively(FS_archive archive,
- FS_path dirLowPath)
+Result FSUSER_DeleteDirectoryRecursively(FS_archive archive, FS_path dirLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[7] = (u32)dirLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Create a File
- *
- * @param[in] archive Open archive
- * @param[in] fileLowPath File path
- * @param[in] fileSize Size of new file in bytes
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08060142]
- * 1 | 0
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | fileLowPath.type
- * 5 | fileLowPath.size
- * 6 | 0
- * 7 | fileSize
- * 8 | 0
- * 9 | (fileLowPath.size << 14) \| 0x2
- * 10 | fileLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_CreateFile(FS_archive archive,
- FS_path fileLowPath,
- u32 fileSize)
+Result FSUSER_CreateFile(FS_archive archive, FS_path fileLowPath, u32 fileSize)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[10] = (u32)fileLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Create a directory
- *
- * @param[in] archive Open archive
- * @param[in] dirLowPath Directory path to create
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08090182]
- * 1 | 0
- * 2 | archive.handleLow
- * 3 | archive.handleHigh
- * 4 | dirLowPath.type
- * 5 | dirLowPath.size
- * 6 | 0
- * 7 | (dirLowPath.size << 14) \| 0x2
- * 8 | dirLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_CreateDirectory(FS_archive archive,
- FS_path dirLowPath)
+Result FSUSER_CreateDirectory(FS_archive archive, FS_path dirLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[8] = (u32)dirLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Renames or moves a directory.
- *
- * @param[in] srcArchive Open archive of source
- * @param[in] srcDirLowPath Dir path to source
- * @param[in] destArchive Open archive of destination
- * @param[in] destDirLowPath Dir path to destination
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080A0244]
- * 1 | 0
- * 2 | srcArchive.handleLow
- * 3 | srcArchive.handleHigh
- * 4 | srcDirLowPath.type
- * 5 | srcDirLowPath.size
- * 6 | destArchive.handleLow
- * 7 | destArchive.handleHigh
- * 8 | destDirLowPath.type
- * 9 | destDirLowPath.size
- * 10 | (srcDirLowPath.size << 14) \| 0x402
- * 11 | srcDirLowPath.data
- * 12 | (destDirLowPath.size << 14) \| 0x802
- * 13 | destDirLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_RenameDirectory(FS_archive srcArchive,
- FS_path srcDirLowPath,
- FS_archive destArchive,
- FS_path destDirLowPath)
+Result FSUSER_RenameDirectory(FS_archive srcArchive, FS_path srcDirLowPath, FS_archive destArchive, FS_path destDirLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[13] = (u32)destDirLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Open a directory
- *
- * @param[out] out Output handle
- * @param[in] archive Open archive
- * @param[in] dirLowPath Directory path
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080B0102]
- * 1 | archive.handleLow
- * 2 | archive.handleHigh
- * 3 | dirLowPath.type
- * 4 | dirLowPath.size
- * 5 | (dirLowPath.size << 14) \| 0x2
- * 6 | dirLowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Directory handle
- */
-Result
-FSUSER_OpenDirectory(Handle *out,
- FS_archive archive,
- FS_path dirLowPath)
+Result FSUSER_OpenDirectory(Handle *out, FS_archive archive, FS_path dirLowPath)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[6] = (u32)dirLowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(out)
- *out = cmdbuf[3];
+ if(out) *out = cmdbuf[3];
return cmdbuf[1];
}
-/*! Open an archive
- *
- * @param[in,out] archive Archive to open
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080C00C2]
- * 1 | archive->id
- * 2 | archive->lowPath.type
- * 3 | archive->lowPath.size
- * 4 | (archive->lowPath.size << 14) \| 0x2
- * 5 | archive->lowPath.data
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | archive->handleLow
- * 3 | archive->handleHigh
- */
-Result
-FSUSER_OpenArchive(FS_archive *archive)
+Result FSUSER_OpenArchive(FS_archive *archive)
{
- if(!archive)
- return -2;
+ if(!archive) return -2;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[5] = (u32)archive->lowPath.data;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
archive->handleLow = cmdbuf[2];
archive->handleHigh = cmdbuf[3];
return cmdbuf[1];
}
-
-/*! Close an open archive
- *
- * @param[in,out] archive Archive to close
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080B0102]
- * 1 | archive->handleLow
- * 2 | archive->handleHigh
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_CloseArchive(FS_archive *archive)
+Result FSUSER_CloseArchive(FS_archive *archive)
{
- if(!archive)
- return -2;
+ if(!archive) return -2;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[2] = archive->handleHigh;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
return cmdbuf[1];
}
-/*! Get SD FAT information
- *
- * @param[out] sectorSize Sector size (bytes)
- * @param[out] clusterSize Cluster size (bytes)
- * @param[out] numClusters Total number of clusters
- * @param[out] freeClusters Number of free clusters
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08140000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Sector (bytes)
- * 3 | Cluster (bytes)
- * 4 | Partition capacity (clusters)
- * 5 | Free space (clusters)
- */
-Result
-FSUSER_GetSdmcArchiveResource(u32 *sectorSize,
- u32 *clusterSize,
- u32 *numClusters,
- u32 *freeClusters)
+Result FSUSER_GetSdmcArchiveResource(u32 *sectorSize, u32 *clusterSize, u32 *numClusters, u32 *freeClusters)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x814,0,0); // 0x8140000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
-
- if(sectorSize)
- *sectorSize = cmdbuf[2];
-
- if(clusterSize)
- *clusterSize = cmdbuf[3];
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(numClusters)
- *numClusters = cmdbuf[4];
-
- if(freeClusters)
- *freeClusters = cmdbuf[5];
+ if(sectorSize) *sectorSize = cmdbuf[2];
+ if(clusterSize) *clusterSize = cmdbuf[3];
+ if(numClusters) *numClusters = cmdbuf[4];
+ if(freeClusters) *freeClusters = cmdbuf[5];
return cmdbuf[1];
}
-/*! Get NAND information
- *
- * @param[out] sectorSize Sector size (bytes)
- * @param[out] clusterSize Cluster size (bytes)
- * @param[out] numClusters Total number of clusters
- * @param[out] freeClusters Number of free clusters
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08140000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Sector (bytes)
- * 3 | Cluster (bytes)
- * 4 | Partition capacity (clusters)
- * 5 | Free space (clusters)
- */
-Result
-FSUSER_GetNandArchiveResource(u32 *sectorSize,
- u32 *clusterSize,
- u32 *numClusters,
- u32 *freeClusters)
+Result FSUSER_GetNandArchiveResource(u32 *sectorSize, u32 *clusterSize, u32 *numClusters, u32 *freeClusters)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x815,0,0); // 0x8150000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
-
- if(sectorSize)
- *sectorSize = cmdbuf[2];
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(clusterSize)
- *clusterSize = cmdbuf[3];
-
- if(numClusters)
- *numClusters = cmdbuf[4];
-
- if(freeClusters)
- *freeClusters = cmdbuf[5];
+ if(sectorSize) *sectorSize = cmdbuf[2];
+ if(clusterSize) *clusterSize = cmdbuf[3];
+ if(numClusters) *numClusters = cmdbuf[4];
+ if(freeClusters) *freeClusters = cmdbuf[5];
return cmdbuf[1];
}
-/*! Check if SD card is detected
- *
- * @param[out] detected Output detected state
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08170000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Whether SD is detected
- */
-Result
-FSUSER_IsSdmcDetected(u8 *detected)
+Result FSUSER_IsSdmcDetected(u8 *detected)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x817,0,0); // 0x8170000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(detected)
- *detected = cmdbuf[2];
+ if(detected) *detected = cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-/*! Get curent process mediatype
- *
- * @param[out] mediatype Output curent process mediatype
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08680000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSUSER_GetMediaType(u8* mediatype)
+Result FSUSER_GetMediaType(u8* mediatype)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x868,0,0); // 0x8680000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(mediatype)
- *mediatype = cmdbuf[2];
+ if(mediatype) *mediatype = cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-/*! Check if SD card is writable
- *
- * @param[out] writable Output writable state
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08180000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Whether SD is writable
- */
-Result
-FSUSER_IsSdmcWritable(u8 *writable)
+Result FSUSER_IsSdmcWritable(u8 *writable)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x818,0,0); // 0x8180000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(fsuHandle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(fsuHandle))) return ret;
- if(writable)
- *writable = cmdbuf[2];
+ if(writable) *writable = cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
-/*! Close an open file
- *
- * @param[in] handle Open file handle
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08080000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSFILE_Close(Handle handle)
+Result FSFILE_Close(Handle handle)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x808,0,0); // 0x8080000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
ret = cmdbuf[1];
- if(R_SUCCEEDED(ret))ret = svcCloseHandle(handle);
+ if(R_SUCCEEDED(ret)) ret = svcCloseHandle(handle);
return ret;
}
-/*! Read data from an open file
- *
- * @param[in] handle Open file handle
- * @param[out] bytesRead Number of bytes read
- * @param[in] offset File offset to read from
- * @param[out] buffer Buffer to read into
- * @param[in] size Number of bytes to read
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x080200C2]
- * 1 | offset (low word)
- * 2 | offset (high word)
- * 3 | size
- * 4 | (size << 4) \| 0xC
- * 5 | buffer
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Number of bytes read
- */
-Result
-FSFILE_Read(Handle handle,
- u32 *bytesRead,
- u64 offset,
- void *buffer,
- u32 size)
+Result FSFILE_Read(Handle handle, u32 *bytesRead, u64 offset, void *buffer, u32 size)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[5] = (u32)buffer;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
- if(bytesRead)
- *bytesRead = cmdbuf[2];
+ if(bytesRead) *bytesRead = cmdbuf[2];
return cmdbuf[1];
}
-/*! Write data to an open file
- *
- * @param[in] handle Open file handle
- * @param[out] bytesWritten Number of bytes written
- * @param[in] offset File offset to write to
- * @param[in] buffer Buffer to write from
- * @param[in] size Number of bytes to write
- * @param[in] flushFlags Flush flags
- *
- * @returns error
- *
- * @sa fs_write_flush_flags
- *
- * @warning
- * Using invalid flushFlags can corrupt the archive you're writing to.
- *
- * @warning
- * Data should not be in read-only memory.
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08030102]
- * 1 | offset (low word)
- * 2 | offset (high word)
- * 3 | size
- * 4 | flushFlags
- * 5 | (size << 4) \| 0xA
- * 6 | buffer
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Number of bytes written
- */
-Result
-FSFILE_Write(Handle handle,
- u32 *bytesWritten,
- u64 offset,
- const void *buffer,
- u32 size,
- u32 flushFlags)
+Result FSFILE_Write(Handle handle, u32 *bytesWritten, u64 offset, const void *buffer, u32 size, u32 flushFlags)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[6] = (u32)buffer;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
- if(bytesWritten)
- *bytesWritten = cmdbuf[2];
+ if(bytesWritten) *bytesWritten = cmdbuf[2];
return cmdbuf[1];
}
-/*! Get the size of an open file
- *
- * @param[in] handle Open file handle
- * @param[out] size Output size
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08040000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | File size (lower word)
- * 3 | File size (upper word)
- */
-Result
-FSFILE_GetSize(Handle handle,
- u64 *size)
+Result FSFILE_GetSize(Handle handle, u64 *size)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x804,0,0); // 0x8040000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
- if(size)
- *size = (u64)cmdbuf[2] | ((u64)cmdbuf[3] << 32);
+ if(size) *size = (u64)cmdbuf[2] | ((u64)cmdbuf[3] << 32);
return cmdbuf[1];
}
-/*! Set the size of an open file
- *
- * @param[in] handle Open file handle
- * @param[in] size Size to set
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08050080]
- * 1 | size (lower word)
- * 2 | size (upper word)
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSFILE_SetSize(Handle handle,
- u64 size)
+Result FSFILE_SetSize(Handle handle, u64 size)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[2] = (u32)(size >> 32);
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
-
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
return cmdbuf[1];
}
-/*! Get attributes for an open file
- *
- * @param[in] handle Open file handle
- * @param[out] attributes Output attributes
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08060000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Attributes
- */
-Result
-FSFILE_GetAttributes(Handle handle,
- u32 *attributes)
+Result FSFILE_GetAttributes(Handle handle, u32 *attributes)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x806,0,0); // 0x8060000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
- if(attributes)
- *attributes = cmdbuf[2];
+ if(attributes) *attributes = cmdbuf[2];
return cmdbuf[1];
}
-/*! Set attributes for an open file
- *
- * @param[in] handle Open file handle
- * @param[in] attributes Attributes to set
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08070040]
- * 1 | Attributes
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSFILE_SetAttributes(Handle handle,
- u32 attributes)
+Result FSFILE_SetAttributes(Handle handle, u32 attributes)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[1] = attributes;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
return cmdbuf[1];
}
-/*! Flush an open file
- *
- * @param[in] handle Open file handle
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08090000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSFILE_Flush(Handle handle)
+Result FSFILE_Flush(Handle handle)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x809,0,0); // 0x8090000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
return cmdbuf[1];
}
-/*! Read a directory entry from an open directory
- *
- * @param[in] handle Open directory handle
- * @param[out] entriesRead Output number of entries read
- * @param[in] entryCount Number of entries to read
- * @param[out] buffer Output buffer
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08010042]
- * 1 | entryCount
- * 2 | ((entrycount*0x228) << 4) \| 0xC
- * 3 | buffer
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- * 2 | Number of entries read
- */
-Result
-FSDIR_Read(Handle handle,
- u32 *entriesRead,
- u32 entryCount,
- FS_dirent *buffer)
+Result FSDIR_Read(Handle handle, u32 *entriesRead, u32 entryCount, FS_dirent *buffer)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[3] = (u32)buffer;
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
- if(entriesRead)
- *entriesRead = cmdbuf[2];
+ if(entriesRead) *entriesRead = cmdbuf[2];
return cmdbuf[1];
}
-/*! Close an open directory
- *
- * @param[in] handle Open directory handle
- *
- * @returns error
- *
- * @internal
- *
- * #### Request
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code [0x08020000]
- *
- * #### Response
- *
- * Index Word | Description
- * -----------|-------------------------
- * 0 | Header code
- * 1 | Result code
- */
-Result
-FSDIR_Close(Handle handle)
+Result FSDIR_Close(Handle handle)
{
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x802,0,0); // 0x8020000
Result ret = 0;
- if(R_FAILED(ret = svcSendSyncRequest(handle)))
- return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(handle))) return ret;
+
ret = cmdbuf[1];
- if(R_SUCCEEDED(ret))ret = svcCloseHandle(handle);
+ if(R_SUCCEEDED(ret)) ret = svcCloseHandle(handle);
+
return ret;
}
-/*
- gsp.c _ Gpu/lcd stuff.
-*/
-
#include <stdlib.h>
#include <string.h>
#include <3ds/types.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
#include <3ds/synchronization.h>
-#include <3ds/services/gsp.h>
+#include <3ds/services/gspgpu.h>
+#include <3ds/ipc.h>
#define GSP_EVENT_STACK_SIZE 0x1000
Handle gspGpuHandle;
-Handle gspLcdHandle;
-Handle gspEvents[GSPEVENT_MAX];
-vu32 gspEventCounts[GSPEVENT_MAX];
+static int gspRefCount;
+
+Handle gspEvents[GSPGPU_EVENT_MAX];
+vu32 gspEventCounts[GSPGPU_EVENT_MAX];
u64 gspEventStack[GSP_EVENT_STACK_SIZE/sizeof(u64)]; //u64 so that it's 8-byte aligned
volatile bool gspRunEvents;
Handle gspEventThread;
static Handle gspEvent;
-static int gspRefCount, gspLcdRefCount;
static vu8* gspEventData;
static void gspEventThreadMain(void *arg);
{
// Create events
int i;
- for (i = 0; i < GSPEVENT_MAX; i ++)
+ for (i = 0; i < GSPGPU_EVENT_MAX; i ++)
{
Result rc = svcCreateEvent(&gspEvents[i], 0);
if (rc != 0)
// Free events
int i;
- for (i = 0; i < GSPEVENT_MAX; i ++)
+ for (i = 0; i < GSPGPU_EVENT_MAX; i ++)
svcCloseHandle(gspEvents[i]);
}
-void gspWaitForEvent(GSP_Event id, bool nextEvent)
+void gspWaitForEvent(GSPGPU_Event id, bool nextEvent)
{
- if(id>=GSPEVENT_MAX)return;
+ if(id>= GSPGPU_EVENT_MAX)return;
if (nextEvent)
svcClearEvent(gspEvents[id]);
if (curEvt == -1)
break;
- if (curEvt < GSPEVENT_MAX) {
+ if (curEvt < GSPGPU_EVENT_MAX) {
svcSignalEvent(gspEvents[curEvt]);
gspEventCounts[curEvt]++;
}
svcExitThread();
}
+//essentially : get commandIndex and totalCommands, calculate offset of new command, copy command and update totalCommands
+//use LDREX/STREX because this data may also be accessed by the GSP module and we don't want to break stuff
+//(mostly, we could overwrite the buffer header with wrong data and make the GSP module reexecute old commands)
+Result gspSubmitGxCommand(u32* sharedGspCmdBuf, u32 gxCommand[0x8])
+{
+ if(!sharedGspCmdBuf || !gxCommand)return -1;
+
+ u32 cmdBufHeader = __ldrex((s32*)sharedGspCmdBuf);
+
+ u8 commandIndex=cmdBufHeader&0xFF;
+ u8 totalCommands=(cmdBufHeader>>8)&0xFF;
+
+ if(totalCommands>=15)return -2;
+
+ u8 nextCmd=(commandIndex+totalCommands)%15; //there are 15 command slots
+ u32* dst=&sharedGspCmdBuf[8*(1+nextCmd)];
+ memcpy(dst, gxCommand, 0x20);
+
+ __dsb();
+ totalCommands++;
+ cmdBufHeader=((cmdBufHeader)&0xFFFF00FF)|(((u32)totalCommands)<<8);
+
+ while(1)
+ {
+ if (!__strex((s32*)sharedGspCmdBuf, cmdBufHeader)) break;
+
+ cmdBufHeader = __ldrex((s32*)sharedGspCmdBuf);
+ totalCommands=((cmdBufHeader&0xFF00)>>8)+1;
+ cmdBufHeader=((cmdBufHeader)&0xFFFF00FF)|((totalCommands<<8)&0xFF00);
+ }
+
+ if(totalCommands==1)return GSPGPU_TriggerCmdReqQueue();
+ return 0;
+}
+
Result GSPGPU_WriteHWRegs(u32 regAddr, u32* data, u8 size)
{
if(size>0x80 || !data)return -1;
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00010082; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x1,2,2); // 0x10082
cmdbuf[1]=regAddr;
cmdbuf[2]=size;
- cmdbuf[3]=(size<<14)|2;
+ cmdbuf[3]=IPC_Desc_StaticBuffer(size, 0);
cmdbuf[4]=(u32)data;
Result ret=0;
if(datasize>0x80 || !data)return -1;
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00020084; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x2,2,4); // 0x20084
cmdbuf[1]=regAddr;
cmdbuf[2]=datasize;
- cmdbuf[3]=(datasize<<14)|2;
+ cmdbuf[3]=IPC_Desc_StaticBuffer(datasize, 0);
cmdbuf[4]=(u32)data;
- cmdbuf[5]=(masksize<<14)|0x402;
+ cmdbuf[5]=IPC_Desc_StaticBuffer(masksize, 1);
cmdbuf[6]=(u32)maskdata;
Result ret=0;
if(size>0x80 || !data)return -1;
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00040080; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x4,2,0); // 0x40080
cmdbuf[1]=regAddr;
cmdbuf[2]=size;
- cmdbuf[0x40]=(size<<14)|2;
+ cmdbuf[0x40]=IPC_Desc_StaticBuffer(size, 0);
cmdbuf[0x40+1]=(u32)data;
Result ret=0;
return cmdbuf[1];
}
-Result GSPGPU_SetBufferSwap(u32 screenid, GSP_FramebufferInfo *framebufinfo)
+Result GSPGPU_SetBufferSwap(u32 screenid, GSPGPU_FramebufferInfo*framebufinfo)
{
u32 *cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00050200;
+ cmdbuf[0] = IPC_MakeHeader(0x5,8,0); // 0x50200
cmdbuf[1] = screenid;
- memcpy(&cmdbuf[2], framebufinfo, sizeof(GSP_FramebufferInfo));
+ memcpy(&cmdbuf[2], framebufinfo, sizeof(GSPGPU_FramebufferInfo));
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
Result GSPGPU_FlushDataCache(const void* adr, u32 size)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00080082; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x8,2,2); // 0x80082
cmdbuf[1]=(u32)adr;
cmdbuf[2]=size;
- cmdbuf[3]=0x0;
+ cmdbuf[3]=IPC_Desc_SharedHandles(1);
cmdbuf[4]=CUR_PROCESS_HANDLE;
Result ret=0;
{
u32 *cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = 0x00090082;
+ cmdbuf[0] = IPC_MakeHeader(0x9,2,2); // 0x90082
cmdbuf[1] = (u32)adr;
cmdbuf[2] = size;
- cmdbuf[3] = 0;
+ cmdbuf[3] = IPC_Desc_SharedHandles(1);
cmdbuf[4] = CUR_PROCESS_HANDLE;
Result ret=0;
Result GSPGPU_SetLcdForceBlack(u8 flags)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x000B0040; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0xB,1,0); // 0xB0040
cmdbuf[1]=flags;
Result ret=0;
Result GSPGPU_TriggerCmdReqQueue(void)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x000C0000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0xC,0,0); // 0xC0000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
Result GSPGPU_RegisterInterruptRelayQueue(Handle eventHandle, u32 flags, Handle* outMemHandle, u8* threadID)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00130042; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x13,1,2); // 0x130042
cmdbuf[1]=flags;
- cmdbuf[2]=0x0;
+ cmdbuf[2]=IPC_Desc_SharedHandles(1);
cmdbuf[3]=eventHandle;
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
- if(threadID)*threadID=cmdbuf[2];
+ if(threadID)*threadID=cmdbuf[2] & 0xFF;
if(outMemHandle)*outMemHandle=cmdbuf[4];
return cmdbuf[1];
Result GSPGPU_UnregisterInterruptRelayQueue(void)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00140000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x14,0,0); // 0x140000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
Result GSPGPU_AcquireRight(u8 flags)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x160042; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x16,1,2); // 0x160042
cmdbuf[1]=flags;
- cmdbuf[2]=0x0;
+ cmdbuf[2]=IPC_Desc_SharedHandles(1);
cmdbuf[3]=CUR_PROCESS_HANDLE;
Result ret=0;
Result GSPGPU_ReleaseRight(void)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x170000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x17,0,0); // 0x170000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
return cmdbuf[1];
}
-Result GSPGPU_ImportDisplayCaptureInfo(GSP_CaptureInfo *captureinfo)
+Result GSPGPU_ImportDisplayCaptureInfo(GSPGPU_CaptureInfo*captureinfo)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00180000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x18,0,0); // 0x180000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
ret = cmdbuf[1];
- if(R_SUCCEEDED(ret))
- memcpy(captureinfo, &cmdbuf[2], 0x20);
+ if(R_SUCCEEDED(ret)) memcpy(captureinfo, &cmdbuf[2], 0x20);
return ret;
}
Result GSPGPU_SaveVramSysArea(void)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x00190000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x19,0,0); // 0x190000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
Result GSPGPU_RestoreVramSysArea(void)
{
u32* cmdbuf=getThreadCommandBuffer();
- cmdbuf[0]=0x001A0000; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x1A,0,0); // 0x1A0000
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(gspGpuHandle)))return ret;
return cmdbuf[1];
}
-//essentially : get commandIndex and totalCommands, calculate offset of new command, copy command and update totalCommands
-//use LDREX/STREX because this data may also be accessed by the GSP module and we don't want to break stuff
-//(mostly, we could overwrite the buffer header with wrong data and make the GSP module reexecute old commands)
-Result GSPGPU_SubmitGxCommand(u32* sharedGspCmdBuf, u32 gxCommand[0x8])
-{
- if(!sharedGspCmdBuf || !gxCommand)return -1;
-
- u32 cmdBufHeader = __ldrex((s32*)sharedGspCmdBuf);
-
- u8 commandIndex=cmdBufHeader&0xFF;
- u8 totalCommands=(cmdBufHeader>>8)&0xFF;
-
- if(totalCommands>=15)return -2;
-
- u8 nextCmd=(commandIndex+totalCommands)%15; //there are 15 command slots
- u32* dst=&sharedGspCmdBuf[8*(1+nextCmd)];
- memcpy(dst, gxCommand, 0x20);
-
- __dsb();
- totalCommands++;
- cmdBufHeader=((cmdBufHeader)&0xFFFF00FF)|(((u32)totalCommands)<<8);
-
- while(1)
- {
- if (!__strex((s32*)sharedGspCmdBuf, cmdBufHeader)) break;
-
- cmdBufHeader = __ldrex((s32*)sharedGspCmdBuf);
- totalCommands=((cmdBufHeader&0xFF00)>>8)+1;
- cmdBufHeader=((cmdBufHeader)&0xFFFF00FF)|((totalCommands<<8)&0xFF00);
- }
-
- if(totalCommands==1)return GSPGPU_TriggerCmdReqQueue();
- return 0;
-}
-
-Result gspLcdInit(void)
-{
- Result res=0;
- if (AtomicPostIncrement(&gspLcdRefCount)) return 0;
- res = srvGetServiceHandle(&gspLcdHandle, "gsp::Lcd");
- if (R_FAILED(res)) AtomicDecrement(&gspLcdRefCount);
- return res;
-}
-
-void gspLcdExit(void)
-{
- if (AtomicDecrement(&gspLcdRefCount)) return;
- svcCloseHandle(gspLcdHandle);
-}
-
-Result GSPLCD_PowerOffBacklight(GSPLCD_Screens screen)
-{
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = 0x00120040;
- cmdbuf[1] = screen;
-
- Result ret=0;
- if (R_FAILED(ret = svcSendSyncRequest(gspLcdHandle)))return ret;
-
- return cmdbuf[1];
-}
-
-Result GSPLCD_PowerOnBacklight(GSPLCD_Screens screen)
-{
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = 0x00110040;
- cmdbuf[1] = screen;
-
- Result ret=0;
- if (R_FAILED(ret = svcSendSyncRequest(gspLcdHandle)))return ret;
-
- return cmdbuf[1];
-}
--- /dev/null
+#include <stdlib.h>
+#include <string.h>
+#include <3ds/types.h>
+#include <3ds/ipc.h>
+#include <3ds/result.h>
+#include <3ds/svc.h>
+#include <3ds/srv.h>
+#include <3ds/synchronization.h>
+#include <3ds/services/gsplcd.h>
+
+Handle gspLcdHandle;
+static int gspLcdRefCount;
+
+Result gspLcdInit(void)
+{
+ Result res=0;
+ if (AtomicPostIncrement(&gspLcdRefCount)) return 0;
+ res = srvGetServiceHandle(&gspLcdHandle, "gsp::Lcd");
+ if (R_FAILED(res)) AtomicDecrement(&gspLcdRefCount);
+ return res;
+}
+
+void gspLcdExit(void)
+{
+ if (AtomicDecrement(&gspLcdRefCount)) return;
+ svcCloseHandle(gspLcdHandle);
+}
+
+Result GSPLCD_PowerOnBacklight(u32 screen)
+{
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x11,1,0); // 0x110040
+ cmdbuf[1] = screen;
+
+ Result ret=0;
+ if (R_FAILED(ret = svcSendSyncRequest(gspLcdHandle))) return ret;
+
+ return cmdbuf[1];
+}
+
+Result GSPLCD_PowerOffBacklight(u32 screen)
+{
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x12,1,0); // 0x120040
+ cmdbuf[1] = screen;
+
+ Result ret=0;
+ if (R_FAILED(ret = svcSendSyncRequest(gspLcdHandle))) return ret;
+
+ return cmdbuf[1];
+}
+
#include <3ds/result.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
-#include <3ds/mappable.h>
+#include <3ds/allocator/mappable.h>
#include <3ds/synchronization.h>
#include <3ds/services/apt.h>
#include <3ds/services/hid.h>
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(hidHandle)))return ret;
- *volume = (u8)cmdbuf[2];
+ *volume = (u8)cmdbuf[2] & 0xFF;
return cmdbuf[1];
}
return HTTPC_ReceiveData(context->servhandle, context->httphandle, buffer, size);
}
-Result httpcGetRequestState(httpcContext *context, httpcReqStatus* out)
+Result httpcGetRequestState(httpcContext *context, HTTPC_RequestStatus* out)
{
return HTTPC_GetRequestState(context->servhandle, context->httphandle, out);
}
return cmdbuf[1];
}
-Result HTTPC_GetRequestState(Handle handle, Handle contextHandle, httpcReqStatus* out)
+Result HTTPC_GetRequestState(Handle handle, Handle contextHandle, HTTPC_RequestStatus* out)
{
u32* cmdbuf=getThreadCommandBuffer();
int name_len=strlen(name)+1;
- cmdbuf[0]=0x001e00c4; //request header code
+ cmdbuf[0]=IPC_MakeHeader(0x1E,3,4); // 0x1E00C4
cmdbuf[1]=contextHandle;
cmdbuf[2]=name_len;
cmdbuf[3]=valuebuf_maxsize;
- cmdbuf[4]=(name_len<<14)|0xC02;
+ cmdbuf[4]=IPC_Desc_StaticBuffer(name_len, 3);
cmdbuf[5]=(u32)name;
- cmdbuf[6]=(valuebuf_maxsize<<4)|0xC;
+ cmdbuf[6]=IPC_Desc_Buffer(valuebuf_maxsize, IPC_BUFFER_W);
cmdbuf[7]=(u32)value;
Result ret=0;
#include <3ds/services/ir.h>
#include <3ds/ipc.h>
-static Handle iru_handle;
-static Handle iru_sharedmem_handle;
-static u32 *iru_sharedmem;
-static u32 iru_sharedmem_size;
-static int iru_refcount;
+static Handle iruHandle;
+static Handle iruSharedMemHandle;
+static u32 *iruSharedMem;
+static u32 iruSharedMemSize;
+static int iruRefCount;
-Result irucmd_Initialize(void)
+Result iruInit(u32 *sharedmem_addr, u32 sharedmem_size)
+{
+ Result ret = 0;
+
+ if(AtomicPostIncrement(&iruRefCount)) return 0;
+
+ ret = srvGetServiceHandle(&iruHandle, "ir:u");
+ if(R_FAILED(ret))goto cleanup0;
+
+ ret = IRU_Initialize();
+ if(R_FAILED(ret))goto cleanup1;
+
+ ret = svcCreateMemoryBlock(&iruSharedMemHandle, (u32)sharedmem_addr, sharedmem_size, 1, 3);
+ if(R_FAILED(ret))goto cleanup2;
+
+ iruSharedMem = sharedmem_addr;
+ iruSharedMemSize = sharedmem_size;
+
+ return ret;
+
+cleanup2:
+ IRU_Shutdown();
+cleanup1:
+ svcCloseHandle(iruHandle);
+cleanup0:
+ AtomicDecrement(&iruRefCount);
+ return ret;
+}
+
+void iruExit(void)
+{
+ if(AtomicDecrement(&iruRefCount)) return;
+
+ IRU_Shutdown();
+ svcCloseHandle(iruHandle);
+ svcCloseHandle(iruSharedMemHandle);
+
+ iruHandle = 0;
+ iruSharedMemHandle = 0;
+}
+
+Handle iruGetServHandle(void)
+{
+ return iruHandle;
+}
+
+Result iruSendData(u8 *buf, u32 size, bool wait)
+{
+ Result ret = 0;
+
+ ret = IRU_StartSendTransfer(buf, size);
+ if(R_FAILED(ret))return ret;
+
+ if(!wait)return 0;
+
+ return IRU_WaitSendTransfer();
+}
+
+Result iruRecvData(u8 *buf, u32 size, u8 flag, u32 *transfercount, bool wait)
+{
+ Result ret = 0;
+
+ *transfercount = 0;
+
+ ret = IRU_StartRecvTransfer(size, flag);
+ if(R_FAILED(ret))return ret;
+
+ if(wait)
+ {
+ ret = IRU_WaitRecvTransfer(transfercount);
+ if(R_FAILED(ret))return ret;
+
+ if(buf)memcpy(buf, iruSharedMem, size);
+ }
+
+ return 0;
+}
+
+Result IRU_Initialize(void)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1,0,0); // 0x10000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
}
-Result irucmd_Shutdown(void)
+Result IRU_Shutdown(void)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x2,0,0); // 0x20000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
}
-Result irucmd_StartSendTransfer(u8 *buf, u32 size)
+Result IRU_StartSendTransfer(u8 *buf, u32 size)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[2] = IPC_Desc_Buffer(size,IPC_BUFFER_R);
cmdbuf[3] = (u32)buf;
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
}
-Result irucmd_WaitSendTransfer(void)
+Result IRU_WaitSendTransfer(void)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x4,0,0); // 0x40000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
}
-Result irucmd_StartRecvTransfer(u32 size, u8 flag)
+Result IRU_StartRecvTransfer(u32 size, u8 flag)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x5,3,2); // 0x500C2
- cmdbuf[1] = iru_sharedmem_size;
+ cmdbuf[1] = iruSharedMemSize;
cmdbuf[2] = size;
cmdbuf[3] = (u8)flag;
cmdbuf[4] = IPC_Desc_SharedHandles(1);
- cmdbuf[5] = iru_sharedmem_handle;
+ cmdbuf[5] = iruSharedMemHandle;
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
}
-Result irucmd_WaitRecvTransfer(u32 *transfercount)
+Result IRU_WaitRecvTransfer(u32 *transfercount)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x6,0,0); // 0x60000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
*transfercount = cmdbuf[2];
cmdbuf[0] = IPC_MakeHeader(0x9,1,0); // 0x90040
cmdbuf[1] = (u32)value;
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
cmdbuf[0] = IPC_MakeHeader(0xA,0,0); // 0xA0000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
- *out = (u8)cmdbuf[2];
+ *out = (u8)cmdbuf[2] & 0xFF;
return ret;
}
cmdbuf[0] = IPC_MakeHeader(0xB,1,0); // 0xB0040
cmdbuf[1] = value;
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
return ret;
cmdbuf[0] = IPC_MakeHeader(0xC,0,0); // 0xC0000
- if(R_FAILED(ret = svcSendSyncRequest(iru_handle)))return ret;
+ if(R_FAILED(ret = svcSendSyncRequest(iruHandle)))return ret;
ret = (Result)cmdbuf[1];
*out = cmdbuf[2];
return ret;
}
-
-Result iruInit(u32 *sharedmem_addr, u32 sharedmem_size)
-{
- Result ret = 0;
-
- if(AtomicPostIncrement(&iru_refcount)) return 0;
-
- ret = srvGetServiceHandle(&iru_handle, "ir:u");
- if(R_FAILED(ret))goto cleanup0;
-
- ret = irucmd_Initialize();
- if(R_FAILED(ret))goto cleanup1;
-
- ret = svcCreateMemoryBlock(&iru_sharedmem_handle, (u32)sharedmem_addr, sharedmem_size, 1, 3);
- if(R_FAILED(ret))goto cleanup2;
-
- iru_sharedmem = sharedmem_addr;
- iru_sharedmem_size = sharedmem_size;
-
- return ret;
-
-cleanup2:
- irucmd_Shutdown();
-cleanup1:
- svcCloseHandle(iru_handle);
-cleanup0:
- AtomicDecrement(&iru_refcount);
- return ret;
-}
-
-void iruExit(void)
-{
- if(AtomicDecrement(&iru_refcount)) return;
-
- irucmd_Shutdown();
- svcCloseHandle(iru_handle);
- svcCloseHandle(iru_sharedmem_handle);
-
- iru_handle = 0;
- iru_sharedmem_handle = 0;
-}
-
-Handle iruGetServHandle(void)
-{
- return iru_handle;
-}
-
-Result iruSendData(u8 *buf, u32 size, bool wait)
-{
- Result ret = 0;
-
- ret = irucmd_StartSendTransfer(buf, size);
- if(R_FAILED(ret))return ret;
-
- if(!wait)return 0;
-
- return irucmd_WaitSendTransfer();
-}
-
-Result iruRecvData(u8 *buf, u32 size, u8 flag, u32 *transfercount, bool wait)
-{
- Result ret = 0;
-
- *transfercount = 0;
-
- ret = irucmd_StartRecvTransfer(size, flag);
- if(R_FAILED(ret))return ret;
-
- if(wait)
- {
- ret = irucmd_WaitRecvTransfer(transfercount);
- if(R_FAILED(ret))return ret;
-
- if(buf)memcpy(buf, iru_sharedmem, size);
- }
-
- return 0;
-}
-
#include <3ds/result.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
-#include <3ds/mappable.h>
+#include <3ds/allocator/mappable.h>
#include <3ds/synchronization.h>
#include <3ds/services/irrst.h>
#include <3ds/ipc.h>
#include <3ds/svc.h>
#include <3ds/srv.h>
#include <3ds/os.h>
-#include <3ds/linear.h>
+#include <3ds/allocator/linear.h>
#include <3ds/synchronization.h>
#include <3ds/services/mvd.h>
#include <3ds/ipc.h>
Handle mvdstdHandle;
static int mvdstdRefCount;
-static mvdstdMode mvdstd_mode;
-static mvdstdTypeInput mvdstd_input_type;
-static mvdstdTypeOutput mvdstd_output_type;
+static MVDSTD_Mode mvdstd_mode;
+static MVDSTD_InputFormat mvdstd_input_type;
+static MVDSTD_OutputFormat mvdstd_output_type;
static u32 *mvdstd_workbuf;
static size_t mvdstd_workbufsize;
-static Result mvdstdipc_Initialize(u32 *buf, u32 bufsize, Handle kprocess)
+static Result MVDSTD_Initialize(u32* buf, u32 bufsize)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1,2,2); // 0x10082
cmdbuf[1] = (u32)buf;
cmdbuf[2] = bufsize;
cmdbuf[3] = IPC_Desc_SharedHandles(1);
- cmdbuf[4] = kprocess;
+ cmdbuf[4] = CUR_PROCESS_HANDLE;
Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(mvdstdHandle)))return ret;
return cmdbuf[1];
}
-static Result mvdstdipc_Shutdown(void)
+static Result MVDSTD_Shutdown(void)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x2,0,0); // 0x20000
return cmdbuf[1];
}
-static Result mvdstdipc_cmd18(void)
+static Result MVDSTD_cmd18(void)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x18,0,0); // 0x180000
return cmdbuf[1];
}
-static Result mvdstdipc_cmd19(void)
+static Result MVDSTD_cmd19(void)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x19,0,0); // 0x190000
return cmdbuf[1];
}
-static Result mvdstdipc_cmd1a(void)
+static Result MVDSTD_cmd1a(void)
{
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1A,0,0); // 0x1A0000
return cmdbuf[1];
}
-Result mvdstdSetConfig(mvdstdConfig *config)
+Result MVDSTD_SetConfig(MVDSTD_Config* config)
{
+ Result ret=0;
u32* cmdbuf = getThreadCommandBuffer();
+
cmdbuf[0] = IPC_MakeHeader(0x1E,1,4); // 0x1E0044
- cmdbuf[1] = sizeof(mvdstdConfig);
+ cmdbuf[1] = sizeof(MVDSTD_Config);
cmdbuf[2] = IPC_Desc_SharedHandles(1);
cmdbuf[3] = CUR_PROCESS_HANDLE;
- cmdbuf[4] = IPC_Desc_Buffer(sizeof(mvdstdConfig),IPC_BUFFER_R);
+ cmdbuf[4] = IPC_Desc_Buffer(sizeof(MVDSTD_Config),IPC_BUFFER_R);
cmdbuf[5] = (u32)config;
- Result ret=0;
if(R_FAILED(ret=svcSendSyncRequest(mvdstdHandle)))return ret;
return cmdbuf[1];
}
-void mvdstdGenerateDefaultConfig(mvdstdConfig *config, u32 input_width, u32 input_height, u32 output_width, u32 output_height, u32 *vaddr_colorconv_indata, u32 *vaddr_outdata0, u32 *vaddr_outdata1_colorconv)
-{
- memset(config, 0, sizeof(mvdstdConfig));
-
- config->input_type = mvdstd_input_type;
-
- config->inwidth = input_width;
- config->inheight = input_height;
-
- if(mvdstd_mode==MVDMODE_COLORFORMATCONV)config->physaddr_colorconv_indata = osConvertVirtToPhys((u32)vaddr_colorconv_indata);
-
- if(mvdstd_mode==MVDMODE_VIDEOPROCESSING)
- {
- config->flag_x40 = 1;
- config->outheight0 = output_height;
- config->outwidth0 = output_width;
- }
-
- config->output_type = mvdstd_output_type;
-
- config->outwidth1 = output_width;
- config->outheight1 = output_height;
-
- config->physaddr_outdata0 = osConvertVirtToPhys((u32)vaddr_outdata0);
- if(mvdstd_mode==MVDMODE_COLORFORMATCONV)config->physaddr_outdata1_colorconv = osConvertVirtToPhys((u32)vaddr_outdata1_colorconv);
-
- config->unk_x6c[0] = 0x1;
- config->unk_x6c[(0x84-0x6c)>>2] = 0x12a;
- config->unk_x6c[(0x88-0x6c)>>2] = 0x199;
- config->unk_x6c[(0x8c-0x6c)>>2] = 0xd0;
- config->unk_x6c[(0x90-0x6c)>>2] = 0x64;
- config->unk_x6c[(0x94-0x6c)>>2] = 0x204;
- config->unk_x6c[(0xa8-0x6c)>>2] = 0x1;
- config->unk_x6c[(0x104-0x6c)>>2] = 0x1;
- config->unk_x6c[(0x110-0x6c)>>2] = 0x200;
- config->unk_x6c[(0x114-0x6c)>>2] = 0x100;
-}
-
-Result mvdstdInit(mvdstdMode mode, mvdstdTypeInput input_type, mvdstdTypeOutput output_type, u32 size)
+Result mvdstdInit(MVDSTD_Mode mode, MVDSTD_InputFormat input_type, MVDSTD_OutputFormat output_type, u32 size)
{
Result ret=0;
mvdstd_workbuf = linearAlloc(mvdstd_workbufsize);
if(mvdstd_workbuf==NULL) goto cleanup1;
- ret = mvdstdipc_Initialize((u32*)osConvertOldLINEARMemToNew((u32)mvdstd_workbuf), mvdstd_workbufsize, CUR_PROCESS_HANDLE);
+ ret = MVDSTD_Initialize((u32*) osConvertOldLINEARMemToNew((u32) mvdstd_workbuf), mvdstd_workbufsize);
if(R_FAILED(ret)) goto cleanup2;
- ret = mvdstdipc_cmd18();
+ ret = MVDSTD_cmd18();
if(R_FAILED(ret)) goto cleanup3;
return ret;
cleanup3:
- mvdstdipc_Shutdown();
+ MVDSTD_Shutdown();
cleanup2:
linearFree(mvdstd_workbuf);
cleanup1:
if(mvdstd_mode==MVDMODE_COLORFORMATCONV)
{
- mvdstdipc_cmd19();
+ MVDSTD_cmd19();
}
- mvdstdipc_Shutdown();
+ MVDSTD_Shutdown();
svcCloseHandle(mvdstdHandle);
linearFree(mvdstd_workbuf);
}
-Result mvdstdProcessFrame(mvdstdConfig *config, u32 *h264_vaddr_inframe, u32 h264_inframesize, u32 h264_frameid)
+void mvdstdGenerateDefaultConfig(MVDSTD_Config*config, u32 input_width, u32 input_height, u32 output_width, u32 output_height, u32 *vaddr_colorconv_indata, u32 *vaddr_outdata0, u32 *vaddr_outdata1_colorconv)
+{
+ memset(config, 0, sizeof(MVDSTD_Config));
+
+ config->input_type = mvdstd_input_type;
+
+ config->inwidth = input_width;
+ config->inheight = input_height;
+
+ if(mvdstd_mode==MVDMODE_COLORFORMATCONV)config->physaddr_colorconv_indata = osConvertVirtToPhys((u32)vaddr_colorconv_indata);
+
+ if(mvdstd_mode==MVDMODE_VIDEOPROCESSING)
+ {
+ config->flag_x40 = 1;
+ config->outheight0 = output_height;
+ config->outwidth0 = output_width;
+ }
+
+ config->output_type = mvdstd_output_type;
+
+ config->outwidth1 = output_width;
+ config->outheight1 = output_height;
+
+ config->physaddr_outdata0 = osConvertVirtToPhys((u32)vaddr_outdata0);
+ if(mvdstd_mode==MVDMODE_COLORFORMATCONV)config->physaddr_outdata1_colorconv = osConvertVirtToPhys((u32)vaddr_outdata1_colorconv);
+
+ config->unk_x6c[0] = 0x1;
+ config->unk_x6c[(0x84-0x6c)>>2] = 0x12a;
+ config->unk_x6c[(0x88-0x6c)>>2] = 0x199;
+ config->unk_x6c[(0x8c-0x6c)>>2] = 0xd0;
+ config->unk_x6c[(0x90-0x6c)>>2] = 0x64;
+ config->unk_x6c[(0x94-0x6c)>>2] = 0x204;
+ config->unk_x6c[(0xa8-0x6c)>>2] = 0x1;
+ config->unk_x6c[(0x104-0x6c)>>2] = 0x1;
+ config->unk_x6c[(0x110-0x6c)>>2] = 0x200;
+ config->unk_x6c[(0x114-0x6c)>>2] = 0x100;
+}
+
+Result mvdstdProcessFrame(MVDSTD_Config*config, u32 *h264_vaddr_inframe, u32 h264_inframesize, u32 h264_frameid)
{
Result ret;
if(config==NULL)return -1;
if(mvdstd_mode!=MVDMODE_COLORFORMATCONV)return -2;
- ret = mvdstdSetConfig(config);
+ ret = MVDSTD_SetConfig(config);
if(R_FAILED(ret))return ret;
- return mvdstdipc_cmd1a();
+ return MVDSTD_cmd1a();
}
if(R_FAILED(ret = svcSendSyncRequest(nsHandle)))return ret;
- if(procid != NULL)
- *procid = cmdbuf[2];
+ if(procid != NULL) *procid = cmdbuf[2];
return (Result)cmdbuf[1];
}
if(R_FAILED(ret = svcSendSyncRequest(nsHandle)))return ret;
return (Result)cmdbuf[1];
-}
\ No newline at end of file
+}
svcCloseHandle(psHandle);
}
-Result PS_EncryptDecryptAes(u32 size, u8* in, u8* out, u32 aes_algo, u32 key_type, u8* iv)
+Result PS_EncryptDecryptAes(u32 size, u8* in, u8* out, PS_AESAlgorithm aes_algo, PS_AESKeyType key_type, u8* iv)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
if(R_FAILED(ret = svcSendSyncRequest(psHandle)))return ret;
- _iv[0] = cmdbuf[2];
- _iv[1] = cmdbuf[3];
- _iv[2] = cmdbuf[4];
- _iv[3] = cmdbuf[5];
+ _iv[0] = cmdbuf[2] & 0xFF;
+ _iv[1] = cmdbuf[3] & 0xFF;
+ _iv[2] = cmdbuf[4] & 0xFF;
+ _iv[3] = cmdbuf[5] & 0xFF;
return (Result)cmdbuf[1];
}
-Result PS_EncryptSignDecryptVerifyAesCcm(u8* in, u32 in_size, u8* out, u32 out_size, u32 data_len, u32 mac_data_len, u32 mac_len, u32 aes_algo, u32 key_type, u8* nonce)
+Result PS_EncryptSignDecryptVerifyAesCcm(u8* in, u32 in_size, u8* out, u32 out_size, u32 data_len, u32 mac_data_len, u32 mac_len, PS_AESAlgorithm aes_algo, PS_AESKeyType key_type, u8* nonce)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
+++ /dev/null
-#include <stdlib.h>
-#include <3ds/types.h>
-#include <3ds/result.h>
-#include <3ds/svc.h>
-#include <3ds/srv.h>
-#include <3ds/synchronization.h>
-#include <3ds/services/ptm.h>
-#include <3ds/ipc.h>
-
-static Handle ptmHandle, ptmSysmHandle;
-static int ptmRefCount, ptmSysmRefCount;
-
-Result ptmInit(void)
-{
- if (AtomicPostIncrement(&ptmRefCount)) return 0;
- Result res = srvGetServiceHandle(&ptmHandle, "ptm:u");
- if (R_FAILED(res)) AtomicDecrement(&ptmRefCount);
- return res;
-}
-
-void ptmExit(void)
-{
- if (AtomicDecrement(&ptmRefCount)) return;
- svcCloseHandle(ptmHandle);
-}
-
-Result ptmSysmInit(void)
-{
- if (AtomicPostIncrement(&ptmSysmRefCount)) return 0;
- Result res = srvGetServiceHandle(&ptmSysmHandle, "ptm:sysm");
- if (R_FAILED(res)) AtomicDecrement(&ptmSysmRefCount);
- return res;
-}
-
-void ptmSysmExit(void)
-{
- if (AtomicDecrement(&ptmSysmRefCount)) return;
- svcCloseHandle(ptmSysmHandle);
-}
-
-Result PTMU_GetShellState(u8 *out)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x6,0,0); // 0x60000
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmHandle)))return ret;
-
- *out = (u8)cmdbuf[2];
-
- return (Result)cmdbuf[1];
-}
-
-Result PTMU_GetBatteryLevel(u8 *out)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x7,0,0); // 0x70000
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmHandle)))return ret;
-
- *out = (u8)cmdbuf[2];
-
- return (Result)cmdbuf[1];
-}
-
-Result PTMU_GetBatteryChargeState(u8 *out)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x8,0,0); // 0x80000
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmHandle)))return ret;
-
- *out = (u8)cmdbuf[2];
-
- return (Result)cmdbuf[1];
-}
-
-Result PTMU_GetPedometerState(u8 *out)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x9,0,0); // 0x90000
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmHandle)))return ret;
-
- *out = (u8)cmdbuf[2];
-
- return (Result)cmdbuf[1];
-}
-
-Result PTMU_GetTotalStepCount(u32 *steps)
-{
- Result ret=0;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0xC,0,0); // 0xC0000
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmHandle)))return ret;
-
- *steps = cmdbuf[2];
-
- return (Result)cmdbuf[1];
-}
-
-Result PTMSYSM_ConfigureNew3DSCPU(u8 value)
-{
- Result ret;
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x818,1,0); // 0x08180040
- cmdbuf[1] = value;
-
- if(R_FAILED(ret = svcSendSyncRequest(ptmSysmHandle)))return ret;
-
- return (Result)cmdbuf[1];
-}
--- /dev/null
+#include <stdlib.h>
+#include <3ds/types.h>
+#include <3ds/result.h>
+#include <3ds/svc.h>
+#include <3ds/srv.h>
+#include <3ds/synchronization.h>
+#include <3ds/services/ptmsysm.h>
+#include <3ds/ipc.h>
+
+static Handle ptmSysmHandle;
+static int ptmSysmRefCount;
+
+Result ptmSysmInit(void)
+{
+ if (AtomicPostIncrement(&ptmSysmRefCount)) return 0;
+ Result res = srvGetServiceHandle(&ptmSysmHandle, "ptm:sysm");
+ if (R_FAILED(res)) AtomicDecrement(&ptmSysmRefCount);
+ return res;
+}
+
+void ptmSysmExit(void)
+{
+ if (AtomicDecrement(&ptmSysmRefCount)) return;
+ svcCloseHandle(ptmSysmHandle);
+}
+
+Result PTMSYSM_ConfigureNew3DSCPU(u8 value)
+{
+ Result ret;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x818,1,0); // 0x08180040
+ cmdbuf[1] = value;
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmSysmHandle)))return ret;
+
+ return (Result)cmdbuf[1];
+}
+
--- /dev/null
+#include <stdlib.h>
+#include <3ds/types.h>
+#include <3ds/result.h>
+#include <3ds/svc.h>
+#include <3ds/srv.h>
+#include <3ds/synchronization.h>
+#include <3ds/services/ptmu.h>
+#include <3ds/ipc.h>
+
+static Handle ptmuHandle;
+static int ptmuRefCount;
+
+Result ptmuInit(void)
+{
+ if (AtomicPostIncrement(&ptmuRefCount)) return 0;
+ Result res = srvGetServiceHandle(&ptmuHandle, "ptm:u");
+ if (R_FAILED(res)) AtomicDecrement(&ptmuRefCount);
+ return res;
+}
+
+void ptmuExit(void)
+{
+ if (AtomicDecrement(&ptmuRefCount)) return;
+ svcCloseHandle(ptmuHandle);
+}
+
+Result PTMU_GetShellState(u8 *out)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x6,0,0); // 0x60000
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmuHandle)))return ret;
+
+ *out = (u8)cmdbuf[2] & 0xFF;
+
+ return (Result)cmdbuf[1];
+}
+
+Result PTMU_GetBatteryLevel(u8 *out)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x7,0,0); // 0x70000
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmuHandle)))return ret;
+
+ *out = (u8)cmdbuf[2] & 0xFF;
+
+ return (Result)cmdbuf[1];
+}
+
+Result PTMU_GetBatteryChargeState(u8 *out)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x8,0,0); // 0x80000
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmuHandle)))return ret;
+
+ *out = (u8)cmdbuf[2] & 0xFF;
+
+ return (Result)cmdbuf[1];
+}
+
+Result PTMU_GetPedometerState(u8 *out)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x9,0,0); // 0x90000
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmuHandle)))return ret;
+
+ *out = (u8)cmdbuf[2] & 0xFF;
+
+ return (Result)cmdbuf[1];
+}
+
+Result PTMU_GetTotalStepCount(u32 *steps)
+{
+ Result ret=0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xC,0,0); // 0xC0000
+
+ if(R_FAILED(ret = svcSendSyncRequest(ptmuHandle)))return ret;
+
+ *steps = cmdbuf[2];
+
+ return (Result)cmdbuf[1];
+}
+
-/*
- qtm.c - New3DS head-tracking
-*/
#include <stdlib.h>
#include <string.h>
#include <3ds/types.h>
return qtmRefCount>0;
}
-Result qtmGetHeadtrackingInfo(u64 val, qtmHeadtrackingInfo *out)
-{
- u32* cmdbuf=getThreadCommandBuffer();
-
- if(!qtmCheckInitialized())return -1;
-
- cmdbuf[0]=IPC_MakeHeader(0x2,2,0); // 0x20080
- cmdbuf[1] = val&0xFFFFFFFF;
- cmdbuf[2] = val>>32;
-
- Result ret=0;
- if(R_FAILED(ret=svcSendSyncRequest(qtmHandle)))return ret;
-
- ret = (Result)cmdbuf[1];
- if(R_FAILED(ret))return ret;
-
- if(out)memcpy(out, &cmdbuf[2], sizeof(qtmHeadtrackingInfo));
-
- return 0;
-}
-
-bool qtmCheckHeadFullyDetected(qtmHeadtrackingInfo *info)
+bool qtmCheckHeadFullyDetected(QTM_HeadTrackingInfo *info)
{
if(info==NULL)return false;
return false;
}
-Result qtmConvertCoordToScreen(qtmHeadtrackingInfoCoord *coord, float *screen_width, float *screen_height, u32 *x, u32 *y)
+Result qtmConvertCoordToScreen(QTM_HeadTrackingInfoCoord *coord, float *screen_width, float *screen_height, u32 *x, u32 *y)
{
float width = 200.0f;
float height = 160.0f;
return 0;
}
+Result QTM_GetHeadTrackingInfo(u64 val, QTM_HeadTrackingInfo* out)
+{
+ if(!qtmCheckInitialized())return -1;
+
+ Result ret = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x2,2,0); // 0x20080
+ cmdbuf[1] = val&0xFFFFFFFF;
+ cmdbuf[2] = val>>32;
+
+ if(R_FAILED(ret=svcSendSyncRequest(qtmHandle)))return ret;
+
+ if(out) memcpy(out, &cmdbuf[2], sizeof(QTM_HeadTrackingInfo));
+
+ return cmdbuf[1];
+}
+
.fchmod_r = NULL,
};
-
-static Result socu_cmd1(Handle memhandle, u32 memsize)
+static Result SOCU_Initialize(Handle memhandle, u32 memsize)
{
Result ret = 0;
u32 *cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result SOC_Initialize(u32 *context_addr, u32 context_size)
+static Result SOCU_Shutdown(void)
+{
+ Result ret = 0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x19,0,0); // 0x190000
+
+ ret = svcSendSyncRequest(SOCU_handle);
+ if(ret != 0) {
+ errno = SYNC_ERROR;
+ return ret;
+ }
+
+ return cmdbuf[1];
+}
+
+Result socInit(u32* context_addr, u32 context_size)
{
Result ret = 0;
return ret;
}
- ret = socu_cmd1(socMemhandle, context_size);
+ ret = SOCU_Initialize(socMemhandle, context_size);
if(ret != 0)
{
svcCloseHandle(socMemhandle);
return 0;
}
-Result SOC_Shutdown(void)
+Result socExit(void)
{
Result ret = 0;
- u32 *cmdbuf = getThreadCommandBuffer();
int dev;
svcCloseHandle(socMemhandle);
socMemhandle = 0;
- cmdbuf[0] = IPC_MakeHeader(0x19,0,0); // 0x190000
-
- ret = svcSendSyncRequest(SOCU_handle);
+ ret = SOCU_Shutdown();
svcCloseHandle(SOCU_handle);
SOCU_handle = 0;
if(dev >= 0)
RemoveDevice("soc:");
- if(ret)return ret;
- else return cmdbuf[1];
+ return ret;
}
static int
--- /dev/null
+#include <stdlib.h>
+#include <3ds/types.h>
+#include <3ds/result.h>
+#include <3ds/svc.h>
+#include <3ds/srv.h>
+#include <3ds/synchronization.h>
+#include <3ds/services/srvpm.h>
+#include <3ds/ipc.h>
+
+static Handle srvPmHandle;
+static int srvPmRefCount;
+
+Result srvPmInit(void)
+{
+ if (AtomicPostIncrement(&srvPmRefCount)) return 0;
+ Result res = srvGetServiceHandle(&srvPmHandle, "srv:pm");
+ if (R_FAILED(res)) AtomicDecrement(&srvPmRefCount);
+ return res;
+}
+
+void srvPmExit(void)
+{
+ if (AtomicDecrement(&srvPmRefCount)) return;
+ svcCloseHandle(srvPmHandle);
+}
+
+Result SRVPM_PublishToProcess(u32 notificationId, Handle process)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x1,1,2); // 0x10042
+ cmdbuf[1] = notificationId;
+ cmdbuf[2] = IPC_Desc_SharedHandles(1);
+ cmdbuf[3] = process;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvPmHandle)))return rc;
+
+ return cmdbuf[1];
+}
+
+Result SRVPM_PublishToAll(u32 notificationId)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x2,1,0); // 0x20040
+ cmdbuf[1] = notificationId;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvPmHandle)))return rc;
+
+ return cmdbuf[1];
+}
+
+Result SRVPM_RegisterProcess(u32 procid, u32 count, void* serviceaccesscontrol)
+{
+ Result rc = 0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x3,2,2); // 0x30082
+ cmdbuf[1] = procid;
+ cmdbuf[2] = count;
+ cmdbuf[3] = IPC_Desc_StaticBuffer(count*4,0);
+ cmdbuf[4] = (u32)serviceaccesscontrol;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvPmHandle))) return rc;
+
+ return cmdbuf[1];
+}
+
+Result SRVPM_UnregisterProcess(u32 procid)
+{
+ Result rc = 0;
+ u32 *cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x4,1,0); // 0x40040
+ cmdbuf[1] = procid;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvPmHandle))) return rc;
+
+ return cmdbuf[1];
+}
+
svcCloseHandle(y2rHandle);
}
-Result Y2RU_SetInputFormat(Y2R_InputFormat format)
+Result Y2RU_SetInputFormat(Y2RU_InputFormat format)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_GetInputFormat(Y2R_InputFormat* format)
+Result Y2RU_GetInputFormat(Y2RU_InputFormat* format)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_SetOutputFormat(Y2R_OutputFormat format)
+Result Y2RU_SetOutputFormat(Y2RU_OutputFormat format)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_GetOutputFormat(Y2R_OutputFormat* format)
+Result Y2RU_GetOutputFormat(Y2RU_OutputFormat* format)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_SetRotation(Y2R_Rotation rotation)
+Result Y2RU_SetRotation(Y2RU_Rotation rotation)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_GetRotation(Y2R_Rotation* rotation)
+Result Y2RU_GetRotation(Y2RU_Rotation* rotation)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_SetBlockAlignment(Y2R_BlockAlignment alignment)
+Result Y2RU_SetBlockAlignment(Y2RU_BlockAlignment alignment)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_GetBlockAlignment(Y2R_BlockAlignment* alignment)
+Result Y2RU_GetBlockAlignment(Y2RU_BlockAlignment* alignment)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_SetCoefficients(const Y2R_ColorCoefficients* coefficients)
+Result Y2RU_SetCoefficients(const Y2RU_ColorCoefficients* coefficients)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1E,4,0); // 0x1E0100
- memcpy(&cmdbuf[1], coefficients, sizeof(Y2R_ColorCoefficients));
+ memcpy(&cmdbuf[1], coefficients, sizeof(Y2RU_ColorCoefficients));
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
return cmdbuf[1];
}
-Result Y2RU_GetCoefficients(Y2R_ColorCoefficients* coefficients)
+Result Y2RU_GetCoefficients(Y2RU_ColorCoefficients* coefficients)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x1F,0,0); // 0x1F0000
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
- memcpy(coefficients,cmdbuf + 2, sizeof(Y2R_ColorCoefficients));
+ memcpy(coefficients,cmdbuf + 2, sizeof(Y2RU_ColorCoefficients));
return cmdbuf[1];
}
-Result Y2RU_SetStandardCoefficient(Y2R_StandardCoefficient coefficient)
+Result Y2RU_SetStandardCoefficient(Y2RU_StandardCoefficient coefficient)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
return cmdbuf[1];
}
-Result Y2RU_GetStandardCoefficient(Y2R_ColorCoefficients* coefficients, Y2R_StandardCoefficient standardCoeff)
+Result Y2RU_GetStandardCoefficient(Y2RU_ColorCoefficients* coefficients, Y2RU_StandardCoefficient standardCoeff)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[1] = standardCoeff;
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
- memcpy(coefficients,cmdbuf + 2, sizeof(Y2R_ColorCoefficients));
+ memcpy(coefficients,cmdbuf + 2, sizeof(Y2RU_ColorCoefficients));
return cmdbuf[1];
}
}
-Result Y2RU_SetDitheringWeightParams(const Y2R_DitheringWeightParams* params)
+Result Y2RU_SetDitheringWeightParams(const Y2RU_DitheringWeightParams* params)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x24,8,0); // 0x240200
- memcpy(&cmdbuf[1], params, sizeof(Y2R_DitheringWeightParams));
+ memcpy(&cmdbuf[1], params, sizeof(Y2RU_DitheringWeightParams));
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
return cmdbuf[1];
}
-Result Y2RU_GetDitheringWeightParams(Y2R_DitheringWeightParams* params)
+Result Y2RU_GetDitheringWeightParams(Y2RU_DitheringWeightParams* params)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x25,0,0); // 0x250000
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
- memcpy(params,cmdbuf+2, sizeof(Y2R_DitheringWeightParams));
+ memcpy(params,cmdbuf+2, sizeof(Y2RU_DitheringWeightParams));
return cmdbuf[1];
}
return cmdbuf[1];
}
-Result Y2RU_SetConversionParams(const Y2R_ConversionParams* params)
+Result Y2RU_SetConversionParams(const Y2RU_ConversionParams* params)
{
Result ret = 0;
u32* cmdbuf = getThreadCommandBuffer();
cmdbuf[0] = IPC_MakeHeader(0x29,7,0); // 0x2901C0
- memcpy(&cmdbuf[1], params, sizeof(Y2R_ConversionParams));
+ memcpy(&cmdbuf[1], params, sizeof(Y2RU_ConversionParams));
if (R_FAILED(ret = svcSendSyncRequest(y2rHandle))) return ret;
return cmdbuf[1];
extern service_list_t* __service_ptr;
-static Handle g_srv_handle;
-
-
static int __name_cmp(const char* a, const char* b) {
u32 i;
__service_ptr->num = 0;
}
+static Handle srvHandle;
Result srvInit(void)
{
Result rc = 0;
- if(g_srv_handle != 0) return rc;
+ if(srvHandle != 0) return rc;
- if(R_FAILED(rc = svcConnectToPort(&g_srv_handle, "srv:")))return rc;
+ if(R_FAILED(rc = svcConnectToPort(&srvHandle, "srv:pm"))) return rc;
if(R_FAILED(rc = srvRegisterClient())) {
- svcCloseHandle(g_srv_handle);
- g_srv_handle = 0;
+ svcCloseHandle(srvHandle);
+ srvHandle = 0;
}
return rc;
Result srvExit(void)
{
- if(g_srv_handle != 0)svcCloseHandle(g_srv_handle);
+ if(srvHandle != 0) svcCloseHandle(srvHandle);
- g_srv_handle = 0;
+ srvHandle = 0;
return 0;
}
Handle *srvGetSessionHandle(void)
{
- return &g_srv_handle;
+ return &srvHandle;
+}
+
+Result srvGetServiceHandle(Handle* out, const char* name)
+{
+ /* Look in service-list given to us by loader. If we find find a match,
+ we return it. */
+ Handle h = __get_handle_from_list(name);
+
+ if(h != 0) {
+ return svcDuplicateHandle(out, h);
+ }
+
+ /* Normal request to service manager. */
+ return srvGetServiceHandleDirect(out, name);
}
Result srvRegisterClient(void)
{
Result rc = 0;
-
u32* cmdbuf = getThreadCommandBuffer();
-
+
cmdbuf[0] = IPC_MakeHeader(0x1,0,2); // 0x10002
cmdbuf[1] = IPC_Desc_CurProcessHandle();
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle)))return rc;
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
return cmdbuf[1];
}
-Result srvGetServiceHandleDirect(Handle* out, const char* name)
+Result srvEnableNotification(Handle* semaphoreOut)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x2,0,0);
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(semaphoreOut) *semaphoreOut = cmdbuf[3];
+
+ return cmdbuf[1];
+}
+
+Result srvRegisterService(Handle* out, const char* name, int maxSessions)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x3,4,0); // 0x30100
+ strncpy((char*) &cmdbuf[1], name,8);
+ cmdbuf[3] = strlen(name);
+ cmdbuf[4] = maxSessions;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(out) *out = cmdbuf[3];
+
+ return cmdbuf[1];
+}
+
+Result srvUnregisterService(const char* name)
{
Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0x4,3,0); // 0x400C0
+ strncpy((char*) &cmdbuf[1], name,8);
+ cmdbuf[3] = strlen(name);
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ return cmdbuf[1];
+}
+Result srvGetServiceHandleDirect(Handle* out, const char* name)
+{
+ Result rc = 0;
u32* cmdbuf = getThreadCommandBuffer();
+
cmdbuf[0] = IPC_MakeHeader(0x5,4,0); // 0x50100
strncpy((char*) &cmdbuf[1], name,8);
cmdbuf[3] = strlen(name);
cmdbuf[4] = 0x0;
-
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle)))return rc;
- *out = cmdbuf[3];
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(out) *out = cmdbuf[3];
+
return cmdbuf[1];
}
-Result srvGetServiceHandle(Handle* out, const char* name)
+Result srvRegisterPort(const char* name, Handle clientHandle)
{
- /* Look in service-list given to us by loader. If we find find a match,
- we return it. */
- Handle h = __get_handle_from_list(name);
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
- if(h != 0) {
- return svcDuplicateHandle(out, h);
- }
+ cmdbuf[0] = IPC_MakeHeader(0x6,3,2); // 0x600C2
+ strncpy((char*) &cmdbuf[1], name,8);
+ cmdbuf[3] = strlen(name);
+ cmdbuf[4] = IPC_Desc_SharedHandles(0);
+ cmdbuf[5] = clientHandle;
- /* Normal request to service manager. */
- return srvGetServiceHandleDirect(out, name);
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ return cmdbuf[1];
}
-Result srvRegisterService(Handle* out, const char* name, int maxSessions)
+Result srvUnregisterPort(const char* name)
{
+ Result rc = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = IPC_MakeHeader(0x3,4,0); // 0x30100
+
+ cmdbuf[0] = IPC_MakeHeader(0x7,3,0); // 0x700C0
strncpy((char*) &cmdbuf[1], name,8);
cmdbuf[3] = strlen(name);
- cmdbuf[4] = maxSessions;
-
- Result rc;
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle)))return rc;
- *out = cmdbuf[3];
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
return cmdbuf[1];
}
-Result srvUnregisterService(const char* name)
+Result srvGetPort(Handle* out, const char* name)
{
+ Result rc = 0;
u32* cmdbuf = getThreadCommandBuffer();
- cmdbuf[0] = IPC_MakeHeader(0x4,3,0); // 0x400C0
+
+ cmdbuf[0] = IPC_MakeHeader(0x8,4,0); // 0x80100
strncpy((char*) &cmdbuf[1], name,8);
cmdbuf[3] = strlen(name);
-
- Result rc;
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle)))return rc;
+ cmdbuf[4] = 0x0;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(out) *out = cmdbuf[3];
return cmdbuf[1];
}
-// Old srv:pm interface, will only work on systems where srv:pm was a port (<7.X)
-Result srvPmInit(void)
-{
+Result srvSubscribe(u32 notificationId)
+{
Result rc = 0;
-
- if(R_FAILED(rc = svcConnectToPort(&g_srv_handle, "srv:pm")))return rc;
-
- if(R_FAILED(rc = srvRegisterClient())) {
- svcCloseHandle(g_srv_handle);
- g_srv_handle = 0;
- }
+ u32* cmdbuf = getThreadCommandBuffer();
- return rc;
+ cmdbuf[0] = IPC_MakeHeader(0x9,1,0); // 0x90040
+ cmdbuf[1] = notificationId;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ return cmdbuf[1];
}
-Result srvRegisterProcess(u32 procid, u32 count, void *serviceaccesscontrol)
+Result srvUnsubscribe(u32 notificationId)
{
Result rc = 0;
-
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x403,2,2); // 0x4030082 // <7.x
- cmdbuf[1] = procid;
- cmdbuf[2] = count;
- cmdbuf[3] = IPC_Desc_StaticBuffer(count*4,0);
- cmdbuf[4] = (u32)serviceaccesscontrol;
-
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle))) return rc;
-
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xA,1,0); // 0xA0040
+ cmdbuf[1] = notificationId;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
return cmdbuf[1];
}
-Result srvUnregisterProcess(u32 procid)
+Result srvReceiveNotification(u32* notificationIdOut)
{
Result rc = 0;
-
- u32 *cmdbuf = getThreadCommandBuffer();
-
- cmdbuf[0] = IPC_MakeHeader(0x404,1,0); // 0x4040040 // <7.x
- cmdbuf[1] = procid;
-
- if(R_FAILED(rc = svcSendSyncRequest(g_srv_handle))) return rc;
-
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xB,0,0); // 0xB0000
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(notificationIdOut) *notificationIdOut = cmdbuf[2];
+
+ return cmdbuf[1];
+}
+
+Result srvPublishToSubscriber(u32 notificationId, u32 flags)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xC,2,0); // 0xC0080
+ cmdbuf[1] = notificationId;
+ cmdbuf[2] = flags;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ return cmdbuf[1];
+}
+
+Result srvPublishAndGetSubscriber(u32* processIdCountOut, u32* processIdsOut, u32 notificationId)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xD,1,0); // 0xD0040
+ cmdbuf[1] = notificationId;
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(processIdCountOut) *processIdCountOut = cmdbuf[2];
+ if(processIdsOut) memcpy(processIdsOut, &cmdbuf[3], cmdbuf[2] * sizeof(u32));
+
+ return cmdbuf[1];
+}
+
+Result srvIsServiceRegistered(bool* registeredOut, const char* name)
+{
+ Result rc = 0;
+ u32* cmdbuf = getThreadCommandBuffer();
+
+ cmdbuf[0] = IPC_MakeHeader(0xE,3,0); // 0xE00C0
+ strncpy((char*) &cmdbuf[1], name,8);
+ cmdbuf[3] = strlen(name);
+
+ if(R_FAILED(rc = svcSendSyncRequest(srvHandle)))return rc;
+
+ if(registeredOut) *registeredOut = cmdbuf[2] & 0xFF;
+
return cmdbuf[1];
}