dotnet / runtime

.NET is a cross-platform runtime for cloud, mobile, desktop, and IoT apps.
https://docs.microsoft.com/dotnet/core/
MIT License
15.3k stars 4.74k forks source link

SSLStream does not clear InternalBuffer after read #17792

Closed andradf closed 4 years ago

andradf commented 8 years ago

SSLStream is vulnerable to memory dump attacks. When working with sensitive data, a programmer has no way to clear the internal buffer of SslStreamInternal after data has been read. And as long as a new packet does not arrive the data will be there indefinitely.

SslStream should provide a mechanism to clear the internal buffer or SslStreamInternal should clear InternalBuffer either during every call to DecrementInternalBufferCount or after data is BlockCopy-ed from InternalBuffer to buffer in ProcessRead.

davidsh commented 8 years ago

cc: @CIPop @stephentoub

CIPop commented 8 years ago

@andradf, this is an interesting point. We've discussed it with the Windows Cryptography team when we were deciding the future of SecureString. The conclusion was that there is no mechanism that would protect sensitive data from in-process inspection and that the security boundary is at the process level. There is no way to limit access if the attacker has access to the application's memory.

Even more, the same problem exists for data at rest:

Deleting the memory can create an apparent sense of security but the data was already in-memory. A correctly timed mem-dump or analyzing the swap file will probably show you the internal buffer content even if it was erased by the framework. Even more, it's very likely that the swap file still contains the data after your process was terminated.

andradf commented 8 years ago

@CIPop, thank you for the helpful response. The reason I ran across this is that we are trying to build a PCI validated application, and in their recommendations they suggest "Minimizing the exposure of PAN/SAD while in memory" (PA-DSS 5.1.6.1). And while protections provided by Windows' process system are good countermeasures, there have been attacks of this kind detected in the wild, specifically "Memory Dump Grabber" which is thought to have already targeted Windows POS applications.

A correctly timed mem-dump ... will probably show you the internal buffer content even if it was erased by the framework.

By not clearing InternalBuffer the mem-dump does not have to be well timed at all as long as another packet is not received. Minimizing the window under which sensitive data will be readable in a mem-dump is something other Microsoft technologies seek to achieve. Such as the ProtectedMemory class in DPAPI and SecureString.

CIPop commented 8 years ago

Thanks for sharing the details @andradf. I will follow-up with the Windows Crypto team to clarify the security scope of DPAPI/ProtectedMemory/SecureString.

CIPop commented 8 years ago

@andradf The recommendation from the Crypto team is to find ways to prevent unauthorized readers of process memory instead of trying to erase memory.

They have pointed out that in certain cases RtlSecureZeroMemory can be used to wipe buffers although. This approach is problematic since the information will also be available in your application's variables and maybe the stack, or other places in GC's internals.

Overall, the effort of adding secure-wipe too expensive both in dev and in run-time cost compared to its effectiveness: an attacker can still read the information if the dump is captured at the right time.