/* * Copyright (c) 2018-2020 Atmosphère-NX * * This program is free software; you can redistribute it and/or modify it * under the terms and conditions of the GNU General Public License, * version 2, as published by the Free Software Foundation. * * This program is distributed in the hope it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for * more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include namespace ams::fssystem { namespace { constexpr inline size_t MaxExternalCodeFileSystem = 0x10; util::BoundedMap g_ecs_map; util::BoundedMap g_hnd_map; } fs::fsa::IFileSystem *GetExternalCodeFileSystem(ncm::ProgramId program_id) { /* Return a fs from the map if one exists. */ if (auto *fs = g_ecs_map.Find(program_id); fs != nullptr) { return fs; } /* Otherwise, we may have a handle. */ if (auto *hnd = g_hnd_map.Find(program_id); hnd != nullptr) { /* Create a service using libnx bindings. */ Service srv; serviceCreate(std::addressof(srv), hnd->Move()); g_hnd_map.Remove(program_id); /* Create a remote filesystem. */ const FsFileSystem fs = { srv }; g_ecs_map.Emplace(program_id, fs); /* Return the created filesystem. */ return g_ecs_map.Find(program_id); } /* Otherwise, we have no filesystem. */ return nullptr; } Result CreateExternalCode(Handle *out, ncm::ProgramId program_id) { /* Create a handle pair. */ Handle server, client; R_TRY(svcCreateSession(std::addressof(server), std::addressof(client), false, 0)); /* Insert the handle into the map. */ g_hnd_map.Emplace(program_id, client); *out = server; return ResultSuccess(); } void DestroyExternalCode(ncm::ProgramId program_id) { g_ecs_map.Remove(program_id); g_hnd_map.Remove(program_id); } }