Ejemplo n.º 1
0
void FS_USER::OpenFile(Kernel::HLERequestContext& ctx) {
    IPC::RequestParser rp(ctx, 0x0802, 7, 2);
    rp.Skip(1, false); // Transaction.

    ArchiveHandle archive_handle = rp.Pop<u64>();
    auto filename_type = rp.PopEnum<FileSys::LowPathType>();
    u32 filename_size = rp.Pop<u32>();
    FileSys::Mode mode{rp.Pop<u32>()};
    u32 attributes = rp.Pop<u32>(); // TODO(Link Mauve): do something with those attributes.
    std::vector<u8> filename = rp.PopStaticBuffer();
    ASSERT(filename.size() == filename_size);
    FileSys::Path file_path(filename_type, filename);

    LOG_DEBUG(Service_FS, "path={}, mode={} attrs={}", file_path.DebugStr(), mode.hex, attributes);

    ResultVal<std::shared_ptr<File>> file_res =
        archives.OpenFileFromArchive(archive_handle, file_path, mode);
    IPC::RequestBuilder rb = rp.MakeBuilder(1, 2);
    rb.Push(file_res.Code());
    if (file_res.Succeeded()) {
        std::shared_ptr<File> file = *file_res;
        rb.PushMoveObjects(file->Connect());
    } else {
        rb.PushMoveObjects<Kernel::Object>(nullptr);
        LOG_ERROR(Service_FS, "failed to get a handle for file {}", file_path.DebugStr());
    }
}
Ejemplo n.º 2
0
void File::OpenSubFile(Kernel::HLERequestContext& ctx) {
    IPC::RequestParser rp(ctx, 0x0801, 4, 0);
    s64 offset = rp.PopRaw<s64>();
    s64 size = rp.PopRaw<s64>();

    IPC::RequestBuilder rb = rp.MakeBuilder(1, 2);

    const FileSessionSlot* original_file = GetSessionData(ctx.Session());

    if (original_file->subfile) {
        // OpenSubFile can not be called on a file which is already as subfile
        rb.Push(FileSys::ERROR_UNSUPPORTED_OPEN_FLAGS);
        return;
    }

    if (offset < 0 || size < 0) {
        rb.Push(FileSys::ERR_WRITE_BEYOND_END);
        return;
    }

    std::size_t end = offset + size;

    // TODO(Subv): Check for overflow and return ERR_WRITE_BEYOND_END

    if (end > original_file->size) {
        rb.Push(FileSys::ERR_WRITE_BEYOND_END);
        return;
    }

    using Kernel::ClientSession;
    using Kernel::ServerSession;
    using Kernel::SharedPtr;
    auto sessions = system.Kernel().CreateSessionPair(GetName());
    auto server = std::get<SharedPtr<ServerSession>>(sessions);
    ClientConnected(server);

    FileSessionSlot* slot = GetSessionData(server);
    slot->priority = original_file->priority;
    slot->offset = offset;
    slot->size = size;
    slot->subfile = true;

    rb.Push(RESULT_SUCCESS);
    rb.PushMoveObjects(std::get<SharedPtr<ClientSession>>(sessions));
}
Ejemplo n.º 3
0
void File::OpenLinkFile(Kernel::HLERequestContext& ctx) {
    LOG_WARNING(Service_FS, "(STUBBED) File command OpenLinkFile {}", GetName());
    using Kernel::ClientSession;
    using Kernel::ServerSession;
    using Kernel::SharedPtr;
    IPC::RequestParser rp(ctx, 0x080C, 0, 0);
    IPC::RequestBuilder rb = rp.MakeBuilder(1, 2);
    auto sessions = system.Kernel().CreateSessionPair(GetName());
    auto server = std::get<SharedPtr<ServerSession>>(sessions);
    ClientConnected(server);

    FileSessionSlot* slot = GetSessionData(server);
    const FileSessionSlot* original_file = GetSessionData(ctx.Session());

    slot->priority = original_file->priority;
    slot->offset = 0;
    slot->size = backend->GetSize();
    slot->subfile = false;

    rb.Push(RESULT_SUCCESS);
    rb.PushMoveObjects(std::get<SharedPtr<ClientSession>>(sessions));
}
Ejemplo n.º 4
0
void IR_RST::GetHandles(Kernel::HLERequestContext& ctx) {
    IPC::RequestParser rp(ctx, 0x01, 0, 0);
    IPC::RequestBuilder rb = rp.MakeBuilder(1, 3);
    rb.Push(RESULT_SUCCESS);
    rb.PushMoveObjects(shared_memory, update_event);
}