+ // Make a new []byte slice and copy the scanner bytes to it. This is critical to avoid a data race as the
+ // scanner re-uses the buffer for subsequent scans.
+ buf := make([]byte, len(scanner.Bytes()))
+ copy(buf, scanner.Bytes())
+
+ var clientLogin Transaction
+ if _, err := clientLogin.Write(buf); err != nil {
+ return err
+ }
+
+ // check if remoteAddr is present in the ban list
+ if banUntil, ok := s.banList[strings.Split(remoteAddr, ":")[0]]; ok {
+ // permaban
+ if banUntil == nil {
+ t := NewTransaction(
+ tranServerMsg,
+ &[]byte{0, 0},
+ NewField(fieldData, []byte("You are permanently banned on this server")),
+ NewField(fieldChatOptions, []byte{0, 0}),
+ )
+
+ b, err := t.MarshalBinary()
+ if err != nil {
+ return err
+ }
+
+ _, err = rwc.Write(b)
+ if err != nil {
+ return err
+ }
+
+ time.Sleep(1 * time.Second)
+ return nil
+ }
+
+ // temporary ban
+ if time.Now().Before(*banUntil) {
+ t := NewTransaction(
+ tranServerMsg,
+ &[]byte{0, 0},
+ NewField(fieldData, []byte("You are temporarily banned on this server")),
+ NewField(fieldChatOptions, []byte{0, 0}),
+ )
+ b, err := t.MarshalBinary()
+ if err != nil {
+ return err
+ }
+
+ _, err = rwc.Write(b)
+ if err != nil {
+ return err
+ }
+
+ time.Sleep(1 * time.Second)
+ return nil
+ }