MCPcopy Create free account
hub / github.com/KhronosGroup/SPIRV-Tools / FoldInstructionToConstant

Method FoldInstructionToConstant

source/opt/fold.cpp:574–661  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

572}
573
574Instruction* InstructionFolder::FoldInstructionToConstant(
575 Instruction* inst, std::function<uint32_t(uint32_t)> id_map) const {
576 analysis::ConstantManager* const_mgr = context_->get_constant_mgr();
577
578 if (!inst->IsFoldableByFoldScalar() && !inst->IsFoldableByFoldVector() &&
579 !GetConstantFoldingRules().HasFoldingRule(inst)) {
580 return nullptr;
581 }
582 // Collect the values of the constant parameters.
583 std::vector<const analysis::Constant*> constants;
584 bool missing_constants = false;
585 inst->ForEachInId([&constants, &missing_constants, const_mgr,
586 &id_map](uint32_t* op_id) {
587 uint32_t id = id_map(*op_id);
588 const analysis::Constant* const_op = const_mgr->FindDeclaredConstant(id);
589 if (!const_op) {
590 constants.push_back(nullptr);
591 missing_constants = true;
592 } else {
593 constants.push_back(const_op);
594 }
595 });
596
597 const analysis::Constant* folded_const = nullptr;
598 for (auto rule : GetConstantFoldingRules().GetRulesForInstruction(inst)) {
599 folded_const = rule(context_, inst, constants);
600 if (folded_const == nullptr && inst->context()->id_overflow()) {
601 return nullptr;
602 }
603 if (folded_const != nullptr) {
604 Instruction* const_inst =
605 const_mgr->GetDefiningInstruction(folded_const, inst->type_id());
606 if (const_inst == nullptr) {
607 return nullptr;
608 }
609 assert(const_inst->type_id() == inst->type_id());
610 // May be a new instruction that needs to be analysed.
611 context_->UpdateDefUse(const_inst);
612 return const_inst;
613 }
614 }
615
616 bool successful = false;
617
618 // If all parameters are constant, fold the instruction to a constant.
619 if (inst->IsFoldableByFoldScalar()) {
620 uint32_t result_val = 0;
621
622 if (!missing_constants) {
623 result_val = FoldScalars(inst->opcode(), constants);
624 successful = true;
625 }
626
627 if (!successful) {
628 successful = FoldIntegerOpToConstant(inst, id_map, &result_val);
629 }
630
631 if (successful) {

Callers 3

VisitAssignmentMethod · 0.80
TEST_PFunction · 0.80

Calls 15

get_constant_mgrMethod · 0.80
HasFoldingRuleMethod · 0.80
ForEachInIdMethod · 0.80
id_overflowMethod · 0.80
AsVectorMethod · 0.80
FindDeclaredConstantMethod · 0.45
push_backMethod · 0.45

Tested by 2

TEST_PFunction · 0.64