package crypto import ( "crypto/rc4" "encoding/binary" ) type Ciphers struct { client *rc4.Cipher // For decryption (client->server) server *rc4.Cipher // For encryption (server->client) } // NewCiphers creates a new pair of RC4 ciphers for the client and server func NewCiphers(key int64) (*Ciphers, error) { keyBytes := make([]byte, 8) binary.LittleEndian.PutUint64(keyBytes, uint64(key)) // Client cipher uses NOT of key clientKeyBytes := make([]byte, 8) binary.LittleEndian.PutUint64(clientKeyBytes, uint64(^key)) clientCipher, err := rc4.NewCipher(keyBytes) if err != nil { return nil, err } serverCipher, err := rc4.NewCipher(clientKeyBytes) if err != nil { return nil, err } // Drop first 20 bytes from both ciphers drop := make([]byte, 20) clientCipher.XORKeyStream(drop, drop) serverCipher.XORKeyStream(drop, drop) return &Ciphers{ client: clientCipher, server: serverCipher, }, nil } // Decrypt decrypts data received from the client func (c *Ciphers) Decrypt(data []byte) { if c.client != nil { c.client.XORKeyStream(data, data) } } // Encrypt encrypts data to be sent to the client func (c *Ciphers) Encrypt(data []byte) { if c.server != nil { c.server.XORKeyStream(data, data) } }