int q_share_work(int worker_p) { LOCK_OR_FRAME(LOCAL_top_or_fr); if (Get_REMOTE_prune_request(worker_p)) { /* worker p with prune request */ UNLOCK_OR_FRAME(LOCAL_top_or_fr); return FALSE; } #ifdef YAPOR_ERRORS if (OrFr_pend_prune_cp(LOCAL_top_or_fr) && BRANCH_LTT(worker_p, OrFr_depth(LOCAL_top_or_fr)) < OrFr_pend_prune_ltt(LOCAL_top_or_fr)) YAPOR_ERROR_MESSAGE("prune ltt > worker_p branch ltt (q_share_work)"); #endif /* YAPOR_ERRORS */ /* there is no pending prune with worker p at right --> safe move to worker p branch */ BRANCH(worker_id, OrFr_depth(LOCAL_top_or_fr)) = BRANCH(worker_p, OrFr_depth(LOCAL_top_or_fr)); LOCAL_prune_request = NULL; UNLOCK_OR_FRAME(LOCAL_top_or_fr); /* make sharing request */ LOCK_WORKER(worker_p); if (BITMAP_member(GLOBAL_bm_idle_workers, worker_p) || REMOTE_share_request(worker_p) != MAX_WORKERS) { /* worker p is idle or has another request */ UNLOCK_WORKER(worker_p); return FALSE; } REMOTE_share_request(worker_p) = worker_id; UNLOCK_WORKER(worker_p); /* wait for an answer */ while (LOCAL_reply_signal == ready); if (LOCAL_reply_signal == no_sharing) { /* sharing request refused */ LOCAL_reply_signal = ready; return FALSE; } /* exit this process */ exit(0); }
int q_share_work(int worker_p) { register tr_fr_ptr aux_tr; register CELL aux_cell; LOCK_OR_FRAME(LOCAL_top_or_fr); if (REMOTE_prune_request(worker_p)) { /* worker p with prune request */ UNLOCK_OR_FRAME(LOCAL_top_or_fr); return FALSE; } YAPOR_ERROR_CHECKING(q_share_work, Get_OrFr_pend_prune_cp(LOCAL_top_or_fr) && BRANCH_LTT(worker_p, OrFr_depth(LOCAL_top_or_fr)) < OrFr_pend_prune_ltt(LOCAL_top_or_fr)); /* there is no pending prune with worker p at right --> safe move to worker p branch */ CUT_reset_prune_request(); if(Get_LOCAL_prune_request()){ UNLOCK_OR_FRAME(LOCAL_top_or_fr); return FALSE; } BRANCH(worker_id, OrFr_depth(LOCAL_top_or_fr)) = BRANCH(worker_p, OrFr_depth(LOCAL_top_or_fr)); UNLOCK_OR_FRAME(LOCAL_top_or_fr); /* unbind variables */ aux_tr = LOCAL_top_cp->cp_tr; TABLING_ERROR_CHECKING(q_share_work, TR < aux_tr); while (aux_tr != TR) { aux_cell = TrailTerm(--TR); /* check for global or local variables */ if (IsVarTerm(aux_cell)) { RESET_VARIABLE(aux_cell); #ifdef TABLING } else if (IsPairTerm(aux_cell)) { aux_cell = (CELL) RepPair(aux_cell); if (IN_BETWEEN(LOCAL_TrailBase, aux_cell, LOCAL_TrailTop)) { /* avoid frozen segments */ TR = (tr_fr_ptr) aux_cell; TABLING_ERROR_CHECKING(q_share_work, TR > (tr_fr_ptr) LOCAL_TrailTop); TABLING_ERROR_CHECKING(q_share_work, TR < aux_tr); } #endif /* TABLING */ #ifdef MULTI_ASSIGNMENT_VARIABLES } else if (IsApplTerm(aux_cell)) { CELL *aux_ptr = RepAppl(aux_cell); Term aux_val = TrailTerm(--aux_tr); *aux_ptr = aux_val; #endif /* MULTI_ASSIGNMENT_VARIABLES */ } } OPTYAP_ERROR_CHECKING(q_share_work, LOCAL_top_cp != LOCAL_top_cp_on_stack); OPTYAP_ERROR_CHECKING(q_share_work, YOUNGER_CP(B_FZ, LOCAL_top_cp)); YAPOR_ERROR_CHECKING(q_share_work, LOCAL_reply_signal != worker_ready); /* make sharing request */ LOCK_WORKER(worker_p); if (BITMAP_member(GLOBAL_bm_idle_workers, worker_p) || REMOTE_share_request(worker_p) != MAX_WORKERS) { /* worker p is idle or has another request */ UNLOCK_WORKER(worker_p); return FALSE; } REMOTE_share_request(worker_p) = worker_id; UNLOCK_WORKER(worker_p); /* wait for an answer */ while (LOCAL_reply_signal == worker_ready); if (LOCAL_reply_signal == no_sharing) { /* sharing request refused */ LOCAL_reply_signal = worker_ready; return FALSE; } /* copy trail stack ? */ LOCK(LOCAL_lock_signals); if (LOCAL_p_fase_signal > trail) { LOCAL_q_fase_signal = trail; UNLOCK(LOCAL_lock_signals); Q_COPY_TRAIL_FROM(worker_p); } else { UNLOCK(LOCAL_lock_signals); goto sync_with_p; } /* copy global stack ? */ LOCK(LOCAL_lock_signals); if (LOCAL_p_fase_signal > global) { LOCAL_q_fase_signal = global; UNLOCK(LOCAL_lock_signals); Q_COPY_GLOBAL_FROM(worker_p); } else { UNLOCK(LOCAL_lock_signals); goto sync_with_p; } /* copy local stack ? */ while (LOCAL_reply_signal < nodes_shared); LOCK(LOCAL_lock_signals); if (LOCAL_p_fase_signal > local) { LOCAL_q_fase_signal = local; UNLOCK(LOCAL_lock_signals); Q_COPY_LOCAL_FROM(worker_p); } else UNLOCK(LOCAL_lock_signals); sync_with_p: #ifdef TABLING REMOTE_reply_signal(worker_p) = worker_ready; #else REMOTE_reply_signal(worker_p) = copy_done; #endif /* TABLING */ while (LOCAL_reply_signal != copy_done); #if INCREMENTAL_COPY /* install fase --> TR and LOCAL_top_cp->cp_tr are equal */ aux_tr = ((choiceptr) LOCAL_start_local_copy)->cp_tr; TR = ((choiceptr) LOCAL_end_local_copy)->cp_tr; Yap_NEW_MAHASH((ma_h_inner_struct *)HR); while (TR != aux_tr) { aux_cell = TrailTerm(--aux_tr); if (IsVarTerm(aux_cell)) { if (aux_cell < LOCAL_start_global_copy || EQUAL_OR_YOUNGER_CP((choiceptr)LOCAL_end_local_copy, (choiceptr)aux_cell)) { YAPOR_ERROR_CHECKING(q_share_work, (CELL *)aux_cell < H0); YAPOR_ERROR_CHECKING(q_share_work, (ADDR)aux_cell > LOCAL_LocalBase); #ifdef TABLING *((CELL *) aux_cell) = TrailVal(aux_tr); #else *((CELL *) aux_cell) = *((CELL *) (worker_offset(worker_p) + aux_cell)); #endif /* TABLING */ } #ifdef TABLING } else if (IsPairTerm(aux_cell)) { aux_cell = (CELL) RepPair(aux_cell); if (IN_BETWEEN(LOCAL_TrailBase, aux_cell, LOCAL_TrailTop)) { /* avoid frozen segments */ aux_tr = (tr_fr_ptr) aux_cell; } #endif /* TABLING */ #ifdef MULTI_ASSIGNMENT_VARIABLES } else if (IsApplTerm(aux_cell)) { CELL *cell_ptr = RepAppl(aux_cell); if (((CELL *)aux_cell < LOCAL_top_cp->cp_h || EQUAL_OR_YOUNGER_CP(LOCAL_top_cp, (choiceptr)aux_cell)) && !Yap_lookup_ma_var(cell_ptr)) { /* first time we found the variable, let's put the new value */ #ifdef TABLING *cell_ptr = TrailVal(aux_tr); #else *cell_ptr = *((CELL *) (worker_offset(worker_p) + (CELL)cell_ptr)); #endif /* TABLING */ } /* skip the old value */ aux_tr--; #endif /* MULTI_ASSIGNMENT_VARIABLES */ } } #endif /* incremental */ /* update registers and return */ PUT_OUT_ROOT_NODE(worker_id); #ifndef TABLING REMOTE_reply_signal(worker_p) = worker_ready; #endif /* TABLING */ TR = (tr_fr_ptr) LOCAL_end_trail_copy; LOCAL_reply_signal = worker_ready; PUT_IN_REQUESTABLE(worker_id); #ifdef TABLING adjust_freeze_registers(); #endif /* TABLING */ return TRUE; }
void Yap_init_local_optyap_data(int wid) { #if defined(YAPOR_THREADS) || defined(THREADS_CONSUMER_SHARING) CACHE_REGS #endif /* YAPOR_THREADS || THREADS_CONSUMER_SHARING */ #if defined(TABLING) && (defined(YAPOR) || defined(THREADS)) /* local data related to memory management */ #ifdef YAPOR REMOTE_next_free_ans_node(wid) = NULL; #elif THREADS #ifdef USE_PAGES_MALLOC INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_void(wid), void *); #endif INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_tab_ent(wid), struct table_entry); #if defined(THREADS_FULL_SHARING) || defined(THREADS_CONSUMER_SHARING) INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_sg_ent(wid), struct subgoal_entry); #endif INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_sg_fr(wid), struct subgoal_frame); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_dep_fr(wid), struct dependency_frame); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_sg_node(wid), struct subgoal_trie_node); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_sg_hash(wid), struct subgoal_trie_hash); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_ans_node(wid), struct answer_trie_node); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_ans_hash(wid), struct answer_trie_hash); #if defined(THREADS_FULL_SHARING) INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_ans_ref_node(wid), struct answer_ref_node); #endif INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_gt_node(wid), struct global_trie_node); INIT_LOCAL_PAGE_ENTRY(REMOTE_pages_gt_hash(wid), struct global_trie_hash); #endif #endif /* TABLING && (YAPOR || THREADS) */ #ifdef YAPOR /* local data related to or-parallelism */ Set_REMOTE_top_cp(wid, (choiceptr)LOCAL_LocalBase); REMOTE_top_or_fr(wid) = GLOBAL_root_or_fr; REMOTE_load(wid) = 0; REMOTE_share_request(wid) = MAX_WORKERS; REMOTE_reply_signal(wid) = worker_ready; #ifdef YAPOR_COPY INIT_LOCK(REMOTE_lock_signals(wid)); #endif /* YAPOR_COPY */ Set_REMOTE_prune_request(wid, NULL); INIT_LOCK(REMOTE_lock(wid)); #endif /* YAPOR */ #ifdef TABLING /* local data related to tabling */ REMOTE_top_sg_fr(wid) = NULL; REMOTE_top_dep_fr(wid) = NULL; #ifdef YAPOR REMOTE_top_dep_fr(wid) = GLOBAL_root_dep_fr; Set_REMOTE_top_cp_on_stack(wid, (choiceptr)LOCAL_LocalBase); /* ??? */ REMOTE_top_susp_or_fr(wid) = GLOBAL_root_or_fr; #endif /* YAPOR */ #ifdef THREADS_CONSUMER_SHARING ThDepFr_terminator(GLOBAL_th_dep_fr(wid)) = 0; ThDepFr_next(GLOBAL_th_dep_fr(wid)) = wid; ThDepFr_state(GLOBAL_th_dep_fr(wid)) = working; INIT_LOCK(ThDepFr_lock(GLOBAL_th_dep_fr(wid))); #endif /* THREADS_CONSUMER_SHARING */ #endif /* TABLING */ return; }
int q_share_work(int worker_p) { register tr_fr_ptr aux_tr; register CELL aux_cell; LOCK_OR_FRAME(LOCAL_top_or_fr); if (Get_REMOTE_prune_request(worker_p)) { /* worker p with prune request */ UNLOCK_OR_FRAME(LOCAL_top_or_fr); return FALSE; } YAPOR_ERROR_CHECKING(q_share_work, OrFr_pend_prune_cp(LOCAL_top_or_fr) && BRANCH_LTT(worker_p, OrFr_depth(LOCAL_top_or_fr)) < OrFr_pend_prune_ltt(LOCAL_top_or_fr)); /* there is no pending prune with worker p at right --> safe move to worker p branch */ BRANCH(worker_id, OrFr_depth(LOCAL_top_or_fr)) = BRANCH(worker_p, OrFr_depth(LOCAL_top_or_fr)); LOCAL_prune_request = NULL; UNLOCK_OR_FRAME(LOCAL_top_or_fr); reset_trail(LOCAL_top_cp->cp_tr, TR); TR = LOCAL_top_cp->cp_tr; /* make sharing request */ LOCK_WORKER(worker_p); if (BITMAP_member(GLOBAL_bm_idle_workers, worker_p) || REMOTE_share_request(worker_p) != MAX_WORKERS) { /* worker p is idle or has another request */ UNLOCK_WORKER(worker_p); return FALSE; } REMOTE_share_request(worker_p) = worker_id; UNLOCK_WORKER(worker_p); /* wait for an answer */ while (LOCAL_reply_signal == worker_ready); if (LOCAL_reply_signal == no_sharing) { /* sharing request refused */ LOCAL_reply_signal = worker_ready; return FALSE; } /* install fase --> TR and LOCAL_top_cp->cp_tr are equal */ TR = ((choiceptr)LOCAL_end_local_copy)->cp_tr; aux_tr = ((choiceptr) LOCAL_start_local_copy)->cp_tr; NEW_MAHASH((ma_h_inner_struct *)H); while (TR != aux_tr) { aux_cell = TrailTerm(--aux_tr); if (IsVarTerm(aux_cell)) { CELL *ptr = STACK_TO_SBA(aux_cell); *ptr = TrailVal(aux_tr); } else if ((ADDR) RepPair(aux_cell) >= HeapTop) { /* avoid frozen segments */ aux_tr = (tr_fr_ptr) RepPair(aux_cell); #ifdef MULTI_ASSIGNMENT_VARIABLES } else if (IsApplTerm(aux_cell)) { CELL *cell_ptr = RepAppl(aux_cell); if (!lookup_ma_var(cell_ptr)) { /* first time we found the variable, let's put the new value */ CELL *ptr = STACK_TO_SBA(cell_ptr); *ptr = TrailVal(aux_tr); } /* skip the old value */ aux_tr--; } #endif /* MULTI_ASSIGNMENT_VARIABLES */ } /* update registers and return */ /* REMOTE_reply_signal(worker_p) = worker_ready; */ LOCAL_reply_signal = worker_ready; PUT_IN_REQUESTABLE(worker_id); TR = LOCAL_top_cp->cp_tr; return TRUE; }