diff --git a/src/js/tools.js b/src/js/tools.js index 09d5e28..cd35b73 100644 --- a/src/js/tools.js +++ b/src/js/tools.js @@ -6,6 +6,12 @@ expandInp.oninput = expandChanged; let compressInp = document.getElementById('address_to_compress'); compressInp.oninput = compressChanged; +let macToEui64Inp = document.getElementById('mac_to_eui64_in'); +macToEui64Inp.oninput = macToEui64Changed; + +let eui64ToMacInp = document.getElementById('eui64_to_mac_in'); +eui64ToMacInp.oninput = eui64ToMacChanged; + let ptrInp = document.getElementById('ptr_to_generate'); ptrInp.oninput = ptrChanged; @@ -52,6 +58,26 @@ function compressChanged(e){ } } +function macToEui64Changed(e){ + try { + $("#mac_to_eui64_out").text(encode_eui64($("#mac_to_eui64_in").val())); + $("#mac_to_eui64_in").parent().removeClass("has-warning"); + } + catch { + $("#mac_to_eui64_in").parent().addClass("has-warning"); + } +} + +function eui64ToMacChanged(e){ + try { + $("#eui64_to_mac_out").text(decode_eui64($("#eui64_to_mac_in").val())); + $("#eui64_to_mac_in").parent().removeClass("has-warning"); + } + catch { + $("#eui64_to_mac_in").parent().addClass("has-warning"); + } +} + function ptrChanged(e){ try { $("#generated_ptr").html(ptr($("#ptr_to_generate").val())); @@ -468,3 +494,32 @@ if (typeof module !== 'undefined' && typeof module.exports !== 'undefined') { window.ip6_randomSubnet = randomSubnet; window.ip6_ptr = ptr; } + +// Credits to iiidefix.net +function decode_eui64(a) { // see rfc7042 Section 2.2 + a = normalize(a).substring(20).replace(/:/g, ''); + if (a.substring(6, 10) == 'fffe') { + a = a.split(''); + a.splice(6, 4); + a[1] = (parseInt(a[1], 16) ^ 2).toString(16); + return a.join('').replace(/(..)/g, ':$1').substring(1); + } + else if (a.match(/^0[0123]005efe/)) { + return a.substring(8,16).replace(/(..)/g, x => parseInt(x, 16)+'.').replace(/\.$/, ''); + } + else throw new Error('Invalid address: ' + a); +} + +function encode_eui64(a) { + if (a.match(/^([0-9a-f]{2}[:.-]?){6}$/i)) { + a = a.replace(/[:.-]/g, '').split(""); + a.splice(6, 0, 'fffe'); + a[1] = (parseInt(a[1], 16) ^ 2).toString(16); + return abbreviate('fe80:' + a.join('').replace(/(....)/g, ':$1')); + } + else if (a.match(/^((25[0-5]|(2[0-4]|1\d|[1-9]|)\d)\.?\b){4}$/)) { + a = a.split('.').map(x => _leftPad(parseInt(x).toString(16), '0', 2)); + return abbreviate('fe80::0200:5efe'+a.join('').replace(/(....)/g, ':$1')); + } + else throw new Error('Invalid address: ' + a); +} diff --git a/src/tools.html b/src/tools.html index 03957a4..aee5e06 100644 --- a/src/tools.html +++ b/src/tools.html @@ -135,6 +135,50 @@ +
+
+
+
+

MAC to EUI-64

+
+
+ + + + + + + +
+ +
+
fe80::b79d:41ff:fee9:8d9d
+
+
+
+
+
+
+
+

EUI-64 to MAC

+
+
+ + + + + + + +
+ +
+
b5:9d:41:e9:8d:9d
+
+
+
+
+
@@ -165,4 +209,4 @@ - \ No newline at end of file +