How to Verify the Digital Signature of a SLIC Table

Discussion in 'BIOS Mods' started by crypto, Aug 4, 2009.

  1. crypto

    crypto MDL Member

    Joined:
    Nov 3, 2008
    Messages:
    114
    Likes Received:
    376
    Trophy Points:
    10
    #1 crypto, Aug 4, 2009
    Last edited by a moderator: Apr 20, 2017
  2. zort

    zort MDL Expert

    Joined:
    Feb 19, 2008
    Messages:
    1,105
    Likes Received:
    18
    Trophy Points:
    60
    Thanks for this guide, crypto!
     
  3. frwil

    frwil MDL Addicted

    Joined:
    Sep 22, 2008
    Messages:
    534
    Likes Received:
    183
    Trophy Points:
    30
    Interesting topic. Wish there were command-line tools like that calculator...
    I think there's a similar way to verify xrm-ms files, and oem-certificates as an example. <DigestValue> is what they sign and it is SHA1 of yet unsigned license (without enveloped <Signature> elements).
     
  4. FreeStyler

    FreeStyler MDL Guru

    Joined:
    Jun 23, 2007
    Messages:
    3,520
    Likes Received:
    3,730
    Trophy Points:
    120
    I wish i have known a way to calculate "s^e mod n" in ASP/VBScript :)
     
  5. justinkb

    justinkb MDL Member

    Joined:
    Jul 16, 2008
    Messages:
    187
    Likes Received:
    7
    Trophy Points:
    10
    i dont know vb.net but (s^e) Mod n should work, otherwise try Math.Pow(s,e) Mod n
    thanks for this guide :)
     
  6. crypto

    crypto MDL Member

    Joined:
    Nov 3, 2008
    Messages:
    114
    Likes Received:
    376
    Trophy Points:
    10
  7. ionsmurf

    ionsmurf MDL Novice

    Joined:
    Jul 6, 2009
    Messages:
    6
    Likes Received:
    0
    Trophy Points:
    0
  8. frwil

    frwil MDL Addicted

    Joined:
    Sep 22, 2008
    Messages:
    534
    Likes Received:
    183
    Trophy Points:
    30
  9. ionsmurf

    ionsmurf MDL Novice

    Joined:
    Jul 6, 2009
    Messages:
    6
    Likes Received:
    0
    Trophy Points:
    0
  10. frwil

    frwil MDL Addicted

    Joined:
    Sep 22, 2008
    Messages:
    534
    Likes Received:
    183
    Trophy Points:
    30
    Thank you for the tips. If possible please could you provide an example with manual verification of Asus oem certificate? And more detailed how to do it with the tool in your previous post.
     
  11. ionsmurf

    ionsmurf MDL Novice

    Joined:
    Jul 6, 2009
    Messages:
    6
    Likes Received:
    0
    Trophy Points:
    0
    The code posted earlier is more sample code. Here is a bit more of a tool.
    Usage: CertInfo "path to certificate" e.g. CertInfo "ASUS.XRM-MS"
     
  12. frwil

    frwil MDL Addicted

    Joined:
    Sep 22, 2008
    Messages:
    534
    Likes Received:
    183
    Trophy Points:
    30
    Thank you again!
    And your previous command-line tool:
     
  13. chaddawkins

    chaddawkins MDL Senior Member

    Joined:
    Sep 16, 2007
    Messages:
    344
    Likes Received:
    66
    Trophy Points:
    10
  14. str8

    str8 MDL Expert

    Joined:
    Jul 3, 2009
    Messages:
    1,506
    Likes Received:
    56
    Trophy Points:
    60
    crypto thank you VERY much for this interesting and valuable information. This should be a "sticky".
     
  15. crypto

    crypto MDL Member

    Joined:
    Nov 3, 2008
    Messages:
    114
    Likes Received:
    376
    Trophy Points:
    10
    #15 crypto, Aug 20, 2009
    Last edited by a moderator: May 23, 2017
    (OP)
  16. dobrogi

    dobrogi MDL Novice

    Joined:
    Apr 4, 2009
    Messages:
    5
    Likes Received:
    0
    Trophy Points:
    0
  17. elffin

    elffin MDL Novice

    Joined:
    Sep 12, 2009
    Messages:
    3
    Likes Received:
    0
    Trophy Points:
    0
    Thanks very much for your explaination.
    Some questions :
    Where did you get the name(description) of these segments ? I searched but could not find other materials. Are there official documents about this?
    if 0xC8 ~ 0xCB is called Windows Marker Version, what is its meaning (or function) ?
    How about 0xE2 ~ 0xE5, I think this part defines the SLIC version. ( It is 01 00 02 00 in SLIC2.1 ) what is its name ?

    Thanks again!
     
  18. crypto

    crypto MDL Member

    Joined:
    Nov 3, 2008
    Messages:
    114
    Likes Received:
    376
    Trophy Points:
    10
    #18 crypto, Sep 15, 2009
    Last edited by a moderator: Apr 20, 2017
    (OP)
  19. chaiilee

    chaiilee MDL Novice

    Joined:
    Oct 8, 2009
    Messages:
    37
    Likes Received:
    0
    Trophy Points:
    0
    I agree, @crypto all of your threads are awsome!
     
  20. MasterDisaster

    MasterDisaster MDL Expert

    Joined:
    Aug 29, 2009
    Messages:
    1,256
    Likes Received:
    674
    Trophy Points:
    60
    #20 MasterDisaster, Nov 16, 2009
    Last edited by a moderator: Apr 20, 2017
    C# functions to verify SLIC bin and OEM Certificate

    Great tutorial crypto :)
    Was able to write this function by just following your instructions.

    Code:
    
    using System;
    using System.IO;
    using System.Security.Cryptography;
    
    /// <summary>
    /// Verifies the Digital Signature in the SLIC Table
    /// </summary>
    /// <param name="path">Path to the bin file</param>
    /// <returns>true if 'signature' matches the signature computed using the specified hash algorithm and key on 'messageHash'; otherwise, false.</returns>
    
    public bool VerifySign(string path)
    {
        byte[] bin = File.ReadAllBytes(path);
        byte[] exponent = new byte[4];
        byte[] modulus = new byte[128];
        byte[] message = new byte[46];
        byte[] signature = new byte[128];
        Array.Copy(bin, 0x3C, exponent, 0, exponent.Length);
        Array.Copy(bin, 0x40, modulus, 0, modulus.Length);
        Array.Copy(bin, 0xC8, message, 0, message.Length);
        Array.Copy(bin, 0xF6, signature, 0, signature.Length);
        Array.Reverse(exponent);
        Array.Reverse(modulus);
        RSAParameters parameter = new RSAParameters();
        parameter.Exponent = exponent;
        parameter.Modulus = modulus;
        RSACryptoServiceProvider RSA = new RSACryptoServiceProvider();
        RSA.ImportParameters(parameter);
        RSAPKCS1SignatureDeformatter RSADeformatter = new RSAPKCS1SignatureDeformatter(RSA);
        RSADeformatter.SetHashAlgorithm("SHA256");
        byte[] messageHash = new SHA256Managed().ComputeHash(message);
        return RSADeformatter.VerifySignature(messageHash, signature);
    }
    
    Function to verify integrity of signature and license info in certificate.

    Code:
    using System;
    using System.Text;
    using System.IO;
    using System.Security.Cryptography;
    using System.Security.Cryptography.Xml;
    using System.Xml;
    
    /// <summary>
    /// Verifies the Signature and Licence Info in the Certificate
    /// </summary>
    /// <param name="path">Path to the certificate file</param>
    /// <returns>true if 'sign' matches the signature computed using the specified hash algorithm and key on 'Signature' and 'Digest' matches the computed hash for license; otherwise, false.</returns>
    
    public bool VerifyCert(string path)
    {
        XmlDocument doc = new XmlDocument();
        doc.Load(path);
        XmlDsigC14NTransform transform = new XmlDsigC14NTransform();
        transform.LoadInput(new MemoryStream(Encoding.UTF8.GetBytes(doc.GetElementsByTagName("SignedInfo")[0].OuterXml)));
        byte[] siHash = transform.GetDigestedOutput(SHA1.Create());
        byte[] Signature = Convert.FromBase64String(doc.GetElementsByTagName("SignatureValue")[0].InnerText);
        byte[] Modulus = Convert.FromBase64String(doc.GetElementsByTagName("Modulus")[0].InnerText);
        byte[] Exponent = Convert.FromBase64String(doc.GetElementsByTagName("Exponent")[0].InnerText);
        string Digest = doc.GetElementsByTagName("DigestValue")[0].InnerText;
        RSAParameters parameter = new RSAParameters();
        parameter.Modulus = Modulus;
        parameter.Exponent = Exponent;
        RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
        rsa.ImportParameters(parameter);
        RSAPKCS1SignatureDeformatter rsaDeformatter = new RSAPKCS1SignatureDeformatter(rsa);
        rsaDeformatter.SetHashAlgorithm("SHA1");
        bool sign = rsaDeformatter.VerifySignature(siHash, Signature);
        XmlLicenseTransform License = new XmlLicenseTransform();
        License.Context = (XmlElement)doc.GetElementsByTagName("Signature")[0];
        License.LoadInput(doc);
        transform = new XmlDsigC14NTransform();
        transform.LoadInput(License.GetOutput());
        string dvHash = Convert.ToBase64String(transform.GetDigestedOutput(SHA1.Create()));
        return sign && dvHash.Equals(Digest);
    }
    
    Function to compare Certificate data with SLIC Table.

    Code:
    using System;
    using System.IO;
    using System.Xml;
    
    /// <summary>
    /// Compare Certificate data and SLIC Table
    /// </summary>
    /// <param name="binFile">Path to bin file</param>
    /// <param name="certFile">Path to certificate file</param>
    /// <returns>true if data matches; otherwise false.</returns>
    
    public bool Compare(string binFile, string certFile)
    {
        byte[] bin = File.ReadAllBytes(binFile);
        XmlDocument doc = new XmlDocument();
        doc.Load(certFile);
        byte[] cert = Convert.FromBase64String(doc.GetElementsByTagName("sl:data")[0].InnerText);
        int i = 0;
        int j = 0;
        bool match = cert.Length == cert;
        for (i = 4, j = 0xC8; i < 14; i++, j++)
            match &= cert == bin[j];
        for (j = 0x3C; i < cert.Length; i++, j++)
            match &= cert == bin[j];
        return match;
    }