Skip to content

Commit d0251a7

Browse files
committed
[mlir][evm] Lower the remaining builtins
This includes: extcodecopy extcodehash balance selfbalance chainid basefee blobbasefee origin gasprice blockhash blobhash coinbase timestamp number prevrandao gaslimit callcode
1 parent 1d6ac85 commit d0251a7

37 files changed

+1395
-52
lines changed

libsolidity/codegen/mlir/Target/EVM/YulToStandard.cpp

Lines changed: 227 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -286,6 +286,32 @@ struct AddressOpLowering : public OpRewritePattern<yul::AddressOp> {
286286
}
287287
};
288288

289+
struct BalanceOpLowering : public OpRewritePattern<yul::BalanceOp> {
290+
using OpRewritePattern<yul::BalanceOp>::OpRewritePattern;
291+
292+
LogicalResult matchAndRewrite(yul::BalanceOp op,
293+
PatternRewriter &r) const override {
294+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_balance,
295+
/*resTy=*/r.getIntegerType(256),
296+
/*ins=*/ValueRange{op.getAddr()},
297+
"evm.balance");
298+
return success();
299+
}
300+
};
301+
302+
struct SelfBalanceOpLowering : public OpRewritePattern<yul::SelfBalanceOp> {
303+
using OpRewritePattern<yul::SelfBalanceOp>::OpRewritePattern;
304+
305+
LogicalResult matchAndRewrite(yul::SelfBalanceOp op,
306+
PatternRewriter &r) const override {
307+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_selfbalance,
308+
/*resTy=*/r.getIntegerType(256),
309+
/*ins=*/ValueRange{},
310+
"evm.selfbalance");
311+
return success();
312+
}
313+
};
314+
289315
struct CallerOpLowering : public OpRewritePattern<yul::CallerOp> {
290316
using OpRewritePattern<yul::CallerOp>::OpRewritePattern;
291317

@@ -311,6 +337,159 @@ struct GasOpLowering : public OpRewritePattern<yul::GasOp> {
311337
}
312338
};
313339

340+
struct ChainIdOpLowering : public OpRewritePattern<yul::ChainIdOp> {
341+
using OpRewritePattern<yul::ChainIdOp>::OpRewritePattern;
342+
343+
LogicalResult matchAndRewrite(yul::ChainIdOp op,
344+
PatternRewriter &r) const override {
345+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_chainid,
346+
/*resTy=*/r.getIntegerType(256),
347+
/*ins=*/ValueRange{}, "evm.chainid");
348+
return success();
349+
}
350+
};
351+
352+
struct BaseFeeOpLowering : public OpRewritePattern<yul::BaseFeeOp> {
353+
using OpRewritePattern<yul::BaseFeeOp>::OpRewritePattern;
354+
355+
LogicalResult matchAndRewrite(yul::BaseFeeOp op,
356+
PatternRewriter &r) const override {
357+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_basefee,
358+
/*resTy=*/r.getIntegerType(256),
359+
/*ins=*/ValueRange{}, "evm.basefee");
360+
return success();
361+
}
362+
};
363+
364+
struct BlobBaseFeeOpLowering : public OpRewritePattern<yul::BlobBaseFeeOp> {
365+
using OpRewritePattern<yul::BlobBaseFeeOp>::OpRewritePattern;
366+
367+
LogicalResult matchAndRewrite(yul::BlobBaseFeeOp op,
368+
PatternRewriter &r) const override {
369+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_blobbasefee,
370+
/*resTy=*/r.getIntegerType(256),
371+
/*ins=*/ValueRange{},
372+
"evm.blobbasefee");
373+
return success();
374+
}
375+
};
376+
377+
struct OriginOpLowering : public OpRewritePattern<yul::OriginOp> {
378+
using OpRewritePattern<yul::OriginOp>::OpRewritePattern;
379+
380+
LogicalResult matchAndRewrite(yul::OriginOp op,
381+
PatternRewriter &r) const override {
382+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_origin,
383+
/*resTy=*/r.getIntegerType(256),
384+
/*ins=*/ValueRange{}, "evm.origin");
385+
return success();
386+
}
387+
};
388+
389+
struct GasPriceOpLowering : public OpRewritePattern<yul::GasPriceOp> {
390+
using OpRewritePattern<yul::GasPriceOp>::OpRewritePattern;
391+
392+
LogicalResult matchAndRewrite(yul::GasPriceOp op,
393+
PatternRewriter &r) const override {
394+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_gasprice,
395+
/*resTy=*/r.getIntegerType(256),
396+
/*ins=*/ValueRange{},
397+
"evm.gasprice");
398+
return success();
399+
}
400+
};
401+
402+
struct BlockHashOpLowering : public OpRewritePattern<yul::BlockHashOp> {
403+
using OpRewritePattern<yul::BlockHashOp>::OpRewritePattern;
404+
405+
LogicalResult matchAndRewrite(yul::BlockHashOp op,
406+
PatternRewriter &r) const override {
407+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_blockhash,
408+
/*resTy=*/r.getIntegerType(256),
409+
/*ins=*/ValueRange{op.getBlock()},
410+
"evm.blockhash");
411+
return success();
412+
}
413+
};
414+
415+
struct BlobHashOpLowering : public OpRewritePattern<yul::BlobHashOp> {
416+
using OpRewritePattern<yul::BlobHashOp>::OpRewritePattern;
417+
418+
LogicalResult matchAndRewrite(yul::BlobHashOp op,
419+
PatternRewriter &r) const override {
420+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_blobhash,
421+
/*resTy=*/r.getIntegerType(256),
422+
/*ins=*/ValueRange{op.getIdx()},
423+
"evm.blobhash");
424+
return success();
425+
}
426+
};
427+
428+
struct CoinBaseOpLowering : public OpRewritePattern<yul::CoinBaseOp> {
429+
using OpRewritePattern<yul::CoinBaseOp>::OpRewritePattern;
430+
431+
LogicalResult matchAndRewrite(yul::CoinBaseOp op,
432+
PatternRewriter &r) const override {
433+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_coinbase,
434+
/*resTy=*/r.getIntegerType(256),
435+
/*ins=*/ValueRange{},
436+
"evm.coinbase");
437+
return success();
438+
}
439+
};
440+
441+
struct TimeStampOpLowering : public OpRewritePattern<yul::TimeStampOp> {
442+
using OpRewritePattern<yul::TimeStampOp>::OpRewritePattern;
443+
444+
LogicalResult matchAndRewrite(yul::TimeStampOp op,
445+
PatternRewriter &r) const override {
446+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_timestamp,
447+
/*resTy=*/r.getIntegerType(256),
448+
/*ins=*/ValueRange{},
449+
"evm.timestamp");
450+
return success();
451+
}
452+
};
453+
454+
struct NumberOpLowering : public OpRewritePattern<yul::NumberOp> {
455+
using OpRewritePattern<yul::NumberOp>::OpRewritePattern;
456+
457+
LogicalResult matchAndRewrite(yul::NumberOp op,
458+
PatternRewriter &r) const override {
459+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_number,
460+
/*resTy=*/r.getIntegerType(256),
461+
/*ins=*/ValueRange{}, "evm.number");
462+
return success();
463+
}
464+
};
465+
466+
struct PrevrandaoOpLowering : public OpRewritePattern<yul::PrevrandaoOp> {
467+
using OpRewritePattern<yul::PrevrandaoOp>::OpRewritePattern;
468+
469+
LogicalResult matchAndRewrite(yul::PrevrandaoOp op,
470+
PatternRewriter &r) const override {
471+
// TODO: fix the intrinsic name in LLVM.
472+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_difficulty,
473+
/*resTy=*/r.getIntegerType(256),
474+
/*ins=*/ValueRange{},
475+
"evm.difficulty");
476+
return success();
477+
}
478+
};
479+
480+
struct GasLimitOpLowering : public OpRewritePattern<yul::GasLimitOp> {
481+
using OpRewritePattern<yul::GasLimitOp>::OpRewritePattern;
482+
483+
LogicalResult matchAndRewrite(yul::GasLimitOp op,
484+
PatternRewriter &r) const override {
485+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_gaslimit,
486+
/*resTy=*/r.getIntegerType(256),
487+
/*ins=*/ValueRange{},
488+
"evm.gaslimit");
489+
return success();
490+
}
491+
};
492+
314493
struct CallValOpLowering : public OpRewritePattern<yul::CallValOp> {
315494
using OpRewritePattern<yul::CallValOp>::OpRewritePattern;
316495

@@ -536,6 +715,19 @@ struct ExtCodeCopyOpLowering : public OpRewritePattern<yul::ExtCodeCopyOp> {
536715
}
537716
};
538717

718+
struct ExtCodeHashOpLowering : public OpRewritePattern<yul::ExtCodeHashOp> {
719+
using OpRewritePattern<yul::ExtCodeHashOp>::OpRewritePattern;
720+
721+
LogicalResult matchAndRewrite(yul::ExtCodeHashOp op,
722+
PatternRewriter &r) const override {
723+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(op, llvm::Intrinsic::evm_extcodehash,
724+
/*resTy=*/r.getIntegerType(256),
725+
/*ins=*/op.getAddr(),
726+
"evm.extcodehash");
727+
return success();
728+
}
729+
};
730+
539731
struct CreateOpLowering : public OpRewritePattern<yul::CreateOp> {
540732
using OpRewritePattern<yul::CreateOp>::OpRewritePattern;
541733

@@ -764,6 +956,25 @@ struct BuiltinCallOpLowering : public OpRewritePattern<yul::CallOp> {
764956
}
765957
};
766958

959+
struct CallCodeOpLowering : public OpRewritePattern<yul::CallCodeOp> {
960+
using OpRewritePattern<yul::CallCodeOp>::OpRewritePattern;
961+
962+
LogicalResult matchAndRewrite(yul::CallCodeOp op,
963+
PatternRewriter &r) const override {
964+
evm::Builder evmB(r, op.getLoc());
965+
966+
r.replaceOpWithNewOp<LLVM::IntrCallOp>(
967+
op, llvm::Intrinsic::evm_callcode,
968+
/*resTy=*/r.getIntegerType(256),
969+
/*ins=*/
970+
ValueRange{op.getGas(), op.getAddress(), op.getValue(),
971+
evmB.genHeapPtr(op.getInpOffset()), op.getInpSize(),
972+
evmB.genHeapPtr(op.getOutOffset()), op.getOutSize()},
973+
"evm.callcode");
974+
return success();
975+
}
976+
};
977+
767978
struct StaticCallOpLowering : public OpRewritePattern<yul::StaticCallOp> {
768979
using OpRewritePattern<yul::StaticCallOp>::OpRewritePattern;
769980

@@ -914,8 +1125,22 @@ void evm::populateYulPats(RewritePatternSet &pats) {
9141125
SignExtendOpLowering,
9151126
LogOpLowering,
9161127
AddressOpLowering,
1128+
BalanceOpLowering,
1129+
SelfBalanceOpLowering,
9171130
CallerOpLowering,
9181131
GasOpLowering,
1132+
ChainIdOpLowering,
1133+
BaseFeeOpLowering,
1134+
BlobBaseFeeOpLowering,
1135+
OriginOpLowering,
1136+
GasPriceOpLowering,
1137+
BlockHashOpLowering,
1138+
BlobHashOpLowering,
1139+
CoinBaseOpLowering,
1140+
TimeStampOpLowering,
1141+
NumberOpLowering,
1142+
PrevrandaoOpLowering,
1143+
GasLimitOpLowering,
9191144
RevertOpLowering,
9201145
StopOpLowering,
9211146
CallValOpLowering,
@@ -934,6 +1159,7 @@ void evm::populateYulPats(RewritePatternSet &pats) {
9341159
CodeCopyOpLowering,
9351160
ExtCodeSizeOpLowering,
9361161
ExtCodeCopyOpLowering,
1162+
ExtCodeHashOpLowering,
9371163
CreateOpLowering,
9381164
Create2OpLowering,
9391165
MLoadOpLowering,
@@ -947,6 +1173,7 @@ void evm::populateYulPats(RewritePatternSet &pats) {
9471173
MCopyOpLowering,
9481174
MemGuardOpLowering,
9491175
BuiltinCallOpLowering,
1176+
CallCodeOpLowering,
9501177
StaticCallOpLowering,
9511178
DelegateCallOpLowering,
9521179
BuiltinRetOpLowering,

0 commit comments

Comments
 (0)