From e5a8a5dbf98f8509c384a2621c35387e2b98d6db Mon Sep 17 00:00:00 2001 From: MaximeBarniaudy Date: Wed, 5 Jun 2024 11:21:39 +0900 Subject: [PATCH] Remove old unused code, and measure parsing speed --- grammar_parser.meta | 386 ++++++-------------------------------------- rawminproto.leg | 46 ++++-- 2 files changed, 76 insertions(+), 356 deletions(-) diff --git a/grammar_parser.meta b/grammar_parser.meta index 141d8f8..b39bcbe 100644 --- a/grammar_parser.meta +++ b/grammar_parser.meta @@ -119,22 +119,7 @@ Object.last() { self[self.length() - 1] } // Input stream -//Stream = Object.subtype(#Stream); - -//newStream(string) { -// self = Stream.new( -// content: string, -// position: 0, -// limit: len(string) -// ); -// self; -//} - -//Stream.atEnd() { self.position >= self.limit } Stream.peek() { self.content[self.position] } -//Stream.inc() { !self.atEnd() && { self.position = self.position + 1; } } - -//Stream.setLastBegin = () { self.lastBegin = self.position; }; // Context @@ -158,196 +143,29 @@ Context.declareVariable(var) { StringLiteral = Object.subtype(#StringLiteral); -StringLiteral.match(stream, context, actions) { - if (stream.match(self.string)) { - stream.position += len(self.string); - true; - } else { - false; - } -} - StringLiteral.getMatchingExpression() { - //return `(@stream).match(@self.string) && ((@stream).position += len(@self.string)) && @true; return `{ - if (stream.content.compareFrom(stream.position, @self.string) == 0) { - stream.position += len(@self.string); - @true; - } else { - @false; - } + ((stream.content.compareFrom(stream.position, @self.string) == 0) && + (stream.position += len(@self.string)) && + @true) + || + @false }; } -//StringLiteral.match(stream, context, actions) { -// -// n = len(self.string); -// i = 0; -// success = 1; -// if (stream.atEnd()) { success = 0; } -// startPosition = stream.position; -// -// while(i < n && success == 1) { -// if (self.string[i] != stream.peek()) { -// success = 0; -// stream.position = startPosition; -// -// } else { -// i = i + 1; -// stream.inc(); -// } -// } -// success; -//} - // Character Class CharacterClass = Object.subtype(#CharacterClass); -CharacterClass.match(stream, context, actions) { - - local classLength = len(self.value); - local i = 0; - local prevChar = nil; - local success = 0; - - while (i < classLength && success == 0 && !stream.atEnd()) { - - // [a] case - if (prevChar == nil) { - // println("[a] case"); - prevChar = self.value[i]; - - if (stream.peek() == self.value[i]) { - success = 1; - } - - } else if (prevChar != nil && self.value[i] == '-') { - - // [a-z] case - if (i+1 < classLength) { - // println("[a-z] case"); - local rangeStart = prevChar; - local rangeEnd = self.value[i+1]; - // print("Range Start: ", rangeStart, " | "); - // print("Range End: ", rangeEnd, "\n"); - if (stream.peek() >= rangeStart - && stream.peek() <= rangeEnd - ) { - success = 1; - } - prevChar = nil; - i = i + 1; - - // [a-] case - } else { - // println("[a-] case"); - if (stream.peek() == '-') { - success = 1; - } - } - - // [ab] case - } else if (prevChar != nil && self.value[i] != '-') { - // println("[ab] case"); - prevChar = self.value[i]; - if (stream.peek() == self.value[i]) { - success = 1; - } - } - // print("prevChar: ", prevChar, "\n"); - i = i + 1; - } - - if (success == 1) { - stream.inc(); - } - - success == 1; -} - -CharacterClass.staticmatch(stream, context, actions, value) { - - local classLength = len(value); - local i = 0; - local prevChar = nil; - local success = 0; - - while (i < classLength && success == 0 && !stream.atEnd()) { - - // [a] case - if (prevChar == nil) { - //println("[a] case"); - prevChar = value[i]; - - if (stream.peek() == value[i]) { - success = 1; - } - - } else if (prevChar != nil && value[i] == '-') { - - // [a-z] case - if (i+1 < classLength) { - // println("[a-z] case"); - local rangeStart = prevChar; - local rangeEnd = value[i+1]; - // print("Range Start: ", rangeStart, " | "); - // print("Range End: ", rangeEnd, "\n"); - if (stream.peek() >= rangeStart - && stream.peek() <= rangeEnd - ) { - success = 1; - } - prevChar = nil; - i = i + 1; - - // [a-] case - } else { - // println("[a-] case"); - if (stream.peek() == '-') { - success = 1; - } - } - - // [ab] case - } else if (prevChar != nil && value[i] != '-') { - // println("[ab] case"); - prevChar = value[i]; - if (stream.peek() == value[i]) { - success = 1; - } - } - // print("prevChar: ", prevChar, "\n"); - i = i + 1; - } - - if (success == 1) { - stream.inc(); - } - - success == 1; -} - CharacterClass.getMatchingExpression() { - //return `CharacterClass.staticmatch(@stream, @context, @actions, @self.value); - return `{ !stream.atEnd() && (@self.value).charClass().bitTest(stream.peek()) && stream.inc() && @true }; + return `{ !stream.atEnd() && (@self.value.charClass()).bitTest(stream.peek()) && stream.inc() && @true }; } // Dot Dot = Object.subtype(#Dot); -Dot.match(stream, context, actions) { - if (!stream.atEnd()) { - stream.inc(); - true; - } else { - false; - } -} - Dot.getMatchingExpression() { - //return `!(@stream).atEnd() && (@stream).inc() && @true; return `{ !stream.atEnd() && stream.inc() && @true }; } @@ -355,13 +173,7 @@ Dot.getMatchingExpression() { Begin = Object.subtype(#Begin); -Begin.match(stream, context, actions) { - stream.setLastBegin(); - true; -} - Begin.getMatchingExpression() { - //return `(@stream).setLastBegin() && true; return `{ stream.setLastBegin() && @true }; } @@ -369,14 +181,7 @@ Begin.getMatchingExpression() { End = Object.subtype(#End); -End.match(stream, context, actions) { - context.variables.yytext = stream.content[stream.lastBegin..stream.position].unescaped(); - true; -} - End.getMatchingExpression() { - //return `((@context.variables).yytext = (@stream.content)[(@stream).lastBegin..(@stream).position].unescaped()) - // && true; return `{ (context.variables.yytext = stream.content[stream.lastBegin..stream.position].unescaped()) && @true }; } @@ -385,13 +190,7 @@ End.getMatchingExpression() { Optional = Object.subtype(#Optional); -Optional.match(stream, context, actions) { - self.expression.match(stream, context, actions); - true; -} - Optional.getMatchingExpression() { - //return `(@self.expression.getMatchingExpression(stream, context, actions)) || @true; return `{ (@self.expression.getMatchingExpression()); @true }; } @@ -399,28 +198,14 @@ Optional.getMatchingExpression() { Star = Object.subtype(#Star); -Star.match(stream, context, actions) { - while (self.expression.match(stream, context, actions)) {} - true; -} - Star.getMatchingExpression() { - return `{ while (@self.expression.getMatchingExpression()) {} @true }; + return `{ while (@self.expression.getMatchingExpression()) @true; @true }; } // Plus Plus = Object.subtype(#Plus); -Plus.match(stream, context, actions) { - if (self.expression.match(stream, context, actions) == true) { - while (self.expression.match(stream, context, actions) == true) {} - true; - } else { - false; - } -} - Plus.getMatchingExpression() { return `{ if (@self.expression.getMatchingExpression()) { @@ -436,17 +221,6 @@ Plus.getMatchingExpression() { And = Object.subtype(#And); -And.match(stream, context, actions) { - local position = stream.position; - - if (self.expression.match(stream, context, actions) == true) { - stream.position = position; - true; - } else { - false; - } -} - And.getMatchingExpression() { return `{ local position = stream.position; @@ -463,17 +237,6 @@ And.getMatchingExpression() { Not = Object.subtype(#Not); -Not.match(stream, context, actions) { - local position = stream.position; - - if (self.expression.match(stream, context, actions) == true) { - stream.position = position; - false; - } else { - true; - } -} - Not.getMatchingExpression() { return `{ local position = stream.position; @@ -490,30 +253,6 @@ Not.getMatchingExpression() { Sequence = Object.subtype(#Sequence); -Sequence._match(stream, context, actions, index) { - if (index == self.length() - 1) { - return self[index].match(stream, context, actions); - } - self[index].match(stream, context, actions) && self._match(stream, context, actions, index + 1); -} - -Sequence.match(stream, context, actions) { - local initialActionCount = actions.length(); - local startingPosition = stream.position; - - local success = self._match(stream, context, actions, 0); - - if (success == false) { - while (actions.length() > initialActionCount) { - actions.pop(); - } - stream.position = startingPosition; - } - - success; -} - - Sequence._getMatchingExpression(index) { if (index == self.length() - 1) { return self[index].getMatchingExpression(); @@ -529,9 +268,8 @@ Sequence.getMatchingExpression() { ({ (@self._getMatchingExpression(0)); } || { - while (actions.length() > initialActionCount) { + while (actions.length() > initialActionCount) actions.pop(); - } stream.position = startingPosition; @false; }); @@ -542,17 +280,6 @@ Sequence.getMatchingExpression() { Alternation = Object.subtype(#Alternation); -Alternation._match(stream, context, actions, index) { - if (index == self.length() - 1) { - return self[index].match(stream, context, actions); - } - self[index].match(stream, context, actions) || self._match(stream, context, actions, index + 1); -} - -Alternation.match(stream, context, actions) { - return self._match(stream, context, actions, 0); -} - Alternation._getMatchingExpression(index) { if (index == self.length() - 1) { return self[index].getMatchingExpression(); @@ -569,11 +296,6 @@ Alternation.getMatchingExpression() { Action = Object.subtype(#Action); -Action.match(stream, context, actions) { - actions.push([action: self, context: context]); - true; -} - Action.getMatchingExpression() { return `{ actions.push([action: @self, context: context]); @true; } } @@ -600,14 +322,6 @@ Action.execute(context) { ParseTimeAction = Object.subtype(#ParseTimeAction); -ParseTimeAction.match(stream, context, actions) { - if(self.action.execute(context)) { - true; - } else { - false; - } -} - ParseTimeAction.getMatchingExpression() { return `{ (@self.action).execute(context) }; } @@ -616,12 +330,6 @@ ParseTimeAction.getMatchingExpression() { Assignment = Object.subtype(#Assignment); -Assignment.match(stream, context, actions) { - context.declareVariable(self.name); - local innerContext = Context.new(outerContext: context, returnValueName: self.name).init(); - self.rule.match(stream, innerContext, actions); -} - Assignment.getMatchingExpression() { return `{ context.declareVariable(@self.name); @@ -634,51 +342,16 @@ Assignment.getMatchingExpression() { RuleCall = Object.subtype(#RuleCall); -RuleCall.match(stream, context, actions) { - //if (rules[self.name] == nil) { print("Trying to call undefined rule: ", self.name, "\n"); exit(); } - //print("calling rule ", self.name, " | ", stream.position, "\n"); - local res = get(self.name).match(stream, context, actions); - //print("matching rule ", self.name, ": ", res, "\n"); - res; -} - RuleCall.getMatchingExpression() { - //print("Calling rule ", self.name, "\n"); - //local res = `{get(@self.name).getMatchingExpression(@stream, @context, @actions).__eval__()}; - - //if (innerContext == nil) { - `{ Invoke.new(self: self, method: @self.name, arguments: [stream, context, actions]).__eval__() }; - //} else { - // `{ self.rules[@self.name](stream, @innerContext, actions) }; - //} - - //print("Pos ", stream.position, " | Called rule ", self.name, "\n"); + `{ /*increaseCount(@self.name);*/ Invoke.new(self: self, method: @self.name, arguments: [stream, context, actions]).__eval__() }; } // NamespacedRuleCall NamespacedRuleCall = Object.subtype(#NamespacedRuleCall); -NamespacedRuleCall.match() { - with(self.namespace); - local res = get(self.name).match(stream, context, actions); - without(); - res; -} - NamespacedRuleCall.getMatchingExpression(innerContext) { - //return `{ - // with(@self.namespace); - // local res = get(@self.name).getMatchingExpression(@stream, @context, @actions).__eval__(); - // without(); - // res; - //} - //if (innerContext == nil) { - `{ Invoke.new(self: @get(self.namespace), method: @self.name, arguments: [stream, context, actions]).__eval__() }; - //} else { - // `{ (@get(self.namespace)).rules[@self.name](stream, @innerContext, actions) }; - //} - + `{ Invoke.new(self: @get(self.namespace), method: @self.name, arguments: [stream, context, actions]).__eval__() }; } Definition = Object.subtype(#Definition); @@ -692,12 +365,24 @@ Grammar.addRulesFromNamespace(namespace) { environment: nil, function: Lambda.new( parameters: [#stream, #context, #actions], - body: __namespaces__[namespace][key].getMatchingExpression().body + body: __namespaces__[namespace][key].getMatchingExpression().body, + name: key, + parent: self ) ) } } +//global functionCounts = []; +// +//increaseCount(function) { +// if (!functionCounts.keys().contains(function)){ +// functionCounts[function] = 1; +// } else { +// functionCounts[function]++; +// } +//} + // ----- Grammar of Meta Language (Minimal) ----- with(#HardCodedMeta); @@ -1258,7 +943,9 @@ global stream = newStream(readfile("rawminproto.leg")); global context = Context.new(outerContext: nil).init(); global actions = []; -print("Matching rawminproto.leg : ", HardCodedPeg.grammar(stream, context, actions), "\n"); +global match = HardCodedPeg.grammar(stream, context, actions); +print("Matching rawminproto.leg : ", match, "\n"); +if (!match) exit(); with(#metaLanguage); for (actionAndContext in actions) { @@ -1347,3 +1034,24 @@ compareGrammars(grammar1, grammar2) { compareGrammars(#peg, #pegCircular); compareGrammars(#metaLanguage, #metaLanguageCircular); + +//global functionCounts = []; +global then = cputime(); + +global stream3 = newStream(readfile("grammar_parser.meta")); +global context3 = Context.new(outerContext: nil).init(); +global actions3 = []; + +while(!stream3.atEnd()) { + metaLanguage.start(stream3, context3, actions3); + for (actionAndContext in actions3) { + actionAndContext.action.execute(actionAndContext.context); + } + //println(len(actions3)); + //println(context3.variables.s); + global actions3 = []; +} + +global now = cputime(); +print("Parse time : ", now - then, "s\n"); +//println(functionCounts); diff --git a/rawminproto.leg b/rawminproto.leg index e79c430..3c3021b 100644 --- a/rawminproto.leg +++ b/rawminproto.leg @@ -1,12 +1,9 @@ -start = - ( s:stmt # { yysval = s } +start = - ( s:stmt { s; } | !. # { yysval = 0 } | < (!EOL .)* > # { fatal("syntax error near: %s", yytext) } ) -stmt = LET l:mklet k:id ASSIGN v:expr { l.keyvals.push(k); l.keyvals.push(v) } - ( COMMA k:id ASSIGN v:expr { l.keyvals.push(k); l.keyvals.push(v) } - )* SEMI { l } - | WHILE LPAREN c:expr RPAREN s:stmt { While.new(condition: c, body: s) } +stmt = WHILE LPAREN c:expr RPAREN s:stmt { While.new(condition: c, body: s) } | IF LPAREN c:expr RPAREN s:stmt ( ELSE t:stmt { If.new(condition: c, consequent: s, alternate: t ) } | { If.new(condition: c, consequent: s, alternate: nil) } @@ -22,20 +19,26 @@ stmt = LET l:mklet k:id ASSIGN v:expr { l.keyvals.push(k); l.keyvals.p TO b:expr RPAREN s:stmt { ForFromTo.new(identifier: i, first: a, last: b, body: s) } | FOR LPAREN i:expr SEMI c:expr SEMI u:expr RPAREN s:stmt { For.new(initialise: i, condition: c, update: u, body: s) } + | TRY t:stmt + ( CATCH LPAREN i:id RPAREN c:stmt { TryCatch.new(statement: t, identifier: i, handler: c) } + | ENSURE e:stmt { TryEnsure.new(statement: t, handler: e) } + ) + | RAISE e:expr EOS { Raise.new(value: e) } + | LOCAL i:id p:params b:block { SetLocal.new(name: i, value: Lambda.new(parameters: p, body: b)) } + | GLOBAL i:id p:params b:block { SetGlobal.new(name: i, value: Lambda.new(parameters: p, body: b)) } | i:id p:params b:block { SetVar.new(name: i, value: Lambda.new(parameters: p, body: b)) } | v:proto DOT i:id p:params b:block { SetProp.new(object: v, key: i, value: Lambda.new(parameters: p, body: b)) } - | v:proto CCOLON i:id p:params b:block { SetProp.new(object: v, key: i, value: Lambda.new(parameters: p, body: b)) } | b:block { Block.new(body: b) } | e:expr EOS { e } -mklet = { Let.new() } - proto = v:var ( DOT j:id !LPAREN { v = GetProp.new(object: v, key: j) } )* { v } -EOS = SEMI+ | &RBRACE | &ELSE +EOS = SEMI+ | &RBRACE | &ELSE | &CATCH -expr = i:id ASSIGN e:expr { SetVar.new(name: i, value: e) } +expr = LOCAL i:id ASSIGN e:expr { SetLocal.new(name: i, value: e) } + | GLOBAL i:id ASSIGN e:expr { SetGlobal.new(name: i, value: e) } + | i:id ASSIGN e:expr { SetVar.new(name: i, value: e) } | l:logor ( ASSIGN r:expr { l = assign(l, r) } | PLUSEQ r:expr { l = newBinop(__opPreAdd, lvalue(l), r) } | MINUSEQ r:expr { l = newBinop(__opPreSub, lvalue(l), r) } @@ -99,13 +102,13 @@ prefix = PPLUS p:prefix { newBinop(__opPreAdd, lvalue(p) | COMMAT e:expr { Unyop.new(operation: __opUnquote).push(e) } | postfix -postfix = p:primary +postfix = SUPER DOT i:id a:args { Super.new(method: i, arguments: a) } + | p:primary ( LBRAK e:expr RBRAK { p = GetArray.new(object: p, index: e) } | DOT i:id ( a:args !LBRACE { p = Invoke.new(self: p, method: i, arguments: a) } | { p = GetProp.new(object: p, key: i) } ) | a:args !LBRACE { p = newApply(p, a) } - | CCOLON i:id { p = GetProp.new(object: p, key: i) } )* ( PPLUS { p = newBinop(__opPostAdd, lvalue(p), 1) } | MMINUS { p = newBinop(__opPostAdd, lvalue(p), -1) } @@ -162,9 +165,9 @@ unsign = < DIGIT* '.' DIGIT+ EXP? > - { yytext.asFloat() } | "0" [xX] < HIGIT+ > - { yytext.asInteger(16) } | "0" < OIGIT* > - { yytext.asInteger(8) } | < DIGIT+ > - { yytext.asInteger() } + | "'" < char > "'" - { ord(yytext.unescaped()) } string = '"' < ( !'"' char )* > '"' - { yytext.unescaped() } - | "'" < ( !"'" char )* > "'" - { yytext.unescaped() } char = "\\" ( ["'\\abfnrtv] | [xX] HIGIT* @@ -174,7 +177,9 @@ char = "\\" ( ["'\\abfnrtv] symbol = HASH i:id { i } -var = i:id { GetVar.new(name: i) } +var = LOCAL i:id { GetLocal.new(name: i) } + | GLOBAL i:id { GetGlobal.new(name: i) } + | i:id { GetVar.new(name: i) } id = < LETTER ALNUM* > - { intern(yytext) } @@ -189,8 +194,10 @@ EXP = [eE] SIGN DIGIT+ - = SPACE* -SPACE = [ \t] | EOL | '//' (!EOL .)* +SPACE = [ \t] | EOL | SLC | MLC EOL = [\n\r] # { ++lineno } +SLC = "//" (!EOL .)* +MLC = "/*" ( MLC | !"*/" (EOL | .))* "*/" - NIL = "nil" !ALNUM - WHILE = "while" !ALNUM - @@ -200,10 +207,16 @@ FOR = "for" !ALNUM - IN = "in" !ALNUM - FROM = "from" !ALNUM - TO = "to" !ALNUM - -LET = "let" !ALNUM - CONT = "continue" !ALNUM - BREAK = "break" !ALNUM - RETURN = "return" !ALNUM - +TRY = "try" !ALNUM - +CATCH = "catch" !ALNUM - +ENSURE = "ensure" !ALNUM - +RAISE = "raise" !ALNUM - +GLOBAL = "global" !ALNUM - +LOCAL = "local" !ALNUM - +SUPER = "super" !ALNUM - BQUOTE = "`" - COMMAT = "@" - @@ -212,7 +225,6 @@ SEMI = ";" - ASSIGN = "=" ![=] - COMMA = "," - COLON = ":" ![:] - -CCOLON = "::" - LPAREN = "(" - RPAREN = ")" - LBRAK = "[" -