1 // Copyright (c) 2012- PPSSPP Project.
2
3 // This program is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, version 2.0 or later versions.
6
7 // This program is distributed in the hope that it will be useful,
8 // but WITHOUT ANY WARRANTY; without even the implied warranty of
9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 // GNU General Public License 2.0 for more details.
11
12 // A copy of the GPL 2.0 should have been included with the program.
13 // If not, see http://www.gnu.org/licenses/
14
15 // Official git repository and contact information can be found at
16 // https://github.com/hrydgard/ppsspp and http://www.ppsspp.org/.
17
18 #include <algorithm>
19
20 #include "Common/Serialize/SerializeFuncs.h"
21 #include "Common/Serialize/SerializeMap.h"
22 #include "Core/HLE/HLE.h"
23 #include "Core/HLE/FunctionWrappers.h"
24 #include "Core/Reporting.h"
25 #include "Core/HLE/sceMp4.h"
26 #include "Core/HW/SimpleAudioDec.h"
27
28 static std::map<u32, AuCtx*> aacMap;
29
getAacCtx(u32 id)30 static AuCtx *getAacCtx(u32 id) {
31 if (aacMap.find(id) == aacMap.end())
32 return NULL;
33 return aacMap[id];
34 }
35
__AACShutdown()36 void __AACShutdown() {
37 for (auto it = aacMap.begin(), end = aacMap.end(); it != end; it++) {
38 delete it->second;
39 }
40 aacMap.clear();
41 }
42
__AACDoState(PointerWrap & p)43 void __AACDoState(PointerWrap &p) {
44 auto s = p.Section("sceAAC", 0, 1);
45 if (!s)
46 return;
47
48 Do(p, aacMap);
49 }
50
sceMp4Init()51 static u32 sceMp4Init()
52 {
53 INFO_LOG(ME, "sceMp4Init()");
54 return 0;
55 }
56
sceMp4Finish()57 static u32 sceMp4Finish()
58 {
59 ERROR_LOG(ME, "UNIMPL sceMp4Finish()");
60 return 0;
61 }
62
sceMp4Create(u32 mp4,u32 unknown2,u32 readBufferAddr,u32 readBufferSize)63 static u32 sceMp4Create(u32 mp4, u32 unknown2, u32 readBufferAddr, u32 readBufferSize)
64 {
65 ERROR_LOG_REPORT(ME, "UNIMPL sceMp4Create(mp4 %i,unknown2 %08x,readBufferAddr %08x,readBufferSize %i)", mp4, unknown2, readBufferAddr, readBufferSize);
66 return 0;
67 }
68
sceMp4GetNumberOfSpecificTrack()69 static u32 sceMp4GetNumberOfSpecificTrack()
70 {
71 ERROR_LOG(ME, "UNIMPL sceMp4GetNumberOfSpecificTrack()");
72 return 1;
73 }
74
sceMp4GetMovieInfo(u32 mp4,u32 unknown2)75 static u32 sceMp4GetMovieInfo(u32 mp4, u32 unknown2)
76 {
77 ERROR_LOG(ME, "UNIMPL sceMp4GetMovieInfo(mp4 %i, unknown2 %08x)",mp4, unknown2);
78 return 0;
79 }
80
sceMp4TrackSampleBufAvailableSize(u32 mp4,u32 trackAddr,u32 writableSamplesAddr,u32 writableBytesAddr)81 static u32 sceMp4TrackSampleBufAvailableSize(u32 mp4, u32 trackAddr, u32 writableSamplesAddr, u32 writableBytesAddr) {
82 return hleLogError(ME, 0, "unimplemented");
83 }
84
sceMp4Delete(u32 mp4)85 static u32 sceMp4Delete(u32 mp4) {
86 return hleLogError(ME, 0, "unimplemented");
87 }
88
sceMp4AacDecodeInitResource(int unknown)89 static u32 sceMp4AacDecodeInitResource(int unknown)
90 {
91 ERROR_LOG(ME, "UNIMPL sceMp4AacDecodeInitResource(%i)",unknown);
92 return 0;
93 }
94
sceMp4InitAu(u32 mp4,u32 unknown2,u32 auAddr)95 static u32 sceMp4InitAu(u32 mp4, u32 unknown2, u32 auAddr)
96 {
97 // unknown2 = return value of sceMpegAvcResourceGetAvcEsBuf()
98 ERROR_LOG(ME, "UNIMPL sceMp4InitAu(mp4 %i,unknown2 %08x,auAddr %08x)", mp4, unknown2, auAddr);
99 return 0;
100 }
101
sceMp4GetAvcAu(u32 mp4,u32 unknown2,u32 auAddr,u32 unknown4)102 static u32 sceMp4GetAvcAu(u32 mp4, u32 unknown2, u32 auAddr, u32 unknown4)
103 {
104 // unknown2 = return value of sceMpegAvcResourceGetAvcEsBuf()
105 ERROR_LOG(ME, "UNIMPL sceMp4InitAu(mp4 %i,unknown2 %08x,auAddr %08x,unknown4 %08x)", mp4, unknown2, auAddr, unknown4);
106 return 0;
107 }
108
109
sceMp4GetAvcTrackInfoData()110 static u32 sceMp4GetAvcTrackInfoData()
111 {
112 ERROR_LOG(ME, "UNIMPL sceMp4GetAvcTrackInfoData()");
113 return 0;
114 }
115
sceMp4TrackSampleBufConstruct(u32 mp4,u32 unknown2,u32 unknown3,u32 unknown4,u32 unknown5,u32 unknown6,u32 unknown7)116 static u32 sceMp4TrackSampleBufConstruct(u32 mp4, u32 unknown2, u32 unknown3, u32 unknown4, u32 unknown5, u32 unknown6, u32 unknown7)
117 {
118 // unknown4 == value returned by sceMp4_BCA9389C
119 ERROR_LOG(ME, "UNIMPL sceMp4TrackSampleBufConstruct(mp4 %i,unknown2 %08x,unknown3 %08x, unknown4 %08x, unknown5 %08x, unknown6 %08x, unknown7 %08x)", mp4, unknown2, unknown3, unknown4, unknown5, unknown6, unknown7);
120 return 0;
121 }
122
sceMp4TrackSampleBufQueryMemSize(u32 unknown1,u32 unknown2,u32 unknown3,u32 unknown4,u32 unknown5)123 static u32 sceMp4TrackSampleBufQueryMemSize(u32 unknown1, u32 unknown2, u32 unknown3, u32 unknown4, u32 unknown5)
124 {
125 u32 value = std::max(unknown2 * unknown3, unknown4 << 1) + (unknown2 << 6) + unknown5 + 256;
126 ERROR_LOG(ME, "sceMp4TrackSampleBufQueryMemSize return %i",value);
127 return value;
128 }
129
sceMp4AacDecode(u32 mp4,u32 auAddr,u32 bufferAddr,u32 init,u32 frequency)130 static u32 sceMp4AacDecode(u32 mp4, u32 auAddr, u32 bufferAddr, u32 init, u32 frequency)
131 {
132 // Decode audio:
133 // - init: 1 at first call, 0 afterwards
134 // - frequency: 44100
135 ERROR_LOG(ME, "sceMp4AacDecode(mp4 %i,auAddr %08x,bufferAddr %08x,init %i,frequency %i ", mp4, auAddr, bufferAddr, init, frequency);
136 return 0;
137 //This is hack
138 //return -1;
139 }
140
sceMp4GetAacAu(u32 mp4,u32 unknown2,u32 auAddr,u32 unknown4)141 static u32 sceMp4GetAacAu(u32 mp4, u32 unknown2, u32 auAddr, u32 unknown4)
142 {
143 // unknown4: pointer to a 40-bytes structure
144 ERROR_LOG(ME, "sceMp4GetAacAu(mp4 %i,unknown2 %08x,auAddr %08x,unknown4 %i ", mp4, unknown2, auAddr, unknown4);
145 return 0;
146 }
147
sceMp4GetSampleInfo()148 static u32 sceMp4GetSampleInfo()
149 {
150 ERROR_LOG(ME, "UNIMPL sceMp4GetSampleInfo()");
151 return 0;
152 }
153
sceMp4GetSampleNumWithTimeStamp()154 static u32 sceMp4GetSampleNumWithTimeStamp()
155 {
156 ERROR_LOG(ME, "UNIMPL sceMp4GetSampleNumWithTimeStamp()");
157 return 0;
158 }
159
sceMp4TrackSampleBufFlush()160 static u32 sceMp4TrackSampleBufFlush()
161 {
162 ERROR_LOG(ME, "UNIMPL sceMp4TrackSampleBufFlush()");
163 return 0;
164 }
165
sceMp4AacDecodeInit(int unknown)166 static u32 sceMp4AacDecodeInit(int unknown)
167 {
168 ERROR_LOG(ME, "UNIMPL sceMp4AacDecodeInit(%i)",unknown);
169 return 0;
170 }
171
sceMp4GetAacTrackInfoData()172 static u32 sceMp4GetAacTrackInfoData()
173 {
174 ERROR_LOG(ME, "UNIMPL sceMp4GetAacTrackInfoData()");
175 return 0;
176 }
177
sceMp4GetNumberOfMetaData()178 static u32 sceMp4GetNumberOfMetaData()
179 {
180 ERROR_LOG(ME, "UNIMPL sceMp4GetNumberOfMetaData()");
181 return 0;
182 }
183
sceMp4RegistTrack(u32 mp4,u32 unknown2,u32 unknown3,u32 callbacks,u32 unknown5)184 static u32 sceMp4RegistTrack(u32 mp4, u32 unknown2, u32 unknown3, u32 callbacks, u32 unknown5)
185 {
186 ERROR_LOG(ME, "UNIMPL sceMp4RegistTrack(mp4 %i,unknown2 %i,unknown3 %i,callbacks %i unknown5 %i)",mp4,unknown2,unknown3,callbacks,unknown5);
187 return 0;
188 }
189
sceMp4SearchSyncSampleNum()190 static u32 sceMp4SearchSyncSampleNum()
191 {
192 ERROR_LOG(ME, "UNIMPL sceMp4SearchSyncSampleNum()");
193 return 0;
194 }
195
196
197 // sceAac module starts from here
198
sceAacExit(u32 id)199 static u32 sceAacExit(u32 id)
200 {
201 INFO_LOG(ME, "sceAacExit(id %i)", id);
202 if (aacMap.find(id) != aacMap.end()) {
203 delete aacMap[id];
204 aacMap.erase(id);
205 }
206 else{
207 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
208 return -1;
209 }
210 return 0;
211 }
212
sceAacInit(u32 id)213 static u32 sceAacInit(u32 id)
214 {
215 INFO_LOG(ME, "UNIMPL sceAacInit(%08x)", id);
216 if (!Memory::IsValidAddress(id)){
217 ERROR_LOG(ME, "sceAacInit() AAC Invalid id address %08x", id);
218 return ERROR_AAC_INVALID_ADDRESS;
219 }
220
221 AuCtx *aac = new AuCtx();
222 aac->startPos = Memory::Read_U64(id); // Audio stream start position.
223 aac->endPos = Memory::Read_U32(id + 8); // Audio stream end position.
224 aac->AuBuf = Memory::Read_U32(id + 16); // Input AAC data buffer.
225 aac->AuBufSize = Memory::Read_U32(id + 20); // Input AAC data buffer size.
226 aac->PCMBuf = Memory::Read_U32(id + 24); // Output PCM data buffer.
227 aac->PCMBufSize = Memory::Read_U32(id + 28); // Output PCM data buffer size.
228 aac->freq = Memory::Read_U32(id + 32); // Frequency.
229 if (aac->AuBuf == 0 || aac->PCMBuf == 0) {
230 ERROR_LOG(ME, "sceAacInit() AAC INVALID ADDRESS AuBuf %08x PCMBuf %08x", aac->AuBuf, aac->PCMBuf);
231 delete aac;
232 return ERROR_AAC_INVALID_ADDRESS;
233 }
234 if (aac->startPos > aac->endPos) {
235 ERROR_LOG(ME, "sceAacInit() AAC INVALID startPos %lli endPos %lli", aac->startPos, aac->endPos);
236 delete aac;
237 return ERROR_AAC_INVALID_PARAMETER;
238 }
239 if (aac->AuBufSize < 8192 || aac->PCMBufSize < 8192) {
240 ERROR_LOG(ME, "sceAacInit() AAC INVALID PARAMETER, bufferSize %i outputSize %i", aac->AuBufSize, aac->PCMBufSize);
241 delete aac;
242 return ERROR_AAC_INVALID_PARAMETER;
243 }
244 if (aac->freq != 24000 && aac->freq != 32000 && aac->freq != 44100 && aac->freq != 48000) {
245 ERROR_LOG(ME, "sceAacInit() AAC INVALID freq %i", aac->freq);
246 delete aac;
247 return ERROR_AAC_INVALID_PARAMETER;
248 }
249
250 DEBUG_LOG(ME, "startPos %llx endPos %llx AuBuf %08x AuBufSize %08x PCMbuf %08x PCMbufSize %08x freq %d",
251 aac->startPos, aac->endPos, aac->AuBuf, aac->AuBufSize, aac->PCMBuf, aac->PCMBufSize, aac->freq);
252
253 aac->Channels = 2;
254 aac->MaxOutputSample = aac->PCMBufSize / 4;
255 aac->readPos = aac->startPos;
256 aac->audioType = PSP_CODEC_AAC;
257
258 // create aac decoder
259 aac->decoder = new SimpleAudio(aac->audioType);
260
261 // close the audio if id already exist.
262 if (aacMap.find(id) != aacMap.end()) {
263 delete aacMap[id];
264 aacMap.erase(id);
265 }
266 aacMap[id] = aac;
267
268 return id;
269 }
270
sceAacInitResource(u32 numberIds)271 static u32 sceAacInitResource(u32 numberIds)
272 {
273 // Do nothing here
274 INFO_LOG_REPORT(ME, "sceAacInitResource(%i)", numberIds);
275 return 0;
276 }
277
sceAacTermResource()278 static u32 sceAacTermResource()
279 {
280 ERROR_LOG(ME, "UNIMPL sceAacTermResource()");
281 return 0;
282 }
283
sceAacDecode(u32 id,u32 pcmAddr)284 static u32 sceAacDecode(u32 id, u32 pcmAddr)
285 {
286 // return the size of output pcm, <0 error
287 DEBUG_LOG(ME, "sceAacDecode(id %i, bufferAddress %08x)", id, pcmAddr);
288 auto ctx = getAacCtx(id);
289 if (!ctx) {
290 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
291 return -1;
292 }
293
294 return ctx->AuDecode(pcmAddr);
295 }
296
sceAacGetLoopNum(u32 id)297 static u32 sceAacGetLoopNum(u32 id)
298 {
299 INFO_LOG(ME, "sceAacGetLoopNum(id %i)", id);
300 auto ctx = getAacCtx(id);
301 if (!ctx) {
302 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
303 return -1;
304 }
305 return ctx->AuGetLoopNum();
306 }
307
sceAacSetLoopNum(u32 id,int loop)308 static u32 sceAacSetLoopNum(u32 id, int loop)
309 {
310 INFO_LOG(ME, "sceAacSetLoopNum(id %i,loop %d)", id, loop);
311 auto ctx = getAacCtx(id);
312 if (!ctx) {
313 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
314 return -1;
315 }
316
317 return ctx->AuSetLoopNum(loop);
318 }
319
sceAacCheckStreamDataNeeded(u32 id)320 static int sceAacCheckStreamDataNeeded(u32 id)
321 {
322 // return 1 to read more data stream, 0 don't read, <0 error
323 DEBUG_LOG(ME, "sceAacCheckStreamDataNeeded(%i)", id);
324
325 auto ctx = getAacCtx(id);
326 if (!ctx) {
327 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
328 return -1;
329 }
330
331 return ctx->AuCheckStreamDataNeeded();
332 }
333
sceAacNotifyAddStreamData(u32 id,int size)334 static u32 sceAacNotifyAddStreamData(u32 id, int size)
335 {
336 // check how many bytes we have read from source file
337 DEBUG_LOG(ME, "sceAacNotifyAddStreamData(%i, %08x)", id, size);
338
339 auto ctx = getAacCtx(id);
340 if (!ctx) {
341 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
342 return -1;
343 }
344
345 return ctx->AuNotifyAddStreamData(size);
346 }
347
sceAacGetInfoToAddStreamData(u32 id,u32 buff,u32 size,u32 srcPos)348 static u32 sceAacGetInfoToAddStreamData(u32 id, u32 buff, u32 size, u32 srcPos)
349 {
350 // read from stream position srcPos of size bytes into buff
351 DEBUG_LOG(ME, "sceAacGetInfoToAddStreamData(%08X, %08X, %08X, %08X)", id, buff, size, srcPos);
352
353 auto ctx = getAacCtx(id);
354 if (!ctx) {
355 ERROR_LOG(ME, "%s: bad aac handle %08x", __FUNCTION__, id);
356 return -1;
357 }
358
359 return ctx->AuGetInfoToAddStreamData(buff, size, srcPos);
360 }
361
sceAacGetMaxOutputSample(u32 id)362 static u32 sceAacGetMaxOutputSample(u32 id)
363 {
364 DEBUG_LOG(ME, "sceAacGetMaxOutputSample(id %i)", id);
365 auto ctx = getAacCtx(id);
366 if (!ctx) {
367 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
368 return -1;
369 }
370
371 return ctx->AuGetMaxOutputSample();
372 }
373
sceAacGetSumDecodedSample(u32 id)374 static u32 sceAacGetSumDecodedSample(u32 id)
375 {
376 DEBUG_LOG(ME, "sceAacGetSumDecodedSample(id %i)", id);
377 auto ctx = getAacCtx(id);
378 if (!ctx) {
379 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
380 return -1;
381 }
382
383 return ctx->AuGetSumDecodedSample();
384 }
385
sceAacResetPlayPosition(u32 id)386 static u32 sceAacResetPlayPosition(u32 id)
387 {
388 INFO_LOG(ME, "sceAacResetPlayPosition(id %i)", id);
389 auto ctx = getAacCtx(id);
390 if (!ctx) {
391 ERROR_LOG(ME, "%s: bad aac id %08x", __FUNCTION__, id);
392 return -1;
393 }
394
395 return ctx->AuResetPlayPosition();
396 }
397
398 const HLEFunction sceMp4[] =
399 {
400 {0X68651CBC, &WrapU_V<sceMp4Init>, "sceMp4Init", 'x', "" },
401 {0X9042B257, &WrapU_V<sceMp4Finish>, "sceMp4Finish", 'x', "" },
402 {0XB1221EE7, &WrapU_UUUU<sceMp4Create>, "sceMp4Create", 'x', "xxxx" },
403 {0X538C2057, &WrapU_U<sceMp4Delete>, "sceMp4Delete", 'x', "x" },
404 {0X113E9E7B, &WrapU_V<sceMp4GetNumberOfMetaData>, "sceMp4GetNumberOfMetaData", 'x', "" },
405 {0X7443AF1D, &WrapU_UU<sceMp4GetMovieInfo>, "sceMp4GetMovieInfo", 'x', "xx" },
406 {0X5EB65F26, &WrapU_V<sceMp4GetNumberOfSpecificTrack>, "sceMp4GetNumberOfSpecificTrack", 'x', "" },
407 {0X7ADFD01C, &WrapU_UUUUU<sceMp4RegistTrack>, "sceMp4RegistTrack", 'x', "xxxxx" },
408 {0XBCA9389C, &WrapU_UUUUU<sceMp4TrackSampleBufQueryMemSize>, "sceMp4TrackSampleBufQueryMemSize", 'x', "xxxxx" },
409 {0X9C8F4FC1, &WrapU_UUUUUUU<sceMp4TrackSampleBufConstruct>, "sceMp4TrackSampleBufConstruct", 'x', "xxxxxxx"},
410 {0X0F0187D2, &WrapU_V<sceMp4GetAvcTrackInfoData>, "sceMp4GetAvcTrackInfoData", 'x', "" },
411 {0X9CE6F5CF, &WrapU_V<sceMp4GetAacTrackInfoData>, "sceMp4GetAacTrackInfoData", 'x', "" },
412 {0X4ED4AB1E, &WrapU_I<sceMp4AacDecodeInitResource>, "sceMp4AacDecodeInitResource", 'x', "i" },
413 {0X10EE0D2C, &WrapU_I<sceMp4AacDecodeInit>, "sceMp4AacDecodeInit", 'x', "i" },
414 {0X496E8A65, &WrapU_V<sceMp4TrackSampleBufFlush>, "sceMp4TrackSampleBufFlush", 'x', "" },
415 {0XB4B400D1, &WrapU_V<sceMp4GetSampleNumWithTimeStamp>, "sceMp4GetSampleNumWithTimeStamp", 'x', "" },
416 {0XF7C51EC1, &WrapU_V<sceMp4GetSampleInfo>, "sceMp4GetSampleInfo", 'x', "" },
417 {0X74A1CA3E, &WrapU_V<sceMp4SearchSyncSampleNum>, "sceMp4SearchSyncSampleNum", 'x', "" },
418 {0XD8250B75, nullptr, "sceMp4PutSampleNum", '?', "" },
419 {0X8754ECB8, &WrapU_UUUU<sceMp4TrackSampleBufAvailableSize>, "sceMp4TrackSampleBufAvailableSize", 'x', "xppp" },
420 {0X31BCD7E0, nullptr, "sceMp4TrackSampleBufPut", '?', "" },
421 {0X5601A6F0, &WrapU_UUUU<sceMp4GetAacAu>, "sceMp4GetAacAu", 'x', "xxxx" },
422 {0X7663CB5C, &WrapU_UUUUU<sceMp4AacDecode>, "sceMp4AacDecode", 'x', "xxxxx" },
423 {0X503A3CBA, &WrapU_UUUU<sceMp4GetAvcAu>, "sceMp4GetAvcAu", 'x', "xxxx" },
424 {0X01C76489, nullptr, "sceMp4TrackSampleBufDestruct", '?', "" },
425 {0X6710FE77, nullptr, "sceMp4UnregistTrack", '?', "" },
426 {0X5D72B333, nullptr, "sceMp4AacDecodeExit", '?', "" },
427 {0X7D332394, nullptr, "sceMp4AacDecodeTermResource", '?', "" },
428 {0X131BDE57, &WrapU_UUU<sceMp4InitAu>, "sceMp4InitAu", 'x', "xxx" },
429 {0X17EAA97D, nullptr, "sceMp4GetAvcAuWithoutSampleBuf", '?', "" },
430 {0X28CCB940, nullptr, "sceMp4GetTrackEditList", '?', "" },
431 {0X3069C2B5, nullptr, "sceMp4GetAvcParamSet", '?', "" },
432 {0XD2AC9A7E, nullptr, "sceMp4GetMetaData", '?', "" },
433 {0X4FB5B756, nullptr, "sceMp4GetMetaDataInfo", '?', "" },
434 {0X427BEF7F, nullptr, "sceMp4GetTrackNumOfEditList", '?', "" },
435 {0X532029B8, nullptr, "sceMp4GetAacAuWithoutSampleBuf", '?', "" },
436 {0XA6C724DC, nullptr, "sceMp4GetSampleNum", '?', "" },
437 {0X3C2183C7, nullptr, "mp4msv_3C2183C7", '?', "" },
438 {0X9CA13D1A, nullptr, "mp4msv_9CA13D1A", '?', "" },
439 };
440
441 // 395
442 const HLEFunction sceAac[] = {
443 {0XE0C89ACA, &WrapU_U<sceAacInit>, "sceAacInit", 'x', "x" },
444 {0X33B8C009, &WrapU_U<sceAacExit>, "sceAacExit", 'x', "x" },
445 {0X5CFFC57C, &WrapU_U<sceAacInitResource>, "sceAacInitResource", 'x', "x" },
446 {0X23D35CAE, &WrapU_V<sceAacTermResource>, "sceAacTermResource", 'x', "" },
447 {0X7E4CFEE4, &WrapU_UU<sceAacDecode>, "sceAacDecode", 'x', "xx" },
448 {0X523347D9, &WrapU_U<sceAacGetLoopNum>, "sceAacGetLoopNum", 'x', "x" },
449 {0XBBDD6403, &WrapU_UI<sceAacSetLoopNum>, "sceAacSetLoopNum", 'x', "xi" },
450 {0XD7C51541, &WrapI_U<sceAacCheckStreamDataNeeded>, "sceAacCheckStreamDataNeeded", 'i', "x" },
451 {0XAC6DCBE3, &WrapU_UI<sceAacNotifyAddStreamData>, "sceAacNotifyAddStreamData", 'x', "xi" },
452 {0X02098C69, &WrapU_UUUU<sceAacGetInfoToAddStreamData>, "sceAacGetInfoToAddStreamData", 'x', "xxxx" },
453 {0X6DC7758A, &WrapU_U<sceAacGetMaxOutputSample>, "sceAacGetMaxOutputSample", 'x', "x" },
454 {0X506BF66C, &WrapU_U<sceAacGetSumDecodedSample>, "sceAacGetSumDecodedSample", 'x', "x" },
455 {0XD2DA2BBA, &WrapU_U<sceAacResetPlayPosition>, "sceAacResetPlayPosition", 'x', "x" },
456 };
457
Register_sceMp4()458 void Register_sceMp4()
459 {
460 RegisterModule("sceMp4", ARRAY_SIZE(sceMp4), sceMp4);
461 RegisterModule("sceAac", ARRAY_SIZE(sceAac), sceAac);
462 }
463