环境
工具:TwinCAT3软件、倍福CX2033控制器、AX5800开发板采用STM32F407芯片!
采用MCU来作为从站,控制器作为主站!
EtherCAT的移植暂时不写,直接将添加PDO步骤!在板子原有代码下进行修改!
首先查看一下原有的设备以及PDO信息:TwinCAT3软件添加XML文件,连接控制器,扫描IO,写入EEprom后可以看到以下信息!

我在原有基础上又添加了PDO_WJ,包含三个通道分别是CH1、CH 2、CH 3;

具体修改如下:
一、XML修改
首先,我添加的三个通道分别是USINT类型的占8bit大小!直接根据原有的文档进行修改!
原来的SM2大小为6;

给改后为10字节;10=6+8bit(CH1)+8bit(CH 2)+8bit(CH 3)+8bit(对齐2字节补充的8位);

继续修改,添加7012object对象,可以仿照7010以及1601去修改和添加我们的变量!!!




这里的<BitSize>为144,计算过程就是索引8位+对齐补充8位+32位地址*4=144;分析一下SubIndex 001的<DefaultData>08011270含义,其中1270表示0x7012对象、01表示子索引01、08表示0x08=8bit数据类型;SubIndex 004的<DefaultData>08000000,就是凑够两字节对齐补充的8位数据。
二、MCU程序修改
找到el9800appl.h文件进行修改!
仿照TOBJ1601结构体编写TOBJ1602,注意内部的aEntries[]的成员个数问题,我这里有CH1、CH2、CH3和对其补充的空8位,所以一共四个成员!

依次往下修改,原先的aEntries成员为1,因为新添加了1602,所以改成aEntries[2];

我们仿照原先定义的TOBJ7010、TOBJ7011结构体,再去定义TOBJ7012结构体


仿照1601对象,去添加1602object对象

在1601下面添加
#ifdef _OBJD_
/**
* \addtogroup PdoMappingObjects PDO Mapping Objects
* @{
*/
/**
* \brief Object 0x1602(Digital output RxPDO) entry descriptions
*
* SubIndex 0 : read only<br>
* SubIndex x : read only<br>
* (x > 0)
*/
OBJCONST TSDOINFOENTRYDESC OBJMEM asEntryDesc0x1602[] = {
{DEFTYPE_UNSIGNED8, 0x3, ACCESS_READ },
{DEFTYPE_UNSIGNED32, 0x20, ACCESS_READ},
{DEFTYPE_UNSIGNED32, 0x20, ACCESS_READ},
{DEFTYPE_UNSIGNED32, 0x20, ACCESS_READ}
};
/**
* \brief Object 0x1601 (Digital output RxPDO) name
*
* In this example no specific entry name is defined ("SubIndex xxx" is used)
*/
OBJCONST UCHAR OBJMEM aName0x1602[] = "AO RxPDO-Map\000\377";
#endif //#ifdef _OBJD_
/**
* \brief Object 0x1602 (Digital output RxPDO) variable to handle object data
*
*/
PROTO TOBJ1602 sAORxPDOMap
#ifdef _EVALBOARD_
= {4, {0x70120108, 0x70120208, 0x70120308, 0x08}}
#endif
;
/** @}*/
把1C12里面的值仿照1C13改为= {0x02, {0x1601,0x1602}}

仿照7010去写7012映射
/***************++++++++++添加修改部分1+++++++++++**************/
/**
* \brief Object 0x7012 (Digital output object) entry descriptions
*
* SubIndex 0 : read only<br>
* SubIndex x : (One description for each led) read only and RxPdo mappable<br>
* (x > 0)
*/
#ifdef _OBJD_
OBJCONST TSDOINFOENTRYDESC OBJMEM asEntryDesc0x7012[] = {
{DEFTYPE_UNSIGNED8, 0x8, ACCESS_READ }, /* Subindex 000 */
{DEFTYPE_UNSIGNED8, 0x01, ACCESS_READ | OBJACCESS_RXPDOMAPPING}, /* SubIndex 001: CH 1 */
{DEFTYPE_UNSIGNED8, 0x01, ACCESS_READ | OBJACCESS_RXPDOMAPPING}, /* SubIndex 002: CH 2 */
{DEFTYPE_UNSIGNED8, 0x01, ACCESS_READ | OBJACCESS_RXPDOMAPPING}, /* SubIndex 003: CH 3 */
{0x0000, 0x08, 0}
}; /* Subindex 008 for align */
/**
* \brief 0x6000 (Digital input object) object and entry names
*/
OBJCONST UCHAR OBJMEM aName0x7012[] = "PDO_WJ\000CH 1\000CH 2\000CH 3\000\000\377";
#endif //#ifdef _OBJD_
/**
* \brief 0x6020 (Analog input object) variable to handle object data
*
*/
PROTO TOBJ7012 PDO_WJ
#ifdef _EVALBOARD_
= {3, 0x00, 0x00, 0x00, 0}
#endif
;
/** @}*/
/*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/
最后找到OBJMEM ApplicationObjDic[]数组进行添加1602和7012成员内容。

el9800appl.c文件修改
找到el9800appl.c文件下找到void APPL_OutputMapping(UINT16* pData)函数,这是我们接收主机发送数据的函数。

进行修改后:
void APPL_OutputMapping(UINT16* pData)
{
UINT16 j = 0;
UINT16 *pTmpData = (UINT16 *)pData;
/* we go through all entries of the RxPDO Assign object to get the assigned RxPDOs */
for (j = 0; j < sRxPDOassign.u16SubIndex0; j++)
{
switch (sRxPDOassign.aEntries[j])
{
/* RxPDO 2 */
case 0x1601:
((UINT16 *) &sDOOutputs)[1] = SWAPWORD(*pTmpData++);//LED数据
((UINT16 *) &Var0x7011)[0] = SWAPWORD(*pTmpData++);//Var0x7011低16位数据
((UINT16 *) &Var0x7011)[1] = SWAPWORD(*pTmpData++);//Var0x7011高16位数据
// test1 = SWAPWORD(*pTmpData++);
break;
case 0x1602:
((UINT16 *) &PDO_WJ)[1] = SWAPWORD(*pTmpData++);//CH1低八位、CH2高八位
((UINT16 *) &PDO_WJ)[2] = SWAPWORD(*pTmpData++);//CH3
// test2= SWAPWORD(*pTmpData++);
break;
}
}
}
下图的函数void APPL_Application(void),我们用来处理接收的数据!!

/////////////////////////////////////////////////////////////////////////////////////////
/**
\brief This function will called from the synchronisation ISR
or from the mainloop if no synchronisation is supported
*////////////////////////////////////////////////////////////////////////////////////////
uint8_t Ch_buff[3]={0};
void APPL_Application(void)
{
Ch_buff[0]= PDO_WJ.CH_1;
Ch_buff[1]= PDO_WJ.CH_2;
Ch_buff[2]= PDO_WJ.CH_3;//这里我新添加的数组去接收Ch通道的值
GPIO_WriteBit(GPIOB, GPIO_Pin_1, (BitAction)sDOOutputs.bLED1);
GPIO_WriteBit(GPIOB, GPIO_Pin_0, (BitAction)sDOOutputs.bLED2);
GPIO_WriteBit(GPIOC, GPIO_Pin_5, (BitAction)sDOOutputs.bLED3);
GPIO_WriteBit(GPIOC, GPIO_Pin_4, (BitAction)sDOOutputs.bLED4);
GPIO_WriteBit(GPIOA, GPIO_Pin_7, (BitAction)sDOOutputs.bLED5);
GPIO_WriteBit(GPIOA, GPIO_Pin_6, (BitAction)sDOOutputs.bLED6);
GPIO_WriteBit(GPIOA, GPIO_Pin_5, (BitAction)sDOOutputs.bLED7);
GPIO_WriteBit(GPIOA, GPIO_Pin_4, (BitAction)sDOOutputs.bLED8);
sDIInputs.bSwitch1 = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_3);
sDIInputs.bSwitch2 = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_2);
sDIInputs.bSwitch3 = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_1);
sDIInputs.bSwitch4 = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0);
sDIInputs.bSwitch5 = GPIO_ReadInputDataBit(GPIOE, GPIO_Pin_5);
sDIInputs.bSwitch6 = GPIO_ReadInputDataBit(GPIOE, GPIO_Pin_4);
sDIInputs.bSwitch7 = GPIO_ReadInputDataBit(GPIOE, GPIO_Pin_3);
sDIInputs.bSwitch8 = GPIO_ReadInputDataBit(GPIOE, GPIO_Pin_2);
}
三、调试
打开TwinCAT3软件连接控制器和从站设备!进行写数据,观察现象!



5252

被折叠的 条评论
为什么被折叠?



