@samitouri / QOS-React-2 / commits / 1228bc8ce5

[codegen] assign some locations in generated code (#802)

Jan Kassens committed Nov 21, 2022 at 15:14 UTC 1228bc8ce5eadd15a4d25ba373afcb4eef8543be
2 files changed +31 -8
compiler/forget/packages/playground/components/Editor/HIRTabContent.tsx
+3 -5
@@ -38,7 +38,7 @@ export default function HIRTabContent({ source }: { source: string }) {
38 });
39
40 return (
41 - <div className="h-full flex flex-col">
41 + <div className="flex flex-col h-full">
42 <div className="flex-1">
43 {astFunctions.map((func, index): React.ReactNode => {
44 let body;
@@ -61,8 +61,6 @@ export default function HIRTabContent({ source }: { source: string }) {
61
62 if (flags.codegen) {
63 const ast = codegen(ir);
64 - // TODO: codegen should set this correctly directly
65 - ast.loc = func.node.loc;
64 const generated = generate(
65 ast,
66 {
@@ -100,8 +98,8 @@ export default function HIRTabContent({ source }: { source: string }) {
98 }
99 const name = func.node.id?.name ?? "anonymous";
100 return (
103 - <div key={index} className="border-b py-4 px-2">
104 - <h3 className="font-medium mb-2">Function: {name}</h3>
101 + <div key={index} className="px-2 py-4 border-b">
102 + <h3 className="mb-2 font-medium">Function: {name}</h3>
103 {body}
104 </div>
105 );
compiler/forget/src/HIR/Codegen.ts
+28 -3
@@ -9,6 +9,7 @@ import * as t from "@babel/types";
9 import { assertExhaustive } from "../Common/utils";
10 import { invariant } from "../CompilerError";
11 import {
12 + GeneratedSource,
13 HIRFunction,
14 Identifier,
15 IdentifierId,
@@ -17,10 +18,28 @@ import {
18 InstructionValue,
19 LValue,
20 Place,
21 + SourceLocation,
22 } from "./HIR";
23 import { BlockTerminal, Visitor, visitTree } from "./HIRTreeVisitor";
24 import { todoInvariant } from "./todo";
25
26 +function withLoc<TNode extends t.Node, T extends (...args: any[]) => TNode>(
27 + fn: T
28 +): (loc: SourceLocation, ...args: Parameters<T>) => ReturnType<T> {
29 + return (loc: SourceLocation, ...args: Parameters<T>): ReturnType<T> => {
30 + const node = fn(...args);
31 + if (loc != GeneratedSource) {
32 + node.loc = loc;
33 + }
34 + // @ts-ignore
35 + return node;
36 + };
37 +}
38 +
39 +const createFunctionDeclaration = withLoc(t.functionDeclaration);
40 +const createVariableDeclaration = withLoc(t.variableDeclaration);
41 +const createAssignmentExpression = withLoc(t.assignmentExpression);
42 +
43 /**
44 * Converts HIR into Babel nodes, which can then be printed into source text.
45 * Note that converting source to HIR and back is not guaranteed to produce
@@ -46,7 +65,8 @@ export default function codegen(fn: HIRFunction): t.Function {
65 const body = visitTree(fn, visitor);
66 invariant(t.isBlockStatement(body), "Expected a block statement");
67 const params = fn.params.map((param) => convertIdentifier(param.identifier));
49 - return t.functionDeclaration(
68 + return createFunctionDeclaration(
69 + fn.loc,
70 fn.id !== null ? convertIdentifier(fn.id) : null,
71 params,
72 body,
@@ -101,13 +121,18 @@ class CodegenVisitor
121 ]);
122 }
123 case InstructionKind.Let: {
104 - return t.variableDeclaration("let", [
124 + return createVariableDeclaration(instr.loc, "let", [
125 t.variableDeclarator(codegenLVal(instr.lvalue), value),
126 ]);
127 }
128 case InstructionKind.Reassign: {
129 return t.expressionStatement(
110 - t.assignmentExpression("=", codegenLVal(instr.lvalue), value)
130 + createAssignmentExpression(
131 + instr.loc,
132 + "=",
133 + codegenLVal(instr.lvalue),
134 + value
135 + )
136 );
137 }
138 default: {