A crash occurred in the odbc_handle_closer function
未关闭
还没有人认领这个 Issue。
Bug
Extension: pdo_odbc
Status: Needs Triage
- 主要语言
- C
- 星标
- 40.4k
- 派生
- 8.1k
- 平均合并
- 2 天 13 小时
- 30 天内合并 PR
- 96
描述
There is an issue with the order of resource release that needs to be corrected by modifying the code.
The correct code might be:
static void odbc_handle_closer(pdo_dbh_t *dbh) {
pdo_odbc_db_handle *H = (pdo_odbc_db_handle *) dbh->driver_data;
SQLFreeHandle(SQL_HANDLE_ENV, H->env);
H->env = NULL;
if (H->dbc != SQL_NULL_HANDLE) {
SQLEndTran(SQL_HANDLE_DBC, H->dbc, SQL_ROLLBACK);
SQLDisconnect(H->dbc);
SQLFreeHandle(SQL_HANDLE_DBC, H->dbc);
H->dbc = NULL;
}
pefree(H, dbh->is_persistent);
dbh->driver_data = NULL;
}
I don't quite understand the logic of the ODBC PDO driver, please review the code above.
==45879== Invalid read of size 8
==45879== at 0x1185F941: ??? (in /usr/lib/libodbccr.so.2.0.0)
==45879== by 0x734F411: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x7351182: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x7359691: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x7B01E10: odbc_handle_closer (odbc_driver.c:139)
==45879== by 0x73F800E: ??? (in /usr/lib/php84/modules/pdo.so)
==45879== by 0x5CE98E: zend_objects_store_del (in /usr/bin/php84)
==45879== by 0x586F32: ??? (in /usr/bin/php84)
==45879== by 0x534247: execute_ex (in /usr/bin/php84)
==45879== by 0x52D64B: zend_call_function (in /usr/bin/php84)
==45879== by 0x799996A: swoole::PHPCoroutine::main_func(void*) (swoole_coroutine.cc:773)
==45879== by 0x7A2B6C7: operator() (std_function.h:591)
==45879== by 0x7A2B6C7: swoole::coroutine::Context::context_func(transfer_t) (context.cc:149)
==45879== Address 0x11079928 is 2,344 bytes inside a block of size 5,256 free'd
==45879== at 0x48B2ECF: free (in /usr/libexec/valgrind/vgpreload_memcheck-amd64-linux.so)
==45879== by 0x73788CA: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x73597E7: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x7B01DFB: odbc_handle_closer (odbc_driver.c:136)
==45879== by 0x73F800E: ??? (in /usr/lib/php84/modules/pdo.so)
==45879== by 0x5CE98E: zend_objects_store_del (in /usr/bin/php84)
==45879== by 0x586F32: ??? (in /usr/bin/php84)
==45879== by 0x534247: execute_ex (in /usr/bin/php84)
==45879== by 0x52D64B: zend_call_function (in /usr/bin/php84)
==45879== by 0x799996A: swoole::PHPCoroutine::main_func(void*) (swoole_coroutine.cc:773)
==45879== by 0x7A2B6C7: operator() (std_function.h:591)
==45879== by 0x7A2B6C7: swoole::coroutine::Context::context_func(transfer_t) (context.cc:149)
==45879== by 0x7B1F70E: swoole_make_fcontext (make_x86_64_sysv_elf_gas.S:135)
==45879== Block was alloc'd at
==45879== at 0x48B640A: calloc (in /usr/libexec/valgrind/vgpreload_memcheck-amd64-linux.so)
==45879== by 0x7378711: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x734A3EE: ??? (in /usr/lib/libodbc.so.2.0.0)
==45879== by 0x7B022FE: pdo_odbc_handle_factory (odbc_driver.c:498)
==45879== by 0x73F2A2D: php_pdo_internal_construct_driver (in /usr/lib/php84/modules/pdo.so)
==45879== by 0x552BD0: ??? (in /usr/bin/php84)
==45879== by 0x534247: execute_ex (in /usr/bin/php84)
==45879== by 0x52D64B: zend_call_function (in /usr/bin/php84)
==45879== by 0x799996A: swoole::PHPCoroutine::main_func(void*) (swoole_coroutine.cc:773)
==45879== by 0x7A2B6C7: operator() (std_function.h:591)
==45879== by 0x7A2B6C7: swoole::coroutine::Context::context_func(transfer_t) (context.cc:149)
==45879== by 0x7B1F70E: swoole_make_fcontext (make_x86_64_sysv_elf_gas.S:135)
贡献指南
从这里开始
- 先读完整个 Issue,再读项目的贡献指南。
- 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
- Fork 仓库,在一个分支上完成修改。
- 提交 Pull Request,并在描述里引用这个 Issue 编号。
调研方向
从 ext/pdo_odbc/odbc_driver.c 中 136-139 行附近的 odbc_handle_closer 开始,然后检查 498 行附近的 pdo_odbc_handle_factory 以及链接的 Valgrind trace。根据报告的无效读取验证资源释放顺序,并确认报告的场景不再访问已释放的 ODBC 状态。
由索引模型根据 Issue 内容生成。
评估
- 技术栈
- c, php
- 领域
- databases
- Issue 类型
- 缺陷
- 难度
- 4/5
- 预计耗时
- 3-5 天
- 活跃度
- 冷清
- 描述清晰度
- 基本清楚
- 新手友好度
- 52/100