AppCode -> ByteBufAllocator.DEFAULT:ioBuffer
ByteBufAllocator -> PoolArena: allocate
== instant a bytebuf object ==
PoolArena -> DirectArena: newByteBuf
DirectArena -> PooledUnsafeDirectByteBuf:newInstance
PooledUnsafeDirectByteBuf -> Recycler: get
PooledUnsafeDirectByteBuf <-- Recycler : PooledUnsafeDirectByteBuf
PooledUnsafeDirectByteBuf -> PooledUnsafeDirectByteBuf: reuse
note left
设置最大容量
被引用数置一
writeIndex 和 readIndex 归零
markReadIndex和markWriteIndex归零
end note
== allocate ==
PoolArena -> PoolArena: allocate(PoolThreadCache, byteBuf, reqCap)
PoolArena -> PoolArena: normalizeCapacity(reqCap)
note left
规范化请求内存大小,
由于内存管理被按照标准大小(tiny (<512), 512<small <8192, normal)
每一块都是2的N次幂大小
规范会内存大小 就是把请求内存大小变成最近的2的N次幂大小
end note
PoolArena -> PoolArena: 计算small table index
PoolArena -> PoolArena: 获取small table head
PoolArena -> PoolArena: allocateNormal
note right
先从 qInit q000 q025
q050 q075 检查分配,
如果以上都没有成功分配
创建一个 chunk
用新创建的chunk分配给 byteBuf
并将该chunk放到 qInit中去
end note
PoolArena ->PoolChunk:allocate
== 大对象(大于等于page)分配==
PoolArena -> PoolChunk: allocateRun
==小对象(不大于chunk)分配==
PoolArena ->PoolChunk:allocateSubpage
PoolChunk -> PoolSubPage: new
PoolChunk -> PoolSubPage:allocate
PoolChunk -> PoolChunk.initBuf(buf, handle, reqCap)
note right
这一步实际上是将一个byteBuf 关联到 chunk 对应的 jdk nio的byteBuffer
一个chunk 的实际存储是关联到一个nio的byteBuffer
那这个ByteBuf 实际上是byteBuffer的adress + offset
每个directByteBuf都有一个address
这个【address ,address+ writeIndex 】的字节数组就是已写入的数据
end note