From 6a2fbd1434138094474a9f8901dc7f351bc4388c Mon Sep 17 00:00:00 2001 From: HimbeerserverDE Date: Sat, 9 Dec 2023 12:01:51 +0100 Subject: fix clients being able to connect to media pools that were down on join This commit fixes #141. --- client_conn.go | 13 +++++++------ content.go | 31 ++++++++++++++++++++++++++----- hop.go | 4 ++++ process.go | 2 +- 4 files changed, 38 insertions(+), 12 deletions(-) diff --git a/client_conn.go b/client_conn.go index d8e69da..da45c8d 100644 --- a/client_conn.go +++ b/client_conn.go @@ -47,12 +47,13 @@ type ClientConn struct { versionStr string formspecVer uint16 - itemDefs []mt.ItemDef - aliases []struct{ Alias, Orig string } - nodeDefs []mt.NodeDef - p0Map param0Map - p0SrvMap param0SrvMap - media []mediaFile + denyPools map[string]struct{} + itemDefs []mt.ItemDef + aliases []struct{ Alias, Orig string } + nodeDefs []mt.NodeDef + p0Map param0Map + p0SrvMap param0SrvMap + media []mediaFile playerCAO, currentCAO mt.AOID diff --git a/content.go b/content.go index 33f788a..f24972f 100644 --- a/content.go +++ b/content.go @@ -32,6 +32,7 @@ type mediaFile struct { type contentConn struct { mt.Peer + denied bool logger *log.Logger @@ -228,6 +229,7 @@ func handleContent(cc *contentConn) { M: M, }) case *mt.ToCltKick: + cc.denied = true cc.log("<-", "deny access", cmd) case *mt.ToCltAcceptAuth: cc.auth.method = 0 @@ -348,6 +350,20 @@ type param0SrvMap map[mt.Content]struct { param0 mt.Content } +func muxErrors(conns []*contentConn) map[string]struct{} { + denyPools := make(map[string]struct{}) + + for _, cc := range conns { + <-cc.done() + + if cc.denied { + denyPools[cc.mediaPool] = struct{}{} + } + } + + return denyPools +} + func muxItemDefs(conns []*contentConn) ([]mt.ItemDef, []struct{ Alias, Orig string }) { var itemDefs []mt.ItemDef var aliases []struct{ Alias, Orig string } @@ -507,11 +523,12 @@ func muxRemotes(conns []*contentConn) []string { return urls } -func muxContent(userName string) (itemDefs []mt.ItemDef, aliases []struct{ Alias, Orig string }, nodeDefs []mt.NodeDef, p0Map param0Map, p0SrvMap param0SrvMap, media []mediaFile, remotes []string, err error) { +func muxContent(userName string) (denyPools map[string]struct{}, itemDefs []mt.ItemDef, aliases []struct{ Alias, Orig string }, nodeDefs []mt.NodeDef, p0Map param0Map, p0SrvMap param0SrvMap, media []mediaFile, remotes []string, err error) { var conns []*contentConn + denyPools = make(map[string]struct{}) PoolLoop: - for _, pool := range Conf().Pools() { + for poolName, pool := range Conf().Pools() { var addr *net.UDPAddr for name, srv := range pool { @@ -537,15 +554,19 @@ PoolLoop: continue PoolLoop } - // There's a pool with no reachable servers. - // We can't safely let clients join. - return + denyPools[poolName] = struct{}{} } + failedPools := muxErrors(conns) itemDefs, aliases = muxItemDefs(conns) nodeDefs, p0Map, p0SrvMap = muxNodeDefs(conns) media = muxMedia(conns) remotes = muxRemotes(conns) + + for pool := range failedPools { + denyPools[pool] = struct{}{} + } + return } diff --git a/hop.go b/hop.go index a931f91..587adb9 100644 --- a/hop.go +++ b/hop.go @@ -91,6 +91,10 @@ func (cc *ClientConn) HopRaw(serverName string) error { return ErrNoSuchServer } + if _, ok := cc.denyPools[newSrv.MediaPool]; ok { + return ErrNewMediaPool + } + if newSrv.poolAdded.After(cc.created) { return ErrNewMediaPool } diff --git a/process.go b/process.go index 5c5edd9..b381a54 100644 --- a/process.go +++ b/process.go @@ -361,7 +361,7 @@ func (cc *ClientConn) process(pkt mt.Pkt) { case *mt.ToSrvInit2: var remotes []string var err error - cc.itemDefs, cc.aliases, cc.nodeDefs, cc.p0Map, cc.p0SrvMap, cc.media, remotes, err = muxContent(cc.Name()) + cc.denyPools, cc.itemDefs, cc.aliases, cc.nodeDefs, cc.p0Map, cc.p0SrvMap, cc.media, remotes, err = muxContent(cc.Name()) if err != nil { cc.Log("<-", err.Error()) cc.Kick("Content multiplexing failed.") -- cgit v1.2.3