Compliance of .Net security libraries about verifying a CMS Advanced Electronic Signatures (CAdES) message

CAdES is an extension of CMS and these extensions, where present, require a different process to check the signature. Our .Net security libraries (System.Security.Cryptography) though verify a CAdES message; it actually ignores the CAdES part within the message.

SignedCms can verify a message with a CAdES signature but it does not verify the CAdES part. The .Net security libraries are a wrapper around the low level Crypto API’s and the low level Crypto messaging APIs don’t understand CAdES signatures.

Sample Code using SignedCms

class CheckSignature

{

    //Reads a file.

    internal static byte[] ReadFile(string fileName)

    {

        FileStream f = new FileStream(fileName, FileMode.Open, FileAccess.Read);

        int size = (int)f.Length;

        byte[] data = new byte[size];

        size = f.Read(data, 0, size);

        f.Close();

        return data;

    }

    //Main method begins here.

    static void Main(string[] args)

    {

        //Test for correct number of arguments.

        if (args.Length < 1)

        {

            Console.WriteLine("Usage: CheckSignature <filename>");

            return;

        }

        try

        {

            byte[] encodedMessage = ReadFile(args[0]);

            // The message content is not detached. The message content is included in the SignedCms message.

            // Create a new, nondetached SignedCms message.

            SignedCms signedCms = new SignedCms();

            // encodedMessage is the encoded message received from

            // the sender.

            signedCms.Decode(encodedMessage);

            // Verify the signature without validating the

            // certificate.

            signedCms.CheckSignature(true);

            if (signedCms.Detached)

            {

                throw new InvalidOperationException("Cannot extract enveloped content from a detached signature.");

            }

            // extract the data which was signed.

            byte[] data = signedCms.ContentInfo.Content;

            string s = Encoding.UTF8.GetString(data);

            Console.WriteLine(s);

        }

        catch (DirectoryNotFoundException)

        {

            Console.WriteLine("Error: The directory specified could not be found.");

        }

        catch (ArgumentNullException e)

        {

            Console.WriteLine(e.ToString());

        }

        catch (CryptographicException e)

        {

            Console.WriteLine(e.ToString());

        }

        catch (InvalidOperationException e)

        {

            Console.WriteLine(e.ToString());

        }

    }

}

So if you are trying to verify a CAdES message make sure that you are implementing your own verification based on the CAdES standards.

-Shamik