在程序中需要厂家提供的wringPi库,才能通过C语言库函数调用实现对其GPIO的控制。
以下是这个单板机GPIO的管脚对应关系,本程序中用到的wPi编号是9和10:
本IOC应用程序,仅需要需要base和asyn模块,在configure/RELEASSE文件中指定:
SUPPORT = /usr/local/EPICS/synApps/support
ASYN = ${SUPPORT}/asyn
EPICS_BASE = /usr/local/EPICS/base
以下是cpp源代码,它继承了asynPortDriver类,并且重写了其writeUInt32Digital方法,用于在指定GPIO管脚上,设置电平状态:
# drvgpioasyn.cpp
#include <iocsh.h>
#include <epicsThread.h>
#include <asynPortDriver.h>
#include <wiringPi.h>
#include <epicsExport.h>
static const char *driverName = "GPIOAsynDriver";
#define digitalOutputString "DIGITAL_OUTPUT"
#define NUM_IO_BITS 2 // Number of digital I/O bits to USE
class GPIOAsynDriverOut : public asynPortDriver {
public:
GPIOAsynDriverOut(const char *portName);
/* These are the methods that we override from asynPortDriver */
virtual asynStatus writeUInt32Digital(asynUser *pasynUser, epicsUInt32 value, epicsUInt32 mask);
virtual void report(FILE *fp, int details);
protected:
// Analog output parameters
int digitalOutput_;
#define FIRST_GPIOOUT_PARAM digitalOutput_
#define LAST_GPIOOUT_PARAM digitalOutput_
private:
int gpio[2];
void init_GPIO_Out();
asynStatus setGPIO(int index, int val);
};
#define NUM_PARAMS ((int)(&LAST_GPIOOUT_PARAM - &FIRST_GPIOOUT_PARAM + 1))
GPIOAsynDriverOut::GPIOAsynDriverOut(const char *portName)
: asynPortDriver(portName, 1 , NUM_PARAMS,
asynUInt32DigitalMask | asynDrvUserMask, // Interfaces that we implement
asynUInt32DigitalMask, // Interfaces that do callbacks
ASYN_MULTIDEVICE | ASYN_CANBLOCK, 1, /* ASYN_CANBLOCK=1, ASYN_MULTIDEVICE=1, autoConnect=1 */
0, 0) /* Default priority and stack size */
{
// Digital I/O parameters
init_GPIO_Out();
createParam(digitalOutputString, asynParamUInt32Digital, &digitalOutput_);
}
asynStatus GPIOAsynDriverOut::writeUInt32Digital(asynUser *pasynUser, epicsUInt32 value, epicsUInt32 mask)
{
int function = pasynUser->reason;
int status=0;
int i;
epicsUInt32 outValue=0, outMask;
static const char *functionName = "writeUInt32Digital";
setUIntDigitalParam(function, value, mask);
if (function == digitalOutput_) {
for (i=0, outMask=1; i<NUM_IO_BITS; i++, outMask = (outMask<<1)) {
// Only write the value if the mask has this bit set
outValue = ((value &outMask) == 0) ? 0 : 1;
if ((mask & outMask ) != 0) {
status = setGPIO(i, outValue);
}
}
}
if (status == 0) {
asynPrint(pasynUser, ASYN_TRACEIO_DRIVER,
"%s:%s, port %s, wrote outValue=0x%x, value=0x%x, mask=0x%x\n",
driverName, functionName, this->portName, outValue, value, mask);
} else {
asynPrint(pasynUser, ASYN_TRACE_ERROR,
"%s:%s, port %s, ERROR writing outValue=0x%x, value=0x%x, mask=0x%x, status=%d\n",
driverName, functionName, this->portName, outValue, value, mask, status);
}
return (status==0) ? asynSuccess : asynError;
}
void GPIOAsynDriverOut::init_GPIO_Out()
{
int i;
this->gpio[0] = 9;
this->gpio[1] = 10;
wiringPiSetup();
for (i = 0; i < NUM_IO_BITS ; i++){
pinMode(this->gpio[i], OUTPUT);
digitalWrite(this->gpio[i], 0);
}
}
asynStatus GPIOAsynDriverOut::setGPIO(int index, int val)
{
digitalWrite(this->gpio[index], val);
return asynSuccess;
}
void GPIOAsynDriverOut::report(FILE *fp, int details)
{
fprintf(fp, " Port: %s,GPIO %d - %d\n", this->portName, this->gpio[0], this->gpio[1]);
asynPortDriver::report(fp, details);
}
extern "C" int GPIOAsynDriverOutConfig(const char *portName)
{
GPIOAsynDriverOut *pGPIOAsynDriverOut = new GPIOAsynDriverOut(portName);
pGPIOAsynDriverOut = NULL;
return(asynSuccess);
}
static const iocshArg configArg0 = { "Port name", iocshArgString};
static const iocshArg * const configArgs[] = {&configArg0,};
static const iocshFuncDef configFuncDef = {"GPIOAsynDriverOutConfig", 1, configArgs};
static void configCallFunc(const iocshArgBuf *args)
{
GPIOAsynDriverOutConfig(args[0].sval);
}
void drvGPIOAsynDriverOutRegister(void)
{
iocshRegister(&configFuncDef,configCallFunc);
}
extern "C" {
epicsExportRegistrar(drvGPIOAsynDriverOutRegister);
}
编写一个数据库定义文件:
# drvgpioasyn.dbd
registrar(drvGPIOAsynDriverOutRegister)
在同级目录下的Makefile中指定需要的数据库定义文件,库文件以及源文件:
TOP=../..
include $(TOP)/configure/CONFIG
#----------------------------------------
# ADD MACRO DEFINITIONS AFTER THIS LINE
#=============================
#=============================
# Build the IOC application
PROD_IOC = gpioasyn
# gpioasyn.dbd will be created and installed
DBD += gpioasyn.dbd
# gpioasyn.dbd will be made up from these files:
gpioasyn_DBD += base.dbd
gpioasyn_DBD += asyn.dbd
gpioasyn_DBD += drvgpioasyn.dbd
# Include dbd files from all support applications:
#gpioasyn_DBD += xxx.dbd
# Add all the support libraries needed by this IOC
gpioasyn_LIBS += asyn
gpioasyn_LIBS += wiringPi
wiringPi_DIR = /usr/lib
**自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。**
**深知大多数大数据工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!**
**因此收集整理了一份《2024年大数据全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友。**
![img](https://img-blog.csdnimg.cn/img_convert/abd7e19f9f4817b52e970616f975cb50.png)
![img](https://img-blog.csdnimg.cn/img_convert/21a45c42315d2a3b214eea2663bde402.png)
![img](https://img-blog.csdnimg.cn/img_convert/afe923952e306f1f7849247fc8ec73cb.png)
![img](https://img-blog.csdnimg.cn/img_convert/3d4cd56f08f29db36f8de513f72cf6ab.png)
![img](https://img-blog.csdnimg.cn/img_convert/59eb1924d57bf74ce19c4ec306c3f49a.png)
**既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上大数据开发知识点,真正体系化!**
**由于文件比较大,这里只是将部分目录大纲截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且后续会持续更新**
**如果你觉得这些内容对你有帮助,可以添加VX:vip204888 (备注大数据获取)**
![img](https://img-blog.csdnimg.cn/img_convert/83b8ca3ba770165089b254a5f07ae442.png)
**一个人可以走的很快,但一群人才能走的更远。不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎扫码加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!**
、源码讲义、实战项目、讲解视频,并且后续会持续更新**
**如果你觉得这些内容对你有帮助,可以添加VX:vip204888 (备注大数据获取)**
[外链图片转存中...(img-Yvxd12ae-1712959996089)]
**一个人可以走的很快,但一群人才能走的更远。不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎扫码加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!**