//////////////////////////////////////////////////////////////////////////////// /// 共同资源模块 /// /// /// 包含设备层和代理层共同资源 /// @file comm_queue.c /// @author gkl /// @date 2017-06-15创建 /// @version v0.1 //////////////////////////////////////////////////////////////////////////////// #include "pdebug.h" #include "includes.h" #include "app_cfg.h" #include "uart_recv.h" #include "comm_resource.h" #include "pdebug.h" /// 最大消息数 #define MAX_MESSAGES 6 /// 上行消息队列指针,device->agent OS_EVENT *p_queue_up; /// 上行消息指针数组 void *queue_up_grp[MAX_MESSAGES]; /// 下行消息队列指针,agent->device OS_EVENT *p_queue_down; /// 下行消息指针数组 void *queue_down_grp[MAX_MESSAGES]; BSP_OS_SEM sem_hy_collect_o2; BSP_OS_SEM sem_hy_collect_co; BSP_OS_SEM sem_hy_collect_water; BSP_OS_SEM sem_hy_collect_current; BSP_OS_SEM sem_hy_collect_well; BSP_OS_SEM sem_hy_collect_ch4; BSP_OS_SEM sem_hy_collect_h2s; BSP_OS_SEM sem_hy_collect_temphumi; BSP_OS_SEM rs485_mutex;//485操作共享资源锁 static u_int8_t rs485_in_buff[RS485_BUFF_SIZE]; /// 初始化rs485串口相关GPIO /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-06-07 void init_rs485_gpio() { /* //weather-power drv_gpio_open(PORTD,9,OUTPUT,1); J26_POWER_OFF; //RD485 drv_gpio_open(PORTC,9,OUTPUT,1); RD485_RECEIVE; //CS485 drv_gpio_open(PORTC,5,OUTPUT,1); CS_RS485_BAT_DISABLE; drv_gpio_open(PORTC,6,OUTPUT,1); CS_485_J27_DISABLE; drv_gpio_open(PORTC,7,OUTPUT,1); CS_485_J28_DISABLE; drv_gpio_open(PORTC,8,OUTPUT,1); CS_485_J26_DISABLE; */ drv_gpio_open(PORTD,11,OUTPUT,1); SENSOR_POWER_OFF; //RD485 drv_gpio_open(PORTC,5,OUTPUT,1); RD485_RECEIVE; } /// 485发送数据 /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-05-31 void send_rs485_data(device_handle dev,const void *data, int len) { RD485_SEND; BSP_OS_TimeDlyMs(150); uart_dev_write(dev,(u_int8_t *)data,len); BSP_OS_TimeDlyMs(3); RD485_RECEIVE; } /// 初始化rs485串口设备 /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-05-31 void init_rs485_uart() { g_rs485_uart_handle = uart_dev_init(RS485_INDEX, RS485_BAUD,rs485_in_buff, sizeof(rs485_in_buff)); BSP_OS_SemCreate(&rs485_mutex,1u,"rs485_mutex"); } void send_up_fault_queue_pack(char *type,u_int8_t code,char *fault_message) { char send_buff[PACK_BUFF_SIZE]; memset(send_buff,0,sizeof(send_buff)); sprintf(send_buff,"%s,%d,%s",type,code,fault_message); if(memcmp(type,"o2",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send o2 fault pack: %s\n\r",send_buff); } if(memcmp(type,"water",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send water fault pack: %s\n\r",send_buff); } if(memcmp(type,"current",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send current fault pack: %s\n\r",send_buff); } if(memcmp(type,"co",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send co fault pack: %s\n\r",send_buff); } if(memcmp(type,"h2s",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send h2s fault pack: %s\n\r",send_buff); } if(memcmp(type,"ch4",sizeof(type)) == 0) { pdebug(DEBUG_LEVEL_ERROR,"send ch4 fault pack: %s\n\r",send_buff); } OSQPostOpt(p_queue_up,send_buff, OS_POST_OPT_BROADCAST); } /// 创建信号量 /// /// 用于设备层直接通信 /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-05-31 static void sem_create_device_module() { #if CFG_MODULE_O2 if (!BSP_OS_SemCreate(&sem_hy_collect_o2,0u,"sem_hy_collect_o2")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_o2 failed\n\r"); } #endif #if CFG_MODULE_CO if (!BSP_OS_SemCreate(&sem_hy_collect_co,0u,"sem_hy_collect_co")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_co failed\n\r"); } #endif #if CFG_MODULE_WATER if (!BSP_OS_SemCreate(&sem_hy_collect_water,0u,"sem_hy_collect_water")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_water failed\n\r"); } #endif #if CFG_MODULE_WELL if (!BSP_OS_SemCreate(&sem_hy_collect_well,0u,"sem_hy_collect_well")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_well failed\n\r"); } #endif #if CFG_MODULE_CURRENT if (!BSP_OS_SemCreate(&sem_hy_collect_current,0u,"sem_hy_collect_current")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_current failed\n\r"); } #endif #if CFG_MODULE_CH4 if (!BSP_OS_SemCreate(&sem_hy_collect_ch4,0u,"sem_hy_collect_ch4")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_ch4 failed\n\r"); } #endif #if CFG_MODULE_H2S if (!BSP_OS_SemCreate(&sem_hy_collect_h2s,0u,"sem_hy_collect_h2s")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_h2s failed\n\r"); } #endif #if CFG_MODULE_TEMPHUMI if (!BSP_OS_SemCreate(&sem_hy_collect_temphumi,0u,"sem_hy_collect_temphumi")) { pdebug(DEBUG_LEVEL_FATAL,"create sem_hy_collect_temphumi failed\n\r"); } #endif } /// 接收下行消息队列任务 /// /// 收到并解析消息队列,以信号量型式通知其他模块 /// 设备层使用 /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-05-31 static void task_listen_queue_down (void *p_arg) { p_arg = p_arg; char *s_recv_down; unsigned char err; char type[20]; char code[20]; char message[20]; while(1){ s_recv_down = OSQPend(p_queue_down,0,&err); //请求消息队列 if (err) { pdebug(DEBUG_LEVEL_ERROR,"recv queue down error: %s\n", err); }else { pdebug(DEBUG_LEVEL_INFO,"recv queue down messages: %s\n", s_recv_down); } sscanf(s_recv_down,"%[^,],%[^,],%s",type,code,message); if(memcmp("o2",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_o2); } } if(memcmp("co",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_co); } } if(memcmp("water",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_water); } } if(memcmp("current",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_current); } } if(memcmp("well",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_well); } } if(memcmp("ch4",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_ch4); } } if(memcmp("h2s",type,strlen(type)) == 0) { if(memcmp("get data",code,strlen(code)) == 0) { BSP_OS_SemPost(&sem_hy_collect_h2s); } } } } /// 创建接收下行消息队列任务 /// /// @param none /// @param none /// @return none /// @note 修改日志 /// jjj于2017-05-31 static OS_STK task_listen_queue_down_stk[TASK_LISTEN_QUEUE_DOWN_STK_SIZE]; static void task_create_listen_queue_down (void) { CPU_INT08U task_err; CPU_INT08U name_err; task_err = OSTaskCreateExt((void (*)(void *)) task_listen_queue_down, (void *) 0, (OS_STK *)&task_listen_queue_down_stk[TASK_LISTEN_QUEUE_DOWN_STK_SIZE - 1], (INT8U ) TASK_LISTEN_QUEUE_DOWN_PRIO, (INT16U ) TASK_LISTEN_QUEUE_DOWN_PRIO, (OS_STK *)&task_listen_queue_down_stk[0], (INT32U ) TASK_LISTEN_QUEUE_DOWN_STK_SIZE, (void *) 0, (INT16U )(OS_TASK_OPT_STK_CHK | OS_TASK_OPT_STK_CLR)); #if (OS_TASK_NAME_EN > 0) OSTaskNameSet(TASK_LISTEN_QUEUE_DOWN_PRIO, "task_listen_queue_down", &name_err); #endif if ((task_err == OS_ERR_NONE) && (name_err == OS_ERR_NONE)) { pdebug(DEBUG_LEVEL_INFO,"create task_listen_queue_down success...\n\r"); } else { pdebug(DEBUG_LEVEL_FATAL,"create task_listen_queue_down failed...\n\r"); } } /// 消息队列模块初始化 /// /// 创建上行、下行消息队列,创建设备层共享资源 /// @param none /// @param none /// @return none /// @note 修改日志 /// gkl与2017-06-02创建 void init_comm_queue_module() { pdebug(DEBUG_LEVEL_INFO,"init common queue module\n\r"); // 创建上行消息队列 pdebug(DEBUG_LEVEL_INFO,"create queue up\n\r"); p_queue_up = OSQCreate(&queue_up_grp[0], MAX_MESSAGES); // 创建下行消息队列 pdebug(DEBUG_LEVEL_INFO,"create queue down\n\r"); p_queue_down = OSQCreate(&queue_down_grp[0], MAX_MESSAGES); // 创建设备层通信用信号量 pdebug(DEBUG_LEVEL_INFO,"create sem device\n\r"); sem_create_device_module(); // 创建设备层模块,监听下行数据,并将解析结果告知其他设备层模块 pdebug(DEBUG_LEVEL_INFO,"create task listen queue down\n\r"); task_create_listen_queue_down(); pdebug(DEBUG_LEVEL_INFO,"init common queue module finished\n\r"); }