Esempio n. 1
0
OBJECT_ID iter_NextNow(ITER_ID iter_id,VM_ID vm_id)
{
	OBJECT_ID next = iter_Next(iter_id,vm_id);
	if(obj_GetType(next) == TYPE_BLOCK) //used only to differentiate between an object to return and a generator not finished
	{
		struct _vm *vm = (struct _vm*)mem_lock(vm_id);
		iter_object *iter = (iter_object*)mem_lock(iter_id);
		OBJECT_ID ret = 0;
		BLOCK_ID bo = iter->tag;
		iter_RestoreBlockStack(iter_id,vm_id);
		obj_IncRefCount(iter_id);
		
		while(ret == 0)//TODO doesnt stop after one block
		{
			ret = vm_Step(vm_id,0);
			if(!stack_Contains(vm->blocks,bo)) //via normal return 
			//TODO switch to integer comparison to block stack num with the block stack num at the beginning
			{
				BLOCK_ID n = stack_Top(vm->blocks);
				if(!stack_IsEmpty(vm->blocks))
				{
					block_object *bn = (block_object*)mem_lock(n);
					ret = stack_Pop(bn->stack);
					mem_unlock(n,0);
				}	
				iter_ClearBlockStack(iter_id,vm_id);
				break;
			}
			else if(ret != 0) //via yield 
			{
				iter_SaveBlockStack(iter_id,vm_id);
				obj_DecRefCount(ret);
			}
		}
		mem_unlock(iter_id,0);
		mem_unlock(vm_id,0);
		obj_DecRefCount(iter_id);
		return(ret);
	}
	obj_DecRefCount(next);
	return(next);
}
Esempio n. 2
0
static int kbo_CompVarCondAndWeight(TERM Term1, BOOL *VarCond1, TERM Term2, BOOL *VarCond2)
/**************************************************************
  INPUT:   Two terms and two pointers to booleans.
  EFFECT:  Sets the booleans with respect to the kbo variable condition.
           Computes the kbo weight difference.
***************************************************************/
{
    SYMBOL MaxVar1,MaxVar2;
    TERM   Term;
    LIST   Scan;
    int    i,Stack,Weight;

    *VarCond1 = *VarCond2 = TRUE;
    MaxVar1   = term_MaxVar(Term1);
    MaxVar2   = term_MaxVar(Term2);
    Stack     = stack_Bottom();
    Weight    = 0;

    if (MaxVar1 < MaxVar2)
        MaxVar1 = MaxVar2;

    for (i = 0; i <= MaxVar1; i++) {
        ord_VARCOUNT[i][0] = 0;
        ord_VARCOUNT[i][1] = 0;
    }

    Term = Term1;
    if (term_IsStandardVariable(Term)) {
        ord_VARCOUNT[term_TopSymbol(Term)][0]++;
        Weight += kbo_MINWEIGHT;
    }
    else {
        Weight += symbol_Weight(term_TopSymbol(Term));
        if (term_IsComplex(Term))
            stack_Push(term_ArgumentList(Term));
    }
    while (!stack_Empty(Stack)) {
        Scan = stack_Top();
        Term = (TERM)list_Car(Scan);
        stack_RplacTop(list_Cdr(Scan));
        if (term_IsStandardVariable(Term)) {
            Weight += kbo_MINWEIGHT;
            ord_VARCOUNT[term_TopSymbol(Term)][0]++;
        }
        else {
            Weight += symbol_Weight(term_TopSymbol(Term));
            if (term_IsComplex(Term))
                stack_Push(term_ArgumentList(Term));
        }
        while (!stack_Empty(Stack) && list_Empty(stack_Top()))
            stack_Pop();
    }

    Term = Term2;
    if (term_IsStandardVariable(Term)) {
        Weight -= kbo_MINWEIGHT;
        ord_VARCOUNT[term_TopSymbol(Term)][1]++;
    }
    else {
        Weight -= symbol_Weight(term_TopSymbol(Term));
        if (term_IsComplex(Term))
            stack_Push(term_ArgumentList(Term));
    }
    while (!stack_Empty(Stack)) {
        Scan = stack_Top();
        Term = (TERM)list_Car(Scan);
        stack_RplacTop(list_Cdr(Scan));
        if (term_IsStandardVariable(Term)) {
            Weight -= kbo_MINWEIGHT;
            ord_VARCOUNT[term_TopSymbol(Term)][1]++;
        }
        else {
            Weight -= symbol_Weight(term_TopSymbol(Term));
            if (term_IsComplex(Term))
                stack_Push(term_ArgumentList(Term));
        }
        while (!stack_Empty(Stack) && list_Empty(stack_Top()))
            stack_Pop();
    }

    for (i = 0; i <= MaxVar1; i++) {
        if (ord_VARCOUNT[i][0] < ord_VARCOUNT[i][1]) {
            *VarCond1 = FALSE;
            if (!*VarCond2)
                return Weight;
        }
        if (ord_VARCOUNT[i][0] > ord_VARCOUNT[i][1]) {
            *VarCond2 = FALSE;
            if (!*VarCond1)
                return Weight;
        }
    }
    return Weight;
}