npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

llvm-node-bindings

v0.1.1

Published

TypeScript bindings for LLVM 22 codegen APIs

Readme

LLVM Bindings for Node.js

TypeScript/JavaScript bindings for LLVM 22 code generation APIs. Designed for building compilers, transpilers, and code generation tools in Node.js.

Features

  • LLVM 22 Support: Built against LLVM 22.1.x with opaque pointer support
  • Type-Safe: Full TypeScript definitions for all APIs
  • Core IR Generation: Complete support for basic LLVM IR generation
    • Contexts, Modules, Types (primitive, function, struct, pointer)
    • Functions, Basic Blocks, Values
    • IRBuilder with all common instructions (arithmetic, comparison, memory, control flow, calls)
  • Output Formats: Generate LLVM IR text (.ll) and bitcode (.bc) files
  • Memory Safe: Proper memory management using shared_ptr/weak_ptr for LLVM objects

Installation

Prerequisites

  • Node.js: 16.x or later
  • LLVM 22: Install LLVM 22.1.x
    • macOS: brew install llvm@22
    • Ubuntu/Debian: Install from LLVM apt repository
    • Windows: Download pre-built binaries from LLVM releases
  • CMake: 3.15 or later
  • C++17 compiler: clang++ or g++

Install

npm install llvm-node-bindings

The native addon will be compiled during installation using cmake-js.

Quick Start

import llvm from 'llvm-node-bindings';

// Create context and module
const context = new llvm.LLVMContext();
const module = new llvm.Module('my_module', context);
const builder = new llvm.IRBuilder(context);

// Create a simple function: i32 @add(i32, i32)
const i32 = llvm.Type.getInt32Ty(context);
const fnType = llvm.FunctionType.get(i32, [i32, i32], false);
const addFunc = llvm.Function.create(fnType, 'external', 'add', module);

// Create entry block and generate IR
const entry = llvm.BasicBlock.create(context, 'entry', addFunc);
builder.setInsertionPoint(entry);

// Add two constants and return result
const a = builder.createConstInt(i32, 10);
const b = builder.createConstInt(i32, 20);
const sum = builder.createAdd(a, b);
builder.createRet(sum);

// Output LLVM IR
console.log(module.print());

// Write bitcode to file
module.writeBitcodeToFile('output.bc');

API Reference

LLVMContext

The top-level container for all LLVM entities. Each context is independent.

const context = new llvm.LLVMContext();

Module

A compilation unit containing functions and global variables.

const module = new llvm.Module('module_name', context);
const ir = module.print();              // Get LLVM IR as string
module.writeBitcodeToFile('out.bc');    // Write bitcode file

Type

Base class for all LLVM types. Static factory methods for primitive types:

const voidTy = llvm.Type.getVoidTy(context);
const i1 = llvm.Type.getInt1Ty(context);     // boolean
const i8 = llvm.Type.getInt8Ty(context);
const i16 = llvm.Type.getInt16Ty(context);
const i32 = llvm.Type.getInt32Ty(context);
const i64 = llvm.Type.getInt64Ty(context);
const f32 = llvm.Type.getFloatTy(context);
const f64 = llvm.Type.getDoubleTy(context);

FunctionType

const fnType = llvm.FunctionType.get(
  returnType,      // Type
  [param1, param2], // Type[]
  false            // isVarArg
);

StructType

const structTy = llvm.StructType.get(
  context,
  [i32, i32, f64],  // field types
  false             // isPacked
);

PointerType

LLVM 22 uses opaque pointers (typed pointers are deprecated).

const ptrTy = llvm.PointerType.get(context, 0); // address space 0

Function

const func = llvm.Function.create(
  functionType,    // FunctionType
  'external',      // linkage: 'external' | 'internal' | 'private'
  'function_name', // string
  module           // Module
);

BasicBlock

const bb = llvm.BasicBlock.create(context, 'entry', parentFunc);
const parent = bb.getParent();  // Get parent function

Value

Base class for all values. Methods available on all values:

const name = value.getName();
value.setName('new_name');
const type = value.getType();

IRBuilder

Helper for generating LLVM instructions.

const builder = new llvm.IRBuilder(context);
builder.setInsertionPoint(basicBlock);

Constants

const constInt = builder.createConstInt(type, value);

Terminator Instructions

builder.createRetVoid();
builder.createRet(value);
builder.createBr(destBlock);
builder.createCondBr(condition, thenBlock, elseBlock);

Arithmetic Instructions

builder.createAdd(lhs, rhs);    // addition
builder.createSub(lhs, rhs);    // subtraction
builder.createMul(lhs, rhs);    // multiplication
builder.createSDiv(lhs, rhs);   // signed division
builder.createUDiv(lhs, rhs);   // unsigned division
builder.createSRem(lhs, rhs);   // signed remainder

Bitwise Instructions

builder.createAnd(lhs, rhs);    // bitwise AND
builder.createOr(lhs, rhs);     // bitwise OR
builder.createXor(lhs, rhs);    // bitwise XOR
builder.createShl(lhs, rhs);    // left shift
builder.createLShr(lhs, rhs);   // logical right shift
builder.createAShr(lhs, rhs);   // arithmetic right shift

Comparison Instructions

builder.createICmpEQ(lhs, rhs);   // equal
builder.createICmpNE(lhs, rhs);   // not equal
builder.createICmpSLT(lhs, rhs);  // signed less than
builder.createICmpSLE(lhs, rhs);  // signed less or equal
builder.createICmpSGT(lhs, rhs);  // signed greater than
builder.createICmpSGE(lhs, rhs);  // signed greater or equal

Memory Instructions

const ptr = builder.createAlloca(type);
const val = builder.createLoad(type, ptr);
builder.createStore(value, ptr);

GEP (GetElementPtr)

const elemPtr = builder.createGEP(baseType, ptr, [index1, index2]);

Call Instruction

const result = builder.createCall(functionType, callee, [arg1, arg2]);

Complete Example

import llvm from 'llvm-node-bindings';
import * as fs from 'fs';

// Setup
const context = new llvm.LLVMContext();
const module = new llvm.Module('example', context);
const builder = new llvm.IRBuilder(context);

// Types
const i32 = llvm.Type.getInt32Ty(context);
const i1 = llvm.Type.getInt1Ty(context);

// Function: i32 @main()
const mainType = llvm.FunctionType.get(i32, [], false);
const mainFunc = llvm.Function.create(mainType, 'external', 'main', module);

// Basic blocks
const entry = llvm.BasicBlock.create(context, 'entry', mainFunc);
const thenBB = llvm.BasicBlock.create(context, 'then', mainFunc);
const elseBB = llvm.BasicBlock.create(context, 'else', mainFunc);
const mergeBB = llvm.BasicBlock.create(context, 'merge', mainFunc);

// Entry block: allocate variable and branch
builder.setInsertionPoint(entry);
const xPtr = builder.createAlloca(i32);
const initialValue = builder.createConstInt(i32, 10);
builder.createStore(initialValue, xPtr);

const x = builder.createLoad(i32, xPtr);
const five = builder.createConstInt(i32, 5);
const cond = builder.createICmpSGT(x, five);
builder.createCondBr(cond, thenBB, elseBB);

// Then block
builder.setInsertionPoint(thenBB);
const twenty = builder.createConstInt(i32, 20);
const thenResult = builder.createAdd(x, twenty);
builder.createStore(thenResult, xPtr);
builder.createBr(mergeBB);

// Else block
builder.setInsertionPoint(elseBB);
const ten = builder.createConstInt(i32, 10);
const elseResult = builder.createMul(x, ten);
builder.createStore(elseResult, xPtr);
builder.createBr(mergeBB);

// Merge block
builder.setInsertionPoint(mergeBB);
const finalValue = builder.createLoad(i32, xPtr);
builder.createRet(finalValue);

// Output
fs.writeFileSync('output.ll', module.print());
module.writeBitcodeToFile('output.bc');

Building from Source

git clone <repository-url>
cd llvm-node-bindings
npm install
npm run build
npm test

Testing

npm test                    # Run all tests
npm test context.test.ts    # Run specific test

Architecture

The bindings use a three-layer architecture:

  1. Native C++ Layer: NAPI wrappers around LLVM C++ APIs
  2. JavaScript Bridge: Node.js addon exposing wrapped classes
  3. TypeScript Definitions: Type-safe interface for TypeScript

Memory management uses shared_ptr for LLVMContext and weak_ptr for dependent objects, ensuring safe cleanup while respecting LLVM's ownership model.

LLVM 22 Notes

  • Opaque Pointers: LLVM 22 uses opaque pointers. Use PointerType::get(context, addressSpace) instead of typed pointers.
  • Constant Folding: LLVM automatically folds constant expressions (e.g., 10 + 20 becomes 30 at compile time).

Comparison with llvm-bindings v14

This is a fresh implementation for LLVM 22, not backward compatible with the v14 bindings at https://github.com/mohitk05/llvm-bindings:

  • Targets LLVM 22 (vs LLVM 14)
  • Uses opaque pointers (LLVM 22 requirement)
  • Focused API surface for basic IR generation
  • Modern C++17 and Node-API
  • TDD approach with comprehensive test coverage

Requirements

  • LLVM 22.1.x
  • Node.js 16+
  • CMake 3.15+
  • C++17 compiler

License

MIT

Contributing

Contributions welcome! Please ensure:

  • All tests pass (npm test)
  • New features include tests
  • Code follows existing style

Roadmap

Future enhancements may include:

  • Global variables and constants
  • Function attributes
  • Additional instruction types (bitcast, phi, select)
  • Optimization passes
  • Target machine codegen

Support

For issues and questions, please file an issue on GitHub.