/* fsm driver routine-1, this procedure might be called from arbitrary context */ LOCAL void peer_event(int code, void * e1, int e2,int e3,int e4) { int c; ke_toggle_flag(FKERN_LED_BUSB); switch(code){ case HSE_PEER_COLLISION: c=peer_lock(); set_state(hsp_s_collision); peer_unlock(c); break; case HSE_PEER_RX: g_kernel.peer->lastMsgTime = ke_get_time(); if(e2 < sizeof(struct peer_cmd_t)){ return; } peer_rx_event((struct peer_cmd_t*)e1,e2); break; case HSE_PEER_STATUS_BROADCAST: c=peer_lock(); /*reset watchdog*/ g_kernel.peer->lastMsgTime=ke_get_time(); #ifdef __VXWORKS__ memcpy(g_kernel.peer->peerAddress,((struct ether_header*)e1)->ether_shost,6); #endif g_kernel.peer_status = *((struct kstatus_t*)e2); if(kernelState == KERN_S_RUNNING && peerState==KERN_S_RUNNING){ ki_log(&g_kernel, F8_IOBUS_COLLISION,0,0,0); set_state(hsp_s_collision); } peer_unlock(c); break; } }
static void module_schat_init(module_manager_t manager){ module_schat_instance = r_calloc(1,sizeof(struct module_schat_st)); module_schat_instance->module_manager = manager; pthread_mutex_init(&module_schat_instance->lock,NULL); pthread_cond_init(&module_schat_instance->cond,NULL); module_schat_instance->fd = memcacheq_init(manager->config->memcacheq_server, manager->config->memcacheq_port); ki_log(module_schat_instance->fd <= 0, "[ki_dispatcher] : memcacheq_init in schat module init procedure failed!\n"); module_schat_instance->status = status_none; module_schat_instance->is_continue = true; module_schat_instance->module = module_manager_get_module(module_schat_instance->module_manager, module_flag_single_chat); }
static void* pthread_run_push(void* arg){ module_schat_t imserver = (module_schat_t)module_schat_instance; imserver->push_socket = zmq_socket(imserver->module_manager->zmq_context,ZMQ_REQ); int temps = zmq_connect(imserver->push_socket,imserver->module_manager->config->schat_push_ip_addr); ki_log(temps != 0, "[ki_dispatcher] : schat thread connect zmq failed!\n"); char temp[50] = ""; // get the memcache data while(imserver->is_continue){ int len = 0; #ifdef DEBUG fprintf(stderr, "[ki_dispatcher] : schat thread start to get the topic:%s msg from memcacheq \n", imserver->module_manager->config->schat_topic); #endif int s = memcacheq_get(imserver->fd,imserver->module_manager->config->schat_topic, (char**)&imserver->push_buf,&len); // 1 for success if(s == 1){ #ifdef DEBUG fprintf(stderr, "[ki_dispatcher] : schat thread get the topic:%s msg from memcacheq success, the data:%s\n", imserver->module_manager->config->schat_topic,imserver->push_buf); #endif // 1. process data imserver->push_buf[len+1] = '\0'; module_t imserver_module = module_schat_instance->module; if(imserver_module != NULL){ imserver_module->module_push_process(imserver->push_buf); } // 2. push the data to zmq int fs = zmq_send(imserver->push_socket,imserver->push_buf,len,0); if(fs != len){ ki_log(fs != len, "zmq_send failed fs != len in schat's pthread_run_push pthread!\n"); } int sf = zmq_recv(imserver->push_socket, imserver->pull_buf, schat_buf_size, 0); if(sf <= 0){ ki_log(sf <= 0, "zmq_recv failed sf <= 0 in schat's pthread_run_push pthread!\n"); } // 3. get the data and push to memcacheq imserver->pull_buf[sf + 1] = '\0'; if (imserver_module != NULL){ imserver_module->module_pull_process(imserver->pull_buf); } #ifdef DEBUG fprintf(stderr, "[ki_dispatcher] : schat thread start to set the topic:%s msg to memcacheq , the data:%s\n", imserver->module_manager->config->imserver_ip,imserver->pull_buf); #endif s = memcacheq_set(imserver->fd, imserver->module_manager->config->imserver_ip, imserver->pull_buf, sf); if (s <= 0){ ki_log(s <= 0, "memcacheq_set failed s <= 0 in schat's pthread_run_push pthread!\n"); } #ifdef DEBUG fprintf(stderr, "[ki_dispatcher] : schat thread set the topic:%s msg to memcacheq success\n", imserver->module_manager->config->imserver_ip); #endif // 4.notify other module to get data from memcache queue module_manager_notify(imserver->module_manager, module_flag_imserver); } // s for nothing , so wait else if(s == 0){ #ifdef DEBUG fprintf(stderr, "[ki_dispatcher] : schat thread get the topic:%s nothing and will wait\n", imserver->module_manager->config->schat_topic); #endif pthread_mutex_lock(&imserver->lock); pthread_cond_wait(&imserver->cond,&imserver->lock); pthread_mutex_unlock(&imserver->lock); } // error to assert else { fprintf(stderr,"memcacheq pull data is error !\n"); assert(0); } } pthread_detach(pthread_self()); return NULL; }
static void module_schat_start(){ int s = 0; pthread_t push_pthread; s = pthread_create(&push_pthread,NULL,pthread_run_push,NULL); ki_log(s != 0, "[ki_dispatcher] : module_schat_start failed because of schat's pthread_run_push pthread \n"); }
/* standby_sync() - standby phase of the BPC */ LOCAL f8_status standby_sync() { int cookie; ktime_t t; f8_uint i, size; long size2; f8_status ret = F8_BUSY; f8_u8 st; static ktime_t syncTime; t = ke_get_time(); /* check automata */ cookie = peer_lock(); st = get_state(); switch(st){ case hsp_s_complete: size = 0; ke_toggle_flag(FKERN_LED_DBG1); syncTime=t; ke_set_flag(FKERN_LED_SYNCHRONIZED,1); for(i=0; i<KERN_NUM_SECTIONS; i++){ if(peerHdr.x_mem_sizes[i] != g_kernel.x_mem_sizes[i]){ ret = F8_VERSION_MISMATCH; set_state(hsp_s_idle); goto __done; } size += peerHdr.x_mem_sizes[i]; } size += sizeof(struct marshalled_timer_t) * peerHdr.timer_q_len + sizeof(struct marshalled_event_t) * peerHdr.event_q_len + peerHdr.i_mem_size; if(size + sizeof(struct kpeer_hdr_t) > F8_VOLATILE_MEM_SIZE){ ret = F8_LOW_MEMORY; set_state(hsp_s_idle); goto __done; } size2=sizeof(peerData); if(uncompress(peerData, &size2, peerDataZipped, peerHdr.zipped_data_len) != Z_OK){ ret=F8_INVALID_DATA; set_state(hsp_s_idle); break; } /* indicate how much memory we can use */ peerGuardian = peerData + size2; ki_load_volatile(&g_kernel); /* start another session */ //peer_flush(); set_state(hsp_s_idle); ret = F8_SUCCESS; peerCounters[1]++; break; case hsp_s_idle: break; case hsp_s_active: if(!ke_get_flag(FKERN_LED_SYNCHRONIZED)){ //peer_flush(); set_state(hsp_s_idle); } break; default: /* last error */ peerCounters[5]++; peerCounters[3] = st; //peer_flush(); set_state(hsp_s_idle); break; } __done: peer_unlock(cookie); if(t>syncTime+ki_get_primary_life()*5) ke_set_flag(FKERN_LED_SYNCHRONIZED,0); if(!ke_get_flag(FKERN_LED_SOFT_STOP)){ if(t > g_kernel.peer->lastMsgTime + ki_get_primary_life()|| (peerState!=KERN_S_RUNNING && !ke_get_peer_flag(FKERN_LED_SOFT_LOCK)) ){ /* primary failure detected */ /* try switch to primary state */ if(g_kernel.peer_status.prog_id == g_kernel.status.prog_id && ke_get_flag(FKERN_LED_SYNCHRONIZED)){ /* adjust kernel clock */ kern_time_bias += hspTimeOffset; ki_log(&g_kernel, F8_PRIMARY_FAILURE,0,0,0); ki_switch_to(KERN_S_ARBITRATING); set_state(hsp_s_idle); } /* reset peer to unknown state */ memset(&g_kernel.peer_status, 0, sizeof g_kernel.peer_status); } } return ret; }