• Skip to main content
  • Skip to search
  • Skip to footer
Cadence Home
  • This search text may be transcribed, used, stored, or accessed by our third-party service providers per our Cookie Policy and Privacy Policy.

  1. Community Forums
  2. Functional Verification
  3. Passing struct as an argument

Stats

  • Locked Locked
  • Replies 9
  • Subscribers 65
  • Views 22610
  • Members are here 0
This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Passing struct as an argument

archive
archive over 19 years ago

Hi,
I am trying my hand on DPI, and have an example in which i want to pass a struct as an argument to 'C'. however i am not getting any results.

**********************************

The code is:

// Program to pass struct data-type as an argument.
// Author: Vivek C. Prasad
// Date  : 20 september 2006

#include
#include "svdpi.h"

  typedef struct {
    char a;
    int b;
    } AB;

  AB sc;
  int str(const AB sc) {
       printf("the byte is: %c\n",sc.a);
       printf("the int is: %d\n",sc.b);
       return(-1);
       }

**********************************

// Program to pass struct data-type as an argument.
// Author: Vivek C. Prasad
// Date  : 20 september 2006

module structPass();
 
  int res;
  typedef struct packed {
    byte a;
    shortint b;
    } AB;

  AB dt_struct;
 
  import "DPI-C" context str = function int structFunction(input dt_struct);

  initial begin
    dt_struct.a = "V";
    dt_struct.b = 10;
    res = structFunction(dt_struct);
    $display("The struct is passed as an argument.\n");
    $display("Byte: %0d\n",dt_struct.a);
    $display("Int : %0d\n",dt_struct.b);
    $display("Return : %0d\n",res);
  end
endmodule

**********************************
The Result is:

the byte is:
the int is: 0
The struct is passed as an argument.

Byte: 86

Int : 10

Return : -1

**********************************

Vivek.


Originally posted in cdnusers.org by prasad_vc
  • Cancel
Parents
  • archive
    archive over 18 years ago

    Here's a complete example of operating on a SystemVerilog packed struct from the DPI (C) side. It's important to look at the svdpi.h file in the /tools/inca/include directory to understand this.

    -----file top.v-------
    module top ();

    // import functions do a call from SV to C
    import "DPI-C" context addone_c= function int addone_sv(input int x);
    import "DPI-C" context function void show_vec_inC(input bit [31:0] some_vec);
    import "DPI-C" context function void show_logic_inC(input logic [31:0] some_vec);

    typedef struct packed {
    int a;
    bit [9:0] b;
    bit [5:0] c;
    } mydata_struct_s;
    import "DPI-C" context function void pass_struct(inout mydata_struct_s t );

    bit [31:0] some_vec = 32'h12345678;
    logic [31:0] some_logic = 32'h8765X32Z;

    mydata_struct_s mydata_struct_i;

    initial
    begin
    $display("Gimme_Int %d",addone_sv(5));
    show_vec_inC(some_vec); // pass reference per SV spec
    show_logic_inC(some_logic); // pass reference per SV spec

    // stuff the structure with data
    mydata_struct_i.a = 9;
    mydata_struct_i.b = 10'b10_1011_0110;
    mydata_struct_i.c = 6'b11_0101;

    pass_struct(mydata_struct_i); // pass reference to packed struct

    $display("Verilog a %d", mydata_struct_i.a);
    $display("Verilog b %h", mydata_struct_i.b);
    $display("Verilog c %h", mydata_struct_i.c); // in this example the DPI inverts this data

    end

    endmodule

    -----file: main_task.c-----
    #include
    #include

    // Copyright Cadence Design Systems, Todd Mackett 2007

    // This is an example of manipulating packed data structure in SystemVerilog
    // Use /tools/inca/include/svdpi.h as a reference

    int addone_c(int x) {
    return x +1;
    }

    void show_vec_inC(svBitVecVal* x) {
    printf("show_vec_inC\n");
    printf("a= %x\n", *x);
    }

    // svLogicVecVal can have 0,1,X,Z
    void show_logic_inC(svLogicVecVal* x) {
    printf("show_Logic_inC\n");
    printf("a= %x\n", *x);
    printf("aval %x\n", x->a);
    printf("bval %x\n", x->b);

    }


    void pass_struct( svBitVecVal* x) { // NOT const so that this can be modified
    // can use x[0] to reference raw array
    // printf("Struct = %x, %x\n", x[0], x[1] );
    svBitVecVal aa; // define a local svBitVecVal
    // extract field a of SV "struct packed {...} mydata_struct_s

    svGetPartselBit(&aa , x, 16, 32);
    printf("mydata_struct_s.a: %x \n", aa);

    svGetPartselBit(&aa , x, 6, 10);
    printf("mydata_struct_s.b: %x \n", aa);
    // everything above here works

    svGetPartselBit(&aa , x, 0, 6);
    printf("mydata_struct_s.c: %x \n", aa);

    // svPutBitselBit(aa, 0, sv_0);
    printf("AA %x \n", aa);
    // do some manipulation on the local svBitVecVal
    aa = ~aa; // invert the bits (some generic bit manipulation routine)

    // can do something like this too: just set the value of Verilog Structure
    // aa = 13;
    printf("AA %x \n", aa);

    svPutPartselBit(x, aa, 0, 6); // this will modify the Verilog structure

    }
    ------file: RUN_NC------(script)------------
    rm -r INCA_libs
    rm *.so
    rm *.log
    rm *.h

    # Create .h file for Exported tasks/functions only
    # (imported function do NOT need .h file):
    ncverilog +sv top.v +ncdpiheader+dpi.h +elaborate +ncelabargs+-messages

    # ncvlog -sv top.v -mess
    # ncelab top -sv -dpiheader dpi.h -mess

    gcc -fPIC -shared -o main_task.so main_task.c -I/`ncroot`/tools/inca/include

    ncverilog +sv top.v +sv_lib=main_task.so +ncsimargs+"-sv_root ./"

    -----screen results, with some comments inserted-----------

    ncsim> run
    Gimme_Int 6
    show_vec_inC
    a= 12345678
    show_Logic_inC
    a= 8765f320
    aval 8765f320
    bval f00f
    mydata_struct_s.a: 9
    mydata_struct_s.b: 2b6
    mydata_struct_s.c: 35
    AA 35
    AA ffffffca
    Verilog a 9
    Verilog b 2b6
    Verilog c 0a <--- notice the DPI inverted the bits in this case
    ncsim: *W,RNQUIE: Simulation is complete.
    ncsim> exit



    Originally posted in cdnusers.org by tmackett
    • Cancel
    • Vote Up 0 Vote Down
    • Cancel
Reply
  • archive
    archive over 18 years ago

    Here's a complete example of operating on a SystemVerilog packed struct from the DPI (C) side. It's important to look at the svdpi.h file in the /tools/inca/include directory to understand this.

    -----file top.v-------
    module top ();

    // import functions do a call from SV to C
    import "DPI-C" context addone_c= function int addone_sv(input int x);
    import "DPI-C" context function void show_vec_inC(input bit [31:0] some_vec);
    import "DPI-C" context function void show_logic_inC(input logic [31:0] some_vec);

    typedef struct packed {
    int a;
    bit [9:0] b;
    bit [5:0] c;
    } mydata_struct_s;
    import "DPI-C" context function void pass_struct(inout mydata_struct_s t );

    bit [31:0] some_vec = 32'h12345678;
    logic [31:0] some_logic = 32'h8765X32Z;

    mydata_struct_s mydata_struct_i;

    initial
    begin
    $display("Gimme_Int %d",addone_sv(5));
    show_vec_inC(some_vec); // pass reference per SV spec
    show_logic_inC(some_logic); // pass reference per SV spec

    // stuff the structure with data
    mydata_struct_i.a = 9;
    mydata_struct_i.b = 10'b10_1011_0110;
    mydata_struct_i.c = 6'b11_0101;

    pass_struct(mydata_struct_i); // pass reference to packed struct

    $display("Verilog a %d", mydata_struct_i.a);
    $display("Verilog b %h", mydata_struct_i.b);
    $display("Verilog c %h", mydata_struct_i.c); // in this example the DPI inverts this data

    end

    endmodule

    -----file: main_task.c-----
    #include
    #include

    // Copyright Cadence Design Systems, Todd Mackett 2007

    // This is an example of manipulating packed data structure in SystemVerilog
    // Use /tools/inca/include/svdpi.h as a reference

    int addone_c(int x) {
    return x +1;
    }

    void show_vec_inC(svBitVecVal* x) {
    printf("show_vec_inC\n");
    printf("a= %x\n", *x);
    }

    // svLogicVecVal can have 0,1,X,Z
    void show_logic_inC(svLogicVecVal* x) {
    printf("show_Logic_inC\n");
    printf("a= %x\n", *x);
    printf("aval %x\n", x->a);
    printf("bval %x\n", x->b);

    }


    void pass_struct( svBitVecVal* x) { // NOT const so that this can be modified
    // can use x[0] to reference raw array
    // printf("Struct = %x, %x\n", x[0], x[1] );
    svBitVecVal aa; // define a local svBitVecVal
    // extract field a of SV "struct packed {...} mydata_struct_s

    svGetPartselBit(&aa , x, 16, 32);
    printf("mydata_struct_s.a: %x \n", aa);

    svGetPartselBit(&aa , x, 6, 10);
    printf("mydata_struct_s.b: %x \n", aa);
    // everything above here works

    svGetPartselBit(&aa , x, 0, 6);
    printf("mydata_struct_s.c: %x \n", aa);

    // svPutBitselBit(aa, 0, sv_0);
    printf("AA %x \n", aa);
    // do some manipulation on the local svBitVecVal
    aa = ~aa; // invert the bits (some generic bit manipulation routine)

    // can do something like this too: just set the value of Verilog Structure
    // aa = 13;
    printf("AA %x \n", aa);

    svPutPartselBit(x, aa, 0, 6); // this will modify the Verilog structure

    }
    ------file: RUN_NC------(script)------------
    rm -r INCA_libs
    rm *.so
    rm *.log
    rm *.h

    # Create .h file for Exported tasks/functions only
    # (imported function do NOT need .h file):
    ncverilog +sv top.v +ncdpiheader+dpi.h +elaborate +ncelabargs+-messages

    # ncvlog -sv top.v -mess
    # ncelab top -sv -dpiheader dpi.h -mess

    gcc -fPIC -shared -o main_task.so main_task.c -I/`ncroot`/tools/inca/include

    ncverilog +sv top.v +sv_lib=main_task.so +ncsimargs+"-sv_root ./"

    -----screen results, with some comments inserted-----------

    ncsim> run
    Gimme_Int 6
    show_vec_inC
    a= 12345678
    show_Logic_inC
    a= 8765f320
    aval 8765f320
    bval f00f
    mydata_struct_s.a: 9
    mydata_struct_s.b: 2b6
    mydata_struct_s.c: 35
    AA 35
    AA ffffffca
    Verilog a 9
    Verilog b 2b6
    Verilog c 0a <--- notice the DPI inverted the bits in this case
    ncsim: *W,RNQUIE: Simulation is complete.
    ncsim> exit



    Originally posted in cdnusers.org by tmackett
    • Cancel
    • Vote Up 0 Vote Down
    • Cancel
Children
No Data

Community Guidelines

The Cadence Design Communities support Cadence users and technologists interacting to exchange ideas, news, technical information, and best practices to solve problems and get the most from Cadence technology. The community is open to everyone, and to provide the most value, we require participants to follow our Community Guidelines that facilitate a quality exchange of ideas and information. By accessing, contributing, using or downloading any materials from the site, you agree to be bound by the full Community Guidelines.

© 2025 Cadence Design Systems, Inc. All Rights Reserved.

  • Terms of Use
  • Privacy
  • Cookie Policy
  • US Trademarks
  • Do Not Sell or Share My Personal Information