--- /dev/null
+/*
+syncer -- stateful file/device data syncer.
+Copyright (C) 2015-2016 Sergey Matveev <stargrave@stargrave.org>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+package main
+
+import (
+ "fmt"
+ "strconv"
+)
+
+const (
+ BufLine = 80
+ CharChanged = byte('%')
+ CharUnchanged = byte('.')
+)
+
+type Printer struct {
+ i int64
+ total int64
+ changed int64
+ frmt string
+ bufSize int
+ outBuf []byte
+}
+
+func NewPrinter(total int64) *Printer {
+ p := Printer{total: total}
+ maxLen := len(fmt.Sprintf("%d", total))
+ p.frmt = "%" + strconv.Itoa(maxLen) + "d/%d %02d%% %s\n"
+ p.bufSize = BufLine - (2*maxLen + 6)
+ p.outBuf = make([]byte, 0, p.bufSize)
+ return &p
+}
+
+func (p *Printer) Changed() {
+ p.i++
+ p.changed++
+ p.outBuf = append(p.outBuf, CharChanged)
+ p.Output()
+}
+
+func (p *Printer) Unchanged() {
+ p.i++
+ p.outBuf = append(p.outBuf, CharUnchanged)
+ p.Output()
+}
+
+func (p *Printer) Output() {
+ if !(len(p.outBuf) == p.bufSize || p.i == p.total) {
+ return
+ }
+ fmt.Printf(p.frmt, p.i, p.total, 100*p.changed/p.i, string(p.outBuf))
+ p.outBuf = p.outBuf[:0]
+}
/*
syncer -- stateful file/device data syncer.
-Copyright (C) 2015 Sergey Matveev <stargrave@stargrave.org>
+Copyright (C) 2015-2016 Sergey Matveev <stargrave@stargrave.org>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
data []byte
}
-func prn(s string) {
- os.Stdout.Write([]byte(s))
- os.Stdout.Sync()
-}
-
func main() {
flag.Parse()
bs := *blkSize * int64(1<<10)
syncs := make(chan chan SyncEvent, workers)
// Writer
- prn("[")
+ prn := NewPrinter(blocks)
finished := make(chan struct{})
go func() {
var event SyncEvent
sumState := state[i*blake2b.Size : i*blake2b.Size+blake2b.Size]
if bytes.Compare(sumState, sum[:]) != 0 {
sync <- SyncEvent{i, buf, buf[:n]}
- prn("%")
+ prn.Changed()
} else {
sync <- SyncEvent{i, buf, nil}
- prn(".")
+ prn.Unchanged()
}
copy(sumState, sum[:])
close(sync)
}
close(syncs)
<-finished
- prn("]\n")
+ prn.Output()
log.Println("Saving state")
stateFile.Write(state)