libSceAudiodec + libSceAudiodecCpu + sceAvPlayerGetVideoData (#82)

* sceAvPlayerGetVideoData

* LongBool->Boolean

* sceAudiodecCreateDecoder + sceAudiodecDecode + sceAudiodecDeleteDecoder

* ps4_sceAudiodecCpuQueryMemSize + ps4_sceAudiodecClearContext

* sceAudiodecCpuDecode

* audiodec dir
This commit is contained in:
Kagamma 2023-02-11 20:20:31 +07:00 committed by GitHub
parent 240963aba2
commit 174b491e44
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 376 additions and 69 deletions

View File

@ -31,7 +31,7 @@
<PackageName Value="LCL"/>
</Item1>
</RequiredPackages>
<Units Count="134">
<Units Count="135">
<Unit0>
<Filename Value="fpPS4.lpr"/>
<IsPartOfProject Value="True"/>
@ -589,33 +589,37 @@
<UnitName Value="ps4_libSceSysCore"/>
</Unit127>
<Unit128>
<Filename Value="src\ps4_libsceaudiodec.pas"/>
<IsPartOfProject Value="True"/>
</Unit128>
<Unit129>
<Filename Value="src\ps4_libscevideorecording.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ps4_libSceVideoRecording"/>
</Unit129>
<Unit130>
</Unit128>
<Unit129>
<Filename Value="src\ps4_libscecontentexport.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ps4_libSceContentExport"/>
</Unit130>
<Unit131>
</Unit129>
<Unit130>
<Filename Value="src\ps4_libsceusbd.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ps4_libSceUsbd"/>
</Unit131>
<Unit132>
</Unit130>
<Unit131>
<Filename Value="src\np\ps4_libscenpcommon.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ps4_libSceNpCommon"/>
</Unit132>
<Unit133>
</Unit131>
<Unit132>
<Filename Value="src\np\np_error.pas"/>
<IsPartOfProject Value="True"/>
</Unit132>
<Unit133>
<Filename Value="src\audiodec\ps4_libsceaudiodec.pas"/>
<IsPartOfProject Value="True"/>
</Unit133>
<Unit134>
<Filename Value="src\audiodec\ps4_libsceaudiodeccpu.pas"/>
<IsPartOfProject Value="True"/>
</Unit134>
</Units>
</ProjectOptions>
<CompilerOptions>
@ -627,7 +631,7 @@
<SearchPaths>
<IncludeFiles Value="$(ProjOutDir);kernel;src\ajm;sys"/>
<Libraries Value="static"/>
<OtherUnitFiles Value="rtl;sys;vulkan;chip;spirv;kernel;src;src\ajm;src\audio;src\np;src\playgo;shaders;src\inputs;src\libcinternal;ffmpeg"/>
<OtherUnitFiles Value="rtl;sys;vulkan;chip;spirv;kernel;src;src\ajm;src\audio;src\np;src\playgo;shaders;src\inputs;src\libcinternal;ffmpeg;src\audiodec"/>
<UnitOutputDirectory Value="lib\$(TargetCPU)-$(TargetOS)"/>
</SearchPaths>
<Parsing>

View File

@ -59,6 +59,7 @@ uses
ps4_libSceVideoRecording,
ps4_libSceContentExport,
ps4_libSceUsbd,
ps4_libSceAudiodecCpu,
ps4_elf,
ps4_pthread,
ps4_program,

View File

@ -0,0 +1,277 @@
unit ps4_libSceAudiodec;
{$mode ObjFPC}{$H+}
interface
uses
hamt,
spinlock,
ps4_program;
implementation
const
SCE_AUDIODEC_TYPE_AT9 =1;
SCE_AUDIODEC_TYPE_MP3 =2;
SCE_AUDIODEC_TYPE_M4AAC=3;
SCE_AUDIODEC_ERROR_API_FAIL=$807F0000;
SCE_AUDIODEC_ERROR_INVALID_TYPE=$807F0001;
SCE_AUDIODEC_ERROR_ARG=$807F0002;
SCE_AUDIODEC_ERROR_INVALID_SIZE=$807F0003;
SCE_AUDIODEC_ERROR_INVALID_PARAM_SIZE=$807F0004;
SCE_AUDIODEC_ERROR_INVALID_BSI_INFO_SIZE=$807F0005;
SCE_AUDIODEC_ERROR_INVALID_AU_INFO_SIZE=$807F0006;
SCE_AUDIODEC_ERROR_INVALID_PCM_ITEM_SIZE=$807F0007;
SCE_AUDIODEC_ERROR_INVALID_CTRL_POINTER=$807F0008;
SCE_AUDIODEC_ERROR_INVALID_PARAM_POINTER=$807F0009;
SCE_AUDIODEC_ERROR_INVALID_BSI_INFO_POINTER=$807F000A;
SCE_AUDIODEC_ERROR_INVALID_AU_INFO_POINTER=$807F000B;
SCE_AUDIODEC_ERROR_INVALID_PCM_ITEM_POINTER=$807F000C;
SCE_AUDIODEC_ERROR_INVALID_AU_POINTER=$807F000D;
SCE_AUDIODEC_ERROR_INVALID_PCM_POINTER=$807F000E;
SCE_AUDIODEC_ERROR_INVALID_HANDLE=$807F000F;
SCE_AUDIODEC_ERROR_INVALID_WORD_LENGTH=$807F0010;
SCE_AUDIODEC_ERROR_INVALID_AU_SIZE=$807F0011;
SCE_AUDIODEC_ERROR_INVALID_PCM_SIZE=$807F0012;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_SAMPLING_FREQ=$807F0300;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_ENABLE_HEAAC=$807F0302;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_CONFIG_NUMBER=$807F0303;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_MAX_CHANNELS=$807F0304;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_ENABLE_NONDELAY_OUTPUT=$807F0305;
SCE_AUDIODEC_ERROR_M4AAC_INVALID_SURROUND_CHANNEL_INTERLEAVE_ORDER=$807F0306;
SCE_AUDIODEC_ERROR_AT9_INVALID_CONFIG_DATA=$807F1000;
type
SceAudiodecAuInfo=packed record
uiSize :DWord;
_align1 :Dword;
pAuAddr :Pointer;
uiAuSize:DWord;
_align2 :DWord;
end;
PSceAudiodecAuInfo=^SceAudiodecAuInfo;
SceAudiodecPcmItem=packed record
uiSize :DWord;
_align1 :Dword;
pPcmAddr :Pointer;
uiPcmSize:DWord;
_align2 :DWord;
end;
PSceAudiodecPcmItem=^SceAudiodecPcmItem;
SceAudiodecParam=packed record
uiSize:DWord;
// TODO: union
end;
PSceAudiodecParam=^SceAudiodecParam;
SceAudiodecBsiInfo=packed record
uiSize:DWord;
// TODO: union
end;
PSceAudiodecBsiInfo=^SceAudiodecBsiInfo;
SceAudiodecCtrl=packed record
pParam :PSceAudiodecParam;
pBsiInfo:PSceAudiodecBsiInfo;
pAuInfo :PSceAudiodecAuInfo;
pPcmItem:PSceAudiodecPcmItem;
end;
PSceAudiodecCtrl=^SceAudiodecCtrl;
SceAudiodecHandle =DWord;
PSceAudiodecHandle=^SceAudiodecHandle;
TAudioDecoderAT9=record
channels :DWord;
sampleRate :DWord;
bitRate :DWord;
configData :DWord;
superFrameRate :DWord;
framesInSuperFrame:DWord;
end;
TAudioDecoderMP3=record
channels:DWord;
end;
TAudioDecoderM4AAC=record
channels :DWord;
sampleRate:DWord;
isAdts :DWord;
isSbr :DWord;
end;
TAudioDecoderInfo=record
param :SceAudiodecParam;
bsiInfo :SceAudiodecBsiInfo;
codecType:DWord;
case Byte of
SCE_AUDIODEC_TYPE_AT9 :(at9:TAudioDecoderAT9);
SCE_AUDIODEC_TYPE_MP3 :(mp3:TAudioDecoderMP3);
SCE_AUDIODEC_TYPE_M4AAC:(aac:TAudioDecoderM4AAC);
end;
TAudioDecoder=class
handle:SceAudiodecHandle;
info :TAudioDecoderInfo;
constructor Create(const pCtrl:PSceAudiodecCtrl;const codecType:DWord);
destructor Destroy; override;
end;
var
hamt_lock :Pointer;
handleCount :QWord=0;
AudiodecHamt:TSTUB_HAMT32;
function _GetDecoder(const handle:SceAudiodecHandle):TAudioDecoder;
var
data:PPointer;
begin
Result:=nil;
spin_lock(hamt_lock);
data:=HAMT_search32(@AudiodecHamt,handle);
if (data<>nil) then
begin
Result:=TAudioDecoder(data^);
end;
spin_unlock(hamt_lock);
end;
function _AddDecoder(const decoder:TAudioDecoder):SceAudiodecHandle;
var
data:PPointer;
begin
spin_lock(hamt_lock);
Inc(handleCount);
data:=HAMT_insert32(@AudiodecHamt,handleCount,decoder);
Assert(data<>nil,'unexpected err');
data^:=decoder;
decoder.handle:=handleCount;
Result:=handleCount;
spin_unlock(hamt_lock);
end;
procedure _DeleteDecoder(const handle:SceAudiodecHandle);
begin
spin_lock(hamt_lock);
HAMT_delete32(@AudiodecHamt,handle);
spin_unlock(hamt_lock);
end;
constructor TAudioDecoder.Create(const pCtrl:PSceAudiodecCtrl;const codecType:DWord);
begin
inherited Create;
_AddDecoder(Self);
info.codecType:=codecType;
Move(pCtrl^.pParam^ ,info.param ,pCtrl^.pParam^.uiSize);
Move(pCtrl^.pBsiInfo^,info.bsiInfo,pCtrl^.pBsiInfo^.uiSize);
case codecType of
SCE_AUDIODEC_TYPE_AT9:
begin
// TODO:
end;
SCE_AUDIODEC_TYPE_MP3:
begin
// TODO:
end;
SCE_AUDIODEC_TYPE_M4AAC:
begin
// TODO:
end;
end;
end;
destructor TAudioDecoder.Destroy;
begin
_DeleteDecoder(handle);
inherited;
end;
function ps4_sceAudiodecInitLibrary(codecType:DWord):Integer; SysV_ABI_CDecl;
begin
Writeln('sceAudiodecInitLibrary,codecType=',codecType);
if not (codecType in [SCE_AUDIODEC_TYPE_AT9..SCE_AUDIODEC_TYPE_M4AAC]) then
Result:=SCE_AUDIODEC_ERROR_INVALID_TYPE
else
Result:=0;
end;
function ps4_sceAudiodecCreateDecoder(pCtrl:PSceAudiodecCtrl;uiCodecType:Dword):Integer; SysV_ABI_CDecl;
var
audioDecoder:TAudioDecoder;
begin
Writeln('sceAudiodecCreateDecoder,uiCodecType=',uiCodecType);
if pCtrl=nil then
Exit(SCE_AUDIODEC_ERROR_INVALID_CTRL_POINTER);
if pCtrl^.pParam=nil then
Exit(SCE_AUDIODEC_ERROR_INVALID_PARAM_POINTER);
if pCtrl^.pBsiInfo=nil then
Exit(SCE_AUDIODEC_ERROR_INVALID_BSI_INFO_POINTER);
case uiCodecType of
SCE_AUDIODEC_TYPE_AT9,
SCE_AUDIODEC_TYPE_MP3,
SCE_AUDIODEC_TYPE_M4AAC:
begin
audioDecoder:=TAudioDecoder.Create(pCtrl,uiCodecType);
Result:=audioDecoder.handle;
end;
else
begin
Writeln(StdErr,'ERROR: Unsupported audio decoder');
Result:=SCE_AUDIODEC_ERROR_INVALID_TYPE;
end;
end;
end;
function ps4_sceAudiodecDecode(handle:Integer;pCtrl:PSceAudiodecCtrl):Integer; SysV_ABI_CDecl;
begin
if pCtrl=nil then
Exit(-1);
//Writeln('sceAudiodecDecode,handle=',handle,',uiAuSize=',pCtrl^.pAuInfo^.uiAuSize,',uiPcmSize=',pCtrl^.pPcmItem^.uiPcmSize);
// TODO:
Result:=0;
end;
function ps4_sceAudiodecDeleteDecoder(handle:Integer):Integer; SysV_ABI_CDecl;
var
audioDecoder:TAudioDecoder;
begin
Writeln('sceAudiodecDeleteDecoder,handle=',handle);
audioDecoder:=_GetDecoder(handle);
if audioDecoder<>nil then
audioDecoder.Free;
Result:=0;
end;
function ps4_sceAudiodecClearContext(handle:Integer):Integer; SysV_ABI_CDecl;
begin
Writeln('sceAudiodecClearContext,handle=',handle);
Result:=0;
end;
function Load_libSceAudiodec(Const name:RawByteString):TElf_node;
var
lib:PLIBRARY;
begin
Result:=TElf_node.Create;
Result.pFileName:=name;
lib:=Result._add_lib('libSceAudiodec');
lib^.set_proc($56386C9B1A5C7B32,@ps4_sceAudiodecInitLibrary);
lib^.set_proc($3B77F5B0B31646FB,@ps4_sceAudiodecCreateDecoder);
lib^.set_proc($2875C73032E420BC,@ps4_sceAudiodecDecode);
lib^.set_proc($4E9F99132EBD98B9,@ps4_sceAudiodecDeleteDecoder);
lib^.set_proc($E957FD5932C3A2CB,@ps4_sceAudiodecClearContext);
end;
initialization
FillChar(AudiodecHamt,SizeOf(AudiodecHamt),0);
ps4_app.RegistredPreLoad('libSceAudiodec.prx' ,@Load_libSceAudiodec);
end.

View File

@ -0,0 +1,58 @@
unit ps4_libSceAudiodecCpu;
{$mode ObjFPC}{$H+}
interface
uses
ps4_program;
implementation
type
PSceAudiodecCpuCtrl=Pointer;
PSceAudiodecCpuResource=Pointer;
function ps4_sceAudiodecCpuQueryMemSize(pCtrl :PSceAudiodecCpuCtrl;
pRes :PSceAudiodecCpuResource;
uiCodecType:DWord):Integer; SysV_ABI_CDecl;
begin
Writeln('sceAudiodecCpuQueryMemSize,uiCodecType=',uiCodecType);
Result:=0;
end;
function ps4_sceAudiodecCpuInitDecoder(pCtrl :PSceAudiodecCpuCtrl;
pRes :PSceAudiodecCpuResource;
uiCodecType:DWord):Integer; SysV_ABI_CDecl;
begin
Writeln('sceAudiodecCpuInitDecoder,uiCodecType=',uiCodecType);
Result:=0;
end;
function ps4_sceAudiodecCpuDecode(pCtrl :PSceAudiodecCpuCtrl;
pRes :PSceAudiodecCpuResource;
uiCodecType:DWord):Integer; SysV_ABI_CDecl;
begin
// Writeln('sceAudiodecCpuDecode,uiCodecType=',uiCodecType);
Result:=0;
end;
function Load_libSceAudiodecCpu(Const name:RawByteString):TElf_node;
var
lib:PLIBRARY;
begin
Result:=TElf_node.Create;
Result.pFileName:=name;
lib:=Result._add_lib('libSceAudiodecCpu');
lib^.set_proc($92D0F6C370F81B65,@ps4_sceAudiodecCpuQueryMemSize);
lib^.set_proc($85D16CC68DCC16EF,@ps4_sceAudiodecCpuInitDecoder);
lib^.set_proc($952553896579C0B7,@ps4_sceAudiodecCpuDecode);
end;
initialization
ps4_app.RegistredPreLoad('libSceAudiodecCpu.prx',@Load_libSceAudiodecCpu);
end.

View File

@ -1,44 +0,0 @@
unit ps4_libSceAudiodec;
{$mode ObjFPC}{$H+}
interface
uses
ps4_program;
implementation
const
SCE_AUDIODEC_TYPE_AT9=1;
SCE_AUDIODEC_TYPE_MP3=2;
SCE_AUDIODEC_TYPE_M4AAC=3;
SCE_AUDIODEC_ERROR_INVALID_TYPE=$807F0001;
function ps4_sceAudiodecInitLibrary(codecType:DWord):Integer; SysV_ABI_CDecl;
begin
Writeln('sceAudiodecInitLibrary,codecType=',codecType);
if not (codecType in [SCE_AUDIODEC_TYPE_AT9..SCE_AUDIODEC_TYPE_M4AAC]) then
Result:=SCE_AUDIODEC_ERROR_INVALID_TYPE
else
Result:=0;
end;
function Load_libSceAudiodec(Const name:RawByteString):TElf_node;
var
lib:PLIBRARY;
begin
Result:=TElf_node.Create;
Result.pFileName:=name;
lib:=Result._add_lib('libSceAudiodec');
lib^.set_proc($56386C9B1A5C7B32,@ps4_sceAudiodecInitLibrary);
end;
initialization
ps4_app.RegistredPreLoad('libSceAudiodec.prx' ,@Load_libSceAudiodec);
end.

View File

@ -1032,8 +1032,7 @@ begin
_sig_unlock;
end;
// TODO: Not working correctly for Descenders?
function ps4_sceAvPlayerIsActive(handle:SceAvPlayerHandle): LongBool; SysV_ABI_CDecl;
function ps4_sceAvPlayerIsActive(handle:SceAvPlayerHandle):Boolean; SysV_ABI_CDecl;
var
player:TAvPlayerInfo;
begin
@ -1049,7 +1048,7 @@ begin
player.dec_ref;
end;
function ps4_sceAvPlayerSetLooping(handle:SceAvPlayerHandle;loopFlag:LongBool):Integer; SysV_ABI_CDecl;
function ps4_sceAvPlayerSetLooping(handle:SceAvPlayerHandle;loopFlag:Boolean):Integer; SysV_ABI_CDecl;
var
player:TAvPlayerInfo;
begin
@ -1068,7 +1067,7 @@ begin
end;
end;
function _sceAvPlayerGetAudioData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):LongBool;
function _sceAvPlayerGetAudioData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):Boolean;
var
audioData:TMemChunk;
player :TAvPlayerInfo;
@ -1103,14 +1102,14 @@ begin
end;
end;
function ps4_sceAvPlayerGetAudioData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):LongBool; SysV_ABI_CDecl;
function ps4_sceAvPlayerGetAudioData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):Boolean; SysV_ABI_CDecl;
begin
_sig_lock;
Result:=_sceAvPlayerGetAudioData(handle,frameInfo);
_sig_unlock;
end;
function _sceAvPlayerGetVideoDataEx(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfoEx):LongBool;
function _sceAvPlayerGetVideoDataEx(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfoEx):Boolean;
var
videoData:TMemChunk;
player :TAvPlayerInfo;
@ -1151,18 +1150,29 @@ begin
end;
end;
function ps4_sceAvPlayerGetVideoDataEx(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfoEx):LongBool; SysV_ABI_CDecl;
function ps4_sceAvPlayerGetVideoDataEx(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfoEx):Boolean; SysV_ABI_CDecl;
begin
_sig_lock;
Result:=_sceAvPlayerGetVideoDataEx(handle,frameInfo);
_sig_unlock;
end;
function ps4_sceAvPlayerGetVideoData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):LongBool; SysV_ABI_CDecl;
function ps4_sceAvPlayerGetVideoData(handle:SceAvPlayerHandle;frameInfo:PSceAvPlayerFrameInfo):Boolean; SysV_ABI_CDecl;
var
frameInfoEx:SceAvPlayerFrameInfoEx;
begin
Writeln(SysLogPrefix,'sceAvPlayerGetVideoData');
// TODO: Rely on ps4_sceAvPlayerGetVideoDataEx to get the frame
Result:=False;
_sig_lock;
Result:=_sceAvPlayerGetVideoDataEx(handle,@frameInfoEx);
if Result then
begin
frameInfo^.timeStamp :=frameInfoEx.timeStamp;
frameInfo^.details.video.width :=frameInfoEx.details.video.width;
frameInfo^.details.video.height :=frameInfoEx.details.video.height;
frameInfo^.details.video.aspectRatio :=frameInfoEx.details.video.aspectRatio;
frameInfo^.details.video.languageCode:=LANGUAGE_CODE_ENG;
frameInfo^.pData :=frameInfoEx.pData;
end;
_sig_unlock;
end;
function ps4_sceAvPlayerSetAvSyncMode(handle:SceAvPlayerHandle;argSyncMode:SceAvPlayerAvSyncMode):Integer; SysV_ABI_CDecl;
@ -1422,6 +1432,7 @@ begin
lib^.set_proc($51B42861AC0EB1F6,@ps4_sceAvPlayerIsActive);
lib^.set_proc($395B61B34C467E1A,@ps4_sceAvPlayerSetLooping);
lib^.set_proc($5A7A7539572B6609,@ps4_sceAvPlayerGetAudioData);
lib^.set_proc($A37F915A71D58928,@ps4_sceAvPlayerGetVideoData);
lib^.set_proc($25D92C42EF2935D4,@ps4_sceAvPlayerGetVideoDataEx);
lib^.set_proc($93FABEC4EC5D7371,@ps4_sceAvPlayerSetAvSyncMode);
lib^.set_proc($C3033DF608C57F56,@ps4_sceAvPlayerCurrentTime);