complete_xsb_i.h

00001 /* File:      complete_xsb_i.h
00002 ** Author(s): Juliana Freire, Kostis Sagonas, Terry Swift
00003 ** Contact:   xsb-contact@cs.sunysb.edu
00004 ** 
00005 ** Copyright (C) The Research Foundation of SUNY, 1986, 1993-1998
00006 ** 
00007 ** XSB is free software; you can redistribute it and/or modify it under the
00008 ** terms of the GNU Library General Public License as published by the Free
00009 ** Software Foundation; either version 2 of the License, or (at your option)
00010 ** any later version.
00011 ** 
00012 ** XSB is distributed in the hope that it will be useful, but WITHOUT ANY
00013 ** WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
00014 ** FOR A PARTICULAR PURPOSE.  See the GNU Library General Public License for
00015 ** more details.
00016 ** 
00017 ** You should have received a copy of the GNU Library General Public License
00018 ** along with XSB; if not, write to the Free Software Foundation,
00019 ** Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00020 **
00021 ** $Id: complete_xsb_i.h,v 1.30 2005/11/07 20:37:41 tswift Exp $
00022 ** 
00023 */
00024 
00025 /* special debug includes */
00026 #include "debugs/debug_delay.h"
00027 
00028 #define FailIfAnswersFound(func) \
00029 { \
00030   CPtr tmp_breg; \
00031   if ((tmp_breg = func)) { \
00032     breg = tmp_breg; \
00033     Fail1; \
00034     XSB_Next_Instr(); \
00035   } \
00036 }
00037 
00038 #define check_fixpoint(sg, b)    find_fixpoint(CTXTc sg, b)
00039 
00040 #define find_leader(cs_ptr)                                             \
00041   while (!(prev_compl_frame(cs_ptr) >= COMPLSTACKBOTTOM                 \
00042            || is_leader(cs_ptr))) {                                     \
00043     cs_ptr = prev_compl_frame(cs_ptr);                                  \
00044       }
00045 
00046 /*----------------------------------------------------------------------*/
00047 
00048 XSB_Start_Instr(check_complete,_check_complete)
00049   CPtr    cs_ptr;
00050 #ifdef CONC_COMPL 
00051   CPtr  new_leader;
00052   CPtr  tmp_breg ;
00053   int busy ;
00054   switch_envs(breg);    /* in CHAT: undo_bindings() */
00055   ptcpreg = tcp_ptcp(breg);
00056   delayreg = tcp_pdreg(breg);
00057 
00058   xsb_dbgmsg((LOG_DEBUG,"Check complete %x",breg));
00059 
00060   cs_ptr = tcp_compl_stack_ptr(breg);
00061   pthread_mutex_lock(&completing_mut);
00062   for(;;)
00063   {
00064         if (prev_compl_frame(cs_ptr) < COMPLSTACKBOTTOM && !is_leader(cs_ptr))
00065         {
00066                 breg = tcp_prevbreg(breg); 
00067                 break ;
00068         }
00069         if( (tmp_breg = check_fixpoint(cs_ptr,breg)) )
00070         {
00071                 th->last_ans++;
00072                 breg = tmp_breg ;
00073                 break ;
00074         }
00075         new_leader = cs_ptr ;
00076 
00077         UpdateDeps( th, &busy, &new_leader ) ;
00078 
00079         if( new_leader > cs_ptr )
00080         {
00081                 adjust_level(new_leader) ;
00082                 breg = tcp_prevbreg(breg); 
00083                 break ;
00084         }
00085 
00086         if( EmptyThreadDepList(&th->TDL) )
00087         {       CPtr orig_breg = breg;  
00088                 batched_compute_wfs(CTXTc cs_ptr, breg, 
00089                                 (VariantSF)tcp_subgoal_ptr(breg));
00090                 if (openreg == prev_compl_frame(cs_ptr))
00091                 {       if (breg == orig_breg)
00092                         {       reclaim_stacks(orig_breg);
00093                                 breg = tcp_prevbreg(breg);
00094                 }       }
00095                 pthread_mutex_unlock(&completing_mut);
00096                 Fail1;
00097                 XSB_Next_Instr();
00098         }
00099         
00100         if( !busy )
00101         {       
00102 
00103                 if( MayHaveAnswers(th) )
00104                         WakeOtherThreads(th) ;
00105                 else if( CheckForSCC(th) )
00106                 {
00107                         CompleteOtherThreads(th);
00108                         CompleteTop(th, cs_ptr);
00109                         break;
00110                 }
00111                 else
00112                         WakeOtherThreads(th) ;
00113         }
00114 
00115         th->completing = TRUE ;
00116         th->completed = FALSE ;
00117         th->cc_leader = cs_ptr ;
00118         pthread_cond_wait(&th->cond_var, &completing_mut) ;
00119         th->completing = FALSE ;
00120         if( th->completed )
00121                 break ;
00122   }
00123   pthread_mutex_unlock(&completing_mut);
00124 #else /* not CONC_COMPL */
00125   CPtr    orig_breg = breg;
00126   xsbBool leader = FALSE;
00127   VariantSF subgoal;
00128 
00129   /* this CP has exhausted program resolution -- backtracking occurs */
00130   switch_envs(breg);    /* in CHAT: undo_bindings() */
00131   ptcpreg = tcp_ptcp(breg);
00132   delayreg = tcp_pdreg(breg);
00133 
00134   subgoal = (VariantSF) tcp_subgoal_ptr(breg);  /* subgoal that is checked */
00135 
00136 /*   print_subgoal(stderr, subgoal);  */
00137 
00138   cs_ptr = subg_compl_stack_ptr(subgoal);
00139 
00140   if ((prev_compl_frame(cs_ptr) >= COMPLSTACKBOTTOM || is_leader(cs_ptr))) {
00141     leader = 1;
00142   }
00143   
00144 /* 
00145  * This code is done regardless of whether breg is a leader.  The
00146  * thought was that as long as we're here, why not schedule answers
00147  * for this subgoal.  Its purely a heuristic -- perhaps we should test
00148  * to see whether its inclusion makes any difference 
00149  */
00150   FailIfAnswersFound(sched_answers(CTXTc subgoal, NULL));
00151 
00152   if (leader) {
00153 
00154     /* The following code is only done in profile mode; it keeps track
00155      * of characteristics of SCCs */
00156 
00157     /* ProfileLeader; */
00158     /* SpitOutGraph(cs_ptr); */
00159     /* check if fixpoint has been reached, otherwise schedule any
00160      * unresolved answers */
00161     FailIfAnswersFound(check_fixpoint(cs_ptr,breg));
00162 
00163 #ifdef LOCAL_EVAL
00164     {
00165       CPtr cc_tbreg = orig_breg;
00166       
00167       breg = orig_breg; /* mark topmost SCC as completed */
00168       
00169       /* schedule completion suspensions if any */
00170       cc_tbreg = ProcessSuspensionFrames(CTXTc cc_tbreg, cs_ptr);
00171       FailIfAnswersFound((cc_tbreg == orig_breg ? 0 : cc_tbreg));
00172       
00173 #ifdef SHARED_COMPL_TABLES
00174     pthread_mutex_lock(&completing_mut);
00175 #endif
00176       CompleteSimplifyAndReclaim(CTXTc cs_ptr);
00177 #ifdef SHARED_COMPL_TABLES
00178     pthread_cond_broadcast(&completing_cond);
00179     pthread_mutex_unlock(&completing_mut);
00180 #endif
00181 
00182     /* TLS: not sure about condition: how could subg_answers be true
00183        and has_answer_code be false? */
00184       /* leader has non-returned answers? */
00185       if (has_answer_code(subgoal) && (subg_answers(subgoal) > COND_ANSWERS)) {
00186         reclaim_incomplete_table_structs(subgoal);
00187         /* schedule return of answers from trie code */
00188         SetupReturnFromLeader(CTXTc orig_breg, cs_ptr, subgoal);
00189         lpcreg = (byte *) subg_ans_root_ptr(subgoal);
00190         XSB_Next_Instr();
00191       } else {  /* There are no answers to return */
00192         reclaim_incomplete_table_structs(subgoal);
00193         /* there is nothing else to be done for this SCC */
00194         cc_tbreg = tcp_prevbreg(orig_breg); /* go to prev SCC */
00195         openreg = prev_compl_frame(cs_ptr); 
00196         reclaim_stacks(orig_breg);
00197       } 
00198       breg = cc_tbreg; /* either orig, prev_cp or compl_susp */
00199     }
00200     
00201 #else /* NOT LOCAL:  FOR BATCHED SCHEDULING */
00202 
00203     batched_compute_wfs(CTXTc cs_ptr, orig_breg, subgoal);
00204 
00205     /* do all possible stack reclamation */
00206     if (openreg == prev_compl_frame(cs_ptr)) {
00207       if (breg == orig_breg) {  
00208         reclaim_stacks(orig_breg); /* lfcastro */
00209         breg = tcp_prevbreg(breg);
00210       }
00211     }
00212 
00213 #endif /* ifdef LOCAL_EVAL */
00214 
00215   }
00216   else {    /* if not leader */
00217     CPtr tmp_breg = breg;
00218     CPtr tmp_cs_ptr = cs_ptr;
00219 
00220 #ifdef LOCAL_EVAL
00221     makeConsumerFromGenerator(CTXTc subgoal);
00222 /*     subg_cp_ptr(subgoal) = NULL; */
00223 #endif
00224     breg = tcp_prevbreg(breg); 
00225     
00226     /* in the case where we backtrack to a check_complete instruction
00227      * for a subtoal that is not the leader, we need to set its
00228      * prevbreg value to the leader.  Otherwise, we could end up
00229      * backtracking into the same choice point multiple times --
00230      * incorrectly if we have a cut. */
00231 
00232     find_leader(tmp_cs_ptr); 
00233     tcp_prevbreg(tmp_breg) = subg_cp_ptr(compl_subgoal_ptr(tmp_cs_ptr));
00234 
00235     xsb_dbgmsg((LOG_SCHED,"backtracking from check complete to: %x @breg %x\n",
00236                   breg,*tcp_pcreg(breg)));
00237 
00238     /* since the trail condition registers are not reset in
00239      * tabletrust for local, they should be restored here
00240      */
00241 #ifdef LOCAL_EVAL
00242     hbreg = tcp_hreg(breg);
00243     ebreg = tcp_ebreg(breg);
00244 #endif
00245   }
00246 #endif /* CONC_COMPL */
00247   Fail1;
00248 XSB_End_Instr()
00249 /* end of check_complete */

Generated on Wed Jul 26 13:30:40 2006 for XSB by  doxygen 1.4.5