// NB for struct there is no finalizer, returning a buffer to the pool would be difficult // and we should manage arrays outside ///// <summary> ///// Create a new FixedBuffer with a new empty array ///// </summary> ///// <param name="length">buffer to which the view is attached.</param> //public FixedBuffer(int length) { // if (length <= 0) throw new ArgumentOutOfRangeException(nameof(length)); // _offset = 0; // _length = length; // _buffer = OptimizationSettings.ArrayPool.TakeBuffer<byte>(length); // _unpinner = null; //} private void PinBuffer() { // we postpone pinning array as much as possible // whenever this struct is copied by value, a reference to // unpinner is copied with it, so there is no way to manually unpin // other than to GC the unpinner, which happens when the last struct goes out of scope _unpinner = new UnpinWhenGCed(GCHandle.Alloc(_buffer, GCHandleType.Pinned)); }
/// <summary> /// Create a new FixedBuffer with a new empty array /// </summary> /// <param name="length">buffer to which the view is attached.</param> public FixedBuffer(int length) { if (length <= 0) { throw new ArgumentOutOfRangeException(nameof(length)); } _offset = 0; _length = length; _buffer = OptimizationSettings.ArrayPool.TakeBuffer <byte>(length); _unpinner = null; }
/// <summary> /// Attach a view to a byte[] for providing direct access. /// </summary> /// <param name="buffer">buffer to which the view is attached.</param> public FixedBuffer(byte[] buffer, int offset = 0, int length = 0) { if (offset < 0) { throw new ArgumentOutOfRangeException(nameof(offset)); } if (length < 0) { throw new ArgumentOutOfRangeException(nameof(length)); } if (length + offset > buffer.Length) { throw new ArgumentException("Length plus offset exceed capacity"); } _offset = 0; _length = buffer.Length; _buffer = buffer; _unpinner = null; }