【问题标题】:What is a TLAB (Thread Local Allocation Buffer)?什么是 TLAB(线程本地分配缓冲区)?
【发布时间】:2017-05-02 21:05:26
【问题描述】:

我找不到可以清楚地解释这个概念的综合资料。我的理解是,一个线程在分配新对象的伊甸园中获得了一些内存。一个竞争线程最终将拥有一个有点连续的伊甸园块。如果第一个线程用完其 TLAB 中的空闲区域会怎样?它会请求一个新的伊甸园吗?

【问题讨论】:

  • 关于你的最后一个问题,我猜想为线程分配了一个新的 TLAB。考虑分配 TLAB 而不是小内存块,就像一个简单的优化使频繁的工作线程在本地而不是需要锁。

标签: java garbage-collection java-memory-model


【解决方案1】:

TLAB 的想法是减少线程之间的同步需求。使用 TLAB 可以减少这种需求,因为任何线程都有一个可以使用的区域,并且期望它是唯一使用该区域的线程。假设一个 TLAB 可以容纳 100 个对象,一个线程在分配 101 个对象时只需要获取一个锁来申请更多的内存。如果没有 TLAB,每个对象都需要这样做。缺点当然是您可能会浪费空间。

大对象通常在 TLAB 之外分配,因为它们无法降低同步内存分配频率的优势。有些对象甚至可能不适合 TLAB。

您可以使用-XX:TLABSize 标志设置 TLAB 的大小,但通常我不建议您乱用这些设置,除非您真的发现了可以通过它解决的问题。

【讨论】:

  • 谢谢。 1) 当一个线程分配一个 TLAB 时,它仍然必须获得一个锁,这样竞争线程就不会在第一个线程所做的相同区域分配一个 TLAB。这个假设正确吗? 2) 在 TLAB 之外分配对象总是很昂贵,因为必须获取锁来分配每个不适合 TLAB 的新对象?
  • 想想线程 1 从偏移量 0 到 99 声明一个 TLAB,线程 2 从偏移量 100 到 199 声明一个 TLAB。合约说一旦声明,线程 2 不能在 0-99 分配,线程 1 不能分配在 100-199 之间。也没有线程可以将此空间作为其未来的分配缓冲区。这样,如果每个对象占用其中一个假设槽,则每个线程可以在不同步的情况下分配 100 个对象。在 TLAB 外部分配不是很昂贵,但显然比在 TLAB 内部更昂贵,因为它需要与可能同时运行的其他线程进行通信。
  • 对不起,如果我的问题不清楚,我会尝试换一种说法——如果两个竞争线程想要为接下来的 100 个对象分配内存,并且下一个可用内存地址从 100 开始那么第一个获得锁的人将获得从 100 到 199 的地址,第二个线程将获得 200 到 299 的地址。这是正确的吗?
  • 是的(而不是锁,而是一些 CAS 例程)。如果没有 TLAB,线程将需要对每个分配进行“双重检查”。使用 TLAB,它最多可以分配 100 个实例,而无需任何额外检查。
  • 我现在明白了。非常感谢。我想我需要阅读 CAS 例程。
猜你喜欢
  • 2014-12-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-13
  • 2014-05-30
  • 1970-01-01
  • 2012-06-21
相关资源
最近更新 更多