- Contains the host code with a protocol implementation, data analyser and web-based visualiser
8.4 KiB
Getting Started with MiniProfiler
This guide will help you get started with MiniProfiler for profiling your embedded STM32 applications.
Prerequisites
Host System
- Python 3.8 or higher
- pip package manager
- Modern web browser (Chrome, Firefox, Edge)
- Serial port access (USB-to-Serial adapter or built-in UART)
Embedded Target (for Phase 2)
- STM32 microcontroller (STM32F4/F7/H7 recommended)
- GCC ARM toolchain
- UART or USB-CDC peripheral configured
- ST-Link or similar programmer/debugger
Installation
1. Clone the Repository
git clone https://github.com/yourusername/miniprofiler.git
cd miniprofiler
2. Install Python Dependencies
cd host
pip install -r requirements.txt
Or install as a package:
pip install -e .
3. Verify Installation
miniprofiler --help
You should see the help message with available options.
Testing Without Hardware
Before connecting to real hardware, you can test the visualization with sample data.
Generate Sample Data
cd host/tests
python sample_data_generator.py
This creates several sample data files:
sample_flamegraph.json- Flame graph visualization datasample_statistics.json- Function statisticssample_timeline.json- Timeline datasample_profile_data.bin- Binary protocol data
View Sample Visualizations
You can view the sample JSON files by loading them in the web interface or by opening them directly:
# View flame graph data
cat sample_flamegraph.json | python -m json.tool
# View statistics
cat sample_statistics.json | python -m json.tool
Running the Host Application
Start the Web Server
# From the host directory
python run.py
# Or using the installed CLI
miniprofiler
The server will start on http://localhost:5000 by default.
Custom Host/Port
miniprofiler --host 0.0.0.0 --port 8080
Enable Debug Mode
miniprofiler --debug --verbose
Using the Web Interface
1. Open the Browser
Navigate to http://localhost:5000
You should see the MiniProfiler dashboard with:
- Connection controls
- Profiling controls (disabled until connected)
- Status display
- Three visualization tabs
2. Configure Connection
Enter your serial port details:
- Serial Port:
/dev/ttyUSB0(Linux/Mac) orCOM3(Windows) - Baud Rate:
115200(default) - ELF Path: Path to your
.elffile (optional, for symbol resolution)
Finding Your Serial Port:
Linux/Mac:
ls /dev/tty* | grep -i usb
# or
ls /dev/tty.usb*
Windows:
- Open Device Manager
- Look under "Ports (COM & LPT)"
- Note the COM port number (e.g., COM3)
3. Connect to Device
Click the Connect button.
If successful, you'll see:
- Status indicator turns green
- "Connected to /dev/ttyUSB0" message
- Metadata panel appears with device information
- Profiling controls become enabled
4. Start Profiling
Click Start Profiling.
The device will begin sending profiling data, and you'll see:
- Real-time updates in all three visualization tabs
- Record count incrementing
- Summary statistics updating
5. Explore Visualizations
Flame Graph Tab
- Shows aggregate CPU time by function
- Wider bars = more time spent
- Click to zoom into specific call stacks
- Search for functions by name
- Hover for details
Timeline Tab
- Shows function execution over time
- X-axis = time in microseconds
- Y-axis = call stack depth
- Color = duration (darker = longer)
- Useful for finding timing issues
Statistics Tab
- Sortable table of function statistics
- Columns: Function, Address, Calls, Total/Avg/Min/Max Time
- Click column headers to sort
- Find hot spots and outliers
6. Control Profiling
- Stop Profiling: Pause data collection
- Clear Data: Reset all visualizations
- Reset Buffers: Clear device-side buffers
7. Disconnect
Click Disconnect when done to close the serial connection.
Understanding the Visualizations
Flame Graph
The flame graph shows aggregated profiling data:
┌─────────────────────────────────┐
│ main (10s) │ ← Root function
├──────────────┬──────────────────┤
│ app_loop │ process_data │ ← Called by main
│ (6s) │ (4s) │
├──────┬───────┼──────────────────┤
│ read │ write │ calculate │ ← Nested calls
│ (3s) │ (3s) │ (4s) │
└──────┴───────┴──────────────────┘
Interpretation:
- Width = total time (including children)
- Read from bottom (root) to top (leaves)
- Widest bars are hotspots to optimize
Timeline
The timeline shows chronological execution:
Time ───────────────────────►
│ ████ func_a
│ ██ func_b (called by func_a)
│ ████ func_c
│ ██ func_d
Interpretation:
- X-axis = time progression
- Y-axis = call depth
- Gaps = idle time or excluded functions
- Useful for timing analysis and debugging
Statistics Table
| Function | Calls | Total Time | Avg Time |
|---|---|---|---|
| main | 1 | 10000 μs | 10000 μs |
| app_loop | 100 | 6000 μs | 60 μs |
| calculate | 100 | 4000 μs | 40 μs |
Interpretation:
- Calls = number of times function was called
- Total = cumulative time across all calls
- Avg = total / calls
- Min/Max = shortest/longest single execution
Troubleshooting
"Failed to connect to /dev/ttyUSB0"
Possible causes:
- Wrong port name
- Port in use by another application
- Insufficient permissions
Solutions:
# Linux: Check permissions
ls -l /dev/ttyUSB0
sudo chmod 666 /dev/ttyUSB0
# Or add user to dialout group
sudo usermod -a -G dialout $USER
# Log out and back in
# Check if port is in use
lsof | grep ttyUSB0
No Data Appearing
Check:
- Is profiling started? (Click "Start Profiling")
- Is embedded device actually profiling?
- Is UART configured correctly on embedded side?
- Check baud rate matches on both sides
- Look for errors in browser console (F12)
CRC Errors in Console
Possible causes:
- Baud rate mismatch
- Electrical noise on UART lines
- Cable issues
Solutions:
- Verify baud rate configuration
- Use shielded cable
- Add delays in embedded UART transmission
- Reduce baud rate to 57600
Buffer Overflows
Symptoms:
buffer_overflowscounter > 0 in device status- Missing profiling data
Solutions:
- Increase baud rate (460800 or 921600)
- Increase embedded ring buffer size
- Reduce instrumentation (exclude more files)
- Use sampling mode (future feature)
Symbols Not Resolved
Symptoms:
- Function names show as
func_0x08000XXXorunknown_0x08000XXX
Solutions:
- Provide path to
.elffile in connection settings - Ensure
.elffile has debug symbols (-gflag) - Verify
.elffile matches firmware on device - Check build ID in metadata matches
Web Interface Not Loading
Check:
- Is server running? Look for "Starting web server..." message
- Correct URL? Should be
http://localhost:5000 - Port already in use? Try different port:
miniprofiler --port 8080 - Firewall blocking? Add exception for Python/Flask
Next Steps
For Development
- Read PROTOCOL.md to understand the communication protocol
- Review the code in
host/miniprofiler/to customize behavior - Modify visualizations in
host/web/
For Embedded Integration
- Wait for Phase 2 implementation of embedded module
- Or start implementing based on protocol specification
- See examples in
embedded/directory (coming soon)
For Testing
- Create custom sample data with
sample_data_generator.py - Test with Renode emulation (Phase 4)
- Benchmark overhead on real hardware
Support
- Documentation: See
docs/directory - Issues: Open an issue on GitHub
- Examples: Check
examples/directory (coming soon)
What's Next?
After getting familiar with the host application:
- Phase 2: Implement embedded module for STM32
- Phase 3: Test on real hardware
- Phase 4: Set up Renode emulation for automated testing
Stay tuned for updates!