gofront 1.8.0 → 1.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -3
- package/package.json +5 -4
- package/src/backend/js/expressions.js +849 -371
- package/src/backend/js/index.js +241 -147
- package/src/backend/js/natives.js +383 -0
- package/src/backend/js/runtime.js +512 -2547
- package/src/backend/js/statements.js +506 -103
- package/src/backend/js/stdlib/index.js +45 -93
- package/src/backend/js/templ.js +32 -45
- package/src/backend/js/type-info.js +177 -13
- package/src/backend/shared/fixed-float.js +20 -0
- package/src/backend/shared/fmt-types.js +63 -171
- package/src/backend/shared/host-unicode.js +36 -0
- package/src/backend/wasm/boundary.js +490 -965
- package/src/backend/wasm/emit-builtins.js +643 -256
- package/src/backend/wasm/emit-exprs.js +124 -57
- package/src/backend/wasm/emit-maps.js +17 -367
- package/src/backend/wasm/emit-stmts.js +325 -75
- package/src/backend/wasm/emit.js +104 -13
- package/src/backend/wasm/globals.js +47 -8
- package/src/backend/wasm/glue.js +2 -4
- package/src/backend/wasm/index.js +36 -530
- package/src/backend/wasm/method-expr.js +12 -1
- package/src/backend/wasm/module-emitter.js +92 -717
- package/src/backend/wasm/monomorph.js +103 -6
- package/src/backend/wasm/natives.js +596 -0
- package/src/backend/wasm/prescan.js +5 -153
- package/src/backend/wasm/prune-funcs.js +89 -0
- package/src/backend/wasm/stdlib/index.js +2 -32
- package/src/backend/wasm/types.js +68 -20
- package/src/backend/wasm/variadic.js +3 -3
- package/src/cli/cli-core.js +5 -1
- package/src/cli/test-runner.js +115 -342
- package/src/compiler.js +108 -130
- package/src/lexer/lexer.js +105 -11
- package/src/lexer/templ-lexer.js +61 -18
- package/src/lexer/tokens.js +1 -0
- package/src/link/stdlib.js +354 -132
- package/src/link/type-names.js +148 -0
- package/src/link/wasm.js +30 -6
- package/src/lower/bounds.js +153 -0
- package/src/lower/captures.js +92 -33
- package/src/lower/embedding.js +32 -3
- package/src/lower/errors-as.js +196 -0
- package/src/lower/fmt-formatters.js +905 -0
- package/src/lower/functions.js +2 -0
- package/src/lower/gen-types.js +274 -0
- package/src/lower/index.js +7 -1
- package/src/lower/json-codecs.js +228 -247
- package/src/lower/ownership.js +25 -7
- package/src/lower/reachability.js +69 -51
- package/src/lower/walk.js +12 -0
- package/src/parser/declarations.js +28 -5
- package/src/parser/expressions.js +86 -16
- package/src/parser/statements.js +1 -0
- package/src/parser/templ.js +44 -5
- package/src/parser/types.js +1 -0
- package/src/resolver.js +1 -2
- package/src/typechecker/assignability.js +124 -11
- package/src/typechecker/const-fold.js +70 -27
- package/src/typechecker/constants.js +32 -6
- package/src/typechecker/expressions.js +326 -98
- package/src/typechecker/index.js +208 -33
- package/src/typechecker/init-order.js +136 -40
- package/src/typechecker/operand-text.js +40 -0
- package/src/typechecker/resolve.js +192 -36
- package/src/typechecker/statements.js +122 -11
- package/src/typechecker/stdlib/excluded.js +9 -5
- package/src/typechecker/stdlib/index.js +25 -9
- package/src/typechecker/termination.js +10 -1
- package/src/typechecker/types.js +203 -573
- package/stdlib/bytes/buffer.go +479 -0
- package/stdlib/bytes/bytes.go +1010 -0
- package/stdlib/bytes/reader.go +161 -0
- package/stdlib/context/context.go +115 -0
- package/stdlib/crypto/rand/rand.go +34 -0
- package/stdlib/crypto/sha256/sha256.go +249 -0
- package/stdlib/encoding/base64/base64.go +331 -0
- package/stdlib/encoding/binary/binary.go +332 -0
- package/stdlib/encoding/hex/hex.go +140 -0
- package/stdlib/encoding/json/json.go +62 -0
- package/stdlib/errors/errors.go +174 -0
- package/stdlib/fmt/errors.go +110 -0
- package/stdlib/fmt/format.go +732 -0
- package/stdlib/fmt/print.go +1232 -0
- package/stdlib/gom/gom.go +293 -0
- package/stdlib/html/html.go +251 -0
- package/stdlib/internal/fmtrt/fmtrt.go +163 -0
- package/stdlib/internal/jsonrt/dec.go +171 -38
- package/stdlib/internal/jsonrt/enc.go +186 -36
- package/stdlib/internal/jsonrt/scanner.go +17 -8
- package/stdlib/io/io.go +157 -1
- package/stdlib/maps/maps.go +131 -0
- package/stdlib/math/bits/bits.go +507 -0
- package/stdlib/math/extra.go +16 -14
- package/stdlib/math/math.go +439 -0
- package/stdlib/math/rand/rand.go +297 -0
- package/stdlib/os/os.go +93 -0
- package/stdlib/path/filepath/filepath.go +47 -0
- package/stdlib/path/path.go +394 -0
- package/stdlib/regexp/regexp.go +231 -0
- package/stdlib/slices/slices.go +526 -0
- package/stdlib/slices/sort.go +209 -0
- package/stdlib/slices/zsort_cmp.go +480 -0
- package/stdlib/slices/zsort_ordered.go +482 -0
- package/stdlib/sort/sort.go +391 -452
- package/stdlib/sort/zsort_func.go +480 -0
- package/stdlib/sort/zsort_iface.go +480 -0
- package/stdlib/strconv/float.go +1699 -0
- package/stdlib/strconv/isprint.go +752 -0
- package/stdlib/strconv/quote.go +235 -50
- package/stdlib/strconv/strconv.go +616 -0
- package/stdlib/strings/builder.go +95 -0
- package/stdlib/strings/reader.go +163 -0
- package/stdlib/strings/replacer.go +102 -0
- package/stdlib/strings/strings.go +807 -0
- package/stdlib/sync/sync.go +268 -0
- package/stdlib/testing/async_js.go +61 -0
- package/stdlib/testing/benchmark.go +297 -0
- package/stdlib/testing/testing.go +523 -0
- package/stdlib/time/duration.go +233 -0
- package/stdlib/time/format.go +745 -0
- package/stdlib/time/parse.go +790 -0
- package/stdlib/time/sleep_js.go +63 -0
- package/stdlib/time/time.go +834 -0
- package/stdlib/unicode/unicode.go +141 -3
- package/stdlib/unicode/utf8/utf8.go +464 -0
- package/src/backend/js/fmt-runtime.js +0 -573
- package/src/backend/js/stdlib/base64.js +0 -12
- package/src/backend/js/stdlib/binary.js +0 -102
- package/src/backend/js/stdlib/bits.js +0 -119
- package/src/backend/js/stdlib/builder.js +0 -98
- package/src/backend/js/stdlib/bytes.js +0 -368
- package/src/backend/js/stdlib/errors.js +0 -45
- package/src/backend/js/stdlib/fmt.js +0 -517
- package/src/backend/js/stdlib/gom.js +0 -155
- package/src/backend/js/stdlib/hex.js +0 -17
- package/src/backend/js/stdlib/html.js +0 -20
- package/src/backend/js/stdlib/io.js +0 -137
- package/src/backend/js/stdlib/json.js +0 -1167
- package/src/backend/js/stdlib/maps.js +0 -37
- package/src/backend/js/stdlib/math.js +0 -85
- package/src/backend/js/stdlib/os.js +0 -13
- package/src/backend/js/stdlib/path.js +0 -48
- package/src/backend/js/stdlib/rand.js +0 -32
- package/src/backend/js/stdlib/regexp.js +0 -54
- package/src/backend/js/stdlib/sha256.js +0 -12
- package/src/backend/js/stdlib/shared.js +0 -17
- package/src/backend/js/stdlib/simd.js +0 -34
- package/src/backend/js/stdlib/slices.js +0 -107
- package/src/backend/js/stdlib/sort.js +0 -30
- package/src/backend/js/stdlib/strconv.js +0 -79
- package/src/backend/js/stdlib/strings.js +0 -301
- package/src/backend/js/stdlib/sync.js +0 -13
- package/src/backend/js/stdlib/testing.js +0 -41
- package/src/backend/js/stdlib/time.js +0 -152
- package/src/backend/js/stdlib/unicode.js +0 -25
- package/src/backend/js/stdlib/utf8.js +0 -26
- package/src/backend/wasm/stdlib/bytes.js +0 -6716
- package/src/backend/wasm/stdlib/core.js +0 -10278
- package/src/backend/wasm/stdlib/io.js +0 -3578
- package/src/backend/wasm/stdlib/packages.js +0 -2402
- package/src/backend/wasm/stdlib/pure.js +0 -720
- package/src/backend/wasm/stdlib/time.js +0 -2229
- package/src/typechecker/stdlib/core.js +0 -1079
- package/src/typechecker/stdlib/extended.js +0 -1210
- package/stdlib/bytes/iter.go +0 -192
- package/stdlib/bytes/search.go +0 -240
- package/stdlib/bytes/split.go +0 -218
- package/stdlib/errors/overlay.go +0 -12
- package/stdlib/maps/iter.go +0 -65
- package/stdlib/slices/extra.go +0 -73
- package/stdlib/slices/iter.go +0 -113
- package/stdlib/strings/extra.go +0 -35
- package/stdlib/strings/iter.go +0 -122
- package/stdlib/sync/extra.go +0 -105
- package/stdlib/unicode/utf8/bytes.go +0 -239
|
@@ -0,0 +1,196 @@
|
|
|
1
|
+
// src/lower/errors-as.js
|
|
2
|
+
// errors.As as generated Go source.
|
|
3
|
+
//
|
|
4
|
+
// `errors.As(err, &x)` stores through a pointer whose type only the checker
|
|
5
|
+
// knows. Each call site gets a function generated for its static target
|
|
6
|
+
// type; it walks the error tree like the real package and honours custom
|
|
7
|
+
// `As(any) bool` methods. The functions are ordinary Go, parsed and checked
|
|
8
|
+
// as part of the package's generated file (src/link/stdlib.js), so both
|
|
9
|
+
// backends compile the same code.
|
|
10
|
+
|
|
11
|
+
import {
|
|
12
|
+
importsFor,
|
|
13
|
+
mentionsTypeParam,
|
|
14
|
+
TypeSpeller,
|
|
15
|
+
walkNodes,
|
|
16
|
+
} from "./gen-types.js";
|
|
17
|
+
|
|
18
|
+
const ERRORS_PATH = "errors";
|
|
19
|
+
const NOT_POINTER =
|
|
20
|
+
"errors.As: second argument must be a non-nil pointer to a type that implements error or to any interface type";
|
|
21
|
+
|
|
22
|
+
// The names the file imports `errors` as.
|
|
23
|
+
function errorsAliases(program) {
|
|
24
|
+
const aliases = new Set();
|
|
25
|
+
for (const imp of program.imports ?? [])
|
|
26
|
+
for (const spec of imp.imports)
|
|
27
|
+
if (spec.path === ERRORS_PATH && spec.alias !== "_")
|
|
28
|
+
aliases.add(spec.alias ?? "errors");
|
|
29
|
+
return aliases;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
const isAsRef = (node, aliases) =>
|
|
33
|
+
node.kind === "SelectorExpr" &&
|
|
34
|
+
node.expr?.kind === "Ident" &&
|
|
35
|
+
node.expr._type?.kind === "namespace" &&
|
|
36
|
+
aliases.has(node.expr.name) &&
|
|
37
|
+
node.field === "As";
|
|
38
|
+
|
|
39
|
+
const isAsCall = (node, aliases) =>
|
|
40
|
+
node.kind === "CallExpr" && isAsRef(node.func, aliases);
|
|
41
|
+
|
|
42
|
+
// Marks `call` to call the generated function `name`. The function takes the
|
|
43
|
+
// typed pointer: the target is not boxed into an interface the way
|
|
44
|
+
// errors.As's `any` parameter asked.
|
|
45
|
+
function markCall(call, name) {
|
|
46
|
+
call.func._genEntry = name;
|
|
47
|
+
const arg = call.args[1];
|
|
48
|
+
arg._ifaceBox = undefined;
|
|
49
|
+
arg._ifaceSrc = undefined;
|
|
50
|
+
arg._ifaceNamedType = undefined;
|
|
51
|
+
arg._ifacePtrFields = undefined;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
// One function per distinct target type; `tparams` ("[T any]") makes it the
|
|
55
|
+
// shared function for targets that are a type parameter.
|
|
56
|
+
function asFunction(name, target, tparams = "") {
|
|
57
|
+
return `func ${name}${tparams}(err error, target *${target}) bool {
|
|
58
|
+
if target == nil {
|
|
59
|
+
panic("errors: target must be a non-nil pointer")
|
|
60
|
+
}
|
|
61
|
+
for err != nil {
|
|
62
|
+
if v, ok := err.(${target}); ok {
|
|
63
|
+
*target = v
|
|
64
|
+
return true
|
|
65
|
+
}
|
|
66
|
+
if a, ok := err.(interface{ As(any) bool }); ok && a.As(target) {
|
|
67
|
+
return true
|
|
68
|
+
}
|
|
69
|
+
switch u := err.(type) {
|
|
70
|
+
case interface{ Unwrap() error }:
|
|
71
|
+
err = u.Unwrap()
|
|
72
|
+
case interface{ Unwrap() []error }:
|
|
73
|
+
for _, e := range u.Unwrap() {
|
|
74
|
+
if e != nil && ${name}${tparams ? "[T]" : ""}(e, target) {
|
|
75
|
+
return true
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
return false
|
|
79
|
+
default:
|
|
80
|
+
return false
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return false
|
|
84
|
+
}`;
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
// The `errors.As` calls of the programs, and a diagnostic for each use of
|
|
88
|
+
// errors.As that is not a call.
|
|
89
|
+
function findSites(programs) {
|
|
90
|
+
const sites = [];
|
|
91
|
+
const diagnostics = [];
|
|
92
|
+
for (const program of programs) {
|
|
93
|
+
const aliases = errorsAliases(program);
|
|
94
|
+
if (aliases.size === 0) continue;
|
|
95
|
+
const callees = new Set();
|
|
96
|
+
const refs = [];
|
|
97
|
+
walkNodes(program.decls, (node) => {
|
|
98
|
+
if (isAsCall(node, aliases)) {
|
|
99
|
+
sites.push({ call: node, program });
|
|
100
|
+
callees.add(node.func);
|
|
101
|
+
} else if (isAsRef(node, aliases)) {
|
|
102
|
+
refs.push(node);
|
|
103
|
+
}
|
|
104
|
+
});
|
|
105
|
+
for (const node of refs)
|
|
106
|
+
if (!callees.has(node))
|
|
107
|
+
diagnostics.push({
|
|
108
|
+
program,
|
|
109
|
+
node: node.expr,
|
|
110
|
+
message: "errors.As cannot be used as a value",
|
|
111
|
+
hint: "call errors.As directly",
|
|
112
|
+
});
|
|
113
|
+
}
|
|
114
|
+
return { sites, diagnostics };
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// What a call's target type allows: { base } for a target to generate for, or
|
|
118
|
+
// { message, hint } for one the generator rejects.
|
|
119
|
+
function classifyTarget(call) {
|
|
120
|
+
const argType = call.args[1]?._type;
|
|
121
|
+
if (argType?.kind !== "pointer") return { message: NOT_POINTER };
|
|
122
|
+
const base = argType.base;
|
|
123
|
+
if (base?.kind === "interface" && !base.name && base.methods?.size > 0)
|
|
124
|
+
return {
|
|
125
|
+
message:
|
|
126
|
+
"errors.As with a target of an anonymous interface type is not yet available",
|
|
127
|
+
hint: "declare a named interface type for the target",
|
|
128
|
+
};
|
|
129
|
+
if (base?.kind !== "typeParam" && mentionsTypeParam(base))
|
|
130
|
+
return {
|
|
131
|
+
message:
|
|
132
|
+
"errors.As with a target that mentions a type parameter is not yet available",
|
|
133
|
+
hint: "use a target that is a type parameter itself, or a concrete type",
|
|
134
|
+
};
|
|
135
|
+
return { base };
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
// Generates the `errors.As` functions for a package's call sites. Returns
|
|
139
|
+
// null when it has none; otherwise { body, imports, diagnostics, link } and
|
|
140
|
+
// marks each call's SelectorExpr with `_genEntry`.
|
|
141
|
+
export function generateErrorsAs(programs, _checker, pkgName) {
|
|
142
|
+
const { sites, diagnostics } = findSites(programs);
|
|
143
|
+
if (sites.length + diagnostics.length === 0) return null;
|
|
144
|
+
const qualifiers = new Map();
|
|
145
|
+
const speller = new TypeSpeller(pkgName, qualifiers, programs);
|
|
146
|
+
const prefix = `gfe_${String(pkgName).replace(/[^A-Za-z0-9_]/g, "_")}_as_`;
|
|
147
|
+
const names = new Map(); // spelled target -> function name
|
|
148
|
+
const out = [];
|
|
149
|
+
const sharedSites = []; // targets that are a type parameter
|
|
150
|
+
for (const { call, program } of sites) {
|
|
151
|
+
const { base, message, hint } = classifyTarget(call);
|
|
152
|
+
let target;
|
|
153
|
+
try {
|
|
154
|
+
if (base?.kind === "typeParam") sharedSites.push(call);
|
|
155
|
+
else if (base) target = speller.spell(base);
|
|
156
|
+
} catch (e) {
|
|
157
|
+
diagnostics.push({
|
|
158
|
+
program,
|
|
159
|
+
node: call.func.expr,
|
|
160
|
+
message: `errors.As: ${e.message}`,
|
|
161
|
+
});
|
|
162
|
+
continue;
|
|
163
|
+
}
|
|
164
|
+
if (!base) {
|
|
165
|
+
diagnostics.push({ program, node: call.func.expr, message, hint });
|
|
166
|
+
continue;
|
|
167
|
+
}
|
|
168
|
+
if (target === undefined) continue;
|
|
169
|
+
if (!names.has(target)) {
|
|
170
|
+
names.set(target, `${prefix}${names.size}`);
|
|
171
|
+
out.push(asFunction(names.get(target), target));
|
|
172
|
+
}
|
|
173
|
+
markCall(call, names.get(target));
|
|
174
|
+
}
|
|
175
|
+
const sharedName = `${prefix}t`;
|
|
176
|
+
if (sharedSites.length > 0) out.push(asFunction(sharedName, "T", "[T any]"));
|
|
177
|
+
for (const call of sharedSites) markCall(call, sharedName);
|
|
178
|
+
// The shared function is generic: once it is checked, its call sites take
|
|
179
|
+
// the type arguments the checker would have inferred.
|
|
180
|
+
const link = (chk) => {
|
|
181
|
+
const generic = chk.globals.symbols.get(sharedName);
|
|
182
|
+
for (const call of sharedSites) {
|
|
183
|
+
const typeArgs = [call.args[1]._type.base];
|
|
184
|
+
for (const n of [call, call.func]) {
|
|
185
|
+
n._typeArgs = typeArgs;
|
|
186
|
+
n._genericFnType = generic;
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
};
|
|
190
|
+
return {
|
|
191
|
+
body: out.join("\n\n"),
|
|
192
|
+
imports: importsFor(qualifiers),
|
|
193
|
+
diagnostics,
|
|
194
|
+
link,
|
|
195
|
+
};
|
|
196
|
+
}
|