sdlparser-scrap/docs/GETTING_STARTED.md

5.5 KiB

Getting Started with SDL3 Parser

This guide will help you get up and running with the SDL3 header parser.

Prerequisites

  • Zig 0.15 or later
  • SDL3 headers (included in ../SDL/include/SDL3/)

Installation

  1. Navigate to the parser directory:
cd lib/sdl3/parser
  1. Build the parser:
zig build
  1. Run tests to verify installation:
zig build test

You should see: All tests passed.

Your First Parse

Step 1: Parse SDL_gpu.h

zig build run -- ../SDL/include/SDL3/SDL_gpu.h --output=my_gpu.zig

You'll see output like:

SDL3 Header Parser
==================

Parsing: ../SDL/include/SDL3/SDL_gpu.h

Found 169 declarations
  - Opaque types: 13
  - Typedefs: 6
  - Enums: 24
  - Structs: 35
  - Flags: 3
  - Functions: 94

Analyzing dependencies...
Found 5 missing types:
  - SDL_FColor
  - SDL_PropertiesID
  - SDL_Rect
  - SDL_Window
  - SDL_FlipMode

Resolving dependencies from included headers...
  ✓ Found SDL_FColor in SDL_pixels.h
  ✓ Found SDL_PropertiesID in SDL_properties.h
  ✓ Found SDL_Rect in SDL_rect.h
  ✓ Found SDL_Window in SDL_video.h
  ✓ Found SDL_FlipMode in SDL_surface.h

Combining 5 dependency declarations with primary declarations...
Generated: my_gpu.zig

Step 2: Examine the Output

head -50 my_gpu.zig

You'll see clean Zig bindings:

pub const c = @import("c.zig").c;

// Dependencies (automatically included)
pub const FColor = extern struct {
    r: f32,
    g: f32,
    b: f32,
    a: f32,
};

pub const PropertiesID = u32;

pub const Rect = extern struct {
    x: c_int,
    y: c_int,
    w: c_int,
    h: c_int,
};

pub const Window = opaque {};

// Primary declarations
pub const GPUDevice = opaque {
    pub inline fn destroyGPUDevice(gpudevice: *GPUDevice) void {
        return c.SDL_DestroyGPUDevice(gpudevice);
    }
    // ... 93 more methods
};

Step 3: Create c.zig Wrapper

Create a file c.zig that imports SDL:

pub const c = @cImport({
    @cInclude("SDL3/SDL.h");
});

Step 4: Use in Your Project

const std = @import("std");
const gpu = @import("my_gpu.zig");

pub fn main() !void {
    const device = gpu.createGPUDevice(true);
    if (device) |d| {
        defer d.destroyGPUDevice();
        
        const driver = d.getGPUDeviceDriver();
        std.debug.print("GPU Driver: {s}\n", .{driver});
    }
}

Command-Line Options

Basic Options

# Output to file
zig build run -- header.h --output=output.zig

# Output to stdout
zig build run -- header.h

Mock Generation

# Generate C mocks for testing
zig build run -- header.h --output=bindings.zig --mocks=mocks.c

The mock file contains stub implementations that return zero/null:

void SDL_DestroyGPUDevice(SDL_GPUDevice *device) {
    // Mock implementation
}

Understanding the Output

Type Name Conversion

The parser follows consistent naming rules:

C Name Zig Name Rule
SDL_GPUDevice GPUDevice Strip SDL_ prefix
SDL_GPU_PRIMITIVE_TYPE_TRIANGLELIST primitiveTypeTrianglelist Strip prefix, camelCase
SDL_CreateGPUDevice createGPUDevice Strip SDL_, camelCase

Method Grouping

Functions are organized as methods when possible:

C API:

void SDL_DestroyGPUDevice(SDL_GPUDevice *device);
const char* SDL_GetGPUDeviceDriver(SDL_GPUDevice *device);

Generated Zig:

pub const GPUDevice = opaque {
    pub inline fn destroyGPUDevice(self: *GPUDevice) void { ... }
    pub inline fn getGPUDeviceDriver(self: *GPUDevice) [*c]const u8 { ... }
};

Usage becomes:

device.destroyGPUDevice();  // Instead of SDL_DestroyGPUDevice(device)

Dependency Inclusion

Dependencies are automatically detected and included at the top of the file:

// Dependencies from included headers
pub const FColor = extern struct { ... };
pub const Rect = extern struct { ... };
pub const Window = opaque {};

// Primary declarations from SDL_gpu.h
pub const GPUDevice = opaque { ... };

Common Workflows

Generate Bindings for a Module

# From lib/sdl3 directory
zig build regenerate-zig

This generates bindings for configured headers in v2/ directory.

Test Your Changes

After modifying the parser:

# Run unit tests
zig build test

# Test with a real header
zig build run -- ../SDL/include/SDL3/SDL_gpu.h --output=test.zig

# Verify output compiles
zig ast-check test.zig

Debug Issues

If you encounter errors:

  1. Check the console output for warnings about missing types
  2. Look at the generated file for syntax errors
  3. See Known Issues for common problems

Next Steps

Quick Reference

# Build
zig build

# Test
zig build test

# Generate bindings
zig build run -- <header> --output=<output>

# Generate with mocks
zig build run -- <header> --output=<output> --mocks=<mocks>

# Generate all configured headers
cd .. && zig build regenerate-zig

Getting Help

  • Documentation: See docs/ directory
  • Examples: Check test/ directory for usage examples
  • Issues: See docs/KNOWN_ISSUES.md

Next: Read Architecture to understand the parser internals.