authorgravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2022-12-02 22:20:12-05:00
committergravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2022-12-02 22:21:24-05:00
loge1216077f0edf0efa0b322c5469e2ab572213271
tree1ed4c92ad403070acb8759276cd50210805781a9
parentfdedd62365b5e3f3fa908ae063df86d11a3c02bb

cbe: add support for constraint modifiers specified after a colon

This translates `%[name:mod]` to `%mod[name]` for C.

2 files changed, 39 insertions(+), 5 deletions(-)

src/codegen/c.zig+39-4
......@@ -4175,11 +4175,46 @@ fn airAsm(f: *Function, inst: Air.Inst.Index) !CValue {
41754175 extra_i += clobber.len / 4 + 1;
41764176 }
41774177 }
4178 const asm_source = std.mem.sliceAsBytes(f.air.extra[extra_i..])[0..extra.data.source_len];
4178 {
4179 const asm_source = std.mem.sliceAsBytes(f.air.extra[extra_i..])[0..extra.data.source_len];
4180
4181 var stack = std.heap.stackFallback(256, f.object.dg.gpa);
4182 const allocator = stack.get();
4183 const fixed_asm_source = try allocator.alloc(u8, asm_source.len);
4184 defer allocator.free(fixed_asm_source);
4185
4186 var src_i: usize = 0;
4187 var dst_i: usize = 0;
4188 while (src_i < asm_source.len) : (src_i += 1) {
4189 fixed_asm_source[dst_i] = asm_source[src_i];
4190 dst_i += 1;
4191 if (asm_source[src_i] != '%' or src_i + 1 >= asm_source.len) continue;
4192 src_i += 1;
4193 if (asm_source[src_i] != '[') {
4194 // This handles %%
4195 fixed_asm_source[dst_i] = asm_source[src_i];
4196 dst_i += 1;
4197 continue;
4198 }
4199 const len = std.mem.indexOfScalar(u8, asm_source[src_i + 1 ..], ']') orelse
4200 return f.fail("CBE: invalid inline asm string '{s}'", .{asm_source});
4201 if (std.mem.indexOfScalar(u8, asm_source[src_i + 1 ..][0..len], ':')) |colon| {
4202 const modifier = asm_source[src_i + 1 + colon + 1 .. src_i + 1 + len];
4203 std.mem.copy(u8, fixed_asm_source[dst_i..], modifier);
4204 dst_i += modifier.len;
4205
4206 const name = asm_source[src_i .. src_i + 1 + colon];
4207 std.mem.copy(u8, fixed_asm_source[dst_i..], name);
4208 dst_i += name.len;
4209
4210 src_i += len;
4211 }
4212 }
41794213
4180 try writer.writeAll("__asm");
4181 if (is_volatile) try writer.writeAll(" volatile");
4182 try writer.print("({s}", .{fmtStringLiteral(asm_source)});
4214 try writer.writeAll("__asm");
4215 if (is_volatile) try writer.writeAll(" volatile");
4216 try writer.print("({s}", .{fmtStringLiteral(fixed_asm_source[0..dst_i])});
4217 }
41834218
41844219 extra_i = constraints_extra_begin;
41854220 var locals_index = locals_begin;
test/behavior/asm.zig-1
......@@ -140,7 +140,6 @@ export fn derp() i32 {
140140test "asm modifiers (AArch64)" {
141141 if (builtin.target.cpu.arch != .aarch64) return error.SkipZigTest;
142142 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
143 if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
144143
145144 var x: u32 = 15;
146145 const double = asm ("add %[ret:w], %[in:w], %[in:w]"