Search code examples
llvmllvm-c++-api

Creating a struct containing a pointer to itself in LLVM


I'm currently using LLVM to build a JIT. There are some C structs that I would like to be able to use in my JIT'd IR. One of them has the following layout:

struct myStruct {
    int depth;
    myStruct* parent;
}

When compiling with clang and using -S -emit-llvm, I get the following, which seems absolutely reasonable:

type myStruct = { i32, myStruct* } 

Alright. Now, if I want to do the same using the LLVM API, I'm not quite sure how I should do it. The following (expectedly) does not work:

auto intType = IntegerType::get(context, 32); // 32 bits integer
Type* myStructPtrType = nullptr; // Pointer to myStruct

// The following crashes because myStructPtrType is null: 
auto myStructType = StructType::create(context, { intType, myStructPtrType }, "myStruct"); // myStruct

myStructPtrType = PointerType::get(myStructType, 0); // Initialise the pointer type now

I don't really know how to proceed here. Any suggestions are welcome.


Solution

  • I was able to answer the question thanks @arnt's comment. In case anyone has the same goal/problem. The idea is first to create an opaque type, then fetch the pointer type to this opaque type, then set the aggregate body (which is the key of the solution) using setBody.

    Here is some code:

    auto intType = IntegerType::get(context, 32); // 32 bits integer
    auto myStructType = StructType::create(context, "myStruct"); // Create opaque type
    auto myStructPtrType = PointerType::get(myStructType, 0); // Initialise the pointer type now
    myStructType->setBody({ intType, myStructPtrType }, /* packed */ false); // Set the body of the aggregate