MachineRegisterInfo use_iterator/reg_iterator?

Hi folks,

I would like to find out the machine instructions that use some given registers in the reverse order, and I came across these iterators (use_iterator/reg_iterator). However, there are two things I noticed:

  1. These iterators seem to traverse the machine function a bit differently from what I get from the machine function dump. In other words, the use_iterator list is not constructed in the same order as the machine function? Maybe from the order that DAG is constructed?

  2. Is there a way to go backward with these two iterators? For example, from use_end() to use_begin() with some decrement operator?

I was wondering if 1) and 2) are true or just there’s something I missed.

Thanks!

Cheng-Chih

Hi Cheng-Chih,

Hi folks,

I would like to find out the machine instructions that use some given registers in the reverse order, and I came across these iterators (use_iterator/reg_iterator). However, there are two things I noticed:

1) These iterators seem to traverse the machine function a bit differently from what I get from the machine function dump. In other words, the use_iterator list is not constructed in the same order as the machine function?

Yes, the use_iterator list is not constructed in the same order as the machine function.

Maybe from the order that DAG is constructed?

No, this is not the case either.
The list is constructed via calls to MachineInstr::setReg (which calls MachineRegisterInfo::addRegOperandToUseList if you are interested by the details), which could basically occur anywhere in the backend.
That said, the main users of this interface is the VirtRegMap pass, which walks through the function and set the register along the way. Therefore, most of the use_iterator should be in the order you want, but not all and more importantly, we do not ensure that this ordering is fulfilled.

2) Is there a way to go backward with these two iterators? For example, from use_end() to use_begin() with some decrement operator?

AFAIK, no, because we did not need so far to traverse them in a specific order.

What are you trying to achieve?

Cheers,
-Quentin

Thanks Quentin. I’m trying to examine from the operands of the return instruction, and then to get the last assignment of those. I thought use_iterator/reg_iterator may suit better than just loop through the machine basicblock in the reverse order.

Cheng-Chih

I guess you want to do that after register allocation.
If that is the case, yes, you have to track the information by your self. You can use the register scavenger for an example of how to do that (RegisterScavenging.cpp).

If you do that before register allocation, you can use the LiveInterval information or directly the MachineRegisterInfo::getVRegDef (or something like that, I haven’t check the exact name).

-Quentin

I guess you want to do that after register allocation.
If that is the case, yes, you have to track the information by your self. You can use the register scavenger for an example of how to do that (RegisterScavenging.cpp).

If you do that before register allocation, you can use the LiveInterval information or directly the MachineRegisterInfo::getVRegDef (or something like that, I haven’t check the exact name).

-Quentin

Thanks Quentin. I’m trying to examine from the operands of the return instruction, and then to get the last assignment of those.

Also, note that the last assignment may not be unique, e.g.,
if (…)
x = …
else
x = …
return x

That means you may need is a reaching-def algorithm.
A complete implementation is available in AArch64CollectLOH.cpp, however, I think you’d better specialize a reaching-def algorithm to your case as it has some nice simplifications (e.g., your uses are always in exit basic block).

-Quentin

Thanks Quentin! I’ll look into that.