github.com/kdevb0x/go@v0.0.0-20180115030120-39687051e9e7/src/cmd/internal/objabi/flag.go (about)

     1  // Copyright 2015 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package objabi
     6  
     7  import (
     8  	"flag"
     9  	"fmt"
    10  	"os"
    11  	"strconv"
    12  	"strings"
    13  )
    14  
    15  func Flagcount(name, usage string, val *int) {
    16  	flag.Var((*count)(val), name, usage)
    17  }
    18  
    19  func Flagfn1(name, usage string, f func(string)) {
    20  	flag.Var(fn1(f), name, usage)
    21  }
    22  
    23  func Flagprint(fd int) {
    24  	if fd == 1 {
    25  		flag.CommandLine.SetOutput(os.Stdout)
    26  	}
    27  	flag.PrintDefaults()
    28  }
    29  
    30  func Flagparse(usage func()) {
    31  	flag.Usage = usage
    32  	flag.Parse()
    33  }
    34  
    35  func AddVersionFlag() {
    36  	flag.Var(versionFlag{}, "V", "print version and exit")
    37  }
    38  
    39  var buildID string // filled in by linker
    40  
    41  type versionFlag struct{}
    42  
    43  func (versionFlag) IsBoolFlag() bool { return true }
    44  func (versionFlag) Get() interface{} { return nil }
    45  func (versionFlag) String() string   { return "" }
    46  func (versionFlag) Set(s string) error {
    47  	name := os.Args[0]
    48  	name = name[strings.LastIndex(name, `/`)+1:]
    49  	name = name[strings.LastIndex(name, `\`)+1:]
    50  	name = strings.TrimSuffix(name, ".exe")
    51  	p := Expstring()
    52  	if p == DefaultExpstring() {
    53  		p = ""
    54  	}
    55  	sep := ""
    56  	if p != "" {
    57  		sep = " "
    58  	}
    59  
    60  	// The go command invokes -V=full to get a unique identifier
    61  	// for this tool. It is assumed that the release version is sufficient
    62  	// for releases, but during development we include the full
    63  	// build ID of the binary, so that if the compiler is changed and
    64  	// rebuilt, we notice and rebuild all packages.
    65  	if s == "full" && strings.HasPrefix(Version, "devel") {
    66  		p += " buildID=" + buildID
    67  	}
    68  	fmt.Printf("%s version %s%s%s\n", name, Version, sep, p)
    69  	os.Exit(0)
    70  	return nil
    71  }
    72  
    73  // count is a flag.Value that is like a flag.Bool and a flag.Int.
    74  // If used as -name, it increments the count, but -name=x sets the count.
    75  // Used for verbose flag -v.
    76  type count int
    77  
    78  func (c *count) String() string {
    79  	return fmt.Sprint(int(*c))
    80  }
    81  
    82  func (c *count) Set(s string) error {
    83  	switch s {
    84  	case "true":
    85  		*c++
    86  	case "false":
    87  		*c = 0
    88  	default:
    89  		n, err := strconv.Atoi(s)
    90  		if err != nil {
    91  			return fmt.Errorf("invalid count %q", s)
    92  		}
    93  		*c = count(n)
    94  	}
    95  	return nil
    96  }
    97  
    98  func (c *count) Get() interface{} {
    99  	return int(*c)
   100  }
   101  
   102  func (c *count) IsBoolFlag() bool {
   103  	return true
   104  }
   105  
   106  func (c *count) IsCountFlag() bool {
   107  	return true
   108  }
   109  
   110  type fn0 func()
   111  
   112  func (f fn0) Set(s string) error {
   113  	f()
   114  	return nil
   115  }
   116  
   117  func (f fn0) Get() interface{} { return nil }
   118  
   119  func (f fn0) String() string { return "" }
   120  
   121  func (f fn0) IsBoolFlag() bool {
   122  	return true
   123  }
   124  
   125  type fn1 func(string)
   126  
   127  func (f fn1) Set(s string) error {
   128  	f(s)
   129  	return nil
   130  }
   131  
   132  func (f fn1) String() string { return "" }