encryption.go 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. package io
  2. import (
  3. "crypto/cipher"
  4. "io"
  5. "github.com/v2ray/v2ray-core/log"
  6. )
  7. // CryptionReader is a general purpose reader that applies
  8. // block cipher on top of a regular reader.
  9. type CryptionReader struct {
  10. stream cipher.Stream
  11. reader io.Reader
  12. }
  13. func NewCryptionReader(stream cipher.Stream, reader io.Reader) *CryptionReader {
  14. this := new(CryptionReader)
  15. this.stream = stream
  16. this.reader = reader
  17. return this
  18. }
  19. // Read reads blocks from underlying reader, the length of blocks must be
  20. // a multiply of BlockSize()
  21. func (reader CryptionReader) Read(blocks []byte) (int, error) {
  22. nBytes, err := reader.reader.Read(blocks)
  23. log.Debug("CryptionReader: Read %d bytes", nBytes)
  24. if nBytes > 0 {
  25. reader.stream.XORKeyStream(blocks[:nBytes], blocks[:nBytes])
  26. }
  27. if err != nil {
  28. log.Error("Error reading blocks: %v", err)
  29. }
  30. return nBytes, err
  31. }
  32. // Cryption writer is a general purpose of byte stream writer that applies
  33. // block cipher on top of a regular writer.
  34. type CryptionWriter struct {
  35. stream cipher.Stream
  36. writer io.Writer
  37. }
  38. func NewCryptionWriter(stream cipher.Stream, writer io.Writer) *CryptionWriter {
  39. this := new(CryptionWriter)
  40. this.stream = stream
  41. this.writer = writer
  42. return this
  43. }
  44. // Write writes the give blocks to underlying writer. The length of the blocks
  45. // must be a multiply of BlockSize()
  46. func (writer CryptionWriter) Write(blocks []byte) (int, error) {
  47. log.Debug("CryptionWriter writing %d bytes", len(blocks))
  48. writer.stream.XORKeyStream(blocks, blocks)
  49. return writer.writer.Write(blocks)
  50. }