From b8205590505535c74e50948e245144d8c86d092a Mon Sep 17 00:00:00 2001 From: Daniel Oaks Date: Wed, 29 Jun 2016 01:09:07 +1000 Subject: [PATCH] modes: Add TLS umode (+Z) --- CHANGELOG.md | 1 + irc/client.go | 5 ++++- irc/modes.go | 7 +++++-- irc/server.go | 25 ++++++++++++++++++++----- 4 files changed, 30 insertions(+), 8 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 88d804a2..0f627189 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -18,6 +18,7 @@ Initial release of Oragono! * Added ability to generate certificates from the command line. * We now advertise the [`RPL_ISUPPORT`](http://modern.ircdocs.horse/#rplisupport-005) numeric. * Parse new mode change syntax commonly used these days (i.e. `+h-ov dan dan dan`). +* User mode for clients connected via TLS (`+Z`). ### Changed * Added channel Founder/Admin/Halfops (`qah`) privileges, and removed channel creator (`O`) privilege (from RFC2812, not used in the real world). diff --git a/irc/client.go b/irc/client.go index bc4543f2..7a992fb6 100644 --- a/irc/client.go +++ b/irc/client.go @@ -44,7 +44,7 @@ type Client struct { isDestroyed bool } -func NewClient(server *Server, conn net.Conn) *Client { +func NewClient(server *Server, conn net.Conn, isTLS bool) *Client { now := time.Now() socket := NewSocket(conn) client := &Client{ @@ -59,6 +59,9 @@ func NewClient(server *Server, conn net.Conn) *Client { socket: &socket, nickString: "*", // * is used until actual nick is given } + if isTLS { + client.flags[TLS] = true + } client.Touch() go client.run() diff --git a/irc/modes.go b/irc/modes.go index 506924d0..afc17dd0 100644 --- a/irc/modes.go +++ b/irc/modes.go @@ -143,6 +143,7 @@ const ( Operator UserMode = 'o' Restricted UserMode = 'r' ServerNotice UserMode = 's' // deprecated + TLS UserMode = 'Z' WallOps UserMode = 'w' ) @@ -292,11 +293,13 @@ func umodeHandler(server *Server, client *Client, msg ircmsg.IrcMessage) bool { applied = append(applied, change) } } + + // can't do anything to TLS mode } } - if len(changes) > 0 { - client.Send(nil, client.nickMaskString, "MODE", target.nickString, changes.String()) + if len(applied) > 0 { + client.Send(nil, client.nickMaskString, "MODE", target.nickString, applied.String()) } else if client == target { client.Send(nil, target.nickMaskString, RPL_UMODEIS, target.nickString, target.ModeString()) } diff --git a/irc/server.go b/irc/server.go index a3078744..92710735 100644 --- a/irc/server.go +++ b/irc/server.go @@ -33,7 +33,7 @@ type Server struct { motdLines []string name Name nameString string // cache for server name string since it's used with almost every reply - newConns chan net.Conn + newConns chan clientConn operators map[Name][]byte password []byte signals chan os.Signal @@ -48,6 +48,11 @@ var ( syscall.SIGTERM, syscall.SIGQUIT} ) +type clientConn struct { + Conn net.Conn + IsTLS bool +} + func NewServer(config *Config) *Server { server := &Server{ channels: make(ChannelNameMap), @@ -58,7 +63,7 @@ func NewServer(config *Config) *Server { idle: make(chan *Client), name: NewName(config.Server.Name), nameString: NewName(config.Server.Name).String(), - newConns: make(chan net.Conn), + newConns: make(chan clientConn), operators: config.Operators(), signals: make(chan os.Signal, len(SERVER_SIGNALS)), proxyAllowedFrom: config.Server.ProxyAllowedFrom, @@ -180,7 +185,7 @@ func (server *Server) Run() { done = true case conn := <-server.newConns: - NewClient(server, conn) + NewClient(server, conn.Conn, conn.IsTLS) /*TODO(dan): LOOK AT THIS MORE CLOSELY case cmd := <-server.commands: @@ -221,7 +226,12 @@ func (s *Server) listen(addr string, tlsMap map[Name]*tls.Config) { } Log.debug.Printf("%s accept: %s", s, conn.RemoteAddr()) - s.newConns <- conn + newConn := clientConn{ + Conn: conn, + IsTLS: listenTLS, + } + + s.newConns <- newConn } }() } @@ -250,7 +260,11 @@ func (s *Server) wslisten(addr string, tlsMap map[string]*TLSListenConfig) { return } - s.newConns <- WSContainer{ws} + newConn := clientConn{ + Conn: WSContainer{ws}, + IsTLS: false, //TODO(dan): track TLS or not here properly + } + s.newConns <- newConn }) go func() { config, listenTLS := tlsMap[addr] @@ -294,6 +308,7 @@ func (s *Server) tryRegister(c *Client) { c.Send(nil, s.nameString, RPL_MYINFO, c.nickString, s.nameString, SEM_VER, supportedUserModesString, supportedChannelModesString) c.RplISupport() s.MOTD(c) + c.Send(nil, c.nickMaskString, RPL_UMODEIS, c.nickString, c.ModeString()) } func (server *Server) MOTD(client *Client) {