mirror of
https://github.com/shadps4-emu/shadPS4.git
synced 2025-08-03 16:02:26 +00:00
Merge remote-tracking branch 'upstream/main' into fs-cleanup
This commit is contained in:
commit
2f91016345
@ -9,29 +9,29 @@
|
|||||||
|
|
||||||
namespace Libraries::DiscMap {
|
namespace Libraries::DiscMap {
|
||||||
|
|
||||||
int PS4_SYSV_ABI sceDiscMapGetPackageSize() {
|
int PS4_SYSV_ABI sceDiscMapGetPackageSize(s64 fflags, int* ret1, int* ret2) {
|
||||||
LOG_WARNING(Lib_DiscMap, "(DUMMY) called");
|
|
||||||
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
||||||
}
|
}
|
||||||
|
|
||||||
int PS4_SYSV_ABI sceDiscMapIsRequestOnHDD() {
|
int PS4_SYSV_ABI sceDiscMapIsRequestOnHDD(char* path, s64 offset, s64 nbytes, int* ret) {
|
||||||
LOG_WARNING(Lib_DiscMap, "(DUMMY) called");
|
|
||||||
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
||||||
}
|
}
|
||||||
|
|
||||||
int PS4_SYSV_ABI Func_7C980FFB0AA27E7A() {
|
int PS4_SYSV_ABI Func_7C980FFB0AA27E7A(char* path, s64 offset, s64 nbytes, int* flags, int* ret1,
|
||||||
LOG_ERROR(Lib_DiscMap, "(STUBBED) called");
|
int* ret2) {
|
||||||
|
*flags = 0;
|
||||||
|
*ret1 = 0;
|
||||||
|
*ret2 = 0;
|
||||||
return ORBIS_OK;
|
return ORBIS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
int PS4_SYSV_ABI Func_8A828CAEE7EDD5E9() {
|
int PS4_SYSV_ABI Func_8A828CAEE7EDD5E9(char* path, s64 offset, s64 nbytes, int* flags, int* ret1,
|
||||||
LOG_ERROR(Lib_DiscMap, "(STUBBED) called");
|
int* ret2) {
|
||||||
return ORBIS_OK;
|
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
||||||
}
|
}
|
||||||
|
|
||||||
int PS4_SYSV_ABI Func_E7EBCE96E92F91F8() {
|
int PS4_SYSV_ABI Func_E7EBCE96E92F91F8() {
|
||||||
LOG_ERROR(Lib_DiscMap, "(STUBBED) called");
|
return ORBIS_DISC_MAP_ERROR_NO_BITMAP_INFO;
|
||||||
return ORBIS_OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void RegisterlibSceDiscMap(Core::Loader::SymbolsResolver* sym) {
|
void RegisterlibSceDiscMap(Core::Loader::SymbolsResolver* sym) {
|
||||||
|
@ -10,10 +10,12 @@ class SymbolsResolver;
|
|||||||
}
|
}
|
||||||
namespace Libraries::DiscMap {
|
namespace Libraries::DiscMap {
|
||||||
|
|
||||||
int PS4_SYSV_ABI sceDiscMapGetPackageSize();
|
int PS4_SYSV_ABI sceDiscMapGetPackageSize(s64 fflags, int* ret1, int* ret2);
|
||||||
int PS4_SYSV_ABI sceDiscMapIsRequestOnHDD();
|
int PS4_SYSV_ABI sceDiscMapIsRequestOnHDD(char* path, s64 offset, s64 nbytes, int* ret);
|
||||||
int PS4_SYSV_ABI Func_7C980FFB0AA27E7A();
|
int PS4_SYSV_ABI Func_7C980FFB0AA27E7A(char* path, s64 offset, s64 nbytes, int* flags, int* ret1,
|
||||||
int PS4_SYSV_ABI Func_8A828CAEE7EDD5E9();
|
int* ret2);
|
||||||
|
int PS4_SYSV_ABI Func_8A828CAEE7EDD5E9(char* path, s64 offset, s64 nbytes, int* flags, int* ret1,
|
||||||
|
int* ret2);
|
||||||
int PS4_SYSV_ABI Func_E7EBCE96E92F91F8();
|
int PS4_SYSV_ABI Func_E7EBCE96E92F91F8();
|
||||||
|
|
||||||
void RegisterlibSceDiscMap(Core::Loader::SymbolsResolver* sym);
|
void RegisterlibSceDiscMap(Core::Loader::SymbolsResolver* sym);
|
||||||
|
@ -115,6 +115,7 @@ void InitHLELibs(Core::Loader::SymbolsResolver* sym) {
|
|||||||
Libraries::NpParty::RegisterlibSceNpParty(sym);
|
Libraries::NpParty::RegisterlibSceNpParty(sym);
|
||||||
Libraries::Zlib::RegisterlibSceZlib(sym);
|
Libraries::Zlib::RegisterlibSceZlib(sym);
|
||||||
Libraries::Hmd::RegisterlibSceHmd(sym);
|
Libraries::Hmd::RegisterlibSceHmd(sym);
|
||||||
|
Libraries::DiscMap::RegisterlibSceDiscMap(sym);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace Libraries
|
} // namespace Libraries
|
||||||
|
@ -289,13 +289,12 @@ void Emulator::Run(const std::filesystem::path& file, const std::vector<std::str
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Emulator::LoadSystemModules(const std::string& game_serial) {
|
void Emulator::LoadSystemModules(const std::string& game_serial) {
|
||||||
constexpr std::array<SysModules, 11> ModulesToLoad{
|
constexpr std::array<SysModules, 10> ModulesToLoad{
|
||||||
{{"libSceNgs2.sprx", &Libraries::Ngs2::RegisterlibSceNgs2},
|
{{"libSceNgs2.sprx", &Libraries::Ngs2::RegisterlibSceNgs2},
|
||||||
{"libSceUlt.sprx", nullptr},
|
{"libSceUlt.sprx", nullptr},
|
||||||
{"libSceJson.sprx", nullptr},
|
{"libSceJson.sprx", nullptr},
|
||||||
{"libSceJson2.sprx", nullptr},
|
{"libSceJson2.sprx", nullptr},
|
||||||
{"libSceLibcInternal.sprx", &Libraries::LibcInternal::RegisterlibSceLibcInternal},
|
{"libSceLibcInternal.sprx", &Libraries::LibcInternal::RegisterlibSceLibcInternal},
|
||||||
{"libSceDiscMap.sprx", &Libraries::DiscMap::RegisterlibSceDiscMap},
|
|
||||||
{"libSceRtc.sprx", &Libraries::Rtc::RegisterlibSceRtc},
|
{"libSceRtc.sprx", &Libraries::Rtc::RegisterlibSceRtc},
|
||||||
{"libSceCesCs.sprx", nullptr},
|
{"libSceCesCs.sprx", nullptr},
|
||||||
{"libSceFont.sprx", nullptr},
|
{"libSceFont.sprx", nullptr},
|
||||||
|
@ -726,20 +726,39 @@ Liverpool::Task Liverpool::ProcessGraphics(std::span<const u32> dcb, std::span<c
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <bool is_indirect>
|
template <bool is_indirect>
|
||||||
Liverpool::Task Liverpool::ProcessCompute(std::span<const u32> acb, u32 vqid) {
|
Liverpool::Task Liverpool::ProcessCompute(const u32* acb, u32 acb_dwords, u32 vqid) {
|
||||||
FIBER_ENTER(acb_task_name[vqid]);
|
FIBER_ENTER(acb_task_name[vqid]);
|
||||||
const auto& queue = asc_queues[{vqid}];
|
auto& queue = asc_queues[{vqid}];
|
||||||
|
|
||||||
auto base_addr = reinterpret_cast<uintptr_t>(acb.data());
|
auto base_addr = reinterpret_cast<VAddr>(acb);
|
||||||
while (!acb.empty()) {
|
while (acb_dwords > 0) {
|
||||||
const auto* header = reinterpret_cast<const PM4Header*>(acb.data());
|
auto* header = reinterpret_cast<const PM4Header*>(acb);
|
||||||
const u32 type = header->type;
|
u32 next_dw_off = header->type3.NumWords() + 1;
|
||||||
if (type != 3) {
|
|
||||||
// No other types of packets were spotted so far
|
// If we have a buffered packet, use it.
|
||||||
UNREACHABLE_MSG("Invalid PM4 type {}", type);
|
if (queue.tmp_dwords > 0) [[unlikely]] {
|
||||||
|
header = reinterpret_cast<const PM4Header*>(queue.tmp_packet.data());
|
||||||
|
next_dw_off = header->type3.NumWords() + 1 - queue.tmp_dwords;
|
||||||
|
std::memcpy(queue.tmp_packet.data() + queue.tmp_dwords, acb, next_dw_off * sizeof(u32));
|
||||||
|
queue.tmp_dwords = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If the packet is split across ring boundary, buffer until next submission
|
||||||
|
if (next_dw_off > acb_dwords) [[unlikely]] {
|
||||||
|
std::memcpy(queue.tmp_packet.data(), acb, acb_dwords * sizeof(u32));
|
||||||
|
queue.tmp_dwords = acb_dwords;
|
||||||
|
if constexpr (!is_indirect) {
|
||||||
|
*queue.read_addr += acb_dwords;
|
||||||
|
*queue.read_addr %= queue.ring_size_dw;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (header->type != 3) {
|
||||||
|
// No other types of packets were spotted so far
|
||||||
|
UNREACHABLE_MSG("Invalid PM4 type {}", header->type.Value());
|
||||||
}
|
}
|
||||||
|
|
||||||
const u32 count = header->type3.NumWords();
|
|
||||||
const PM4ItOpcode opcode = header->type3.opcode;
|
const PM4ItOpcode opcode = header->type3.opcode;
|
||||||
const auto* it_body = reinterpret_cast<const u32*>(header) + 1;
|
const auto* it_body = reinterpret_cast<const u32*>(header) + 1;
|
||||||
switch (opcode) {
|
switch (opcode) {
|
||||||
@ -749,8 +768,8 @@ Liverpool::Task Liverpool::ProcessCompute(std::span<const u32> acb, u32 vqid) {
|
|||||||
}
|
}
|
||||||
case PM4ItOpcode::IndirectBuffer: {
|
case PM4ItOpcode::IndirectBuffer: {
|
||||||
const auto* indirect_buffer = reinterpret_cast<const PM4CmdIndirectBuffer*>(header);
|
const auto* indirect_buffer = reinterpret_cast<const PM4CmdIndirectBuffer*>(header);
|
||||||
auto task = ProcessCompute<true>(
|
auto task = ProcessCompute<true>(indirect_buffer->Address<const u32>(),
|
||||||
{indirect_buffer->Address<const u32>(), indirect_buffer->ib_size}, vqid);
|
indirect_buffer->ib_size, vqid);
|
||||||
RESUME_ASC(task, vqid);
|
RESUME_ASC(task, vqid);
|
||||||
|
|
||||||
while (!task.handle.done()) {
|
while (!task.handle.done()) {
|
||||||
@ -800,7 +819,7 @@ Liverpool::Task Liverpool::ProcessCompute(std::span<const u32> acb, u32 vqid) {
|
|||||||
}
|
}
|
||||||
case PM4ItOpcode::SetShReg: {
|
case PM4ItOpcode::SetShReg: {
|
||||||
const auto* set_data = reinterpret_cast<const PM4CmdSetData*>(header);
|
const auto* set_data = reinterpret_cast<const PM4CmdSetData*>(header);
|
||||||
const auto set_size = (count - 1) * sizeof(u32);
|
const auto set_size = (header->type3.NumWords() - 1) * sizeof(u32);
|
||||||
|
|
||||||
if (set_data->reg_offset >= 0x200 &&
|
if (set_data->reg_offset >= 0x200 &&
|
||||||
set_data->reg_offset <= (0x200 + sizeof(ComputeProgram) / 4)) {
|
set_data->reg_offset <= (0x200 + sizeof(ComputeProgram) / 4)) {
|
||||||
@ -895,14 +914,14 @@ Liverpool::Task Liverpool::ProcessCompute(std::span<const u32> acb, u32 vqid) {
|
|||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
UNREACHABLE_MSG("Unknown PM4 type 3 opcode {:#x} with count {}",
|
UNREACHABLE_MSG("Unknown PM4 type 3 opcode {:#x} with count {}",
|
||||||
static_cast<u32>(opcode), count);
|
static_cast<u32>(opcode), header->type3.NumWords());
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto packet_size_dw = header->type3.NumWords() + 1;
|
acb += next_dw_off;
|
||||||
acb = NextPacket(acb, packet_size_dw);
|
acb_dwords -= next_dw_off;
|
||||||
|
|
||||||
if constexpr (!is_indirect) {
|
if constexpr (!is_indirect) {
|
||||||
*queue.read_addr += packet_size_dw;
|
*queue.read_addr += next_dw_off;
|
||||||
*queue.read_addr %= queue.ring_size_dw;
|
*queue.read_addr %= queue.ring_size_dw;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -969,7 +988,7 @@ void Liverpool::SubmitAsc(u32 gnm_vqid, std::span<const u32> acb) {
|
|||||||
auto& queue = mapped_queues[gnm_vqid];
|
auto& queue = mapped_queues[gnm_vqid];
|
||||||
|
|
||||||
const auto vqid = gnm_vqid - 1;
|
const auto vqid = gnm_vqid - 1;
|
||||||
const auto& task = ProcessCompute(acb, vqid);
|
const auto& task = ProcessCompute(acb.data(), acb.size(), vqid);
|
||||||
{
|
{
|
||||||
std::scoped_lock lock{queue.m_access};
|
std::scoped_lock lock{queue.m_access};
|
||||||
queue.submits.emplace(task.handle);
|
queue.submits.emplace(task.handle);
|
||||||
|
@ -1496,10 +1496,13 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct AscQueueInfo {
|
struct AscQueueInfo {
|
||||||
|
static constexpr size_t Pm4BufferSize = 1024;
|
||||||
VAddr map_addr;
|
VAddr map_addr;
|
||||||
u32* read_addr;
|
u32* read_addr;
|
||||||
u32 ring_size_dw;
|
u32 ring_size_dw;
|
||||||
u32 pipe_id;
|
u32 pipe_id;
|
||||||
|
std::array<u32, Pm4BufferSize> tmp_packet;
|
||||||
|
u32 tmp_dwords;
|
||||||
};
|
};
|
||||||
Common::SlotVector<AscQueueInfo> asc_queues{};
|
Common::SlotVector<AscQueueInfo> asc_queues{};
|
||||||
|
|
||||||
@ -1541,7 +1544,7 @@ private:
|
|||||||
Task ProcessGraphics(std::span<const u32> dcb, std::span<const u32> ccb);
|
Task ProcessGraphics(std::span<const u32> dcb, std::span<const u32> ccb);
|
||||||
Task ProcessCeUpdate(std::span<const u32> ccb);
|
Task ProcessCeUpdate(std::span<const u32> ccb);
|
||||||
template <bool is_indirect = false>
|
template <bool is_indirect = false>
|
||||||
Task ProcessCompute(std::span<const u32> acb, u32 vqid);
|
Task ProcessCompute(const u32* acb, u32 acb_dwords, u32 vqid);
|
||||||
|
|
||||||
void Process(std::stop_token stoken);
|
void Process(std::stop_token stoken);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user