Netty精粹之轻量级内存池技术实现原理与应用(3)
- UID
- 1066743
|
Netty精粹之轻量级内存池技术实现原理与应用(3)
Recycler对象池的对象存储分为两个部分,Stack的Handle数组和Stack指向的WeakOrderQueue链表。
1
2
3
| <code class="hljs cpp"><span class="hljs-keyword">private DefaultHandle[] elements;
<span class="hljs-keyword">private <span class="hljs-keyword">volatile WeakOrderQueue head;
<span class="hljs-keyword">private WeakOrderQueue cursor, prev;</span></span></span></span></code>
|
Stack保留着WeakOrderQueue链表的头指针和读游标。WeakOrderQueue链表的每个节点都是一个Link,而每个Link都维护者一个Handle数组。
池中对象的读取和写入
从对象池获取对象主要是从Stack的Handle数组,而Handle数组的后备资源来源于WeakOrderQueue链表。而elements数组和WeakOrderQueue链表中对象的来源有些区别:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| <code class="hljs cpp"><span class="hljs-function"><span class="hljs-keyword"><span class="hljs-function"><span class="hljs-keyword">public<span class="hljs-function"> <span class="hljs-keyword"><span class="hljs-function"><span class="hljs-keyword">void<span class="hljs-function"> <span class="hljs-title"><span class="hljs-function"><span class="hljs-title">recycle<span class="hljs-params"><span class="hljs-function"><span class="hljs-params">()<span class="hljs-function"> {
Thread thread = Thread.currentThread();
<span class="hljs-keyword">if (thread == <span class="hljs-built_in">stack.thread) {
<span class="hljs-built_in">stack.push(<span class="hljs-keyword">this);
<span class="hljs-keyword">return;
}
<span class="hljs-comment">// we don't want to have a ref to the queue as the value in our weak map
<span class="hljs-comment">// so we null it out; to ensure there are no races with restoring it later
<span class="hljs-comment">// we impose a memory ordering here (no-op on x86)
Map<Stack<?>, WeakOrderQueue> delayedRecycled = DELAYED_RECYCLED.get();
WeakOrderQueue <span class="hljs-built_in">queue = delayedRecycled.get(<span class="hljs-built_in">stack);
<span class="hljs-keyword">if (<span class="hljs-built_in">queue == null) {
delayedRecycled.put(<span class="hljs-built_in">stack, <span class="hljs-built_in">queue = <span class="hljs-keyword">new WeakOrderQueue(<span class="hljs-built_in">stack, thread));
}
<span class="hljs-built_in">queue.add(<span class="hljs-keyword">this);
}</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code>
|
从Handle的recycle实现看出:如果由拥有Stack的线程回收对象,则直接调用Stack的push方法将该对象直接放入Stack的数组中;如果由其他线程回收,则对象被放入线程关联的<Stack,WeakOrderQueue>的队列中,这个队列其实在这里被放入了stack关联的WeakOrderQueue链表的表头:
1
2
3
4
5
6
7
8
| <code class="hljs cpp">WeakOrderQueue(Stack<?> <span class="hljs-built_in">stack, Thread thread) {
head = tail = <span class="hljs-keyword">new Link();
owner = <span class="hljs-keyword">new WeakReference<Thread>(thread);
synchronized (<span class="hljs-built_in">stack) {
next = <span class="hljs-built_in">stack.head;
<span class="hljs-built_in">stack.head = <span class="hljs-keyword">this;
}
}</span></span></span></span></span></span></span></code>
|
每一个没有拥有stack的线程回收对象的时候都会重新创建一个WeakOrderQueue节点放入stask关联的WeakOrderQueue链表的表头,这样做最终实现了多线程回收对象统统放入stack关联的WeakOrderQueue链表中而拥有stack的线程都能够读取其他线程供给的对象。 |
|
|
|
|
|