/**
 * Copyright 2016 the WHATAP project authors. All rights reserved.
 * Use of this source code is governed by a license that
 * can be found in the LICENSE file.
 */

const empty = '0.0.0.0';
const emptyBytes = [0, 0, 0, 0];
const up10 = [1, 10, 100];
function wordToInt(w) {
    var n = 0;
    var k = Math.min(w.length, 3);
    for (i = 0; i < k; i++) {
        n += charToInt(w.charAt(i)) * up10[k - i - 1];
    }
    return n;
}
function charToInt(ch) {
    switch (ch) {
        case '0': return 0;
        case '1': return 1;
        case '2': return 2;
        case '3': return 3;
        case '4': return 4;
        case '5': return 5;
        case '6': return 6;
        case '7': return 7;
        case '8': return 8;
        case '9': return 9;
        default: return 0;
    }
}
function IPUtil() {
}
IPUtil.prototype.stringToBytes = function (ipStr) {
    try{
        if (ipStr === null || ipStr === undefined) {
            return emptyBytes;
        }
        var ipArr = ipStr.split(".");
        if (ipArr.length < 4)
            return emptyBytes;

        var buf = [0, 0, 0, 0];
        buf[0] = wordToInt(ipArr[0]) & 0xFF;
        buf[1] = wordToInt(ipArr[1]) & 0xFF;
        buf[2] = wordToInt(ipArr[2]) & 0xFF;
        buf[3] = wordToInt(ipArr[3]) & 0xFF;
        return buf;
    }catch (e) {
        return emptyBytes;
    }
}

IPUtil.prototype.stringToInt = function (ip) {
    var b = this.stringToBytes(ip);
    return this.bytesToInt(b);
}

IPUtil.prototype.intToBytes = function (ipInt) {
    var buf = new Array(4);
    buf[0] = ((ipInt >>> 24) & 0xFF);
    buf[1] = ((ipInt >>> 16) & 0xFF);
    buf[2] = ((ipInt >>> 8) & 0xFF);
    buf[3] = ((ipInt >>> 0) & 0xFF);
    return buf;
}
IPUtil.prototype.intToString = function (ipInt) {
    var buf = this.intToBytes(ipInt);
    return this.bytesToString(buf);
}

IPUtil.prototype.bytesToString = function (buff) {
    if (buff == null)
        return empty;
    return buff[0] + '.' + buff[1] + '.' + buff[2] + '.' + buff[3];
}

IPUtil.prototype.bytesToInt = function (buf) {
    if (buf == null || buf.length < 4)
        return 0;

    var ch1 = buf[0] & 0xff;
    var ch2 = buf[1] & 0xff;
    var ch3 = buf[2] & 0xff;
    var ch4 = buf[3] & 0xff;
    return ((ch1 << 24) + (ch2 << 16) + (ch3 << 8) + (ch4 << 0));
};

IPUtil.prototype.isOK = function (ip) {
    try {
        return ip != null && ip.length == 4;
    } catch (e) {
        return false;
    }
};
IPUtil.prototype.checkIp4 = function (ip) {
    if (ip == null || ip.length <= 3)
        return empty;
    if (ip.charAt(0) === ':') {
        return ip.substring(ip.lastIndexOf(':') + 1);
    }
    return ip;
};
IPUtil.prototype.isNotLocal = function (ip) {
    return this.isOK(ip) && (ip[0] & 0xff) != 127;
};
IPUtil.prototype.getIp = function () {
    var interfaces = require('os').networkInterfaces();
    var results = [];
    Object
        .keys(interfaces)
        .map(function (key) {
            results = results.concat(interfaces[key]);
        });

    results = results
        .filter(function (iface) {
            return iface.family === 'IPv4' && !iface.internal;
        })
        .map(function (iface) { return iface.address });
    return (results[0] || "127.0.0.1");
}
module.exports = new IPUtil();