func main() { flag.Var(&needleBytes, "b", "bytes to look for within input(s); e.g., \"-b 00ff00AA\"") flag.Parse() // scan the arguments list if len(*needleString) != 0 { if len(needleBytes) == 0 { needle = substr.NewNeedleStr(*needleString) } else { myerr.MyFatal(status_fatal_error, "error: specified both -t and -b parameters") } } else if len(needleBytes) == 0 { myerr.MyFatal(status_fatal_error, "error: specified neither -t nor -b parameter") } else { needle = substr.NewNeedleBytes(needleBytes) } if *followSymbolicLinks { statFunction = os.Stat } else { statFunction = os.Lstat } if *quiet { *findAll = false } if *swapOutput { *findAll = true } inputs := flag.Args() if len(inputs) == 0 && !*processStdin { myerr.MyFatal(status_fatal_error, "error: did not specify any input files or directories or provide the standard input flag") } if *processStdin { processReader("STDIN", os.Stdin, 0) } for _, fname := range inputs { processInputs(fname, fname) } if *quiet { os.Exit(status_none_found) } }
func main() { defer myerr.MyDefer() var err error flag.Var(&fromBytes, "fromb", "bytes to replace; used to make sure you don't overwrite wrong data; e.g., \"-b 00ff00AA\"") flag.Var(&toBytes, "tob", "replacement bytes; e.g., \"-b 0FE32d17\"") flag.Parse() // scan the arguments list if len(*fromString) != 0 { if len(fromBytes) == 0 { fromBytes = []byte(*fromString) } else { myerr.MyFatal(status_fatal_error, "error: specified both -from and -fromb parameters") return } } if len(*toString) != 0 { if len(toBytes) == 0 { toBytes = []byte(*toString) } else { myerr.MyFatal(status_fatal_error, "error: specified both -to and -tob parameters") return } } else if len(toBytes) == 0 { myerr.MyFatal(status_fatal_error, "error: must specify either -to or -tob parameter") return } if len(fromBytes) != 0 && len(fromBytes) != len(toBytes) { myerr.MyFatal(status_fatal_error, "error: if you specify -from or -fromb it must be the same size as -to or -tob; %d is not equal to %d", len(fromBytes), len(toBytes)) return } var inFileName string positions := NewUint64Slice() gotError := false for i, arg := range flag.Args() { if i == 0 { inFileName = arg } else { var v uint64 v, err = strconv.ParseUint(arg, 10, 64) if err != nil { myerr.MyError("error: trying to parse \"%s\" as an offset; got %s", arg, err) gotError = true } else { positions = append(positions, v) } } } sort.Sort(positions) if gotError { myerr.MyFatal(status_fatal_error, "must exit due to errors") return } inFile, oe := os.Open(inFileName) if oe != nil { myerr.MyFatal(status_fatal_error, "could not open file \"%s\"; %s", inFileName, oe) } defer func() { inFile.Close() }() outFileName, outFile, oe2 := makeTempFile(inFileName, "tmp") if oe2 != nil { myerr.MyFatal(status_fatal_error, "%s", oe2) } complete := false defer func() { outFile.Close() if complete { var mode os.FileMode if fi, e := inFile.Stat(); e == nil { mode = fi.Mode() } else { myerr.MyPanic(e) } var backupName string var backupFile *os.File backupName, backupFile, err = makeTempFile(inFileName, "backup") myerr.MyPanic(err) err = backupFile.Close() myerr.MyPanic(err) err = os.Rename(inFileName, backupName) myerr.MyPanic(err) err = os.Rename(outFileName, inFileName) myerr.MyPanic(err) err = os.Chmod(inFileName, mode) myerr.MyPanic(err) } else { err = os.Remove(outFileName) } }() if _, err = io.Copy(outFile, inFile); err != nil { myerr.MyFatal(status_fatal_error, "error: %s", err) return } buffer := make([]byte, len(fromBytes), len(fromBytes)) for _, offset := range positions { skip := false if len(fromBytes) != 0 { _, err = outFile.ReadAt(buffer, int64(offset)) myerr.MyPanic(err) if !sameBytes(fromBytes, buffer) { fmt.Printf("warning: not same at offset %d; skipping\n", offset) skip = true } } if !skip { _, err = outFile.WriteAt(toBytes, int64(offset)) myerr.MyPanic(err) } } complete = true }