从pkcs7文件中提取ICP-Brasil信息

时间:2017-11-01 18:01:27

标签: c# bouncycastle pkcs#7

只是分享我的代码:

抱歉差错处理。

我花了一些时间来到这里。令人惊讶的是,在 Receita Federal do Brasil 然后是ITI本身更容易找到证书布局文档。 较旧的证书具有不同的布局。我会花一点时间寻找更多文档。

如果有人有官方文档,请分享。

         public static List<Certificado> ListarSignatariosArquivo(byte[] arquivo)
    {
        /* http://www.receita.fazenda.gov.br/acsrf/LeiautedeCertificadosdaSRF.pdf
         * 2.2.5. Subject Alternative Name
         *   Campos Obrigatórios
         *      OID = 2.16.76.1.3.1 com o seguinte conteúdo:
         *           Nas primeiras 8 (oito) posições, a data de nascimento da pessoa física titular do certificado, no formato ddmmaaaa; 
         *           nas 11 (onze) posições subseqüentes, o número de inscrição no Cadastro de Pessoa Física (CPF) da pessoa física titular do certificado;
         *           nas 11 (onze) posições subseqüentes, o número de Identificação Social da pessoa física titular do certificado - NIS (PIS, PASEP ou CI);
         *           nas 15 (quinze) posições subseqüentes, o número do Registro Geral - RG da pessoa física titular do certificado; 
         *           nas 6 (seis) posições subseqüentes, as siglas do órgão expedidor do RG e respectiva UF.
         *
         *       OID = 2.16.76.1.3.5 com o seguinte conteúdo:
         *           Nas primeiras 12 (onze) posições, o número de inscrição do Título de Eleitor da pessoa física titular do certificado;
         *           nas 3 (três) posições subseqüentes, o número correspondente a Zona Eleitoral;
         *           nas 4 (quatro) posições seguintes, o número correspondente a Seção;
         *           nas 22 (vinte e duas) posições subseqüentes, o nome do município e a UF do Título de Eleitor.
         *
         *       OID = 2.16.76.1.3.6 com o seguinte conteúdo:
         *           Nas 12 (doze) posições, o número do Cadastro Especifico do INSS (CEI) da pessoa física titular do certificado.
         *
         *   Campos Opcionais
         *       OID = 2.16.76.1.4.x.y.z com o seguinte conteúdo:
         *           Tamanho variável correspondente ao número de habilitação ou identificação profissional emitido por conselho de classe ou órgão competente.
         *           A AC Raiz, por meio do documento ATRIBUIÇÃO DE OID DA ICP-BRASIL (DOC ICP-04-01) regulamentará a correspondência de cada conselho de classe
         *           ou órgão competente ao conjunto de OID acima definido.
         *
         *       OID = 1.3.6.1.4.1.311.20.2.3 com o seguinte conteúdo:
         *           Este campo Principal Name contém a Identificação do endereço de login do titular do certificado no diretório Active Direct (AD) Microsoft.
         *           O conjunto de informações definido em cada campo OtherName deve ser armazenado como uma cadeia de caracteres do tipo ASN.1 OCTET STRING,
         *           com exceção do campo Principal Name cuja cadeia de caracteres é do tipo UTF-8 String.
         *
         *   Os seguintes campos são de preenchimento obrigatório:
         *   - Nome;
         *   - CPF;
         *   - Data de nascimento; e
         *   - Email. 
         */


        CmsSignedData signedData = null;
        List<Certificado> listaCpf = new List<Certificado>();
        try
        {
            signedData = new CmsSignedData(arquivo);
        }
        catch (CmsException)
        {
            return listaCpf;
        }
        catch (Exception e)
        {
            throw new IntegridadeArquivoException("Arquivo corrompido.", e);
        }

        if (signedData != null)
        {
            IX509Store store = signedData.GetCertificates("Collection/Certificate");


            SignerInformationStore signers = signedData.GetSignerInfos();

            foreach (var it in signers.GetSigners())
            {
                SignerInformation signer = (SignerInformation)it;

                foreach (var certificado in store.GetMatches(signer.SignerID))
                {

                    X509Certificate x509cert = (X509Certificate)certificado;

                    IList tmp;
                    tmp = x509cert.SubjectDN.GetValueList(X509Name.CN);
                    string nome = tmp.Count > 0 ? tmp[0].ToString() : "";
                    tmp = x509cert.IssuerDN.GetValueList(X509Name.CN);
                    string autoridadeCertificadora = tmp.Count > 0 ? tmp[0].ToString() : "";
                    DateTime dtValidadeCertificado = x509cert.NotAfter;



                    Nullable<DateTime> dtNascimento = null;
                    string cpf = null;
                    string rg = null;
                    string orgaoExpedidorRg = null;

                    string pessoaFisicaOid = "2.16.76.1.3.1";
                    foreach (ArrayList a in x509cert.GetSubjectAlternativeNames())
                    {

                        string conteudo = a.ToArray()[1].ToString();
                        Match moid = Regex.Match(conteudo, @"\[[0-9\.]*");
                        string oid = moid.Success ? moid.Value.Replace("[", string.Empty) : "";
                        if (pessoaFisicaOid.Equals(oid))
                        {
                            Match mvalor = Regex.Match(conteudo, "#[0-9a-fA-F]+");
                            string valor = mvalor.Success ? mvalor.Value.Replace("#", string.Empty) : "";
                            //converter string hexadecimal em string decimal.
                            valor = FromHexToString(valor);

                            int i = 0;
                            dtNascimento = DateTime.ParseExact(valor.Substring(i, 8),"ddMMyyyy", CultureInfo.InvariantCulture);
                            i += 8;
                            cpf = valor.Substring(i, 11);
                            i += 22;
                            rg = valor.Substring(i, 15);
                            i += 15;
                            orgaoExpedidorRg = valor.Substring(i, 6);
                        }
                    }


                    listaCpf.Add(new Certificado {
                        Nome = nome,
                        DtNascimento = dtNascimento,
                        AutoridadeCertificadora = autoridadeCertificadora,
                        DtValidadeCertificado = dtValidadeCertificado,
                        Cpf = cpf,
                        Rg = rg,
                        OrgaoExpedidorRg = orgaoExpedidorRg
                    });
                }
            }

        }
        return listaCpf;
    }
    public static string FromHexToString(string hex)
    {
        byte[] raw = new byte[hex.Length / 2];
        for (int i = 0; i < raw.Length; i++)
        {
            raw[i] = Convert.ToByte(hex.Substring(i * 2, 2), 16);
        }
        return Encoding.ASCII.GetString(raw);
    }

0 个答案:

没有答案