http://blog.eccn.com/u/107250/archives/2007/474.htm C6000实时在线仿真系统设计实例 本章通过实例向读者介绍TI公司的实时在线仿真系统在C6000系列DSP中的应用。首先介绍RTDX配置和RTDX的开发步骤;然后分别介绍RTDX主机与目标机相关的函数;最后介绍了RTDX的两个案例。 1 实时在线仿真系统概述 实时在线仿真系统的英文全称为Real-Time Data Exchange,简称RTDX(TI公司已经将它注册为商标)。TI公司提出这个概念主要是为了实现计算机和DSP芯片之间的实时数据交换。读者可以将RTDX理解为一个时分复用的全双工数据通道管道,在这个过程中,计算机被称为主机,DSP芯片被称为目标机。读者可以通过RTDX在程序运行过程中,而不必终止程序来将所需要的信息在主机和目标机之问来回传送。 图7-1是RDTX的逻辑模型图。从图中可以看出,目标机和主机之间的通信实际上是通过JTAG口完成的。目标机中的RTDX目标库和位于CCS(code Composer studio)中的RTDX主机库之间实时交换数据。RTDX目标库向目标应用程序提供用户接口,目标应用程序可以通过此接口发送和接受数据。RTDX主机库提供COM接口,主机客户程序通过COM接口发送和接受数据。RTDX主机库还可以将数据保存在日志文件中,供非实时数据分析使用。 从逻辑上看,可以把此数据管道分成若干个虚拟管道,每个虚拟管道称为一个通道(Channel)。每种类型的数据通过各自的通道传送,这样能够将具有不同意义的数据从逻辑上分开。每个通道只能够单向传送数据,当然不同的通道可能具有不同的方向。可以异步地向通道写入数据,也就是说,可以在任意时刻写入数据。
同样,当主机应用程序向客户应用程序发送数据时,数据被放在RTDX主机库的缓冲区中。当RTDX主机库接收到目标应用程序要求数据的请求时,如果缓冲区中有足够的数据满足要求,数据就会发送到目标应用程序。数据被写入指定的存储器,不干扰目标应用程序的运行,同时主机会通知RTDX目标库操作已经完成。 2 RTDX配置 在进行RTDX配置之前,必须首先启动和设置好CCS,读者将CCS安装完成后,单击Setup CCS 2(C6000),进入图7-2所示的界面。
图7-4中Current Settings下显示的就是当前RTDX的设置情况。 ·使能,禁止RTDX 在窗口的左下角有一个Enable rtdx选钮。选中则使能RTDX,否则为禁止RTDX。 ·进入RTDX发置菜单 单击右小角的Configure菜单。则会进入如图7-5所示的RTDX Configuration Control对
·Non-Continuous Mode,非连续模式。在此模式下,从RTDX目录库传送过来的数据被记录存日志文件中,日志文件的扩展名为rd。 ·Continuous Mode,连续模式。在此模式下,从RTDX目标库传送过来的数据被记录 在内部的循环缓冲区中。 当需要捕获有限的数据并保存数据时,可以使用非连续模式。当需要从目标应用程序连续地获取和显示数据而小需要保存数据时,可以使用连续模式。 Data Source栏用于设置RTDX主机库通过COM接口向主机客户程序提供数据时,可以有以下两种数据来源: ·Live:Data(from target):从目标系统传送过来的实时数据; ·Playback(from log file):回放,从日志文件中得到以前记录的数据。 读者可以在“Log Filename”文本框中选择日志文件的位置。当使用Live Data,且工作在非连续模式下,此日志文件是用于记录数据的日志文件。当使用Playback时,此日志文件是用于读取以前记录的数据的文件。 在一些非实时分析的情况下,绎常先用非连续模式,记录大量目标应用程序发送的数据(此时主机客户程序可能没有运行)到日志文件,然后利用Playback方法,由主机客户程序从COM接口获取记录的数据分析显示(此时目标应用程序可能没有运行),此时就需要现在的Playback作为数据来源。 当选择Tools菜单下的RTDX子菜单下的Channel Viewer Control选项时,系统会弹出如图7-6所示的窗口。
·增加和删减通道; ·使能/禁止通道; Channel Viewer Control窗口上有两个选项:Output Channel,Input Channel分别显示输出和输入通道号。当显示OutputChannel窗口时,系统将会显示以下信息: Adress 通道十六进制地址 XFRCout。 传送信息的数目 ByteCout 等待读取的字节数目 MsgCount 等待读取的信息数目 MsgLen 当前信息长度 MsgNum 当前信息的序列号 当显示Input Channel窗口时,系统将会显示以下信息: Adress XFRCout RReqCout ABvteCount 通道十六进制地址 传送信息的数目 目标机等待读取的数目 能够被发送给目标机的字节数目 RByteCount目标机应用程序已经申请的字节数目 不干扰目标机上程序正常运行的情况下,实现主机与目标图7-7所示的菜单。单击DeleteChannel将删除该通道,单击Add Channel将出现如图7-8所示的对话框。
当选择TOOLS菜单下的RTDX子菜单下的Diagnostics Control选项时,系统会弹出如图7-9所示的窗口。
●Internal Test 这个测试仿真从目标应用程序接受数据,用来测试ccs是否工作正常,它和实际的目标程序没有关系。 ● Target-To-Host Test 这个测试使目标能够发送数据给HOST,HOST能够接受目标板的数据。 ●Host-To-Target Test 这个测试使目标能够接受HOST发送的数据,HOST能够发送数据给目标板。 3程序设计流程 RTDX可以在不干扰目标机上程序正常运行的情况下,实现主机与目标机之间的数据交 无论是目标机向主机传送数据,还是主机发送数据到目标机,都可以分为以下几步来完 ·第1步:编制目标机程序用来发送或接受数据。这一步是在CCS下完成的。这一步 必须先行,因为在这一步中需要定义用于主机访问的RTDX数据通道并向这些通道写入或读取数据,RTDX编程有无必要,关键在于看这一步有无必要。 ·第2步:编写主机程序用于接受或发送数据。这一步是在PC机各种软件下完成的。 这一步需要使用第一步中定义的RTDX数据通道,并通过这些通道读取或写入数据。以上两步的程序设计格式对于同一系列的DSP芯片来讲是固定的,对于不同系列的DSP,其格式稍有不同。 ·第3步:将目标程序写入到目标机上。特别注意,因为RTDX是通过JTAG完成数据 交换的,在编译连接和写入程序时,一定不要肩动RTDX,否则程序运行是没有结果的。 ·第4步:启动RTDX。 ·第5步:运行目标机程序。 ·第6步:运行主机程序。 ·第7步:在主机上对目标机传送来的数据进行分析。 通过以上几步,读者就可以利用RTDX在程序运行时将自己所需要的数据在主机和目标机之间来回传送。 4 RTDX函数 在7.3节中介绍了要设计RTDX程序流程,要分别编制目标机程序和主机程序,对应这两种程序T1分别提供了两种函数给用户调用。 4.1 主机函数 TI公司提供的RTDX主机接口函数可以完成通道的操作、配置、诊断、查询等功能。这些函数大致可以分为以下几类: 1.配置函数 ·long ConfigureRtdx(short Mode,long MainBufferSize,long NumOfMainBuffers); 参数: Mode 连续或非连续模式,1.连续模式,0。非连续模式 MainBufferSize 缓冲区大小,默认为1024 NumOfMainBuffers 缓冲区数目 默认为4 返回值:0-成功,非0-失败 函数描述:ConfigureRtdx函数用来设置RTDX模式和缓冲区的大小和数目。 ●long ConfigureLogFilefBSTR FileName,long FileSize,shott FileFullMode,short FileOpenMode); 参数:FileName LOG文件名 FileSize 文件人小 FileFullMode 覆盖旧文件模式:0-覆盖旧数据;1-抛弃新数据 FileOpenMode 打开文件模式:O-只读;1-在现成文件上附加:2-覆盖现成文件。 返回值:0-成功,非0-失败 函数描述:ConfigureLogFile函数用来设置RTDX log文件。 ·long EnableRtdx(); 参数: 无 返回值:0-成功,非0-失败 函数描述:使能RTDX ·long DisableRtdx(); 参数: 无 返回值:0-成功,非0-失败 函数描述:禁止RTDX ·long EnableChannel(BSTR ChannelName); 参数: ChannelName 通道号 返回值:0-成功,非0-失败 函数描述:使能该通道 ·long DisableChannel(BSTR ChannelName); 参数: ChannelName 通道号 返回值:0-成功,非0-失败 函数描述:禁止该通道 2.通道操作函数 ·long Open(BSTR Channel_String,BSTR Read_Write); 参数: Channel_String 通道标识符 Read_Write “r”.读;“W”-写 返回值:0-成功,非0-失败 函数描述:为读写操作打开相应通道 ·long Close(); 参数: 无 返回值:0-成功,非0-失败 函数描述:关闭数据通道 ·long ReadSAll(VARIANT*pArr); 参数:pArr VARIANT变最指针 返回值:0-成功,非O-失败 函数描述:从数据通道读取8位整数 ·long ReadSAl2(VARIANT*pArr); 参数:pArr VARIANT变量指针 返回值:0-成功,非0-失败 函数描述:从数据通道读取·16位整数 ·long ReadSAl4(VARIANT*pArr); 参数:pArr VARIANT变量指针 返回值:0-成功,非0-失败 函数描述:从数据通道读取32位整数 ·long ReadSAF4(VARIANT*parr); 参数:pArr VARIANT变量指针 返回值:0-成功,非0-失败 函数描述:从数据通道读取32位浮点数。 ·long ReadSAF8(VARIANT*pArr); 参数:pArr VARIANT变量指针 返回值:0-成功,非0-失败 函数描述:从数据通道读取64位浮点数。 ·VARIANT ReadSAl2V(long*pStatus); 参数:pStatus返回状态指针 返回值:SAFERRAY指针变量。 函数描述:从数据通道中读取信息放置到SAFERRAY变量中,返叫SAFERRAY指针。 ·VARIANT ReadSAl4V(long*pStatus); 参数:pStatus 返回状态指针 返回值:SAFERRAY指针变量 函数描述:从数据通道中渎取信息放置到SAFERRAY变量中,返回SAFERRAY指针。 ·long Read(VARIANT*pArr,long dataType,long numBytes); 参数:pArr VARIANT变量指针 dataType 数据类型 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:从数据通道中读取特定类型和特定数日的数据。 ·long Readll(BYTE*pData); 参数:pData VARIANT变量指针 dataType 数据类犁 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:返回读取的8位整数数据指针。 ·long Readl2(short*pData); 参数:pData VARIANT变量指针 dataType数据类型 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:返回渎取的16位整数数据指针。 ·long Readl3(10ng*pData); 参数:pDam VARIANT变量指针 dataType数据类型 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:返回读取的32位整数数据指针。 ·long ReadF4(float*pData); 参数:pDma VARIANT变量指针 dataType数据类型 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:返回读取的32位浮点数数据指针。 ·long ReadF8(double*pData); 参数:pData VARIANT变量指针 dataType数据类型 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:返回读取的64位浮点数数据指针。 ·long Write(VARIANT Art,long*numBytes); 参数: Arr 指向SAFERRAY数据的VARIANT变量指针 numBytes字节数 返回值:0-成功,非0-失败 函数描述:写信息到数据通道。 ·long Writell(unsigned char Data,long*numBytes); 参数:Data 向目标板的数据 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:写8位整数数据到目标板。 ·long Writel2(short Data,long*numBytes); 参数:Data 发送给目标板的数据 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:写16位整数数据到目标板。 ·long Writel4(long Data.long*numBytes); 参数:Data 发送给目标板的数据 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:写32位整数数据到目标板。 ·long WriteF4(float Data.long*numBytes); 参数:Data 发送给目标板的数据 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:写32位浮点数数据到目标板。 ·long WriteF8(double Data,long*numBytes); 参数:Data 发送给目标板的数据 numBytes 字节数 返回值:0-成功,非0-失败 函数描述:写64位浮点数数据到目标板。 ·long StatusWrite(long*numBytes); 参数: numBytes 字节数 返回值:0-成功,非0-失败 函数捕述:获取以前写操作的信息。 ·long Seek(long MsgNum); 参数: MsgNum 信息数 返回值:0-成功,非0-失败 函数描述:与GetMsgNumber、GetNumMsgs函数一起获取log文件中的信息。 ·long SeekData(long numBytes); 参数: numBytes 字节 返回值:0-成功,非0-失败 函数描述:将内部读指针向前或向后移动numBytes个字节数。 ·long Flush(); 参数: 无 返回值:0-成功,非0-失败 函数描述:将通道内所有的数据发送给目标板。 ·long Rewind(); 参数: 无 返同值:0-成功,非0-失败 函数描述:将读指针移到log文件的开头。 3.查询函数 ·long GetChannelID(BSTR Channel_String,long*chanId); 参数: Channel_String 通道名 chanld 通道内部ID号 返回值:0-成功,非0-失败 函数描述:得到通道的内部ID号。 ·long GetMsgID(long*pMsgId); 参数:pMsgld信息ID号 返回值:0-成功,非0-失败 函数描述:得到当前信息的内部ID号。 ·long GetMsgLength(long*pLength); 参数:pLength当前信息长度指针 返回值:0-成功,非0-失败 函数描述:得到当前信息字节长度。 ·long GetMsgNumber(long*pMsgNum); 参数:pMsgNum 当前信息序列号指针 返回值:0-成功,非0-失败 函数描述:得到当前信息序列号。 ·long GetNumMsgs(long*pNum); 参数:pNum log文件中的信息数指针 返回值:0-成功,非0-失败 函数描述:得到log文件中的信息数目。 ·long GotoNextMsg(); 参数: 无 返回值:0-成功,非0-失败 函数描述:转到log文件中下一个指针。 4.诊断函数 ·long GetChannelStatus(BSTR ChannelName,long*pChannelStatus); 参数: ChannelName通道名 DChannelStatus 通道状态 返回值:0-成功,非0-失败 函数描述:返回指定通道的状态。 ·long GetRTDXRev(long*RevNum); 参数: RevNum版本号 返回值:0-成功,非0-失败 函数描述:返回RTDX的版本号。 ·long GetStatusString(BSTr*StatusString); 参数: StamsString 状态字符串 . 返回值:0-成功,非0-失败 函数描述:返同RTDX中最后一组错误状态信息字符串。 ·long GetCapability(long*Capability); 参数: Capability 能力 返回值:0-成功,非0-失败 函数描述:返回RTDX的能力 ·long RunDiagnostics(short TestType,long TestMode,long TestInfo); 参数: TestType 测试类型:0-Intemal 1-目标板到主机;2-主机到目标板 TestMode 测试模式:0-开始;1-停止;2-得到结果 Testlnfo 测试信息:0-成功;l-失败;2-超时 返回值:0-成功,非0-失败 函数描述:执行测试操作 ·BSTR GetDiagFilePath(short TestType); 参数:TestType 测试类型:0-Internal;1-目标板到主机;2.主机到日标扳 返回值:路径和文件名 函数描述:返回指定测试的路径和文件名 7.4.2目标机函数 TMS320C6000 DSP/BIOS API里向包含的RTDX函数模块包含了以下几个函数: int RTDX_channelBusy(RTDX_inputChannel*pichan): 参数:pichan通道号 返回值:0表示该通道不忙,l表示该通道忙 函数描述:RTDX_channelBusy该函数与RTDX_readNB函数结合使用,用来表示指定通道当前是否正在被使用,如果该通道被使用,则状态寄存器0(ST0)的TC标志位被设置成 1,否则被设置成0。该函数不能被中断函数调用。 RTDX_CreateInputChannel(ichan): 参数:ichan输入通道标号 返回值:无 函数描述:RTDX_CreateInputChannel用来声明一个用于输入的通道。它不能被中断函数调用。 RTDX_CreateOutputChannel(ochan): 参数:ochan输入通道标号 返旧值:无 函数描述:RTDX_CreateOutputChannel用来声叫一个用于输出的通道。它不能被中断函数凋用。 void RTDX_disablelnput(RTDX_inputChannel*ichan): 参数:ichan输入通道标号 返旧值:无 函数描述:RTDX_disablelnput用来禁止指定的输入通道。它不能被中断函数调用。 void RTDX_disableOutput(RTDX_outputChanneI*ochan); 参数:ochan输出通道标号 返回值:无 函数描述:RTDX_disableOutput用来禁止指定的输出通道。它不能被中断函数调用。 void RTDX_enablelnput(RTDX_inputChannel*ichan): 参数:ichan输入通道标号 返回值:无 函数描述:RTDX_disablelnput用来使能指定的输入通道。它不能被中断函数调用。 void RTDX_enableOutput(RTDX_outputChannel*ochan); 参数:ochan输出通道标号 返回值:无 函数描述:RTDX_disableOutput用来使能指定的输出通道。它不能被中断函数调用。 RTDX_isInputEnabIed(ichan): 参数:ichan输入通道标号 返回值:无 函数描述:RTDX_isInputEnabled用来测试指定的输入通道是否被使能,如果被使能,则状态寄存器0的TC标志位被置为1,否则被置为0。 RTDX_isOutputEnabled(ohan); 参数:ochan输出通道标号 返回值:无 函数描述:RTDX_isOutputEnabled用来测试指定的输出通道是否被使能,如果被使能,则状态寄存器0的TC标志位被置为1,否则被置为0。 int RTDX_read(RTDX_inputChannel*ichan,void*buffer,int bsize): 参数:ichan输入通道标号 buffer 接受缓冲区指针 bsize 接受缓冲区大小 返回值:>0缓冲区接受的数据量的长度 0 失败 RTDX_READ_ERROR该通道没有被使能 函数描述:RTDX_read用来向指定的输入通道发送读数据请求,如果该通道是被使能的,则该函数在收到数据后将返回收到的数据长度,如果该通道没有被使能,则该函数将返回RTDX_READ_ERROR错误。RTDX_read不能被中断子程序调用。 int RTDX_readNB(RTDX_inputChannel*ichan,void*buffer,int bsize): 参数:ichan输入通道标号 buffer接受缓冲区指针 bsize 接受缓冲区大小 返回值:RTDX_OK 成功 0 失败,缓冲区已满 RTDX_READ_ERROR该通道没有被使能 函数描述:RTDX_readNB与RTDX_read函数一样,用来向指定的输入通道发送读数据请求,但它不会向RTDX_read一样一直等待下去,而是立即返回。它一般与TDX_channelBusy和RTDX_sizeofInput函数结合使用。RTDX_readNB不能被中断子程序调用。 int RTDX_sizeoflnput(RTDX_inputChannel*pichan); 参数:pichan输入通道标号 返回值:缓冲区内数据的数量 函数描述:RTDX_sizeoflnput用来与RTDX_readNB结合使用,它返回从数据通道传送给A的数据体的数量。该函数不能被中断子程序调用。 int RTDX_write(RTDX_outputChannel*ochan,void*bLAfter,int bsize); 参数:ochan输出通道标号 buffer 接受缓冲区指针 bsize 接受缓冲区大小 返回值:非0成功 0 失败 函数描述:RTDX_write用来将数据传送给指定的输出通道,当数据被传送给RTDX缓冲区后,该函数返回。该函数不能被中断子程序调用。 5系统设计实例 本节将通过从目标机接受整数数据和向目标机发送整数数据两个实例向读者展示如何使用RTDX,其中每个实例都必须包含主机和目标机上两个程序。其中PC机上的程序可以住C环境下编制,也可以在VB的环境下编制,甚至还可以用MATLAB实现,本节第一个案例是用C编制,第二个案例是用VB编制的。 5.1 从目标机接受整数数据实例 该程序完成的是目标机向PC机发送一个整数5,编制这个实例程序的流程如下: (1)打开C语言编辑环境。 (2)输入源代码,如下:
·加入RTDX头文件——#i nclude。 ·定义一个全局的PC主机数据输出通道,RTDX通道是一种必须在DSP目标存储器中 定义成全局数据对象的数据结构,通道的名字可以任取: RTDX_CreateOutputChannel(ochan); ·初始化DSP目标系统。使用宏TARGET_INITIALIZEO或者自己编写的代码初始化 DSP目标系统,在初始化目标系统时,需要注意的是,初始化的顺序是与DSP处理器相关的。 TARGET_INITIALIZE(); ·使能输出通道写数据。RTDX通道在初始化时默认是禁止的,在数据传输的时候必须 事先使能RTDX通道。 RTDX_enableoutput(&ochan);/*使能输出通道*/ ·传送数据到PC主机。 Status=RTDX_write(&ochan,&data,sizeof(data)); ·禁止输出通道传输数据。需要禁止CCS从DSP目标系统处理或传输数据,则需要调 用RTDX_disableOutput函数。 RTDX_disableOutput( &ochan ); (6)保存源代码文件,编译链接并生成OUT输出文件。 (7)在CCS File菜单里载入生成的OUT文件。 (9)在Debug菜单下运行Run命令,执行DSP应用程序。 (10)在PC机上运行对应的C语言程序。 (11)在PC机屏幕上将会显示数字“5”,表示PC主机已经从DSP目标系统读取了整数5。 5.2 向目标机发送整数数据实例 该程序完成的是目标机从PC机接受一个整数5,编制这个实例程序的流程如下:
·定义一个全局的PC主机数据输入通道,RTDX通道是一种必须在DSP目标存储器中定义成全局数据对象的数据结构,通道的名字可以任取: RTDX_CreateInputChannel( ichan ); ·初始化DSP目标系统。使用宏TARGET_INITIALIZEO或者自己编写的代码初始化 DSP目标系统,在初始化目标系统时,需要注意的是,初始化的顺序是与DSP处理器相关的。 TARGET_INITIALIZE(); ·使能输出通道写数据。RTDX通道在初始化时默认是禁止的,在数据传输的时候必须 事先使能RTDX通道。 RTDX_enableInput(&ichan)j ·从PC主机接受数据。 status=RTDX_read(&ichan,&data,siZeof(data)); ·禁止输出通道传输数据。需要禁止CCS从DSP日标系统处理或传输数据,则需要调 用RTDX_disableInput函数。 (6)保存源代码文件,编译链接并生成OUT输出文件。 (7)在CCS File菜单里载入生成的OUT文件。 (8)选择CCS菜单命令Tools→RTDX→Configuration Control,相对应的图7-4的EnableRTDX栏前面画上‘个“√”。 (9)在Debug菜单.下运行Run命令,执行DSP应用程序。 (10)在PC机上运行对应的Visual Basic程序。 (11)在CCS的标准窗口上就会显示 5 was received from the host,表示DSP目标系统已经从PC机读取了整数5。 6本章小结 RTDX虽然只是方便调试的一种工具,但它在现在DSP特别是C6000系列的开发中占据着很重要的位置。了解和熟悉RTDX对于读者熟练掌握DSP的开发有重要的作用。本章则向读者详细介绍了RTDX的使用,并提供了RTDX的2个实例供读者实践学习。 |
文章评论(0条评论)
登录后参与讨论