Netty源码解析(4)-内存分配

ByteBuf直接与底层IO打交道

1、内存类别有哪些

2、如何减少多线程内存分配竞争

3、不同大小内存是如何分配的

内存与内存管理器的抽象

不同规格大小和不同内存类别的分配策略

内存回收

ByteBuf结构

  readerIndex,表示要读数据从当前指针开始读,从0到readerIndex这段空间表示是无效的

  writerIndex,必须大于readerIndex,表示要写数据从当前指针开始写,从readerIndex到writerIndex这段空间表示可以读的

  capacity,必须,从writerIndex到capacity这段空间表示空闲可以写的

ByteBuf API

  read,从readerIndex往后开始读

  write 从writerIndex往后开始写

  set 不移动任何指针,直接再当前指针地方进行设置

  markReaderIndex 将readerIndex进行保存起来

  resetReaderIndex 将readerIndex进行恢复,这样读数据就不会移动指针

  markWriterIndex 同上

  resetWriterIndex  同上

  readableBytes() writerIndex - readerIndex

  writeableBytes() capacity - writerIndex

ByteBuf分类

  

   Pooled和UnPooled,内存分配时从已经分配的一块内存中分配一块,有预分配过程,UnPooled就是直接向操作系统申请内存

  Unsafe和非UnSafe,Unsafe可以直接拿到内存地址,可以直接拿到ByteBuf在JVM内存通过内存地址和偏移量,非unsafe可以直接调用jdk api读写,通过数组和下标访问数据,。jdk自动判断Unsafe或者非Unsafe

  Heap和Direct,在堆上直接分配,jc自动回收管理,依赖一个数组,Direct调用jdk api分配不会被jvm内存回收管理,依赖jdk底层的ByteBuffer。

ByteBufAllocator 内存管理器

    AbstractByteBufAllocator骨架实现

      UnPooledByteBufAllocator,直接分配一个容量大小的数组

        newHeapBuffer 在堆上new一个数组出来传入并保存

        newDirectBuffer 依赖于jdk底层ByteBuffer,保存初始地址和容量。

      PooledByteBufAllocator,首先拿到线程局部缓存,PoolThreadCache先创建PoolArena<byte[]>,PoolArena<ByteBuf>这两种内存池,在线程上的Arena上进行内存分配。创建内存分配器时会创建两种类型的数组,PoolArena.HeapArena和PoolArena.directArena

        newHeapBuffer

        newDirectBuffer

猜你喜欢

转载自www.cnblogs.com/xiaofeiyang/p/12688010.html
今日推荐