tablegen generated enums in tablegen

I’d like to store a tablegen generated enumeration in a record field/value. Clearly this enumeration isn’t available yet so it seems that a code fragment should be the escape mechanism I need. Looking at the other backends for examples, I see things like

[{ return Imm >= 0 && Imm < 64; }] // promising
code Requires = [{ {} }]; // this looks like a string
let Requires = [{ {AArch64::FeatureETE} }]. // which is not promising

So I think that this would look something like:

int reg_index = -1;


let reg_index = [{ return XX::R8; }]; // or
let reg_index = [{ {XX::R8} }];

However, then I get errors of the form:

error: Value ‘reg_index’ of type ‘int’ is incompatible with initializer ‘[{ {XX::R8} }]’ of type ‘code’

error: Value ‘reg_index’ of type ‘int’ is incompatible with initializer ‘[{ return XX::R8; }]’ of type ‘code’

Is there a way of doing this? I don’t understand TableGen casting but is that necessary?

I figured out the answer to my problem. I use const MCInstrDesc desc = MCII->get(x) to get the same information. It’s just that I was writing TableGen descriptions and so I thought the answer would be in TableGen.

Hi Chris,

I'd like to store a tablegen generated enumeration in a record field/value. Clearly this enumeration isn't available yet so it seems that a code fragment should be the escape mechanism I need.

I don't think this is clear at all. Maybe you can explain what you're
trying to do and why simply using the enumeration fails?

[snip]

So I think that this would look something like:

    int reg_index = -1;
    ...
    let reg_index = [{ return XX::R8; }]; // or
    let reg_index = [{ {XX::R8} }];

However, then I get errors of the form:

    error: Value 'reg_index' of type 'int' is incompatible with initializer '[{ {XX::R8} }]' of type 'code'
    error: Value 'reg_index' of type 'int' is incompatible with initializer '[{ return XX::R8; }]' of type 'code'

Well, yes. [{ }] is really just more convenient syntax for strings
that are meant to contain code snippets, and you can't assign a string
to an integer :slight_smile: Those code snippets aren't executed by TableGen,
they're pasted into TableGen-generated C++ and only executed at
runtime.

Why doesn't

    let reg_index = R8;

or whatever work, if R8 is an object known to TableGen?

Cheers,
Nicolai

As a generic note, I don’t believe that there are many places within TableGen’s set of code generators that handle ‘code’ values as pass-through in the way you hint at below. One place that does is SearchableTable/GenericTable field values, and that is pretty useful.

-Hal

Hal and Nicolai

I figured out my problem and I’m using TSFlags. Basically if I want to indicate register R8, I encode it as 8 in some bits in TSFlags. Then in my Disassembler that 8 indexes into a lookup table and returns Target::R8. This works for my backend and now I’m on to fixups and relocs. It may seem that a uint64_t isn’t a lot of bandwidth to communicate with between the TableGen defs and the MC layer, but I don’t need a lot.

I tried using the MCInst operand list but I wasn’t convinced I really understood it. It seems to me that an operand has a fairly general definition. I also tried various plausible escape syntaxes in TableGen but none worked. TSFlags has the virtue of being reserved for the backend’s use and, in my case, working.

C