function normalizeSource(source) {
    var lines = source.split(rLineSplit);
    var lineCount = lines.length;
    var tabOnlyOffset = false;
    var spaceOnlyOffset = false;
    var offset;

    // remove first list if it's an empty string
    // usually <script> starts with new line
    if (!rHasNonWhitespace.test(lines[0])) {
        lines.shift();
    }

    // replace last line by empty string if it contains only whitespaces
    // it helps avoid disallowTrailingWhitespace errors on last line
    if (!rHasNonWhitespace.test(lines[lines.length - 1])) {
        lines[lines.length - 1] = '';
    }

    // calculate min line offset
    offset = Math.min.apply(null, lines.map(function(line) {
        // skip empty lines
        if (!line) {
            return Infinity;
        }

        // fetch whitespaces at the line beginning
        var offsetStr = line.match(/^\s*/)[0];
        var tabCount = offsetStr.match(/\t*/)[0].length;

        if (offsetStr.length === line.length) {
            return 0;
        }

        // mixed spaces and tabs in one offset -> don't remove offsets
        if (tabCount && tabCount !== offsetStr.length) {
            return 0;
        }

        if (tabCount) {
            if (spaceOnlyOffset) {
                // no spaces, but previous offset has ony spaces -> mixed spaces and tabs
                return 0;
            } else {
                // remember offset contains only tabs
                tabOnlyOffset = true;
            }
        } else {
            if (tabOnlyOffset) {
                // no tabs, but previous offset has only tabs -> mixed spaces and tabs
                return 0;
            } else {
                // remember offset contains only spaces
                spaceOnlyOffset = true;
            }
        }

        return offsetStr.length;
    }));

    // remove common offsets if possible
    if (offset) {
        lines = lines.map(function(line) {
            return line.substr(offset);
        });
    }

    return {
        source: lines.join('\n'),
        offset: offset,
        lineCount: lineCount
    };
}
JavaScript in HTML usually shifted based on first JS line. For example
if first line of fragment is offset by 4 spaces, each line in this
fragment will have offset 4 to restore the original column.
This function trim script source and normalize lines offset.

@param {String} source
@returns {Object[]}