diff --git a/include/content_redirection/redirection.h b/include/content_redirection/redirection.h index 34a289e..f0ae2d0 100644 --- a/include/content_redirection/redirection.h +++ b/include/content_redirection/redirection.h @@ -46,6 +46,7 @@ typedef enum ContentRedirectionStatus { CONTENT_REDIRECTION_RESULT_UNKNOWN_FS_LAYER_TYPE = -0x12, CONTENT_REDIRECTION_RESULT_LAYER_NOT_FOUND = -0x13, CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED = -0x20, + CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND = -0x21, CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR = -0x1000, } ContentRedirectionStatus; @@ -81,32 +82,33 @@ ContentRedirectionStatus ContentRedirection_DeInitLibrary(); *
* @param outVersion pointer to the variable where the version will be stored. * - * @return CONTENT_REDIRECTION_RESULT_SUCCESS: The API version has been store in the version ptr.
- * CONTENT_REDIRECTION_RESULT_INVALID_ARGUMENT: Invalid version pointer.
- * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Retrieving the module version failed. + * @return CONTENT_REDIRECTION_RESULT_SUCCESS: The API version has been store in the version ptr.
+ * CONTENT_REDIRECTION_RESULT_MODULE_NOT_FOUND: The module could not be found. Make sure the module is loaded.
+ * CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT: The module is missing an expected export.
+ * CONTENT_REDIRECTION_RESULT_INVALID_ARGUMENT: Invalid version pointer.
+ * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Retrieving the module version failed. */ ContentRedirectionStatus ContentRedirection_GetVersion(ContentRedirectionVersion *outVersion); /** - * Adds a a FSLayers that redirects the /vol/content or /vol/save fs calles for the Game/Wii U Menu process. - * Make sure to remove all added the layers before the application ends. - * The replacement dir has be to valid in the ContentRedirection Module, use "ContentRedirection_AddDevice" to add a Device for the ContentRedirection Module. - * Multiple layers can be added. Each layer is valid system wide for the Game/Wii U Menu process. - * The layers will be processed in reverse adding order. e.g. when you add Layer1, Layer2 and then Layer3; Layer3, Layer2 and finally Layer1 will be processed. + * Adds a a FSLayers that redirects the /vol/content or /vol/save fs calles for the Game/Wii U Menu process.
+ * Make sure to remove all added the layers before the application ends.
+ * The replacement dir has be to valid in the ContentRedirection Module, use "ContentRedirection_AddDevice" to add a Device for the ContentRedirection Module.
+ * Multiple layers can be added. Each layer is valid system wide for the Game/Wii U Menu process.
+ * The layers will be processed in reverse adding order. e.g. when you add Layer1, Layer2 and then Layer3; Layer3, Layer2 and finally Layer1 will be processed.
* An added layer is active by default. * * @param handlePtr The handle of the layer is written to this pointer. * @param layerName Name of the layer, used for debugging. * @param replacementDir Path to the directory that will replace / merge into the original one. - * @param layerType Type of the layer, see FSLayerType for more information. - * + * @param layerType Type of the layer, see FSLayerType for more information.
* If set to to false, errors of this layer will be returned to the OS. -* @return CONTENT_REDIRECTION_RESULT_SUCCESS: The layer had been added successfully. - * The layer has to be removed before the currently running application ends. -* CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_Init()" was not called. -* CONTENT_REDIRECTION_API_ERROR_INVALID_ARG: "handlePtr", "layerName" or "replacementDir" is NULL -* CONTENT_REDIRECTION_API_ERROR_NO_MEMORY: Not enough memory to create this layer. -* CONTENT_REDIRECTION_API_ERROR_UNKNOWN_LAYER_TYPE: Unknown/invalid LayerType. See FSLayerType for all supported layers. +* @return CONTENT_REDIRECTION_RESULT_SUCCESS: The layer had been added successfully.
+ * The layer has to be removed before the currently running application ends.
+* CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_InitLibrary()" was not called.
+* CONTENT_REDIRECTION_RESULT_INVALID_ARGUMENT: "handlePtr", "layerName" or "replacementDir" is NULL
+* CONTENT_REDIRECTION_API_ERROR_NO_MEMORY: Not enough memory to create this layer.
+* CONTENT_REDIRECTION_API_ERROR_UNKNOWN_LAYER_TYPE: Unknown/invalid LayerType. See FSLayerType for all supported layers.
* CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error. */ ContentRedirectionStatus ContentRedirection_AddFSLayer(CRLayerHandle *handlePtr, const char *layerName, const char *replacementDir, FSLayerType layerType); @@ -119,28 +121,30 @@ ContentRedirectionStatus ContentRedirection_AddFSLayer(CRLayerHandle *handlePtr, ContentRedirectionStatus ContentRedirection_RemoveFSLayer(CRLayerHandle handle); /** - * Set the "active" flag for a given FSLayer. + * Set the "active" flag for a given FSLayer.
* * @param handle Handle of the FSLayer. * @param active New "active"-state of the layer - * @return CONTENT_REDIRECTION_RESULT_SUCCESS: The active state has been set successfully. - * CONTENT_REDIRECTION_RESULT_LAYER_NOT_FOUND: Invalid FSLayer handle. - * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_Init()" was not called. - * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error. + * @return CONTENT_REDIRECTION_RESULT_SUCCESS: The active state has been set successfully.
+ * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_InitLibrary()" was not called.
+ * CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND: This command is not supported by the currently loaded Module.
+ * CONTENT_REDIRECTION_RESULT_LAYER_NOT_FOUND: Invalid FSLayer handle.
+ * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error. */ ContentRedirectionStatus ContentRedirection_SetActive(CRLayerHandle handle, bool active); /** - * Calls "AddDevice" for the ContentRedirection Module. - * When a device is added for the ContentRedirection Module, it can be used in FSLayers. + * Calls "AddDevice" for the ContentRedirection Module.
+ * When a device is added for the ContentRedirection Module, it can be used in FSLayers.
* * @param device Device that will be added * @param resultOut Will hold the result of the "AddDevice" call. - * @return CONTENT_REDIRECTION_RESULT_SUCCESS: AddDevice has been called, result is written to resultOut. - * See documentation of AddDevice for more information - * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_Init()" was not called. - * CONTENT_REDIRECTION_RESULT_INVALID_ARG: resultOut is NULL. - * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error. + * @return CONTENT_REDIRECTION_RESULT_SUCCESS: AddDevice has been called, result is written to resultOut.
+ * See documentation of AddDevice for more information
+ * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_InitLibrary()" was not called.
+ * CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND: This command is not supported by the currently loaded Module.
+ * CONTENT_REDIRECTION_RESULT_INVALID_ARG: resultOut is NULL.
+ * CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error.
*/ ContentRedirectionStatus ContentRedirection_AddDevice(const devoptab_t *device, int *resultOut); @@ -149,10 +153,11 @@ ContentRedirectionStatus ContentRedirection_AddDevice(const devoptab_t *device, * * @param name name of the device that will be added. e.g. "romfs:" * @param resultOut Will hold the result of the "AddDevice" call. - * @return CONTENT_REDIRECTION_RESULT_SUCCESS: RemoveDevice has been called, result is written to resultOut. - * See documentation of RemoveDevice for more information - * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_Init()" was not called. - * CONTENT_REDIRECTION_RESULT_INVALID_ARG: resultOut is NULL. + * @return CONTENT_REDIRECTION_RESULT_SUCCESS: RemoveDevice has been called, result is written to resultOut.
+ * See documentation of RemoveDevice for more information
+ * CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED: "ContentRedirection_InitLibrary()" was not called.
+ * CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND: This command is not supported by the currently loaded Module.
+ * CONTENT_REDIRECTION_RESULT_INVALID_ARG: resultOut is NULL.
* CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: Unknown error. */ ContentRedirectionStatus ContentRedirection_RemoveDevice(const char *name, int *resultOut); diff --git a/source/logger.h b/source/logger.h new file mode 100644 index 0000000..0b5258d --- /dev/null +++ b/source/logger.h @@ -0,0 +1,23 @@ +#pragma once +#include +#include + +#define __FILENAME__ ({ \ + const char *__filename = __FILE__; \ + const char *__pos = strrchr(__filename, '/'); \ + if (!__pos) __pos = strrchr(__filename, '\\'); \ + __pos ? __pos + 1 : __filename; \ +}) + +#define LOG_APP_TYPE "L" +#define LOG_APP_NAME "libcontentredirection" + +#define LOG_EX(FILENAME, FUNCTION, LINE, LOG_FUNC, LOG_LEVEL, LINE_END, FMT, ARGS...) \ + do { \ + LOG_FUNC("[(%s)%18s][%23s]%30s@L%04d: " LOG_LEVEL "" FMT "" LINE_END, LOG_APP_TYPE, LOG_APP_NAME, FILENAME, FUNCTION, LINE, ##ARGS); \ + } while (0) + +#define LOG_EX_DEFAULT(LOG_FUNC, LOG_LEVEL, LINE_END, FMT, ARGS...) LOG_EX(__FILENAME__, __FUNCTION__, __LINE__, LOG_FUNC, LOG_LEVEL, LINE_END, FMT, ##ARGS) + +#define DEBUG_FUNCTION_LINE_ERR(FMT, ARGS...) LOG_EX_DEFAULT(OSReport, "##ERROR## ", "\n", FMT, ##ARGS) +#define DEBUG_FUNCTION_LINE_WARN(FMT, ARGS...) LOG_EX_DEFAULT(OSReport, "##WARNING## ", "\n", FMT, ##ARGS) diff --git a/source/utils.cpp b/source/utils.cpp index 7488b4f..e8be32c 100644 --- a/source/utils.cpp +++ b/source/utils.cpp @@ -1,4 +1,5 @@ #include "content_redirection/redirection.h" +#include "logger.h" #include #include #include @@ -36,18 +37,20 @@ const char *ContentRedirection_GetStatusStr(ContentRedirectionStatus status) { return "CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED"; case CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR: return "CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR"; + case CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND: + return "CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND"; } return "CONTENT_REDIRECTION_RESULT_UNKNOWN_ERROR"; } ContentRedirectionStatus ContentRedirection_InitLibrary() { if (OSDynLoad_Acquire("homebrew_content_redirection", &sModuleHandle) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: OSDynLoad_Acquire failed.\n"); + DEBUG_FUNCTION_LINE_ERR("OSDynLoad_Acquire failed."); return CONTENT_REDIRECTION_RESULT_MODULE_NOT_FOUND; } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRGetVersion", (void **) &sCRGetVersion) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRGetVersion failed.\n"); + DEBUG_FUNCTION_LINE_ERR("FindExport CRGetVersion failed."); return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; } auto res = ContentRedirection_GetVersion(&sContentRedirectionVersion); @@ -56,28 +59,28 @@ ContentRedirectionStatus ContentRedirection_InitLibrary() { } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRAddFSLayer", (void **) &sCRAddFSLayer) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRAddFSLayer failed.\n"); - return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + DEBUG_FUNCTION_LINE_ERR("FindExport CRAddFSLayer failed."); + sCRAddFSLayer = nullptr; } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRRemoveFSLayer", (void **) &sCRRemoveFSLayer) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRRemoveFSLayer failed.\n"); - return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + DEBUG_FUNCTION_LINE_ERR("FindExport CRRemoveFSLayer failed."); + sCRRemoveFSLayer = nullptr; } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRSetActive", (void **) &sCRSetActive) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRSetActive failed.\n"); - return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + DEBUG_FUNCTION_LINE_ERR("FindExport CRSetActive failed."); + sCRSetActive = nullptr; } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRAddDevice", (void **) &sCRAddDevice) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRAddDevice failed.\n"); - return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + DEBUG_FUNCTION_LINE_ERR("FindExport CRAddDevice failed."); + sCRAddDevice = nullptr; } if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRRemoveDevice", (void **) &sCRRemoveDevice) != OS_DYNLOAD_OK) { - OSReport("ContentRedirection_Init: CRRemoveDevice failed.\n"); - return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + DEBUG_FUNCTION_LINE_ERR("FindExport CRRemoveDevice failed."); + sCRRemoveDevice = nullptr; } return CONTENT_REDIRECTION_RESULT_SUCCESS; @@ -90,7 +93,15 @@ ContentRedirectionStatus ContentRedirection_DeInitLibrary() { ContentRedirectionApiErrorType GetVersion(ContentRedirectionVersion *); ContentRedirectionStatus ContentRedirection_GetVersion(ContentRedirectionVersion *outVariable) { if (sCRGetVersion == nullptr) { - return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; + if (OSDynLoad_Acquire("homebrew_content_redirection", &sModuleHandle) != OS_DYNLOAD_OK) { + DEBUG_FUNCTION_LINE_WARN("OSDynLoad_Acquire failed."); + return CONTENT_REDIRECTION_RESULT_MODULE_NOT_FOUND; + } + + if (OSDynLoad_FindExport(sModuleHandle, FALSE, "CRGetVersion", (void **) &sCRGetVersion) != OS_DYNLOAD_OK) { + DEBUG_FUNCTION_LINE_WARN("FindExport CRGetVersion failed."); + return CONTENT_REDIRECTION_RESULT_MODULE_MISSING_EXPORT; + } } auto res = reinterpret_cast(sCRGetVersion)(outVariable); @@ -103,9 +114,12 @@ ContentRedirectionStatus ContentRedirection_GetVersion(ContentRedirectionVersion ContentRedirectionApiErrorType AddFSLayer(CRLayerHandle *, const char *, const char *, FSLayerType); ContentRedirectionStatus ContentRedirection_AddFSLayer(CRLayerHandle *handlePtr, const char *layerName, const char *replacementDir, FSLayerType layerType) { - if (sCRAddFSLayer == nullptr) { + if (sContentRedirectionVersion == CONTENT_REDIRECTION_MODULE_VERSION_ERROR) { return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; } + if (sCRAddFSLayer == nullptr || sContentRedirectionVersion < 1) { + return CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND; + } auto res = reinterpret_cast(sCRAddFSLayer)(handlePtr, layerName, replacementDir, layerType); if (res == CONTENT_REDIRECTION_API_ERROR_NONE) { return CONTENT_REDIRECTION_RESULT_SUCCESS; @@ -124,9 +138,12 @@ ContentRedirectionStatus ContentRedirection_AddFSLayer(CRLayerHandle *handlePtr, ContentRedirectionApiErrorType RemoveFSLayer(CRLayerHandle); ContentRedirectionStatus ContentRedirection_RemoveFSLayer(CRLayerHandle handlePtr) { - if (sCRAddFSLayer == nullptr) { + if (sContentRedirectionVersion == CONTENT_REDIRECTION_MODULE_VERSION_ERROR) { return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; } + if (sCRRemoveFSLayer == nullptr || sContentRedirectionVersion < 1) { + return CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND; + } auto res = reinterpret_cast(sCRRemoveFSLayer)(handlePtr); if (res == CONTENT_REDIRECTION_API_ERROR_NONE) { return CONTENT_REDIRECTION_RESULT_SUCCESS; @@ -141,9 +158,12 @@ ContentRedirectionStatus ContentRedirection_RemoveFSLayer(CRLayerHandle handlePt ContentRedirectionApiErrorType SetActive(CRLayerHandle, bool); ContentRedirectionStatus ContentRedirection_SetActive(CRLayerHandle handle, bool active) { - if (sCRAddFSLayer == nullptr) { + if (sContentRedirectionVersion == CONTENT_REDIRECTION_MODULE_VERSION_ERROR) { return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; } + if (sCRSetActive == nullptr || sContentRedirectionVersion < 1) { + return CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND; + } auto res = reinterpret_cast(sCRSetActive)(handle, active); if (res == CONTENT_REDIRECTION_API_ERROR_NONE) { return CONTENT_REDIRECTION_RESULT_SUCCESS; @@ -157,9 +177,12 @@ ContentRedirectionStatus ContentRedirection_SetActive(CRLayerHandle handle, bool } ContentRedirectionStatus ContentRedirection_AddDevice(const devoptab_t *device, int *resultOut) { - if (sCRAddFSLayer == nullptr) { + if (sContentRedirectionVersion == CONTENT_REDIRECTION_MODULE_VERSION_ERROR) { return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; } + if (sCRAddDevice == nullptr || sContentRedirectionVersion < 1) { + return CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND; + } if (resultOut == nullptr) { return CONTENT_REDIRECTION_RESULT_INVALID_ARGUMENT; @@ -170,9 +193,12 @@ ContentRedirectionStatus ContentRedirection_AddDevice(const devoptab_t *device, } ContentRedirectionStatus ContentRedirection_RemoveDevice(const char *name, int *resultOut) { - if (sCRAddFSLayer == nullptr) { + if (sContentRedirectionVersion == CONTENT_REDIRECTION_MODULE_VERSION_ERROR) { return CONTENT_REDIRECTION_RESULT_LIB_UNINITIALIZED; } + if (sCRRemoveDevice == nullptr || sContentRedirectionVersion < 1) { + return CONTENT_REDIRECTION_RESULT_UNSUPPORTED_COMMAND; + } if (resultOut == nullptr) { return CONTENT_REDIRECTION_RESULT_INVALID_ARGUMENT; }