Diff
Not logged in

Differences From Artifact [ca0ab118700475a8]:

To Artifact [a7c677ad83621b47]:


98 98 } 99 99 100 100 Value eval( App e, Layer lay, Table ctx, bool overwriteCtx=CascadeCtx ) 101 101 { 102 102 Value f = eval( e.fun, lay, ctx ); 103 103 if( isMacroishLayer(lay) ) 104 104 if( auto ff = cast(FunValue)f ) 105 - return invokeFunction(ff, e.args, MacroLayer, ctx, e.pos); 105 + return invokeFunction(ff, e.args, MacroLayer, ctx, e.pos, getNameIfPossible(e.fun)); 106 106 else 107 107 return ast2table(e, (AST e){return eval(e,lay,ctx);}); 108 - return invokeFunction(f, e.args, lay, ctx, e.pos); 108 + return invokeFunction(f, e.args, lay, ctx, e.pos, getNameIfPossible(e.fun)); 109 109 } 110 110 111 111 Value eval( Fun e, Layer lay, Table ctx, bool overwriteCtx=CascadeCtx ) 112 112 { 113 113 if( isMacroishLayer(lay) ) 114 114 return ast2table(e, (AST e){return eval(e,lay,ctx);}); 115 115 else ................................................................................ 137 137 string theLayer = e.layer.empty ? lay : e.layer; // neutral layer 138 138 ctx.set(e.name, theLayer, ri); 139 139 return eval(e.expr, lay, ctx, OverwriteCtx); 140 140 } 141 141 } 142 142 143 143 private: 144 - Value invokeFunction(Value _f, AST[] args, Layer lay, Table ctx, LexPosition pos=null) 144 + string getNameIfPossible(AST e) 145 + { 146 + if(auto v = cast(Var)e) 147 + return v.name; 148 + return ""; 149 + } 150 + 151 + Value invokeFunction(Value _f, AST[] args, Layer lay, Table ctx, LexPosition pos, string callstackmsg) 145 152 { 146 153 if(auto f = cast(FunValue)_f) 147 154 { 148 155 Table newCtx = new Table(f.definitionContext(), Table.Kind.NotPropagateSet); 149 156 foreach(i,p; f.params()) 150 157 if( p.layers.empty ) 151 158 newCtx.set(p.name, (lay==RawMacroLayer ? MacroLayer : lay), eval(args[i], lay, ctx)); 152 159 else 153 160 foreach(argLay; p.layers) 154 161 newCtx.set(p.name, argLay, eval(args[i], argLay, ctx)); 162 + scope _ = new PushCallStack(pos, callstackmsg); 155 163 return f.invoke(lay==RawMacroLayer ? MacroLayer : lay, newCtx, pos); 156 164 } 157 165 throw genex!RuntimeException(pos, text("tried to call non-function: ",_f)); 158 166 } 159 167 160 - Value lift(Value v, Layer lay, Table ctx, LexPosition pos=null) 168 + Value lift(Value v, Layer lay, Table ctx, LexPosition pos) 161 169 { 162 - assert( !isMacroishLayer(lay), "lift to the @macro layer should not happen" ); 170 + assert( !isMacroishLayer(lay), "lift to the @macro layer should never happen" ); 163 171 164 172 // functions are automatically lifterd 165 173 if( cast(FunValue) v ) 166 174 return v; 167 175 168 - // similar to invoke Function, but with only one argument bound to ValueLayer 169 - if(auto f = cast(FunValue)ctx.get(lay, SystemLayer, pos)) 176 + if( !ctx.has(lay, SystemLayer) ) 177 + throw genex!RuntimeException(pos, "lift function for "~lay~" is not registered" ); 178 + 179 + // similar to invokeFunction, but with only one argument bound to ValueLayer 180 + auto _f = ctx.get(lay, SystemLayer, pos); 181 + if(auto f = cast(FunValue)_f) 170 182 { 171 183 Table newCtx = new Table(f.definitionContext(), Table.Kind.NotPropagateSet); 172 184 auto ps = f.params(); 173 185 if( ps.length != 1 ) 174 - throw genex!RuntimeException(pos, "lift function must take exactly one argument at "~ValueLayer~" layer"); 186 + throw genex!RuntimeException(pos, 187 + text("lift function for", lay, " must take exactly one argument of ", ValueLayer)); 175 188 if( ps[0].layers.length==0 || ps[0].layers.length==1 && ps[0].layers[0]==ValueLayer ) 176 189 { 177 190 newCtx.set(ps[0].name, ValueLayer, v); 191 + scope _ = new PushCallStack(pos, lay); 178 192 return f.invoke(ValueLayer, newCtx, pos); 179 193 } 180 194 else 181 - throw genex!RuntimeException(pos, "lift function must take exactly one argument at "~ValueLayer~" layer"); 195 + throw genex!RuntimeException(pos, 196 + text("lift function for", lay, " must take exactly one argument of ", ValueLayer)); 182 197 } 183 - throw genex!RuntimeException(pos, "tried to call non-function"); 198 + throw genex!RuntimeException(pos, 199 + text("non-function ", _f, " is registered as the lift function for ", lay)); 184 200 } 185 201 186 202 Value createNewFunction(Fun e, Table ctx) 187 203 { 188 204 class UserDefinedFunValue : FunValue 189 205 { 190 206 Fun ast; ................................................................................ 215 231 assert(false, sprintf!"Cannot compare %s with %s"(typeid(this), typeid(rhs_))); 216 232 } 217 233 218 234 override Value invoke(Layer lay, Table ctx, LexPosition pos) 219 235 { 220 236 if( lay == MacroLayer ) 221 237 return eval(ast.funbody, lay, ctx); 222 - if( afterMacroAST is null ) 223 - afterMacroAST = tableToAST(ValueLayer, eval(e.funbody, RawMacroLayer, ctx)); 224 - return eval(afterMacroAST, lay, ctx); 238 + try { 239 + if( afterMacroAST is null ) 240 + afterMacroAST = polemy2d!(AST)(eval(e.funbody, RawMacroLayer, ctx), pos); 241 + return eval(afterMacroAST, lay, ctx); 242 + } catch( RuntimeException e ) { 243 + throw e.pos is null ? new RuntimeException(pos, e.msg, e.file, e.line, e.next) : e; 244 + } 225 245 } 226 246 227 247 AST afterMacroAST; 228 248 } 229 249 return new UserDefinedFunValue(e,ctx); 230 250 } 231 251