Partilhar via


Classe System.Security.SecureString

Importante

Recomendamos que não se use a classe SecureString para novo desenvolvimento em .NET (Core) ou quando se migra o código existente para .NET (Core). Para obter mais informações, consulte SecureString não deve ser usado.

Este artigo fornece observações complementares à documentação de referência para esta API.

SecureString é um tipo de cadeia de caracteres que fornece uma medida de segurança. Ele tenta evitar o armazenamento de cadeias de caracteres potencialmente sensíveis na memória do processo como texto sem formatação. (Para limitações, no entanto, consulte a seção Quão seguro é o SecureString? .) O valor de uma instância de SecureString é automaticamente protegido usando um mecanismo suportado pela plataforma subjacente quando a instância é inicializada ou quando o valor é modificado. Seu aplicativo pode tornar a instância imutável e impedir modificações adicionais invocando o MakeReadOnly método.

O comprimento máximo de uma SecureString instância é de 65.536 caracteres.

Importante

Este tipo implementa a interface IDisposable. Quando terminar de usar uma instância do tipo, você deve descartá-la direta ou indiretamente. Para descartar o tipo diretamente, chame seu método Dispose em um bloco try/catch. Para descartá-lo indiretamente, use uma construção de linguagem como using (em C#) ou Using (em Visual Basic). Para obter mais informações, consulte a seção "Usando um objeto que implementa IDisposable" no tópico da IDisposable interface.

A SecureString classe e seus membros não são visíveis para COM. Para obter mais informações, consulte ComVisibleAttribute.

String versus SecureString

Uma instância da classe System.String é imutável e, quando já não for necessária, não pode ser programaticamente agendada para recolha de lixo; ou seja, a instância é de apenas leitura depois de criada e não é possível prever quando será removida da memória do computador. Como System.String as instâncias são imutáveis, as operações que parecem modificar uma instância existente na verdade criam uma cópia dela para manipular. Consequentemente, se um String objeto contiver informações confidenciais, como uma senha, número de cartão de crédito ou dados pessoais, há um risco de que as informações possam ser reveladas depois de serem usadas, porque seu aplicativo não pode excluir os dados da memória do computador.

Um SecureString objeto é semelhante a um String objeto na medida em que tem um valor de texto. No entanto, o valor de um objeto SecureString é fixado na memória, pode usar um mecanismo de proteção, como criptografia, fornecido pelo sistema operativo subjacente, pode ser modificado até que a sua aplicação o marque como somente leitura e pode ser excluído da memória do computador pela aplicação ao chamar o método Dispose ou pelo coletor de lixo .NET.

Para obter uma discussão sobre as SecureString limitações da classe, consulte a seção Quão seguro é o SecureString?

Operações SecureString

A SecureString classe inclui membros que permitem que você faça o seguinte:

Instanciar um SecureString objeto Você instancia um SecureString objeto chamando seu construtor sem parâmetros.

Adicionar caracteres a um SecureString objeto Pode adicionar um único caractere a um SecureString objeto de cada vez chamando o seu método AppendChar ou InsertAt.

Importante

Um SecureString objeto nunca deve ser construído a partir de um String, porque os dados confidenciais já estão sujeitos às consequências de persistência de memória da classe imutável String . A melhor maneira de construir um SecureString objeto é a partir de uma fonte não gerenciada de caractere por vez, como o Console.ReadKey método.

Remover caracteres de um SecureString objeto Você pode substituir um caractere individual chamando o SetAt método, remover um caractere individual chamando o RemoveAt método ou remover todos os caracteres da SecureString ocorrência chamando o Clear método.

Tornar o SecureString objeto somente leitura Depois de definir a cadeia de caracteres que o SecureString objeto representa, você chama seu MakeReadOnly método para tornar a cadeia de caracteres somente leitura.

Obter informações sobre o SecureString objeto A SecureString classe tem apenas dois membros que fornecem informações sobre a string: a sua propriedade Length, que indica o número de unidades de código em UTF16 presentes na string, e o método IsReadOnly, que indica se a instância está em modo de leitura.

Liberar a memória alocada para a SecureString instância Como SecureString implementa a IDisposable interface, você libera sua memória chamando o Dispose método.

A SecureString classe não tem membros que inspecionem, comparem ou convertam o valor de um SecureString. A ausência desses membros ajuda a proteger o valor da instância contra exposição acidental ou maliciosa. Use membros apropriados da System.Runtime.InteropServices.Marshal classe, como o SecureStringToBSTR método, para manipular o valor de um SecureString objeto.

A Biblioteca de Classes do .NET usa comumente instâncias de SecureString das seguintes maneiras:

SecureString e interoperabilidade

Como o sistema operacional não oferece suporte direto ao SecureString, você deve converter o SecureString valor do objeto para o tipo de cadeia de caracteres necessário antes de passar a cadeia de caracteres para um método nativo. A Marshal classe tem cinco métodos que fazem isso:

Cada um desses métodos cria uma cadeia de caracteres de texto não criptografado na memória não gerenciada. É responsabilidade do desenvolvedor zerar e liberar essa memória assim que ela não for mais necessária. Cada um dos métodos de conversão de cadeia de caracteres e alocação de memória tem um método correspondente para zerar e liberar a memória alocada:

Método de atribuição e conversão Método zero e livre
Marshal.SecureStringToBSTR Marshal.ZeroFreeBSTR
Marshal.SecureStringToCoTaskMemAnsi Marshal.ZeroFreeCoTaskMemAnsi
Marshal.SecureStringToCoTaskMemUnicode Marshal.ZeroFreeCoTaskMemUnicode
Marshal.SecureStringToGlobalAllocAnsi Marshal.ZeroFreeGlobalAllocAnsi
Marshal.SecureStringToGlobalAllocUnicode Marshal.ZeroFreeGlobalAllocUnicode

Quão seguro é o SecureString?

Quando criada corretamente, uma SecureString instância oferece mais proteção de dados do que String. Ao criar uma string a partir de uma fonte que processa um caractere de cada vez, String cria vários intermediários na memória, enquanto SecureString cria apenas uma única instância. A coleta de lixo de objetos String não é determinística. Além disso, como a sua memória não está fixa, o coletor de lixo fará cópias adicionais dos valores String durante o processo de movimentação e compactação da memória. Por outro lado, a memória alocada a um SecureString objeto é fixada e essa memória pode ser liberada chamando o Dispose método.

Embora os dados armazenados em uma SecureString instância sejam mais seguros do que os dados armazenados em uma String instância, há limitações significativas sobre o quão segura é uma SecureString instância. Estes são, entre outros:

Plataforma

No sistema operacional Windows, o conteúdo da matriz de caracteres interna de uma SecureString instância é criptografado. No entanto, seja devido a APIs ausentes ou problemas de gerenciamento de chaves, a criptografia não está disponível em todas as plataformas. Devido a essa dependência de plataforma, SecureString não criptografa o armazenamento interno em plataforma não-Windows. Outras técnicas são usadas nessas plataformas para fornecer proteção adicional.

Duração

Mesmo que a SecureString implementação seja capaz de tirar proveito da criptografia, o texto sem formatação atribuído à SecureString instância pode ser exposto em vários momentos:

  • Como o Windows não oferece uma implementação de cadeia de caracteres segura no nível do sistema operacional, o .NET ainda precisa converter o valor da cadeia de caracteres segura em sua representação de texto sem formatação para usá-la.

  • Sempre que o valor da cadeia de caracteres segura é modificado por métodos como AppendChar ou RemoveAt, ela deve ser descriptografada (ou seja, convertida de volta para texto sem formatação), modificada e, em seguida, criptografada novamente.

  • Se a cadeia de caracteres segura for usada em uma chamada de interoperabilidade, ela deverá ser convertida em uma cadeia de caracteres ANSI, uma cadeia de caracteres Unicode ou uma cadeia binária (BSTR). Para obter mais informações, consulte a seção SecureString e interoperabilidade .

O valor da instância SecureString é exposto apenas durante um intervalo de tempo mais curto em comparação com a classe String.

Armazenamento versus uso Mais geralmente, a SecureString classe define um mecanismo de armazenamento para valores de cadeia de caracteres que devem ser protegidos ou mantidos confidenciais. No entanto, fora do próprio .NET, nenhum mecanismo de uso oferece suporte ao SecureString. Isso significa que a cadeia de caracteres segura deve ser convertida em um formulário utilizável (normalmente um formulário de texto não criptografado) que possa ser reconhecido por seu destino e que a descriptografia e a conversão devem ocorrer no espaço do usuário.

No geral, SecureString é mais seguro do que String porque limita a exposição de dados confidenciais de cadeia de caracteres. No entanto, essas cadeias de caracteres ainda podem ser expostas a qualquer processo ou operação que tenha acesso à memória bruta, como um processo mal-intencionado em execução no computador host, um despejo de processo ou um arquivo de permuta visível pelo usuário. Em vez de usar SecureString para proteger senhas, a alternativa recomendada é usar um identificador opaco para credenciais que são armazenadas fora do processo.