|
Using Git in Hardware Projects: Practical Guide for Schematic/PCB Version Control

Using Git in Hardware Projects: Practical Guide for Schematic/PCB Version Control

Why Do Hardware Projects Need Git?

Software folks might not understand: isn’t hardware design just drawing schematics and laying out boards? Why do you need version control?

Until one day, you change a resistor value, find the board doesn’t work, want to revert but can’t find the original file; or when collaborating, two people modify the schematic at the same time, and in the end you don’t know whose version to use…

That’s when you understand: hardware design is also code, and it also needs version management.

Today we’ll talk about how to use Git to manage hardware projects, especially files generated by EDA tools like KiCad and Eagle.

What Do You Need?

ItemModel/SpecPrice
ComputerAny Linux/Mac/WindowsAlready have
EDA ToolKiCad 7.x (recommended)Free
GitVersion 2.x or aboveFree
Code HostingGitHub/GiteeFree
Total¥0

Yes, this toolchain is completely free! KiCad is an open-source EDA tool, Git is also open-source, and GitHub personal repositories are free.

Step 1: Git Basic Configuration

First install Git (if not already installed):

# Ubuntu/Debian
sudo apt-get update
sudo apt-get install git

# macOS
brew install git

# Windows
# Download from https://git-scm.com/download/win

Configure your identity information:

git config --global user.name "Your Name"
git config --global user.email "your.email@example.com"

# Recommended: Set default branch to main
git config --global init.defaultBranch main

# Recommended: Enable colored output
git config --global color.ui auto

Step 2: Git Structure for Hardware Projects

Hardware projects have a big difference from software projects: there are many binary files (Gerber, PDF, 3D models, etc.). These files aren’t suitable for diff comparison, but need version tracking.

Recommended project structure:

my-hardware-project/
├── .gitignore          # Git ignore file configuration
├── README.md           # Project description
├── docs/               # Documentation
│   ├── BOM.md          # Bill of materials
│   └── assembly.md     # Assembly instructions
├── hardware/           # Hardware design files
│   ├── schematic/      # Schematics
│   │   └── project.kicad_sch
│   ├── pcb/            # PCB layout
│   │   └── project.kicad_pcb
│   └── lib/            # Component libraries
├── firmware/           # Firmware code
│   └── src/
├── gerber/             # Generated Gerber files
└── 3d-models/          # 3D model files

Step 3: Write .gitignore

This is the most critical step! EDA tools generate many temporary files and backup files, we don’t need to track them.

Example .gitignore for KiCad projects:

# KiCad auto-generated backup files
*-backup.kicad_sch
*-backup.kicad_pcb
*.kicad_sch-bak
*.kicad_pcb-bak

# KiCad cache and temporary files
cache/
tmp/
*.cache

# Auto-generated output files (optional, depends on team needs)
gerber/
production/
*.pdf
*.step
*.wrl

# Editor temporary files
.vscode/
.idea/
*.swp
*.swo
*~

# Operating system files
.DS_Store
Thumbs.db

Note: Whether to include Gerber files in version control depends on your team’s strategy. If every commit includes Gerber, the repository will grow large; if not included, you need to regenerate for each release. My suggestion is: don’t commit Gerber during development, generate and attach them when tagging releases.

Step 4: Initialize Repository and Commit

# Create project directory
mkdir my-hardware-project
cd my-hardware-project

# Initialize Git repository
git init

# Create .gitignore
cat > .gitignore << 'EOF'
*-backup.kicad_sch
*-backup.kicad_pcb
*.kicad_sch-bak
*.kicad_pcb-bak
cache/
tmp/
*.cache
gerber/
production/
*.pdf
*.step
*.wrl
.vscode/
.idea/
*.swp
*.swo
*~
.DS_Store
Thumbs.db
EOF

# Create README.md
cat > README.md << 'EOF'
# My Hardware Project

## Description
Brief project description

## Hardware
- MCU: STM32F103C8T6
- Power: 5V USB
- Communication: UART, I2C, SPI

## Directory Structure
- `hardware/schematic/` - Schematic files
- `hardware/pcb/` - PCB layout files
- `firmware/` - Firmware source code
- `docs/` - Documentation

## Version History
- v1.0 (2024-01-15) - Initial release
EOF

# Add all files
git add .

# First commit
git commit -m "Initial commit: project structure and basic design"

# Create version tag
git tag -a v1.0 -m "Version 1.0: Initial design complete"

Step 5: Daily Workflow

Branch Strategy

Hardware projects can use a simplified branching strategy:

# Main branch - stable version
main

# Development branch - active development
develop

# Feature branch - specific feature development
feature/power-supply
feature/communication-module

# Fix branch - bug fixes
fix/revision-b-spi-issue

Daily workflow:

# Create development branch
git checkout -b develop

# Create feature branch
git checkout -b feature/power-supply

# Complete development, merge to develop
git checkout develop
git merge feature/power-supply

# Merge to main after testing
git checkout main
git merge develop

# Create release tag
git tag -a v1.1 -m "Version 1.1: Power supply optimization"

Commit Message Specification

Hardware project commit messages should include:

  1. What changed (which file, which module)
  2. Why change (fix bug, optimize performance, add feature)
  3. Impact (affects which function, needs retesting?)

Good example:

git commit -m "Optimize power supply circuit: C3 capacitor changed from 100nF to 1μF

Reason: Testing found 50mV ripple on 3.3V power rail
Impact: Power supply noise reduced to <10mV, no need to retest other functions"

Bad example:

Update PCB

Step 6: Handling Binary Files

KiCad’s .kicad_pcb files are essentially text format (S-expressions), so they can be diffed. But some files are pure binary (like 3D models, images).

Viewing PCB File Differences

# KiCad PCB files can be directly viewed with git diff
git diff hardware/pcb/project.kicad_pcb

# Example output:
- (segment (start 100 100) (end 150 100) (width 0.25) (layer "F.Cu"))
+ (segment (start 100 100) (end 150 100) (width 0.5) (layer "F.Cu"))

You can see the trace width changed from 0.25mm to 0.5mm.

Git LFS Support for Binary Files

If the project has many large files (3D models, high-resolution images), it’s recommended to use Git LFS:

# Install Git LFS
git lfs install

# Track large file types
git lfs track "*.step"
git lfs track "*.wrl"
git lfs track "*.png"

# This modifies the .gitattributes file
git add .gitattributes
git commit -m "Configure Git LFS to track 3D models and images"

Note: GitHub free accounts have a 1GB LFS quota, you need to pay for more.

Step 7: Team Collaboration and Code Review

Using Pull Request/Merge Request

  1. Create a team repository on GitHub/Gitee, set branch protection rules (like main branch prohibits direct push)

  2. Members pull feature branches from main for development, create Pull Request when done

  3. Designate at least one team member for code review, focusing on schematic changes and PCB routing modifications

  4. Resolve all review comments before merging, ensure KiCad files can be opened normally

  5. Delete feature branch after merging, keep the repository clean

KiCad can export schematics to PDF for review:

# Export schematic to PDF
kicad-cli sch export pdf \
  -o docs/schematic-v1.2.pdf \
  hardware/schematic/project.kicad_sch

# Attach PDF to PR description for review

Or use KiCad’s “Compare Schematics” feature to visually view differences between two versions.

Common Problem Troubleshooting

Problem 1: KiCad files can’t be opened after commit

  • Cause: May be file encoding issue or incomplete commit

  • Solution: Ensure .kicad_sch and .kicad_pcb files are completely committed, don’t split; use git lfs to track large files

Problem 2: How to handle merge conflicts?

  • Cause: Two people modified the same file simultaneously

  • Solution:

Open the conflict file in a text editor

  • Find >>>>>> markers

  • Manually select which changes to keep

  • Open and verify in KiCad

  • Commit the resolved file

  • Prevention: Clear division of work among team members, avoid modifying the same module simultaneously

Problem 3: Repository is too large

  • Cause: Committed too many large files or accumulated historical versions

  • Solution:

# Check repository size
git count-objects -vH

# Clean unreferenced objects
git gc --prune=now

# If output files like Gerber are too large, remove from history
git filter-branch --tree-filter 'rm -rf gerber/' HEAD

Problem 4: How to revert to a previous version?

  • Solution:
# View commit history
git log --oneline

# Revert to a specific commit (keep working directory changes)
git checkout <commit-hash>

# Or create a revert commit
git revert <commit-hash>

Summary

Benefits of using Git to manage hardware projects:

  1. All design changes have complete history, can revert to any version anytime

  2. No more conflicts in team collaboration, each person has their own branch, unified review when merging

  3. Commit messages record the reasons for design decisions, making it easier for successors to understand “why this change was made”

  4. Mark Gerber files for each release with tags, ready for production

  5. Use PR/MR mechanism for design review, reducing low-level errors reaching production

  • Write a clear .gitignore to avoid committing temporary files

  • Commit messages should be detailed, explaining “what changed” and “why”

  • Use Git LFS for large files

  • Generate output files like Gerber at release time, mark with tags

  • Regularly run git gc to clean the repository

Hope this blog article is helpful to you!


Related resources:

  • Git official documentation

  • KiCad version control best practices

  • Git LFS usage guide

  • GitHub hardware project examples