Paul C. Anagnostopoulos via llvm-dev
2020-Nov-02 19:09 UTC
[llvm-dev] TableGen: Named template arguments
Here is a TableGen feature that I think would be useful, but I'd like some feedback. TableGen would allow the template arguments in a class or multiclass invocation to be named (in the venerable tradition of macro arguments). For example: class InstSubst<string Asm, dag Result, bit EmitPriority = 0> : InstAlias<Asm, Result, EmitPriority>, Requires<[UseNegativeImmediates]>; This class could be invoked as follows: def : InstSubst<Result: (!cast<Instruction>(NAME # "Wri") GPR32sp:$Rd, GPR32:$Rn, logical_imm32_not:$imm), Asm: Alias # "\t$Rd, $Rn, $imm", EmitPriority: 0>; Note that each template argument is named, so that they do not have to be in order. An argument list could start with positional arguments and then switch to named arguments, but not vice versa.
Nicolai Hähnle via llvm-dev
2020-Nov-02 21:03 UTC
[llvm-dev] TableGen: Named template arguments
Hi Paul, On Mon, Nov 2, 2020 at 8:14 PM Paul C. Anagnostopoulos via llvm-dev <llvm-dev at lists.llvm.org> wrote:> Here is a TableGen feature that I think would be useful, but I'd like some feedback. > > TableGen would allow the template arguments in a class or multiclass invocation to be named (in the venerable tradition of macro arguments). For example: > > class InstSubst<string Asm, dag Result, bit EmitPriority = 0> > : InstAlias<Asm, Result, EmitPriority>, Requires<[UseNegativeImmediates]>; > > This class could be invoked as follows: > > def : InstSubst<Result: (!cast<Instruction>(NAME # "Wri") GPR32sp:$Rd, > GPR32:$Rn, logical_imm32_not:$imm), > Asm: Alias # "\t$Rd, $Rn, $imm", > EmitPriority: 0>;I assume `Alias` is defined externally, e.g. because you took this example from a multiclass definition?> Note that each template argument is named, so that they do not have to be in order. An argument list could start with positional arguments and then switch to named arguments, but not vice versa.This is a pretty natural idea, but I'd like to think through some implications a bit more. There is a bit of implicit overlap between what you're proposing here and the `let` facility combined with late resolution. In the past, I have occasionally resisted the urge to add more template parameters consciously, because having so many parameters with meaningful positions tends to make for hard-to-read instantiations. I then solved the problem you're proposing to solve here with named parameters with `let` statements instead. So there is a bit of a risk of having multiple ways of saying the same thing. Then again: the `let` approach doesn't work when using classes for functional programming; and perhaps we should consider too much late resolution a bad thing anyway. Do you have a concrete use case for this? I think I'd tentatively say I'd be okay with adding this, but only if we have a compelling near-term use case for it; otherwise, we're adding unused features to TableGen which risks bit-rot. Cheers, Nicolai
Paul C. Anagnostopoulos via llvm-dev
2020-Nov-02 21:45 UTC
[llvm-dev] TableGen: Named template arguments
I took that example from AAarch64/AArch64InstrFormats.td. The InstSubst class is defined in Target/Target.td. At 11/2/2020 04:03 PM, Nicolai Hähnle wrote:>Hi Paul, > >On Mon, Nov 2, 2020 at 8:14 PM Paul C. Anagnostopoulos via llvm-dev ><llvm-dev at lists.llvm.org> wrote: >> Here is a TableGen feature that I think would be useful, but I'd like some feedback. >> >> TableGen would allow the template arguments in a class or multiclass invocation to be named (in the venerable tradition of macro arguments). For example: >> >> class InstSubst<string Asm, dag Result, bit EmitPriority = 0> >> : InstAlias<Asm, Result, EmitPriority>, Requires<[UseNegativeImmediates]>; >> >> This class could be invoked as follows: >> >> def : InstSubst<Result: (!cast<Instruction>(NAME # "Wri") GPR32sp:$Rd, >> GPR32:$Rn, logical_imm32_not:$imm), >> Asm: Alias # "\t$Rd, $Rn, $imm", >> EmitPriority: 0>; > >I assume `Alias` is defined externally, e.g. because you took this >example from a multiclass definition?--------------------------------- I have no specific use case in mind. I think this would be helpful in clarifying invocations of classes and multiclasses with many template arguments. In particular, it would allow you to specify one of the optional arguments without having to list multiple optional arguments. There are plenty of classes with 5 or more arguments; BaseSIMDDifferentThreeVectorTied takes 11. I hadn't really thought of `let` as a method of passing arguments, but only as a way of overriding fields. But that is, indeed, pretty much the same thing. As you say, `let` doesn't help if the class needs to compute other values based on the field being `let`, since 'let` uses late binding. In this case the value needs to be an argument. I think we can let this float and see whether people would like to use named arguments to clarify TableGen code. If not, then it is probably not worth implementing.>> Note that each template argument is named, so that they do not have to be in order. An argument list could start with positional arguments and then switch to named arguments, but not vice versa. > >This is a pretty natural idea, but I'd like to think through some >implications a bit more. > >There is a bit of implicit overlap between what you're proposing here >and the `let` facility combined with late resolution. In the past, I >have occasionally resisted the urge to add more template parameters >consciously, because having so many parameters with meaningful >positions tends to make for hard-to-read instantiations. I then solved >the problem you're proposing to solve here with named parameters with >`let` statements instead. > >So there is a bit of a risk of having multiple ways of saying the same thing. > >Then again: the `let` approach doesn't work when using classes for >functional programming; and perhaps we should consider too much late >resolution a bad thing anyway. > >Do you have a concrete use case for this? > >I think I'd tentatively say I'd be okay with adding this, but only if >we have a compelling near-term use case for it; otherwise, we're >adding unused features to TableGen which risks bit-rot. > >Cheers, >Nicolai