首批通过分布式安全可靠测评,为关键业务系统打造
动态 SQL 执行存储过程显式抛异常时,计算 sqlerrm crash 问题
更新时间:2026-05-29 08:46
问题现象
存储过程 A 内部使用动态 SQL 执行另一个存储过程B时,B 内部使用 raise_application_error 抛出异常,存储过程 A 内部捕获异常后,使用 sqlerrm 获取异常信息时,OBServer crash 了。
关键诊断信息
触发条件
存储过程 A 内部使用动态 SQL 执行另一个存储过程B时,B 内部使用 raise_application_error 抛出异常,存储过程 A 内部捕获异常后,使用 sqlerrm 获取异常信息。
问题原因
动态 SQL 执行时,会生成新的执行上下文,存储过程B内部 raise_application_error 执行时,会使用执行上下文上的 allocator 来分配内存存储诊断信息;动态 SQL 执行完执行上下文会清理掉,内存也回收了。使用 sqlerrm 获取诊断信息时,访问了已释放的内存空间,触发 crash。
问题的风险及影响
业务遇到该场景时,OBServer 可能会 crash 掉。
影响租户
影响 OceanBase 数据库中的 Oracle 租户和 MySQL 租户,对于 SYS 租户无影响。
影响版本
OceanBase 数据库企业版 V2.2.77 GA(oceanbase-2.2.77-20210508211731)及之后版本、V3.1.2 GA(oceanbase-3.1.2-20210618150922)及之后版本、V3.2.3 GA(oceanbase-3.2.3.0-20220418212020)及之后版本、V3.2.4 GA(oceanbase-3.2.4.0-100000072022102819)及之后版本、V4.1.0 GA(oceanbase-4.1.0.0-100001122023040322)及之后版本
解决方法
升级到问题已修复版本。目前已修复的版本包含 OceanBase 数据库企业版 V2.2.77 BP19(oceanbase-2.2.77-119000122024060513)及之后版本、V3.2.3 BP10(oceanbase-3.2.3.3-110000092023091219)及之后版本、V3.2.4 BP5(oceanbase-3.2.4.5-105000012023081513)及之后版本、V4.1.0 BP4(oceanbase-4.1.0.2-104000032023092119)及之后版本。
不使用动态 SQL 执行存储过程,或者动态 SQL 执行的存储过程内部不使用
raise_application_error显式抛异常。
规避方式
不使用动态 SQL 执行存储过程,或者动态 SQL 执行的存储过程内部不使用 raise_application_error 显式抛异常。