ES: Separate behavior of IOCtlV into separate functions
This function is exceptionally large. Everything within a switch like this also makes it quite error prone. Separating the functions out makes it easier to change a certain request implementation as well as improving code locality.
This commit is contained in:
parent
3c88c248dd
commit
ac973e61bb
|
@ -249,15 +249,101 @@ u32 ES::OpenTitleContent(u32 CFD, u64 TitleID, u16 Index)
|
||||||
IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
DEBUG_LOG(IOS_ES, "%s (0x%x)", GetDeviceName().c_str(), request.request);
|
DEBUG_LOG(IOS_ES, "%s (0x%x)", GetDeviceName().c_str(), request.request);
|
||||||
|
|
||||||
// Clear the IO buffers. Note that this is unsafe for other ioctlvs.
|
// Clear the IO buffers. Note that this is unsafe for other ioctlvs.
|
||||||
for (const auto& io_vector : request.io_vectors)
|
for (const auto& io_vector : request.io_vectors)
|
||||||
{
|
{
|
||||||
if (!request.HasInputVectorWithAddress(io_vector.address))
|
if (!request.HasInputVectorWithAddress(io_vector.address))
|
||||||
Memory::Memset(io_vector.address, 0, io_vector.size);
|
Memory::Memset(io_vector.address, 0, io_vector.size);
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (request.request)
|
switch (request.request)
|
||||||
{
|
{
|
||||||
case IOCTL_ES_ADDTICKET:
|
case IOCTL_ES_ADDTICKET:
|
||||||
|
return AddTicket(request);
|
||||||
|
case IOCTL_ES_ADDTITLESTART:
|
||||||
|
return AddTitleStart(request);
|
||||||
|
case IOCTL_ES_ADDCONTENTSTART:
|
||||||
|
return AddContentStart(request);
|
||||||
|
case IOCTL_ES_ADDCONTENTDATA:
|
||||||
|
return AddContentData(request);
|
||||||
|
case IOCTL_ES_ADDCONTENTFINISH:
|
||||||
|
return AddContentFinish(request);
|
||||||
|
case IOCTL_ES_ADDTITLEFINISH:
|
||||||
|
return AddTitleFinish(request);
|
||||||
|
case IOCTL_ES_GETDEVICEID:
|
||||||
|
return ESGetDeviceID(request);
|
||||||
|
case IOCTL_ES_GETTITLECONTENTSCNT:
|
||||||
|
return GetTitleContentsCount(request);
|
||||||
|
case IOCTL_ES_GETTITLECONTENTS:
|
||||||
|
return GetTitleContents(request);
|
||||||
|
case IOCTL_ES_OPENTITLECONTENT:
|
||||||
|
return OpenTitleContent(request);
|
||||||
|
case IOCTL_ES_OPENCONTENT:
|
||||||
|
return OpenContent(request);
|
||||||
|
case IOCTL_ES_READCONTENT:
|
||||||
|
return ReadContent(request);
|
||||||
|
case IOCTL_ES_CLOSECONTENT:
|
||||||
|
return CloseContent(request);
|
||||||
|
case IOCTL_ES_SEEKCONTENT:
|
||||||
|
return SeekContent(request);
|
||||||
|
case IOCTL_ES_GETTITLEDIR:
|
||||||
|
return GetTitleDirectory(request);
|
||||||
|
case IOCTL_ES_GETTITLEID:
|
||||||
|
return GetTitleID(request);
|
||||||
|
case IOCTL_ES_SETUID:
|
||||||
|
return SetUID(request);
|
||||||
|
case IOCTL_ES_GETTITLECNT:
|
||||||
|
return GetTitleCount(request);
|
||||||
|
case IOCTL_ES_GETTITLES:
|
||||||
|
return GetTitles(request);
|
||||||
|
case IOCTL_ES_GETVIEWCNT:
|
||||||
|
return GetViewCount(request);
|
||||||
|
case IOCTL_ES_GETVIEWS:
|
||||||
|
return GetViews(request);
|
||||||
|
case IOCTL_ES_GETTMDVIEWCNT:
|
||||||
|
return GetTMDViewCount(request);
|
||||||
|
case IOCTL_ES_GETTMDVIEWS:
|
||||||
|
return GetTMDViews(request);
|
||||||
|
case IOCTL_ES_GETCONSUMPTION:
|
||||||
|
return GetConsumption(request);
|
||||||
|
case IOCTL_ES_DELETETICKET:
|
||||||
|
return DeleteTicket(request);
|
||||||
|
case IOCTL_ES_DELETETITLECONTENT:
|
||||||
|
return DeleteTitleContent(request);
|
||||||
|
case IOCTL_ES_GETSTOREDTMDSIZE:
|
||||||
|
return GetStoredTMDSize(request);
|
||||||
|
case IOCTL_ES_GETSTOREDTMD:
|
||||||
|
return GetStoredTMD(request);
|
||||||
|
case IOCTL_ES_ENCRYPT:
|
||||||
|
return Encrypt(request);
|
||||||
|
case IOCTL_ES_DECRYPT:
|
||||||
|
return Decrypt(request);
|
||||||
|
case IOCTL_ES_LAUNCH:
|
||||||
|
return Launch(request);
|
||||||
|
case IOCTL_ES_CHECKKOREAREGION:
|
||||||
|
return CheckKoreaRegion(request);
|
||||||
|
case IOCTL_ES_GETDEVICECERT:
|
||||||
|
return GetDeviceCertificate(request);
|
||||||
|
case IOCTL_ES_SIGN:
|
||||||
|
return Sign(request);
|
||||||
|
case IOCTL_ES_GETBOOT2VERSION:
|
||||||
|
return GetBoot2Version(request);
|
||||||
|
|
||||||
|
// Unsupported functions
|
||||||
|
case IOCTL_ES_DIGETTICKETVIEW:
|
||||||
|
return DIGetTicketView(request);
|
||||||
|
case IOCTL_ES_GETOWNEDTITLECNT:
|
||||||
|
return GetOwnedTitleCount(request);
|
||||||
|
default:
|
||||||
|
request.DumpUnknown(GetDeviceName(), LogTypes::IOS);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
|
IPCCommandResult ES::AddTicket(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 3,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 3,
|
||||||
"IOCTL_ES_ADDTICKET wrong number of inputs");
|
"IOCTL_ES_ADDTICKET wrong number of inputs");
|
||||||
|
@ -266,10 +352,11 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
std::vector<u8> ticket(request.in_vectors[0].size);
|
std::vector<u8> ticket(request.in_vectors[0].size);
|
||||||
Memory::CopyFromEmu(ticket.data(), request.in_vectors[0].address, request.in_vectors[0].size);
|
Memory::CopyFromEmu(ticket.data(), request.in_vectors[0].address, request.in_vectors[0].size);
|
||||||
DiscIO::AddTicket(ticket);
|
DiscIO::AddTicket(ticket);
|
||||||
break;
|
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_ADDTITLESTART:
|
IPCCommandResult ES::AddTitleStart(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 4,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 4,
|
||||||
"IOCTL_ES_ADDTITLESTART wrong number of inputs");
|
"IOCTL_ES_ADDTITLESTART wrong number of inputs");
|
||||||
|
@ -292,10 +379,11 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
File::IOFile fp(tmd_path, "wb");
|
File::IOFile fp(tmd_path, "wb");
|
||||||
fp.WriteBytes(tmd.data(), tmd.size());
|
fp.WriteBytes(tmd.data(), tmd.size());
|
||||||
break;
|
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_ADDCONTENTSTART:
|
IPCCommandResult ES::AddContentStart(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
||||||
"IOCTL_ES_ADDCONTENTSTART wrong number of inputs");
|
"IOCTL_ES_ADDCONTENTSTART wrong number of inputs");
|
||||||
|
@ -332,7 +420,7 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
return GetDefaultReply(content_fd);
|
return GetDefaultReply(content_fd);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_ADDCONTENTDATA:
|
IPCCommandResult ES::AddContentData(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
||||||
"IOCTL_ES_ADDCONTENTDATA wrong number of inputs");
|
"IOCTL_ES_ADDCONTENTDATA wrong number of inputs");
|
||||||
|
@ -345,10 +433,10 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
u8* data_start = Memory::GetPointer(request.in_vectors[1].address);
|
u8* data_start = Memory::GetPointer(request.in_vectors[1].address);
|
||||||
u8* data_end = data_start + request.in_vectors[1].size;
|
u8* data_end = data_start + request.in_vectors[1].size;
|
||||||
m_addtitle_content_buffer.insert(m_addtitle_content_buffer.end(), data_start, data_end);
|
m_addtitle_content_buffer.insert(m_addtitle_content_buffer.end(), data_start, data_end);
|
||||||
break;
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_ADDCONTENTFINISH:
|
IPCCommandResult ES::AddContentFinish(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1,
|
||||||
"IOCTL_ES_ADDCONTENTFINISH wrong number of inputs");
|
"IOCTL_ES_ADDCONTENTFINISH wrong number of inputs");
|
||||||
|
@ -389,16 +477,16 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
fp.WriteBytes(decrypted_data.data(), decrypted_data.size());
|
fp.WriteBytes(decrypted_data.data(), decrypted_data.size());
|
||||||
|
|
||||||
m_addtitle_content_id = 0xFFFFFFFF;
|
m_addtitle_content_id = 0xFFFFFFFF;
|
||||||
break;
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_ADDTITLEFINISH:
|
IPCCommandResult ES::AddTitleFinish(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_ADDTITLEFINISH");
|
INFO_LOG(IOS_ES, "IOCTL_ES_ADDTITLEFINISH");
|
||||||
break;
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_GETDEVICEID:
|
IPCCommandResult ES::ESGetDeviceID(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETDEVICEID no io vectors");
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETDEVICEID no io vectors");
|
||||||
|
|
||||||
|
@ -408,7 +496,7 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLECONTENTSCNT:
|
IPCCommandResult ES::GetTitleContentsCount(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
||||||
|
@ -438,9 +526,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(return_value);
|
return GetDefaultReply(return_value);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLECONTENTS:
|
IPCCommandResult ES::GetTitleContents(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2,
|
||||||
"IOCTL_ES_GETTITLECONTENTS bad in buffer");
|
"IOCTL_ES_GETTITLECONTENTS bad in buffer");
|
||||||
|
@ -470,9 +557,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(return_value);
|
return GetDefaultReply(return_value);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_OPENTITLECONTENT:
|
IPCCommandResult ES::OpenTitleContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 3);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 3);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
||||||
|
@ -487,9 +573,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(CFD);
|
return GetDefaultReply(CFD);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_OPENCONTENT:
|
IPCCommandResult ES::OpenContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
||||||
|
@ -500,9 +585,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(CFD);
|
return GetDefaultReply(CFD);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_READCONTENT:
|
IPCCommandResult ES::ReadContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
||||||
|
@ -547,14 +631,13 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
}
|
}
|
||||||
|
|
||||||
DEBUG_LOG(IOS_ES,
|
DEBUG_LOG(IOS_ES,
|
||||||
"IOCTL_ES_READCONTENT: CFD %x, Address 0x%x, Size %i -> stream pos %i (Index %i)",
|
"IOCTL_ES_READCONTENT: CFD %x, Address 0x%x, Size %i -> stream pos %i (Index %i)", CFD,
|
||||||
CFD, Addr, Size, rContent.m_Position, rContent.m_Index);
|
Addr, Size, rContent.m_Position, rContent.m_Index);
|
||||||
|
|
||||||
return GetDefaultReply(Size);
|
return GetDefaultReply(Size);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_CLOSECONTENT:
|
IPCCommandResult ES::CloseContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
||||||
|
@ -581,9 +664,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_SEEKCONTENT:
|
IPCCommandResult ES::SeekContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 3);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 3);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 0);
|
||||||
|
@ -619,9 +701,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(rContent.m_Position);
|
return GetDefaultReply(rContent.m_Position);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLEDIR:
|
IPCCommandResult ES::GetTitleDirectory(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 1);
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
||||||
|
@ -632,34 +713,34 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
sprintf(Path, "/title/%08x/%08x/data", (u32)(TitleID >> 32), (u32)TitleID);
|
sprintf(Path, "/title/%08x/%08x/data", (u32)(TitleID >> 32), (u32)TitleID);
|
||||||
|
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLEDIR: %s", Path);
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLEDIR: %s", Path);
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLEID:
|
IPCCommandResult ES::GetTitleID(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 0);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 0);
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETTITLEID no out buffer");
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETTITLEID no out buffer");
|
||||||
|
|
||||||
Memory::Write_U64(m_TitleID, request.io_vectors[0].address);
|
Memory::Write_U64(m_TitleID, request.io_vectors[0].address);
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLEID: %08x/%08x", (u32)(m_TitleID >> 32), (u32)m_TitleID);
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLEID: %08x/%08x", (u32)(m_TitleID >> 32), (u32)m_TitleID);
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_SETUID:
|
IPCCommandResult ES::SetUID(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_SETUID no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_SETUID no in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 0,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 0,
|
||||||
"IOCTL_ES_SETUID has a payload, it shouldn't");
|
"IOCTL_ES_SETUID has a payload, it shouldn't");
|
||||||
|
|
||||||
// TODO: fs permissions based on this
|
// TODO: fs permissions based on this
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_SETUID titleID: %08x/%08x", (u32)(TitleID >> 32), (u32)TitleID);
|
INFO_LOG(IOS_ES, "IOCTL_ES_SETUID titleID: %08x/%08x", (u32)(TitleID >> 32), (u32)TitleID);
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLECNT:
|
IPCCommandResult ES::GetTitleCount(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 0,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 0, "IOCTL_ES_GETTITLECNT has an in buffer");
|
||||||
"IOCTL_ES_GETTITLECNT has an in buffer");
|
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
||||||
"IOCTL_ES_GETTITLECNT has no out buffer");
|
"IOCTL_ES_GETTITLECNT has no out buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors[0].size == 4,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors[0].size == 4,
|
||||||
|
@ -671,13 +752,11 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTITLES:
|
IPCCommandResult ES::GetTitles(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETTITLES has an in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETTITLES has an in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETTITLES has no out buffer");
|
||||||
"IOCTL_ES_GETTITLES has no out buffer");
|
|
||||||
|
|
||||||
u32 MaxCount = Memory::Read_U32(request.in_vectors[0].address);
|
u32 MaxCount = Memory::Read_U32(request.in_vectors[0].address);
|
||||||
u32 Count = 0;
|
u32 Count = 0;
|
||||||
|
@ -694,9 +773,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLES: Number of titles returned %i", Count);
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETTITLES: Number of titles returned %i", Count);
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETVIEWCNT:
|
IPCCommandResult ES::GetViewCount(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETVIEWCNT no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETVIEWCNT no in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETVIEWCNT no out buffer");
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETVIEWCNT no out buffer");
|
||||||
|
@ -744,9 +822,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
Memory::Write_U32(ViewCount, request.io_vectors[0].address);
|
Memory::Write_U32(ViewCount, request.io_vectors[0].address);
|
||||||
return GetDefaultReply(retVal);
|
return GetDefaultReply(retVal);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETVIEWS:
|
IPCCommandResult ES::GetViews(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2, "IOCTL_ES_GETVIEWS no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2, "IOCTL_ES_GETVIEWS no in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETVIEWS no out buffer");
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETVIEWS no out buffer");
|
||||||
|
@ -811,18 +888,16 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETVIEWS for titleID: %08x/%08x (MaxViews = %i)",
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETVIEWS for titleID: %08x/%08x (MaxViews = %i)", (u32)(TitleID >> 32),
|
||||||
(u32)(TitleID >> 32), (u32)TitleID, maxViews);
|
(u32)TitleID, maxViews);
|
||||||
|
|
||||||
return GetDefaultReply(retVal);
|
return GetDefaultReply(retVal);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTMDVIEWCNT:
|
IPCCommandResult ES::GetTMDViewCount(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETTMDVIEWCNT no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1, "IOCTL_ES_GETTMDVIEWCNT no in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETTMDVIEWCNT no out buffer");
|
||||||
"IOCTL_ES_GETTMDVIEWCNT no out buffer");
|
|
||||||
|
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
|
|
||||||
|
@ -834,22 +909,19 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
TMDViewCnt += DiscIO::CNANDContentLoader::TMD_VIEW_SIZE;
|
TMDViewCnt += DiscIO::CNANDContentLoader::TMD_VIEW_SIZE;
|
||||||
TMDViewCnt += 2; // title version
|
TMDViewCnt += 2; // title version
|
||||||
TMDViewCnt += 2; // num entries
|
TMDViewCnt += 2; // num entries
|
||||||
TMDViewCnt +=
|
TMDViewCnt += (u32)Loader.GetContentSize() * (4 + 2 + 2 + 8); // content id, index, type, size
|
||||||
(u32)Loader.GetContentSize() * (4 + 2 + 2 + 8); // content id, index, type, size
|
|
||||||
}
|
}
|
||||||
Memory::Write_U32(TMDViewCnt, request.io_vectors[0].address);
|
Memory::Write_U32(TMDViewCnt, request.io_vectors[0].address);
|
||||||
|
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETTMDVIEWCNT: title: %08x/%08x (view size %i)",
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETTMDVIEWCNT: title: %08x/%08x (view size %i)", (u32)(TitleID >> 32),
|
||||||
(u32)(TitleID >> 32), (u32)TitleID, TMDViewCnt);
|
(u32)TitleID, TMDViewCnt);
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETTMDVIEWS:
|
IPCCommandResult ES::GetTMDViews(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2, "IOCTL_ES_GETTMDVIEWCNT no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 2, "IOCTL_ES_GETTMDVIEWCNT no in buffer");
|
||||||
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETTMDVIEWCNT no out buffer");
|
||||||
"IOCTL_ES_GETTMDVIEWCNT no out buffer");
|
|
||||||
|
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
u32 MaxCount = Memory::Read_U32(request.in_vectors[1].address);
|
u32 MaxCount = Memory::Read_U32(request.in_vectors[1].address);
|
||||||
|
@ -887,44 +959,50 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
_dbg_assert_(IOS_ES, (Address - request.io_vectors[0].address) == request.io_vectors[0].size);
|
_dbg_assert_(IOS_ES, (Address - request.io_vectors[0].address) == request.io_vectors[0].size);
|
||||||
}
|
}
|
||||||
|
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETTMDVIEWS: title: %08x/%08x (buffer size: %i)",
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETTMDVIEWS: title: %08x/%08x (buffer size: %i)", (u32)(TitleID >> 32),
|
||||||
(u32)(TitleID >> 32), (u32)TitleID, MaxCount);
|
(u32)TitleID, MaxCount);
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETCONSUMPTION: // This is at least what crediar's ES module does
|
IPCCommandResult ES::GetConsumption(const IOCtlVRequest& request)
|
||||||
|
{
|
||||||
|
// This is at least what crediar's ES module does
|
||||||
Memory::Write_U32(0, request.io_vectors[1].address);
|
Memory::Write_U32(0, request.io_vectors[1].address);
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETCONSUMPTION");
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETCONSUMPTION");
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
case IOCTL_ES_DELETETICKET:
|
IPCCommandResult ES::DeleteTicket(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_DELETETICKET: title: %08x/%08x", (u32)(TitleID >> 32), (u32)TitleID);
|
INFO_LOG(IOS_ES, "IOCTL_ES_DELETETICKET: title: %08x/%08x", (u32)(TitleID >> 32), (u32)TitleID);
|
||||||
|
|
||||||
// Presumably return -1017 when delete fails
|
// Presumably return -1017 when delete fails
|
||||||
if (!File::Delete(Common::GetTicketFileName(TitleID, Common::FROM_SESSION_ROOT)))
|
if (!File::Delete(Common::GetTicketFileName(TitleID, Common::FROM_SESSION_ROOT)))
|
||||||
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_DELETETITLECONTENT:
|
IPCCommandResult ES::DeleteTitleContent(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_DELETETITLECONTENT: title: %08x/%08x", (u32)(TitleID >> 32),
|
INFO_LOG(IOS_ES, "IOCTL_ES_DELETETITLECONTENT: title: %08x/%08x", (u32)(TitleID >> 32),
|
||||||
(u32)TitleID);
|
(u32)TitleID);
|
||||||
|
|
||||||
// Presumably return -1017 when title not installed TODO verify
|
// Presumably return -1017 when title not installed TODO verify
|
||||||
if (!DiscIO::CNANDContentManager::Access().RemoveTitle(TitleID, Common::FROM_SESSION_ROOT))
|
if (!DiscIO::CNANDContentManager::Access().RemoveTitle(TitleID, Common::FROM_SESSION_ROOT))
|
||||||
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
case IOCTL_ES_GETSTOREDTMDSIZE:
|
IPCCommandResult ES::GetStoredTMDSize(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1,
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() == 1,
|
||||||
"IOCTL_ES_GETSTOREDTMDSIZE no in buffer");
|
"IOCTL_ES_GETSTOREDTMDSIZE no in buffer");
|
||||||
// _dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_ES_GETSTOREDTMDSIZE
|
// _dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
||||||
// no out buffer");
|
// "IOCTL_ES_ES_GETSTOREDTMDSIZE no out buffer");
|
||||||
|
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
const DiscIO::CNANDContentLoader& Loader = AccessContentDevice(TitleID);
|
const DiscIO::CNANDContentLoader& Loader = AccessContentDevice(TitleID);
|
||||||
|
@ -936,22 +1014,24 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
TMDCnt += DiscIO::CNANDContentLoader::TMD_HEADER_SIZE;
|
TMDCnt += DiscIO::CNANDContentLoader::TMD_HEADER_SIZE;
|
||||||
TMDCnt += (u32)Loader.GetContentSize() * DiscIO::CNANDContentLoader::CONTENT_HEADER_SIZE;
|
TMDCnt += (u32)Loader.GetContentSize() * DiscIO::CNANDContentLoader::CONTENT_HEADER_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (request.io_vectors.size())
|
if (request.io_vectors.size())
|
||||||
Memory::Write_U32(TMDCnt, request.io_vectors[0].address);
|
Memory::Write_U32(TMDCnt, request.io_vectors[0].address);
|
||||||
|
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETSTOREDTMDSIZE: title: %08x/%08x (view size %i)",
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETSTOREDTMDSIZE: title: %08x/%08x (view size %i)",
|
||||||
(u32)(TitleID >> 32), (u32)TitleID, TMDCnt);
|
(u32)(TitleID >> 32), (u32)TitleID, TMDCnt);
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case IOCTL_ES_GETSTOREDTMD:
|
IPCCommandResult ES::GetStoredTMD(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() > 0, "IOCTL_ES_GETSTOREDTMD no in buffer");
|
_dbg_assert_msg_(IOS_ES, request.in_vectors.size() > 0, "IOCTL_ES_GETSTOREDTMD no in buffer");
|
||||||
// requires 1 inbuffer and no outbuffer, presumably outbuffer required when second inbuffer is
|
// requires 1 inbuffer and no outbuffer, presumably outbuffer required when second inbuffer is
|
||||||
// used for maxcount (allocated mem?)
|
// used for maxcount (allocated mem?)
|
||||||
// called with 1 inbuffer after deleting a titleid
|
// called with 1 inbuffer after deleting a titleid
|
||||||
//_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1, "IOCTL_ES_GETSTOREDTMD no out
|
//_dbg_assert_msg_(IOS_ES, request.io_vectors.size() == 1,
|
||||||
// buffer");
|
// "IOCTL_ES_GETSTOREDTMD no out buffer");
|
||||||
|
|
||||||
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
u64 TitleID = Memory::Read_U64(request.in_vectors[0].address);
|
||||||
u32 MaxCount = 0;
|
u32 MaxCount = 0;
|
||||||
|
@ -969,8 +1049,7 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
u32 Address = request.io_vectors[0].address;
|
u32 Address = request.io_vectors[0].address;
|
||||||
|
|
||||||
Memory::CopyToEmu(Address, Loader.GetTMDHeader(),
|
Memory::CopyToEmu(Address, Loader.GetTMDHeader(), DiscIO::CNANDContentLoader::TMD_HEADER_SIZE);
|
||||||
DiscIO::CNANDContentLoader::TMD_HEADER_SIZE);
|
|
||||||
Address += DiscIO::CNANDContentLoader::TMD_HEADER_SIZE;
|
Address += DiscIO::CNANDContentLoader::TMD_HEADER_SIZE;
|
||||||
|
|
||||||
const std::vector<DiscIO::SNANDContent>& rContent = Loader.GetContent();
|
const std::vector<DiscIO::SNANDContent>& rContent = Loader.GetContent();
|
||||||
|
@ -988,9 +1067,8 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
(u32)(TitleID >> 32), (u32)TitleID, MaxCount);
|
(u32)(TitleID >> 32), (u32)TitleID, MaxCount);
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_ENCRYPT:
|
IPCCommandResult ES::Encrypt(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
u32 keyIndex = Memory::Read_U32(request.in_vectors[0].address);
|
u32 keyIndex = Memory::Read_U32(request.in_vectors[0].address);
|
||||||
u8* IV = Memory::GetPointer(request.in_vectors[1].address);
|
u8* IV = Memory::GetPointer(request.in_vectors[1].address);
|
||||||
|
@ -1006,10 +1084,10 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
_dbg_assert_msg_(IOS_ES, keyIndex == 6,
|
_dbg_assert_msg_(IOS_ES, keyIndex == 6,
|
||||||
"IOCTL_ES_ENCRYPT: Key type is not SD, data will be crap");
|
"IOCTL_ES_ENCRYPT: Key type is not SD, data will be crap");
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_DECRYPT:
|
IPCCommandResult ES::Decrypt(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
u32 keyIndex = Memory::Read_U32(request.in_vectors[0].address);
|
u32 keyIndex = Memory::Read_U32(request.in_vectors[0].address);
|
||||||
u8* IV = Memory::GetPointer(request.in_vectors[1].address);
|
u8* IV = Memory::GetPointer(request.in_vectors[1].address);
|
||||||
|
@ -1022,10 +1100,10 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
|
|
||||||
_dbg_assert_msg_(IOS_ES, keyIndex == 6,
|
_dbg_assert_msg_(IOS_ES, keyIndex == 6,
|
||||||
"IOCTL_ES_DECRYPT: Key type is not SD, data will be crap");
|
"IOCTL_ES_DECRYPT: Key type is not SD, data will be crap");
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_LAUNCH:
|
IPCCommandResult ES::Launch(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
_dbg_assert_(IOS_ES, request.in_vectors.size() == 2);
|
_dbg_assert_(IOS_ES, request.in_vectors.size() == 2);
|
||||||
bool bSuccess = false;
|
bool bSuccess = false;
|
||||||
|
@ -1150,28 +1228,30 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
EnqueueCommandAcknowledgement(request.address, 0);
|
EnqueueCommandAcknowledgement(request.address, 0);
|
||||||
return GetNoReply();
|
return GetNoReply();
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_CHECKKOREAREGION: // note by DacoTaco : name is unknown, i just tried to name it
|
IPCCommandResult ES::CheckKoreaRegion(const IOCtlVRequest& request)
|
||||||
// SOMETHING
|
{
|
||||||
|
// note by DacoTaco : name is unknown, I just tried to name it SOMETHING.
|
||||||
// IOS70 has this to let system menu 4.2 check if the console is region changed. it returns
|
// IOS70 has this to let system menu 4.2 check if the console is region changed. it returns
|
||||||
// -1017
|
// -1017
|
||||||
// if the IOS didn't find the Korean keys and 0 if it does. 0 leads to a error 003
|
// if the IOS didn't find the Korean keys and 0 if it does. 0 leads to a error 003
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_CHECKKOREAREGION: Title checked for Korean keys.");
|
INFO_LOG(IOS_ES, "IOCTL_ES_CHECKKOREAREGION: Title checked for Korean keys.");
|
||||||
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
return GetDefaultReply(ES_PARAMETER_SIZE_OR_ALIGNMENT);
|
||||||
|
}
|
||||||
|
|
||||||
case IOCTL_ES_GETDEVICECERT: // (Input: none, Output: 384 bytes)
|
IPCCommandResult ES::GetDeviceCertificate(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
|
// (Input: none, Output: 384 bytes)
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETDEVICECERT");
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETDEVICECERT");
|
||||||
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
_dbg_assert_(IOS_ES, request.io_vectors.size() == 1);
|
||||||
u8* destination = Memory::GetPointer(request.io_vectors[0].address);
|
u8* destination = Memory::GetPointer(request.io_vectors[0].address);
|
||||||
|
|
||||||
EcWii& ec = EcWii::GetInstance();
|
EcWii& ec = EcWii::GetInstance();
|
||||||
get_ng_cert(destination, ec.getNgId(), ec.getNgKeyId(), ec.getNgPriv(), ec.getNgSig());
|
get_ng_cert(destination, ec.getNgId(), ec.getNgKeyId(), ec.getNgPriv(), ec.getNgSig());
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_SIGN:
|
IPCCommandResult ES::Sign(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_SIGN");
|
INFO_LOG(IOS_ES, "IOCTL_ES_SIGN");
|
||||||
u8* ap_cert_out = Memory::GetPointer(request.io_vectors[1].address);
|
u8* ap_cert_out = Memory::GetPointer(request.io_vectors[1].address);
|
||||||
|
@ -1182,34 +1262,30 @@ IPCCommandResult ES::IOCtlV(const IOCtlVRequest& request)
|
||||||
EcWii& ec = EcWii::GetInstance();
|
EcWii& ec = EcWii::GetInstance();
|
||||||
get_ap_sig_and_cert(sig_out, ap_cert_out, m_TitleID, data, data_size, ec.getNgPriv(),
|
get_ap_sig_and_cert(sig_out, ap_cert_out, m_TitleID, data, data_size, ec.getNgPriv(),
|
||||||
ec.getNgId());
|
ec.getNgId());
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case IOCTL_ES_GETBOOT2VERSION:
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
|
IPCCommandResult ES::GetBoot2Version(const IOCtlVRequest& request)
|
||||||
{
|
{
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETBOOT2VERSION");
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETBOOT2VERSION");
|
||||||
|
|
||||||
Memory::Write_U32(
|
// as of 26/02/2012, this was latest bootmii version
|
||||||
4, request.io_vectors[0].address); // as of 26/02/2012, this was latest bootmii version
|
Memory::Write_U32(4, request.io_vectors[0].address);
|
||||||
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
|
||||||
// ===============================================================================================
|
IPCCommandResult ES::DIGetTicketView(const IOCtlVRequest& request)
|
||||||
// unsupported functions
|
{
|
||||||
// ===============================================================================================
|
// (Input: none, Output: 216 bytes) bug crediar :D
|
||||||
case IOCTL_ES_DIGETTICKETVIEW: // (Input: none, Output: 216 bytes) bug crediar :D
|
|
||||||
WARN_LOG(IOS_ES, "IOCTL_ES_DIGETTICKETVIEW: this looks really wrong...");
|
WARN_LOG(IOS_ES, "IOCTL_ES_DIGETTICKETVIEW: this looks really wrong...");
|
||||||
break;
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
case IOCTL_ES_GETOWNEDTITLECNT:
|
IPCCommandResult ES::GetOwnedTitleCount(const IOCtlVRequest& request)
|
||||||
|
{
|
||||||
INFO_LOG(IOS_ES, "IOCTL_ES_GETOWNEDTITLECNT");
|
INFO_LOG(IOS_ES, "IOCTL_ES_GETOWNEDTITLECNT");
|
||||||
Memory::Write_U32(0, request.io_vectors[0].address);
|
Memory::Write_U32(0, request.io_vectors[0].address);
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
request.DumpUnknown(GetDeviceName(), LogTypes::IOS);
|
|
||||||
}
|
|
||||||
|
|
||||||
return GetDefaultReply(IPC_SUCCESS);
|
return GetDefaultReply(IPC_SUCCESS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -151,6 +151,44 @@ private:
|
||||||
u8 padding[0x3c];
|
u8 padding[0x3c];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
IPCCommandResult AddTicket(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult AddTitleStart(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult AddContentStart(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult AddContentData(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult AddContentFinish(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult AddTitleFinish(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult ESGetDeviceID(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitleContentsCount(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitleContents(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult OpenTitleContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult OpenContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult ReadContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult CloseContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult SeekContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitleDirectory(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitleID(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult SetUID(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitleCount(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTitles(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetViewCount(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetViews(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTMDViewCount(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetTMDViews(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetConsumption(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult DeleteTicket(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult DeleteTitleContent(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetStoredTMDSize(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetStoredTMD(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult Encrypt(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult Decrypt(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult Launch(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult CheckKoreaRegion(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetDeviceCertificate(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult Sign(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetBoot2Version(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult DIGetTicketView(const IOCtlVRequest& request);
|
||||||
|
IPCCommandResult GetOwnedTitleCount(const IOCtlVRequest& request);
|
||||||
|
|
||||||
const DiscIO::CNANDContentLoader& AccessContentDevice(u64 title_id);
|
const DiscIO::CNANDContentLoader& AccessContentDevice(u64 title_id);
|
||||||
u32 OpenTitleContent(u32 CFD, u64 TitleID, u16 Index);
|
u32 OpenTitleContent(u32 CFD, u64 TitleID, u16 Index);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue