1 /*---------------------------------------------------------------------------*
2   Project:  TwlSDK - FS - demos - async
3   File:     main.c
4 
5   Copyright 2003-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-10-02 #$
14   $Rev: 8827 $
15   $Author: yosizaki $
16  *---------------------------------------------------------------------------*/
17 
18 #include <nitro.h>
19 
20 
21 // Behavioral test of asynchronous FS operations
22 
23 enum
24 {
25     data_00,
26     data_ff,
27     data_inc,
28     data_dec,
29     datamode_max
30 };
31 
32 #define	TASK_THREAD_MAX	4
33 #define	TASK_REPEAT_TIMES	1
34 
35 typedef struct
36 {
37     OSThread thread;
38     u8      stack[4096] ATTRIBUTE_ALIGN(32);
39     u8      buf[CARD_ROM_PAGE_SIZE] ATTRIBUTE_ALIGN(32);
40     int     mode;
41     u32     priority;
42     u8      padding[24];
43 }
44 TaskThread;
45 
46 
47 static TaskThread task_thread[TASK_THREAD_MAX] ATTRIBUTE_ALIGN(32);
48 static u32 total_read_size = 0;
49 
50 // A task that opens a file and continues to read
AsyncAccessTask(void * p)51 static void AsyncAccessTask(void *p)
52 {
53     TaskThread *const pt = (TaskThread *) p;
54     int     i;
55     int     repeat;
56     int     count;
57     int     total_size;
58     BOOL    ret;
59     FSFile  file;
60     count = 0;
61     repeat = 0;
62     total_size = 0;
63     for (;;)
64     {
65         switch (pt->mode)
66         {
67         case data_00:
68             ret = FS_OpenFileEx(&file, "rom:/00.bin", FS_FILEMODE_R);
69             break;
70         case data_ff:
71             ret = FS_OpenFileEx(&file, "rom:/ff.bin", FS_FILEMODE_R);
72             break;
73         case data_inc:
74             ret = FS_OpenFileEx(&file, "rom:/inc.bin", FS_FILEMODE_R);
75             break;
76         case data_dec:
77             ret = FS_OpenFileEx(&file, "rom:/dec.bin", FS_FILEMODE_R);
78             break;
79         default:
80             ret = FALSE;
81             break;
82         }
83         SDK_ASSERT(ret);
84         for (;;)
85         {
86             int     n = FS_ReadFile(&file, pt->buf, sizeof(pt->buf));
87             SDK_ASSERT(n >= 0);
88             if (n == 0)
89                 break;
90             switch (pt->mode)
91             {
92             case data_00:
93                 for (i = 0; i < n; ++i)
94                 {
95                     SDK_ASSERT(pt->buf[i] == 0x00);
96                 }
97                 break;
98             case data_ff:
99                 for (i = 0; i < n; ++i)
100                 {
101                     SDK_ASSERT(pt->buf[i] == 0xFF);
102                 }
103                 break;
104             case data_inc:
105                 for (i = 0; i < n; ++i)
106                 {
107                     SDK_ASSERT(pt->buf[i] == (u8)i);
108                 }
109                 break;
110             case data_dec:
111                 for (i = 0; i < n; ++i)
112                 {
113                     SDK_ASSERT(pt->buf[i] == (u8)~i);
114                 }
115                 break;
116             }
117             total_size += n;
118         }
119         ret = FS_CloseFile(&file);
120         SDK_ASSERT(ret);
121         ++count;
122         if (++repeat >= TASK_REPEAT_TIMES)
123         {
124             u32     current_total;
125             OSIntrMode bak_psr = OS_DisableInterrupts();
126             total_read_size += total_size;
127             current_total = total_read_size;
128             total_size = 0;
129             OS_TPrintf("thread[%d](priority=%2d) : %8d times done. (mode=%d) ... total %8d byte\n",
130                        pt - task_thread, pt->priority, count, pt->mode, current_total);
131             (void)OS_RestoreInterrupts(bak_psr);
132             repeat = 0;
133             if (++pt->mode >= datamode_max)
134             {
135                 pt->mode = data_00;
136             }
137         }
138     }
139 }
140 
NitroMain(void)141 void NitroMain(void)
142 {
143     // Initialize the OS and memory allocator
144     OS_Init();
145     {
146         OSHeapHandle hh;
147         void   *tmp;
148         tmp = OS_InitAlloc(OS_ARENA_MAIN, OS_GetMainArenaLo(), OS_GetMainArenaHi(), 1);
149         OS_SetArenaLo(OS_ARENA_MAIN, tmp);
150         hh = OS_CreateHeap(OS_ARENA_MAIN, OS_GetMainArenaLo(), OS_GetMainArenaHi());
151         if (hh < 0)
152         {
153             OS_TPanic("ARM9: Fail to create heap...\n");
154         }
155         (void)OS_SetCurrentHeap(OS_ARENA_MAIN, hh);
156     }
157     (void)OS_EnableIrq();
158     // Initialize the FS
159     FS_Init(3);
160     {
161         u32     need_size = FS_GetTableSize();
162         void   *p_table = OS_Alloc(need_size);
163         SDK_ASSERT(p_table != NULL);
164         (void)FS_LoadTable(p_table, need_size);
165     }
166 
167     OS_TPrintf("\n"
168                "++++++++++++++++++++++++++++++++++++++++\n"
169                "test : create %d threads to check asynchronous access ... \n\n", TASK_THREAD_MAX);
170     {
171         int     i;
172         // Create multiple threads that continue to read a file
173         for (i = 0; i < TASK_THREAD_MAX; ++i)
174         {
175             TaskThread * pt = &task_thread[i];
176             pt->mode = data_00 + i;
177             pt->priority = (u32)(OS_THREAD_LAUNCHER_PRIORITY - (pt - task_thread));
178             OS_CreateThread(&pt->thread,
179                             AsyncAccessTask, pt,
180                             pt->stack + sizeof(pt->stack), sizeof(pt->stack), pt->priority);
181             OS_WakeupThreadDirect(&pt->thread);
182         }
183     }
184 
185     // As for the rest, a log will continue to be output for each thread
186     for (;;)
187     {
188         OS_Halt();
189     }
190 
191 }
192