func NewChunkWriter(w io.Writer, c btncrypt.Cipher, h ChunkHeader) (io.WriteCloser, error) { if err := h.WriteTo(w, c); err != nil { return nil, fmt.Errorf("Failed to write header: %v", err) } return btncrypt.NewWriteCloser(w, c, int(h.PayloadLen)) }
func TestBtnEncryptWriter_PartialWrite(t *testing.T) { payload := util.RandomBytes(1024 * 1024) var b bytes.Buffer bew, err := btncrypt.NewWriteCloser(&b, tu.TestCipher(), len(payload)) if err != nil { t.Errorf("Failed to create BtnEncryptWriter: %v", err) } verifyWrite(t, bew, payload[:3]) verifyWrite(t, bew, payload[3:1024]) verifyWrite(t, bew, payload[1024:4096]) verifyWrite(t, bew, payload[4096:]) if err := bew.Close(); err != nil { t.Errorf("bew.Close failed: %v", err) } plain, err := btncrypt.Decrypt(tu.TestCipher(), b.Bytes(), len(payload)) if err != nil { t.Errorf("Failed to decrypt: %v", err) } if !bytes.Equal(payload, plain) { t.Errorf("Failed to restore original payload") } }
func (h ChunkHeader) WriteTo(w io.Writer, c btncrypt.Cipher) error { h.FrameEncapsulation = CurrentFrameEncapsulation if h.PayloadLen > MaxChunkPayloadLen { return fmt.Errorf("payload length too big: %d", h.PayloadLen) } if len(h.OrigFilename) > MaxOrigFilenameLen { h.OrigFilename = filepath.Base(h.OrigFilename) if len(h.OrigFilename) > MaxOrigFilenameLen { h.OrigFilename = "<filename_too_long>" } } if _, err := w.Write([]byte{ChunkSignatureMagic1, ChunkSignatureMagic2}); err != nil { return fmt.Errorf("Failed to write signature magic: %v", err) } if _, err := w.Write([]byte{CurrentFormat}); err != nil { return fmt.Errorf("Failed to write format byte: %v", err) } var b bytes.Buffer enc := gob.NewEncoder(&b) if err := enc.Encode(h); err != nil { return err } framelen := ChunkHeaderLength - c.FrameOverhead() - SignatureLength - 1 paddinglen := framelen - b.Len() if paddinglen < 0 { log.Fatalf("SHOULD NOT BE REACHED: Marshaled ChunkHeader size too large") } bew, err := btncrypt.NewWriteCloser(w, c, framelen) if _, err := b.WriteTo(bew); err != nil { return fmt.Errorf("Failed to initialize frame encryptor: %v", err) } if err != nil { return fmt.Errorf("Header frame gob payload write failed: %v", err) } // zero padding if _, err := bew.Write(make([]byte, paddinglen)); err != nil { return fmt.Errorf("Header frame zero padding write failed: %v", err) } if err := bew.Close(); err != nil { return fmt.Errorf("Header frame close failed: %v", err) } return nil }
func (ch *ChunkIO) writeContentFrame(i int, f *decryptedContentFrame) error { // the offset of the start of the frame in blob blobOffset := ch.encryptedFrameOffset(i) wr := &blobstore.OffsetWriter{ch.bh, int64(blobOffset)} bew, err := btncrypt.NewWriteCloser(wr, ch.c, len(f.P)) if err != nil { return fmt.Errorf("Failed to create BtnEncryptWriteCloser: %v", err) } defer func() { if err := bew.Close(); err != nil { log.Printf("Failed to Close BtnEncryptWriteCloser: %v", err) } }() if _, err := bew.Write(f.P); err != nil { return fmt.Errorf("Failed to encrypt frame: %v", err) } ch.header.PayloadVersion++ ch.needsHeaderUpdate = true log.Printf("ChunkIO: Wrote content frame idx: %d", i) return nil }
func TestBtnEncryptWriter_WriteAtOnce(t *testing.T) { //payload := RandomBytes(1024 * 1024) payload := []byte("short string") var b bytes.Buffer bew, err := btncrypt.NewWriteCloser(&b, tu.TestCipher(), len(payload)) if err != nil { t.Errorf("Failed to create BtnEncryptWriter: %v", err) } verifyWrite(t, bew, payload) if err := bew.Close(); err != nil { t.Errorf("bew.Close failed: %v", err) } plain, err := btncrypt.Decrypt(tu.TestCipher(), b.Bytes(), len(payload)) if err != nil { t.Errorf("Failed to decrypt: %v", err) } if !bytes.Equal(payload, plain) { t.Errorf("Failed to restore original payload") } }