mirror of
https://github.com/ziglang/zig.git
synced 2025-12-06 14:23:09 +00:00
C backend: fix crash when number of Decls passes a threshold
The ensureUnusedCapacity did not reserve a big enough number. I changed it to no longer guess the capacity because I saw that the number of possible items was not determinable ahead of time and this can therefore avoid allocating more memory than necessary.
This commit is contained in:
parent
c59ee3157f
commit
1c93cf52d8
@ -251,8 +251,8 @@ pub fn flushModule(self: *C, comp: *Compilation) !void {
|
|||||||
var f: Flush = .{};
|
var f: Flush = .{};
|
||||||
defer f.deinit(gpa);
|
defer f.deinit(gpa);
|
||||||
|
|
||||||
// This is at least enough until we get to the function bodies without error handling.
|
// Covers zig.h and err_typedef_item.
|
||||||
try f.all_buffers.ensureTotalCapacity(gpa, self.decl_table.count() + 2);
|
try f.all_buffers.ensureUnusedCapacity(gpa, 2);
|
||||||
|
|
||||||
f.all_buffers.appendAssumeCapacity(.{
|
f.all_buffers.appendAssumeCapacity(.{
|
||||||
.iov_base = zig_h,
|
.iov_base = zig_h,
|
||||||
@ -261,7 +261,8 @@ pub fn flushModule(self: *C, comp: *Compilation) !void {
|
|||||||
f.file_size += zig_h.len;
|
f.file_size += zig_h.len;
|
||||||
|
|
||||||
const err_typedef_writer = f.err_typedef_buf.writer(gpa);
|
const err_typedef_writer = f.err_typedef_buf.writer(gpa);
|
||||||
const err_typedef_item = f.all_buffers.addOneAssumeCapacity();
|
const err_typedef_index = f.all_buffers.items.len;
|
||||||
|
f.all_buffers.items.len += 1;
|
||||||
|
|
||||||
render_errors: {
|
render_errors: {
|
||||||
if (module.global_error_set.size == 0) break :render_errors;
|
if (module.global_error_set.size == 0) break :render_errors;
|
||||||
@ -291,7 +292,7 @@ pub fn flushModule(self: *C, comp: *Compilation) !void {
|
|||||||
try flushDecl(self, &f, decl);
|
try flushDecl(self, &f, decl);
|
||||||
}
|
}
|
||||||
|
|
||||||
err_typedef_item.* = .{
|
f.all_buffers.items[err_typedef_index] = .{
|
||||||
.iov_base = f.err_typedef_buf.items.ptr,
|
.iov_base = f.err_typedef_buf.items.ptr,
|
||||||
.iov_len = f.err_typedef_buf.items.len,
|
.iov_len = f.err_typedef_buf.items.len,
|
||||||
};
|
};
|
||||||
@ -371,7 +372,7 @@ fn flushDecl(self: *C, f: *Flush, decl: *const Module.Decl) FlushDeclError!void
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
const buf = decl_block.fwd_decl.items;
|
const buf = decl_block.fwd_decl.items;
|
||||||
f.all_buffers.appendAssumeCapacity(.{
|
try f.all_buffers.append(gpa, .{
|
||||||
.iov_base = buf.ptr,
|
.iov_base = buf.ptr,
|
||||||
.iov_len = buf.len,
|
.iov_len = buf.len,
|
||||||
});
|
});
|
||||||
@ -381,7 +382,7 @@ fn flushDecl(self: *C, f: *Flush, decl: *const Module.Decl) FlushDeclError!void
|
|||||||
f.fn_count += 1;
|
f.fn_count += 1;
|
||||||
} else if (decl_block.code.items.len != 0) {
|
} else if (decl_block.code.items.len != 0) {
|
||||||
const buf = decl_block.code.items;
|
const buf = decl_block.code.items;
|
||||||
f.all_buffers.appendAssumeCapacity(.{
|
try f.all_buffers.append(gpa, .{
|
||||||
.iov_base = buf.ptr,
|
.iov_base = buf.ptr,
|
||||||
.iov_len = buf.len,
|
.iov_len = buf.len,
|
||||||
});
|
});
|
||||||
|
|||||||
@ -43,7 +43,6 @@ test {
|
|||||||
_ = @import("behavior/generics.zig");
|
_ = @import("behavior/generics.zig");
|
||||||
_ = @import("behavior/hasdecl.zig");
|
_ = @import("behavior/hasdecl.zig");
|
||||||
_ = @import("behavior/hasfield.zig");
|
_ = @import("behavior/hasfield.zig");
|
||||||
_ = @import("behavior/if_llvm.zig");
|
|
||||||
_ = @import("behavior/math.zig");
|
_ = @import("behavior/math.zig");
|
||||||
_ = @import("behavior/maximum_minimum.zig");
|
_ = @import("behavior/maximum_minimum.zig");
|
||||||
_ = @import("behavior/member_func.zig");
|
_ = @import("behavior/member_func.zig");
|
||||||
|
|||||||
@ -73,3 +73,18 @@ test "const result loc, runtime if cond, else unreachable" {
|
|||||||
const x = if (t) Num.Two else unreachable;
|
const x = if (t) Num.Two else unreachable;
|
||||||
try expect(x == .Two);
|
try expect(x == .Two);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test "if copies its payload" {
|
||||||
|
const S = struct {
|
||||||
|
fn doTheTest() !void {
|
||||||
|
var tmp: ?i32 = 10;
|
||||||
|
if (tmp) |value| {
|
||||||
|
// Modify the original variable
|
||||||
|
tmp = null;
|
||||||
|
try expect(value == 10);
|
||||||
|
} else unreachable;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
try S.doTheTest();
|
||||||
|
comptime try S.doTheTest();
|
||||||
|
}
|
||||||
|
|||||||
@ -1,18 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
const expect = std.testing.expect;
|
|
||||||
const expectEqual = std.testing.expectEqual;
|
|
||||||
|
|
||||||
test "if copies its payload" {
|
|
||||||
const S = struct {
|
|
||||||
fn doTheTest() !void {
|
|
||||||
var tmp: ?i32 = 10;
|
|
||||||
if (tmp) |value| {
|
|
||||||
// Modify the original variable
|
|
||||||
tmp = null;
|
|
||||||
try expect(value == 10);
|
|
||||||
} else unreachable;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
try S.doTheTest();
|
|
||||||
comptime try S.doTheTest();
|
|
||||||
}
|
|
||||||
Loading…
x
Reference in New Issue
Block a user