void *workerThread(void *data) { signal(SIGTERM, signal_kill_handler); try { PThreadParameter pThrParam = reinterpret_cast<PThreadParameter>(data); CSocket sockDrv; sockDrv.setSocketFd(pThrParam->iSockfd); // client socket #ifndef NO_DEBUG_INFO ostringstream msg2; msg2<<"workerThread "<<pThrParam->t_id<<", start, iSockfd = "<<pThrParam->iSockfd<<endl; pThrParam->pBrokerageHouse->logErrorMessage(msg2.str()); #endif PMsgDriverBrokerage pMessage = new TMsgDriverBrokerage; memset(pMessage, 0, sizeof(TMsgDriverBrokerage)); // zero the structure TMsgBrokerageDriver Reply; // return message INT32 iRet = 0; // transaction return code CDBConnection *pDBConnection = NULL; #ifdef DB_PGSQL // new database connection pDBConnection = new CDBConnection( pThrParam->pBrokerageHouse->m_szHost, pThrParam->pBrokerageHouse->m_szDBName, pThrParam->pBrokerageHouse->m_szDBPort); #else pDBConnection = new CDBConnection( pThrParam->pBrokerageHouse, pThrParam->pBrokerageHouse->mysql_dbname, pThrParam->pBrokerageHouse->mysql_host, pThrParam->pBrokerageHouse->mysql_user, pThrParam->pBrokerageHouse->mysql_pass, pThrParam->pBrokerageHouse->mysql_port_t, pThrParam->pBrokerageHouse->mysql_socket_t); pDBClist[pThrParam->t_id] = pDBConnection; #ifdef CAL_RESP_TIME pDBConnection->init_profile_node(pThrParam->t_id, pThrParam->outputDir); #endif #endif pDBConnection->setBrokerageHouse(pThrParam->pBrokerageHouse); CSendToMarket sendToMarket = CSendToMarket( &(pThrParam->pBrokerageHouse->m_fLog)); #ifdef NO_MEE_FOR_TRADERESULT sendToMarket.m_pCMEE = pThrParam->pBrokerageHouse->m_pCMEE[pThrParam->t_id%pThrParam->pBrokerageHouse->iUsers]; #endif CMarketFeedDB marketFeedDB(pDBConnection); CMarketFeed marketFeed = CMarketFeed(&marketFeedDB, &sendToMarket); CTradeOrderDB tradeOrderDB(pDBConnection); CTradeOrder tradeOrder = CTradeOrder(&tradeOrderDB, &sendToMarket); // Initialize all classes that will be used to execute transactions. CBrokerVolumeDB brokerVolumeDB(pDBConnection); CBrokerVolume brokerVolume = CBrokerVolume(&brokerVolumeDB); CCustomerPositionDB customerPositionDB(pDBConnection); CCustomerPosition customerPosition = CCustomerPosition(&customerPositionDB); CMarketWatchDB marketWatchDB(pDBConnection); CMarketWatch marketWatch = CMarketWatch(&marketWatchDB); CSecurityDetailDB securityDetailDB = CSecurityDetailDB(pDBConnection); CSecurityDetail securityDetail = CSecurityDetail(&securityDetailDB); CTradeLookupDB tradeLookupDB(pDBConnection); CTradeLookup tradeLookup = CTradeLookup(&tradeLookupDB); CTradeStatusDB tradeStatusDB(pDBConnection); CTradeStatus tradeStatus = CTradeStatus(&tradeStatusDB); CTradeUpdateDB tradeUpdateDB(pDBConnection); CTradeUpdate tradeUpdate = CTradeUpdate(&tradeUpdateDB); CDataMaintenanceDB dataMaintenanceDB(pDBConnection); CDataMaintenance dataMaintenance = CDataMaintenance(&dataMaintenanceDB); CTradeCleanupDB tradeCleanupDB(pDBConnection); CTradeCleanup tradeCleanup = CTradeCleanup(&tradeCleanupDB); CTradeResultDB tradeResultDB(pDBConnection); CTradeResult tradeResult = CTradeResult(&tradeResultDB); int txn_cnt = 0; int abort_cnt = 0; double txn_time = 0; bool commit = true; double receiving_time = 0; // gettimeofday(&(pDBConnection->t1), NULL); do { try { //gettimeofday(&tt1, NULL); sockDrv.dbt5Receive(reinterpret_cast<void *>(pMessage), sizeof(TMsgDriverBrokerage)); //gettimeofday(&tt2, NULL); //if(txn_cnt > 0 && difftimeval(tt2, tt1)>1)pDBConnection->outfile<<"END"<<endl; //pDBConnection->outfile.flush(); } catch(CSocketErr *pErr) { sockDrv.dbt5Disconnect(); ostringstream osErr; osErr << "Error on Receive: " << pErr->ErrorText() << " at BrokerageHouse::workerThread" << endl; pThrParam->pBrokerageHouse->logErrorMessage(osErr.str()); delete pErr; // The socket has been closed, break and let this thread die. break; } loop: timeval t1, t2; double exec_time; gettimeofday(&t1, NULL); commit = true; iRet = CBaseTxnErr::SUCCESS; try { // Parse Txn type switch (pMessage->TxnType) { /*case BROKER_VOLUME: iRet = pThrParam->pBrokerageHouse->RunBrokerVolume( &(pMessage->TxnInput.BrokerVolumeTxnInput), brokerVolume); break; case CUSTOMER_POSITION: iRet = pThrParam->pBrokerageHouse->RunCustomerPosition( &(pMessage->TxnInput.CustomerPositionTxnInput), customerPosition); break; case MARKET_FEED: iRet = pThrParam->pBrokerageHouse->RunMarketFeed( &(pMessage->TxnInput.MarketFeedTxnInput), marketFeed); break; case MARKET_WATCH: iRet = pThrParam->pBrokerageHouse->RunMarketWatch( &(pMessage->TxnInput.MarketWatchTxnInput), marketWatch); break; case SECURITY_DETAIL: iRet = pThrParam->pBrokerageHouse->RunSecurityDetail( &(pMessage->TxnInput.SecurityDetailTxnInput), securityDetail); break; case TRADE_LOOKUP: iRet = pThrParam->pBrokerageHouse->RunTradeLookup( &(pMessage->TxnInput.TradeLookupTxnInput), tradeLookup); break;*/ #ifdef TRADEORDER case TRADE_ORDER: iRet = pThrParam->pBrokerageHouse->RunTradeOrder( &(pMessage->TxnInput.TradeOrderTxnInput), tradeOrder); break; #endif #ifdef TRADEMIX case TRADE_ORDER: iRet = pThrParam->pBrokerageHouse->RunTradeOrder( &(pMessage->TxnInput.TradeOrderTxnInput), tradeOrder); break; case TRADE_RESULT: iRet = pThrParam->pBrokerageHouse->RunTradeResult( &(pMessage->TxnInput.TradeResultTxnInput), tradeResult); break; #endif #ifdef TRADESTATUS case TRADE_STATUS: iRet = pThrParam->pBrokerageHouse->RunTradeStatus( &(pMessage->TxnInput.TradeStatusTxnInput), tradeStatus); break; #endif #ifdef TRADEUPDATE case TRADE_UPDATE: iRet = pThrParam->pBrokerageHouse->RunTradeUpdate( &(pMessage->TxnInput.TradeUpdateTxnInput), tradeUpdate); break; #endif /*case DATA_MAINTENANCE: iRet = pThrParam->pBrokerageHouse->RunDataMaintenance( &(pMessage->TxnInput.DataMaintenanceTxnInput), dataMaintenance); break; case TRADE_CLEANUP: iRet = pThrParam->pBrokerageHouse->RunTradeCleanup( &(pMessage->TxnInput.TradeCleanupTxnInput), tradeCleanup); break;*/ default: //cout << "wrong txn type" << endl; iRet = ERR_TYPE_WRONGTXN; } txn_cnt++; pDBConnection->txn_cnt = txn_cnt; if(txn_cnt==1)gettimeofday(&(t_start_values[pThrParam->t_id]), NULL); } catch (const char *str) { pDBConnection->rollback(); #ifdef CAL_RESP_TIME // gettimeofday(&t2, NULL); // exec_time = difftimeval(t2, t1); // txn_time += exec_time; //pDBConnection->append_profile_node(t1, t2, pMessage->TxnType, false); // pDBConnection->outfile<<"error: "<<str<<endl; //#ifdef PROFILE_EACH_QUERY // pDBConnection->print_profile_query(); //#endif // pDBConnection->outfile.flush(); #endif //ostringstream msg; //msg << time(NULL) << " " << (long long) pthread_self() << " " << // szTransactionName[pMessage->TxnType] << "; "<<str<<endl; //pThrParam->pBrokerageHouse->logErrorMessage(msg.str()); iRet = CBaseTxnErr::EXPECTED_ROLLBACK; //cout<<"query fail:"<<str<<endl; commit = false; abort_cnt++; pDBConnection->abort_cnt = abort_cnt; //XXX:debug for trade result } gettimeofday(&t2, NULL); exec_time = difftimeval(t2, t1); txn_time += exec_time; pDBConnection->txn_time = txn_time; #ifdef CAL_RESP_TIME // pDBConnection->append_profile_node(t1, t2, pMessage->TxnType, true); // pDBConnection->outfile<<commit<<" start=( "<<t1.tv_sec<<" "<<t1.tv_usec<<" ), end=( "<<t2.tv_sec<<" "<<t2.tv_usec<<" ), "<<exec_time<<", txn_cnt = "<<txn_cnt<<"total: "<<txn_time<<endl; #ifdef PROFILE_EACH_QUERY // pDBConnection->print_profile_query(); #endif // pDBConnection->outfile.flush(); #endif // send status to driver Reply.iStatus = iRet; try { sockDrv.dbt5Send(reinterpret_cast<void *>(&Reply), sizeof(Reply)); } catch(CSocketErr *pErr) { sockDrv.dbt5Disconnect(); ostringstream osErr; osErr << "Error on Send: " << pErr->ErrorText() << " at BrokerageHouse::workerThread" << endl; pThrParam->pBrokerageHouse->logErrorMessage(osErr.str()); delete pErr; // The socket has been closed, break and let this thread die. break; } } while (true); // delete pDBConnection; // close connection with the database close(pThrParam->iSockfd); // close socket connection with the driver delete pThrParam; delete pMessage; } catch (CSocketErr *err) { } return NULL; }
void *workerThread(void *data) { signal(SIGTERM, signal_kill_handler); try { PThreadParameter pThrParam = reinterpret_cast<PThreadParameter>(data); CSocket sockDrv; sockDrv.setSocketFd(pThrParam->iSockfd); // client socket PMsgDriverTPCC pMessage = new TMsgDriverTPCC; memset(pMessage, 0, sizeof(TMsgDriverTPCC)); // zero the structure TMsgTPCCDriver Reply; // return message INT32 iRet = 0; // transaction return code CDBConnection *pDBConnection = NULL; pDBConnection = new CDBConnection( pThrParam->pTPCC, pThrParam->pTPCC->mysql_dbname, pThrParam->pTPCC->mysql_host, pThrParam->pTPCC->mysql_user, pThrParam->pTPCC->mysql_pass, pThrParam->pTPCC->mysql_port_t, pThrParam->pTPCC->mysql_socket_t); #ifdef CAL_RESP_TIME timeval t1, t2; double exec_time; pDBClist[pThrParam->t_id] = pDBConnection; pDBConnection->init_profile_node(pThrParam->t_id, pThrParam->outputDir); #endif CTPCCDB tpccDB(pDBConnection); int txn_cnt = 0; int abort_cnt = 0; double txn_time = 0; bool commit = true; double receiving_time = 0; do { try { sockDrv.dbt5Receive(reinterpret_cast<void *>(pMessage), sizeof(TMsgDriverTPCC)); } catch(CSocketErr *pErr) { sockDrv.dbt5Disconnect(); delete pErr; // The socket has been closed, break and let this thread die. break; } timeval t1, t2; double exec_time; gettimeofday(&t1, NULL); commit = true; iRet = CBaseTxnErr::SUCCESS; try { // Parse Txn type switch (pMessage->TxnType) { case NEWORDER: iRet = pThrParam->pTPCC->RunNewOrder(&pMessage->TxnInput.neworderTxnInput, tpccDB); break; case PAYMENT: iRet = pThrParam->pTPCC->RunPayment(&pMessage->TxnInput.paymentTxnInput, tpccDB); break; case DELIVERY: iRet = pThrParam->pTPCC->RunDelivery(&pMessage->TxnInput.deliveryTxnInput, tpccDB); break; case STOCKLEVEL: iRet = pThrParam->pTPCC->RunStocklevel(&pMessage->TxnInput.stocklevelTxnInput, tpccDB); break; case ORDERSTATUS: iRet = pThrParam->pTPCC->RunOrderstatus(&pMessage->TxnInput.orderstatusTxnInput, tpccDB); break; default: pDBConnection->outfile<<"Wrong txn type!"<<endl; iRet = ERR_TYPE_WRONGTXN; } txn_cnt++; pDBConnection->txn_cnt = txn_cnt; }catch (const char *str) { pDBConnection->rollback(); //#ifdef CAL_RESP_TIME // gettimeofday(&t2, NULL); // exec_time = difftimeval(t2, t1); // txn_time += exec_time; //#ifdef PROFILE_EACH_QUERY // pDBConnection->print_profile_query(); //#endif // pDBConnection->outfile.flush(); //#endif //cout<<"error: "<<str<<endl; iRet = CBaseTxnErr::EXPECTED_ROLLBACK; commit = false; abort_cnt++; pDBConnection->abort_cnt = abort_cnt; //XXX:debug for trade result } gettimeofday(&t2, NULL); exec_time = difftimeval(t2, t1); txn_time += exec_time; pDBConnection->txn_time = txn_time; #ifdef CAL_RESP_TIME // pDBConnection->outfile<<commit<<" start=( "<<t1.tv_sec<<" "<<t1.tv_usec<<" ), end=( "<<t2.tv_sec<<" "<<t2.tv_usec<<" ), "<<exec_time<<", txn_cnt = "<<txn_cnt<<"total: "<<txn_time<<endl; #ifdef PROFILE_EACH_QUERY // pDBConnection->print_profile_query(); #endif //pDBConnection->outfile<<"commit txn "<<txn_cnt<<endl; // pDBConnection->outfile.flush(); #endif // send status to driver Reply.iStatus = iRet; try { sockDrv.dbt5Send(reinterpret_cast<void *>(&Reply), sizeof(Reply)); } catch(CSocketErr *pErr) { sockDrv.dbt5Disconnect(); delete pErr; // The socket has been closed, break and let this thread die. break; } } while (true); delete pDBConnection; // close connection with the database close(pThrParam->iSockfd); // close socket connection with the driver delete pThrParam; delete pMessage; } catch (CSocketErr *err) { } return NULL; }