コード例 #1
0
ファイル: LogBuffers.cs プロジェクト: malat/Aeron.NET
        public LogBuffers(string logFileName)
        {
            var fileInfo = new FileInfo(logFileName);

            var logLength  = fileInfo.Length;
            var termLength = LogBufferDescriptor.ComputeTermLength(logLength);

            LogBufferDescriptor.CheckTermLength(termLength);

            _termLength = termLength;

            // if log length exceeds MAX_INT we need multiple mapped buffers, (see FileChannel.map doc).
            if (logLength < int.MaxValue)
            {
                var mappedBuffer = IoUtil.MapExistingFile(logFileName);

                _mappedByteBuffers = new[] { mappedBuffer };

                var metaDataSectionOffset = termLength * LogBufferDescriptor.PARTITION_COUNT;

                for (var i = 0; i < LogBufferDescriptor.PARTITION_COUNT; i++)
                {
                    var metaDataOffset = metaDataSectionOffset + (i * LogBufferDescriptor.TERM_META_DATA_LENGTH);

                    _atomicBuffers[i] = new UnsafeBuffer(mappedBuffer.Pointer, i * termLength, termLength);
                    _atomicBuffers[i + LogBufferDescriptor.PARTITION_COUNT] = new UnsafeBuffer(mappedBuffer.Pointer, metaDataOffset, LogBufferDescriptor.TERM_META_DATA_LENGTH);
                }

                _atomicBuffers[_atomicBuffers.Length - 1] = new UnsafeBuffer(mappedBuffer.Pointer, (int)(logLength - LogBufferDescriptor.LOG_META_DATA_LENGTH), LogBufferDescriptor.LOG_META_DATA_LENGTH);
            }
            else
            {
                _mappedByteBuffers = new MappedByteBuffer[LogBufferDescriptor.PARTITION_COUNT + 1];
                var metaDataSectionOffset = termLength * (long)LogBufferDescriptor.PARTITION_COUNT;
                var metaDataSectionLength = (int)(logLength - metaDataSectionOffset);

                var memoryMappedFile     = IoUtil.OpenMemoryMappedFile(logFileName);
                var metaDataMappedBuffer = new MappedByteBuffer(memoryMappedFile, metaDataSectionOffset, metaDataSectionLength);

                _mappedByteBuffers[_mappedByteBuffers.Length - 1] = metaDataMappedBuffer;

                for (var i = 0; i < LogBufferDescriptor.PARTITION_COUNT; i++)
                {
                    _mappedByteBuffers[i] = new MappedByteBuffer(memoryMappedFile, termLength * (long)i, termLength);

                    _atomicBuffers[i] = new UnsafeBuffer(_mappedByteBuffers[i].Pointer, termLength);
                    _atomicBuffers[i + LogBufferDescriptor.PARTITION_COUNT] = new UnsafeBuffer(metaDataMappedBuffer.Pointer, i * LogBufferDescriptor.TERM_META_DATA_LENGTH, LogBufferDescriptor.TERM_META_DATA_LENGTH);
                }

                _atomicBuffers[_atomicBuffers.Length - 1] = new UnsafeBuffer(metaDataMappedBuffer.Pointer, metaDataSectionLength - LogBufferDescriptor.LOG_META_DATA_LENGTH, LogBufferDescriptor.LOG_META_DATA_LENGTH);
            }

            // TODO try/catch

            foreach (var buffer in _atomicBuffers)
            {
                buffer.VerifyAlignment();
            }
        }
コード例 #2
0
        /// <summary>
        /// Set the length of buffer used for each term of the log. Valid values are powers of 2 in the 64K - 1G range.
        /// </summary>
        /// <param name="termLength"> of the buffer used for each term of the log. </param>
        /// <returns> this for a fluent API. </returns>
        /// <seealso cref="Aeron.Context.TERM_LENGTH_PARAM_NAME"/>
        public ChannelUriStringBuilder TermLength(int?termLength)
        {
            if (null != termLength)
            {
                LogBufferDescriptor.CheckTermLength(termLength.Value);
            }

            _termLength = termLength;
            return(this);
        }
コード例 #3
0
        public LogBuffers(string logFileName, int termLength = LogBufferDescriptor.TERM_MIN_LENGTH)
        {
            try {
                long logLength = LogBufferDescriptor.PARTITION_COUNT *
                                 (LogBufferDescriptor.TERM_META_DATA_LENGTH + termLength) +
                                 LogBufferDescriptor.LOG_META_DATA_LENGTH;
                termLength = LogBufferDescriptor.ComputeTermLength(logLength);
                LogBufferDescriptor.CheckTermLength(termLength);
                _df         = new DirectFile(logFileName, logLength);
                _termLength = termLength;

                // if log length exceeds MAX_INT we need multiple mapped buffers, (see FileChannel.map doc).
                if (logLength < int.MaxValue)
                {
                    int metaDataSectionOffset = termLength * LogBufferDescriptor.PARTITION_COUNT;

                    for (int i = 0; i < LogBufferDescriptor.PARTITION_COUNT; i++)
                    {
                        int metaDataOffset = metaDataSectionOffset + (i * LogBufferDescriptor.TERM_META_DATA_LENGTH);

                        _buffers[i] = new DirectBuffer(termLength, _df.Buffer.Data + i * termLength);
                        _buffers[i + LogBufferDescriptor.PARTITION_COUNT] = new DirectBuffer(LogBufferDescriptor.TERM_META_DATA_LENGTH, _df.Buffer.Data + metaDataOffset);
                        _partitions[i] = new LogBufferPartition(_buffers[i], _buffers[i + LogBufferDescriptor.PARTITION_COUNT]);
                    }

                    _buffers[_buffers.Length - 1] = new DirectBuffer(LogBufferDescriptor.LOG_META_DATA_LENGTH,
                                                                     _df.Buffer.Data + (int)(logLength - LogBufferDescriptor.LOG_META_DATA_LENGTH));
                }
                else
                {
                    throw new NotImplementedException("TODO Check .NET mapping limit");
                }
            } catch (IOException ex) {
                throw new AggregateException(ex);
            }

            foreach (var buffer in _buffers)
            {
                buffer.VerifyAlignment(8);
            }
        }
コード例 #4
0
        /// <summary>
        /// Construct the log buffers for a given log file.
        /// </summary>
        /// <param name="logFileName"></param>
        public LogBuffers(string logFileName)
        {
            try
            {
                var fileInfo = new FileInfo(logFileName);

                var logLength = fileInfo.Length;

                // if log length exceeds MAX_INT we need multiple mapped buffers, (see FileChannel.map doc).
                if (logLength < int.MaxValue)
                {
                    var mappedBuffer = IoUtil.MapExistingFile(logFileName, MapMode.ReadWrite); // TODO Java has sparse hint & Little Endian
                    _mappedByteBuffers = new[] { mappedBuffer };

                    _logMetaDataBuffer = new UnsafeBuffer(mappedBuffer.Pointer,
                                                          (int)(logLength - LogBufferDescriptor.LOG_META_DATA_LENGTH),
                                                          LogBufferDescriptor.LOG_META_DATA_LENGTH);

                    int termLength = LogBufferDescriptor.TermLength(_logMetaDataBuffer);
                    int pageSize   = LogBufferDescriptor.PageSize(_logMetaDataBuffer);

                    LogBufferDescriptor.CheckTermLength(termLength);
                    LogBufferDescriptor.CheckPageSize(pageSize);

                    _termLength = termLength;

                    for (var i = 0; i < LogBufferDescriptor.PARTITION_COUNT; i++)
                    {
                        _termBuffers[i] = new UnsafeBuffer(mappedBuffer.Pointer, i * termLength, termLength);
                    }
                }
                else
                {
                    _mappedByteBuffers = new MappedByteBuffer[LogBufferDescriptor.PARTITION_COUNT + 1];

                    int  assumedTermLength     = LogBufferDescriptor.TERM_MAX_LENGTH;
                    long metaDataSectionOffset = assumedTermLength * (long)LogBufferDescriptor.PARTITION_COUNT;
                    long metaDataMappingLength = logLength - metaDataSectionOffset;

                    var memoryMappedFile = IoUtil.OpenMemoryMappedFile(logFileName);

                    var metaDataMappedBuffer =
                        new MappedByteBuffer(memoryMappedFile, metaDataSectionOffset, metaDataMappingLength);  // Little Endian

                    _mappedByteBuffers[LogBufferDescriptor.LOG_META_DATA_SECTION_INDEX] = metaDataMappedBuffer;
                    _logMetaDataBuffer = new UnsafeBuffer(
                        metaDataMappedBuffer.Pointer,
                        (int)metaDataMappingLength - LogBufferDescriptor.LOG_META_DATA_LENGTH,
                        LogBufferDescriptor.LOG_META_DATA_LENGTH);

                    int metaDataTermLength = LogBufferDescriptor.TermLength(_logMetaDataBuffer);
                    int pageSize           = LogBufferDescriptor.PageSize(_logMetaDataBuffer);

                    LogBufferDescriptor.CheckPageSize(pageSize);
                    if (metaDataTermLength != assumedTermLength)
                    {
                        throw new InvalidOperationException(
                                  $"assumed term length {assumedTermLength} does not match metadta: termLength = {metaDataTermLength}");
                    }

                    _termLength = assumedTermLength;

                    for (var i = 0; i < LogBufferDescriptor.PARTITION_COUNT; i++)
                    {
                        long position = assumedTermLength * (long)i;

                        _mappedByteBuffers[i] = new MappedByteBuffer(memoryMappedFile, position, assumedTermLength); // Little Endian
                        _termBuffers[i]       = new UnsafeBuffer(_mappedByteBuffers[i].Pointer, 0, assumedTermLength);
                    }
                }
            }
            catch (InvalidOperationException ex)
            {
                Dispose();
                throw ex;
            }
        }