| ... | @@ -564,7 +564,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -564,7 +564,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 564 | .is_err => try self.airIsErr(inst), | 564 | .is_err => try self.airIsErr(inst), |
| 565 | .is_err_ptr => @panic("TODO try self.airIsErrPtr(inst)"), | 565 | .is_err_ptr => @panic("TODO try self.airIsErrPtr(inst)"), |
| 566 | .load => try self.airLoad(inst), | 566 | .load => try self.airLoad(inst), |
| 567 | .loop => @panic("TODO try self.airLoop(inst)"), | 567 | .loop => try self.airLoop(inst), |
| 568 | .not => @panic("TODO try self.airNot(inst)"), | 568 | .not => @panic("TODO try self.airNot(inst)"), |
| 569 | .ptrtoint => @panic("TODO try self.airPtrToInt(inst)"), | 569 | .ptrtoint => @panic("TODO try self.airPtrToInt(inst)"), |
| 570 | .ret => try self.airRet(inst), | 570 | .ret => try self.airRet(inst), |
| ... | @@ -1342,6 +1342,17 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -1342,6 +1342,17 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 1342 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 1342 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 1343 | } | 1343 | } |
| 1344 | | 1344 | |
| | 1345 | fn airLoop(self: *Self, inst: Air.Inst.Index) !void { |
| | 1346 | // A loop is a setup to be able to jump back to the beginning. |
| | 1347 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| | 1348 | const loop = self.air.extraData(Air.Block, ty_pl.payload); |
| | 1349 | const body = self.air.extra[loop.end .. loop.end + loop.data.body_len]; |
| | 1350 | const start = @intCast(u32, self.mir_instructions.len); |
| | 1351 | try self.genBody(body); |
| | 1352 | try self.jump(start); |
| | 1353 | return self.finishAirBookkeeping(); |
| | 1354 | } |
| | 1355 | |
| 1345 | fn airRet(self: *Self, inst: Air.Inst.Index) !void { | 1356 | fn airRet(self: *Self, inst: Air.Inst.Index) !void { |
| 1346 | const un_op = self.air.instructions.items(.data)[inst].un_op; | 1357 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 1347 | const operand = try self.resolveInst(un_op); | 1358 | const operand = try self.resolveInst(un_op); |
| ... | @@ -2231,6 +2242,26 @@ fn iterateBigTomb(self: *Self, inst: Air.Inst.Index, operand_count: usize) !BigT | ... | @@ -2231,6 +2242,26 @@ fn iterateBigTomb(self: *Self, inst: Air.Inst.Index, operand_count: usize) !BigT |
| 2231 | }; | 2242 | }; |
| 2232 | } | 2243 | } |
| 2233 | | 2244 | |
| | 2245 | /// Send control flow to `inst`. |
| | 2246 | fn jump(self: *Self, inst: Mir.Inst.Index) !void { |
| | 2247 | _ = try self.addInst(.{ |
| | 2248 | .tag = .bpcc, |
| | 2249 | .data = .{ |
| | 2250 | .branch_predict_int = .{ |
| | 2251 | .cond = .al, |
| | 2252 | .ccr = .xcc, |
| | 2253 | .inst = inst, |
| | 2254 | }, |
| | 2255 | }, |
| | 2256 | }); |
| | 2257 | |
| | 2258 | // TODO find out a way to fill this delay slot |
| | 2259 | _ = try self.addInst(.{ |
| | 2260 | .tag = .nop, |
| | 2261 | .data = .{ .nop = {} }, |
| | 2262 | }); |
| | 2263 | } |
| | 2264 | |
| 2234 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { | 2265 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { |
| 2235 | const elem_ty = ptr_ty.elemType(); | 2266 | const elem_ty = ptr_ty.elemType(); |
| 2236 | const elem_size = elem_ty.abiSize(self.target.*); | 2267 | const elem_size = elem_ty.abiSize(self.target.*); |