nvservices: unmap only on last container free
This commit is contained in:
		| @@ -49,6 +49,7 @@ SessionId Container::OpenSession(Kernel::KProcess* process) { | ||||
|             continue; | ||||
|         } | ||||
|         if (session.process == process) { | ||||
|             session.ref_count++; | ||||
|             return session.id; | ||||
|         } | ||||
|     } | ||||
| @@ -66,6 +67,7 @@ SessionId Container::OpenSession(Kernel::KProcess* process) { | ||||
|     } | ||||
|     auto& session = impl->sessions[new_id]; | ||||
|     session.is_active = true; | ||||
|     session.ref_count = 1; | ||||
|     // Optimization | ||||
|     if (process->IsApplication()) { | ||||
|         auto& page_table = process->GetPageTable().GetBasePageTable(); | ||||
| @@ -114,8 +116,11 @@ SessionId Container::OpenSession(Kernel::KProcess* process) { | ||||
|  | ||||
| void Container::CloseSession(SessionId session_id) { | ||||
|     std::scoped_lock lk(impl->session_guard); | ||||
|     impl->file.UnmapAllHandles(session_id); | ||||
|     auto& session = impl->sessions[session_id.id]; | ||||
|     if (--session.ref_count > 0) { | ||||
|         return; | ||||
|     } | ||||
|     impl->file.UnmapAllHandles(session_id); | ||||
|     auto& smmu = impl->host1x.MemoryManager(); | ||||
|     if (session.has_preallocated_area) { | ||||
|         const DAddr region_start = session.mapper->GetRegionStart(); | ||||
|   | ||||
| @@ -46,6 +46,7 @@ struct Session { | ||||
|     bool has_preallocated_area{}; | ||||
|     std::unique_ptr<HeapMapper> mapper{}; | ||||
|     bool is_active{}; | ||||
|     s32 ref_count{}; | ||||
| }; | ||||
|  | ||||
| class Container { | ||||
|   | ||||
| @@ -333,9 +333,13 @@ void NvMap::UnmapAllHandles(NvCore::SessionId session_id) { | ||||
|     }(); | ||||
|  | ||||
|     for (auto& [id, handle] : handles_copy) { | ||||
|         if (handle->session_id.id == session_id.id) { | ||||
|             FreeHandle(id, false); | ||||
|         { | ||||
|             std::scoped_lock lk{handle->mutex}; | ||||
|             if (handle->session_id.id != session_id.id || handle->dupes <= 0) { | ||||
|                 continue; | ||||
|             } | ||||
|         } | ||||
|         FreeHandle(id, false); | ||||
|     } | ||||
| } | ||||
|  | ||||
|   | ||||
		Reference in New Issue
	
	Block a user