mirror of
https://github.com/mumble-voip/grumble.git
synced 2025-12-19 21:59:59 -08:00
Send correct channel tree. Update mumbleproto. Add comments regarding UserState permission handling.
This commit is contained in:
parent
8a836ac3af
commit
1e67afca46
5 changed files with 141 additions and 25 deletions
29
client.go
29
client.go
|
|
@ -285,20 +285,29 @@ func (client *Client) receiver() {
|
|||
}
|
||||
}
|
||||
|
||||
// Send the channel list to a client.
|
||||
func (client *Client) sendChannelList() {
|
||||
server := client.server
|
||||
root := server.root
|
||||
client.sendChannelTree(client.server.root)
|
||||
}
|
||||
|
||||
func (client *Client) sendChannelTree(channel *Channel) {
|
||||
// Start at the root channel.
|
||||
err := client.sendProtoMessage(MessageChannelState, &mumbleproto.ChannelState{
|
||||
ChannelId: proto.Uint32(uint32(root.Id)),
|
||||
Name: proto.String(root.Name),
|
||||
Description: proto.String(root.Description),
|
||||
})
|
||||
log.Printf("sending channel ID=%i, NAME=%s", channel.Id, channel.Name)
|
||||
chanstate := &mumbleproto.ChannelState{
|
||||
ChannelId: proto.Uint32(uint32(channel.Id)),
|
||||
Name: proto.String(channel.Name),
|
||||
Description: proto.String(channel.Description),
|
||||
}
|
||||
if channel.parent != nil {
|
||||
chanstate.Parent = proto.Uint32(uint32(channel.parent.Id))
|
||||
}
|
||||
|
||||
err := client.sendProtoMessage(MessageChannelState, chanstate)
|
||||
if err != nil {
|
||||
// panic!
|
||||
log.Printf("poanic!")
|
||||
client.Panic(err.String())
|
||||
}
|
||||
|
||||
for _, subchannel := range channel.children {
|
||||
client.sendChannelTree(subchannel)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
92
message.go
92
message.go
|
|
@ -137,6 +137,98 @@ func (server *Server) handleUserRemoveMessage(client *Client, msg *Message) {
|
|||
}
|
||||
|
||||
func (server *Server) handleUserStateMessage(client *Client, msg *Message) {
|
||||
log.Printf("UserState!")
|
||||
userstate := &mumbleproto.UserState{}
|
||||
err := proto.Unmarshal(msg.buf, userstate)
|
||||
if err != nil {
|
||||
client.Panic(err.String())
|
||||
}
|
||||
|
||||
if userstate.Session == nil {
|
||||
log.Printf("UserState without session.")
|
||||
return
|
||||
}
|
||||
|
||||
actor := server.clients[client.Session]
|
||||
user := server.clients[*userstate.Session]
|
||||
|
||||
log.Printf("actor = %v", actor)
|
||||
log.Printf("user = %v", user)
|
||||
|
||||
userstate.Session = proto.Uint32(user.Session)
|
||||
userstate.Actor = proto.Uint32(actor.Session)
|
||||
|
||||
// Has a channel ID
|
||||
if userstate.ChannelId != nil {
|
||||
// Destination channel
|
||||
dstChan := server.channels[int(*userstate.ChannelId)]
|
||||
log.Printf("dstChan = %v", dstChan)
|
||||
|
||||
// If the user and the actor aren't the same, check whether the actor has the 'move' permission
|
||||
// on the user's channel to move.
|
||||
|
||||
// Check whether the actor has 'move' permissions on dstChan. Check whether user has 'enter'
|
||||
// permissions on dstChan.
|
||||
|
||||
// Check whether the channel is full.
|
||||
}
|
||||
|
||||
if userstate.Mute != nil || userstate.Deaf != nil || userstate.Suppress != nil || userstate.PrioritySpeaker != nil {
|
||||
// Disallow for SuperUser
|
||||
|
||||
// Check whether the actor has 'mutedeafen' permission on user's channel.
|
||||
|
||||
// Check if this was a suppress operation. Only the server can suppress users.
|
||||
}
|
||||
|
||||
// Comment set/clear
|
||||
if userstate.Comment != nil {
|
||||
comment := *userstate.Comment
|
||||
log.Printf("comment = %v", comment)
|
||||
|
||||
// Clearing another user's comment.
|
||||
if user != actor {
|
||||
// Check if actor has 'move' permissions on the root channel. It is needed
|
||||
// to clear another user's comment.
|
||||
|
||||
// Only allow empty text.
|
||||
}
|
||||
|
||||
// Check if the text is allowed.
|
||||
|
||||
// Only set the comment if it is different from the current
|
||||
// user comment.
|
||||
}
|
||||
|
||||
// Texture change
|
||||
if userstate.Texture != nil {
|
||||
// Check the length of the texture
|
||||
}
|
||||
|
||||
// Registration
|
||||
if userstate.UserId != nil {
|
||||
// If user == actor, check for 'selfregister' permission on root channel.
|
||||
// If user != actor, check for 'register' permission on root channel.
|
||||
|
||||
// Check if the UserId in the message is >= 0. A registration attempt
|
||||
// must use a negative UserId.
|
||||
}
|
||||
|
||||
// Prevent self-targetting state changes to be applied to other users
|
||||
// That is, if actor != user, then:
|
||||
// Discard message if it has any of the following things set:
|
||||
// - SelfDeaf
|
||||
// - SelfMute
|
||||
// - Texture
|
||||
// - PluginContext
|
||||
// - PluginIdentity
|
||||
// - Recording
|
||||
if actor != user && (userstate.SelfDeaf != nil || userstate.SelfMute != nil ||
|
||||
userstate.Texture != nil || userstate.PluginContext != nil || userstate.PluginIdentity != nil ||
|
||||
userstate.Recording != nil) {
|
||||
return
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func (server *Server) handleBanListMessage(client *Client, msg *Message) {
|
||||
|
|
|
|||
|
|
@ -245,6 +245,8 @@ type UserState struct {
|
|||
Hash *string "PB(bytes,15,opt,name=hash)"
|
||||
CommentHash []byte "PB(bytes,16,opt,name=comment_hash)"
|
||||
TextureHash []byte "PB(bytes,17,opt,name=texture_hash)"
|
||||
PrioritySpeaker *bool "PB(varint,18,opt,name=priority_speaker)"
|
||||
Recording *bool "PB(varint,19,opt,name=recording)"
|
||||
XXX_unrecognized []byte
|
||||
}
|
||||
func (this *UserState) Reset() {
|
||||
|
|
|
|||
|
|
@ -106,6 +106,8 @@ message UserState {
|
|||
optional string hash = 15;
|
||||
optional bytes comment_hash = 16;
|
||||
optional bytes texture_hash = 17;
|
||||
optional bool priority_speaker = 18;
|
||||
optional bool recording = 19;
|
||||
}
|
||||
|
||||
message BanList {
|
||||
|
|
|
|||
41
server.go
41
server.go
|
|
@ -41,7 +41,6 @@ type Server struct {
|
|||
udpconn *net.UDPConn
|
||||
|
||||
incoming chan *Message
|
||||
outgoing chan *Message
|
||||
udpsend chan *Message
|
||||
voicebroadcast chan *VoiceBroadcast
|
||||
|
||||
|
|
@ -63,7 +62,10 @@ type Server struct {
|
|||
BetaCodec int32
|
||||
PreferAlphaCodec bool
|
||||
|
||||
// Channels
|
||||
chanid int
|
||||
root *Channel
|
||||
channels map[int]*Channel
|
||||
}
|
||||
|
||||
// Allocate a new Murmur instance
|
||||
|
|
@ -78,7 +80,6 @@ func NewServer(addr string, port int) (s *Server, err os.Error) {
|
|||
s.hclients = make(map[string][]*Client)
|
||||
s.hpclients = make(map[string]*Client)
|
||||
|
||||
s.outgoing = make(chan *Message)
|
||||
s.incoming = make(chan *Message)
|
||||
s.udpsend = make(chan *Message)
|
||||
s.voicebroadcast = make(chan *VoiceBroadcast)
|
||||
|
|
@ -86,10 +87,13 @@ func NewServer(addr string, port int) (s *Server, err os.Error) {
|
|||
s.MaxBandwidth = 300000
|
||||
s.MaxUsers = 10
|
||||
|
||||
s.root = NewChannel(0, "Root")
|
||||
s.channels = make(map[int]*Channel)
|
||||
|
||||
s.root = s.NewChannel("Root")
|
||||
subChan := s.NewChannel("SubChannel")
|
||||
s.root.AddChild(subChan)
|
||||
|
||||
go s.handler()
|
||||
go s.multiplexer()
|
||||
|
||||
return
|
||||
}
|
||||
|
|
@ -152,6 +156,23 @@ func (server *Server) RemoveClient(client *Client) {
|
|||
}
|
||||
}
|
||||
|
||||
// Add a new channel to the server.
|
||||
func (server *Server) NewChannel(name string) (channel *Channel) {
|
||||
channel = NewChannel(server.chanid, name)
|
||||
server.channels[channel.Id] = channel
|
||||
server.chanid += 1
|
||||
return
|
||||
}
|
||||
|
||||
// Remove a channel from the server.
|
||||
func (server *Server) RemoveChanel(channel *Channel) {
|
||||
if (channel.Id == 0) {
|
||||
log.Printf("Attempted to remove root channel.")
|
||||
return
|
||||
}
|
||||
server.channels[channel.Id] = nil, false
|
||||
}
|
||||
|
||||
// This is the synchronous handler goroutine.
|
||||
// Important control channel messages are routed through this Goroutine
|
||||
// to keep server state synchronized.
|
||||
|
|
@ -263,7 +284,6 @@ func (server *Server) handleAuthenticate(client *Client, msg *Message) {
|
|||
|
||||
// Broadcast the the user entered a channel
|
||||
server.root.AddClient(client)
|
||||
log.Printf("server.root = %p", server.root)
|
||||
err = server.broadcastProtoMessage(MessageUserState, &mumbleproto.UserState{
|
||||
Session: proto.Uint32(client.Session),
|
||||
Name: proto.String(client.Username),
|
||||
|
|
@ -364,10 +384,8 @@ func (server *Server) sendUserList(client *Client) {
|
|||
ChannelId: proto.Uint32(0),
|
||||
})
|
||||
|
||||
log.Printf("Sent one user")
|
||||
|
||||
if err != nil {
|
||||
log.Printf("unable to send!")
|
||||
// Server panic?
|
||||
continue
|
||||
}
|
||||
}
|
||||
|
|
@ -432,13 +450,6 @@ func (server *Server) handleIncomingMessage(client *Client, msg *Message) {
|
|||
}
|
||||
}
|
||||
|
||||
func (server *Server) multiplexer() {
|
||||
for {
|
||||
_ = <-server.outgoing
|
||||
log.Printf("recvd message to multiplex")
|
||||
}
|
||||
}
|
||||
|
||||
func (s *Server) SetupUDP() (err os.Error) {
|
||||
addr := &net.UDPAddr{
|
||||
Port: s.port,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue