Added flags to language specifiction. Added optional expect string to language specification. Added some exaple grammars for testing and demos
This commit is contained in:
1
examples/book.doge
Normal file
1
examples/book.doge
Normal file
@@ -0,0 +1 @@
|
||||
wow c so language such book
|
47
examples/doge.c
Normal file
47
examples/doge.c
Normal file
@@ -0,0 +1,47 @@
|
||||
#include "../mpc.h"
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
|
||||
mpc_parser_t* Adjective = mpc_new("adjective");
|
||||
mpc_parser_t* Noun = mpc_new("noun");
|
||||
mpc_parser_t* Phrase = mpc_new("phrase");
|
||||
mpc_parser_t* Doge = mpc_new("doge");
|
||||
|
||||
mpca_lang(MPC_LANG_DEFAULT,
|
||||
" \
|
||||
adjective : \"wow\" | \"many\" | \"so\" | \"such\"; \
|
||||
noun : \"lisp\" | \"language\" | \"c\" | \"book\" | \"build\"; \
|
||||
phrase : <adjective> <noun>; \
|
||||
doge : /^/ <phrase>* /$/; \
|
||||
",
|
||||
Adjective, Noun, Phrase, Doge);
|
||||
|
||||
if (argc > 1) {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_contents(argv[1], Doge, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_pipe("<stdin>", stdin, Doge, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
mpc_cleanup(4, Adjective, Noun, Phrase, Doge);
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
21
examples/fib.smallc
Normal file
21
examples/fib.smallc
Normal file
@@ -0,0 +1,21 @@
|
||||
#include "stdio.h"
|
||||
|
||||
int fib(int n) {
|
||||
if (n == 0) { return 0; }
|
||||
if (n == 1) { return 1; }
|
||||
return fib(n - 1) + fib(n - 2);
|
||||
}
|
||||
|
||||
main() {
|
||||
|
||||
int n;
|
||||
int i;
|
||||
|
||||
while (i < 10) {
|
||||
n = fib(10);
|
||||
print(n);
|
||||
i = i + 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
56
examples/lispy.c
Normal file
56
examples/lispy.c
Normal file
@@ -0,0 +1,56 @@
|
||||
#include "../mpc.h"
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
|
||||
mpc_parser_t* Number = mpc_new("number");
|
||||
mpc_parser_t* Symbol = mpc_new("symbol");
|
||||
mpc_parser_t* String = mpc_new("string");
|
||||
mpc_parser_t* Comment = mpc_new("comment");
|
||||
mpc_parser_t* Sexpr = mpc_new("sexpr");
|
||||
mpc_parser_t* Qexpr = mpc_new("qexpr");
|
||||
mpc_parser_t* Expr = mpc_new("expr");
|
||||
mpc_parser_t* Lispy = mpc_new("lispy");
|
||||
|
||||
mpca_lang(MPC_LANG_PREDICTIVE,
|
||||
" \
|
||||
number \"number\" : /[0-9]+/ ; \
|
||||
symbol \"symbol\" : /[a-zA-Z0-9_+\\-*\\/\\\\=<>!&]+/ ; \
|
||||
string \"string\" : /\"(\\\\.|[^\"])*\"/ ; \
|
||||
comment : /;[^\\r\\n]*/ ; \
|
||||
sexpr : '(' <expr>* ')' ; \
|
||||
qexpr : '{' <expr>* '}' ; \
|
||||
expr : <number> | <symbol> | <string> \
|
||||
| <comment> | <sexpr> | <qexpr> ; \
|
||||
lispy : /^/ <expr>* /$/ ; \
|
||||
",
|
||||
Number, Symbol, String, Comment, Sexpr, Qexpr, Expr, Lispy);
|
||||
|
||||
if (argc > 1) {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_contents(argv[1], Lispy, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_pipe("<stdin>", stdin, Lispy, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
mpc_cleanup(8, Number, Symbol, String, Comment, Sexpr, Qexpr, Expr, Lispy);
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
47
examples/maths.c
Normal file
47
examples/maths.c
Normal file
@@ -0,0 +1,47 @@
|
||||
#include "../mpc.h"
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
|
||||
mpc_parser_t *Expr = mpc_new("expression");
|
||||
mpc_parser_t *Prod = mpc_new("product");
|
||||
mpc_parser_t *Value = mpc_new("value");
|
||||
mpc_parser_t *Maths = mpc_new("maths");
|
||||
|
||||
mpca_lang(MPC_LANG_PREDICTIVE,
|
||||
" \
|
||||
expression : <product> (('+' | '-') <product>)*; \
|
||||
product : <value> (('*' | '/') <value>)*; \
|
||||
value : /[0-9]+/ | '(' <expression> ')'; \
|
||||
maths : /^/ <expression> /$/; \
|
||||
",
|
||||
Expr, Prod, Value, Maths);
|
||||
|
||||
if (argc > 1) {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_contents(argv[1], Maths, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_pipe("<stdin>", stdin, Maths, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
mpc_cleanup(4, Expr, Prod, Value, Maths);
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
11
examples/minimal.smallc
Normal file
11
examples/minimal.smallc
Normal file
@@ -0,0 +1,11 @@
|
||||
#include "stdio.h"
|
||||
|
||||
main() {
|
||||
|
||||
int i;
|
||||
int j;
|
||||
|
||||
j = 10;
|
||||
|
||||
return 0;
|
||||
}
|
239
examples/prelude.lspy
Normal file
239
examples/prelude.lspy
Normal file
@@ -0,0 +1,239 @@
|
||||
;;;
|
||||
;;; Lispy Standard Prelude
|
||||
;;;
|
||||
|
||||
;;; Atoms
|
||||
(def {nil} {})
|
||||
(def {true} 1)
|
||||
(def {false} 0)
|
||||
|
||||
;;; Functional Functions
|
||||
|
||||
; Function Definitions
|
||||
(def {fun} (\ {f b} {
|
||||
def (head f) (\ (tail f) b)
|
||||
}))
|
||||
|
||||
; Open new scope
|
||||
(fun {let b} {
|
||||
((\ {_} b) ())
|
||||
})
|
||||
|
||||
; Unpack List to Function
|
||||
(fun {unpack f l} {
|
||||
eval (join (list f) l)
|
||||
})
|
||||
|
||||
; Unapply List to Function
|
||||
(fun {pack f & xs} {f xs})
|
||||
|
||||
; Curried and Uncurried calling
|
||||
(def {curry} {unpack})
|
||||
(def {uncurry} {pack})
|
||||
|
||||
; Perform Several things in Sequence
|
||||
(fun {do & l} {
|
||||
if (== l {})
|
||||
{{}}
|
||||
{last l}
|
||||
})
|
||||
|
||||
;;; Logical Functions
|
||||
|
||||
; Logical Functions
|
||||
(fun {not x} {- 1 x})
|
||||
(fun {or x y} {+ x y})
|
||||
(fun {and x y} {* x y})
|
||||
|
||||
|
||||
;;; Numeric Functions
|
||||
|
||||
; Minimum of Arguments
|
||||
(fun {min & xs} {
|
||||
if (== (tail xs) {}) {fst xs}
|
||||
{do
|
||||
(= {rest} (unpack min (tail xs)))
|
||||
(= {item} (fst xs))
|
||||
(if (< item rest) {item} {rest})
|
||||
}
|
||||
})
|
||||
|
||||
; Minimum of Arguments
|
||||
(fun {max & xs} {
|
||||
if (== (tail xs) {}) {fst xs}
|
||||
{do
|
||||
(= {rest} (unpack max (tail xs)))
|
||||
(= {item} (fst xs))
|
||||
(if (> item rest) {item} {rest})
|
||||
}
|
||||
})
|
||||
|
||||
;;; Conditional Functions
|
||||
|
||||
(fun {select & cs} {
|
||||
if (== cs {})
|
||||
{error "No Selection Found"}
|
||||
{if (fst (fst cs)) {snd (fst cs)} {unpack select (tail cs)}}
|
||||
})
|
||||
|
||||
(fun {case x & cs} {
|
||||
if (== cs {})
|
||||
{error "No Case Found"}
|
||||
{if (== x (fst (fst cs))) {snd (fst cs)} {unpack case (join (list x) (tail cs))}}
|
||||
})
|
||||
|
||||
(def {otherwise} true)
|
||||
|
||||
|
||||
;;; Misc Functions
|
||||
|
||||
(fun {flip f a b} {f b a})
|
||||
(fun {ghost & xs} {eval xs})
|
||||
(fun {comp f g x} {f (g x)})
|
||||
|
||||
;;; List Functions
|
||||
|
||||
; First, Second, or Third Item in List
|
||||
(fun {fst l} { eval (head l) })
|
||||
(fun {snd l} { eval (head (tail l)) })
|
||||
(fun {trd l} { eval (head (tail (tail l))) })
|
||||
|
||||
; List Length
|
||||
(fun {len l} {
|
||||
if (== l {})
|
||||
{0}
|
||||
{+ 1 (len (tail l))}
|
||||
})
|
||||
|
||||
; Nth item in List
|
||||
(fun {nth n l} {
|
||||
if (== n 0)
|
||||
{fst l}
|
||||
{nth (- n 1) (tail l)}
|
||||
})
|
||||
|
||||
; Last item in List
|
||||
(fun {last l} {nth (- (len l) 1) l})
|
||||
|
||||
; Apply Function to List
|
||||
(fun {map f l} {
|
||||
if (== l {})
|
||||
{{}}
|
||||
{join (list (f (fst l))) (map f (tail l))}
|
||||
})
|
||||
|
||||
; Apply Filter to List
|
||||
(fun {filter f l} {
|
||||
if (== l {})
|
||||
{{}}
|
||||
{join (if (f (fst l)) {head l} {{}}) (filter f (tail l))}
|
||||
})
|
||||
|
||||
; Return all of list but last element
|
||||
(fun {init l} {
|
||||
if (== (tail l) {})
|
||||
{{}}
|
||||
{join (head l) (init (tail l))}
|
||||
})
|
||||
|
||||
; Reverse List
|
||||
(fun {reverse l} {
|
||||
if (== l {})
|
||||
{{}}
|
||||
{join (reverse (tail l)) (head l)}
|
||||
})
|
||||
|
||||
; Fold Left
|
||||
(fun {foldl f z l} {
|
||||
if (== l {})
|
||||
{z}
|
||||
{foldl f (f z (fst l)) (tail l)}
|
||||
})
|
||||
|
||||
; Fold Right
|
||||
(fun {foldr f z l} {
|
||||
if (== l {})
|
||||
{z}
|
||||
{f (fst l) (foldr f z (tail l))}
|
||||
})
|
||||
|
||||
(fun {sum l} {foldl + 0 l})
|
||||
(fun {product l} {foldl * 1 l})
|
||||
|
||||
; Take N items
|
||||
(fun {take n l} {
|
||||
if (== n 0)
|
||||
{{}}
|
||||
{join (head l) (take (- n 1) (tail l))}
|
||||
})
|
||||
|
||||
; Drop N items
|
||||
(fun {drop n l} {
|
||||
if (== n 0)
|
||||
{l}
|
||||
{drop (- n 1) (tail l)}
|
||||
})
|
||||
|
||||
; Split at N
|
||||
(fun {split n l} {list (take n l) (drop n l)})
|
||||
|
||||
; Take While
|
||||
(fun {take-while f l} {
|
||||
if (not (unpack f (head l)))
|
||||
{{}}
|
||||
{join (head l) (take-while f (tail l))}
|
||||
})
|
||||
|
||||
; Drop While
|
||||
(fun {drop-while f l} {
|
||||
if (not (unpack f (head l)))
|
||||
{l}
|
||||
{drop-while f (tail l)}
|
||||
})
|
||||
|
||||
; Element of List
|
||||
(fun {elem x l} {
|
||||
if (== l {})
|
||||
{false}
|
||||
{if (== x (fst l)) {true} {elem x (tail l)}}
|
||||
})
|
||||
|
||||
; Find element in list of pairs
|
||||
(fun {lookup x l} {
|
||||
if (== l {})
|
||||
{error "No Element Found"}
|
||||
{do
|
||||
(= {key} (fst (fst l)))
|
||||
(= {val} (snd (fst l)))
|
||||
(if (== key x) {val} {lookup x (tail l)})
|
||||
}
|
||||
})
|
||||
|
||||
; Zip two lists together into a list of pairs
|
||||
(fun {zip x y} {
|
||||
if (or (== x {}) (== y {}))
|
||||
{{}}
|
||||
{join (list (join (head x) (head y))) (zip (tail x) (tail y))}
|
||||
})
|
||||
|
||||
; Unzip a list of pairs into two lists
|
||||
(fun {unzip l} {
|
||||
if (== l {})
|
||||
{{{} {}}}
|
||||
{do
|
||||
(= {x} (fst l))
|
||||
(= {xs} (unzip (tail l)))
|
||||
(list (join (head x) (fst xs)) (join (tail x) (snd xs)))
|
||||
}
|
||||
})
|
||||
|
||||
;;; Other Fun
|
||||
|
||||
; Fibonacci
|
||||
(fun {fib n} {
|
||||
select
|
||||
{ (== n 0) 0 }
|
||||
{ (== n 1) 1 }
|
||||
{ otherwise (+ (fib (- n 1)) (fib (- n 2))) }
|
||||
})
|
||||
|
1
examples/simple.maths
Normal file
1
examples/simple.maths
Normal file
@@ -0,0 +1 @@
|
||||
29 + 2 * 3 - 99 - (5 + 5 + 2) / 100
|
102
examples/smallc.c
Normal file
102
examples/smallc.c
Normal file
@@ -0,0 +1,102 @@
|
||||
#include "../mpc.h"
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
|
||||
mpc_parser_t* Ident = mpc_new("ident");
|
||||
mpc_parser_t* Number = mpc_new("number");
|
||||
mpc_parser_t* Character = mpc_new("character");
|
||||
mpc_parser_t* String = mpc_new("string");
|
||||
mpc_parser_t* Factor = mpc_new("factor");
|
||||
mpc_parser_t* Term = mpc_new("term");
|
||||
mpc_parser_t* Lexp = mpc_new("lexp");
|
||||
mpc_parser_t* Stmt = mpc_new("stmt");
|
||||
mpc_parser_t* Exp = mpc_new("exp");
|
||||
mpc_parser_t* Typeident = mpc_new("typeident");
|
||||
mpc_parser_t* Decls = mpc_new("decls");
|
||||
mpc_parser_t* Args = mpc_new("args");
|
||||
mpc_parser_t* Body = mpc_new("body");
|
||||
mpc_parser_t* Procedure = mpc_new("procedure");
|
||||
mpc_parser_t* Main = mpc_new("main");
|
||||
mpc_parser_t* Includes = mpc_new("includes");
|
||||
mpc_parser_t* Smallc = mpc_new("smallc");
|
||||
|
||||
mpc_err_t* err = mpca_lang(MPC_LANG_DEFAULT,
|
||||
" \n\
|
||||
ident : /[a-zA-Z_][a-zA-Z0-9_]*/ ; \n\
|
||||
number : /[0-9]+/ ; \n\
|
||||
character : /'.'/ ; \n\
|
||||
string : /\"(\\\\.|[^\"])*\"/ ; \n\
|
||||
\n\
|
||||
factor : '(' <lexp> ')' \n\
|
||||
| <number> \n\
|
||||
| <character> \n\
|
||||
| <string> \n\
|
||||
| <ident> '(' <lexp>? (',' <lexp>)* ')' \n\
|
||||
| <ident> ; \n\
|
||||
\n\
|
||||
term : <factor> (('*' | '/' | '%') <factor>)* ; \n\
|
||||
lexp : <term> (('+' | '-') <term>)* ; \n\
|
||||
\n\
|
||||
stmt : '{' <stmt>* '}' \n\
|
||||
| \"while\" '(' <exp> ')' <stmt> \n\
|
||||
| \"if\" '(' <exp> ')' <stmt> \n\
|
||||
| <ident> '=' <lexp> ';' \n\
|
||||
| \"print\" '(' <lexp>? ')' ';' \n\
|
||||
| \"return\" <lexp>? ';' \n\
|
||||
| <ident> '(' <ident>? (',' <ident>)* ')' ';' ; \n\
|
||||
\n\
|
||||
exp : <lexp> '>' <lexp> \n\
|
||||
| <lexp> '<' <lexp> \n\
|
||||
| <lexp> \">=\" <lexp> \n\
|
||||
| <lexp> \"<=\" <lexp> \n\
|
||||
| <lexp> \"!=\" <lexp> \n\
|
||||
| <lexp> \"==\" <lexp> ; \n\
|
||||
\n\
|
||||
typeident : (\"int\" | \"char\") <ident> ; \n\
|
||||
decls : (<typeident> ';')* ; \n\
|
||||
args : <typeident>? (',' <typeident>)* ; \n\
|
||||
body : '{' <decls> <stmt>* '}' ; \n\
|
||||
procedure : (\"int\" | \"char\") <ident> '(' <args> ')' <body> ; \n\
|
||||
main : \"main\" '(' ')' <body> ; \n\
|
||||
includes : (\"#include\" <string>)* ; \n\
|
||||
smallc : /^/ <includes> <decls> <procedure>* <main> /$/ ; \n\
|
||||
",
|
||||
Ident, Number, Character, String, Factor, Term, Lexp, Stmt, Exp,
|
||||
Typeident, Decls, Args, Body, Procedure, Main, Includes, Smallc);
|
||||
|
||||
if (err != NULL) {
|
||||
mpc_err_print(err);
|
||||
mpc_err_delete(err);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if (argc > 1) {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_contents(argv[1], Smallc, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
mpc_result_t r;
|
||||
if (mpc_parse_pipe("<stdin>", stdin, Smallc, &r)) {
|
||||
mpc_ast_print(r.output);
|
||||
mpc_ast_delete(r.output);
|
||||
} else {
|
||||
mpc_err_print(r.error);
|
||||
mpc_err_delete(r.error);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
mpc_cleanup(17, Ident, Number, Character, String, Factor, Term, Lexp, Stmt, Exp,
|
||||
Typeident, Decls, Args, Body, Procedure, Main, Includes, Smallc);
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
Reference in New Issue
Block a user