public inbox for gcc@gcc.gnu.org
 help / color / mirror / Atom feed
* Setting insn mnemonic partly automagically
@ 2024-06-17 19:13 Stefan Schulze Frielinghaus
  2024-06-21 19:50 ` Georg-Johann Lay
  0 siblings, 1 reply; 5+ messages in thread
From: Stefan Schulze Frielinghaus @ 2024-06-17 19:13 UTC (permalink / raw)
  To: gcc

Hi all,

I'm trying to add an alternative to an existing insn foobar:

(define_insn "foobar"
  [(set (match_operand ...)
        (match_operand ...))]
  ""
  "@
   foo
   bar
   #")

Since the asm output depends on the operands in a non-trivial way which isn't
easily solved via iterators, I went for a general C function and came up with:

(define_insn "foobar"
  [(set (match_operand ...)
        (match_operand ...))]
  ""
  "@
   foo
   * return foobar_helper (operands[0], operands[1]);
   bar
   #"
  [(set_attr_alternative "mnemonic" [(const_string "foo")
                                     (const_string "specialcase")
                                     (const_string "bar")
                                     (const_string "unknown")])])

If there exist a lot of alternatives, then setting the mnemonic attribute like
this feels repetitive and is error prone.  Furthermore, if there exists no
other insn with an output template containing foo/bar, then I would have to
declare foo/bar via

(define_attr "mnemonic" "...,foo,bar,..." (const_string "unknown"))

which again is repetitive.  Thus, I'm wondering if there exists a more elegant
way to achieve this?  Ultimately, I would like to set the mnemonic
attribute only manually for the alternative which is implemented via C
code and let the mnemonic attribute for the remaining alternatives be
set automagically.  Not sure whether this is supported?

If all fails, I have another idea how to solve this by utilizing PRINT_OPERAND.
However, now I'm curious whether my current attempt is feasible or not.

Cheers,
Stefan

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: Setting insn mnemonic partly automagically
  2024-06-17 19:13 Setting insn mnemonic partly automagically Stefan Schulze Frielinghaus
@ 2024-06-21 19:50 ` Georg-Johann Lay
  2024-06-22  8:46   ` Stefan Schulze Frielinghaus
  0 siblings, 1 reply; 5+ messages in thread
From: Georg-Johann Lay @ 2024-06-21 19:50 UTC (permalink / raw)
  To: Stefan Schulze Frielinghaus, gcc



Am 17.06.24 um 21:13 schrieb Stefan Schulze Frielinghaus via Gcc:
> Hi all,
> 
> I'm trying to add an alternative to an existing insn foobar:
> 
> (define_insn "foobar"
>    [(set (match_operand ...)
>          (match_operand ...))]
>    ""
>    "@
>     foo
>     bar
>     #")
> 
> Since the asm output depends on the operands in a non-trivial way which isn't
> easily solved via iterators, I went for a general C function and came up with:
> 
> (define_insn "foobar"
>    [(set (match_operand ...)
>          (match_operand ...))]
>    ""
>    "@
>     foo
>     * return foobar_helper (operands[0], operands[1]);
>     bar
>     #"
>    [(set_attr_alternative "mnemonic" [(const_string "foo")
>                                       (const_string "specialcase")
>                                       (const_string "bar")
>                                       (const_string "unknown")])])
> 
> If there exist a lot of alternatives, then setting the mnemonic attribute like
> this feels repetitive and is error prone.  Furthermore, if there exists no
> other insn with an output template containing foo/bar, then I would have to
> declare foo/bar via
> 
> (define_attr "mnemonic" "...,foo,bar,..." (const_string "unknown"))
> 
> which again is repetitive.  Thus, I'm wondering if there exists a more elegant
> way to achieve this?  Ultimately, I would like to set the mnemonic
> attribute only manually for the alternative which is implemented via C
> code and let the mnemonic attribute for the remaining alternatives be
> set automagically.  Not sure whether this is supported?
> 
> If all fails, I have another idea how to solve this by utilizing PRINT_OPERAND.
> However, now I'm curious whether my current attempt is feasible or not.
> 
> Cheers,
> Stefan

It's a bit unclear to me what you are trying to do, as you are not only
adding an insn alternative, but also are adding insn attribute
"mnemonic", which the original insn did not have.

Also, it's unclear how PRINT_OPERAND would help with setting the attribute.

Johann

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: Setting insn mnemonic partly automagically
  2024-06-21 19:50 ` Georg-Johann Lay
@ 2024-06-22  8:46   ` Stefan Schulze Frielinghaus
  2024-06-22 11:00     ` Georg-Johann Lay
  0 siblings, 1 reply; 5+ messages in thread
From: Stefan Schulze Frielinghaus @ 2024-06-22  8:46 UTC (permalink / raw)
  To: Georg-Johann Lay; +Cc: gcc

On Fri, Jun 21, 2024 at 09:50:43PM +0200, Georg-Johann Lay wrote:
> 
> 
> Am 17.06.24 um 21:13 schrieb Stefan Schulze Frielinghaus via Gcc:
> > Hi all,
> > 
> > I'm trying to add an alternative to an existing insn foobar:
> > 
> > (define_insn "foobar"
> >    [(set (match_operand ...)
> >          (match_operand ...))]
> >    ""
> >    "@
> >     foo
> >     bar
> >     #")
> > 
> > Since the asm output depends on the operands in a non-trivial way which isn't
> > easily solved via iterators, I went for a general C function and came up with:
> > 
> > (define_insn "foobar"
> >    [(set (match_operand ...)
> >          (match_operand ...))]
> >    ""
> >    "@
> >     foo
> >     * return foobar_helper (operands[0], operands[1]);
> >     bar
> >     #"
> >    [(set_attr_alternative "mnemonic" [(const_string "foo")
> >                                       (const_string "specialcase")
> >                                       (const_string "bar")
> >                                       (const_string "unknown")])])
> > 
> > If there exist a lot of alternatives, then setting the mnemonic attribute like
> > this feels repetitive and is error prone.  Furthermore, if there exists no
> > other insn with an output template containing foo/bar, then I would have to
> > declare foo/bar via
> > 
> > (define_attr "mnemonic" "...,foo,bar,..." (const_string "unknown"))
> > 
> > which again is repetitive.  Thus, I'm wondering if there exists a more elegant
> > way to achieve this?  Ultimately, I would like to set the mnemonic
> > attribute only manually for the alternative which is implemented via C
> > code and let the mnemonic attribute for the remaining alternatives be
> > set automagically.  Not sure whether this is supported?
> > 
> > If all fails, I have another idea how to solve this by utilizing PRINT_OPERAND.
> > However, now I'm curious whether my current attempt is feasible or not.
> > 
> > Cheers,
> > Stefan
> 
> It's a bit unclear to me what you are trying to do, as you are not only
> adding an insn alternative, but also are adding insn attribute
> "mnemonic", which the original insn did not have.

My take so far is that every insn has a mnemonic attribute which is set
either explicitly or implicitly (assuming that the target requested this
via define_attr "mnemonic" "...").  This is done in function
gen_mnemonic_attr() from gensupport.cc.  Thus, something like

(define_insn "foobar"
   [(set (match_operand ...)
         (match_operand ...))]
   ""
   "@
    foo
    bar
    #")

and

(define_insn "foobar"
   [(set (match_operand ...)
         (match_operand ...))]
   ""
   "@
    foo
    bar
    #"
   [(set_attr_alternative "mnemonic" [(const_string "foo")
                                      (const_string "bar")
                                      (const_string "unknown")])])

should be equivalent.

Of course, the implicit method fails if the pattern is generated via C
statements which is way I set it manually in the initial example.  The
initial example contained 3 alternatives plus 1 for the generated one.
Setting it manually there might be feasible, however, for my actual
problem I have an insn with 27 alternatives where I do not want to set
and maintain it manually.  A side effect of setting the attribute
implicitly is that each mnemonic is added automatically to the mnemonic
hash table which I would have to do manually for my 27 alternatives
which I would like to avoid, too.

> 
> Also, it's unclear how PRINT_OPERAND would help with setting the attribute.

For my particular problem I think one can also utilize PRINT_OPERAND
which I should have elaborated a bit more but feared to make the example
unnecessarily complicated.  The C code

  foobar_helper (operands[0], operands[1])

emits actually an extended mnemonic "specialcase$VAR\t%0,%1" where $VAR
can be either A, B, or C.  The extended mnemonic is just syntactic sugar
for the base mnemonic "specialcase\t%0,%1,$IMM" which is why we can lie
and hard code the mnemonic attribute to specialcase since this won't
effect scheduling.  Since the choice which extended mnemonic should be
used depends only on operands[1] I thought about rewriting all this into

(define_insn "foobar"
   [(set (match_operand ...)
         (match_operand ...))]
   ""
   "@
    foo
    specialcase\t%0,%1,%X1
    bar
    #")

Obviously we have to sacrifice the usage of an extended mnemonic but
more problematic is that we have to allocate one of those very few codes
X just for this insn.  So this doesn't scale either if one has to come
up with many different codes.  Furthermore, this only works in my very
particular case since I can split the extended mnemonic into a base
mnemonic and an immediate which only depends on one operand, i.e., it
would fail if it depended on operands[0] and operands[1].

I hope this makes it a bit more clear, if not just let me know.

Cheers,
Stefan

> 
> Johann

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: Setting insn mnemonic partly automagically
  2024-06-22  8:46   ` Stefan Schulze Frielinghaus
@ 2024-06-22 11:00     ` Georg-Johann Lay
  2024-06-22 15:24       ` Stefan Schulze Frielinghaus
  0 siblings, 1 reply; 5+ messages in thread
From: Georg-Johann Lay @ 2024-06-22 11:00 UTC (permalink / raw)
  To: Stefan Schulze Frielinghaus; +Cc: gcc

Am 22.06.24 um 10:46 schrieb Stefan Schulze Frielinghaus:
> On Fri, Jun 21, 2024 at 09:50:43PM +0200, Georg-Johann Lay wrote:
>>
>>
>> Am 17.06.24 um 21:13 schrieb Stefan Schulze Frielinghaus via Gcc:
>>> Hi all,
>>>
>>> I'm trying to add an alternative to an existing insn foobar:
>>>
>>> (define_insn "foobar"
>>>     [(set (match_operand ...)
>>>           (match_operand ...))]
>>>     ""
>>>     "@
>>>      foo
>>>      bar
>>>      #")
>>>
>>> Since the asm output depends on the operands in a non-trivial way which isn't
>>> easily solved via iterators, I went for a general C function and came up with:
>>>
>>> (define_insn "foobar"
>>>     [(set (match_operand ...)
>>>           (match_operand ...))]
>>>     ""
>>>     "@
>>>      foo
>>>      * return foobar_helper (operands[0], operands[1]);
>>>      bar
>>>      #"
>>>     [(set_attr_alternative "mnemonic" [(const_string "foo")
>>>                                        (const_string "specialcase")
>>>                                        (const_string "bar")
>>>                                        (const_string "unknown")])])
>>>
>>> If there exist a lot of alternatives, then setting the mnemonic attribute like
>>> this feels repetitive and is error prone.  Furthermore, if there exists no
>>> other insn with an output template containing foo/bar, then I would have to
>>> declare foo/bar via
>>>
>>> (define_attr "mnemonic" "...,foo,bar,..." (const_string "unknown"))
>>>
>>> which again is repetitive.  Thus, I'm wondering if there exists a more elegant
>>> way to achieve this?  Ultimately, I would like to set the mnemonic
>>> attribute only manually for the alternative which is implemented via C
>>> code and let the mnemonic attribute for the remaining alternatives be
>>> set automagically.  Not sure whether this is supported?
>>>
>>> If all fails, I have another idea how to solve this by utilizing PRINT_OPERAND.
>>> However, now I'm curious whether my current attempt is feasible or not.
>>>
>>> Cheers,
>>> Stefan
>>
>> It's a bit unclear to me what you are trying to do, as you are not only
>> adding an insn alternative, but also are adding insn attribute
>> "mnemonic", which the original insn did not have.
> 
> My take so far is that every insn has a mnemonic attribute which is set
> either explicitly or implicitly (assuming that the target requested this
> via define_attr "mnemonic" "...").  This is done in function
> gen_mnemonic_attr() from gensupport.cc.  Thus, something like
> 
> (define_insn "foobar"
>     [(set (match_operand ...)
>           (match_operand ...))]
>     ""
>     "@
>      foo
>      bar
>      #")
> 
> and
> 
> (define_insn "foobar"
>     [(set (match_operand ...)
>           (match_operand ...))]
>     ""
>     "@
>      foo
>      bar
>      #"
>     [(set_attr_alternative "mnemonic" [(const_string "foo")
>                                        (const_string "bar")
>                                        (const_string "unknown")])])
> 
> should be equivalent.
> 
> Of course, the implicit method fails if the pattern is generated via C
> statements which is way I set it manually in the initial example.  The
> initial example contained 3 alternatives plus 1 for the generated one.
> Setting it manually there might be feasible, however, for my actual
> problem I have an insn with 27 alternatives where I do not want to set
> and maintain it manually.  A side effect of setting the attribute
> implicitly is that each mnemonic is added automatically to the mnemonic
> hash table which I would have to do manually for my 27 alternatives
> which I would like to avoid, too.
> 
>>
>> Also, it's unclear how PRINT_OPERAND would help with setting the attribute.
> 
> For my particular problem I think one can also utilize PRINT_OPERAND
> which I should have elaborated a bit more but feared to make the example
> unnecessarily complicated.  The C code
> 
>    foobar_helper (operands[0], operands[1])
> 
> emits actually an extended mnemonic "specialcase$VAR\t%0,%1" where $VAR
> can be either A, B, or C.  The extended mnemonic is just syntactic sugar
> for the base mnemonic "specialcase\t%0,%1,$IMM" which is why we can lie
> and hard code the mnemonic attribute to specialcase since this won't
> effect scheduling.  Since the choice which extended mnemonic should be
> used depends only on operands[1] I thought about rewriting all this into
> 
> (define_insn "foobar"
>     [(set (match_operand ...)
>           (match_operand ...))]
>     ""
>     "@
>      foo
>      specialcase\t%0,%1,%X1
>      bar
>      #")
> 
> Obviously we have to sacrifice the usage of an extended mnemonic but
> more problematic is that we have to allocate one of those very few codes
> X just for this insn.  So this doesn't scale either if one has to come
> up with many different codes.  Furthermore, this only works in my very
> particular case since I can split the extended mnemonic into a base
> mnemonic and an immediate which only depends on one operand, i.e., it
> would fail if it depended on operands[0] and operands[1].
> 
> I hope this makes it a bit more clear, if not just let me know.
> 
> Cheers,
> Stefan

Maybe the following syntax for setting an attribute is a better
fit in your case?

   [(set (attr "length")
         (symbol_ref ("4 + reg_overlap_mentioned_p (operands[0], 
operands[1])")))

So you can hook in some function that spits out the attributes,
and it could also provide mnemonics.

Johann

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: Setting insn mnemonic partly automagically
  2024-06-22 11:00     ` Georg-Johann Lay
@ 2024-06-22 15:24       ` Stefan Schulze Frielinghaus
  0 siblings, 0 replies; 5+ messages in thread
From: Stefan Schulze Frielinghaus @ 2024-06-22 15:24 UTC (permalink / raw)
  To: Georg-Johann Lay; +Cc: gcc

On Sat, Jun 22, 2024 at 01:00:54PM +0200, Georg-Johann Lay wrote:
> Am 22.06.24 um 10:46 schrieb Stefan Schulze Frielinghaus:
> > On Fri, Jun 21, 2024 at 09:50:43PM +0200, Georg-Johann Lay wrote:
> > > 
> > > 
> > > Am 17.06.24 um 21:13 schrieb Stefan Schulze Frielinghaus via Gcc:
> > > > Hi all,
> > > > 
> > > > I'm trying to add an alternative to an existing insn foobar:
> > > > 
> > > > (define_insn "foobar"
> > > >     [(set (match_operand ...)
> > > >           (match_operand ...))]
> > > >     ""
> > > >     "@
> > > >      foo
> > > >      bar
> > > >      #")
> > > > 
> > > > Since the asm output depends on the operands in a non-trivial way which isn't
> > > > easily solved via iterators, I went for a general C function and came up with:
> > > > 
> > > > (define_insn "foobar"
> > > >     [(set (match_operand ...)
> > > >           (match_operand ...))]
> > > >     ""
> > > >     "@
> > > >      foo
> > > >      * return foobar_helper (operands[0], operands[1]);
> > > >      bar
> > > >      #"
> > > >     [(set_attr_alternative "mnemonic" [(const_string "foo")
> > > >                                        (const_string "specialcase")
> > > >                                        (const_string "bar")
> > > >                                        (const_string "unknown")])])
> > > > 
> > > > If there exist a lot of alternatives, then setting the mnemonic attribute like
> > > > this feels repetitive and is error prone.  Furthermore, if there exists no
> > > > other insn with an output template containing foo/bar, then I would have to
> > > > declare foo/bar via
> > > > 
> > > > (define_attr "mnemonic" "...,foo,bar,..." (const_string "unknown"))
> > > > 
> > > > which again is repetitive.  Thus, I'm wondering if there exists a more elegant
> > > > way to achieve this?  Ultimately, I would like to set the mnemonic
> > > > attribute only manually for the alternative which is implemented via C
> > > > code and let the mnemonic attribute for the remaining alternatives be
> > > > set automagically.  Not sure whether this is supported?
> > > > 
> > > > If all fails, I have another idea how to solve this by utilizing PRINT_OPERAND.
> > > > However, now I'm curious whether my current attempt is feasible or not.
> > > > 
> > > > Cheers,
> > > > Stefan
> > > 
> > > It's a bit unclear to me what you are trying to do, as you are not only
> > > adding an insn alternative, but also are adding insn attribute
> > > "mnemonic", which the original insn did not have.
> > 
> > My take so far is that every insn has a mnemonic attribute which is set
> > either explicitly or implicitly (assuming that the target requested this
> > via define_attr "mnemonic" "...").  This is done in function
> > gen_mnemonic_attr() from gensupport.cc.  Thus, something like
> > 
> > (define_insn "foobar"
> >     [(set (match_operand ...)
> >           (match_operand ...))]
> >     ""
> >     "@
> >      foo
> >      bar
> >      #")
> > 
> > and
> > 
> > (define_insn "foobar"
> >     [(set (match_operand ...)
> >           (match_operand ...))]
> >     ""
> >     "@
> >      foo
> >      bar
> >      #"
> >     [(set_attr_alternative "mnemonic" [(const_string "foo")
> >                                        (const_string "bar")
> >                                        (const_string "unknown")])])
> > 
> > should be equivalent.
> > 
> > Of course, the implicit method fails if the pattern is generated via C
> > statements which is way I set it manually in the initial example.  The
> > initial example contained 3 alternatives plus 1 for the generated one.
> > Setting it manually there might be feasible, however, for my actual
> > problem I have an insn with 27 alternatives where I do not want to set
> > and maintain it manually.  A side effect of setting the attribute
> > implicitly is that each mnemonic is added automatically to the mnemonic
> > hash table which I would have to do manually for my 27 alternatives
> > which I would like to avoid, too.
> > 
> > > 
> > > Also, it's unclear how PRINT_OPERAND would help with setting the attribute.
> > 
> > For my particular problem I think one can also utilize PRINT_OPERAND
> > which I should have elaborated a bit more but feared to make the example
> > unnecessarily complicated.  The C code
> > 
> >    foobar_helper (operands[0], operands[1])
> > 
> > emits actually an extended mnemonic "specialcase$VAR\t%0,%1" where $VAR
> > can be either A, B, or C.  The extended mnemonic is just syntactic sugar
> > for the base mnemonic "specialcase\t%0,%1,$IMM" which is why we can lie
> > and hard code the mnemonic attribute to specialcase since this won't
> > effect scheduling.  Since the choice which extended mnemonic should be
> > used depends only on operands[1] I thought about rewriting all this into
> > 
> > (define_insn "foobar"
> >     [(set (match_operand ...)
> >           (match_operand ...))]
> >     ""
> >     "@
> >      foo
> >      specialcase\t%0,%1,%X1
> >      bar
> >      #")
> > 
> > Obviously we have to sacrifice the usage of an extended mnemonic but
> > more problematic is that we have to allocate one of those very few codes
> > X just for this insn.  So this doesn't scale either if one has to come
> > up with many different codes.  Furthermore, this only works in my very
> > particular case since I can split the extended mnemonic into a base
> > mnemonic and an immediate which only depends on one operand, i.e., it
> > would fail if it depended on operands[0] and operands[1].
> > 
> > I hope this makes it a bit more clear, if not just let me know.
> > 
> > Cheers,
> > Stefan
> 
> Maybe the following syntax for setting an attribute is a better
> fit in your case?
> 
>   [(set (attr "length")
>         (symbol_ref ("4 + reg_overlap_mentioned_p (operands[0],
> operands[1])")))
> 
> So you can hook in some function that spits out the attributes,
> and it could also provide mnemonics.

I have been thinking about a symbel_ref hook, too.  However, came to the
conclusion that this would involve manual book keeping, too, i.e., I
would have to set and keep in sync in my symbol_ref expression for my 27
alternative insn all 26 static mnemonics manually only in order to
generate the 27th mnemonic.  Maybe my case is a bit too special.
Ultimately, I was hoping for something like

(define_insn "foobar"
  [(set (match_operand ...)
        (match_operand ...))]
  ""
  "@
   foo
   * return foobar_helper (operands[0], operands[1], insn);
   bar
   #")

where the function which generates the mnemonic is also able to set the
mnemonic attribute e.g. by passing the current insn reference as a
parameter.  Then function gen_mnemonic_attr() could deal with
alternatives 0 and 2 as usual and alternative 1 would have been dealt
with via C code.  However, the more I dig into the generation pipeline I
realize that this is not easily possible.  Function foobar_helper is
called during the final pass where scheduling is already done.  Too late
to set the mnemonic attribute.

Cheers,
Stefan

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2024-06-22 16:11 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2024-06-17 19:13 Setting insn mnemonic partly automagically Stefan Schulze Frielinghaus
2024-06-21 19:50 ` Georg-Johann Lay
2024-06-22  8:46   ` Stefan Schulze Frielinghaus
2024-06-22 11:00     ` Georg-Johann Lay
2024-06-22 15:24       ` Stefan Schulze Frielinghaus

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).