Add a third I/O mode: O_DIRECT|O_SYNC, change parameters to data_io/meta_io/journal_io

fsync-feedback
Vitaliy Filippov 2023-08-06 01:14:44 +03:00
parent ab8627c9fa
commit 7333022adf
14 changed files with 236 additions and 157 deletions

View File

@ -96,8 +96,9 @@ SSD cache or "media-cache" - for example, a lot of Seagate EXOS drives have
it (they have internal SSD cache even though it's not stated in datasheets). it (they have internal SSD cache even though it's not stated in datasheets).
Setting this parameter to "all" or "small" in OSD parameters requires enabling Setting this parameter to "all" or "small" in OSD parameters requires enabling
disable_journal_fsync and disable_meta_fsync, setting it to "all" also requires [disable_journal_fsync](layout-osd.en.yml#disable_journal_fsync) and
enabling disable_data_fsync. [disable_meta_fsync](layout-osd.en.yml#disable_meta_fsync), setting it to
"all" also requires enabling [disable_data_fsync](layout-osd.en.yml#disable_data_fsync).
TLDR: For optimal performance, set immediate_commit to "all" if you only use TLDR: For optimal performance, set immediate_commit to "all" if you only use
SSDs with supercapacitor-based power loss protection (nonvolatile SSDs with supercapacitor-based power loss protection (nonvolatile

View File

@ -103,8 +103,9 @@ HDD-дисках с внутренним SSD или "медиа" кэшем - н
указано в спецификациях). указано в спецификациях).
Указание "all" или "small" в настройках / командной строке OSD требует Указание "all" или "small" в настройках / командной строке OSD требует
включения disable_journal_fsync и disable_meta_fsync, значение "all" также включения [disable_journal_fsync](layout-osd.ru.yml#disable_journal_fsync) и
требует включения disable_data_fsync. [disable_meta_fsync](layout-osd.ru.yml#disable_meta_fsync), значение "all"
также требует включения [disable_data_fsync](layout-osd.ru.yml#disable_data_fsync).
Итого, вкратце: для оптимальной производительности установите Итого, вкратце: для оптимальной производительности установите
immediate_commit в значение "all", если вы используете в кластере только SSD immediate_commit в значение "all", если вы используете в кластере только SSD

View File

@ -213,6 +213,6 @@ Thus, recommended setups are:
3. Hybrid HDD+SSD: csum_block_size=4k + inmemory_metadata=false 3. Hybrid HDD+SSD: csum_block_size=4k + inmemory_metadata=false
4. HDD-only, faster random read: csum_block_size=32k 4. HDD-only, faster random read: csum_block_size=32k
5. HDD-only, faster random write: csum_block_size=4k + 5. HDD-only, faster random write: csum_block_size=4k +
inmemory_metadata=false + cached_io_meta=true inmemory_metadata=false + meta_io=cached
See also [cached_io_meta](osd.en.md#cached_io_meta). See also [meta_io](osd.en.md#meta_io).

View File

@ -226,6 +226,6 @@ csum_block_size данных.
3. Гибридные HDD+SSD: csum_block_size=4k + inmemory_metadata=false 3. Гибридные HDD+SSD: csum_block_size=4k + inmemory_metadata=false
4. Только HDD, быстрее случайное чтение: csum_block_size=32k 4. Только HDD, быстрее случайное чтение: csum_block_size=32k
5. Только HDD, быстрее случайная запись: csum_block_size=4k + 5. Только HDD, быстрее случайная запись: csum_block_size=4k +
inmemory_metadata=false + cached_io_meta=true inmemory_metadata=false + meta_io=cached
Смотрите также [cached_io_meta](osd.ru.md#cached_io_meta). Смотрите также [meta_io](osd.ru.md#meta_io).

View File

@ -31,9 +31,9 @@ them, even without restarting by updating configuration in etcd.
- [max_flusher_count](#max_flusher_count) - [max_flusher_count](#max_flusher_count)
- [inmemory_metadata](#inmemory_metadata) - [inmemory_metadata](#inmemory_metadata)
- [inmemory_journal](#inmemory_journal) - [inmemory_journal](#inmemory_journal)
- [cached_io_data](#cached_io_data) - [data_io](#data_io)
- [cached_io_meta](#cached_io_meta) - [meta_io](#meta_io)
- [cached_io_journal](#cached_io_journal) - [journal_io](#journal_io)
- [journal_sector_buffer_count](#journal_sector_buffer_count) - [journal_sector_buffer_count](#journal_sector_buffer_count)
- [journal_no_same_sector_overwrites](#journal_no_same_sector_overwrites) - [journal_no_same_sector_overwrites](#journal_no_same_sector_overwrites)
- [throttle_small_writes](#throttle_small_writes) - [throttle_small_writes](#throttle_small_writes)
@ -258,47 +258,59 @@ is typically very small because it's sufficient to have 16-32 MB journal
for SSD OSDs. However, in theory it's possible that you'll want to turn it for SSD OSDs. However, in theory it's possible that you'll want to turn it
off for hybrid (HDD+SSD) OSDs with large journals on quick devices. off for hybrid (HDD+SSD) OSDs with large journals on quick devices.
## cached_io_data ## data_io
- Type: boolean - Type: string
- Default: false - Default: direct
Read and write *data* through Linux page cache, i.e. use a file descriptor I/O mode for *data*. One of "direct", "cached" or "directsync". Corresponds
opened with O_SYNC, but without O_DIRECT for I/O. May improve read to O_DIRECT, O_SYNC and O_DIRECT|O_SYNC, respectively.
performance for hot data and slower disks - HDDs and maybe SATA SSDs.
Not recommended for desktop SSDs without capacitors because O_SYNC flushes
disk cache on every write.
## cached_io_meta Choose "cached" to use Linux page cache. This may improve read performance
for hot data and slower disks - HDDs and maybe SATA SSDs - but will slightly
decrease write performance for fast disks because page cache is an overhead
itself.
- Type: boolean Choose "directsync" to use [immediate_commit](layout-cluster.ru.md#immediate_commit)
- Default: false (which requires disable_data_fsync) with drives having write-back cache
which can't be turned off, for example, Intel Optane. Also note that *some*
desktop SSDs (for example, HP EX950) may ignore O_SYNC thus making
disable_data_fsync unsafe even with "directsync".
Read and write *metadata* through Linux page cache. May improve read ## meta_io
performance only if your drives are relatively slow (HDD, SATA SSD), and
only if checksums are enabled and [inmemory_metadata](#inmemory_metadata)
is disabled, because in this case metadata blocks are read from disk
on every read request to verify checksums and caching them may reduce this
extra read load.
Absolutely pointless to enable with enabled inmemory_metadata because all - Type: string
metadata is kept in memory anyway, and likely pointless without checksums, - Default: direct
because in that case, metadata blocks are read from disk only during journal
I/O mode for *metadata*. One of "direct", "cached" or "directsync".
"cached" may improve read performance, but only under the following conditions:
1. your drives are relatively slow (HDD, SATA SSD), and
2. checksums are enabled, and
3. [inmemory_metadata](#inmemory_metadata) is disabled.
Under all these conditions, metadata blocks are read from disk on every
read request to verify checksums and caching them may reduce this extra
read load. Without (3) metadata is never read from the disk after starting,
and without (2) metadata blocks are read from disk only during journal
flushing. flushing.
If the same device is used for data and metadata, enabling [cached_io_data](#cached_io_data) "directsync" is the same as above.
also enables this parameter, given that it isn't turned off explicitly.
## cached_io_journal If the same device is used for data and metadata, meta_io by default is set
to the same value as [data_io](#data_io).
- Type: boolean ## journal_io
- Default: false
Read and write *journal* through Linux page cache. May improve read - Type: string
performance if [inmemory_journal](#inmemory_journal) is turned off. - Default: direct
If the same device is used for metadata and journal, enabling [cached_io_meta](#cached_io_meta) I/O mode for *journal*. One of "direct", "cached" or "directsync".
also enables this parameter, given that it isn't turned off explicitly.
Here, "cached" may only improve read performance for recent writes and
only if [inmemory_journal](#inmemory_journal) is turned off.
If the same device is used for metadata and journal, journal_io by default
is set to the same value as [meta_io](#meta_io).
## journal_sector_buffer_count ## journal_sector_buffer_count

View File

@ -32,9 +32,9 @@
- [max_flusher_count](#max_flusher_count) - [max_flusher_count](#max_flusher_count)
- [inmemory_metadata](#inmemory_metadata) - [inmemory_metadata](#inmemory_metadata)
- [inmemory_journal](#inmemory_journal) - [inmemory_journal](#inmemory_journal)
- [cached_io_data](#cached_io_data) - [data_io](#data_io)
- [cached_io_meta](#cached_io_meta) - [meta_io](#meta_io)
- [cached_io_journal](#cached_io_journal) - [journal_io](#journal_io)
- [journal_sector_buffer_count](#journal_sector_buffer_count) - [journal_sector_buffer_count](#journal_sector_buffer_count)
- [journal_no_same_sector_overwrites](#journal_no_same_sector_overwrites) - [journal_no_same_sector_overwrites](#journal_no_same_sector_overwrites)
- [throttle_small_writes](#throttle_small_writes) - [throttle_small_writes](#throttle_small_writes)
@ -266,51 +266,62 @@ Flusher - это микро-поток (корутина), которая коп
параметра может оказаться полезным для гибридных OSD (HDD+SSD) с большими параметра может оказаться полезным для гибридных OSD (HDD+SSD) с большими
журналами, расположенными на быстром по сравнению с HDD устройстве. журналами, расположенными на быстром по сравнению с HDD устройстве.
## cached_io_data ## data_io
- Тип: булево (да/нет) - Тип: строка
- Значение по умолчанию: false - Значение по умолчанию: direct
Читать и записывать *данные* через системный кэш Linux (page cache), то есть, Режим ввода-вывода для *данных*. Одно из значений "direct", "cached" или
использовать для данных файловый дескриптор, открытый без флага O_DIRECT, но "directsync", означающих O_DIRECT, O_SYNC и O_DIRECT|O_SYNC, соответственно.
с флагом O_SYNC. Может улучшить скорость чтения для относительно медленных
дисков - HDD и, возможно, SATA SSD. Не рекомендуется для потребительских
SSD без конденсаторов, так как O_SYNC сбрасывает кэш диска при каждой записи.
## cached_io_meta Выберите "cached", чтобы использовать системный кэш Linux (page cache) при
чтении и записи. Это может улучшить скорость чтения горячих данных с
относительно медленных дисков - HDD и, возможно, SATA SSD - но немного
снижает производительность записи для быстрых дисков, так как кэш сам по
себе тоже добавляет накладные расходы.
- Тип: булево (да/нет) Выберите "directsync", если хотите задействовать
- Значение по умолчанию: false [immediate_commit](layout-cluster.ru.md#immediate_commit) (требующий
включенияd disable_data_fsync) на дисках с неотключаемым кэшем. Пример таких
дисков - Intel Optane. При этом также стоит иметь в виду, что *некоторые*
настольные SSD (например, HP EX950) игнорируют флаг O_SYNC, делая отключение
fsync небезопасным даже с режимом "directsync".
Читать и записывать *метаданные* через системный кэш Linux. Может улучшить ## meta_io
скорость чтения, если у вас медленные диски, и только если контрольные суммы
включены, а параметр [inmemory_metadata](#inmemory_metadata) отключён, так - Тип: строка
как в этом случае блоки метаданных читаются с диска при каждом запросе чтения - Значение по умолчанию: direct
Режим ввода-вывода для *метаданных*. Одно из значений "direct", "cached" или
"directsync".
"cached" может улучшить скорость чтения, если:
1. у вас медленные диски (HDD, SATA SSD)
2. контрольные суммы включены
3. параметр [inmemory_metadata](#inmemory_metadata) отключён.
При этих условиях блоки метаданных читаются с диска при каждом запросе чтения
для проверки контрольных сумм и их кэширование может снизить дополнительную для проверки контрольных сумм и их кэширование может снизить дополнительную
нагрузку на диск. нагрузку на диск. Без (3) метаданные никогда не читаются с диска после
запуска OSD, а без (2) блоки метаданных читаются только при сбросе журнала.
Абсолютно бессмысленно включать данный параметр, если параметр Если одно и то же устройство используется для данных и метаданных, режим
inmemory_metadata включён (по умолчанию это так), и также вероятно ввода-вывода метаданных по умолчанию устанавливается равным [data_io](#data_io).
бессмысленно включать его, если не включены контрольные суммы, так как в
этом случае блоки метаданных читаются с диска только во время сброса
журнала.
Если одно и то же устройство используется для данных и метаданных, включение ## journal_io
[cached_io_data](#cached_io_data) также включает данный параметр, при
условии, что он не отключён явным образом.
## cached_io_journal - Тип: строка
- Значение по умолчанию: direct
- Тип: булево (да/нет) Режим ввода-вывода для *журнала*. Одно из значений "direct", "cached" или
- Значение по умолчанию: false "directsync".
Читать и записывать *журнал* через системный кэш Linux. Может улучшить Здесь "cached" может улучшить скорость чтения только недавно записанных
скорость чтения, если параметр [inmemory_journal](#inmemory_journal) данных и только если параметр [inmemory_journal](#inmemory_journal)
отключён. отключён.
Если одно и то же устройство используется для метаданных и журнала, Если одно и то же устройство используется для метаданных и журнала,
включение [cached_io_meta](#cached_io_meta) также включает данный режим ввода-вывода журнала по умолчанию устанавливается равным
параметр, при условии, что он не отключён явным образом. [meta_io](#meta_io).
## journal_sector_buffer_count ## journal_sector_buffer_count

View File

@ -87,8 +87,9 @@
it (they have internal SSD cache even though it's not stated in datasheets). it (they have internal SSD cache even though it's not stated in datasheets).
Setting this parameter to "all" or "small" in OSD parameters requires enabling Setting this parameter to "all" or "small" in OSD parameters requires enabling
disable_journal_fsync and disable_meta_fsync, setting it to "all" also requires [disable_journal_fsync](layout-osd.en.yml#disable_journal_fsync) and
enabling disable_data_fsync. [disable_meta_fsync](layout-osd.en.yml#disable_meta_fsync), setting it to
"all" also requires enabling [disable_data_fsync](layout-osd.en.yml#disable_data_fsync).
TLDR: For optimal performance, set immediate_commit to "all" if you only use TLDR: For optimal performance, set immediate_commit to "all" if you only use
SSDs with supercapacitor-based power loss protection (nonvolatile SSDs with supercapacitor-based power loss protection (nonvolatile
@ -140,8 +141,9 @@
указано в спецификациях). указано в спецификациях).
Указание "all" или "small" в настройках / командной строке OSD требует Указание "all" или "small" в настройках / командной строке OSD требует
включения disable_journal_fsync и disable_meta_fsync, значение "all" также включения [disable_journal_fsync](layout-osd.ru.yml#disable_journal_fsync) и
требует включения disable_data_fsync. [disable_meta_fsync](layout-osd.ru.yml#disable_meta_fsync), значение "all"
также требует включения [disable_data_fsync](layout-osd.ru.yml#disable_data_fsync).
Итого, вкратце: для оптимальной производительности установите Итого, вкратце: для оптимальной производительности установите
immediate_commit в значение "all", если вы используете в кластере только SSD immediate_commit в значение "all", если вы используете в кластере только SSD

View File

@ -244,9 +244,9 @@
3. Hybrid HDD+SSD: csum_block_size=4k + inmemory_metadata=false 3. Hybrid HDD+SSD: csum_block_size=4k + inmemory_metadata=false
4. HDD-only, faster random read: csum_block_size=32k 4. HDD-only, faster random read: csum_block_size=32k
5. HDD-only, faster random write: csum_block_size=4k + 5. HDD-only, faster random write: csum_block_size=4k +
inmemory_metadata=false + cached_io_meta=true inmemory_metadata=false + meta_io=cached
See also [cached_io_meta](osd.en.md#cached_io_meta). See also [meta_io](osd.en.md#meta_io).
info_ru: | info_ru: |
Размер блока расчёта контрольных сумм. Размер блока расчёта контрольных сумм.
@ -271,6 +271,6 @@
3. Гибридные HDD+SSD: csum_block_size=4k + inmemory_metadata=false 3. Гибридные HDD+SSD: csum_block_size=4k + inmemory_metadata=false
4. Только HDD, быстрее случайное чтение: csum_block_size=32k 4. Только HDD, быстрее случайное чтение: csum_block_size=32k
5. Только HDD, быстрее случайная запись: csum_block_size=4k + 5. Только HDD, быстрее случайная запись: csum_block_size=4k +
inmemory_metadata=false + cached_io_meta=true inmemory_metadata=false + meta_io=cached
Смотрите также [cached_io_meta](osd.ru.md#cached_io_meta). Смотрите также [meta_io](osd.ru.md#meta_io).

View File

@ -260,73 +260,96 @@
достаточно 16- или 32-мегабайтного журнала. Однако в теории отключение достаточно 16- или 32-мегабайтного журнала. Однако в теории отключение
параметра может оказаться полезным для гибридных OSD (HDD+SSD) с большими параметра может оказаться полезным для гибридных OSD (HDD+SSD) с большими
журналами, расположенными на быстром по сравнению с HDD устройстве. журналами, расположенными на быстром по сравнению с HDD устройстве.
- name: cached_io_data - name: data_io
type: bool type: string
default: false default: direct
info: | info: |
Read and write *data* through Linux page cache, i.e. use a file descriptor I/O mode for *data*. One of "direct", "cached" or "directsync". Corresponds
opened with O_SYNC, but without O_DIRECT for I/O. May improve read to O_DIRECT, O_SYNC and O_DIRECT|O_SYNC, respectively.
performance for hot data and slower disks - HDDs and maybe SATA SSDs.
Not recommended for desktop SSDs without capacitors because O_SYNC flushes
disk cache on every write.
info_ru: |
Читать и записывать *данные* через системный кэш Linux (page cache), то есть,
использовать для данных файловый дескриптор, открытый без флага O_DIRECT, но
с флагом O_SYNC. Может улучшить скорость чтения для относительно медленных
дисков - HDD и, возможно, SATA SSD. Не рекомендуется для потребительских
SSD без конденсаторов, так как O_SYNC сбрасывает кэш диска при каждой записи.
- name: cached_io_meta
type: bool
default: false
info: |
Read and write *metadata* through Linux page cache. May improve read
performance only if your drives are relatively slow (HDD, SATA SSD), and
only if checksums are enabled and [inmemory_metadata](#inmemory_metadata)
is disabled, because in this case metadata blocks are read from disk
on every read request to verify checksums and caching them may reduce this
extra read load.
Absolutely pointless to enable with enabled inmemory_metadata because all Choose "cached" to use Linux page cache. This may improve read performance
metadata is kept in memory anyway, and likely pointless without checksums, for hot data and slower disks - HDDs and maybe SATA SSDs - but will slightly
because in that case, metadata blocks are read from disk only during journal decrease write performance for fast disks because page cache is an overhead
itself.
Choose "directsync" to use [immediate_commit](layout-cluster.ru.md#immediate_commit)
(which requires disable_data_fsync) with drives having write-back cache
which can't be turned off, for example, Intel Optane. Also note that *some*
desktop SSDs (for example, HP EX950) may ignore O_SYNC thus making
disable_data_fsync unsafe even with "directsync".
info_ru: |
Режим ввода-вывода для *данных*. Одно из значений "direct", "cached" или
"directsync", означающих O_DIRECT, O_SYNC и O_DIRECT|O_SYNC, соответственно.
Выберите "cached", чтобы использовать системный кэш Linux (page cache) при
чтении и записи. Это может улучшить скорость чтения горячих данных с
относительно медленных дисков - HDD и, возможно, SATA SSD - но немного
снижает производительность записи для быстрых дисков, так как кэш сам по
себе тоже добавляет накладные расходы.
Выберите "directsync", если хотите задействовать
[immediate_commit](layout-cluster.ru.md#immediate_commit) (требующий
включенияd disable_data_fsync) на дисках с неотключаемым кэшем. Пример таких
дисков - Intel Optane. При этом также стоит иметь в виду, что *некоторые*
настольные SSD (например, HP EX950) игнорируют флаг O_SYNC, делая отключение
fsync небезопасным даже с режимом "directsync".
- name: meta_io
type: string
default: direct
info: |
I/O mode for *metadata*. One of "direct", "cached" or "directsync".
"cached" may improve read performance, but only under the following conditions:
1. your drives are relatively slow (HDD, SATA SSD), and
2. checksums are enabled, and
3. [inmemory_metadata](#inmemory_metadata) is disabled.
Under all these conditions, metadata blocks are read from disk on every
read request to verify checksums and caching them may reduce this extra
read load. Without (3) metadata is never read from the disk after starting,
and without (2) metadata blocks are read from disk only during journal
flushing. flushing.
If the same device is used for data and metadata, enabling [cached_io_data](#cached_io_data) "directsync" is the same as above.
also enables this parameter, given that it isn't turned off explicitly.
If the same device is used for data and metadata, meta_io by default is set
to the same value as [data_io](#data_io).
info_ru: | info_ru: |
Читать и записывать *метаданные* через системный кэш Linux. Может улучшить Режим ввода-вывода для *метаданных*. Одно из значений "direct", "cached" или
скорость чтения, если у вас медленные диски, и только если контрольные суммы "directsync".
включены, а параметр [inmemory_metadata](#inmemory_metadata) отключён, так
как в этом случае блоки метаданных читаются с диска при каждом запросе чтения "cached" может улучшить скорость чтения, если:
1. у вас медленные диски (HDD, SATA SSD)
2. контрольные суммы включены
3. параметр [inmemory_metadata](#inmemory_metadata) отключён.
При этих условиях блоки метаданных читаются с диска при каждом запросе чтения
для проверки контрольных сумм и их кэширование может снизить дополнительную для проверки контрольных сумм и их кэширование может снизить дополнительную
нагрузку на диск. нагрузку на диск. Без (3) метаданные никогда не читаются с диска после
запуска OSD, а без (2) блоки метаданных читаются только при сбросе журнала.
Абсолютно бессмысленно включать данный параметр, если параметр Если одно и то же устройство используется для данных и метаданных, режим
inmemory_metadata включён (по умолчанию это так), и также вероятно ввода-вывода метаданных по умолчанию устанавливается равным [data_io](#data_io).
бессмысленно включать его, если не включены контрольные суммы, так как в - name: journal_io
этом случае блоки метаданных читаются с диска только во время сброса type: string
журнала. default: direct
Если одно и то же устройство используется для данных и метаданных, включение
[cached_io_data](#cached_io_data) также включает данный параметр, при
условии, что он не отключён явным образом.
- name: cached_io_journal
type: bool
default: false
info: | info: |
Read and write *journal* through Linux page cache. May improve read I/O mode for *journal*. One of "direct", "cached" or "directsync".
performance if [inmemory_journal](#inmemory_journal) is turned off.
If the same device is used for metadata and journal, enabling [cached_io_meta](#cached_io_meta) Here, "cached" may only improve read performance for recent writes and
also enables this parameter, given that it isn't turned off explicitly. only if [inmemory_journal](#inmemory_journal) is turned off.
If the same device is used for metadata and journal, journal_io by default
is set to the same value as [meta_io](#meta_io).
info_ru: | info_ru: |
Читать и записывать *журнал* через системный кэш Linux. Может улучшить Режим ввода-вывода для *журнала*. Одно из значений "direct", "cached" или
скорость чтения, если параметр [inmemory_journal](#inmemory_journal) "directsync".
Здесь "cached" может улучшить скорость чтения только недавно записанных
данных и только если параметр [inmemory_journal](#inmemory_journal)
отключён. отключён.
Если одно и то же устройство используется для метаданных и журнала, Если одно и то же устройство используется для метаданных и журнала,
включение [cached_io_meta](#cached_io_meta) также включает данный режим ввода-вывода журнала по умолчанию устанавливается равным
параметр, при условии, что он не отключён явным образом. [meta_io](#meta_io).
- name: journal_sector_buffer_count - name: journal_sector_buffer_count
type: int type: int
default: 32 default: 32

View File

@ -45,13 +45,31 @@ void blockstore_disk_t::parse_config(std::map<std::string, std::string> & config
meta_block_size = parse_size(config["meta_block_size"]); meta_block_size = parse_size(config["meta_block_size"]);
bitmap_granularity = parse_size(config["bitmap_granularity"]); bitmap_granularity = parse_size(config["bitmap_granularity"]);
meta_format = stoull_full(config["meta_format"]); meta_format = stoull_full(config["meta_format"]);
cached_io_data = config["cached_io_data"] == "true" || config["cached_io_data"] == "yes" || config["cached_io_data"] == "1"; if (config.find("data_io") == config.end() &&
cached_io_meta = cached_io_data && (meta_device == data_device || meta_device == "") && config.find("meta_io") == config.end() &&
config.find("cached_io_meta") == config.end() || config.find("journal_io") == config.end())
config["cached_io_meta"] == "true" || config["cached_io_meta"] == "yes" || config["cached_io_meta"] == "1"; {
cached_io_journal = cached_io_meta && (journal_device == meta_device || journal_device == "") && bool cached_io_data = config["cached_io_data"] == "true" || config["cached_io_data"] == "yes" || config["cached_io_data"] == "1";
config.find("cached_io_journal") == config.end() || bool cached_io_meta = cached_io_data && (meta_device == data_device || meta_device == "") &&
config["cached_io_journal"] == "true" || config["cached_io_journal"] == "yes" || config["cached_io_journal"] == "1"; config.find("cached_io_meta") == config.end() ||
config["cached_io_meta"] == "true" || config["cached_io_meta"] == "yes" || config["cached_io_meta"] == "1";
bool cached_io_journal = cached_io_meta && (journal_device == meta_device || journal_device == "") &&
config.find("cached_io_journal") == config.end() ||
config["cached_io_journal"] == "true" || config["cached_io_journal"] == "yes" || config["cached_io_journal"] == "1";
data_io = cached_io_data ? "cached" : "direct";
meta_io = cached_io_meta ? "cached" : "direct";
journal_io = cached_io_journal ? "cached" : "direct";
}
else
{
data_io = config.find("data_io") != config.end() ? config["data_io"] : "direct";
meta_io = config.find("meta_io") != config.end()
? config["meta_io"]
: (meta_device == data_device || meta_device == "" ? data_io : "direct");
journal_io = config.find("journal_io") != config.end()
? config["journal_io"]
: (journal_device == meta_device || journal_device == "" ? meta_io : "direct");
}
if (config["data_csum_type"] == "crc32c") if (config["data_csum_type"] == "crc32c")
{ {
data_csum_type = BLOCKSTORE_CSUM_CRC32C; data_csum_type = BLOCKSTORE_CSUM_CRC32C;
@ -272,9 +290,19 @@ static void check_size(int fd, uint64_t *size, uint64_t *sectsize, std::string n
} }
} }
static int bs_openmode(const std::string & mode)
{
if (mode == "directsync")
return O_DIRECT|O_SYNC;
else if (mode == "cached")
return O_SYNC;
else
return O_DIRECT;
}
void blockstore_disk_t::open_data() void blockstore_disk_t::open_data()
{ {
data_fd = open(data_device.c_str(), (cached_io_data ? O_SYNC : O_DIRECT) | O_RDWR); data_fd = open(data_device.c_str(), bs_openmode(data_io) | O_RDWR);
if (data_fd == -1) if (data_fd == -1)
{ {
throw std::runtime_error("Failed to open data device "+data_device+": "+std::string(strerror(errno))); throw std::runtime_error("Failed to open data device "+data_device+": "+std::string(strerror(errno)));
@ -299,9 +327,9 @@ void blockstore_disk_t::open_data()
void blockstore_disk_t::open_meta() void blockstore_disk_t::open_meta()
{ {
if (meta_device != data_device || cached_io_meta != cached_io_data) if (meta_device != data_device || meta_io != data_io)
{ {
meta_fd = open(meta_device.c_str(), (cached_io_meta ? O_SYNC : O_DIRECT) | O_RDWR); meta_fd = open(meta_device.c_str(), bs_openmode(meta_io) | O_RDWR);
if (meta_fd == -1) if (meta_fd == -1)
{ {
throw std::runtime_error("Failed to open metadata device "+meta_device+": "+std::string(strerror(errno))); throw std::runtime_error("Failed to open metadata device "+meta_device+": "+std::string(strerror(errno)));
@ -337,9 +365,9 @@ void blockstore_disk_t::open_meta()
void blockstore_disk_t::open_journal() void blockstore_disk_t::open_journal()
{ {
if (journal_device != meta_device || cached_io_journal != cached_io_meta) if (journal_device != meta_device || journal_io != meta_io)
{ {
journal_fd = open(journal_device.c_str(), (cached_io_journal ? O_SYNC : O_DIRECT) | O_RDWR); journal_fd = open(journal_device.c_str(), bs_openmode(journal_io) | O_RDWR);
if (journal_fd == -1) if (journal_fd == -1)
{ {
throw std::runtime_error("Failed to open journal device "+journal_device+": "+std::string(strerror(errno))); throw std::runtime_error("Failed to open journal device "+journal_device+": "+std::string(strerror(errno)));

View File

@ -31,8 +31,9 @@ struct blockstore_disk_t
uint32_t csum_block_size = 4096; uint32_t csum_block_size = 4096;
// By default, Blockstore locks all opened devices exclusively. This option can be used to disable locking // By default, Blockstore locks all opened devices exclusively. This option can be used to disable locking
bool disable_flock = false; bool disable_flock = false;
// Use Linux page cache for reads and writes, i.e. open FDs with O_SYNC instead of O_DIRECT // I/O modes for data, metadata and journal: direct or "" = O_DIRECT, cached = O_SYNC, directsync = O_DIRECT|O_SYNC
bool cached_io_data = false, cached_io_meta = false, cached_io_journal = false; // O_SYNC without O_DIRECT = use Linux page cache for reads and writes
std::string data_io, meta_io, journal_io;
int meta_fd = -1, data_fd = -1, journal_fd = -1; int meta_fd = -1, data_fd = -1, journal_fd = -1;
uint64_t meta_offset, meta_device_sect, meta_device_size, meta_len, meta_format = 0; uint64_t meta_offset, meta_device_sect, meta_device_size, meta_len, meta_format = 0;

View File

@ -74,7 +74,7 @@ static const char *help_text =
" If it doesn't succeed it issues a warning in the system log.\n" " If it doesn't succeed it issues a warning in the system log.\n"
" \n" " \n"
" You can also pass other OSD options here as arguments and they'll be persisted\n" " You can also pass other OSD options here as arguments and they'll be persisted\n"
" in the superblock: cached_io_data, cached_io_meta, cached_io_journal,\n" " in the superblock: data_io, meta_io, journal_io,\n"
" inmemory_metadata, inmemory_journal, max_write_iodepth,\n" " inmemory_metadata, inmemory_journal, max_write_iodepth,\n"
" min_flusher_count, max_flusher_count, journal_sector_buffer_count,\n" " min_flusher_count, max_flusher_count, journal_sector_buffer_count,\n"
" journal_no_same_sector_overwrites, throttle_small_writes, throttle_target_iops,\n" " journal_no_same_sector_overwrites, throttle_small_writes, throttle_target_iops,\n"

View File

@ -8,9 +8,9 @@
int disk_tool_t::prepare_one(std::map<std::string, std::string> options, int is_hdd) int disk_tool_t::prepare_one(std::map<std::string, std::string> options, int is_hdd)
{ {
static const char *allow_additional_params[] = { static const char *allow_additional_params[] = {
"cached_io_data", "data_io",
"cached_io_meta", "meta_io",
"cached_io_journal", "journal_io",
"max_write_iodepth", "max_write_iodepth",
"max_write_iodepth", "max_write_iodepth",
"min_flusher_count", "min_flusher_count",
@ -119,7 +119,7 @@ int disk_tool_t::prepare_one(std::map<std::string, std::string> options, int is_
try try
{ {
dsk.parse_config(options); dsk.parse_config(options);
dsk.cached_io_data = dsk.cached_io_meta = dsk.cached_io_journal = false; dsk.data_io = dsk.meta_io = dsk.journal_io = "direct";
dsk.open_data(); dsk.open_data();
dsk.open_meta(); dsk.open_meta();
dsk.open_journal(); dsk.open_journal();
@ -483,7 +483,7 @@ int disk_tool_t::get_meta_partition(std::vector<vitastor_dev_info_t> & ssds, std
{ {
blockstore_disk_t dsk; blockstore_disk_t dsk;
dsk.parse_config(options); dsk.parse_config(options);
dsk.cached_io_data = dsk.cached_io_meta = dsk.cached_io_journal = false; dsk.data_io = dsk.meta_io = dsk.journal_io = "direct";
dsk.open_data(); dsk.open_data();
dsk.open_meta(); dsk.open_meta();
dsk.open_journal(); dsk.open_journal();

View File

@ -91,7 +91,7 @@ int disk_tool_t::resize_parse_params()
try try
{ {
dsk.parse_config(options); dsk.parse_config(options);
dsk.cached_io_data = dsk.cached_io_meta = dsk.cached_io_journal = false; dsk.data_io = dsk.meta_io = dsk.journal_io = "direct";
dsk.open_data(); dsk.open_data();
dsk.open_meta(); dsk.open_meta();
dsk.open_journal(); dsk.open_journal();