This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
您好!
我们 制造了 通过 MODBUS 进行通信的设备(完全相同),这些设备可通过 MCU 的输入引脚进行配置。 主器件将从以太网获取命令、并且正在工作。 主器件将向从器件发送相同的命令、而从器件应相应地工作。 但是当主控方通过 Modbus 向从属方发送第一条命令时,从属方接收到的命令非常完美,但即使主控方没有给出第二条命令,从属方也会再次输出 UARTCharget()函数,这会导致接收到垃圾字节,并且不会起到阻塞作用,为什么会发生这种情况?
我已附加代码、请查看计时器 ISR 中的从器件部分。 Modbus_REC_BUF= UARTCharGet (UART6_BASE);函数执行两次并导致读取两个字节、即使主器件仅发送一个字节也是如此。
TI RTOS:- 2.16.0.14
编译器:- GNU -7.2.1 (Linaro)
此致
Khodidas Domadiya
/* * Author : - KHODIDAS DOMADIYA\ * Organization: - Optimzed Solutions Ltd. * Department: -Product ENgineering services. * * Date:- 12-05-2021 *=> IP ADDRESS USED IS STATIC * * * * Indication OF leds - For ethernet , default LEDs used * * */ /* * ======== tcpEcho.c ======== */ /* XDCtools Header files */ #include <stdint.h> #include <stdio.h> #include <stdbool.h> #include <string.h> #include <stdlib.h> #include <math.h> #include <xdc/std.h> #include <xdc/cfg/global.h> #include <ti/sysbios/hal/Hwi.h> #include <xdc/runtime/Error.h> #include <xdc/runtime/Memory.h> #include <xdc/runtime/System.h> /* BIOS Header files */ #include <ti/sysbios/BIOS.h> #include <ti/sysbios/knl/Clock.h> #include <ti/sysbios/knl/Task.h> /* NDK Header files */ #include <ti/ndk/inc/netmain.h> #include <ti/ndk/inc/_stack.h> /* TI-RTOS Header files */ #include <ti/drivers/GPIO.h> /* Example/Board Header files */ #include "Board.h" //#include <time.h> #include "inc/hw_memmap.h" #include "inc/hw_types.h" #include "inc/hw_sysctl.h" #include "driverlib/sysctl.h" #include "driverlib/pin_map.h" #include "inc/hw_gpio.h" #include "driverlib/gpio.h" #include "inc/hw_ints.h" #include "driverlib/interrupt.h" #include "inc/hw_timer.h" #include "driverlib/timer.h" #include <xdc/cfg/global.h> #include <ti/sysbios/hal/Timer.h> #include "inc/hw_flash.h" #include "driverlib/flash.h" #include "driverlib/uart.h" #include "inc/hw_uart.h" #include "utils/uartstdio.h" Timer_Params Timer2; Timer_Handle myTimer; SOCKET lSocket; struct sockaddr_in sLocalAddr; #define TCPPACKETSIZE 256 #define NUMTCPWORKERS 3 /**************************************************************** Global variable ****************************************************************/ bool MASTER; #define MODBUS_TRANSMIT (GPIOPinWrite(GPIO_PORTP_BASE, GPIO_PIN_2, GPIO_PIN_2)) #define MODBUS_RECIEVE (GPIOPinWrite(GPIO_PORTP_BASE, GPIO_PIN_2, 0x00)) #define SYNC_START (GPIOPinWrite(GPIO_PORTB_BASE, GPIO_PIN_0, GPIO_PIN_0)) #define SYNC_STOP (GPIOPinWrite(GPIO_PORTB_BASE, GPIO_PIN_0, 0x00)) #define SYNC_READ (GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_0)) #define SLAVE (!MASTER) #define MODBUS_COM_LED_ON (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_2, 0)) #define START_STP_LED_ON (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_1, 0)) #define MASTER_SLAVE_LED_ON (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_0, 0)) #define ETH_LED_ON (GPIOPinWrite(GPIO_PORTH_BASE, GPIO_PIN_3, GPIO_PIN_3)) #define MODBUS_COM_LED_OFF (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_2, GPIO_PIN_2)) #define START_STP_LED_OFF (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_1, GPIO_PIN_1)) #define MASTER_SLAVE_LED_OFF (GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_0, GPIO_PIN_0)) #define ETH_LED_OFF (GPIOPinWrite(GPIO_PORTH_BASE, GPIO_PIN_3, 0)) #define SNAP1_ON GPIOPinWrite(GPIO_PORTL_BASE,GPIO_PIN_4,GPIO_PIN_4) #define SNAP2_ON GPIOPinWrite(GPIO_PORTL_BASE,GPIO_PIN_5,GPIO_PIN_5) #define SNAP1_OFF GPIOPinWrite(GPIO_PORTL_BASE,GPIO_PIN_4,0) #define SNAP2_OFF GPIOPinWrite(GPIO_PORTL_BASE,GPIO_PIN_5,0) //**************************************************************************** // System clock rate in Hz. //**************************************************************************** uint32_t g_ui32SysClock; #define MODBUS_DATA_SIZE 28 //***************************************************************************** // Global flag to indicate data was received //***************************************************************************** volatile uint32_t g_bReceiveFlag = 0; //***************************************************************************** // Flags that contain the current value of the interrupt indicator as displayed // on the UART. //***************************************************************************** uint32_t g_ui32Flags; //uint8_t Eth_Buffer[50]="ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmn"; uint8_t Eth_Buffer[50]; uint8_t Modbus_Buffer[28]; // UART INT variable uint32_t c; uint32_t C; // for looping purpose of GPIO uint8_t i = 0; uint8_t j = 0; // Different buffer for signals bool pin_data[208]; uint8_t SET_1[8]; uint8_t SET_2[8]; uint8_t SET_3[8]; /*uint8_t portD_data; uint8_t portE_data; uint8_t portN_data; uint8_t portP_data; uint8_t portB_data; uint8_t portL_data; uint8_t portM_data;*/ // Start and Stop command from host char rcvd_data[1]; char MODBUS_REC_BUF; // Slave command receive buffer uint8_t slave_cmd[2]; // data store in slave buffer uint8_t SLAVE_1_BUFFER[28],SLAVE_2_BUFFER[28],SLAVE_3_BUFFER[28],SLAVE_4_BUFFER[28],SLAVE_5_BUFFER[28]; // timer initial define 0 bool TIMER_ON=0,START_FLAG; // Master and Slave address uint8_t SLAVE_ADDRESS; //counting verible uint16_t timerCount; //**************************************************************** TIMER INIT FUNCTIONS****************************************************************/ void timer_init(void); void timerIntHandler(void); //**************************************************************** APPLICATION FUNCTIONS****************************************************************/ void decoderAddrLineSelect(uint8_t temp); void readSignal(); void Snap_Config(void); void modbusUART6init(void); void DebugUART0(void); void UARTSend( const uint8_t *pui8Buffer, uint32_t ui32Count); void UARTRecieve(uint8_t *BUFF, uint32_t ui32Count); void Timer_init(); void Debug_Send( const uint8_t *pui8Buffer, uint32_t ui32Count); /**************************************************************** LOGIC *****************************************************************/ //*********************************inialaization 24 GPIO for different input signals*******************************// void signalconfigure(void) { HWREG(GPIO_PORTD_BASE+GPIO_O_LOCK) = GPIO_LOCK_KEY; // HWREG(GPIO_PORTD_BASE+GPIO_O_CR) |= GPIO_PIN_7; // Unlock port D pin 7 GPIODirModeSet(GPIO_PORTD_BASE,GPIO_PIN_7,GPIO_DIR_MODE_IN);// GPIOPinTypeGPIOInput(GPIO_PORTD_BASE, GPIO_PIN_7|GPIO_PIN_6|GPIO_PIN_4); HWREG(GPIO_PORTE_AHB_BASE+GPIO_O_LOCK) = GPIO_LOCK_KEY; // HWREG(GPIO_PORTE_AHB_BASE+GPIO_O_CR) |= GPIO_PIN_4; // Unlock port E pin 4 GPIOPinTypeGPIOInput(GPIO_PORTE_BASE, GPIO_PIN_4); // GPIODirModeSet(GPIO_PORTE_BASE,GPIO_PIN_4,GPIO_DIR_MODE_IN); // GPIOPinTypeGPIOInput(GPIO_PORTN_BASE, GPIO_PIN_0|GPIO_PIN_1); GPIOPinTypeGPIOInput(GPIO_PORTP_BASE, GPIO_PIN_5|GPIO_PIN_4|GPIO_PIN_3); GPIOPinTypeGPIOInput(GPIO_PORTB_BASE, GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4); GPIOPinTypeGPIOInput(GPIO_PORTL_BASE, GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_3|GPIO_PIN_1|GPIO_PIN_0); GPIOPinTypeGPIOInput(GPIO_PORTM_BASE, GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4|GPIO_PIN_6|GPIO_PIN_7); } //*********************************Signal read of 24 GPIO*******************************// /*void readSignal() { portD_data = GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_7 |GPIO_PIN_6|GPIO_PIN_4) & 0xD0; portE_data = GPIOPinRead(GPIO_PORTE_BASE, GPIO_PIN_4) & 0x10; portB_data = GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_4|GPIO_PIN_3|GPIO_PIN_2) & 0x1C; portN_data = GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_0|GPIO_PIN_1) & 0x03; portP_data = GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_5|GPIO_PIN_4|GPIO_PIN_3) & 0x38; portL_data = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_7|GPIO_PIN_6|GPIO_PIN_3|GPIO_PIN_1|GPIO_PIN_0) & 0xC7; portM_data = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4|GPIO_PIN_6|GPIO_PIN_7) & 0xDF; }*/ void readSignal() { /* pin_data[j] = GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_7); pin_data[j+1] = GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_6); pin_data[j+2] = GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_4); pin_data[j+3] = GPIOPinRead(GPIO_PORTE_BASE, GPIO_PIN_4); pin_data[j+4] = GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_4); pin_data[j+5] = GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_0); pin_data[j+6] = GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_1); pin_data[j+7] = GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_5); pin_data[j+8] = GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_4); pin_data[j+9] = GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_3); pin_data[j+10] = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_6); pin_data[j+11] = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_7); pin_data[j+12] = GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_3); pin_data[j+13] = GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_2); pin_data[j+14] = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_3); pin_data[j+15] = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_1); pin_data[j+16] = GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_0); pin_data[j+17] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_0); pin_data[j+18] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_1); pin_data[j+19] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_2); pin_data[j+20] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_3); pin_data[j+21] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_4); pin_data[j+22] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_6); pin_data[j+23] = GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_7); j+=24; if( j == 192) { j = 0; }*/ SET_1[j]= (GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_7) << 0) + (GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_6) << 1) \ + (GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_4) << 2) + (GPIOPinRead(GPIO_PORTE_BASE, GPIO_PIN_4) << 3) \ + (GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_4) << 4) + (GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_0) << 5) \ + (GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_1) << 6) + (GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_5) << 7); SET_1[j]= (GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_4) << 0) + (GPIOPinRead(GPIO_PORTP_BASE, GPIO_PIN_3) << 1) \ + (GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_6) << 2) + (GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_7) << 3) \ + (GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_3) << 4) + (GPIOPinRead(GPIO_PORTB_BASE, GPIO_PIN_2) << 5) \ + (GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_3) << 6) + (GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_1) << 7); SET_1[j]= (GPIOPinRead(GPIO_PORTL_BASE, GPIO_PIN_0) << 0) + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_0) << 1) \ + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_0) << 2) + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_1) << 3) \ + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_2) << 4) + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_4) << 5) \ + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_6) << 6) + (GPIOPinRead(GPIO_PORTM_BASE, GPIO_PIN_7) << 7); } //*********************************SNAP RELAY PIN CONFIGURATION*******************************// void Snap_Config(void) { GPIOPinTypeGPIOInput(GPIO_PORTL_BASE, GPIO_PIN_4|GPIO_PIN_5); GPIOPinWrite(GPIO_PORTL_BASE,GPIO_PIN_4|GPIO_PIN_5, 0|0); } //********************************* EXTERNAL MUX ADDRESS SELECTOR RESET*******************************// void resetExternalMuxSelect(void) { GPIOPinTypeGPIOOutput(GPIO_PORTB_BASE, GPIO_PIN_5); // Pin low GPIOPinWrite(GPIO_PORTB_BASE, GPIO_PIN_5, 0); // GPIOPinTypeGPIOOutput(GPIO_PORTE_BASE, GPIO_PIN_5); // Pin high GPIOPinWrite(GPIO_PORTE_BASE, GPIO_PIN_5, GPIO_PIN_5); // } //********************************* MASTER SLAVE ADDRESS SELECT PIN CONFIGURATION*******************************// void Master_Slave_Pin_Config(void) { // Enable the GPIO Peripheral SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD); SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOQ); // select GPIO for MODBUS address GPIOPinTypeGPIOInput(GPIO_PORTD_BASE, GPIO_PIN_0); GPIOPinTypeGPIOInput(GPIO_PORTD_BASE, GPIO_PIN_1); GPIOPinTypeGPIOInput(GPIO_PORTD_BASE, GPIO_PIN_2); GPIOPinTypeGPIOInput(GPIO_PORTD_BASE, GPIO_PIN_3); GPIOPinTypeGPIOInput(GPIO_PORTQ_BASE, GPIO_PIN_0); } //********************************* MUX ADDRESS GENERATOR PIN (S0, S1, S2) CONFIGURATION*******************************// void MuxAddress_Pin_Configuration() { GPIOPinTypeGPIOOutput(GPIO_PORTK_BASE, GPIO_PIN_0); // s1 GPIOPinTypeGPIOOutput(GPIO_PORTK_BASE, GPIO_PIN_1); // s0 GPIOPinTypeGPIOOutput(GPIO_PORTK_BASE, GPIO_PIN_2); //s2 } //********************************* MUX ADDRESS GENERATOR FUNCTION (S0, S1, S2) *******************************// void decoderAddrLineSelect(uint8_t temp) { GPIOPinWrite(GPIO_PORTK_BASE, GPIO_PIN_0, temp); GPIOPinWrite(GPIO_PORTK_BASE, GPIO_PIN_1, temp); GPIOPinWrite(GPIO_PORTK_BASE, GPIO_PIN_2, temp); } //***************************************************************************** // Master and slave address selection //***************************************************************************** bool Master_Slave_Select() { bool t1,t2,t3; t1=GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_0); t2=GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_1); t3=GPIOPinRead(GPIO_PORTD_BASE, GPIO_PIN_2); SLAVE_ADDRESS = (t1<<0) + (t2<<1) +(t3<<2); if(SLAVE_ADDRESS==0x00) { MASTER_SLAVE_LED_ON; Debug_Send((uint8_t *)"Device is Master",20); return 1; } else { MASTER_SLAVE_LED_OFF; char debug_buf[]="Device is slave:-"; sprintf(debug_buf,"Device is slave:-%d",SLAVE_ADDRESS); Debug_Send((uint8_t *)debug_buf,20); return 0; } } //***************************************************************************** // MODBUS UART6 interrupt handler. //***************************************************************************** void modbusUART6IntHandler(void) { uint32_t ui32Status; // Get the interrupt status. ui32Status = UARTIntStatus(UART6_BASE, true); // Clear the asserted interrupts. UARTIntClear(UART6_BASE, ui32Status); if( ( (UART_INT_RX & ui32Status) == UART_INT_RX ) || ( (UART_INT_RT & ui32Status) == UART_INT_RT) ) { // Receive UART char while(UARTCharsAvail(UART6_BASE)) { // Read the next character from the UART and write it back to the UART. UARTCharGetNonBlocking(UART6_BASE); C = UARTCharGet(UART6_BASE); } } } //***************************************************************************** // MODBUS UART6 configure //***************************************************************************** void modbusUART6init(void) { // Enable UART6. SysCtlPeripheralEnable(SYSCTL_PERIPH_UART6); SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOP); // Enable processor interrupts. IntMasterEnable(); // Configure GPIO Pins for UART mode. GPIOPinConfigure(GPIO_PP0_U6RX); GPIOPinConfigure(GPIO_PP1_U6TX); GPIOPinTypeUART(GPIO_PORTP_BASE, GPIO_PIN_0 | GPIO_PIN_1); // Initialize the UART for console I/O. UARTConfigSetExpClk(UART6_BASE, g_ui32SysClock, 1000000,(UART_CONFIG_WLEN_8 | UART_CONFIG_STOP_ONE |UART_CONFIG_PAR_NONE)); //IntEnable(INT_UART6); //UARTIntEnable(UART6_BASE, UART_INT_RX | UART_INT_TX |UART_INT_RT); UARTEnable(UART6_BASE); GPIOPinTypeGPIOOutput(GPIO_PORTP_BASE, GPIO_PIN_2); //MODBUS_TX_RX_CNTRL } void DebugUART0(void) { // Enable the GPIO Peripheral used by the UART. SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOA); // Enable UART0. SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0); // Enable processor interrupts. IntMasterEnable(); // Configure GPIO Pins for UART mode. GPIOPinConfigure(GPIO_PA0_U0RX); GPIOPinConfigure(GPIO_PA1_U0TX); GPIOPinTypeUART(GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1); UARTConfigSetExpClk(UART0_BASE, g_ui32SysClock, 115200,(UART_CONFIG_WLEN_8 | UART_CONFIG_STOP_ONE |UART_CONFIG_PAR_NONE)); // Enable the UART interrupt. UARTEnable(UART0_BASE); } //***************************************************************************** // Send a string to the UART. //***************************************************************************** void UARTSend( const uint8_t *pui8Buffer, uint32_t ui32Count) { // Loop while there are more characters to send. while(ui32Count--) { // Write the next character to the UART. UARTCharPut(UART6_BASE, *pui8Buffer++); } } //***************************************************************************** // Receive a string to the UART. //***************************************************************************** void UARTRecieve(uint8_t *BUFF, uint32_t ui32Count) { while(UARTCharsAvail(UART6_BASE)) { while(ui32Count--) { // Read the next character from the UART UARTCharGetNonBlocking(UART6_BASE); *BUFF++ = UARTCharGet(UART6_BASE); } } } void Debug_Send( const uint8_t *pui8Buffer, uint32_t ui32Count) { // Loop while there are more characters to send. while(ui32Count--) { // Write the next character to the UART. UARTCharPut(UART0_BASE, *pui8Buffer++); } } // Timer configuration as RTOS base void Timer_init() { timer_init(); Timer_Params_init(&Timer2); Timer2.arg=0; // Timer2.period= 10; // 20us //Timer2.period= 1000; //1 ms (Milliseconds) Timer2.period= 800; //800 us (Microseconds) Timer2.periodType=Timer_PeriodType_MICROSECS; myTimer=Timer_create(2,(Timer_FuncPtr)timerIntHandler,&Timer2,NULL); //Timer_start(myTimer); Timer_stop(myTimer); } // Timer start void Timer_Start(void) { Timer_start(myTimer); } // Timer stop void Timer_Stop(void) { Timer_stop(myTimer); } void Sync_Config() { if(MASTER) { GPIOPinTypeGPIOOutput(GPIO_PORTB_BASE, GPIO_PIN_0); // SYNCH PIN SYNC_STOP; } else { GPIOPinTypeGPIOInput(GPIO_PORTB_BASE, GPIO_PIN_0); // SYNCH PIN } } void Indication_Led_config() { GPIOPinTypeGPIOOutput(GPIO_PORTE_BASE, GPIO_PIN_2); // MODBUS COM GPIOPinTypeGPIOOutput(GPIO_PORTE_BASE, GPIO_PIN_1); //START/ STOP LED GPIOPinTypeGPIOOutput(GPIO_PORTE_BASE, GPIO_PIN_0); //MASTER/SLAVE LED GPIOPinTypeGPIOOutput(GPIO_PORTH_BASE, GPIO_PIN_3); //ETH_LED MODBUS_COM_LED_OFF; START_STP_LED_OFF; MASTER_SLAVE_LED_OFF; ETH_LED_OFF; } /* * ======== tcpHandler ======== * Creates new Task to handle new TCP connections. */ Void tcpHandler(UArg arg0, UArg arg1) { fdOpenSession(TaskSelf()); lSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); if (lSocket < 0) { // System_printf("tcpHandler: socket failed\n"); Task_exit(); return; } memset((char *)&sLocalAddr, 0, sizeof(sLocalAddr)); sLocalAddr.sin_family = AF_INET; sLocalAddr.sin_addr.s_addr = inet_addr("192.168.1.130");//htonl(INADDR_ANY); sLocalAddr.sin_port = htons(arg0); while(connect(lSocket, (struct sockaddr *)&sLocalAddr, sizeof(sLocalAddr)) < 0) { ETH_LED_OFF; SysCtlDelay(400000); } ETH_LED_ON; Timer_init(); while (1) { recv(lSocket,(char *)rcvd_data,sizeof(rcvd_data), MSG_DONTWAIT); while(MASTER) { recv(lSocket,(char *)rcvd_data,sizeof(rcvd_data), MSG_DONTWAIT); if(strcmp(rcvd_data, "L" )==0) //SNAP { SNAP1_ON; SNAP2_ON; UARTSend((uint8_t *)"L",1); } if(strcmp(rcvd_data, "U" )==0) //UNSNAP { SNAP1_OFF; SNAP2_OFF; UARTSend((uint8_t *)"U",1); } if(strcmp(rcvd_data, "S" )==0) //START { START_STP_LED_ON; TIMER_ON=1; SYNC_START; UARTSend((uint8_t *)"S",1); Timer_Start(); } //send(lSocket, flashbuffer,sizeof(flashbuffer), 0 ); while(TIMER_ON) { recv(lSocket,(char *)rcvd_data,sizeof(rcvd_data), MSG_DONTWAIT); send(lSocket, Eth_Buffer,sizeof(Eth_Buffer), 0 ); if(strcmp(rcvd_data, "E" )==0) //STOP { START_STP_LED_OFF; TIMER_ON=0; SYNC_STOP; UARTSend((uint8_t *)"E",1); Timer_Stop(); timerCount=0; } } } } } /* * ======== main ======== */ int main(void) { // Task_Handle taskHandle; // Task_Params taskParams; // Error_Block eb; g_ui32SysClock = SysCtlClockFreqSet((SYSCTL_XTAL_25MHZ |SYSCTL_OSC_MAIN |SYSCTL_USE_PLL |SYSCTL_CFG_VCO_320), 120000000); /* Call board init functions */ Board_initGeneral(); Board_initGPIO(); Board_initEMAC(); Indication_Led_config(); signalconfigure(); resetExternalMuxSelect(); DebugUART0(); modbusUART6init(); Master_Slave_Pin_Config(); MuxAddress_Pin_Configuration(); MASTER = Master_Slave_Select(); Sync_Config(); //Timer_Start(); while(SLAVE) { //uint8_t SYNC_CHAR=0; //SYNC_CHAR=UARTCharGet(UART6_BASE); MODBUS_RECIEVE; if(START_FLAG==0) { if(UARTCharGetNonBlocking(UART6_BASE)==0x53); { Timer_init(); START_STP_LED_ON; Timer_Start(); START_FLAG=1; } } // MODBUS_RECIEVE; // if((SYNC_READ==0 || UARTCharGetNonBlocking(UART6_BASE) == 0x45) && START_FLAG==1) // { // START_STP_LED_OFF; // Timer_Stop(); // START_FLAG=0; // } } /* Start BIOS */ BIOS_start(); return (0); } void timer_init(void) { uint32_t ui32Period; //Set CPU Clock to 40MHz. 400MHz PLL/2 = 200 DIV 5 = 40MHz SysCtlClockSet(SYSCTL_SYSDIV_5|SYSCTL_USE_PLL|SYSCTL_XTAL_16MHZ|SYSCTL_OSC_MAIN); SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOF); GPIOPinTypeGPIOOutput(GPIO_PORTF_BASE, GPIO_PIN_1); // Timer 2 setup code SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER2); // enable Timer 2 periph clks TimerConfigure(TIMER2_BASE, TIMER_CFG_PERIODIC); // cfg Timer 2 mode - periodic ui32Period = (SysCtlClockGet() /100); TimerLoadSet(TIMER2_BASE, TIMER_A, ui32Period); // set Timer 2 period TimerIntEnable(TIMER2_BASE, TIMER_TIMA_TIMEOUT); // enables Timer 2 to interrupt CPU TimerEnable(TIMER2_BASE, TIMER_A); // enable Timer 2 } //--------------------------------------- ------------------------------------ // timer interrupt //--------------------------------------------------------------------------- void timerIntHandler(void) { uint8_t ui32count=0; TimerIntClear(TIMER2_BASE, TIMER_TIMA_TIMEOUT); // must clear timer flag FROM timer timerCount++; // counting time if(timerCount>4000) { timerCount=1; } /* Read 26 signals 8 times */ while(i<8) { decoderAddrLineSelect(i); // MUX line selection readSignal(); i++; } i=0; /* Master and Slave logic */ if(MASTER) { memcpy(Eth_Buffer,&MASTER,sizeof(MASTER)); memcpy(Eth_Buffer+8,&timerCount,sizeof(timerCount)); MODBUS_TRANSMIT; // slave_cmd[0]=0x01; // SLAVE ADDRESS MODBUS_REC_BUF=0x01; UARTSend(&MODBUS_REC_BUF,1); // Send command to slave //slave_cmd[1]=0x54; //"T" -Transfer data Command MODBUS_REC_BUF=0x54; UARTSend(&MODBUS_REC_BUF,1); // UARTSend(slave_cmd,2); // Send command to slave MODBUS_RECIEVE; while(ui32count<MODBUS_DATA_SIZE) { SLAVE_1_BUFFER[ui32count]= UARTCharGet(UART6_BASE); // data receive from the slave ui32count++; } memcpy(Eth_Buffer+10,&SLAVE_1_BUFFER,sizeof(SLAVE_1_BUFFER)); /* slave_cmd[0]=0x02; // SLAVE ADDRESS slave_cmd[1]=0x54; //"T" -Transfer data Command MODBUS_TRANSMIT; UARTSend(slave_cmd,2); // Send command to slave MODBUS_RECIEVE; while(ui32count<MODBUS_DATA_SIZE) { SLAVE_2_BUFFER[ui32count]= UARTCharGet(UART6_BASE); ui32count++; } memcpy(Eth_Buffer+20,&SLAVE_2_BUFFER,sizeof(SLAVE_2_BUFFER)); slave_cmd[0]=0x03; // SLAVE ADDRESS slave_cmd[1]=0x54; //"T" -Transfer data Command MODBUS_TRANSMIT; UARTSend(slave_cmd,2); // Send command to slave MODBUS_RECIEVE; while(ui32count<MODBUS_DATA_SIZE) { SLAVE_3_BUFFER[ui32count]= UARTCharGet(UART6_BASE); ui32count++; } memcpy(Eth_Buffer+30,&SLAVE_3_BUFFER,sizeof(SLAVE_3_BUFFER)); slave_cmd[0]=0x04; // SLAVE ADDRESS slave_cmd[1]=0x54; //"T" -Transfer data Command MODBUS_TRANSMIT; UARTSend(slave_cmd,2); // Send command to slave MODBUS_RECIEVE; while(ui32count<MODBUS_DATA_SIZE) { SLAVE_4_BUFFER[ui32count]= UARTCharGet(UART6_BASE); ui32count++; } slave_cmd[0]=0x05; // SLAVE ADDRESS slave_cmd[1]=0x54; //"T" -Transfer data Command MODBUS_TRANSMIT; UARTSend(slave_cmd,2); // Send command to slave MODBUS_RECIEVE; while(ui32count<28) { SLAVE_5_BUFFER[ui32count]= UARTCharGet(UART6_BASE); ui32count++; }*/ } else { MODBUS_RECIEVE; //slave_cmd[0]= UARTCharGet(UART6_BASE); // Command receive from master MODBUS_REC_BUF= UARTCharGet(UART6_BASE); switch (MODBUS_REC_BUF) { case 0x01: MODBUS_REC_BUF= UARTCharGet(UART6_BASE); // Command receive from master if(MODBUS_REC_BUF==0x54) { //UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); MODBUS_TRANSMIT; //memcpy(Modbus_Buffer,&SLAVE_ADDRESS,sizeof(SLAVE_ADDRESS)); /*memcpy(Modbus_Buffer+1,&portB_data,sizeof(portB_data)); memcpy(Modbus_Buffer+2,&portD_data,sizeof(portD_data)); memcpy(Modbus_Buffer+3,&portE_data,sizeof(portE_data)); memcpy(Modbus_Buffer+4,&portL_data,sizeof(portL_data)); memcpy(Modbus_Buffer+5,&portM_data,sizeof(portM_data)); memcpy(Modbus_Buffer+6,&portN_data,sizeof(portN_data)); memcpy(Modbus_Buffer+7,&portP_data,sizeof(portP_data)); memcpy(Modbus_Buffer+8,&timerCount,sizeof(timerCount));*/ UARTSend(Modbus_Buffer,sizeof(Modbus_Buffer)); } break; case 0x02: MODBUS_REC_BUF= UARTCharGet(UART6_BASE); // Command receive from master if(MODBUS_REC_BUF==0x54) { //UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); MODBUS_TRANSMIT; memcpy(Modbus_Buffer,&SLAVE_ADDRESS,sizeof(SLAVE_ADDRESS)); /* memcpy(Modbus_Buffer+1,&portB_data,sizeof(portB_data)); memcpy(Modbus_Buffer+2,&portD_data,sizeof(portD_data)); memcpy(Modbus_Buffer+3,&portE_data,sizeof(portE_data)); memcpy(Modbus_Buffer+4,&portL_data,sizeof(portL_data)); memcpy(Modbus_Buffer+5,&portM_data,sizeof(portM_data)); memcpy(Modbus_Buffer+6,&portN_data,sizeof(portN_data)); memcpy(Modbus_Buffer+7,&portP_data,sizeof(portP_data));*/ memcpy(Modbus_Buffer+8,&timerCount,sizeof(timerCount)); UARTSend(Modbus_Buffer,sizeof(Modbus_Buffer)); } break; case 0x03: MODBUS_REC_BUF= UARTCharGet(UART6_BASE); // Command receive from master if(slave_cmd[1]==0x54) { //UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); MODBUS_TRANSMIT; memcpy(Modbus_Buffer,&SLAVE_ADDRESS,sizeof(SLAVE_ADDRESS)); /* memcpy(Modbus_Buffer+1,&portB_data,sizeof(portB_data)); memcpy(Modbus_Buffer+2,&portD_data,sizeof(portD_data)); memcpy(Modbus_Buffer+3,&portE_data,sizeof(portE_data)); memcpy(Modbus_Buffer+4,&portL_data,sizeof(portL_data)); memcpy(Modbus_Buffer+5,&portM_data,sizeof(portM_data)); memcpy(Modbus_Buffer+6,&portN_data,sizeof(portN_data)); memcpy(Modbus_Buffer+7,&portP_data,sizeof(portP_data));*/ memcpy(Modbus_Buffer+8,&timerCount,sizeof(timerCount)); UARTSend(Modbus_Buffer,sizeof(Modbus_Buffer)); } break; case 0x04: MODBUS_REC_BUF= UARTCharGet(UART6_BASE); // Command receive from master if(slave_cmd[1]==0x54) { //UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); MODBUS_TRANSMIT; /* memcpy(Modbus_Buffer,&SLAVE_ADDRESS,sizeof(SLAVE_ADDRESS)); memcpy(Modbus_Buffer+1,&portB_data,sizeof(portB_data)); memcpy(Modbus_Buffer+2,&portD_data,sizeof(portD_data)); memcpy(Modbus_Buffer+3,&portE_data,sizeof(portE_data)); memcpy(Modbus_Buffer+4,&portL_data,sizeof(portL_data)); memcpy(Modbus_Buffer+5,&portM_data,sizeof(portM_data)); memcpy(Modbus_Buffer+6,&portN_data,sizeof(portN_data)); memcpy(Modbus_Buffer+7,&portP_data,sizeof(portP_data));*/ memcpy(Modbus_Buffer+8,&timerCount,sizeof(timerCount)); UARTSend(Modbus_Buffer,sizeof(Modbus_Buffer)); } break; case 0x05: MODBUS_REC_BUF= UARTCharGet(UART6_BASE); // Command receive from master if(slave_cmd[1]==0x54) { //UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); MODBUS_TRANSMIT; memcpy(Modbus_Buffer,&SLAVE_ADDRESS,sizeof(SLAVE_ADDRESS)); /* memcpy(Modbus_Buffer+1,&portB_data,sizeof(portB_data)); memcpy(Modbus_Buffer+2,&portD_data,sizeof(portD_data)); memcpy(Modbus_Buffer+3,&portE_data,sizeof(portE_data)); memcpy(Modbus_Buffer+4,&portL_data,sizeof(portL_data)); memcpy(Modbus_Buffer+5,&portM_data,sizeof(portM_data)); memcpy(Modbus_Buffer+6,&portN_data,sizeof(portN_data)); memcpy(Modbus_Buffer+7,&portP_data,sizeof(portP_data));*/ memcpy(Modbus_Buffer+8,&timerCount,sizeof(timerCount)); UARTSend(Modbus_Buffer,sizeof(Modbus_Buffer)); } break; case 0x45: START_STP_LED_OFF; Timer_Stop(); START_FLAG=0; break; } /* if(slave_cmd[0] == 0x01) { if(slave_cmd[1]==0x54) { UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); // UARTSend(&portD_data,1); // UARTSend(&portE_data,1); // UARTSend(&portB_data,1); // UARTSend(&portN_data,1); // UARTSend(&portP_data,1); // UARTSend(&portL_data,1); // UARTSend(&portM_data,1); } } if(slave_cmd[0] == 0x02) { if(slave_cmd[1]==0x54) { UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); // UARTSend(&portD_data,1); // UARTSend(&portE_data,1); // UARTSend(&portB_data,1); // UARTSend(&portN_data,1); // UARTSend(&portP_data,1); // UARTSend(&portL_data,1); // UARTSend(&portM_data,1); } } if(slave_cmd[0] == 0x03) { if(slave_cmd[1]==0x54) { UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); // UARTSend(&portD_data,1); // UARTSend(&portE_data,1); // UARTSend(&portB_data,1); // UARTSend(&portN_data,1); // UARTSend(&portP_data,1); // UARTSend(&portL_data,1); // UARTSend(&portM_data,1); } } if(slave_cmd[0] == 0x04) { if(slave_cmd[1]==0x54) { UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); // UARTSend(&portD_data,1); // UARTSend(&portE_data,1); // UARTSend(&portB_data,1); // UARTSend(&portN_data,1); // UARTSend(&portP_data,1); // UARTSend(&portL_data,1); // UARTSend(&portM_data,1); } } if(slave_cmd[0] == 0x05) { if(slave_cmd[1]==0x54) { UARTSend((uint8_t *)"ABCDEFGHIJKLMNOPQRSTUVWXYZ01",28); // UARTSend(&portD_data,1); // UARTSend(&portE_data,1); // UARTSend(&portB_data,1); // UARTSend(&portN_data,1); // UARTSend(&portP_data,1); // UARTSend(&portL_data,1); // UARTSend(&portM_data,1); } }*/ } }
您好、Khodidas、
您是否查看过具有示波器或 LSA 的 UART 线路、以查看是否发送了任何意外数据?
查看您的代码、我不熟悉 MODBUS 协议、但由于问题是接收到第二个字节、我看到您执行 的是 MODBUS_REC_BUF= UARTCharGet (UART6_BASE);在778行上、然后输入一条 switch 语句、在这里您执行另一 个 MODBUS_REC_BUF= UARTGet (UART6_BASE);
第二个调用是您希望代码阻止而不是接收垃圾数据的位置吗?
如果 UART 线路上没有显示垃圾数据、那么您可能需要像使用以下类似函数刷新 FIFO:
//***************************************************************************** // // Flush the FIFO for the RX UART to ensure there is no garbage data present. // //***************************************************************************** static void FlushUARTRXFIFO(void) { while(UARTCharGetNonBlocking(UART0_BASE) != -1) { } }
此致、
Ralph Jacobi
尊敬的 Ralph:
是的问题与 您提到的内容完全相同。 当 Boar 中断主站时、它将向从站发送"S"命令(请参阅 TCP 连接处理程序中的) 、该主站将启动其自己的计时器、并且它将 分别发送0x01和0x54。 为了解决这个问题、 我在单个 PC 中将主从都置于调试中。 在从器件侧 、从器件完美地接收"S"、然后执行情况检查和操作、同样、即使主器件不发送0x01和0x54、它也会接收 UART 并在缓冲区中提供0xFF。 因此、我们散热片的问题是、在接收到"S"单字节后、为什么 MODBUS_REC_BUF= UARTCharGet (UART6_BASE); 即使主器 件不传输、也像非阻塞一样进行输出。
此致
Khodidas Domadiya
您好、Khodidas、
我想知道的另一件事是、如何使用 UART6 中断处理程序和计时器中断处理程序、两者都涉及读取 UART6数据。 也许会有优先事项的问题吗? 也许接收到了字节、所以 while 循环被清除、但是 UART6中断停止读取、而是读取数据、然后阻断函数完成执行、数据消失、因此它获得0xFF。
除此之外...
[引用 userid="289369" URL"~/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/1054306/tm4c1294ncpdt-uart-recieve-issue/3901181 #3901181"]要解决问题, 我在单个 PC 中将主设备和从设备都置于调试中。正常运行期间是否不会出现此问题?
[引用 userid="289369" URL"~/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/1054306/tm4c1294ncpdt-uart-recieve-issue/3901181 #3901181"]即使主控方未发送0x01和0x54、ART 也会接收并在缓冲区中提供0xFF。您是否看过 UART 线路以确认唯一显示的数据是"S"?
FIFO 刷新可能甚至没有实际意义、因为如果 FIFO 中有垃圾数据、它将首先发出、然后发出"S"命令。
您可以做的另一件事是、当您收到第一个计时器中断时查看 FIFO 寄存器、并查看 FIFO 中的内容以及设置了哪些标志等
此致、
Ralph Jacobi
您好、@找到了代码的确切问题、T Ü V S Ü D 菜单部分(更正了下面的一个)
Modbus_transmit;
Modbus_REC_BUF=0x01;
UARTSend (((uint8_t *)&MODBUS_REC_BUF、1);//向从属方发送命令
Modbus_REC_BUF=0x54;
UARTSend (((uint8_t *)&MODBUS_REC_BUF、1);
SysCtlDelay (4000);
while (ui32 <MODBUS_DATA_SIZE)
{
Modbus_receve;
SLAVE_1_BUFFER[ui32count]= UARTCharGet (UART6_BASE);//从从器件接收数据
ui32count++;
}
}
SysCtlDelay (4000);
如果您看一下我之前的共享代码-转到计时器处理程序 并在主控条件下,当启用主控传输时(这将启用 MAX485 的传输模式),然后我们将在 阻塞模式下通过 UART 传输0x01和0x54, 但是、在使用示波器查找原因后、MCU 不会在发送中获取块并执行 UART_SEND 行、并且10会转至之前为 MODBU_RECIVE 的下一个命令、即使 MCU 尚未完成传输、也会导致 MAX485处于接收模式。
因为、我们解决了4000克时钟周期的延迟问题、并得到了解决。
我的问题是 、为什么在阻塞模式下 UART 传输不会实际阻塞 CPU、它会将数据放入 UART 的硬件缓冲区、并立即执行下一个操作。 此外、在 SDK 中没有传输完整指示功能、如果有、这将对我们有所帮助、尤其是在时间关键型应用中。
此致
Khodidas Domadiya
您好、Khodidas、
[引用 userid="289369" URL"~/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/1054306/tm4c1294ncpdt-uart-recieve-issue/3903195 #3903195"]因此我的问题是、 为什么在阻塞模式下 UART 传输不会实际阻塞 CPU、它会将数据放入 UART 的硬件缓冲区并立即执行下一步操作。"阻断"功能 被设计成 在 FIFO 中没有空间时工作。 如果 FIFO 中有空间、那么它将加载字节并继续执行代码。 在应用程序中、您可以使用轮询来等待、直到发送字节以执行如下操作:
while(HWREG(ui32Base + UART_O_FR) & UART_FR_TXFF) { }
我可以看到、您没有使用 FIFO、这意味着您可以配置 UART 中断来指示 EOT。 任何"传输完成"功能都需要从 ISR 驱动。 仅供参考、但如果使用 FIFO、则仅当阈值通过且没有可用的'FIFO 空'中断时、FIFO 级别水印的中断才会触发。
此致、
Ralph Jacobi
尊敬的 Ralph:
很抱歉、由于我们在同一个项目中遇到另一个问题、并且我们正在对其进行调试、因此我们迟到了响应。 根据、您的建议将实施建议的代码行。 作为不使用 FIFO 的一部分、我们需要同步数据以及由于缓冲区中的数据模式而产生的其他信号、这是系统的另一端固定的。
在我获得结果时、将在这里更新相同的内容。
此致
霍迪达斯