1 /*---------------------------------------------------------------------------*
2 Project: Revolution THP Converting tool
3 File: THPConv.c
4
5 Copyright (C)2002-2006 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 $Log: THPConv.c,v $
14 Revision 1.3 2007/11/26 07:17:29 nakano_yoshinobu
15 Fix for VC2005.
16
17 Revision 1.2 2006/12/21 07:07:22 aka
18 Removed resampling code.
19
20 Revision 1.1 2006/02/08 02:55:34 aka
21 Imported from Dolphin Tree.
22
23
24 22 2003/12/24 4:20p Akagi
25 Revised frame rate check.
26
27 21 2003/12/24 1:36p Akagi
28 Removed a function copyFile().
29 Changed calling from copyFile() to THPUtyCopyTHPFile().
30 Added frame rate check.
31
32 20 2003/12/08 2:27p Akagi
33 Revised 2 error messages.
34
35 19 2003/09/21 6:48p Akagi
36 Added several file checks.
37
38 18 2003/09/18 10:07a Akagi
39 Added option check.
40
41 17 2003/09/17 9:59p Akagi
42 Fixed some bugs.
43
44 16 2003/07/03 2:58p Akagi
45 Fixed 2 trivial bugs.
46
47 15 2003/07/03 11:09a Akagi
48 Renamed some functions.
49
50 14 2003/07/02 4:20p Akagi
51 Renamed from THPConv_main.c to THPConv.c.
52
53 13 2003/07/02 4:13p Akagi
54 Rewrote with DolphinSDK coding style.
55
56 12 2003/07/02 1:02p Akagi
57 Modified appendAudioData().
58
59 11 2003/07/01 2:55p Akagi
60 Modified to divide old THPConv.exe into 2 DLLs and 1 EXE by
61 Ohki-san@NTSC.
62
63 10 2003/07/01 9:54a Akagi
64 Moved from securebuild/tools.
65
66 9 2002/10/16 11:28a Akagi
67 JPEG & WAV file name bug fixed. (by iRD tsuji)
68
69 8 2002/05/30 2:21p Akagi
70 Stopped supporting QuickTime MJPEG By Tsuji (IRD)
71
72 7 2002/05/27 9:45a Akagi
73 Modified output error messages in English, by Tsuji (IRD)
74
75 6 2002/05/08 2:31p Akagi
76 Modified [-trk] option By Tsuji (IRD)
77
78 5 2002/05/01 3:09p Akagi
79 Added JPEG files sort program. By Tsuji (IRD)
80
81 4 2002/03/28 11:15a Akagi
82 Modified by Tsuji (IRD)
83
84 2 2002/01/22 10:10a Akagi
85 Added error message, when can't load "dsptools.dll" by Tsuji.
86
87 1 2002/01/16 4:58p Akagi
88 Initial revision made by Tsuji-san (IRD).
89
90 $NoKeywords: $
91
92 *---------------------------------------------------------------------------*/
93
94 #include <windows.h>
95 #include <CRTDBG.h>
96 #include <stdlib.h>
97 #include <stdio.h>
98 #include <sys/types.h>
99 #include <sys/stat.h>
100 #include <assert.h>
101 #include <string.h>
102
103 #include <revolution/types.h>
104 #include <revolution/thpfile.h>
105 #include <win32/thpcommon.h>
106 #include <win32/thpcore.h>
107 #include <win32/thputilities.h>
108 #include <win32/thpaudio.h>
109
110 //-----------------------------------------------------------------------------
111 // <The THP library functions being used>
112 //
113 // #include <win32/thputilities.h>
114 //
115 // THPUtyConvertToUnixFmt()
116 // THPUtyHeaderInit()
117 // THPUtyCreateTHP()
118 // THPUtyChangeAudioTrack()
119 // THPUtyReadTHPFileHeader()
120 // THPUtyCopyTHPFile()
121 //
122 // #include <win32/thpaudio.h>
123 //
124 // THPAudioInit()
125 // THPAudioCreateHandle()
126 // THPAudioGetInfo()
127 // THPAudioGetMaxFrameSamples()
128 // THPAudioGetTotalSamples()
129 // THPAudioQuit()
130 // THPAudioFreeHandle()
131 //
132 //-----------------------------------------------------------------------------
133
134 //-----------------------------------------------------------------------------
135 // Define
136 //-----------------------------------------------------------------------------
137 #define TMP_FILENAME "__tmp_VD"
138
139 #pragma warning (disable: 4996) //for VC2005
140
141 //-----------------------------------------------------------------------------
142 // Static Value
143 //-----------------------------------------------------------------------------
144 static char** jpegFilesPtr = NULL; // JPEG File name string array pointer
145 static u32 num_JPGfiles = 0; // Number of JPEG files
146
147 static char** waveFilesPtr = NULL; // WAV File name string array pointer
148 static u32 num_WAVfiles = 0; // Number of WAV files
149
150 static char* inFile = NULL; // Input filename
151 static char* outFile = NULL; // Output filename
152
153 static u32 pack_jpegs = 0; // Convert jpegs files to THP flag (-j)
154 static u32 change_snd_data = 0; // Change sound data flag (-c)
155 static u32 change_alltrack = 0; // Change all track data flag (-s)
156 static u32 change_onetrack = 0; // Change one track data flag (-trk)
157 static u8 change_framerate = 0; // Change framerate (-r)
158 static u8 change_videotype = 0; // Change videotype (-non/odd/even)
159 static u32 offset_mode = 0; // Offset flag (-o)
160
161 static f32 frame_rate = 29.97F; // Frame rate
162 static u32 videotype = THP_VIDEO_NON_INTERLACE;// Video Type
163
164 static u8 trackNo = 0; // Track # (-trk)
165
166 static u32 Convert_Verbose = 0;
167
168 //-----------------------------------------------------------------------------
169 // Function
170 //-----------------------------------------------------------------------------
171 static void Usage ( const char* progName );
172 static s32 verifyWriteOverInputData( const char* fileName );
173 static u32 getFileNameList ( const char *sWildcardPattern, THPFileName* filename );
174 static int compare ( const void *arg1, const void *arg2 );
175 static s32 checkArguments ( u32 argument_count, char *argv[] );
176 static s32 convertJPEGtoTHP ( void );
177 static s32 changeAudioTrack ( THPFileHeader* fileHeader );
178 static s32 appendAudioData ( THPFileHeader* fileHeader );
179 static s32 changeAudioData ( void );
180 static void logPrintFunc ( const char* format, va_list argptr );
181
182 /*---------------------------------------------------------------------------*
183 Name: Usage
184
185 Description: Command usage display
186
187 Arguments: progName Pointer to the program name
188
189 Returns: None
190 *---------------------------------------------------------------------------*/
Usage(const char * progName)191 static void Usage(const char* progName)
192 {
193 fprintf(stderr, "usage: %s [-OPTIONS]\n", progName);
194 fprintf(stderr, "\n");
195 fprintf(stderr, " <<JPEGs -> THP>>\n");
196 fprintf(stderr, " -j [*.jpg] # some JPEGs are packed into one file\n");
197 fprintf(stderr, " -d [file.thp] # output THP file name\n");
198 fprintf(stderr, "\n");
199 fprintf(stderr, " <SubOptions>\n");
200 fprintf(stderr, " -s [file.wav] [file.wav] [file.wav] ...\n");
201 fprintf(stderr, " # input WAV file names\n");
202 fprintf(stderr, " -o # put offset data in THP\n");
203 fprintf(stderr, " -r [f32 number] # set FrameRate (default is 29.97)\n");
204 fprintf(stderr, "\n");
205 fprintf(stderr, " (THP Video Type)\n");
206 fprintf(stderr, " -non # default Video Type NON Interlace\n");
207 fprintf(stderr, " -odd # set Video Type ODD Interlace\n");
208 fprintf(stderr, " -even # set Video Type EVEN Interlace\n");
209 fprintf(stderr, "\n");
210 fprintf(stderr, " -v # verbose mode\n");
211 fprintf(stderr, " -h # show this usage\n");
212 fprintf(stderr, "\n");
213 fprintf(stderr, " ------------------------------------------------------------------\n");
214 fprintf(stderr, "\n");
215 fprintf(stderr, " <<Change THP sound file Data>>\n");
216 fprintf(stderr, " -c [file.thp] # input THP file name\n");
217 fprintf(stderr, " -s [file.wav] [file.wav] [file.wav] ...\n");
218 fprintf(stderr, " # input WAV file names\n");
219 fprintf(stderr, " -trk [u8 track No.] [file.wav] \n");
220 fprintf(stderr, " # change Track No.[0... ] & input WAV file name\n");
221 fprintf(stderr, "\n");
222 fprintf(stderr, " <SubOptions>\n");
223 fprintf(stderr, " -d [file.thp] # output THP file name\n");
224 fprintf(stderr, " -o # put offset data in THP\n");
225 fprintf(stderr, " -r [f32 number] # set FrameRate (default is 29.97)\n");
226 fprintf(stderr, "\n");
227 fprintf(stderr, " (THP Video Type)\n");
228 fprintf(stderr, " -non # default Video Type NON Interlace \n");
229 fprintf(stderr, " -odd # set Video Type ODD Interlace \n");
230 fprintf(stderr, " -even # set Video Type EVEN Interlace \n");
231 fprintf(stderr, "\n");
232 fprintf(stderr, " -v # verbose mode\n");
233 fprintf(stderr, " -h # show this usage\n");
234 fprintf(stderr, "\n");
235 }
236
237 /*---------------------------------------------------------------------------*
238 Name: verifyWriteOverInputData
239
240 Description: Confirms overwriting of input file
241
242 Arguments: fileName Pointer to the file name
243
244 Returns: TRUE Overwrite permitted
245 FALSE Overwrite denied
246 *---------------------------------------------------------------------------*/
verifyWriteOverInputData(const char * fileName)247 static s32 verifyWriteOverInputData(const char* fileName)
248 {
249 char answer = 0;
250 u8 loop_flag = 1;
251
252 while (loop_flag)
253 {
254 printf("\a>Overwrite the inputfile[%s] by OutputData ? [Y/N] ", fileName);
255 answer = toupper(getchar());
256
257 if (answer == 'Y')
258 {
259 loop_flag = 0;
260 }
261 else if (answer == 'N')
262 {
263 printf("\a\n Please try using [-d] option.\n");
264 return FALSE;
265 }
266 else
267 {
268 // Loop //
269 }
270 }
271
272 return TRUE;
273 }
274
275 /*---------------------------------------------------------------------------*
276 Name: getFileNameList
277
278 Description: Searches for file names matching sWildcardPattern and stores them all in filename.
279 The filename buffer must be allocated in advance.
280
281 Arguments: sWildcardPattern File name including the wildcard
282 filename Buffer storing the file names
283
284 Returns: Number of files
285 *---------------------------------------------------------------------------*/
getFileNameList(const char * sWildcardPattern,THPFileName * filename)286 static u32 getFileNameList(const char *sWildcardPattern, THPFileName* filename)
287 {
288 u32 f_count = 0;
289 WIN32_FIND_DATA wfd;
290 HANDLE hFind;
291 struct stat;
292
293 if ((hFind = FindFirstFile(sWildcardPattern, &wfd)) == INVALID_HANDLE_VALUE)
294 {
295 return f_count;
296 }
297
298 do
299 {
300 if (filename != NULL)
301 {
302 strcpy(filename[f_count].name, wfd.cFileName);
303 strlwr(filename[f_count].name);
304 filename[f_count].fileSize = wfd.nFileSizeLow;
305 }
306 f_count++;
307
308 } while (FindNextFile(hFind, &wfd));
309
310 FindClose(hFind);
311
312 if (filename != NULL)
313 {
314 u32 i;
315 char drive[_MAX_DRIVE];
316 char dir[_MAX_DIR];
317 char pathCopy[_MAX_PATH];
318 char path[_MAX_PATH];
319
320 qsort(filename, f_count, sizeof(THPFileName), compare);
321
322 _splitpath(sWildcardPattern, drive, dir, NULL, NULL);
323 _makepath(path, drive, dir, NULL, NULL);
324
325 for (i = 0; i < f_count; i++)
326 {
327 strcpy(pathCopy, path);
328 strcat(pathCopy, filename[i].name);
329 strcpy(filename[i].name, pathCopy);
330 }
331 }
332
333 return f_count++;
334 }
335
336 /*---------------------------------------------------------------------------*
337 Name: compare
338
339 Description: The comparison function specified in qsort()
340
341 Arguments: arg1, arg2 The elements to be compared
342
343 Returns: negative arg1 is less than arg2
344 0 arg1 = arg2
345 positive arg1 is greater than arg2
346 *---------------------------------------------------------------------------*/
compare(const void * arg1,const void * arg2)347 static int compare(const void *arg1, const void *arg2)
348 {
349 // Compares two strings until their ends
350 return strcmp(((THPFileName *)arg1)->name, ((THPFileName *)arg2)->name);
351 }
352
353 /*---------------------------------------------------------------------------*
354 Name: checkArguments
355
356 Description: Argument checker
357
358 Arguments: argument_count Number of arguments
359 argv Array of argument strings
360
361 Returns: TRUE Ended successfully
362 FALSE Ended in an error
363 (when the argument is '-h', immediately use exit(0))
364 *---------------------------------------------------------------------------*/
365 /*---------------------------------------------------------------------------*
366 [Flags]
367
368 <Required>
369
370 -j option: Create THP files from serial JPEG file (group)
371 Flag specifying serial JPEG files pack_jpegs : 0 -> 1
372 Serial JPEG file's file name jpegFilesPtr : NULL -> XXXX
373 Number of serial JPEG files num_JPGfiles : 0 -> XX
374
375 -c option: Replace audio data in existing THP file
376 Flag specifying the input THP file change_snd_data : 0 -> 1
377 Input THP file's file name inFile : NULL -> XXXX
378
379 *** -j and -c are exclusive ***
380
381 <Recommended>
382
383 -d option
384 Output THP file name outFile : NULL -> XXXX
385
386 *** Required when using -j/optional when using -c ***
387
388 -s option
389 Flag specifying the input WAV file change_alltrack : 0 -> 1
390 Input WAV file's file name waveFilesPtr : NULL -> XXXX
391 Number of input WAV files num_WAVfiles : 0 -> XX
392
393 *** Not required when using -j ***
394
395 -trk option
396 Audio track file exchange flag change_onetrack : 0 -> 1
397 Exchange WAV file name waveFilesPtr : NULL -> XXXX
398 Exchange track number trackNo : 0 -> XX
399
400 *** Invalid when using -j/when using -c, although -s and -trk are exclusive, one of the two must be included ***
401
402 <Other>
403
404 -r option
405 Flag specifying frame rate change_framerate : 0 -> 1
406 Frame rate frame_rate : 29.97f -> XXXXXX
407
408 -o option
409 Flag for creating offset table offset_mode : 0 -> 1
410
411 -non/odd/even option
412 Flag specifying display start field change_videotype : 0 -> 1
413 Specified field videotype : THP_VIDEO_NON_INTERLACE -> XXXXX
414
415 *** Invalid when using -trk ***
416
417 -v option
418 verbose mode flag Convert_Verbose : 0 -> 1
419
420 *---------------------------------------------------------------------------*/
421
checkArguments(u32 argument_count,char * argv[])422 static s32 checkArguments(u32 argument_count, char *argv[])
423 {
424 u32 i;
425
426 if (argument_count < 2)
427 {
428 Usage(argv[0]);
429 exit(0);
430 }
431
432 // Check Options //
433 for (i = 1; i < argument_count; i++)
434 {
435 if (argv[i][0] == '-')
436 {
437 u8* option = argv[i];
438
439 //
440 // -j : Specify input JPEG file(s)
441 //
442 if (strcmp(option, "-j") == 0)
443 {
444 // -j (pack_jpegs = 1) and -c (change_snd_data) are mutually exclusive
445 if (change_snd_data)
446 {
447 printf("\aERROR : Can't use both [-j] and [-c] at the same time.\n");
448 return FALSE;
449 }
450
451 // -j can only be specified once
452 if (pack_jpegs)
453 {
454 printf("\aERROR : [-j] is specified twice.\n");
455 return FALSE;
456 }
457
458 // Check to see if there are subsequent file names
459 i++;
460 if (i >= argument_count)
461 {
462 printf("\aERROR : Must specify input filename after [-j].\n");
463 return FALSE;
464 }
465
466 jpegFilesPtr = &argv[i];
467
468 // Check the number of specified JPEG files
469 while (i < argument_count && argv[i][0] != '-')
470 {
471 num_JPGfiles++;
472 i++;
473 }
474
475 if (num_JPGfiles == 0)
476 {
477 printf("\aERROR : There is no jpeg file after [-j].\n");
478 return FALSE;
479 }
480
481 i--;
482 pack_jpegs = 1;
483 }
484
485 //
486 // -c : Specify input THP file
487 //
488 else if (strcmp(option, "-c") == 0)
489 {
490 // -j (pack_jpegs = 1) and -c (change_snd_data) are mutually exclusive
491 if (pack_jpegs)
492 {
493 printf("\aERROR : Can't use both [-j] and [-c] at the same time.\n");
494 return FALSE;
495 }
496
497 // -c can only be specified once
498 if (change_snd_data)
499 {
500 printf("\aERROR : [-c] is specified twice.\n");
501 return FALSE;
502 }
503
504 // Check to see if there are subsequent file names
505 i++;
506 if (i >= argument_count || argv[i][0] == '-')
507 {
508 printf("\aERROR : Must specify input filename after [-c].\n");
509 return FALSE;
510 }
511
512 // Acquire input THP file name
513 inFile = argv[i];
514 THPUtyConvertToUnixFmt(inFile);
515
516 change_snd_data = 1;
517 }
518
519 //
520 // -d : Specify output THP file name
521 //
522 else if (strcmp(option, "-d") == 0)
523 {
524 // -d can only be specified once
525 if (outFile)
526 {
527 printf("\aERROR : [-d] is specified twice.\n");
528 return FALSE;
529 }
530
531 // Check to see if there are subsequent file names
532 i++;
533 if (i >= argument_count || argv[i][0] == '-')
534 {
535 printf("\aERROR : Must specify output THP filename after [-d].\n");
536 return FALSE;
537 }
538
539 // Get output THP file name
540 outFile = argv[i];
541 THPUtyConvertToUnixFmt(outFile);
542 }
543
544 //
545 // -s : Specify input WAV file(s)
546 //
547 else if (strcmp(option, "-s") == 0)
548 {
549 // -s (change_alltrack = 1) and -trk (change_onetrack) are mutually exclusive
550 if (change_onetrack)
551 {
552 printf("\aERROR : Can't use both [-s] and [-trk] at the same time.\n");
553 return FALSE;
554 }
555
556 // -s can only be specified once
557 if (change_alltrack)
558 {
559 printf("\aERROR : [-s] is specified twice.\n");
560 return FALSE;
561 }
562
563 // Check to see if there are subsequent file names
564 i++;
565 if (i >= argument_count)
566 {
567 printf("\aERROR : Must specify input filename after [-s].\n");
568 return FALSE;
569 }
570
571 waveFilesPtr = &argv[i];
572
573 // Check the number of specified WAV files
574 while ((i < argument_count) && argv[i][0] != '-')
575 {
576 num_WAVfiles++;
577 i++;
578 }
579
580 if (num_WAVfiles == 0)
581 {
582 printf("\aERROR : There is no WAV file after [-s].\n");
583 return FALSE;
584 }
585
586 i--;
587 change_alltrack = 1;
588 }
589
590 //
591 // -trk : Specify track number and input WAV file
592 //
593 else if (strcmp(option, "-trk") == 0)
594 {
595 // -s (change_alltrack = 1) and -trk (change_onetrack) are mutually exclusive
596 if (change_alltrack)
597 {
598 printf("\aERROR : Can't use both [-s] and [-trk] at the same time.\n");
599 return FALSE;
600 }
601
602 // -trk can only be specified once
603 if (change_onetrack)
604 {
605 printf("\aERROR : [-trk] is specified twice.\n");
606 return FALSE;
607 }
608
609 // Check to see if there are subsequent track numbers and file names
610 i++;
611 if (i + 1 >= argument_count)
612 {
613 printf("\aERROR : Must specify trackNo and input filename after [-trk].\n");
614 return FALSE;
615 }
616
617 // Get the track number
618 if (argv[i][0] < '0' || argv[i][0] > '9')
619 {
620 printf("\aERROR : Invalid trackNo.\n");
621 return FALSE;
622 }
623
624 trackNo = atoi(argv[i]);
625
626 // Get the input WAV file name
627 i++;
628 if (i >= argument_count || argv[i][0] == '-')
629 {
630 printf("\aERROR : Must specify trackNo and input filename after [-trk].\n");
631 return FALSE;
632 }
633 waveFilesPtr = &argv[i];
634 THPUtyConvertToUnixFmt(waveFilesPtr[0]);
635
636 change_onetrack = 1;
637 }
638
639 //
640 // -r : Specify frame rate
641 //
642 else if (strcmp(option, "-r") == 0)
643 {
644 // Check to see if there are subsequent specified frame rates
645 i++;
646 if (i >= argument_count)
647 {
648 printf("\aERROR : Must specify output framerate after [-r].\n");
649 return FALSE;
650 }
651
652 // Get the frame rate
653 frame_rate = (f32)atof(argv[i]);
654 if (frame_rate > 59.94 || frame_rate < 1.0)
655 {
656 printf("\aERROR : Framarate should be between 1.0 to 59.94.\n");
657 return FALSE;
658 }
659
660 change_framerate = 1;
661 }
662
663 //
664 // -o : Specify making an offset table
665 //
666 else if (strcmp(option, "-o") == 0)
667 {
668 offset_mode = 1;
669 }
670
671 //
672 // -non : Specify video type non-interlace
673 //
674 else if (strcmp(option, "-non") == 0)
675 {
676 if (change_videotype)
677 {
678 printf("\aERROR : Already used -non/odd/even.\n");
679 return FALSE;
680 }
681
682 videotype = THP_VIDEO_NON_INTERLACE;
683 change_videotype = 1;
684 }
685
686 //
687 // -odd : Specify video type interlace beginning from odd field
688 //
689 else if (strcmp(option, "-odd") == 0)
690 {
691 if (change_videotype)
692 {
693 printf("\aERROR : Already used -non/odd/even.\n");
694 return FALSE;
695 }
696
697 videotype = THP_VIDEO_ODD_INTERLACE;
698 change_videotype = 1;
699 }
700
701 //
702 // -even : Specify video type interlace beginning from even field
703 //
704 else if (strcmp(option, "-even") == 0)
705 {
706 if (change_videotype)
707 {
708 printf("\aERROR : Already used -non/odd/even.\n");
709 return FALSE;
710 }
711
712 videotype = THP_VIDEO_EVEN_INTERLACE;
713 change_videotype = 1;
714 }
715
716 //
717 // -v : Specify setting verbose mode
718 //
719 else if (strcmp(option, "-v") == 0)
720 {
721 Convert_Verbose = 1;
722 }
723
724 //
725 // -on : old option
726 //
727 else if (strcmp(option, "-on") == 0)
728 {
729 ;
730 }
731
732 //
733 // -h : Specify displaying usage
734 //
735 else if (strcmp(option, "-h") == 0)
736 {
737 Usage(argv[0]);
738 exit(0);
739 }
740
741 //
742 // etc.
743 //
744 else
745 {
746 printf("\aERROR : Unknown option <%s>.\n", option);
747 return FALSE;
748 }
749
750 } // if (argv[i][0] == '-')
751
752 // Invalid argument
753 else
754 {
755 printf("\aERROR : Invalid arguments!\n");
756 return FALSE;
757
758 } // if (argv[i][0] == '-')
759
760 } // for (i = 1; i < argument_count; i++)
761
762
763 // Check if either conversion (-j : pack_jpegs = 1) or audio replacement (-c : change_snd_data = 1) has been specified.
764 //
765 if (!pack_jpegs && !change_snd_data)
766 {
767 printf("\aERROR : Must input either [-j] or [-c].\n");
768 return FALSE;
769 }
770
771 // When converting from JPEG to THP (-j : pack_jpegs = 1), check that the output THP files have been specified (-d : outFile != NULL).
772 //
773 if (pack_jpegs)
774 {
775 if (outFile == NULL)
776 {
777 printf("\aERROR : Must specify output THP filename [-d] [file.thp].\n");
778 return FALSE;
779 }
780 }
781
782 // When replacing THP audio data (-c: change_snd_data = 1), check if an input WAV file has been specified (-s: change_alltrack = 1 or -trk: change_one_track = 1).
783 //
784 if (change_snd_data)
785 {
786 if (!change_alltrack && !change_onetrack)
787 {
788 printf("\aERROR : Must input [-s] [file.wav] or [-trk] [track No.] [file.wav].\n");
789 return FALSE;
790 }
791 }
792
793 return TRUE;
794 }
795
796 /*---------------------------------------------------------------------------*
797 Name: convertJPEGtoTHP
798
799 Description: Converts serial JPEG files to THP data
800
801 Arguments: None
802
803 Returns: TRUE Ended successfully
804 FALSE Ended in an error
805 *---------------------------------------------------------------------------*/
convertJPEGtoTHP(void)806 static s32 convertJPEGtoTHP(void)
807 {
808 s32 rtn;
809 s32 error = TRUE;
810 u32 cnt;
811 FILE* thpFp = NULL;
812 THPFileName* jpegFileList = NULL;
813 THPAudioHandle** audioHandle = NULL;
814 THPFileHeader fileHeader;
815
816 //
817 // Create a JPEG file list
818 //
819 if (num_JPGfiles == 1)
820 {
821 // When a single JPEG file or wildcard is specified
822
823 THPUtyConvertToUnixFmt(jpegFilesPtr[0]);
824
825 // Confirm the number of JPEG files
826 num_JPGfiles = getFileNameList(jpegFilesPtr[0], NULL);
827 if (num_JPGfiles == 0)
828 {
829 printf("\aERROR : There is no jpeg files. Input right argument.\n");
830 error = FALSE;
831 goto ERROR_END;
832 }
833
834 jpegFileList = (THPFileName*)malloc(sizeof(THPFileName) * num_JPGfiles);
835 if (jpegFileList == NULL)
836 {
837 printf("\aERROR : Can't alloc memory.\n");
838 error = FALSE;
839 goto ERROR_END;
840 }
841
842 // Save the JPEG file name
843 getFileNameList(jpegFilesPtr[0], jpegFileList);
844 }
845
846 else
847 {
848 // When multiple JPEG files are specified
849
850 jpegFileList = (THPFileName*)malloc(sizeof(THPFileName) * num_JPGfiles);
851 if (jpegFileList == NULL)
852 {
853 printf("\aERROR : Can't alloc memory.\n");
854 error = FALSE;
855 goto ERROR_END;
856 }
857
858 for (cnt = 0; cnt < num_JPGfiles; cnt++)
859 {
860 struct stat statBuf;
861 char ext[_MAX_EXT];
862
863 // Save the JPEG file name
864 strcpy(jpegFileList[cnt].name, jpegFilesPtr[cnt]);
865 THPUtyConvertToUnixFmt(jpegFileList[cnt].name);
866
867 // Confirm the extension
868 _splitpath(jpegFileList[cnt].name, NULL, NULL, NULL, ext);
869 if ((stricmp(ext, ".jpg") != 0) && (stricmp(ext, ".jpeg") != 0))
870 {
871 printf("\aERROR : Please input filename is [***.jpg] or [***.jpeg].\n");
872 error = FALSE;
873 goto ERROR_END;
874 }
875
876 // Get the JPEG file size
877 rtn = stat(jpegFileList[cnt].name, &statBuf);
878 if (rtn != 0)
879 {
880 printf("\aERROR : Can't get JPEG file status!\n");
881 error = FALSE;
882 goto ERROR_END;
883 }
884
885 jpegFileList[cnt].fileSize = statBuf.st_size;
886 }
887 }
888
889 if (Convert_Verbose)
890 {
891 printf("Total Frames = %ld\n", num_JPGfiles);
892 printf("Frame Rate = %f\n", frame_rate);
893 }
894
895 // Set THPHeader
896 THPUtyHeaderInit(&fileHeader.header);
897 fileHeader.header.frameRate = frame_rate;
898 fileHeader.header.numFrames = num_JPGfiles;
899 fileHeader.header.compInfoDataOffsets = sizeof(THPHeader);
900 fileHeader.header.offsetDataOffsets = offset_mode;
901
902 // Set THPFrameCompInfo
903 fileHeader.frameCompInfo.frameComp[0] = THP_VIDEO_COMP;
904 fileHeader.frameCompInfo.numComponents = 1;
905 for (cnt = 1; cnt < THP_COMP_MAX; cnt++)
906 {
907 fileHeader.frameCompInfo.frameComp[cnt] = THP_NOCOMP_COMP;
908 }
909
910 // Set THPVideoInfo
911 fileHeader.videoInfo.videoType = videotype;
912
913 // Audio data encoding settings
914 if (change_alltrack)
915 {
916 if (Convert_Verbose)
917 {
918 printf("START: Audio Initializing.\n");
919 }
920
921 if (THPAudioInit() == FALSE)
922 {
923 printf("\aERROR : Fail to execute THPAudioInit().\n");
924 error = FALSE;
925 goto ERROR_END;
926 }
927
928 audioHandle = (THPAudioHandle**)malloc(sizeof(THPAudioHandle*) * num_WAVfiles);
929 if (audioHandle == NULL)
930 {
931 printf("\aERROR : Can't alloc memory.\n");
932 error = FALSE;
933 goto ERROR_END;
934 }
935
936 // Create the WAV file list
937 for (cnt = 0; cnt < num_WAVfiles; cnt++)
938 {
939 THPUtyConvertToUnixFmt(waveFilesPtr[cnt]);
940
941 audioHandle[cnt] = THPAudioCreateHandle(waveFilesPtr[cnt], frame_rate);
942 if (audioHandle[cnt] == NULL)
943 {
944 printf("\aERROR : Fail to execute THPAudioCreateHandle().\n");
945 error = FALSE;
946 goto ERROR_END;
947 }
948 }
949
950 // Main Sound
951 rtn = THPAudioGetInfo(audioHandle[0], &fileHeader.audioInfo);
952 if (rtn == FALSE)
953 {
954 printf("\aERROR : Fail to execute THPAudioGetInfo().\n");
955 error = FALSE;
956 goto ERROR_END;
957 }
958
959 if (Convert_Verbose)
960 {
961 printf(" [AudioData]:(%2ld Tracks)\n", num_WAVfiles);
962 printf(" >> Channels = %ld\n", fileHeader.audioInfo.sndChannels);
963 printf(" >> Frequency = %ld\n", fileHeader.audioInfo.sndFrequency);
964 printf(" <+> Track%02d <= [%s]\n", 0, waveFilesPtr[0]);
965 }
966
967 // Sub Sound
968 for (cnt = 1; cnt < num_WAVfiles; cnt++)
969 {
970 THPAudioInfo subAudioInfo;
971
972 rtn = THPAudioGetInfo(audioHandle[cnt], &subAudioInfo);
973 if (rtn == FALSE)
974 {
975 printf("\aERROR : Fail to execute THPAudioGetInfo().\n");
976 error = FALSE;
977 goto ERROR_END;
978 }
979
980 // Check the number of channels in a WAV file
981 if (audioHandle[0]->audioInfo.channel != subAudioInfo.sndChannels)
982 {
983 printf("\aERROR : Channels of [%s] is %d (!= %d).\n",
984 waveFilesPtr[cnt],
985 subAudioInfo.sndChannels,
986 audioHandle[0]->audioInfo.channel);
987 error = FALSE;
988 goto ERROR_END;
989 }
990
991 // Check the playback frequency in a WAV file
992 if (audioHandle[0]->audioInfo.frequency != subAudioInfo.sndFrequency)
993 {
994 printf("\aERROR : Frequency of [%s] is %d (!= %d).\n",
995 waveFilesPtr[cnt],
996 subAudioInfo.sndFrequency,
997 audioHandle[0]->audioInfo.frequency);
998 error = FALSE;
999 goto ERROR_END;
1000 }
1001
1002 if (Convert_Verbose)
1003 {
1004 printf(" <+> Track%02d <= [%s]\n", cnt, waveFilesPtr[cnt]);
1005 }
1006 }
1007
1008 if (Convert_Verbose)
1009 {
1010 printf("END : Audio Initializing.\n");
1011 }
1012
1013 // Update THPHeader
1014 fileHeader.header.audioMaxSamples
1015 = THPAudioGetMaxFrameSamples(audioHandle[0], num_JPGfiles);
1016
1017 // Update THPAudioInfo
1018 fileHeader.audioInfo.sndNumTracks = num_WAVfiles;
1019 fileHeader.audioInfo.sndNumSamples = THPAudioGetTotalSamples(audioHandle[0],
1020 num_JPGfiles);
1021
1022 // Update THPFrameCompInfo
1023 fileHeader.frameCompInfo.frameComp[1] = THP_AUDIO_COMP;
1024 fileHeader.frameCompInfo.numComponents++;
1025 }
1026
1027 // Open Output File
1028 thpFp = fopen(outFile, "wb");
1029 if (thpFp == NULL)
1030 {
1031 THPPrintError("\aERROR : Can't output [%s].\n", outFile);
1032 THPPrintError(" Please input valid directory & file name.\n");
1033 error = FALSE;
1034 goto ERROR_END;
1035 }
1036
1037 // Convert serial JPEGs to THP
1038 rtn = THPUtyCreateTHP(thpFp, THP_CREATETHP_FILEFLAG_JPEGS,
1039 (void*)jpegFileList,
1040 &fileHeader,
1041 audioHandle);
1042 if (rtn != THP_ERROR_NOERROR)
1043 {
1044 printf("\aERROR : Fail to execute THPUtyCreateTHP().\n");
1045 error = FALSE;
1046 goto ERROR_END;
1047 }
1048
1049 ERROR_END:
1050
1051 if (audioHandle)
1052 {
1053 THPAudioQuit();
1054 for (cnt = 0; cnt < num_WAVfiles; cnt++)
1055 {
1056 if (audioHandle[cnt] != NULL)
1057 {
1058 THPAudioFreeHandle(audioHandle[cnt]);
1059 }
1060 }
1061 free(audioHandle);
1062 }
1063
1064 if (jpegFileList != NULL)
1065 {
1066 free(jpegFileList);
1067 }
1068
1069 if (thpFp != NULL)
1070 {
1071 fclose(thpFp);
1072 }
1073
1074 return error;
1075 }
1076
1077 /*---------------------------------------------------------------------------*
1078 Name: changeAudioTrack
1079
1080 Description: Replaces the existing audio tracks within THP file
1081
1082 Arguments: fileHeader Pointer to the THP file header
1083
1084 Returns: TRUE Ended successfully
1085 FALSE Ended in an error
1086 *---------------------------------------------------------------------------*/
changeAudioTrack(THPFileHeader * fileHeader)1087 static s32 changeAudioTrack(THPFileHeader* fileHeader)
1088 {
1089 s32 rtn;
1090 s32 error = TRUE;
1091 u32 cnt;
1092 //u32 adjustFrequency;
1093 char tmpFilename[_MAX_PATH];
1094 char* fileName = NULL;
1095 FILE* outTHPFp = NULL;
1096 FILE* inTHPFp = NULL;
1097 THPAudioHandle** audioHandle = NULL;
1098 THPAudioInfo audioInfo;
1099
1100 // Check whether the THP file has an audio track
1101 for (cnt = 0; cnt < fileHeader->frameCompInfo.numComponents; cnt++)
1102 {
1103 if (fileHeader->frameCompInfo.frameComp[cnt] == THP_AUDIO_COMP)
1104 {
1105 break;
1106 }
1107 }
1108
1109 if (cnt >= fileHeader->frameCompInfo.numComponents)
1110 {
1111 printf("\aERROR : [%s] doesn't have a Sound Data!\n", inFile);
1112 error = FALSE;
1113 goto ERROR_END;
1114 }
1115
1116 // Check the THP file's number of channels and playback frequency
1117 if (fileHeader->audioInfo.sndChannels == 0 || fileHeader->audioInfo.sndFrequency == 0)
1118 {
1119 printf("\aERROR : [%s] doesn't have a Sound Data!\n", inFile);
1120 error = FALSE;
1121 goto ERROR_END;
1122 }
1123
1124 // Check the number of THP file tracks
1125 if (trackNo >= fileHeader->audioInfo.sndNumTracks)
1126 {
1127 printf("\aERROR : Must input [u8 track No.] < %d.\n",
1128 fileHeader->audioInfo.sndNumTracks);
1129 error = FALSE;
1130 goto ERROR_END;
1131 }
1132
1133 if (Convert_Verbose)
1134 {
1135 printf("START: Audio Initializing.\n");
1136 }
1137
1138 // Set THPAudioHandle
1139 audioHandle = (THPAudioHandle**)malloc(sizeof(THPAudioHandle*)
1140 * fileHeader->audioInfo.sndNumTracks);
1141 if (audioHandle == NULL)
1142 {
1143 printf("\aERROR : Can't alloc memory.\n");
1144 error = FALSE;
1145 goto ERROR_END;
1146 }
1147
1148 for (cnt = 0; cnt < fileHeader->audioInfo.sndNumTracks; cnt++)
1149 {
1150 audioHandle[cnt] = NULL;
1151 }
1152
1153 THPUtyConvertToUnixFmt(waveFilesPtr[0]);
1154
1155 audioHandle[trackNo] = THPAudioCreateHandle(waveFilesPtr[0],
1156 fileHeader->header.frameRate);
1157 if (audioHandle[trackNo] == NULL)
1158 {
1159 printf("\aERROR : Fail to execute THPAudioCreateHandle().\n");
1160 error = FALSE;
1161 goto ERROR_END;
1162 }
1163
1164 // Get additional audio data information
1165 rtn = THPAudioGetInfo(audioHandle[trackNo], &audioInfo);
1166 if (rtn == FALSE)
1167 {
1168 printf("\aERROR : Fail to execute THPAudioGetInfo().\n");
1169 error = FALSE;
1170 goto ERROR_END;
1171 }
1172
1173 // Check the number of channels
1174 if (fileHeader->audioInfo.sndChannels != audioInfo.sndChannels )
1175 {
1176 printf("\aERROR : Channels of [%s] is %d (!= %d).\n",
1177 waveFilesPtr[0],
1178 audioInfo.sndChannels,
1179 fileHeader->audioInfo.sndChannels);
1180 error = FALSE;
1181 goto ERROR_END;
1182 }
1183
1184 // Check the playback frequency
1185 if (fileHeader->audioInfo.sndFrequency != audioInfo.sndFrequency)
1186 {
1187 printf("\aERROR : Frequency of [%s] is %d (!= %d).\n",
1188 waveFilesPtr[0],
1189 audioInfo.sndFrequency,
1190 fileHeader->audioInfo.sndFrequency);
1191 error = FALSE;
1192 goto ERROR_END;
1193 }
1194
1195 if (Convert_Verbose)
1196 {
1197 printf(" [AudioData]:(%2ld Tracks)\n", fileHeader->audioInfo.sndNumTracks);
1198 printf(" >> Channels = %ld\n", fileHeader->audioInfo.sndChannels);
1199 printf(" >> Frequency = %ld\n", fileHeader->audioInfo.sndFrequency);
1200 printf(" <+> Track%02d <= [%s]\n", trackNo, waveFilesPtr[0]);
1201
1202 printf("END : Audio Initializing.\n");
1203 }
1204
1205 // Open the input THP file
1206 inTHPFp = fopen(inFile, "rb");
1207 if (inTHPFp == NULL)
1208 {
1209 printf("\aERROR : Can't open [%s].\n", inFile);
1210 error = FALSE;
1211 goto ERROR_END;
1212 }
1213
1214 // Open the output THP file
1215 if (outFile != NULL)
1216 {
1217 fileName = outFile;
1218 }
1219 else
1220 {
1221 char drive[_MAX_DRIVE];
1222 char dir[_MAX_DIR];
1223 _splitpath(inFile, drive, dir, NULL, NULL);
1224 _makepath(tmpFilename, drive, dir, TMP_FILENAME, NULL);
1225 fileName = tmpFilename;
1226 }
1227
1228 outTHPFp = fopen(fileName, "w+b");
1229 if (outTHPFp == NULL)
1230 {
1231 printf("\aERROR : Can't open [%s].\n", fileName);
1232 error = FALSE;
1233 goto ERROR_END;
1234 }
1235
1236 // Copy the input THP file to the output THP file
1237 rtn = THPUtyCopyTHPFile(inTHPFp, fileHeader, outTHPFp);
1238 if (rtn != THP_ERROR_NOERROR)
1239 {
1240 printf("\aERROR : Fail to execute THPUtyCopyTHPFile().\n");
1241 error = FALSE;
1242 goto ERROR_END;
1243 }
1244
1245 rtn = fseek(outTHPFp, 0, SEEK_SET);
1246 if (rtn != 0)
1247 {
1248 THPPrintError("\aERROR : Can't rewind output THP file.\n");
1249 error = FALSE;
1250 goto ERROR_END;
1251 }
1252
1253 // Exchange the audio track
1254 rtn = THPUtyChangeAudioTrack(outTHPFp, fileHeader, audioHandle);
1255 if (rtn != THP_ERROR_NOERROR)
1256 {
1257 printf("\aERROR : Fail to execute THPUtyChangeAudioTrack().\n");
1258 error = FALSE;
1259 goto ERROR_END;
1260 }
1261
1262 ERROR_END:
1263
1264 if (audioHandle)
1265 {
1266 for (cnt = 0; cnt < fileHeader->audioInfo.sndNumTracks; cnt++)
1267 {
1268 if (audioHandle[cnt] != NULL)
1269 {
1270 THPAudioFreeHandle(audioHandle[cnt]);
1271 }
1272 }
1273 free(audioHandle);
1274 }
1275
1276 if (inTHPFp != NULL)
1277 {
1278 fclose(inTHPFp);
1279 }
1280
1281 if (outTHPFp != NULL)
1282 {
1283 fclose(outTHPFp);
1284 }
1285
1286 // Rename the temporary file during an overwrite
1287 if (outFile == NULL)
1288 {
1289 if (error == TRUE)
1290 {
1291 if (remove(inFile) == -1)
1292 {
1293 printf("\aERROR : Can't remove old THP file[%s].\n", inFile);
1294 }
1295
1296 if (rename(fileName, inFile))
1297 {
1298 printf("\aERROR : Can't rename THP file[%s -> %s].\n", fileName, inFile);
1299 }
1300 }
1301 else
1302 {
1303 if (fileName)
1304 {
1305 if (remove(fileName) == -1)
1306 {
1307 printf("\aERROR : Can't remove temporary THP file[%s].\n", fileName);
1308 }
1309 }
1310 }
1311 }
1312
1313 return error;
1314 }
1315
1316 /*---------------------------------------------------------------------------*
1317 Name: appendAudioData
1318
1319 Description: Adds audio data when none exists.
1320 If it does exist, replace it.
1321 (with the -s option)
1322
1323 Arguments: fileHeader Pointer to the file header
1324
1325 Returns: TRUE Ended successfully
1326 FALSE Ended in an error
1327 *---------------------------------------------------------------------------*/
appendAudioData(THPFileHeader * fileHeader)1328 static s32 appendAudioData(THPFileHeader* fileHeader)
1329 {
1330 s32 rtn;
1331 s32 error = TRUE;
1332 u32 cnt;
1333 char tmpFilename[_MAX_PATH];
1334 char* fileName = NULL;
1335 FILE* outTHPFp = NULL;
1336 FILE* inTHPFp = NULL;
1337 THPAudioHandle** audioHandle = NULL;
1338
1339 // Open the input THP file
1340 inTHPFp = fopen(inFile, "rb");
1341 if (inTHPFp == NULL)
1342 {
1343 printf("\aERROR : Can't open [%s].\n", inFile);
1344 error = FALSE;
1345 goto ERROR_END;
1346 }
1347
1348 // Open the output THP file
1349 if (outFile != NULL)
1350 {
1351 fileName = outFile;
1352 }
1353 else
1354 {
1355 char drive[_MAX_DRIVE];
1356 char dir[_MAX_DIR];
1357 _splitpath(inFile, drive, dir, NULL, NULL);
1358 _makepath(tmpFilename, drive, dir, TMP_FILENAME, NULL);
1359 fileName = tmpFilename;
1360 }
1361
1362 outTHPFp = fopen(fileName, "wb");
1363 if (outTHPFp == NULL)
1364 {
1365 printf("\aERROR : Can't open [%s].\n", fileName);
1366 error = FALSE;
1367 goto ERROR_END;
1368 }
1369
1370 if (Convert_Verbose)
1371 {
1372 printf("START: Audio Initializing.\n");
1373 }
1374
1375 // Update THPAudioInfo (number of tracks: sndNumTracks)
1376 fileHeader->audioInfo.sndNumTracks = num_WAVfiles;
1377
1378 audioHandle = (THPAudioHandle**)malloc(sizeof(THPAudioHandle*) * num_WAVfiles);
1379 if (audioHandle == NULL)
1380 {
1381 printf("\aERROR : Can't alloc memory.\n");
1382 error = FALSE;
1383 goto ERROR_END;
1384 }
1385
1386 // Create the WAV file list
1387 for (cnt = 0; cnt < num_WAVfiles; cnt++)
1388 {
1389 THPUtyConvertToUnixFmt(waveFilesPtr[cnt]);
1390
1391 audioHandle[cnt] = THPAudioCreateHandle(waveFilesPtr[cnt],
1392 fileHeader->header.frameRate);
1393 if (audioHandle[cnt] == NULL)
1394 {
1395 printf("\aERROR : Fail to execute THPAudioCreateHandle().\n");
1396 error = FALSE;
1397 goto ERROR_END;
1398 }
1399 }
1400
1401 // Main Sound
1402 rtn = THPAudioGetInfo(audioHandle[0], &fileHeader->audioInfo);
1403 if (rtn == FALSE)
1404 {
1405 printf("\aERROR : Fail to execute THPAudioGetInfo().\n");
1406 error = FALSE;
1407 goto ERROR_END;
1408 }
1409
1410 if (Convert_Verbose)
1411 {
1412 printf(" [AudioData]:(%2ld Tracks)\n", num_WAVfiles);
1413 printf(" >> Channels = %ld\n", fileHeader->audioInfo.sndChannels);
1414 printf(" >> Frequency = %ld\n", fileHeader->audioInfo.sndFrequency);
1415 printf(" <+> Track%02d <= [%s]\n", 0, waveFilesPtr[0]);
1416 }
1417
1418 // Sub Sound
1419 for (cnt = 1; cnt < num_WAVfiles; cnt++)
1420 {
1421 THPAudioInfo subAudioInfo;
1422
1423 rtn = THPAudioGetInfo(audioHandle[cnt], &subAudioInfo);
1424 if (rtn == FALSE)
1425 {
1426 printf("\aERROR : Fail to execute THPAudioGetInfo().\n");
1427 error = FALSE;
1428 goto ERROR_END;
1429 }
1430
1431 // Check the number of channels in a WAV file
1432 if (audioHandle[0]->audioInfo.channel != subAudioInfo.sndChannels)
1433 {
1434 printf("\aERROR : Channels of [%s] is %d (!= %d).\n",
1435 waveFilesPtr[cnt],
1436 subAudioInfo.sndChannels,
1437 audioHandle[0]->audioInfo.channel);
1438 error = FALSE;
1439 goto ERROR_END;
1440 }
1441
1442 // Check the playback frequency in a WAV file
1443 if (audioHandle[0]->audioInfo.frequency != subAudioInfo.sndFrequency)
1444 {
1445 printf("\aERROR : Frequency of [%s] is %d (!= %d).\n",
1446 waveFilesPtr[cnt],
1447 subAudioInfo.sndFrequency,
1448 audioHandle[0]->audioInfo.frequency);
1449 error = FALSE;
1450 goto ERROR_END;
1451 }
1452
1453 if (Convert_Verbose)
1454 {
1455 printf(" <+> Track%02d <= [%s]\n", cnt, waveFilesPtr[cnt]);
1456 }
1457 }
1458
1459 if (Convert_Verbose)
1460 {
1461 printf("END : Audio Initializing.\n");
1462 }
1463
1464 // Update THPHeader
1465 fileHeader->header.audioMaxSamples
1466 = THPAudioGetMaxFrameSamples(audioHandle[0], fileHeader->header.numFrames);
1467
1468 // Update THPAudioInfo
1469 fileHeader->audioInfo.sndNumTracks = num_WAVfiles;
1470 fileHeader->audioInfo.sndNumSamples
1471 = THPAudioGetTotalSamples(audioHandle[0], fileHeader->header.numFrames);
1472
1473 // Update THPFrameCompInfo
1474 if (fileHeader->frameCompInfo.frameComp[1] == THP_NOCOMP_COMP)
1475 {
1476 fileHeader->frameCompInfo.numComponents++;
1477 fileHeader->frameCompInfo.frameComp[1] = THP_AUDIO_COMP;
1478 }
1479
1480 // Add/exchange audio data in THP data
1481 rtn = THPUtyCreateTHP(outTHPFp, THP_CREATETHP_FILEFLAG_THP,
1482 (void*)inTHPFp,
1483 fileHeader,
1484 audioHandle);
1485 if (rtn != THP_ERROR_NOERROR)
1486 {
1487 printf("\aERROR : Fail to execute THPUtyCreateTHP().\n");
1488 error = FALSE;
1489 goto ERROR_END;
1490 }
1491
1492 ERROR_END:
1493
1494 if (audioHandle)
1495 {
1496 for (cnt = 0; cnt < num_WAVfiles; cnt++)
1497 {
1498 if (audioHandle[cnt] != NULL)
1499 {
1500 THPAudioFreeHandle(audioHandle[cnt]);
1501 }
1502 }
1503 free(audioHandle);
1504 }
1505
1506 if (inTHPFp != NULL)
1507 {
1508 fclose(inTHPFp);
1509 }
1510
1511 if (outTHPFp != NULL)
1512 {
1513 fclose(outTHPFp);
1514 }
1515
1516 // Rename the temporary file during an overwrite
1517 if (outFile == NULL)
1518 {
1519 if (error == TRUE)
1520 {
1521 if (remove(inFile) == -1)
1522 {
1523 printf("\aERROR : Can't remove old THP file[%s].\n", inFile);
1524 }
1525
1526 if (rename(fileName, inFile))
1527 {
1528 printf("\aERROR : Can't rename THP file[%s -> %s].\n", fileName, inFile);
1529 }
1530 }
1531 else
1532 {
1533 if (fileName)
1534 {
1535 if (remove(fileName) == -1)
1536 {
1537 printf("\aERROR : Can't remove temporary THP file[%s].\n", fileName);
1538 }
1539 }
1540 }
1541 }
1542
1543 return error;
1544 }
1545
1546 /*---------------------------------------------------------------------------*
1547 Name: changeAudioData
1548
1549 Description: Adds or replaces audio data
1550
1551 Arguments: None
1552
1553 Returns: TRUE Ended successfully
1554 FALSE Ended in an error
1555 *---------------------------------------------------------------------------*/
changeAudioData(void)1556 static s32 changeAudioData(void)
1557 {
1558 THPFileHeader fileHeader;
1559 FILE* inTHPFp = NULL;
1560 s32 rtn;
1561 s32 error = TRUE;
1562
1563 if (THPAudioInit() == FALSE)
1564 {
1565 printf("\aERROR : Fail to execute THPAudioInit().\n");
1566 error = FALSE;
1567 goto ERROR_END;
1568 }
1569
1570 // Open the input THP file
1571 inTHPFp = fopen(inFile, "rb");
1572 if (inTHPFp == NULL)
1573 {
1574 printf("\aERROR : Can't open [%s].\n", inFile);
1575 error = FALSE;
1576 goto ERROR_END;
1577 }
1578
1579 // Read the input THP file's THPFileHeader
1580 rtn = THPUtyReadTHPFileHeader(inTHPFp, &fileHeader);
1581 if (rtn != THP_ERROR_NOERROR)
1582 {
1583 printf("\aERROR : Can't read THPHeader of [%s].\n", inFile);
1584 fclose(inTHPFp);
1585 error = FALSE;
1586 goto ERROR_END;
1587 }
1588
1589 fclose(inTHPFp);
1590
1591 // Add or replace audio data
1592 if (change_onetrack)
1593 {
1594 // When replacing audio data for a specific track (-trk)
1595
1596 if (Convert_Verbose)
1597 {
1598 printf("Replace audio data of one track.\n");
1599 }
1600
1601 // -o/-r/-non/-odd/-even are ignored
1602
1603 error = changeAudioTrack(&fileHeader);
1604
1605 }
1606 else
1607 {
1608 // When replacing audio data for all tracks (-s)
1609
1610 if (Convert_Verbose)
1611 {
1612 printf("Append/Replace audio data of all tracks.\n");
1613 }
1614
1615 // Frame rate update (-r)
1616 if (change_framerate)
1617 {
1618 fileHeader.header.frameRate = frame_rate;
1619 }
1620
1621 // Update existence of offset table (-o)
1622 if (offset_mode)
1623 {
1624 fileHeader.header.offsetDataOffsets = offset_mode;
1625 }
1626
1627 // Update the specification of the display start field (-non/odd/even)
1628 if (change_videotype)
1629 {
1630 fileHeader.videoInfo.videoType = videotype;
1631 }
1632
1633 error = appendAudioData(&fileHeader);
1634 }
1635
1636 ERROR_END:
1637
1638 THPAudioQuit();
1639
1640 return error;
1641 }
1642
1643 /*---------------------------------------------------------------------------*
1644 Name: logPrintFunc
1645
1646 Description: Outputs messages, logs and errors
1647
1648 Arguments: ...
1649
1650 Returns: None
1651 *---------------------------------------------------------------------------*/
logPrintFunc(const char * format,va_list argptr)1652 static void logPrintFunc(const char* format, va_list argptr)
1653 {
1654 vfprintf(stdout, format, argptr);
1655 }
1656
1657 /*---------------------------------------------------------------------------*
1658 Name: Main
1659
1660 Description: THPConv main
1661
1662 Arguments: (references Usage())
1663
1664 Returns: 0 Ended normally
1665 1 Ends in an error
1666 *---------------------------------------------------------------------------*/
main(int argc,char * argv[])1667 int main(int argc, char *argv[])
1668 {
1669 s32 error = 0;
1670
1671 // Hook the function for output of messages by the THP Library
1672 THPPrintFunc = logPrintFunc;
1673 THPPrintLogFunc = logPrintFunc;
1674 THPPrintErrorFunc = logPrintFunc;
1675
1676 // Argument checker
1677 error = checkArguments(argc, argv);
1678
1679 // Set the verbose mode flag for the THP Library
1680 THPVerboseFlag = Convert_Verbose;
1681
1682 if (Convert_Verbose)
1683 {
1684 printf("Dolphin Jpegs to THP converter. Copyright 2002-2003 Nintendo.\n");
1685 printf("Built : %s %s\n\n", __DATE__, __TIME__);
1686 }
1687
1688 if ((error == FALSE) || (argc == 1))
1689 {
1690 exit(1);
1691 }
1692
1693 printf("THP file Version is %X.%X\n", THP_VERSION >> 16, THP_VERSION & 0xFFFF);
1694
1695 // Create THP
1696 if (pack_jpegs)
1697 {
1698 // Convert from JPEG to THP (-j)
1699
1700 if (Convert_Verbose)
1701 {
1702 printf("Convert from JPEGs to THP...\n");
1703 }
1704
1705 error = convertJPEGtoTHP();
1706 }
1707
1708 else if (change_snd_data)
1709 {
1710 // Add/replace audio data in existing THP (-c)
1711
1712 if (Convert_Verbose)
1713 {
1714 printf("Append/Replace audio data...\n");
1715 }
1716
1717 // Overwrite confirmation
1718 if (outFile == NULL)
1719 {
1720 if (verifyWriteOverInputData(inFile) == FALSE)
1721 {
1722 exit(0);
1723 }
1724 }
1725
1726 error = changeAudioData();
1727 }
1728
1729 if (error == FALSE)
1730 {
1731 printf("WARNING : Errors occurred while converting to THP.\n");
1732 printf(" Please check for error messages above!\n");
1733
1734 exit(1);
1735 }
1736 else
1737 {
1738 if (outFile)
1739 {
1740 printf("Successfully generated [%s].\n", outFile);
1741 }
1742 else
1743 {
1744 printf("Successfully overwrote [%s].\n", inFile);
1745 }
1746 }
1747
1748 exit(0);
1749 }
1750