ref: f15de4539efb079f7c27ceb1daf4858a347ac832
parent: f756e0926ef4b94848ad8b7963cf85f088b81621
author: Ori Bernstein <ori@eigenstate.org>
date: Wed Sep 24 08:16:59 EDT 2014
Implement attribute list parsing.
--- a/bldfile
+++ b/bldfile
@@ -1,5 +1,5 @@
# comment
-bin mbld2 =
+bin mbld2 {ldscript = link.ld} =
build.myr
clean.myr
config.myr
--- a/build.myr
+++ b/build.myr
@@ -10,7 +10,7 @@
const buildall : (p : parser# -> bool)
const test : (p : parser# -> bool)
const build : (p : parser#, target : byte[:] -> bool)
- const buildbin : (bin : byte[:], inputs : byte[:][:] -> void)
+ const buildbin : (bin : byte[:], inputs : byte[:][:], ldscript : byte[:] -> void)
const buildlib : (lib : byte[:], inputs : byte[:][:] -> void)
;;
@@ -17,8 +17,8 @@
const buildall = {p
for t in p.targs
match t
- | `Bin [.name=bin, .inputs=leaves]:
- buildbin(bin, leaves)
+ | `Bin [.name=bin, .inputs=leaves, .ldscript=ldscript]:
+ buildbin(bin, leaves, ldscript)
| `Lib [.name=lib, .inputs=leaves]:
buildlib(lib, leaves)
| `Sub subs:
@@ -43,9 +43,9 @@
built = false
for t in p.targs
match t
- | `Bin [.name=bin, .inputs=leaves]:
+ | `Bin [.name=bin, .inputs=leaves, .ldscript=ldscript]:
if std.sleq(bin, targ)
- buildbin(bin, leaves)
+ buildbin(bin, leaves, ldscript)
built = true
;;
| `Lib [.name=lib, .inputs=leaves]:
@@ -70,9 +70,10 @@
-> built
}
-const buildbin = {bin, inputs
+const buildbin = {bin, inputs, ldscript
var dg
+ std.put("LD SCRIPT: %s\n", ldscript)
if !myrdeps(&dg, bin, inputs, false)
std.fatal(1, "Could not load dependencies for %s\n", bin)
;;
@@ -81,7 +82,7 @@
for d in deps
builddep(&dg, d, bin)
;;
- linkbin(&dg, bin, inputs, "")
+ linkbin(&dg, bin, inputs, ldscript)
| `std.None:
std.fatal(1, "No such binary %s\n", bin)
;;
@@ -137,6 +138,7 @@
cmd = std.slpush(cmd, std.sldup(bin))
/* [-T script] */
+ std.put("ldscript = %s\n")
if ldscript.len > 0
cmd = std.slpush(cmd, std.sldup("-T"))
cmd = std.slpush(cmd, std.sldup(ldscript))
--- a/main.myr
+++ b/main.myr
@@ -42,7 +42,7 @@
;;
if bld.opt_binname.len != 0
- bld.buildbin(bld.opt_binname, optctx.args)
+ bld.buildbin(bld.opt_binname, optctx.args, bld.opt_ldscript)
elif bld.opt_libname.len != 0
bld.buildlib(bld.opt_libname, optctx.args)
else
--- a/parse.myr
+++ b/parse.myr
@@ -89,7 +89,8 @@
}
const myrtarget = {p, targ
- var name, inputs
+ var name, inputs, attrs
+ var ldscript, runtime, inst
match word(p)
| `std.Some n: name = n
@@ -97,9 +98,18 @@
;;
skipspace(p)
+ if matchc(p, '{')
+ match attrlist(p)
+ | `std.Some al: attrs = al
+ | `std.None: failparse(p, "invalid attr list for %s %s", targ, name)
+ ;;
+ ;;
+
+ skipspace(p)
if !matchc(p, '=')
failparse(p, "expected '=' after '%s %s'", targ, name)
;;
+
match wordlist(p)
| `std.Some wl: inputs = wl
| `std.None: failparse(p, "expected list of file names after %s target\n", targ)
@@ -108,7 +118,26 @@
if !matchc(p, ';')
failparse(p, "expected ';' terminating input list, got %c\n", peekc(p))
;;
- -> [.name=name, .inputs=inputs, .install=true, .ldscript=[][:], .runtime=[][:]]
+ inst = true
+ for elt in attrs
+ match elt
+ | ("ldscript", lds): ldscript = std.sldup(lds)
+ | ("runtime", rt): runtime = std.sldup(rt)
+ | ("noinst", val):
+ if val.len != 0
+ failparse(p, "noinst attr does not take argument\n")
+ ;;
+ inst = false
+ ;;
+ ;;
+ std.slfree(attrs)
+ -> [
+ .name=name,
+ .inputs=inputs,
+ .install=inst,
+ .ldscript=ldscript,
+ .runtime=runtime
+ ]
}
const anontarget = {p, targ
@@ -124,6 +153,38 @@
;;
-> inputs
}
+
+const attrlist = {p
+ var al
+
+ al = [][:]
+ while true
+ match word(p)
+ | `std.Some k:
+ skipspace(p)
+ if matchc(p, '=')
+ match word(p)
+ | `std.Some v:
+ al = std.slpush(al, (k, v))
+ | `std.None:
+ failparse(p, "invalid attr in attribute list\n")
+ ;;
+ else
+ al = std.slpush(al, (k, [][:]))
+ ;;
+ | `std.None: break
+ ;;
+ ;;
+ if !matchc(p, '}')
+ failparse(p, "expected '}' at end of attr list\n")
+ ;;
+ if al.len == 0
+ -> `std.None
+ else
+ -> `std.Some al
+ ;;
+}
+
const wordlist = {p
var wl