wa 命令调整目录结构
This commit is contained in:
parent
d4c997cc1e
commit
c79fbbc593
|
|
@ -1,11 +1,36 @@
|
|||
// 版权 @2023 凹语言 作者。保留所有权利。
|
||||
|
||||
package appast
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/ast"
|
||||
"wa-lang.org/wa/internal/parser"
|
||||
"wa-lang.org/wa/internal/token"
|
||||
)
|
||||
|
||||
var CmdAst = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "ast",
|
||||
Usage: "parse Wa source code and print ast",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
err := PrintAST(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func PrintAST(filename string) error {
|
||||
fset := token.NewFileSet() // positions are relative to fset
|
||||
f, err := parser.ParseFile(nil, fset, filename, nil, 0)
|
||||
|
|
|
|||
|
|
@ -5,12 +5,99 @@ package appbuild
|
|||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/backends/compiler_wat"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
"wa-lang.org/wa/internal/loader"
|
||||
"wa-lang.org/wa/internal/wabt"
|
||||
)
|
||||
|
||||
var CmdBuild = &cli.Command{
|
||||
Name: "build",
|
||||
Usage: "compile Wa source code",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "output",
|
||||
Aliases: []string{"o"},
|
||||
Usage: "set output file",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
&cli.IntFlag{
|
||||
Name: "ld-stack-size",
|
||||
Usage: "set stack size",
|
||||
},
|
||||
&cli.IntFlag{
|
||||
Name: "ld-max-memory",
|
||||
Usage: "set max memory size",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
var input string
|
||||
if c.NArg() > 0 {
|
||||
input = c.Args().First()
|
||||
} else {
|
||||
input, _ = os.Getwd()
|
||||
}
|
||||
|
||||
outfile := c.String("output")
|
||||
if outfile == "" {
|
||||
if fi, _ := os.Lstat(input); fi != nil && fi.IsDir() {
|
||||
// /xxx/yyy/ => /xxx/yyy/output/yyy.wat
|
||||
} else {
|
||||
// /xxx/yyy/zzz.wa => /xxx/yyy/zzz.wat
|
||||
}
|
||||
outfile = "a.out.wasm"
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
watOutput, err := Build(opt, input)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
if outfile != "" && outfile != "-" {
|
||||
watFilename := outfile
|
||||
if !strings.HasSuffix(watFilename, ".wat") {
|
||||
watFilename += ".wat"
|
||||
}
|
||||
err := os.WriteFile(watFilename, []byte(watOutput), 0666)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
if strings.HasSuffix(outfile, ".wasm") {
|
||||
wasmBytes, err := wabt.Wat2Wasm(watOutput)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
if err := os.WriteFile(outfile, wasmBytes, 0666); err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
os.Remove(watFilename)
|
||||
}
|
||||
} else {
|
||||
fmt.Println(string(watOutput))
|
||||
}
|
||||
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func Build(opt *appbase.Option, filename string) ([]byte, error) {
|
||||
if _, err := os.Lstat(filename); err != nil {
|
||||
return nil, fmt.Errorf("%q not found", filename)
|
||||
|
|
|
|||
|
|
@ -1,13 +1,37 @@
|
|||
// 版权 @2023 凹语言 作者。保留所有权利。
|
||||
|
||||
package appcir
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/backends/compiler_c"
|
||||
"wa-lang.org/wa/internal/loader"
|
||||
)
|
||||
|
||||
var CmdCir = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "cir",
|
||||
Usage: "print cir code",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
err := PrintCIR(opt, c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func PrintCIR(opt *appbase.Option, filename string) error {
|
||||
cfg := opt.Config()
|
||||
prog, err := loader.LoadProgram(cfg, filename)
|
||||
|
|
|
|||
|
|
@ -0,0 +1,32 @@
|
|||
package appdev
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
|
||||
"wa-lang.org/wa/api"
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
)
|
||||
|
||||
var CmdDev = &cli.Command{
|
||||
// go run main.go debug
|
||||
Hidden: true,
|
||||
Name: "debug",
|
||||
Usage: "only for dev/debug",
|
||||
Action: func(c *cli.Context) error {
|
||||
wat, err := api.BuildFile(
|
||||
config.DefaultConfig(),
|
||||
"hello.wa", "func main() { println(123) }",
|
||||
)
|
||||
if err != nil {
|
||||
if len(wat) != 0 {
|
||||
fmt.Println(string(wat))
|
||||
}
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
fmt.Println(string(wat))
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
package appdoc
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
)
|
||||
|
||||
var CmdDoc = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "doc",
|
||||
Usage: "show documentation for package or symbol",
|
||||
Action: func(c *cli.Context) error {
|
||||
fmt.Println("TODO")
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
|
@ -9,9 +9,23 @@ import (
|
|||
"sort"
|
||||
"strings"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/format"
|
||||
)
|
||||
|
||||
var CmdFmt = &cli.Command{
|
||||
Name: "fmt",
|
||||
Usage: "format Wa source code file",
|
||||
Action: func(c *cli.Context) error {
|
||||
err := Fmt(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func Fmt(path string) error {
|
||||
if path == "" {
|
||||
if _, err := os.Lstat("wa.mod.json"); err == nil {
|
||||
|
|
|
|||
|
|
@ -12,9 +12,43 @@ import (
|
|||
"time"
|
||||
"unicode"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/waroot"
|
||||
)
|
||||
|
||||
var CmdInit = &cli.Command{
|
||||
Name: "init",
|
||||
Usage: "init a sketch Wa module",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "name",
|
||||
Aliases: []string{"n"},
|
||||
Usage: "set app name",
|
||||
Value: "hello",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "pkgpath",
|
||||
Aliases: []string{"p"},
|
||||
Usage: "set pkgpath file",
|
||||
Value: "myapp",
|
||||
},
|
||||
&cli.BoolFlag{
|
||||
Name: "update",
|
||||
Aliases: []string{"u"},
|
||||
Usage: "update example",
|
||||
},
|
||||
},
|
||||
|
||||
Action: func(c *cli.Context) error {
|
||||
err := InitApp(c.String("name"), c.String("pkgpath"), c.Bool("update"))
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func InitApp(name, pkgpath string, update bool) error {
|
||||
if name == "" {
|
||||
return fmt.Errorf("init failed: <%s> is empty", name)
|
||||
|
|
|
|||
|
|
@ -9,10 +9,30 @@ import (
|
|||
"io"
|
||||
"os"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/scanner"
|
||||
"wa-lang.org/wa/internal/token"
|
||||
)
|
||||
|
||||
var CmdLex = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "lex",
|
||||
Usage: "lex Wa source code and print token list",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
err := Lex(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func Lex(filename string) error {
|
||||
src, err := readSource(filename, nil)
|
||||
if err != nil {
|
||||
|
|
|
|||
|
|
@ -9,11 +9,68 @@ import (
|
|||
"path"
|
||||
"strings"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/backends/compiler_llvm"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
"wa-lang.org/wa/internal/loader"
|
||||
)
|
||||
|
||||
var CmdNative = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "native",
|
||||
Usage: "compile Wa source code to native executable",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "output",
|
||||
Aliases: []string{"o"},
|
||||
Usage: "set output file",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: "set native target",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
&cli.BoolFlag{
|
||||
Name: "debug",
|
||||
Usage: "dump orginal intermediate representation",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "clang",
|
||||
Usage: "set llvm/clang path",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "llc",
|
||||
Usage: "set llvm/llc path",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
outfile := c.String("output")
|
||||
target := c.String("target")
|
||||
debug := c.Bool("debug")
|
||||
infile := ""
|
||||
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
infile = c.Args().First()
|
||||
|
||||
opt := appbase.BuildOptions(c, config.WaBackend_llvm)
|
||||
if err := LLVMRun(opt, infile, outfile, target, debug); err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func LLVMRun(opt *appbase.Option, infile string, outfile string, target string, debug bool) error {
|
||||
cfg := opt.Config()
|
||||
|
||||
|
|
|
|||
|
|
@ -1,3 +1,21 @@
|
|||
// 版权 @2023 凹语言 作者。保留所有权利。
|
||||
|
||||
package applogo
|
||||
|
||||
import "wa-lang.org/wa/internal/3rdparty/cli"
|
||||
|
||||
var CmdLogo = &cli.Command{
|
||||
Name: "logo",
|
||||
Usage: "print Wa text format logo",
|
||||
Flags: []cli.Flag{
|
||||
&cli.BoolFlag{
|
||||
Name: "more",
|
||||
Aliases: []string{"m"},
|
||||
Usage: "print more logos",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
PrintLogo(c.Bool("more"))
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,23 @@
|
|||
package applsp
|
||||
|
||||
import (
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/lsp"
|
||||
)
|
||||
|
||||
var CmdLsp = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "lsp",
|
||||
Usage: "run Wa langugage server",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "log-file",
|
||||
Usage: "set log file",
|
||||
Value: "",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
lsp.NewLSPServer(&lsp.Option{}).Run()
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
|
@ -4,12 +4,35 @@ package appplay
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"os/exec"
|
||||
"runtime"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
)
|
||||
|
||||
var CmdPlay = &cli.Command{
|
||||
Name: "play",
|
||||
Usage: "start Wa playground",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "http",
|
||||
Value: ":2023",
|
||||
Usage: "set http address",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
err := RunPlayground(c.String("http"))
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func RunPlayground(addr string) error {
|
||||
if strings.HasPrefix(addr, ":") {
|
||||
addr = "localhost" + addr
|
||||
|
|
|
|||
|
|
@ -10,10 +10,31 @@ import (
|
|||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/app/appbuild"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
"wa-lang.org/wa/internal/wabt"
|
||||
"wa-lang.org/wa/internal/wazero"
|
||||
)
|
||||
|
||||
var CmdRun = &cli.Command{
|
||||
Name: "run",
|
||||
Usage: "compile and run Wa program",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
Run(c)
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func Run(c *cli.Context) {
|
||||
var infile string
|
||||
if c.NArg() > 0 {
|
||||
|
|
|
|||
|
|
@ -3,14 +3,36 @@
|
|||
package appssa
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"sort"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/loader"
|
||||
"wa-lang.org/wa/internal/ssa"
|
||||
)
|
||||
|
||||
var CmdSsa = &cli.Command{
|
||||
Hidden: true,
|
||||
Name: "ssa",
|
||||
Usage: "print Wa ssa code",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
err := SSARun(opt, c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func SSARun(opt *appbase.Option, filename string) error {
|
||||
cfg := opt.Config()
|
||||
prog, err := loader.LoadProgram(cfg, filename)
|
||||
|
|
|
|||
|
|
@ -9,6 +9,8 @@ import (
|
|||
"strings"
|
||||
"time"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/backends/compiler_wat"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
"wa-lang.org/wa/internal/loader"
|
||||
|
|
@ -17,6 +19,31 @@ import (
|
|||
"wa-lang.org/wa/waroot"
|
||||
)
|
||||
|
||||
var CmdTest = &cli.Command{
|
||||
Name: "test",
|
||||
Usage: "test Wa packages",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() < 1 {
|
||||
cli.ShowAppHelpAndExit(c, 0)
|
||||
}
|
||||
appArgs := c.Args().Slice()[1:]
|
||||
opt := appbase.BuildOptions(c)
|
||||
RunTest(opt.Config(), c.Args().First(), appArgs...)
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func RunTest(cfg *config.Config, pkgpath string, appArgs ...string) {
|
||||
var pkgList = []string{pkgpath}
|
||||
if pkgpath == "std" {
|
||||
|
|
|
|||
|
|
@ -0,0 +1,58 @@
|
|||
package appyacc
|
||||
|
||||
import (
|
||||
"os"
|
||||
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
)
|
||||
|
||||
var CmdYacc = &cli.Command{
|
||||
Name: "yacc",
|
||||
Usage: "generates parsers for LALR(1) grammars",
|
||||
ArgsUsage: "<input>",
|
||||
Flags: []cli.Flag{
|
||||
&cli.BoolFlag{
|
||||
Name: "l",
|
||||
Usage: "disable line directives",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "o",
|
||||
Usage: "set parser output file",
|
||||
Value: "y.wa",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "p",
|
||||
Usage: "name prefix to use in generated code",
|
||||
Value: "yy",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "v",
|
||||
Usage: "create parsing tables",
|
||||
Value: "y.output",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "c",
|
||||
Usage: "set copyright file",
|
||||
Value: "",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() != 1 {
|
||||
cli.ShowSubcommandHelpAndExit(c, 1)
|
||||
}
|
||||
InitFlags(Flags{
|
||||
Oflag: c.String("o"),
|
||||
Vflag: c.String("v"),
|
||||
Lflag: c.Bool("l"),
|
||||
Prefix: c.String("p"),
|
||||
Copyright: loadCopyright(c.String("c")),
|
||||
})
|
||||
Main(c.Args().First())
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func loadCopyright(filename string) string {
|
||||
data, _ := os.ReadFile(filename)
|
||||
return string(data)
|
||||
}
|
||||
|
|
@ -7,29 +7,26 @@
|
|||
package app
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
|
||||
"wa-lang.org/wa/api"
|
||||
"wa-lang.org/wa/internal/3rdparty/cli"
|
||||
"wa-lang.org/wa/internal/app/appast"
|
||||
"wa-lang.org/wa/internal/app/appbase"
|
||||
"wa-lang.org/wa/internal/app/appbuild"
|
||||
"wa-lang.org/wa/internal/app/appcir"
|
||||
"wa-lang.org/wa/internal/app/appdev"
|
||||
"wa-lang.org/wa/internal/app/appdoc"
|
||||
"wa-lang.org/wa/internal/app/appfmt"
|
||||
"wa-lang.org/wa/internal/app/appinit"
|
||||
"wa-lang.org/wa/internal/app/applex"
|
||||
"wa-lang.org/wa/internal/app/appllvm"
|
||||
"wa-lang.org/wa/internal/app/applogo"
|
||||
"wa-lang.org/wa/internal/app/applsp"
|
||||
"wa-lang.org/wa/internal/app/appplay"
|
||||
"wa-lang.org/wa/internal/app/apprun"
|
||||
"wa-lang.org/wa/internal/app/appssa"
|
||||
"wa-lang.org/wa/internal/app/apptest"
|
||||
"wa-lang.org/wa/internal/app/appyacc"
|
||||
"wa-lang.org/wa/internal/config"
|
||||
"wa-lang.org/wa/internal/lsp"
|
||||
"wa-lang.org/wa/internal/wabt"
|
||||
"wa-lang.org/wa/waroot"
|
||||
)
|
||||
|
||||
|
|
@ -40,6 +37,7 @@ func Main() {
|
|||
cliApp.Copyright = "Copyright 2018 The Wa Authors. All rights reserved."
|
||||
cliApp.Version = waroot.GetVersion()
|
||||
cliApp.EnableBashCompletion = true
|
||||
cliApp.HideHelpCommand = true
|
||||
|
||||
cliApp.CustomAppHelpTemplate = cli.AppHelpTemplate +
|
||||
"\nSee \"https://wa-lang.org\" for more information.\n"
|
||||
|
|
@ -74,443 +72,30 @@ func Main() {
|
|||
}
|
||||
|
||||
cliApp.Commands = []*cli.Command{
|
||||
{
|
||||
// go run main.go debug
|
||||
Hidden: true,
|
||||
Name: "debug",
|
||||
Usage: "only for dev/debug",
|
||||
Action: func(c *cli.Context) error {
|
||||
wat, err := api.BuildFile(
|
||||
config.DefaultConfig(),
|
||||
"hello.wa", "func main() { println(123) }",
|
||||
)
|
||||
if err != nil {
|
||||
if len(wat) != 0 {
|
||||
fmt.Println(string(wat))
|
||||
}
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
fmt.Println(string(wat))
|
||||
return nil
|
||||
},
|
||||
},
|
||||
// 用于调试(隐藏)
|
||||
appdev.CmdDev,
|
||||
|
||||
{
|
||||
Name: "play",
|
||||
Usage: "start Wa playground",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "http",
|
||||
Value: ":2023",
|
||||
Usage: "set http address",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
err := appplay.RunPlayground(c.String("http"))
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
// 用户可见子命令
|
||||
appplay.CmdPlay,
|
||||
appinit.CmdInit,
|
||||
appbuild.CmdBuild,
|
||||
apprun.CmdRun,
|
||||
appfmt.CmdFmt,
|
||||
apptest.CmdTest,
|
||||
appyacc.CmdYacc,
|
||||
applogo.CmdLogo,
|
||||
|
||||
{
|
||||
Name: "init",
|
||||
Usage: "init a sketch Wa module",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "name",
|
||||
Aliases: []string{"n"},
|
||||
Usage: "set app name",
|
||||
Value: "hello",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "pkgpath",
|
||||
Aliases: []string{"p"},
|
||||
Usage: "set pkgpath file",
|
||||
Value: "myapp",
|
||||
},
|
||||
&cli.BoolFlag{
|
||||
Name: "update",
|
||||
Aliases: []string{"u"},
|
||||
Usage: "update example",
|
||||
},
|
||||
},
|
||||
// 开发者用于测试(隐藏)
|
||||
applex.CmdLex,
|
||||
appast.CmdAst,
|
||||
appssa.CmdSsa,
|
||||
|
||||
Action: func(c *cli.Context) error {
|
||||
err := appinit.InitApp(c.String("name"), c.String("pkgpath"), c.Bool("update"))
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Name: "build",
|
||||
Usage: "compile Wa source code",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "output",
|
||||
Aliases: []string{"o"},
|
||||
Usage: "set output file",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
&cli.IntFlag{
|
||||
Name: "ld-stack-size",
|
||||
Usage: "set stack size",
|
||||
},
|
||||
&cli.IntFlag{
|
||||
Name: "ld-max-memory",
|
||||
Usage: "set max memory size",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
var input string
|
||||
if c.NArg() > 0 {
|
||||
input = c.Args().First()
|
||||
} else {
|
||||
input, _ = os.Getwd()
|
||||
}
|
||||
|
||||
outfile := c.String("output")
|
||||
if outfile == "" {
|
||||
if fi, _ := os.Lstat(input); fi != nil && fi.IsDir() {
|
||||
// /xxx/yyy/ => /xxx/yyy/output/yyy.wat
|
||||
} else {
|
||||
// /xxx/yyy/zzz.wa => /xxx/yyy/zzz.wat
|
||||
}
|
||||
outfile = "a.out.wasm"
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
watOutput, err := appbuild.Build(opt, input)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
if outfile != "" && outfile != "-" {
|
||||
watFilename := outfile
|
||||
if !strings.HasSuffix(watFilename, ".wat") {
|
||||
watFilename += ".wat"
|
||||
}
|
||||
err := os.WriteFile(watFilename, []byte(watOutput), 0666)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
if strings.HasSuffix(outfile, ".wasm") {
|
||||
wasmBytes, err := wabt.Wat2Wasm(watOutput)
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
if err := os.WriteFile(outfile, wasmBytes, 0666); err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
os.Remove(watFilename)
|
||||
}
|
||||
} else {
|
||||
fmt.Println(string(watOutput))
|
||||
}
|
||||
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Name: "run",
|
||||
Usage: "compile and run Wa program",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
apprun.Run(c)
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Name: "fmt",
|
||||
Usage: "format Wa source code file",
|
||||
Action: func(c *cli.Context) error {
|
||||
err := appfmt.Fmt(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Name: "test",
|
||||
Usage: "test Wa packages",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: fmt.Sprintf("set target os (%s)", strings.Join(config.WaOS_List, "|")),
|
||||
Value: config.WaOS_Default,
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() < 1 {
|
||||
cli.ShowAppHelpAndExit(c, 0)
|
||||
}
|
||||
appArgs := c.Args().Slice()[1:]
|
||||
opt := appbase.BuildOptions(c)
|
||||
apptest.RunTest(opt.Config(), c.Args().First(), appArgs...)
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "native",
|
||||
Usage: "compile Wa source code to native executable",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "output",
|
||||
Aliases: []string{"o"},
|
||||
Usage: "set output file",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "target",
|
||||
Usage: "set native target",
|
||||
Value: "",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "tags",
|
||||
Usage: "set build tags",
|
||||
},
|
||||
&cli.BoolFlag{
|
||||
Name: "debug",
|
||||
Usage: "dump orginal intermediate representation",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "clang",
|
||||
Usage: "set llvm/clang path",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "llc",
|
||||
Usage: "set llvm/llc path",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
outfile := c.String("output")
|
||||
target := c.String("target")
|
||||
debug := c.Bool("debug")
|
||||
infile := ""
|
||||
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
infile = c.Args().First()
|
||||
|
||||
opt := appbase.BuildOptions(c, config.WaBackend_llvm)
|
||||
if err := appllvm.LLVMRun(opt, infile, outfile, target, debug); err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "lex",
|
||||
Usage: "lex Wa source code and print token list",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
err := applex.Lex(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "ast",
|
||||
Usage: "parse Wa source code and print ast",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
err := appast.PrintAST(c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "ssa",
|
||||
Usage: "print Wa ssa code",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
err := appssa.SSARun(opt, c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "cir",
|
||||
Usage: "print cir code",
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() == 0 {
|
||||
fmt.Fprintf(os.Stderr, "no input file")
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
opt := appbase.BuildOptions(c)
|
||||
err := appcir.PrintCIR(opt, c.Args().First())
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "doc",
|
||||
Usage: "show documentation for package or symbol",
|
||||
Action: func(c *cli.Context) error {
|
||||
fmt.Println("TODO")
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Name: "yacc",
|
||||
Usage: "generates parsers for LALR(1) grammars",
|
||||
ArgsUsage: "<input>",
|
||||
Flags: []cli.Flag{
|
||||
&cli.BoolFlag{
|
||||
Name: "l",
|
||||
Usage: "disable line directives",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "o",
|
||||
Usage: "set parser output file",
|
||||
Value: "y.wa",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "p",
|
||||
Usage: "name prefix to use in generated code",
|
||||
Value: "yy",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "v",
|
||||
Usage: "create parsing tables",
|
||||
Value: "y.output",
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "c",
|
||||
Usage: "set copyright file",
|
||||
Value: "",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
if c.NArg() != 1 {
|
||||
cli.ShowSubcommandHelpAndExit(c, 1)
|
||||
}
|
||||
appyacc.InitFlags(appyacc.Flags{
|
||||
Oflag: c.String("o"),
|
||||
Vflag: c.String("v"),
|
||||
Lflag: c.Bool("l"),
|
||||
Prefix: c.String("p"),
|
||||
Copyright: loadCopyright(c.String("c")),
|
||||
})
|
||||
appyacc.Main(c.Args().First())
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Hidden: true,
|
||||
Name: "lsp",
|
||||
Usage: "run Wa langugage server",
|
||||
Flags: []cli.Flag{
|
||||
&cli.StringFlag{
|
||||
Name: "log-file",
|
||||
Usage: "set log file",
|
||||
Value: "",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
lsp.NewLSPServer(&lsp.Option{}).Run()
|
||||
return nil
|
||||
},
|
||||
},
|
||||
|
||||
{
|
||||
Name: "logo",
|
||||
Usage: "print Wa text format logo",
|
||||
Flags: []cli.Flag{
|
||||
&cli.BoolFlag{
|
||||
Name: "more",
|
||||
Aliases: []string{"m"},
|
||||
Usage: "print more logos",
|
||||
},
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
applogo.PrintLogo(c.Bool("more"))
|
||||
return nil
|
||||
},
|
||||
},
|
||||
// 待完善的子命令(隐藏)
|
||||
appllvm.CmdNative,
|
||||
appcir.CmdCir,
|
||||
appdoc.CmdDoc,
|
||||
applsp.CmdLsp,
|
||||
}
|
||||
|
||||
cliApp.Run(os.Args)
|
||||
}
|
||||
|
||||
func loadCopyright(filename string) string {
|
||||
data, _ := os.ReadFile(filename)
|
||||
return string(data)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -43,5 +43,7 @@ func setEnableTrace(parten string) {
|
|||
EnableTrace_app = true
|
||||
EnableTrace_compiler = true
|
||||
EnableTrace_loader = true
|
||||
default:
|
||||
panic("unknown trace flag: " + parten)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@ type PkgVFS struct {
|
|||
|
||||
// 通用配置信息
|
||||
type Config struct {
|
||||
WatOutput string // 输出的 wat 文件路径
|
||||
WaBackend string // 编译器后端
|
||||
WaRoot string // 凹 程序根目录, src 目录下是包代码, 为空时用内置标准库实现
|
||||
WaArch string // 目标 CPU
|
||||
|
|
|
|||
Loading…
Reference in New Issue