- 第一章 SystemVerilog导论
- 第二章 文本值
- 第三章 数据类型
- 第四章 数组
- 第五章 数据声明
- 第六章 属性
- 第七章 操作符与表达式
- 第八章 过程语句和控制流
- 第九章 进程
- 第十章 任务与函数
- 第十一章 类
- 第十二章 随机约束
- 第十三章 进程间的同步与通信
- 第十四章 调度语义
- 第十五章 时钟控制块
- 第十六章 程序块
- 第十七章 断言
- 第十八章 层次
- 第十九章 接口
- 第二十章 覆盖
- 第二十一章 参数
- 第二十二章 配置库
- 第二十三章 系统任务与系统函数
- 23.1 简介(一般信息)
- 23.2 确立时的typeof函数
- 23.3 typename函数
- 23.4 表达式尺寸系统函数
- 23.5 范围系统函数
- 23.6 Shortreal转换
- 23.7 数组查询系统函数
- 23.8 断言严重性系统任务
- 23.9 断言控制系统任务
- 23.10 断言系统函数
- 23.11 随机数系统函数
- 23.12 程序控制
- 23.13 覆盖系统函数
- 23.14 对Verilog-2001系统任务的增强
- 23.15 $readmemb与$readmemh
- 23.16 $writememb and $writememh
- 23.17 File format considerations for multi-dimensional unpacked arrays
- 23.18 System task arguments for multi-dimensional unpacked arrays
- 第二十四章 VCD数据
- 第二十五章 编译器指令
- 第二十六章 考虑从SystemVerilog中删除的功能
- 第二十七章 直接编程接口(DPI)
- 27.1 概述
- 27.2 Two layers of the DPI
- 27.3 Global name space of imported and exported functions
- 27.4 导入的任务和函数
- 27.5 Calling imported functions
- 27.6 Exported functions
- 27.7 Exported tasks
- 27.8 Disabling DPI tasks and functions
- 第二十八章 SystemVerilog断言API
- 第二十九章 SystemVerilog覆盖API
- 29.1 需求
- 29.2 SystemVerilog real-time coverage access
- 29.3 FSM recognition
- 29.3.1 Specifying the signal that holds the current state
- 29.3.2 Specifying the part-select that holds the current state
- 29.3.3 Specifying the concatenation that holds the current state
- 29.3.4 Specifying the signal that holds the next state
- 29.3.5 Specifying the current and next state signals in the same declaration
- 29.3.6 Specifying the possible states of the FSM
- 29.3.7 Pragmas in one-line comments
- 29.3.8 Example
- 29.4 VPI coverage extensions
- 第三十章 SystemVerilog数据读API
- 30.1 简介(一般信息)
- 30.2 需求
- 30.3 Extensions to VPI enumerations
- 30.4 VPI object type additions
- 30.5 Object model diagrams
- 30.6 Usage extensions to VPI routines
- 30.7 VPI routines added in SystemVerilog
- 30.8 Reading data
- 30.9 Optionally unloading the data
- 30.10 Reading data from multiple databases and/or different read library providers
- 30.11 VPI routines extended in SystemVerilog
- 30.12 VPI routines added in SystemVerilog
- 30.12.1 VPI reader routines
- 第三十一章 SystemVerilog VPI Object Model
- 31.1 简介(一般信息)
- 31.2 Instance
- 31.3 Interface
- 31.4 Program
- 31.5 Module (supersedes IEEE 1364-2001 26.6.1)
- 31.6 Modport
- 31.7 Interface tf decl
- 31.8 Ports (supersedes IEEE 1364-2001 26.6.5)
- 31.9 Ref Obj
- 31.9.1 Examples
- 31.10 Variables (supersedes IEEE 1364-2001 section 26.6.8)
- 31.11 Var Select (supersedes IEEE 1364-2001 26.6.8)
- 31.12 Typespec
- 31.13 Variable Drivers and Loads (supersedes IEEE 1364-2001 26.6.23)
- 31.14 Instance Arrays (supersedes IEEE 1364-2001 26.6.2)
- 31.15 Scope (supersedes IEEE 1364-2001 26.6.3)
- 31.16 IO Declaration (supersedes IEEE 1364-2001 26.6.4)
- 31.17 Clocking Block
- 31.18 Class Object Definition
- 31.19 Constraint, constraint ordering, distribution,
- 31.20 Constraint expression
- 31.21 Class Variables
- 31.22 Structure/Union
- 31.23 Named Events (supersedes IEEE 1364-2001 26.6.11)
- 31.24 Task, Function Declaration (supersedes IEEE 1364-2001 26.6.18)
- 31.25 Alias Statement
- 31.25.1 Examples
- 31.26 Frames (supersedes IEEE 1364-2001 26.6.20)
- 31.27 Threads
- 31.28 tf call (supersedes IEEE 1364-2001 26.6.19)
- 31.29 Module path, path term (supersedes IEEE 1364-2001 26.6.15)
- 31.30 Concurrent assertions
- 31.31 Property Decl
- 31.32 Property Specification
- 31.33 Multiclock Sequence Expression
- 31.34 Sequence Declaration
- 31.35 Sequence Expression
- 31.36 Attribute (supersedes IEEE 1364-2001 26.6.42)
- 31.37 Atomic Statement (supersedes IEEE 1364-2001 26.6.27)
- 31.38 If, if else, return, case, do while (supersedes IEEE 1364-2001 26.6.35, 26.6.36)
- 31.39 waits, disables, expect, foreach (supersedes IEEE 1364 26.6.38)
- 31.40 Simple expressions (supersedes IEEE 1364-2001 26.6.25)
- 31.41 Expressions (supersedes IEEE 1364-2001 26.6.26)
- 31.42 Event control (supersedes IEEE 1364-2001 26.6.30)
- 31.43 Event stmt (supersedes IEEE 1364-2001 26.6.27)
- 31.44 Process (supersedes IEEE 1364-2001 26.6.27)
- 31.45 Assignment (supersedes IEEE 1364-2001 26.6.28)
- 附录A 形式语法
- A.1 源文本
- A.2 声明
- A.3 Primitive instances
- A.4 Module, interface and generated instantiation
- A.5 UDP declaration and instantiation
- A.6 Behavioral statements
- A.6.1 Continuous assignment and net alias statements
- A.6.2 Procedural blocks and assignments
- A.6.3 Parallel and sequential blocks
- A.6.4 Statements
- A.6.5 Timing control statements
- A.6.6 Conditional statements
- A.6.7 Case statements
- A.6.8 Looping statements
- A.6.9 Subroutine call statements
- A.6.10 Assertion statements
- A.6.11 Clocking block
- A.6.12 Randsequence
- A.7 Specify section
- A.8 Expressions
- A.9 General
- A.10 Footnotes (normative)
- 附录B 关键字
- 附录C 标准包
- 附录D 链表
- 附录E DPI C-layer
- E.1 概述
- E.2 Naming conventions
- E.3 Portability
- E.4 Include files
- E.5 Semantic constraints
- E.6 Data types
- E.7 Argument passing modes
- E.8 Context tasks and functions
- E.9 Include files
- E.10 Arrays
- E.11 Open arrays
- E.11.1 Actual ranges
- E.11.2 Array querying functions
- E.11.3 Access functions
- E.11.4 Access to the actual representation
- E.11.5 Access to elements via canonical representation
- E.11.6 Access to scalar elements (bit and logic)
- E.11.7 Access to array elements of other types
- E.11.8 Example 4— two-dimensional open array
- E.11.9 Example 5 — open array
- E.11.10 Example 6 — access to packed arrays
- E.11.11 Example 7 — binary compatible calls of exported functions
- 附录F 包含文件
- 附录G 包含外部语言代码
- 附录H 并发断言的形式语义
- 附录I svvpiuser.h
- 附录J 术语表
- 附录K 参考书目
- 其他
30.10 Reading data from multiple databases and/or different read library providers
The VPI routine vpi_load_extension() is used to load VPI extensions. Such extensions include reader libraries from such tools as waveform viewers. vpi_load_extension() shall return a pointer to a function pointer structure with the following definition.
typedef struct { void *user_data; /* Attach user data here if needed */ /* Below this point user application MUST NOT modify any values */ size_t struct_size; /* Must be set to sizeof(s_vpi_extension) */ long struct_version; /* Set to 1 for SystemVerilog 3.1a */ PLI_BYTE8 *extension_version; PLI_BYTE8 *extension_name; /* One function pointer for each of the defined VPI routines: - Each function pointer has to have the correct prototype */ ... PLI_INT32 (*vpi_chk_error)(error_info_p); ... PLI_INT32 (*vpi_vprintf)(PLI_BYTE8 *format, ...); ... } s_vpi_extension, *p_vpi_extension;
Subsequent versions of the s_vpi_extension structure shall only extend it by adding members at the end; previously existing entries must not be changed, removed, or re-ordered in order to preserve backward compatability. The struct_size entry allows users to perform basic sanity checks (e.g. before type casting), and the struct_version permits keeping track and checking the version of the s_vpi_extension structure. The structure also has a user_data field to give users a way to attach data to a particular load of an extension if they wish to do so.
The structure shall have an entry for every VPI routine; the order and synopsis of these entries within the structure shall exactly match the order and synopsis of function definitions in Chapter 27 of the Verilog Standard, IEEE Std 1364-2001. After those entries the SystemVerilog VPI routine additions for assertions vpi_get_assertion_info() and then vpi_register_assertion_cb() shall be added in that order. Then all new reader routines defined in Table 30-3 shall be added in exactly the order noted in the table. If a particular extension does not support a specific VPI routine, then it shall still have an entry (with the correct prototype), and a dummy body that shall always have a return (consistent with the VPI prototype) to signify failure (i.e. NULL or FALSE ). The routine call must also raise the appropriate VPI error, which can be checked by vpi_chk_error(), and/or automatically generate an error message in a manner consistent with the specific VPI routine.
If tool providers want to add their own implementation extensions, those extensions must only have the effect of making the s_vpi_extension structure larger and any non-standard content must occur after all the standard fields. This permits applications to use the pointer to the extended structure as if it was a p_vpi_extension pointer, yet still allow the applications to go beyond and access or call tool-specific fields or routines in the extended structure. For example, a tool extended s_vpi_extension could be:
typedef struct { /* inline a copy of s_vpi_extension */ /* begin */ void *user_data; ... /* end */ /* “toolZ” extension with one additional routine */ int (*toolZfunc)(int); } s_toolZ_extension, *p_toolZ_extension;
An example of use of the above extended structure is as follows:
p_vpi_extension h; p_toolZ_extension hZ; h = vpi_load_extension(“toolZ”, <args>); if ( h && (h->struct_size >= sizeof(s_toolZ_extension)) && !(strcmp(h->extension_version, “...”) && !strcmp(h->extension_name, “toolZ”) ) { hZ = (p_toolZ_extension) h; /* Can now use hZ to access all the VPI routines, including toolZ’s ‘toolZfunc’ */ ... }
The SystemVerilog tool the user application is running under is responsible for loading the appropriate extension, i.e. the reader API library in the case of the read API. The extension name is used for this purpose, following a specific policy, for example, this extension name can be the name of the library to be loaded. Once the reader API library is loaded all VPI function calls that wish to use the implementation in the library shall be performed using the returned p_vpi_extension pointer as an indirection to call the function pointers specified in s_vpi_extension or the extended vendor specific structure as described above. Note that, as stated earlier, in the case the application is using the built-in routine implementation (i.e. the ones provided by the tool (e.g. simulator) it is running under) then the de-reference through the pointer is not necessary.
Multiple databases can be opened for read simultaneously by the application. After a vpi_load_extension() call, a top scope handle can be created for that database to be used later to derive any other handles for objects in that database. An example of multiple database access is shown below. In the example, scope1 and scope2 are the top scope handles used to point into database1 and database2 respectively and perform the processing (comparing data in the two databases for example).
p_vpi_extension reader_pX; /* Pointer to reader libraryfunction struct */ p_vpi_extension reader_pY; /* Pointer to reader libraryfunction struct */ vpiHandle scope1, scope2; /* Some scope being looked at */ vpiHandle var_handle; /* Object handle */ vpiHandle some_net; /* Handle of some net */ vpiHandle some_reg; /* Handle of some reg */ vpiHandle vc_trvs_hdl1; /* Traverse handle */ vpiHandle vc_trvs_hdl2; /* Traverse handle */ vpiHandle itr; /* Iterator */ vpiHandle objCollection1, objCollection2; /* Object collection */ vpiHandle trvsCollection1, trvsCollection2; /* Traverse collection */ p_vpi_time time_p; /* time */ PLI_BYTE8 *data1 = “database1”; PLI_BYTE8 *data2 = “database2”; /* Initialize the read interface: Post process mode, read from a database */ /* NOTE: Use library from “toolX” */ reader_pX = vpi_load_extension(“toolX”, data1, vpiAccessPostProcess); /* Get the scope using its name */ /* NOTE: scope handle comes from database: data1 */ scope1 = reader_pX->vpi_handle_by_name(“top.m1.s1”, NULL); /* Initialize the read interface: Post process mode, read from a database */ /* NOTE: Use library from “toolY” */ reader_pY = vpi_load_extension(“toolY”, data2, vpiAccessPostProcess); /* Get the scope using its name */ /* NOTE: scope handle comes from database: data2 */ scope2 = reader_pY->vpi_handle_by_name(“top.m1.s1”, NULL); /* Create object collections */ objCollection1 = reader_pX->vpi_create(vpiObjCollection, NULL, NULL); objCollection2 = reader_pY->vpi_create(vpiObjCollection, NULL, NULL); /* Add data to collection1: All the nets in scope1, data comes from database1 */ /* ASSUMPTION: (waveform) tool supports this navigation relationship */ itr = reader_pX->vpi_iterate(vpiNet, scope1); while (var_handle = reader_pX->vpi_scan(itr)) { objCollection1 = reader_pX->vpi_create(vpiObjCollection, objCollection1, var_handle); } /* Add data to collection2: All the nets in scope2, data comes from database2 */ /* ASSUMPTION: (waveform) tool supports this navigation relationship */ itr = reader_pY->vpi_iterate(vpiNet, scope2); while (var_handle = reader_pY->vpi_scan(itr)) { objCollection2 = reader_pY->vpi_create(vpiObjCollection, objCollection2, var_handle); } /* Initialize the load: focus only on the signals in the object collection: objCollection */ reader_pX->vpi_load_init(objCollection1, NULL, 0); reader_pY->vpi_load_init(objCollection2, NULL, 0); /* Demo: Scan the object collection */ itr = reader_pX->vpi_iterate(vpiMember, objCollection1); while (var_handle = reader_pX->vpi_scan(itr)) { ... } itr = reader_pY->vpi_iterate(vpiMember, objCollection2); while (var_handle = reader_pY->vpi_scan(itr)) { ... } /* Application code here: Access Objects from database1 or database2 */ some_net = ...; time_p = ...; some_reg = ...; .... /* Data querying and processing here */ .... /* free handles*/ reader_pX->vpi_free_object(...); reader_pY->vpi_free_object(...); /* close databases */ reader_pX->vpi_close(0, vpiAccessPostProcess, data1); reader_pY->vpi_close(0, vpiAccessPostProcess, data2);
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论