- Intelligent hardware detection and analysis - Modular optimization system with profiles - Automatic tmpfs, zram, and kernel tuning - Real-time monitoring and health checks - Support for desktop, gaming, and development workloads - Safe backup and rollback capabilities - Systemd integration for persistent optimizations
286 lines
9.3 KiB
Bash
Executable File
286 lines
9.3 KiB
Bash
Executable File
#!/bin/bash
|
|
# Usage Analysis Module
|
|
# Analyzes file access patterns and cache usage
|
|
|
|
analyze_usage_patterns() {
|
|
local output_file="${1:-/dev/stdout}"
|
|
local analysis_duration="${2:-300}" # 5 minutes default
|
|
|
|
log "Analyzing file access patterns (duration: ${analysis_duration}s)..."
|
|
|
|
# Create temporary files for analysis
|
|
local temp_dir="/tmp/usage-analysis-$$"
|
|
mkdir -p "$temp_dir"
|
|
|
|
# Start monitoring file access
|
|
start_file_access_monitoring "$temp_dir" "$analysis_duration" &
|
|
local monitor_pid=$!
|
|
|
|
# Analyze current cache usage
|
|
analyze_current_cache_usage "$temp_dir"
|
|
|
|
# Analyze browser usage
|
|
analyze_browser_usage "$temp_dir"
|
|
|
|
# Analyze development tools usage
|
|
analyze_development_usage "$temp_dir"
|
|
|
|
# Wait for file access monitoring to complete
|
|
wait $monitor_pid 2>/dev/null || true
|
|
|
|
# Compile results
|
|
compile_usage_analysis "$temp_dir" "$output_file"
|
|
|
|
# Cleanup
|
|
rm -rf "$temp_dir"
|
|
}
|
|
|
|
start_file_access_monitoring() {
|
|
local temp_dir="$1"
|
|
local duration="$2"
|
|
|
|
# Monitor file access using inotifywait if available
|
|
if command -v inotifywait >/dev/null 2>&1; then
|
|
timeout "$duration" inotifywait -m -r /home --format '%w%f %e' \
|
|
-e access,modify,create,delete \
|
|
2>/dev/null > "$temp_dir/file_access.log" || true
|
|
else
|
|
# Fallback: use find to detect recently accessed files
|
|
find /home -type f -atime -1 2>/dev/null > "$temp_dir/recent_files.log" || true
|
|
fi
|
|
}
|
|
|
|
analyze_current_cache_usage() {
|
|
local temp_dir="$1"
|
|
|
|
{
|
|
echo "=== CURRENT CACHE ANALYSIS ==="
|
|
|
|
# Browser caches
|
|
echo "Browser cache sizes:"
|
|
find /home -type d \( -name "*cache*" -o -name "*Cache*" \) \
|
|
-path "*/.mozilla/*" -o -path "*/.config/google-chrome/*" \
|
|
-o -path "*/.config/chromium/*" -o -path "*/.cache/mozilla/*" \
|
|
2>/dev/null | while read -r dir; do
|
|
if [[ -d "$dir" ]]; then
|
|
size=$(du -sh "$dir" 2>/dev/null | cut -f1)
|
|
echo " $dir: $size"
|
|
fi
|
|
done
|
|
|
|
echo ""
|
|
echo "System caches:"
|
|
|
|
# Package manager caches
|
|
[[ -d /var/cache/apt ]] && echo " APT cache: $(du -sh /var/cache/apt 2>/dev/null | cut -f1)"
|
|
[[ -d /var/cache/pacman ]] && echo " Pacman cache: $(du -sh /var/cache/pacman 2>/dev/null | cut -f1)"
|
|
[[ -d /var/cache/yum ]] && echo " YUM cache: $(du -sh /var/cache/yum 2>/dev/null | cut -f1)"
|
|
|
|
# User application caches
|
|
find /home -maxdepth 3 -type d -name ".cache" 2>/dev/null | while read -r cache_dir; do
|
|
if [[ -d "$cache_dir" ]]; then
|
|
size=$(du -sh "$cache_dir" 2>/dev/null | cut -f1)
|
|
echo " User cache ($cache_dir): $size"
|
|
fi
|
|
done
|
|
|
|
} > "$temp_dir/cache_analysis.txt"
|
|
}
|
|
|
|
analyze_browser_usage() {
|
|
local temp_dir="$1"
|
|
|
|
{
|
|
echo "=== BROWSER USAGE ANALYSIS ==="
|
|
|
|
# Firefox profiles
|
|
find /home -path "*/.mozilla/firefox/*/prefs.js" 2>/dev/null | while read -r prefs_file; do
|
|
profile_dir=$(dirname "$prefs_file")
|
|
profile_name=$(basename "$profile_dir")
|
|
size=$(du -sh "$profile_dir" 2>/dev/null | cut -f1)
|
|
last_used=$(stat -c %Y "$prefs_file" 2>/dev/null || echo "0")
|
|
last_used_human=$(date -d "@$last_used" 2>/dev/null || echo "unknown")
|
|
|
|
echo "Firefox profile: $profile_name"
|
|
echo " Size: $size"
|
|
echo " Last used: $last_used_human"
|
|
echo " Path: $profile_dir"
|
|
echo ""
|
|
done
|
|
|
|
# Chrome/Chromium profiles
|
|
find /home -path "*/.config/google-chrome/*/Preferences" -o \
|
|
-path "*/.config/chromium/*/Preferences" 2>/dev/null | while read -r prefs_file; do
|
|
profile_dir=$(dirname "$prefs_file")
|
|
browser_type=$(echo "$profile_dir" | grep -o -E "(google-chrome|chromium)")
|
|
profile_name=$(basename "$profile_dir")
|
|
size=$(du -sh "$profile_dir" 2>/dev/null | cut -f1)
|
|
last_used=$(stat -c %Y "$prefs_file" 2>/dev/null || echo "0")
|
|
last_used_human=$(date -d "@$last_used" 2>/dev/null || echo "unknown")
|
|
|
|
echo "$browser_type profile: $profile_name"
|
|
echo " Size: $size"
|
|
echo " Last used: $last_used_human"
|
|
echo " Path: $profile_dir"
|
|
echo ""
|
|
done
|
|
|
|
} > "$temp_dir/browser_analysis.txt"
|
|
}
|
|
|
|
analyze_development_usage() {
|
|
local temp_dir="$1"
|
|
|
|
{
|
|
echo "=== DEVELOPMENT TOOLS ANALYSIS ==="
|
|
|
|
# VS Code
|
|
find /home -path "*/.vscode/extensions" -o \
|
|
-path "*/.config/Code/CachedData" 2>/dev/null | while read -r vscode_dir; do
|
|
size=$(du -sh "$vscode_dir" 2>/dev/null | cut -f1)
|
|
echo "VS Code data: $size ($vscode_dir)"
|
|
done
|
|
|
|
# Node.js caches
|
|
find /home -name "node_modules" -type d 2>/dev/null | head -10 | while read -r node_dir; do
|
|
size=$(du -sh "$node_dir" 2>/dev/null | cut -f1)
|
|
echo "Node modules: $size ($node_dir)"
|
|
done
|
|
|
|
# Python caches
|
|
find /home -name "__pycache__" -type d 2>/dev/null | wc -l | xargs echo "Python cache directories:"
|
|
|
|
# Docker (if accessible)
|
|
if [[ -d /var/lib/docker ]] && command -v docker >/dev/null 2>&1; then
|
|
docker_size=$(du -sh /var/lib/docker 2>/dev/null | cut -f1 || echo "unknown")
|
|
echo "Docker data: $docker_size"
|
|
fi
|
|
|
|
# Git repositories
|
|
find /home -name ".git" -type d 2>/dev/null | wc -l | xargs echo "Git repositories found:"
|
|
|
|
} > "$temp_dir/development_analysis.txt"
|
|
}
|
|
|
|
compile_usage_analysis() {
|
|
local temp_dir="$1"
|
|
local output_file="$2"
|
|
|
|
# Calculate recommendations based on analysis
|
|
local total_browser_cache=0
|
|
local total_dev_cache=0
|
|
local total_system_cache=0
|
|
|
|
# Parse cache sizes and convert to MB for calculations
|
|
if [[ -f "$temp_dir/cache_analysis.txt" ]]; then
|
|
total_browser_cache=$(grep -E "(firefox|chrome|chromium)" "$temp_dir/cache_analysis.txt" | \
|
|
grep -oE "[0-9.]+[KMG]" | sed 's/G/*1024/g;s/M/*1/g;s/K\/1024/g' | bc -l 2>/dev/null | \
|
|
awk '{sum+=$1} END {print int(sum)}' || echo "0")
|
|
fi
|
|
|
|
cat > "$output_file" << EOF
|
|
{
|
|
"analysis_timestamp": "$(date -Iseconds)",
|
|
"cache_usage": {
|
|
"browser_cache_mb": $total_browser_cache,
|
|
"development_cache_mb": $total_dev_cache,
|
|
"system_cache_mb": $total_system_cache
|
|
},
|
|
"recommendations": {
|
|
"browser_tmpfs_size": "$(recommend_browser_tmpfs_size $total_browser_cache)",
|
|
"development_tmpfs_size": "$(recommend_dev_tmpfs_size $total_dev_cache)",
|
|
"priority_directories": $(generate_priority_directories "$temp_dir")
|
|
},
|
|
"frequent_paths": $(analyze_frequent_paths "$temp_dir"),
|
|
"optimization_score": $(calculate_optimization_potential "$temp_dir")
|
|
}
|
|
EOF
|
|
}
|
|
|
|
recommend_browser_tmpfs_size() {
|
|
local current_mb=$1
|
|
|
|
if [[ $current_mb -gt 2048 ]]; then
|
|
echo "4G"
|
|
elif [[ $current_mb -gt 1024 ]]; then
|
|
echo "2G"
|
|
elif [[ $current_mb -gt 512 ]]; then
|
|
echo "1G"
|
|
else
|
|
echo "512M"
|
|
fi
|
|
}
|
|
|
|
recommend_dev_tmpfs_size() {
|
|
local current_mb=$1
|
|
|
|
if [[ $current_mb -gt 1024 ]]; then
|
|
echo "2G"
|
|
elif [[ $current_mb -gt 512 ]]; then
|
|
echo "1G"
|
|
else
|
|
echo "512M"
|
|
fi
|
|
}
|
|
|
|
generate_priority_directories() {
|
|
local temp_dir="$1"
|
|
|
|
# Generate JSON array of priority directories for tmpfs
|
|
cat << 'EOF'
|
|
[
|
|
{"path": "/var/cache/apt", "type": "package_cache", "priority": "high"},
|
|
{"path": "~/.cache", "type": "user_cache", "priority": "medium"},
|
|
{"path": "~/.mozilla/firefox/*/storage", "type": "browser_storage", "priority": "high"},
|
|
{"path": "~/.config/google-chrome/*/storage", "type": "browser_storage", "priority": "high"},
|
|
{"path": "~/.vscode/extensions", "type": "ide_extensions", "priority": "medium"}
|
|
]
|
|
EOF
|
|
}
|
|
|
|
analyze_frequent_paths() {
|
|
local temp_dir="$1"
|
|
|
|
if [[ -f "$temp_dir/file_access.log" ]]; then
|
|
# Parse inotify log to find most accessed paths
|
|
awk '{print $1}' "$temp_dir/file_access.log" | \
|
|
sort | uniq -c | sort -nr | head -10 | \
|
|
jq -R -s 'split("\n") | map(select(length > 0)) | map(split(" ") | {count: .[0], path: .[1]})'
|
|
else
|
|
echo "[]"
|
|
fi
|
|
}
|
|
|
|
calculate_optimization_potential() {
|
|
local temp_dir="$1"
|
|
local score=0
|
|
|
|
# Base score calculation
|
|
local ram_gb=$(free -g | awk '/^Mem:/{print $2}')
|
|
|
|
# More RAM = higher potential
|
|
if [[ $ram_gb -gt 16 ]]; then
|
|
score=$((score + 40))
|
|
elif [[ $ram_gb -gt 8 ]]; then
|
|
score=$((score + 30))
|
|
else
|
|
score=$((score + 20))
|
|
fi
|
|
|
|
# Check for existing optimizations
|
|
if mount | grep -q "tmpfs.*cache"; then
|
|
score=$((score + 10))
|
|
fi
|
|
|
|
if [[ -e /dev/zram0 ]]; then
|
|
score=$((score + 15))
|
|
fi
|
|
|
|
# Check for large caches that could benefit from tmpfs
|
|
if [[ -f "$temp_dir/cache_analysis.txt" ]]; then
|
|
local large_caches=$(grep -c "[0-9][0-9][0-9]M\|[0-9]G" "$temp_dir/cache_analysis.txt" 2>/dev/null || echo "0")
|
|
score=$((score + large_caches * 5))
|
|
fi
|
|
|
|
echo $score
|
|
} |