mirror of
https://github.com/DarkMatterCore/nxdumptool.git
synced 2024-11-26 20:22:17 +00:00
Use linked lists to deal with user applications available in multiple storages at the same time.
This commit is contained in:
parent
ad401d559d
commit
90c6d8a9f8
2 changed files with 36 additions and 34 deletions
|
@ -629,7 +629,7 @@ bool titleGetUserApplicationData(u64 app_id, TitleUserApplicationData *out)
|
||||||
/* Clear output. */
|
/* Clear output. */
|
||||||
memset(out, 0, sizeof(TitleUserApplicationData));
|
memset(out, 0, sizeof(TitleUserApplicationData));
|
||||||
|
|
||||||
/* Get user application title info. */
|
/* Get first user application title info. */
|
||||||
out->app_info = _titleGetInfoFromStorageByTitleId(NcmStorageId_Any, app_id, false);
|
out->app_info = _titleGetInfoFromStorageByTitleId(NcmStorageId_Any, app_id, false);
|
||||||
|
|
||||||
/* Get first patch title info. */
|
/* Get first patch title info. */
|
||||||
|
@ -653,9 +653,6 @@ bool titleGetUserApplicationData(u64 app_id, TitleUserApplicationData *out)
|
||||||
goto end;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Update 'gamecard_available' flag. */
|
|
||||||
out->gamecard_available = (out->app_info && (out->app_info->storage_id == NcmStorageId_GameCard || _titleGetInfoFromStorageByTitleId(NcmStorageId_GameCard, app_id, false) != NULL));
|
|
||||||
|
|
||||||
end:
|
end:
|
||||||
mutexUnlock(&g_titleMutex);
|
mutexUnlock(&g_titleMutex);
|
||||||
|
|
||||||
|
@ -1219,14 +1216,19 @@ static bool titleRetrieveContentMetaKeysFromDatabase(u8 storage_id)
|
||||||
/* Update title info count. */
|
/* Update title info count. */
|
||||||
g_titleInfoCount += total;
|
g_titleInfoCount += total;
|
||||||
|
|
||||||
/* Fill patch / add-on content specific info. */
|
/* Update linked lists pointers for user applications, patches and add-on contents. */
|
||||||
g_titleInfoOrphanCount = 0;
|
g_titleInfoOrphanCount = 0;
|
||||||
for(u32 i = 0; i < g_titleInfoCount; i++)
|
for(u32 i = 0; i < g_titleInfoCount; i++)
|
||||||
{
|
{
|
||||||
TitleInfo *child_info = &(g_titleInfo[i]);
|
TitleInfo *child_info = &(g_titleInfo[i]);
|
||||||
if (child_info->meta_key.type != NcmContentMetaType_Patch && child_info->meta_key.type != NcmContentMetaType_AddOnContent) continue;
|
child_info->parent = child_info->previous = child_info->next = NULL;
|
||||||
|
|
||||||
/* Retrieve pointer to parent entry. */
|
if (child_info->meta_key.type != NcmContentMetaType_Application && child_info->meta_key.type != NcmContentMetaType_Patch && \
|
||||||
|
child_info->meta_key.type != NcmContentMetaType_AddOnContent) continue;
|
||||||
|
|
||||||
|
if (child_info->meta_key.type == NcmContentMetaType_Patch || child_info->meta_key.type == NcmContentMetaType_AddOnContent)
|
||||||
|
{
|
||||||
|
/* Retrieve pointer to parent user application entry for patches and add-on contents. */
|
||||||
/* Since gamecard title info entries are always appended to the end of the buffer, this guarantees we will first retrieve an eMMC / SD card entry (if available). */
|
/* Since gamecard title info entries are always appended to the end of the buffer, this guarantees we will first retrieve an eMMC / SD card entry (if available). */
|
||||||
for(u32 j = 0; j < g_titleInfoCount; j++)
|
for(u32 j = 0; j < g_titleInfoCount; j++)
|
||||||
{
|
{
|
||||||
|
@ -1247,18 +1249,18 @@ static bool titleRetrieveContentMetaKeysFromDatabase(u8 storage_id)
|
||||||
g_titleInfoOrphanCount++;
|
g_titleInfoOrphanCount++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Locate previous patch / add-on content entry. */
|
/* Locate previous user application, patch or add-on content entry. */
|
||||||
/* If it's found, we will update both its next pointer and the previous pointer from the current entry. */
|
/* If it's found, we will update both its next pointer and the previous pointer from the current entry. */
|
||||||
/* We will also update its parent entry pointer. */
|
|
||||||
for(u32 j = i; j > 0; j--)
|
for(u32 j = i; j > 0; j--)
|
||||||
{
|
{
|
||||||
TitleInfo *previous_info = &(g_titleInfo[j - 1]);
|
TitleInfo *previous_info = &(g_titleInfo[j - 1]);
|
||||||
|
|
||||||
if (previous_info->meta_key.type == child_info->meta_key.type && ((child_info->meta_key.type == NcmContentMetaType_Patch && previous_info->meta_key.id == child_info->meta_key.id) || \
|
if (previous_info->meta_key.type == child_info->meta_key.type && (((child_info->meta_key.type == NcmContentMetaType_Application || child_info->meta_key.type == NcmContentMetaType_Patch) && \
|
||||||
(child_info->meta_key.type == NcmContentMetaType_AddOnContent && titleCheckIfAddOnContentIdsAreSiblings(previous_info->meta_key.id, child_info->meta_key.id))))
|
previous_info->meta_key.id == child_info->meta_key.id) || (child_info->meta_key.type == NcmContentMetaType_AddOnContent && \
|
||||||
|
titleCheckIfAddOnContentIdsAreSiblings(previous_info->meta_key.id, child_info->meta_key.id))))
|
||||||
{
|
{
|
||||||
previous_info->parent = child_info->parent;
|
|
||||||
previous_info->next = child_info;
|
previous_info->next = child_info;
|
||||||
child_info->previous = previous_info;
|
child_info->previous = previous_info;
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -59,15 +59,15 @@ typedef struct _TitleInfo {
|
||||||
u64 title_size; ///< Total title size.
|
u64 title_size; ///< Total title size.
|
||||||
char title_size_str[32]; ///< Total title size string.
|
char title_size_str[32]; ///< Total title size string.
|
||||||
TitleApplicationMetadata *app_metadata; ///< Only available for system titles and applications.
|
TitleApplicationMetadata *app_metadata; ///< Only available for system titles and applications.
|
||||||
struct _TitleInfo *parent, *previous, *next; ///< Used with TitleInfo entries from patches and add-on contents.
|
struct _TitleInfo *parent, *previous, *next; ///< Used with TitleInfo entries from user applications, patches and add-on contents. The parent pointer is unused in user applications.
|
||||||
} TitleInfo;
|
} TitleInfo;
|
||||||
|
|
||||||
/// Used to deal with user applications stored in the eMMC, SD card and/or gamecard.
|
/// Used to deal with user applications stored in the eMMC, SD card and/or gamecard.
|
||||||
|
/// The parent, previous and next pointers from the TitleInfo elements are used to traverse through multiple user applications, patches and/or add-on contents.
|
||||||
typedef struct {
|
typedef struct {
|
||||||
bool gamecard_available; ///< Set to true if one or more titles matching this user application are stored in the inserted gamecard.
|
TitleInfo *app_info; ///< Pointer to a TitleInfo element holding info for the first detected user application entry matching the provided application ID.
|
||||||
TitleInfo *app_info; ///< Pointer to a TitleInfo element for this application.
|
TitleInfo *patch_info; ///< Pointer to a TitleInfo element holding info for the first detected patch entry matching the provided application ID.
|
||||||
TitleInfo *patch_info; ///< Pointer to a TitleInfo element for the first detected patch.
|
TitleInfo *aoc_info; ///< Pointer to a TitleInfo element holding info for the first detected add-on content entry matching the provided application ID.
|
||||||
TitleInfo *aoc_info; ///< Pointer to a TitleInfo element for the first detected add-on content.
|
|
||||||
} TitleUserApplicationData;
|
} TitleUserApplicationData;
|
||||||
|
|
||||||
/// Initializes the title interface.
|
/// Initializes the title interface.
|
||||||
|
@ -97,7 +97,7 @@ TitleInfo *titleGetInfoFromStorageByTitleId(u8 storage_id, u64 title_id);
|
||||||
bool titleGetUserApplicationData(u64 app_id, TitleUserApplicationData *out);
|
bool titleGetUserApplicationData(u64 app_id, TitleUserApplicationData *out);
|
||||||
|
|
||||||
/// Returns true if orphan titles are available.
|
/// Returns true if orphan titles are available.
|
||||||
/// Orphan titles are patches or add-on contents with no NsApplicationControlData available for its parent user application ID.
|
/// Orphan titles are patches or add-on contents with no NsApplicationControlData available for their parent user application ID.
|
||||||
bool titleAreOrphanTitlesAvailable(void);
|
bool titleAreOrphanTitlesAvailable(void);
|
||||||
|
|
||||||
/// Returns a pointer to a dynamically allocated buffer of pointers to TitleInfo entries from orphan titles, as well as their count. The allocated buffer must be freed by the calling function.
|
/// Returns a pointer to a dynamically allocated buffer of pointers to TitleInfo entries from orphan titles, as well as their count. The allocated buffer must be freed by the calling function.
|
||||||
|
|
Loading…
Reference in a new issue