diff options
Diffstat (limited to '')
| -rw-r--r-- | src/core/hle/service/am/am.cpp | 170 | ||||
| -rw-r--r-- | src/core/hle/service/am/am.h | 1 |
2 files changed, 105 insertions, 66 deletions
diff --git a/src/core/hle/service/am/am.cpp b/src/core/hle/service/am/am.cpp index 6b1d6bf97..40922ec3a 100644 --- a/src/core/hle/service/am/am.cpp +++ b/src/core/hle/service/am/am.cpp | |||
| @@ -3,6 +3,7 @@ | |||
| 3 | // Refer to the license.txt file included. | 3 | // Refer to the license.txt file included. |
| 4 | 4 | ||
| 5 | #include <cinttypes> | 5 | #include <cinttypes> |
| 6 | #include <stack> | ||
| 6 | #include "core/file_sys/filesystem.h" | 7 | #include "core/file_sys/filesystem.h" |
| 7 | #include "core/hle/ipc_helpers.h" | 8 | #include "core/hle/ipc_helpers.h" |
| 8 | #include "core/hle/kernel/event.h" | 9 | #include "core/hle/kernel/event.h" |
| @@ -348,6 +349,87 @@ void ICommonStateGetter::GetPerformanceMode(Kernel::HLERequestContext& ctx) { | |||
| 348 | NGLOG_WARNING(Service_AM, "(STUBBED) called"); | 349 | NGLOG_WARNING(Service_AM, "(STUBBED) called"); |
| 349 | } | 350 | } |
| 350 | 351 | ||
| 352 | class IStorageAccessor final : public ServiceFramework<IStorageAccessor> { | ||
| 353 | public: | ||
| 354 | explicit IStorageAccessor(std::vector<u8> buffer) | ||
| 355 | : ServiceFramework("IStorageAccessor"), buffer(std::move(buffer)) { | ||
| 356 | static const FunctionInfo functions[] = { | ||
| 357 | {0, &IStorageAccessor::GetSize, "GetSize"}, | ||
| 358 | {10, &IStorageAccessor::Write, "Write"}, | ||
| 359 | {11, &IStorageAccessor::Read, "Read"}, | ||
| 360 | }; | ||
| 361 | RegisterHandlers(functions); | ||
| 362 | } | ||
| 363 | |||
| 364 | private: | ||
| 365 | std::vector<u8> buffer; | ||
| 366 | |||
| 367 | void GetSize(Kernel::HLERequestContext& ctx) { | ||
| 368 | IPC::ResponseBuilder rb{ctx, 4}; | ||
| 369 | |||
| 370 | rb.Push(RESULT_SUCCESS); | ||
| 371 | rb.Push(static_cast<u64>(buffer.size())); | ||
| 372 | |||
| 373 | NGLOG_DEBUG(Service_AM, "called"); | ||
| 374 | } | ||
| 375 | |||
| 376 | void Write(Kernel::HLERequestContext& ctx) { | ||
| 377 | IPC::RequestParser rp{ctx}; | ||
| 378 | |||
| 379 | const u64 offset{rp.Pop<u64>()}; | ||
| 380 | const std::vector<u8> data{ctx.ReadBuffer()}; | ||
| 381 | |||
| 382 | ASSERT(offset + data.size() <= buffer.size()); | ||
| 383 | |||
| 384 | std::memcpy(&buffer[offset], data.data(), data.size()); | ||
| 385 | |||
| 386 | IPC::ResponseBuilder rb{rp.MakeBuilder(2, 0, 0)}; | ||
| 387 | rb.Push(RESULT_SUCCESS); | ||
| 388 | |||
| 389 | NGLOG_DEBUG(Service_AM, "called, offset={}", offset); | ||
| 390 | } | ||
| 391 | |||
| 392 | void Read(Kernel::HLERequestContext& ctx) { | ||
| 393 | IPC::RequestParser rp{ctx}; | ||
| 394 | |||
| 395 | const u64 offset{rp.Pop<u64>()}; | ||
| 396 | const size_t size{ctx.GetWriteBufferSize()}; | ||
| 397 | |||
| 398 | ASSERT(offset + size <= buffer.size()); | ||
| 399 | |||
| 400 | ctx.WriteBuffer(buffer.data() + offset, size); | ||
| 401 | |||
| 402 | IPC::ResponseBuilder rb{rp.MakeBuilder(2, 0, 0)}; | ||
| 403 | rb.Push(RESULT_SUCCESS); | ||
| 404 | |||
| 405 | NGLOG_DEBUG(Service_AM, "called, offset={}", offset); | ||
| 406 | } | ||
| 407 | }; | ||
| 408 | |||
| 409 | class IStorage final : public ServiceFramework<IStorage> { | ||
| 410 | public: | ||
| 411 | explicit IStorage(std::vector<u8> buffer) | ||
| 412 | : ServiceFramework("IStorage"), buffer(std::move(buffer)) { | ||
| 413 | static const FunctionInfo functions[] = { | ||
| 414 | {0, &IStorage::Open, "Open"}, | ||
| 415 | {1, nullptr, "OpenTransferStorage"}, | ||
| 416 | }; | ||
| 417 | RegisterHandlers(functions); | ||
| 418 | } | ||
| 419 | |||
| 420 | private: | ||
| 421 | std::vector<u8> buffer; | ||
| 422 | |||
| 423 | void Open(Kernel::HLERequestContext& ctx) { | ||
| 424 | IPC::ResponseBuilder rb{ctx, 2, 0, 1}; | ||
| 425 | |||
| 426 | rb.Push(RESULT_SUCCESS); | ||
| 427 | rb.PushIpcInterface<AM::IStorageAccessor>(buffer); | ||
| 428 | |||
| 429 | NGLOG_DEBUG(Service_AM, "called"); | ||
| 430 | } | ||
| 431 | }; | ||
| 432 | |||
| 351 | class ILibraryAppletAccessor final : public ServiceFramework<ILibraryAppletAccessor> { | 433 | class ILibraryAppletAccessor final : public ServiceFramework<ILibraryAppletAccessor> { |
| 352 | public: | 434 | public: |
| 353 | explicit ILibraryAppletAccessor() : ServiceFramework("ILibraryAppletAccessor") { | 435 | explicit ILibraryAppletAccessor() : ServiceFramework("ILibraryAppletAccessor") { |
| @@ -359,7 +441,7 @@ public: | |||
| 359 | {25, nullptr, "Terminate"}, | 441 | {25, nullptr, "Terminate"}, |
| 360 | {30, nullptr, "GetResult"}, | 442 | {30, nullptr, "GetResult"}, |
| 361 | {50, nullptr, "SetOutOfFocusApplicationSuspendingEnabled"}, | 443 | {50, nullptr, "SetOutOfFocusApplicationSuspendingEnabled"}, |
| 362 | {100, nullptr, "PushInData"}, | 444 | {100, &ILibraryAppletAccessor::PushInData, "PushInData"}, |
| 363 | {101, nullptr, "PopOutData"}, | 445 | {101, nullptr, "PopOutData"}, |
| 364 | {102, nullptr, "PushExtraStorage"}, | 446 | {102, nullptr, "PushExtraStorage"}, |
| 365 | {103, nullptr, "PushInteractiveInData"}, | 447 | {103, nullptr, "PushInteractiveInData"}, |
| @@ -388,6 +470,17 @@ private: | |||
| 388 | NGLOG_WARNING(Service_AM, "(STUBBED) called"); | 470 | NGLOG_WARNING(Service_AM, "(STUBBED) called"); |
| 389 | } | 471 | } |
| 390 | 472 | ||
| 473 | void PushInData(Kernel::HLERequestContext& ctx) { | ||
| 474 | IPC::RequestParser rp{ctx}; | ||
| 475 | storage_stack.push(rp.PopIpcInterface<AM::IStorage>()); | ||
| 476 | |||
| 477 | IPC::ResponseBuilder rb{rp.MakeBuilder(2, 0, 0)}; | ||
| 478 | rb.Push(RESULT_SUCCESS); | ||
| 479 | |||
| 480 | NGLOG_DEBUG(Service_AM, "called"); | ||
| 481 | } | ||
| 482 | |||
| 483 | std::stack<std::shared_ptr<AM::IStorage>> storage_stack; | ||
| 391 | Kernel::SharedPtr<Kernel::Event> state_changed_event; | 484 | Kernel::SharedPtr<Kernel::Event> state_changed_event; |
| 392 | }; | 485 | }; |
| 393 | 486 | ||
| @@ -396,7 +489,7 @@ ILibraryAppletCreator::ILibraryAppletCreator() : ServiceFramework("ILibraryApple | |||
| 396 | {0, &ILibraryAppletCreator::CreateLibraryApplet, "CreateLibraryApplet"}, | 489 | {0, &ILibraryAppletCreator::CreateLibraryApplet, "CreateLibraryApplet"}, |
| 397 | {1, nullptr, "TerminateAllLibraryApplets"}, | 490 | {1, nullptr, "TerminateAllLibraryApplets"}, |
| 398 | {2, nullptr, "AreAnyLibraryAppletsLeft"}, | 491 | {2, nullptr, "AreAnyLibraryAppletsLeft"}, |
| 399 | {10, nullptr, "CreateStorage"}, | 492 | {10, &ILibraryAppletCreator::CreateStorage, "CreateStorage"}, |
| 400 | {11, nullptr, "CreateTransferMemoryStorage"}, | 493 | {11, nullptr, "CreateTransferMemoryStorage"}, |
| 401 | {12, nullptr, "CreateHandleStorage"}, | 494 | {12, nullptr, "CreateHandleStorage"}, |
| 402 | }; | 495 | }; |
| @@ -412,72 +505,17 @@ void ILibraryAppletCreator::CreateLibraryApplet(Kernel::HLERequestContext& ctx) | |||
| 412 | NGLOG_DEBUG(Service_AM, "called"); | 505 | NGLOG_DEBUG(Service_AM, "called"); |
| 413 | } | 506 | } |
| 414 | 507 | ||
| 415 | class IStorageAccessor final : public ServiceFramework<IStorageAccessor> { | 508 | void ILibraryAppletCreator::CreateStorage(Kernel::HLERequestContext& ctx) { |
| 416 | public: | 509 | IPC::RequestParser rp{ctx}; |
| 417 | explicit IStorageAccessor(std::vector<u8> buffer) | 510 | const u64 size{rp.Pop<u64>()}; |
| 418 | : ServiceFramework("IStorageAccessor"), buffer(std::move(buffer)) { | 511 | std::vector<u8> buffer(size); |
| 419 | static const FunctionInfo functions[] = { | ||
| 420 | {0, &IStorageAccessor::GetSize, "GetSize"}, | ||
| 421 | {10, nullptr, "Write"}, | ||
| 422 | {11, &IStorageAccessor::Read, "Read"}, | ||
| 423 | }; | ||
| 424 | RegisterHandlers(functions); | ||
| 425 | } | ||
| 426 | |||
| 427 | private: | ||
| 428 | std::vector<u8> buffer; | ||
| 429 | |||
| 430 | void GetSize(Kernel::HLERequestContext& ctx) { | ||
| 431 | IPC::ResponseBuilder rb{ctx, 4}; | ||
| 432 | |||
| 433 | rb.Push(RESULT_SUCCESS); | ||
| 434 | rb.Push(static_cast<u64>(buffer.size())); | ||
| 435 | |||
| 436 | NGLOG_DEBUG(Service_AM, "called"); | ||
| 437 | } | ||
| 438 | |||
| 439 | void Read(Kernel::HLERequestContext& ctx) { | ||
| 440 | IPC::RequestParser rp{ctx}; | ||
| 441 | |||
| 442 | u64 offset = rp.Pop<u64>(); | ||
| 443 | |||
| 444 | const size_t size{ctx.GetWriteBufferSize()}; | ||
| 445 | |||
| 446 | ASSERT(offset + size <= buffer.size()); | ||
| 447 | |||
| 448 | ctx.WriteBuffer(buffer.data() + offset, size); | ||
| 449 | |||
| 450 | IPC::ResponseBuilder rb{ctx, 2}; | ||
| 451 | |||
| 452 | rb.Push(RESULT_SUCCESS); | ||
| 453 | |||
| 454 | NGLOG_DEBUG(Service_AM, "called"); | ||
| 455 | } | ||
| 456 | }; | ||
| 457 | |||
| 458 | class IStorage final : public ServiceFramework<IStorage> { | ||
| 459 | public: | ||
| 460 | explicit IStorage(std::vector<u8> buffer) | ||
| 461 | : ServiceFramework("IStorage"), buffer(std::move(buffer)) { | ||
| 462 | static const FunctionInfo functions[] = { | ||
| 463 | {0, &IStorage::Open, "Open"}, | ||
| 464 | {1, nullptr, "OpenTransferStorage"}, | ||
| 465 | }; | ||
| 466 | RegisterHandlers(functions); | ||
| 467 | } | ||
| 468 | |||
| 469 | private: | ||
| 470 | std::vector<u8> buffer; | ||
| 471 | |||
| 472 | void Open(Kernel::HLERequestContext& ctx) { | ||
| 473 | IPC::ResponseBuilder rb{ctx, 2, 0, 1}; | ||
| 474 | 512 | ||
| 475 | rb.Push(RESULT_SUCCESS); | 513 | IPC::ResponseBuilder rb{rp.MakeBuilder(2, 0, 1)}; |
| 476 | rb.PushIpcInterface<AM::IStorageAccessor>(buffer); | 514 | rb.Push(RESULT_SUCCESS); |
| 515 | rb.PushIpcInterface<AM::IStorage>(std::move(buffer)); | ||
| 477 | 516 | ||
| 478 | NGLOG_DEBUG(Service_AM, "called"); | 517 | NGLOG_DEBUG(Service_AM, "called, size={}", size); |
| 479 | } | 518 | } |
| 480 | }; | ||
| 481 | 519 | ||
| 482 | IApplicationFunctions::IApplicationFunctions() : ServiceFramework("IApplicationFunctions") { | 520 | IApplicationFunctions::IApplicationFunctions() : ServiceFramework("IApplicationFunctions") { |
| 483 | static const FunctionInfo functions[] = { | 521 | static const FunctionInfo functions[] = { |
diff --git a/src/core/hle/service/am/am.h b/src/core/hle/service/am/am.h index ff8eb14d7..301a6c798 100644 --- a/src/core/hle/service/am/am.h +++ b/src/core/hle/service/am/am.h | |||
| @@ -121,6 +121,7 @@ public: | |||
| 121 | 121 | ||
| 122 | private: | 122 | private: |
| 123 | void CreateLibraryApplet(Kernel::HLERequestContext& ctx); | 123 | void CreateLibraryApplet(Kernel::HLERequestContext& ctx); |
| 124 | void CreateStorage(Kernel::HLERequestContext& ctx); | ||
| 124 | }; | 125 | }; |
| 125 | 126 | ||
| 126 | class IApplicationFunctions final : public ServiceFramework<IApplicationFunctions> { | 127 | class IApplicationFunctions final : public ServiceFramework<IApplicationFunctions> { |