public MappedBuffer(uint id, BufferAccessMask mask, Action <uint> callback)
 {
     ID            = id;
     Mask          = mask;
     this.callback = callback;
     Map();
 }
示例#2
0
 /// <summary>
 /// Get a portion of the buffer's memory as pointer to it, allowing you to map data.
 /// When finished mapping you should invoke <see cref="FinishMapping" /> to flush the data to the GPU.
 /// </summary>
 /// <param name="offset">Offset for the mapping region from the beginning of the buffer - in bytes.</param>
 /// <param name="length">The length to map in bytes.</param>
 /// <param name="mask">The mapping access params.</param>
 /// <returns>A mapper used to map data in the buffer.</returns>
 public unsafe byte *CreateUnsafeMapper(int offset = 0, uint length = 0, BufferAccessMask mask = BufferAccessMask.MapWriteBit)
 {
     if (!Mapping)
     {
         StartMapping(offset, length, mask);
     }
     return(!Mapping ? null : _mappingPtr);
 }
示例#3
0
        /// <summary>
        /// Maps the buffer.
        /// </summary>
        /// <param name="mask"></param>
        /// <returns></returns>
        /// <exception cref="InvalidOperationException"></exception>
        public IntPtr MapBufferRange(BufferAccessMask mask)
        {
            if (IsMapped)
            {
                throw new InvalidOperationException("Buffer is already mapped.");
            }

            IsMapped = true;

            MapLocation = GL.MapNamedBufferRange(Handle, IntPtr.Zero, SizeInBytes, mask);
            return(MapLocation);
        }
示例#4
0
        /// <summary>
        /// Map a portion of the buffer to program memory for writing/reading
        /// </summary>
        /// <param name="bufferAccess"></param>
        /// <param name="start">Element to start at</param>
        /// <param name="count"></param>
        public unsafe IntPtr Map(BufferAccessMask bufferAccess, long start, long count)
        {
            this.Assert();

            Bind(BufferTarget.ArrayBuffer);
            return(GL.MapBufferRange(
                       BufferTarget.ArrayBuffer,
                       (IntPtr)(start * TypeInfo <T> .TypeSize),
                       (IntPtr)(count * TypeInfo <T> .TypeSize),
                       bufferAccess
                       ));
        }
        public PersistentBufferObject(BufferUsageHint hint, UInt32 size)
            : base(BufferTarget.ArrayBuffer, hint)
        {
            mySize = size;
            bind();
            BufferStorageFlags flags = BufferStorageFlags.MapWriteBit | BufferStorageFlags.MapPersistentBit | BufferStorageFlags.MapCoherentBit;

            GL.BufferStorage(BufferTarget.ArrayBuffer, new IntPtr(size), IntPtr.Zero, flags);
            BufferAccessMask flags2 = BufferAccessMask.MapWriteBit | BufferAccessMask.MapPersistentBit | BufferAccessMask.MapCoherentBit;

            myPtr = GL.MapBufferRange(BufferTarget.ArrayBuffer, IntPtr.Zero, new IntPtr(size), flags2);
            unbind();
        }
示例#6
0
        internal BufferMap(BaseBuffer buffer, int first, int count, BufferAccessMask access)
        {
            this.buffer = buffer;
            this.count  = count;
            this.offset = new IntPtr(first * Size);

            if (buffer.GetInt32(BufferParameterName.BufferMapped) != 0)
            {
                throw new Exception("The buffer is already mapped.");
            }
            using (buffer.Lock())
                this.pointer = GL.MapBufferRange(buffer.Target, offset, new IntPtr(count * Size), access);
        }
示例#7
0
        ///<summary> Begin a write. Select position and size. (datasize=0=all buffer).
        /// Buffer access mask decides what to keep about the range, default is to wipe the mapped area. Use 0 in bam not to do this. Trap for young players here</summary>
        public void StartWrite(int fillpos, int datasize = 0, BufferAccessMask bufferaccessmask = BufferAccessMask.MapInvalidateRangeBit)
        {
            if (datasize == 0)
            {
                datasize = Length - fillpos;
            }

            System.Diagnostics.Debug.Assert(mapmode == MapMode.None && fillpos >= 0 && fillpos + datasize <= Length); // catch double maps
            System.Diagnostics.Debug.Assert(context == GLStatics.GetContext(), "Context incorrect");                  // safety

            CurrentPtr = GL.MapNamedBufferRange(Id, (IntPtr)fillpos, datasize, BufferAccessMask.MapWriteBit | bufferaccessmask);

            CurrentPos = fillpos;
            mapmode    = MapMode.Write;
            GLStatics.Check();
        }
示例#8
0
        void CreateMappableBuffer()
        {
//			int localBuffer = GL.GenBuffer ();
//			GL.BindBuffer( BufferTarget.ElementArrayBuffer, localBuffer);
//
            var indices = new ushort[] { 0, 1, 2, 1, 2, 3 };
//
//			var bufferSize = (IntPtr)(indices.Length * sizeof(ushort));
//			GL.BufferData (BufferTarget.ElementArrayBuffer, bufferSize, IntPtr.Zero, BufferUsageHint.DynamicDraw);
//			GL.Arb.BufferStorage(
//
//			IntPtr VideoMemoryIntPtr = GL.Ext.MapNamedBufferRange(localBuffer, IntPtr.Zero, bufferSize, BufferAccessMask.MapWriteBit);
//			GL.Ext.UnmapNamedBuffer(localBuffer);
//
//			GL.DeleteBuffer (localBuffer);
            var buffers = new int[1];

            // ARB_direct_state_access
            // Allows buffer objects to be initialised without binding them
            GL.CreateBuffers(1, buffers);
            var targetType = BufferTarget.ElementArrayBuffer;
            //GL.BindBuffer (targetType, buffers[0]);
            var bufferSize           = (indices.Length * sizeof(ushort));
            BufferStorageFlags flags = BufferStorageFlags.MapCoherentBit;

            GL.NamedBufferStorage(buffers[0], bufferSize, IntPtr.Zero, BufferStorageFlags.MapWriteBit | BufferStorageFlags.MapPersistentBit | BufferStorageFlags.MapCoherentBit);

            var error = GL.GetError();

            Debug.WriteLineIf(error != ErrorCode.NoError, "NamedBufferStorage " + error);

            BufferAccessMask rangeFlags = BufferAccessMask.MapWriteBit | BufferAccessMask.MapPersistentBit | BufferAccessMask.MapCoherentBit;
            IntPtr           Handle     = GL.MapNamedBufferRange(buffers[0], IntPtr.Zero, bufferSize, rangeFlags);

            error = GL.GetError();
            Debug.WriteLineIf(error != ErrorCode.NoError, "MapNamedBufferRange " + error);

            var result = GL.Ext.UnmapNamedBuffer(buffers[0]);

            error = GL.GetError();
            Debug.WriteLineIf(error != ErrorCode.NoError, "UnmapNamedBuffer " + error);


            GL.DeleteBuffer(buffers[0]);
        }
示例#9
0
        public GraphicsBuffer(
            BufferTarget target,
            BufferStorageFlags storageFlags =
            BufferStorageFlags.MapReadBit | BufferStorageFlags.MapWriteBit | BufferStorageFlags.DynamicStorageBit |
            BufferStorageFlags.MapCoherentBit | BufferStorageFlags.MapPersistentBit,
            BufferAccessMask accessMask =
            BufferAccessMask.MapReadBit | BufferAccessMask.MapWriteBit |
            BufferAccessMask.MapCoherentBit | BufferAccessMask.MapPersistentBit)
        {
            Target       = target;
            StorageFlags = storageFlags;
            AccessMask   = accessMask;

            Cursor = 0;
            Length = DefaultLength;

            Allocate();
        }
示例#10
0
        public Result MapMemory(IMgDevice device, ulong offset, ulong size, uint flags, out IntPtr ppData)
        {
            if (mIsHostCached)
            {
                if (offset > (ulong)Int32.MaxValue)
                {
                    throw new ArgumentOutOfRangeException("offset >= Int32.MaxValue");
                }

                var handleOffset = (Int32)offset;
                ppData    = IntPtr.Add(mHandle, handleOffset);
                mIsMapped = true;
                return(Result.SUCCESS);
            }
            else
            {
                if (offset >= (ulong)Int64.MaxValue)
                {
                    throw new ArgumentOutOfRangeException("offset >= Int64.MaxValue");
                }

                if (size >= (ulong)int.MaxValue)
                {
                    throw new ArgumentOutOfRangeException("size >= Int64.MaxValue");
                }

                var handleOffset = (IntPtr)((Int64)offset);
                var handleSize   = (int)size;

                // TODO: flags translate
                BufferAccessMask rangeFlags = BufferAccessMask.MapWriteBit | BufferAccessMask.MapPersistentBit | BufferAccessMask.MapCoherentBit;
                ppData = GL.MapNamedBufferRange(mBufferId, IntPtr.Zero, handleSize, rangeFlags);

                mErrHandler.LogGLError("GL.MapNamedBufferRange");

                //ppData = GL.Ext.MapNamedBufferRange(BufferId, handleOffset, handleSize, BufferAccessMask.MapWriteBit | BufferAccessMask.MapCoherentBit);


                mIsMapped = true;
                return(Result.SUCCESS);
            }
        }
示例#11
0
        public void StartMapping(BufferTarget target = BufferTarget.ArrayBuffer, bool invalidate = false)
        {
            const BufferAccessMask access = BufferAccessMask.MapWriteBit | BufferAccessMask.MapUnsynchronizedBit;

            if (_mapping)
            {
                return;
            }
            Bind(target);
            unsafe {
                var newAccess = access;
                if (invalidate)
                {
                    newAccess |= BufferAccessMask.MapInvalidateBufferBit;
                }

                _pointer = GL.MapBufferRange(target, IntPtr.Zero, _size, newAccess).ToPointer();
            }

            _mapping = true;
        }
示例#12
0
        /// <summary>
        /// Start mapping the memory of the buffer.
        /// </summary>
        public unsafe void StartMapping(int byteOffset = 0, uint length = 0, BufferAccessMask mask = BufferAccessMask.MapWriteBit)
        {
            if (Mapping)
            {
                Engine.Log.Warning("Tried to start mapping a buffer which is already mapping.", MessageSource.GL);
                return;
            }

            if (Size == 0)
            {
                Engine.Log.Warning("Tried to start mapping a buffer with no memory.", MessageSource.GL);
                return;
            }

            if (length == 0)
            {
                length = Size;
            }

            if (Engine.Renderer.Dsa)
            {
                _mappingPtr = (byte *)Gl.MapNamedBufferRange(Pointer, (IntPtr)byteOffset, length, mask);
            }
            else
            {
                EnsureBound(Pointer, Type);
                _mappingPtr = (byte *)Gl.MapBufferRange(Type, (IntPtr)byteOffset, length, mask);
            }

            if ((IntPtr)_mappingPtr == IntPtr.Zero)
            {
                Engine.Log.Warning("Couldn't start mapping buffer. Expect a crash.", MessageSource.GL);
                Debug.Assert(false);
            }

            Mapping = true;
        }
示例#13
0
        public StreamBuffer(string name, BufferTarget target, int size, BufferStorageFlags flags = BufferStorageFlags.MapWriteBit, BufferAccessMask mask = (BufferAccessMask)0, int bufferingLevel = 3)
        {
            Size = size;

            TotalBytesPerFrame += size;

            _bufferingLevel = bufferingLevel;
            _fences         = new FenceSync[bufferingLevel];
            _handle         = GL.GenBuffer();
            GL.BindBuffer(target, _handle);
            GL.BufferStorage(target, new IntPtr(size * bufferingLevel), IntPtr.Zero,
                             (BufferStorageFlags)flags | BufferStorageFlags.MapPersistentBit);
            Glob.Utils.SetObjectLabel(ObjectLabelIdentifier.Buffer, _handle, name);

            var accessFlags = (BufferAccessMask)0;

            if (flags.HasFlag(BufferStorageFlags.MapWriteBit))
            {
                accessFlags = accessFlags | BufferAccessMask.MapWriteBit;
            }
            if (flags.HasFlag(BufferStorageFlags.MapReadBit))
            {
                accessFlags = accessFlags | BufferAccessMask.MapReadBit;
            }

            _bufferPointer = GL.MapBufferRange(target, IntPtr.Zero, new IntPtr(size * bufferingLevel),
                                               accessFlags | mask | BufferAccessMask.MapPersistentBit);
        }
示例#14
0
 public IntPtr MapRange(BufferAccessMask mask)
 {
     return(IGL.Primary.MapBufferRange((int)BufferTarget.ShaderStorageBuffer, IntPtr.Zero, lastKnownSize, (int)mask));
 }
示例#15
0
        void CreateVAOs()
        {
            int[] result = new int[1];
            GL.CreateVertexArrays(1, result);

            Debug.Assert(GL.IsVertexArray(result[0]));
            mRender_VertexArray = result[0];

            var indexOffset = IntPtr.Zero;
            var indexSize   = sizeof(uint) * indicesVboData.Length;

            var bufferIndex = 0;

            GL.VertexArrayElementBuffer(mRender_VertexArray, mRender_VBO_position);

            var positionOffset = new IntPtr(indexSize);

            GL.VertexArrayVertexBuffer(mRender_VertexArray, bufferIndex, mRender_VBO_position, positionOffset, Vector3.SizeInBytes);


            var stride       = Marshal.SizeOf(typeof(Vector3));
            int positionSize = stride * positionVboData.Length;

            var positionIndex = 0;

            GL.VertexArrayAttribBinding(mRender_VertexArray, positionIndex, bufferIndex);
            GL.EnableVertexArrayAttrib(mRender_VertexArray, positionIndex);
            GL.VertexArrayAttribFormat(mRender_VertexArray, positionIndex, 3, VertexAttribType.Float, true, 0);

            // SAME DATA
            var normalOffset = positionOffset;
            var normalSize   = positionSize;
            var normalIndex  = 1;

            GL.VertexArrayAttribBinding(mRender_VertexArray, normalIndex, bufferIndex);
            GL.EnableVertexArrayAttrib(mRender_VertexArray, normalIndex);
            //GL.VertexArrayVertexBuffer (vaoHandle, normalIndex, positionVboHandle, positionOffset, Vector3.SizeInBytes);
            GL.VertexArrayAttribFormat(mRender_VertexArray, normalIndex, 3, VertexAttribType.Float, true, 0);


            BufferAccessMask rangeFlags = BufferAccessMask.MapWriteBit | BufferAccessMask.MapPersistentBit | BufferAccessMask.MapCoherentBit;
            var indexDest = GL.MapNamedBufferRange(mRender_VBO_position, indexOffset, indexSize, rangeFlags);
            // Copy here
            const int START_INDEX = 0;

            Marshal.Copy(indicesVboData, START_INDEX, indexDest, indicesVboData.Length);
            GL.Ext.UnmapNamedBuffer(mRender_VBO_position);

            // Copy here
            IntPtr vertexDest = GL.MapNamedBufferRange(mRender_VBO_position, positionOffset, positionSize, rangeFlags);

            // Copy the struct to unmanaged memory.
            int copyOffset   = 0;
            int elementCount = positionVboData.Length;
            var dest         = vertexDest;
            var data         = positionVboData;
            var startIndex   = 0;

            for (int i = 0; i < elementCount; ++i)
            {
                IntPtr localDest = IntPtr.Add(dest, copyOffset);
                Marshal.StructureToPtr(data[i + startIndex], localDest, false);
                copyOffset += stride;
            }

            GL.Ext.UnmapNamedBuffer(mRender_VBO_position);

            {
                var error = GL.GetError();
                //Debug.WriteLineIf (error != ErrorCode.NoError, "GL.Ext.UnmapNamedBuffer " + error);
            }
        }
示例#16
0
        void CreateVAOs()
        {
            int[] result = new int[1];
            GL.CreateVertexArrays(1, result);

            Debug.Assert(GL.IsVertexArray(result [0]));
            vaoHandle = result [0];


            // GL3 allows us to store the vertex layout in a "vertex array object" (VAO).
            // This means we do not have to re-issue VertexAttribPointer calls
            // every time we try to use a different vertex layout - these calls are
            // stored in the VAO so we simply need to bind the correct VAO.
            //GL.BindVertexArray(vaoHandle);

            var indexOffset = IntPtr.Zero;
            var indexSize   = sizeof(uint) * indicesVboData.Length;

            var bufferIndex = 0;

            GL.VertexArrayElementBuffer(vaoHandle, positionVboHandle);

            var positionOffset = new IntPtr(indexSize);

            GL.VertexArrayVertexBuffer(vaoHandle, bufferIndex, positionVboHandle, positionOffset, Vector3.SizeInBytes);

            //GL.BindBufferRange(BufferTarget.ElementArrayBuffer, 0, positionVboHandle, indexOffset, indexSize);

//			GL.EnableVertexAttribArray(0);
//            GL.BindBuffer(BufferTarget.ArrayBuffer, positionVboHandle);


            var stride       = Marshal.SizeOf(typeof(Vector3));
            int positionSize = stride * positionVboData.Length;

            var positionIndex = 0;

            GL.VertexArrayAttribBinding(vaoHandle, positionIndex, bufferIndex);
            GL.EnableVertexArrayAttrib(vaoHandle, positionIndex);
            GL.VertexArrayAttribFormat(vaoHandle, positionIndex, 3, VertexAttribType.Float, true, 0);
            //GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, true, Vector3.SizeInBytes, positionOffset);

//            GL.EnableVertexAttribArray(1);
//			GL.BindBuffer(BufferTarget.ArrayBuffer, positionVboHandle);

            // SAME DATA
            var normalOffset = positionOffset;
            var normalSize   = positionSize;
            var normalIndex  = 1;

            //GL.VertexArrayAttribFormat (vaoHandle, 0, 3, VertexAttribType.Float, true, positionOffset);
            //GL.VertexAttribPointer(1, 3, VertexAttribPointerType.Float, true, Vector3.SizeInBytes, normalOffset);

            GL.VertexArrayAttribBinding(vaoHandle, normalIndex, bufferIndex);
            GL.EnableVertexArrayAttrib(vaoHandle, normalIndex);
            //GL.VertexArrayVertexBuffer (vaoHandle, normalIndex, positionVboHandle, positionOffset, Vector3.SizeInBytes);
            GL.VertexArrayAttribFormat(vaoHandle, normalIndex, 3, VertexAttribType.Float, true, 0);


            BufferAccessMask rangeFlags = BufferAccessMask.MapWriteBit | BufferAccessMask.MapPersistentBit | BufferAccessMask.MapCoherentBit;
            var indexDest = GL.MapNamedBufferRange(positionVboHandle, indexOffset, indexSize, rangeFlags);
            // Copy here
            const int START_INDEX = 0;

            Marshal.Copy(indicesVboData, START_INDEX, indexDest, indicesVboData.Length);
            GL.Ext.UnmapNamedBuffer(positionVboHandle);

            // Copy here
            IntPtr vertexDest = GL.MapNamedBufferRange(positionVboHandle, positionOffset, positionSize, rangeFlags);

            // Copy the struct to unmanaged memory.
            int copyOffset   = 0;
            int elementCount = positionVboData.Length;
            var dest         = vertexDest;
            var data         = positionVboData;
            var startIndex   = 0;

            for (int i = 0; i < elementCount; ++i)
            {
                IntPtr localDest = IntPtr.Add(dest, copyOffset);
                Marshal.StructureToPtr(data[i + startIndex], localDest, false);
                copyOffset += stride;
            }

            GL.Ext.UnmapNamedBuffer(positionVboHandle);

            {
                var error = GL.GetError();
                //Debug.WriteLineIf (error != ErrorCode.NoError, "GL.Ext.UnmapNamedBuffer " + error);
            }

            // Copy here

//			var normalDest = GL.MapNamedBufferRange (positionVboHandle, normalOffset, normalSize, rangeFlags);
//
//			GL.Ext.UnmapNamedBuffer (positionVboHandle);


            // GL.BindVertexArray(0);
        }
示例#17
0
        /// <summary>
        /// Map a range of the GPU buffer allocated by this Buffer.
        /// </summary>
        /// <param name="ctx">
        /// A <see cref="GraphicsContext"/> required for mapping this Buffer.
        /// </param>
        /// <param name="mask">
        /// A <see cref="BufferAccessMask"/> that specify the map access.
        /// </param>
        /// <exception cref="InvalidOperationException">
        /// Exception thrown if this Buffer is already mapped.
        /// </exception>
        /// <exception cref="InvalidOperationException">
        /// Exception thrown if this Buffer does not exist for <paramref name="ctx"/>.
        /// </exception>
        public void Map(GraphicsContext ctx, BufferAccessMask mask, IntPtr offset = default(IntPtr), uint size = 0)
        {
            CheckThisExistence(ctx);

            uint mapSize = size != 0 ? size : Size;

            if (IsMapRangeSupported(ctx))
            {
#if !MONODROID
                if (ctx.Extensions.DirectStateAccess_ARB || ctx.Version.IsCompatible(Gl.Version_450))
                {
                    if ((MappedBuffer = Gl.MapNamedBufferRange(ObjectName, offset, mapSize, mask)) == IntPtr.Zero)
                    {
                        Gl.CheckErrors();
                    }
                }
                else
                {
#endif
                ctx.Bind(this);

                if ((MappedBuffer = Gl.MapBufferRange(Target, offset, mapSize, mask)) == IntPtr.Zero)
                {
                    Gl.CheckErrors();
                }
#if !MONODROID
            }
#endif
            }
            else
            {
                if (GpuBuffer == null)
                {
                    throw new GlException(ErrorCode.InvalidOperation);
                }
                if (GpuBuffer.AlignedBuffer == IntPtr.Zero)
                {
                    throw new GlException(ErrorCode.InvalidOperation);
                }

                MappedBuffer = new IntPtr(GpuBuffer.AlignedBuffer.ToInt64() + offset.ToInt64());
            }

            // Determine map access
            if (mask.HasFlag(BufferAccessMask.MapReadBit) && mask.HasFlag(BufferAccessMask.MapWriteBit))
            {
                _Access = BufferAccess.ReadWrite;
            }
            else if (mask.HasFlag(BufferAccessMask.MapReadBit))
            {
                _Access = BufferAccess.ReadOnly;
            }
            else if (mask.HasFlag(BufferAccessMask.MapWriteBit))
            {
                _Access = BufferAccess.WriteOnly;
            }
            else
            {
                _Access = 0;
            }

            Debug.Assert(MappedBuffer != IntPtr.Zero);

            MapOffset   = offset;
            MapSize     = mapSize;
            _AccessMask = mask;
        }
示例#18
0
 public MappedBuffer(uint id, BufferAccessMask mask)
 {
     ID   = id;
     Mask = mask;
     Map();
 }
示例#19
0
		public static IntPtr MapBufferRange(BufferTarget target, IntPtr offset, IntPtr length, BufferAccessMask access)
		{
			glMapBufferRange deleg = BaseGraphicsContext.Current.Loader.Get<glMapBufferRange>();
			if (deleg != null)
				return deleg(target, offset, length, access);
			return default(IntPtr);
		}