Add and use Conn.CloseWith (#67)
parent
cda0be69c5
commit
7b9d58cb5c
24
ban.go
24
ban.go
|
@ -1,14 +1,11 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"database/sql"
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net"
|
||||
|
||||
"github.com/anon55555/mt/rudp"
|
||||
_ "github.com/mattn/go-sqlite3"
|
||||
)
|
||||
|
||||
|
@ -114,26 +111,7 @@ func (c *Conn) Ban() error {
|
|||
return err
|
||||
}
|
||||
|
||||
reason := []byte("Banned.")
|
||||
l := len(reason)
|
||||
|
||||
data := make([]byte, 7+l)
|
||||
data[0] = uint8(0x00)
|
||||
data[1] = uint8(ToClientAccessDenied)
|
||||
data[2] = uint8(AccessDeniedCustomString)
|
||||
binary.BigEndian.PutUint16(data[3:5], uint16(l))
|
||||
copy(data[5:5+l], reason)
|
||||
data[5+l] = uint8(0x00)
|
||||
data[6+l] = uint8(0x00)
|
||||
|
||||
ack, err := c.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
<-ack
|
||||
|
||||
c.Close()
|
||||
|
||||
c.CloseWith(AccessDeniedCustomString, "Banned.", false)
|
||||
return nil
|
||||
}
|
||||
|
||||
|
|
22
conn.go
22
conn.go
|
@ -141,6 +141,28 @@ func (c *Conn) MakeRpcOnly() {
|
|||
// Inv returns the inventory of the Conn
|
||||
func (c *Conn) Inv() *mt.Inv { return c.inv }
|
||||
|
||||
// CloseWith denies access and disconnects the Conn
|
||||
func (c *Conn) CloseWith(reason uint8, custom string, reconnect bool) error {
|
||||
defer c.Close()
|
||||
|
||||
w := bytes.NewBuffer([]byte{0x00, ToClientAccessDenied})
|
||||
WriteUint8(w, reason)
|
||||
WriteBytes16(w, []byte(custom))
|
||||
if reconnect {
|
||||
WriteUint8(w, 1)
|
||||
} else {
|
||||
WriteUint8(w, 0)
|
||||
}
|
||||
|
||||
ack, err := c.Send(rudp.Pkt{Reader: w})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
<-ack
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Connect connects to the server on conn
|
||||
// and closes conn when the Conn disconnects
|
||||
func Connect(conn net.Conn) (*Conn, error) {
|
||||
|
|
31
end.go
31
end.go
|
@ -1,44 +1,22 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"log"
|
||||
"os"
|
||||
"time"
|
||||
|
||||
"github.com/anon55555/mt/rudp"
|
||||
)
|
||||
|
||||
// End disconnects (from) all Peers and stops the process
|
||||
func End(crash, reconnect bool) {
|
||||
log.Print("Ending")
|
||||
|
||||
data := make([]byte, 7)
|
||||
data[0] = uint8(0x00)
|
||||
data[1] = uint8(ToClientAccessDenied)
|
||||
var reason uint8 = AccessDeniedShutdown
|
||||
if crash {
|
||||
data[2] = uint8(AccessDeniedCrash)
|
||||
} else {
|
||||
data[2] = uint8(AccessDeniedShutdown)
|
||||
reason = AccessDeniedCrash
|
||||
}
|
||||
data[3] = uint8(0x00)
|
||||
data[4] = uint8(0x00)
|
||||
if reconnect {
|
||||
data[5] = uint8(0x01)
|
||||
} else {
|
||||
data[5] = uint8(0x00)
|
||||
}
|
||||
data[6] = uint8(0x00)
|
||||
|
||||
r := bytes.NewReader(data)
|
||||
|
||||
for _, clt := range Conns() {
|
||||
_, err := clt.Send(rudp.Pkt{Reader: r})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
|
||||
clt.Close()
|
||||
clt.CloseWith(reason, "", reconnect)
|
||||
}
|
||||
|
||||
rpcSrvMu.Lock()
|
||||
|
@ -53,7 +31,6 @@ func End(crash, reconnect bool) {
|
|||
|
||||
if crash {
|
||||
os.Exit(1)
|
||||
} else {
|
||||
os.Exit(0)
|
||||
}
|
||||
os.Exit(0)
|
||||
}
|
||||
|
|
146
init.go
146
init.go
|
@ -178,18 +178,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
return
|
||||
}
|
||||
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedServerFail, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
<-ack
|
||||
|
||||
c.Close()
|
||||
c.CloseWith(AccessDeniedServerFail, "", false)
|
||||
return
|
||||
case ToClientAuthAccept:
|
||||
// Auth succeeded
|
||||
|
@ -290,18 +279,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
c2.protoVer = protov
|
||||
|
||||
if strict, ok := ConfKey("force_latest_proto").(bool); (ok && strict) && (protov != ProtoLatest) || protov < ProtoMin || protov > ProtoLatest {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedWrongVersion, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedWrongVersion, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
@ -324,58 +302,22 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
if banned {
|
||||
log.Print("Banned user " + bname + " at " + c2.Addr().String() + " tried to connect")
|
||||
|
||||
reason := []byte("Your IP address is banned. Banned name is " + bname)
|
||||
|
||||
w := bytes.NewBuffer([]byte{0x00, ToClientAccessDenied})
|
||||
WriteUint8(w, AccessDeniedCustomString)
|
||||
WriteBytes16(w, reason)
|
||||
WriteUint8(w, 0)
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: w})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
reason := "Your IP address is banned. Banned name is " + bname
|
||||
c2.CloseWith(AccessDeniedCustomString, reason, false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
||||
// Check if user is already connected
|
||||
if IsOnline(c2.Username()) {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedAlreadyConnected, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedAlreadyConnected, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
||||
// Check if username is reserved for media or RPC
|
||||
if c2.Username() == "media" || c2.Username() == "rpc" {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedWrongName, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedWrongName, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
@ -419,20 +361,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
if c2.authMech != AuthMechFirstSRP {
|
||||
log.Print(c2.Addr().String() + " used unsupported AuthMechFirstSRP")
|
||||
|
||||
// Send ACCESS_DENIED
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedUnexpectedData, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedUnexpectedData, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
@ -448,20 +377,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
if ok && disallow && empty > 0 {
|
||||
log.Print(c2.Addr().String() + " used an empty password but disallow_empty_passwords is true")
|
||||
|
||||
// Send ACCESS_DENIED
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedEmptyPassword, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedEmptyPassword, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
@ -516,21 +432,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
if c2.authMech != AuthMechSRP {
|
||||
log.Print(c2.Addr().String() + " used unsupported AuthMechSRP")
|
||||
|
||||
// Send ACCESS_DENIED
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedUnexpectedData, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedUnexpectedData, "", false)
|
||||
return
|
||||
}
|
||||
|
||||
|
@ -592,20 +494,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
if c2.authMech != AuthMechSRP {
|
||||
log.Print(c2.Addr().String() + " used unsupported AuthMechSRP")
|
||||
|
||||
// Send ACCESS_DENIED
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedUnexpectedData, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedUnexpectedData, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
@ -641,20 +530,7 @@ func Init(c, c2 *Conn, ignMedia, noAccessDenied bool, fin chan *Conn) {
|
|||
// Client supplied wrong password
|
||||
log.Print("User " + c2.Username() + " at " + c2.Addr().String() + " supplied wrong password")
|
||||
|
||||
// Send ACCESS_DENIED
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedWrongPassword, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
ack, err := c2.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
|
||||
c2.Close()
|
||||
c2.CloseWith(AccessDeniedWrongPassword, "", false)
|
||||
fin <- c
|
||||
return
|
||||
}
|
||||
|
|
12
listen.go
12
listen.go
|
@ -1,7 +1,6 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"errors"
|
||||
"net"
|
||||
"sync"
|
||||
|
@ -60,16 +59,7 @@ func (l *Listener) Accept() (*Conn, error) {
|
|||
}
|
||||
|
||||
if ConnCount() >= maxConns {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedTooManyUsers, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
_, err := clt.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
clt.CloseWith(AccessDeniedTooManyUsers, "", true)
|
||||
return nil, ErrPlayerLimitReached
|
||||
}
|
||||
|
||||
|
|
|
@ -5,11 +5,8 @@ media and definition multiplexing
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"log"
|
||||
"net"
|
||||
|
||||
"github.com/anon55555/mt/rudp"
|
||||
)
|
||||
|
||||
func main() {
|
||||
|
@ -56,22 +53,13 @@ func main() {
|
|||
srv := <-fin
|
||||
|
||||
if srv == nil {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedServerFail, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
select {
|
||||
case <-clt.Closed():
|
||||
clt.Close()
|
||||
default:
|
||||
ack, err := clt.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
<-ack
|
||||
clt.CloseWith(AccessDeniedServerFail, "", false)
|
||||
}
|
||||
|
||||
clt.Close()
|
||||
return
|
||||
}
|
||||
|
||||
|
|
15
proxy.go
15
proxy.go
|
@ -1,28 +1,15 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"errors"
|
||||
"log"
|
||||
"net"
|
||||
|
||||
"github.com/anon55555/mt/rudp"
|
||||
)
|
||||
|
||||
// Proxy processes and forwards packets from src to dst
|
||||
func Proxy(src, dst *Conn) {
|
||||
if src == nil {
|
||||
data := []byte{
|
||||
0, ToClientAccessDenied,
|
||||
AccessDeniedServerFail, 0, 0, 0, 0,
|
||||
}
|
||||
|
||||
_, err := dst.Send(rudp.Pkt{Reader: bytes.NewReader(data)})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
|
||||
dst.Close()
|
||||
dst.CloseWith(AccessDeniedServerFail, "", false)
|
||||
processLeave(dst)
|
||||
return
|
||||
} else if dst == nil {
|
||||
|
|
Loading…
Reference in New Issue