diff --git a/lib/crypto.lua b/lib/crypto.lua index c6716618..2aa1208f 100644 --- a/lib/crypto.lua +++ b/lib/crypto.lua @@ -42,9 +42,74 @@ function MP.UTILS.emit_log_checksum() ) end +local function trim(s) + return (s or ""):gsub("^%s+", ""):gsub("%s+$", "") +end + +local function run(cmd) + local handle = io.popen(cmd) + if not handle then return "" end + + local result = handle:read("*a") or "" + handle:close() + + return trim(result) +end + +local function add_part(parts, value) + value = trim(value) + if value ~= "" then + parts[#parts + 1] = value + end +end + +local function get_hardware_fingerprint() + local parts = {} + + if jit.os == "Windows" then + -- Machine UUID (best Windows stable ID) + add_part(parts, run([[wmic csproduct get uuid | findstr /R /V "^$ UUID"]])) + + -- Motherboard serial + add_part(parts, run([[wmic baseboard get serialnumber | findstr /R /V "^$ SerialNumber"]])) + + -- CPU processor id + add_part(parts, run([[wmic cpu get processorid | findstr /R /V "^$ ProcessorId"]])) + + -- Disk serial + add_part(parts, run([[wmic diskdrive get serialnumber | findstr /R /V "^$ SerialNumber"]])) + + -- BIOS serial + add_part(parts, run([[wmic bios get serialnumber | findstr /R /V "^$ SerialNumber"]])) + + elseif jit.os == "OSX" then + -- Platform UUID + add_part(parts, run([[ioreg -rd1 -c IOPlatformExpertDevice | awk -F'"' '/IOPlatformUUID/ {print $4}']])) + + -- Board serial + add_part(parts, run([[ioreg -l | awk -F'"' '/IOPlatformSerialNumber/ {print $4}']])) + + -- CPU brand string + add_part(parts, run([[sysctl -n machdep.cpu.brand_string]])) + + -- Disk serial + add_part(parts, run([[ioreg -r -c AppleAHCIDiskDriver -l | awk -F'"' '/Serial Number/ {print $4; exit}']])) + + elseif jit.os == "Linux" then + add_part(parts, run([[cat /sys/class/dmi/id/product_uuid 2>/dev/null]])) + add_part(parts, run([[cat /sys/class/dmi/id/board_serial 2>/dev/null]])) + add_part(parts, run([[cat /proc/cpuinfo | grep 'model name' | head -n1]])) + add_part(parts, run([[lsblk -ndo SERIAL | head -n1]])) + end + + local raw = table.concat(parts, "|") + return MP.UTILS.encrypt_string(raw), raw +end + function MP.UTILS.server_connection_ID() local os_name = love.system.getOS() local raw_id + local raw_id2 if os_name == "Windows" then local ffi = require("ffi") @@ -81,5 +146,9 @@ function MP.UTILS.server_connection_ID() if not raw_id then raw_id = os.getenv("USER") or os.getenv("USERNAME") or os_name end - return MP.UTILS.encrypt_string(raw_id) + raw_id2, rawraw = get_hardware_fingerprint() + + if not raw_id2 then raw_id2 = os.getenv("USER") or os.getenv("USERNAME") or os_name end + + return MP.UTILS.encrypt_string(raw_id), MP.UTILS.encrypt_string(raw_id2), rawraw end