Files
TheRock/rocm-libraries/shared/stinkytofu/docs/user/ir-converter.md
T
derek.holloway 7502bf64a4
CodeQL / Analyze (actions) (push) Canceled after 0s
CodeQL / Analyze (python) (push) Canceled after 0s
pre-commit / pre-commit (push) Canceled after 0s
Multi-Arch CI / setup (push) Canceled after 0s
Publish build_manylinux_x86_64 images / publish_build_manylinux_x86_64 (push) Canceled after 0s
Setup (Multi-Arch) / setup (push) Canceled after 0s
Multi-Arch CI / Linux::${{ fromJSON(needs.setup.outputs.linux_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubi10 image / publish_no_rocm_image_ubi10 (push) Canceled after 0s
Multi-Arch CI / Windows::${{ fromJSON(needs.setup.outputs.windows_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Multi-Arch CI / Manifest Diff (push) Canceled after 0s
TheRock Manifest Diff Report / Generate Manifest Diff Report (push) Canceled after 0s
Multi-Arch CI / CI Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_ocl_rt images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_rocgdb images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Unit Tests / Unit Tests :: ubuntu-24.04 (push) Canceled after 0s
Unit Tests / Unit Tests :: windows-2022 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_media (push) Canceled after 0s
Unit Tests / Unit Tests Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_openmpi (push) Canceled after 0s
Flatten subprojects into a single base monorepo
2026-09-02 16:34:47 -07:00

6.1 KiB

IR Converter - Converting Strings to IRList

StinkyTofu provides the 'StinkyIRConverter' class to programmatically convert MLIR-style instruction strings to 'IRList' objects.

Note: For detailed information about error codes, see Error Codes.

Basic Usage

'''cpp #include "stinkytofu/core/stinkytofu.hpp"

using namespace stinkytofu;

std::string irText = R"( v[0:3] = "st.ds_load_b128"(v40) { issueCycles = 4, latencyCycles = 56 } v[4:7] = "st.ds_load_b128"(v40) { issueCycles = 4, latencyCycles = 56 } )";

// Create converter with default architecture (gfx1250) StinkyIRConverter converter;

// Convert string to IRList IRList* irlist = converter.convertToIRList(irText);

if(irlist) { // Successfully converted, use the IRList std::cout << "Converted " << irlist->size() << " instructions\n"; } else { std::cerr << "Conversion failed\n"; } '''

Custom Architecture

You can specify a different target architecture:

'''cpp // For gfx1250 std::array<int, 3> arch = {12, 5, 0}; StinkyIRConverter converter(arch);

IRList* irlist = converter.convertToIRList(irText); '''

Accessing the PassContext

After conversion, you can access the 'PassContext' to run optimization passes:

'''cpp StinkyIRConverter converter; IRList* irlist = converter.convertToIRList(irText);

if(irlist) { PassContext* ctx = converter.getPassContext(); if(ctx) { // Run passes on the IR PassManager pm; pm.addPass(std::make_unique()); pm.run(*ctx); } } '''

Using the Static Method

For more control, use the static 'populateFunctionFromString' method:

'''cpp // Create your own PassContext auto ctx = PassContext::create(GfxArchID::gfx1250); IRList& irlist = ctx->getIRList();

// Populate it with instructions from string std::string irText = /* ... */; GfxArchID arch = GfxArchID::gfx1250;

StinkyErrorCode result = StinkyIRConverter::populateFunctionFromString( irText, irlist, *ctx, arch);

if(result == StinkyErrorCode::SUCCESS) { // Successfully populated std::cout << "Populated " << irlist.size() << " instructions\n"; } else { // Handle error std::cerr << "Error: " << static_cast(result) << "\n"; } '''

Complete Example

Here's a complete example showing conversion and assembly emission:

'''cpp #include "stinkytofu/core/stinkytofu.hpp" #include "stinkytofu/serialization/asm/StinkyAsmEmitter.hpp" #include

using namespace stinkytofu;

int main() { // IR text with two ds_read instructions std::string irText = R"( v[0:3] = "st.ds_load_b128"(v40) { issueCycles = 4, latencyCycles = 52 } v[4:7] = "st.ds_load_b128"(v40) { issueCycles = 4, latencyCycles = 52 } )";

// Convert to IRList
StinkyIRConverter converter;
IRList* irlist = converter.convertToIRList(irText);

if(!irlist) {
    std::cerr << "Failed to convert IR\n";
    return 1;
}

std::cout << "Converted " << irlist->size() << " instructions\n";

// Emit as assembly
StinkyAsmEmitter emitter;
std::string assembly = emitter.emit(*irlist);

std::cout << "\nGenerated Assembly:\n" << assembly << std::endl;

return 0;

} '''

Expected Output

''' Converted 2 instructions

Generated Assembly: // ================================================== // StinkyTofu Assembly Output // Instructions: 2 // ==================================================

ds_read_b128 v[0:3], v[40] // issue=4 latency=52
ds_read_b128 v[4:7], v[40] // issue=4 latency=52

'''

IR Format

The IR string should follow the MLIR-style StinkyTofu format:

''' destRegs = "st.mnemonic"(srcRegs) { attributes } '''

Examples

Simple instruction: ''' v[0] = "st.v_mov_b32"(v1) '''

Multiple destinations: ''' v[0:3] = "st.ds_load_b128"(v40) '''

With attributes: ''' v[0:3] = "st.ds_load_b128"(v40) { issueCycles = 4, latencyCycles = 52 } '''

Multiple source registers: ''' acc[0:15] = "st.v_mfma_f32_16x16x16_f16"(v6:7, v22:23, acc0:15) '''

Error Handling

Always check the return value:

'''cpp StinkyIRConverter converter; IRList* irlist = converter.convertToIRList(irText);

if(!irlist) { std::cerr << "Conversion failed. Possible reasons:\n" << " - Invalid IR syntax\n" << " - Unsupported instruction mnemonic\n" << " - Invalid register format\n"; return 1; } '''

For the static method, check the error code:

'''cpp StinkyErrorCode result = StinkyIRConverter::populateFunctionFromString( irText, irlist, *ctx, arch);

switch(result) { case StinkyErrorCode::SUCCESS: // Success break; case StinkyErrorCode::PASSCTX_EMPTY: std::cerr << "PassContext is empty or invalid\n"; break; default: std::cerr << "Unknown error\n"; break; } '''

Integration with Optimization Passes

After converting IR, you can run optimization passes:

'''cpp // Convert IR StinkyIRConverter converter; IRList* irlist = converter.convertToIRList(irText);

if(irlist) { PassContext* ctx = converter.getPassContext(); if(ctx) { // Create pass manager and add passes. The public API exposes passes // through factory functions (the concrete pass types are not installed). PassManager pm; pm.addPass(createStinkyDAGSchedulerPass()); pm.addPass(createStinkyWaitCntInsertionPass());

    // Run the passes
    pm.run(*ctx);

    // Emit optimized assembly
    StinkyAsmEmitter emitter;
    std::string optimizedAsm = emitter.emit(*irlist);
    std::cout << optimizedAsm << std::endl;
}

} '''

Thread Safety

'StinkyIRConverter' is not thread-safe. If you need to convert IR in multiple threads, create a separate converter instance for each thread:

'''cpp // In each thread: void processIRInThread(const std::string& irText) { StinkyIRConverter converter; // Thread-local instance IRList* irlist = converter.convertToIRList(irText); // ... process irlist ... } '''

See Also