Spec-Zone.ru › OpenJDK 24

Интерфейс Arena

Все суперинтерфейсы:
AutoCloseable, SegmentAllocator
public interface Arena extends SegmentAllocator, AutoCloseable
Арена управляет жизненным циклом сегментов памяти, обеспечивая гибкое выделение и своевременное освобождение.

Арена имеет область — область арены. Все сегменты, выделенные арендой, связаны с областью арены. Таким образом, арена определяет временные границы всех сегментов памяти, выделенных ею.

Кроме того, арена также определяет, должен ли доступ к сегментам памяти, выделенным ей, быть ограничен определенными потоками. Арена является SegmentAllocator и имеет несколько методов выделения, которые могут быть использованы клиентами для получения нативных сегментов.

Наиболее простой арендой является глобальная арена. Глобальная арена характеризуется неограниченным сроком жизни. Областью глобальной арены является глобальная область. Таким образом, нативные сегменты, выделенные с помощью глобальной арены, всегда доступны, и их области памяти никогда не освобождаются. Более того, к сегментам памяти, выделенным с помощью глобальной арены, можно обратиться из любого потока.

 MemorySegment segment = Arena.global().allocate(100, 1);
 ...
 // segment is never deallocated!

В качестве альтернативы клиенты могут получить автоматическую арену, которая является арендой с ограниченным сроком жизни, управляемым автоматически сборщиком мусора. Областью автоматической арены является автоматическая область. Таким образом, области памяти, поддерживающие сегменты памяти, выделенные с помощью автоматической арены, освобождаются в некоторый неопределенный момент после того, как автоматическая арена (и все выделенные ею сегменты) станет недоступной, как показано ниже:

 MemorySegment segment = Arena.ofAuto().allocate(100, 1);
 ...
 segment = null; // the segment region becomes available for deallocation after this point
К сегментам памяти, выделенным с помощью автоматической арены, также можно обратиться из любого потока.

Вместо того чтобы оставлять освобождение памяти в руках среды выполнения Java, клиенты часто захотят контролировать момент освобождения областей памяти, поддерживающих сегменты памяти. Для этого предназначены два типа арен — ограниченные и совместные арены. Они оба имеют ограниченный срок жизни, который управляется вручную. Например, когда ограниченная арена закрывается успешно, ее область становится недоступной. В результате все сегменты памяти, выделенные арендой, больше недоступны, а их области памяти освобождаются:

 MemorySegment segment = null;
 try (Arena arena = Arena.ofConfined()) {
     segment = arena.allocate(100);
     ...
 } // segment region deallocated here
 segment.get(ValueLayout.JAVA_BYTE, 0); // throws IllegalStateException
К сегментам памяти, выделенным с помощью ограниченной арены, можно получить доступ (и закрыть) только из потока, который создал арену. Если доступ к сегменту памяти из нескольких потоков необходим, клиенты могут выделить сегменты в совместной арене вместо этого.

Характеристики различных арен суммированы в следующей таблице:

Характеристики арен
Тип Ограниченный срок жизни Явно закрываемая Доступна из нескольких потоков
Глобальная Нет Нет Да
Автоматическая Да Нет Да
Ограниченная Да Да Нет
Совместная Да Да Да

Безопасность и ограничение по потокам

Арены обеспечивают строгие гарантии временной безопасности: к сегменту памяти, выделенному арендой, нельзя получить доступ после закрытия арены. Стоимость обеспечения этой гарантии зависит от числа потоков, имеющих доступ к сегментам памяти, выделенным арендой. Например, если арена всегда создается и закрывается одним потоком, а сегменты памяти, выделенные арендой, всегда используются тем же потоком, то обеспечение корректности тривиально.

И наоборот, если арена выделяет сегменты, к которым можно получить доступ из нескольких потоков, или если арена может быть закрыта потоком, отличным от потока доступа, обеспечение корректности намного сложнее. Например, к сегменту, выделенному с помощью арены, можно получить доступ в то время, как другой поток пытается одновременно закрыть арену. Чтобы обеспечить строгую гарантию временной безопасности, не заставляя каждого клиента, даже самого простого, нести производительные издержки, арены делятся на ограниченные потоками арены и совместные арены.

Ограниченные арены поддерживают строгие гарантии ограничения потоков. При создании им назначается владеющий поток, обычно поток, который инициировал операцию создания. К сегментам, созданным ограниченной арендой, можно получить доступ только из владеющего потока. Кроме того, любая попытка закрыть ограниченную арену из потока, отличного от владеющего, завершится ошибкой WrongThreadException.

У арен совместно используемого доступа нет владельца потока. К сегментам, созданным арендой совместно используемого доступа, может получить доступ любой поток. Это может быть полезно, когда нескольким потокам необходимо одновременно получить доступ к одному и тому же сегменту памяти (например, в случае параллельной обработки). Кроме того, совместную арену может закрыть любой поток.

Пользовательские арены

Клиенты могут определить пользовательские арены для реализации более эффективных стратегий выделения или для лучшего контроля над тем, когда (и кем) арена может быть закрыта. В качестве примера, следующий код определяет срезовую арену, которая ведет себя как ограниченная арена (т.е., доступ с использованием одного потока), но внутренне использует аллокатор срезов для обработки запросов на выделение. Когда срезовая арена закрывается, связанная ограниченная арена также закрывается; это сделает все сегменты, выделенные с помощью срезовой арены, недоступными (поскольку область срезовой арены такая же, как и у базовой ограниченной арены):
class SlicingArena implements Arena {
    final Arena arena = Arena.ofConfined();
    final SegmentAllocator slicingAllocator;

    SlicingArena(long size) {
        slicingAllocator = SegmentAllocator.slicingAllocator(arena.allocate(size));
    }

    public MemorySegment allocate(long byteSize, long byteAlignment) {
        return slicingAllocator.allocate(byteSize, byteAlignment);
    }

    public MemorySegment.Scope scope() {
        return arena.scope();
    }

    public void close() {
        arena.close();
    }

}
Другими словами, срезовая арена обеспечивает значительно более эффективную и масштабируемую стратегию выделения, сохраняя при этом гарантию своевременного освобождения, предоставляемую базовой ограниченной арендой:
try (Arena slicingArena = new SlicingArena(1000)) {
    for (int i = 0; i < 10; i++) {
        MemorySegment s = slicingArena.allocateFrom(JAVA_INT, 1, 2, 3, 4, 5);
        ...
    }
} // all memory allocated is released here
Требования к реализации:
Реализации этого интерфейса потокобезопасны.
С:
22
См. также:
  • MemorySegment

Краткое описание методов

Модификатор и тип Метод Описание
MemorySegment allocate(long byteSize, long byteAlignment)
Возвращает нативный сегмент памяти с заданным размером (в байтах) и ограничением выравнивания (в байтах).
void close()
Закрывает эту арену.
static Arena global()
Возвращает глобальную арену.
static Arena ofAuto()
Создает новую арену, управляемую автоматически сборщиком мусора.
static Arena ofConfined()
Возвращает новую ограниченную арену.
static Arena ofShared()
Возвращает новую общую арену.
MemorySegment.Scope scope()
Возвращает область арены.

Методы, объявленные в интерфейсе java.lang.foreign.SegmentAllocator

allocate, allocate, allocate, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom, allocateFrom

Подробное описание методов

ofAuto

static Arena ofAuto()
Создаёт новую арену, управляемую сборщиком мусора автоматически. Секции, выделенные с помощью возвращённой арены, могут быть доступны любому потоку. Вызов close() на возвращённой арене приведёт к исключению UnsupportedOperationException.

Секции памяти, выделенные возвращённой ареной, инициализируются нулями.

Возвращает:
новую арену, управляемую автоматически сборщиком мусора

global

static Arena global()
Возвращает глобальную арену. Секции, выделенные с помощью глобальной арены, могут быть доступны любому потоку. Вызов close() на возвращённой арене приведёт к исключению UnsupportedOperationException.

Секции памяти, выделенные возвращённой ареной, инициализируются нулями.

Возвращает:
глобальную арену

ofConfined

static Arena ofConfined()
Возвращает новую ограниченную арену. Секции, выделенные с помощью ограниченной арены, могут быть доступны потоку, который создал арену, владеющему потоку арены.

Секции памяти, выделенные возвращённой ареной, инициализируются нулями.

Возвращает:
новую ограниченную арену

ofShared

static Arena ofShared()
Возвращает новую общую арену. Секции, выделенные с помощью общей арены, могут быть доступны любому потоку.

Секции памяти, выделенные возвращённой ареной, инициализируются нулями.

Возвращает:
новую общую арену

allocate

MemorySegment allocate(long byteSize, long byteAlignment)
Возвращает сегмент нативной памяти заданного размера (в байтах) и ограничения выравнивания (в байтах). Возвращённый сегмент связан с данным объёмом аренды. Адрес сегмента (address) является начальным адресом выделенной вне кучи области памяти, поддерживающей сегмент, и адрес выровнен в соответствии с предоставленным ограничением выравнивания.
Определено в:
allocate в интерфейсе SegmentAllocator
Требования к реализации:
Реализации этого метода должны возвращать нативный сегмент с запрошенным размером, совместимый с заданным ограничением выравнивания. Кроме того, для любых двух сегментов S1, S2, возвращаемых этим методом, должно соблюдаться следующее свойство:
    S1.asOverlappingSlice(S2).isEmpty() == true
Параметры:
byteSize - размер (в байтах) области памяти вне кучи, поддерживающей сегмент нативной памяти
byteAlignment - ограничение выравнивания (в байтах) области памяти вне кучи, поддерживающей сегмент нативной памяти
Возвращает:
новый сегмент нативной памяти
Исключения:
IllegalArgumentException - если bytesSize < 0, byteAlignment <= 0, или если byteAlignment не является степенью двойки
IllegalStateException - если эта арена уже была закрыта
WrongThreadException - если эта арена ограничена, и этот метод вызывается из потока, отличного от владельца аренды

scope

MemorySegment.Scope scope()
Возвращает объем аренды.
Возвращает:
объём аренды

close

void close()
Закрывает эту арену. Если этот метод завершается успешно, область аренды больше не активна, и к всем сегментам памяти, связанным с ней, больше нельзя получить доступ. Кроме того, любая область памяти вне кучи, поддерживающая сегменты, полученные из этой аренды, также освобождается.
Определено в:
close в интерфейсе AutoCloseable
Примечание API:
Эта операция не является идемпотентной; то есть закрытие уже закрытой арены всегда приводит к тому, что будет брошено исключение. Это отражает продуманный выбор дизайна: отказ от закрытия арены может раскрыть ошибку в логике приложения.
Требования к реализации:
Если этот метод завершается успешно, то this.scope().isAlive() == false. Реализации разрешается выбрасывать UnsupportedOperationException, если явная операция закрытия не поддерживается.
Исключения:
IllegalStateException - если арена уже закрыта
IllegalStateException - если сегмент, связанный с этой ареной, используется одновременно, например, методом обработки вызова внизОГРАНИЧЕНО
WrongThreadException - если эта арена ограничена, и этот метод вызывается из потока, отличного от владельца аренды
UnsupportedOperationException - если эту арену нельзя закрыть явно
RuntimeException - если при выполнении пользовательской операции очистки, связанной с этой ареной (например, в результате вызова MemorySegment.reinterpret(long, Arena, Consumer)ОГРАНИЧЕНО или MemorySegment.reinterpret(Arena, Consumer)ОГРАНИЧЕНО), возникает исключение.
См. также:
  • MemorySegment.Scope.isAlive()

© 1993, 2025, Oracle and/or its affiliates. All rights reserved.
Documentation extracted from Debian's OpenJDK Development Kit package.
Licensed under the GNU General Public License, version 2, with the Classpath Exception.
Various third party code in OpenJDK is licensed under different licenses (see Debian package).
Java and OpenJDK are trademarks or registered trademarks of Oracle and/or its affiliates.
https://download.java.net/java/early_access/jdk24/docs/api/java.base/java/lang/foreign/Arena.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API