瀏覽代碼

js -> eberon transition

Vladislav Folts 10 年之前
父節點
當前提交
d395c88254

二進制
bin/compiled.zip


+ 1 - 1
build.py

@@ -127,7 +127,7 @@ def run_tests(bin, unit_test=None, code_test=None):
 def recompile(bin):
     print('recompile oberon sources using "%s"...' % bin)
     compiler = os.path.join(root, 'src', 'oc_nodejs.js')
-    sources = ['ContextConst.ob', 'ContextIdentdef', 'ContextType.ob', 'EberonSymbols.ob', 'EberonCast.ob', 
+    sources = ['ContextConst.ob', 'ContextIdentdef', 'ContextProcedure.ob', 'EberonSymbols.ob', 'EberonCast.ob', 
                'EberonConstructor.ob', 'EberonOperator.ob', 'EberonScope.ob',
                'OberonSymbols.ob', 'Lexer.ob', 'Module.ob']
     

+ 7 - 25
src/context.js

@@ -6,6 +6,7 @@ var CodeGenerator = require("js/CodeGenerator.js");
 var ConstValue = require("js/ConstValue.js");
 var ContextExpression = require("js/ContextExpression.js");
 var ContextHierarchy = require("js/ContextHierarchy.js");
+var ContextProcedure = require("js/ContextProcedure.js");
 var ContextType = require("js/ContextType.js");
 var Designator = require("js/Designator.js");
 var Errors = require("js/Errors.js");
@@ -40,21 +41,6 @@ var HandleSymbolAsType = ContextType.HandleSymbolAsType;
 HandleSymbolAsType.extend = Class.extend;
 HandleSymbolAsType.prototype.init = ContextType.HandleSymbolAsType;
 
-var ProcArg = Class.extend({
-    init: function(type, isVar){
-        this.type = type;
-        this.isVar = isVar;
-    },
-    description: function(){
-        return (this.isVar ? "VAR " : "") + this.type.description();
-    }
-});
-
-function AddArgumentMsg(name, arg){
-    this.name = name;
-    this.arg = arg;
-}
-
 exports.FormalParameters = ChainedContext.extend({
     init: function FormalParametersContext(context){
         ChainedContext.prototype.init.call(this, context);
@@ -69,7 +55,7 @@ exports.FormalParameters = ChainedContext.extend({
         parent.setType(this.__type);
     },
     handleMessage: function(msg){
-        if (msg instanceof AddArgumentMsg){
+        if (msg instanceof ContextProcedure.AddArgumentMsg){
             this.__arguments.push(msg.arg);
             return undefined;
         }
@@ -92,21 +78,19 @@ exports.FormalParameters = ChainedContext.extend({
     }
 });
 
-function endParametersMsg(){}
-
 exports.FormalParametersProcDecl = exports.FormalParameters.extend({
     init: function FormalParametersProcDeclContext(context){
         exports.FormalParameters.prototype.init.call(this, context);
     },
     handleMessage: function(msg){
         var result = exports.FormalParameters.prototype.handleMessage.call(this, msg);
-        if (msg instanceof AddArgumentMsg)
+        if (msg instanceof ContextProcedure.AddArgumentMsg)
             this.parent().handleMessage(msg);
         return result;
     },
     endParse: function(){
         exports.FormalParameters.prototype.endParse.call(this);
-        this.handleMessage(endParametersMsg);
+        this.handleMessage(new ContextProcedure.EndParametersMsg());
     }
 });
 
@@ -166,12 +150,12 @@ exports.ProcDecl = ChainedContext.extend({
         return new Variable.ArgumentVariable(name, arg.type, arg.isVar);
     },
     handleMessage: function(msg){
-        if (msg == endParametersMsg){
+        if (msg instanceof ContextProcedure.EndParametersMsg){
             this.codeGenerator().write(")");
             this._beginBody();
             return;
         }
-        if (msg instanceof AddArgumentMsg)
+        if (msg instanceof ContextProcedure.AddArgumentMsg)
             return this.__addArgument(msg.name, msg.arg);
         return ChainedContext.prototype.handleMessage.call(this, msg);
     },
@@ -229,7 +213,7 @@ exports.ProcParams = HandleSymbolAsType.extend({
         for(var i = 0; i < names.length; ++i){
             var name = names[i];
             this.handleMessage(
-                new AddArgumentMsg(name, new Type.ProcedureArgument(type, this.__isVar)));
+                new ContextProcedure.AddArgumentMsg(name, new Type.ProcedureArgument(type, this.__isVar)));
         }
         this.__isVar = false;
         this.__argNamesForType = [];
@@ -807,11 +791,9 @@ function makeProcCall(context, type, info){
         });
 }
 
-exports.AddArgumentMsg = AddArgumentMsg;
 exports.assertProcStatementResult = assertProcStatementResult;
 exports.beginCallMsg = beginCallMsg;
 exports.endCallMsg = endCallMsg;
 exports.Chained = ChainedContext;
-exports.endParametersMsg = endParametersMsg;
 exports.makeProcCall = makeProcCall;
 exports.HandleSymbolAsType = HandleSymbolAsType;

+ 6 - 5
src/eberon/EberonArray.ob

@@ -1,5 +1,6 @@
 MODULE EberonArray;
-IMPORT EberonTypes, Errors, Expression, LanguageContext, Procedure, Types;
+IMPORT 
+    EberonTypes, Errors, Expression, LanguageContext, Procedure, Types;
 CONST
     methodNameIndexOf = "indexOf";
 TYPE
@@ -7,9 +8,9 @@ TYPE
     END;
 
     MethodIndexOf = RECORD(Method)
-        PROCEDURE MethodIndexOf(elementsType: Types.PType);
+        PROCEDURE MethodIndexOf(elementsType: Types.PStorageType);
 
-        elementsType: Types.PType
+        elementsType: Types.PStorageType
     END;
 
     MethodCallIndexOf = RECORD(Procedure.StdCall)
@@ -25,7 +26,7 @@ PROCEDURE Method.description(): STRING;
     RETURN "array method '" + SELF.name + "'"
 END Method.description;
 
-PROCEDURE MethodIndexOf.MethodIndexOf(elementsType: Types.PType)
+PROCEDURE MethodIndexOf.MethodIndexOf(elementsType: Types.PStorageType)
     | SUPER(methodNameIndexOf, NIL),
       elementsType(elementsType);
 BEGIN
@@ -46,7 +47,7 @@ BEGIN
     RETURN Expression.makeSimple("(" + argCode.result() + ")", Types.basic.integer)
 END MethodCallIndexOf.make;
 
-PROCEDURE denoteMethod*(id: STRING; elementsType: Types.PType): Types.PField;
+PROCEDURE denoteMethod*(id: STRING; elementsType: Types.PStorageType): Types.PField;
 VAR
     result: Types.PField;
 BEGIN

+ 6 - 6
src/eberon/EberonDynamicArray.ob

@@ -14,7 +14,7 @@ TYPE
 
     AddCallGenerator = RECORD(Procedure.CallGenerator)
         cx: LanguageContext.PType;
-        elementsType: Types.PType;
+        elementsType: Types.PStorageType;
         code: STRING
     END;
 
@@ -22,9 +22,9 @@ TYPE
     END;
 
     MethodAdd = RECORD(Method)
-        PROCEDURE MethodAdd(elementsType: Types.PType);
+        PROCEDURE MethodAdd(elementsType: Types.PStorageType);
 
-        elementsType: Types.PType
+        elementsType: Types.PStorageType;
     END;
 
     MethodClear = RECORD(Method)
@@ -40,7 +40,7 @@ TYPE
     END;
 
     MethodAddField = RECORD(EberonTypes.MethodField)
-        PROCEDURE MethodAddField(elementsType: Types.PType);
+        PROCEDURE MethodAddField(elementsType: Types.PStorageType);
     END;
 
     MethodClearField = RECORD(EberonTypes.MethodField)
@@ -75,7 +75,7 @@ PROCEDURE DynamicArray.description(): STRING;
     RETURN Types.arrayDescription(SELF, arrayDimensionDescription)
 END DynamicArray.description;
 
-PROCEDURE MethodAdd.MethodAdd(elementsType: Types.PType)
+PROCEDURE MethodAdd.MethodAdd(elementsType: Types.PStorageType)
     | SUPER(methodNameAdd, NIL),
       elementsType(elementsType);
 END;
@@ -164,7 +164,7 @@ BEGIN
     RETURN result
 END MethodAdd.callGenerator;
 
-PROCEDURE MethodAddField.MethodAddField(elementsType: Types.PType)
+PROCEDURE MethodAddField.MethodAddField(elementsType: Types.PStorageType)
     | SUPER(NEW MethodAdd(elementsType));
 END;
 

+ 21 - 20
src/eberon/eberon_context.js

@@ -10,6 +10,7 @@ var ContextDesignator = require("js/ContextDesignator.js");
 var ContextExpression = require("js/ContextExpression.js");
 var ContextIdentdef = require("js/ContextIdentdef.js");
 var ContextHierarchy = require("js/ContextHierarchy.js");
+var ContextProcedure = require("js/ContextProcedure.js");
 var ContextType = require("js/ContextType.js");
 var EberonConstructor= require("js/EberonConstructor.js");
 var EberonContext= require("js/EberonContext.js");
@@ -565,9 +566,9 @@ var RecordDecl = Class.extend.call(ContextType.Record, {
             return;
         }
 
-        if (msg == Context.endParametersMsg) // not used
+        if (msg instanceof ContextProcedure.EndParametersMsg) // not used
             return undefined;
-        if (msg instanceof Context.AddArgumentMsg) // not used
+        if (msg instanceof ContextProcedure.AddArgumentMsg) // not used
             return undefined;
         return ContextType.Record.prototype.handleMessage.call(this, msg);
     },
@@ -669,9 +670,9 @@ var BaseInit = Context.Chained.extend({
     }
 });
 
-var ProcOrMethodDecl = Context.ProcDecl.extend({
+var ProcOrMethodDecl = Class.extend.call(ContextProcedure.Declaration, {
     init: function EberonContext$ProcOrMethodDecl(parent, stdSymbols){
-        Context.ProcDecl.prototype.init.call(this, parent, stdSymbols);
+        ContextProcedure.Declaration.call(this, parent, stdSymbols);
         this.__methodId = undefined;
         this.__methodType = undefined;
         this.__boundType = undefined;
@@ -718,64 +719,64 @@ var ProcOrMethodDecl = Context.ProcDecl.extend({
                 this.__isConstructor = name == id.id();
             }
 
-            Context.ProcDecl.prototype.handleIdentdef.call(this, id);
+            ContextProcedure.Declaration.prototype.handleIdentdef.call(this, id);
             return;
         }
 
         if (handleTypePromotionMadeInSeparateStatement(msg))
             return;
 
-        return Context.ProcDecl.prototype.handleMessage.call(this, msg);
+        return ContextProcedure.Declaration.prototype.handleMessage.call(this, msg);
     },
-    _prolog: function(){
+    doProlog: function(){
         return this.__boundType
             ? this.__isConstructor ? "function " + Type.typeName(this.__boundType) + "("
                                    : Type.typeName(this.__boundType) + ".prototype." + this.__methodId.id() + " = function("
-            : Context.ProcDecl.prototype._prolog.call(this);
+            : ContextProcedure.Declaration.prototype.doProlog.call(this);
     },
-    _epilog: function(){
+    doEpilog: function(){
         return this.__boundType && !this.__isConstructor
             ? ";\n"
-            : Context.ProcDecl.prototype._epilog.call(this);
+            : ContextProcedure.Declaration.prototype.doEpilog.call(this);
     },
-    _beginBody: function(){
-        Context.ProcDecl.prototype._beginBody.call(this);
+    doBeginBody: function(){
+        ContextProcedure.Declaration.prototype.doBeginBody.call(this);
         if (this.__isConstructor)
             this.codeGenerator().write(
                 this.__boundType.baseConstructorCallCode
               + EberonRecord.fieldsInitializationCode(this.__boundType, this));
     },
-    _makeArgumentVariable: function(arg, name){
+    doMakeArgumentVariable: function(arg, name){
         if (!arg.isVar)
             return new TypeNarrowVariable(arg.type, false, true, name);
 
         if (arg.type instanceof Type.Record)
             return new TypeNarrowVariable(arg.type, true, false, name);
 
-        return Context.ProcDecl.prototype._makeArgumentVariable.call(this, arg, name);
+        return ContextProcedure.Declaration.prototype.doMakeArgumentVariable.call(this, arg, name);
     },
     setType: function(type){
         if (this.__methodId){
             this.__methodType = new EberonTypes.MethodType(this.__methodId.id(), type, Procedure.makeProcCallGenerator);
-            this.__type = type;
+            this.type = type;
             }            
         else
-            Context.ProcDecl.prototype.setType.call(this, type);
+            ContextProcedure.Declaration.prototype.setType.call(this, type);
     },
     handleIdent: function(id){
         if (!this.__boundType)
-            Context.ProcDecl.prototype.handleIdent.call(this, id);
+            ContextProcedure.Declaration.prototype.handleIdent.call(this, id);
         else if (this.__endingId)
             this.__endingId = this.__endingId + "." + id;
         else
             this.__endingId = id;
     },
     endParse: function(){
-        Context.ProcDecl.prototype.endParse.call(this);
+        ContextProcedure.Declaration.prototype.endParse.call(this);
 
         if (this.__boundType){
             if (this.__endingId){
-                var expected = Type.typeName(this.__boundType) + "." + this.__id.id();
+                var expected = Type.typeName(this.__boundType) + "." + this.id.id();
                 if (this.__endingId != expected)
                     throw new Errors.Error(
                           "mismatched method names: expected '" 
@@ -1335,7 +1336,7 @@ var ArrayDecl = Class.extend.call(ContextType.Array, {
 });
 
 function assertArgumentIsNotNonVarDynamicArray(msg){
-    if (msg instanceof Context.AddArgumentMsg){
+    if (msg instanceof ContextProcedure.AddArgumentMsg){
         var arg = msg.arg;
         if (!arg.isVar){
             var type = arg.type;

+ 5 - 5
src/ob/ContextHierarchy.ob

@@ -6,10 +6,10 @@ TYPE
     PRoot = POINTER TO Root;
     PNode* = POINTER TO Node;
 
-    Message = RECORD
+    Message* = RECORD
     END;
 
-    PMessageResult = POINTER TO RECORD
+    PMessageResult* = POINTER TO RECORD
     END;
 
     QIdent* = RECORD
@@ -29,7 +29,7 @@ TYPE
 
         PROCEDURE root*(): PRoot;
         PROCEDURE parent*(): PNode;
-        PROCEDURE handleMessage(VAR msg: Message): PMessageResult;
+        PROCEDURE handleMessage*(VAR msg: Message): PMessageResult;
         PROCEDURE codeGenerator*(): CodeGenerator.PIGenerator;
         PROCEDURE handleLiteral*(s: STRING);
         PROCEDURE handleIdent*(s: STRING);
@@ -49,8 +49,8 @@ TYPE
         PROCEDURE findModule(name: STRING): Types.PModule;
 
         PROCEDURE currentScope*(): Scope.PType;
-        PROCEDURE pushScope(scope: Scope.PType);
-        PROCEDURE popScope();
+        PROCEDURE pushScope*(scope: Scope.PType);
+        PROCEDURE popScope*();
 
         mLanguage: LanguageContext.PType;
         scopes: ARRAY * OF Scope.PType;

+ 160 - 0
src/ob/ContextProcedure.ob

@@ -0,0 +1,160 @@
+MODULE ContextProcedure;
+IMPORT
+    Cast, Chars, Context, ContextHierarchy, ContextType, 
+    Errors, Expression, LanguageContext,
+    Procedure, Scope, Symbols, Types, Variable;
+TYPE
+    Declaration* = RECORD(ContextType.DeclarationHandle)
+        PROCEDURE Declaration(parent: ContextHierarchy.PNode);
+
+        PROCEDURE doProlog(): STRING;
+        PROCEDURE doEpilog(): STRING;
+        PROCEDURE doBeginBody();
+        PROCEDURE doMakeArgumentVariable(arg: Types.ProcedureArgument; name: STRING): Types.PVariable;
+
+        PROCEDURE handleReturn(e: Expression.PType);
+
+        outerScope: Scope.PType;
+        id: Context.PIdentdefInfo;
+        type: Types.PDefinedProcedure;
+        multipleArguments: BOOLEAN;
+        returnParsed: BOOLEAN;
+    END;
+
+    AddArgumentMsg* = RECORD(ContextHierarchy.Message)
+        PROCEDURE AddArgumentMsg(name: STRING; arg: Types.PProcedureArgument);
+
+        name: STRING;
+        arg: Types.PProcedureArgument;
+    END;
+
+    EndParametersMsg* = RECORD(ContextHierarchy.Message)
+    END;
+
+PROCEDURE Declaration.Declaration(parent: ContextHierarchy.PNode)
+    | SUPER(parent),
+      outerScope(SELF.root().currentScope());
+END;
+
+PROCEDURE Declaration.handleIdentdef(id: Context.PIdentdefInfo);
+BEGIN
+    SELF.id := id;
+    SELF.codeGenerator().write(SELF.doProlog());
+    root <- SELF.root();
+    root.pushScope(Scope.makeProcedure(root.language().stdSymbols));
+END;
+
+PROCEDURE Declaration.handleIdent(id: STRING);
+BEGIN
+    expectId <- SELF.id.id();
+    IF expectId # id THEN
+        Errors.raise("mismatched procedure names: '" + expectId
+                     + "' at the begining and '" + id + "' at the end");
+    END;
+END;
+
+PROCEDURE Declaration.doProlog(): STRING;
+    RETURN Chars.ln + "function " + SELF.id.id() + "(";
+END;
+
+PROCEDURE Declaration.doEpilog(): STRING;
+    RETURN "";
+END;
+
+PROCEDURE Declaration.doBeginBody();
+BEGIN
+    SELF.codeGenerator().openScope();
+END;
+
+PROCEDURE Declaration.typeName(): STRING;
+    RETURN "";
+END;
+
+PROCEDURE Declaration.setType(type: Types.PStorageType);
+BEGIN
+    t <- type(Types.PDefinedProcedure);
+    procSymbol <- NEW Symbols.Symbol(
+        SELF.id.id(), NEW Types.ProcedureId(t));
+    SELF.outerScope.addSymbol(procSymbol, SELF.id.exported());
+    SELF.type := t;
+END;
+
+PROCEDURE addArgument(VAR declaration: Declaration; name: STRING; arg: Types.ProcedureArgument);
+BEGIN
+    IF name = declaration.id.id() THEN
+        Errors.raise("argument '" + name + "' has the same name as procedure");
+    END;
+    v <- declaration.doMakeArgumentVariable(arg, name);
+    s <- NEW Symbols.Symbol(name, v);
+    declaration.root().currentScope().addSymbol(s, FALSE);
+
+    code <- declaration.codeGenerator();
+    IF declaration.multipleArguments THEN
+        code.write(", ");
+    ELSE
+        declaration.multipleArguments := TRUE;
+    END;
+    code.write(name + "/*" + arg.description() + "*/");
+END;
+
+PROCEDURE Declaration.doMakeArgumentVariable(arg: Types.ProcedureArgument; name: STRING): Types.PVariable;
+    RETURN NEW Variable.ArgumentVariable(name, arg.type, arg.isVar);
+END;
+
+PROCEDURE Declaration.handleMessage(VAR msg: ContextHierarchy.Message): ContextHierarchy.PMessageResult;
+VAR
+    result: ContextHierarchy.PMessageResult;
+BEGIN
+    IF msg IS EndParametersMsg THEN
+        SELF.codeGenerator().write(")");
+        SELF.doBeginBody();
+    ELSIF msg IS AddArgumentMsg THEN
+        ASSERT(msg.arg # NIL);
+        addArgument(SELF, msg.name, msg.arg^);
+    ELSE
+        result := SUPER(msg);
+    END;
+    RETURN result;
+END;
+
+PROCEDURE Declaration.handleReturn(e: Expression.PType);
+VAR
+    op: LanguageContext.PCastOp;
+BEGIN
+    type <- e.type();
+    result <- SELF.type.result();
+    IF result = NIL THEN
+        Errors.raise("unexpected RETURN in PROCEDURE declared with no result type");
+    END;
+    
+    language <- SELF.root().language();
+    IF language.types.implicitCast(type, result, FALSE, op) # Cast.errNo THEN
+        Errors.raise(
+            "RETURN '" + result.description() + "' expected, got '"
+            + type.description() + "'");
+    END;
+
+    SELF.codeGenerator().write("return " + op.clone(language, e) + ";" + Chars.ln);
+
+    SELF.returnParsed := TRUE;
+END;
+
+PROCEDURE Declaration.endParse(): BOOLEAN;
+BEGIN
+    SELF.codeGenerator().closeScope(SELF.doEpilog());
+    SELF.root().popScope();
+
+    result <- SELF.type.result();
+    IF (result # NIL) & ~SELF.returnParsed THEN
+        Errors.raise("RETURN expected at the end of PROCEDURE declared with '"
+                     + result.description() + "' result type");
+    END;
+    RETURN TRUE;
+END;
+
+PROCEDURE AddArgumentMsg.AddArgumentMsg(name: STRING; arg: Types.PProcedureArgument)
+    | name(name),
+      arg(arg);
+END;
+
+END ContextProcedure.

+ 2 - 2
src/ob/ContextType.ob

@@ -6,7 +6,7 @@ IMPORT
 TYPE
     HandleSymbolAsType* = RECORD(ContextHierarchy.Node)
         PROCEDURE handleQIdent(q: ContextHierarchy.QIdent);
-        PROCEDURE setType(type: Types.PStorageType);
+        PROCEDURE setType*(type: Types.PStorageType);
     END;
     PHandleSymbolAsType = POINTER TO HandleSymbolAsType;
 
@@ -39,7 +39,7 @@ TYPE
         PROCEDURE isAnonymousDeclaration(): BOOLEAN;
         PROCEDURE exportField(name: STRING);
         PROCEDURE handleIdentdef*(id: Context.PIdentdefInfo);
-        PROCEDURE typeName(): STRING;
+        PROCEDURE typeName*(): STRING;
     END;
     PDeclarationHandle* = POINTER TO DeclarationHandle;
 

+ 2 - 1
src/ob/LanguageContext.ob

@@ -1,5 +1,5 @@
 MODULE LanguageContext;
-IMPORT Context, CodeGenerator, Expression, T := Types;
+IMPORT Context, CodeGenerator, Expression, Symbols, T := Types;
 
 TYPE
     PType* = POINTER TO Type;
@@ -24,6 +24,7 @@ TYPE
         moduleResolver*: PROCEDURE(name: STRING): T.PModule;
         codeGenerator*: CodeGenerator.PIGenerator;
         types*: PTypes;
+        stdSymbols*: Symbols.Map;
     END;
 
 END LanguageContext.

+ 2 - 2
src/ob/Procedure.ob

@@ -267,12 +267,12 @@ PROCEDURE makeSymbol*(p: Types.PProcedure): Symbols.PSymbol;
     RETURN NEW Symbols.Symbol(p.name, NEW Types.ProcedureId(p))
 END;
 
-PROCEDURE hasArgument(call: PStdCall; type: Types.PType);
+PROCEDURE hasArgument(call: PStdCall; type: Types.PStorageType);
 BEGIN
     call.args.add(NEW Types.ProcedureArgument(type, FALSE));
 END hasArgument;
 
-PROCEDURE hasVarArgument(call: PStdCall; type: Types.PType);
+PROCEDURE hasVarArgument(call: PStdCall; type: Types.PStorageType);
 BEGIN
     call.args.add(NEW Types.ProcedureArgument(type, TRUE));
 END hasVarArgument;

+ 4 - 4
src/ob/Types.ob

@@ -109,11 +109,11 @@ TYPE
     END;
 
     ProcedureArgument* = RECORD
-        PROCEDURE ProcedureArgument*(type: PType; isVar: BOOLEAN);
+        PROCEDURE ProcedureArgument*(type: PStorageType; isVar: BOOLEAN);
 
-        PROCEDURE description(): STRING;
+        PROCEDURE description*(): STRING;
 
-        type*: PType;
+        type*: PStorageType;
         isVar*: BOOLEAN
     END;
 
@@ -336,7 +336,7 @@ BEGIN
     RETURN result + SELF.type.description()
 END ProcedureArgument.description;
 
-PROCEDURE ProcedureArgument.ProcedureArgument(type: PType; isVar: BOOLEAN)
+PROCEDURE ProcedureArgument.ProcedureArgument(type: PStorageType; isVar: BOOLEAN)
     | type(type),
       isVar(isVar);
 END;

+ 1 - 1
src/ob/Variable.ob

@@ -15,7 +15,7 @@ TYPE
     END;
 
     ArgumentVariable* = RECORD(DeclaredVariable)
-        PROCEDURE ArgumentVariable(id: STRING; type: Types.PStorageType; var: BOOLEAN);
+        PROCEDURE ArgumentVariable*(id: STRING; type: Types.PStorageType; var: BOOLEAN);
 
         var: BOOLEAN;
     END;

+ 2 - 1
src/oberon/oberon_grammar.js

@@ -7,6 +7,7 @@ var ContextConst = require("js/ContextConst.js");
 var ContextDesignator = require("js/ContextDesignator.js");
 var ContextExpression = require("js/ContextExpression.js");
 var ContextIdentdef = require("js/ContextIdentdef.js");
+var ContextProcedure = require("js/ContextProcedure.js");
 var ContextType = require("js/ContextType.js");
 var Grammar = require("grammar.js");
 var ObContext = require("oberon/oberon_context.js");
@@ -64,7 +65,7 @@ function makeProcedureDeclaration(ident, procedureHeading, procedureBody){
     return context(and(procedureHeading, ";",
                        procedureBody,
                        ident),
-                   Context.ProcDecl);
+                   ContextProcedure.Declaration);
 }
 
 function makeFieldList(identdef, identList, type){