封装socket网络线程实现对智能家居中各种灯光的控制
main.Pro(主函数)
#include
#include "controlDevice.h"
#include "inputCommand.h"
#include
struct Devices *pdeviceHead = NULL; //设备工厂链表头
struct InputCommander *pcommandHead = NULL; //指令工厂链表头
struct InputCommander *socketHander = NULL;
struct Devices* findDeviceByName(struct Devices *phead,char *name) //在设备链表中查找设备
{
struct Devices *tmp = phead;
if(tmp == NULL){
printf("The devicesLink is NULL");
return NULL;
}else{
while(tmp != NULL){
if(strcmp(tmp->deviceName,name) == 0){
return tmp;
}
tmp = tmp->next;
}
return NULL;
}
}
struct InputCommander* findCommanderByName(struct InputCommander *phead,char *name) //控制链表查找相关控制
{
struct InputCommander *tmp = phead;
if(tmp == NULL){
printf("The commanderLink is NULL");
return NULL;
}else{
while(tmp != NULL){
if(strcmp(tmp->commandName,name) == 0){
return tmp;
}
tmp = tmp->next;
}
return NULL;
}
}
void doCommand(struct InputCommander *cmd) //根据传入的命令控制相关设备
{
struct Devices *tmp = NULL;
if(strstr(cmd->command,"START")){ //初始化所有设备
tmp = findDeviceByName(pdeviceHead,"bathroomLight");
if(tmp != NULL) tmp->deviceInit(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"bedroomLight");
if(tmp != NULL) tmp->deviceInit(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"livingroomLight");
if(tmp != NULL) tmp->deviceInit(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"restaurantLight");
if(tmp != NULL) tmp->deviceInit(tmp->pinNum);
printf("The devices all init success\n");
}else if(strstr(cmd->command,"OL1")){ //打开卫生间灯
tmp = findDeviceByName(pdeviceHead,"bathroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
printf("The bathroomLight already open\n");
}else if(strstr(cmd->command,"CL1")){ //关闭卫生间灯
tmp = findDeviceByName(pdeviceHead,"bathroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
printf("The bathroomLight already close\n");
}else if(strstr(cmd->command,"OL2")){ //打开卧室灯
tmp = findDeviceByName(pdeviceHead,"bedroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
printf("The bedroomLight already open\n");
}else if(strstr(cmd->command,"CL2")){ //关闭卧室灯
tmp = findDeviceByName(pdeviceHead,"bedroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
printf("The bedroomLight already close\n");
}else if(strstr(cmd->command,"OL3")){ //打开客厅灯
tmp = findDeviceByName(pdeviceHead,"livingroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
printf("The livingroomLight already open\n");
}else if(strstr(cmd->command,"CL3")){ //关闭客厅灯
tmp = findDeviceByName(pdeviceHead,"livingroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
printf("The livingroomLight already close\n");
}else if(strstr(cmd->command,"OL4")){ //打开餐厅灯
tmp = findDeviceByName(pdeviceHead,"restaurantLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
printf("The restaurantLight already open\n");
}else if(strstr(cmd->command,"CL4")){ //关闭餐厅灯
tmp = findDeviceByName(pdeviceHead,"restaurantLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
printf("The restaurantLight already close\n");
}else if(strstr(cmd->command,"ALL1")){ //打开所有的灯
tmp = findDeviceByName(pdeviceHead,"bathroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"bedroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"livingroomLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"restaurantLight");
if(tmp != NULL) tmp->open(tmp->pinNum);
printf("The Light all open success\n");
}else if(strstr(cmd->command,"ALL0")){ //关闭所有的灯
tmp = findDeviceByName(pdeviceHead,"bathroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"bedroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"livingroomLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
tmp = findDeviceByName(pdeviceHead,"restaurantLight");
if(tmp != NULL) tmp->close(tmp->pinNum);
printf("The Light all close success\n");
}
}
void* read_pthread(void *data) //socket获取命令线程处理函数
{
int n_read;
while(1){
memset(socketHander->command,0,sizeof(socketHander->command));
n_read = read(socketHander->c_fd,socketHander->command,sizeof(socketHander->command));
if(n_read < 0){
perror("read");
}else if(n_read > 0){
printf("get %d message-->: %s",n_read,socketHander->command);
doCommand(socketHander); //执行命令
}else{
printf("client quit\n");
close(socketHander->c_fd);
pthread_exit(NULL);
}
}
}
void* socket_pthread(void *data) //socket控制线程处理函数
{
int c_fd;
pthread_t read_pth;
struct sockaddr_in c_addr;
memset(&c_addr,0,sizeof(struct sockaddr_in));
socklen_t c_len = sizeof(c_addr);
socketHander = findCommanderByName(pcommandHead,"socketServer");
if(socketHander == NULL){
printf("find socketServer error\n");
pthread_exit(NULL);
}
if(socketHander->Init(socketHander) < 0){
printf("socket init error\n");
pthread_exit(NULL);
}else
printf("%s init success\n",socketHander->commandName);
while(1){
c_fd = accept(socketHander->s_fd,(struct sockaddr *)&c_addr,&c_len);
if(c_fd == -1){
perror("accept");
}else
printf("get connect: %s\n",inet_ntoa(c_addr.sin_addr));
socketHander->c_fd = c_fd;
pthread_create(&read_pth,NULL,read_pthread,NULL);
}
}
int main()
{
pthread_t socket_pth;
if(wiringPiSetup()<0){//初始化wiringPi外设库
printf("wiringPi Init failed\n");
return -1;
}
//1.指令工厂初始化
pcommandHead = addSocketToCommandLink(pcommandHead); //将socket控制加入命令控制链表
//2.设备控制工厂初始化
pdeviceHead = addBathroomLightToDeviceLink(pdeviceHead); //将卫生灯加入设备链表
pdeviceHead = addbedroomLightToDeviceLink(pdeviceHead); //将卧室灯加入设备链表
pdeviceHead = addRestaurantLightToDeviceLink(pdeviceHead); //将餐厅灯加入设备链表
pdeviceHead = addLivingroomLightToDeviceLink(pdeviceHead); //将客厅灯加入设备链表
pdeviceHead = addFireToDeviceLink(pdeviceHead); //将火灾检测加入设备链表
pdeviceHead = addBeepToDeviceLink(pdeviceHead); //将蜂鸣器加入设备链表
//3.线程池建立
//3.2socket线程
ret = pthread_create(&socket_pth,NULL,socket_pthread,NULL);
if (ret != 0) {
printf("Failed to create socketthread.\n");
return -1;
}
//等待线程退出
pthread_join(socket_pth,NULL);
return 0;
}
inputCommand.h(控制类)
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
struct InputCommander
{
char commandName[128]; //命令名字
char command[32]; //具体命令
char deviceName[128]; //打开的设备名,比如串口
char port[12]; //端口号
char ipAddress[32]; //ip地址
int (*Init)(struct InputCommander *commder);
int (*getCommand)(struct InputCommander *commder);
int fd; //文件描述符
int baud; //波特率
int s_fd; //socket服务端文件描述符
int c_fd; //客户端文件描述符
char log[1024]; //日志
struct InputCommander *next;
};
struct InputCommander *addSocketToCommandLink(struct InputCommander *phead); //socket控制加入命令控制链表
socketControl.c(socket)
#include "inputCommand.h"
int socketInit(struct InputCommander *socketMes)
{
int s_fd;//服务端
struct sockaddr_in s_addr;
memset(&s_addr,0,sizeof(struct sockaddr_in));
//1.socket
s_fd = socket(AF_INET,SOCK_STREAM,0); //创建套接字
if(s_fd == -1){
perror("socket");
exit(-1);
}
//2.bind
s_addr.sin_family = AF_INET;
s_addr.sin_port = htons(atoi(socketMes->port)); //将主机字节序的端口号转换为网络字节序
inet_aton(socketMes->ipAddress,&(s_addr.sin_addr)); //转换ip地址为网络字节序
bind(s_fd,(struct sockaddr *)&s_addr,sizeof(struct sockaddr_in)); //绑定相关的网络信息,如ip地址和端口号
//3.listen
listen(s_fd,10);//监听,可连接10个客户端
printf("socket Server listen success......\n");
socketMes->s_fd = s_fd;
return s_fd;
}
struct InputCommander socketControl = {
.commandName = "socketServer",
.command = {0},
.port = "8090",
.ipAddress = "192.168.31.227",
.Init = socketInit,
.getCommand = socketGetCommand,
.log = {0},
.next = NULL,
};
struct InputCommander *addSocketToCommandLink(struct InputCommander *phead)
{
if(phead == NULL){
return &socketControl;
}else{
socketControl.next=phead;
phead = &socketControl;
return phead;
}
}