aboutsummaryrefslogtreecommitdiff
path: root/cmd/hlang/main.go
blob: 538e0a93c218de9a1f57df207533224f0403eeb9 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
package main

import (
	"flag"
	"fmt"
	"io/ioutil"
	"log"
	"os"

	"within.website/x/cmd/hlang/run"
	"within.website/x/internal"
)

var _ = func() error { log.SetFlags(log.LstdFlags | log.Llongfile); return nil }()

var (
	program      = flag.String("p", "", "h program to compile/run")
	outFname     = flag.String("o", "", "if specified, write the webassembly binary created by -p here")
	port         = flag.String("port", "", "HTTP port to listen on")
	sockpath     = flag.String("sockpath", "", "Unix domain socket to listen on")
	writeTao     = flag.Bool("koan", false, "if true, print the h koan and then exit")
	writeVersion = flag.Bool("v", false, "if true, print the version of h and then exit")
)

const koan = `And Jesus said unto the theologians, "Who do you say that I am?"

They replied: "You are the eschatological manifestation of the ground of our
being, the kerygma of which we find the ultimate meaning in our interpersonal
relationships."

And Jesus said "...What?"

Some time passed and one of them spoke "h".

Jesus was enlightened.`

func tao() {
	fmt.Println(koan)
	os.Exit(0)
}

func oneOff() error {
	log.Println("compiling...")
	comp, err := compile(*program)
	if err != nil {
		return err
	}

	log.Println("running...")
	er, err := run.Run(comp.Binary)
	if err != nil {
		return err
	}

	log.Println("success!")

	log.Printf("exec time:\t%s", er.ExecTime)
	log.Println("output:")
	fmt.Print(er.Output)

	if *outFname != "" {
		err := ioutil.WriteFile(*outFname, comp.Binary, 0666)
		if err != nil {
			return err
		}

		log.Printf("wrote %d bytes to %s", len(comp.Binary), *outFname)
	}

	return nil
}

func main() {
	internal.HandleStartup()

	if *writeVersion {
		dumpVersion()
	}

	if *writeTao {
		tao()
	}

	if *program != "" {
		err := oneOff()
		if err != nil {
			panic(err)
		}

		return
	}

	if *port != "" || *sockpath != "" {
		err := doHTTP()
		if err != nil {
			panic(err)
		}

		return
	}
}