Fixed weak self method pointer bug

Better formatting of function calls in pretty printer
This commit is contained in:
Michael Schimmel
2025-10-07 10:42:53 +02:00
parent 039a7c4b3e
commit 51265ce945
3 changed files with 38 additions and 48 deletions
+1 -1
View File
@@ -45,10 +45,10 @@ end;
destructor TUpvalueAnalyzer.Destroy;
begin
FBoxedDeclarations.Free;
for var dict in FDeclarationMap.Values do
dict.Free;
FDeclarationMap.Free;
FBoxedDeclarations.Free;
inherited Destroy;
end;
+32 -35
View File
@@ -193,46 +193,43 @@ begin
var scopeDescriptor := boundNode.ScopeDescriptor;
var params := boundNode.Parameters;
// [weak] prevents a reference cycle since the closure captures itself for 'recur'.
var [weak] closure: TDataValue.TFunc;
var cNode: ILambdaExpressionNode := Node;
// [unsafe] prevents a reference cycle since the closure captures itself for 'recur'.
var [unsafe] closure: TDataValue.TFunc;
closure :=
TDataValue.TFunc(
function(const ArgValues: TArray<TDataValue>): TDataValue
var
lambdaScope: IExecutionScope;
bodyVisitor: IAstVisitor;
i: Integer;
adr: TResolvedAddress;
function(const ArgValues: TArray<TDataValue>): TDataValue
var
lambdaScope: IExecutionScope;
bodyVisitor: IAstVisitor;
i: Integer;
adr: TResolvedAddress;
begin
if (Length(ArgValues) <> Length(params)) then
raise EArgumentException.CreateFmt('Argument count mismatch: expected %d, got %d', [Length(params), Length(ArgValues)]);
// Create the new execution scope for this function call.
lambdaScope := TScope.CreateScope(closureScope, scopeDescriptor, capturedCells);
adr.Kind := akLocalOrParent;
adr.ScopeDepth := 0;
// Capture the closure itself in slot 0 for 'recur' to find it.
adr.SlotIndex := 0;
lambdaScope[adr] := closure;
// Populate the scope with the actual parameters passed to the function.
for i := 0 to High(ArgValues) do
begin
if (Length(ArgValues) <> Length(params)) then
raise EArgumentException.CreateFmt('Argument count mismatch: expected %d, got %d', [Length(params), Length(ArgValues)]);
// Parameters in a bound lambda must be bound identifiers.
adr.SlotIndex := (params[i] as TBoundIdentifierNode).Address.SlotIndex;
lambdaScope[adr] := ArgValues[i];
end;
// Create the new execution scope for this function call.
lambdaScope := TScope.CreateScope(closureScope, scopeDescriptor, capturedCells);
adr.Kind := akLocalOrParent;
adr.ScopeDepth := 0;
// Capture the closure itself in slot 0 for 'recur' to find it.
adr.SlotIndex := 0;
lambdaScope[adr] := TDataValue(closure);
// Populate the scope with the actual parameters passed to the function.
for i := 0 to High(ArgValues) do
begin
// Parameters in a bound lambda must be bound identifiers.
adr.SlotIndex := (params[i] as TBoundIdentifierNode).Address.SlotIndex;
lambdaScope[adr] := ArgValues[i];
end;
// Create a visitor with the new scope and execute the lambda's body.
bodyVisitor := visitorFactory(lambdaScope);
Result := cNode.Body.Accept(bodyVisitor);
end
);
// Create a visitor with the new scope and execute the lambda's body.
bodyVisitor := visitorFactory(lambdaScope);
Result := cNode.Body.Accept(bodyVisitor);
end;
// The result of visiting a lambda node is the callable closure itself.
Result := closure;
+5 -12
View File
@@ -398,13 +398,11 @@ begin
begin
if (Length(tailNodes) <> 3) or (tailTokens[0].Kind <> tkIdentifier) then
raise Exception.Create('Syntax Error: ''defmacro'' requires a name, a parameter list, and a body.');
if elements[2].Params = nil then
raise Exception.Create('Syntax Error: Expected a parameter list [...] after macro name.');
var macroName := IIdentifierNode(tailNodes[0]);
var macroParams := elements[2].Params;
if tailTokens[2].Kind <> tkQuote then
if tailTokens[2].Kind <> tkBacktick then
raise Exception.Create('Syntax Error: Expected a quasiquote as macro body.');
var macroBody := IQuasiQuoteNode(tailNodes[2]);
@@ -421,8 +419,6 @@ begin
begin
if Length(tailNodes) <> 2 then
raise Exception.Create('Syntax Error: ''fn'' requires a parameter list and a body.');
if elements[1].Params = nil then
raise Exception.Create('Syntax Error: Expected a parameter list [...] after ''fn''.');
Result := TAst.LambdaExpr(elements[1].Params, tailNodes[1]);
end
else if SameText(head.Token.Text, 'do') then
@@ -453,6 +449,7 @@ var
expr: TExpr;
begin
// Handle reader macros.
Result.Token := FCurrentToken;
case FCurrentToken.Kind of
tkBacktick:
begin
@@ -735,14 +732,11 @@ begin
Indent;
for arg in Node.Arguments do
begin
NewLine;
Append(' ');
arg.Accept(Self);
end;
Unindent;
if Length(Node.Arguments) > 0 then
NewLine;
Append(')');
Result := TDataValue.Void;
end;
@@ -762,12 +756,11 @@ begin
Indent;
for arg in Node.Arguments do
begin
NewLine;
Append(' ');
arg.Accept(Self);
end;
Unindent;
if Length(Node.Arguments) > 0 then
NewLine;
Append(')');
Result := TDataValue.Void;
end;