authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-12-03 19:20:15-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-12-04 15:57:40-07:00
logf2e59e41c1ea3884a50e45f54a74c29f52954b24
treea2fb870f95ddb3427b33016c345aa4e45479a740
parent6c0a1417c6edb40cfc86e546c5c853a2d19c22f0

CBE: fix various regressions caught by behavior tests


1 files changed, 85 insertions(+), 51 deletions(-)

src/codegen/c.zig+85-51
......@@ -4096,9 +4096,7 @@ fn lowerTry(
40964096 const is_array = lowersToArray(payload_ty, target);
40974097 try reap(f, inst, &.{operand});
40984098 const local = try f.allocLocal(inst, result_ty);
4099 try f.writeCValue(writer, local, .Other);
41004099 if (is_array) {
4101 try writer.writeAll(";\n");
41024100 try writer.writeAll("memcpy(");
41034101 try f.writeCValue(writer, local, .FunctionArgument);
41044102 try writer.writeAll(", ");
......@@ -4107,6 +4105,7 @@ fn lowerTry(
41074105 try f.renderTypecast(writer, payload_ty);
41084106 try writer.writeAll("));\n");
41094107 } else {
4108 try f.writeCValue(writer, local, .Other);
41104109 try writer.writeAll(" = ");
41114110 if (operand_is_ptr or isByRef(payload_ty)) {
41124111 try writer.writeByte('&');
......@@ -4849,16 +4848,18 @@ fn airOptionalPayloadPtr(f: *Function, inst: Air.Inst.Index) !CValue {
48494848 return CValue{ .undef = inst_ty };
48504849 }
48514850
4851 const local = try f.allocLocal(inst, inst_ty);
4852 try f.writeCValue(writer, local, .Other);
4853
48524854 if (opt_ty.optionalReprIsPayload()) {
48534855 // the operand is just a regular pointer, no need to do anything special.
48544856 // *?*T -> **T and ?*T -> *T are **T -> **T and *T -> *T in C
4855 return operand;
4857 try writer.writeAll(" = ");
4858 try f.writeCValue(writer, operand, .Other);
4859 } else {
4860 try writer.writeAll(" = &");
4861 try f.writeCValueDerefMember(writer, operand, .{ .identifier = "payload" });
48564862 }
4857
4858 const local = try f.allocLocal(inst, inst_ty);
4859 try f.writeCValue(writer, local, .Other);
4860 try writer.writeAll(" = &");
4861 try f.writeCValueDerefMember(writer, operand, .{ .identifier = "payload" });
48624863 try writer.writeAll(";\n");
48634864 return local;
48644865}
......@@ -4872,25 +4873,37 @@ fn airOptionalPayloadPtrSet(f: *Function, inst: Air.Inst.Index) !CValue {
48724873
48734874 const opt_ty = operand_ty.elemType();
48744875
4876 const inst_ty = f.air.typeOfIndex(inst);
4877
48754878 if (opt_ty.optionalReprIsPayload()) {
4879 if (f.liveness.isUnused(inst)) {
4880 return CValue.none;
4881 }
4882 const local = try f.allocLocal(inst, inst_ty);
48764883 // The payload and the optional are the same value.
48774884 // Setting to non-null will be done when the payload is set.
4878 return operand;
4879 }
4880
4881 try f.writeCValueDeref(writer, operand);
4882 try writer.writeAll(".is_null = ");
4883 try f.object.dg.renderValue(writer, Type.bool, Value.false, .Initializer);
4884 try writer.writeAll(";\n");
4885 try f.writeCValue(writer, local, .Other);
4886 try writer.writeAll(" = ");
4887 try f.writeCValue(writer, operand, .Other);
4888 try writer.writeAll(";\n");
4889 return local;
4890 } else {
4891 try f.writeCValueDeref(writer, operand);
4892 try writer.writeAll(".is_null = ");
4893 try f.object.dg.renderValue(writer, Type.bool, Value.false, .Initializer);
4894 try writer.writeAll(";\n");
48854895
4886 const inst_ty = f.air.typeOfIndex(inst);
4887 const local = try f.allocLocal(inst, inst_ty);
4888 try f.writeCValue(writer, local, .Other);
4889 try writer.writeAll(" = &");
4890 try f.writeCValueDeref(writer, operand);
4896 if (f.liveness.isUnused(inst)) {
4897 return CValue.none;
4898 }
48914899
4892 try writer.writeAll(".payload;\n");
4893 return local;
4900 const local = try f.allocLocal(inst, inst_ty);
4901 try f.writeCValue(writer, local, .Other);
4902 try writer.writeAll(" = &");
4903 try f.writeCValueDeref(writer, operand);
4904 try writer.writeAll(".payload;\n");
4905 return local;
4906 }
48944907}
48954908
48964909fn airStructFieldPtr(f: *Function, inst: Air.Inst.Index) !CValue {
......@@ -5164,7 +5177,6 @@ fn airStructFieldVal(f: *Function, inst: Air.Inst.Index) !CValue {
51645177 } else struct_byval;
51655178
51665179 const local = try f.allocLocal(inst, inst_ty);
5167 try f.writeCValue(writer, local, .Other);
51685180 try writer.writeAll("memcpy(&");
51695181 try f.writeCValue(writer, local, .FunctionArgument);
51705182 try writer.writeAll(", &");
......@@ -5230,25 +5242,28 @@ fn airUnwrapErrUnionErr(f: *Function, inst: Air.Inst.Index) !CValue {
52305242 const inst_ty = f.air.typeOfIndex(inst);
52315243 const operand = try f.resolveInst(ty_op.operand);
52325244 const operand_ty = f.air.typeOf(ty_op.operand);
5245 try reap(f, inst, &.{ty_op.operand});
52335246
52345247 const operand_is_ptr = operand_ty.zigTypeTag() == .Pointer;
52355248 const error_union_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty;
52365249 const error_ty = error_union_ty.errorUnionSet();
52375250 const payload_ty = error_union_ty.errorUnionPayload();
5238 if (!payload_ty.hasRuntimeBits()) return operand;
5239 try reap(f, inst, &.{ty_op.operand});
5240
5241 const writer = f.object.writer();
52425251 const local = try f.allocLocal(inst, inst_ty);
5252 const writer = f.object.writer();
52435253 try f.writeCValue(writer, local, .Other);
52445254 try writer.writeAll(" = ");
5245 if (!error_ty.errorSetIsEmpty())
5246 if (operand_is_ptr)
5247 try f.writeCValueDerefMember(writer, operand, .{ .identifier = "error" })
5255
5256 if (!payload_ty.hasRuntimeBits()) {
5257 try f.writeCValue(writer, operand, .Other);
5258 } else {
5259 if (!error_ty.errorSetIsEmpty())
5260 if (operand_is_ptr)
5261 try f.writeCValueDerefMember(writer, operand, .{ .identifier = "error" })
5262 else
5263 try f.writeCValueMember(writer, operand, .{ .identifier = "error" })
52485264 else
5249 try f.writeCValueMember(writer, operand, .{ .identifier = "error" })
5250 else
5251 try f.object.dg.renderValue(writer, error_ty, Value.zero, .Initializer);
5265 try f.object.dg.renderValue(writer, error_ty, Value.zero, .Initializer);
5266 }
52525267 try writer.writeAll(";\n");
52535268 return local;
52545269}
......@@ -5345,13 +5360,19 @@ fn airWrapErrUnionErr(f: *Function, inst: Air.Inst.Index) !CValue {
53455360
53465361 const writer = f.object.writer();
53475362 const operand = try f.resolveInst(ty_op.operand);
5363 try reap(f, inst, &.{ty_op.operand});
53485364 const error_union_ty = f.air.typeOfIndex(inst);
53495365 const payload_ty = error_union_ty.errorUnionPayload();
5350 if (!payload_ty.hasRuntimeBits()) return operand;
5366 const local = try f.allocLocal(inst, error_union_ty);
53515367
5352 try reap(f, inst, &.{ty_op.operand});
5368 if (!payload_ty.hasRuntimeBits()) {
5369 try f.writeCValue(writer, local, .Other);
5370 try writer.writeAll(" = ");
5371 try f.writeCValue(writer, operand, .Other);
5372 try writer.writeAll(";\n");
5373 return local;
5374 }
53535375
5354 const local = try f.allocLocal(inst, error_union_ty);
53555376 {
53565377 // TODO: set the payload to undefined
53575378 //try f.writeCValue(writer, local, .Other);
......@@ -5754,6 +5775,11 @@ fn airCmpxchg(f: *Function, inst: Air.Inst.Index, flavor: [*:0]const u8) !CValue
57545775 try writer.writeAll(";\n");
57555776 }
57565777
5778 if (f.liveness.isUnused(inst)) {
5779 try freeLocal(f, inst, local.local, 0);
5780 return CValue.none;
5781 }
5782
57575783 return local;
57585784}
57595785
......@@ -5790,6 +5816,11 @@ fn airAtomicRmw(f: *Function, inst: Air.Inst.Index) !CValue {
57905816 try writeMemoryOrder(writer, extra.ordering());
57915817 try writer.writeAll(");\n");
57925818
5819 if (f.liveness.isUnused(inst)) {
5820 try freeLocal(f, inst, local.local, 0);
5821 return CValue.none;
5822 }
5823
57935824 return local;
57945825}
57955826
......@@ -6222,30 +6253,28 @@ fn airAggregateInit(f: *Function, inst: Air.Inst.Index) !CValue {
62226253
62236254 const writer = f.object.writer();
62246255 const local = try f.allocLocal(inst, inst_ty);
6225 try f.writeCValue(writer, local, .Other);
6226 try writer.writeAll(" = (");
6227 try f.renderTypecast(writer, inst_ty);
6228 try writer.writeAll(")");
62296256 switch (inst_ty.zigTypeTag()) {
62306257 .Array, .Vector => {
62316258 const elem_ty = inst_ty.childType();
6232 try writer.writeByte('{');
6233 var empty = true;
6234 for (resolved_elements) |element| {
6235 if (!empty) try writer.writeAll(", ");
6236 try f.writeCValue(writer, element, .Initializer);
6237 empty = false;
6259 for (resolved_elements) |element, i| {
6260 try f.writeCValue(writer, local, .Other);
6261 try writer.print("[{d}] = ", .{i});
6262 try f.writeCValue(writer, element, .Other);
6263 try writer.writeAll(";\n");
62386264 }
62396265 if (inst_ty.sentinel()) |sentinel| {
6240 if (!empty) try writer.writeAll(", ");
6241 try f.object.dg.renderValue(writer, elem_ty, sentinel, .Initializer);
6242 empty = false;
6266 try f.writeCValue(writer, local, .Other);
6267 try writer.print("[{d}] = ", .{resolved_elements.len});
6268 try f.object.dg.renderValue(writer, elem_ty, sentinel, .Other);
6269 try writer.writeAll(";\n");
62436270 }
6244 if (empty) try writer.print("{}", .{try f.fmtIntLiteral(Type.u8, Value.zero)});
6245 try writer.writeAll("};\n");
62466271 },
62476272 .Struct => switch (inst_ty.containerLayout()) {
62486273 .Auto, .Extern => {
6274 try f.writeCValue(writer, local, .Other);
6275 try writer.writeAll(" = (");
6276 try f.renderTypecast(writer, inst_ty);
6277 try writer.writeAll(")");
62496278 try writer.writeByte('{');
62506279 var empty = true;
62516280 for (elements) |element, index| {
......@@ -6291,6 +6320,10 @@ fn airAggregateInit(f: *Function, inst: Air.Inst.Index) !CValue {
62916320 }
62926321 },
62936322 .Packed => {
6323 try f.writeCValue(writer, local, .Other);
6324 try writer.writeAll(" = (");
6325 try f.renderTypecast(writer, inst_ty);
6326 try writer.writeAll(")");
62946327 const int_info = inst_ty.intInfo(target);
62956328
62966329 var bit_offset_ty_pl = Type.Payload.Bits{
......@@ -6468,6 +6501,7 @@ fn airFloatNeg(f: *Function, inst: Air.Inst.Index) !CValue {
64686501 }
64696502
64706503 const operand = try f.resolveInst(un_op);
6504 try reap(f, inst, &.{un_op});
64716505 const operand_ty = f.air.typeOf(un_op);
64726506
64736507 const writer = f.object.writer();