Ruby bindings for the LLDB debugger.
Overview
This gem provides Ruby bindings for LLDB (Low Level Debugger), allowing you to access LLDB's debugging functionality from Ruby. It uses FFI (Foreign Function Interface) with a C wrapper around LLDB's C++ API.
Requirements
- Ruby 3.0 or later
- LLDB 14 or later
- C++17 compatible compiler (gcc 8+ / clang 10+)
- libffi-dev (for the FFI gem)
Installing LLDB
Ubuntu/Debian:
sudo apt-get install lldb-14 liblldb-14-devFedora/RHEL:
sudo dnf install lldb-develmacOS:
xcode-select --install
# or
brew install llvmInstallation
Add this line to your application's Gemfile:
gem 'lldb'And then execute:
bundle installOr install it yourself as:
gem install lldbUsage
Basic Example
require 'lldb'
# Initialize LLDB
LLDB.initialize
# Create a debugger
debugger = LLDB::Debugger.create
debugger.async = false # Run synchronously
# Create a target from an executable
target = debugger.create_target('./my_program')
# Set a breakpoint at main
bp = target.breakpoint_create_by_name('main')
puts "Breakpoint #{bp.id} created with #{bp.num_locations} locations"
# Launch the process
process = target.launch
# Check if stopped at breakpoint
if process.stopped?
thread = process.selected_thread
frame = thread.selected_frame
puts "Stopped at: #{frame.function_name}"
puts "Location: #{frame.location}"
# Find a variable
var = frame.find_variable('argc')
puts "argc = #{var.value}" if var
# Evaluate an expression
result = frame.evaluate_expression('argc + 1')
puts "argc + 1 = #{result.value}" if result
# Continue execution
process.continue
end
# Clean up
process.kill if process.valid?
LLDB.terminateCreating Breakpoints
# By function name
bp = target.breakpoint_create_by_name('main')
# By source location
bp = target.breakpoint_create_by_location('main.c', 10)
# By address
bp = target.breakpoint_create_by_address(0x100001000)
# Configure breakpoint
bp.condition = 'x > 5'
bp.ignore_count = 2
bp.one_shot = true
bp.disable
bp.enableStepping Through Code
thread = process.selected_thread
# Step over (next line)
thread.step_over
# Step into (enter function)
thread.step_into
# Step out (return from function)
thread.step_out
# Step one instruction
thread.step_instructionInspecting Variables
frame = thread.selected_frame
# Find a variable by name
var = frame.find_variable('my_variable')
if var && var.valid?
puts "Name: #{var.name}"
puts "Type: #{var.type_name}"
puts "Value: #{var.value}"
puts "Size: #{var.byte_size} bytes"
# For integer types
puts "As integer: #{var.to_i}"
# For complex types with children
if var.might_have_children?
var.each do |child|
puts " #{child.name} = #{child.value}"
end
end
endWorking with Threads
# Get all threads
process.threads.each do |thread|
puts "Thread #{thread.id}: #{thread.name || 'unnamed'}"
puts " Stop reason: #{thread.stop_reason_name}"
end
# Get the call stack
thread.frames.each_with_index do |frame, i|
puts "##{i}: #{frame.function_name} at #{frame.location}"
endAttaching to a Running Process
process = target.attach(pid: 12345)API Reference
Main Classes
-
LLDB::Debugger- Entry point for debugging operations -
LLDB::Target- Represents a debug target (executable) -
LLDB::Process- Represents a running process -
LLDB::Thread- Represents an execution thread -
LLDB::Frame- Represents a stack frame -
LLDB::Breakpoint- Represents a breakpoint -
LLDB::Value- Represents a variable or expression result -
LLDB::Module- Represents a loaded module -
LLDB::Error- Represents an error from LLDB
Constants
Process states are available in LLDB::State:
-
INVALID,UNLOADED,CONNECTED,ATTACHING,LAUNCHING -
STOPPED,RUNNING,STEPPING,CRASHED,DETACHED,EXITED,SUSPENDED
Stop reasons are available in LLDB::StopReason:
-
INVALID,NONE,TRACE,BREAKPOINT,WATCHPOINT -
SIGNAL,EXCEPTION,EXEC,PLAN_COMPLETE,THREAD_EXITING,INSTRUMENTATION
Development
After checking out the repo, run:
bundle install
cd ext/lldb && ruby extconf.rb && make && cd ../..
bundle exec rspecTo run tests, you need to compile the test fixtures:
gcc -g -O0 -o spec/fixtures/simple spec/fixtures/simple.cContributing
Bug reports and pull requests are welcome on GitHub.
License
Dual licensed under the MIT License and Apache License 2.0.