X-Git-Url: http://www.git.stargrave.org/?a=blobdiff_plain;f=main.go;h=0965a93e8eef7dcd68df08b9b1f3760c8e93286bbbdefdf74b3bf8e3c813bfa9;hb=512b4ec45c040338f9aea5c1e53783b817dfb85198b801eba892a452681f40b0;hp=c8615fdd85d4f2b76db67f755348feb0a9baf32c17bfdab0b72473fdb634dd58;hpb=db65ffeff7274def395c8ee747873d0e9d8250b75f543b6ac0d7bbd079cce66d;p=glocate.git diff --git a/main.go b/main.go index c8615fd..0965a93 100644 --- a/main.go +++ b/main.go @@ -1,13 +1,34 @@ +/* +glocate -- ZFS-diff-friendly locate-like utility +Copyright (C) 2022-2023 Sergey Matveev + +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, version 3 of the License. + +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 . +*/ + package main import ( "flag" "log" "os" + "path" + "path/filepath" "strings" "syscall" ) +var TmpDir string + type Ent struct { name []string mtime int64 @@ -32,14 +53,21 @@ func dbCommit(dbPath string, tmp *os.File) { func main() { dbPath := flag.String("db", "glocate.db", "Path to database") doIndex := flag.Bool("index", false, "Perform indexing") - doUpdate := flag.Bool("update", false, "Feed zfs-diff and update the database") - strip := flag.String("strip", "", "Strip prefix from zfs-diff's paths") + doUpdate := flag.String("update", "", "Update database") showMachine := flag.Bool("machine", false, "Show machine friendly") showTree := flag.Bool("tree", false, "Show human-friendly tree") dryRun := flag.Bool("n", false, "Dry run, do not overwrite database") + rootPath := flag.String("root", "", "Search only that part of tree") flag.Parse() log.SetFlags(log.Ldate | log.Ltime | log.Lmicroseconds | log.Lshortfile) + var err error + TmpDir, err = filepath.Abs(*dbPath) + if err != nil { + panic(err) + } + TmpDir = path.Dir(TmpDir) + if *doIndex { tmp := index() tmp.Close() @@ -49,8 +77,8 @@ func main() { return } - if *doUpdate { - tmp := updateWithDiff(*dbPath, *strip) + if *doUpdate != "" { + tmp := updateWithDiff(*dbPath, *doUpdate) tmp.Close() if !*dryRun { dbCommit(*dbPath, tmp) @@ -79,15 +107,42 @@ func main() { }() var root []string + if *rootPath != "" { + root = strings.Split("./"+*rootPath, "/") + } + + var pat string if len(flag.Args()) > 0 { - root = strings.Split("./"+flag.Arg(0), "/") + pat = "*" + flag.Arg(0) + "*" } rootMet := false + var matched bool + var namePrev []string + var i int for ent := range entsReader { if hasPrefix(ent.name, root) { - entsPrinter <- ent rootMet = true + if pat == "" { + entsPrinter <- ent + continue + } + for i = 0; i < len(ent.name); i++ { + if i == len(namePrev) || ent.name[i] != namePrev[i] { + break + } + } + for ; i < len(ent.name); i++ { + matched, err = path.Match(pat, + strings.ToLower(strings.TrimSuffix(ent.name[i], "/"))) + if err != nil { + log.Fatalln(err) + } + } + if matched { + entsPrinter <- ent + } + namePrev = ent.name } else if rootMet { break }