1 /*---------------------------------------------------------------------------*
2 Project: TwlSDK - FS - libraries
3 File: fs_proc_mem.c
4
5 Copyright 2007-2008 Nintendo. All rights reserved.
6
7 These coded instructions, statements, and computer programs contain
8 proprietary information of Nintendo of America Inc. and/or Nintendo
9 Company Ltd., and are protected by Federal copyright law. They may
10 not be disclosed to third parties or copied or duplicated in any form,
11 in whole or in part, without the prior written consent of Nintendo.
12
13 $Date:: 2008-12-04#$
14 $Rev: 9513 $
15 $Author: yosizaki $
16
17 *---------------------------------------------------------------------------*/
18
19
20 #include <nitro/fs/romfat.h>
21 #include <nitro/fs/api.h>
22
23 #include "../include/util.h"
24 #include "../include/command.h"
25
26
27 #if defined(FS_IMPLEMENT)
28
29 /*---------------------------------------------------------------------------*/
30 /* Variables */
31
32 // Memory mapped file archive
33 static FSArchive fsi_arc_mem;
34 static BOOL fsi_mem_init;
35
36
37 /*---------------------------------------------------------------------------*/
38 /* functions */
39
40 /*---------------------------------------------------------------------------*
41 Name: FSi_MemArchiveProc
42
43 Description: Memory mapped file archive procedure
44
45 Arguments: p_file: FSFile structure that stores command information.
46 cmd: Command type.
47
48 Returns: Command processing result.
49 *---------------------------------------------------------------------------*/
FSi_MemArchiveProc(FSFile * p_file,FSCommandType cmd)50 static FSResult FSi_MemArchiveProc(FSFile *p_file, FSCommandType cmd)
51 {
52 #pragma unused(p_file)
53
54 switch (cmd)
55 {
56 case FS_COMMAND_READDIR:
57 {
58 FSResult result;
59 FSDirEntry *entry = p_file->arg.readdir.p_entry;
60 FSArchive *current = (FSArchive *)p_file->prop.dir.pos.pos;
61 if (current == NULL)
62 {
63 entry->name_len = 0;
64 entry->is_directory = 0;
65 result = FS_RESULT_FAILURE;
66 }
67 else
68 {
69 const char *arcname = FS_GetArchiveName(current);
70 entry->name_len = (u32)(STD_GetStringLength(arcname) + 1);
71 entry->is_directory = TRUE;
72 if (!p_file->arg.readdir.skip_string)
73 {
74 (void)STD_TSPrintf(entry->name, "%s:", arcname);
75 entry->dir_id.arc = p_file->arc;
76 entry->dir_id.own_id = 0;
77 entry->dir_id.index = 0;
78 entry->dir_id.pos = 0;
79 }
80 result = FS_RESULT_SUCCESS;
81 p_file->prop.dir.pos.pos = (u32)current->next;
82 }
83 return result;
84 }
85 case FS_COMMAND_SEEKDIR:
86 case FS_COMMAND_FINDPATH:
87 case FS_COMMAND_GETPATH:
88 case FS_COMMAND_OPENFILEFAST:
89 return FS_RESULT_UNSUPPORTED;
90 default:
91 return FS_RESULT_PROC_UNKNOWN;
92 }
93 }
94
95 /*---------------------------------------------------------------------------*
96 Name: FSi_InitMemArchive
97
98 Description: Initializes a memory mapped file archive.
99
100 Arguments: None.
101
102 Returns: None.
103 *---------------------------------------------------------------------------*/
FSi_InitMemArchive(void)104 static void FSi_InitMemArchive(void)
105 {
106 OSIntrMode bak_cpsr = OS_DisableInterrupts();
107
108 if (!fsi_mem_init || !FS_IsArchiveLoaded(&fsi_arc_mem))
109 {
110 FS_InitArchive(&fsi_arc_mem);
111 FS_SetArchiveProc(&fsi_arc_mem, FSi_MemArchiveProc, (u32)FS_ARCHIVE_PROC_ALL);
112 if (!FS_LoadArchive(&fsi_arc_mem, 0, 0, 0, 0, 0, NULL, NULL))
113 {
114 OS_TPanic("failed to load memory-mapping archive!");
115 }
116 fsi_mem_init = TRUE;
117 }
118
119 (void)OS_RestoreInterrupts(bak_cpsr);
120 }
121
122 /*---------------------------------------------------------------------------*
123 Name: FS_CreateFileFromMemory
124
125 Description: Temporarily generates file that maps memory region.
126
127 Arguments: p_file: FSFile structure that stores file handle
128 buf: Memory that is target of READ and WRITE
129 size: Byte size of buf
130
131 Returns: None.
132 *---------------------------------------------------------------------------*/
FS_CreateFileFromMemory(FSFile * p_file,void * buf,u32 size)133 BOOL FS_CreateFileFromMemory(FSFile *p_file, void *buf, u32 size)
134 {
135 FSi_InitMemArchive();
136 return FS_OpenFileDirect(p_file, &fsi_arc_mem, (u32)buf, (u32)buf + size, 0);
137 }
138
139 /*---------------------------------------------------------------------------*
140 Name: FS_OpenTopLevelDirectory
141
142 Description: Opens the special high-level directory that can enumerate the archive name
143
144 Arguments: dir: FSFile structure that stores directory handle
145
146 Returns: If successful, TRUE.
147 *---------------------------------------------------------------------------*/
FS_OpenTopLevelDirectory(FSFile * dir)148 BOOL FS_OpenTopLevelDirectory(FSFile *dir)
149 {
150 FSi_InitMemArchive();
151 FS_InitFile(dir);
152 dir->prop.dir.pos.pos = (u32)FSi_GetArchiveChain();
153 FS_SetDirectoryHandle(dir, &fsi_arc_mem, &dir->prop);
154 return TRUE;
155 }
156
157
158 #endif /* FS_IMPLEMENT */
159