github.com/tinygo-org/tinygo@v0.31.3-0.20240404173401-90b0bf646c27/compileopts/options.go (about)

     1  package compileopts
     2  
     3  import (
     4  	"fmt"
     5  	"regexp"
     6  	"strings"
     7  	"time"
     8  )
     9  
    10  var (
    11  	validGCOptions            = []string{"none", "leaking", "conservative", "custom", "precise"}
    12  	validSchedulerOptions     = []string{"none", "tasks", "asyncify"}
    13  	validSerialOptions        = []string{"none", "uart", "usb", "rtt"}
    14  	validPrintSizeOptions     = []string{"none", "short", "full"}
    15  	validPanicStrategyOptions = []string{"print", "trap"}
    16  	validOptOptions           = []string{"none", "0", "1", "2", "s", "z"}
    17  )
    18  
    19  // Options contains extra options to give to the compiler. These options are
    20  // usually passed from the command line, but can also be passed in environment
    21  // variables for example.
    22  type Options struct {
    23  	GOOS            string // environment variable
    24  	GOARCH          string // environment variable
    25  	GOARM           string // environment variable (only used with GOARCH=arm)
    26  	Directory       string // working dir, leave it unset to use the current working dir
    27  	Target          string
    28  	Opt             string
    29  	GC              string
    30  	PanicStrategy   string
    31  	Scheduler       string
    32  	StackSize       uint64 // goroutine stack size (if none could be automatically determined)
    33  	Serial          string
    34  	Work            bool // -work flag to print temporary build directory
    35  	InterpTimeout   time.Duration
    36  	PrintIR         bool
    37  	DumpSSA         bool
    38  	VerifyIR        bool
    39  	SkipDWARF       bool
    40  	PrintCommands   func(cmd string, args ...string) `json:"-"`
    41  	Semaphore       chan struct{}                    `json:"-"` // -p flag controls cap
    42  	Debug           bool
    43  	PrintSizes      string
    44  	PrintAllocs     *regexp.Regexp // regexp string
    45  	PrintStacks     bool
    46  	Tags            []string
    47  	GlobalValues    map[string]map[string]string // map[pkgpath]map[varname]value
    48  	TestConfig      TestConfig
    49  	Programmer      string
    50  	OpenOCDCommands []string
    51  	LLVMFeatures    string
    52  	PrintJSON       bool
    53  	Monitor         bool
    54  	BaudRate        int
    55  	Timeout         time.Duration
    56  }
    57  
    58  // Verify performs a validation on the given options, raising an error if options are not valid.
    59  func (o *Options) Verify() error {
    60  	if o.GC != "" {
    61  		valid := isInArray(validGCOptions, o.GC)
    62  		if !valid {
    63  			return fmt.Errorf(`invalid gc option '%s': valid values are %s`,
    64  				o.GC,
    65  				strings.Join(validGCOptions, ", "))
    66  		}
    67  	}
    68  
    69  	if o.Scheduler != "" {
    70  		valid := isInArray(validSchedulerOptions, o.Scheduler)
    71  		if !valid {
    72  			return fmt.Errorf(`invalid scheduler option '%s': valid values are %s`,
    73  				o.Scheduler,
    74  				strings.Join(validSchedulerOptions, ", "))
    75  		}
    76  	}
    77  
    78  	if o.Serial != "" {
    79  		valid := isInArray(validSerialOptions, o.Serial)
    80  		if !valid {
    81  			return fmt.Errorf(`invalid serial option '%s': valid values are %s`,
    82  				o.Serial,
    83  				strings.Join(validSerialOptions, ", "))
    84  		}
    85  	}
    86  
    87  	if o.PrintSizes != "" {
    88  		valid := isInArray(validPrintSizeOptions, o.PrintSizes)
    89  		if !valid {
    90  			return fmt.Errorf(`invalid size option '%s': valid values are %s`,
    91  				o.PrintSizes,
    92  				strings.Join(validPrintSizeOptions, ", "))
    93  		}
    94  	}
    95  
    96  	if o.PanicStrategy != "" {
    97  		valid := isInArray(validPanicStrategyOptions, o.PanicStrategy)
    98  		if !valid {
    99  			return fmt.Errorf(`invalid panic option '%s': valid values are %s`,
   100  				o.PanicStrategy,
   101  				strings.Join(validPanicStrategyOptions, ", "))
   102  		}
   103  	}
   104  
   105  	if o.Opt != "" {
   106  		if !isInArray(validOptOptions, o.Opt) {
   107  			return fmt.Errorf("invalid -opt=%s: valid values are %s", o.Opt, strings.Join(validOptOptions, ", "))
   108  		}
   109  	}
   110  
   111  	return nil
   112  }
   113  
   114  func isInArray(arr []string, item string) bool {
   115  	for _, i := range arr {
   116  		if i == item {
   117  			return true
   118  		}
   119  	}
   120  	return false
   121  }