diff --git a/doc/chat_audit_findings.txt b/doc/chat_audit_findings.txt index d94971f53..41d1e6d82 100644 --- a/doc/chat_audit_findings.txt +++ b/doc/chat_audit_findings.txt @@ -1204,3 +1204,52 @@ libuasync/Opus в собственной копии,без смешения об Desktop/Android/GUI11/JVM155 PASS указаны выше. Последующая маленькая правка Android headless1b0034e1 не входит в APK/CMake-targets;отдельная C99 syntax проверка этого C-файла PASS. Внешние отметки feedback/poll закрыты,прочие chat/ продолжаются. + +Атомарное создание канала — 27.10.2026,после1c5faaff + +Создание раньше сохраняло описание/схему/runtime до проверки подписи root JOIN. +Правильный отрицательный контроль отбирает именно112-байтовое JOIN-тело с +публичным ключом instance по смещению72:/tmp/chat-channel-root-negative.log. +Первая проба выбирала вторую подпись по счётчику и задевала другое57-байтовое +runtime-тело;она не доказывала отказ root JOIN и заменена точным условием. + +Теперь direct create проверяет канонический ID1..INT64_MAX,локального владельца, +NUL-имя<=127байт,обе пары ключей и подпись описания. Подписи root JOIN,приглашения +и профиля готовятся до SQL. Своя BEGIN IMMEDIATE объединяет новое описание, +таблицы,полный root-member и Merkle;занятый ID не заменяется. Автор повторно +проверяется из сохранённых блоков до commit. Внешняя транзакция отклоняется. +Неудачный rollback с оставшейся транзакцией запрашивает stop,закрытие остаётся +владельцу БД вне callback. CHANNEL_UPDATED и member-notification идут после commit. + +Runtime подготавливается после commit;его ошибка логируется как отложенная +активация,сохранённый канал остаётся успешным результатом. Повтор +ensure_channel_ready либо restart завершает подготовку. Полный откат SQL вместе +с файловыми/сетевыми ресурсами не имитируется. Auto проверяет все этапы независимой +генерации X25519 и raw Ed25519 seed,размеры извлечённых ключей,RNG и подписи; +очищает временную структуру OPENSSL_cleanse и возвращает ID>0 только при commit. +Native headless передаёт отказ либо created:true/channel_id;trampoline очищает +переданную структуру с приватными ключами перед освобождением. + +Один codec описания используется создателем и двумя JOIN/invite-проверками: +id\0||name\0||owner(native u64)||X25519(32)||Ed25519(32). Он проверяет границы +и не меняет выход при отказе;существующий порядок байтов wire сохранён. +Generic channel_put имеет собственный savepoint для схемы/индексов/метаданных; +отказ ROLLBACK TO не сопровождается RELEASE частичных изменений. + +Дополнительная настоящая регрессия выявила отдельный дефект:ошибка шестого bind +профильной подписи становилась NULL,а канал объявлялся созданным. Контроль: +/tmp/chat-channel-profile-bind-negative.log. member_block_put теперь проверяет +все11 bind,step,changes=1,finalize и передаёт ошибку общей транзакции. + +Новый test_chat_channel проверяет42 SQL-отказа и19 криптоотказов с отдельным +успешным повтором каждого,реальные ABORT/IGNORE и commit veto,чужую транзакцию, +ошибку rollback с последующим owner-close,отказ выделения SQL и сохранность +runtime-групп. Readonly-соединение сверяет канальные поля/ключи,схему и все +Merkle-хеши до/после отказа и уже из обработчика события;root-профиль проверяется +настоящей Ed25519-подписью. Проверены канонические ID,точный wire348,неизменность +error-output,предельные имя127/codec255 и INT64_MAX,несогласованные ключи/владелец/ +подпись,занятый ID. Настоящий локальный TCP/uasync API выдаёт ok:false при отказе +BEGIN и committed channel_id при повторе. Allocation balance восстановлен. +/tmp/chat-channel-boundaries-{build,test}.log — PASS;профиль13/13 до последнего +расширения SQL-проверок — /tmp/chat-channel-profile.log. Новые общие результаты +записываются отдельно после завершения;весь chat_core/chat/ ещё не закрыт. diff --git a/doc/tasks.md b/doc/tasks.md index 5f47685f8..59624d4f9 100644 --- a/doc/tasks.md +++ b/doc/tasks.md @@ -4,6 +4,17 @@ ## Текущие задачи +[+] **chat_channel: атомарное создание канала и правдивый результат команды** — 27.10.2026. + Канальные пары ключей и подпись проверяются до записи; описание, схема, root JOIN, подписанный профиль, + приглашение и Merkle сохраняются одним commit. Runtime-подготовка и события выполняются после него. + Ошибка подготовки не удаляет сохранённый канал, допускается повтор ensure_channel_ready. + Исправлены частичная схема channel_put и незамеченный отказ bind подписи профиля в member_block_put. + Auto возвращает committed ID или0; native headless возвращает ошибку при отказе, очищаются временные ключи. + test_chat_channel:42 SQL-отказа и19 криптоотказов с успешными повторами,ABORT/IGNORE/veto, + чужая транзакция,ошибка rollback,границы и TCP API;readonly-проверка данных/схемы/Merkle до события. + Профильные проверки PASS;общая проверка текущего блока записывается в отчёт после завершения. + Подробнее:[chat_audit_findings.txt](chat_audit_findings.txt),«Атомарное создание канала». + [+] **feedback/poll: проверенное чтение версий, собственные транзакции и подтверждение уже сохранённой команды** — 27.10.2026. SQL-ошибка поиска не считается отсутствием старого состояния:отмена не заменяется прежней реакцией. apply/set/page/init владеют BEGIN IMMEDIATE/COMMIT;версия/допуск/запись/Merkle фиксируются вместе, diff --git a/src/routing_layer/topo_node_sqlite_doc.md b/src/routing_layer/topo_node_sqlite_doc.md index 7cef75dd3..9f0eb96e1 100644 --- a/src/routing_layer/topo_node_sqlite_doc.md +++ b/src/routing_layer/topo_node_sqlite_doc.md @@ -84,6 +84,9 @@ update_rtt обновляет node_addresses.rtt и peers_*.node_RTT в един channel_put требует публичные ключи по 32 байта и подпись 64 байта. При конфликте channel_id публичные ключи должны совпасть: меняются имя/владелец/подпись, переданные privkey заменяют прежние, NULL сохраняет их. Криптографическую проверку делает вызывающий. +SAVEPOINT channel_put атомарно объединяет описание с peers-таблицей, локальной схемой и индексами. +Проверяются выделение SQL, все bind/step/changes=1/finalize и RELEASE; при отказе частичная схема не фиксируется. +Если ROLLBACK TO сам завершился ошибкой, RELEASE не выполняется: открытая транзакция требует отката/закрытия БД владельцем. Суффикс таблиц строится из первых 63 символов channel_id: вне [A-Za-z0-9_] заменяются на '_'. Штатные channel_id — десятичные uint64. Строка channels.channel_id хранит исходное значение. @@ -91,6 +94,7 @@ channel_put требует публичные ключи по 32 байта и member_placeholder_put вставляет source=1 с нулевой join_sig; существующую строку не меняет. member_block_put заменяет ключи/join/update/userinfo/дерево приглашений и устанавливает source=0, сохраняя owner-блок и локальные поля. NULL join_sig записывается как 64 нулевых байта. +Все 11 bind, step, changes=1 и finalize проверяются; функция работает в транзакции вызывающего. member_owner_put меняет adm_tags/подпись/storage/deleted без вставки отсутствующей строки. Placeholder не участвует в Merkle-хеше; сетевой формат и проверка версий принадлежат member_sync.