//------------------------------------------------------------------------------------- void Baseapp::createInNewSpace(Base* base, PyObject* cell) { ENTITY_ID id = base->getID(); std::string entityType = base->ob_type->tp_name; std::string strCellData = script::Pickler::pickle(base->getCellData()); uint32 cellDataLength = strCellData.length(); Mercury::Bundle bundle; bundle.newMessage(CellappmgrInterface::reqCreateInNewSpace); bundle << entityType; bundle << id; bundle << componentID_; bundle << cellDataLength; if(cellDataLength > 0) bundle.append(strCellData.data(), cellDataLength); Components::COMPONENTS& components = Components::getSingleton().getComponents(CELLAPPMGR_TYPE); Components::COMPONENTS::iterator iter = components.begin(); if(iter != components.end()) { bundle.send(this->getNetworkInterface(), (*iter).pChannel); return; } ERROR_MSG("Baseapp::createInNewSpace: not found cellappmgr.\n"); }
//------------------------------------------------------------------------------------- void Loginapp::onChannelDeregister(Mercury::Channel * pChannel) { // 如果是外部通道则处理 if(!pChannel->isInternal()) { const std::string& extra = pChannel->extra(); // 通知billing从队列中清除他的请求, 避免拥塞 if(extra.size() > 0) { Components::COMPONENTS& cts = Components::getSingleton().getComponents(DBMGR_TYPE); Components::ComponentInfos* dbmgrinfos = NULL; if(cts.size() > 0) dbmgrinfos = &(*cts.begin()); if(dbmgrinfos == NULL || dbmgrinfos->pChannel == NULL || dbmgrinfos->cid == 0) { } else { Mercury::Bundle bundle; bundle.newMessage(DbmgrInterface::eraseClientReq); bundle << extra; bundle.send(this->getNetworkInterface(), dbmgrinfos->pChannel); } } } ServerApp::onChannelDeregister(pChannel); }
//------------------------------------------------------------------------------------- void Loginapp::onReqCreateAccountResult(Mercury::Channel* pChannel, MemoryStream& s) { SERVER_ERROR_CODE failedcode; std::string accountName; std::string password; std::string retdatas = ""; s >> failedcode >> accountName >> password; s.readBlob(retdatas); DEBUG_MSG(boost::format("Loginapp::onReqCreateAccountResult: accountName=%1%, failedcode=%2%.\n") % accountName.c_str() % failedcode); PendingLoginMgr::PLInfos* ptinfos = pendingCreateMgr_.remove(accountName); if(ptinfos == NULL) return; Mercury::Channel* pClientChannel = this->getNetworkInterface().findChannel(ptinfos->addr); if(pClientChannel == NULL) return; pClientChannel->extra(""); Mercury::Bundle bundle; bundle.newMessage(ClientInterface::onCreateAccountResult); bundle << failedcode; bundle.appendBlob(retdatas); bundle.send(this->getNetworkInterface(), pClientChannel); SAFE_RELEASE(ptinfos); }
//------------------------------------------------------------------------------------- void ServerApp::queryWatcher(Mercury::Channel* pChannel, MemoryStream& s) { AUTO_SCOPED_PROFILE("watchers"); std::string path; s >> path; MemoryStream::SmartPoolObjectPtr readStreamPtr = MemoryStream::createSmartPoolObj(); WatcherPaths::root().readWatchers(path, readStreamPtr.get()->get()); MemoryStream::SmartPoolObjectPtr readStreamPtr1 = MemoryStream::createSmartPoolObj(); WatcherPaths::root().readChildPaths(path, path, readStreamPtr1.get()->get()); Mercury::Bundle bundle; ConsoleInterface::ConsoleWatcherCBMessageHandler msgHandler; bundle.newMessage(msgHandler); uint8 type = 0; bundle << type; bundle.append(readStreamPtr.get()->get()); bundle.send(getNetworkInterface(), pChannel); Mercury::Bundle bundle1; bundle1.newMessage(msgHandler); type = 1; bundle1 << type; bundle1.append(readStreamPtr1.get()->get()); bundle1.send(getNetworkInterface(), pChannel); }
//------------------------------------------------------------------------------------- void Base::reqTeleportOther(Mercury::Channel* pChannel, ENTITY_ID reqTeleportEntityID, COMPONENT_ID reqTeleportEntityCellAppID, COMPONENT_ID reqTeleportEntityBaseAppID) { DEBUG_MSG("Base::reqTeleportOther: reqTeleportEntityID=%d, reqTeleportEntityCellAppID=%"PRAppID".\n", reqTeleportEntityID, reqTeleportEntityCellAppID); if(this->getCellMailbox() == NULL || this->getCellMailbox()->getChannel() == NULL) { ERROR_MSG("%s::reqTeleportOther: %d, teleport is error, cellMailbox is NULL, reqTeleportEntityID, reqTeleportEntityCellAppID=%"PRAppID".\n", this->getScriptName(), this->getID(), reqTeleportEntityID, reqTeleportEntityCellAppID); return; } Components::ComponentInfos* cinfos = Components::getSingleton().findComponent(reqTeleportEntityCellAppID); if(cinfos == NULL || cinfos->pChannel == NULL) { ERROR_MSG("%s::reqTeleportOther: %d, teleport is error, not found cellapp, reqTeleportEntityID, reqTeleportEntityCellAppID=%"PRAppID".\n", this->getScriptName(), this->getID(), reqTeleportEntityID, reqTeleportEntityCellAppID); return; } Mercury::Bundle bundle; bundle.newMessage(CellappInterface::teleportFromBaseapp); bundle << reqTeleportEntityID; CellappInterface::teleportFromBaseappArgs3::staticAddToBundle(bundle, this->getCellMailbox()->getComponentID(), this->getID(), reqTeleportEntityBaseAppID); bundle.send(Baseapp::getSingleton().getNetworkInterface(), cinfos->pChannel); }
void EntityApp<E>::onExecScriptCommand(Mercury::Channel* pChannel, KBEngine::MemoryStream& s) { std::string cmd; s.readBlob(cmd); PyObject* pycmd = PyUnicode_DecodeUTF8(cmd.data(), cmd.size(), NULL); if(pycmd == NULL) { SCRIPT_ERROR_CHECK(); return; } DEBUG_MSG(boost::format("EntityApp::onExecScriptCommand: size(%1%), command=%2%.\n") % cmd.size() % cmd); std::string retbuf = ""; PyObject* pycmd1 = PyUnicode_AsEncodedString(pycmd, "utf-8", NULL); if(script_.run_simpleString(PyBytes_AsString(pycmd1), &retbuf) == 0) { // 将结果返回给客户端 Mercury::Bundle bundle; ConsoleInterface::ConsoleExecCommandCBMessageHandler msgHandler; bundle.newMessage(msgHandler); ConsoleInterface::ConsoleExecCommandCBMessageHandlerArgs1::staticAddToBundle(bundle, retbuf); bundle.send(this->getNetworkInterface(), pChannel); } Py_DECREF(pycmd); Py_DECREF(pycmd1); }
//------------------------------------------------------------------------------------- void TelnetHandler::processPythonCommand(std::string command) { if(pTelnetServer_->pScript() == NULL || command.size() == 0) return; command += "\n"; PyObject* pycmd = PyUnicode_DecodeUTF8(command.data(), command.size(), NULL); if(pycmd == NULL) { SCRIPT_ERROR_CHECK(); return; } DEBUG_MSG(boost::format("TelnetHandler::processPythonCommand: size(%1%), command=%2%.\n") % command.size() % command); std::string retbuf = ""; PyObject* pycmd1 = PyUnicode_AsEncodedString(pycmd, "utf-8", NULL); pTelnetServer_->pScript()->run_simpleString(PyBytes_AsString(pycmd1), &retbuf); if(retbuf.size() > 0) { // 将结果返回给客户端 Mercury::Bundle bundle; bundle << retbuf; bundle.send(*pEndPoint_); sendEnter(); } Py_DECREF(pycmd); Py_DECREF(pycmd1); }
//------------------------------------------------------------------------------------- bool ClientObject::loginGateWay() { // 请求登录网关 Mercury::Bundle bundle; bundle.newMessage(BaseappInterface::loginGateway); bundle << name_; bundle << password_; bundle.send(*pChannel_->endpoint()); return true; }
//------------------------------------------------------------------------------------- bool ClientObject::createAccount() { // 创建账号 Mercury::Bundle bundle; bundle.newMessage(LoginappInterface::reqCreateAccount); bundle << name_; bundle << password_; bundle.send(*pChannel_->endpoint()); return true; }
//------------------------------------------------------------------------------------- void Loginapp::reqAccountResetPassword(Mercury::Channel* pChannel, std::string& accountName) { AUTO_SCOPED_PROFILE("reqAccountResetPassword"); accountName = KBEngine::strutil::kbe_trim(accountName); INFO_MSG(boost::format("Loginapp::reqAccountResetPassword: accountName(%1%)\n") % accountName); Components::COMPONENTS& cts = Components::getSingleton().getComponents(DBMGR_TYPE); Components::ComponentInfos* dbmgrinfos = NULL; if(cts.size() > 0) dbmgrinfos = &(*cts.begin()); if(dbmgrinfos == NULL || dbmgrinfos->pChannel == NULL || dbmgrinfos->cid == 0) { ERROR_MSG(boost::format("Loginapp::_createAccount: create(%1%), not found dbmgr!\n") % accountName); Mercury::Bundle bundle; bundle.newMessage(ClientInterface::onReqAccountResetPasswordCB); SERVER_ERROR_CODE retcode = SERVER_ERR_SRV_NO_READY; bundle << retcode; bundle.send(this->getNetworkInterface(), pChannel); return; } { Mercury::Bundle bundle; bundle.newMessage(DbmgrInterface::accountReqResetPassword); bundle << accountName; bundle.send(this->getNetworkInterface(), dbmgrinfos->pChannel); } { Mercury::Bundle bundle; bundle.newMessage(ClientInterface::onReqAccountResetPasswordCB); SERVER_ERROR_CODE retcode = SERVER_SUCCESS; bundle << retcode; bundle.send(this->getNetworkInterface(), pChannel); } }
//------------------------------------------------------------------------------------- void Cellappmgr::forwardMessage(Mercury::Channel* pChannel, MemoryStream& s) { COMPONENT_ID sender_componentID, forward_componentID; s >> sender_componentID >> forward_componentID; Components::ComponentInfos* cinfos = Components::getSingleton().findComponent(forward_componentID); KBE_ASSERT(cinfos != NULL && cinfos->pChannel != NULL); Mercury::Bundle bundle; bundle.append((char*)s.data() + s.rpos(), s.opsize()); bundle.send(this->getNetworkInterface(), cinfos->pChannel); s.opfini(); }
void EntityApp<E>::onExecScriptCommand(Mercury::Channel* pChannel, std::string& strcommand) { DEBUG_MSG("EntityApp::onExecScriptCommand: command size(%d).\n", strcommand.size()); std::string retbuf = ""; if(script_.run_simpleString(strcommand, &retbuf) == 0) { // 将结果返回给客户端 Mercury::Bundle bundle; ConsoleInterface::ConsoleExecCommandCBMessageHandler msgHandler; bundle.newMessage(msgHandler); ConsoleInterface::ConsoleExecCommandCBMessageHandlerArgs1::staticAddToBundle(bundle, retbuf); bundle.send(this->getNetworkInterface(), pChannel); } }
void CLogWindow::OnBnClickedButton1() { // TODO: Add your control notification handler code here // 请求服务器拉取日志 CguiconsoleDlg* dlg = static_cast<CguiconsoleDlg*>(theApp.m_pMainWnd); HTREEITEM item = dlg->hasCheckApp(MESSAGELOG_TYPE); if(item == NULL) { ::AfxMessageBox(L"messagelog no select!"); return; } Mercury::Address addr = dlg->getTreeItemAddr(item); Mercury::Channel* pChannel = dlg->networkInterface().findChannel(addr); if(pChannel == NULL) { ::AfxMessageBox(L"messagelog is error!"); return; } Mercury::Bundle bundle; bundle.newMessage(MessagelogInterface::registerLogWatcher); bundle << getSelLogTypes(); CString apporder; m_appIDEdit.GetWindowTextW(apporder); char* cs = KBEngine::strutil::wchar2char(apporder.GetBuffer(0)); COMPONENT_ORDER order = atoi(cs); free(cs); bundle << order; int8 count = 0; std::vector<KBEngine::COMPONENT_TYPE> vec = getSelComponents(); count = vec.size(); bundle << count; std::vector<KBEngine::COMPONENT_TYPE>::iterator iter = vec.begin(); for(; iter != vec.end(); iter++) { bundle << (*iter); } bundle.send(dlg->networkInterface(), pChannel); }
//------------------------------------------------------------------------------------- bool Base::destroyCellEntity(void) { if(isDestroyed()) { return false; } if(cellMailbox_ == NULL || cellMailbox_->getChannel() == NULL) return false; Mercury::Bundle bundle; bundle.newMessage(CellappInterface::onDestroyCellEntityFromBaseapp); bundle << id_; bundle.send(Baseapp::getSingleton().getNetworkInterface(), cellMailbox_->getChannel()); return true; }
//------------------------------------------------------------------------------------- void ClientObject::sendTick() { // 向服务器发送tick uint64 check = uint64( Mercury::g_channelExternalTimeout * stampsPerSecond() ) / 2; if (timestamp() - lastSentActiveTickTime_ > check) { lastSentActiveTickTime_ = timestamp(); Mercury::Bundle bundle; if(connectedGateway_) bundle.newMessage(BaseappInterface::onClientActiveTick); else bundle.newMessage(LoginappInterface::onClientActiveTick); bundle.send(*pChannel_->endpoint()); } }
//------------------------------------------------------------------------------------- void EntityIDClient::onAlloc(void) { if(hasReqServerAlloc() || getSize() > ID_ENOUGH_LIMIT || idList_.size() > 0) return; Mercury::Bundle bundle; bundle.newMessage(DbmgrInterface::onReqAllocEntityID); DbmgrInterface::onReqAllocEntityIDArgs2::staticAddToBundle(bundle, pApp_->componentType(), pApp_->componentID()); Components::COMPONENTS cts = Components::getSingleton().getComponents(DBMGR_TYPE); KBE_ASSERT(cts.size() > 0); Components::ComponentInfos* cinfos = &(*cts.begin()); KBE_ASSERT(cinfos->pChannel != NULL); bundle.send(pApp_->getNetworkInterface(), cinfos->pChannel); ERROR_MSG("EntityIDClient::onAlloc: not enough(%d) entityIDs!\n", ID_ENOUGH_LIMIT); }
//------------------------------------------------------------------------------------- bool EntityMailboxAbstract::postMail(Mercury::Bundle& bundle) { KBE_ASSERT(Components::getSingleton().pNetworkInterface() != NULL); Mercury::Channel* pChannel = getChannel(); if(pChannel && !pChannel->isDead()) { bundle.send(*Components::getSingleton().pNetworkInterface(), pChannel); return true; } else { ERROR_MSG("EntityMailboxAbstract::postMail: invalid channel(%s)!\n", addr_.c_str()); } return false; }
//------------------------------------------------------------------------------------- void Baseapp::onGetEntityAppFromDbmgr(Mercury::Channel* pChannel, int32 uid, std::string& username, int8 componentType, uint64 componentID, uint32 intaddr, uint16 intport, uint32 extaddr, uint16 extport) { if(pChannel->isExternal()) return; EntityApp<Base>::onRegisterNewApp(pChannel, uid, username, componentType, componentID, intaddr, intport, extaddr, extport); KBEngine::COMPONENT_TYPE tcomponentType = (KBEngine::COMPONENT_TYPE)componentType; Components::COMPONENTS cts = Componentbridge::getComponents().getComponents(DBMGR_TYPE); KBE_ASSERT(cts.size() >= 1); Components::ComponentInfos* cinfos = Componentbridge::getComponents().findComponent(tcomponentType, uid, componentID); cinfos->pChannel = NULL; int ret = Components::getSingleton().connectComponent(tcomponentType, uid, componentID); KBE_ASSERT(ret != -1); Mercury::Bundle bundle; switch(tcomponentType) { case BASEAPP_TYPE: bundle.newMessage(BaseappInterface::onRegisterNewApp); BaseappInterface::onRegisterNewAppArgs8::staticAddToBundle(bundle, getUserUID(), getUsername(), BASEAPP_TYPE, componentID_, this->getNetworkInterface().intaddr().ip, this->getNetworkInterface().intaddr().port, this->getNetworkInterface().extaddr().ip, this->getNetworkInterface().extaddr().port); break; case CELLAPP_TYPE: bundle.newMessage(CellappInterface::onRegisterNewApp); CellappInterface::onRegisterNewAppArgs8::staticAddToBundle(bundle, getUserUID(), getUsername(), BASEAPP_TYPE, componentID_, this->getNetworkInterface().intaddr().ip, this->getNetworkInterface().intaddr().port, this->getNetworkInterface().extaddr().ip, this->getNetworkInterface().extaddr().port); break; default: KBE_ASSERT(false && "no support!\n"); break; }; bundle.send(this->getNetworkInterface(), cinfos->pChannel); }
//------------------------------------------------------------------------------------- bool ClientObject::login() { if(error_ != C_ERROR_NONE) return false; Mercury::Bundle bundle; std::string bindatas = "bots client"; // 提交账号密码请求登录 bundle.newMessage(LoginappInterface::login); CLIENT_CTYPE tclient = CLIENT_TYPE_BOTS; bundle << tclient; bundle.appendBlob(bindatas); bundle << name_; bundle << password_; bundle.send(*pChannel_->endpoint()); return true; }
//------------------------------------------------------------------------------------- void Machine::onFindInterfaceAddr(Mercury::Channel* pChannel, int32 uid, std::string& username, int8 componentType, int8 findComponentType, uint32 finderAddr, uint16 finderRecvPort) { INFO_MSG("Machine::onFindInterfaceAddr: uid:%d, username:%s, componentType:%s, " "find:%s, finderaddr:%s, finderRecvPort:%u.\n", uid, username.c_str(), COMPONENT_NAME_EX((COMPONENT_TYPE)componentType), COMPONENT_NAME_EX((COMPONENT_TYPE)findComponentType), inet_ntoa((struct in_addr&)finderAddr), ntohs(finderRecvPort)); Mercury::EndPoint ep; ep.socket(SOCK_DGRAM); if (!ep.good()) { ERROR_MSG("Machine::onFindInterfaceAddr: Failed to create socket.\n"); return; } const Components::ComponentInfos* pinfos = Componentbridge::getComponents().findComponent((KBEngine::COMPONENT_TYPE)findComponentType, uid, 0); Mercury::Bundle bundle; if(pinfos == NULL) { WARNING_MSG("Machine::onFindInterfaceAddr: %s not found %s.\n", COMPONENT_NAME_EX((COMPONENT_TYPE)componentType), COMPONENT_NAME_EX((COMPONENT_TYPE)findComponentType)); MachineInterface::onBroadcastInterfaceArgs8::staticAddToBundle(bundle, 0, "", UNKNOWN_COMPONENT_TYPE, 0, 0, 0, 0, 0); } else MachineInterface::onBroadcastInterfaceArgs8::staticAddToBundle(bundle, pinfos->uid, pinfos->username, findComponentType, pinfos->cid, pinfos->pIntAddr->ip, pinfos->pIntAddr->port, pinfos->pExtAddr->ip, pinfos->pExtAddr->port); if(finderAddr != 0 && finderRecvPort != 0) bundle.sendto(ep, finderRecvPort, finderAddr); else bundle.send(this->getNetworkInterface(), pChannel); }
//------------------------------------------------------------------------------------- void Loginapp::onReqCreateMailAccountResult(Mercury::Channel* pChannel, MemoryStream& s) { SERVER_ERROR_CODE failedcode; std::string accountName; std::string password; std::string retdatas = ""; s >> failedcode >> accountName >> password; s.readBlob(retdatas); DEBUG_MSG(boost::format("Loginapp::onReqCreateMailAccountResult: accountName=%1%, failedcode=%2%.\n") % accountName.c_str() % failedcode); if(failedcode == SERVER_SUCCESS) { threadPool_.addTask(new SendActivateEMailTask(accountName, retdatas, g_kbeSrvConfig.getLoginApp().http_cbhost, g_kbeSrvConfig.getLoginApp().http_cbport)); } PendingLoginMgr::PLInfos* ptinfos = pendingCreateMgr_.remove(accountName); if(ptinfos == NULL) return; Mercury::Channel* pClientChannel = this->getNetworkInterface().findChannel(ptinfos->addr); if(pClientChannel == NULL) return; pClientChannel->extra(""); retdatas = ""; Mercury::Bundle bundle; bundle.newMessage(ClientInterface::onCreateAccountResult); bundle << failedcode; bundle.appendBlob(retdatas); bundle.send(this->getNetworkInterface(), pClientChannel); SAFE_RELEASE(ptinfos); }
//------------------------------------------------------------------------------------- void Base::onCellWriteToDBCompleted() { PyObject* pyResult = PyObject_CallMethod(this, const_cast<char*>("onPreArchive"), const_cast<char*>("")); if(pyResult != NULL) Py_DECREF(pyResult); else PyErr_PrintEx(0); hasDB(true); onWriteToDB(); isArchiveing_ = false; MemoryStream* s = MemoryStream::ObjPool().createObject(); addPersistentsDataToStream(ED_FLAG_ALL, s); Components::COMPONENTS cts = Components::getSingleton().getComponents(DBMGR_TYPE); Components::ComponentInfos* dbmgrinfos = NULL; if(cts.size() > 0) dbmgrinfos = &(*cts.begin()); if(dbmgrinfos == NULL || dbmgrinfos->pChannel == NULL || dbmgrinfos->cid == 0) { ERROR_MSG("Base::onCellWriteToDBCompleted: not found dbmgr!\n"); return; } Mercury::Bundle bundle; bundle.newMessage(DbmgrInterface::writeEntity); bundle << this->getID(); bundle << this->getScriptModule()->getUType(); bundle.append(*s); bundle.send(Baseapp::getSingleton().getNetworkInterface(), dbmgrinfos->pChannel); MemoryStream::ObjPool().reclaimObject(s); }
//------------------------------------------------------------------------------------- void Baseapp::createCellEntity(EntityMailboxAbstract* createToCellMailbox, Base* base) { if(base->getCellMailbox()) { ERROR_MSG("Baseapp::createCellEntity: %s %d has a cell!\n", base->getScriptName(), base->getID()); return; } Mercury::Bundle bundle; bundle.newMessage(CellappInterface::onCreateCellEntityFromBaseapp); ENTITY_ID id = base->getID(); std::string entityType = base->ob_type->tp_name; std::string strCellData = script::Pickler::pickle(base->getCellData()); uint32 cellDataLength = strCellData.length(); EntityMailbox* clientMailbox = base->getClientMailbox(); bool hasClient = (clientMailbox != NULL); bundle << createToCellMailbox->getID(); // 在这个mailbox所在的cellspace上创建 bundle << entityType; bundle << id; bundle << componentID_; bundle << hasClient; bundle << cellDataLength; if(cellDataLength > 0) bundle.append(strCellData.data(), cellDataLength); if(createToCellMailbox->getChannel() == NULL) { ERROR_MSG("Baseapp::createCellEntity: not found cellapp(createToCellMailbox:componentID=%"PRAppID", entityID=%d), create is error!\n", createToCellMailbox->getComponentID(), createToCellMailbox->getID()); base->onCreateCellFailure(); return; } bundle.send(this->getNetworkInterface(), createToCellMailbox->getChannel()); }
//------------------------------------------------------------------------------------- void Baseapp::createBaseAnywhere(const char* entityType, PyObject* params, PyObject* pyCallback) { std::string strInitData = ""; uint32 initDataLength = 0; if(params != NULL && PyDict_Check(params)) { strInitData = script::Pickler::pickle(params); initDataLength = strInitData.length(); } Mercury::Bundle bundle; bundle.newMessage(BaseappmgrInterface::reqCreateBaseAnywhere); bundle << entityType; bundle << initDataLength; if(initDataLength > 0) bundle.append(strInitData.data(), initDataLength); bundle << componentID_; CALLBACK_ID callbackID = 0; if(pyCallback != NULL) { callbackID = callbackMgr().save(pyCallback); } bundle << callbackID; Components::COMPONENTS& components = Components::getSingleton().getComponents(BASEAPPMGR_TYPE); Components::COMPONENTS::iterator iter = components.begin(); if(iter != components.end()) { bundle.send(this->getNetworkInterface(), (*iter).pChannel); return; } ERROR_MSG("Baseapp::createBaseAnywhere: not found baseappmgr.\n"); }
//------------------------------------------------------------------------------------- void ServerApp::handleTimeout(TimerHandle, void * arg) { switch (reinterpret_cast<uintptr>(arg)) { case TIMEOUT_ACTIVE_TICK: { int8 findComponentTypes[] = {BASEAPPMGR_TYPE, CELLAPPMGR_TYPE, DBMGR_TYPE, CELLAPP_TYPE, BASEAPP_TYPE, LOGINAPP_TYPE, MESSAGELOG_TYPE, RESOURCEMGR_TYPE, UNKNOWN_COMPONENT_TYPE }; int ifind = 0; while(findComponentTypes[ifind] != UNKNOWN_COMPONENT_TYPE) { COMPONENT_TYPE componentType = (COMPONENT_TYPE)findComponentTypes[ifind]; Components::COMPONENTS& components = Components::getSingleton().getComponents(componentType); Components::COMPONENTS::iterator iter = components.begin(); for(; iter != components.end(); iter++) { Mercury::Bundle bundle; COMMON_MERCURY_MESSAGE(componentType, bundle, onAppActiveTick); bundle << g_componentType; bundle << componentID_; if((*iter).pChannel != NULL) bundle.send(getNetworkInterface(), (*iter).pChannel); } ifind++; } break; } default: break; } }
//------------------------------------------------------------------------------------- void LogWatcher::onMessage(uint32 logtype, COMPONENT_TYPE componentType, COMPONENT_ID componentID, COMPONENT_ORDER componentOrder, int64 tm, GAME_TIME kbetime, const std::string& str, const std::stringstream& sstr) { if(!VALID_COMPONENT(componentType) || componentBitmap_[componentType] == 0) return; if((logtypes_ & logtype) <= 0) return; if(appOrder_ > 0 && appOrder_ != componentOrder) return; Mercury::Channel* pChannel = Messagelog::getSingleton().getNetworkInterface().findChannel(addr_); if(pChannel == NULL) return; Mercury::Bundle bundle; ConsoleInterface::ConsoleLogMessageHandler msgHandler; bundle.newMessage(msgHandler); bundle << sstr.str().c_str(); bundle.send(Messagelog::getSingleton().getNetworkInterface(), pChannel); }
//------------------------------------------------------------------------------------- void Baseapp::executeRawDatabaseCommand(const char* datas, uint32 size, PyObject* pycallback) { if(datas == NULL) { ERROR_MSG("Baseapp::executeRawDatabaseCommand: execute is error!\n"); return; } Components::COMPONENTS cts = Components::getSingleton().getComponents(DBMGR_TYPE); Components::ComponentInfos* dbmgrinfos = NULL; if(cts.size() > 0) dbmgrinfos = &(*cts.begin()); if(dbmgrinfos == NULL || dbmgrinfos->pChannel == NULL || dbmgrinfos->cid == 0) { ERROR_MSG("Baseapp::executeRawDatabaseCommand: not found dbmgr!\n"); return; } DEBUG_MSG("KBEngine::executeRawDatabaseCommand:%s.\n", datas); Mercury::Bundle bundle; bundle.newMessage(DbmgrInterface::executeRawDatabaseCommand); bundle << componentID_ << componentType_; CALLBACK_ID callbackID = 0; if(pycallback && PyCallable_Check(pycallback)) callbackID = callbackMgr().save(pycallback); bundle << callbackID; bundle << size; bundle.append(datas, size); bundle.send(this->getNetworkInterface(), dbmgrinfos->pChannel); }
//------------------------------------------------------------------------------------- void Machine::stopserver(Mercury::Channel* pChannel, KBEngine::MemoryStream& s) { int32 uid = 0; COMPONENT_TYPE componentType; uint32 recvip; uint16 recvport; Mercury::Bundle bundle; bool success = true; s >> uid; s >> componentType; s >> recvip; s >> recvport; Mercury::EndPoint ep; ep.socket(SOCK_DGRAM); if (!ep.good()) { ERROR_MSG("Machine::stopserver: Failed to create socket.\n"); return; } Components::COMPONENTS& components = Componentbridge::getComponents().getComponents(componentType); Components::COMPONENTS::iterator iter = components.begin(); Components::ComponentInfos* cinfos = NULL; for(; iter != components.end(); ) { if((*iter).uid != uid) continue; if(componentType != (*iter).componentType) { continue; } bool usable = Componentbridge::getComponents().checkComponentUsable(&(*iter)); if(!usable) { success = true; break; } cinfos = &(*iter); Mercury::Bundle closebundle; COMMON_MERCURY_MESSAGE(componentType, closebundle, reqCloseServer); Mercury::EndPoint ep1; ep1.socket(SOCK_STREAM); if (!ep1.good()) { ERROR_MSG("Machine::stopserver: Failed to create socket.\n"); success = false; break; } if(ep1.connect((*iter).pIntAddr.get()->port, (*iter).pIntAddr.get()->ip) == -1) { ERROR_MSG("Machine::stopserver: connect server is error(%s)!\n", kbe_strerror()); success = false; break; } closebundle.send(ep1); Mercury::TCPPacket recvpacket; recvpacket.resize(255); int len = ep1.recv(recvpacket.data(), 1); if(len != 1) { success = false; break; } recvpacket >> success; break; } bundle << success; bundle.sendto(ep, recvport, recvip); }
//------------------------------------------------------------------------------------- bool RestoreEntityHandler::process() { Components::COMPONENTS& cts = Components::getSingleton().getComponents(CELLAPP_TYPE); Mercury::Channel* pChannel = NULL; if(cts.size() > 0) { Components::COMPONENTS::iterator ctiter = cts.begin(); if((*ctiter).pChannel == NULL) return true; pChannel = (*ctiter).pChannel; } if(pChannel == NULL) return true; int count = 0; // 首先需要找到这个cell上的space // KBE_ASSERT(restoreSpaces_.size() > 0); // 如果spaceEntity不在这个baseapp上创建则继续等待 // 当spaceEntity的cell创建好了之后会广播给所有的baseapp, 每个baseapp // 去判断是否有需要恢复的entity if(restoreSpaces_.size() > 0) { if(timestamp() - tickReport_ > uint64( 3 * stampsPerSecond() )) { tickReport_ = timestamp(); INFO_MSG(boost::format("RestoreEntityHandler::process(%3%): wait for localSpace to get cell!, entitiesSize(%1%), spaceSize=%2%\n") % entities_.size() % restoreSpaces_.size() % cellappID_); } int spaceCellCount = 0; // 必须等待space恢复 std::vector<RestoreData>::iterator restoreSpacesIter = restoreSpaces_.begin(); for(; restoreSpacesIter != restoreSpaces_.end(); restoreSpacesIter++) { Base* pBase = Baseapp::getSingleton().findEntity((*restoreSpacesIter).id); if(pBase) { if(++count > (int)g_kbeSrvConfig.getBaseApp().entityRestoreSize) { return true; } if((*restoreSpacesIter).creatingCell == false) { (*restoreSpacesIter).creatingCell = true; pBase->restoreCell(NULL); } else { if(pBase->cellMailbox() == NULL) { return true; } else { spaceCellCount++; if(!(*restoreSpacesIter).processed) { (*restoreSpacesIter).processed = true; pBase->onRestore(); } } } } else { ERROR_MSG(boost::format("RestoreEntityHandler::process(%1%): lose space(%2%).\n") % cellappID_ % (*restoreSpacesIter).id); } } if(spaceCellCount != (int)restoreSpaces_.size()) return true; // 通知其他baseapp, space恢复了cell if(!broadcastOtherBaseapps_) { broadcastOtherBaseapps_ = true; INFO_MSG(boost::format("RestoreEntityHandler::process(%1%): begin broadcast-spaceGetCell to otherBaseapps...\n") % cellappID_); std::vector<RestoreData>::iterator restoreSpacesIter = restoreSpaces_.begin(); for(; restoreSpacesIter != restoreSpaces_.end(); restoreSpacesIter++) { Base* pBase = Baseapp::getSingleton().findEntity((*restoreSpacesIter).id); bool destroyed = (pBase == NULL || pBase->isDestroyed()); COMPONENT_ID baseappID = g_componentID; COMPONENT_ID cellappID = 0; SPACE_ID spaceID = (*restoreSpacesIter).spaceID; ENTITY_ID spaceEntityID = (*restoreSpacesIter).id; ENTITY_SCRIPT_UID utype = 0; if(!destroyed) { utype = pBase->scriptModule()->getUType(); cellappID = pBase->cellMailbox()->componentID(); } spaceIDs_.erase(std::remove(spaceIDs_.begin(), spaceIDs_.end(), spaceID), spaceIDs_.end()); Mercury::Channel* pChannel = NULL; Components::COMPONENTS& cts = Componentbridge::getComponents().getComponents(BASEAPP_TYPE); Components::COMPONENTS::iterator comsiter = cts.begin(); for(; comsiter != cts.end(); comsiter++) { pChannel = (*comsiter).pChannel; if(pChannel) { INFO_MSG(boost::format("RestoreEntityHandler::process(%5%): broadcast baseapp[%1%, %2%], spaceID[%3%], utype[%4%]...\n") % (*comsiter).cid % pChannel->c_str() % spaceID % utype % cellappID_); Mercury::Bundle* pBundle = Mercury::Bundle::ObjPool().createObject(); (*pBundle).newMessage(BaseappInterface::onRestoreSpaceCellFromOtherBaseapp); (*pBundle) << baseappID << cellappID << spaceID << spaceEntityID << utype << destroyed; pBundle->send(Baseapp::getSingleton().getNetworkInterface(), pChannel); Mercury::Bundle::ObjPool().reclaimObject(pBundle); } } } } } if(spaceIDs_.size() > 0) { if(timestamp() - tickReport_ > uint64( 3 * stampsPerSecond() )) { tickReport_ = timestamp(); INFO_MSG(boost::format("RestoreEntityHandler::process(%1%): wait for otherBaseappSpaces to get cell!, entitiesSize(%2%), spaceSize=%3%\n") % cellappID_ % entities_.size() % spaceIDs_.size()); } return true; } // 恢复其他entity std::vector<RestoreData>::iterator iter = entities_.begin(); for(; iter != entities_.end(); ) { RestoreData& data = (*iter); Base* pBase = Baseapp::getSingleton().findEntity(data.id); if(pBase) { if(++count > g_kbeSrvConfig.getBaseApp().entityRestoreSize) { return true; } if(pBase->cellMailbox() != NULL) { if(!data.processed) { data.processed = true; pBase->onRestore(); } iter = entities_.erase(iter); } else { if(!data.creatingCell) { data.creatingCell = true; EntityMailboxAbstract* cellMailbox = NULL; std::vector<RestoreData>::iterator restoreSpacesIter = restoreSpaces_.begin(); for(; restoreSpacesIter != restoreSpaces_.end(); restoreSpacesIter++) { Base* pSpace = Baseapp::getSingleton().findEntity((*restoreSpacesIter).id); if(pSpace && pBase->spaceID() == pSpace->spaceID()) { cellMailbox = pSpace->cellMailbox(); break; } } if(cellMailbox == NULL) { restoreSpacesIter = otherRestoredSpaces_.begin(); for(; restoreSpacesIter != otherRestoredSpaces_.end(); restoreSpacesIter++) { if(pBase->spaceID() == (*restoreSpacesIter).spaceID && (*restoreSpacesIter).cell) { cellMailbox = (*restoreSpacesIter).cell; break; } } } if(cellMailbox) { pBase->restoreCell(cellMailbox); } else { ENTITY_ID delID = pBase->id(); pBase->destroy(); WARNING_MSG(boost::format("RestoreEntityHandler::process(%1%): not fount spaceCell, killed base(%2%)!") % cellappID_ % delID); if(Baseapp::getSingleton().findEntity(delID) == NULL) iter = entities_.erase(iter); continue; } } iter++; } } else { iter = entities_.erase(iter); } } if(entities_.size() == 0) { std::vector<RestoreData>::iterator restoreSpacesIter = otherRestoredSpaces_.begin(); for(; restoreSpacesIter != otherRestoredSpaces_.end(); restoreSpacesIter++) { if((*restoreSpacesIter).cell) { Py_DECREF((*restoreSpacesIter).cell); (*restoreSpacesIter).cell = NULL; } } otherRestoredSpaces_.clear(); inProcess_ = false; Baseapp::getSingleton().onRestoreEntitiesOver(this); return false; } return true; }
//------------------------------------------------------------------------------------- void Baseapp::onCreateBaseAnywhere(Mercury::Channel* pChannel, MemoryStream& s) { if(pChannel->isExternal()) return; std::string strInitData = ""; uint32 initDataLength = 0; PyObject* params = NULL; std::string entityType; COMPONENT_ID componentID; CALLBACK_ID callbackID; s >> entityType; s >> initDataLength; if(initDataLength > 0) { strInitData.assign((char*)(s.data() + s.rpos()), initDataLength); s.read_skip(initDataLength); } s >> componentID; s >> callbackID; if(strInitData.size() > 0) params = script::Pickler::unpickle(strInitData); Base* base = createEntityCommon(entityType.c_str(), params); Py_XDECREF(params); if(base == NULL) return; // 如果不是在发起创建entity的baseapp上创建则需要转发回调到发起方 if(componentID != componentID_) { Components::ComponentInfos* cinfos = Components::getSingleton().findComponent(componentID); if(cinfos == NULL || cinfos->pChannel == NULL) { ForwardItem* pFI = new ForwardItem(); pFI->pHandler = NULL; pFI->bundle.newMessage(BaseappInterface::onCreateBaseAnywhereCallback); pFI->bundle << callbackID; pFI->bundle << entityType; pFI->bundle << base->getID(); pFI->bundle << componentID_; forward_messagebuffer_.push(componentID, pFI); WARNING_MSG("Baseapp::onCreateBaseAnywhere: not found baseapp, message is buffered.\n"); return; } Mercury::Channel* lpChannel = cinfos->pChannel; // 需要baseappmgr转发给目的baseapp Mercury::Bundle forwardbundle; forwardbundle.newMessage(BaseappInterface::onCreateBaseAnywhereCallback); forwardbundle << callbackID; forwardbundle << entityType; forwardbundle << base->getID(); forwardbundle << componentID_; forwardbundle.send(this->getNetworkInterface(), lpChannel); } else { ENTITY_ID eid = base->getID(); _onCreateBaseAnywhereCallback(NULL, callbackID, entityType, eid, componentID_); } }