Skip to content

Safer handling and guaranteed memory clearing of sensitive strings in .NET #118484

@mustafasariel

Description

@mustafasariel

Background and motivation

Hi .NET team,

I'm a senior developer working in security-conscious applications, and I’d like to raise a concern about how sensitive data (like passwords, tokens, etc.) are handled in .NET at runtime.

As you know, string in .NET is immutable and GC-managed, meaning sensitive data (like a user password) may stay in memory longer than expected and cannot be deterministically cleared.

While SecureString used to offer a partial solution, it's now deprecated, and no built-in alternative exists. Today, even if we use char[] or Span<char>, the moment we pass the data to any library (e.g., logging, JSON serialization, or internal string conversion), it ends up in RAM again as a string.

This makes .NET unsafe for handling sensitive information unless we avoid string entirely — which is not always practical due to APIs expecting it.

I have two questions:

  1. Is there any plan to introduce a safer string abstraction or a way to ensure sensitive data is cleared from memory immediately after use (like Rust's zeroize or Go's slice)?
  2. Can we expect a first-class support for "secure strings" or "ephemeral memory-backed data" in future versions of .NET?

I understand it's a complex issue due to .NET’s GC and interop design, but I believe this is critical for the platform's future in security-sensitive applications.

Best regards,
Mustafa

API Proposal

System.Security.SecureBuffer or System.Memory.SensitiveBuffer;
namespace System.Security
{
public sealed class SecureBuffer : IDisposable where T : unmanaged
{
public SecureBuffer(int length);
public Span AsSpan();
public void Zero(); // manually clears memory
public void Dispose(); // clears and frees memory
}

API Usage

using System.Security;

var buffer = new SecureBuffer(32);
Span span = buffer.AsSpan();
// Fill span with password, token etc.

Process(span); // Do your operation here

buffer.Zero(); // Wipe memory immediately
buffer.Dispose(); // Free it securely

Alternative Designs

No response

Risks

Developers might misuse Span and accidentally expose the data via string, loggers, serializers etc.

Platform-specific implementations (e.g., Linux mlock, Windows VirtualLock) may be needed.

GC and memory pressure should be tested carefully.

Metadata

Metadata

Labels

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions