1 /*---------------------------------------------------------------------------*
2   Project:  TwlSDK - OS
3   File:     os_argument.c
4 
5   Copyright 2005-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:: 2009-02-04#$
14   $Rev: 9969 $
15   $Author: yada $
16  *---------------------------------------------------------------------------*/
17 #include <nitro/os.h>
18 #include <nitro/std/string.h>
19 #ifdef SDK_TWL
20 #include <twl/os/common/systemWork.h>
21 #endif
22 
23 #define OSi_INIVALUE    0xffff
24 
25 #ifndef OS_NO_ARGUMENT
26 
27 #ifdef SDK_NITRO
28 //---- for Nitro
29 #include <nitro/version_begin.h>
30 //---- This area is for argument string, and may be
31 //     modified from external tools.
32 static OSArgumentBuffer OSi_ArgumentBuffer = {
33     OS_ARGUMENT_ID_STRING,
34     OS_ARGUMENT_BUFFER_SIZE,
35     {'\0', '\0'},
36 };
37 #include <nitro/version_end.h>
38 
39 //---- pointer to current argument buffer
40 const char *sCurrentArgBuffer = &OSi_ArgumentBuffer.buffer[0];
41 #endif
42 #ifdef SDK_TWL
43 const char *sCurrentArgBuffer = (const char*)(HW_TWL_ROM_HEADER_BUF + 0xe00);
44 #endif
45 
46 static const char *match_opt(int optchar, const char *optstring);
47 #endif //ifndef OS_NO_ARGUMENT
48 
49 //---- for TWL
50 #ifdef SDK_TWL
51 static u32                  sBufferState = OS_DELIVER_ARG_BUF_INVALID;
52 static OSDeliverArgInfo*    sBufferPtr = NULL;
53 static u8*                  sPtr;
54 static OSTitleId            sEncodedTitleId = 0;
55 #endif
56 
57 static int OSi_GetArgc_core(const char* p);
58 static const char *OSi_GetArgv_core(const char *p, int n);
59 
60 
61 /*---------------------------------------------------------------------------*
62   Name:         ( OSi_GetArgc_core )
63 
64   Description:  Get number of valid arguments.
65 
66   Arguments:    p: pointer to argument buffer
67 
68   Returns:      number of valid arguments.
69  *---------------------------------------------------------------------------*/
OSi_GetArgc_core(const char * p)70 static int OSi_GetArgc_core(const char* p)
71 {
72     int     n = 0;
73     for (; *p; p++, n++)
74     {
75         while (*p)
76         {
77             p++;
78         }
79     }
80     return n;
81 }
82 
83 /*---------------------------------------------------------------------------*
84   Name:         OS_GetArgc
85 
86   Description:  Get number of valid arguments.
87                 This function is for debug.
88 
89   Arguments:    None.
90 
91   Returns:      number of valid arguments.
92                 return 1 if no argument.
93                 return 0 if not set argument buffer.
94  *---------------------------------------------------------------------------*/
95 #ifndef OS_NO_ARGC_AND_ARGV
OS_GetArgc(void)96 int OS_GetArgc(void)
97 {
98 	return OSi_GetArgc_core( (const char *)sCurrentArgBuffer );
99 }
100 #endif
101 
102 
103 /*---------------------------------------------------------------------------*
104   Name:         ( OSi_GetArgv_core )
105 
106   Description:  Get the pointer to the specified argument string.
107 
108   Arguments:    n: index of argument. n==1 means the first argument.
109 
110   Returns:      n must less than value of OS_GetArgc()
111  *---------------------------------------------------------------------------*/
OSi_GetArgv_core(const char * p,int n)112 static const char *OSi_GetArgv_core(const char *p, int n)
113 {
114     SDK_ASSERT(n >= 0);
115 	for (; *p && n > 0; p++, n--)
116 	{
117 		while (*p)
118 		{
119 			p++;
120 		}
121     }
122     return (*p) ? p : NULL;
123 }
124 
125 /*---------------------------------------------------------------------------*
126   Name:         OS_GetArgv
127 
128   Description:  Get the pointer to the specified argument string.
129                 This function is for debug.
130 
131   Arguments:    n: index of argument. n==1 means the first argument.
132                     n must less than value of OS_GetArgc()
133 
134   Returns:      pointer to the specified argument string
135  *---------------------------------------------------------------------------*/
136 #ifndef OS_NO_ARGC_AND_ARGV
OS_GetArgv(int n)137 const char* OS_GetArgv(int n)
138 {
139 	return OSi_GetArgv_core( (const char *)sCurrentArgBuffer, n );
140 }
141 #endif
142 
143 
144 /*---------------------------------------------------------------------------*
145   Name:         OS_GetOpt
146 
147   Description:  getopt() like function to get command line options
148 
149   Arguments:    optstring: Option character string
150                            Internal parameters are reset if NULL.
151 
152   Returns:      Option character code.
153                 '?' Indicates the option character code is unclear.
154                 If -1, the option does not exist
155  *---------------------------------------------------------------------------*/
156 #ifndef OS_NO_ARGUMENT
157 const char *OSi_OptArg = NULL;
158 int     OSi_OptInd = 1;
159 int     OSi_OptOpt = 0;
160 
OS_GetOpt(const char * optstring)161 int OS_GetOpt(const char *optstring)
162 {
163     static BOOL end_of_option = FALSE;
164     int     optchar;
165     const char *arg;
166     const char *opt;
167     const char *optarg;
168 
169     OSi_OptArg = NULL;
170     OSi_OptOpt = 0;
171 
172     // Reset if optstring is NULL
173     if (optstring == NULL)
174     {
175         OSi_OptInd = 1;
176         end_of_option = FALSE;
177         return 0;
178     }
179 
180     // Get command line arguments
181     arg = OS_GetArgv(OSi_OptInd);
182 
183     if (arg == NULL)
184     {
185         return -1;
186     }
187 
188     if (optstring[0] == '-')           // Minus Mode
189     {
190         OSi_OptInd++;                  // Consume arguments
191 
192         // Normal argument when it does not start with '-'
193         if (end_of_option || arg[0] != '-')
194         {
195             OSi_OptArg = arg;          // Normal arguments are also set to OptArg.
196             return 1;
197         }
198 
199         // Option analysis
200         optchar = arg[1];
201 
202         if (optchar == '-')            // End of options when '--' is encountered
203         {
204             end_of_option = TRUE;      // Normal arguments from here on
205             return OS_GetOpt(optstring);
206         }
207     }
208     else                               // normal mode
209     {
210         // Normal argument when it does not start with '-'
211         if (end_of_option || arg[0] != '-')
212         {
213             return -1;                 // OptArg remains NULL
214         }
215 
216         OSi_OptInd++;                  // Consume arguments
217 
218         // Option analysis
219         optchar = arg[1];
220 
221         if (optchar == '-')            // End of options when '--' is encountered
222         {
223             end_of_option = TRUE;      // Normal arguments from here on
224             return -1;
225         }
226 
227     }
228 
229     opt = match_opt(optchar, optstring);
230 
231     if (opt == NULL)
232     {
233         OSi_OptOpt = optchar;          // Unknown option
234         return '?';
235     }
236 
237     if (opt[1] == ':')                 // OptArg search specification?
238     {
239         optarg = OS_GetArgv(OSi_OptInd);
240 
241         if (optarg == NULL || optarg[0] == '-')
242         {
243             if (opt[2] != ':')         // '::' Or not?
244             {
245                 OSi_OptOpt = optchar;  // OptArg not present.
246                 return '?';
247             }
248             // OptArg not present.
249             // OSi_OptArg = NULL
250         }
251         else
252         {
253             OSi_OptArg = optarg;
254             OSi_OptInd++;              // Consume arguments
255         }
256     }
257     return optchar;
258 }
259 
match_opt(int optchar,const char * optstring)260 static const char *match_opt(int optchar, const char *optstring)
261 {
262     if (optstring[0] == '-' || optstring[0] == '+')
263     {
264         optstring++;
265     }
266 
267     if (optchar != ':')
268     {
269         while (*optstring)
270         {
271             if (optchar == *optstring)
272             {
273                 return optstring;
274             }
275             optstring++;
276         }
277     }
278     return NULL;
279 }
280 #endif // ifndef OS_NO_ARGUMENT
281 
282 /*---------------------------------------------------------------------------*
283   Name:         OS_ConvertToArguments
284 
285   Description:  convert string data to arg binary
286 
287   Arguments:    str : string
288                 cs      : character to separate
289                 buffer: buffer to store
290                 bufSize: max buffer size
291 
292   Returns:      None.
293  *---------------------------------------------------------------------------*/
294 #ifndef OS_NO_ARGUMENT
OS_ConvertToArguments(const char * str,char cs,char * buffer,u32 bufSize)295 void OS_ConvertToArguments(const char *str, char cs, char *buffer, u32 bufSize)
296 {
297     char   *p = buffer;
298     char   *pEnd = buffer + bufSize;
299     BOOL    isQuoted = FALSE;
300 
301     while (1)
302     {
303         //---- skip separator
304         while (*str == cs && p < pEnd)
305         {
306             str++;
307         }
308 
309         //---- store argument string
310         while (*str && p < pEnd)
311         {
312             //---- check quote
313             if (*str == '\"')
314             {
315                 isQuoted = (isQuoted == FALSE);
316                 str++;
317                 continue;
318             }
319 
320             //---- found separator
321             else if (*str == cs && isQuoted == FALSE)
322             {
323                 break;
324             }
325 
326             *p++ = *str++;
327         }
328 
329         //---- 1) reached to the buffer end
330         if (p >= pEnd)
331         {
332             *(pEnd - 2) = '\0';
333             *(pEnd - 1) = '\0';
334             break;
335         }
336 
337         //---- 2) reached to the string end
338         if (*str == '\0')
339         {
340             while ((p + 1) >= pEnd)
341             {
342                 p--;
343             }
344             *p++ = '\0';
345             *p = '\0';
346             break;
347         }
348 
349         //---- 3) separator
350         if (*str == cs)
351         {
352             *p++ = '\0';
353         }
354     }
355 
356     //---- end mark
357     if (p < pEnd)
358     {
359         *p++ = '\0';
360     }
361 }
362 #endif //ifndef OS_NO_ARGUMENT
363 
364 /*---------------------------------------------------------------------------*
365   Name:         OS_SetArgumentBuffer
366 
367   Description:  force to set argument buffer.
368 
369   Arguments:    buffer: argument buffer
370 
371   Returns:      None.
372  *---------------------------------------------------------------------------*/
373 #ifndef OS_NO_ARGUMENT
OS_SetArgumentBuffer(const char * buffer)374 void OS_SetArgumentBuffer(const char *buffer)
375 {
376     sCurrentArgBuffer = buffer;
377 }
378 #endif //ifndef OS_NO_ARGUMENT
379 
380 /*---------------------------------------------------------------------------*
381   Name:         OS_GetArgumentBuffer
382 
383   Description:  get pointer to argument buffer.
384 
385   Arguments:    None.
386 
387   Returns:      pointer to argument buffer.
388  *---------------------------------------------------------------------------*/
389 #ifndef OS_NO_ARGUMENT
OS_GetArgumentBuffer(void)390 const char *OS_GetArgumentBuffer(void)
391 {
392     return sCurrentArgBuffer;
393 }
394 #endif //ifndef OS_NO_ARGUMENT
395 
396 
397 //================================================================================
398 // for TWL
399 //================================================================================
400 #ifdef SDK_TWL
401 /*---------------------------------------------------------------------------*
402   Name:         OS_InitDeliverArgInfo
403 
404   Description:  initialize the argument delivery system for TWL
405 
406   Arguments:    binSize : buffer size for binary area.
407 
408   Returns:      None.
409  *---------------------------------------------------------------------------*/
OS_InitDeliverArgInfo(OSDeliverArgInfo * info,int binSize)410 void OS_InitDeliverArgInfo( OSDeliverArgInfo* info, int binSize )
411 {
412     SDK_ASSERT( 2<=(OS_DELIVER_ARG_BUFFER_SIZE-binSize) && binSize>=0);
413     SDK_ASSERT( info != NULL );
414 
415     sBufferPtr = info;
416 
417     //---- clear whole buffer
418     MI_CpuClear8( sBufferPtr, HW_PARAM_DELIVER_ARG_SIZE );
419 
420     //---- set parameters
421     sBufferState = OS_DELIVER_ARG_BUF_ACCESSIBLE | OS_DELIVER_ARG_BUF_WRITABLE;
422     sBufferPtr->header.argBufferSize = (u16)(OS_DELIVER_ARG_BUFFER_SIZE - binSize);
423     sBufferPtr->header.binarySize = 0;
424 
425     //---- init pointer
426     sPtr = &sBufferPtr->buf[0];
427     *sPtr = '\0';
428     *(sPtr+1) = '\0';
429 }
430 
431 /*---------------------------------------------------------------------------*
432   Name:         OS_SetStringToDeliverArg
433 
434   Description:  write specified string as argument data
435 
436   Arguments:    str : string to write
437 
438   Returns:      OS_DELIVER_ARG_SUCCESS   ... success.
439                 OS_DELIVER_ARG_OVER_SIZE ... failed. (over buffer)
440                 OS_DELIVER_ARG_NOT_READY ... failed. (buffer is not writable)
441  *---------------------------------------------------------------------------*/
OS_SetStringToDeliverArg(const char * str)442 int OS_SetStringToDeliverArg( const char* str )
443 {
444     int length;
445 
446     //---- check buffer state
447     if ( !(sBufferState & OS_DELIVER_ARG_BUF_WRITABLE) )
448     {
449         return OS_DELIVER_ARG_NOT_READY;
450     }
451 
452     //---- check buffer over
453     length = STD_StrLen( str );
454 
455     if ( length > sBufferPtr->header.argBufferSize - (sPtr - &sBufferPtr->buf[0]) - 2)
456     {
457         return OS_DELIVER_ARG_OVER_SIZE;
458     }
459 
460     //---- copy string
461     (void)STD_StrCpy( (char*)sPtr, str );
462     sPtr += length;
463     *sPtr++ = '\0';
464     *sPtr = '\0';
465 
466     //---- return result
467     return OS_DELIVER_ARG_SUCCESS;
468 }
469 
470 
471 /*---------------------------------------------------------------------------*
472   Name:         OS_SetBinaryToDeliverArg
473 
474   Description:  write specified binary
475 
476   Arguments:    bin  : pointer for binary
477                 size: binary size
478 
479   Returns:      OS_DELIVER_ARG_SUCCESS   ... success.
480                 OS_DELIVER_ARG_OVER_SIZE ... failed. (over buffer)
481                 OS_DELIVER_ARG_NOT_READY ... failed. (buffer is not writable)
482  *---------------------------------------------------------------------------*/
OS_SetBinaryToDeliverArg(const void * bin,int size)483 int OS_SetBinaryToDeliverArg( const void* bin, int size )
484 {
485     u8* dest = &sBufferPtr->buf[ sBufferPtr->header.argBufferSize + sBufferPtr->header.binarySize ];
486 
487     //---- check buffer state
488     if ( !(sBufferState & OS_DELIVER_ARG_BUF_WRITABLE) )
489     {
490         return OS_DELIVER_ARG_NOT_READY;
491     }
492 
493     //---- check buffer over
494     if ( size > OS_DELIVER_ARG_BUFFER_SIZE - sBufferPtr->header.argBufferSize - sBufferPtr->header.binarySize )
495     {
496         return OS_DELIVER_ARG_OVER_SIZE;
497     }
498 
499     //---- write binary data to buffer
500     MI_CpuCopy8( bin, dest, (u32)size );
501     sBufferPtr->header.binarySize += (u16)size;
502 
503     //---- return result
504     return OS_DELIVER_ARG_SUCCESS;
505 }
506 
507 /*---------------------------------------------------------------------------*
508   Name:         OS_ConvertStringToDeliverArg
509 
510   Description:  Coverts string to arguments
511 
512   Arguments:    str : string
513                 cs      : character to separate
514 
515   Returns:      OS_DELIVER_ARG_SUCCESS    ... success
516                 OS_DELIVER_ARG_OVER_SIZE ... failed. (over buffer)
517                 OS_DELIVER_ARG_NOT_READY ... failed. (buffer is not writable)
518  *---------------------------------------------------------------------------*/
OS_ConvertStringToDeliverArg(const char * str,char cs)519 int OS_ConvertStringToDeliverArg(const char *str, char cs)
520 {
521     int length;
522     const char* endp;
523 
524     //---- check buffer state
525     if ( !(sBufferState & OS_DELIVER_ARG_BUF_WRITABLE) )
526     {
527         return OS_DELIVER_ARG_NOT_READY;
528     }
529 
530     while (1)
531     {
532         //---- skip separator
533         while ( *str == cs )
534         {
535             str++;
536         }
537 
538         //---- check string end
539         if ( ! *str )
540         {
541             break;
542 
543         }
544 
545         //---- search separator
546         endp = str;
547         while ( *endp != cs && *endp != '\0' )
548         {
549             endp++;
550         }
551         length = endp - str;
552 
553         //---- check buffer over
554         if ( length > sBufferPtr->header.argBufferSize - (sPtr - &sBufferPtr->buf[0]) - 2)
555         {
556             return OS_DELIVER_ARG_OVER_SIZE;
557         }
558 
559         //---- copy string
560         while( str != endp )
561         {
562             *sPtr ++ = *(u8*)str ++;
563         }
564         *sPtr ++ = '\0';
565         *sPtr = '\0';
566     }
567 
568     return OS_DELIVER_ARG_SUCCESS;
569 }
570 
571 /*---------------------------------------------------------------------------*
572   Name:         OS_EncodeDeliverArg
573 
574   Description:  Encodes argument buffer.
575 
576   Arguments:    None.
577 
578   Returns:      OS_DELIVER_ARG_SUCCESS    ... success
579                 OS_DELIVER_ARG_NOT_READY  ... failed. (buffer is not accesible)
580  *---------------------------------------------------------------------------*/
OS_EncodeDeliverArg(void)581 int OS_EncodeDeliverArg(void)
582 {
583     //---- check buffer state
584     if ( !(sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE) )
585     {
586         return OS_DELIVER_ARG_NOT_READY;
587     }
588 
589     //---- set makerCode, titleId
590     sBufferPtr->header.makerCode = OS_GetMakerCode();
591     sBufferPtr->header.titleId = OS_GetTitleId();
592 
593     //---- set flag
594     sBufferPtr->header.flag = OS_DELIVER_ARG_ENCODE_FLAG | OS_DELIVER_ARG_VALID_FLAG;
595 
596     //---- set encoded titleId
597     sEncodedTitleId = sBufferPtr->header.titleId;
598 
599     //---- calculate crc
600     sBufferPtr->header.crc = 0;
601     sBufferPtr->header.crc = SVC_GetCRC16( OSi_INIVALUE, (const void*)sBufferPtr, sizeof(OSDeliverArgInfo) );
602 
603     //---- copy to HW_PARAM_DELIVER_ARG
604     MI_CpuCopy8( sBufferPtr, (void*)HW_PARAM_DELIVER_ARG, sizeof(OSDeliverArgInfo) );
605 
606     //---- clearArea
607     MI_CpuClear8( sBufferPtr, sizeof(OSDeliverArgInfo) );
608 
609     //---- buffer state
610     sBufferState = OS_DELIVER_ARG_BUF_INVALID;
611 
612     return OS_DELIVER_ARG_SUCCESS;
613 }
614 
615 /*---------------------------------------------------------------------------*
616   Name:         OS_DecodeDeliverArg
617 
618   Description:  Decodes to work buffer from HW_PARAM_DELIVER_ARG
619 
620   Arguments:    None.
621 
622   Returns:      OS_DELIVER_ARG_SUCCESS    ... success
623                 OS_DELIVER_ARG_NOT_READY  ... not ready
624                 OS_DELIVER_ARG_INVALID    ... invalid CRC check
625  *---------------------------------------------------------------------------*/
OS_DecodeDeliverArg(void)626 int OS_DecodeDeliverArg(void)
627 {
628     //----check if deliver arg contains valid data
629     if ( !OS_IsValidDeliverArg() )
630     {
631         return OS_DELIVER_ARG_NOT_READY;
632     }
633 
634     //----check buffer
635     if ( ! sBufferPtr )
636     {
637         return OS_DELIVER_ARG_NOT_READY;
638     }
639 
640     //---- copy from HW_PARAM_DELIVER_ARG
641     MI_CpuCopy8( (void*)HW_PARAM_DELIVER_ARG, sBufferPtr, sizeof(OSDeliverArgInfo) );
642 
643     //---- crc check
644     {
645         u16 crc = sBufferPtr->header.crc;
646         sBufferPtr->header.crc = 0;
647         sBufferPtr->header.crc = SVC_GetCRC16( OSi_INIVALUE, (const void*)sBufferPtr, sizeof(OSDeliverArgInfo) );
648         if ( crc != sBufferPtr->header.crc )
649         {
650             MI_CpuClear8( sBufferPtr, sizeof(OSDeliverArgInfo) );
651             OS_SetDeliverArgStateInvalid();
652             return OS_DELIVER_ARG_BUF_INVALID;
653         }
654     }
655 
656     //---- unset encode flag
657     sBufferPtr->header.flag &= ~OS_DELIVER_ARG_ENCODE_FLAG;
658 
659     //---- buffer state
660     sBufferState = OS_DELIVER_ARG_BUF_ACCESSIBLE;
661 
662     return OS_DELIVER_ARG_SUCCESS;
663 }
664 
665 /*---------------------------------------------------------------------------*
666   Name:         OS_GetDeliverArgState
667 
668   Description:  Gets deliver arg state
669 
670   Arguments:    None.
671 
672   Returns:      state.
673                 one of the following:
674                   OS_DELIVER_ARG_BUF_INVALID
675                   OS_DELIVER_ARG_BUF_ACCESSIBLE
676                   OS_DELIVER_ARG_BUF_ACCESSIBLE | OS_DELIVER_ARG_BUF_WRITABLE
677  *---------------------------------------------------------------------------*/
OS_GetDeliverArgState(void)678 u32 OS_GetDeliverArgState(void)
679 {
680     return sBufferState;
681 }
682 
683 /*---------------------------------------------------------------------------*
684   Name:         OSi_SetDeliverArgState
685 
686   Description:  Sets deliver arg state
687 
688   Arguments:    state.
689                 one of the following:
690                   OS_DELIVER_ARG_BUF_INVALID
691                   OS_DELIVER_ARG_BUF_ACCESSIBLE
692                   OS_DELIVER_ARG_BUF_ACCESSIBLE | OS_DELIVER_ARG_BUF_WRITABLE
693 
694   Returns:      None.
695  *---------------------------------------------------------------------------*/
OSi_SetDeliverArgState(u32 state)696 void OSi_SetDeliverArgState(u32 state)
697 {
698     sBufferState = state;
699 }
700 
701 /*---------------------------------------------------------------------------*
702   Name:         OS_SetDeliverArgStateInvalid
703 
704   Description:  Sets OS_DELIVER_ARG_BUF_INVALID to deliver arg state
705 
706   Arguments:    None.
707 
708   Returns:      None.
709  *---------------------------------------------------------------------------*/
OS_SetDeliverArgStateInvalid(void)710 void OS_SetDeliverArgStateInvalid( void )
711 {
712     sBufferState = OS_DELIVER_ARG_BUF_INVALID;
713 }
714 
715 /*---------------------------------------------------------------------------*
716   Name:         OS_GetBinarySizeFromDeliverArg
717 
718   Description:  Reads binary size
719 
720   Arguments:    None.
721 
722   Returns:      0> ... size
723                 -1 ... work area not ready
724  *---------------------------------------------------------------------------*/
OS_GetBinarySizeFromDeliverArg(void)725 int OS_GetBinarySizeFromDeliverArg(void)
726 {
727     if ( !(sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE) )
728     {
729         return -1;
730     }
731 
732     return sBufferPtr->header.binarySize;
733 }
734 
735 /*---------------------------------------------------------------------------*
736   Name:         OS_GetBinaryFromDeliverArg
737 
738   Description:  Reads binary data
739 
740   Arguments:    buffer: pointer for binary
741                 size: pointer for binary size
742                 maxSize : Max size
743 
744   Returns:      OS_DELIVER_ARG_SUCCESS   ... success.
745                 OS_DELIVER_ARG_OVER_SIZE ... success but buffer over.
746                 OS_DELIVER_ARG_NOT_READY ...
747  *---------------------------------------------------------------------------*/
OS_GetBinaryFromDeliverArg(void * buffer,int * size,int maxSize)748 int OS_GetBinaryFromDeliverArg( void* buffer, int* size, int maxSize )
749 {
750     int retval;
751     int copySize;
752 
753     //---- check buffer state
754     if ( !(sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE) )
755     {
756         return OS_DELIVER_ARG_NOT_READY;
757     }
758 
759     //---- check buffer over
760     if ( maxSize < sBufferPtr->header.binarySize )
761     {
762         retval = OS_DELIVER_ARG_OVER_SIZE;
763         copySize = maxSize;
764     }
765     else
766     {
767         retval = OS_DELIVER_ARG_SUCCESS;
768         copySize = sBufferPtr->header.binarySize;
769     }
770 
771     //---- read binary data
772     MI_CpuCopy8( &sBufferPtr->buf[sBufferPtr->header.argBufferSize], buffer, (u32)copySize );
773     if ( size )
774     {
775         *size = copySize;
776     }
777 
778     return retval;
779 }
780 
781 /*---------------------------------------------------------------------------*
782   Name:         OS_GetTitleIdFromDeliverArg
783 
784   Description:  Gets the title ID
785 
786   Arguments:    None.
787 
788   Returns:      title ID.
789                 if not accessible, return 0
790  *---------------------------------------------------------------------------*/
OS_GetTitleIdFromDeliverArg(void)791 OSTitleId OS_GetTitleIdFromDeliverArg( void )
792 {
793     return (sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE)? sBufferPtr->header.titleId: 0;
794 }
795 
796 /*---------------------------------------------------------------------------*
797   Name:         OS_GetGameCodeFromDeliverArg
798 
799   Description:  Gets the game code
800 
801   Arguments:    None.
802 
803   Returns:      game code
804                 if not accessible, return 0
805  *---------------------------------------------------------------------------*/
OS_GetGameCodeFromDeliverArg(void)806 u32 OS_GetGameCodeFromDeliverArg( void )
807 {
808     return (sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE)? *(u32*)(&sBufferPtr->header.titleId): 0;
809 }
810 
811 /*---------------------------------------------------------------------------*
812   Name:         OS_GetMakerCodeFromDeliverArg
813 
814   Description:  Gets the maker code
815 
816   Arguments:    None.
817 
818   Returns:      maker code
819                 if not accessible, return 0
820  *---------------------------------------------------------------------------*/
OS_GetMakerCodeFromDeliverArg(void)821 u16 OS_GetMakerCodeFromDeliverArg( void )
822 {
823     return (u16)((sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE)? sBufferPtr->header.makerCode: 0);
824 }
825 
826 /*---------------------------------------------------------------------------*
827   Name:         OS_IsValidDeliverArg
828 
829   Description:  Checks if deliver arg contains valid data
830 
831   Arguments:    None.
832 
833   Returns:      TRUE if valid
834                 FALSE if not valid
835  *---------------------------------------------------------------------------*/
OS_IsValidDeliverArg(void)836 BOOL OS_IsValidDeliverArg( void )
837 {
838     // TODO: a more reliable verification
839     OSDeliverArgInfo* p = (OSDeliverArgInfo*)HW_PARAM_DELIVER_ARG;
840 
841     return (p->header.flag & OS_DELIVER_ARG_VALID_FLAG) ? TRUE : FALSE;
842 }
843 
844 /*---------------------------------------------------------------------------*
845   Name:         OS_IsDeliverArgEncoded
846 
847   Description:  Gets titleId that is contained in last encoded deliverArg
848 
849   Arguments:    None.
850 
851   Returns:      TRUE  if deliverArg has been encoded
852                 FALSE if deliverArg has never been encoded since application was
853                 launched
854  *---------------------------------------------------------------------------*/
OS_IsDeliverArgEncoded(void)855 BOOL OS_IsDeliverArgEncoded( void )
856 {
857     OSDeliverArgInfo* p = (OSDeliverArgInfo*)HW_PARAM_DELIVER_ARG;
858     return (p->header.flag & (OS_DELIVER_ARG_ENCODE_FLAG | OS_DELIVER_ARG_VALID_FLAG)) ? TRUE : FALSE;
859 }
860 
861 /*---------------------------------------------------------------------------*
862   Name:         OS_GetTitleIdLastEncoded
863 
864   Description:  Gets titleId that is contained in last encoded deliverArg
865 
866   Arguments:    None.
867 
868   Returns:      TitleID if deliverArg has been encoded
869                 0 if deliverArg has never been encoded since application was
870                 launched
871  *---------------------------------------------------------------------------*/
OS_GetTitleIdLastEncoded(void)872 OSTitleId OS_GetTitleIdLastEncoded( void )
873 {
874 	return sEncodedTitleId;
875 }
876 
877 /*---------------------------------------------------------------------------*
878   Name:         OS_SetSysParamToDeliverArg
879 
880   Description:  set sysParam to deliverArg
881 
882   Arguments:    param: parameter to set
883 
884   Returns:      None.
885  *---------------------------------------------------------------------------*/
OS_SetSysParamToDeliverArg(u16 param)886 int OS_SetSysParamToDeliverArg( u16 param )
887 {
888     if ( !(sBufferState & OS_DELIVER_ARG_BUF_WRITABLE) )
889     {
890         return OS_DELIVER_ARG_NOT_READY;
891     }
892 
893     sBufferPtr->header.sysParam = param;
894     return OS_DELIVER_ARG_SUCCESS;
895 }
896 
897 /*---------------------------------------------------------------------------*
898   Name:         OS_GetSysParamFromDeliverArg
899 
900   Description:  Gets sysParam from deliverArg
901 
902   Arguments:    None.
903 
904   Returns:      parameter. 0 if FAIL.
905  *---------------------------------------------------------------------------*/
OS_GetSysParamFromDeliverArg(void)906 u16 OS_GetSysParamFromDeliverArg( void )
907 {
908     if ( !(sBufferState & OS_DELIVER_ARG_BUF_ACCESSIBLE) )
909     {
910         return 0;
911     }
912 
913     return sBufferPtr->header.sysParam;
914 }
915 
916 /*---------------------------------------------------------------------------*
917   Name:         OS_GetDeliverArgc
918 
919   Description:  GEts number of valid arguments in deliverArg.
920 
921   Arguments:    None.
922 
923   Returns:      number of valid arguments.
924                 return 1 if no argument.
925                 return 0 if buffer is not prepared.
926  *---------------------------------------------------------------------------*/
OS_GetDeliverArgc(void)927 int OS_GetDeliverArgc(void)
928 {
929     if ( sBufferPtr && sBufferState == OS_DELIVER_ARG_BUF_ACCESSIBLE )
930     {
931 		return OSi_GetArgc_core( (const char *)sBufferPtr->buf ) + 1;
932     }
933 
934     return 0;
935 }
936 
937 /*---------------------------------------------------------------------------*
938   Name:         OS_GetDeliverArgv
939 
940   Description:  Gets the pointer to the specified argument string in deliverArg.
941 
942   Arguments:    n: index of argument. n==1 means the first argument.
943                     n must be less than value of the OS_GetDeliverArgc function
944 
945   Returns:      pointer to string
946  *---------------------------------------------------------------------------*/
OS_GetDeliverArgv(int n)947 const char *OS_GetDeliverArgv(int n)
948 {
949     static const char *procName = "main";
950     SDK_ASSERT(n >= 0);
951 
952     if ( sBufferPtr && sBufferState == OS_DELIVER_ARG_BUF_ACCESSIBLE )
953     {
954 		return (n==0)? procName: OSi_GetArgv_core( (const char *)sBufferPtr->buf, n-1 );
955     }
956 
957     return NULL;
958 }
959 #endif //ifdef SDK_TWL
960