// xds-gdb: a wrapper on gdb tool for X(cross) Development System. package main import ( "bufio" "fmt" "io/ioutil" "os" "os/signal" "os/user" "syscall" "time" "strings" "path" "github.com/Sirupsen/logrus" "github.com/codegangsta/cli" common "github.com/iotbzh/xds-common/golib" "github.com/joho/godotenv" ) var appAuthors = []cli.Author{ cli.Author{Name: "Sebastien Douheret", Email: "sebastien@iot.bzh"}, } // AppName name of this application var AppName = "xds-gdb" // AppVersion Version of this application // (set by Makefile) var AppVersion = "?.?.?" // AppSubVersion is the git tag id added to version string // Should be set by compilation -ldflags "-X main.AppSubVersion=xxx" // (set by Makefile) var AppSubVersion = "unknown-dev" // Create logger var log = logrus.New() var logFileInitial = "/tmp/xds-gdb.log" // Application details const ( appCopyright = "Apache-2.0" defaultLogLevel = "warning" ) // Exit events type exitResult struct { error error code int } // EnvVar - Environment variables used by application type EnvVar struct { Name string Usage string Destination *string } // exitError terminates this program with the specified error func exitError(code syscall.Errno, f string, a ...interface{}) { err := fmt.Sprintf(f, a...) fmt.Fprintf(os.Stderr, err+"\n") log.Debugf("Exit: code=%v, err=%s", code, err) os.Exit(int(code)) } // main func main() { var uri, prjID, rPath, logLevel, logFile, sdkid, confFile, gdbNative string var listProject bool var err error // Init Logger and set temporary file and level for the 1st part // IOW while XDS_LOGLEVEL and XDS_LOGFILE options are not parsed logFile = logFileInitial fdL, err := os.OpenFile(logFileInitial, os.O_CREATE|os.O_TRUNC|os.O_WRONLY, 0666) if err != nil { msgErr := fmt.Sprintf("Cannot create log file %s", logFileInitial) exitError(syscall.EPERM, msgErr) } log.Formatter = &logrus.TextFormatter{} log.Out = fdL log.Level = logrus.DebugLevel uri = "localhost:8000" logLevel = defaultLogLevel // Create a new App instance app := cli.NewApp() app.Name = AppName app.Usage = "wrapper on gdb for X(cross) Development System." app.Version = AppVersion + " (" + AppSubVersion + ")" app.Authors = appAuthors app.Copyright = appCopyright app.Metadata = make(map[string]interface{}) app.Metadata["version"] = AppVersion app.Metadata["git-tag"] = AppSubVersion app.Metadata["logger"] = log app.Flags = []cli.Flag{ cli.BoolFlag{ Name: "list, ls", Usage: "list existing xds projects", Destination: &listProject, }, } appEnvVars := []EnvVar{ EnvVar{ Name: "XDS_CONFIG", Usage: "env config file to source on startup", Destination: &confFile, }, EnvVar{ Name: "XDS_LOGLEVEL", Usage: "logging level (supported levels: panic, fatal, error, warn, info, debug)", Destination: &logLevel, }, EnvVar{ Name: "XDS_LOGFILE", Usage: "logging file (default: " + logFileInitial + ")", Destination: &logFile, }, EnvVar{ Name: "XDS_NATIVE_GDB", Usage: "use native gdb instead of remote XDS server", Destination: &gdbNative, }, EnvVar{ Name: "XDS_PROJECT_ID", Usage: "project ID you want to build (mandatory variable)", Destination: &prjID, }, EnvVar{ Name: "XDS_RPATH", Usage: "relative path into project", Destination: &rPath, }, EnvVar{ Name: "XDS_SDK_ID", Usage: "Cross Sdk ID to use to build project", Destination: &sdkid, }, EnvVar{ Name: "XDS_SERVER_URL", Usage: "remote XDS server url", Destination: &uri, }, } // Process gdb arguments log.Debugf("xds-gdb started with args: %v", os.Args) args := make([]string, len(os.Args)) args[0] = os.Args[0] gdbArgs := make([]string, len(os.Args)) // Split xds-xxx options from gdb options copy(gdbArgs, os.Args[1:]) for idx, a := range os.Args[1:] { // Specific case to print help or version of xds-gdb switch a { case "--help", "-h", "--version", "-v", "--list", "-ls": args[1] = a goto endloop case "--": // Detect skip option (IOW '--') to split arguments copy(args, os.Args[0:idx+1]) copy(gdbArgs, os.Args[idx+2:]) goto endloop } } endloop: // Parse gdb arguments to detect: // --tty option: used for inferior/ tty of debugged program // -x/--command option: XDS env vars may be set within gdb command file clientPty := "" gdbCmdFile := "" for idx, a := range gdbArgs { switch { case strings.HasPrefix(a, "--tty="): clientPty = a[len("--tty="):] gdbArgs[idx] = "" case a == "--tty": case strings.HasPrefix(a, "-tty"): clientPty = gdbArgs[idx+1] gdbArgs[idx] = "" gdbArgs[idx+1] = "" case strings.HasPrefix(a, "--command="): gdbCmdFile = a[len("--command="):] case a == "--command": case strings.HasPrefix(a, "-x"): gdbCmdFile = gdbArgs[idx+1] } } // Source config env file // (we cannot use confFile var because env variables setting is just after) envMap, confFile, err := loadConfigEnvFile(os.Getenv("XDS_CONFIG"), gdbCmdFile) log.Infof("Load env config: envMap=%v, confFile=%v, err=%v", envMap, confFile, err) // Only rise an error when args is not set (IOW when --help or --version is not set) if len(args) == 1 { if err != nil { exitError(syscall.ENOENT, err
Different components of the AGL layers are under different licenses (a mix
of MIT and GPLv2). See LICENSE.GPL-2.0-only and LICENSE.MIT for further
details of the individual licenses.

All metadata (e.g. .bb, .bbappend, .bbclass, .inc, templates/* and similar)
is MIT licensed unless otherwise stated.
Source code included in tree for individual recipes (e.g. patches) are under
the LICENSE stated in the associated recipe (.bb file) unless otherwise stated.

License information for any other files (scripts) is either explicitly stated
or defaults to GPL version 2 only.

Individual files can contain the following style tags instead of the full
license text to identify their license:

    SPDX-License-Identifier: GPL-2.0-only
    SPDX-License-Identifier: MIT

This enables machine processing of license information based on the SPDX
License Identifiers that are here available: http://spdx.org/licenses/
URL=localhost:8800 */ func extractEnvFromCmdFile(cmdFile string) (string, error) { if !common.Exists(cmdFile) { return "", nil } cFd, err := os.Open(cmdFile) if err != nil { return "", fmt.Errorf("Cannot open %s : %s", cmdFile, err.Error()) } defer cFd.Close() var lines []string scanner := bufio.NewScanner(cFd) for scanner.Scan() { lines = append(lines, scanner.Text()) } if err = scanner.Err(); err != nil { return "", fmt.Errorf("Cannot parse %s : %s", cmdFile, err.Error()) } envFile, err := ioutil.TempFile("", "xds-gdb_env.ini") if err != nil { return "", fmt.Errorf("Error while creating temporary env file: %s", err.Error()) } envFileName := envFile.Name() defer envFile.Close() envFound := false for _, ln := range lines { ln = strings.TrimSpace(ln) if strings.HasPrefix(ln, "#") && strings.Contains(ln, ":XDS-ENV:") { env := strings.SplitAfterN(ln, ":XDS-ENV:", 2) if len(env) == 2 { envFound = true if _, err := envFile.WriteString(strings.TrimSpace(env[1]) + "\n"); err != nil { return "", fmt.Errorf("Error write into temporary env file: %s", err.Error()) } } else { log.Warnf("Error while decoding line %s", ln) } } } if !envFound { ff := envFileName defer os.Remove(ff) envFileName = "" } return envFileName, nil }