diff --git a/cmd/main.go b/cmd/main.go index 45bcfe7..ac73ff3 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -10,11 +10,11 @@ import ( ) type Arguments struct { - Input string `arg:"positional,required"` - Output string `arg:"positional"` + Output string `arg:"positional,required"` + Input []string `arg:"positional,required"` - RamStart int `arg:"--ram-start" default:"0x5000"` - RomStart int `arg:"--rom-start" default:"0xE000"` + RamStart int `arg:"--ram-start" default:"0x6000"` + RomStart int `arg:"--rom-start" default:"0x8000"` } func main() { @@ -29,20 +29,41 @@ func main() { } func run(args *Arguments) error { - input, err := os.ReadFile(args.Input) - if err != nil { - return err + var config *dasmlbl.Config + var err error + + for _, infile := range args.Input { + input, err := os.ReadFile(infile) + if err != nil { + return err + } + + + l, ch := dasmlbl.NewLexer(string(input)) + go l.Run() + + parser := dasmlbl.NewParser(ch) + cfg, err := parser.Run() + if err != nil { + fmt.Printf("[%s] %s\n", infile, err) + } + + if config == nil { + config = cfg + } else { + config.Append(cfg) + } } - l, ch := dasmlbl.NewLexer(string(input)) - go l.Run() - - parser := dasmlbl.NewParser(ch) - config, err := parser.Run() - if err != nil { - fmt.Println(err) + if config == nil { + return fmt.Errorf("no configs parsed") } + //input, err := os.ReadFile(args.Input) + //if err != nil { + // return err + //} + var output *os.File if args.Output == "" { output = os.Stdout diff --git a/config.go b/config.go index 34a7493..bd3b842 100644 --- a/config.go +++ b/config.go @@ -30,6 +30,12 @@ type Config struct { Segments []Segment } +func (c *Config) Append(other *Config) { + c.Labels = append(c.Labels, other.Labels...) + c.Ranges = append(c.Ranges, other.Ranges...) + c.Segments = append(c.Segments, other.Segments...) +} + type Label struct { Name string Address int diff --git a/lex.go b/lex.go index 361ae7a..f28b497 100644 --- a/lex.go +++ b/lex.go @@ -61,6 +61,19 @@ func (l *Lexer) next() rune { return r } +func (l *Lexer) peek() rune { + if l.pos >= len(l.input) { + l.width = 0 + return unicode_EOF + } + + r, size := utf8.DecodeRuneInString(l.input[l.pos:]) + if size == 0 { + panic(fmt.Sprintf("zero width at %d", l.pos)) + } + return r +} + func (l *Lexer) backup() { l.pos -= l.width } @@ -177,6 +190,13 @@ func lexString(l *Lexer) stateFn { l.items <- LexItem{lex_Error, "EOF before string end"} return nil } + + if r == '\\' && l.peek() == '"' { + r = l.next() + //fmt.Printf("consuming %c\n", r) // consume + continue + } + if r == '"' { break } diff --git a/parse.go b/parse.go index 8ed9b69..8df74bd 100644 --- a/parse.go +++ b/parse.go @@ -139,7 +139,7 @@ func (p *Parser) parseRange() error { itm = p.next() if itm.typ != lex_Semicolon { - return fmt.Errorf("missing semicolon") + return fmt.Errorf("[parseRange] missing semicolon") } } @@ -213,7 +213,7 @@ func (p *Parser) parseLabel() error { itm = p.next() if itm.typ != lex_Semicolon { - return fmt.Errorf("missing semicolon") + return fmt.Errorf("[parseLabel] missing semicolon; %#v", lbl) } }