aldl_comq_t *aldl_get_command() { set_lock(LOCK_COMQ); if(comq == NULL) { unset_lock(LOCK_COMQ); return NULL; /* no command available */ } aldl_comq_t *c = comq; comq = c->next; /* advance to next command */ unset_lock(LOCK_COMQ); return c; /* WARNING you need to free this after you're done with it ... */ }
aldl_record_t *newest_record(aldl_conf_t *aldl) { aldl_record_t *rec = NULL; set_lock(LOCK_RECORDPTR); rec = aldl->r; unset_lock(LOCK_RECORDPTR); return rec; }
void aldl_add_command(byte *command, byte length, int delay) { if(command == NULL) return; /* build new command */ aldl_comq_t *n; /* new command */ n = smalloc(sizeof(aldl_comq_t)); n->length = length; n->delay = delay; n->command = smalloc(sizeof(char) * length); int x; for(x=0;x<length;x++) { /* copy command */ n->command[x] = command[x]; } n->next = NULL; /* link in new command */ set_lock(LOCK_COMQ); if(comq == NULL) { /* no other commands exist */ comq = n; } else { aldl_comq_t *e = comq; /* end of linked list */ while(e->next != NULL) e = e->next; /* seek end */ e->next = n; } unset_lock(LOCK_COMQ); }
void set_connstate(aldl_state_t s, aldl_conf_t *aldl) { set_lock(LOCK_CONNSTATE); #ifdef DEBUGSTRUCT printf("set connection state to %i (%s)\n",s,get_state_string(s)); #endif aldl->state = s; unset_lock(LOCK_CONNSTATE); }
void link_record(aldl_record_t *rec, aldl_conf_t *aldl) { rec->next = NULL; /* terminate linked list */ rec->prev = aldl->r; /* previous link */ set_lock(LOCK_RECORDPTR); aldl->r->next = rec; /* attach to linked list */ aldl->r = rec; /* fix master link */ unset_lock(LOCK_RECORDPTR); }
void dlthread_unexclude( dlthread_comm_t const comm_idx) { comm_t * gcomm; if (comm_idx != DLTHREAD_COMM_SINGLE) { gcomm = my_comms+comm_idx; unset_lock(&gcomm->loc); } }
void aldl_data_init(aldl_conf_t *aldl) { aldl_alloc_pool(aldl); aldl_record_t *rec = aldl_create_record(aldl); set_lock(LOCK_RECORDPTR); rec->next = NULL; rec->prev = NULL; aldl->r = rec; unset_lock(LOCK_RECORDPTR); firstrecordtime = get_time(); comq = NULL; /* no records yet */ }
aldl_record_t *next_record(aldl_record_t *rec) { #ifdef DEBUGSTRUCT /* check for underrun ... */ if(rec->prev == NULL) { error(1,ERROR_BUFFER,"underrun in record retrieve %p",rec); } #endif aldl_record_t *next; set_lock(LOCK_RECORDPTR); next = rec->next; unset_lock(LOCK_RECORDPTR); return next; }
void dlthread_comm_finalize( dlthread_comm_t const comm_idx) { size_t i, myid; comm_t * comm; if (comm_idx != DLTHREAD_COMM_SINGLE) { myid = dlthread_get_id(comm_idx); dlthread_barrier(comm_idx); comm = my_comms+comm_idx; if (comm->larray) { /* destroy locks if they exist */ for (i=0;i<comm->nlarray;++i) { free_lock(comm->larray[myid]+i); } dl_free(comm->larray[myid]); dlthread_barrier(comm_idx); if (myid == 0) { dl_free(comm->larray); } } if (myid == 0) { dl_free(comm->buffer); free_barrier(&(comm->bar)); free_lock(&(comm->loc)); comm->in_use = 0; set_lock(ncomms_lock); if (comm_idx < last_free_comm) { last_free_comm = comm_idx; } unset_lock(ncomms_lock); } } else { /* clear this threads local buffer if it exists */ if (__local_buffer) { dl_free(__local_buffer); __local_buffer = NULL; __local_buffer_size = 0; } } }
void dlthread_unlock_index( size_t const tid, size_t const idx, dlthread_comm_t const comm_idx) { size_t i; comm_t * gcomm; if (comm_idx != DLTHREAD_COMM_SINGLE) { gcomm = my_comms+comm_idx; i = idx % gcomm->nlarray; unset_lock(gcomm->larray[tid]+i); } }
dlthread_comm_t dlthread_comm_split( size_t group, size_t ngroups, dlthread_comm_t const comm_idx) { size_t i, lid, cidx, myid, nthreads; size_t volatile * tid; comm_t * lcomm; dlthread_comm_t volatile * gcom; dlthread_comm_t cid; if (comm_idx != DLTHREAD_COMM_SINGLE) { myid = dlthread_get_id(comm_idx); nthreads = dlthread_get_nthreads(comm_idx); DL_ASSERT(group < ngroups,"Invalid group %zu/%zu for thread %zu/%zu\n", \ group,ngroups,myid,nthreads); gcom = dlthread_get_buffer((sizeof(dlthread_comm_t)*ngroups) + \ (sizeof(size_t)*nthreads),comm_idx); tid = (size_t*)(gcom+ngroups); if (myid == 0) { /* number the new communicators */ set_lock(ncomms_lock); for (i=0;i<ngroups;++i) { /* find the next free communicator */ while (my_comms[last_free_comm].in_use == 1) { ++last_free_comm; } gcom[i] = last_free_comm++; /* initialize my comm */ my_comms[gcom[i]].nthreads = 0; my_comms[gcom[i]].in_use = 1; } unset_lock(ncomms_lock); } /* I use an alarming number of barriers here -- someday reduce this */ dlthread_barrier(comm_idx); cid = gcom[group]; DL_ASSERT(cid < __MAX_NCOMMS,"Exceeded maximum number of communicators\n"); lcomm = my_comms+cid; tid[myid] = group; dlthread_barrier(comm_idx); if (myid == 0) { /* number the threads per communicator */ for (i=0;i<nthreads;++i) { cidx = gcom[tid[i]]; tid[i] = my_comms[cidx].nthreads++; } } dlthread_barrier(comm_idx); lid = tid[myid]; if (lid == 0) { /* root for each comm */ __config_comm(lcomm,lcomm->nthreads); } my_ids[cid] = lid; dlthread_barrier(comm_idx); dprintf("[%zu:%zu] new communicator %zu with %zu threads\n",myid,lid, \ (size_t)cid,lcomm->nthreads); } else { cid = DLTHREAD_COMM_SINGLE; } return cid; }
void dlthread_unset_lock( dlthread_lock_t * const lock) { unset_lock(lock); }
void unlock_stats() { unset_lock(LOCK_STATS); }
aldl_state_t get_connstate(aldl_conf_t *aldl) { set_lock(LOCK_CONNSTATE); aldl_state_t st = aldl->state; unset_lock(LOCK_CONNSTATE); return st; }