1 module cfg_grammar_gen; 2 3 /// PEG grammar for libconfig 4 enum configGrammar = r" 5 # Comments and include directive are not part of this grammar. 6 # They must be handled before the input is given to the PEG parser 7 8 Config: 9 Document < eoi / Setting+ 10 11 Setting < Name (':' / '=') Value (';' / ',')? 12 13 Value <- Scalar / Array / List / Group 14 Scalar <- Bool / Float / Integer / String # Float MUST be before Integer 15 Array < '[' ( Scalar (',' Scalar)* )? ']' 16 List < '(' ( Value (',' Value)* )? ')' 17 Group < '{' Setting* '}' 18 19 Name <~ [A-Za-z] ( [-A-Za-z0-9_] )* 20 21 Bool <~ [Tt] [Rr] [Uu] [Ee] / [Ff] [Aa] [Ll] [Ss] [Ee] 22 23 Integer <- (Hex / Dec) ('LL' / 'L')? 24 Hex <~ :'0' :[Xx] hexDigit+ 25 Dec <~ [-+]? digits 26 27 Float <~ ( [-+]? digit* ^'.' digit* ( [eE] [-+]? digits )? ) / 28 ( [-+]? digit+ (^'.' digit*)? [eE] [-+]? digits ) 29 30 StringQuot <~ :doublequote ( 31 backslash backslash / 32 backslash doublequote / 33 backslash ^'f' / 34 backslash ^'n' / 35 backslash ^'r' / 36 backslash ^'t' / 37 !doublequote !backslash . 38 )* :doublequote 39 40 String <~ (StringQuot spacing?)+ 41 "; 42 43 int main(string[] args) { 44 import pegged.grammar : asModule; 45 import std.stdio : stdout, stderr; 46 import std.format : format; 47 48 if (args.length == 0) args = ["cfg_grammar_gen"]; 49 50 immutable usage = ( 51 "usage:\n" ~ 52 " %1$s [Options]\n" ~ 53 " Options:\n" ~ 54 " -h --help print this help message\n" ~ 55 " -m --module grammar module qualified name [mandatory]\n" ~ 56 " -o --output grammar module filename without extension [mandatory]\n" ~ 57 " Example:\n" ~ 58 " %1$s -m config.grammar -o src/config/grammar\n") 59 .format(args[0]); 60 61 int reportError(string msg) { 62 stderr.writeln(msg); 63 stderr.writeln(usage); 64 return 1; 65 } 66 67 string modulefile; 68 string modulename; 69 70 for (size_t i=0; i<args.length; ++i) { 71 if (args[i] == "-h" || args[i] == "--help") { 72 stdout.writeln(usage); 73 return 0; 74 } 75 if (args[i] == "-m" || args[i] == "--module") { 76 ++i; 77 if (i == args.length) return reportError("missing argument(s)"); 78 modulename = args[i]; 79 } 80 if (args[i] == "-o" || args[i] == "--output") { 81 ++i; 82 if (i == args.length) return reportError("missing argument(s)"); 83 modulefile = args[i]; 84 } 85 } 86 87 if (!modulefile || !modulename) return reportError("missing argument(s)"); 88 89 asModule(modulename, modulefile, configGrammar); 90 91 return 0; 92 }