w_rc_t sthread_t::fork() { { sthread_init_t::do_init(); CRITICAL_SECTION(cs, _start_terminate_lock); /* can only fork a new thread */ if (_forked) return RC(stOS); /* Add us to the list of threads, unless we are the main thread */ if(this != _main_thread) { CRITICAL_SECTION(cs, _class_list_lock); _class_list->append(this); } _forked = true; if(this == _main_thread) { // happens at global constructor time CRITICAL_SECTION(cs_thread, _wait_lock); _status = t_running; } else { // happens after main() called DO_PTHREAD( pthread_cond_signal(_start_cond) ); } } return RCOK; }
w_rc_t bf_prefetch_thread_t::fetch( const lpid_t& pid, page_p& page ) { FUNC(bf_prefetch_thread_t::fetch); bool got; latch_mode_t mode; DBGTHRD(<<"fetching -- awaiting mutex..."); CRITICAL_SECTION(cs, _prefetch_mutex); if(get_error()) { w_rc_t rc(_fix_error.delegate()); return rc; } int i = _f; bf_prefetch_thread_t::frame_info &inf = _info[i]; w_assert3(inf._status != pf_init); // caller must have requested it mode = inf._mode; if(inf._pid == pid && inf._status == pf_available ) { page = inf._page; // refixes got = true; } else { w_assert3(inf._status == pf_requested || inf._status == pf_in_transit || inf._status == pf_grabbed ); got = false; } new_state(i,pf_fetch); w_assert3( inf._status == pf_init || inf._status == pf_grabbed); cs.exit(); DBGTHRD(<<"fetching -- released mutex..."); w_rc_t rc; if(!got) { // Just go ahead and fix it here. // If _status is pf_in_transit, we should // block in the buffer manger; if it's // pf_requested, the thread hasn't run yet (which // really shouldn't be the case if we're prefetching // at most 1 at a time). DBGTHRD(<<"did not get -- fixing page..."); smlevel_0::store_flag_t store_flags = smlevel_0::st_bad; rc = page.fix(pid, page_p::t_any_p, mode, 0, store_flags); if(rc.is_error()) { CRITICAL_SECTION(cs2, _prefetch_mutex); _fix_error = rc; new_state(i, pf_error); } }
bool Working_Ant::walk(Ant_Graph * g, Ant_Graph::Node * tgt_node, Ant_Graph::Arc * ant_arc) { g->leave_agent_from_location(this); double distance; { CRITICAL_SECTION(ant_arc->mutex); distance = ant_arc->distance; // deposita feromona (mayor distancia ==> menor feromona) ant_arc->feromone_level += Q/distance; } { CRITICAL_SECTION(tgt_node->mutex); // Comida que consume hormiga (mayor distancia ==> mayor consumo) tgt_node->food -= F*distance/max_dist; } // vida que consume hormiga (mayor distancia ==> menos vida) life -= L*distance/max_dist; g->enter_agent_in_node(this, tgt_node); return true; }
void pong_thread_t::run() { int i; int self = id; { CRITICAL_SECTION(cs, game.theBall); for(i=0; i<PongTimes; ++i){ while(game.whoseShot != self){ DO_PTHREAD(pthread_cond_wait(&game.paddle[self], &game.theBall)); } game.whoseShot = 1-self; DO_PTHREAD(pthread_cond_signal(&game.paddle[1-self])); } } // OUT.form("pong(%#lx) id=%d done\n", (long)this, id); note.done(); if (DumpInThreads) { OUT << *this << endl; FLUSHOUT; } }
w_rc_t sthread_t::close(int fd) { fd -= fd_base; if (fd < 0 || fd >= (int)open_max || !_disks[fd]) return RC(stBADFD); w_rc_t e; // sync before close e = _disks[fd]->sync(); if (e.is_error()) return e; e = _disks[fd]->close(); if (e.is_error()) return e; sdisk_t *togo; { CRITICAL_SECTION(cs, protectFDs); togo = _disks[fd]; _disks[fd] = 0; open_count--; } delete togo; return e; }
void wait_for_t::wait() { CRITICAL_SECTION(cs, _lock); while (have < expected) { DO_PTHREAD(pthread_cond_wait(&_done, &_lock)); } }
void ShoreYCSBEnv::print_throughput(const double iQueriedSF, const int iSpread, const int iNumOfThreads, const double delay) { CRITICAL_SECTION(last_stats_cs, _last_stats_mutex); // get the current statistics ShoreYCSBTrxStats current_stats = _get_stats(); // now calculate the diff current_stats -= _last_stats; uint trxs_att = current_stats.attempted.total(); uint trxs_abt = current_stats.failed.total(); uint trxs_dld = current_stats.deadlocked.total(); TRACE( TRACE_ALWAYS, "*******\n" \ "QueriedSF: (%.1f)\n" \ "Spread: (%s)\n" \ "Threads: (%d)\n" \ "Trxs Att: (%d)\n" \ "Trxs Abt: (%d)\n" \ "Trxs Dld: (%d)\n" \ "Secs: (%.2f)\n" \ "TPS: (%.2f)\n", iQueriedSF, (iSpread ? "Yes" : "No"), iNumOfThreads, trxs_att, trxs_abt, trxs_dld, delay, (trxs_att-trxs_abt-trxs_dld)/delay); }
// prints all the env vars void envVar::printVars(void) { TRACE( TRACE_DEBUG, "Environment variables\n"); CRITICAL_SECTION(evm_cs,_lock); for (envVarConstIt cit= _evm.begin(); cit != _evm.end(); ++cit) TRACE( TRACE_STATISTICS, "%s -> %s\n", cit->first.c_str(), cit->second.c_str()); }
int rvp_t::append_actions(const baseActionsList& actionList) { CRITICAL_SECTION(action_cs, _actions_lock); // append new actionList to the end of the list _actions.insert(_actions.end(), actionList.begin(),actionList.end()); return (0); }
int trx_worker_t::_pre_STOP_impl() { Request* pr; int reqs_read = 0; int reqs_write = 0; int reqs_abt = 0; assert (_pqueue); // Go over the readers list for (; _pqueue->_read_pos != _pqueue->_for_readers->end(); _pqueue->_read_pos++) { pr = *(_pqueue->_read_pos); ++reqs_read; if (abort_one_trx(pr->_xct)) ++reqs_abt; } // Go over the writers list { CRITICAL_SECTION(q_cs, _pqueue->_lock); for (_pqueue->_read_pos = _pqueue->_for_writers->begin(); _pqueue->_read_pos != _pqueue->_for_writers->end(); _pqueue->_read_pos++) { pr = *(_pqueue->_read_pos); ++reqs_write; if (abort_one_trx(pr->_xct)) ++reqs_abt; } } if ((reqs_read + reqs_write) > 0) { TRACE( TRACE_ALWAYS, "(%d) aborted before stopping. (%d) (%d)\n", reqs_abt, reqs_read, reqs_write); } return (reqs_abt); }
bool htab_remove(bf_core_m *core, bfpid_t const &pid, bf_core_m::Tstats &s) { bool ret(false); bfcb_t *cb = core->_htab->lookup(pid); if(cb) { // find the bucket so we can acquire the lock, // necessary for removal. // also ensure pin count is zero. int idx = core->_htab->hash(cb->hash_func(), pid); bf_core_m::htab::bucket &b = core->_htab->_table[idx]; cb->zero_pin_cnt(); CRITICAL_SECTION(cs, b._lock); bool bull = core->_htab->remove(cb); w_assert0(bull); w_assert1(cb->pin_cnt() == 0); } // It's possible that it couldn't remove the item // because the lock is not held or the pin count is > 0 if(ret) { w_assert2(cb->hash_func() == bf_core_m::htab::HASH_COUNT); } s = me()->TL_stats().bfht; return ret; }
w_rc_t bf_tree_m::_grab_free_block(bf_idx& ret, bool evict) { ret = 0; while (true) { // once the bufferpool becomes full, getting _freelist_lock everytime will be // too costly. so, we check _freelist_len without lock first. // false positive : fine. we do real check with locks in it // false negative : fine. we will eventually get some free block anyways. if (_freelist_len > 0) { CRITICAL_SECTION(cs, &_freelist_lock); if (_freelist_len > 0) { // here, we do the real check bf_idx idx = FREELIST_HEAD; DBG5(<< "Grabbing idx " << idx); w_assert1(_is_valid_idx(idx)); w_assert1 (!get_cb(idx)._used); ret = idx; --_freelist_len; if (_freelist_len == 0) { FREELIST_HEAD = 0; } else { FREELIST_HEAD = _freelist[idx]; w_assert1 (FREELIST_HEAD > 0 && FREELIST_HEAD < _block_cnt); } DBG5(<< "New head " << FREELIST_HEAD); w_assert1(ret != FREELIST_HEAD); return RCOK; } } // exit the scope to do the following out of the critical section
void Aleph::error(const char* file, int line, const char* format, ...) { # ifdef _PTHREAD_H CRITICAL_SECTION(aleph_message_mutex); # endif va_list ap; va_start(ap, format); if (Aleph::daemonized) { ::syslog(LOG_ERR, "Fatal error detected at %s %u\n", file, line); Aleph::syslog(format, ap); } else { printf("Fatal error detected in %s %u\n", file, line); vfprintf(stdout, format, ap); printf("\n"); } va_end(ap); abort(); }
void Aleph::exit(const char* file, int line, const char* format, ...) { # ifdef _PTHREAD_H CRITICAL_SECTION(aleph_message_mutex); # endif va_list ap; va_start(ap, format); if (Aleph::daemonized) { ::syslog(LOG_NOTICE, "%s: %u\n", file, line); Aleph::syslog(format, ap); } else { vfprintf(stdout, format, ap); printf("%s:%u\n", file, line); printf("\n"); } va_end(ap); ::exit(0); }
w_rc_t sthread_t::join(timeout_in_ms /*timeout*/) { w_rc_t rc; { CRITICAL_SECTION(cs, _start_terminate_lock); /* A thread that hasn't been forked can't be wait()ed for. It's not a thread until it has been fork()ed. */ if (!_forked) { rc = RC(stOS); } else { cs.exit(); /* * Wait for thread to finish. */ sthread_core_exit(_core, _terminated); } } return rc; }
void asc_sort_man_impl::add_tuple(table_row_t& atuple) { CRITICAL_SECTION(cs, _sorted_lock); /* setup the tuple size */ if (!_tuple_size) init(); /* check if more space is needed */ if (_buf_size == _tuple_count) { /* double the buffer size if needed */ char* tmp = new char[(2*_buf_size)*_tuple_size]; memcpy(tmp, _sort_buf, _buf_size*_tuple_size); delete [] _sort_buf; _sort_buf = tmp; _buf_size *= 2; //fprintf(stderr,"+\n"); } /* add the current tuple to the end of the buffer */ size_t ksz = _preprow->_bufsz; atuple.store_key(_preprow->_dest, ksz); memcpy(_sort_buf+(_tuple_count*_tuple_size), _preprow->_dest, _tuple_size); _tuple_count++; _is_sorted = false; }
void ant_transit(void * __graph, void * __ant, void *) { Ant_Graph * graph = static_cast<Ant_Graph*>(__graph); Working_Ant * working_ant = static_cast<Working_Ant*>(__ant); { CRITICAL_SECTION(graph->bit_mutex); working_ant->my_bit = Working_Ant::bit_idx; Working_Ant::bit_idx = (Working_Ant::bit_idx + 1) % graph->get_num_threads(); } Ant_Graph::Node * current_node = graph->get_agent_node_location(working_ant); Ant_Graph::Node * next_node = NULL; Ant_Graph::Arc * next_arc = NULL; while (true) { const bool ant_is_alive = working_ant->select_path(current_node, next_node, next_arc); if (not ant_is_alive) break; working_ant->walk(graph, next_node, next_arc); current_node = next_node; } graph->remove_agent(working_ant); }
// refreshes all the env vars from the conf file int envVar::refreshVars(void) { TRACE( TRACE_DEBUG, "Refreshing environment variables\n"); CRITICAL_SECTION(evm_cs,_lock); for (envVarIt it= _evm.begin(); it != _evm.end(); ++it) _readConfVar(it->first,it->second); return (0); }
// sets as input another conf file void envVar::setConfFile(const string& sConfFile) { assert (!sConfFile.empty()); CRITICAL_SECTION(evm_cs,_lock); _cfname = sConfFile; _pfparser = new ConfigFile(_cfname); assert (_pfparser); }
void wait_for_t::done() { CRITICAL_SECTION(cs, _lock); have++; if (have >= expected) { DO_PTHREAD(pthread_cond_signal(&_done)); } }
ShoreYCSBTrxStats ShoreYCSBEnv::_get_stats() { CRITICAL_SECTION(cs, _statmap_mutex); ShoreYCSBTrxStats rval; rval -= rval; // dirty hack to set all zeros for (statmap_t::iterator it=_statmap.begin(); it != _statmap.end(); ++it) rval += *it->second; return (rval); }
bool bf_core_m::htab::cuckold(bucket* dest, bucket* src, int which, int hashfunc, bfcb_t* &moved) { ADD_BFSTAT(_slots_tried, 1); if(dest->_count < SLOT_COUNT) { ADD_BFSTAT(_cuckolds, 1); // dest has room // Order the lock-grabbing to avoid deadlock bucket* b1 = (src < dest)? src : dest; bucket* b2 = (src < dest)? dest : src; CRITICAL_SECTION(cs1, b1->_lock); CRITICAL_SECTION(cs2, b2->_lock); if(src->_count < SLOT_COUNT) { // src now has room - don't do anything after all return true; } if(dest->_count < SLOT_COUNT) { // good to go : dest still has room. // Copy over src, update slot _count bfcb_t *b; dest->_slots[dest->_count++] = b = src->_slots[which]; b->set_hash_func(hashfunc); b->set_hash(dest-_table); // adjust dest hash info while we have the locks. // // compress src, update slot _count src->_slots[which] = src->_slots[--src->_count]; moved = src->_slots[which]; CHECK_ENTRY(src-_table, true); CHECK_ENTRY(dest-_table, true); return true; } } CHECK_TABLE(); return false; // possibly stale }
EventDescription* EventDescription::Create(const char* eventName, const char* fileName, const unsigned long fileLine, const unsigned long eventColor /*= Color::Null*/) { CRITICAL_SECTION(lock) EventDescription* result = EventDescriptionBoard::Get().CreateDescription(); result->name = eventName; result->file = fileName; result->line = fileLine; result->color = eventColor; return result; }
// sets a new parameter int envVar::setVar(const string& sParam, const string& sValue) { if ((!sParam.empty())&&(!sValue.empty())) { TRACE( TRACE_DEBUG, "(%s) (%s)\n", sParam.c_str(), sValue.c_str()); CRITICAL_SECTION(evm_cs,_lock); _evm[sParam] = sValue; return (_evm.size()); } return (0); }
int ShoreTPCBEnv::statistics() { // read the current trx statistics CRITICAL_SECTION(cs, _statmap_mutex); ShoreTPCBTrxStats rval; rval -= rval; // dirty hack to set all zeros for (statmap_t::iterator it=_statmap.begin(); it != _statmap.end(); ++it) rval += *it->second; TRACE( TRACE_STATISTICS, "AcctUpd. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.acct_update, rval.failed.acct_update, rval.deadlocked.acct_update); TRACE( TRACE_STATISTICS, "MbenchInsertOnly. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_insert_only, rval.failed.mbench_insert_only, rval.deadlocked.mbench_insert_only); TRACE( TRACE_STATISTICS, "MbenchDeleteOnly. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_delete_only, rval.failed.mbench_delete_only, rval.deadlocked.mbench_delete_only); TRACE( TRACE_STATISTICS, "MbenchProbeOnly. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_probe_only, rval.failed.mbench_probe_only, rval.deadlocked.mbench_probe_only); TRACE( TRACE_STATISTICS, "MbenchInsertDelte. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_insert_delete, rval.failed.mbench_insert_delete, rval.deadlocked.mbench_insert_delete); TRACE( TRACE_STATISTICS, "MbenchInsertProbe. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_insert_probe, rval.failed.mbench_insert_probe, rval.deadlocked.mbench_insert_probe); TRACE( TRACE_STATISTICS, "MbenchDeleteProbe. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_delete_probe, rval.failed.mbench_delete_probe, rval.deadlocked.mbench_delete_probe); TRACE( TRACE_STATISTICS, "MbenchMix. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_mix, rval.failed.mbench_mix, rval.deadlocked.mbench_mix); ShoreEnv::statistics(); return (0); }
rc_t lid_m::generate_new_volid(lvid_t& lvid) { FUNC(lid_m::_generate_new_volid); /* * For now the logical volume ID will consists of * the machine network address and the current time-of-day. * * Since the time of day resolution is in seconds, * we protect this function with a mutex to guarantee we * don't generate duplicates. */ static long last_time = 0; const int max_name = 100; char name[max_name+1]; // Mutex only for generating new volume ids. static queue_based_block_lock_t lidmgnrt_mutex; CRITICAL_SECTION(cs, lidmgnrt_mutex); #ifdef HAVE_UTSNAME struct utsname uts; if (uname(&uts) == -1) return RC(eOS); strncpy(name, uts.nodename, max_name); #else if (gethostname(name, max_name)) return RC(eOS); #endif struct hostent* hostinfo = gethostbyname(name); if (!hostinfo) W_FATAL(eINTERNAL); memcpy(&lvid.high, hostinfo->h_addr, sizeof(lvid.high)); DBG( << "lvid " << lvid ); /* XXXX generating ids fast enough can create a id time sequence that grows way faster than real time! This could be a problem! Better time resolution than seconds does exist, might be worth using it. */ stime_t curr_time = stime_t::now(); if (curr_time.secs() > last_time) last_time = curr_time.secs(); else last_time++; lvid.low = last_time; return RCOK; }
void sthread_t::sleep(timeout_in_ms timeout, const char *reason) { reason = (reason && *reason) ? reason : "sleep"; /* FRJ: even though we could just use the posix sleep() call, we'll stick to the sthreads way and block on a cond var. That way the sthreads debug stuff will keep working. Besides, we're here to waste time, right? */ CRITICAL_SECTION(cs, _wait_lock); _sleeping = true; (void) _block(timeout, reason, this); // W_IGNORE _sleeping = false; }
// checks the map for a specific param // if it doesn't find it checks also the config file string envVar::getVar(const string& sParam, const string& sDefValue) { if (sParam.empty()) { TRACE( TRACE_ALWAYS, "Invalid Param input\n"); return (""); } CRITICAL_SECTION(evm_cs,_lock); envVarIt it = _evm.find(sParam); if (it==_evm.end()) { //TRACE( TRACE_DEBUG, "(%s) param not set. Searching conf\n", sParam.c_str()); return (_readConfVar(sParam,sDefValue)); } return (it->second); }
bool asc_sort_man_impl::get_sorted(const int index, table_row_t* ptuple) { CRITICAL_SECTION(cs, _sorted_lock); if (_is_sorted) { if (index >=0 && index < _tuple_count) { ptuple->load_key(_sort_buf + (index * _tuple_size)); return true; } //TRACE( TRACE_DEBUG, "out of bounds index...\n"); return (false); } TRACE( TRACE_DEBUG, "buffer not sorted yet...\n"); return (false); }
int ShoreTPCCEnv::statistics() { // read the current trx statistics CRITICAL_SECTION(cs, _statmap_mutex); ShoreTPCCTrxStats rval; rval -= rval; // dirty hack to set all zeros for (statmap_t::iterator it=_statmap.begin(); it != _statmap.end(); ++it) rval += *it->second; TRACE( TRACE_STATISTICS, "NewOrder. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.new_order, rval.failed.new_order, rval.deadlocked.new_order); TRACE( TRACE_STATISTICS, "Payment. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.payment, rval.failed.payment, rval.deadlocked.payment); TRACE( TRACE_STATISTICS, "OrderStatus. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.order_status, rval.failed.order_status, rval.deadlocked.order_status); TRACE( TRACE_STATISTICS, "Delivery. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.delivery, rval.failed.delivery, rval.deadlocked.delivery); TRACE( TRACE_STATISTICS, "StockLevel. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.stock_level, rval.failed.stock_level, rval.deadlocked.stock_level); TRACE( TRACE_STATISTICS, "MBenchWh. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_wh, rval.failed.mbench_wh, rval.deadlocked.mbench_wh); TRACE( TRACE_STATISTICS, "MBenchCust. Att (%d). Abt (%d). Dld (%d)\n", rval.attempted.mbench_cust, rval.failed.mbench_cust, rval.deadlocked.mbench_cust); ShoreEnv::statistics(); return (0); }