zoukankan      html  css  js  c++  java
  • HDL文件操作总结

    VHDL  

    文件操作都在tb中,因为涉及到操作系统,所以无法综合。

      在vhdl中,文件被看作 行 组成的一维数组。

      预先要把两个文件读写相关的库声明。

    1 use STD.TEXTIO.all;

    2 use ieee.STD_LOGIC_TEXTIO.all; 

      首先要声明用来存储文件数据的数组,以一个80X64的32位浮点图像数据为例。

    1     type TYPE_MdlImgDat32_r is array (0 to 79) of std_logic_vector(31 downto 0);
    2     type TYPE_MdlImgDat32 is array (0 to 63) of TYPE_MdlImgDat32_r;

      首先定义了一个80大小的一维数组类型,数组成员为32位std_logic_vector

      然后再定义了一个64大小的一维数组类型,数组成员类型为一维数组。

      这样我们就得到了一个二维数组类型,当然我们也可以用下面的方法来直接定义:

        type matrix is array(0 to 63, 79 downto 0) of std_logic_vector;

      在定义完用来存数的数组结构之后,我们需要申明文件句柄。

    1     file FILE_MdlImg          : TEXT;
    2     file FILE_MdlImg_rad      : TEXT;
    3     file FILE_MdlImg_mag      : TEXT;
    4     file FILE_RefImg          : TEXT;
    5     file FILE_RefImg_Software : TEXT;
    6     file FILE_MdlImg_Software : TEXT;

      申明完文件句柄之后,记得要把前面定义的数组初始化。、

     1 variable vMdlImgDat32 : TYPE_MdlImgDat32 := (others => (others => (others => '0')));      

       因为文件内部是一行一个数据,而且是32位的HEX表示,所以还需要声明行句柄

    1         variable MdlL_OUT : LINE;
    2 
    3         variable RefL_OUT : LINE;
    4 
    5         variable RefL_OUT_Software : LINE;
    6 
    7         variable MdlL_OUT_Software : LINE;

      把文件读入二维数组中

      file_open,第一个参数是前面定义的文件句柄,后面是文件的绝对路径,最后是读或者写模式。

      readline,第一个参数还是文件句柄,第二个是前面定义的行句柄。

      hread,第一个参数是行句柄,第二个参数是二维数组里面的某个元素。

      file_close,关闭之前打开的文件。

    1         FILE_OPEN(FILE_MdlImg_Software, "C:UsersMekiXDocumentsRecorded_projectscal_magmag_cal_ready_validDatasrcimg_oactave__80x64_hex.txt", READ_MODE);
    2         ReadMdlImgFromFiles : for i in 0 to 63 loop
    3             loopX               : for j in 0 to 79 loop
    4                 READLINE(FILE_MdlImg_Software, MdlL_OUT_Software);
    5                 HREAD(MdlL_OUT_Software, vMdlImgDat32(i)(j));
    6             end loop;
    7         end loop;
    8         FILE_CLOSE(FILE_MdlImg_Software);

      总结一下就是,先把文件打开,再把文件的行读取,之后再把文件的行内元素依次写入到二维数组中。(readline应该可以放到loopx上面,还未验证)。

     

      对于写操作,基本类似。

      先也是file_open,

      HWRITE,第一个参数是行句柄,第二个数据,第三个是光标向右移动的位置,10是移动的长度。32位的HEX表示应该是8,写成10留了点余量。数据前面会有两个空格。写入方式也就是一个数据一行。

      WRITELINE,第一个参数是文件句柄,第二个是行变量。

      最后再把文件关闭。

      生成的文件在vivado工程的sim文件夹下.

     1         FILE_OPEN(FILE_MdlImg_rad, "MdlImg_rad.txt", WRITE_MODE);
     2         wait until rising_edge(aclk);
     3 
     4         while m_axis_rad_tuser = '0' loop
     5             wait until rising_edge(aclk);
     6             if (m_axis_rad_tvalid and m_axis_rad_tready) = '1'then
     7                 HWRITE(MdlL_OUT, m_axis_rad_tdata, right, 10); 9                 WRITELINE(FILE_MdlImg_rad, MdlL_OUT);
    10             else
    11                 wait until (m_axis_rad_tvalid and m_axis_rad_tready) = '1';
    12                 wait until rising_edge(aclk);
    13                 HWRITE(MdlL_OUT, m_axis_rad_tdata, right, 10);15                 WRITELINE(FILE_MdlImg_rad, MdlL_OUT);
    16             end if;
    17         end loop;
    18         FILE_CLOSE(FILE_MdlImg_rad);

     Verilog

      以下都是task类型的.

      读文件一般使用$readmemb,$readmemh,分别是读二进制和16进制的文件。

      同样需要先建立一个数组

        

      但是不需要再打开文件

       1 $readmemb("file1.txt",mem); 

      这个可以按次序填充多维数组,即先79到0.

      

    1  $readmemb("file1.txt",mem,1);//这个代表从mem[1]往后写
    2  $readmemb("file1.txt",mem,1,2);//这个代表从mem[1]写到[2]

      上面的文件可以使用绝对地址,只需要把""换成"/".

      写文件一般是

      首先定义一个整数类型的文件指针,然后用$fopen打开文件.

      $fopen实际上可以有两个参数,中间用 , 隔开,后面一个是mode

      常用mode包括

      “w",“wb"              清除文件内容并从文件头开始写,如果不存在就创建文件,只写模式。(默认模式) .

      “w+",'w+b","wb+"清除文件内容并从文件头开始读写,如果不存在就创建文件,可读写模式.

      "a","ab"     从文件末尾开始写,如果不存在就创建文件,只写模式。

      “a+","a+b","ab+"  文件末尾开始读写,如果不存在就创建文件,可读写模式.

      "r","rb"       只读模式.

      "r+","r+b","rb+"    可读写方式.

      多一个b为binary

       1 integer hex_image_80X64; 2 hex_image_80X64 = $fopen("hex_image_80X64.txt") 

      然后我们向文件写入信息,常用的task有:

      $fdisplay, $fwrite,$fstrobe,$fmonitor. 格式控制有

          %c %C character (low 8 bits)
                        %d %D decimal  %0d for minimum width field
                        %e %E E format floating point %15.7E
                        %f %F F format floating point %9.7F
                        %g %G G general format floating point
                        %h %H hexadecimal
                        %l %L library binding information
                        %m %M hierarchical name, no expression
                        %o %O octal
                        %s %S string, 8 bits per character, 2´h00 does not print
                        %t %T simulation time, expression is  $time
                        %u %U unformatted two value data  0 and 1 
                        %v %V net signal strength
                        %z %Z unformatted four value data  0, 1, x, z

      %5d, %5b.前面的数字类似vhdl,也是长度控制.,也可以直接在task后面加b/h/o,也可以直接把默认格式切换成指定的格式,例如$fdisplayb,就是二进制.

      $fdisplay和 $fwrite在每次被执行的时候都会向文件中写入指定格式的数据,区别在于$fdisplay每次执行完毕会添加新的一行,而$fwrite不会.

      $fstrobe也是写入数据但是是在同一时刻所有语句执行完毕之后再执行,举例:

    1 initial 
    2 #1 a=1; 
    3 b=0; 
    4 $fstrobe(hand1,a,b); // 默认格式将ab写入
    5 b=1;

      此时,文件名是hand1,写入的ab都是1;

      $fmonitor是在参数变化的时候往文件里写数.

      它们的具体格式非常类似c,这也是因为verilog开发的初衷就是为了比VHDL贴近C.举例如下:

      

    1 f = $fopen("output.txt","w");
    2 $fmonitor(f, "%h", acc_out);
    3 $fclose(f);

      这些task前面的f去掉之后就是在屏幕上显示而非写入文件.而具体的语法区别在于最前面的参数从文件句柄(通过$fopen得到)换成了类似c的字符串输出,举例如下

     1 $monitor("monitor a:%h @ %0t", acc_out, $time); 

      分别将accout以16进制替换%h,time替换%0t. 同时,与c语言类似,也有

    1                                                  	   tab
    2                                                  \   backslash反斜杠
    3                                                  "   quote引号
    4                                                  %%   percent

      如果这些task没有指定输出或者写入格式会怎么样?

      写入完成之后,调用$fclose关闭文件,参数是整数句柄变量而非文件名.

      读取和写入一般只执行一次,放在initial块中.

      task还有很多,下次用到再写.

  • 相关阅读:
    利用strstr和sscanf解析GPS信息
    利用STM32CubeMX之SPI
    浅析USB之设备枚举
    利用STM32CubeMX来生成USB_HID_host工程
    利用pyusb来查询当前所以usb设备
    usb之python(pyusb)
    使用STM32CubeMX生成USB_HOST_HID工程[添加对CAPS_LOCK指示灯的控制][SetReport]
    java基本数据类型
    shell kill掉含同一字符的关键字的进程
    Java之内存分析和String对象
  • 原文地址:https://www.cnblogs.com/aliothx/p/13426988.html
Copyright © 2011-2022 走看看