📄 wma_parsenew.c
字号:
/******************************************************************************
*
* Copyright (C),2007, Fuzhou Rockchip Co.,Ltd.
*
* File name : wma_parse.c
* Description: 得到wma歌曲的ID3信息
* Remark:
*
* History:
* <author> <time> <version> <desc>
* Huweiguo 07/11/05 1.0
*
*******************************************************************************/
#if ((defined(BOARD)) || defined(ROCK_FS))
#include "include.h"
#include "wma_parseNew.h"
#ifdef _MEIDA_SORT_NEW
#define MIN_OBJECT_SIZE 24
#define DATA_OBJECT_SIZE 50
#define LOAD_DWORD(p) ((p)[0] | ((p)[1]<<8) | ((p)[2]<<16) | ((p)[3]<<24) )
#define LOAD_WORD(p) ((p)[0] | ((p)[1]<<8))
#define ECD_STRING 0
static unsigned char AsfHeaderObjectV0[16] =
{
0x30, 0x26, 0xb2, 0x75, 0x8e, 0x66, 0xcf, 0x11, 0xa6, 0xd9, 0x00, 0xaa, 0x00, 0x62, 0xce, 0x6c
};
static unsigned char AsfContentDescriptionObjectV0[16] =
{
0x33, 0x26, 0xb2, 0x75, 0x8e, 0x66, 0xcf, 0x11, 0xa6, 0xd9, 0x00, 0xaa, 0x00, 0x62, 0xce, 0x6c
};
static unsigned char AsfExtendedContentDescObject[16] =
{
0x40, 0xa4, 0xd0, 0xd2, 0x07, 0xe3, 0xd2, 0x11, 0x97, 0xf0, 0x0, 0xa0, 0xc9, 0x5e, 0xa8, 0x50
};
static unsigned short WM_AlbumTitle[13] =
{
'W', 'M', '/', 'A', 'l', 'b', 'u', 'm', 'T', 'i', 't', 'l', 'e'
};
static unsigned short WM_Genre[8] =
{
'W', 'M', '/', 'G', 'e', 'n', 'r', 'e'
};
int AP_FileSeek(AP_FILE *fhandle, long offset, int mode)
{
return FSFileSeek((AP_FILE *)fhandle, offset, mode);
}
int AP_FileRead(unsigned char *buffer, long cbLen, AP_FILE *fhandle)
{
return FSFileRead(buffer, cbLen, (AP_FILE *)fhandle);
}
int WMALoadExtendedContentDescObject(unsigned char* pObject, long currPacketOffset, long cbObject, WMA_ID3 *id3)
{
long cbWanted;
short cDescriptors = 0;
short cbName, data_type, cbValue;
long iCurrFileOffset;
long iMaxFileOffset;
int i;
//assert (cbSize >= MIN_OBJECT_SIZE);
iCurrFileOffset = currPacketOffset;
iMaxFileOffset = iCurrFileOffset + cbObject - MIN_OBJECT_SIZE;
// Get descriptor count
cbWanted = sizeof(short);
if (iCurrFileOffset + cbWanted > iMaxFileOffset)
{
return AP_FAIL;
}
cDescriptors = LOAD_WORD(pObject + iCurrFileOffset);
iCurrFileOffset += cbWanted;
// Read in each descriptor record
for (i = 0; i < cDescriptors; i++)
{
int fAlbumFind = 0;
int fGenreFind = 0;
// Load in descriptor name length
cbWanted = sizeof(short);
if (iCurrFileOffset + cbWanted > iMaxFileOffset)
{
return AP_FAIL;
}
cbName = LOAD_WORD(pObject + iCurrFileOffset);
iCurrFileOffset += cbWanted;
// Load in descriptor name
if (0 == memcmp(WM_AlbumTitle, pObject + iCurrFileOffset, sizeof(WM_AlbumTitle)))
{
fAlbumFind = 1; // 找到AlbumTitle,然后读出AlbumTitle
}
else if (0 == memcmp(WM_Genre, pObject + iCurrFileOffset, sizeof(WM_Genre)))
{
fGenreFind = 1; // 找到Genre 信息,
}
iCurrFileOffset += cbName;
// Load in descriptor value type, and descriptor value length
cbWanted = 2 * sizeof(short);
if (iCurrFileOffset + cbWanted > iMaxFileOffset)
{
return AP_FAIL;
}
data_type = LOAD_WORD(pObject + iCurrFileOffset);
cbValue = LOAD_WORD(pObject + iCurrFileOffset + sizeof(short));
iCurrFileOffset += cbWanted;
// Load in descriptor value
if (ECD_STRING == data_type)
{
if (fAlbumFind)
{
cbWanted = cbValue > MAX_STRING_SIZE_CHAR ? MAX_STRING_SIZE_CHAR : cbValue;
memcpy(id3->Album, pObject + iCurrFileOffset, cbWanted);
cbWanted >>= 1; // char to wchar, so /2
id3->Album[cbWanted-1] = 0; // null
if (fGenreFind)
break;
}
else if (fGenreFind)
{
cbWanted = cbValue > MAX_STRING_SIZE_CHAR ? MAX_STRING_SIZE_CHAR : cbValue;
memcpy(id3->Genre, pObject + iCurrFileOffset, cbWanted);
cbWanted >>= 1; // char to wchar, so /2
id3->Genre[cbWanted-1] = 0; // null
if (fAlbumFind)
break;
}
}
iCurrFileOffset += cbValue;
} // for
return AP_SUCESS;
}
int WMALoadContentDescriptionObject(unsigned char* pObject, long currPacketOffset, long cbObject, WMA_ID3 *id3)
{
long iCurrFileOffset;
long iMaxFileOffset;
long cbWanted;
short title_len, author_len;
//assert (cbSize >= MIN_OBJECT_SIZE);
iCurrFileOffset = currPacketOffset;
iMaxFileOffset = iCurrFileOffset + cbObject - MIN_OBJECT_SIZE;
cbWanted = 5 * sizeof(short);
if (iCurrFileOffset + cbWanted > iMaxFileOffset)
{
return AP_FAIL;
}
title_len = LOAD_WORD(pObject + iCurrFileOffset);
author_len = LOAD_WORD(pObject + iCurrFileOffset + sizeof(short));
//copyright_len = LOAD_WORD(pData+iCurrFileOffset);
//description_len = LOAD_WORD(pData+iCurrFileOffset);
//rating_len = LOAD_WORD(pData+iCurrFileOffset);
iCurrFileOffset += cbWanted;
// Get Title
cbWanted = title_len > MAX_STRING_SIZE_CHAR ? MAX_STRING_SIZE_CHAR : title_len;
memcpy(id3->Title, pObject + iCurrFileOffset, cbWanted);
cbWanted >>= 1; // char to wchar, so /2
id3->Title[cbWanted-1] = 0; // null
iCurrFileOffset += title_len;
// Get Author
cbWanted = author_len > MAX_STRING_SIZE_CHAR ? MAX_STRING_SIZE_CHAR : author_len;
memcpy(id3->Author, pObject + iCurrFileOffset, cbWanted);
cbWanted >>= 1;
id3->Author[cbWanted-1] = 0; // null
//assert(iCurrFileOffset == iMaxFileOffset);
return AP_SUCESS;
}
#if 1
// 一次性打头文件都读出来
int WMAParseAsfHeader(AP_FILE *fhandle, WMA_ID3 *id3)
{
int wmarc;
unsigned char *pObjId;
unsigned char hdrObj[30];
long objSize;
long currPacketOffset, cbHeader, cbFirstPacketOffset;
unsigned char *pHeader;
int ContentOK = 0;
//memset(id3, 0, sizeof(WMA_ID3));
/* initialize the some state */
currPacketOffset = 0;
/* ASF Header Object */
AP_FileRead(hdrObj, 30, (AP_FILE*)fhandle);
if (0 != memcmp(AsfHeaderObjectV0, hdrObj, 16))
{
return AP_FAIL;
}
currPacketOffset += 16;
cbHeader = LOAD_DWORD(&hdrObj[currPacketOffset]);
cbFirstPacketOffset = cbHeader + DATA_OBJECT_SIZE;
currPacketOffset = 30;
pHeader = (unsigned char*)malloc(cbHeader);
if (0 == pHeader)
{
return AP_FAIL;
}
AP_FileRead(pHeader + currPacketOffset, cbHeader - currPacketOffset, (AP_FILE*)fhandle);
/* Scan Header Objects */
while (currPacketOffset < cbHeader)
{
if (ContentOK >= 2)
{
break; // 表示已经得到了ID3信息,没必要再继续解析
}
pObjId = pHeader + currPacketOffset;
objSize = LOAD_DWORD(pObjId + 16);
currPacketOffset += MIN_OBJECT_SIZE;
if (0 == memcmp(AsfContentDescriptionObjectV0, pObjId, 16))
{
if (currPacketOffset + (objSize - MIN_OBJECT_SIZE) > cbFirstPacketOffset)
{
return AP_FAIL;
}
wmarc = WMALoadContentDescriptionObject(pHeader, currPacketOffset, objSize, id3);
if (AP_SUCESS != wmarc)
{
return AP_FAIL;
}
currPacketOffset += objSize - MIN_OBJECT_SIZE;
ContentOK += 1;
}
else if (0 == memcmp(AsfExtendedContentDescObject, pObjId, 16))
{
if (currPacketOffset + (objSize - MIN_OBJECT_SIZE) > cbFirstPacketOffset)
{
return AP_FAIL;
}
wmarc = WMALoadExtendedContentDescObject(pHeader, currPacketOffset, objSize, id3);
if (AP_SUCESS != wmarc)
{
return AP_FAIL;
}
currPacketOffset += objSize - MIN_OBJECT_SIZE;
ContentOK += 1;
}
else
{
/* skip over this object */
currPacketOffset += objSize - MIN_OBJECT_SIZE;
}
}
if (0 != pHeader)
{
free(pHeader);
}
return AP_SUCESS;
}
#else
// 需要多少时读多少的内容
int WMAParseAsfHeader(AP_FILE *fhandle, WMA_ID3 *id3)
{
int wmarc;
unsigned char *pObjId;
unsigned char hdrObj[30];
long objSize;
long currPacketOffset, cbHeader, cbFirstPacketOffset;
unsigned char *pHeader;
int ContentOK = 0;
memset(id3, 0, sizeof(ID3));
/* initialize the some state */
currPacketOffset = 0;
/* ASF Header Object */
AP_FileRead(hdrObj, 30, (AP_FILE*)fhandle);
if (0 != memcmp(AsfHeaderObjectV0, hdrObj, 16))
{
return AP_FAIL;
}
currPacketOffset += 16;
cbHeader = LOAD_DWORD(&hdrObj[currPacketOffset]);
cbFirstPacketOffset = cbHeader + DATA_OBJECT_SIZE;
currPacketOffset = 30;
pHeader = (unsigned char*)malloc(cbHeader);
if (0 == pHeader)
{
return AP_FAIL;
}
/* Scan Header Objects */
while (currPacketOffset < cbHeader)
{
if (ContentOK >= 2)
{
break; // 表示已经得到了ID3信息,没必要再继续解析
}
AP_FileSeek((AP_FILE*)fhandle, currPacketOffset, SEEK_SET);
AP_FileRead(pHeader + currPacketOffset, MIN_OBJECT_SIZE, (AP_FILE*)fhandle);
pObjId = pHeader + currPacketOffset;
objSize = LOAD_DWORD(pObjId + 16);
currPacketOffset += MIN_OBJECT_SIZE;
if (0 == memcmp(AsfContentDescriptionObjectV0, pObjId, 16))
{
if (currPacketOffset + (objSize - MIN_OBJECT_SIZE) > cbFirstPacketOffset)
{
return AP_FAIL;
}
AP_FileRead(pHeader + currPacketOffset, objSize - MIN_OBJECT_SIZE, (AP_FILE*)fhandle);
wmarc = WMALoadContentDescriptionObject(pHeader, currPacketOffset, objSize, id3);
if (AP_SUCESS != wmarc)
{
return AP_FAIL;
}
currPacketOffset += objSize - MIN_OBJECT_SIZE;
ContentOK += 1;
}
else if (0 == memcmp(AsfExtendedContentDescObject, pObjId, 16))
{
if (currPacketOffset + (objSize - MIN_OBJECT_SIZE) > cbFirstPacketOffset)
{
return AP_FAIL;
}
AP_FileRead(pHeader + currPacketOffset, objSize - MIN_OBJECT_SIZE, (AP_FILE*)fhandle);
wmarc = WMALoadExtendedContentDescObject(pHeader, currPacketOffset, objSize, id3);
if (AP_SUCESS != wmarc)
{
return AP_FAIL;
}
currPacketOffset += objSize - MIN_OBJECT_SIZE;
ContentOK += 1;
}
else
{
/* skip over this object */
currPacketOffset += objSize - MIN_OBJECT_SIZE;
}
}
if (0 != pHeader)
{
free(pHeader);
}
return AP_SUCESS;
}
#endif
#endif
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -