- Refactored client.setNick
- Fixed an invalid memory access error that occurs whenever a chan op kicks a user from their channel after changing their nick (forgot to update the channel's modeMap in client.setNick)
This commit is contained in:
parent
272ea046c4
commit
4fb9253cc5
50
client.go
50
client.go
@ -4,49 +4,41 @@ import (
|
|||||||
"bytes"
|
"bytes"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"sort"
|
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (c *Client) setNick(nick string) {
|
func (c *Client) setNick(nick string) {
|
||||||
if c.nick != "" {
|
|
||||||
delete(c.server.clientMap, c.key)
|
|
||||||
for _, channel := range c.channelMap {
|
|
||||||
delete(channel.clientMap, c.key)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//Set up new nick
|
//Set up new nick
|
||||||
oldNick := c.nick
|
oldNick := c.nick
|
||||||
|
oldKey := c.key
|
||||||
c.nick = nick
|
c.nick = nick
|
||||||
c.key = strings.ToLower(c.nick)
|
c.key = strings.ToLower(c.nick)
|
||||||
|
|
||||||
|
delete(c.server.clientMap, oldKey)
|
||||||
c.server.clientMap[c.key] = c
|
c.server.clientMap[c.key] = c
|
||||||
|
|
||||||
clients := make([]string, 0, 100)
|
//Update the relevant channels and notify everyone who can see us about our
|
||||||
|
//nick change
|
||||||
|
c.reply(rplNickChange, oldNick, c.nick)
|
||||||
|
visited := make(map[*Client]struct{}, 100)
|
||||||
for _, channel := range c.channelMap {
|
for _, channel := range c.channelMap {
|
||||||
|
delete(channel.clientMap, oldKey)
|
||||||
|
|
||||||
|
for _, client := range channel.clientMap {
|
||||||
|
if _, skip := visited[client]; skip {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
client.reply(rplNickChange, oldNick, c.nick)
|
||||||
|
visited[client] = struct{}{}
|
||||||
|
}
|
||||||
|
|
||||||
|
//Insert the new nick after iterating through channel.clientMap to avoid
|
||||||
|
//sending a duplicate message to ourselves
|
||||||
channel.clientMap[c.key] = c
|
channel.clientMap[c.key] = c
|
||||||
|
|
||||||
//Collect list of client nicks who can see us
|
channel.modeMap[c.key] = channel.modeMap[oldKey]
|
||||||
for _, client := range channel.clientMap {
|
delete(channel.modeMap, oldKey)
|
||||||
clients = append(clients, client.nick)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//By sorting the nicks and skipping duplicates we send each client one message
|
|
||||||
sort.Strings(clients)
|
|
||||||
prevNick := ""
|
|
||||||
for _, nick := range clients {
|
|
||||||
if nick == prevNick {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
prevNick = nick
|
|
||||||
|
|
||||||
client, exists := c.server.clientMap[strings.ToLower(nick)]
|
|
||||||
if exists {
|
|
||||||
client.reply(rplNickChange, oldNick, c.nick)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user