#!/usr/bin/env python
#
# Copyright (c) 2014 Google, Inc
#
# SPDX-License-Identifier:      GPL-2.0+
#
# Intel microcode update tool

from optparse import OptionParser
import os
import re
import struct
import sys

MICROCODE_DIR = 'arch/x86/dts/microcode'

class Microcode:
    """Holds information about the microcode for a particular model of CPU.

    Attributes:
        name:  Name of the CPU this microcode is for, including any version
                   information (e.g. 'm12206a7_00000029')
        model: Model code string (this is cpuid(1).eax, e.g. '206a7')
        words: List of hex words containing the microcode. The first 16 words
                   are the public header.
    """
    def __init__(self, name, data):
        self.name = name
        # Convert data into a list of hex words
        self.words = []
        for value in ''.join(data).split(','):
            hexval = value.strip()
            if hexval:
                self.words.append(int(hexval, 0))

        # The model is in the 4rd hex word
        self.model = '%x' % self.words[3]

def ParseFile(fname):
    """Parse a micrcode.dat file and return the component parts

    Args:
        fname: Filename to parse
    Returns:
        3-Tuple:
            date:         String containing date from the file's header
            license_text: List of text lines for the license file
            microcodes:   List of Microcode objects from the file
    """
    re_date = re.compile('/\* *(.* [0-9]{4}) *\*/$')
    re_license = re.compile('/[^-*+] *(.*)$')
    re_name = re.compile('/\* *(.*)\.inc *\*/', re.IGNORECASE)
    microcodes = {}
    license_text = []
    date = ''
    data = []
    name = None
    with open(fname) as fd:
        for line in fd:
            line = line.rstrip()
            m_date = re_date.match(line)
            m_license = re_license.match(line)
            m_name = re_name.match(line)
            if m_name:
                if name:
                    microcodes[name] = Microcode(name, data)
                name = m_name.group(1).lower()
                data = []
            elif m_license:
                license_text.append(m_license.group(1))
            elif m_date:
                date = m_date.group(1)
            else:
                data.append(line)
    if name:
        microcodes[name] = Microcode(name, data)
    return date, license_text, microcodes

def ParseHeaderFiles(fname_list):
    """Parse a list of header files and return the component parts

    Args:
        fname_list: List of files to parse
    Returns:
            date:         String containing date from the file's header
            license_text: List of text lines for the license file
            microcodes:   List of Microcode objects from the file
    """
    microcodes = {}
    license_text = []
    date = ''
    name = None
    for fname in fname_list:
        name = os.path.basename(fname).lower()
        name = os.path.splitext(name)[0]
        data = []
        with open(fname) as fd:
            license_start = False
            license_end = False
            for line in fd:
                line = line.rstrip()

                if len(line) >= 2:
                    if line[0] == '/' and line[1] == '*':
                        license_start = True
                        continue
                    if line[0] == '*' and line[1] == '/':
                        license_end = True
                        continue
                if license_start and not license_end:
                    # Ignore blank line
                    if len(line) > 0:
                        license_text.append(line)
                    continue
                # Omit anything after the last comma
                words = line.split(',')[:-1]
                data += [word + ',' for word in words]
        microcodes[name] = Microcode(name, data)
    return date, license_text, microcodes


def List(date, microcodes, model):
    """List the available microcode chunks

    Args:
        date:           Date of the microcode file
        microcodes:     Dict of Microcode objects indexed by name
        model:          Model string to search for, or None
    """
    print 'Date: %s' % date
    if model:
        mcode_list, tried = FindMicrocode(microcodes, model.lower())
        print 'Matching models %s:' % (', '.join(tried))
    else:
        print 'All models:'
        mcode_list = [microcodes[m] for m in microcodes.keys()]
    for mcode in mcode_list:
        print '%-20s: model %s' % (mcode.name, mcode.model)

def FindMicrocode(microcodes, model):
    """Find all the microcode chunks which match the given model.

    This model is something like 306a9 (the value returned in eax from
    cpuid(1) when running on Intel CPUs). But we allow a partial match,
    omitting the last 1 or two characters to allow many families to have the
    same microcode.

    If the model name is ambiguous we return a list of matches.

    Args:
        microcodes: Dict of Microcode objects indexed by name
        model:      String containing model name to find
    Returns:
        Tuple:
            List of matching Microcode objects
            List of abbreviations we tried
    """
    # Allow a full name to be used
    mcode = microcodes.get(model)
    if mcode:
        return [mcode], []

    tried = []
    found = []
    for i in range(3):
        abbrev = model[:-i] if i else model
        tried.append(abbrev)
        for mcode in microcodes.values():
            if mcode.model.startswith(abbrev):
                found.append(mcode)
        if found:
            break
    return found, tried

def CreateFile(date, license_text, mcodes, outfile):
    """Create a microcode file in U-Boot's .dtsi format

    Args:
        date:       String containing date of original microcode file
        license:    List of text lines for the license file
        mcodes:      Microcode objects to write (normally only 1)
        outfile:    Filename to write to ('-' for stdout)
    """
    out = '''/*%s
 * ---
 * This is a device tree fragment. Use #include to add these properties to a
 * node.
 *
 * Date: %s
 */

compatible = "intel,microcode";
intel,header-version = <%d>;
intel,update-revision = <%#x>;
intel,date-code = <%#x>;
intel,processor-signature = <%#x>;
intel,checksum = <%#x>;
intel,loader-revision = <%d>;
intel,processor-flags = <%#x>;

/* The first 48-bytes are the public header which repeats the above data */
data = <%s
\t>;'''
    words = ''
    add_comments = len(mcodes) > 1
    for mcode in mcodes:
        if add_comments:
            words += '\n/* %s */' % mcode.name
        for i in range(len(mcode.words)):
            if not (i & 3):
                words += '\n'
            val = mcode.words[i]
            # Change each word so it will be little-endian in the FDT
            # This data is needed before RAM is available on some platforms so
            # we cannot do an endianness swap on boot.
            val = struct.unpack("<I", struct.pack(">I", val))[0]
            words += '\t%#010x' % val

    # Use the first microcode for the headers
    mcode = mcodes[0]

    # Take care to avoid adding a space before a tab
    text = ''
    for line in license_text:
        if line[0] == '\t':
            text += '\n *' + line
        else:
            text += '\n * ' + line
    args = [text, date]
    args += [mcode.words[i] for i in range(7)]
    args.append(words)
    if outfile == '-':
        print out % tuple(args)
    else:
        if not outfile:
            if not os.path.exists(MICROCODE_DIR):
                print >> sys.stderr, "Creating directory '%s'" % MICROCODE_DIR
                os.makedirs(MICROCODE_DIR)
            outfile = os.path.join(MICROCODE_DIR, mcode.name + '.dtsi')
        print >> sys.stderr, "Writing microcode for '%s' to '%s'" % (
                ', '.join([mcode.name for mcode in mcodes]), outfile)
        with open(outfile, 'w') as fd:
            print >> fd, out % tuple(args)

def MicrocodeTool():
    """Run the microcode tool"""
    commands = 'create,license,list'.split(',')
    parser = OptionParser()
    parser.add_option('-d', '--mcfile', type='string', action='store',
                    help='Name of microcode.dat file')
    parser.add_option('-H', '--headerfile', type='string', action='append',
                    help='Name of .h file containing microcode')
    parser.add_option('-m', '--model', type='string', action='store',
                    help="Model name to extract ('all' for all)")
    parser.add_option('-M', '--multiple', type='string', action='store',
                    help="Allow output of multiple models")
    parser.add_option('-o', '--outfile', type='string', action='store',
                    help='Filename to use for output (- for stdout), default is'
                    ' %s/<name>.dtsi' % MICROCODE_DIR)
    parser.usage += """ command

    Process an Intel microcode file (use -h for help). Commands:

       create     Create microcode .dtsi file for a model
       list       List available models in microcode file
       license    Print the license

    Typical usage:

       ./tools/microcode-tool -d microcode.dat -m 306a create

    This will find the appropriate file and write it to %s.""" % MICROCODE_DIR

    (options, args) = parser.parse_args()
    if not args:
        parser.error('Please specify a command')
    cmd = args[0]
    if cmd not in commands:
        parser.error("Unknown command '%s'" % cmd)

    if (not not options.mcfile) != (not not options.mcfile):
        parser.error("You must specify either header files or a microcode file, not both")
    if options.headerfile:
        date, license_text, microcodes = ParseHeaderFiles(options.headerfile)
    elif options.mcfile:
        date, license_text, microcodes = ParseFile(options.mcfile)
    else:
        parser.error('You must specify a microcode file (or header files)')

    if cmd == 'list':
        List(date, microcodes, options.model)
    elif cmd == 'license':
        print '\n'.join(license_text)
    elif cmd == 'create':
        if not options.model:
            parser.error('You must specify a model to create')
        model = options.model.lower()
        if options.model == 'all':
            options.multiple = True
            mcode_list = microcodes.values()
            tried = []
        else:
            mcode_list, tried = FindMicrocode(microcodes, model)
        if not mcode_list:
            parser.error("Unknown model '%s' (%s) - try 'list' to list" %
                        (model, ', '.join(tried)))
        if not options.multiple and len(mcode_list) > 1:
            parser.error("Ambiguous model '%s' (%s) matched %s - try 'list' "
                        "to list or specify a particular file" %
                        (model, ', '.join(tried),
                        ', '.join([m.name for m in mcode_list])))
        CreateFile(date, license_text, mcode_list, options.outfile)
    else:
        parser.error("Unknown command '%s'" % cmd)

if __name__ == "__main__":
    MicrocodeTool()
