aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Jarred Sumner <jarred@jarredsumner.com> 2021-04-22 14:24:28 -0700
committerGravatar Jarred Sumner <jarred@jarredsumner.com> 2021-04-22 14:24:28 -0700
commitda509f3d5a732145afebbc7400a832785f1b439f (patch)
tree11384b2bc80b405bffa1515e3ac2dfe993a229d2
parentbee68ecc004864d1a1bbdfb0d49acf42ffe1f0d3 (diff)
downloadbun-da509f3d5a732145afebbc7400a832785f1b439f.tar.gz
bun-da509f3d5a732145afebbc7400a832785f1b439f.tar.zst
bun-da509f3d5a732145afebbc7400a832785f1b439f.zip
a
-rw-r--r--src/ast/base.zig5
-rw-r--r--src/js_ast.zig9
-rw-r--r--src/js_parser.zig59
-rw-r--r--src/logger.zig15
-rw-r--r--src/string_mutable.zig13
5 files changed, 92 insertions, 9 deletions
diff --git a/src/ast/base.zig b/src/ast/base.zig
index 59193adc1..744b7e2d9 100644
--- a/src/ast/base.zig
+++ b/src/ast/base.zig
@@ -1,4 +1,9 @@
+const unicode = @import("std").unicode;
+
pub const JavascriptString = []u16;
+pub fn newJavascriptString(comptime text: []const u8) JavascriptString {
+ return unicode.utf8ToUtf16LeStringLiteral(text);
+}
pub const NodeIndex = u32;
pub const NodeIndexNone = 4294967293;
diff --git a/src/js_ast.zig b/src/js_ast.zig
index 4bcc945a3..0a0bddbf3 100644
--- a/src/js_ast.zig
+++ b/src/js_ast.zig
@@ -26,10 +26,13 @@ const ImportRecord = @import("import_record.zig").ImportRecord;
// But also it uses the least memory.
// Since Data is a union, the size in bytes of Data is the max of all types
// So with #1 or #2, if S.Function consumes 768 bits, that means Data must be >= 768 bits
-// Which means "true" in codenow takes up over 768 bits, probably more than what v8 spends
-// With this approach, Data is the size of a pointer. The value of the type decides the size.
+// Which means "true" in code now takes up over 768 bits, probably more than what v8 spends
+// Instead, this approach means Data is the size of a pointer.
// It's not really clear which approach is best without benchmarking it.
-
+// The downside with this approach is potentially worse memory locality, since the data for the node is somewhere else.
+// But it could also be better memory locality due to smaller in-memory size (more likely to hit the cache)
+// only benchmarks will provide an answer!
+// But we must have pointers somewhere in here because can't have types that contain themselves
pub const BindingNodeIndex = Binding;
pub const StmtNodeIndex = Stmt;
pub const ExprNodeIndex = Expr;
diff --git a/src/js_parser.zig b/src/js_parser.zig
index 5d604b247..723e828dc 100644
--- a/src/js_parser.zig
+++ b/src/js_parser.zig
@@ -1910,6 +1910,53 @@ const P = struct {
}, loc);
}
+ pub fn parseTemplateParts(p: *P, include_raw: bool) Tup([]E.TemplatePart, logger.Loc) {
+ var parts = List(E.TemplatePart).initCapacity(p.allocator, 1) catch unreachable;
+ // Allow "in" inside template literals
+ var oldAllowIn = p.allow_in;
+ p.allow_in = true;
+ var legacy_octal_loc = logger.Loc.Empty;
+
+ parseTemplatePart: while (true) {
+ p.lexer.next();
+ var value = p.parseExpr(.lowest);
+ var tail_loc = p.lexer.loc();
+ p.lexer.rescanCloseBraceAsTemplateToken();
+ var tail = p.lexer.string_literal;
+ var tailRaw = "";
+
+ if (include_raw) {
+ tail_raw = p.lexer.rawTemplateContents();
+ } else if (p.lexer.legacy_octal_loc.start > tail_loc.start) {
+ legacy_octal_loc = p.lexer.legacy_octal_loc;
+ }
+
+
+ if (p.lexer.token == .t_template_tail) {
+
+ }
+ }
+
+ return .{parts.toOwnedSlice(), legacy_octal_loc};
+ }
+
+ // This assumes the caller has already checked for TStringLiteral or TNoSubstitutionTemplateLiteral
+ pub fn parseStringLiteral(p: *P) Expr {
+ var legacy_octal_loc: logger.Loc = logger.Loc.Empty;
+ var loc = p.lexer.loc();
+ if (p.lexer.legacy_octal_loc.start > loc.start) {
+ legacy_octal_loc = p.lexer.legacy_octal_loc;
+ }
+
+ const expr = p.e(E.String{
+ .value = p.lexer.string_literal,
+ .legacy_octal_loc = legacy_octal_loc,
+ .prefer_template = p.lexer.token == .t_no_substitution_template_literal,
+ }, loc);
+ p.lexer.next();
+ return expr;
+ }
+
pub fn parseSuffix(p: *P, left: Expr, level: Level, errors: ?*DeferredErrors, flags: Expr.EFlags) Expr {
return _parseSuffix(p, left, level, errors orelse &DeferredErrors.None, flags);
}
@@ -2059,8 +2106,16 @@ const P = struct {
}, loc);
}
},
- .t_string_literal, .t_no_substitution_template_literal => {},
- .t_template_head => {},
+ .t_string_literal, .t_no_substitution_template_literal => {
+ return p.parseStringLiteral();
+ },
+ .t_template_head => {
+ var legacy_octal_loc = logger.Loc.Empty;
+ var head = p.lexer.string_literal;
+ if (p.lexer.legacy_octal_loc.start > loc.start) {
+ legacy_octal_loc = p.lexer.legacy_octal_loc;
+ }
+ },
.t_numeric_literal => {},
.t_big_integer_literal => {},
.t_slash, .t_slash_equals => {},
diff --git a/src/logger.zig b/src/logger.zig
index ccc922cbe..026d46aca 100644
--- a/src/logger.zig
+++ b/src/logger.zig
@@ -99,7 +99,18 @@ pub const Location = struct {
pub const Data = struct { text: string, location: ?Location = null };
-pub const Msg = struct { kind: Kind = Kind.err, data: Data, notes: ?[]Data = null };
+pub const Msg = struct {
+ kind: Kind = Kind.err,
+ data: Data,
+ notes: ?[]Data = null,
+ pub fn format(msg: *const Msg, to: anytype, formatterFunc: @TypeOf(std.fmt.format)) !void {
+ try formatterFunc(to, "\n\n{s}: {s}\n{s}\n{s}:{}:{}", .{ msg.kind.string(), msg.data.text, msg.data.location.?.line_text, msg.data.location.?.file, msg.data.location.?.line, msg.data.location.?.column });
+ }
+
+ pub fn formatNoWriter(msg: *const Msg, comptime formatterFunc: @TypeOf(std.debug.panic)) void {
+ formatterFunc("\n\n{s}: {s}\n{s}\n{s}:{}:{}", .{ msg.kind.string(), msg.data.text, msg.data.location.?.line_text, msg.data.location.?.file, msg.data.location.?.line, msg.data.location.?.column });
+ }
+};
pub const Range = packed struct {
loc: Loc = Loc.Empty,
@@ -190,7 +201,7 @@ pub const Log = struct {
// TODO:
pub fn print(self: *Log, to: anytype) !void {
for (self.msgs.items) |msg| {
- try std.fmt.format(to, "\n\n{s}: {s}\n{s}\n{s}:{}:{}", .{ msg.kind.string(), msg.data.text, msg.data.location.?.line_text, msg.data.location.?.file, msg.data.location.?.line, msg.data.location.?.column });
+ try msg.format(to, std.fmt.format);
}
}
};
diff --git a/src/string_mutable.zig b/src/string_mutable.zig
index d846bf312..f6cf12799 100644
--- a/src/string_mutable.zig
+++ b/src/string_mutable.zig
@@ -70,8 +70,8 @@ pub const MutableString = struct {
try self.list.append(self.allocator, char);
}
- pub fn appendCharAssumeCapacity(self: *MutableString, char: u8) !void {
- try self.list.appendAssumeCapacity(self.allocator, char);
+ pub fn appendCharAssumeCapacity(self: *MutableString, char: u8) void {
+ self.list.appendAssumeCapacity(char);
}
pub fn append(self: *MutableString, char: []const u8) !void {
@@ -82,6 +82,15 @@ pub const MutableString = struct {
try self.list.appendSliceAssumeCapacity(self.allocator, char);
}
+ pub fn toOwnedSlice(self: *MutableString) string {
+ return self.list.toOwnedSlice(self.allocator);
+ }
+
+ pub fn toOwnedSliceLength(self: *MutableString, length: usize) string {
+ self.list.shrinkAndFree(self.allocator, length);
+ return self.list.toOwnedSlice(self.allocator);
+ }
+
// pub fn deleteAt(self: *MutableString, i: usize) {
// self.list.swapRemove(i);
// }