Christoph Müllner <christoph.muell...@vrull.eu> writes:
> On Tue, Jun 24, 2025 at 9:29 PM Richard Sandiford
> <richard.sandif...@arm.com> wrote:
>>
>> Christoph Müllner <christoph.muell...@vrull.eu> writes:
>> > insn_info::has_been_deleted () is documented to return true if an
>> > instruction is deleted.  Such instructions have their `volatile` bit set,
>> > which can be tested via rtx_insn::deleted ().
>> >
>> > The current condition for insn_info::has_been_deleted () is:
>> > * m_rtl is not NULL: this can't happen as no member of insn_info
>> >   changes this pointer.
>>
>> Yeah, it's invariant after creation, but it starts off null for some
>> artificial instructions:
>>
>>   // Return the underlying RTL insn.  This instruction is null if is_phi ()
>>   // or is_bb_end () are true.  The instruction is a basic block note if
>>   // is_bb_head () is true.
>>   rtx_insn *rtl () const { return m_rtl; }
>>
>> So I think we should keep the null check.  (But then is_call and is_jump
>> should check m_rtl is nonnull too -- that's preapproved if you want to
>> do it while you're here.)
>
> I have a tested patch for this, but I don't think that it would be sufficient,
> as there are also other places to check for a NULL dereference:
> * member-fns.inl: insn_info::uid -> what to return here?

That one's ok, because m_rtl is nonnull whenever m_cost_or_uid >= 0.
(m_cost_or_uid >= 0 is the test for whether something is a "real"
instruction, in which case it always has an associated RTL insn.)

> * internals.inl: insn_info::set_properties
> * insns.cc: insn_info::calculate_cost

Those two are ok because they're internal routines that are only
reached when we already know that we're dealing with real instructions.

> Ok, if I add NULL-checks there as well?

I think just is_call and is_jump for now, since they're publicly-facing
routines that don't assume any preconditions.  Others might crop up later
though...

>> > * !INSN_P (m_rtl): this will likely fail for rtx_insn objects and
>> >   does not test the `volatile` bit.
>>
>> Because of the need to stage multiple simultaneous changes, rtl-ssa first
>> uses set_insn_deleted to convert an insn to a NOTE_INSN_DELETED note,
>> then uses remove_insn to remove the underlying instruction.  It doesn't
>> use delete_insn directly.  The call to remove_insn is fairly recent;
>> the original code just used set_insn_deleted, but not removing the notes
>> caused trouble for later passes.
>>
>> The test was therefore supposed to be checking whether set_insn_deleted
>> had been called.  It should also have checked the note kind though.
>
> Thanks for the explanation. I missed the fact that set_insn_delete () is used.
> Assuming that code using RTL-SSA will use the insn_change class, it makes
> sense now.

Ah, yeah, that's pretty much required, since otherwise things will get out
of sync.

> I'm converting the fold-mem-offsets pass to RTL-SSA (see PR117922).
> And I ran into this issue because I've already converted the analysis
> part to RTL-SSA,
> but the code changes are still performed directly on the rtx_insn objects
> (in do_commit_insn ()). I'll try to use RTL-SSA in do_commit_insn () as well,
> which should also allow RTL-SSA to see the changes.

Sounds good!  Thanks for doing this.

Richard

Reply via email to