FreeModbus移植到STM32F103(串行传输方式)
1.创建工程
2.将FreeModbus源码,拷贝到工程目录
3.将FreeModbus文件添加进工程
添加好之后,编译出现错误
4.移植底层接口
先看第一个错误,缺少port.h
借鉴AVR架构的程序,将demo里面AVR中的port文件夹,拷贝到工程中
进入port文件夹,删除重复文件,mbcrc.c
添加好之后,重新编译,出现错误,port.h中包含了很多iar相关代码
将这些代码删除或修改
重新编译,错误少了很多,剩下的错误是,portserial和porttimer中包含avr相关代码
将portserial和porttimer中,串口和定时器的驱动,改成STM32架构的代码
#include "port.h"/* ----------------------- Modbus includes ----------------------------------*/
#include "mb.h"
#include "mbport.h"/* GPIO配置 */
static void gpio_config(void)
{GPIO_InitTypeDef GPIO_InitStructure;/* 使能GPIOA时钟 */RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);/* 设置PA2为复用推挽输出 */GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOA, &GPIO_InitStructure); /* 设置PA3为浮空输入 */GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; GPIO_Init(GPIOA, &GPIO_InitStructure);
}/* 中断配置 */
static void nvic_config(void)
{NVIC_InitTypeDef NVIC_InitStructure;/* 设置串口1中断的先占优先级为2,从占优先级为2 */NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;NVIC_Init(&NVIC_InitStructure);
}/* 串口配置 */
static void usart_config(uint32_t baudRate, uint16_t wordLength, uint16_t parity)
{USART_InitTypeDef USART_InitStruct; /* 使能GPIOA时钟和串口时钟 */RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);/* 设置串口波特率115200、数据位8bit、停止位1bit、校验位无、无硬件流、接收发送 */if(wordLength == 9)USART_InitStruct.USART_WordLength = USART_WordLength_9b;elseUSART_InitStruct.USART_WordLength = USART_WordLength_8b;if(MB_PAR_NONE != parity)USART_InitStruct.USART_StopBits = USART_StopBits_1;elseUSART_InitStruct.USART_StopBits = USART_StopBits_2;if(MB_PAR_NONE == parity)USART_InitStruct.USART_Parity = USART_Parity_No;else if(MB_PAR_EVEN == parity)USART_InitStruct.USART_Parity = USART_Parity_Even;elseUSART_InitStruct.USART_Parity = USART_Parity_Odd;USART_InitStruct.USART_HardwareFlowControl = USART_HardwareFlowControl_None;USART_InitStruct.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;USART_Init(USART1, &USART_InitStruct);
}void vMBPortSerialEnable(BOOL xRxEnable, BOOL xTxEnable)
{if(xRxEnable == FALSE && xTxEnable == FALSE)USART_Cmd(USART1, DISABLE);elseUSART_Cmd(USART1, ENABLE);if(xRxEnable == TRUE){USART_ClearITPendingBit(USART1, USART_IT_RXNE);USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);}elseUSART_ITConfig(USART1, USART_IT_RXNE, DISABLE);if(xTxEnable == TRUE){USART_ClearITPendingBit(USART1, USART_IT_TC);USART_ITConfig(USART1, USART_IT_TC, ENABLE);pxMBFrameCBTransmitterEmpty();}elseUSART_ITConfig(USART1, USART_IT_TC, DISABLE);
}BOOL xMBPortSerialInit(UCHAR ucPORT, ULONG ulBaudRate, UCHAR ucDataBits, eMBParity eParity)
{(void)ucPORT;/* 串口配置 */usart_config(ulBaudRate, ucDataBits, eParity); /* GPIO配置 */gpio_config();/* 中断配置 */nvic_config();vMBPortSerialEnable(FALSE, FALSE);return TRUE;
}BOOL xMBPortSerialPutByte(CHAR ucByte)
{ USART_SendData(USART1, ucByte);return TRUE;
}BOOL xMBPortSerialGetByte(CHAR *pucByte)
{*pucByte = USART_ReceiveData(USART1);return TRUE;
}void USART1_IRQHandler(void)
{ if(USART_GetITStatus(USART1, USART_IT_ORE) != RESET){ USART_ClearITPendingBit(USART1, USART_IT_ORE);pxMBFrameCBByteReceived();} if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET){ USART_ClearITPendingBit(USART1, USART_IT_RXNE);pxMBFrameCBByteReceived();} if(USART_GetITStatus(USART1, USART_IT_TC) != RESET){ USART_ClearITPendingBit(USART1, USART_IT_TC);pxMBFrameCBTransmitterEmpty();}
}
/* ----------------------- Platform includes --------------------------------*/
#include "port.h"/* ----------------------- Modbus includes ----------------------------------*/
#include "mb.h"
#include "mbport.h"/* 功能: 定时器配置参数: period 自动重载值返回值: 无 */
static void timer_config(uint16_t period)
{TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;/* 允许TIM3的时钟 */RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);/* 将定时器3寄存器设为初始值 */TIM_DeInit(TIM3);/* 设置定时器3由内部时钟 */TIM_InternalClockConfig(TIM3);/* 预分频值 */TIM_TimeBaseStructure.TIM_Prescaler = 3600 - 1;/* 时钟分割 */TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;/* 向上计数 */TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;/* 自动重载值 */TIM_TimeBaseStructure.TIM_Period = period - 1;/* 初始化定时器3 */TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);/* 清除溢出中断标志 */TIM_ClearFlag(TIM3, TIM_FLAG_Update);/* 禁止ARR预装载缓冲器 */TIM_ARRPreloadConfig(TIM3, DISABLE);
}/* 功能: 中断配置参数: 无返回值: 无 */
static void nvic_config(void)
{NVIC_InitTypeDef NVIC_InitStructure;/* 选择TIM3的中断通道 */NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;/* 抢占式中断优先级设置为2 */NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;/* 响应式中断优先级设置为2 */NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;/* 使能中断 */NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;/* 中断初始化 */NVIC_Init(&NVIC_InitStructure);
}BOOL xMBPortTimersInit(USHORT usTim1Timerout50us)
{/* 设置定时器定时时间 */timer_config(usTim1Timerout50us);/* 中断配置 */nvic_config();return TRUE;
}void vMBPortTimersEnable(void)
{/* 清空定时器3计数器 */TIM_SetCounter(TIM3, 0);/* 使能定时器3 */TIM_Cmd(TIM3, ENABLE);/* 使能TIM3的中断 */TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
}void vMBPortTimersDisable(void)
{/* 禁止定时器3 */TIM_Cmd(TIM3, DISABLE);/* 关闭TIM3的中断 */TIM_ITConfig(TIM3, TIM_IT_Update, DISABLE);
}/* 定时器3中断向量 */
void TIM3_IRQHandler(void)
{/* 定时器3溢出标志位 */if(TIM_GetITStatus(TIM3, TIM_IT_Update) != RESET){/* 定时器3清除溢出标志位 */TIM_ClearITPendingBit(TIM3 , TIM_FLAG_Update);/* 关闭TIM3的中断 */TIM_ITConfig(TIM3, TIM_IT_Update, DISABLE);/* 关闭定时器3 */TIM_Cmd(TIM3, DISABLE);(void)pxMBPortCBTimerExpired();}
}
重新编译,驱动相关的错误,已经不存在。
报告eMBRegCoilsCB、eMBRegDiscreteCB、eMBRegHoldingCB和eMBRegInputCB没有定义。
这四个接口是协议栈预留给用户自己去实现的,分别创建user_mb_app.h和user_mb_app.c两个文件
#ifndef _USER_MB_APP_H_
#define _USER_MB_APP_H_/* ----------------------- Modbus includes ----------------------------------*/
#include "mb.h"
#include "mbconfig.h"
#include "mbframe.h"
#include "mbutils.h"/* -----------------------Slave Defines -------------------------------------*/
#define S_DISCRETE_INPUT_START 0
#define S_DISCRETE_INPUT_NDISCRETES 16
#define S_COIL_START 0
#define S_COIL_NCOILS 64
#define S_REG_INPUT_START 0
#define S_REG_INPUT_NREGS 100
#define S_REG_HOLDING_START 0
#define S_REG_HOLDING_NREGS 100
/* salve mode: holding register's all address */
#define S_HD_RESERVE 0
#define S_HD_CPU_USAGE_MAJOR 1
#define S_HD_CPU_USAGE_MINOR 2
/* salve mode: input register's all address */
#define S_IN_RESERVE 0
/* salve mode: coil's all address */
#define S_CO_RESERVE 0
/* salve mode: discrete's all address */
#define S_DI_RESERVE 0/* -----------------------Master Defines -------------------------------------*/
#define M_DISCRETE_INPUT_START 0
#define M_DISCRETE_INPUT_NDISCRETES 16
#define M_COIL_START 0
#define M_COIL_NCOILS 64
#define M_REG_INPUT_START 0
#define M_REG_INPUT_NREGS 100
#define M_REG_HOLDING_START 0
#define M_REG_HOLDING_NREGS 100
/* master mode: holding register's all address */
#define M_HD_RESERVE 0
/* master mode: input register's all address */
#define M_IN_RESERVE 0
/* master mode: coil's all address */
#define M_CO_RESERVE 0
/* master mode: discrete's all address */
#define M_DI_RESERVE 0#endif
/** FreeModbus Libary: user callback functions and buffer define in slave mode* Copyright (C) 2013 Armink <armink.ztl@gmail.com>** This library is free software; you can redistribute it and/or* modify it under the terms of the GNU Lesser General Public* License as published by the Free Software Foundation; either* version 2.1 of the License, or (at your option) any later version.** This library is distributed in the hope that it will be useful,* but WITHOUT ANY WARRANTY; without even the implied warranty of* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU* Lesser General Public License for more details.** You should have received a copy of the GNU Lesser General Public* License along with this library; if not, write to the Free Software* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA** File: $Id: user_mb_app.c,v 1.60 2013/11/23 11:49:05 Armink $*/
#include "user_mb_app.h"/*------------------------Slave mode use these variables----------------------*/
//Slave mode:DiscreteInputs variables
USHORT usSDiscInStart = S_DISCRETE_INPUT_START;
#if S_DISCRETE_INPUT_NDISCRETES%8
UCHAR ucSDiscInBuf[S_DISCRETE_INPUT_NDISCRETES/8+1];
#else
UCHAR ucSDiscInBuf[S_DISCRETE_INPUT_NDISCRETES/8] ;
#endif
//Slave mode:Coils variables
USHORT usSCoilStart = S_COIL_START;
#if S_COIL_NCOILS%8
UCHAR ucSCoilBuf[S_COIL_NCOILS/8+1] ;
#else
UCHAR ucSCoilBuf[S_COIL_NCOILS/8] ;
#endif
//Slave mode:InputRegister variables
USHORT usSRegInStart = S_REG_INPUT_START;
USHORT usSRegInBuf[S_REG_INPUT_NREGS] ;
//Slave mode:HoldingRegister variables
USHORT usSRegHoldStart = S_REG_HOLDING_START;
USHORT usSRegHoldBuf[S_REG_HOLDING_NREGS] ;/*** Modbus slave input register callback function.** @param pucRegBuffer input register buffer* @param usAddress input register address* @param usNRegs input register number** @return result*/
eMBErrorCode eMBRegInputCB(UCHAR *pucRegBuffer, USHORT usAddress, USHORT usNRegs)
{eMBErrorCode eStatus = MB_ENOERR;USHORT iRegIndex;USHORT * pusRegInputBuf;USHORT REG_INPUT_START;USHORT REG_INPUT_NREGS;USHORT usRegInStart;pusRegInputBuf = usSRegInBuf;REG_INPUT_START = S_REG_INPUT_START;REG_INPUT_NREGS = S_REG_INPUT_NREGS;usRegInStart = usSRegInStart;/* it already plus one in modbus function method. */usAddress--;if ((usAddress >= REG_INPUT_START)&& (usAddress + usNRegs <= REG_INPUT_START + REG_INPUT_NREGS)){iRegIndex = usAddress - usRegInStart;while (usNRegs > 0){*pucRegBuffer++ = (UCHAR) (pusRegInputBuf[iRegIndex] >> 8);*pucRegBuffer++ = (UCHAR) (pusRegInputBuf[iRegIndex] & 0xFF);iRegIndex++;usNRegs--;}}else{eStatus = MB_ENOREG;}return eStatus;
}/*** Modbus slave holding register callback function.** @param pucRegBuffer holding register buffer* @param usAddress holding register address* @param usNRegs holding register number* @param eMode read or write** @return result*/
eMBErrorCode eMBRegHoldingCB(UCHAR *pucRegBuffer, USHORT usAddress, USHORT usNRegs, eMBRegisterMode eMode)
{eMBErrorCode eStatus = MB_ENOERR;USHORT iRegIndex;USHORT * pusRegHoldingBuf;USHORT REG_HOLDING_START;USHORT REG_HOLDING_NREGS;USHORT usRegHoldStart;pusRegHoldingBuf = usSRegHoldBuf;REG_HOLDING_START = S_REG_HOLDING_START;REG_HOLDING_NREGS = S_REG_HOLDING_NREGS;usRegHoldStart = usSRegHoldStart;/* it already plus one in modbus function method. */usAddress--;if ((usAddress >= REG_HOLDING_START)&& (usAddress + usNRegs <= REG_HOLDING_START + REG_HOLDING_NREGS)){iRegIndex = usAddress - usRegHoldStart;switch (eMode){/* read current register values from the protocol stack. */case MB_REG_READ:while (usNRegs > 0){*pucRegBuffer++ = (UCHAR) (pusRegHoldingBuf[iRegIndex] >> 8);*pucRegBuffer++ = (UCHAR) (pusRegHoldingBuf[iRegIndex] & 0xFF);iRegIndex++;usNRegs--;}break;/* write current register values with new values from the protocol stack. */case MB_REG_WRITE:while (usNRegs > 0){pusRegHoldingBuf[iRegIndex] = *pucRegBuffer++ << 8;pusRegHoldingBuf[iRegIndex] |= *pucRegBuffer++;iRegIndex++;usNRegs--;}break;}}else{eStatus = MB_ENOREG;}return eStatus;
}/*** Modbus slave coils callback function.** @param pucRegBuffer coils buffer* @param usAddress coils address* @param usNCoils coils number* @param eMode read or write** @return result*/
eMBErrorCode eMBRegCoilsCB(UCHAR *pucRegBuffer, USHORT usAddress, USHORT usNCoils, eMBRegisterMode eMode)
{eMBErrorCode eStatus = MB_ENOERR;USHORT iRegIndex , iRegBitIndex , iNReg;UCHAR * pucCoilBuf;USHORT COIL_START;USHORT COIL_NCOILS;USHORT usCoilStart;iNReg = usNCoils / 8 + 1;pucCoilBuf = ucSCoilBuf;COIL_START = S_COIL_START;COIL_NCOILS = S_COIL_NCOILS;usCoilStart = usSCoilStart;/* it already plus one in modbus function method. */usAddress--;if( ( usAddress >= COIL_START ) &&( usAddress + usNCoils <= COIL_START + COIL_NCOILS ) ){iRegIndex = (USHORT) (usAddress - usCoilStart) / 8;iRegBitIndex = (USHORT) (usAddress - usCoilStart) % 8;switch ( eMode ){/* read current coil values from the protocol stack. */case MB_REG_READ:while (iNReg > 0){*pucRegBuffer++ = xMBUtilGetBits(&pucCoilBuf[iRegIndex++],iRegBitIndex, 8);iNReg--;}pucRegBuffer--;/* last coils */usNCoils = usNCoils % 8;/* filling zero to high bit */*pucRegBuffer = *pucRegBuffer << (8 - usNCoils);*pucRegBuffer = *pucRegBuffer >> (8 - usNCoils);break;/* write current coil values with new values from the protocol stack. */case MB_REG_WRITE:while (iNReg > 1){xMBUtilSetBits(&pucCoilBuf[iRegIndex++], iRegBitIndex, 8,*pucRegBuffer++);iNReg--;}/* last coils */usNCoils = usNCoils % 8;/* xMBUtilSetBits has bug when ucNBits is zero */if (usNCoils != 0){xMBUtilSetBits(&pucCoilBuf[iRegIndex++], iRegBitIndex, usNCoils,*pucRegBuffer++);}break;}}else{eStatus = MB_ENOREG;}return eStatus;
}/*** Modbus slave discrete callback function.** @param pucRegBuffer discrete buffer* @param usAddress discrete address* @param usNDiscrete discrete number** @return result*/
eMBErrorCode eMBRegDiscreteCB(UCHAR *pucRegBuffer, USHORT usAddress, USHORT usNDiscrete)
{eMBErrorCode eStatus = MB_ENOERR;USHORT iRegIndex , iRegBitIndex , iNReg;UCHAR * pucDiscreteInputBuf;USHORT DISCRETE_INPUT_START;USHORT DISCRETE_INPUT_NDISCRETES;USHORT usDiscreteInputStart;iNReg = usNDiscrete / 8 + 1;pucDiscreteInputBuf = ucSDiscInBuf;DISCRETE_INPUT_START = S_DISCRETE_INPUT_START;DISCRETE_INPUT_NDISCRETES = S_DISCRETE_INPUT_NDISCRETES;usDiscreteInputStart = usSDiscInStart;/* it already plus one in modbus function method. */usAddress--;if ((usAddress >= DISCRETE_INPUT_START)&& (usAddress + usNDiscrete <= DISCRETE_INPUT_START + DISCRETE_INPUT_NDISCRETES)){iRegIndex = (USHORT) (usAddress - usDiscreteInputStart) / 8;iRegBitIndex = (USHORT) (usAddress - usDiscreteInputStart) % 8;while (iNReg > 0){*pucRegBuffer++ = xMBUtilGetBits(&pucDiscreteInputBuf[iRegIndex++],iRegBitIndex, 8);iNReg--;}pucRegBuffer--;/* last discrete */usNDiscrete = usNDiscrete % 8;/* filling zero to high bit */*pucRegBuffer = *pucRegBuffer << (8 - usNDiscrete);*pucRegBuffer = *pucRegBuffer >> (8 - usNDiscrete);}else{eStatus = MB_ENOREG;}return eStatus;
}
重新编译,0错误,0警告
5.添加接口
分别创建rcc.h、rcc.c、nvic.h、nvic.c文件
/************************************** 文件名:rcc.h* 作者: stone* 版本: V0.1* 日期: 2018-3-29* 描述: 配置时钟源************************************/
#ifndef __RCC_H_
#define __RCC_H_/* 功能: RCC时钟配置参数: 无返回值:无*/
void rcc_config(void);#endif
/************************************** 文件名: rcc.c* 作者: stone* 版本: V0.1* 日期: 2018-3-29* 描述: 配置时钟源************************************/
#include "stm32f10x.h"
#include "stm32f10x_flash.h"
#include "rcc.h"/* 功能: RCC时钟配置参数: 无返回值:无*/
void rcc_config(void)
{ ErrorStatus HSEStartUpStatus;/* RCC寄存器设置为默认配置 */RCC_DeInit();/* 打开外部高速时钟 */RCC_HSEConfig(RCC_HSE_ON);/* 等待外部高速时钟稳定 */HSEStartUpStatus = RCC_WaitForHSEStartUp();if(HSEStartUpStatus == SUCCESS) { /* 设置HCLK = SYSCLK */RCC_HCLKConfig(RCC_SYSCLK_Div1);/* 设置PCLK2 = HCLK */RCC_PCLK2Config(RCC_HCLK_Div1);/* 设置PCLK1 = HCLK / 2 */RCC_PCLK1Config(RCC_HCLK_Div2);/* 设置FLASH代码延时 */FLASH_SetLatency(FLASH_Latency_2);/* 使能预取址缓存 */FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);/* 设置PLL时钟源为HSE倍频9 72MHz */RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_9);/* 使能PLL */RCC_PLLCmd(ENABLE);/* 等待PLL稳定 */while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET);/* 设置PLL为系统时钟源 */RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);/* 等待系统时钟源切换到PLL */while(RCC_GetSYSCLKSource() != 0x08);}
}
/************************************** 文件名: nvic.h* 作者: stone* 版本: V0.1* 日期: 2018-3-29* 描述: 设置中断控制器************************************/
#ifndef __NVIC_H_
#define __NVIC_H_/* 功能: 中断嵌套控制器配置参数: 无返回值:无*/
void nvic_config(void);#endif
/************************************** 文件名: nvic.c* 作者: stone* 版本: V0.1* 日期: 2018-3-29* 描述: 设置中断控制器************************************/
#include "stm32f10x.h"
#include "nvic.h"/* 功能: 中断嵌套控制器配置参数: 无返回值:无*/
void nvic_config(void)
{/* 选择中断分组2 */NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
}
8.协议栈移植工作完成。
#include "stm32f10x.h"
#include "rcc.h"
#include "nvic.h"
#include "mb.h"int main(void)
{/* RCC时钟配置 */rcc_config();/* 中断嵌套控制器配置 */nvic_config();/* 设置从节点ID */eMBSetSlaveID(1, TRUE, 0, 0);/* 初始化Modbus */eMBInit(MB_RTU, 1, 1, 115200, MB_PAR_NONE);/* 使能Modbus */eMBEnable();/* 主循环 */while(1){/* 轮询Modbus */eMBPoll();}
}
FreeModbus移植到STM32F103(串行传输方式)相关推荐
- STM32F407 freemodbus移植
STM32F407 freemodbus移植 一.ModBus介绍 Modbus是一种串行通信协议,是Modicon公司(现在的施耐德电气Schneider Electric)于1979年为使用可编程 ...
- FreeModbus 移植笔记- 1-认识FreeModbus
FreeModbus 移植笔记 目录 1 FreeMODBUS介绍 2 FreeMODBUS官网及源码下载地址 3 移植之前的准备 3.1 FreeModbus V1.6 3.2 Mod ...
- LiteOS移植到STM32F103系列单片机,非常简单
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 LiteOS移植到STM32F103系列单片机 前言 一.下载老版本liteos 二.参考官方的推荐移植步骤 1.新建项目 1.1打开 ...
- 将uc/OS移植到stm32F103上
将uc/OS移植到stm32F103上 一.嵌入式实时操作系统(RTOS) 1.定义 2.实时任务 3.特征 二.使用CubeMX建立STM32F103C8T6HAL库 三.移植uC/OS-III 四 ...
- uC/OS-III移植到STM32F103
**广西河池学院广西高校重点实验室培训基地系统控制与信息处理重点实验室本篇文章来自河池学院:OpenWRT无线路由组写作时间:2021年07月22日** uC/OS-III移植到STM32F103 4 ...
- FreeModbus移植到STM32F107(以太网传输方式)
1.创建工程 配置好之后生成工程 2.将FreeModbus源码,拷贝到工程目录 3.将FreeModbus文件添加进工程 打开mbtcp.c文件发现,受MB_TCP_ENABLED宏定义的影响,所有 ...
- FreeModbus 移植于STM32 实现Modbus RTU通信
http://ntn314.blog.163.com/blog/static/161743584201233084434579/ 毕业设计自己要做个基于STM32的PLC能直接跑语句表的,现在看来好像 ...
- freemodbus移植
freemodbus下载地址:GitHub - cwalter-at/freemodbus: BSD licensed MODBUS RTU/ASCII and TCP slave freemodbu ...
- FreeRTOS移植到STM32F103
1.创建工程 2.将FreeRTOS源码,拷贝到工程目录 3.删除其它架构和编译器的代码 查看portable文件夹发现 MemMang为内存管理相关文件需要保留 Commom里面有个mpu相关代码, ...
最新文章
- Linux配置协同工作目录,Linux学习二:文件权限与目录配置
- 分区格式化/挂载数据盘
- python 中有趣的库tqdm
- C++之链表中头指针、头节点、首元结点的
- 【Spark】SparkStreaming-Kafka-Redis-集成-基础参考资料
- 如何使用弱网环境来验证游戏中的一些延迟问题
- 4种方法帮你解决IntelliJ IDEA控制台中文乱码问题
- linux下安装 Sublime Text 3
- 共享代码库,为何总被程序员弃用?
- php魔术方法例子,PHP魔术方法示例
- JBoss 目录结构解释
- 华为中级编程题目python_华为研发工程师编程题2019(python3)
- nodejs gulp less编辑
- ua获取手机型号_如何根据 UA 判断手机型号和厂家?
- 三思笔记专区,即将闪亮登场
- 计算机视觉论文-2021-03-10
- 网易云音乐灰色歌曲在线听的方法
- Zabbix企业微信告警最新版
- 支付宝和微信支付合作伙伴RiverPay加速全球化战略布局
- 称为超级计算机,怎样的计算机被称为“巨型计算机”呢?
热门文章
- 使用docker搭建FastDFS文件系统
- java自学路线图_JAVA自学路线图
- 计组之中央处理器:5、微程序控制器(组成、原理、概念对比)
- (王道408考研数据结构)第七章查找-第三节:B树(基本概念及其操作)
- C++11 并发指南五(std::condition_variable 详解)
- 小学生计算机辅助教学系统--练习加,减,乘,除法
- E: Sub-process /usr/bin/dpkg returned an error code (1)解决办法
- 西门子S7comm-plus通信过程及重放攻击分析
- WiresharkTCP的状态 (SYN, FIN, ACK, PSH, RST, URG)
- Windows内存保护机制及绕过方法