Ok the code looks like this:
Code: Select all
#define bswapLE16(X) (X)
#define READU16(X) ((((unsigned short)((X)[0]))<<0) | \
(((unsigned short)((X)[1]))<<8) )
BOOL CSoundFile::ReadAMF(LPCBYTE lpStream, DWORD dwMemLength)
//-----------------------------------------------------------
{
AMFFILEHEADER *pfh = (AMFFILEHEADER *)lpStream;
DWORD dwMemPos;
if ((!lpStream) || (dwMemLength < 2048)) return FALSE;
if ((!strncmp((LPCTSTR)lpStream, "ASYLUM Music Format V1.0", 25)) && (dwMemLength > 4096))
{
UINT numorders, numpats, numsamples;
dwMemPos = 32;
numpats = lpStream[dwMemPos+3];
numorders = lpStream[dwMemPos+4];
numsamples = 64;
dwMemPos += 6;
if ((!numpats) || (numpats > MAX_PATTERNS) || (!numorders)
|| (numpats*64*32 + 294 + 37*64 >= dwMemLength)) return FALSE;
m_nType = MOD_TYPE_AMF0;
m_nChannels = 8;
m_nInstruments = 0;
m_nSamples = 31;
m_nDefaultTempo = 125;
m_nDefaultSpeed = 6;
for (UINT iOrd=0; iOrd<MAX_ORDERS; iOrd++)
{
Order[iOrd] = (iOrd < numorders) ? lpStream[dwMemPos+iOrd] : 0xFF;
}
dwMemPos = 294; // ???
for (UINT iSmp=0; iSmp<numsamples; iSmp++)
{
MODINSTRUMENT *psmp = &Ins[iSmp+1];
memcpy(m_szNames[iSmp+1], lpStream+dwMemPos, 22);
psmp->nFineTune = MOD2XMFineTune(lpStream[dwMemPos+22]);
psmp->nVolume = lpStream[dwMemPos+23];
psmp->nGlobalVol = 64;
if (psmp->nVolume > 0x40) psmp->nVolume = 0x40;
psmp->nVolume <<= 2;
psmp->nLength = READU32(lpStream+dwMemPos+25);
psmp->nLoopStart = READU32(lpStream+dwMemPos+29);
psmp->nLoopEnd = psmp->nLoopStart + READU32(lpStream+dwMemPos+33);
if ((psmp->nLoopEnd > psmp->nLoopStart) && (psmp->nLoopEnd <= psmp->nLength))
{
psmp->uFlags = CHN_LOOP;
} else
{
psmp->nLoopStart = psmp->nLoopEnd = 0;
}
if ((psmp->nLength) && (iSmp>31)) m_nSamples = iSmp+1;
dwMemPos += 37;
}
for (UINT iPat=0; iPat<numpats; iPat++)
{
MODCOMMAND *p = AllocatePattern(64, m_nChannels);
if (!p) break;
Patterns[iPat] = p;
PatternSize[iPat] = 64;
const UCHAR *pin = lpStream + dwMemPos;
for (UINT i=0; i<8*64; i++)
{
p->note = 0;
if (pin[0])
{
p->note = pin[0] + 13;
}
p->instr = pin[1];
p->command = pin[2];
p->param = pin[3];
if (p->command > 0x0F)
{
#ifdef AMFLOG
Log("0x%02X.0x%02X ?", p->command, p->param);
#endif
p->command = 0;
}
ConvertModCommand(p);
pin += 4;
p++;
}
dwMemPos += 64*32;
}
// Read samples
for (UINT iData=0; iData<m_nSamples; iData++)
{
MODINSTRUMENT *psmp = &Ins[iData+1];
if (psmp->nLength)
{
dwMemPos += ReadSample(psmp, RS_PCM8S, (LPCSTR)(lpStream+dwMemPos), dwMemLength);
}
}
return TRUE;
}
////////////////////////////
// DSM/AMF
USHORT *ptracks[MAX_PATTERNS];
DWORD sampleseekpos[MAX_SAMPLES];
if ((pfh->szAMF[0] != 'A') || (pfh->szAMF[1] != 'M') || (pfh->szAMF[2] != 'F')
|| (pfh->version < 10) || (pfh->version > 14) || (!bswapLE16(pfh->numtracks))
|| (!pfh->numorders) || (pfh->numorders > MAX_PATTERNS)
|| (!pfh->numsamples) || (pfh->numsamples > MAX_SAMPLES)
|| (pfh->numchannels < 4) || (pfh->numchannels > 32))
return FALSE;
memcpy(m_szNames[0], pfh->title, 32);
dwMemPos = sizeof(AMFFILEHEADER);
m_nType = MOD_TYPE_AMF;
m_nChannels = pfh->numchannels;
m_nSamples = pfh->numsamples;
m_nInstruments = 0;
// Setup Channel Pan Positions
if (pfh->version >= 11)
{
signed char *panpos = (signed char *)(lpStream + dwMemPos);
UINT nchannels = (pfh->version >= 13) ? 32 : 16;
for (UINT i=0; i<nchannels; i++)
{
int pan = (panpos[i] + 64) * 2;
if (pan < 0) pan = 0;
if (pan > 256) { pan = 128; ChnSettings[i].dwFlags |= CHN_SURROUND; }
ChnSettings[i].nPan = pan;
}
dwMemPos += nchannels;
} else
{
for (UINT i=0; i<16; i++)
{
ChnSettings[i].nPan = (lpStream[dwMemPos+i] & 1) ? 0x30 : 0xD0;
}
dwMemPos += 16;
}
// Get Tempo/Speed
m_nDefaultTempo = 125;
m_nDefaultSpeed = 6;
if (pfh->version >= 13)
{
if (lpStream[dwMemPos] >= 32) m_nDefaultTempo = lpStream[dwMemPos];
if (lpStream[dwMemPos+1] <= 32) m_nDefaultSpeed = lpStream[dwMemPos+1];
dwMemPos += 2;
}
// Setup sequence list
for (UINT iOrd=0; iOrd<MAX_ORDERS; iOrd++)
{
Order[iOrd] = 0xFF;
if (iOrd < pfh->numorders)
{
Order[iOrd] = iOrd;
PatternSize[iOrd] = 64;
if (pfh->version >= 14)
{
PatternSize[iOrd] = READU16(lpStream+dwMemPos);
dwMemPos += 2;
}
ptracks[iOrd] = (USHORT *)(lpStream+dwMemPos);
dwMemPos += m_nChannels * sizeof(USHORT);
}
}
if (dwMemPos + m_nSamples * (sizeof(AMFSAMPLE)+8) > dwMemLength) return TRUE;
// Read Samples
UINT maxsampleseekpos = 0;
for (UINT iIns=0; iIns<m_nSamples; iIns++)
{
MODINSTRUMENT *pins = &Ins[iIns+1];
AMFSAMPLE *psh = (AMFSAMPLE *)(lpStream + dwMemPos);
dwMemPos += sizeof(AMFSAMPLE);
memcpy(m_szNames[iIns+1], psh->samplename, 32);
memcpy(pins->name, psh->filename, 13);
pins->nLength = bswapLE32(psh->length);
pins->nC4Speed = bswapLE16(psh->c2spd);
pins->nGlobalVol = 64;
pins->nVolume = psh->volume * 4;
if (pfh->version >= 11)
{
pins->nLoopStart = READU32(lpStream+dwMemPos);
pins->nLoopEnd = READU32(lpStream+dwMemPos+4);
dwMemPos += 8;
} else
{
pins->nLoopStart = READU16(lpStream+dwMemPos);
pins->nLoopEnd = pins->nLength;
dwMemPos += 2;
}
sampleseekpos[iIns] = 0;
if ((psh->type) && (bswapLE32(psh->offset) < dwMemLength-1))
{
sampleseekpos[iIns] = bswapLE32(psh->offset);
if (bswapLE32(psh->offset) > maxsampleseekpos)
maxsampleseekpos = bswapLE32(psh->offset);
if ((pins->nLoopEnd > pins->nLoopStart + 2)
&& (pins->nLoopEnd <= pins->nLength)) pins->uFlags |= CHN_LOOP;
}
}
// Read Track Mapping Table
USHORT *pTrackMap = (USHORT *)(lpStream+dwMemPos);
UINT realtrackcnt = 0;
dwMemPos += pfh->numtracks * sizeof(USHORT);
for (UINT iTrkMap=0; iTrkMap<pfh->numtracks; iTrkMap++)
{
if (realtrackcnt < pTrackMap[iTrkMap]) realtrackcnt = pTrackMap[iTrkMap];
}
// Store tracks positions
BYTE **pTrackData = new BYTE *[realtrackcnt];
memset(pTrackData, 0, sizeof(pTrackData));
for (UINT iTrack=0; iTrack<realtrackcnt; iTrack++) if (dwMemPos + 3 <= dwMemLength)
{
UINT nTrkSize = READU16(lpStream+dwMemPos);
nTrkSize += (UINT)lpStream[dwMemPos+2] << 16;
if (dwMemPos + nTrkSize * 3 + 3 <= dwMemLength)
{
pTrackData[iTrack] = (BYTE *)(lpStream + dwMemPos);
}
dwMemPos += nTrkSize * 3 + 3;
}
// Create the patterns from the list of tracks
for (UINT iPat=0; iPat<pfh->numorders; iPat++)
{
MODCOMMAND *p;
p = AllocatePattern(PatternSize[iPat], m_nChannels);
if (!p) break;
Patterns[iPat] = p;
for (UINT iChn=0; iChn<m_nChannels; iChn++)
{
fprintf(stderr, "foo error\n");
UINT nTrack = bswapLE16(ptracks[iPat][iChn]);
if ((nTrack) && (nTrack <= pfh->numtracks))
{
UINT realtrk = bswapLE16(pTrackMap[nTrack-1]);
if (realtrk)
{
realtrk--;
if ((realtrk < realtrackcnt) && (pTrackData[realtrk]))
{
AMF_Unpack(p+iChn, pTrackData[realtrk], PatternSize[iPat], m_nChannels);
}
}
}
}
}
delete pTrackData;
// Read Sample Data
for (UINT iSeek=1; iSeek<=maxsampleseekpos; iSeek++)
{
if (dwMemPos >= dwMemLength) break;
for (UINT iSmp=0; iSmp<m_nSamples; iSmp++) if (iSeek == sampleseekpos[iSmp])
{
MODINSTRUMENT *pins = &Ins[iSmp+1];
dwMemPos += ReadSample(pins, RS_PCM8U, (LPCSTR)(lpStream+dwMemPos), dwMemLength-dwMemPos);
break;
}
}
return TRUE;
}
UINT nTrack = bswapLE16(ptracks[iPat][iChn]);
Well i have tried to understand whats hapenning but i have only found that the problem is with the ptracks pointer array and that the exception occurs exactly in that line :|.
And also does anyone knows how to use the psp-addr2line in a prx? Well hope anyone can help