GNAT SQLite绑定中extension aggregate报错及错误处理问题咨询
GNAT SQLite绑定错误处理问题排查与解决
使用GNAT的SQLite绑定(Gnade)时,需要捕获绑定产生的错误。查阅代码后得知可通过提供错误处理对象建立连接,但调整该对象时要么库不接受,要么触发运行时访问检查错误(指针未离开声明作用域本应有效,但Ada机制可能不同)。
遇到的错误信息
type of aggregate has private ancestor "Error_Reporter"
must use extension aggregate
原始Error_Reporter定义
type Error_Reporter is abstract tagged private; ... private type Error_Reporter is abstract tagged null record;
问题代码结构
头文件
-- type Error_Handler is new Gse.Error_Reporter with private; type Error_Handler is new Gse.Error_Reporter with record Message : Asu.Unbounded_String; end record; type Error_Handler_Access is access Error_Handler; procedure On_Error (Self : in out Error_Handler; Connection : access Gse.Database_Connection_Record'Class; Message : String); -- more stuff ... -- private -- type Error_Handler is new Gse.Error_Reporter with record -- Message : Asu.Unbounded_String; -- end record;
实现部分
... declare pragma Suppress (Accessibility_Check); -- Handler : constant Error_Handler_Access := -- new Error_Handler'(Message => Asu.Null_Unbounded_String); Handler : constant access Error_Handler := new Error_Handler'(Message => Asu.Null_Unbounded_String); -- Handler : aliased Error_Handler; Descr : Gse.Database_Description := Gss.Setup (Db_File, Errors => Handler); -- Gss.Setup (Db_File, Errors => Handler'Access); ...
尝试过的方案
注释代码均为尝试过的写法:
- 使用
Error_Handler_Access类型创建处理对象 - 直接用
access Error_Handler声明对象 - 声明别名
Error_Handler对象 - 添加
pragma Suppress (Accessibility_Check)禁用可访问性检查(无效)
理想状态是不使用new操作创建对象,除非GNAT接口强制要求;更希望能绕过错误处理对象,直接获取SQLite连接与错误信息,但这种写法可读性差且会隐藏核心功能。
最终解决方法
问题根源在于不会使用Gnade包的Bind_XXX系列过程,转而使用Execute包导致错误报告异常。解决Bind_XXX(尤其是Bind_Text的Ada与C指针转换)问题后,重写代码仅使用Gnade包,错误处理问题得到解决。
内容的提问来源于stack exchange,提问作者wvxvw
相关产品推荐
相关产品推荐

