Overview
Bytecode Viewer is a comprehensive Java reverse engineering tool that combines multiple decompiler backends (Procyon, CFR, JD-GUI, Fernflower, and others) into a single interface. It supports analysis of JAR files, Android APKs, and raw Java class files. The tool enables researchers and security professionals to decompile, disassemble, and analyze Java bytecode across multiple formats and decompilers simultaneously.
Installation
Windows
# Download latest release
# https://github.com/Konloch/bytecode-viewer/releases
# Extract ZIP file
unzip Bytecode-Viewer-x.x.x-all.zip -d C:\BytecodeViewer
# Run the application
C:\BytecodeViewer\Bytecode Viewer.exe
# Or via command line
java -jar "Bytecode Viewer.jar"
Linux
# Install dependencies
sudo apt-get update
sudo apt-get install -y openjdk-11-jdk git wget
# Download latest JAR
wget https://github.com/Konloch/bytecode-viewer/releases/download/v2.x.x/Bytecode-Viewer-v2.x.x.jar
# Run the application
java -jar Bytecode-Viewer-v2.x.x.jar
# Or clone and build from source
git clone https://github.com/Konloch/bytecode-viewer.git
cd bytecode-viewer
gradle build
java -jar build/libs/Bytecode-Viewer-all.jar
macOS
# Install Java via Homebrew
brew install openjdk
# Download Bytecode Viewer
wget https://github.com/Konloch/bytecode-viewer/releases/download/v2.x.x/Bytecode-Viewer-v2.x.x.jar
# Run the application
java -jar Bytecode-Viewer-v2.x.x.jar
# Add to Applications folder
cp Bytecode-Viewer-v2.x.x.jar ~/Applications/
Docker
# Build Docker image
docker build -t bytecode-viewer:latest .
# Run with GUI (requires X11 forwarding)
docker run -e DISPLAY=$DISPLAY -v /tmp/.X11-unix:/tmp/.X11-unix \
-v /path/to/jars:/data bytecode-viewer:latest
# Run headless analysis
docker run -v /path/to/jars:/data bytecode-viewer:latest \
java -jar Bytecode-Viewer.jar --file /data/target.jar --decompiler cfr
Opening Files
Load JAR Files
# GUI method:
# File → Open → Select JAR file
# Command line (via Gradle plugin):
java -jar Bytecode-Viewer.jar --file target.jar
# Open multiple JAR files
java -jar Bytecode-Viewer.jar --file file1.jar --file file2.jar
# Open with specific decompiler
java -jar Bytecode-Viewer.jar --file target.jar --decompiler cfr
# Open and search
java -jar Bytecode-Viewer.jar --file target.jar --search "Main"
Load Class Files
# Open individual class files
# File → Open → Select .class file
# Batch process class files
for file in *.class; do
java -jar Bytecode-Viewer.jar --file "$file" --export-as java
done
# Extract classes from JAR first
unzip target.jar "*.class" -d extracted_classes/
Load APK Files
# GUI method:
# File → Open → Select APK file
# Automatic decompilation of APK
java -jar Bytecode-Viewer.jar --file app.apk
# APK requires DEX to JAR conversion
d2j-dex2jar classes.dex
java -jar Bytecode-Viewer.jar --file classes-dex2jar.jar
# One-liner APK processing
unzip app.apk -d apk_extracted/ && \
d2j-dex2jar apk_extracted/classes.dex && \
java -jar Bytecode-Viewer.jar --file classes-dex2jar.jar
Decompiler Selection
Available Decompilers
| Decompiler | Strengths | Use Case |
|---|
| CFR | Modern Java features, lambdas, records | Latest Java code analysis |
| Procyon | Clean output, Java 8+ support | General purpose decompilation |
| JD-GUI | Classic, readable output | Traditional analysis |
| Fernflower | JetBrains official, accurate | Production code analysis |
| Krakatau | Python-based, detailed analysis | Research and academic |
| Javassist | Bytecode manipulation | Direct bytecode inspection |
Switch Between Decompilers
# GUI method:
# View → Decompilers → Select decompiler
# Compare all decompilers at once
# View → Display results from all decompilers simultaneously
# Command line decompiler selection
java -jar Bytecode-Viewer.jar --file target.jar --decompiler cfr
# Test multiple decompilers
for decompiler in cfr procyon jd-gui fernflower; do
echo "=== Testing $decompiler ==="
java -jar Bytecode-Viewer.jar --file target.jar --decompiler $decompiler
done
CFR Decompiler
# CFR specializes in modern Java features
# - Lambda expressions
# - Try-with-resources
# - Records
# - Sealed classes
# - Pattern matching
# Configure CFR options
java -jar Bytecode-Viewer.jar --file target.jar --decompiler cfr \
--decompiler-options "decodeenumswitch=true,decodefinally=true"
# Export CFR output
java -jar Bytecode-Viewer.jar --file target.jar --decompiler cfr \
--export-as java --output cfr_output/
Procyon Decompiler
# Procyon features clean syntax
# - Variable name recovery
# - Type inference
# - Exception handling
# - Annotation support
# Run Procyon decompilation
java -jar Bytecode-Viewer.jar --file target.jar --decompiler procyon
# Procyon command line (if installed separately)
java -jar procyon.jar target.jar -o output/
# Combine with Bytecode Viewer
java -jar Bytecode-Viewer.jar --file target.jar --decompiler procyon \
--export-as java
JD-GUI Decompiler
# JD-GUI provides traditional Java decompilation
# - Long history
# - Stable output
# - Good error handling
# Select JD-GUI in Bytecode Viewer
# View → Decompilers → JD-GUI
# Configuration options
java -jar Bytecode-Viewer.jar --file target.jar --decompiler jd-gui \
--decompiler-options "showDefaultValues=true"
Fernflower Decompiler
# Fernflower is JetBrains official decompiler
# - Production quality
# - Used in IntelliJ IDEA
# - Accurate bytecode analysis
# Use Fernflower decompilation
java -jar Bytecode-Viewer.jar --file target.jar --decompiler fernflower
# Fernflower standalone usage
java -jar fernflower.jar source.jar output/
# Advanced options
java -jar Bytecode-Viewer.jar --file target.jar --decompiler fernflower \
--decompiler-options "rbr=false,cfo=true"
Disassembly View
Display Bytecode Instructions
# GUI method:
# View → Bytecode (Disassembly tab)
# Show JVM instructions
# Right-click class → Show Bytecode
# Display with line numbers
# View → Show line numbers (checked)
# Color-coded bytecode
# View → Syntax highlighting (ON)
| View Type | Content |
|---|
| Disassembly | JVM bytecode instructions |
| Hex | Raw hexadecimal dump |
| Javap | Official javap tool output |
| Procyon | Procyon decompiled code |
| CFR | CFR decompiled code |
| Decompiled | Human-readable Java code |
Export Bytecode
# Export bytecode view
# View → Bytecode → Right-click → Copy
# Save bytecode to file
java -jar Bytecode-Viewer.jar --file target.jar --export-as bytecode \
--output bytecode_output/
# Generate javap output
javap -v -cp target.jar ClassName > output.txt
# Disassembler command line
java -jar Bytecode-Viewer.jar --file target.jar --show-bytecode \
--export-as javap
Code Searching
Find Classes and Methods
# GUI search method:
# Edit → Find (Ctrl+F)
# Search for specific class
# Type class name in search field → Enter
# Search for method names
# Type method name → Filter results
# Regular expression search
# Enable regex option → Search pattern.*
Advanced Searching
| Search Type | Syntax | Example |
|---|
| Class name | ClassName | MainActivity |
| Method name | methodName | onCreate |
| Package | package.* | com.example.* |
| String literal | "text" | "password" |
| Regex pattern | ^class.* | ^Test.* |
Search Examples
# Find all classes with Main
# Search: Main
# Result: MainActivity, MainApplication, etc.
# Find password-related code
# Search: password
# Find API calls
# Search: .execute\(
# Find reflection usage
# Search: .forName
# Find network operations
# Search: HttpClient|Socket
# Find database operations
# Search: SQLite|Database
Editing Bytecode
Bytecode Modification (Advanced)
# Edit bytecode instructions directly
# Select bytecode section → Edit
# GUI editing steps:
# 1. Open class file
# 2. Show Bytecode tab
# 3. Right-click instruction → Edit
# 4. Modify JVM instruction
# 5. Save changes
# Warning: Complex bytecode manipulation
# Verify modifications before saving
Javassist Integration
# Use Javassist for bytecode manipulation
# View → Bytecode → Use Javassist
# Javassist allows:
# - Add methods
# - Modify code
# - Insert logging
# - Change behavior
# Example javassist modification
javassist> /open target.jar
javassist> get ClassName.methodName
javassist> replace System.out.println("MODIFIED");
javassist> save target.jar
Save Modified Classes
# Export modified classes
# File → Export as JAR
# Export specific class
# Select class → Export → Save as .class
# Create new JAR with modifications
java -jar Bytecode-Viewer.jar --file target.jar \
--export-as jar --output modified.jar
# Verify modifications
javap -v modified.jar | grep "MODIFIED"
APK Analysis
Decompile Android Applications
# Extract APK contents
unzip app.apk -d apk_extracted/
# Convert DEX to JAR
d2j-dex2jar apk_extracted/classes.dex -o classes.jar
# Analyze with Bytecode Viewer
java -jar Bytecode-Viewer.jar --file classes.jar
# View manifest
cat apk_extracted/AndroidManifest.xml | xmllint --format -
# List all resources
unzip -l app.apk | grep -E "\.(xml|png|jpg)$"
# GUI method:
# Tools → Extract Strings
# Command line string extraction
strings classes.dex | grep -E "^[a-z]{3,}" | sort -u
# Search for API endpoints
strings classes.dex | grep -E "http(s)?://"
# Find hardcoded credentials
strings classes.dex | grep -iE "password|api_key|secret"
# Extract domain names
strings classes.dex | grep -E "\w+\.\w{2,}"
# Use APKTool for full APK analysis
apktool d app.apk -o apk_decompiled/
# Analyze with Bytecode Viewer in parallel
java -jar Bytecode-Viewer.jar --file app.apk
# Check for suspicious permissions
grep "android:name.*permission" apk_decompiled/AndroidManifest.xml
# Find native code references
grep "System.load\|System.loadLibrary" classes.dex
Plugin System
Available Plugins
| Plugin | Function |
|---|
| Plugin Manager | Browse and install plugins |
| Custom Decompilers | Add new decompiler backends |
| Export Filters | Custom export formats |
| Analysis Tools | Additional analysis plugins |
Install Plugins
# GUI method:
# File → Plugin Manager
# Browse available plugins
# Check official Bytecode Viewer plugin repository
# Manual plugin installation
# 1. Download .jar file
# 2. Place in plugins/ directory
# 3. Restart Bytecode Viewer
# Plugin directory location
# Windows: C:\Users\[User]\AppData\Roaming\Bytecode Viewer\plugins
# Linux: ~/.bytecode-viewer/plugins
# macOS: ~/Library/Application Support/Bytecode Viewer/plugins
Create Custom Plugin
# Plugin development requires:
# - Java IDE (IntelliJ IDEA, Eclipse)
# - Bytecode Viewer SDK
# - Plugin template
# Basic plugin structure
public class CustomPlugin extends Plugin {
@Override
public String getName() {
return "Custom Plugin";
}
@Override
public void execute(ClassNode node) {
// Custom analysis logic
}
}
# Build and deploy plugin
gradle build
cp build/libs/CustomPlugin.jar ~/.bytecode-viewer/plugins/
Comparison with Other Java Decompilers
| Tool | Pros | Cons | Best For |
|---|
| JD-GUI | User-friendly, fast | Limited to one decompiler | Quick analysis |
| Fernflower | Accurate, official | Command-line only | Production code |
| CFR | Modern features | Can be slow | Latest Java code |
| Procyon | Clean output | No longer maintained | Java 8 code |
| Krakatau | Detailed bytecode | Python-based | Research |
When to Use Bytecode Viewer
# Use Bytecode Viewer when you need:
# - Multiple decompilers comparison
# - Bytecode inspection
# - APK analysis (with DEX conversion)
# - GUI-based analysis
# - Bytecode modification
# - Plugin extensibility
# Choose alternatives when:
# - Automation is priority → Use CFR/Fernflower CLI
# - Only need one format → Use JD-GUI
# - Need research tools → Use Krakatau
# - Integration required → Use Procyon
Advanced Workflows
Malware Analysis Workflow
# 1. Open suspicious JAR/APK
java -jar Bytecode-Viewer.jar --file suspicious.apk
# 2. Check manifest (APK)
# File → Properties → View manifest
# 3. Search for suspicious patterns
# Edit → Find → "System.loadLibrary"
# Edit → Find → "Runtime.exec"
# Edit → Find → "HttpClient"
# 4. Analyze in multiple decompilers
# View → Decompilers → Select all
# 5. Export findings
# File → Export as Java
# 6. Cross-reference with YARA
yara malware.yara suspicious.apk
Code Review Workflow
# 1. Load project JAR
java -jar Bytecode-Viewer.jar --file app.jar
# 2. Review all classes
# Left panel → Expand packages
# 3. Search for security issues
# Edit → Find → "encrypt"
# Edit → Find → "password"
# Edit → Find → "sql"
# 4. Compare decompilers for accuracy
# View → Show all decompilers
# 5. Export reviewed code
# File → Export as Java
# 6. Generate report
# Tools → Analysis → Generate Report
# Search for performance bottlenecks
# Edit → Find → "synchronized"
# Edit → Find → "loop"
# Edit → Find → "sleep"
# Analyze thread usage
# Edit → Find → "Thread"
# Edit → Find → "Runnable"
# Check for memory leaks
# Edit → Find → "static"
# Edit → Find → "Cache"
# Review I/O operations
# Edit → Find → "FileInputStream"
# Edit → Find → "BufferedReader"
Export and Integration
# Export as Java source code
# File → Export → Java
# Export as JAR file
java -jar Bytecode-Viewer.jar --file target.jar \
--export-as jar --output modified.jar
# Export bytecode
# File → Export → Bytecode
# Export documentation
# Tools → Generate Javadoc
# Batch export multiple classes
java -jar Bytecode-Viewer.jar --file target.jar \
--export-all --output exported_code/
Integration with IDEs
# Import decompiled code into IntelliJ IDEA
# File → New → Project from Existing Sources
# Select exported Java directory
# Import into Eclipse
# File → Import → Existing Projects into Workspace
# Select exported code
# Create IDE project
# File → Export → Generate IDE Project
# Maven integration
# Export as Maven project structure
java -jar Bytecode-Viewer.jar --file target.jar \
--export-as maven --output project/
Troubleshooting
Common Issues
| Problem | Solution |
|---|
| Out of Memory | Increase JVM heap: java -Xmx4G -jar Bytecode-Viewer.jar |
| Class not found | Ensure all dependencies in classpath; load all JARs |
| Corrupted decompilation | Try different decompiler; check file integrity |
| APK won’t open | Convert DEX to JAR first using d2j-dex2jar |
| Slow performance | Close other decompilers; reduce display details |
| Plugins not loading | Restart application; check plugin permissions |
Debug Commands
# Verify JAR integrity
jar tf target.jar | head -20
# Check Java version
java -version
# Increase verbosity
java -jar Bytecode-Viewer.jar --file target.jar --verbose
# Check available decompilers
java -jar Bytecode-Viewer.jar --list-decompilers
# View application logs
tail -f ~/.bytecode-viewer/logs/error.log
Large File Analysis
# Increase heap for large files
java -Xmx8G -jar Bytecode-Viewer.jar
# Load specific classes only
java -jar Bytecode-Viewer.jar --file target.jar --class "com.example.*"
# Use lightweight decompiler first
java -jar Bytecode-Viewer.jar --file target.jar --decompiler procyon
# Disable unnecessary features
# View → Disable syntax highlighting
# View → Disable line numbers
Batch Processing
# Process multiple files
for jar in *.jar; do
java -jar Bytecode-Viewer.jar --file "$jar" \
--export-as java --output "${jar%.jar}/"
done
# Parallel processing with xargs
ls *.jar | xargs -P 4 -I {} \
java -jar Bytecode-Viewer.jar --file {} --export-as java
# Generate analysis reports
for jar in *.jar; do
echo "=== Analyzing $jar ===" >> analysis.txt
java -jar Bytecode-Viewer.jar --file "$jar" --analyze >> analysis.txt
done
Security Considerations
Safe Analysis
# Analyze untrusted files in isolated VM
# Use virtual machine for suspicious APKs/JARs
# Verify file integrity before analysis
sha256sum target.jar
# Compare with known hash
# Scan decompiled code for malware signatures
yara malware.yara exported_code/
# Monitor system resources during analysis
top -p $(pgrep -f Bytecode-Viewer)
Resources