< Summary - Combined Code Coverage

Information
Class: NLightning.Infrastructure.Crypto.Primitives.SecureMemory
Assembly: NLightning.Infrastructure
File(s): /home/runner/work/nlightning/nlightning/src/NLightning.Infrastructure/Crypto/Primitives/SecureMemory.cs
Tag: 36_15743069263
Line coverage
79%
Covered lines: 38
Uncovered lines: 10
Coverable lines: 48
Total lines: 115
Line coverage: 79.1%
Branch coverage
44%
Covered branches: 8
Total branches: 18
Branch coverage: 44.4%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
get_Length()100%11100%
.ctor(...)50%4.73464.29%
op_Implicit(...)50%22100%
op_Implicit(...)50%22100%
Equals(...)0%2040%
GetHashCode()100%210%
ReleaseUnmanagedResources()50%2290%
Dispose(...)75%4.05485.71%
Dispose()100%11100%
Finalize()100%11100%

File(s)

/home/runner/work/nlightning/nlightning/src/NLightning.Infrastructure/Crypto/Primitives/SecureMemory.cs

#LineLine coverage
 1namespace NLightning.Infrastructure.Crypto.Primitives;
 2
 3using Factories;
 4using Interfaces;
 5
 6public sealed class SecureMemory : IDisposable
 7{
 8    private readonly ICryptoProvider _cryptoProvider;
 9    private readonly IntPtr _handle;
 10
 1916411    public int Length { get; }
 12
 47613    public SecureMemory(int size)
 14    {
 47615        if (size <= 0)
 016            throw new ArgumentOutOfRangeException(nameof(size), "Size must be positive.");
 17
 47618        _cryptoProvider = CryptoFactory.GetCryptoProvider();
 47619        Length = size;
 47620        _handle = _cryptoProvider.MemoryAlloc((ulong)size);
 21
 47622        if (_handle == IntPtr.Zero)
 023            throw new OutOfMemoryException("Failed to allocate secure memory.");
 24
 25        try
 26        {
 47627            _cryptoProvider.MemoryLock(new IntPtr(_handle), (ulong)Length);
 47628        }
 029        catch
 30        {
 031            _cryptoProvider.MemoryFree(new IntPtr(_handle));
 032            throw;
 33        }
 47634    }
 35
 36    #region Implicit Conversions
 37
 38    public static unsafe implicit operator Span<byte>(SecureMemory secureMemory)
 39    {
 93240        ArgumentNullException.ThrowIfNull(secureMemory);
 93241        return secureMemory._disposed
 93242            ? throw new ObjectDisposedException(nameof(SecureMemory))
 93243            : new Span<byte>(secureMemory._handle.ToPointer(), secureMemory.Length);
 44    }
 45
 46    public static unsafe implicit operator ReadOnlySpan<byte>(SecureMemory secureMemory)
 47    {
 1680448        ArgumentNullException.ThrowIfNull(secureMemory);
 1680449        return secureMemory._disposed
 1680450            ? throw new ObjectDisposedException(nameof(SecureMemory))
 1680451            : new ReadOnlySpan<byte>(secureMemory._handle.ToPointer(), secureMemory.Length);
 52    }
 53    #endregion
 54
 55    public override bool Equals(object? obj)
 56    {
 057        if (obj is not SecureMemory castObj) return false;
 58
 059        return castObj.Length == Length && castObj._handle == _handle;
 60    }
 61    public override int GetHashCode()
 62    {
 063        return HashCode.Combine(Length, _handle);
 64    }
 65
 66    #region Dispose Pattern
 67    private bool _disposed;
 68    private void ReleaseUnmanagedResources()
 69    {
 47470        if (_handle == IntPtr.Zero)
 071            return;
 72
 73        try
 74        {
 47475            _cryptoProvider.MemoryZero(_handle, (ulong)Length);
 47476        }
 77        finally
 78        {
 79            try
 80            {
 47481                _cryptoProvider.MemoryUnlock(_handle, (ulong)Length);
 47482            }
 83            finally
 84            {
 47485                _cryptoProvider.MemoryFree(_handle);
 47486            }
 47487        }
 47488    }
 89
 90    private void Dispose(bool disposing)
 91    {
 47492        if (_disposed)
 093            return;
 94
 47495        ReleaseUnmanagedResources();
 47496        if (disposing)
 97        {
 37698            _cryptoProvider.Dispose();
 99        }
 100
 474101        _disposed = true;
 474102    }
 103
 104    public void Dispose()
 105    {
 376106        Dispose(true);
 376107        GC.SuppressFinalize(this);
 376108    }
 109
 110    ~SecureMemory()
 111    {
 98112        Dispose(false);
 196113    }
 114    #endregion
 115}