Skip to content

refactor(crc): убрать повторные чтения файлов в FileCRC (буферный API)#3373

Merged
bylins merged 7 commits into
masterfrom
refactor/file-crc-buffer
May 31, 2026
Merged

refactor(crc): убрать повторные чтения файлов в FileCRC (буферный API)#3373
bylins merged 7 commits into
masterfrom
refactor/file-crc-buffer

Conversation

@kvirund
Copy link
Copy Markdown
Collaborator

@kvirund kvirund commented May 31, 2026

Вторая часть оптимизации CRC-подсистемы (продолжение #3369, цель — ветка PR #3369). Убирает все повторные чтения файлов в FileCRC: подсистема больше не читает файлы сама, а считает/сверяет CRC из буферов, которые вызывающий код и так держит в памяти.

Что сделано

  • Буферный API FileCRC: update_from_content (запись), verify_from_contentbool (сверка), reset (сброс для удалённого файла) поверх общего внутреннего сеттера.
  • Загрузка .obj/.time/pfile: сверка CRC из уже прочитанного буфера вместо второго чтения файла. ReadCrashTimerFile переписан на «слить в буфер → сверить → парсить из буфера» (заодно починена утечка дескриптора в ветке corrupt).
  • Удаление (Crash_delete_files): прямой reset вместо check_crc на уже удалённом файле.
  • Сохранение pfile: переведено с ~160 fprintf(FILE*) на BufferedFileWriter — printf-совместимый писатель в std::string через vsnprintf (без переполнения при любой длине поля, в отличие от legacy fbprintf/vsprintf). CRC из буфера, файл пишется бинарно.
  • Удалены осиротевшие check_crc и calculate_file_crcFileCRC больше не делает файлового I/O.

Тесты

  • tests/file_crc.cpp — буферный API (roundtrip, обнаружение расхождения, reset, базовый снимок, независимость типов файлов).
  • tests/buffered_file_writer.cpp — golden-тесты writer'а (побайтовое совпадение с snprintf, длинные поля без обрезки).
  • Полный сьют: 429 passed.

Refs #3368

@kvirund kvirund force-pushed the perf/player-frac-save-async branch from c434a03 to 70d967f Compare May 31, 2026 04:33
kvirund added 3 commits May 31, 2026 06:34
Готовит почву для устранения повторных чтений файлов в CRC-подсистеме.
Общий внутренний сеттер set_crc_field (upsert + поле по типу файла);
update_from_content переведён на него и снова поддерживает все три типа.
Добавлено:
- reset(uid, mode) -- сброс CRC в 0 для удалённого файла;
- verify_from_content(uid, mode, buf, len) -> bool -- сверка CRC из
  готового буфера вместо повторного чтения файла на загрузке.

tests/file_crc.cpp покрывает roundtrip, обнаружение расхождений, reset,
базовый снимок и независимость типов файлов.

Refs #3368
…вания

- Crash_delete_files: вместо check_crc на уже удалённом файле (чтобы
  получить 0 повторным чтением) -- прямой FileCRC::reset.
- Загрузка .obj: сверка CRC из уже прочитанного буфера readdata через
  verify_from_content, без второго чтения файла. В ветке ошибки чтения
  бессмысленная сверка перечитыванием убрана (валидного буфера нет).

Refs #3368
- ReadCrashTimerFile: файл читается целиком в буфер, CRC сверяется из
  него (verify_from_content), записи парсятся из того же буфера -- без
  второго чтения. Заодно починена утечка дескриптора в ветке "corrupt".
- Загрузка pfile: сверка CRC из fb-буфера (весь файл уже в памяти) до
  fbclose, без повторного чтения.

Refs #3368
@kvirund kvirund force-pushed the refactor/file-crc-buffer branch from 3135620 to 92472d3 Compare May 31, 2026 04:36
kvirund added 2 commits May 31, 2026 07:01
pfile теперь пишется в BufferedFileWriter (printf-совместимый писатель в
std::string через vsnprintf -- без переполнения при любой длине поля), а
CRC считается из этого буфера (update_from_content), без перечитывания
только что записанного файла. Файл пишется в бинарном режиме (байты ==
буфер на всех платформах).

Переведены на BufferedFileWriter все цепочки записи pfile:
- Player::save_char + quested_save/mobmax_save;
- save_pkills (pk.cpp);
- Quested::save, MobMax::save.

tests/buffered_file_writer.cpp -- golden-тесты writer'а (совпадение с
snprintf, длинные поля без обрезки).

Refs #3368
После перевода всех путей (сохранение, загрузка, удаление) на буферный
API (update_from_content/verify_from_content/reset) у check_crc и
calculate_file_crc не осталось вызовов -- FileCRC больше не читает файлы
сам, а работает с буферами, которые вызывающий код и так держит в памяти.

Refs #3368
@kvirund kvirund force-pushed the refactor/file-crc-buffer branch from 92472d3 to 8131d42 Compare May 31, 2026 05:12
enum EType { kPlayer, kTextObjs, kTimeObjs } (unscoped, в namespace
FileCRC) вместо анонимного int-enum с PLAYER/.../UPDATE_*. update/reset/
verify_from_content берут EType; switch'и исчерпывающие -- компилятор
ловит непокрытый кейс, рантайм-проверки "неподдерживаемый режим" убраны.
Глагол (запись, сверка, сброс) и так в имени функции, поэтому UPDATE_-
варианты схлопнуты. Вызовы двухкомпонентные: FileCRC::kTextObjs.

Refs #3368
@kvirund kvirund force-pushed the refactor/file-crc-buffer branch from 8131d42 to 2bd9cf0 Compare May 31, 2026 05:18
На clang-cl новые тест-файлы оказывались первыми в unity-чанке и тянули
utils/*.h -> conf.h/sysdep.h -> structs.h -> <vector> раньше системных
заголовков, ломая интринсик-заголовки MSVC/clang (mmintrin.h, __v2si).
Подключаем <gtest/gtest.h> первым, как в остальных тестах.

Refs #3368
Base automatically changed from perf/player-frac-save-async to master May 31, 2026 06:01
@bylins bylins merged commit cdb615e into master May 31, 2026
20 checks passed
@bylins bylins deleted the refactor/file-crc-buffer branch May 31, 2026 06:01
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants