4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Haejeong Kim <backto.kim@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
22 #include <string.h> /*memcmp*/
23 #include <stdlib.h> /*malloc*/
24 #include "mm_file_debug.h"
25 #include "mm_file_utils.h"
27 /* Description of return value
32 /***********************************************************************/
33 /* Internal functions */
34 /***********************************************************************/
35 static int _MMFileSearchID3Tag(MMFileIOHandle *fp, unsigned int *offset);
36 static int _MMFileIsMP3Header(void *header);
37 static int _MMFileIsOGGHeader(void *header);
38 static int _MMFileIsREALHeader(void *header);
39 static int _MMFileIsMP4Header(void *header);
40 static int _MMFileIsWAVHeader(void *header);
41 static int _MMFileIsAVIHeader(void *header);
42 static int _MMFileIsMIDHeader(void *header);
43 static int _MMFileIsMMFHeader(void *header);
44 static int _MMFileIsIMYHeader(void *header);
45 static int _MMFileIsASFHeader(void *header);
46 static int _MMFileIsAMRHeader(void *header);
47 static int _MMFileIsFLACHeader(void *header);
48 static int _MMFileIsFLVHeader(void *header);
49 static int _MMFileIsMPEGTSHeader(MMFileIOHandle *fp);
50 static int _MMFileIsMPEGPSHeader(void *header);
51 static int _MMFileIsMPEGAUDIOHeader(void *header);
52 static int _MMFileIsMPEGVIDEOHeader(void *header);
53 static int _MMFileIsAIFFHeader(void *header);
54 static int _MMFileIsAPEHeader(void *header);
56 /***********************************************************************/
57 /* MP3 Header Check API */
58 /***********************************************************************/
60 int MMFileFormatIsValidMP3(MMFileIOHandle *pFileIO, const char *mmfileuri, int frameCnt)
62 #define _MMFILE_MP3_HEADER_LENGTH 4
63 #define _MMFILE_MP3_BUFFER_LENGTH 8200
65 MMFileIOHandle *fp = pFileIO;
66 unsigned char buffer[_MMFILE_MP3_BUFFER_LENGTH] = {0, };
67 long long filesize = 0;
68 unsigned int sizeID3 = 0;
69 int readed = 0, i = 0, j = 0;;
70 unsigned int startoffset = 0;
73 int ret = 0, count = 0, offset = 0;
76 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
77 if (ret == MMFILE_IO_FAILED) {
78 debug_error(DEBUG, "error: mmfile_open\n");
83 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
85 mmfile_seek(fp, 0L, MMFILE_SEEK_END);
86 filesize = mmfile_tell(fp);
87 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
89 if (filesize < _MMFILE_MP3_HEADER_LENGTH) {
90 debug_error(DEBUG, "header is too small.\n");
95 /* Search the existance of ID3 tag */
96 ret = _MMFileSearchID3Tag(fp, &sizeID3);
98 debug_error(RELEASE, "Error in searching the ID3 tag\n");
104 /* set begin and end point at the file */
105 startoffset += sizeID3;
106 endoffset = startoffset + 102400;
107 if (endoffset > filesize - _MMFILE_MP3_HEADER_LENGTH)
108 endoffset = filesize - _MMFILE_MP3_HEADER_LENGTH;
114 while (i < endoffset) {
115 mmfile_seek(fp, i, MMFILE_SEEK_SET);
116 readed = mmfile_read(fp, buffer, _MMFILE_MP3_BUFFER_LENGTH);
117 if (readed < _MMFILE_MP3_HEADER_LENGTH) {
118 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
124 for (j = 0; (j <= readed - _MMFILE_MP3_HEADER_LENGTH); j = j + offset) {
125 frameSize = _MMFileIsMP3Header(buffer + j);
131 if ((j + frameSize) >= (endoffset - (i + _MMFILE_MP3_HEADER_LENGTH))) {
135 if ((j + frameSize) >= (readed - _MMFILE_MP3_HEADER_LENGTH)) {
136 debug_msg(RELEASE, "MP3 coner hit %d %d\n", j, frameSize);
140 frameSize = _MMFileIsMP3Header(buffer + j + frameSize);
145 if (count == frameCnt) {
147 debug_msg(RELEASE, "Header Detected at %d\n", i + j);
156 /*If j is zero, this loop is infinite */
163 debug_msg(RELEASE, "Header Not Detected at: %d\n", i + j);
165 if (pFileIO == NULL && fp != NULL)
173 /***********************************************************************/
174 /* AAC Header Check API */
175 /***********************************************************************/
177 int MMFileFormatIsValidAAC(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
179 #define _MMFILE_AAC_HEADER_LENGTH 4
180 #define _MMFILE_AAC_BUFFER_LENGTH 8200
182 MMFileIOHandle *fp = pFileIO;
183 unsigned char buffer[_MMFILE_AAC_BUFFER_LENGTH] = {0, };
184 unsigned int sizeID3 = 0;
185 long long filesize = 0;
186 int readed = 0, i = 0, j = 0;
190 unsigned int sync = 0;
194 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
195 if (ret == MMFILE_IO_FAILED) {
196 debug_error(DEBUG, "error: mmfile_open\n");
201 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
203 /* Initialize the members of handle */
204 mmfile_seek(fp, 0, MMFILE_SEEK_END);
205 filesize = mmfile_tell(fp);
206 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
208 if (filesize < _MMFILE_AAC_HEADER_LENGTH) {
209 debug_error(DEBUG, "header is too small.\n");
214 /* Search the existance of ID3 tag */
215 ret = _MMFileSearchID3Tag(fp, &sizeID3);
217 debug_error(RELEASE, "Error in searching the ID3 tag\n");
223 /* set begin and end point at the file */
224 startoffset += sizeID3;
225 endoffset = startoffset + 10240;
226 if (endoffset > filesize - _MMFILE_AAC_HEADER_LENGTH)
227 endoffset = filesize - _MMFILE_AAC_HEADER_LENGTH;
231 while (i < endoffset) {
232 mmfile_seek(fp, i, MMFILE_SEEK_SET);
234 readed = mmfile_read(fp, buffer, _MMFILE_AAC_BUFFER_LENGTH);
236 if (readed < _MMFILE_AAC_HEADER_LENGTH) {
237 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
242 debug_msg(RELEASE, "read error. size = %d. i = %d\n", readed, i);
244 for (j = 0; (j < readed - _MMFILE_AAC_HEADER_LENGTH); j++) {
246 sync = ((buffer[j] << 8) | (buffer[j + 1]));
248 if ((sync & 0xFFF6) == 0xFFF0) {
249 frameSize = (((buffer[j + 3] & 0x03) << 11) | (buffer[j + 4] << 3) | ((buffer[j + 5] & 0xE0) >> 5));
251 if (frameSize == 0) {
255 if ((j + frameSize) >= (endoffset - (i + 2))) {
258 if ((j + frameSize) >= (readed - 2)) {
259 debug_msg(RELEASE, "AAC coner hit %d %d\n", j, frameSize);
263 sync = ((buffer[j + frameSize] << 8) | (buffer[j + frameSize + 1]));
265 if ((sync & 0xFFF6) == 0xFFF0) {
267 debug_msg(RELEASE, "AAC ADTS Header Detected at %d\n", i + j);
270 } else if (!memcmp((buffer + j), "ADIF", 4)) {
272 debug_msg(RELEASE, "AAC ADIF Header Detected at %d\n", i + j);
276 /*If j is zero, this loop is infinite */
284 debug_msg(RELEASE, "Header Detected Failed\n");
286 if (pFileIO == NULL && fp != NULL)
294 /***********************************************************************/
295 /* OGG Header Check API */
296 /***********************************************************************/
298 int MMFileFormatIsValidOGG(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
300 #define _MMFILE_OGG_HEADER_LENGTH 4
301 #define _MMFILE_OGG_BUFFER_LENGTH 512
302 #define _MMFILE_OGG_CHECK_LIMIT (_MMFILE_OGG_HEADER_LENGTH * 1000)
304 MMFileIOHandle *fp = pFileIO;
305 unsigned char buffer[_MMFILE_OGG_BUFFER_LENGTH] = {0, };
306 unsigned int sizeID3 = 0;
307 long long filesize = 0;
308 int readed = 0, i = 0, j = 0;
315 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
316 if (ret == MMFILE_IO_FAILED) {
317 debug_error(DEBUG, "error: mmfile_open\n");
323 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
325 /* Initialize the members of handle */
326 mmfile_seek(fp, 0, MMFILE_SEEK_END);
327 filesize = mmfile_tell(fp);
328 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
330 if (filesize < _MMFILE_OGG_HEADER_LENGTH) {
331 debug_error(DEBUG, "header is too small.\n");
336 /* Search the existance of ID3 tag */
337 ret = _MMFileSearchID3Tag(fp, &sizeID3);
339 debug_error(RELEASE, "Error in searching the ID3 tag\n");
345 /* set begin and end point at the file */
346 startoffset += sizeID3;
347 endoffset = filesize - _MMFILE_OGG_HEADER_LENGTH;
349 check_limit = (endoffset > _MMFILE_OGG_CHECK_LIMIT) ? _MMFILE_OGG_CHECK_LIMIT : endoffset;
352 while (i <= check_limit) {
353 mmfile_seek(fp, i, MMFILE_SEEK_SET);
354 readed = mmfile_read(fp, buffer, _MMFILE_OGG_BUFFER_LENGTH);
355 if (readed < _MMFILE_OGG_HEADER_LENGTH) {
356 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
361 for (j = 0; (j <= readed - _MMFILE_OGG_HEADER_LENGTH); j++) {
362 if (1 == _MMFileIsOGGHeader(buffer + j)) {
364 debug_msg(RELEASE, "Header Detected at %d\n", i + j);
369 memset(buffer, 0x00, _MMFILE_OGG_BUFFER_LENGTH);
375 if (pFileIO == NULL && fp != NULL)
383 /***********************************************************************/
384 /* MIDI Header Check API */
385 /***********************************************************************/
387 int MMFileFormatIsValidMID(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
389 #define _MMFILE_MIDI_HEADER_LENGTH 4
390 #define _MMFILE_MIDI_BUFFER_LENGTH 512
391 #define _MMFILE_MIDI_CHECK_LIMIT (_MMFILE_MIDI_HEADER_LENGTH * 1024)
393 MMFileIOHandle *fp = pFileIO;
394 unsigned char buffer[_MMFILE_MIDI_BUFFER_LENGTH] = {0, };
395 long long filesize = 0;
396 int readed = 0, i = 0, j = 0;
403 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
404 if (ret == MMFILE_IO_FAILED) {
405 debug_error(DEBUG, "error: mmfile_open\n");
410 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
412 /* Initialize the members of handle */
413 mmfile_seek(fp, 0, MMFILE_SEEK_END);
414 filesize = mmfile_tell(fp);
415 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
417 if (filesize < _MMFILE_MIDI_HEADER_LENGTH) {
418 debug_error(DEBUG, "header is too small.\n");
425 /* set begin and end point at the file */
427 endoffset = filesize - _MMFILE_MIDI_HEADER_LENGTH;
429 check_limit = (endoffset > _MMFILE_MIDI_CHECK_LIMIT) ? _MMFILE_MIDI_CHECK_LIMIT : endoffset;
432 while (i <= check_limit) {
433 mmfile_seek(fp, i, MMFILE_SEEK_SET);
434 readed = mmfile_read(fp, buffer, _MMFILE_MIDI_BUFFER_LENGTH);
435 if (readed < _MMFILE_MIDI_HEADER_LENGTH) {
436 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
441 for (j = 0; (j <= readed - _MMFILE_MIDI_HEADER_LENGTH); j++) {
442 if (1 == _MMFileIsMIDHeader(buffer + j)) {
444 debug_msg(RELEASE, "Header Detected at %d\n", i + j);
449 memset(buffer, 0x00, _MMFILE_MIDI_BUFFER_LENGTH);
455 if (pFileIO == NULL && fp != NULL)
462 /***********************************************************************/
463 /* WAV Header Check API */
464 /***********************************************************************/
466 int MMFileFormatIsValidWAV(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
468 #define _MMFILE_WAV_HEADER_LENGTH 15
470 MMFileIOHandle *fp = pFileIO;
471 unsigned char buffer[_MMFILE_WAV_HEADER_LENGTH] = {0, };
476 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
477 if (ret == MMFILE_IO_FAILED) {
478 debug_error(DEBUG, "error: mmfile_open\n");
483 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
485 readed = mmfile_read(fp, buffer, _MMFILE_WAV_HEADER_LENGTH);
487 if (_MMFILE_WAV_HEADER_LENGTH != readed) {
488 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
493 if (1 == _MMFileIsWAVHeader(buffer)) {
494 debug_msg(RELEASE, "Header Detected\n");
500 if (pFileIO == NULL && fp != NULL)
508 /***********************************************************************/
509 /* MP4 Header Check API */
510 /***********************************************************************/
512 int MMFileFormatIsValidMP4(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
514 #define _MMFILE_MP4_HEADER_LENGTH 4
515 #define _MMFILE_MP4_CHECK_LIMIT (1024*10) /*10Kbyte*/
516 MMFileIOHandle *fp = pFileIO;
517 unsigned char buffer[_MMFILE_MP4_HEADER_LENGTH] = {0, };
518 long long filesize = 0;
520 unsigned int startoffset = 0;
522 unsigned int check_limit = 0;
525 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
526 if (ret == MMFILE_IO_FAILED) {
527 debug_error(DEBUG, "error: mmfile_open\n");
532 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
534 /* Initialize the members of handle */
535 mmfile_seek(fp, 0, MMFILE_SEEK_END);
536 filesize = mmfile_tell(fp);
537 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
539 if (filesize < _MMFILE_MP4_HEADER_LENGTH) {
540 debug_error(DEBUG, "header is too small.\n");
547 /**@note weak check*/
548 check_limit = (filesize > _MMFILE_MP4_CHECK_LIMIT) ? _MMFILE_MP4_CHECK_LIMIT : filesize;
549 for (startoffset = 0; check_limit - (startoffset + _MMFILE_MP4_HEADER_LENGTH) > 0; startoffset++) {
550 mmfile_seek(fp, startoffset, MMFILE_SEEK_SET);
552 readed = mmfile_read(fp, buffer, _MMFILE_MP4_HEADER_LENGTH);
553 if (readed != _MMFILE_MP4_HEADER_LENGTH) {
554 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
560 if (1 == _MMFileIsMP4Header(buffer)) {
561 debug_msg(RELEASE, "MP4 Header Detected\n");
568 if (pFileIO == NULL && fp != NULL)
575 /***********************************************************************/
576 /* AVI Header Check API */
577 /***********************************************************************/
579 int MMFileFormatIsValidAVI(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
581 #define _MMFILE_AVI_HEADER_LENGTH 12
583 MMFileIOHandle *fp = pFileIO;
584 unsigned char buffer[_MMFILE_AVI_HEADER_LENGTH] = {0, };
589 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
590 if (ret == MMFILE_IO_FAILED) {
591 debug_error(DEBUG, "error: mmfile_open\n");
596 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
598 readed = mmfile_read(fp, buffer, _MMFILE_AVI_HEADER_LENGTH);
600 if (_MMFILE_AVI_HEADER_LENGTH != readed) {
601 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
606 if (1 == _MMFileIsAVIHeader(buffer)) {
607 debug_msg(RELEASE, "Header Detected \n");
613 if (pFileIO == NULL && fp != NULL)
621 /***********************************************************************/
622 /* ASF Header Check API */
623 /***********************************************************************/
625 int MMFileFormatIsValidASF(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
627 #define _MMFILE_ASF_HEADER_LENGTH 16
628 MMFileIOHandle *fp = pFileIO;
629 unsigned char buffer[_MMFILE_ASF_HEADER_LENGTH] = {0, };
634 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
635 if (ret == MMFILE_IO_FAILED) {
636 debug_error(DEBUG, "error: mmfile_open\n");
641 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
643 readed = mmfile_read(fp, buffer, _MMFILE_ASF_HEADER_LENGTH);
645 if (_MMFILE_ASF_HEADER_LENGTH != readed) {
646 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
651 if (1 == _MMFileIsASFHeader(buffer)) {
652 debug_msg(RELEASE, "Header Detected\n");
658 if (pFileIO == NULL && fp != NULL)
664 /***********************************************************************/
665 /* WMA Header Check API */
666 /***********************************************************************/
668 int MMFileFormatIsValidWMA(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
670 return MMFileFormatIsValidASF(pFileIO, mmfileuri, dummy);
675 /***********************************************************************/
676 /* WMV Header Check API */
677 /***********************************************************************/
679 int MMFileFormatIsValidWMV(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
681 return MMFileFormatIsValidASF(pFileIO, mmfileuri, dummy);
685 /***********************************************************************/
686 /* MMF Header Check API */
687 /***********************************************************************/
689 int MMFileFormatIsValidMMF(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
691 #define _MMFILE_MMF_HEADER_LENGTH 18
693 MMFileIOHandle *fp = pFileIO;
694 unsigned char buffer[_MMFILE_MMF_HEADER_LENGTH] = {0, };
699 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
700 if (ret == MMFILE_IO_FAILED) {
701 debug_error(DEBUG, "error: mmfile_open\n");
706 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
708 readed = mmfile_read(fp, buffer, _MMFILE_MMF_HEADER_LENGTH);
710 if (_MMFILE_MMF_HEADER_LENGTH != readed) {
711 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
716 if (1 == _MMFileIsMMFHeader(buffer)) {
717 debug_msg(RELEASE, "Header Detected\n");
723 if (pFileIO == NULL && fp != NULL)
731 /***********************************************************************/
732 /* MMF Header Check API */
733 /***********************************************************************/
735 int MMFileFormatIsValidIMY(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
737 #define _MMFILE_IMY_HEADER_LENGTH 13
739 MMFileIOHandle *fp = pFileIO;
740 unsigned char buffer[_MMFILE_IMY_HEADER_LENGTH] = {0, };
745 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
746 if (ret == MMFILE_IO_FAILED) {
747 debug_error(DEBUG, "error: mmfile_open\n");
752 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
754 readed = mmfile_read(fp, buffer, _MMFILE_IMY_HEADER_LENGTH);
756 if (_MMFILE_IMY_HEADER_LENGTH != readed) {
757 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
762 if (1 == _MMFileIsIMYHeader(buffer)) {
763 debug_msg(RELEASE, "Header Detected\n");
769 if (pFileIO == NULL && fp != NULL)
777 /***********************************************************************/
778 /* AMR Header Check API */
779 /***********************************************************************/
781 int MMFileFormatIsValidAMR(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
783 #define _MMFILE_AMR_MAX_HEADER_SIZE 15
784 #define _MMFILE_AMR_MIN_HEADER_SIZE 6
786 MMFileIOHandle *fp = pFileIO;
787 unsigned char buffer[_MMFILE_AMR_MAX_HEADER_SIZE] = {0, };
792 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
793 if (ret == MMFILE_IO_FAILED) {
794 debug_error(DEBUG, "error: mmfile_open\n");
799 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
801 readed = mmfile_read(fp, buffer, _MMFILE_AMR_MAX_HEADER_SIZE);
803 if (_MMFILE_AMR_MAX_HEADER_SIZE != readed) {
804 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
809 if (1 == _MMFileIsAMRHeader(buffer)) {
810 debug_msg(RELEASE, "Header Detected\n");
816 if (pFileIO == NULL && fp != NULL)
822 /***********************************************************************/
823 /* Matroska Header Check API */
824 /***********************************************************************/
826 int MMFileFormatIsValidMatroska(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
828 #define _MMFILE_EBML_MARKER_LENGTH 4
829 #define _MMFILE_MKV_READ_BUFFER_LENGTH 2048
831 MMFileIOHandle *fp = pFileIO;
832 unsigned char buffer[_MMFILE_MKV_READ_BUFFER_LENGTH] = {0, };
836 unsigned int size = 1, n = 1, total = 0;
837 //char probe_data[] = { 'm', 'a', 't', 'r', 'o', 's', 'k', 'a' };
838 /*support webm, add probe data*/
839 const char * probe_data[2] = { "matroska", "webm" };
841 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
842 if (ret == MMFILE_IO_FAILED) {
843 debug_error(DEBUG, "error: mmfile_open\n");
848 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
850 readed = mmfile_read(fp, buffer, _MMFILE_MKV_READ_BUFFER_LENGTH);
852 if (_MMFILE_MKV_READ_BUFFER_LENGTH != readed) {
853 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
859 if (buffer[0] != 0x1A || buffer[1] != 0x45 || buffer[2] != 0xDF || buffer[3] != 0xA3) {
860 debug_msg(RELEASE, "This is not a EBML format\n");
865 /* length of header */
868 debug_msg(RELEASE, "Initial total header size = [0x%x]\n", total);
870 while (size <= 8 && !(total & len_mask)) {
871 debug_msg(DEBUG, "This case can not be handled yet....");
876 debug_msg(RELEASE, "Final total header size = [%d]\n", total);
879 debug_msg(DEBUG, "This case can not be handled yet....");
884 total &= (len_mask - 1);
887 total = (total << 8) | buffer[4 + n++];
888 debug_msg(DEBUG, "This case can not be handled yet....");
891 /* Does the probe data contain the whole header? */
892 if (_MMFILE_MKV_READ_BUFFER_LENGTH < 4 + size + total)
895 /*compare two kinds of probe data*/
896 for (int i = 0; i < 2; i++) {
897 unsigned int probelen = strlen(probe_data[i]);
898 if (total < probelen)
900 for (n = 4 + size ; n <= 4 + size + total - probelen; n++) {
901 if (!memcmp(&buffer[n], probe_data[i], probelen)) {
902 debug_msg(RELEASE, "String %s found!!!\n", probe_data[i]);
910 if (pFileIO == NULL && fp != NULL)
916 /***********************************************************************/
917 /* QT Header Check API */
918 /***********************************************************************/
920 int MMFileFormatIsValidQT(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
925 /***********************************************************************/
926 /* Flac Header Check API */
927 /***********************************************************************/
929 int MMFileFormatIsValidFLAC(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
931 #define _MMFILE_FLAC_HEADER_LENGTH 5 /*fLaC*/
933 MMFileIOHandle *fp = pFileIO;
934 unsigned char buffer[_MMFILE_FLAC_HEADER_LENGTH] = {0, };
939 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
940 if (ret == MMFILE_IO_FAILED) {
941 debug_error(DEBUG, "error: mmfile_open\n");
946 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
948 readed = mmfile_read(fp, buffer, _MMFILE_FLAC_HEADER_LENGTH);
950 if (_MMFILE_FLAC_HEADER_LENGTH != readed) {
951 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
956 if (1 == _MMFileIsFLACHeader(buffer)) {
957 debug_msg(RELEASE, "Header Detected\n");
963 if (pFileIO == NULL && fp != NULL)
969 /***********************************************************************/
970 /* FLV(flash video) Header Check API */
971 /***********************************************************************/
973 int MMFileFormatIsValidFLV(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
975 #define _MMFILE_FLV_HEADER_LENGTH 4 /*FLV*/
977 MMFileIOHandle *fp = pFileIO;
978 unsigned char buffer[_MMFILE_FLV_HEADER_LENGTH] = {0, };
983 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
984 if (ret == MMFILE_IO_FAILED) {
985 debug_error(DEBUG, "error: mmfile_open\n");
990 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
992 readed = mmfile_read(fp, buffer, _MMFILE_FLV_HEADER_LENGTH);
994 if (_MMFILE_FLV_HEADER_LENGTH != readed) {
995 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1000 if (1 == _MMFileIsFLVHeader(buffer)) {
1001 debug_msg(RELEASE, "Header Detected\n");
1007 if (pFileIO == NULL && fp != NULL)
1014 /***********************************************************************/
1015 /* REAL Header Check API */
1016 /***********************************************************************/
1018 int MMFileFormatIsValidREAL(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1020 #define _MMFILE_RMVB_HEADER_LENGTH 4 /*RMF*/
1022 MMFileIOHandle *fp = pFileIO;
1023 unsigned char buffer[_MMFILE_RMVB_HEADER_LENGTH] = {0, };
1028 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1029 if (ret == MMFILE_IO_FAILED) {
1030 debug_error(DEBUG, "error: mmfile_open\n");
1035 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1037 readed = mmfile_read(fp, buffer, _MMFILE_RMVB_HEADER_LENGTH);
1039 if (_MMFILE_RMVB_HEADER_LENGTH != readed) {
1040 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1045 if (1 == _MMFileIsREALHeader(buffer)) {
1046 debug_msg(RELEASE, "Header Detected\n");
1053 if (pFileIO == NULL && fp != NULL)
1059 /***********************************************************************/
1060 /* MPEGTS Header Check API */
1061 /***********************************************************************/
1062 #define MPEGTS_NONE 0x00
1063 #define MPEGTS_FECE 0x10
1064 #define MPEGTS_DVHS 0x20
1065 #define MPEGTS_PACKET 0x40
1067 #define TS_PACKET_SIZE 188
1068 #define TS_DVHS_PACKET_SIZE 192
1069 #define TS_FEC_PACKET_SIZE 204
1070 #define TS_MAX_PACKET_SIZE 204
1073 int MMFileFormatIsValidMPEGTS(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1075 MMFileIOHandle *fp = pFileIO;
1076 unsigned char buffer[TS_MAX_PACKET_SIZE] = {0, };
1081 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1082 if (ret == MMFILE_IO_FAILED) {
1083 debug_error(DEBUG, "error: mmfile_open\n");
1088 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1090 readed = mmfile_read(fp, buffer, TS_MAX_PACKET_SIZE);
1092 if (TS_MAX_PACKET_SIZE != readed) {
1093 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1098 if (_MMFileIsMPEGTSHeader(fp) != MPEGTS_NONE) {
1099 debug_msg(RELEASE, "Header Detected\n");
1105 if (pFileIO == NULL && fp != NULL)
1111 /***********************************************************************/
1112 /* MPEG-PS Header Check API */
1113 /***********************************************************************/
1115 int MMFileFormatIsValidMPEGPS(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1117 #define _MMFILE_MPEGPS_HEADER_LENGTH 4
1119 MMFileIOHandle *fp = pFileIO;
1120 unsigned char buffer[_MMFILE_MPEGPS_HEADER_LENGTH] = {0, };
1125 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1126 if (ret == MMFILE_IO_FAILED) {
1127 debug_error(DEBUG, "error: mmfile_open\n");
1132 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1134 readed = mmfile_read(fp, buffer, _MMFILE_MPEGPS_HEADER_LENGTH);
1136 if (_MMFILE_MPEGPS_HEADER_LENGTH != readed) {
1137 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1142 if (1 == _MMFileIsMPEGPSHeader(buffer)) {
1143 debug_msg(RELEASE, "Header Detected\n");
1149 if (pFileIO == NULL && fp != NULL)
1155 /***********************************************************************/
1156 /* MPEG AUDIO Header Check API */
1157 /***********************************************************************/
1159 int MMFileFormatIsValidMPEGAUDIO(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1161 #define _MMFILE_MPEGAUDIO_HEADER_LENGTH 4
1163 MMFileIOHandle *fp = pFileIO;
1164 unsigned char buffer[_MMFILE_MPEGAUDIO_HEADER_LENGTH] = {0, };
1169 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1170 if (ret == MMFILE_IO_FAILED) {
1171 debug_error(DEBUG, "error: mmfile_open\n");
1176 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1178 readed = mmfile_read(fp, buffer, _MMFILE_MPEGAUDIO_HEADER_LENGTH);
1180 if (_MMFILE_MPEGAUDIO_HEADER_LENGTH != readed) {
1181 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1186 if (1 == _MMFileIsMPEGAUDIOHeader(buffer)) {
1187 debug_msg(RELEASE, "Header Detected\n");
1193 if (pFileIO == NULL && fp != NULL)
1199 /***********************************************************************/
1200 /* MPEG VIDEO Header Check API */
1201 /***********************************************************************/
1203 int MMFileFormatIsValidMPEGVIDEO(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1205 #define _MMFILE_MPEGVIDEO_HEADER_LENGTH 4
1207 MMFileIOHandle *fp = pFileIO;
1208 unsigned char buffer[_MMFILE_MPEGVIDEO_HEADER_LENGTH] = {0, };
1213 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1214 if (ret == MMFILE_IO_FAILED) {
1215 debug_error(DEBUG, "error: mmfile_open\n");
1220 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1222 readed = mmfile_read(fp, buffer, _MMFILE_MPEGVIDEO_HEADER_LENGTH);
1224 if (_MMFILE_MPEGVIDEO_HEADER_LENGTH != readed) {
1225 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1230 if (1 == _MMFileIsMPEGVIDEOHeader(buffer)) {
1231 debug_msg(RELEASE, "Header Detected\n");
1237 if (pFileIO == NULL && fp != NULL)
1243 /***********************************************************************/
1244 /* AIFF Header Check API */
1245 /***********************************************************************/
1247 int MMFileFormatIsValidAIFF(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1249 #define _MMFILE_AIFF_HEADER_LENGTH 13
1251 MMFileIOHandle *fp = pFileIO;
1252 unsigned char buffer[_MMFILE_AIFF_HEADER_LENGTH] = {0, };
1257 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1258 if (ret == MMFILE_IO_FAILED) {
1259 debug_error(DEBUG, "error: mmfile_open\n");
1264 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1266 readed = mmfile_read(fp, buffer, _MMFILE_AIFF_HEADER_LENGTH);
1268 if (_MMFILE_AIFF_HEADER_LENGTH != readed) {
1269 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1274 if (1 == _MMFileIsAIFFHeader(buffer)) {
1275 debug_msg(RELEASE, "Header Detected\n");
1281 if (pFileIO == NULL && fp != NULL)
1288 int MMFileFormatIsValidAPE(MMFileIOHandle *pFileIO, const char *mmfileuri, int dummy)
1290 #define _MMFILE_APE_HEADER_LENGTH 4 /*APE*/
1292 MMFileIOHandle *fp = pFileIO;
1293 unsigned char buffer[_MMFILE_APE_HEADER_LENGTH] = {0, };
1298 ret = mmfile_open(&fp, mmfileuri, MMFILE_RDONLY);
1299 if (ret == MMFILE_IO_FAILED) {
1300 debug_error(DEBUG, "error: mmfile_open\n");
1305 mmfile_seek(fp, 0L, MMFILE_SEEK_SET);
1307 readed = mmfile_read(fp, buffer, _MMFILE_APE_HEADER_LENGTH);
1309 if (_MMFILE_APE_HEADER_LENGTH != readed) {
1310 debug_error(RELEASE, "read error. size = %d. Maybe end of file.\n", readed);
1315 if (1 == _MMFileIsAPEHeader(buffer)) {
1316 debug_msg(RELEASE, "Header Detected\n");
1322 if (pFileIO == NULL && fp != NULL)
1328 /***********************************************************************/
1329 /* Implementation of Internal Functions */
1330 /***********************************************************************/
1331 static int _MMFileIsASFHeader(void *header)
1333 /* ID: 30 26 B2 75 8E 66 CF 11 A6 D9 00 AA 00 62 CE 6C */
1334 unsigned char *s = header;
1336 if ((*(s + 0) == 0x30) &&
1337 (*(s + 1) == 0x26) &&
1338 (*(s + 2) == 0xB2) &&
1339 (*(s + 3) == 0x75) &&
1340 (*(s + 4) == 0x8E) &&
1341 (*(s + 5) == 0x66) &&
1342 (*(s + 6) == 0xCF) &&
1343 (*(s + 7) == 0x11) &&
1344 (*(s + 8) == 0xA6) &&
1345 (*(s + 9) == 0xD9) &&
1346 (*(s + 10) == 0x00) &&
1347 (*(s + 11) == 0xAA) &&
1348 (*(s + 12) == 0x00) &&
1349 (*(s + 13) == 0x62) &&
1350 (*(s + 14) == 0xCE) &&
1351 (*(s + 15) == 0x6C)) {
1359 static int _MMFileIsAMRHeader(void *header)
1361 #define _MMFILE_AMR_SINGLE_CH_HEADER_SIZE 6
1362 #define _MMFILE_AMR_SINGLE_CH_HEADER "#!AMR\n"
1364 #define _MMFILE_AMR_WB_SINGLE_CH_HEADER_SIZE 9
1365 #define _MMFILE_AMR_WB_SINGLE_CH_HEADER "#!AMR-WB\n"
1367 #define _MMFILE_AMR_MULTI_CH_HEADER_SIZE 12
1368 #define _MMFILE_AMR_MULTI_CH_HEADER "#!AMR_MC1.0\n"
1370 #define _MMFILE_AMR_WB_MULTI_CH_HEADER_SIZE 15
1371 #define _MMFILE_AMR_WB_MULTI_CH_HEADER "#!AMR-WB_MC1.0\n"
1373 unsigned char *s = header;
1375 if (!memcmp(s, _MMFILE_AMR_SINGLE_CH_HEADER, _MMFILE_AMR_SINGLE_CH_HEADER_SIZE) ||
1376 !memcmp(s, _MMFILE_AMR_WB_SINGLE_CH_HEADER, _MMFILE_AMR_WB_SINGLE_CH_HEADER_SIZE) ||
1377 !memcmp(s, _MMFILE_AMR_MULTI_CH_HEADER, _MMFILE_AMR_MULTI_CH_HEADER_SIZE) ||
1378 !memcmp(s, _MMFILE_AMR_WB_MULTI_CH_HEADER, _MMFILE_AMR_WB_MULTI_CH_HEADER_SIZE)) {
1386 static int _MMFileIsIMYHeader(void *header)
1388 unsigned char *s = header;
1390 if (!memcmp(s, "BEGIN:IMELODY", 13)) {
1397 static int _MMFileIsMIDHeader(void *header)
1399 unsigned char *s = header;
1401 if (!memcmp(s, "MThd", 4)) { /*general MIDI*/
1403 } else if (!memcmp(s, "XMF_", 4)) { /*XMF*/
1405 } else if (!memcmp(s, "IREZ", 4)) {
1406 return 1; /*RMF format*/
1412 static int _MMFileIsMMFHeader(void *header)
1414 #define _MMFILE_MMF_TYPE_POSITION ((char)0x11)
1415 unsigned char *s = header;
1417 if (!memcmp(s, "MMMD", 4)) {
1418 /* warning: comparison is always true due to limited range of data type */
1419 if (*(s + _MMFILE_MMF_TYPE_POSITION) <= 0x2F) {
1421 } else if (((*(s + _MMFILE_MMF_TYPE_POSITION) >= 0x30) && (*(s + _MMFILE_MMF_TYPE_POSITION) <= 0x38)) /* MA3, MA5 type */
1422 || ((*(s + _MMFILE_MMF_TYPE_POSITION) >= 0x40) && (*(s + _MMFILE_MMF_TYPE_POSITION) <= 0x48))
1423 || ((*(s + _MMFILE_MMF_TYPE_POSITION) >= 0x50) && (*(s + _MMFILE_MMF_TYPE_POSITION) <= 0x58))
1424 || ((*(s + _MMFILE_MMF_TYPE_POSITION) == 0xF0))) {
1434 static int _MMFileIsAVIHeader(void *header)
1436 unsigned char *s = header;
1438 if (!memcmp(s, "RIFF", 4) && !memcmp(s + 8, "AVI", 3)) {
1446 static int _MMFileIsWAVHeader(void *header)
1448 unsigned char *s = header;
1450 if (!memcmp(s, "RIFF", 4) && !memcmp(s + 8, "WAVE", 4)) {
1459 static int _MMFileIsMP4Header(void *header)
1461 unsigned char *s = header;
1463 if (!memcmp(s, "moov", 4) ||
1464 !memcmp(s, "mdat", 4) ||
1465 !memcmp(s, "ftyp", 4) ||
1466 !memcmp(s, "free", 4) ||
1467 !memcmp(s, "uuid", 4) ||
1468 !memcmp(s, "skip", 4) ||
1470 !memcmp(s, "PICT", 4) ||
1471 !memcmp(s, "wide", 4) ||
1472 !memcmp(s, "prfl", 4)) {
1479 static int _MMFileIsOGGHeader(void *header)
1481 unsigned char *s = header;
1483 if (!memcmp(s, "OggS", 4)) {
1490 static int _MMFileIsREALHeader(void *header)
1492 unsigned char *s = header;
1494 if (!memcmp(s, ".RMF", 4)) {
1501 static int _MMFileIsMPEGTSHeader(MMFileIOHandle *fp)
1503 unsigned char header[TS_MAX_PACKET_SIZE] = {0, };
1504 unsigned char *s = NULL;
1506 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
1507 mmfile_read(fp, header, sizeof(header));
1509 s = (unsigned char *)memchr(header, 0x47, sizeof(header));
1512 unsigned char buffer[TS_PACKET_SIZE] = {0, };
1513 unsigned int startoffset = s - header + 1;
1515 mmfile_seek(fp, startoffset, MMFILE_SEEK_SET);
1516 mmfile_read(fp, buffer, sizeof(buffer));
1518 if (buffer[sizeof(buffer) - 1] & 0x47) {
1519 return MPEGTS_PACKET;
1521 unsigned char dvhs_buf[TS_DVHS_PACKET_SIZE] = {0, };
1523 mmfile_seek(fp, startoffset, MMFILE_SEEK_SET);
1524 mmfile_read(fp, dvhs_buf, sizeof(dvhs_buf));
1526 if (dvhs_buf[sizeof(dvhs_buf) - 1] & 0x47) {
1529 unsigned char fec_buf[TS_FEC_PACKET_SIZE] = {0, };
1531 mmfile_seek(fp, startoffset, MMFILE_SEEK_SET);
1532 mmfile_read(fp, fec_buf, sizeof(fec_buf));
1534 if (fec_buf[sizeof(fec_buf) - 1] & 0x47) {
1544 static int _MMFileIsMPEGPSHeader(void *header)
1546 unsigned char *s = header;
1548 if ((*(s + 0) == 0x00) &&
1549 (*(s + 1) == 0x00) &&
1550 (*(s + 2) == 0x01) &&
1551 (*(s + 3) == 0xba)) { /* mpeg-ps header */
1558 static int _MMFileIsMPEGAUDIOHeader(void *header)
1560 unsigned char *s = header;
1562 if ((*(s + 0) == 0xFF) &&
1563 ((*(s + 1) == 0xFE) || (*(s + 1) == 0xFF))) { /* mpeg audio layer 1 header ,FE: protected by CRC ,FF: not protected */
1570 static int _MMFileIsMPEGVIDEOHeader(void *header)
1572 unsigned char *s = header;
1574 if ((*(s + 0) == 0x00) &&
1575 (*(s + 1) == 0x00) &&
1576 (*(s + 2) == 0x01) &&
1577 (*(s + 3) == 0xb3)) { /* mpeg1 video header */
1584 static int _MMFileIsMP3Header(void *header)
1586 unsigned long head = 0;
1587 unsigned char *headc = header;
1588 unsigned int bitrate, layer, length/*, mode*/;
1589 unsigned int coef, samplerate, version/*, channels*/;
1590 static const unsigned int mp3types_bitrates[2][3][16] = {
1591 { {0, 32, 64, 96, 128, 160, 192, 224, 256, 288, 320, 352, 384, 416, 448,},
1592 {0, 32, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320, 384,},
1593 {0, 32, 40, 48, 56, 64, 80, 96, 112, 128, 160, 192, 224, 256, 320,}
1595 { {0, 32, 48, 56, 64, 80, 96, 112, 128, 144, 160, 176, 192, 224, 256,},
1596 {0, 8, 16, 24, 32, 40, 48, 56, 64, 80, 96, 112, 128, 144, 160,},
1597 {0, 8, 16, 24, 32, 40, 48, 56, 64, 80, 96, 112, 128, 144, 160,}
1601 static const unsigned int mp3types_freqs[3][3] = {
1602 {11025, 12000, 8000},
1603 {22050, 24000, 16000},
1604 {44100, 48000, 32000}
1607 static const unsigned int mp3FrameCoef[4][4] = {
1615 head = (*(headc + 0) << 24 | *(headc + 1) << 16 | *(headc + 2) << 8 | *(headc + 3));
1617 if ((head & 0xffe00000) != 0xffe00000) {
1621 /* we don't need extension, copyright, original or
1622 * emphasis for the frame length */
1626 /*mode = head & 0x3;*/
1630 length = head & 0x1;
1633 /* sampling frequency */
1634 samplerate = head & 0x3;
1635 if (samplerate == 3) {
1641 bitrate = head & 0xF;
1643 if (bitrate == 15) {
1647 /* ignore error correction, too */
1651 layer = 4 - (head & 0x3);
1657 /* version 0=MPEG2.5; 2=MPEG2; 3=MPEG1 */
1658 version = head & 0x3;
1664 /*channels = (mode == 3) ? 1 : 2;*/
1665 samplerate = mp3types_freqs[version > 0 ? version - 1 : 0][samplerate];
1668 bitrate = mp3types_bitrates[version == 3 ? 0 : 1][layer - 1][bitrate];
1669 coef = mp3FrameCoef[version][layer];
1671 length = length * 4;
1673 length = length + ((coef * bitrate * 1000) / samplerate);
1679 static int _MMFileSearchID3Tag(MMFileIOHandle *fp, unsigned int *offset)
1681 #define _MMFILE_MP3_TAGV2_HEADER_LEN 10
1682 #define _MMFILE_GET_INT_NUMBER(buff) (int)((((int)(buff)[0]) << 24) | (((int)(buff)[1]) << 16) | (((int)(buff)[2]) << 8) | (((int)(buff)[3])))
1684 unsigned char tagHeader[_MMFILE_MP3_TAGV2_HEADER_LEN] = {0, };
1685 unsigned int tagInfoSize = 0;
1686 unsigned int acc_tagsize = 0;
1695 mmfile_seek(fp, 0, MMFILE_SEEK_SET);
1699 readed = mmfile_read(fp, tagHeader, _MMFILE_MP3_TAGV2_HEADER_LEN);
1700 if (readed != _MMFILE_MP3_TAGV2_HEADER_LEN) {
1701 debug_error(RELEASE, "read error occured.\n");
1705 if (memcmp(tagHeader, "ID3", 3) == 0) {
1706 debug_msg(RELEASE, "'ID3' found.\n");
1708 debug_msg(RELEASE, "'ID3' not found.\n");
1712 /**@note weak id3v2 tag checking*/
1713 if (tagHeader[3] != 0xFF && tagHeader[4] != 0xFF &&
1714 (tagHeader[6] & 0x80) == 0 && (tagHeader[7] & 0x80) == 0 &&
1715 (tagHeader[8] & 0x80) == 0 && (tagHeader[9] & 0x80) == 0) {
1716 debug_msg(RELEASE, "good ID3V2 tag.\n");
1718 debug_warning(DEBUG, "It's bad ID3V2 tag.\n");
1722 tagVersion = tagHeader[3];
1724 if (tagVersion > 4) {
1725 debug_msg(RELEASE, "Tag version not supported\n");
1729 encSize = _MMFILE_GET_INT_NUMBER(&tagHeader[6]);
1730 tagInfoSize = _MMFILE_MP3_TAGV2_HEADER_LEN;
1731 tagInfoSize += (((encSize & 0x0000007F) >> 0) | ((encSize & 0x00007F00) >> 1) | ((encSize & 0x007F0000) >> 2) | ((encSize & 0x7F000000) >> 3));
1733 /**@note unfortunately, some contents has many id3 tag.*/
1734 acc_tagsize += tagInfoSize;
1735 debug_msg(RELEASE, "tag size: %u, offset: %u\n", tagInfoSize, acc_tagsize);
1737 mmfile_seek(fp, acc_tagsize, MMFILE_SEEK_SET);
1738 *offset = acc_tagsize;
1742 goto _START_TAG_SEARCH;
1748 static int _MMFileIsFLACHeader(void *header)
1750 unsigned char *s = header;
1752 if (!memcmp(s, "fLaC", 4)) {
1759 static int _MMFileIsFLVHeader(void *header)
1761 unsigned char *s = header;
1763 if (!memcmp(s, "FLV", 3)) {
1770 static int _MMFileIsAIFFHeader(void *header)
1772 unsigned char *s = header;
1774 if (!memcmp(s, "FORM", 4) && !memcmp(s + 8, "AIFF", 4)) {
1780 static int _MMFileIsAPEHeader(void *header)
1782 unsigned char *s = header;
1784 if (!memcmp(s, "MAC ", 4)) {