/// <summary> /// Maps a file into a set of buffers </summary> internal virtual ByteBuffer[] Map(MMapIndexInput input, FileStream fc, long offset, long length) { if (Number.URShift(length, chunkSizePower) >= int.MaxValue) { throw new ArgumentException("RandomAccessFile too big for chunk size: " + fc.ToString()); } // LUCENENET specific: Return empty buffer if length is 0, rather than attempting to create a MemoryMappedFile. // Part of a solution provided by Vincent Van Den Berghe: http://apache.markmail.org/message/hafnuhq2ydhfjmi2 if (length == 0) { return(new[] { ByteBuffer.Allocate(0).AsReadOnlyBuffer() }); } long chunkSize = 1L << chunkSizePower; // we always allocate one more buffer, the last one may be a 0 byte one int nrBuffers = (int)((long)((ulong)length >> chunkSizePower)) + 1; ByteBuffer[] buffers = new ByteBuffer[nrBuffers]; if (input.memoryMappedFile == null) { input.memoryMappedFile = MemoryMappedFile.CreateFromFile( fileStream: fc, mapName: null, capacity: length, access: MemoryMappedFileAccess.Read, #if !NETSTANDARD memoryMappedFileSecurity: null, #endif inheritability: HandleInheritability.Inheritable, leaveOpen: true); // LUCENENET: We explicitly dispose the FileStream separately. } long bufferStart = 0L; for (int bufNr = 0; bufNr < nrBuffers; bufNr++) { int bufSize = (int)((length > (bufferStart + chunkSize)) ? chunkSize : (length - bufferStart)); // LUCENENET: We get an UnauthorizedAccessException if we create a 0 byte file at the end of the range. // See: https://stackoverflow.com/a/5501331 // We can fix this by moving back 1 byte on the offset if the bufSize is 0. int adjust = 0; if (bufSize == 0 && bufNr == (nrBuffers - 1) && (offset + bufferStart) > 0) { adjust = 1; } buffers[bufNr] = new MemoryMappedFileByteBuffer( input.memoryMappedFile.CreateViewAccessor( offset: (offset + bufferStart) - adjust, size: bufSize, access: MemoryMappedFileAccess.Read), bufSize); bufferStart += bufSize; } return(buffers); }
// Closing a file closes its channel. private static ByteBuffer MapFile(FileInfo path) { MemoryMappedFile file; try { //file = new FileStream(path.FullName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); file = MemoryMappedFile.CreateFromFile(path.FullName); var channel = file.CreateViewAccessor(); //FileChannel channel = file.getChannel(); ByteBuffer bytes = null; try { //bytes = channel.map(FileChannel.MapMode.READ_ONLY, 0, channel.size()); bytes = new MemoryMappedFileByteBuffer(channel, 0, 0); } finally { file.Dispose(); channel.Dispose(); } return(bytes); } catch (FileNotFoundException ignored) { Console.Error.WriteLine(ignored); } catch (IOException ignored) { Console.Error.WriteLine(ignored); } return(null); }
/// <summary> /// Maps a file into a set of buffers </summary> internal virtual ByteBuffer[] Map(MMapIndexInput input, FileStream fc, long offset, long length) { if (Number.URShift(length, chunkSizePower) >= int.MaxValue) { throw new ArgumentException("RandomAccessFile too big for chunk size: " + fc.ToString()); } long chunkSize = 1L << chunkSizePower; // we always allocate one more buffer, the last one may be a 0 byte one int nrBuffers = (int)((long)((ulong)length >> chunkSizePower)) + 1; ByteBuffer[] buffers = new ByteBuffer[nrBuffers]; /* * public static MemoryMappedFile CreateFromFile(FileStream fileStream, String mapName, Int64 capacity, * MemoryMappedFileAccess access, MemoryMappedFileSecurity memoryMappedFileSecurity, * HandleInheritability inheritability, bool leaveOpen) */ long fileCapacity = length == 0 ? ushort.MaxValue : length; if (input.memoryMappedFile == null) { #if NETSTANDARD input.memoryMappedFile = MemoryMappedFile.CreateFromFile(fc, null, fileCapacity, MemoryMappedFileAccess.ReadWrite, HandleInheritability.Inheritable, false); #else input.memoryMappedFile = MemoryMappedFile.CreateFromFile(fc, null, fileCapacity, MemoryMappedFileAccess.ReadWrite, null, HandleInheritability.Inheritable, false); #endif } long bufferStart = 0L; for (int bufNr = 0; bufNr < nrBuffers; bufNr++) { int bufSize = (int)((length > (bufferStart + chunkSize)) ? chunkSize : (length - bufferStart)); // LUCENENET: We get a file access exception if we create a 0 byte file at the end of the range. // We can fix this by moving back 1 byte if the bufSize is 0. int adjust = 0; if (bufSize == 0 && bufNr == (nrBuffers - 1) && (offset + bufferStart) > 0) { adjust = 1; } //buffers[bufNr] = new MemoryMappedFileByteBuffer(input.memoryMappedFile.CreateViewAccessor((offset + bufferStart) - adjust, bufSize, MemoryMappedFileAccess.Read), -1, 0, bufSize, bufSize); buffers[bufNr] = new MemoryMappedFileByteBuffer(input.memoryMappedFile.CreateViewAccessor((offset + bufferStart) - adjust, bufSize, MemoryMappedFileAccess.Read), bufSize); bufferStart += bufSize; } return(buffers); }
/// <summary> /// Maps a file into a set of buffers </summary> internal virtual ByteBuffer[] Map(MMapIndexInput input, FileStream fc, long offset, long length) { if (Number.URShift(length, ChunkSizePower) >= int.MaxValue) { throw new ArgumentException("RandomAccessFile too big for chunk size: " + fc.ToString()); } long chunkSize = 1L << ChunkSizePower; // we always allocate one more buffer, the last one may be a 0 byte one int nrBuffers = (int)((long)((ulong)length >> ChunkSizePower)) + 1; ByteBuffer[] buffers = new ByteBuffer[nrBuffers]; /* * public static MemoryMappedFile CreateFromFile(FileStream fileStream, String mapName, Int64 capacity, * MemoryMappedFileAccess access, MemoryMappedFileSecurity memoryMappedFileSecurity, * HandleInheritability inheritability, bool leaveOpen) */ if (input.memoryMappedFile == null) { input.memoryMappedFile = MemoryMappedFile.CreateFromFile(fc, null, length == 0 ? 100 : length, MemoryMappedFileAccess.Read, null, HandleInheritability.Inheritable, false); } long bufferStart = 0L; for (int bufNr = 0; bufNr < nrBuffers; bufNr++) { int bufSize = (int)((length > (bufferStart + chunkSize)) ? chunkSize : (length - bufferStart)); //LUCENE TO-DO buffers[bufNr] = new MemoryMappedFileByteBuffer(input.memoryMappedFile.CreateViewAccessor(offset + bufferStart, bufSize, MemoryMappedFileAccess.Read), -1, 0, bufSize, bufSize); //buffers[bufNr] = fc.Map(FileStream.MapMode.READ_ONLY, offset + bufferStart, bufSize); bufferStart += bufSize; } return(buffers); }