From a7c6aad065fc41fb7be6cd7d1fd7263c5b557f7c Mon Sep 17 00:00:00 2001 From: sergystepanov Date: Sat, 4 Jul 2026 21:21:54 +0300 Subject: [PATCH] Use concurrent-safe game lib iterators --- pkg/games/launcher.go | 5 +++-- pkg/games/library.go | 26 +++++++++++++++++++++++++- pkg/worker/coordinator.go | 13 ++++++------- 3 files changed, 34 insertions(+), 10 deletions(-) diff --git a/pkg/games/launcher.go b/pkg/games/launcher.go index 8850ea7f..76197811 100644 --- a/pkg/games/launcher.go +++ b/pkg/games/launcher.go @@ -39,9 +39,10 @@ func (gl GameLauncher) FindAppByName(name string) (AppMeta, error) { func (gl GameLauncher) ExtractAppNameFromUrl(name string) string { return ExtractGame(name) } func (gl GameLauncher) GetAppNames() (apps []AppMeta) { - for _, game := range gl.lib.GetAll() { + apps = make([]AppMeta, 0, gl.lib.GamesCount()) + gl.lib.ForEach(func(game GameMetadata) { apps = append(apps, AppMeta{Alias: game.Alias, Name: game.Name, System: game.System}) - } + }) return } diff --git a/pkg/games/library.go b/pkg/games/library.go index 5586f464..dd83b21a 100644 --- a/pkg/games/library.go +++ b/pkg/games/library.go @@ -57,6 +57,8 @@ type GameLibrary interface { FindGameByName(name string) GameMetadata Sessions() []string Scan() + ForEach(func(GameMetadata)) + GamesCount() int } type WithEmulatorInfo interface { @@ -118,14 +120,32 @@ func NewLib(conf config.Library, emu WithEmulatorInfo, log *logger.Logger) GameL } func (lib *library) Sessions() []string { + lib.mu.Lock() + defer lib.mu.Unlock() return lib.sessions } +func (lib *library) ForEach(fn func(GameMetadata)) { + lib.mu.Lock() + defer lib.mu.Unlock() + for _, v := range lib.games { + fn(v) + } +} + +func (lib *library) GamesCount() int { + lib.mu.Lock() + defer lib.mu.Unlock() + return len(lib.games) +} + func (lib *library) GetAll() []GameMetadata { - var res []GameMetadata + lib.mu.Lock() + res := make([]GameMetadata, 0, len(lib.games)) for _, value := range lib.games { res = append(res, value) } + lib.mu.Unlock() return res } @@ -246,7 +266,9 @@ func (lib *library) Scan() { } if len(games) > 0 { + lib.mu.Lock() lib.set(games) + lib.mu.Unlock() } var sessions []string @@ -261,7 +283,9 @@ func (lib *library) Scan() { } return nil }) + lib.mu.Lock() lib.sessions = sessions + lib.mu.Unlock() lib.lastScanDuration = time.Since(start) if lib.config.verbose { diff --git a/pkg/worker/coordinator.go b/pkg/worker/coordinator.go index 05bfa969..a537ec12 100644 --- a/pkg/worker/coordinator.go +++ b/pkg/worker/coordinator.go @@ -6,6 +6,7 @@ import ( "github.com/giongto35/cloud-game/v3/pkg/api" "github.com/giongto35/cloud-game/v3/pkg/com" "github.com/giongto35/cloud-game/v3/pkg/config" + "github.com/giongto35/cloud-game/v3/pkg/games" "github.com/giongto35/cloud-game/v3/pkg/logger" "github.com/giongto35/cloud-game/v3/pkg/network/webrtc" ) @@ -115,12 +116,10 @@ func (c *coordinator) IceCandidate(candidate string, sessionId string) { } func (c *coordinator) SendLibrary(w *Worker) { - g := w.lib.GetAll() - - var gg = make([]api.GameInfo, len(g)) - for i, g := range g { - gg[i] = api.GameInfo(g) - } + gg := make([]api.GameInfo, 0, w.lib.GamesCount()) + w.lib.ForEach(func(g games.GameMetadata) { + gg = append(gg, api.GameInfo(g)) + }) c.Notify(api.LibNewGameList, api.LibGameListInfo{T: 1, List: gg}) } @@ -129,7 +128,7 @@ func (c *coordinator) SendPrevSessions(w *Worker) { sessions := w.lib.Sessions() // extract ids from save states, i.e. sessions - var ids []string + ids := make([]string, 0, len(sessions)) for _, id := range sessions { x, _ := api.ExplodeDeepLink(id)