Jump to content

RAL register read through an adaptor

Recommended Posts

When your front door interface is pipelined and targeting multiple slaves where read transaction responses from different slaves may not be in the same order of request transactions, the read response could be all mixed up if multiple treads are issuing read transactions. The issue is that in  reg/uvm_reg_map.svh (UVM 1.2, see bellow) call to rw.parent.get_base_response(bus_rsp); used default transaction_id = -1 as opposed to the read request transaction id, which results in popping next response item from the response queue in the get_base_response task which could be wrong response as it is not matching the transaction id !!


    - tread#1 issued read to slave#1

    - then thread#2 issued read to slave#2

    ---> now both threads are waiting for response and trying to pop net element available in the response_queue.

    - slave#2 responded first and its response get put into the response_queue.

    - thread#1 could be served first and get the response from slave#2 which is meant for thread#2 !!!


The solution is at line# 2085 bellow, the call to get_base_response should be:   rw.parent.get_base_response(bus_rsp, rw.get_transaction_id());



In file reg/uvm_reg_map.svh:


1976 task uvm_reg_map::do_bus_read (


2081       if (adapter.provides_responses) begin

2082              uvm_sequence_item bus_rsp;

2083              uvm_access_e op;

2084              // TODO: need to test for right trans type, if not put back in q

2085             rw.parent.get_base_response(bus_rsp);

2086             adapter.bus2reg(bus_rsp,rw_access);

2087       end

2088       else begin

2089            adapter.bus2reg(bus_req,rw_access);

2090       end


1976 task uvm_reg_map::do_bus_read (


In file: seq/uvm_sequence_base.svh:


1157   virtual task get_base_response(output uvm_sequence_item response, input int transaction_id = -1);


1159     int queue_size, i;


1161     if (response_queue.size() == 0)

1162       wait (response_queue.size() != 0);


1164     if (transaction_id == -1) begin

1165       response = response_queue.pop_front();

1166       return;

1167     end


1169     forever begin

1170       queue_size = response_queue.size();

1171       for (i = 0; i < queue_size; i++) begin

1172         if (response_queue.get_transaction_id() == transaction_id)

1173           begin

1174             $cast(response,response_queue);

1175             response_queue.delete(i);

1176             return;

1177           end

1178       end

1179       wait (response_queue.size() != queue_size);

1180     end

1181   endtask

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

  • Create New...