第二段:sequence/sequencer的调用

本文深入浅出地讲解了UVM中的Sequence机制,包括sequence_item、sequence、sequencer等核心概念的关系,以及如何通过sequence机制实现激励数据的生成与传递。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

   

简绍:

        transaction/sequence_item/sequence/sequencer 这几个东西对刚接触的人来说比较绕,刚开始看这个部分的时候我头都是大的,满屏幕的sequence sequencer 还有base,傻傻分不清楚,后来想了想,只要把sequence_base跟sequence理解成一个整体,把sequencer_base和sequencer理解成一个整体就好了。

        虽然这几个东西名字很像,但他们背后其实是有两套逻辑。

        对于sequence,它的本质是一个从object拓展出来的transaction,sequence是sequence_item的子类,也就是一个普通payload的加强版。

                preview

        对于sequencer,它的本质是一个从object扩展出来的component,它本身跟sequence_item没什么关系,要类比起来,它跟driver这种component更像,它跟driver可以理解成是同事。

                      

        打个比方,sequence_item是一个子弹,sequence是弹夹,它的作用是装子弹,而sequencer是一把枪,它的作用是把子弹射出去,driver也是一把枪。

        接下来就到了第二步,展开来看,sequence这个弹夹是怎么装子弹的。

        我们建立一个sequence类后,最主要要做的事情是建立一个函数来装子弹,如下所示:               

task body();
jelly_bean_transaction jb_tx;//这是个sequence_item
jb_tx = jelly_bean_transaction::type_id::create(.name("jb_tx"), .contxt(get_full_name()));
start_item(jb_tx);
assert(jb_tx.randomize());
finish_item(jb_tx);

        这篇总结的目的只有一个,理解从start_item到finish_item背后的逻辑。

        1)基础用法: 在sequence中合成激励数据,然后通过start函数启动body函数,我们在body函数中通过uvm_do(或者start_item,finish_item或者send)将激励发送出去,之后就通过fifo在drive拿到数据,然后波形化。

        2)项目升级用法:

        在tc中的csim通过start启动tb_mac的sequence的body(sequence的嵌套),

        然后设置发送激励参数,再次调用start进入主sequence的body函数,通过pack组装报文,send发出,进入driver中。

        3)底层原理分析:

       

调用start后,就会进入下图内容。

        在uvm第二章给我们介绍了最简单的uvm_do相应的宏,方便我们发送激励,在官方源码中,详细解释了这个宏主要下图几件事:

       

        从描述可以看到,start_item到finish_item的过程调用了两个东西,一个是sequencer,一个是parent_seq,parent_seq是眼下这个sequence的父类sequence,那说到底还是个sequence,也就是说儿子把父亲做的事情先做一遍,那不重要,我们不用管它。就看sequencer的调用好了,一看发现这就是一个wait-send-再wait的通信过程。Wait中定义了很多指针和队列,用来存储start函数放入的数据。

       

        我们在通过sequence_item来构造子弹的时候,系统帮我们实现声明了一把可以用的枪,这个枪就是sequencer_base,如果我们只是构造这个子弹,那么这个子弹和枪之间没有关系,但当我们通过sequence(弹夹)调用start_item的时候,系统就会为我们把子弹和枪联系起来。建立了这种联系后,我们后面才能调用枪(sequencer)的那三个通信函数。

        最后总结整个流程:

               a. 我们在声明sequence_item这个子弹和sequence这个弹夹的时候,系统都给我们预留了一把枪的位置。

                b. 当我们实现sequence(弹夹)的时候,具体而言是在sequence类中的start_item函数内,系统帮我们把子弹,弹夹和枪联系了起来。

                c. 在sequence类的ramdomize函数中实例化出具体的子弹。

               d. 在sequence类的finish_item函数中把实例化的子弹发送出去。

               

        Response的使用:sequence机制提供了一个机制,根据driver对tansaction的反应决定时候就接下来发送transaction(反馈机制),具有阻塞的功能,同时在pre_body函数中使用use_repinse_handler中重载,$cast(rsp,response),防止环境卡死。

String localPart参数指的是一下wdsl文件的那个参数;<wsdl:definitions xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:tns="http://webservice.mes.service.basic.example.com" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:ns1="http://schemas.xmlsoap.org/soap/http" name="MesWebServiceImplService" targetNamespace="http://webservice.mes.service.basic.example.com"> <wsdl:types> <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://webservice.mes.service.basic.example.com" elementFormDefault="unqualified" targetNamespace="http://webservice.mes.service.basic.example.com" version="1.0"> <xs:element name="getAllTechByProCode" type="tns:getAllTechByProCode"/> <xs:element name="getAllTechByProCodeResponse" type="tns:getAllTechByProCodeResponse"/> <xs:complexType name="getAllTechByProCode"> <xs:sequence> <xs:element minOccurs="0" name="productCode" type="xs:string"/> </xs:sequence> </xs:complexType> <xs:complexType name="getAllTechByProCodeResponse"> <xs:sequence> <xs:element minOccurs="0" name="return" type="tns:result"/> </xs:sequence> </xs:complexType> <xs:complexType name="result"> <xs:sequence> <xs:element minOccurs="0" name="code" type="xs:int"/> <xs:element minOccurs="0" name="data" type="xs:anyType"/> <xs:element minOccurs="0" name="msg" type="xs:string"/> </xs:sequence> </xs:complexType> </xs:schema> </wsdl:types> <wsdl:message name="getAllTechByProCodeResponse"> <wsdl:part element="tns:getAllTechByProCodeResponse" name="parameters"> </wsdl:part> </wsdl:message> <wsdl:message name="getAllTechByProCode"> <wsdl:part element="tns:getAllTechByProCode" name="parameters"> </wsdl:part> </wsdl:message> <wsdl:portType name="IMesWebService"> <wsdl:operation name="getAllTechByProCode"> <wsdl:input message="tns:getAllTechByProCode" name="getAllTechByProCode"> </wsdl:input> <wsdl:output message="tns:getAllTechByProCodeResponse" name="getAllTechByProCodeResponse"> </wsdl:output> </wsdl:operation> </wsdl:portType> <wsdl:bindi
最新发布
03-13
<think>好的,用户的问题是关于在WSDL文件中找到对应于String localPart参数的消息部分或元素。我需要根据提供的引用内容来解答这个问题。首先,用户引用了三个不同的来源,其中引用[1]提到了@PayloadRoot注解中的localPart属性,引用[2]讨论了添加参数到call对象,而引用[3]是关于组件扫描的,可能不太相关。 首先,我需要理解localPart在Web服务中的作用。根据引用[1],@PayloadRoot的localPart属性用于指定处理程序方法处理的XML元素的本地名称。这意味着在WSDL中,这个localPart应该对应某个具体的请求元素名称。例如,如果某个方法被注解为@PayloadRoot(namespace = "http://example.com", localPart = "MyRequest"),那么在WSDL中应该有一个命名空间为http://example.com的元素MyRequest。 接下来,引用[2]提到在调用Web服务时添加参数,例如arg0、arg1等,类型为String。这可能意味着在SOAP请求中,这些参数会被包装在一个元素中,而该元素的名称就是localPart指定的值。因此,在WSDL中需要查找与这些参数对应的消息部分,可能是在types部分定义的元素,或者在portTypebinding部分的操作中引用的消息。 可能的步骤是: 1. 在WSDL的types部分查找与目标命名空间对应的schema,找到与localPart名称匹配的元素。 2. 检查portType中的操作,特别是输入消息,确定引用的消息部分。 3. 在消息部分中,查看每个part对应的元素,匹配localPart的名称命名空间。 需要注意,WSDL的结构可能比较复杂,不同的部分如message、portType、binding、types需要相互关联。用户需要根据@PayloadRoot注解中的namespacelocalPart值,在WSDL的相应位置找到对应的元素。例如,如果注解中的namespace是"http://example.com/ws",localPart是"getDataRequest",那么在WSDL的types部分应该有一个该命名空间下的getDataRequest元素定义。 此外,用户可能需要检查SOAP请求的示例结构,确认参数是如何封装的。如果参数被包装在一个复合类型中,可能需要进一步解析该类型的结构,找到对应的String类型参数的位置。 总结来说,用户需要根据@PayloadRoot的namespacelocalPart属性,在WSDL的types部分找到对应的元素,并确认该元素的结构是否包含String类型的参数。同时,结合调用时添加的参数名(如arg0),可能需要查看消息定义中的part名称或元素属性,以确定对应的位置。</think>### 逐步解答 在 WSDL 文件中定位与 `String localPart` 参数对应的元素需要以下步骤: #### 1. **理解 `localPart` 的上下文** - 根据引用[1],`@PayloadRoot` 注解中的 `localPart` 表示 **XML 元素的本地名称**,例如: 若注解为 `@PayloadRoot(namespace = "http://example.com/ws", localPart = "getDataRequest")`,则对应的 XML 元素名为 `getDataRequest`,且属于命名空间 `http://example.com/ws`[^1]。 - 在调用时,`call.addParameter("arg0", XMLType.XSD_STRING, ...)` 中的 `arg0` 是参数名,需对应到 XML 元素中的具体字段名[^2]。 #### 2. **在 WSDL 中定位元素** - **查找 `types` 部分**: WSDL 的 `<types>` 部分定义了 XML Schema(XSD)。需在 `schema` 中搜索与 `namespace` 匹配的目标命名空间,并找到 `localPart` 对应的元素。 例如: ```xml <xs:schema targetNamespace="http://example.com/ws"> <xs:element name="getDataRequest"> <xs:complexType> <xs:sequence> <xs:element name="arg0" type="xs:string"/> <!-- 对应 String 参数 --> </xs:sequence> </xs:complexType> </xs:element> </xs:schema> ``` 这里 `arg0` 对应 `call.addParameter` 中的参数名,`getDataRequest` 对应 `@PayloadRoot` 的 `localPart`[^2]。 - **检查 `message` `portType` 部分**: `<message>` 定义输入输出参数的结构。例如: ```xml <message name="getDataRequestMessage"> <part name="parameters" element="tns:getDataRequest"/> <!-- 引用上述元素 --> </message> <portType name="DataServicePortType"> <operation name="getData"> <input message="tns:getDataRequestMessage"/> <!-- 输入消息 --> </operation> </portType> ``` #### 3. **验证参数类型** - 在 XML Schema 中,`String` 类型对应 `xs:string`。确保目标元素的类型声明为 `type="xs:string"` 或类似类型。 #### 4. **工具辅助(可选)** - 使用 **SoapUI** 或 **WSDL 浏览器** 导入 WSDL 文件,自动生成请求模板,直接观察参数结构。 --- ### 示例总结 假设 WSDL 中存在以下定义: ```xml <definitions targetNamespace="http://example.com/ws"> <types> <xs:schema targetNamespace="http://example.com/ws"> <xs:element name="submitFormRequest"> <xs:complexType> <xs:sequence> <xs:element name="username" type="xs:string"/> <!-- 对应 arg0 --> <xs:element name="password" type="xs:string"/> <!-- 对应 arg1 --> </xs:sequence> </xs:complexType> </xs:element> </xs:schema> </types> <message name="submitFormInput"> <part name="body" element="tns:submitFormRequest"/> </message> </definitions> ``` - 若代码中 `localPart = "submitFormRequest"`,则对应 `<xs:element name="submitFormRequest">`。 - `call.addParameter("arg0", XMLType.XSD_STRING, ...)` 对应 `<xs:element name="username">`。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱吃辣椒的年糕

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值