Функция управления буфером ОЗУ

Обновлено: 21.11.2024

Диспетчер буферов — это новая функция, добавленная в платформу версии 1.6.0. Эта функция объединяет хранилище подсистем платформы, чтобы упростить управление оперативной памятью и флэш-памятью.

Буферы имеют длину 4096 байт (4 КБ). Буферы сгруппированы в буферные пулы, при этом один пул назначается каждой системе, которой необходимо буферизовать данные. Например, буферу вывода RPC и каждой группе отчетов ZCL (см. Отчеты) назначается собственный пул буферов. Каждому пулу буферов всегда гарантировано два буфера ОЗУ; кроме того, общий объем доступной оперативной памяти и буферов флэш-памяти распределяется между пулами буферов в зависимости от их приоритета. Обратите внимание, что пока память не будет исчерпана, любой пул буферов может свободно получать дополнительные буферы. Приоритет буферного пула имеет значение только тогда, когда нет места и некоторые данные должны быть удалены, и в этот момент пулы с более высоким приоритетом получат относительно больше доступной памяти.

Диспетчер буферов по умолчанию пытается обеспечить безопасность данных. Для этого буферы пула перемещаются во флэш-память по истечении некоторого настраиваемого периода времени, когда пул буферов не пуст (параметры реестра в разделе «Buffer_Manager.store_to_flash_delay»).

Приоритет¶

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

  1. Узнайте общее количество доступной оперативной памяти и флэш-памяти для системы в настройках реестра, используя Buffer_Manager.max_ram_size и Buffer_Manager.max_flash_size.
  2. Разделение всей оперативной памяти и флэш-памяти на буферы по 4096 байт (4 КБ).
  3. Вычтите 2 буфера ОЗУ для каждого пула буферов из общего объема ОЗУ (минимум всегда гарантируется) и назначьте это как скорректированный общий объем ОЗУ.
  4. Сложите приоритеты всех буферных пулов, чтобы получить общий приоритет для системы. Обратите внимание, что пулы буферов по умолчанию имеют нулевой приоритет.
  5. Если общий приоритет равен нулю, пулы буферов равномерно распределяют буферы.
  6. Рассчитайте гарантированный объем ОЗУ для каждого пула буферов: гарантированный объем ОЗУ = 2 + (скорректированный общий объем ОЗУ * приоритет / общий приоритет).
  7. Все оставшееся ОЗУ добавляется в пул буферов с наивысшим приоритетом.
  8. Рассчитайте гарантированный объем флэш-памяти для каждого пула буферов: гарантированный объем флэш-памяти = общий объем флэш-памяти * приоритет / общий приоритет.
  9. Все оставшиеся флэш-памяти добавляются в пул буферов с наивысшим приоритетом.
  • После того, как диспетчер буферов инициализирует все пулы буферов
  • При добавлении или удалении буферного пула
  • При изменении общего доступного ОЗУ или флэш-памяти

Управление буфером¶

Каждый буферный пул будет пытаться хранить свои данные в ОЗУ для быстрого доступа и во флэш-памяти, чтобы предотвратить потерю данных при сбросе. Это не всегда практично или возможно из-за медленной записи во флэш-память, беспокойства по поводу износа флэш-памяти и ограничений ресурсов. Менеджер буфера пытается сбалансировать эти требования для достижения наилучшей производительности без потери данных во время сброса.

Все пулы буферов изначально хранят данные в буфере оперативной памяти.

Буферы добавляются в ОЗУ по мере необходимости (при наличии свободных буферов ОЗУ).

RAM Flash
1 2

Если прошло более секунд, указанных в параметрах реестра «Buffer_Manager.store_to_flash_delay», и буфер не был очищен, данные зеркально отображаются во флэш-памяти. Задержка реализована, чтобы система не изнашивала флэш-память из-за слишком большого количества операций записи во флэш-память. Кроме того, запись во флэш-память выполняется относительно медленно и не нужна, если данные быстро обрабатываются из буферного пула. Любые данные, добавленные в буфер, будут добавлены как в ОЗУ, так и во флэш-память.

RAM Flash
1 2 1 2
< /p>

Буферы добавляются в ОЗУ и флэш-память по мере необходимости (при условии наличия свободного ОЗУ и буферов флэш-памяти).

RAM Flash
1 2 3 1 2 3< /td>

Все становится интереснее, когда больше нет доступных буферов ОЗУ или флэш-памяти. Если пулу буферов требуется еще один буфер ОЗУ или флэш-памяти и ему гарантировано дополнительное пространство, он возьмет один из избыточных буферов из другого пула буферов. Всегда будет доступный буфер, так как общий размер гарантированных буферов ОЗУ и флэш-памяти не превышает общий размер доступной оперативной памяти и флэш-памяти.Если пул буферов больше не может хранить данные как в ОЗУ, так и во флэш-памяти, он может начать хранить более новые данные во флэш-памяти, а более старые данные — в ОЗУ. Это позволяет быстро отправлять старые данные из ОЗУ и сохраняет новые данные от потери при сбросе. Если для новых данных больше нет доступной флэш-памяти, данные, которые в данный момент находятся во флэш-памяти, будут перемещены в ОЗУ, а новые данные будут добавлены во флэш-память.

Предположим, что наш пул буферов имеет 3 гарантированных буфера оперативной памяти и 2 гарантированных буфера флэш-памяти. Если бы не было свободного ОЗУ или доступных буферов флэш-памяти, а другой пул буферов нуждался бы в буфере флэш-памяти, пул буферов удалял бы буфер 1 из флэш-памяти. Обратите внимание, что некоторые буферы по-прежнему дублируются как в ОЗУ, так и во флэш-памяти.

RAM (3) Flash (2)
1 2 3 2 3

Если не было свободного ОЗУ или буферов флэш-памяти и требовался четвертый буфер, пул буферов удалял бы второй буфер флэш-памяти. Обратите внимание, что буфер 3 по-прежнему дублируется как в ОЗУ, так и во флэш-памяти.

RAM (3) Flash (2)
1 2 3 3 4

Если не было свободного ОЗУ или буферов флэш-памяти и требовался 5-й буфер, пул буферов удалял бы 3-й буфер флэш-памяти. Обратите внимание, что буферы больше не зеркалируются.

RAM (3) Flash (2)
1 2 3 4 5

Если бы не было свободного ОЗУ или буферов флэш-памяти и требовался 6-й буфер, пул буферов полностью удалял бы 1-й буфер, перемещал бы 4-й буфер из флэш-памяти в ОЗУ и добавлял 6-й буфер во флэш-память.

RAM (3) Flash (2)
2 3 4 5 6

Если ОЗУ становится доступным, но флэш-память недоступна и требуется 7-й буфер, пул буферов перемещает 5-й пул буферов в ОЗУ и добавляет 7-й буфер во флэш-память.

RAM (3) Flash (2)
2 3 4 5 6 7

Если флэш-память станет доступной и потребуется 8-й буфер, пул буферов добавит 8-й буфер во флэш-память.

RAM (3) Flash (2)
2 3 4 5 6 7 8

Если другому пулу буферов потребуется украсть буфер RAM из этого пула буферов, этот пул буферов отбросит второй пул буферов.

RAM (3) Flash (2)
3 4 5 6 7 8

Если нет свободного ОЗУ или флэш-памяти и для кражи буфера флэш-памяти из этого пула буферов требуется другой пул буферов, этот пул буферов отбрасывает буфер 3 и перемещает буфер 6 из флэш-памяти в ОЗУ.

RAM (3) Flash (2)
4 5 6 7 8

Авторские права 2011-2016, Digi International Inc. Все права защищены. 90001931 Д

Функции управления буфером памяти управляют выделением, расширением и освобождением буферов динамической памяти, используемых некоторыми функциями кодирования/декодирования.

Буферы динамической памяти — это буферы, которые могут увеличиваться или уменьшаться для хранения объемов данных переменного размера. Эта группа функций позволяет добавлять данные в буферы, устанавливать их в буферах и извлекать из буферов. В настоящее время эти функции используются в сгенерированных процедурах декодирования SAX для сбора данных по мере их анализа синтаксическим анализатором XML.

Документация по функциям

Эта функция добавляет данные в конец буфера памяти.

Если буфер был динамическим и полным, буфер будет перераспределен. Если он статичен (статический буфер был назначен вызовом rtxMemBufInitBuffer) или пуст (ранее память не выделена), то будет выделен новый буфер.

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

Эта функция отсекает часть буфера памяти.

Начало области вырезания задается смещением "fromOffset", а длина задается "nbytes". Все данные в этой части будут потеряны. Данные со смещения "fromOffset + nbytes" будут перемещены на смещение "fromOffset".

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

Эта функция освобождает буфер памяти.

Если память была выделена, она будет освобождена. Не используйте структуру буфера памяти после вызова этой функции.

Эта функция возвращает указатель на используемую часть буфера памяти.

Эта функция возвращает длину используемой части буфера памяти.

Эта функция инициализирует структуру буфера памяти.

Она не выделяет память; он устанавливает поля структуры в правильные состояния. Эта функция должна вызываться перед любыми операциями с буфером памяти.

Эта функция назначает статический буфер структуре буфера памяти.

Она не выделяет память; он устанавливает указатель на переданный буфер. Если требуется дополнительная память (например, к буферу добавляются дополнительные данные с помощью rtxMemBufAppend), будет выделен динамический буфер, и все данные будут скопированы в новый буфер.

Эта функция выделяет буфер с заданным объемом памяти.

Эта функция сбрасывает структуру буфера памяти.

Она не освобождает память, а просто устанавливает указатель на начало и используемую длину на ноль.

Эта функция устанавливает часть буфера памяти в указанное значение октета.

Заполнение начинается с конца буфера памяти. Если буфер динамический и полный, то буфер будет перераспределен. Если он статичен (статический буфер был назначен вызовом rtxMemBufInitBuffer) или пуст (память ранее не выделялась), то будет выделен новый буфер.

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

Эта функция устанавливает флаг "isExpandable" для объекта буфера памяти.

По умолчанию этот флаг установлен в TRUE, поэтому буфер памяти может быть расширен, даже если он был инициализирован статическим буфером (см. rtMemBufInitBuffer). Если флаг снят и буфер заполнен, функции rtMemBufAppend/rtMemBufPreAllocate вернут статус ошибки.

Функции управления буфером памяти управляют выделением, расширением и освобождением буферов динамической памяти, используемых некоторыми функциями кодирования/декодирования. Буферы динамической памяти — это буферы, которые могут увеличиваться или уменьшаться для хранения объемов данных переменного размера. Эта группа функций позволяет добавлять данные в буферы, устанавливать их в буферах и извлекать из буферов. В настоящее время эти функции используются в сгенерированных процедурах декодирования SAX для сбора данных по мере их анализа синтаксическим анализатором XML.

Документация по определению макросов

◆ OSMBAPPENDSTR

◆ OSMBAPPENDUTF8

Документация по функциям

◆ rtxMemBufAppend()

int rtxMemBufAppend ( OSRTMEMBUF * pMemBuf,
const OSOCTET * pdata,
OSSIZE < em>nbytes
)

Эта функция добавляет данные в конец буфера памяти. Если буфер был динамическим и полным, буфер будет перераспределен. Если он статичен (статический буфер был назначен вызовом rtxMemBufInitBuffer) или пуст (ранее память не выделена), то будет выделен новый буфер.

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

◆ rtxMemBufCut()

int rtxMemBufCut ( OSRTMEMBUF * pMemBuf,
OSSIZE fromOffset,
OSSIZE nbytes
)

Эта функция отсекает часть буфера памяти. Начало области вырезания задается смещением «fromOffset», а длина задается «nbytes». Все данные в этой части будут потеряны. Данные со смещения "fromOffset + nbytes" будут перемещены на смещение "fromOffset".

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

◆ rtxMemBufFree()

Эта функция освобождает буфер памяти. Если память была выделена, то она будет освобождена. Не используйте структуру буфера памяти после вызова этой функции.

Параметры

pMemBufУказатель на структуру буфера памяти.

◆ rtxMemBufGetData()

Эта функция возвращает указатель на используемую часть буфера памяти.

Параметры

OSOCTET* rtxMemBufGetData ( const OSRTMEMBUF * pMemBuf,
int * длина
)
pMemBufУказатель на структуру буфера памяти.
lengthУказатель на длину используемой части буфера памяти.
Возвращает Указатель на используемую часть буфера памяти.

◆ rtxMemBufGetDataExt()

Эта функция возвращает указатель на используемую часть буфера памяти. Расширенная версия возвращает длину в аргументе типа size, который во многих системах является 64-битным значением.

Параметры

OSOCTET* rtxMemBufGetDataExt ( const OSRTMEMBUF * pMemBuf,
OSSIZE * длина
)
pMemBufУказатель на структуру буфера памяти.
lengthУказатель на длину используемой части буфера памяти.
Возвращает Указатель на используемую часть буфера памяти.

◆ rtxMemBufGetDataLen()

Эта функция возвращает длину используемой части буфера памяти.

Параметры

pMemBufУказатель на структуру буфера памяти.
Возвращает Длина используемой части буфер.

◆ rtxMemBufInit()

void rtxMemBufInit ( OSCTXT * pCtxt,
OSRTMEMBUF * pMemBuf,
OSSIZE segsize
)

Эта функция инициализирует структуру буфера памяти. Он не выделяет память; он устанавливает поля структуры в правильные состояния. Эта функция должна вызываться перед любыми операциями с буфером памяти.

Параметры

pCtxtA обеспечивает область хранения для функции для хранения всех рабочих переменных, которые должны поддерживаться между вызовами функции.
pMemBufУказатель на инициализированную структуру буфера памяти.
segsizeКоличество байтов в которой буфер памяти будет расширен в случае его заполнения.

◆ rtxMemBufInitBuffer()

void rtxMemBufInitBuffer ( OSCTXT * pCtxt,
OSRTMEMBUF * pMemBuf,
OSOCTET * < em>buf,
OSSIZE bufsize,
OSSIZE segsize
)

Эта функция назначает статический буфер структуре буфера памяти. Он не выделяет память; он устанавливает указатель на переданный буфер. Если требуется дополнительная память (например, к буферу добавляются дополнительные данные с помощью rtxMemBufAppend), будет выделен динамический буфер, и все данные будут скопированы в новый буфер.

Параметры

pCtxtУказатель на структуру контекста. Это обеспечивает область хранения для функции t, в которой хранятся все рабочие переменные, которые должны поддерживаться между вызовами функции.
pMemBufУказатель на структуру буфера памяти. .
bufУказатель на назначаемый буфер.
bufsizeРазмер буфера.
segsizeКоличество байтов, на которое будет расширен буфер памяти в случае его заполнения.

◆ rtxMemBufPreAllocate()

int rtxMemBufPreAllocate ( OSRTMEMBUF * pMemBuf,
OSSIZE nbytes
)

Эта функция выделяет буфер с заданным объемом памяти.

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

◆ rtxMemBufReset()

Эта функция сбрасывает структуру буфера памяти. Он не освобождает память, а просто устанавливает указатель на начало и используемую длину на ноль.

Параметры

pMemBufУказатель на структуру буфера памяти.

◆ rtxMemBufSet()

int rtxMemBufSet ( OSRTMEMBUF * pMemBuf,
OSOCTET значение,
OSSIZE nbytes
)

Эта функция устанавливает часть буфера памяти в указанное значение октета. Заполнение начинается с конца буфера памяти. Если буфер динамический и полный, то буфер будет перераспределен. Если он статичен (статический буфер был назначен вызовом rtxMemBufInitBuffer) или пуст (память ранее не выделялась), то будет выделен новый буфер.

  • 0 = успех,
  • отрицательное возвращаемое значение является ошибкой.

◆ rtxMemBufSetExpandable()

OSBOOL rtxMemBufSetExpandable ( OSRTMEMBUF * pMemBuf,
OSBOOL isExpandable
)

Эта функция устанавливает флаг "isExpandable" для объекта буфера памяти.По умолчанию этот флаг установлен в TRUE, поэтому буфер памяти мог быть расширен, даже если он был инициализирован статическим буфером (см. rtMemBufInitBuffer). Если флаг снят и буфер заполнен, функции rtMemBufAppend/rtMemBufPreAllocate вернут статус ошибки.

Параметры

pMemBufУказатель на структуру буфера памяти.
isExpandableTRUE, если буфер должен быть расширяемым.
Возвращает предыдущее состояние флага "isExpandable".

◆ rtxMemBufSetUseSysMem()

OSBOOL rtxMemBufSetUseSysMem ( OSRTMEMBUF * pMemBuf,
OSBOOL значение
)

Эта функция устанавливает флаг, указывающий, что вместо пользовательского диспетчера памяти следует использовать управление системной памятью. Это следует использовать, если выделенный буфер должен быть сохранен после вызовов rtxMemFree или rtxMemReset.

В SQL Server буферный кеш — это память, которая позволяет быстро запрашивать часто используемые данные. Когда данные записываются в базу данных SQL Server или считываются из нее, диспетчер буферов копирует их в буферный кеш (он же буферный пул). Когда он заполняется, старые или менее часто используемые страницы данных перемещаются на жесткий диск.

Зачем нужно отслеживать буферный кеш?

Использование памяти может существенно повлиять на производительность. При нехватке памяти страницы данных часто удаляются из буферного кеша. Это замедляет запросы, поскольку SQL Server должен обратиться к диску, чтобы найти страницу данных, восстановить ее в буферном кеше, а затем прочитать страницу, прежде чем он сможет вернуть результаты запроса.

Существует множество причин, по которым запросы начинают выполняться медленно. Но если вы хотите исключить проблемы с памятью, посмотрите, что происходит внутри буферного кеша. Заглянув внутрь, можно определить, какая база данных, таблица или индекс занимают много памяти и оказывают давление на буфер.

Чтобы узнать, какая база данных потребляет больше всего памяти, используйте запрос:

Чтобы определить таблицу или индекс, которые потребляют больше всего памяти, запустите этот запрос в базе данных, которую вы хотите проверить:

Управление памятью с помощью показателей

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

Вот пять основных показателей, которые следует отслеживать для решения проблем с производительностью, связанных с памятью:

1. Коэффициент попаданий в кэш буфера

  • Эта метрика показывает, как SQL Server использует буферный кеш.
  • Коэффициент совпадений определяет процент запросов страниц, которые были выполнены страницами данных из буферного кеша, по сравнению со всеми запросами страниц данных.
  • Страницы, не найденные в буферном кеше, считываются с диска, что намного медленнее
  • Идеальный коэффициент буферного кеша – 100 (т. е. SQL Server считывает все страницы из буферного кеша и ни одной с диска).
  • Рекомендуемое значение кэша буфера больше 90

2. Ожидаемый срок службы страницы (PLE)

    измеряет, как долго (в секундах) страница данных находится в буферном кеше.
  • Чем длиннее PLE, тем выше вероятность того, что SQL Server прочитает страницы из буферного кеша и не будет обращаться к диску.
  • Если памяти недостаточно, страницы данных чаще сбрасываются из буферного кеша, чтобы освободить место для новых страниц.
  • Исторически, когда в системах было гораздо меньше памяти, чем сейчас, «нормальное» значение PLE составляло 300 секунд.
  • Сегодня для определения "хорошего" PLE используется формула: ожидаемая продолжительность жизни страницы = 300 секунд на каждые 4 ГБ ОЗУ на вашем сервере.
  • PLE должен оставаться стабильным при постоянном мониторинге.
  • Быстрое и частое снижение указывает на проблемы с памятью.
  • При снижении более чем на 50 % необходимо немедленно расследовать

3. Число чтений страниц/сек (уровень сервера)

  • Эта метрика показывает, сколько операций физического чтения (т. е. чтения с диска) произошло за одну секунду во всех базах данных экземпляра.
  • Физическое чтение дорого и медленно.
  • Уменьшите число физических операций чтения, используя больший кэш данных, интеллектуальные индексы и более эффективные запросы или изменив структуру базы данных.
  • Рекомендуемое значение меньше 90.
  • Значение выше 90 указывает на нехватку памяти и проблемы с индексацией.

4. Записей страниц/сек

  • Этот показатель показывает, сколько раз страницы записывались на диск на уровне сервера за одну секунду.
  • Рекомендуемое значение меньше 90.

5.Ввод страниц/сек и вывод страниц/сек (счетчики памяти)

  • Ввод страниц в секунду – это количество страниц, загружаемых с диска каждую секунду.
  • Вывод страниц в секунду – это количество страниц, записываемых на диск каждую секунду, чтобы освободить место в буферном кеше.
  • Страниц в секунду — это сумма количества входных страниц в секунду и выходных страниц в секунду.
  • Если значение страниц в секунду постоянно превышает 50, необходимо дополнительное расследование.

Исправный буферный кеш — важный компонент оптимизации скорости запросов SQL Server. Хотя проблемы с памятью — лишь один из нескольких факторов, которые могут замедлить ответы на запросы, их довольно легко выявить и устранить. Отслеживание этих пяти ключевых показателей может помочь вам дольше сохранять страницы данных в пуле буферов, чтобы SQL Server не тратил время на поиск на диске перед возвратом результатов запроса.

Об авторе

Дженис Гриффин

Об авторе

Дженис Гриффин (Janis Griffin) — старший инженер-программист в Quest Software. Имеет более чем 30-летний опыт работы администратором баз данных Oracle, включая проектирование, разработку и внедрение многих критически важных приложений баз данных. До прихода в Quest Дженис занимала должности администратора баз данных в основном в телекоммуникационной отрасли, работая как с базами данных сетевой маршрутизации в реальном времени, так и с OLTP-приложениями типа Business-to-Business. Она отвечала за обучение других администраторов баз данных передовым методам настройки производительности баз данных и управлению всеми аспектами баз данных голосовой сети. Дженис имеет несколько патентов на схемы и алгоритмы баз данных телефонной маршрутизации.

Статьи по теме

10 показателей мониторинга базы данных, которые необходимо отслеживать для достижения оптимальной производительности

Отставание в производительности базы данных? Узнайте о мониторинге баз данных: что это такое, как его выполнять и основные показатели, за которыми нужно следить.

Мониторинг базы данных: почему важно следить за этими четырьмя уровнями

Ваша база данных работает медленно? Сосредоточьте мониторинг базы данных на четырех уровнях, которые оказывают наибольшее влияние на производительность базы данных.

Почему мониторинг базы данных необходим для настройки производительности

Настроить производительность перед мониторингом — значит поставить телегу впереди лошади. Узнайте, почему мониторинг базы данных необходим для повышения производительности.

Подпишитесь на обновления блога Quest

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

Читайте также: