benhoyt / goawk

A POSIX-compliant AWK interpreter written in Go, with CSV support
https://benhoyt.com/writings/goawk/
MIT License
1.94k stars 84 forks source link

fflush() stops on first flush error #208

Closed juster closed 1 year ago

juster commented 1 year ago

During my reading of the interp.flushAll method I noticed that it accidentally uses conditional evaluation. Because the && operator is "short-circuited", if any Flush() returns a non-nil error, then all of the following Flush()-es will be skipped. allGood will be false so the right-hand side of && will not be evaluated.

// Flush all output streams as well as standard output. Report whether all
// streams were flushed successfully (logging error(s) if not).
func (p *interp) flushAll() bool {
    allGood := true
    for name, writer := range p.outputStreams {
        allGood = allGood && p.flushWriter(name, writer)
    }
    if _, ok := p.output.(flusher); ok {
        // User-provided output may or may not be flushable
        allGood = allGood && p.flushWriter("stdout", p.output)
    }
    return allGood
}

Code changes are trivial but I'm not sure how to create a regression test as an interpreter "black box" test.

benhoyt commented 1 year ago

Thanks for the bug report and fix! Out of interest, did you notice this when looking at the code, or did you run into it happening?

juster commented 1 year ago

This was purely from reading the code.