Skip to content

Commit

Permalink
fix(storage): fix read-write race in Writer.Write (#6817)
Browse files Browse the repository at this point in the history
Fixes #6816

w.monitorCancel() -> w.CloseWithError() reads the values of w.opened and w.pw concurrently with the calling routine initializing them; if the incoming context is cancelled before or during initialization.

The fix is simply to deploy starting the monitor until all fields are initialized. The older open() code from previous releases did this in the right order:

https://github.com/googleapis/google-cloud-go/blob/storage/v1.24.0/storage/writer.go#L130-L134
  • Loading branch information
dragonsinth committed Oct 13, 2022
1 parent ae7441a commit 4766d3e
Showing 1 changed file with 4 additions and 1 deletion.
5 changes: 4 additions & 1 deletion storage/writer.go
Expand Up @@ -176,7 +176,6 @@ func (w *Writer) openWriter() (err error) {

isIdempotent := w.o.conds != nil && (w.o.conds.GenerationMatch >= 0 || w.o.conds.DoesNotExist == true)
opts := makeStorageOpts(isIdempotent, w.o.retry, w.o.userProject)
go w.monitorCancel()
params := &openWriterParams{
ctx: w.ctx,
chunkSize: w.ChunkSize,
Expand All @@ -191,11 +190,15 @@ func (w *Writer) openWriter() (err error) {
progress: w.progress,
setObj: func(o *ObjectAttrs) { w.obj = o },
}
if err := w.ctx.Err(); err != nil {
return err // short-circuit
}
w.pw, err = w.o.c.tc.OpenWriter(params, opts...)
if err != nil {
return err
}
w.opened = true
go w.monitorCancel()

return nil
}
Expand Down

0 comments on commit 4766d3e

Please sign in to comment.