Пример #1
0
func main() {
	defer app.Exiting()
	x := app.New()
	stacks := false
	opts.NewFlag("F", "debug fuse requests", &zxfs.Debug)
	opts.NewFlag("D", "debug", &x.Debug)
	opts.NewFlag("s", "statistics", &sflag)
	opts.NewFlag("x", "addr: re-export locally the ql tree to this address", &xaddr)
	opts.NewFlag("S", "dump stacks on unmount for debugging", &stacks)
	args, err := opts.Parse(x.Args)
	if err != nil {
		app.Warn("%s", err)
		opts.Usage()
		app.Exits(err)
	}
	switch len(args) {
	case 0:
	case 1:
		mntdir = args[1]
	default:
		app.Warn("wrong number of arguments")
		opts.Usage()
		app.Exits("usage")
	}
	dprintf("debug on\n")
	qfs, err := qlfs.New("qlfs")
	if err != nil {
		app.Fatal(err)
	}
	qfs.Dbg = x.Debug
	qfs.Flags.Add("fdebug", &zxfs.Debug)
	st := &zx.IOstats{}
	qfs.IOstats = st
	if xaddr != "" {
		rfs.Server(qfs, xaddr)
	}
	err = zxfs.MountServer(qfs, mntdir)
	if sflag {
		st.Averages()
		app.Warn("%s iostats:\n%s\n", qfs.Name(), st)
	}
	if stacks {
		app.Warn("*** PANICING ON USER REQUEST (-S) ***")
		panic("stack dump")
	}
	if err != nil {
		app.Fatal("%s", err)
	}
	app.Warn("unmounted: exiting")
}
Пример #2
0
func pspdf(t *Text, wid int, out io.Writer, cline, outfig string) {
	// pipe the roff writer into a command to output ps and pdf
	cmd := exec.Command("sh", "-c", cline)
	cmd.Stdout = out
	stdin, err := cmd.StdinPipe()
	if err != nil {
		app.Fatal("pipe to sh: %s", err)
	}
	if err := cmd.Start(); err != nil {
		app.Fatal("pipe to sh: %s", err)
	}
	wrroff(t, wid, stdin, outfig)
	stdin.Close()
	if err := cmd.Wait(); err != nil {
		app.Warn("pspdf: sh: %s", err)
	}
}
Пример #3
0
func main() {
	defer app.Exiting()
	os.Args[0] = "auth"
	app.New()
	dfltdir := auth.KeyDir()
	dir = dfltdir
	opts.NewFlag("d", "adir: clive auth dir", &dir)
	opts.NewFlag("f", "force write of key file when file already exists", &force)
	args, err := opts.Parse(os.Args)
	if err != nil {
		app.Warn("%s", err)
		opts.Usage()
		app.Exits(err)
	}
	if len(args) < 3 {
		opts.Usage()
		app.Exits("usage")
	}
	name, user, secret := args[0], args[1], args[2]
	groups := args[3:]
	file := auth.KeyFile(dir, name)
	fi, _ := os.Stat(file)
	if fi != nil && !force {
		app.Fatal("key file already exists")
	}
	err = auth.SaveKey(dir, name, user, secret, groups...)
	if err != nil {
		app.Fatal("%s: %s", file, err)
	}
	ks, err := auth.LoadKey(dir, name)
	if err != nil {
		app.Fatal("can't load key: %s", err)
	}
	for _, k := range ks {
		if k.Uid == user {
			app.Warn("%s", file)
			return
		}
	}
	app.Fatal("bad user")
}
Пример #4
0
func (t *Text) indentPars() {
	top := &Elem{}
	t.Elems = indentedPars(top, t.Elems)
	if len(t.Elems) > 0 {
		app.Fatal("paragraphs left at lvl %d", t.Elems[0].indent)
	}
	t.Elems = top.Child
	t.iprintf("\nindented pars:\n")
	for _, e := range t.Elems {
		t.iprintf("%s\n", e)
	}
	t.iprintf("\n")
}
Пример #5
0
// Add lf or gf to the 1st child of a pipe if it's a std pipe and not |a b c or -|a b c
// Add |pf to std pipes that have a single child
// No rewrite happens in inner pipes within subcmds, because they inherit the
// input from the outer command.
// builtins that do run here do not use a rewrite.
func (x *xCmd) pipeRewrite(nd *Nd) *Nd {
	if x.plvl > 0 || nd == nil {
		return nd
	}
	if nd.Kind != Npipe {
		app.Fatal("pipeRewrite bug")
	}
	if len(nd.Child) == 0 {
		return nd
	}
	c := nd.Child[0]
	if c.Kind != Nexec || c.hasInOutRedirs() {
		return nd
	}
	if c.isHereCmd() || c.isCmd(noRewrites...) {
		return nd
	}
	c.Child = append(c.Child, nil)
	copy(c.Child[1:], c.Child[0:])
	lf := "lf"
	if nd.IsGet {
		lf = "gf"
	}
	c.Child[0] = &Nd{Kind: Nname, Args: []string{lf}}
	if len(nd.Child) > 1{
		f := nd.Child[1]
		if nd.IsGet || f.Kind != Nfor  || len(f.Child) == 0 || len(f.Child[0].Child) != 1 {
			return nd
		}
		// insert pf between lf and for
		nd.Child = append(nd.Child, nil)
		copy(nd.Child[2:], nd.Child[1:])
		pfnames := &Nd{Kind: Nname, Args: []string{"pf"}}
		pf := &Nd{Kind: Nexec, Child: []*Nd{pfnames}}
		pf.Redirs = append(pf.Redirs, x.newRedir("0", "|", false)...)
		pf.Redirs = append(pf.Redirs, x.newRedir("1", "|", false)...)
		nd.Child[1] = pf
		return nd
	}
	c.Redirs = append(c.Redirs, x.newRedir("1", "|", false)...)
	x.noDups(c.Redirs)
	pfnames := &Nd{Kind: Nname, Args: []string{"pf"}}
	pf := &Nd{Kind: Nexec, Child: []*Nd{pfnames}}
	pf.Redirs = append(pf.Redirs, x.newRedir("0", "|", false)...)
	nd.Child = append(nd.Child, pf)
	return nd
}
Пример #6
0
func runTODO(x *xEnv, argv ...string) error {
	defer app.Exiting()
	app.Fatal("bug: todo: %v", app.Args())
	return nil
}
Пример #7
0
func main() {
	defer app.Exiting()
	os.Args[0] = "Q"
	c := app.New()
	opts.NewFlag("c", "ignored for compatibility", &dummy)
	opts.NewFlag("D", "debug", &c.Debug)
	edir := dbg.Usr
	opts.NewFlag("e", "env: qlfs environment name (defaults to uid)", &edir)
	opts.NewFlag("q", "qldir: qlfs root dir (defaults to /n/ql)", &ql)
	args, err := opts.Parse(os.Args)
	if err != nil {
		app.Warn("%s", err)
		opts.Usage()
		app.Exits(err)
	}
	cmd := ""
	if len(args) == 0 {
		app.Warn("no command given")
		opts.Usage()
		app.Exits(err)
	}
	cmd = strings.Join(args, " ")
	app.Dprintf("run %s\n", cmd)
	_, err = os.Stat(path.Join(ql, "Ctl"))
	if err != nil {
		app.Fatal("qlfs: %s", err)
	}
	env := path.Join(ql, edir)
	_, err = os.Stat(env)
	if err != nil {
		err = os.Mkdir(env, 0775)
	}
	if err != nil {
		app.Fatal("%s", err)
	}

	cdir := fmt.Sprintf("%s/%d", env, os.Getpid())
	if err := os.Mkdir(cdir, 0755); err != nil {
		app.Fatal("%s", err)
	}
	var b bytes.Buffer
	io.Copy(&b, os.Stdin)
	if err := ioutil.WriteFile(path.Join(cdir, "in"), b.Bytes(), 0644); err != nil {
		os.RemoveAll(cdir)
		app.Fatal("writing in: %s", err)
	}
	if err := ioutil.WriteFile(path.Join(cdir, "cmd"), []byte(cmd), 0644); err != nil {
		os.RemoveAll(cdir)
		app.Fatal("writing cmd: %s", err)
	}
	oc := make(chan bool, 2)
	pfd, err := os.Open(path.Join(cdir, "pout"))
	if err != nil {
		app.Warn("out: %s", err)
		oc <- true
	} else {
		go func() {
			io.Copy(os.Stdout, pfd)
			pfd.Close()
			oc <- true
		}()
	}
	efd, err := os.Open(path.Join(cdir, "perr"))
	if err != nil {
		app.Warn("err: %s", err)
		oc <- true
	} else {
		go func() {
			io.Copy(os.Stderr, efd)
			efd.Close()
			oc <- true
		}()
	}
	<-oc
	<-oc
	sts, err := ioutil.ReadFile(path.Join(cdir, "wait"))
	os.RemoveAll(cdir)
	if err != nil {
		app.Exits(err)
	}
	s := string(sts)
	if s == "success" {
		s = ""
	}
	app.Exits(s)
}
Пример #8
0
// Define a new flag with the given name and usage.
// valuep must be a pointer to the argument type and will be set to
// the command line flag value if the flag is found.
// Known types are bool, int, Counter, Octal, Hexa, int64, uint64, string,
// float64, time.Duration, time.Time, and []string.
// []string is a string option that may be repeated.
// The time formats understood are
//	"01/02"
//	"01/02/06"
//	"01/02/2006"
//	"2006/0102"
//	"15:04:05"
//	"15:04"
//	"3pm"
//	"3:04pm"
//	"01/02 15:04"
//	"01/02/06 15:04"
//	"01/02/2006 15:04"
//	"2006/0102 15:04 "
//
// If the name is "+..." or "-..." and vp is *int, then it is understood as
// a request to accept +number or -number as an argument.
//
// The help string should just describe the flag for flags with no
// argument, and should be something like "dir: do this with dir"
// if the flag accepts a "dir" argument. This convention is used to generate
// a good usage diagnostic.
func (f *Flags) NewFlag(name, help string, vp interface{}) {
	if vp == nil {
		app.Fatal("flag %s: nil value", name)
	}
	if len(name) == 0 {
		app.Fatal("empty flag name")
	}
	if f.defs[name] != nil {
		app.Fatal("flag %s redefined", name)
	}
	aname := ""
	if i := strings.Index(help, ":"); i > 0 {
		aname = help[:i]
	}
	switch vp.(type) {
	case *bool:

	case *int:
		if aname == "" {
			aname = "num"
		}
		if name[0] == '+' {
			if f.plus != nil {
				app.Fatal("flag +number redefined")
			}
			f.plus = &def{name: name, help: help, valp: vp, argname: aname}
			return
		}
		if name[0] == '-' {
			if f.minus != nil {
				app.Fatal("flag -number redefined")
			}
			f.minus = &def{name: name, help: help, valp: vp, argname: aname}
			return
		}
	case *Counter:
	case *Octal, *Hexa, *int64, *uint64, *float64:
		if aname == "" {
			aname = "num"
		}
	case *string, *[]string:
		if aname == "" {
			aname = "str"
		}
	case *time.Duration:
		if aname == "" {
			aname = "ival"
		}
	case *time.Time:
		if aname == "" {
			aname = "time"
		}
	case *Range:
		if aname == "" {
			aname = "range"
		}
	default:
		app.Fatal("flag %s: unknown flag type", name)
	}
	if name[0]=='+' || name[0]=='-' {
		app.Fatal("name '±...' is only for *int")
	}
	f.defs[name] = &def{name: name, help: help, valp: vp, argname: aname}
}