void CommandService::_process_timeout(const int64_t now){ /* clear timeout command */ if(m_queue_tb->size()>0){ Int64Array* ls =0; HashIterator* it =static_cast< HashIterator* >(m_queue_tb->iterator()); while(it->next()){ const int64_t who =static_cast< Int64* >(it->getKey())->getValue(); Array* queue =static_cast< Array* >(it->getValue()); while(Command* cmd =dynamic_cast< Command* >(queue->front())){ if(cmd->isTimeout(now)){ if(cmd->isProcessing()){ WARN("service %s(%lld) who %lld command %lld cancel", name(), (long long)m_id, (long long)cmd->getWho(), (long long)cmd->getCommand()); } queue->pop_front(); } else{ break; } } if(Command* cmd =dynamic_cast< Command* >(queue->front())){ if(cmd->isProcessing()){ continue; } ASSERT(cmd->isInit()); if(!ls){ ls =SafeNew<Int64Array>(); } ls->push_back(who); } } const int64_t n= ls ? ls->size() : 0; for(int64_t i=0; i<n; ++i){ _process_request(ls->get(i)); } } /* clear timeout rpc */ if(m_rpc_tb->size()>0){ Array* ls =0; HashIterator* it =static_cast< HashIterator* >(m_rpc_tb->iterator()); while(it->next()){ RpcInfo* ri =static_cast< RpcInfo* >(it->getValue()); if(now >= ri->getExpireTime()){ if(!ls){ ls =SafeNew<Array>(); } ls->push_back(ri); it->remove(); } } const int64_t n =ls ? ls->size() : 0; for(int64_t i=0; i<n; ++i){ RpcInfo* ri =static_cast< RpcInfo* >(ls->get(i)); WARN("service %s(%lld) rpc %lld cancel", name(), (long long)m_id, (long long)ri->getId()); ri->invoke(SafeNew<Error>(ErrorCode::TIMEOUT)); } } }
int Ardb::HMIncrby(Context& ctx, RedisCommandFrame& cmd) { if ((cmd.GetArguments().size() - 1) % 2 != 0) { fill_error_reply(ctx.reply, "wrong number of arguments for HMIncrby"); return 0; } ValueObject meta; int err = GetMetaValue(ctx, cmd.GetArguments()[0], HASH_META, meta); CHECK_ARDB_RETURN_VALUE(ctx.reply, err); ctx.reply.type = REDIS_REPLY_ARRAY; DataMap fs; Int64Array vs; for (uint32 i = 1; i < cmd.GetArguments().size(); i += 2) { int64 inc = 0; if (!GetInt64Value(ctx, cmd.GetArguments()[i + 1], inc)) { return 0; } Data field(cmd.GetArguments()[i]); if (err == ERR_NOT_EXIST) { fs[field].SetInt64(inc); vs.push_back(inc); } else { Data value; HashGet(ctx, meta, field, value); int64 val = 0; if (!value.GetInt64(val)) { fill_error_reply(ctx.reply, "value is not a float or out of range"); return 0; } fs[field].SetInt64(inc + val); vs.push_back(inc + val); } } HashMultiSet(ctx, meta, fs); fill_int_array_reply(ctx.reply, vs); return 0; }
Int64Array* ServiceManager::_get_need_unload_service_id(){ std::lock_guard<LOCK_TYPE> guard(m_lock); if(m_unloading_service_tb->empty()){ return 0; } const int64_t now =DateTime::Now(); Int64Array* arr =SafeNew<Int64Array>(); HashIterator* it =static_cast< HashIterator* >(m_unloading_service_tb->iterator()); while(it->next()){ const int64_t id_srv =static_cast< Int64* >(it->getKey())->getValue(); const int64_t t =static_cast< Int64* >(it->getValue())->getValue(); if(now >= t){ arr->push_back(id_srv); it->remove(); } } return arr; }
/** coroutine manager **/ void CoroutinePool::update(const int64_t now){ // process timeout if(m_active_coroutine_table && m_active_coroutine_table->size()>0){ // prepare Int64Array* ls =0; HashIterator* it =static_cast< HashIterator* >(m_active_coroutine_table->iterator()); while(it->next()){ Coroutine* cr =static_cast< Coroutine* >(it->getValue()); if(cr->isWaitingAndExpire(now)){ if(!ls){ ls =SafeNew<Int64Array>(); } ls->push_back(cr->getId()); } } // resume if(ls && ls->size()>0){ const int64_t n =ls->size(); for(int64_t i=0; i<n; ++i){ resume(ls->get(i), SafeNew<Error>(ErrorCode::TIMEOUT), 0); } } } }
void test_array(){ OPH(); DEBUG("testing array ......"); Array* a =SafeNew<Array>(); for(int64_t i=0; i<14; ++i){ a->push_back(SafeNew<Int32>()); } for(int64_t i=0; i<14; ++i){ a->pop_back(); } ASSERT(a->empty()); // common array { Array* arr =SafeNew<Array>(); // push_back, size, pop_front, front for(int i=0; i<100; ++i){ arr->push_back(String::Format("%d", i)); } for(int i=0; i<100; ++i){ CHECK_EXIT(((String*)(arr->front()))->is(String::Format("%d", i)), 1); arr->pop_front(); } CHECK_EXIT(arr->size()==0, 1); // push_front, size, pop_back, back for(int i=99; i>=0; --i){ arr->push_front(String::Format("%d", i)); } CHECK_EXIT(arr->size()==100, 1); for(int i=99; i>=0; --i){ CHECK_EXIT(((String*)(arr->back()))->is(String::Format("%d", i)), 1); arr->pop_back(); } CHECK_EXIT(arr->size()==0, 1); // insert, remove for(int i=0; i<100; ++i){ arr->push_back(SafeNew<Int64, int64_t>(i)); } arr->push_front(SafeNew<Int64, int64_t>(-1)); arr->push_back(SafeNew<Int64, int64_t>(100)); for(int i=0; i<102; ++i){ CHECK_EXIT(((Int64*)(arr->get(i)))->getValue() == i-1, 1); } arr->insert(50, SafeNew<Int64, int64_t>(9999)); CHECK_EXIT(((Int64*)(arr->get(50)))->getValue() == 9999, 1); CHECK_EXIT(((Int64*)(arr->get(51)))->getValue() == 49, 1); CHECK_EXIT(((Int64*)(arr->get(49)))->getValue() == 48, 1); arr->remove(102); arr->remove(50); arr->remove(0); for(int i=0; i<100; ++i){ CHECK_EXIT(((Int64*)(arr->front()))->getValue() == i, 1); arr->pop_front(); } CHECK_EXIT(arr->size()==0, 1); } // int64 array { Int64Array* arr =SafeNew<Int64Array>(); // push_back, size, pop_front, front for(int i=0; i<100; ++i){ arr->push_back(i); } for(int i=0; i<100; ++i){ CHECK_EXIT(arr->front() == i, 1); arr->pop_front(); } CHECK_EXIT(arr->size()==0, 1); // push_front, size, pop_back, back for(int i=99; i>=0; --i){ arr->push_front(i); } CHECK_EXIT(arr->size()==100, 1); for(int i=99; i>=0; --i){ CHECK_EXIT(arr->back() == i, 1); arr->pop_back(); } CHECK_EXIT(arr->size()==0, 1); // insert, remove for(int i=0; i<100; ++i){ arr->push_back(i); } arr->push_front(-1); arr->push_back(100); for(int i=0; i<102; ++i){ CHECK_EXIT(arr->get(i) == i-1, 1); } arr->insert(50, 9999); CHECK_EXIT(arr->get(50) == 9999, 1); CHECK_EXIT(arr->get(51) == 49, 1); CHECK_EXIT(arr->get(49) == 48, 1); arr->remove(102); arr->remove(50); arr->remove(0); for(int i=0; i<100; ++i){ CHECK_EXIT(arr->front() == i, 1); arr->pop_front(); } CHECK_EXIT(arr->size()==0, 1); } }