Last active
August 30, 2022 10:04
-
-
Save suzumura-ss/7fe3e4959322e463cf02d2681ce5568a to your computer and use it in GitHub Desktop.
Detect confricted IPs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env node | |
// eth0とdocker0がコンフリクトすると docker run によるコンテナが異常になる | |
// eth0とbr-xxxxがコンフリクトすると docker compose によるコンテナが異常になる | |
const { execSync } = require('child_process'); | |
function ipAddr () { | |
if (process.env.NODE_ENV === 'test') { | |
return [ | |
'inet 172.17.53.125/20 brd 172.17.63.255 scope global eth0', | |
'inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0', | |
'inet 172.19.0.1/16 brd 172.19.255.255 scope global br-xxyyzzaabbcc', | |
'inet 172.18.0.1/16 brd 172.18.255.255 scope global br-ddeeffgghhii' | |
]; | |
} | |
return execSync('ip addr|grep global').toString().split(/[\r\n]+/); | |
} | |
function getMask (bits) { | |
const mbits = 32n - bits; | |
return (0xfffffffn >> mbits) << mbits; | |
} | |
function min_n (...values) { | |
return values.reduce((sum, v) => { | |
if (v < sum) return v; | |
return sum; | |
}, values[0]); | |
} | |
function resolveRange (str) { | |
const bits = BigInt(str.split('/')[1]); | |
const mask = getMask(bits); | |
const addr = str.split('/')[0].split('.').map(v => BigInt(v)) | |
.reduce((sum, v) => { | |
sum = sum << 8n; | |
sum += v; | |
return sum; | |
}, 0n); | |
const range = addr & mask; | |
return { addr, range, bits }; | |
} | |
const IPs = ipAddr() | |
.map(line => line.trim().split(/ +/).filter((_v, i) => [1, 6].includes(i))) | |
.filter(line => line[1]?.match(/^(eth|docker|br-)/)) | |
.reduce((sum, v) => { | |
const [token, name] = v; | |
const range = resolveRange(token); | |
sum[name] = { ...range, token }; | |
return sum; | |
}, {}); | |
const minMask = getMask(min_n(...Object.values(IPs).map(v => v.bits))); | |
const eth0 = IPs.eth0.addr & minMask; | |
const confricted = Object.keys(IPs).filter(key => key !== 'eth0').reduce((sum, key) => { | |
if (eth0 === (IPs[key].addr & minMask)) { | |
console.log(`eth0 [${IPs.eth0.token}] and ${key} [${IPs[key].token}] is CONFRICTED.`); | |
return 1; | |
} | |
return sum; | |
}, 0); | |
if (process.argv.includes('-v')) { | |
console.log(IPs); | |
} | |
process.exit(confricted); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment