diff --git a/Makefile.in b/Makefile.in new file mode 100644 index 0000000..c80058c --- /dev/null +++ b/Makefile.in @@ -0,0 +1,350 @@ +# FileName [ Makefile.in ] +# +# PackageName [ glu ] +# +# Synopsis [ Package-wide Makefile ] +# +# Description [ This file requires GNU's make program. +# Run "configure" to generate the Makefile, or use +# "config.status" (created by configure) to regenerate the +# Makefile after modifying this file. +# +# Type "gmake help" for a list of valid targets. ] +# +# SeeAlso [ configure.in ] +# +# Author [ Rajeev K. Ranjan (Modified from the file written by +# Stephen Edwards ] +# +# Copyright [ +# Copyright (c) 1994-1998 The Regents of the Univ. of California. +# All rights reserved. +# +# Permission is hereby granted, without written agreement and without license +# or royalty fees, to use, copy, modify, and distribute this software and its +# documentation for any purpose, provided that the above copyright notice and +# the following two paragraphs appear in all copies of this software. +# +# IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR +# DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT +# OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF +# CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +# THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, +# INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND +# FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN +# "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE +# MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. +# ] +# +# Default target: + +.PHONY : default + +default : all + +#---------------------------------------------------------------------- +# This Makefile is designed for three different situations: +# +# 1. Single platform build (the default) +# +# All packages listed in the PKGS variable +# local_srcdir = master_srcdir = . +# +# 2. Multi-platform build +# +# All packages listed in the PKGS variable +# local_srcdir = master_srcdir = /where/source/files/reside +# + +#---------------------------------------------------------------------- +# For safety +#---------------------------------------------------------------------- + +SHELL = /bin/sh +.SUFFIXES: + +#---------------------------------------------------------------------- +# The name of the product and its version +#---------------------------------------------------------------------- + +PRODUCT = cal +VERSION = 2.1 + +#---------------------------------------------------------------------- +# Source directories +#---------------------------------------------------------------------- + +# Directory containing master source files. This directory is searched +# for packages NOT listed in the PKGS variable. Defaults to "." +# Override with ./configure --srcdir= +master_srcdir = @srcdir@ + +# Directory containing local source files. This directory is searched +# for packages listed in the PKGS variable. Defaults to the master source +# directory (see above). +# Override with ./configure --with-local-srcdir= +local_srcdir = @local_srcdir@ + +#---------------------------------------------------------------------- +# Directories used while building +#---------------------------------------------------------------------- + +# Directory where object files will be placed during the build +objectdir = . + + +#---------------------------------------------------------------------- +# Installation names and directories +#---------------------------------------------------------------------- + +# Name of the library to create +LIBRARY = lib$(PRODUCT).a + +# Directory in which to install architecture-independent files +# Set by ./configure --prefix=... +prefix = @prefix@ + +# Directory in which to install architecture-dependent files +# Set by ./configure --exec-prefix=... +exec_prefix = @exec_prefix@ + +# Directory in which to install libraries +libdir = $(exec_prefix)/lib + +# Directory in which to install headers +includedir = $(prefix)/include + +#---------------------------------------------------------------------- +# The following are set by the configure script +#---------------------------------------------------------------------- + +AC_FLAGS = @DEFS@ +RANLIB = @RANLIB@ +AR = @AR@ +CC = @CC@ +CFLAGS = @CFLAGS@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ + + +CSRC = cal.c calBddOp.c calBddManager.c calMemoryManagement.c\ + calHashTable.c calUtil.c calGC.c \ + calTerminal.c calAssociation.c \ + calBddSubstitute.c calReduce.c calQuant.c \ + calBddSwapVars.c calBddSatisfy.c calBddSize.c \ + calBddSupport.c calPrint.c calPrintProfile.c calDump.c\ + calHashTableOne.c calPipeline.c calPerformanceTest.c \ + calHashTableThree.c calBddITE.c calBddCompose.c\ + calCacheTableTwo.c calApplyReduce.c calBlk.c \ + calReorderBF.c calReorderDF.c calInteract.c\ + calBddVarSubstitute.c calReorderUtil.c calMem.c + +HEADERS = cal.h calInt.h calMem.h + +MISC = calBddReorderTest.c calPerformanceTest.c calTest.c\ + calAllAbs.html calAllByFile.html calAllByFunc.html\ + calAllDet.html calAllFile.html calDesc.html\ + calExt.html calExtAbs.html calExtDet.html calTitle.html credit.html\ + calDoc.txt + +DEPENDENCYFILES = $(CSRC) + +OBJECTS = $(addprefix $(objectdir)/,$(CSRC:.c=.o)) + + +INCLUDEDIRS = -I. + +#---------------------------------------------------------------------- +# Implicit rules for compiling and archiving +#---------------------------------------------------------------------- + +# For compiling a source file into the object directory + +$(objectdir)/%.o : %.c + umask 2; $(CC) -c $(CFLAGS) $(AC_FLAGS) $(INCLUDEDIRS) -o $@ $< + +# Place object files into an archive + +%.a : + rm -f $@ + umask 2; $(AR) cq $@ $^ + $(RANLIB) $@ + +###################################################################### +# RULES # +###################################################################### + +#: +#: Useful targets: +#: + +#---------------------------------------------------------------------- +# Rule for getting help +#---------------------------------------------------------------------- + +.PHONY : help + +#: help -- Print a list of targets + +# This prints all lines in this Makefile that begin with #: + +help : + @sed -n "s/^#://p" Makefile + +#---------------------------------------------------------------------- +# Always executed once when the Makefile is run +#---------------------------------------------------------------------- + +# Make sure the directory in which to place the objects exists + +ignored := $(shell umask 2; test -d $(objectdir) || mkdir $(objectdir)) + +#---------------------------------------------------------------------- +# Rules to compile and build libraries +#---------------------------------------------------------------------- + +.PHONY : all + +#: +#: all (the default) -- Create the libraries + +all : $(LIBRARY) + +$(LIBRARY) : $(OBJECTS) + +#---------------------------------------------------------------------- +# Warts +#---------------------------------------------------------------------- + +# Work around an optimizer bug in the native Ultrix compiler + +ifeq (@target@,mips-dec-ultrix4.5) +$(objectdir)/calReduce.o : calReduce.c + umask 2; $(CC) -c -std1 -g $(AC_FLAGS) $(INCLUDEDIRS) -o $@ $< +endif + +# Work around a bug in gcc 2.7.0 + +ifeq ($(CC),gcc) + ifeq ($(shell gcc --version),2.7.0) + +$(objectdir)/cal.o : cal.c + umask 2; $(CC) -c -g $(AC_FLAGS) $(INCLUDEDIRS) -o $@ $< + +$(objectdir)/calBddSwapVars.o : calBddSwapVars.c + umask 2; $(CC) -c -g $(AC_FLAGS) $(INCLUDEDIRS) -o $@ $< + + endif +endif + +#---------------------------------------------------------------------- +# Rules to build test programs +#---------------------------------------------------------------------- + +.PHONY : check check-cal + +#: +#: check -- Test the libraries (runs check-bdd) + + +check : checkcal + checkcal > checkcal.out + @echo "Test appears successful -- results in checkcal.out" + +checkcal : libcal.a calTest.c + $(CC) -o checkcal -DTEST $(CFLAGS) $(AC_FLAGS) $(INCLUDEDIRS) \ + $(filter %.c, $^) -L. -lcal + + +#---------------------------------------------------------------------- +# Rules for rebuilding the configure file and Makefile +#---------------------------------------------------------------------- + +${master_srcdir}/configure : configure.in + cd ${master_srcdir} && autoconf + chmod -f 0775 ${master_srcdir}/config* + +config.status : configure + ./config.status --recheck + +Makefile : Makefile.in config.status + @echo "The master Makefile.in has been changed:" + @echo "run config.status" + @echo "Warning: This will overwrite any local Makefile modifications" + @exit 1 + +#---------------------------------------------------------------------- +# Rules for cleaning +#---------------------------------------------------------------------- + +.PHONY : clean mostlyclean distclean + +clean mostlyclean : + rm -rf $(OBJECTS) checkcal.out + + +#---------------------------------------------------------------------- +# Rule for performing a lint-like check on the source code +# +# Note: This requires gcc +#---------------------------------------------------------------------- + +.PHONY : check_code + +#: +#: check-code -- Run a lint-like check on the source code. +#: (useful for development) + +check-code : $(CSRC) +ifeq ($(CC),gcc) + @rm -f *.o_checkcode + @for file in $^; do \ + echo "------------------------ Checking $$file"; \ + gcc -c $(CFLAGS) $(AC_FLAGS) $(VERDATE) $(INCLUDEDIRS) \ + -Wall -Wno-comment -o $(objectdir)/checkcode_output.o $$file; \ + rm -f $(objectdir)/checkcode_output.o; \ + done + @rm -f *.o_checkcode +else + @echo "check-code requires gcc" + @echo "Reconfigure with gcc" +endif + +#---------------------------------------------------------------------- +# Rules for debugging the Makefile +#---------------------------------------------------------------------- + +DEBUG_VARS = \ + SHELL \ + PRODUCT \ + VERSION \ + prefix \ + exec_prefix \ + master_srcdir \ + local_srcdir \ + libdir \ + includedir \ + objectdir \ + headerdir \ + LIBRARY \ + AC_FLAGS \ + RANLIB \ + CC \ + CFLAGS \ + INSTALL \ + INSTALL_DATA \ + MAKEINCLUDES \ + OBJECTS \ + BDD_CSRC \ + BDD_HEADERS \ + INCLUDEDIRS \ + VPATH + +.PHONY : debug-make + +#: +#: debug-make - Print a list of Makefile variables + +debug-make: + @$(foreach var, $(DEBUG_VARS), echo $(var)=$($(var)) ; ) diff --git a/cal.c b/cal.c new file mode 100644 index 0000000..6c048d4 --- /dev/null +++ b/cal.c @@ -0,0 +1,1034 @@ +/**CFile*********************************************************************** + + FileName [cal.c] + + PackageName [cal] + + Synopsis [Miscellaneous collection of exported BDD functions] + + Description [] + + SeeAlso [] + + Author [ + Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: cal.c,v 1.1.1.5 1998/05/04 00:58:48 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t BddIntersectsStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns 1 if argument BDDs are equal, 0 otherwise.] + + Description [Returns 1 if argument BDDs are equal, 0 otherwise.] + + SideEffects [None.] + + SeeAlso [] + +******************************************************************************/ +int +Cal_BddIsEqual(Cal_BddManager bddManager, Cal_Bdd userBdd1, Cal_Bdd userBdd2) +{ + return (userBdd1 == userBdd2); +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is constant one, 0 otherwise.] + + Description [Returns 1 if the argument BDD is constant one, 0 otherwise.] + + SideEffects [None.] + + SeeAlso [Cal_BddIsBddZero] + +******************************************************************************/ +int +Cal_BddIsBddOne(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + return (userBdd == bddManager->userOneBdd); +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is constant zero, 0 otherwise.] + + Description [Returns 1 if the argument BDD is constant zero, 0 otherwise.] + + SideEffects [None.] + + SeeAlso [Cal_BddIsBddOne] + +******************************************************************************/ +int +Cal_BddIsBddZero( + Cal_BddManager bddManager, + Cal_Bdd userBdd) +{ + return (userBdd == bddManager->userZeroBdd); +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is NULL, 0 otherwise.] + + Description [Returns 1 if the argument BDD is NULL, 0 otherwise.] + + SideEffects [None.] + +******************************************************************************/ +int +Cal_BddIsBddNull(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + return (userBdd == 0); +} + + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is a constant, 0 otherwise.] + + Description [Returns 1 if the argument BDD is either constant one or + constant zero, otherwise returns 0.] + + SideEffects [None.] + + SeeAlso [Cal_BddIsBddOne, Cal_BddIsBddZero] + +******************************************************************************/ +int +Cal_BddIsBddConst( + Cal_BddManager bddManager, + Cal_Bdd userBdd) +{ + return ((userBdd == bddManager->userOneBdd) || + (userBdd == bddManager->userZeroBdd)); +} + +/**Function******************************************************************** + + Synopsis [Returns the duplicate BDD of the argument BDD.] + + Description [Returns the duplicate BDD of the argument BDD.] + + SideEffects [The reference count of the BDD is increased by 1.] + + SeeAlso [Cal_BddNot] + +******************************************************************************/ +Cal_Bdd +Cal_BddIdentity(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + /* Interface BDD reference count */ + CalBddNode_t *bddNode = CAL_BDD_POINTER(userBdd); + CalBddNodeIcrRefCount(bddNode); + return userBdd; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for the constant one] + + Description [Returns the BDD for the constant one] + + SideEffects [None] + + SeeAlso [Cal_BddZero] + +******************************************************************************/ +Cal_Bdd +Cal_BddOne(Cal_BddManager bddManager) +{ + return bddManager->userOneBdd; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for the constant zero] + + Description [Returns the BDD for the constant zero] + + SideEffects [None] + + SeeAlso [Cal_BddOne] + +******************************************************************************/ +Cal_Bdd +Cal_BddZero(Cal_BddManager bddManager) +{ + return bddManager->userZeroBdd; +} + + +/**Function******************************************************************** + + Synopsis [Returns the complement of the argument BDD.] + + Description [Returns the complement of the argument BDD.] + + SideEffects [The reference count of the argument BDD is increased by 1.] + + SeeAlso [Cal_BddIdentity] + +******************************************************************************/ +Cal_Bdd +Cal_BddNot(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + /* Interface BDD reference count */ + CalBddNode_t *bddNode = CAL_BDD_POINTER(userBdd); + CalBddNodeIcrRefCount(bddNode); + return CalBddNodeNot(userBdd); +} + +/**Function******************************************************************** + + Synopsis [Returns the index of the top variable of the argument BDD.] + + Description [Returns the index of the top variable of the argument BDD.] + + SideEffects [None] + + SeeAlso [Cal_BddGetIfId] + +******************************************************************************/ +Cal_BddId_t +Cal_BddGetIfIndex(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t F; + if (CalBddPreProcessing(bddManager, 1, userBdd) == 1){ + F = CalBddGetInternalBdd(bddManager, userBdd); + if (CalBddIsBddConst(F)){ + return -1; + } + return CalBddGetBddIndex(bddManager, F); + } + return -1; +} + + +/**Function******************************************************************** + + Synopsis [Returns the id of the top variable of the argument BDD.] + + Description [Returns the id of the top variable of the argument BDD.] + + SideEffects [None] + + SeeAlso [Cal_BddGetIfIndex] + +******************************************************************************/ +Cal_BddId_t +Cal_BddGetIfId(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t F; + if (CalBddPreProcessing(bddManager, 1, userBdd) == 1){ + F = CalBddGetInternalBdd(bddManager, userBdd); + if (CalBddIsBddConst(F)){ + return 0; + } + return CalBddGetBddId(F); + } + return -1; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD corresponding to the top variable of + the argument BDD.] + + Description [Returns the BDD corresponding to the top variable of + the argument BDD.] + + SideEffects [None.] + +******************************************************************************/ +Cal_Bdd +Cal_BddIf(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t F; + if (CalBddPreProcessing(bddManager, 1, userBdd) == 0){ + return (Cal_Bdd)0; + } + F = CalBddGetInternalBdd(bddManager, userBdd); + if (CalBddIsBddConst(F)){ + CalBddWarningMessage("Cal_BddIf: argument is constant"); + } + return CalBddGetExternalBdd(bddManager, bddManager->varBdds[CalBddGetBddId(F)]); +} + + +/**Function******************************************************************** + + Synopsis [Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD.] + + Description [Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD.] + + SideEffects [The reference count of the returned BDD is increased by 1.] + + SeeAlso [Cal_BddElse] + +******************************************************************************/ +Cal_Bdd +Cal_BddThen(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t thenBdd; + Cal_Bdd_t F; + if (CalBddPreProcessing(bddManager, 1, userBdd) == 0){ + return (Cal_Bdd)0; + } + F = CalBddGetInternalBdd(bddManager, userBdd); + CalBddGetThenBdd(F, thenBdd); + return CalBddGetExternalBdd(bddManager, thenBdd); +} + +/**Function******************************************************************** + + Synopsis [Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD.] + + Description [Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD.] + + SideEffects [The reference count of the returned BDD is increased by 1.] + + SeeAlso [Cal_BddThen] + +******************************************************************************/ +Cal_Bdd +Cal_BddElse(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t elseBdd; + Cal_Bdd_t F; + if (CalBddPreProcessing(bddManager, 1, userBdd) == 0){ + return (Cal_Bdd) 0; + } + F = CalBddGetInternalBdd(bddManager, userBdd); + CalBddGetElseBdd(F, elseBdd); + return CalBddGetExternalBdd(bddManager, elseBdd); +} + +/**Function******************************************************************** + + Synopsis [Frees the argument BDD.] + + Description [Frees the argument BDD. It is an error to free a BDD + more than once.] + + SideEffects [The reference count of the argument BDD is decreased by 1.] + + SeeAlso [Cal_BddUnFree] + +******************************************************************************/ +void +Cal_BddFree(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + /* Interface BDD reference count */ + CalBddNodeDcrRefCount(CAL_BDD_POINTER(userBdd)); +} + + +/**Function******************************************************************** + + Synopsis [Unfrees the argument BDD.] + + Description [Unfrees the argument BDD. It is an error to pass a BDD + with reference count of zero to be unfreed.] + + SideEffects [The reference count of the argument BDD is increased by 1.] + + SeeAlso [Cal_BddFree] + +******************************************************************************/ +void +Cal_BddUnFree(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + /* Interface BDD reference count */ + CalBddNode_t *bddNode = CAL_BDD_POINTER(userBdd); + CalBddNodeIcrRefCount(bddNode); +} + + +/**Function******************************************************************** + + Synopsis [Returns a BDD with positive from a given BDD with arbitrary phase] + + Description [Returns a BDD with positive from a given BDD with arbitrary phase] + + SideEffects [None.] + +******************************************************************************/ +Cal_Bdd +Cal_BddGetRegular(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + return CAL_BDD_POINTER(userBdd); +} + +/**Function******************************************************************** + + Synopsis [Computes a BDD that implies conjunction of f and g.] + + Description [Computes a BDD that implies conjunction of f and g.] + + SideEffects [None] + + SeeAlso [Cal_BddImplies] + +******************************************************************************/ +Cal_Bdd +Cal_BddIntersects(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd + gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd_t f, g; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd) == 0){ + return (Cal_Bdd) 0; + } + f = CalBddGetInternalBdd(bddManager, fUserBdd); + g = CalBddGetInternalBdd(bddManager, gUserBdd); + result = BddIntersectsStep(bddManager,f,g); + return CalBddGetExternalBdd(bddManager, result); +} + +/**Function******************************************************************** + + Synopsis [Computes a BDD that implies conjunction of f and Cal_BddNot(g)] + + Description [Computes a BDD that implies conjunction of f and Cal_BddNot(g)] + + SideEffects [none] + + SeeAlso [Cal_BddIntersects] + +******************************************************************************/ +Cal_Bdd +Cal_BddImplies(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd_t f, g; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + Cal_Bdd_t gNot; + f = CalBddGetInternalBdd(bddManager, fUserBdd); + g = CalBddGetInternalBdd(bddManager, gUserBdd); + CalBddNot(g, gNot); + result = BddIntersectsStep(bddManager,f, gNot); + } + else{ + return (Cal_Bdd) 0; + } + return CalBddGetExternalBdd(bddManager, result); +} + +/**Function******************************************************************** + + Synopsis [Returns the number of nodes in the Unique table] + + Description [Returns the number of nodes in the Unique table] + + SideEffects [None] + + SeeAlso [Cal_BddManagerGetNumNodes] + +******************************************************************************/ +unsigned long +Cal_BddTotalSize(Cal_BddManager bddManager) +{ + return Cal_BddManagerGetNumNodes(bddManager); +} + + +/**Function******************************************************************** + + Synopsis [Prints miscellaneous BDD statistics] + + Description [Prints miscellaneous BDD statistics] + + SideEffects [None] + +******************************************************************************/ +void +Cal_BddStats(Cal_BddManager bddManager, FILE * fp) +{ + unsigned long cacheInsertions = 0; + unsigned long cacheEntries = 0; + unsigned long cacheSize = 0; + unsigned long cacheHits = 0; + unsigned long cacheLookups = 0; + unsigned long cacheCollisions = 0; + unsigned long numLockedNodes = 0; + int i, id, depth; + long numPages; + unsigned long totalBytes; + + + fprintf(fp, "**** CAL modifiable parameters ****\n"); + fprintf(fp, "Node limit: %ld\n", bddManager->nodeLimit); + fprintf(fp, "Garbage collection enabled: %s\n", + ((bddManager->gcMode) ? "yes" : "no")); + fprintf(fp, "Maximum number of variables sifted per reordering: %ld\n", + bddManager->maxNumVarsSiftedPerReordering); + fprintf(fp, "Maximum number of variable swaps per reordering: %ld\n", + bddManager->maxNumSwapsPerReordering); + fprintf(fp, "Maximum growth while sifting a variable: %2.2f\n", + bddManager->maxSiftingGrowth); + fprintf(fp, "Dynamic reordering of BDDs enabled: %s\n", + ((bddManager->dynamicReorderingEnableFlag) ? "yes" : "no")); + fprintf(fp, "Repacking after GC Threshold: %f\n", + bddManager->repackAfterGCThreshold); + fprintf(fp, "**** CAL statistics ****\n"); + fprintf(fp, "Total BDD Node Usage : %ld nodes, %ld Bytes\n", + bddManager->numNodes, bddManager->numNodes*sizeof(CalBddNode_t)); + fprintf(fp, "Peak BDD Node Usage : %ld nodes, %ld Bytes\n", + bddManager->numPeakNodes, + bddManager->numPeakNodes*sizeof(CalBddNode_t)); + for (i=1; i<=bddManager->numVars; i++){ + numLockedNodes += CalBddUniqueTableNumLockedNodes(bddManager, + bddManager->uniqueTable[i]); + } + fprintf(fp, "Number of nodes locked: %ld\n", numLockedNodes); + fprintf(fp, "Total Number of variables: %d\n", bddManager->numVars); + numPages = + bddManager->pageManager1->totalNumPages+ + bddManager->pageManager2->totalNumPages; + fprintf(fp, "Total memory allocated for BDD nodes: %ld pages (%ld Bytes)\n", + numPages, PAGE_SIZE*numPages); + /* Calculate the memory consumed */ + totalBytes = + /* Over all bdd manager */ + sizeof(Cal_BddManager_t)+ + bddManager->maxNumVars*(sizeof(Cal_Bdd_t)+sizeof(CalNodeManager_t *)+ + sizeof(CalHashTable_t *) + + sizeof(CalHashTable_t *) + sizeof(CalRequestNode_t*)*2)+ + sizeof(CalPageManager_t)*2+ + /* Page manager */ + bddManager->pageManager1->maxNumSegments*(sizeof(CalAddress_t *)+sizeof(int))+ + bddManager->pageManager2->maxNumSegments* + (sizeof(CalAddress_t *)+sizeof(int)); + + for (id=0; id <= bddManager->numVars; id++){ + totalBytes += bddManager->nodeManagerArray[id]->maxNumPages*sizeof(int);; + } + /* IndexToId and IdToIndex */ + totalBytes += 2*bddManager->maxNumVars*(sizeof(Cal_BddIndex_t)); + for (id=0; id <= bddManager->numVars; id++){ + totalBytes += bddManager->uniqueTable[id]->numBins*sizeof(int);; + } + /* Cache Table */ + totalBytes += CalCacheTableMemoryConsumption(bddManager->cacheTable); + + /* Req que */ + totalBytes += bddManager->maxDepth*sizeof(CalHashTable_t **); + for (depth = 0; depth < bddManager->depth; depth++){ + for (id=0; id <= bddManager->numVars; id++){ + if (bddManager->reqQue[depth][id]){ + totalBytes += + bddManager->reqQue[depth][id]->numBins* + sizeof(CalBddNode_t*); + } + } + } + /* Association */ + totalBytes += sizeof(CalAssociation_t)*2; + /* Block */ + totalBytes += CalBlockMemoryConsumption(bddManager->superBlock); + + fprintf(fp, "Total memory consumed: %ld Pages (%ld Bytes)\n", + numPages+totalBytes/PAGE_SIZE, + PAGE_SIZE*numPages+totalBytes); + + CalBddManagerGetCacheTableData(bddManager, &cacheSize, + &cacheEntries, &cacheInsertions, + &cacheLookups, &cacheHits, &cacheCollisions); + fprintf(fp, "Cache Size: %ld\n", cacheSize); + fprintf(fp, "Cache Entries: %ld\n", cacheEntries); + fprintf(fp, "Cache Insertions: %ld\n", cacheInsertions); + fprintf(fp, "Cache Collisions: %ld\n", cacheCollisions); + fprintf(fp, "Cache Hits: %ld\n", cacheHits); + if (cacheLookups){ + fprintf(fp, "Cache Lookup: %ld\n", cacheLookups); + fprintf(fp, "Cache hit ratio: %-.2f\n", ((double)cacheHits)/cacheLookups); + } + fprintf(fp, "Number of nodes garbage collected: %ld\n", + bddManager->numNodesFreed); + fprintf(fp,"number of garbage collections: %d\n", bddManager->numGC); + fprintf(fp,"number of dynamic reorderings: %d\n", + bddManager->numReorderings); + fprintf(fp,"number of trivial swaps: %ld\n", bddManager->numTrivialSwaps); + fprintf(fp,"number of swaps in last reordering: %ld\n", bddManager->numSwaps); + fprintf(fp,"garbage collection limit: %ld\n", bddManager->uniqueTableGCLimit); + fflush(fp); +} + +/**Function******************************************************************** + + Synopsis [Specify dynamic reordering technique.] + + Description [Selects the method for dynamic reordering.] + + SideEffects [None] + + SeeAlso [Cal_BddReorder] + +******************************************************************************/ +void +Cal_BddDynamicReordering(Cal_BddManager bddManager, int technique) +{ + bddManager->reorderTechnique = technique; + bddManager->dynamicReorderingEnableFlag = 1; +} + +/**Function******************************************************************** + + Synopsis [Invoke the current dynamic reodering method.] + + Description [Invoke the current dynamic reodering method.] + + SideEffects [Index of a variable may change due to reodering] + + SeeAlso [Cal_BddDynamicReordering] + +******************************************************************************/ +void +Cal_BddReorder(Cal_BddManager bddManager) +{ + if ((bddManager->dynamicReorderingEnableFlag == 0) || + (bddManager->reorderTechnique == CAL_REORDER_NONE)){ + return; + } + CalCacheTableTwoFlush(bddManager->cacheTable); + if (bddManager->reorderMethod == CAL_REORDER_METHOD_DF){ + CalBddReorderAuxDF(bddManager); + } + else if (bddManager->reorderMethod == CAL_REORDER_METHOD_BF){ + Cal_BddManagerGC(bddManager); + CalBddReorderAuxBF(bddManager); + } +} + + +/**Function******************************************************************** + + Synopsis [Returns type of a BDD ( 0, 1, +var, -var, ovrflow, nonterminal)] + + Description [Returns BDD_TYPE_ZERO if f is false, BDD_TYPE_ONE + if f is true, BDD_TYPE_POSVAR is f is an unnegated variable, + BDD_TYPE_NEGVAR if f is a negated variable, BDD_TYPE_OVERFLOW if f + is null, and BDD_TYPE_NONTERMINAL otherwise.] + + SideEffects [None] + +******************************************************************************/ +int +Cal_BddType(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + Cal_Bdd_t f; + if (CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + return (CalBddTypeAux(bddManager, f)); + } + return (CAL_BDD_TYPE_OVERFLOW); +} +/**Function******************************************************************** + + Synopsis [Returns the number of BDD variables] + + Description [Returns the number of BDD variables] + + SideEffects [None] + +******************************************************************************/ +long +Cal_BddVars(Cal_BddManager bddManager) +{ + return (bddManager->numVars); +} + + +/**Function******************************************************************** + + Synopsis [Sets the node limit to new_limit and returns the old limit.] + + Description [Sets the node limit to new_limit and returns the old limit.] + + SideEffects [Threshold for garbage collection may change] + + SeeAlso [Cal_BddManagerGC] + +******************************************************************************/ +long +Cal_BddNodeLimit( + Cal_BddManager bddManager, + long newLimit) +{ + long oldLimit; + + oldLimit = bddManager->nodeLimit; + if (newLimit < 0){ + newLimit=0; + } + bddManager->nodeLimit = newLimit; + if (newLimit && (bddManager->uniqueTableGCLimit > newLimit)){ + bddManager->uniqueTableGCLimit = newLimit; + } + return (oldLimit); +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared.] + + Description [Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared.] + + SideEffects [None] + + SeeAlso [Cal_BddNodeLimit] + +******************************************************************************/ +int +Cal_BddOverflow(Cal_BddManager bddManager) +{ + int result; + result = bddManager->overflow; + bddManager->overflow = 0; + return (result); +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is a cube, 0 otherwise] + + Description [Returns 1 if the argument BDD is a cube, 0 otherwise] + + SideEffects [None] + +******************************************************************************/ +int +Cal_BddIsCube( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd) +{ + Cal_Bdd_t f0, f1; + Cal_Bdd_t f; + f = CalBddGetInternalBdd(bddManager, fUserBdd); + if (CalBddIsBddConst(f)){ + if (CalBddIsBddZero(bddManager, f)){ + CalBddFatalMessage("Cal_BddIsCube called with 0"); + } + else return 1; + } + + CalBddGetThenBdd(f, f1); + CalBddGetElseBdd(f, f0); + /* + * Exactly one branch of f must point to ZERO to be a cube. + */ + if (CalBddIsBddZero(bddManager, f1)){ + return (CalBddIsCubeStep(bddManager, f0)); + } else if (CalBddIsBddZero(bddManager, f0)){ + return (CalBddIsCubeStep(bddManager, f1)); + } else { /* not a cube, because neither branch is zero */ + return 0; + } +} + +/**Function******************************************************************** + + Synopsis [Returns the hooks field of the manager.] + + Description [Returns the hooks field of the manager.] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +void * +Cal_BddManagerGetHooks(Cal_BddManager bddManager) +{ + return bddManager->hooks; +} + +/**Function******************************************************************** + + Synopsis [Sets the hooks field of the manager.] + + Description [Sets the hooks field of the manager.] + + SideEffects [Hooks field changes. ] + + SeeAlso [] + +******************************************************************************/ +void +Cal_BddManagerSetHooks(Cal_BddManager bddManager, void *hooks) +{ + bddManager->hooks = hooks; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the BDD corresponding to the top variable of + the argument BDD.] + + Description [Returns the BDD corresponding to the top variable of + the argument BDD.] + + SideEffects [None.] + +******************************************************************************/ +Cal_Bdd_t +CalBddIf(Cal_BddManager bddManager, Cal_Bdd_t F) +{ + if (CalBddIsBddConst(F)){ + CalBddWarningMessage("CalBddIf: argument is constant"); + } + return bddManager->varBdds[CalBddGetBddId(F)]; +} + +/**Function******************************************************************** + + Synopsis [Returns 1 if the argument BDD is a cube, 0 otherwise] + + Description [Returns 1 if the argument BDD is a cube, 0 otherwise] + + SideEffects [None] + +******************************************************************************/ +int +CalBddIsCubeStep(Cal_BddManager bddManager, Cal_Bdd_t f) +{ + Cal_Bdd_t f0, f1; + if (CalBddIsBddConst(f)){ + if (CalBddIsBddZero(bddManager, f)){ + CalBddFatalMessage("Cal_BddIsCube called with 0"); + } + else return 1; + } + + CalBddGetThenBdd(f, f1); + CalBddGetElseBdd(f, f0); + /* + * Exactly one branch of f must point to ZERO to be a cube. + */ + if (CalBddIsBddZero(bddManager, f1)){ + return (CalBddIsCubeStep(bddManager, f0)); + } else if (CalBddIsBddZero(bddManager, f0)){ + return (CalBddIsCubeStep(bddManager, f1)); + } else { /* not a cube, because neither branch is zero */ + return 0; + } +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD type by recursively traversing the argument BDD] + + Description [Returns the BDD type by recursively traversing the argument BDD] + + SideEffects [None] + +******************************************************************************/ +int +CalBddTypeAux(Cal_BddManager_t * bddManager, Cal_Bdd_t f) +{ + Cal_Bdd_t thenBdd, elseBdd; + + if (CalBddIsBddConst(f)){ + if (CalBddIsBddZero(bddManager, f)) return (CAL_BDD_TYPE_ZERO); + if (CalBddIsBddOne(bddManager, f)) return (CAL_BDD_TYPE_ONE); + } + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + if (CalBddIsBddOne(bddManager, thenBdd) && + CalBddIsBddZero(bddManager, elseBdd)) + return CAL_BDD_TYPE_POSVAR; + if (CalBddIsBddZero(bddManager, thenBdd) && + CalBddIsBddOne(bddManager, elseBdd)) + return (CAL_BDD_TYPE_NEGVAR); + return (CAL_BDD_TYPE_NONTERMINAL); +} + +/**Function******************************************************************** + + Synopsis [Returns the duplicate BDD of the argument BDD.] + + Description [Returns the duplicate BDD of the argument BDD.] + + SideEffects [The reference count of the BDD is increased by 1.] + + SeeAlso [Cal_BddNot] + +******************************************************************************/ +Cal_Bdd_t +CalBddIdentity(Cal_BddManager_t *bddManager, Cal_Bdd_t calBdd) +{ + CalBddIcrRefCount(calBdd); + return calBdd; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Recursive routine to returns a BDD that implies conjunction of + argument BDDs] + + Description [Recursive routine to returns a BDD that implies conjunction of + argument BDDs] + + SideEffects [None] + +******************************************************************************/ +static Cal_Bdd_t +BddIntersectsStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g) +{ + Cal_Bdd_t f1, f2, g1, g2, result, temp; + Cal_BddId_t topId; + + + if (CalBddIsBddConst(f)){ + if (CalBddIsBddZero(bddManager, f)){ + return f; + } + else { + return g; + } + } + if (CalBddIsBddConst(g)){ + if (CalBddIsBddZero(bddManager, g)){ + return g; + } + else { + return f; + } + } + if (CalBddSameOrNegation(f, g)){ + if (CalBddIsEqual(f, g)){ + return f; + } + else + return bddManager->bddZero; + } + if (CAL_BDD_OUT_OF_ORDER(f, g)) CAL_BDD_SWAP(f, g); + CalBddGetMinId2(bddManager, f, g, topId); + CalBddGetCofactors(f, topId, f1, f2); + CalBddGetCofactors(g, topId, g1, g2); + temp = BddIntersectsStep(bddManager, f1, g1); + if (CalBddIsBddZero(bddManager, temp)){ + temp = BddIntersectsStep(bddManager, f2, g2); + if (CalBddIsBddZero(bddManager, temp)){ + return bddManager->bddZero; + } + else{ + if(CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[topId], + bddManager->bddZero, temp, + &result) == 0){ + CalBddIcrRefCount(temp); + } + } + } + else { + if(CalUniqueTableForIdFindOrAdd(bddManager, bddManager->uniqueTable[topId], + temp, bddManager->bddZero,&result) == 0){ + CalBddIcrRefCount(temp); + } + } + return result; +} + + + + + + + + + + + + + + + + + + + + + + diff --git a/cal.h b/cal.h new file mode 100644 index 0000000..317722a --- /dev/null +++ b/cal.h @@ -0,0 +1,246 @@ +/**CHeaderFile***************************************************************** + + FileName [cal.h] + + PackageName [cal] + + Synopsis [Header CAL file for exported data structures and functions.] + + Description [] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: cal.h,v 1.6 1998/09/15 19:02:51 ravi Exp $] + +******************************************************************************/ + +#ifndef _CAL +#define _CAL +#include +#include +#include +#if HAVE_SYS_TYPES_H +# include +#endif +#if HAVE_SYS_TIME_H +# include +#endif +#if HAVE_SYS_RESOURCE_H +# include +#endif +#if HAVE_UNISTD_H +# include +#endif +#if HAVE_TIME_H +# include +#endif + +#include +#include + +#include "calMem.h" +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +#ifndef EXTERN +#define EXTERN extern +#endif + +#define CAL_BDD_TYPE_NONTERMINAL 0 +#define CAL_BDD_TYPE_ZERO 1 +#define CAL_BDD_TYPE_ONE 2 +#define CAL_BDD_TYPE_POSVAR 3 +#define CAL_BDD_TYPE_NEGVAR 4 +#define CAL_BDD_TYPE_OVERFLOW 5 +#define CAL_BDD_TYPE_CONSTANT 6 + +#define CAL_BDD_UNDUMP_FORMAT 1 +#define CAL_BDD_UNDUMP_OVERFLOW 2 +#define CAL_BDD_UNDUMP_IOERROR 3 +#define CAL_BDD_UNDUMP_EOF 4 + +#define CAL_REORDER_NONE 0 +#define CAL_REORDER_SIFT 1 +#define CAL_REORDER_WINDOW 2 +#define CAL_REORDER_METHOD_BF 0 +#define CAL_REORDER_METHOD_DF 1 + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef struct Cal_BddManagerStruct *Cal_BddManager; +typedef struct Cal_BddManagerStruct Cal_BddManager_t; +typedef struct CalBddNodeStruct *Cal_Bdd; +typedef unsigned short int Cal_BddId_t; +typedef unsigned short int Cal_BddIndex_t; +typedef char * (*Cal_VarNamingFn_t)(Cal_BddManager, Cal_Bdd, Cal_Pointer_t); +typedef char * (*Cal_TerminalIdFn_t)(Cal_BddManager, Cal_Address_t, Cal_Address_t, Cal_Pointer_t); +typedef struct Cal_BlockStruct *Cal_Block; + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ +enum Cal_BddOpEnum {CAL_AND, CAL_OR, CAL_XOR}; +typedef enum Cal_BddOpEnum Cal_BddOp_t; + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#define Cal_BddNamingFnNone ((char *(*)(Cal_BddManager, Cal_Bdd, Cal_Pointer_t))0) +#define Cal_BddTerminalIdFnNone ((char *(*)(Cal_BddManager, Cal_Address_t, Cal_Address_t, Cal_Pointer_t))0) +#ifdef _CAL_DEBUG_ +#define Cal_Assert(valid) assert(valid) +#else +#define Cal_Assert(ignore) ((void)0) +#endif + + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Function prototypes */ +/*---------------------------------------------------------------------------*/ + +EXTERN int Cal_BddIsEqual(Cal_BddManager bddManager, Cal_Bdd userBdd1, Cal_Bdd userBdd2); +EXTERN int Cal_BddIsBddOne(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN int Cal_BddIsBddZero(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN int Cal_BddIsBddNull(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN int Cal_BddIsBddConst(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddIdentity(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddOne(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddZero(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddNot(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_BddId_t Cal_BddGetIfIndex(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_BddId_t Cal_BddGetIfId(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddIf(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddThen(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddElse(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN void Cal_BddFree(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN void Cal_BddUnFree(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddGetRegular(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddIntersects(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddImplies(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN unsigned long Cal_BddTotalSize(Cal_BddManager bddManager); +EXTERN void Cal_BddStats(Cal_BddManager bddManager, FILE * fp); +EXTERN void Cal_BddDynamicReordering(Cal_BddManager bddManager, int technique); +EXTERN void Cal_BddReorder(Cal_BddManager bddManager); +EXTERN int Cal_BddType(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN long Cal_BddVars(Cal_BddManager bddManager); +EXTERN long Cal_BddNodeLimit(Cal_BddManager bddManager, long newLimit); +EXTERN int Cal_BddOverflow(Cal_BddManager bddManager); +EXTERN int Cal_BddIsCube(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN void * Cal_BddManagerGetHooks(Cal_BddManager bddManager); +EXTERN void Cal_BddManagerSetHooks(Cal_BddManager bddManager, void *hooks); +EXTERN int Cal_AssociationInit(Cal_BddManager bddManager, Cal_Bdd *associationInfoUserBdds, int pairs); +EXTERN void Cal_AssociationQuit(Cal_BddManager bddManager, int associationId); +EXTERN int Cal_AssociationSetCurrent(Cal_BddManager bddManager, int associationId); +EXTERN void Cal_TempAssociationAugment(Cal_BddManager bddManager, Cal_Bdd *associationInfoUserBdds, int pairs); +EXTERN void Cal_TempAssociationInit(Cal_BddManager bddManager, Cal_Bdd *associationInfoUserBdds, int pairs); +EXTERN void Cal_TempAssociationQuit(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddCompose(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd, Cal_Bdd hUserBdd); +EXTERN Cal_Bdd Cal_BddITE(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd, Cal_Bdd hUserBdd); +EXTERN Cal_BddManager Cal_BddManagerInit(); +EXTERN int Cal_BddManagerQuit(Cal_BddManager bddManager); +EXTERN void Cal_BddManagerSetParameters(Cal_BddManager bddManager, long reorderingThreshold, long maxForwardedNodes, double repackAfterGCThreshold, double tableRepackThreshold); +EXTERN unsigned long Cal_BddManagerGetNumNodes(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddManagerCreateNewVarFirst(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddManagerCreateNewVarLast(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_BddManagerCreateNewVarBefore(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddManagerCreateNewVarAfter(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd Cal_BddManagerGetVarWithIndex(Cal_BddManager bddManager, Cal_BddIndex_t index); +EXTERN Cal_Bdd Cal_BddManagerGetVarWithId(Cal_BddManager bddManager, Cal_BddId_t id); +EXTERN Cal_Bdd Cal_BddAnd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddNand(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddOr(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddNor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddXor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddXnor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd * Cal_BddPairwiseAnd(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd * Cal_BddPairwiseOr(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd * Cal_BddPairwiseXor(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd Cal_BddMultiwayAnd(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd Cal_BddMultiwayOr(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd Cal_BddMultiwayXor(Cal_BddManager bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd Cal_BddSatisfy(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN Cal_Bdd Cal_BddSatisfySupport(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN double Cal_BddSatisfyingFraction(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN long Cal_BddSize(Cal_BddManager bddManager, Cal_Bdd fUserBdd, int negout); +EXTERN long Cal_BddSizeMultiple(Cal_BddManager bddManager, Cal_Bdd *fUserBddArray, int negout); +EXTERN void Cal_BddProfile(Cal_BddManager bddManager, Cal_Bdd fUserBdd, long * levelCounts, int negout); +EXTERN void Cal_BddProfileMultiple(Cal_BddManager bddManager, Cal_Bdd *fUserBddArray, long * levelCounts, int negout); +EXTERN void Cal_BddFunctionProfile(Cal_BddManager bddManager, Cal_Bdd fUserBdd, long * funcCounts); +EXTERN void Cal_BddFunctionProfileMultiple(Cal_BddManager bddManager, Cal_Bdd *fUserBddArray, long * funcCounts); +EXTERN Cal_Bdd Cal_BddSubstitute(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN void Cal_BddSupport(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd *support); +EXTERN int Cal_BddDependsOn(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd varUserBdd); +EXTERN Cal_Bdd Cal_BddSwapVars(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd, Cal_Bdd hUserBdd); +EXTERN Cal_Bdd Cal_BddVarSubstitute(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN Cal_Block Cal_BddNewVarBlock(Cal_BddManager bddManager, Cal_Bdd variable, long length); +EXTERN void Cal_BddVarBlockReorderable(Cal_BddManager bddManager, Cal_Block block, int reorderable); +EXTERN Cal_Bdd Cal_BddUndumpBdd(Cal_BddManager bddManager, Cal_Bdd * userVars, FILE * fp, int * error); +EXTERN int Cal_BddDumpBdd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd * userVars, FILE * fp); +EXTERN void Cal_BddSetGCMode(Cal_BddManager bddManager, int gcMode); +EXTERN int Cal_BddManagerGC(Cal_BddManager bddManager); +EXTERN void Cal_BddManagerSetGCLimit(Cal_BddManager manager); +EXTERN void Cal_MemFatal(char *message); +EXTERN Cal_Address_t Cal_MemAllocation(void); +EXTERN Cal_Pointer_t Cal_MemGetBlock(Cal_Address_t size); +EXTERN void Cal_MemFreeBlock(Cal_Pointer_t p); +EXTERN Cal_Pointer_t Cal_MemResizeBlock(Cal_Pointer_t p, Cal_Address_t newSize); +EXTERN Cal_Pointer_t Cal_MemNewRec(Cal_RecMgr mgr); +EXTERN void Cal_MemFreeRec(Cal_RecMgr mgr, Cal_Pointer_t rec); +EXTERN Cal_RecMgr Cal_MemNewRecMgr(int size); +EXTERN void Cal_MemFreeRecMgr(Cal_RecMgr mgr); +EXTERN int Cal_PerformanceTest(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions, int iteration, int seed, int andPerformanceFlag, int multiwayPerformanceFlag, int onewayPerformanceFlag, int quantifyPerformanceFlag, int composePerformanceFlag, int relprodPerformanceFlag, int swapPerformanceFlag, int substitutePerformanceFlag, int sanityCheckFlag, int computeMemoryOverheadFlag, int superscalarFlag); +EXTERN void Cal_PipelineSetDepth(Cal_BddManager bddManager, int depth); +EXTERN int Cal_PipelineInit(Cal_BddManager bddManager, Cal_BddOp_t bddOp); +EXTERN Cal_Bdd Cal_PipelineCreateProvisionalBdd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN int Cal_PipelineExecute(Cal_BddManager bddManager); +EXTERN Cal_Bdd Cal_PipelineUpdateProvisionalBdd(Cal_BddManager bddManager, Cal_Bdd provisionalBdd); +EXTERN int Cal_BddIsProvisional(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN void Cal_PipelineQuit(Cal_BddManager bddManager); +EXTERN void Cal_BddPrintBdd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_VarNamingFn_t VarNamingFn, Cal_TerminalIdFn_t TerminalIdFn, Cal_Pointer_t env, FILE *fp); +EXTERN void Cal_BddPrintProfile(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_VarNamingFn_t varNamingProc, char * env, int lineLength, FILE * fp); +EXTERN void Cal_BddPrintProfileMultiple(Cal_BddManager bddManager, Cal_Bdd *userBdds, Cal_VarNamingFn_t varNamingProc, char * env, int lineLength, FILE * fp); +EXTERN void Cal_BddPrintFunctionProfile(Cal_BddManager bddManager, Cal_Bdd f, Cal_VarNamingFn_t varNamingProc, char * env, int lineLength, FILE * fp); +EXTERN void Cal_BddPrintFunctionProfileMultiple(Cal_BddManager bddManager, Cal_Bdd *userBdds, Cal_VarNamingFn_t varNamingProc, char * env, int lineLength, FILE * fp); +EXTERN Cal_Bdd Cal_BddExists(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN Cal_Bdd Cal_BddRelProd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd); +EXTERN Cal_Bdd Cal_BddForAll(Cal_BddManager bddManager, Cal_Bdd fUserBdd); +EXTERN Cal_Bdd Cal_BddCofactor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd cUserBdd); +EXTERN Cal_Bdd Cal_BddReduce(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd cUserBdd); +EXTERN Cal_Bdd Cal_BddBetween(Cal_BddManager bddManager, Cal_Bdd fMinUserBdd, Cal_Bdd fMaxUserBdd); +EXTERN void Cal_BddFunctionPrint(Cal_BddManager bddManager, Cal_Bdd userBdd, char *name); + +/**AutomaticEnd***************************************************************/ + +#endif /* _CAL */ diff --git a/calAllAbs.html b/calAllAbs.html new file mode 100644 index 0000000..7f048cc --- /dev/null +++ b/calAllAbs.html @@ -0,0 +1,1293 @@ + +cal package abstract + + + + + +
+
AddBlock() +
required + +
AddToFreeList() +
required + +
AssociationIsEqual() +
Checks for equality of two associations + +
BddAddInternalReferences() +
required + +
BddArrayOpBF() +
Internal common routine for Cal_BddPairwiseAnd and Cal_BddPairwiseOr + +
BddArrayToRequestNodeListArray() +
Converts an array of BDDs to a list of requests representing BDD + pairs + +
BddCofactorBF() +
required + +
BddConvertDataStructBack() +
Changes the data structure of the bdd nodes to + the original one. + +
BddConvertDataStruct() +
Changes the data structure of the bdd nodes. + +
BddCountNoNodes() +
+ +
BddCountNodes() +
+ +
BddDFStep() +
required + +
BddDefaultTransformFn() +
required + +
BddDominatedStep() +
+ +
BddDumpBddStep() +
+ +
BddExchangeAux() +
required + +
BddExchangeVarBlocks() +
required + +
BddExchange() +
required + +
BddExistsApply() +
required + +
BddExistsBFAux() +
required + +
BddExistsBFPlusDF() +
required + +
BddExistsReduce() +
required + +
BddExistsStep() +
required + +
BddHighestRefStep() +
+ +
BddIntersectsStep() +
Recursive routine to returns a BDD that implies conjunction of + argument BDDs + +
BddMarkBdd() +
+ +
BddMultiwayOp() +
Internal routine for multiway operations + +
BddNukeInternalReferences() +
required + +
BddPrintBddStep() +
required + +
BddPrintTopVar() +
required + +
BddProfileStep() +
+ +
BddReallocateNodesInPlace() +
required + +
BddReallocateNodes() +
required + +
BddReduceBF() +
required + +
BddRelProdApply() +
required + +
BddRelProdBFAux() +
required + +
BddRelProdBFPlusDF() +
required + +
BddRelProdReduce() +
required + +
BddRelProdStep() +
required + +
BddReorderFixAndFreeForwardingNodes() +
Traverses the forwarding node lists of index, + index+1 .. up to index+level. Frees the intermediate forwarding nodes. + +
BddReorderFixForwardingNodes() +
Fixes the forwarding nodes in a unique table. + +
BddReorderFreeNodes() +
required + +
BddReorderSiftAux() +
Reorder variables using "sift" algorithm. + +
BddReorderSiftToBestPos() +
required + +
BddReorderSift() +
required + +
BddReorderStableWindow3Aux() +
required + +
BddReorderStableWindow3() +
required + +
BddReorderSwapVarIndex() +
required + +
BddReorderVarSift() +
Reorder variables using "sift" algorithm. + +
BddReorderVarWindow() +
required + +
BddReorderWindow2() +
required + +
BddReorderWindow2() +
required + +
BddReorderWindow3() +
required + +
BddReorderWindow3() +
required + +
BddSatisfyStep() +
Returns a BDD which implies f, is true for some valuation + on which f is true, and which has at most one node at each level + +
BddSatisfySupportStep() +
+ +
BddSatisfyingFractionStep() +
+ +
BddSiftBlock() +
required + +
BddSiftPerfromPhaseIV() +
required + +
BddSizeStep() +
+ +
BddTerminalId() +
required + +
BddTerminalValueAux() +
required + +
BddUndumpBddStep() +
+ +
BlockSizeIndex() +
required + +
Buddy() +
required + +
BytesNeeded() +
+ +
CacheTablePrint() +
required + +
CacheTableTwoRehash() +
required + +
CalAlignCollisionChains() +
required + +
CalAssociationListFree() +
Frees the variable associations + +
CalBddArrayPreProcessing() +
required + +
CalBddBlockDelta() +
required + +
CalBddDependsOnStep() +
required + +
CalBddFatalMessage() +
Prints fatal message and exits. + +
CalBddFindBlock() +
required + +
CalBddFunctionPrint() +
Prints the function implemented by the argument BDD + +
CalBddGetExternalBdd() +
Prints fatal message and exits. + +
CalBddGetInternalBdd() +
Prints fatal message and exits. + +
CalBddITE() +
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h + +
CalBddIdentity() +
Returns the duplicate BDD of the argument BDD. + +
CalBddIf() +
Returns the BDD corresponding to the top variable of + the argument BDD. + +
CalBddIsCubeStep() +
Returns 1 if the argument BDD is a cube, 0 otherwise + +
CalBddManagerCreateNewVar() +
This function creates and returns a new variable with given + index value. + +
CalBddManagerGCCheck() +
required + +
CalBddManagerGetCacheTableData() +
required + +
CalBddManagerPrint() +
required + +
CalBddMarkSharedNodes() +
required + +
CalBddNodePrint() +
required + +
CalBddNumberSharedNodes() +
required + +
CalBddOpBF() +
Internal routine to compute a logical operation on a pair of BDDs + +
CalBddOpITEBF() +
required + +
CalBddPackNodesAfterReorderForSingleId() +
Packs the nodes if the variables which has just + been sifted. + +
CalBddPackNodesForMultipleIds() +
required + +
CalBddPackNodesForSingleId() +
required + +
CalBddPostProcessing() +
required + +
CalBddPreProcessing() +
required + +
CalBddPrintProfileAux() +
Prints a profile to the file given by fp. The varNamingProc + is as in Cal_BddPrintBdd. lineLength gives the line width to scale + the profile to. + +
CalBddPrint() +
required + +
CalBddReorderAuxBF() +
required + +
CalBddReorderAuxDF() +
required + +
CalBddReorderFixCofactors() +
Fixes the cofactors of the nodes belonging to + the given index. + +
CalBddReorderFixProvisionalNodes() +
required + +
CalBddReorderFixUserBddPtrs() +
required + +
CalBddReorderReclaimForwardedNodes() +
required + +
CalBddShiftBlock() +
required + +
CalBddSupportStep() +
returns the support of f as a null-terminated array of variables + +
CalBddTypeAux() +
Returns the BDD type by recursively traversing the argument BDD + +
CalBddUniqueTableNumLockedNodes() +
required + +
CalBddUnmarkNodes() +
recursively unmarks the nodes + +
CalBddVarName() +
required + +
CalBddVarSubstitute() +
Substitute a set of variables by functions + +
CalBddWarningMessage() +
Prints warning message. + +
CalBlockMemoryConsumption() +
required + +
CalCacheTableMemoryConsumption() +
required + +
CalCacheTablePrint() +
required + +
CalCacheTableRehash() +
required + +
CalCacheTableTwoFixResultPointers() +
required + +
CalCacheTableTwoFlushAll() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoFlushAssociationId() +
Flushes the entries from the cache which + correspond to the given associationId. + +
CalCacheTableTwoFlush() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoGCFlush() +
required + +
CalCacheTableTwoInit() +
Initialize a Cache table using default parameters. + +
CalCacheTableTwoInsert() +
Directly insert a BDD node in the Cache table. + +
CalCacheTableTwoLookup() +
required + +
CalCacheTableTwoQuit() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoRepackUpdate() +
required + +
CalCheckAllValidity() +
required + +
CalCheckAssociationValidity() +
Checks the validity of association. + +
CalCheckAssoc() +
required + +
CalCheckCacheTableValidity() +
required + +
CalCheckPipelineValidity() +
required + +
CalCheckRefCountValidity() +
required + +
CalCheckValidityOfANode() +
required + +
CalCheckValidityOfNodesForId() +
required + +
CalCheckValidityOfNodesForWindow() +
required + +
CalComposeRequestCreate() +
required + +
CalDecreasingOrderCompare() +
required + +
CalFixupAssoc() +
required + +
CalFreeBlockRecursively() +
required + +
CalHashTableAddDirectAux() +
required + +
CalHashTableAddDirect() +
Directly insert a BDD node in the hash table. + +
CalHashTableApply() +
required + +
CalHashTableCleanUp() +
required + +
CalHashTableComposeApply() +
required + +
CalHashTableDelete() +
Deletes a BDD node in the hash table. + +
CalHashTableFindOrAdd() +
required + +
CalHashTableGC() +
This function performs the garbage collection operation + for a particular index. + +
CalHashTableITEApply() +
required + +
CalHashTableInit() +
Initialize a hash table using default parameters. + +
CalHashTableLookup() +
required + +
CalHashTableOneInit() +
Initialize a hash table using default parameters. + +
CalHashTableOneInsert() +
Directly insert a BDD node in the hash table. + +
CalHashTableOneLookup() +
required + +
CalHashTableOnePrint() +
required + +
CalHashTableOneQuit() +
Free a hash table along with the associated storage. + +
CalHashTablePrint() +
Prints a hash table. + +
CalHashTableQuit() +
Free a hash table along with the associated storage. + +
CalHashTableReduce() +
required + +
CalHashTableRehash() +
required + +
CalHashTableSubstituteApply() +
required + +
CalHashTableSubstituteApply() +
required + +
CalHashTableSubstituteReduce() +
required + +
CalHashTableSubstituteReduce() +
required + +
CalHashTableSwapVarsApply() +
required + +
CalHashTableSwapVarsMinusApply() +
required + +
CalHashTableSwapVarsPlusApply() +
required + +
CalHashTableThreeFindOrAdd() +
required + +
CalHashTableThreeRehash() +
required + +
CalIncreasingOrderCompare() +
required + +
CalInitInteract() +
Initializes the interaction matrix. + +
CalNodeManagerInit() +
Initializes a node manager. + +
CalNodeManagerPrint() +
Prints address of each free node. + +
CalNodeManagerQuit() +
Frees a node manager. + +
CalOpAnd() +
required + +
CalOpBddVarSubstitute() +
required + +
CalOpCofactor() +
required + +
CalOpExists() +
required + +
CalOpITE() +
required + +
CalOpNand() +
required + +
CalOpOr() +
required + +
CalOpRelProd() +
required + +
CalOpXor() +
required + +
CalPackNodes() +
required + +
CalPageManagerAllocPage() +
Allocs a new page. + +
CalPageManagerFreePage() +
Free a page. + +
CalPageManagerInit() +
Initializes a pageManager. + +
CalPageManagerPrint() +
Prints address of each memory segment and address of each page. + +
CalPageManagerQuit() +
Frees pageManager and associated pages. + +
CalPerformaceTestSuperscalar() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceMemoryOverhead() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestAnd() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestCompose() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestMultiway() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestNonSuperscalar() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestOneway() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestQuantifyAllTogether() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestRelProd() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestSubstitute() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestSwapVars() +
Performance test routine for quantify (all variables at the same + time). + +
CalQuantifySanityCheck() +
Performance test routine for quantify (all variables at the same + time). + +
CalReorderAssociationFix() +
required + +
CalRepackNodesAfterGC() +
required + +
CalRequestNodeListArrayITE() +
required + +
CalRequestNodeListArrayOp() +
Computes result BDDs for an array of lists, each entry of which + is pair of pointers, each of which points to a operand BDD or an entry in + another list with a smaller array index + +
CalRequestNodeListCompose() +
required + +
CalSetInteract() +
Set interaction matrix entries. + +
CalTestInteract() +
Test interaction matrix entries. + +
CalUniqueTableForIdFindOrAdd() +
find or add in the unique table for id. + +
CalUniqueTableForIdLookup() +
Lookup unique table for id. + +
CalUniqueTableForIdRehashNode() +
required + +
CalUniqueTablePrint() +
required + +
CalVarAssociationRepackUpdate() +
Need to be called after repacking. + +
Cal_AssociationInit() +
Creates or finds a variable association. + +
Cal_AssociationQuit() +
Deletes the variable association given by id + +
Cal_AssociationSetCurrent() +
Sets the current variable association to the one given by id and + returns the ID of the old association. + +
Cal_BddAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddBetween() +
Returns a minimal BDD whose function contains fMin and is + contained in fMax. + +
Cal_BddCofactor() +
Returns the generalized cofactor of BDD f with respect + to BDD c. + +
Cal_BddCompose() +
composition - substitute a BDD variable by a function + +
Cal_BddDependsOn() +
Returns 1 if f depends on var and returns 0 otherwise. + +
Cal_BddDumpBdd() +
Write a BDD to a file + +
Cal_BddDynamicReordering() +
Specify dynamic reordering technique. + +
Cal_BddElse() +
Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddExists() +
Returns the result of existentially quantifying some + variables from the given BDD. + +
Cal_BddForAll() +
Returns the result of universally quantifying some + variables from the given BDD. + +
Cal_BddFree() +
Frees the argument BDD. + +
Cal_BddFunctionPrint() +
Prints the function implemented by the argument BDD + +
Cal_BddFunctionProfileMultiple() +
Returns a "function profile" for fArray. + +
Cal_BddFunctionProfile() +
Returns a "function profile" for f. + +
Cal_BddGetIfId() +
Returns the id of the top variable of the argument BDD. + +
Cal_BddGetIfIndex() +
Returns the index of the top variable of the argument BDD. + +
Cal_BddGetRegular() +
Returns a BDD with positive from a given BDD with arbitrary phase + +
Cal_BddITE() +
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h + +
Cal_BddIdentity() +
Returns the duplicate BDD of the argument BDD. + +
Cal_BddIf() +
Returns the BDD corresponding to the top variable of + the argument BDD. + +
Cal_BddImplies() +
Computes a BDD that implies conjunction of f and Cal_BddNot(g) + +
Cal_BddIntersects() +
Computes a BDD that implies conjunction of f and g. + +
Cal_BddIsBddConst() +
Returns 1 if the argument BDD is a constant, 0 otherwise. + +
Cal_BddIsBddNull() +
Returns 1 if the argument BDD is NULL, 0 otherwise. + +
Cal_BddIsBddOne() +
Returns 1 if the argument BDD is constant one, 0 otherwise. + +
Cal_BddIsBddZero() +
Returns 1 if the argument BDD is constant zero, 0 otherwise. + +
Cal_BddIsCube() +
Returns 1 if the argument BDD is a cube, 0 otherwise + +
Cal_BddIsEqual() +
Returns 1 if argument BDDs are equal, 0 otherwise. + +
Cal_BddIsProvisional() +
Returns 1, if the given user BDD contains + provisional BDD node. + +
Cal_BddManagerCreateNewVarAfter() +
Creates and returns a new variable after the specified one in + the variable order. + +
Cal_BddManagerCreateNewVarBefore() +
Creates and returns a new variable before the specified one in + the variable order. + +
Cal_BddManagerCreateNewVarFirst() +
Creates and returns a new variable at the start of the variable + order. + +
Cal_BddManagerCreateNewVarLast() +
Creates and returns a new variable at the end of the variable + order. + +
Cal_BddManagerGC() +
Invokes the garbage collection at the manager level. + +
Cal_BddManagerGetHooks() +
Returns the hooks field of the manager. + +
Cal_BddManagerGetNumNodes() +
Returns the number of BDD nodes + +
Cal_BddManagerGetVarWithId() +
Returns the variable with the specified id, null if no + such variable exists + +
Cal_BddManagerGetVarWithIndex() +
Returns the variable with the specified index, null if no + such variable exists + +
Cal_BddManagerInit() +
Creates and initializes a new BDD manager. + +
Cal_BddManagerQuit() +
Frees the BDD manager and all the associated allocations + +
Cal_BddManagerSetGCLimit() +
Sets the limit of the garbage collection. + +
Cal_BddManagerSetHooks() +
Sets the hooks field of the manager. + +
Cal_BddManagerSetParameters() +
Sets appropriate fields of BDD Manager. + +
Cal_BddMultiwayAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddMultiwayOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddMultiwayXor() +
Returns the BDD for logical XOR of argument BDDs + +
Cal_BddNand() +
Returns the BDD for logical NAND of argument BDDs + +
Cal_BddNewVarBlock() +
Creates and returns a variable block used for + controlling dynamic reordering. + +
Cal_BddNodeLimit() +
Sets the node limit to new_limit and returns the old limit. + +
Cal_BddNor() +
Returns the BDD for logical NOR of argument BDDs + +
Cal_BddNot() +
Returns the complement of the argument BDD. + +
Cal_BddOne() +
Returns the BDD for the constant one + +
Cal_BddOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddOverflow() +
Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared. + +
Cal_BddPairwiseAnd() +
Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseOr() +
Returns an array of BDDs obtained by logical OR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseXor() +
Returns an array of BDDs obtained by logical XOR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPrintBdd() +
Prints a BDD in the human readable form. + +
Cal_BddPrintFunctionProfileMultiple() +
Cal_BddPrintFunctionProfileMultiple is like + Cal_BddPrintFunctionProfile except for multiple BDDs + +
Cal_BddPrintFunctionProfile() +
Cal_BddPrintFunctionProfile is like Cal_BddPrintProfile except + it displays a function profile for f + +
Cal_BddPrintProfileMultiple() +
Cal_BddPrintProfileMultiple is like Cal_BddPrintProfile except + it displays the profile for a set of BDDs + +
Cal_BddPrintProfile() +
Displays the node profile for f on fp. lineLength specifies + the maximum line length. varNamingFn is as in + Cal_BddPrintBdd. + +
Cal_BddProfileMultiple() +
+ +
Cal_BddProfile() +
Returns a "node profile" of f, i.e., the number of nodes at each + level in f. + +
Cal_BddReduce() +
Returns a BDD which agrees with f for all valuations + which satisfy c. + +
Cal_BddRelProd() +
Returns the result of taking the logical AND of the + argument BDDs and existentially quantifying some variables from the + product. + +
Cal_BddReorder() +
Invoke the current dynamic reodering method. + +
Cal_BddSatisfySupport() +
Returns a special cube contained in f. + +
Cal_BddSatisfyingFraction() +
Returns the fraction of valuations which make f true. (Note that + this fraction is independent of whatever set of variables f is supposed to be + a function of) + +
Cal_BddSatisfy() +
Returns a BDD which implies f, true for + some valuation on which f is true, and which has at most + one node at each level + +
Cal_BddSetGCMode() +
Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on. + +
Cal_BddSizeMultiple() +
The routine is like Cal_BddSize, but takes a null-terminated + array of BDDs and accounts for sharing of nodes. + +
Cal_BddSize() +
Returns the number of nodes in f when negout is nonzero. If + negout is zero, we pretend that the BDDs don't have negative-output pointers. + +
Cal_BddStats() +
Prints miscellaneous BDD statistics + +
Cal_BddSubstitute() +
Substitute a set of variables by functions + +
Cal_BddSupport() +
returns the support of f as a null-terminated array of variables + +
Cal_BddSwapVars() +
Return a function obtained by swapping two variables + +
Cal_BddThen() +
Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddTotalSize() +
Returns the number of nodes in the Unique table + +
Cal_BddType() +
Returns type of a BDD ( 0, 1, +var, -var, ovrflow, nonterminal) + +
Cal_BddUnFree() +
Unfrees the argument BDD. + +
Cal_BddUndumpBdd() +
Reads a BDD from a file + +
Cal_BddVarBlockReorderable() +
Sets the reoderability of a particular block. + +
Cal_BddVarSubstitute() +
Substitute a set of variables by set of another variables. + +
Cal_BddVars() +
Returns the number of BDD variables + +
Cal_BddXnor() +
Returns the BDD for logical exclusive NOR of argument BDDs + +
Cal_BddXor() +
Returns the BDD for logical exclusive OR of argument BDDs + +
Cal_BddZero() +
Returns the BDD for the constant zero + +
Cal_MemAllocation() +
Returns the memory allocated. + +
Cal_MemFatal() +
Prints an error message and exits. + +
Cal_MemFreeBlock() +
Frees the block. + +
Cal_MemFreeRecMgr() +
Frees all the storage associated with the specified record manager. + +
Cal_MemFreeRec() +
Frees a record managed by the indicated record manager. + +
Cal_MemGetBlock() +
Allocates a new block of the specified size. + +
Cal_MemNewRecMgr() +
Creates a new record manager with the given record size. + +
Cal_MemNewRec() +
Allocates a record from the specified record manager. + +
Cal_MemResizeBlock() +
Expands or contracts the block to a new size. + We try to avoid moving the block if possible. + +
Cal_PerformanceTest() +
Main routine for testing performances of various routines. + +
Cal_PipelineCreateProvisionalBdd() +
Create a provisional BDD in the pipeline. + +
Cal_PipelineExecute() +
Executes a pipeline. + +
Cal_PipelineInit() +
Initialize a BDD pipeline. + +
Cal_PipelineQuit() +
Resets the pipeline freeing all resources. + +
Cal_PipelineSetDepth() +
Set depth of a BDD pipeline. + +
Cal_PipelineUpdateProvisionalBdd() +
Update a provisional Bdd obtained during pipelining. + +
Cal_TempAssociationAugment() +
Adds to the temporary variable association. + +
Cal_TempAssociationInit() +
Sets the temporary variable association. + +
Cal_TempAssociationQuit() +
Cleans up temporary association + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
CeilingLog2() +
required + +
Chars() +
required + +
CheckAssoc() +
required + +
CheckValidityOfNodes() +
required + +
CofactorFixAndReclaimForwardedNodes() +
required + +
Cofactor() +
required + +
Decode() +
required + +
Error() +
required + +
GetRandomNumbers() +
Generates "count" many random numbers ranging between + "lowerBound" and "upperBound". + +
HashTableAddDirect() +
Directly insert a BDD node in the hash table. + +
HashTableApply() +
required + +
HashTableCofactorApply() +
required + +
HashTableCofactorReduce() +
required + +
HashTableFindOrAdd() +
required + +
HashTableOneRehash() +
required + +
HashTableReduceApply() +
required + +
HashTableReduce() +
required + +
IndexCmp() +
+ +
MergeAndFree() +
required + +
PageAlign() +
Return page aligned address greater than or equal to + the pointer. + +
PageManagerExpandStorage() +
Allocates a segment of memory to expand the storage managed by + pageManager. The allocated segment is divided into free pages + which are linked as a freePageList. + +
PrintBddProfileAfterReorder() +
required + +
PrintBdd() +
required + +
RandomTests() +
required + +
Read() +
+ +
RemoveFromFreeList() +
required + +
SegmentToPageList() +
Converts a memory segment into a linked list of pages. + if p is a pointer to a page, *p contains address of the next page + if p is a pointer to the last page, *p contains lastPointer. + +
SweepVarTable() +
required + +
TestAnd() +
required + +
TestArrayOp() +
required + +
TestAssoc() +
required + +
TestCompose() +
required + +
TestDump() +
required + +
TestGenCof() +
required + +
TestITE() +
required + +
TestIdNot() +
required + +
TestInterImpl() +
required + +
TestMultiwayAnd() +
required + +
TestMultiwayLarge() +
required + +
TestMultiwayOr() +
required + +
TestNand() +
required + +
TestOr() +
required + +
TestPipeline() +
required + +
TestQnt() +
required + +
TestReduce() +
required + +
TestRelProd() +
required + +
TestReorderBlock() +
required + +
TestReorder() +
required + +
TestSatisfy() +
required + +
TestSize() +
required + +
TestSubstitute() +
required + +
TestSwapVars() +
required + +
TestVarSubstitute() +
required + +
TestXor() +
required + +
TrimToSize() +
required + +
UniqueTableForIdFindOrAdd() +
find or add in the unique table for id. + +
Write() +
+ +
asAddress() +
required + +
asDouble() +
required + +
chars() +
+ +
cpuTime() +
Computes the number of page faults. + +
cpuTime() +
required + +
ddClearLocal() +
Performs a DFS from f, clearing the LSB of the then pointers. + +
ddSuppInteract() +
Find the support of f. + +
ddUpdateInteract() +
Marks as interacting all pairs of variables that appear in + support. + +
elapsedTime() +
Computes the time. + +
elapsedTime() +
Computes the time. + +
handler() +
required + +
main() +
required + +
main() +
required + +
pageFaults() +
Computes the number of page faults. + +
terminalIdFn() +
required + +
+ +
+ +Last updated on 970711 20h11 + diff --git a/calAllByFile.html b/calAllByFile.html new file mode 100644 index 0000000..0db90e0 --- /dev/null +++ b/calAllByFile.html @@ -0,0 +1,13 @@ + +The cal package for maintainers + + + + + + + + + + + diff --git a/calAllByFunc.html b/calAllByFunc.html new file mode 100644 index 0000000..2a9096d --- /dev/null +++ b/calAllByFunc.html @@ -0,0 +1,13 @@ + +The cal package for maintainers + + + + + + + + + + + diff --git a/calAllDet.html b/calAllDet.html new file mode 100644 index 0000000..b8e1df1 --- /dev/null +++ b/calAllDet.html @@ -0,0 +1,7870 @@ + +The cal package: all functions + + + +
+
+
+
+static void 
+AddBlock(
+  Cal_Block  b1, 
+  Cal_Block  b2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+static void 
+AddToFreeList(
+  Block  b 
+)
+
+
AddToFreeList(b) adds b to the appropriate free list. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static int 
+AssociationIsEqual(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t * p, 
+  Cal_Bdd_t * q 
+)
+
+
Checks for equality of two associations +

+ +

Side Effects None +

+ +

Defined in calAssociation.c + +
+
+static void 
+BddAddInternalReferences(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static Cal_Bdd_t * 
+BddArrayOpBF(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t* bddArray, 
+  int  numFunction, 
+  CalOpProc_t  calOpProc 
+)
+
+
Internal common routine for Cal_BddPairwiseAnd and Cal_BddPairwiseOr +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+static void 
+BddArrayToRequestNodeListArray(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t * calBddArray, 
+  int  numBdds 
+)
+
+
Converts an array of BDDs to a list of requests representing BDD +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+static Cal_Bdd_t 
+BddCofactorBF(
+  Cal_BddManager_t * bddManager, 
+  CalOpProc_t  calOpProc, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  c 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+static void 
+BddConvertDataStructBack(
+  Cal_BddManager_t * bddManager 
+)
+
+
Data structure conversion: thenBddId -> id + elseBddId -> ref count +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddConvertDataStruct(
+  Cal_BddManager_t * bddManager 
+)
+
+
New data structure: thenBddId -> id + elseBddId -> ref count +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static int 
+BddCountNoNodes(
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static int 
+BddCountNodes(
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static Cal_Bdd_t 
+BddDFStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  CalOpProc_t  calOpProc, 
+  unsigned short  opCode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddDefaultTransformFn(
+  Cal_BddManager_t * bddManager, 
+  CalAddress_t  value1, 
+  CalAddress_t  value2, 
+  CalAddress_t * result1, 
+  CalAddress_t * result2, 
+  Cal_Pointer_t  pointer 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddManager.c + +
+
+static void 
+BddDominatedStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  long * funcCounts, 
+  CalHashTable_t * h 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static void 
+BddDumpBddStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  FILE * fp, 
+  CalHashTable_t * h, 
+  Cal_BddIndex_t * normalizedIndexes, 
+  int  indexSize, 
+  int  nodeNumberSize 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+static void 
+BddExchangeAux(
+  Cal_BddManager_t * bddManager, 
+  CalBddNode_t * f, 
+  int  id, 
+  int  nextId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddExchangeVarBlocks(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  parent, 
+  long  blockIndex 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddExchange(
+  Cal_BddManager_t * bddManager, 
+  long  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddExistsApply(
+  Cal_BddManager_t * bddManager, 
+  int  quantifying, 
+  CalHashTable_t * existHashTable, 
+  CalHashTable_t ** existHashTableArray, 
+  CalOpProc1_t  calOpProc, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddExistsBFAux(
+  Cal_BddManager_t * bddManager, 
+  int  minIndex, 
+  CalHashTable_t ** existHashTableArray, 
+  CalHashTable_t ** orHashTableArray, 
+  CalOpProc1_t  calOpProc, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static Cal_Bdd_t 
+BddExistsBFPlusDF(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  unsigned short  opCode, 
+  CalAssociation_t * association 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddExistsReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * existHashTable, 
+  CalHashTable_t ** existHashTableArray, 
+  CalHashTable_t ** orHashTableArray, 
+  unsigned short  opCode, 
+  CalAssociation_t * association 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static Cal_Bdd_t 
+BddExistsStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  unsigned short  opCode, 
+  CalAssociation_t * association 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddHighestRefStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  CalHashTable_t * h 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static Cal_Bdd_t 
+BddIntersectsStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g 
+)
+
+
Recursive routine to returns a BDD that implies conjunction of + argument BDDs +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+static void 
+BddMarkBdd(
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static Cal_Bdd_t 
+BddMultiwayOp(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t * calBddArray, 
+  int  numBdds, 
+  CalOpProc_t  op 
+)
+
+
Internal routine for multiway operations +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+static void 
+BddNukeInternalReferences(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddPrintBddStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_VarNamingFn_t  VarNamingFn, 
+  Cal_TerminalIdFn_t  TerminalIdFn, 
+  Cal_Pointer_t  env, 
+  FILE * fp, 
+  CalHashTable_t* hashTable, 
+  int  indentation 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+static void 
+BddPrintTopVar(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_VarNamingFn_t  VarNamingFn, 
+  Cal_Pointer_t  env, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+static void 
+BddProfileStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  long * levelCounts, 
+  CountFn_t  countFn 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static void 
+BddReallocateNodesInPlace(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddReallocateNodes(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static Cal_Bdd_t 
+BddReduceBF(
+  Cal_BddManager_t * bddManager, 
+  CalOpProc_t  calOpProc, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  c 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+static void 
+BddRelProdApply(
+  Cal_BddManager_t * bddManager, 
+  int  quantifying, 
+  CalHashTable_t * relProdHashTable, 
+  CalHashTable_t ** relProdHashTableArray, 
+  CalHashTable_t ** andHashTableArray, 
+  CalOpProc_t  calOpProc, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddRelProdBFAux(
+  Cal_BddManager_t * bddManager, 
+  int  minIndex, 
+  CalHashTable_t ** relProdHashTableArray, 
+  CalHashTable_t ** andHashTableArray, 
+  CalHashTable_t ** orHashTableArray, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static Cal_Bdd_t 
+BddRelProdBFPlusDF(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  unsigned short  opCode, 
+  CalAssociation_t * association 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddRelProdReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * relProdHashTable, 
+  CalHashTable_t ** relProdHashTableArray, 
+  CalHashTable_t ** andHashTableArray, 
+  CalHashTable_t ** orHashTableArray, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static Cal_Bdd_t 
+BddRelProdStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+BddReorderFixAndFreeForwardingNodes(
+  Cal_BddManager  bddManager, 
+  Cal_BddId_t  id, 
+  int  numLevels 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+BddReorderFixForwardingNodes(
+  Cal_BddManager  bddManager, 
+  Cal_BddId_t  id 
+)
+
+
As opposed to CalBddReorderFixCofactors, which fixes + the cofactors of the non-forwarding nodes, this routine traverses + the list of forwarding nodes and removes the intermediate level of + forwarding. Number of levels should be 1 or 2. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+BddReorderFreeNodes(
+  Cal_BddManager_t * bddManager, 
+  int  varId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+BddReorderSiftAux(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  block, 
+  Cal_Block * toSift, 
+  double  maxSizeFactor 
+)
+
+
Reorder variables using "sift" algorithm. +

+ +

Side Effects None +

+ +

Defined in calReorderDF.c + +
+
+static int 
+BddReorderSiftToBestPos(
+  Cal_BddManager_t * bddManager, 
+  int  varStartIndex, 
+  double  maxSizeFactor 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+BddReorderSift(
+  Cal_BddManager_t * bddManager, 
+  double  maxSizeFactor 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddReorderStableWindow3Aux(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  block, 
+  char * levels 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddReorderStableWindow3(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddReorderSwapVarIndex(
+  Cal_BddManager_t * bddManager, 
+  int  varIndex, 
+  int  forwardCheckFlag 
+)
+
+
Traversesoptional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+BddReorderVarSift(
+  Cal_BddManager  bddManager, 
+  double  maxSizeFactor 
+)
+
+
Reorder variables using "sift" algorithm. +

+ +

Side Effects None +

+ +

Defined in calReorderBF.c + +
+
+static void 
+BddReorderVarWindow(
+  Cal_BddManager  bddManager, 
+  char * levels 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static int 
+BddReorderWindow2(
+  Cal_BddManager  bddManager, 
+  long  index, 
+  int  directionFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static int 
+BddReorderWindow2(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  block, 
+  long  i 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static int 
+BddReorderWindow3(
+  Cal_BddManager  bddManager, 
+  long  index, 
+  int  directionFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static int 
+BddReorderWindow3(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  block, 
+  long  i 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static Cal_Bdd_t 
+BddSatisfyStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+static Cal_Bdd_t 
+BddSatisfySupportStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_BddId_t * support 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+static double 
+BddSatisfyingFractionStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  CalHashTable_t * hashTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+static void 
+BddSiftBlock(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  block, 
+  long  startPosition, 
+  double  maxSizeFactor 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+BddSiftPerfromPhaseIV(
+  Cal_BddManager_t * bddManager, 
+  int  varStartIndex, 
+  int  bestIndex, 
+  int  bottomMostSwapIndex 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static long 
+BddSizeStep(
+  Cal_Bdd_t  f, 
+  CountFn_t  countFn 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+static char * 
+BddTerminalId(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_TerminalIdFn_t  TerminalIdFn, 
+  Cal_Pointer_t  env 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+static void 
+BddTerminalValueAux(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  CalAddress_t * value1, 
+  CalAddress_t * value2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+static Cal_Bdd_t 
+BddUndumpBddStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t * vars, 
+  FILE * fp, 
+  Cal_BddIndex_t  numberVars, 
+  Cal_Bdd_t * shared, 
+  long  numberShared, 
+  long * sharedSoFar, 
+  int  indexSize, 
+  int  nodeNumberSize, 
+  int * error 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+static int 
+BlockSizeIndex(
+  Cal_Address_t  size 
+)
+
+
BlockSizeIndex(size) return the coded size for a block. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static Block 
+Buddy(
+  Block  b 
+)
+
+
Buddy(b) returns the Buddy block of b, or null if there is no Buddy. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static int 
+BytesNeeded(
+  long  n 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+static void 
+CacheTablePrint(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+static void 
+CacheTableTwoRehash(
+  CalCacheTable_t * cacheTable, 
+  int  grow 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalAlignCollisionChains(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+void 
+CalAssociationListFree(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calAssociation.c + +
+
+int 
+CalBddArrayPreProcessing(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+void 
+CalBddBlockDelta(
+  Cal_Block  b, 
+  long  delta 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+static int 
+CalBddDependsOnStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_BddIndex_t  varIndex, 
+  int  mark 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSupport.c + +
+
+void 
+CalBddFatalMessage(
+  char * string 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+long 
+CalBddFindBlock(
+  Cal_Block  block, 
+  long  index 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+void 
+CalBddFunctionPrint(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  calBdd, 
+  char * name 
+)
+
+
Prints the function implemented by the argument BDD +

+ +

Side Effects None +

+ +

Defined in calUtil.c + +
+
+Cal_Bdd 
+CalBddGetExternalBdd(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  internalBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+Cal_Bdd_t 
+CalBddGetInternalBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+Cal_Bdd_t 
+CalBddITE(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G, 
+  Cal_Bdd_t  H 
+)
+
+
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h +

+ +

Side Effects None +

+ +

See Also Cal_BddAnd +Cal_BddNand +Cal_BddOr +Cal_BddNor +Cal_BddXor +Cal_BddXnor + + +
Defined in calBddITE.c + +
+
+Cal_Bdd_t 
+CalBddIdentity(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  calBdd 
+)
+
+
Returns the duplicate BDD of the argument BDD. +

+ +

Side Effects The reference count of the BDD is increased by 1. +

+ +

See Also Cal_BddNot + + +
Defined in cal.c + +
+
+Cal_Bdd_t 
+CalBddIf(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd_t  F 
+)
+
+
Returns the BDD corresponding to the top variable of + the argument BDD. +

+ +

Side Effects None. +

+ +

Defined in cal.c + +
+
+int 
+CalBddIsCubeStep(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd_t  f 
+)
+
+
Returns 1 if the argument BDD is a cube, 0 otherwise +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+Cal_Bdd_t 
+CalBddManagerCreateNewVar(
+  Cal_BddManager_t * bddManager, 
+  Cal_BddIndex_t  index 
+)
+
+
Right now this function does not handle the case when the + package is working in multiprocessor mode. We need to put in the necessary + code later. +

+ +

Side Effects If the number of variables in the manager exceeds that of value + of numMaxVars, then we need to reallocate various fields of the manager. Also + depending upon the value of "index", idToIndex and indexToId tables would + change. +

+ +

Defined in calBddManager.c + +
+
+void 
+CalBddManagerGCCheck(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calGC.c + +
+
+void 
+CalBddManagerGetCacheTableData(
+  Cal_BddManager_t * bddManager, 
+  unsigned long * cacheSize, 
+  unsigned long * cacheEntries, 
+  unsigned long * cacheInsertions, 
+  unsigned long * cacheLookups, 
+  unsigned long * cacheHits, 
+  unsigned long * cacheCollisions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+static int 
+CalBddManagerPrint(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddManager.c + +
+
+void 
+CalBddMarkSharedNodes(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+void 
+CalBddNodePrint(
+  CalBddNode_t * bddNode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+void 
+CalBddNumberSharedNodes(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  CalHashTable_t * hashTable, 
+  long * next 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+Cal_Bdd_t 
+CalBddOpBF(
+  Cal_BddManager_t * bddManager, 
+  CalOpProc_t  calOpProc, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G 
+)
+
+
Internal routine to compute a logical operation on a pair of BDDs +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd_t 
+CalBddOpITEBF(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  Cal_Bdd_t  h 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddITE.c + +
+
+void 
+CalBddPackNodesAfterReorderForSingleId(
+  Cal_BddManager_t * bddManager, 
+  int  fixForwardedNodesFlag, 
+  int  bestIndex, 
+  int  bottomIndex 
+)
+
+
fixForwardedNodesFlag: Whether we need to fix + the forwarded nodes of variables corresponding to bestIndex through + bottomIndex. If this flag is set, then the forwarded nodes of these + variables are traversed and updated after the nodes of the bestIndex + have been copied. At the end the forwarded nodes are freed. If this + flag is not set, it is assumed that the cleanup pass has already + been performed. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalBddPackNodesForMultipleIds(
+  Cal_BddManager_t * bddManager, 
+  Cal_BddId_t  beginId, 
+  int  numLevels 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalBddPackNodesForSingleId(
+  Cal_BddManager_t * bddManager, 
+  Cal_BddId_t  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+int 
+CalBddPostProcessing(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+int 
+CalBddPreProcessing(
+  Cal_BddManager_t * bddManager, 
+  int  count, 
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+static void 
+CalBddPrintProfileAux(
+  Cal_BddManager_t * bddManager, 
+  long * levelCounts, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+void 
+CalBddPrint(
+  Cal_Bdd_t  calBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+void 
+CalBddReorderAuxBF(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+void 
+CalBddReorderAuxDF(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+void 
+CalBddReorderFixCofactors(
+  Cal_BddManager  bddManager, 
+  Cal_BddId_t  id 
+)
+
+
This routine traverses the unique table and for + each node, looks at the then and else cofactors. If needed fixes the + cofactors. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalBddReorderFixProvisionalNodes(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPipeline.c + +
+
+void 
+CalBddReorderFixUserBddPtrs(
+  Cal_BddManager  bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalBddReorderReclaimForwardedNodes(
+  Cal_BddManager  bddManager, 
+  int  startIndex, 
+  int  endIndex 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+Cal_Block 
+CalBddShiftBlock(
+  Cal_BddManager_t * bddManager, 
+  Cal_Block  b, 
+  long  index 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+static Cal_Bdd_t * 
+CalBddSupportStep(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t * support 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSupport.c + +
+
+int 
+CalBddTypeAux(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f 
+)
+
+
Returns the BDD type by recursively traversing the argument BDD +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+unsigned long 
+CalBddUniqueTableNumLockedNodes(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * uniqueTableForId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+static void 
+CalBddUnmarkNodes(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSupport.c + +
+
+char * 
+CalBddVarName(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  v, 
+  Cal_VarNamingFn_t  VarNamingFn, 
+  Cal_Pointer_t  env 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+Cal_Bdd_t 
+CalBddVarSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd_t  f, 
+  unsigned short  opCode, 
+  CalAssociation_t * assoc 
+)
+
+
Returns a BDD for f using the substitution defined by current + variable association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously +

+ +

Side Effects None +

+ +

See Also Cal_BddCompose + + +
Defined in calBddVarSubstitute.c + +
+
+void 
+CalBddWarningMessage(
+  char * string 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+unsigned long 
+CalBlockMemoryConsumption(
+  Cal_Block  block 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+unsigned long 
+CalCacheTableMemoryConsumption(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTablePrint(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableRehash(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoFixResultPointers(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+int 
+CalCacheTableTwoFlushAll(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoFlushAssociationId(
+  Cal_BddManager_t * bddManager, 
+  int  associationId 
+)
+
+
Flushes the entries from the cache which + correspond to the given associationId. +

+ +

Side Effects Cache entries are affected. +

+ +

Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoFlush(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoGCFlush(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+CalCacheTable_t * 
+CalCacheTableTwoInit(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoInsert(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  Cal_Bdd_t  result, 
+  unsigned long  opCode, 
+  int  cacheLevel 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+int 
+CalCacheTableTwoLookup(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  unsigned long  opCode, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+int 
+CalCacheTableTwoQuit(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCacheTableTwoRepackUpdate(
+  CalCacheTable_t * cacheTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+int 
+CalCheckAllValidity(
+  Cal_BddManager  bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalCheckAssociationValidity(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calAssociation.c + +
+
+int 
+CalCheckAssoc(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalCheckCacheTableValidity(
+  Cal_BddManager  bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calCacheTableTwo.c + +
+
+void 
+CalCheckPipelineValidity(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPipeline.c + +
+
+void 
+CalCheckRefCountValidity(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+int 
+CalCheckValidityOfANode(
+  Cal_BddManager_t * bddManager, 
+  CalBddNode_t * bddNode, 
+  int  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+int 
+CalCheckValidityOfNodesForId(
+  Cal_BddManager  bddManager, 
+  int  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+int 
+CalCheckValidityOfNodesForWindow(
+  Cal_BddManager  bddManager, 
+  Cal_BddIndex_t  index, 
+  int  numLevels 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalComposeRequestCreate(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  h, 
+  Cal_BddIndex_t  composeIndex, 
+  CalHashTable_t ** reqQueForCompose, 
+  CalHashTable_t ** reqQueForITE, 
+  Cal_Bdd_t * resultPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddCompose.c + +
+
+int 
+CalDecreasingOrderCompare(
+  const void * a, 
+  const void * b 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+void 
+CalFixupAssoc(
+  Cal_BddManager_t * bddManager, 
+  long  id1, 
+  long  id2, 
+  CalAssociation_t * assoc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderUtil.c + +
+
+void 
+CalFreeBlockRecursively(
+  Cal_Block  block 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBlk.c + +
+
+int 
+CalHashTableAddDirectAux(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  thenBdd, 
+  Cal_Bdd_t  elseBdd, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalHashTableAddDirect(
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * bddNode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalHashTableApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reqQueAtPipeDepth, 
+  CalOpProc_t  calOpProc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calApplyReduce.c + +
+
+void 
+CalHashTableCleanUp(
+  CalHashTable_t * hashTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalHashTableComposeApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_BddIndex_t  gIndex, 
+  CalHashTable_t ** reqQueForCompose, 
+  CalHashTable_t ** reqQueForITE 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddCompose.c + +
+
+void 
+CalHashTableDelete(
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * bddNode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+int 
+CalHashTableFindOrAdd(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  thenBdd, 
+  Cal_Bdd_t  elseBdd, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+int 
+CalHashTableGC(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable 
+)
+
+
The input is the hash table containing the nodes + belonging to that level. Each bin of the hash table is traversed and + the Bdd nodes with 0 reference count are put at the appropriate + level in the processing que of the manager. +

+ +

Side Effects The number of nodes in the hash table can possibly decrease. +

+ +

See Also optional + + +
Defined in calGC.c + +
+
+void 
+CalHashTableITEApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reqQueAtPipeDepth 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddITE.c + +
+
+CalHashTable_t * 
+CalHashTableInit(
+  Cal_BddManager_t * bddManager, 
+  Cal_BddId_t  bddId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+int 
+CalHashTableLookup(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  thenBdd, 
+  Cal_Bdd_t  elseBdd, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+CalHashTable_t * 
+CalHashTableOneInit(
+  Cal_BddManager_t * bddManager, 
+  int  itemSize 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableOne.c + +
+
+void 
+CalHashTableOneInsert(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  keyBdd, 
+  char * valuePtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableOne.c + +
+
+int 
+CalHashTableOneLookup(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  keyBdd, 
+  char ** valuePtrPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableOne.c + +
+
+void 
+CalHashTableOnePrint(
+  CalHashTable_t * hashTable, 
+  int  flag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+void 
+CalHashTableOneQuit(
+  CalHashTable_t * hashTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableOne.c + +
+
+void 
+CalHashTablePrint(
+  CalHashTable_t * hashTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+int 
+CalHashTableQuit(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalHashTableReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t * uniqueTableForId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calApplyReduce.c + +
+
+void 
+CalHashTableRehash(
+  CalHashTable_t * hashTable, 
+  int  grow 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+static void 
+CalHashTableSubstituteApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  int  lastIndex, 
+  CalHashTable_t ** reqQueForSubstitute 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSubstitute.c + +
+
+static void 
+CalHashTableSubstituteApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  int  lastIndex, 
+  CalHashTable_t ** reqQueForSubstitute, 
+  unsigned short  opCode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddVarSubstitute.c + +
+
+static void 
+CalHashTableSubstituteReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reqQueForITE, 
+  CalHashTable_t * uniqueTableForId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSubstitute.c + +
+
+static void 
+CalHashTableSubstituteReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reqQueForITE, 
+  CalHashTable_t * uniqueTableForId, 
+  unsigned short  opCode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddVarSubstitute.c + +
+
+static void 
+CalHashTableSwapVarsApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_BddIndex_t  gIndex, 
+  Cal_BddIndex_t  hIndex, 
+  CalHashTable_t ** reqQueForSwapVars, 
+  CalHashTable_t ** reqQueForSwapVarsPlus, 
+  CalHashTable_t ** reqQueForSwapVarsMinus, 
+  CalHashTable_t ** reqQueForCompose, 
+  CalHashTable_t ** reqQueForITE 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSwapVars.c + +
+
+static void 
+CalHashTableSwapVarsMinusApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_BddIndex_t  hIndex, 
+  CalHashTable_t ** reqQueForSwapVars, 
+  CalHashTable_t ** reqQueForSwapVarsPlus, 
+  CalHashTable_t ** reqQueForSwapVarsMinus, 
+  CalHashTable_t ** reqQueForCompose 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSwapVars.c + +
+
+static void 
+CalHashTableSwapVarsPlusApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_BddIndex_t  hIndex, 
+  CalHashTable_t ** reqQueForSwapVars, 
+  CalHashTable_t ** reqQueForSwapVarsPlus, 
+  CalHashTable_t ** reqQueForSwapVarsMinus, 
+  CalHashTable_t ** reqQueForCompose 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSwapVars.c + +
+
+int 
+CalHashTableThreeFindOrAdd(
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  Cal_Bdd_t  h, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableThree.c + +
+
+static void 
+CalHashTableThreeRehash(
+  CalHashTable_t * hashTable, 
+  int  grow 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableThree.c + +
+
+int 
+CalIncreasingOrderCompare(
+  const void * a, 
+  const void * b 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+int 
+CalInitInteract(
+  Cal_BddManager_t * bddManager 
+)
+
+
Initializes the interaction matrix. The interaction + matrix is implemented as a bit vector storing the upper triangle of + the symmetric interaction matrix. The bit vector is kept in an array + of long integers. The computation is based on a series of depth-first + searches, one for each root of the DAG. A local flag (the mark bits) + is used. +

+ +

Side Effects None +

+ +

Defined in calInteract.c + +
+
+CalNodeManager_t * 
+CalNodeManagerInit(
+  CalPageManager_t * pageManager 
+)
+
+
optional +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+void 
+CalNodeManagerPrint(
+  CalNodeManager_t * nodeManager 
+)
+
+
optional +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+int 
+CalNodeManagerQuit(
+  CalNodeManager_t * nodeManager 
+)
+
+
optional +

+ +

Side Effects The associated nodes are lost. +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+int 
+CalOpAnd(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTerminal.c + +
+
+int 
+CalOpBddVarSubstitute(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddVarSubstitute.c + +
+
+int 
+CalOpCofactor(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  c, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+int 
+CalOpExists(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+Cal_Bdd_t 
+CalOpITE(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  Cal_Bdd_t  h, 
+  CalHashTable_t ** reqQueForITE 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTerminal.c + +
+
+int 
+CalOpNand(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTerminal.c + +
+
+int 
+CalOpOr(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTerminal.c + +
+
+int 
+CalOpRelProd(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  Cal_Bdd_t  g, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+int 
+CalOpXor(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  F, 
+  Cal_Bdd_t  G, 
+  Cal_Bdd_t * resultBddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTerminal.c + +
+
+void 
+CalPackNodes(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+CalAddress_t * 
+CalPageManagerAllocPage(
+  CalPageManager_t * pageManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+void 
+CalPageManagerFreePage(
+  CalPageManager_t * pageManager, 
+  CalAddress_t * page 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+CalPageManager_t * 
+CalPageManagerInit(
+  int  numPagesPerSegment 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+void 
+CalPageManagerPrint(
+  CalPageManager_t * pageManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+int 
+CalPageManagerQuit(
+  CalPageManager_t * pageManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+static void 
+CalPerformaceTestSuperscalar(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceMemoryOverhead(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestCompose(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestMultiway(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestNonSuperscalar(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestOneway(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestQuantifyAllTogether(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions, 
+  int  bfZeroBFPlusDFOne, 
+  int  cacheExistsResultsFlag, 
+  int  cacheOrResultsFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestRelProd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions, 
+  int  bfZeroBFPlusDFOne, 
+  int  cacheRelProdResultsFlag, 
+  int  cacheAndResultsFlag, 
+  int  cacheOrResultsFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalPerformanceTestSwapVars(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+CalQuantifySanityCheck(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+void 
+CalReorderAssociationFix(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calAssociation.c + +
+
+static void 
+CalRepackNodesAfterGC(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calGC.c + +
+
+void 
+CalRequestNodeListArrayITE(
+  Cal_BddManager_t * bddManager, 
+  CalRequestNode_t ** requestNodeListArray 
+)
+
+
This routine is to be used for pipelined and + superscalar ITE operations. Currently there is no user interface + provided to this routine. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddITE.c + +
+
+void 
+CalRequestNodeListArrayOp(
+  Cal_BddManager_t * bddManager, 
+  CalRequestNode_t ** requestNodeListArray, 
+  CalOpProc_t  calOpProc 
+)
+
+
Computes result BDDs for an array of lists, each entry of which + is pair of pointers, each of which points to a operand BDD or an entry in + another list with a smaller array index +

+ +

Side Effects ThenBDD pointer of an entry is over written by the result BDD + and ElseBDD pointer is marked using FORWARD_FLAG +

+ +

Defined in calBddOp.c + +
+
+void 
+CalRequestNodeListCompose(
+  Cal_BddManager_t * bddManager, 
+  CalRequestNode_t * requestNodeList, 
+  Cal_BddIndex_t  composeIndex 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddCompose.c + +
+
+void 
+CalSetInteract(
+  Cal_BddManager_t * bddManager, 
+  int  x, 
+  int  y 
+)
+
+
Given a pair of variables 0 <= x < y < table->size, + sets the corresponding bit of the interaction matrix to 1. +

+ +

Side Effects None +

+ +

Defined in calInteract.c + +
+
+int 
+CalTestInteract(
+  Cal_BddManager_t * bddManager, 
+  int  x, 
+  int  y 
+)
+
+
Given a pair of variables 0 <= x < y < bddManager->numVars, + tests whether the corresponding bit of the interaction matrix is 1. + Returns the value of the bit. +

+ +

Side Effects None +

+ +

Defined in calInteract.c + +
+
+int 
+CalUniqueTableForIdFindOrAdd(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  thenBdd, 
+  Cal_Bdd_t  elseBdd, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects If a new BDD node is created (found == false), then the + numNodes field of the manager needs to be incremented. +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+int 
+CalUniqueTableForIdLookup(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  Cal_Bdd_t  thenBdd, 
+  Cal_Bdd_t  elseBdd, 
+  Cal_Bdd_t * bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalUniqueTableForIdRehashNode(
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * bddNode, 
+  CalBddNode_t * thenBddNode, 
+  CalBddNode_t * elseBddNode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTable.c + +
+
+void 
+CalUniqueTablePrint(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calUtil.c + +
+
+void 
+CalVarAssociationRepackUpdate(
+  Cal_BddManager_t * bddManager, 
+  Cal_BddId_t  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calAssociation.c + +
+
+int 
+Cal_AssociationInit(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Creates or finds a variable association. The association is + specified by associationInfo, which is a an array of BDD with + Cal_BddNull(bddManager) as the end marker. If pairs is 0, the array is + assumed to be an array of variables. In this case, each variable is paired + with constant BDD one. Such an association may viewed as specifying a set + of variables for use with routines such as Cal_BddExists. If pair is not 0, + then the even numbered array elements should be variables and the odd numbered + elements should be the BDDs which they are mapped to. In both cases, the + return value is an integer identifier for this association. If the given + association is equivalent to one which already exists, the same identifier + is used for both, and the reference count of the association is increased by + one. +

+ +

Side Effects None +

+ +

See Also Cal_AssociationQuit + + +
Defined in calAssociation.c + +
+
+void 
+Cal_AssociationQuit(
+  Cal_BddManager  bddManager, 
+  int  associationId 
+)
+
+
Decrements the reference count of the variable association with + identifier id, and frees it if the reference count becomes zero. +

+ +

Side Effects None +

+ +

See Also Cal_AssociationInit + + +
Defined in calAssociation.c + +
+
+int 
+Cal_AssociationSetCurrent(
+  Cal_BddManager  bddManager, 
+  int  associationId 
+)
+
+
Sets the current variable association to the one given by id and + returns the ID of the old association. An id of -1 indicates the temporary + association +

+ +

Side Effects None +

+ +

Defined in calAssociation.c + +
+
+Cal_Bdd 
+Cal_BddAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical AND of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddBetween(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fMinUserBdd, 
+  Cal_Bdd  fMaxUserBdd 
+)
+
+
Returns a minimal BDD f which is contains fMin and is + contained in fMax ( fMin <= f <= fMax). + This operation is typically used in state space searches to simplify + the representation for the set of states wich will be expanded at + each step (Rk Rk-1' <= f <= Rk). +

+ +

Side Effects None +

+ +

See Also Cal_BddReduce + + +
Defined in calReduce.c + +
+
+Cal_Bdd 
+Cal_BddCofactor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  cUserBdd 
+)
+
+
Returns the generalized cofactor of BDD f with respect + to BDD c. The constrain operator given by Coudert et al (ICCAD90) is + used to find the generalized cofactor. +

+ +

Side Effects None. +

+ +

See Also Cal_BddReduce + + +
Defined in calReduce.c + +
+
+Cal_Bdd 
+Cal_BddCompose(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD obtained by substituting a variable by a function +

+ +

Side Effects None +

+ +

Defined in calBddCompose.c + +
+
+int 
+Cal_BddDependsOn(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  varUserBdd 
+)
+
+
Returns 1 if f depends on var and returns 0 otherwise. +

+ +

Side Effects None +

+ +

Defined in calBddSupport.c + +
+
+int 
+Cal_BddDumpBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd * userVars, 
+  FILE * fp 
+)
+
+
Writes an encoded description of the BDD to the file given by fp. + The argument vars should be a null-terminated array of variables that include + the support of f . These variables need not be in order of increasing index. + The function returns a nonzero value if f was written to the file successfully. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+void 
+Cal_BddDynamicReordering(
+  Cal_BddManager  bddManager, 
+  int  technique 
+)
+
+
Selects the method for dynamic reordering. +

+ +

Side Effects None +

+ +

See Also Cal_BddReorder + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddElse(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD. +

+ +

Side Effects The reference count of the returned BDD is increased by 1. +

+ +

See Also Cal_BddThen + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddExists(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns the BDD for f with all the variables that are + paired with something in the current variable association + existentially quantified out. +

+ +

Side Effects None. +

+ +

See Also Cal_BddRelProd + + +
Defined in calQuant.c + +
+
+Cal_Bdd 
+Cal_BddForAll(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns the BDD for f with all the variables that are + paired with something in the current variable association + universally quantified out. +

+ +

Side Effects None. +

+ +

Defined in calQuant.c + +
+
+void 
+Cal_BddFree(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Frees the argument BDD. It is an error to free a BDD + more than once. +

+ +

Side Effects The reference count of the argument BDD is decreased by 1. +

+ +

See Also Cal_BddUnFree + + +
Defined in cal.c + +
+
+void 
+Cal_BddFunctionPrint(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd, 
+  char * name 
+)
+
+
Prints the function implemented by the argument BDD +

+ +

Side Effects None +

+ +

Defined in calUtil.c + +
+
+void 
+Cal_BddFunctionProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  long * funcCounts 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+void 
+Cal_BddFunctionProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  long * funcCounts 
+)
+
+
The nth entry of the function + profile array is the number of subfunctions of f which may be obtained by + restricting the variables whose index is less than n. An entry of zero + indicates that f is independent of the variable with the corresponding index. +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+Cal_BddId_t 
+Cal_BddGetIfId(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the id of the top variable of the argument BDD. +

+ +

Side Effects None +

+ +

See Also Cal_BddGetIfIndex + + +
Defined in cal.c + +
+
+Cal_BddId_t 
+Cal_BddGetIfIndex(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the index of the top variable of the argument BDD. +

+ +

Side Effects None +

+ +

See Also Cal_BddGetIfId + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddGetRegular(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns a BDD with positive from a given BDD with arbitrary phase +

+ +

Side Effects None. +

+ +

Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddITE(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h +

+ +

Side Effects None +

+ +

See Also Cal_BddAnd +Cal_BddNand +Cal_BddOr +Cal_BddNor +Cal_BddXor +Cal_BddXnor + + +
Defined in calBddITE.c + +
+
+Cal_Bdd 
+Cal_BddIdentity(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the duplicate BDD of the argument BDD. +

+ +

Side Effects The reference count of the BDD is increased by 1. +

+ +

See Also Cal_BddNot + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddIf(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the BDD corresponding to the top variable of + the argument BDD. +

+ +

Side Effects None. +

+ +

Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddImplies(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Computes a BDD that implies conjunction of f and Cal_BddNot(g) +

+ +

Side Effects none +

+ +

See Also Cal_BddIntersects + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddIntersects(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Computes a BDD that implies conjunction of f and g. +

+ +

Side Effects None +

+ +

See Also Cal_BddImplies + + +
Defined in cal.c + +
+
+int 
+Cal_BddIsBddConst(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is either constant one or + constant zero, otherwise returns 0. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddOne +Cal_BddIsBddZero + + +
Defined in cal.c + +
+
+int 
+Cal_BddIsBddNull(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is NULL, 0 otherwise. +

+ +

Side Effects None. +

+ +

Defined in cal.c + +
+
+int 
+Cal_BddIsBddOne(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is constant one, 0 otherwise. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddZero + + +
Defined in cal.c + +
+
+int 
+Cal_BddIsBddZero(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is constant zero, 0 otherwise. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddOne + + +
Defined in cal.c + +
+
+int 
+Cal_BddIsCube(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns 1 if the argument BDD is a cube, 0 otherwise +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+int 
+Cal_BddIsEqual(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd1, 
+  Cal_Bdd  userBdd2 
+)
+
+
Returns 1 if argument BDDs are equal, 0 otherwise. +

+ +

Side Effects None. +

+ +

Defined in cal.c + +
+
+int 
+Cal_BddIsProvisional(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1, if the given user BDD contains + provisional BDD node. +

+ +

Side Effects None. +

+ +

Defined in calPipeline.c + +
+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarAfter(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Creates and returns a new variable after the specified one in + the variable order. +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarBefore(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Creates and returns a new variable before the specified one in + the variable order. +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarFirst(
+  Cal_BddManager  bddManager 
+)
+
+
Creates and returns a new variable at the start of the + variable order. +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarLast(
+  Cal_BddManager  bddManager 
+)
+
+
Creates and returns a new variable at the end of the variable + order. +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+int 
+Cal_BddManagerGC(
+  Cal_BddManager  bddManager 
+)
+
+
For each variable in the increasing id free nodes with reference + count equal to zero freeing a node results in decrementing reference count of + then and else nodes by one. +

+ +

Side Effects None. +

+ +

Defined in calGC.c + +
+
+void * 
+Cal_BddManagerGetHooks(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the hooks field of the manager. +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+unsigned long 
+Cal_BddManagerGetNumNodes(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of BDD nodes +

+ +

Side Effects None +

+ +

See Also Cal_BddTotalSize + + +
Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddManagerGetVarWithId(
+  Cal_BddManager  bddManager, 
+  Cal_BddId_t  id 
+)
+
+
Returns the variable with the specified id, null if no + such variable exists +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddManagerGetVarWithIndex(
+  Cal_BddManager  bddManager, 
+  Cal_BddIndex_t  index 
+)
+
+
Returns the variable with the specified index, null if no + such variable exists +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+Cal_BddManager 
+Cal_BddManagerInit(
+    
+)
+
+
Initializes and allocates fields of the BDD manager. Some of the + fields are initialized for maxNumVars+1 or numVars+1, whereas some of them are + initialized for maxNumVars or numVars. The first kind of fields are associated + with the id of a variable and the second ones are with the index of the + variable. +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerQuit + + +
Defined in calBddManager.c + +
+
+int 
+Cal_BddManagerQuit(
+  Cal_BddManager  bddManager 
+)
+
+
Frees the BDD manager and all the associated allocations +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerInit + + +
Defined in calBddManager.c + +
+
+void 
+Cal_BddManagerSetGCLimit(
+  Cal_BddManager  manager 
+)
+
+
It tries to set the limit at twice the number of nodes + in the manager at the current point. However, the limit is not + allowed to fall below the MIN_GC_LIMIT or to exceed the value of + node limit (if one exists). +

+ +

Side Effects None. +

+ +

Defined in calGC.c + +
+
+void 
+Cal_BddManagerSetHooks(
+  Cal_BddManager  bddManager, 
+  void * hooks 
+)
+
+
Sets the hooks field of the manager. +

+ +

Side Effects Hooks field changes. +

+ +

Defined in cal.c + +
+
+void 
+Cal_BddManagerSetParameters(
+  Cal_BddManager  bddManager, 
+  long  reorderingThreshold, 
+  long  maxForwardedNodes, 
+  double  repackAfterGCThreshold, 
+  double  tableRepackThreshold 
+)
+
+
This function is used to set the parameters which are + used to control the reordering process. "reorderingThreshold" + determines the number of nodes below which reordering will NOT be + invoked, "maxForwardedNodes" determines the maximum number of + forwarded nodes which are allowed (at that point the cleanup must be + done), and "repackingThreshold" determines the fraction of the page + utilized below which repacking has to be invoked. These parameters + have different affect on the computational and memory usage aspects + of reordeing. For instance, higher value of "maxForwardedNodes" will + result in process consuming more memory, and a lower value on the + other hand would invoke the cleanup process repeatedly resulting in + increased computation. +

+ +

Side Effects None +

+ +

Defined in calBddManager.c + +
+
+Cal_Bdd 
+Cal_BddMultiwayAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical AND of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddMultiwayOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical OR of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddMultiwayXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical XOR of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddNand(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical NAND of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Block 
+Cal_BddNewVarBlock(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  variable, 
+  long  length 
+)
+
+
The block is specified by passing the first + variable and the length of the block. The "length" number of + consecutive variables starting from "variable" are put in the + block. +

+ +

Side Effects A new block is created. +

+ +

Defined in calBlk.c + +
+
+long 
+Cal_BddNodeLimit(
+  Cal_BddManager  bddManager, 
+  long  newLimit 
+)
+
+
Sets the node limit to new_limit and returns the old limit. +

+ +

Side Effects Threshold for garbage collection may change +

+ +

See Also Cal_BddManagerGC + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddNor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical NOR of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddNot(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the complement of the argument BDD. +

+ +

Side Effects The reference count of the argument BDD is increased by 1. +

+ +

See Also Cal_BddIdentity + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddOne(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the BDD for the constant one +

+ +

Side Effects None +

+ +

See Also Cal_BddZero + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical OR of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+int 
+Cal_BddOverflow(
+  Cal_BddManager  bddManager 
+)
+
+
Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared. +

+ +

Side Effects None +

+ +

See Also Cal_BddNodeLimit + + +
Defined in cal.c + +
+
+Cal_Bdd * 
+Cal_BddPairwiseAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseOr + + +
Defined in calBddOp.c + +
+
+Cal_Bdd * 
+Cal_BddPairwiseOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical OR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseAnd + + +
Defined in calBddOp.c + +
+
+Cal_Bdd * 
+Cal_BddPairwiseXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical XOR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseAnd + + +
Defined in calBddOp.c + +
+
+void 
+Cal_BddPrintBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_VarNamingFn_t  VarNamingFn, 
+  Cal_TerminalIdFn_t  TerminalIdFn, 
+  Cal_Pointer_t  env, 
+  FILE * fp 
+)
+
+
Prints a human-readable representation of the BDD f to + the file given by fp. The namingFn should be a pointer to a function + taking a bddManager, a BDD and the pointer given by env. This + function should return either a null pointer or a srting that is the + name of the supplied variable. If it returns a null pointer, a + default name is generated based on the index of the variable. It is + also legal for naminFN to e null; in this case, default names are + generated for all variables. The macro bddNamingFnNone is a null + pointer of suitable type. terminalIdFn should be apointer to a + function taking a bddManager and two longs. plus the pointer given + by the env. It should return either a null pointer. If it returns a + null pointer, or if terminalIdFn is null, then default names are + generated for the terminals. The macro bddTerminalIdFnNone is a null + pointer of suitable type. +

+ +

Side Effects None. +

+ +

Defined in calPrint.c + +
+
+void 
+Cal_BddPrintFunctionProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBdds, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+void 
+Cal_BddPrintFunctionProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+void 
+Cal_BddPrintProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBdds, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+void 
+Cal_BddPrintProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+void 
+Cal_BddProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  long * levelCounts, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+void 
+Cal_BddProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  long * levelCounts, 
+  int  negout 
+)
+
+
negout is as in Cal_BddSize. levelCounts should be an array of + size Cal_BddVars(bddManager)+1 to hold the profile. +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+Cal_Bdd 
+Cal_BddReduce(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  cUserBdd 
+)
+
+
Returns a BDD which agrees with f for all valuations + which satisfy c. The result is usually smaller in terms of number of + BDD nodes than f. This operation is typically used in state space + searches to simplify the representation for the set of states wich + will be expanded at each step. +

+ +

Side Effects None +

+ +

See Also Cal_BddCofactor + + +
Defined in calReduce.c + +
+
+Cal_Bdd 
+Cal_BddRelProd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for the logical AND of f and g with all + the variables that are paired with something in the current variable + association existentially quantified out. +

+ +

Side Effects None. +

+ +

Defined in calQuant.c + +
+
+void 
+Cal_BddReorder(
+  Cal_BddManager  bddManager 
+)
+
+
Invoke the current dynamic reodering method. +

+ +

Side Effects Index of a variable may change due to reodering +

+ +

See Also Cal_BddDynamicReordering + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddSatisfySupport(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
The returned BDD which implies f, is true for some valuation on + which f is true, which has at most one node at each level, + and which has exactly one node corresponding to each variable + which is associated with something in the current variable + association. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+double 
+Cal_BddSatisfyingFraction(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+Cal_Bdd 
+Cal_BddSatisfy(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+void 
+Cal_BddSetGCMode(
+  Cal_BddManager  bddManager, 
+  int  gcMode 
+)
+
+
Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on. +

+ +

Side Effects None. +

+ +

Defined in calGC.c + +
+
+long 
+Cal_BddSizeMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+long 
+Cal_BddSize(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSize.c + +
+
+void 
+Cal_BddStats(
+  Cal_BddManager  bddManager, 
+  FILE * fp 
+)
+
+
Prints miscellaneous BDD statistics +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns a BDD for f using the substitution defined by current + variable association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously +

+ +

Side Effects None +

+ +

See Also Cal_BddCompose + + +
Defined in calBddSubstitute.c + +
+
+void 
+Cal_BddSupport(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd * support 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
Defined in calBddSupport.c + +
+
+Cal_Bdd 
+Cal_BddSwapVars(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD obtained by simultaneously substituting variable + g by variable h and variable h and variable g in the BDD f +

+ +

Side Effects None +

+ +

See Also Cal_BddSubstitute + + +
Defined in calBddSwapVars.c + +
+
+Cal_Bdd 
+Cal_BddThen(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD. +

+ +

Side Effects The reference count of the returned BDD is increased by 1. +

+ +

See Also Cal_BddElse + + +
Defined in cal.c + +
+
+unsigned long 
+Cal_BddTotalSize(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of nodes in the Unique table +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerGetNumNodes + + +
Defined in cal.c + +
+
+int 
+Cal_BddType(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns BDD_TYPE_ZERO if f is false, BDD_TYPE_ONE + if f is true, BDD_TYPE_POSVAR is f is an unnegated variable, + BDD_TYPE_NEGVAR if f is a negated variable, BDD_TYPE_OVERFLOW if f + is null, and BDD_TYPE_NONTERMINAL otherwise. +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+void 
+Cal_BddUnFree(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Unfrees the argument BDD. It is an error to pass a BDD + with reference count of zero to be unfreed. +

+ +

Side Effects The reference count of the argument BDD is increased by 1. +

+ +

See Also Cal_BddFree + + +
Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddUndumpBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userVars, 
+  FILE * fp, 
+  int * error 
+)
+
+
Loads an encoded description of a BDD from the file given by + fp. The argument vars should be a null terminated array of variables that will + become the support of the BDD. As in Cal_BddDumpBdd, these need not be in + the order of increasing index. If the same array of variables in used in + dumping and undumping, the BDD returned will be equal to the one that was + dumped. More generally, if array v1 is used when dumping, and the array v2 + is used when undumping, the BDD returned will be equal to the original BDD + with the ith variable in v2 substituted for the ith variable in v1 for all i. + Null BDD is returned in the operation fails for reason (node limit reached, + I/O error, invalid file format, etc.). In this case, an error code is stored + in error. the code will be one of the following. + CAL_BDD_UNDUMP_FORMAT Invalid file format + CAL_BDD_UNDUMP_OVERFLOW Node limit exceeded + CAL_BDD_UNDUMP_IOERROR File I/O error + CAL_BDD_UNDUMP_EOF Unexpected EOF +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+void 
+Cal_BddVarBlockReorderable(
+  Cal_BddManager  bddManager, 
+  Cal_Block  block, 
+  int  reorderable 
+)
+
+
If a block is reorderable, the child blocks are + recursively involved in swapping. +

+ +

Side Effects None. +

+ +

Defined in calBlk.c + +
+
+Cal_Bdd 
+Cal_BddVarSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns a BDD for f using the substitution defined by current + variable association. It is assumed that each variable is replaced + by another variable. For the substitution of a variable by a + function, use Cal_BddSubstitute instead. +

+ +

Side Effects None +

+ +

See Also Cal_BddSubstitute + + +
Defined in calBddVarSubstitute.c + +
+
+long 
+Cal_BddVars(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of BDD variables +

+ +

Side Effects None +

+ +

Defined in cal.c + +
+
+Cal_Bdd 
+Cal_BddXnor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical exclusive NOR of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical exclusive OR of f and g +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+Cal_Bdd 
+Cal_BddZero(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the BDD for the constant zero +

+ +

Side Effects None +

+ +

See Also Cal_BddOne + + +
Defined in cal.c + +
+
+Cal_Address_t 
+Cal_MemAllocation(
+    
+)
+
+
Returns the memory allocated. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+void 
+Cal_MemFatal(
+  char * message 
+)
+
+
Prints an error message and exits. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+void 
+Cal_MemFreeBlock(
+  Cal_Pointer_t  p 
+)
+
+
Frees the block. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+void 
+Cal_MemFreeRecMgr(
+  Cal_RecMgr  mgr 
+)
+
+
Frees all the storage associated with the specified record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+void 
+Cal_MemFreeRec(
+  Cal_RecMgr  mgr, 
+  Cal_Pointer_t  rec 
+)
+
+
Frees a record managed by the indicated record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+Cal_Pointer_t 
+Cal_MemGetBlock(
+  Cal_Address_t  size 
+)
+
+
Allocates a new block of the specified size. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+Cal_RecMgr 
+Cal_MemNewRecMgr(
+  int  size 
+)
+
+
Creates a new record manager with the given record size. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+Cal_Pointer_t 
+Cal_MemNewRec(
+  Cal_RecMgr  mgr 
+)
+
+
Allocates a record from the specified record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+Cal_Pointer_t 
+Cal_MemResizeBlock(
+  Cal_Pointer_t  p, 
+  Cal_Address_t  newSize 
+)
+
+
Expands or contracts the block to a new size. + We try to avoid moving the block if possible. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+int 
+Cal_PerformanceTest(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions, 
+  int  iteration, 
+  int  seed, 
+  int  andPerformanceFlag, 
+  int  multiwayPerformanceFlag, 
+  int  onewayPerformanceFlag, 
+  int  quantifyPerformanceFlag, 
+  int  composePerformanceFlag, 
+  int  relprodPerformanceFlag, 
+  int  swapPerformanceFlag, 
+  int  substitutePerformanceFlag, 
+  int  sanityCheckFlag, 
+  int  computeMemoryOverheadFlag, 
+  int  superscalarFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+Cal_Bdd 
+Cal_PipelineCreateProvisionalBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
The provisional BDD is automatically freed once the + pipeline is quitted. +

+ +

Defined in calPipeline.c + +
+
+int 
+Cal_PipelineExecute(
+  Cal_BddManager  bddManager 
+)
+
+
All the results are computed. User should update the + BDDs of interest. Eventually this feature would become transparent. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPipeline.c + +
+
+int 
+Cal_PipelineInit(
+  Cal_BddManager  bddManager, 
+  Cal_BddOp_t  bddOp 
+)
+
+
All the operations for this pipeline must be of the + same kind. +

+ +

Side Effects None. +

+ +

Defined in calPipeline.c + +
+
+void 
+Cal_PipelineQuit(
+  Cal_BddManager  bddManager 
+)
+
+
The user must make sure to update all provisional BDDs + of interest before calling this routine. +

+ +

Defined in calPipeline.c + +
+
+void 
+Cal_PipelineSetDepth(
+  Cal_BddManager  bddManager, 
+  int  depth 
+)
+
+
The "depth" determines the amount of dependency we + would allow in pipelined computation. +

+ +

Side Effects None. +

+ +

Defined in calPipeline.c + +
+
+Cal_Bdd 
+Cal_PipelineUpdateProvisionalBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  provisionalBdd 
+)
+
+
The provisional BDD is automatically freed after + quitting pipeline. +

+ +

Defined in calPipeline.c + +
+
+void 
+Cal_TempAssociationAugment(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Pairs is 0 if the information represents only a list of + variables rather than a full association. +

+ +

Side Effects None +

+ +

Defined in calAssociation.c + +
+
+void 
+Cal_TempAssociationInit(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Pairs is 0 if the information represents only a list of + variables rather than a full association. +

+ +

Side Effects None +

+ +

Defined in calAssociation.c + +
+
+void 
+Cal_TempAssociationQuit(
+  Cal_BddManager  bddManager 
+)
+
+
Cleans up temporary associationoptional +

+ +

Side Effects None +

+ +

Defined in calAssociation.c + +
+
+static int 
+CeilLog2(
+  int  number 
+)
+
+
Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1) +

+ +

Side Effects None +

+ +

Defined in calBddOp.c + +
+
+static int 
+CeilLog2(
+  int  number 
+)
+
+
Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1) +

+ +

Side Effects None +

+ +

Defined in calGC.c + +
+
+static int 
+CeilLog2(
+  int  number 
+)
+
+
Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1) +

+ +

Side Effects None +

+ +

Defined in calHashTable.c + +
+
+static int 
+CeilLog2(
+  int  number 
+)
+
+
Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1) +

+ +

Side Effects None +

+ +

Defined in calReorderDF.c + +
+
+static int 
+CeilingLog2(
+  Cal_Address_t  i 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static void 
+Chars(
+  char  c, 
+  int  n, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrint.c + +
+
+static int 
+CheckAssoc(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd * assocInfo, 
+  int  pairs 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calAssociation.c + +
+
+static int 
+CheckValidityOfNodes(
+  Cal_BddManager_t * bddManager, 
+  long  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static int 
+CofactorFixAndReclaimForwardedNodes(
+  Cal_BddManager_t * bddManager, 
+  int  cofactorCheckStartIndex, 
+  int  cofactorCheckEndIndex, 
+  int  reclaimStartIndex, 
+  int  reclaimEndIndex 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static TruthTable_t 
+Cofactor(
+  TruthTable_t  table, 
+  int  var, 
+  int  value 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static Cal_Bdd 
+Decode(
+  int  var, 
+  TruthTable_t  table 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+Error(
+  char * op, 
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  result, 
+  Cal_Bdd  expected, 
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+GetRandomNumbers(
+  int  lowerBound, 
+  int  upperBound, 
+  int  count, 
+  int * resultVector 
+)
+
+
The restriction is that count <= upperBound-lowerBound+1. The + size of the resultVector should be >= count. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+HashTableAddDirect(
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * bddNode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+HashTableApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reqQueAtPipeDepth, 
+  CalOpProc_t  calOpProc, 
+  unsigned long  opCode 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static void 
+HashTableCofactorApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** cofactorHashTableArray, 
+  CalOpProc_t  calOpProc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+static void 
+HashTableCofactorReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t * uniqueTableForId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+static int 
+HashTableFindOrAdd(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * thenBdd, 
+  CalBddNode_t * elseBdd, 
+  CalBddNode_t ** bddPtr 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+HashTableOneRehash(
+  CalHashTable_t * hashTable, 
+  int  grow 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calHashTableOne.c + +
+
+static void 
+HashTableReduceApply(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t ** reduceHashTableArray, 
+  CalHashTable_t ** orHashTableArray, 
+  CalOpProc_t  calOpProc 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReduce.c + +
+
+static void 
+HashTableReduce(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalHashTable_t * uniqueTableForId 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calQuant.c + +
+
+static int 
+IndexCmp(
+  const void * p1, 
+  const void * p2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddSatisfy.c + +
+
+static void 
+MergeAndFree(
+  Block  b 
+)
+
+
MergeAndFree(b) repeatedly merges b its Buddy until b has no Buddy or the Buddy isn't free, then adds the result to the appropriate free list. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static CalAddress_t * 
+PageAlign(
+  CalAddress_t * p 
+)
+
+
optional +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+static int 
+PageManagerExpandStorage(
+  CalPageManager_t * pageManager 
+)
+
+
optional +

+ +

Side Effects The size of the segment is stored in one of the fields + of page manager - numPagesPerSegment. If a memory + segment of a specific size cannot be allocated, the + routine calls itself recursively by reducing + numPagesPerSegment by a factor of 2. +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+static void 
+PrintBddProfileAfterReorder(
+  Cal_BddManager_t * bddManager 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderBF.c + +
+
+static void 
+PrintBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+RandomTests(
+  int  numVars, 
+  int  iterations 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static unsigned long 
+Read(
+  int * error, 
+  int  bytes, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+static Block 
+RemoveFromFreeList(
+  Block  b 
+)
+
+
RemoveFromFreeList(b) removes b from the free list which it is on. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static int 
+SegmentToPageList(
+  CalAddress_t * segment, 
+  int  numPages, 
+  CalAddress_t * lastPointer 
+)
+
+
optional +

+ +

See Also optional + + +
Defined in calMemoryManagement.c + +
+
+static void 
+SweepVarTable(
+  Cal_BddManager_t * bddManager, 
+  long  id 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+TestAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestArrayOp(
+  Cal_BddManager  bddManager, 
+  int  numBdds 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestAssoc(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  TruthTable_t  table 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestCompose(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestDump(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestGenCof(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestITE(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestIdNot(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  TruthTable_t  table 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestInterImpl(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestMultiwayAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestMultiwayLarge(
+  Cal_BddManager  bddManager, 
+  int  numBdds 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestMultiwayOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestNand(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestPipeline(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestQnt(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  TruthTable_t  table, 
+  int  bfZeroBFPlusDFOne, 
+  int  cacheExistsResultsFlag, 
+  int  cacheOrResultsFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestReduce(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestRelProd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  int  bfZeroBFPlusDFOne, 
+  int  cacheRelProdResultsFlag, 
+  int  cacheAndResultsFlag, 
+  int  cacheOrResultsFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestReorderBlock(
+  Cal_BddManager  bddManager, 
+  TruthTable_t  table, 
+  Cal_Bdd  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestReorder(
+  Cal_BddManager  bddManager, 
+  TruthTable_t  table, 
+  Cal_Bdd  f 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestSatisfy(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  TruthTable_t  table 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestSize(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestSwapVars(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  TruthTable_t  table 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestVarSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2, 
+  Cal_Bdd  f3, 
+  TruthTable_t  table3 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TestXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f1, 
+  TruthTable_t  table1, 
+  Cal_Bdd  f2, 
+  TruthTable_t  table2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+TrimToSize(
+  Block  b, 
+  int  sizeIndex 
+)
+
+
TrimToSize(b, sizeIndex) repeatedly splits b until it has the indicated size. Blocks which are split off are added to the appropriate free list. +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calMem.c + +
+
+static int 
+UniqueTableForIdFindOrAdd(
+  Cal_BddManager_t * bddManager, 
+  CalHashTable_t * hashTable, 
+  CalBddNode_t * thenBdd, 
+  CalBddNode_t * elseBdd, 
+  CalBddNode_t ** bddPtr 
+)
+
+
optional +

+ +

Side Effects If a new BDD node is created (found == false), then the + numNodes field of the manager needs to be incremented. +

+ +

See Also optional + + +
Defined in calReorderDF.c + +
+
+static void 
+Write(
+  Cal_BddManager_t * bddManager, 
+  unsigned long  n, 
+  int  bytes, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calDump.c + +
+
+static void 
+asAddress(
+  double  n, 
+  CalAddress_t * r1, 
+  CalAddress_t * r2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static double 
+asDouble(
+  CalAddress_t  v1, 
+  CalAddress_t  v2 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static void 
+chars(
+  char  c, 
+  int  n, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPrintProfile.c + +
+
+static double 
+cpuTime(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static double 
+cpuTime(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddReorderTest.c + +
+
+static void 
+ddClearLocal(
+  Cal_Bdd_t  f 
+)
+
+
Performs a DFS from f, clearing the LSB of the then pointers. +

+ +

Side Effects None +

+ +

Defined in calInteract.c + +
+
+static void 
+ddSuppInteract(
+  Cal_BddManager_t * bddManager, 
+  Cal_Bdd_t  f, 
+  int * support 
+)
+
+
Performs a DFS from f. Uses the LSB of the then pointer + as visited flag. +

+ +

Side Effects Accumulates in support the variables on which f depends. +

+ +

Defined in calInteract.c + +
+
+static void 
+ddUpdateInteract(
+  Cal_BddManager_t * bddManager, 
+  int * support 
+)
+
+
If support[i +

+ +

Side Effects None +

+ +

Defined in calInteract.c + +
+
+static long 
+elapsedTime(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddReorderTest.c + +
+
+static long 
+elapsedTime(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static void 
+handler(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+int 
+main(
+  int  argc, 
+  char ** argv 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calBddReorderTest.c + +
+
+int 
+main(
+  int  argc, 
+  char ** argv 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + +
+
+static long 
+pageFaults(
+    
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calPerformanceTest.c + +
+
+static char * 
+terminalIdFn(
+  Cal_BddManager  bddManager, 
+  CalAddress_t  v1, 
+  CalAddress_t  v2, 
+  Cal_Pointer_t  pointer 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
Defined in calTest.c + + +
+
+Last updated on 970711 20h11 + diff --git a/calAllFile.html b/calAllFile.html new file mode 100644 index 0000000..64ebe42 --- /dev/null +++ b/calAllFile.html @@ -0,0 +1,1756 @@ + +The cal package: files + + +
+
cal.h +
External header file +
calInt.h +
Internal header file +
cal.c +
Miscellaneous collection of exported BDD functions +
calApplyReduce.c +
Generic routines for processing temporary nodes during + "apply" and "reduce" phases. +
calAssociation.c +
Contains the routines related to the variable association. +
calBddCompose.c +
Routine for composing one BDD into another. +
calBddITE.c +
Routine for computing ITE of 3 BDD operands. +
calBddManager.c +
Routines for maintaing the manager and creating + variables etc. +
calBddOp.c +
Routines for performing simple boolean operations on a + pair of BDDs or on an array of pair of BDDs or on an array of BDDs. +
calBddReorderTest.c +
A test routine for checking the functionality of + dynamic reordering. +
calBddSatisfy.c +
Routines for BDD satisfying valuation. +
calBddSize.c +
BDD size and profile routines +
calBddSubstitute.c +
Routine for simultaneous substitution of an array of + variables with an array of functions. +
calBddSupport.c +
Routines related to the support of a BDD. +
calBddSwapVars.c +
Routine for swapping two variables. +
calBddVarSubstitute.c +
Routine for simultaneous substitution of an array of + variables with another array of variables. +
calBlk.c +
Routines for manipulating blocks of variables. +
calCacheTableTwo.c +
Functions to manage the Cache tables. +
calDump.c +
BDD library dump/undump routines +
calGC.c +
Garbage collection routines +
calHashTable.c +
Functions to manage the hash tables that are a part of + 1. unique table + 2. request queue +
calHashTableOne.c +
Routines for managing hash table with Bdd is a key and + int, long, or double as a value +
calHashTableThree.c +
Functions to manage the hash tables that are a part of + ITE operation +
calInteract.c +
Functions to manipulate the variable interaction matrix. +
calMem.c +
Routines for memory management. +
calMemoryManagement.c +
Special memory management routines specific to CAL. +
calPerformanceTest.c +
This file contains the performance test routines for + the CAL package. +
calPipeline.c +
Routines for creating and managing the pipelined BDD + operations. +
calPrint.c +
Routine for printing a BDD. +
calPrintProfile.c +
Routines for printing various profiles for a BDD. +
calQuant.c +
Routines for existential/universal quantification and + relational product. +
calReduce.c +
Routines for optimizing a BDD with respect to a don't + care set (cofactor and restrict). +
calReorderBF.c +
Routines for dynamic reordering of variables. +
calReorderDF.c +
Routines for dynamic reordering of variables. +
calReorderUtil.c +
Some utility routines used by both breadth-first and + depth-first reordering techniques. +
calTerminal.c +
Contains the terminal function for various BDD operations. +
calTest.c +
This file contains the test routines for the CAL package. +
calUtil.c +
Utility functions for the Cal package. +

+

cal.h

+External header file

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu)

+

See Alsooptional +

+
+
+

calInt.h

+Internal header file

+By: Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu + Jagesh Sanghavi (sanghavi@ic.eecs.berkeley.edu)

+

See Alsocal.h +

+
+
+

cal.c

+Miscellaneous collection of exported BDD functions

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu

+

+
Cal_BddIsEqual() +
Returns 1 if argument BDDs are equal, 0 otherwise. + +
Cal_BddIsBddOne() +
Returns 1 if the argument BDD is constant one, 0 otherwise. + +
Cal_BddIsBddZero() +
Returns 1 if the argument BDD is constant zero, 0 otherwise. + +
Cal_BddIsBddNull() +
Returns 1 if the argument BDD is NULL, 0 otherwise. + +
Cal_BddIsBddConst() +
Returns 1 if the argument BDD is a constant, 0 otherwise. + +
Cal_BddIdentity() +
Returns the duplicate BDD of the argument BDD. + +
Cal_BddOne() +
Returns the BDD for the constant one + +
Cal_BddZero() +
Returns the BDD for the constant zero + +
Cal_BddNot() +
Returns the complement of the argument BDD. + +
Cal_BddGetIfIndex() +
Returns the index of the top variable of the argument BDD. + +
Cal_BddGetIfId() +
Returns the id of the top variable of the argument BDD. + +
Cal_BddIf() +
Returns the BDD corresponding to the top variable of + the argument BDD. + +
Cal_BddThen() +
Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddElse() +
Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddFree() +
Frees the argument BDD. + +
Cal_BddUnFree() +
Unfrees the argument BDD. + +
Cal_BddGetRegular() +
Returns a BDD with positive from a given BDD with arbitrary phase + +
Cal_BddIntersects() +
Computes a BDD that implies conjunction of f and g. + +
Cal_BddImplies() +
Computes a BDD that implies conjunction of f and Cal_BddNot(g) + +
Cal_BddTotalSize() +
Returns the number of nodes in the Unique table + +
Cal_BddStats() +
Prints miscellaneous BDD statistics + +
Cal_BddDynamicReordering() +
Specify dynamic reordering technique. + +
Cal_BddReorder() +
Invoke the current dynamic reodering method. + +
Cal_BddType() +
Returns type of a BDD ( 0, 1, +var, -var, ovrflow, nonterminal) + +
Cal_BddVars() +
Returns the number of BDD variables + +
Cal_BddNodeLimit() +
Sets the node limit to new_limit and returns the old limit. + +
Cal_BddOverflow() +
Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared. + +
Cal_BddIsCube() +
Returns 1 if the argument BDD is a cube, 0 otherwise + +
Cal_BddManagerGetHooks() +
Returns the hooks field of the manager. + +
Cal_BddManagerSetHooks() +
Sets the hooks field of the manager. + +
CalBddIf() +
Returns the BDD corresponding to the top variable of + the argument BDD. + +
CalBddIsCubeStep() +
Returns 1 if the argument BDD is a cube, 0 otherwise + +
CalBddTypeAux() +
Returns the BDD type by recursively traversing the argument BDD + +
CalBddIdentity() +
Returns the duplicate BDD of the argument BDD. + +
BddIntersectsStep() +
Recursive routine to returns a BDD that implies conjunction of + argument BDDs + +
+
+

calApplyReduce.c

+Generic routines for processing temporary nodes during + "apply" and "reduce" phases.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

See Alsooptional +

+
CalHashTableApply() +
required + +
CalHashTableReduce() +
required + +
+
+

calAssociation.c

+Contains the routines related to the variable association.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+optional

+

See Alsooptional +

+
Cal_AssociationInit() +
Creates or finds a variable association. + +
Cal_AssociationQuit() +
Deletes the variable association given by id + +
Cal_AssociationSetCurrent() +
Sets the current variable association to the one given by id and + returns the ID of the old association. + +
Cal_TempAssociationAugment() +
Adds to the temporary variable association. + +
Cal_TempAssociationInit() +
Sets the temporary variable association. + +
Cal_TempAssociationQuit() +
Cleans up temporary association + +
CalAssociationListFree() +
Frees the variable associations + +
CalVarAssociationRepackUpdate() +
Need to be called after repacking. + +
CalCheckAssociationValidity() +
Checks the validity of association. + +
CalReorderAssociationFix() +
required + +
AssociationIsEqual() +
Checks for equality of two associations + +
CheckAssoc() +
required + +
+
+

calBddCompose.c

+Routine for composing one BDD into another.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

+
Cal_BddCompose() +
composition - substitute a BDD variable by a function + +
CalRequestNodeListCompose() +
required + +
CalHashTableComposeApply() +
required + +
CalComposeRequestCreate() +
required + +
+
+

calBddITE.c

+Routine for computing ITE of 3 BDD operands.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

See Alsooptional +

+
Cal_BddITE() +
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h + +
CalRequestNodeListArrayITE() +
required + +
CalBddOpITEBF() +
required + +
CalHashTableITEApply() +
required + +
CalBddITE() +
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h + +
+
+

calBddManager.c

+Routines for maintaing the manager and creating + variables etc.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+

See Alsooptional +

+
Cal_BddManagerInit() +
Creates and initializes a new BDD manager. + +
Cal_BddManagerQuit() +
Frees the BDD manager and all the associated allocations + +
Cal_BddManagerSetParameters() +
Sets appropriate fields of BDD Manager. + +
Cal_BddManagerGetNumNodes() +
Returns the number of BDD nodes + +
Cal_BddManagerCreateNewVarFirst() +
Creates and returns a new variable at the start of the variable + order. + +
Cal_BddManagerCreateNewVarLast() +
Creates and returns a new variable at the end of the variable + order. + +
Cal_BddManagerCreateNewVarBefore() +
Creates and returns a new variable before the specified one in + the variable order. + +
Cal_BddManagerCreateNewVarAfter() +
Creates and returns a new variable after the specified one in + the variable order. + +
Cal_BddManagerGetVarWithIndex() +
Returns the variable with the specified index, null if no + such variable exists + +
Cal_BddManagerGetVarWithId() +
Returns the variable with the specified id, null if no + such variable exists + +
CalBddManagerCreateNewVar() +
This function creates and returns a new variable with given + index value. + +
BddDefaultTransformFn() +
required + +
CalBddManagerPrint() +
required + +
+
+

calBddOp.c

+Routines for performing simple boolean operations on a + pair of BDDs or on an array of pair of BDDs or on an array of BDDs.

+By: Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+The "cal" specific routines are "Cal_BddPairwiseAnd/Or", + "Cal_BddMultiwayAnd/Or".

+

See Alsooptional +

+
Cal_BddAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddNand() +
Returns the BDD for logical NAND of argument BDDs + +
Cal_BddOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddNor() +
Returns the BDD for logical NOR of argument BDDs + +
Cal_BddXor() +
Returns the BDD for logical exclusive OR of argument BDDs + +
Cal_BddXnor() +
Returns the BDD for logical exclusive NOR of argument BDDs + +
Cal_BddPairwiseAnd() +
Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseOr() +
Returns an array of BDDs obtained by logical OR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseXor() +
Returns an array of BDDs obtained by logical XOR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddMultiwayAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddMultiwayOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddMultiwayXor() +
Returns the BDD for logical XOR of argument BDDs + +
CalRequestNodeListArrayOp() +
Computes result BDDs for an array of lists, each entry of which + is pair of pointers, each of which points to a operand BDD or an entry in + another list with a smaller array index + +
CalBddOpBF() +
Internal routine to compute a logical operation on a pair of BDDs + +
BddArrayOpBF() +
Internal common routine for Cal_BddPairwiseAnd and Cal_BddPairwiseOr + +
BddMultiwayOp() +
Internal routine for multiway operations + +
BddArrayToRequestNodeListArray() +
Converts an array of BDDs to a list of requests representing BDD + pairs + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
+
+

calBddReorderTest.c

+A test routine for checking the functionality of + dynamic reordering.

+By: Wilsin Gosti (wilsin@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+

See Alsooptional +

+
main() +
required + +
cpuTime() +
required + +
elapsedTime() +
Computes the time. + +
+
+

calBddSatisfy.c

+Routines for BDD satisfying valuation.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

See Alsooptional +

+
Cal_BddSatisfy() +
Returns a BDD which implies f, true for + some valuation on which f is true, and which has at most + one node at each level + +
Cal_BddSatisfySupport() +
Returns a special cube contained in f. + +
Cal_BddSatisfyingFraction() +
Returns the fraction of valuations which make f true. (Note that + this fraction is independent of whatever set of variables f is supposed to be + a function of) + +
BddSatisfyStep() +
Returns a BDD which implies f, is true for some valuation + on which f is true, and which has at most one node at each level + +
BddSatisfySupportStep() +
+ +
IndexCmp() +
+ +
BddSatisfyingFractionStep() +
+ +
+
+

calBddSize.c

+BDD size and profile routines

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long.

+

See Alsooptional +

+
Cal_BddSize() +
Returns the number of nodes in f when negout is nonzero. If + negout is zero, we pretend that the BDDs don't have negative-output pointers. + +
Cal_BddSizeMultiple() +
The routine is like Cal_BddSize, but takes a null-terminated + array of BDDs and accounts for sharing of nodes. + +
Cal_BddProfile() +
Returns a "node profile" of f, i.e., the number of nodes at each + level in f. + +
Cal_BddProfileMultiple() +
+ +
Cal_BddFunctionProfile() +
Returns a "function profile" for f. + +
Cal_BddFunctionProfileMultiple() +
Returns a "function profile" for fArray. + +
BddMarkBdd() +
+ +
BddCountNoNodes() +
+ +
BddCountNodes() +
+ +
BddSizeStep() +
+ +
BddProfileStep() +
+ +
BddHighestRefStep() +
+ +
BddDominatedStep() +
+ +
+
+

calBddSubstitute.c

+Routine for simultaneous substitution of an array of + variables with an array of functions.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+Routine for simultaneous substitution of an array of + variables with an array of functions.

+

See Alsooptional +

+
Cal_BddSubstitute() +
Substitute a set of variables by functions + +
CalHashTableSubstituteApply() +
required + +
CalHashTableSubstituteReduce() +
required + +
+
+

calBddSupport.c

+Routines related to the support of a BDD.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long.

+

See Alsooptional +

+
Cal_BddSupport() +
returns the support of f as a null-terminated array of variables + +
Cal_BddDependsOn() +
Returns 1 if f depends on var and returns 0 otherwise. + +
CalBddSupportStep() +
returns the support of f as a null-terminated array of variables + +
CalBddUnmarkNodes() +
recursively unmarks the nodes + +
CalBddDependsOnStep() +
required + +
+
+

calBddSwapVars.c

+Routine for swapping two variables.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+Routine for swapping two variables.

+

See AlsoNone +

+
Cal_BddSwapVars() +
Return a function obtained by swapping two variables + +
CalHashTableSwapVarsApply() +
required + +
CalHashTableSwapVarsPlusApply() +
required + +
CalHashTableSwapVarsMinusApply() +
required + +
+
+

calBddVarSubstitute.c

+Routine for simultaneous substitution of an array of + variables with another array of variables.

+By: Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+

See Alsooptional +

+
Cal_BddVarSubstitute() +
Substitute a set of variables by set of another variables. + +
CalBddVarSubstitute() +
Substitute a set of variables by functions + +
CalOpBddVarSubstitute() +
required + +
CalHashTableSubstituteApply() +
required + +
CalHashTableSubstituteReduce() +
required + +
+
+

calBlk.c

+Routines for manipulating blocks of variables.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu). Modelled on the BDD package + developed by David Long.

+Routines for manipulating blocks of variables.

+

+
Cal_BddNewVarBlock() +
Creates and returns a variable block used for + controlling dynamic reordering. + +
Cal_BddVarBlockReorderable() +
Sets the reoderability of a particular block. + +
CalBddFindBlock() +
required + +
CalBddBlockDelta() +
required + +
CalBddShiftBlock() +
required + +
CalBlockMemoryConsumption() +
required + +
CalFreeBlockRecursively() +
required + +
AddBlock() +
required + +
+
+

calCacheTableTwo.c

+Functions to manage the Cache tables.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+

See Alsooptional +

+
CalCacheTableTwoInit() +
Initialize a Cache table using default parameters. + +
CalCacheTableTwoQuit() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoInsert() +
Directly insert a BDD node in the Cache table. + +
CalCacheTableTwoLookup() +
required + +
CalCacheTableTwoFlush() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoFlushAll() +
Free a Cache table along with the associated storage. + +
CalCacheTableTwoGCFlush() +
required + +
CalCacheTableTwoRepackUpdate() +
required + +
CalCheckCacheTableValidity() +
required + +
CalCacheTableTwoFixResultPointers() +
required + +
CalCacheTablePrint() +
required + +
CalBddManagerGetCacheTableData() +
required + +
CalCacheTableRehash() +
required + +
CalCacheTableTwoFlushAssociationId() +
Flushes the entries from the cache which + correspond to the given associationId. + +
CalCacheTableMemoryConsumption() +
required + +
CacheTableTwoRehash() +
required + +
CacheTablePrint() +
required + +
+
+

calDump.c

+BDD library dump/undump routines

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long.

+

See Alsooptional +

+
Cal_BddUndumpBdd() +
Reads a BDD from a file + +
Cal_BddDumpBdd() +
Write a BDD to a file + +
Write() +
+ +
BddDumpBddStep() +
+ +
Read() +
+ +
BddUndumpBddStep() +
+ +
BytesNeeded() +
+ +
+
+

calGC.c

+Garbage collection routines

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+optional

+

See Alsooptional +

+
Cal_BddSetGCMode() +
Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on. + +
Cal_BddManagerGC() +
Invokes the garbage collection at the manager level. + +
Cal_BddManagerSetGCLimit() +
Sets the limit of the garbage collection. + +
CalBddManagerGCCheck() +
required + +
CalHashTableGC() +
This function performs the garbage collection operation + for a particular index. + +
CalRepackNodesAfterGC() +
required + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
+
+

calHashTable.c

+Functions to manage the hash tables that are a part of + 1. unique table + 2. request queue

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

+
CalHashTableInit() +
Initialize a hash table using default parameters. + +
CalHashTableQuit() +
Free a hash table along with the associated storage. + +
CalHashTableAddDirect() +
Directly insert a BDD node in the hash table. + +
CalHashTableFindOrAdd() +
required + +
CalHashTableAddDirectAux() +
required + +
CalHashTableCleanUp() +
required + +
CalHashTableLookup() +
required + +
CalHashTableDelete() +
Deletes a BDD node in the hash table. + +
CalUniqueTableForIdLookup() +
Lookup unique table for id. + +
CalUniqueTableForIdFindOrAdd() +
find or add in the unique table for id. + +
CalHashTableRehash() +
required + +
CalUniqueTableForIdRehashNode() +
required + +
CalBddUniqueTableNumLockedNodes() +
required + +
CalPackNodes() +
required + +
CalBddPackNodesForSingleId() +
required + +
CalBddPackNodesAfterReorderForSingleId() +
Packs the nodes if the variables which has just + been sifted. + +
CalBddPackNodesForMultipleIds() +
required + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
+
+

calHashTableOne.c

+Routines for managing hash table with Bdd is a key and + int, long, or double as a value

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+

See Alsooptional +

+
CalHashTableOneInit() +
Initialize a hash table using default parameters. + +
CalHashTableOneQuit() +
Free a hash table along with the associated storage. + +
CalHashTableOneInsert() +
Directly insert a BDD node in the hash table. + +
CalHashTableOneLookup() +
required + +
HashTableOneRehash() +
required + +
+
+

calHashTableThree.c

+Functions to manage the hash tables that are a part of + ITE operation

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+CalHashTableThreeFindOrAdd

+

See Alsooptional +

+
CalHashTableThreeFindOrAdd() +
required + +
CalHashTableThreeRehash() +
required + +
+
+

calInteract.c

+Functions to manipulate the variable interaction matrix.

+By: Original author:Fabio Somenzi. Modified for CAL package + by Rajeev K. Ranjan

+The interaction matrix tells whether two variables are + both in the support of some function of the DD. The main use of the + interaction matrix is in the in-place swapping. Indeed, if two + variables do not interact, there is no arc connecting the two layers; + therefore, the swap can be performed in constant time, without + scanning the subtables. Another use of the interaction matrix is in + the computation of the lower bounds for sifting. Finally, the + interaction matrix can be used to speed up aggregation checks in + symmetric and group sifting.

+ The computation of the interaction matrix is done with a series of + depth-first searches. The searches start from those nodes that have + only external references. The matrix is stored as a packed array of bits; + since it is symmetric, only the upper triangle is kept in memory. + As a final remark, we note that there may be variables that do + intercat, but that for a given variable order have no arc connecting + their layers when they are adjacent.

+

+
CalSetInteract() +
Set interaction matrix entries. + +
CalTestInteract() +
Test interaction matrix entries. + +
CalInitInteract() +
Initializes the interaction matrix. + +
ddSuppInteract() +
Find the support of f. + +
ddClearLocal() +
Performs a DFS from f, clearing the LSB of the then pointers. + +
ddUpdateInteract() +
Marks as interacting all pairs of variables that appear in + support. + +
+
+

calMem.c

+Routines for memory management.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu). Originally + written by David Long.

+Contains allocation, free, resize routines. Also has + routines for managing records of fixed size.

+

See Alsooptional +

+
Cal_MemFatal() +
Prints an error message and exits. + +
Cal_MemAllocation() +
Returns the memory allocated. + +
Cal_MemGetBlock() +
Allocates a new block of the specified size. + +
Cal_MemFreeBlock() +
Frees the block. + +
Cal_MemResizeBlock() +
Expands or contracts the block to a new size. + We try to avoid moving the block if possible. + +
Cal_MemNewRec() +
Allocates a record from the specified record manager. + +
Cal_MemFreeRec() +
Frees a record managed by the indicated record manager. + +
Cal_MemNewRecMgr() +
Creates a new record manager with the given record size. + +
Cal_MemFreeRecMgr() +
Frees all the storage associated with the specified record manager. + +
CeilingLog2() +
required + +
BlockSizeIndex() +
required + +
AddToFreeList() +
required + +
RemoveFromFreeList() +
required + +
Buddy() +
required + +
TrimToSize() +
required + +
MergeAndFree() +
required + +
+
+

calMemoryManagement.c

+Special memory management routines specific to CAL.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)

+Functions for managing the system memory using a set of + nodeManagers. Each nodeManager manages a set of fixed size + nodes obtained from a set of pages. When additional memory + is required, nodeManager obtains a new page from the pageManager. + The new page is divided into ( PAGE_SIZE/NODE_SIZE ) number of + nodes.

+

+
CalPageManagerInit() +
Initializes a pageManager. + +
CalPageManagerQuit() +
Frees pageManager and associated pages. + +
CalPageManagerPrint() +
Prints address of each memory segment and address of each page. + +
CalNodeManagerInit() +
Initializes a node manager. + +
CalNodeManagerQuit() +
Frees a node manager. + +
CalNodeManagerPrint() +
Prints address of each free node. + +
CalPageManagerAllocPage() +
Allocs a new page. + +
CalPageManagerFreePage() +
Free a page. + +
PageManagerExpandStorage() +
Allocates a segment of memory to expand the storage managed by + pageManager. The allocated segment is divided into free pages + which are linked as a freePageList. + +
PageAlign() +
Return page aligned address greater than or equal to + the pointer. + +
SegmentToPageList() +
Converts a memory segment into a linked list of pages. + if p is a pointer to a page, *p contains address of the next page + if p is a pointer to the last page, *p contains lastPointer. + +
+
+

calPerformanceTest.c

+This file contains the performance test routines for + the CAL package.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+optional

+

See Alsooptional +

+
Cal_PerformanceTest() +
Main routine for testing performances of various routines. + +
CalIncreasingOrderCompare() +
required + +
CalDecreasingOrderCompare() +
required + +
CalPerformanceTestAnd() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceMemoryOverhead() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformaceTestSuperscalar() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestNonSuperscalar() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestMultiway() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestOneway() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestCompose() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestQuantifyAllTogether() +
Performance test routine for quantify (all variables at the same + time). + +
CalQuantifySanityCheck() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestRelProd() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestSubstitute() +
Performance test routine for quantify (all variables at the same + time). + +
CalPerformanceTestSwapVars() +
Performance test routine for quantify (all variables at the same + time). + +
elapsedTime() +
Computes the time. + +
cpuTime() +
Computes the number of page faults. + +
pageFaults() +
Computes the number of page faults. + +
GetRandomNumbers() +
Generates "count" many random numbers ranging between + "lowerBound" and "upperBound". + +
+
+

calPipeline.c

+Routines for creating and managing the pipelined BDD + operations.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu)

+Eventually we would like to have this feature + transparent to the user.

+

See Alsooptional +

+
Cal_PipelineSetDepth() +
Set depth of a BDD pipeline. + +
Cal_PipelineInit() +
Initialize a BDD pipeline. + +
Cal_PipelineCreateProvisionalBdd() +
Create a provisional BDD in the pipeline. + +
Cal_PipelineExecute() +
Executes a pipeline. + +
Cal_PipelineUpdateProvisionalBdd() +
Update a provisional Bdd obtained during pipelining. + +
Cal_BddIsProvisional() +
Returns 1, if the given user BDD contains + provisional BDD node. + +
Cal_PipelineQuit() +
Resets the pipeline freeing all resources. + +
CalBddReorderFixProvisionalNodes() +
required + +
CalCheckPipelineValidity() +
required + +
+
+

calPrint.c

+Routine for printing a BDD.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu) + Originally written by David Long.

+

See AlsoNone +

+
Cal_BddPrintBdd() +
Prints a BDD in the human readable form. + +
CalBddVarName() +
required + +
CalBddNumberSharedNodes() +
required + +
CalBddMarkSharedNodes() +
required + +
Chars() +
required + +
BddPrintTopVar() +
required + +
BddPrintBddStep() +
required + +
BddTerminalId() +
required + +
BddTerminalValueAux() +
required + +
+
+

calPrintProfile.c

+Routines for printing various profiles for a BDD.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long.

+

See Alsooptional +

+
Cal_BddPrintProfile() +
Displays the node profile for f on fp. lineLength specifies + the maximum line length. varNamingFn is as in + Cal_BddPrintBdd. + +
Cal_BddPrintProfileMultiple() +
Cal_BddPrintProfileMultiple is like Cal_BddPrintProfile except + it displays the profile for a set of BDDs + +
Cal_BddPrintFunctionProfile() +
Cal_BddPrintFunctionProfile is like Cal_BddPrintProfile except + it displays a function profile for f + +
Cal_BddPrintFunctionProfileMultiple() +
Cal_BddPrintFunctionProfileMultiple is like + Cal_BddPrintFunctionProfile except for multiple BDDs + +
CalBddPrintProfileAux() +
Prints a profile to the file given by fp. The varNamingProc + is as in Cal_BddPrintBdd. lineLength gives the line width to scale + the profile to. + +
chars() +
+ +
+
+

calQuant.c

+Routines for existential/universal quantification and + relational product.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu)

+

See AlsoNone +

+
Cal_BddExists() +
Returns the result of existentially quantifying some + variables from the given BDD. + +
Cal_BddRelProd() +
Returns the result of taking the logical AND of the + argument BDDs and existentially quantifying some variables from the + product. + +
Cal_BddForAll() +
Returns the result of universally quantifying some + variables from the given BDD. + +
CalOpExists() +
required + +
CalOpRelProd() +
required + +
BddExistsStep() +
required + +
BddRelProdStep() +
required + +
BddDFStep() +
required + +
HashTableApply() +
required + +
HashTableReduce() +
required + +
BddExistsApply() +
required + +
BddExistsBFAux() +
required + +
BddExistsReduce() +
required + +
BddExistsBFPlusDF() +
required + +
BddRelProdApply() +
required + +
BddRelProdReduce() +
required + +
BddRelProdBFAux() +
required + +
BddRelProdBFPlusDF() +
required + +
+
+

calReduce.c

+Routines for optimizing a BDD with respect to a don't + care set (cofactor and restrict).

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu

+

See AlsoNone +

+
Cal_BddCofactor() +
Returns the generalized cofactor of BDD f with respect + to BDD c. + +
Cal_BddReduce() +
Returns a BDD which agrees with f for all valuations + which satisfy c. + +
Cal_BddBetween() +
Returns a minimal BDD whose function contains fMin and is + contained in fMax. + +
CalOpCofactor() +
required + +
BddReduceBF() +
required + +
BddCofactorBF() +
required + +
HashTableReduceApply() +
required + +
HashTableCofactorApply() +
required + +
HashTableCofactorReduce() +
required + +
+
+

calReorderBF.c

+Routines for dynamic reordering of variables.

+By: Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu) + Wilsin Gosti (wilsin@ic.eecs.berkeley.edu)

+This method dynamically reorders variables while + preserving their locality. This entails both memory and + computational overheads. Conceptually and experimentally it has + been observed that these overheads lead to poorer performance + compared to the traditional reordering methods. For details, please + refer to the work by Rajeev K. Ranjan et al - "Dynamic variable + reordering in a breadth-first manipulation based package: Challenges + and Solutions"- Proceedings of ICCD'97.

+

See AlsocalReorderDF.c +calReorderUtil.c +

+
CalBddReorderAuxBF() +
required + +
BddReorderFixForwardingNodes() +
Fixes the forwarding nodes in a unique table. + +
BddReorderFixAndFreeForwardingNodes() +
Traverses the forwarding node lists of index, + index+1 .. up to index+level. Frees the intermediate forwarding nodes. + +
BddReorderSwapVarIndex() +
required + +
CofactorFixAndReclaimForwardedNodes() +
required + +
BddReorderFreeNodes() +
required + +
PrintBddProfileAfterReorder() +
required + +
BddReorderVarSift() +
Reorder variables using "sift" algorithm. + +
BddReorderSiftToBestPos() +
required + +
BddSiftPerfromPhaseIV() +
required + +
BddReorderVarWindow() +
required + +
BddReorderWindow2() +
required + +
BddReorderWindow3() +
required + +
+
+

calReorderDF.c

+Routines for dynamic reordering of variables.

+By: Rajeev K. Ranjan (rajeev@@ic. eecs.berkeley.edu)

+This method is based on traditional dynamic reordering + technique found in depth-first based packages. The data structure is + first converted to conform to traditional one and then reordering is + performed. At the end the nodes are arranged back on the pages. The + computational overheads are in terms of converting the data + structure back and forth and the memory overhead due to the extra + space needed to arrange the nodes. This overhead can be eliminated + by proper implementation. For details, please refer to the work by + Rajeev K. Ranjan et al - "Dynamic variable reordering in a + breadth-first manipulation based package: Challenges and Solutions"- + Proceedings of ICCD'97.

+

See AlsocalReorderBF.c +calReorderUtil.c +

+
CalBddReorderAuxDF() +
required + +
UniqueTableForIdFindOrAdd() +
find or add in the unique table for id. + +
HashTableAddDirect() +
Directly insert a BDD node in the hash table. + +
HashTableFindOrAdd() +
required + +
BddConvertDataStruct() +
Changes the data structure of the bdd nodes. + +
BddConvertDataStructBack() +
Changes the data structure of the bdd nodes to + the original one. + +
BddReallocateNodesInPlace() +
required + +
CalAlignCollisionChains() +
required + +
BddReallocateNodes() +
required + +
BddExchangeAux() +
required + +
CheckValidityOfNodes() +
required + +
SweepVarTable() +
required + +
BddExchange() +
required + +
BddExchangeVarBlocks() +
required + +
BddReorderWindow2() +
required + +
BddReorderWindow3() +
required + +
BddReorderStableWindow3Aux() +
required + +
BddReorderStableWindow3() +
required + +
BddSiftBlock() +
required + +
BddReorderSiftAux() +
Reorder variables using "sift" algorithm. + +
BddReorderSift() +
required + +
BddAddInternalReferences() +
required + +
BddNukeInternalReferences() +
required + +
CeilLog2() +
Returns the smallest integer greater than or equal to log2 of a + number + +
+
+

calReorderUtil.c

+Some utility routines used by both breadth-first and + depth-first reordering techniques.

+By: Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu) + Wilsin Gosti (wilsin@ic.eecs.berkeley.edu)

+

See Alsooptional +

+
CalBddReorderFixUserBddPtrs() +
required + +
CalCheckAllValidity() +
required + +
CalCheckValidityOfNodesForId() +
required + +
CalCheckValidityOfNodesForWindow() +
required + +
CalCheckValidityOfANode() +
required + +
CalCheckRefCountValidity() +
required + +
CalCheckAssoc() +
required + +
CalFixupAssoc() +
required + +
CalBddReorderFixCofactors() +
Fixes the cofactors of the nodes belonging to + the given index. + +
CalBddReorderReclaimForwardedNodes() +
required + +
+
+

calTerminal.c

+Contains the terminal function for various BDD operations.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu

+

+
CalOpAnd() +
required + +
CalOpNand() +
required + +
CalOpOr() +
required + +
CalOpXor() +
required + +
CalOpITE() +
required + +
+
+

calTest.c

+This file contains the test routines for the CAL package.

+By: Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Modified and extended from the original version written + by David Long.

+optional

+

See Alsooptional +

+
main() +
required + +
asDouble() +
required + +
asAddress() +
required + +
terminalIdFn() +
required + +
PrintBdd() +
required + +
Error() +
required + +
Cofactor() +
required + +
Decode() +
required + +
TestAnd() +
required + +
TestNand() +
required + +
TestOr() +
required + +
TestITE() +
required + +
TestXor() +
required + +
TestIdNot() +
required + +
TestCompose() +
required + +
TestSubstitute() +
required + +
TestVarSubstitute() +
required + +
TestSwapVars() +
required + +
TestMultiwayAnd() +
required + +
TestMultiwayOr() +
required + +
TestMultiwayLarge() +
required + +
TestArrayOp() +
required + +
TestInterImpl() +
required + +
TestQnt() +
required + +
TestAssoc() +
required + +
TestRelProd() +
required + +
TestReduce() +
required + +
TestGenCof() +
required + +
TestSize() +
required + +
TestSatisfy() +
required + +
TestPipeline() +
required + +
TestDump() +
required + +
TestReorderBlock() +
required + +
TestReorder() +
required + +
handler() +
required + +
RandomTests() +
required + +
+
+

calUtil.c

+Utility functions for the Cal package.

+By: Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev K. Ranjan (rajeev@eecs.berkeley.edu)

+Utility functions used in the Cal package.

+

See Alsooptional +

+
Cal_BddFunctionPrint() +
Prints the function implemented by the argument BDD + +
CalUniqueTablePrint() +
required + +
CalBddFunctionPrint() +
Prints the function implemented by the argument BDD + +
CalBddPreProcessing() +
required + +
CalBddPostProcessing() +
required + +
CalBddArrayPreProcessing() +
required + +
CalBddGetInternalBdd() +
Prints fatal message and exits. + +
CalBddGetExternalBdd() +
Prints fatal message and exits. + +
CalBddFatalMessage() +
Prints fatal message and exits. + +
CalBddWarningMessage() +
Prints warning message. + +
CalBddNodePrint() +
required + +
CalBddPrint() +
required + +
CalHashTablePrint() +
Prints a hash table. + +
CalHashTableOnePrint() +
required + +
+
+Last updated on 970711 20h11 + diff --git a/calApplyReduce.c b/calApplyReduce.c new file mode 100644 index 0000000..4c66e1b --- /dev/null +++ b/calApplyReduce.c @@ -0,0 +1,224 @@ +/**CFile*********************************************************************** + + FileName [calApplyReduce.c] + + PackageName [cal] + + Synopsis [Generic routines for processing temporary nodes during + "apply" and "reduce" phases.] + + Description [] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calApplyReduce.c,v 1.1.1.3 1998/05/04 00:58:49 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableApply(Cal_BddManager_t * bddManager, CalHashTable_t * + hashTable, CalHashTable_t ** reqQueAtPipeDepth, CalOpProc_t + calOpProc) +{ + int i, numBins; + CalBddNode_t **bins = 0; + CalRequestNode_t *requestNode; + Cal_Bdd_t fx, gx, fxbar, gxbar, result; + Cal_BddId_t bddId; + + numBins = hashTable->numBins; + bins = hashTable->bins; + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + /* Process the requestNode */ + CalRequestNodeGetCofactors(bddManager, requestNode, fx, fxbar, gx, gxbar); + Cal_Assert(((CalAddress_t)(fx.bddNode)) & ~0xf); + Cal_Assert(((CalAddress_t)(gx.bddNode)) & ~0xf); + Cal_Assert(((CalAddress_t)(fxbar.bddNode)) & ~0xf); + Cal_Assert(((CalAddress_t)(gxbar.bddNode)) & ~0xf); + if((*calOpProc)(bddManager, fx, gx, &result) == 0){ + CalBddNormalize(fx, gx); + CalBddGetMinId2(bddManager, fx, gx, bddId); + CalHashTableFindOrAdd(reqQueAtPipeDepth[bddId], fx, gx, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + if((*calOpProc)(bddManager, fxbar, gxbar, &result) == 0){ + CalBddNormalize(fxbar, gxbar); + CalBddGetMinId2(bddManager, fxbar, gxbar, bddId); + CalHashTableFindOrAdd(reqQueAtPipeDepth[bddId], fxbar, gxbar, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableReduce(Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t * uniqueTableForId) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + Cal_BddId_t currentBddId = uniqueTableForId->bddId; + CalNodeManager_t *nodeManager = uniqueTableForId->nodeManager; + CalRequestNode_t *requestNode, *next; + CalBddNode_t *bddNode, *endNode; + Cal_Bdd_t thenBdd, elseBdd, result; + Cal_BddRefCount_t refCount; + + endNode = hashTable->endNode; + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalRequestNodeGetRefCount(requestNode, refCount); + CalRequestAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else + if(CalUniqueTableForIdLookup(bddManager, uniqueTableForId, + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalRequestNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequest(requestNode, elseBdd); + CalHashTableAddDirect(uniqueTableForId, requestNode); + bddManager->numNodes++; + bddManager->gcCheck--; + } + else{ + CalNodeManagerAllocNode(nodeManager, bddNode); + CalBddNodePutThenBddId(bddNode, CalBddGetBddId(thenBdd)); + CalBddNodePutThenBddNode(bddNode, CalBddGetBddNodeNot(thenBdd)); + CalBddNodePutElseBddId(bddNode, CalBddGetBddId(elseBdd)); + CalBddNodePutElseBddNode(bddNode, CalBddGetBddNodeNot(elseBdd)); + CalRequestNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(uniqueTableForId, bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, currentBddId); + CalRequestNodePutThenRequestNode(requestNode, CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + } + memset((char *)bins, 0, hashTable->numBins * sizeof(CalBddNode_t *)); + hashTable->endNode = endNode; +} +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + + + + + + diff --git a/calAssociation.c b/calAssociation.c new file mode 100644 index 0000000..1243957 --- /dev/null +++ b/calAssociation.c @@ -0,0 +1,601 @@ +/**CFile*********************************************************************** + + FileName [calAssociation.c] + + PackageName [cal] + + Synopsis [Contains the routines related to the variable association.] + + Description [optional] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calAssociation.c,v 1.1.1.3 1998/05/04 00:58:50 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int AssociationIsEqual(Cal_BddManager_t * bddManager, Cal_Bdd_t * p, Cal_Bdd_t * q); +static int CheckAssoc(Cal_BddManager_t *bddManager, Cal_Bdd *assocInfo, int pairs); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Creates or finds a variable association.] + + Description [Creates or finds a variable association. The association is + specified by associationInfo, which is a an array of BDD with + Cal_BddNull(bddManager) as the end marker. If pairs is 0, the array is + assumed to be an array of variables. In this case, each variable is paired + with constant BDD one. Such an association may viewed as specifying a set + of variables for use with routines such as Cal_BddExists. If pair is not 0, + then the even numbered array elements should be variables and the odd numbered + elements should be the BDDs which they are mapped to. In both cases, the + return value is an integer identifier for this association. If the given + association is equivalent to one which already exists, the same identifier + is used for both, and the reference count of the association is increased by + one.] + + SideEffects [None] + + SeeAlso [Cal_AssociationQuit] + +******************************************************************************/ +int +Cal_AssociationInit(Cal_BddManager bddManager, + Cal_Bdd *associationInfoUserBdds, + int pairs) +{ + int i, numAssociations; + CalAssociation_t *p, **q; + Cal_Bdd_t f; + Cal_Bdd_t *varAssociation; + Cal_BddId_t j; + long last; + Cal_Bdd_t *associationInfo; + + if (!CheckAssoc(bddManager, associationInfoUserBdds, pairs)){ + return (-1); + } + + +/* First count the number of elements */ + for (i=0; associationInfoUserBdds[i]; i++); + if (pairs) numAssociations = i/2; + else numAssociations = i; + associationInfo = Cal_MemAlloc(Cal_Bdd_t, i+1); + for (j=0; j < i; j++){ + associationInfo[j] = + CalBddGetInternalBdd(bddManager,associationInfoUserBdds[j]); + } + associationInfo[j] = bddManager->bddNull; + + + varAssociation = Cal_MemAlloc(Cal_Bdd_t, bddManager->maxNumVars+1); + for(i = 0; i <= bddManager->maxNumVars; i++){ + varAssociation[i] = bddManager->bddNull; + } + + + if(pairs){ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[(i<<1)]; + varAssociation[CalBddGetBddId(f)] = associationInfo[(i<<1)+1]; + } + } + else{ + for(i = 0; i < numAssociations; i++){ + f=associationInfo[i]; + varAssociation[CalBddGetBddId(f)] = CalBddOne(bddManager); + } + } + /* Check for existence. */ + for(p = bddManager->associationList; p; p = p->next){ + if(AssociationIsEqual(bddManager, p->varAssociation, varAssociation)){ + Cal_MemFree(varAssociation); + Cal_MemFree(associationInfo); + p->refCount++; + return (p->id); + } + } + /* Find the first unused id. */ + for(q = &bddManager->associationList, p = *q, i = 0; + p && p->id == i; q = &p->next, p = *q, ++i){ + } + /*p = Cal_MemAlloc(CalAssociation_t, 1);*/ + /*p = CAL_BDD_NEW_REC(bddManager, CalAssociation_t);*/ + p = Cal_MemAlloc(CalAssociation_t, 1); + p->id = i; + p->next = *q; + *q = p; + p->varAssociation = varAssociation; + last = -1; + if(pairs){ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[(i<<1)]; + j = CalBddGetBddIndex(bddManager, f); + if((long)j > last){ + last = j; + } + } + } + else{ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[i]; + j = CalBddGetBddIndex(bddManager, f); + if((long)j > last){ + last = j; + } + } + } + p->lastBddIndex = last; + p->refCount = 1; + /* Protect BDDs in the association. */ + if(pairs){ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[(i<<1)+1]; + CalBddIcrRefCount(f); + } + } + Cal_MemFree(associationInfo); + return p->id; +} + + +/**Function******************************************************************** + + Synopsis [Deletes the variable association given by id] + + Description [Decrements the reference count of the variable association with + identifier id, and frees it if the reference count becomes zero.] + + SideEffects [None] + + SeeAlso [Cal_AssociationInit] + +******************************************************************************/ +void +Cal_AssociationQuit(Cal_BddManager bddManager, int associationId) +{ + Cal_BddId_t i; + Cal_Bdd_t f; + CalAssociation_t *p, **q; + + if(bddManager->currentAssociation->id == associationId){ + bddManager->currentAssociation = bddManager->tempAssociation; + } + for(q = &bddManager->associationList, p = *q; p; q = &p->next, p = *q){ + if(p->id == associationId){ + p->refCount--; + if(!p->refCount){ + /* Unprotect the BDDs in the association. */ + for(i = 1; i <= bddManager->numVars; i++){ + f = p->varAssociation[i]; + if(!CalBddIsBddNull(bddManager, f)){ + CalBddDcrRefCount(f); + } + } + *q = p->next; + Cal_MemFree(p->varAssociation); + /*CAL_BDD_FREE_REC(bddManager, p, CalAssociation_t);*/ + Cal_MemFree(p); + CalCacheTableTwoFlushAssociationId(bddManager, associationId); + } + return; + } + } + CalBddWarningMessage("Cal_AssociationQuit: no association with specified ID"); +} + +/**Function******************************************************************** + + Synopsis [Sets the current variable association to the one given by id and + returns the ID of the old association.] + + Description [Sets the current variable association to the one given by id and + returns the ID of the old association. An id of -1 indicates the temporary + association] + + SideEffects [None] + +******************************************************************************/ +int +Cal_AssociationSetCurrent(Cal_BddManager bddManager, int associationId) +{ + int oldAssociationId; + CalAssociation_t *p; + + oldAssociationId = bddManager->currentAssociation->id; + if(associationId != -1){ + for(p = bddManager->associationList; p; p = p->next){ + if(p->id == associationId){ + bddManager->currentAssociation = p; + return (oldAssociationId); + } + } + CalBddWarningMessage( + "Cal_AssociationSetCurrent: no variable association with specified ID.\n May have been discarded during dynamic reordering."); + } + bddManager->currentAssociation = bddManager->tempAssociation; + return oldAssociationId; +} + + +/**Function******************************************************************** + + Synopsis [Adds to the temporary variable association.] + + Description [Pairs is 0 if the information represents only a list of + variables rather than a full association.] + + SideEffects [None] + +******************************************************************************/ +void +Cal_TempAssociationAugment(Cal_BddManager bddManager, + Cal_Bdd *associationInfoUserBdds, + int pairs) +{ + int i, j, numAssociations; + Cal_Bdd_t f; + long last; + Cal_Bdd_t *associationInfo; + + if (CheckAssoc(bddManager, associationInfoUserBdds, pairs) == 0) { + return; + } + + /*while (associationInfoUserBdds[i++]);*/ + for (i=0; associationInfoUserBdds[i]; i++); + if (pairs) numAssociations = i/2; + else numAssociations = i; + associationInfo = Cal_MemAlloc(Cal_Bdd_t, i+1); + for (j=0; j < i; j++){ + associationInfo[j] = + CalBddGetInternalBdd(bddManager,associationInfoUserBdds[j]); + } + associationInfo[j] = bddManager->bddNull; + + last = bddManager->tempAssociation->lastBddIndex; + if(pairs){ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[(i<<1)]; + j = CalBddGetBddId(f); + if(bddManager->idToIndex[j] > last){ + last = bddManager->idToIndex[j]; + } + f = bddManager->tempAssociation->varAssociation[j]; + if(!CalBddIsBddNull(bddManager, f)){ + CalBddDcrRefCount(f); + } + f = associationInfo[(i<<1)+1]; + bddManager->tempAssociation->varAssociation[j] = f; + /* Protect BDDs in the association. */ + CalBddIcrRefCount(f); + } + } + else{ + for(i = 0; i < numAssociations; i++){ + f = associationInfo[i]; + j = CalBddGetBddId(f); + if(bddManager->idToIndex[j] > last){ + last = bddManager->idToIndex[j]; + } + f = bddManager->tempAssociation->varAssociation[j]; + if(!CalBddIsBddNull(bddManager, f)){ + CalBddDcrRefCount(f); + } + bddManager->tempAssociation->varAssociation[j] = CalBddOne(bddManager); + } + } + bddManager->tempAssociation->lastBddIndex = last; + Cal_MemFree(associationInfo); +} + + + +/**Function******************************************************************** + + Synopsis [Sets the temporary variable association.] + + Description [Pairs is 0 if the information represents only a list of + variables rather than a full association.] + + SideEffects [None] + +******************************************************************************/ +void +Cal_TempAssociationInit(Cal_BddManager bddManager, + Cal_Bdd *associationInfoUserBdds, + int pairs) +{ + long i; + Cal_Bdd_t f; + + /* Clean up old temporary association. */ + for(i = 1; i <= bddManager->numVars; i++){ + f = bddManager->tempAssociation->varAssociation[i]; + if(!CalBddIsBddNull(bddManager, f)){ + CalBddDcrRefCount(f); + bddManager->tempAssociation->varAssociation[i] = bddManager->bddNull; + } + } + bddManager->tempAssociation->lastBddIndex = -1; + Cal_TempAssociationAugment(bddManager, associationInfoUserBdds, pairs); +} + +/**Function******************************************************************** + + Synopsis [Cleans up temporary association] + + Description [Cleans up temporary associationoptional] + + SideEffects [None] + +******************************************************************************/ +void +Cal_TempAssociationQuit(Cal_BddManager bddManager) +{ + int i; + Cal_Bdd_t f; + + /* Clean up old temporary association. */ + for(i = 1; i <= bddManager->numVars; i++){ + f = bddManager->tempAssociation->varAssociation[i]; + if(!CalBddIsBddNull(bddManager, f)){ + CalBddDcrRefCount(f); + bddManager->tempAssociation->varAssociation[i] = bddManager->bddNull; + } + } + bddManager->tempAssociation->lastBddIndex = -1; +} + + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Frees the variable associations] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalAssociationListFree(Cal_BddManager_t * bddManager) +{ + CalAssociation_t *assoc, *nextAssoc; + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + Cal_MemFree(assoc->varAssociation); + /*CAL_BDD_FREE_REC(bddManager, assoc, CalAssociation_t);*/ + Cal_MemFree(assoc); + } +} + +/**Function******************************************************************** + + Synopsis [Need to be called after repacking.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalVarAssociationRepackUpdate(Cal_BddManager_t * bddManager, + Cal_BddId_t id) +{ + CalAssociation_t *assoc, *nextAssoc; + int i; + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) == id){ + CalBddForward(assoc->varAssociation[i]); + } + } + } + /* fix temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) == id){ + CalBddForward(assoc->varAssociation[i]); + } + } +} + +/**Function******************************************************************** + + Synopsis [Checks the validity of association.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCheckAssociationValidity(Cal_BddManager_t * bddManager) +{ + CalAssociation_t *assoc, *nextAssoc; + int i; + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + Cal_Assert(CalBddIsForwarded(assoc->varAssociation[i]) == 0); + } + } + /* temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + Cal_Assert(CalBddIsForwarded(assoc->varAssociation[i]) == 0); + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalReorderAssociationFix(Cal_BddManager_t *bddManager) +{ + CalAssociation_t *assoc, *nextAssoc; + int i; + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddIsForwardedTo(assoc->varAssociation[i]); + } + } + } + /* fix temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddIsForwardedTo(assoc->varAssociation[i]); + } + } +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Checks for equality of two associations] + + Description [Checks for equality of two associations] + + SideEffects [None] + +******************************************************************************/ +static int +AssociationIsEqual(Cal_BddManager_t * bddManager, + Cal_Bdd_t * p, + Cal_Bdd_t * q) +{ + int i; + for(i = 1; i <= bddManager->maxNumVars; i++){ + if(CalBddIsEqual(p[i], q[i]) == 0){ + return (0); + } + } + return (1); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +CheckAssoc(Cal_BddManager_t *bddManager, Cal_Bdd *assocInfo, int pairs) +{ + CalBddArrayPreProcessing(bddManager, assocInfo); + if (pairs){ + while (assocInfo[0] && assocInfo[1]){ + if (CalBddTypeAux(bddManager, + CalBddGetInternalBdd(bddManager, assocInfo[0])) != + CAL_BDD_TYPE_POSVAR){ + CalBddWarningMessage("CheckAssoc: first element in pair is not a positive variable"); + return (0); + } + assocInfo+=2; + } + } + return (1); +} + diff --git a/calBdd.make b/calBdd.make new file mode 100644 index 0000000..3ed7cbd --- /dev/null +++ b/calBdd.make @@ -0,0 +1,21 @@ +CSRC_cal += cal.c calBddOp.c calBddManager.c calMemoryManagement.c\ + calHashTable.c calUtil.c calGC.c \ + calTerminal.c calAssociation.c \ + calBddSubstitute.c calReduce.c calQuant.c \ + calBddSwapVars.c calBddSatisfy.c calBddSize.c \ + calBddSupport.c calPrint.c calPrintProfile.c calDump.c\ + calHashTableOne.c calPipeline.c calPerformanceTest.c \ + calHashTableThree.c calBddITE.c calBddCompose.c\ + calCacheTableTwo.c calApplyReduce.c calBlk.c \ + calReorderBF.c calReorderDF.c calInteract.c\ + calBddVarSubstitute.c calReorderUtil.c calMem.c + +HEADERS_cal += cal.h calInt.h calMem.h + +MISC += calBddReorderTest.c calPerformanceTest.c calTest.c\ + calAllAbs.html calAllByFile.html calAllByFunc.html\ + calAllDet.html calAllFile.html calDesc.html\ + calExt.html calExtAbs.html calExtDet.html calTitle.html credit.html\ + calDoc.txt + +DEPENDENCYFILES = $(CSRC_cal) diff --git a/calBddCompose.c b/calBddCompose.c new file mode 100644 index 0000000..73cc60d --- /dev/null +++ b/calBddCompose.c @@ -0,0 +1,334 @@ +/**CFile*********************************************************************** + + FileName [calBddCompose.c] + + PackageName [cal] + + Synopsis [Routine for composing one BDD into another.] + + Description [] + + SeeAlso [] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddCompose.c,v 1.1.1.3 1998/05/04 00:58:50 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [composition - substitute a BDD variable by a function] + + Description [Returns the BDD obtained by substituting a variable by a function] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddCompose(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd, Cal_Bdd hUserBdd) +{ + Cal_Bdd_t result; + CalRequestNode_t *requestNode; + Cal_Bdd_t F, G, H; + + if (CalBddPreProcessing(bddManager, 3, fUserBdd, gUserBdd, hUserBdd) == 0){ + result = bddManager->bddNull; + } + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + H = CalBddGetInternalBdd(bddManager, hUserBdd); + + if(CalBddIsBddConst(G)){ + CalBddNodeIcrRefCount(fUserBdd); + return fUserBdd; + } + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], requestNode); + CalRequestNodePutF(requestNode, F); + CalRequestNodePutG(requestNode, H); + CalRequestNodePutNextRequestNode(requestNode, 0); + bddManager->requestNodeListArray[0] = requestNode; + /* + ** We can achieve a superscalar compose operation, provided G + ** is the same for all the compose operation + */ + + CalRequestNodeListCompose(bddManager, bddManager->requestNodeListArray[0], + CalBddGetBddIndex(bddManager, G)); + + CalRequestNodeGetThenRequest(requestNode, result); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], requestNode); + bddManager->requestNodeListArray[0] = Cal_Nil(CalRequestNode_t); + + return CalBddGetExternalBdd(bddManager, result); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + + note [THERE IS A POSSIBILITY OF HAVING A PIPELINED VERSION + NEED TO THINK IT THROUGH] + +******************************************************************************/ +void +CalRequestNodeListCompose(Cal_BddManager_t * bddManager, + CalRequestNode_t * requestNodeList, + Cal_BddIndex_t composeIndex) +{ + CalRequestNode_t *requestNode; + CalRequest_t F, H, result; + int bddId, bddIndex; + CalHashTable_t *hashTable, *uniqueTableForId; + CalHashTable_t **reqQueForCompose = bddManager->reqQue[0]; + CalHashTable_t **reqQueForITE = bddManager->reqQue[1]; + + /* ReqQueForComposeInsertUsingReqList */ + for(requestNode = requestNodeList; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, F); + CalRequestNodeGetG(requestNode, H); + CalComposeRequestCreate(bddManager, F, H, composeIndex, + reqQueForCompose, reqQueForITE, &result); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + } + + /* ReqQueApply */ + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reqQueForCompose[bddId]; + if(hashTable->numEntries){ + CalHashTableComposeApply(bddManager, hashTable, composeIndex, + reqQueForCompose, reqQueForITE); + } + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableITEApply(bddManager, hashTable, reqQueForITE); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reqQueForCompose[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + + /* ReqListArrayReqForward */ + for(requestNode = requestNodeList; requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, result); + CalRequestIsForwardedTo(result); + CalRequestNodePutThenRequest(requestNode, result); + } + + /* ReqQueCleanUp */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForCompose[bddId]); + CalHashTableCleanUp(reqQueForITE[bddId]); + } +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableComposeApply(Cal_BddManager_t *bddManager, + CalHashTable_t *hashTable, + Cal_BddIndex_t gIndex, + CalHashTable_t **reqQueForCompose, + CalHashTable_t **reqQueForITE) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_Bdd_t fx, fxbar; + Cal_Bdd_t hx, hxbar; + Cal_Bdd_t calBdd1, calBdd2, calBdd3; + Cal_Bdd_t result; + Cal_BddId_t bddId; + Cal_BddIndex_t index; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + + /* Process the requestNode */ + CalRequestNodeGetCofactors(bddManager, requestNode, fx, fxbar, hx, hxbar); + + /* Process left cofactor */ + index = CalBddGetBddIndex(bddManager, fx); + if(index > gIndex){ + CalBddIcrRefCount(fx); + CalRequestNodePutThenRequest(requestNode, fx); + } + else if(index < gIndex){ + CalBddGetMinId2(bddManager, fx, hx, bddId); + CalHashTableFindOrAdd(reqQueForCompose[bddId], fx, hx, &result); + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + } + else{ + /* fxIndex == gIndex */ + /* RequestNodeThen = ITE(hx, fxThen, fxElse) */ + calBdd1 = hx; + CalBddGetThenBdd(fx, calBdd2); + CalBddGetElseBdd(fx, calBdd3); + result = CalOpITE(bddManager, calBdd1, calBdd2, calBdd3, reqQueForITE); + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + } + + /* Process right cofactor */ + index = CalBddGetBddIndex(bddManager, fxbar); + if(index > gIndex){ + CalBddIcrRefCount(fxbar); + CalRequestNodePutElseRequest(requestNode, fxbar); + } + else if(index < gIndex){ + CalBddGetMinId2(bddManager, fxbar, hxbar, bddId); + CalHashTableFindOrAdd(reqQueForCompose[bddId], fxbar, hxbar, &result); + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + else{ + /* fxbarIndex == gIndex */ + /* RequestNodeElse = ITE(hxbar, fxbarThen, fxbarElse) */ + calBdd1 = hxbar; + CalBddGetThenBdd(fxbar, calBdd2); + CalBddGetElseBdd(fxbar, calBdd3); + result = CalOpITE(bddManager, calBdd1, calBdd2, calBdd3, reqQueForITE); + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalComposeRequestCreate(Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + Cal_Bdd_t h, + Cal_BddIndex_t composeIndex, + CalHashTable_t **reqQueForCompose, + CalHashTable_t **reqQueForITE, + Cal_Bdd_t *resultPtr) +{ + Cal_BddIndex_t index; + Cal_BddId_t bddId; + + index = CalBddGetBddIndex(bddManager, f); + if(index > composeIndex){ + *resultPtr = f; + } + else if(index < composeIndex){ + CalBddGetMinId2(bddManager, f, h, bddId); + CalHashTableFindOrAdd(reqQueForCompose[bddId], f, h, resultPtr); + } + else{ + Cal_Bdd_t calBdd1, calBdd2, calBdd3; + calBdd1 = h; + CalBddGetThenBdd(f, calBdd2); + CalBddGetElseBdd(f, calBdd3); + *resultPtr = CalOpITE(bddManager, calBdd1, calBdd2, calBdd3, reqQueForITE); + } +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ diff --git a/calBddITE.c b/calBddITE.c new file mode 100644 index 0000000..aec8a49 --- /dev/null +++ b/calBddITE.c @@ -0,0 +1,333 @@ +/**CFile*********************************************************************** + + FileName [calBddITE.c] + + PackageName [cal] + + Synopsis [Routine for computing ITE of 3 BDD operands.] + + Description [] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddITE.c,v 1.1.1.3 1998/05/04 00:58:51 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h] + + SideEffects [None] + + SeeAlso [Cal_BddAnd, Cal_BddNand, Cal_BddOr, Cal_BddNor, Cal_BddXor, + Cal_BddXnor] + +******************************************************************************/ +Cal_Bdd +Cal_BddITE(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd, + Cal_Bdd hUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + Cal_Bdd_t F, G, H; + if (CalBddPreProcessing(bddManager, 3, fUserBdd, gUserBdd, hUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + H = CalBddGetInternalBdd(bddManager, hUserBdd); + result = CalBddOpITEBF(bddManager, F, G, H); + } + else { + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + + +/**Function******************************************************************** + + Name [CalRequestNodeListArrayOp] + + Synopsis [required] + + Description [This routine is to be used for pipelined and + superscalar ITE operations. Currently there is no user interface + provided to this routine.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalRequestNodeListArrayITE(Cal_BddManager_t *bddManager, + CalRequestNode_t **requestNodeListArray) +{ + CalRequestNode_t *requestNode, *ptrIndirect; + CalRequest_t F, G, H, result; + int pipeDepth, bddId, bddIndex; + CalHashTable_t **reqQueAtPipeDepth, *hashTable, *uniqueTableForId; + CalHashTable_t ***reqQue = bddManager->reqQue; + + /* ReqQueInsertUsingReqListArray */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + for(requestNode = requestNodeListArray[pipeDepth]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, F); + CalRequestIsForwardedTo(F); + ptrIndirect = CalRequestNodeGetElseRequestNode(requestNode); + CalRequestNodeGetThenRequest(ptrIndirect, G); + CalRequestIsForwardedTo(G); + CalRequestNodeGetElseRequest(ptrIndirect, H); + CalRequestIsForwardedTo(H); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], ptrIndirect); + result = CalOpITE(bddManager, F, G, H, reqQueAtPipeDepth); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + } + } + + /* ReqQueApply */ + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + hashTable = reqQueAtPipeDepth[bddId]; + if(hashTable->numEntries){ + CalHashTableITEApply(bddManager, hashTable, reqQueAtPipeDepth); + } + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + hashTable = reqQue[pipeDepth][bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + } + + /* ReqListArrayReqForward */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + for(requestNode = requestNodeListArray[pipeDepth]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, result); + CalRequestIsForwardedTo(result); + CalRequestNodePutThenRequest(requestNode, result); + } + } + + /* ReqQueCleanUp */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueAtPipeDepth[bddId]); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd_t +CalBddOpITEBF( + Cal_BddManager_t *bddManager, + Cal_Bdd_t f, + Cal_Bdd_t g, + Cal_Bdd_t h) +{ + Cal_Bdd_t result; + Cal_BddId_t bddId; + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + int bddIndex; + CalHashTable_t *hashTable; + CalHashTable_t *uniqueTableForId; + CalHashTable_t **reqQueForITE = bddManager->reqQue[0]; + + result = CalOpITE(bddManager, f, g, h, reqQueForITE); + + CalBddGetMinIndex3(bddManager, f, g, h, minIndex); + /* ReqQueApply */ + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableITEApply(bddManager, hashTable, reqQueForITE); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + + CalRequestIsForwardedTo(result); + + /* Clean up */ + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(reqQueForITE[bddId]); + } + + return result; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableITEApply( + Cal_BddManager_t *bddManager, + CalHashTable_t *hashTable, + CalHashTable_t **reqQueAtPipeDepth) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_Bdd_t fx, gx, fxbar, gxbar, hx, hxbar, result; + CalNodeManager_t *nodeManager = hashTable->nodeManager; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + /* Process the requestNode */ + CalITERequestNodeGetCofactors(bddManager, requestNode, + fx, fxbar, gx, gxbar, hx, hxbar); + result = CalOpITE(bddManager, fx, gx, hx, reqQueAtPipeDepth); + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + result = CalOpITE(bddManager, fxbar, gxbar, hxbar, reqQueAtPipeDepth); + CalBddIcrRefCount(result); + CalNodeManagerFreeNode(nodeManager, + CalRequestNodeGetElseRequestNode(requestNode)); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h] + + SideEffects [None] + + SeeAlso [Cal_BddAnd, Cal_BddNand, Cal_BddOr, Cal_BddNor, Cal_BddXor, + Cal_BddXnor] + +******************************************************************************/ +Cal_Bdd_t +CalBddITE(Cal_BddManager_t *bddManager, Cal_Bdd_t F, Cal_Bdd_t G, + Cal_Bdd_t H) +{ + Cal_Bdd_t result; + result = CalBddOpITEBF(bddManager, F, G, H); + CalBddIcrRefCount(result); + return result; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ diff --git a/calBddManager.c b/calBddManager.c new file mode 100644 index 0000000..6146d78 --- /dev/null +++ b/calBddManager.c @@ -0,0 +1,833 @@ +/**CFile*********************************************************************** + + FileName [calBddManager.c] + + PackageName [cal] + + Synopsis [Routines for maintaing the manager and creating + variables etc.] + + Description [] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddManager.c,v 1.7 1998/09/16 16:07:44 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +unsigned long calPrimes[] = +{ + 1, + 2, + 3, + 7, + 13, + 23, + 59, + 113, + 241, + 503, + 1019, + 2039, + 4091, + 8179, + 11587, + 16369, + 23143, + 32749, + 46349, + 65521, + 92683, + 131063, + 185363, + 262139, + 330287, + 416147, + 524269, + 660557, + 832253, + 1048571, + 1321109, + 1664501, + 2097143, + 2642201, + 3328979, + 4194287, + 5284393, + 6657919, + 8388593, + 10568797, + 13315831, + 16777199, + 33554393, + 67108859, + 134217689, + 268435399, + 536870879, + 1073741789, + 2147483629 +}; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#define CalBddManagerGetNodeManager(bddManager, id) \ + bddManager->nodeManagerArray[id] + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void BddDefaultTransformFn(Cal_BddManager_t * bddManager, CalAddress_t value1, CalAddress_t value2, CalAddress_t * result1, CalAddress_t * result2, Cal_Pointer_t pointer); +#ifdef CALBDDMANAGER +static int CalBddManagerPrint(Cal_BddManager_t *bddManager); +#endif /* CALBDDMANAGER */ + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Creates and initializes a new BDD manager.] + + Description [Initializes and allocates fields of the BDD manager. Some of the + fields are initialized for maxNumVars+1 or numVars+1, whereas some of them are + initialized for maxNumVars or numVars. The first kind of fields are associated + with the id of a variable and the second ones are with the index of the + variable.] + + SideEffects [None] + + SeeAlso [Cal_BddManagerQuit] + +******************************************************************************/ +Cal_BddManager +Cal_BddManagerInit( ) +{ + Cal_BddManager_t *bddManager; + int i; + CalBddNode_t *bddNode; + Cal_Bdd_t resultBdd; + + + bddManager = Cal_MemAlloc(Cal_BddManager_t, 1); + + bddManager->numVars = 0; + + bddManager->maxNumVars = 30; + + bddManager->varBdds = Cal_MemAlloc(Cal_Bdd_t, bddManager->maxNumVars+1); + + bddManager->pageManager1 = CalPageManagerInit(4); + bddManager->pageManager2 = CalPageManagerInit(NUM_PAGES_PER_SEGMENT); + + bddManager->nodeManagerArray = Cal_MemAlloc(CalNodeManager_t*, bddManager->maxNumVars+1); + + bddManager->nodeManagerArray[0] = CalNodeManagerInit(bddManager->pageManager1); + bddManager->uniqueTable = Cal_MemAlloc(CalHashTable_t *, + bddManager->maxNumVars+1); + bddManager->uniqueTable[0] = CalHashTableInit(bddManager, 0); + + /* Constant One */ + CalBddPutBddId(bddManager->bddOne, CAL_BDD_CONST_ID); + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], bddNode); + CalBddPutBddNode(bddManager->bddOne, bddNode); + /* ~0x0 put so that the node is not mistaken for forwarded node */ + CalBddPutThenBddNode(bddManager->bddOne, (CalBddNode_t *)~0x0); + CalBddPutElseBddNode(bddManager->bddOne, (CalBddNode_t *)~0x0); + CalBddPutRefCount(bddManager->bddOne, CAL_MAX_REF_COUNT); + CalBddNot(bddManager->bddOne, bddManager->bddZero); + + /* Create a user BDD */ + CalHashTableAddDirectAux(bddManager->uniqueTable[0], bddManager->bddOne, + bddManager->bddOne, &resultBdd); + CalBddPutRefCount(resultBdd, CAL_MAX_REF_COUNT); + bddManager->userOneBdd = CalBddGetBddNode(resultBdd); + bddManager->userZeroBdd = CalBddNodeNot(bddManager->userOneBdd); + + /* Null BDD */ + CalBddPutBddId(bddManager->bddNull, CAL_BDD_NULL_ID); + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], bddNode); + CalBddPutBddNode(bddManager->bddNull, bddNode); + /* ~0x10 put so that the node is not mistaken for forwarded node or + the constant nodes. */ + CalBddPutThenBddNode(bddManager->bddNull, (CalBddNode_t *)~0x10); + CalBddPutElseBddNode(bddManager->bddNull, (CalBddNode_t *)~0x10); + CalBddPutRefCount(bddManager->bddNull, CAL_MAX_REF_COUNT); + /* Put in the unique table, so that it gets locked */ + /*CalHashTableAddDirect(bddManager->uniqueTable[0], bddNode);*/ + + bddManager->indexToId = Cal_MemAlloc(Cal_BddId_t, bddManager->maxNumVars); + bddManager->idToIndex = Cal_MemAlloc(Cal_BddIndex_t, bddManager->maxNumVars+1); + bddManager->idToIndex[CAL_BDD_CONST_ID] = CAL_BDD_CONST_INDEX; + + bddManager->depth = DEFAULT_DEPTH; + bddManager->maxDepth = DEFAULT_MAX_DEPTH; + bddManager->pipelineState = READY; + bddManager->pipelineDepth = PIPELINE_EXECUTION_DEPTH; + bddManager->currentPipelineDepth = 0; + bddManager->pipelineFn = CalOpAnd; + + + bddManager->reqQue = Cal_MemAlloc(CalHashTable_t **, bddManager->maxDepth); + bddManager->cacheTable = CalCacheTableTwoInit(bddManager); + + for (i=0; i < bddManager->maxDepth; i++){ + bddManager->reqQue[i] = Cal_MemAlloc(CalHashTable_t *, + bddManager->maxNumVars+1); + bddManager->reqQue[i][0] = CalHashTableInit(bddManager, 0); + } + + bddManager->requestNodeListArray = Cal_MemAlloc(CalRequestNode_t*, + MAX_INSERT_DEPTH); + for(i = 0; i < MAX_INSERT_DEPTH; i++){ + bddManager->requestNodeListArray[i] = Cal_Nil(CalRequestNode_t); + } + bddManager->userProvisionalNodeList = Cal_Nil(CalRequestNode_t); + + /* Garbage collection related information */ + bddManager->numNodes = bddManager->numPeakNodes = 1; + bddManager->numNodesFreed = 0; + bddManager->gcCheck = CAL_GC_CHECK; + bddManager->uniqueTableGCLimit = CAL_MIN_GC_LIMIT; + bddManager->numGC = 0; + bddManager->gcMode = 1; + bddManager->nodeLimit = 0; + bddManager->overflow = 0; + bddManager->repackAfterGCThreshold = CAL_REPACK_AFTER_GC_THRESHOLD; + + + /* Special functions */ + bddManager->TransformFn = BddDefaultTransformFn; + bddManager->transformEnv = 0; + + + /* Association related information */ + bddManager->associationList = Cal_Nil(CalAssociation_t); + /*bddManager->tempAssociation = CAL_BDD_NEW_REC(bddManager, CalAssociation_t);*/ + bddManager->tempAssociation = Cal_MemAlloc(CalAssociation_t, 1); + bddManager->tempAssociation->id = -1; + bddManager->tempAssociation->lastBddIndex = -1; + bddManager->tempAssociation->varAssociation = + Cal_MemAlloc(Cal_Bdd_t, bddManager->maxNumVars+1); + for(i = 0; i < bddManager->maxNumVars+1; i++){ + bddManager->tempAssociation->varAssociation[i] = bddManager->bddNull; + } + bddManager->tempOpCode = -1; + bddManager->currentAssociation = bddManager->tempAssociation; + + /* BDD reordering related information */ + bddManager->dynamicReorderingEnableFlag = 1; + bddManager->reorderMethod = CAL_REORDER_METHOD_DF; + bddManager->reorderTechnique = CAL_REORDER_NONE; + bddManager->numForwardedNodes = 0; + bddManager->numReorderings = 0; + bddManager->maxNumVarsSiftedPerReordering = 1000; + bddManager->maxNumSwapsPerReordering = 2000000; + bddManager->numSwaps = 0; + bddManager->numTrivialSwaps = 0; + bddManager->maxSiftingGrowth = 2.0; + bddManager->reorderingThreshold = CAL_BDD_REORDER_THRESHOLD; + bddManager->maxForwardedNodes = CAL_NUM_FORWARDED_NODES_LIMIT; + bddManager->tableRepackThreshold = CAL_TABLE_REPACK_THRESHOLD; + + + /*bddManager->superBlock = CAL_BDD_NEW_REC(bddManager, Cal_Block_t);*/ + bddManager->superBlock = Cal_MemAlloc(Cal_Block_t, 1); + bddManager->superBlock->numChildren=0; + bddManager->superBlock->children=0; + bddManager->superBlock->reorderable=1; + bddManager->superBlock->firstIndex= -1; + bddManager->superBlock->lastIndex=0; + + bddManager->hooks = Cal_Nil(void); + + return bddManager; +} + +/**Function******************************************************************** + + Synopsis [Frees the BDD manager and all the associated allocations] + + Description [Frees the BDD manager and all the associated allocations] + + SideEffects [None] + + SeeAlso [Cal_BddManagerInit] + +******************************************************************************/ +int +Cal_BddManagerQuit(Cal_BddManager bddManager) +{ + int i, j; + + if(bddManager == Cal_Nil(Cal_BddManager_t)) return 1; + + for (i=0; i < bddManager->maxDepth; i++){ + for (j=0; j <= bddManager->numVars; j++){ + CalHashTableQuit(bddManager, bddManager->reqQue[i][j]); + } + Cal_MemFree(bddManager->reqQue[i]); + } + + for (i=0; i <= bddManager->numVars; i++){ + CalHashTableQuit(bddManager, bddManager->uniqueTable[i]); + CalNodeManagerQuit(bddManager->nodeManagerArray[i]); + } + + CalCacheTableTwoQuit(bddManager->cacheTable); + Cal_MemFree(bddManager->tempAssociation->varAssociation); + /*CAL_BDD_FREE_REC(bddManager, bddManager->tempAssociation, CalAssociation_t);*/ + Cal_MemFree(bddManager->tempAssociation); + /*CAL_BDD_FREE_REC(bddManager, bddManager->superBlock, Cal_Block_t);*/ + CalFreeBlockRecursively(bddManager->superBlock); + CalAssociationListFree(bddManager); + Cal_MemFree(bddManager->varBdds); + Cal_MemFree(bddManager->indexToId); + Cal_MemFree(bddManager->idToIndex); + Cal_MemFree(bddManager->uniqueTable); + Cal_MemFree(bddManager->reqQue); + Cal_MemFree(bddManager->requestNodeListArray); + Cal_MemFree(bddManager->nodeManagerArray); + CalPageManagerQuit(bddManager->pageManager1); + CalPageManagerQuit(bddManager->pageManager2); + Cal_MemFree(bddManager); + + return 0; +} + +/**Function******************************************************************** + + Synopsis [Sets appropriate fields of BDD Manager.] + + Description [This function is used to set the parameters which are + used to control the reordering process. "reorderingThreshold" + determines the number of nodes below which reordering will NOT be + invoked, "maxForwardedNodes" determines the maximum number of + forwarded nodes which are allowed (at that point the cleanup must be + done), and "repackingThreshold" determines the fraction of the page + utilized below which repacking has to be invoked. These parameters + have different affect on the computational and memory usage aspects + of reordeing. For instance, higher value of "maxForwardedNodes" will + result in process consuming more memory, and a lower value on the + other hand would invoke the cleanup process repeatedly resulting in + increased computation.] + Sets appropriate fields of BDD Manager] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +void +Cal_BddManagerSetParameters(Cal_BddManager bddManager, long + reorderingThreshold, long + maxForwardedNodes, + double repackAfterGCThreshold, + double tableRepackThreshold) +{ + if (reorderingThreshold >= 0){ + bddManager->reorderingThreshold = reorderingThreshold; + } + if (maxForwardedNodes >= 0){ + bddManager->maxForwardedNodes = maxForwardedNodes; + } + if (repackAfterGCThreshold >= 0.0){ + bddManager->repackAfterGCThreshold = repackAfterGCThreshold; + } + if (tableRepackThreshold >= 0.0){ + bddManager->tableRepackThreshold = tableRepackThreshold; + } +} + + +/**Function******************************************************************** + + Synopsis [Returns the number of BDD nodes] + + Description [Returns the number of BDD nodes] + + SideEffects [None] + + SeeAlso [Cal_BddTotalSize] + +******************************************************************************/ +unsigned long +Cal_BddManagerGetNumNodes(Cal_BddManager bddManager) +{ + return bddManager->numNodes; +} + + + +/**Function******************************************************************** + + Synopsis [Creates and returns a new variable at the start of the variable + order.] + + Description [Creates and returns a new variable at the start of the + variable order.] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerCreateNewVarFirst(Cal_BddManager bddManager) +{ + return CalBddGetExternalBdd(bddManager, CalBddManagerCreateNewVar(bddManager, + (Cal_BddIndex_t)0)); +} + +/**Function******************************************************************** + + Synopsis [Creates and returns a new variable at the end of the variable + order.] + + Description [Creates and returns a new variable at the end of the variable + order.] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerCreateNewVarLast(Cal_BddManager bddManager) +{ + return CalBddGetExternalBdd(bddManager, + CalBddManagerCreateNewVar(bddManager, + (Cal_BddIndex_t) + bddManager->numVars)); +} + + + +/**Function******************************************************************** + + Synopsis [Creates and returns a new variable before the specified one in + the variable order.] + + Description [Creates and returns a new variable before the specified one in + the variable order.] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerCreateNewVarBefore(Cal_BddManager bddManager, + Cal_Bdd userBdd) +{ + Cal_Bdd_t calBdd = CalBddGetInternalBdd(bddManager, userBdd); + if (CalBddIsBddConst(calBdd)){ + return Cal_BddManagerCreateNewVarLast(bddManager); + } + else{ + return CalBddGetExternalBdd(bddManager, + CalBddManagerCreateNewVar(bddManager, + CalBddGetBddIndex(bddManager, + calBdd))); + } +} + +/**Function******************************************************************** + + Synopsis [Creates and returns a new variable after the specified one in + the variable order.] + + Description [Creates and returns a new variable after the specified one in + the variable order.] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerCreateNewVarAfter(Cal_BddManager bddManager, + Cal_Bdd userBdd) +{ + Cal_Bdd_t calBdd = CalBddGetInternalBdd(bddManager, userBdd); + if (CalBddIsBddConst(calBdd)){ + return Cal_BddManagerCreateNewVarLast(bddManager); + } + else{ + return CalBddGetExternalBdd(bddManager, + CalBddManagerCreateNewVar(bddManager, + CalBddGetBddIndex(bddManager, calBdd)+1)); + } +} + + +/**Function******************************************************************** + + Synopsis [Returns the variable with the specified index, null if no + such variable exists] + + Description [Returns the variable with the specified index, null if no + such variable exists] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerGetVarWithIndex(Cal_BddManager bddManager, Cal_BddIndex_t index) +{ + if (index >= bddManager->numVars){ + CalBddWarningMessage("Index out of range"); + return (Cal_Bdd) 0; + } + return CalBddGetExternalBdd(bddManager, + bddManager->varBdds[bddManager->indexToId[index]]); +} + +/**Function******************************************************************** + + Synopsis [Returns the variable with the specified id, null if no + such variable exists] + + Description [Returns the variable with the specified id, null if no + such variable exists] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd +Cal_BddManagerGetVarWithId(Cal_BddManager bddManager, Cal_BddId_t id) +{ + if (id <= 0 || id > bddManager->numVars){ + CalBddWarningMessage("Id out of range"); + return (Cal_Bdd) 0; + } + return CalBddGetExternalBdd(bddManager, bddManager->varBdds[id]); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [This function creates and returns a new variable with given + index value.] + + Description [Right now this function does not handle the case when the + package is working in multiprocessor mode. We need to put in the necessary + code later.] + + SideEffects [If the number of variables in the manager exceeds that of value + of numMaxVars, then we need to reallocate various fields of the manager. Also + depending upon the value of "index", idToIndex and indexToId tables would + change.] + +******************************************************************************/ +Cal_Bdd_t +CalBddManagerCreateNewVar(Cal_BddManager_t * bddManager, Cal_BddIndex_t index) +{ + Cal_Bdd_t calBdd; + Cal_BddId_t varId; + int totalNumVars, maxNumVars, i; + CalAssociation_t *association; + + if (bddManager->numVars == CAL_MAX_VAR_ID){ + CalBddFatalMessage("Cannot create any new variable, no more Id left."); + } + + /* + * Get the total number of variables. If the index is more than the total + * number of variables, then report error. + */ + totalNumVars = bddManager->numVars; + + if (index > totalNumVars){ + CalBddFatalMessage("The variable index out of range"); + } + + + /* + * Create a new variable in the manager which contains this index. + * This might lead to change in the id->index, and index->id + * for other managers. + */ + + /* + * If the number of variables is equal to the maximum number of variables + * then reallocate memory. + */ + if (bddManager->numVars == bddManager->maxNumVars){ + int oldMaxNumVars; + CalAssociation_t *p; + + oldMaxNumVars = bddManager->maxNumVars; + if ((maxNumVars = 2*oldMaxNumVars) > CAL_MAX_VAR_ID){ + maxNumVars = CAL_MAX_VAR_ID; + } + bddManager->maxNumVars = maxNumVars; + bddManager->varBdds = Cal_MemRealloc(Cal_Bdd_t, + bddManager->varBdds, maxNumVars+1); + + bddManager->nodeManagerArray = Cal_MemRealloc(CalNodeManager_t *, + bddManager->nodeManagerArray, + maxNumVars+1); + + bddManager->idToIndex = Cal_MemRealloc(Cal_BddIndex_t, bddManager->idToIndex, + maxNumVars+1); + + bddManager->indexToId = Cal_MemRealloc(Cal_BddIndex_t, bddManager->indexToId, + maxNumVars); + + bddManager->uniqueTable = Cal_MemRealloc(CalHashTable_t *, + bddManager->uniqueTable, maxNumVars+1); + + for (i=0; imaxDepth; i++){ + bddManager->reqQue[i] = Cal_MemRealloc(CalHashTable_t *, bddManager->reqQue[i], + maxNumVars+1); + } + bddManager->tempAssociation->varAssociation = + Cal_MemRealloc(Cal_Bdd_t, bddManager->tempAssociation->varAssociation, + maxNumVars+1); + /* CHECK LOOP INDICES */ + for(i = oldMaxNumVars+1; i < maxNumVars+1; i++){ + bddManager->tempAssociation->varAssociation[i] = bddManager->bddNull; + } + for(p = bddManager->associationList; p; p = p->next){ + p->varAssociation = + Cal_MemRealloc(Cal_Bdd_t, p->varAssociation, maxNumVars+1); + /* CHECK LOOP INDICES */ + for(i = oldMaxNumVars+1; i < maxNumVars+1; i++){ + p->varAssociation[i] = bddManager->bddNull; + } + } + } + + /* If the variable has been created in the middle, shift the indices. */ + if (index != bddManager->numVars){ + for (i=0; inumVars; i++){ + if (bddManager->idToIndex[i+1] >= index){ + bddManager->idToIndex[i+1]++; + } + } + } + + /* Fix indexToId table */ + for (i=bddManager->numVars; i>index; i--){ + bddManager->indexToId[i] = bddManager->indexToId[i-1]; + } + + for(association = bddManager->associationList; association; + association = + association->next){ + if (association->lastBddIndex >= index){ + association->lastBddIndex++; + } + } + if (bddManager->tempAssociation->lastBddIndex >= index){ + bddManager->tempAssociation->lastBddIndex++; + } + + bddManager->numVars++; + varId = bddManager->numVars; + + bddManager->idToIndex[varId] = index; + bddManager->indexToId[index] = varId; + + bddManager->nodeManagerArray[varId] = + CalNodeManagerInit(bddManager->pageManager2); + bddManager->uniqueTable[varId] = + CalHashTableInit(bddManager, varId); + + /* insert node in the uniqueTableForId */ + CalHashTableAddDirectAux(bddManager->uniqueTable[varId], + bddManager->bddOne, bddManager->bddZero, &calBdd); + CalBddPutRefCount(calBdd, CAL_MAX_REF_COUNT); + bddManager->varBdds[varId] = calBdd; + + bddManager->numNodes++; + +#ifdef __OLD__ + /* initialize req_que_for_id */ + bddManager->reqQue[varId] = Cal_MemAlloc(CalHashTable_t*, bddManager->maxDepth); + for (i=0; imaxDepth; i++){ + bddManager->reqQue[varId][i] = CalHashTableInit(bddManager, varId); + } +#endif + + /* initialize req_que_for_id */ + for (i=0; imaxDepth; i++){ + bddManager->reqQue[i][varId] = + CalHashTableInit(bddManager, varId); + } + CalBddShiftBlock(bddManager, bddManager->superBlock, (long)index); + return calBdd; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddDefaultTransformFn( + Cal_BddManager_t * bddManager, + CalAddress_t value1, + CalAddress_t value2, + CalAddress_t * result1, + CalAddress_t * result2, + Cal_Pointer_t pointer) +{ + if (!value2) + /* Will be a carry when taking 2's complement of value2. Thus, */ + /* take 2's complement of high part. */ + value1= -(long)value1; + else + { + value2= -(long)value2; + value1= ~value1; + } + *result1=value1; + *result2=value2; +} + +#ifdef CALBDDMANAGER + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +CalBddManagerPrint(Cal_BddManager_t *bddManager) +{ + int i; + CalHashTable_t *uniqueTableForId; + printf("##################### BDD MANAGER #####################\n"); + for(i = 1; i < bddManager->numVars; i++){ + uniqueTableForId = bddManager->uniqueTable[i]; + CalHashTablePrint(uniqueTableForId); + } + fflush(stdout); + return 0; +} + + +main(argc, argv) +int argc; +char **argv; +{ + Cal_Bdd_t n; + Cal_BddManager_t *manager; + + manager = CalBddManagerInit(argc, argv); + n = CalBddManagerCreateVariable(bddManager); + CalBddFunctionPrint(n); + n = CalBddManagerGetVariable(bddManager, 0); + CalBddFunctionPrint(n); +} +#endif /* CALBDDMANAGER */ + +#ifdef __GC__ +main(argc, argv) +int argc; +char **argv; +{ + Cal_BddManager_t *manager; + Cal_Bdd_t vars[256]; + Cal_Bdd_t function, tempFunction; + int i; + int numVars; + + if (argc >= 2) + numVars = atoi(argv[1]); + else + numVars = 3; + + manager = Cal_BddManagerInit(); + + for (i = 0; i < numVars; i++){ + vars[i] = Cal_BddManagerCreateNewVarLast(bddManager); + } + + function = vars[0]; + for (i = 1; i < numVars - 1; i++){ + tempFunction = Cal_BddITE(bddManager, vars[i], vars[i+1], function); + Cal_BddFree(function); + function = tempFunction; + /*fprintf(stdout, "i = %d\n", i); + unique_table_write(stdout, CalBddManager->unique_table); + */ + } + fprintf(stdout, "\n******************Before Free****************\n"); + for (i = 1; i <= numVars; i++){ + CalHashTablePrint(bddManager->uniqueTable[i]); + } + Cal_BddFree(function); + fprintf(stdout, "\n****************After Free****************\n"); + for (i = 1; i <= numVars; i++){ + CalHashTablePrint(bddManager->uniqueTable[i]); + } + Cal_BddManagerGC(bddManager); + fprintf(stdout, "\n****************After GC****************\n"); + for (i = 1; i <= numVars; i++){ + CalHashTablePrint(bddManager->uniqueTable[i]); + } +} +#endif diff --git a/calBddOp.c b/calBddOp.c new file mode 100644 index 0000000..5e88f7b --- /dev/null +++ b/calBddOp.c @@ -0,0 +1,1015 @@ +/**CFile*********************************************************************** + + FileName [calBddOp.c] + + PackageName [cal] + + Synopsis [Routines for performing simple boolean operations on a + pair of BDDs or on an array of pair of BDDs or on an array of BDDs.] + + Description [The "cal" specific routines are "Cal_BddPairwiseAnd/Or", + "Cal_BddMultiwayAnd/Or".] + + SeeAlso [optional] + + Author [Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddOp.c,v 1.1.1.3 1998/05/04 00:58:52 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t * BddArrayOpBF(Cal_BddManager_t * bddManager, Cal_Bdd_t* bddArray, int numFunction, CalOpProc_t calOpProc); +static Cal_Bdd_t BddMultiwayOp(Cal_BddManager_t * bddManager, Cal_Bdd_t * calBddArray, int numBdds, CalOpProc_t op); +static void BddArrayToRequestNodeListArray(Cal_BddManager_t * bddManager, Cal_Bdd_t * calBddArray, int numBdds); +static int CeilLog2(int number); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical AND of argument BDDs] + + Description [Returns the BDD for logical AND of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddAnd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + Cal_Bdd_t F, G; + + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpAnd, F, G); + } + else { + return (Cal_Bdd)0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical NAND of argument BDDs] + + Description [Returns the BDD for logical NAND of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddNand( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd_t F, G; + Cal_Bdd userResult; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpNand, F, G); + } + else{ + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical OR of argument BDDs] + + Description [Returns the BDD for logical OR of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddOr(Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd_t F, G; + Cal_Bdd userResult; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpOr, F, G); + } + else{ + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical NOR of argument BDDs] + + Description [Returns the BDD for logical NOR of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddNor(Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + Cal_Bdd_t F, G; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpOr, F, G); + CalBddNot(result, result); + } + else{ + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical exclusive OR of argument BDDs] + + Description [Returns the BDD for logical exclusive OR of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddXor(Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + Cal_Bdd_t F, G; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpXor, F, G); + } + else{ + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns the BDD for logical exclusive NOR of argument BDDs] + + Description [Returns the BDD for logical exclusive NOR of f and g] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd +Cal_BddXnor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + Cal_Bdd_t F, G; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + F = CalBddGetInternalBdd(bddManager, fUserBdd); + G = CalBddGetInternalBdd(bddManager, gUserBdd); + result = CalBddOpBF(bddManager, CalOpXor, F, G); + CalBddNot(result, result); + } + else{ + return (Cal_Bdd) 0; + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; +} + +/**Function******************************************************************** + + Synopsis [Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array] + + Description [Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array] + + SideEffects [None] + + SeeAlso [Cal_BddPairwiseOr] + +******************************************************************************/ +Cal_Bdd * +Cal_BddPairwiseAnd(Cal_BddManager bddManager, Cal_Bdd *userBddArray) +{ + int i, num; + Cal_Bdd_t *bddArray; + Cal_Bdd_t *resultArray; + Cal_Bdd userBdd; + Cal_Bdd *userResultArray; + + for (num = 0; (userBdd = userBddArray[num]); num++){ + if (CalBddPreProcessing(bddManager, 1, userBdd) == 0){ + return Cal_Nil(Cal_Bdd); + } + } + if ((num == 0) || (num%2 != 0)){ + fprintf(stdout,"Odd number of arguments passed to array AND\n"); + return Cal_Nil(Cal_Bdd); + } + bddArray = Cal_MemAlloc(Cal_Bdd_t, num); + for (i = 0; i < num; i++){ + bddArray[i] = CalBddGetInternalBdd(bddManager, userBddArray[i]); + } + resultArray = BddArrayOpBF(bddManager, bddArray, num, CalOpAnd); + userResultArray = Cal_MemAlloc(Cal_Bdd, num/2); + for (i=0; ireqQue; + + /* ReqQueInsertUsingReqListArray */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + for(requestNode = requestNodeListArray[pipeDepth]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, F); + CalRequestIsForwardedTo(F); + CalRequestNodeGetG(requestNode, G); + CalRequestIsForwardedTo(G); + if((*calOpProc)(bddManager, F, G, &result) == 0){ + CalBddNormalize(F, G); + CalBddGetMinId2(bddManager, F, G, bddId); + CalHashTableFindOrAdd(reqQueAtPipeDepth[bddId], F, G, &result); + } + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + } + } + + /* ReqQueApply */ + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + hashTable = reqQueAtPipeDepth[bddId]; + if(hashTable->numEntries){ + CalHashTableApply(bddManager, hashTable, reqQueAtPipeDepth, calOpProc); + } + } + } + +#ifdef COMPUTE_MEMORY_OVERHEAD + { + calNumEntriesAfterApply = 0; + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + hashTable = reqQueAtPipeDepth[bddId]; + calNumEntriesAfterApply += hashTable->numEntries; + } + } + } +#endif + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + hashTable = reqQue[pipeDepth][bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + } + +#ifdef COMPUTE_MEMORY_OVERHEAD + { + CalRequestNode_t *requestNode; + calNumEntriesAfterReduce = 0; + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + CalRequestNode_t *next; + Cal_BddId_t bddId; + bddId = bddManager->indexToId[bddIndex]; + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + hashTable = reqQue[pipeDepth][bddId]; + for (requestNode = hashTable->requestNodeList; + requestNode != Cal_Nil(CalRequestNode_t); requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + calNumEntriesAfterReduce++; + } + } + } + calAfterReduceToAfterApplyNodesRatio = + ((double)calNumEntriesAfterReduce)/((double)calNumEntriesAfterApply); + calAfterReduceToUniqueTableNodesRatio = + ((double)calNumEntriesAfterReduce)/((double)bddManager->numNodes); + } +#endif + + /* ReqListArrayReqForward */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + for(requestNode = requestNodeListArray[pipeDepth]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, result); + CalRequestIsForwardedTo(result); + Cal_Assert(CalBddIsForwarded(result) == 0); + CalRequestNodePutThenRequest(requestNode, result); + } + } + + /* ReqQueCleanUp */ + for(pipeDepth = 0; pipeDepth < bddManager->depth; pipeDepth++){ + reqQueAtPipeDepth = reqQue[pipeDepth]; + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueAtPipeDepth[bddId]); + } + } +} + +/**Function******************************************************************** + + Synopsis [Internal routine to compute a logical operation on a pair of BDDs] + + Description [Internal routine to compute a logical operation on a pair of BDDs] + + SideEffects [None] + +******************************************************************************/ +Cal_Bdd_t +CalBddOpBF( + Cal_BddManager_t * bddManager, + CalOpProc_t calOpProc, + Cal_Bdd_t F, + Cal_Bdd_t G) +{ + Cal_Bdd_t result; + Cal_BddId_t minId, bddId; + /*Cal_BddIndex_t minIndex; Commented out because of the problem on alpha*/ + int minIndex; + int bddIndex; + CalHashTable_t *hashTable, **hashTableArray, *uniqueTableForId; + + if (calOpProc(bddManager, F, G, &result)){ + return result; + } + CalBddGetMinIdAndMinIndex(bddManager, F, G, minId, minIndex); + hashTableArray = bddManager->reqQue[0]; + CalHashTableFindOrAdd(hashTableArray[minId], F, G, &result); + + /* ReqQueApply */ + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = hashTableArray[bddId]; + if(hashTable->numEntries){ + CalHashTableApply(bddManager, hashTable, hashTableArray, calOpProc); + } + } +#ifdef COMPUTE_MEMORY_OVERHEAD + { + calNumEntriesAfterApply = 0; + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = hashTableArray[bddId]; + calNumEntriesAfterApply += hashTable->numEntries; + } + } +#endif + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = hashTableArray[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + CalRequestIsForwardedTo(result); + +#ifdef COMPUTE_MEMORY_OVERHEAD + { + CalRequestNode_t *requestNode; + calNumEntriesAfterReduce = 0; + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + CalRequestNode_t *next; + Cal_BddId_t bddId; + + bddId = bddManager->indexToId[bddIndex]; + hashTable = hashTableArray[bddId]; + for (requestNode = hashTable->requestNodeList; requestNode != + Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + calNumEntriesAfterReduce++; + } + } + calAfterReduceToAfterApplyNodesRatio = + ((double)calNumEntriesAfterReduce)/((double)calNumEntriesAfterApply); + calAfterReduceToUniqueTableNodesRatio = + ((double)calNumEntriesAfterReduce)/((double)bddManager->numNodes); + } +#endif + + /* Clean up */ + for(bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(hashTableArray[bddId]); + } + return result; +} + + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Internal common routine for Cal_BddPairwiseAnd and Cal_BddPairwiseOr] + + SideEffects [None] + +******************************************************************************/ +static Cal_Bdd_t * +BddArrayOpBF(Cal_BddManager_t * bddManager, Cal_Bdd_t* bddArray, + int numFunction, CalOpProc_t calOpProc) +{ + Cal_BddId_t minId, bddId; + /*Cal_BddIndex_t minIndex = 0;*/ + int minIndex = 0; + int bddIndex; + CalHashTable_t *hashTable, **hashTableArray, *uniqueTableForId; + Cal_Bdd_t F, G, result; + int numPairs = numFunction/2; + Cal_Bdd_t *resultArray = Cal_MemAlloc(Cal_Bdd_t, numPairs); + int i; + + hashTableArray = bddManager->reqQue[0]; + for (i=0; inumVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = hashTableArray[bddId]; + if(hashTable->numEntries){ + CalHashTableApply(bddManager, hashTable, hashTableArray, calOpProc); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = hashTableArray[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + for (i=0; inumVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(hashTableArray[bddId]); + } + return resultArray; +} + +/**Function******************************************************************** + + Synopsis [Internal routine for multiway operations] + + Description [Internal routine for multiway operations] + + SideEffects [None] + +******************************************************************************/ +static Cal_Bdd_t +BddMultiwayOp(Cal_BddManager_t * bddManager, Cal_Bdd_t * calBddArray, + int numBdds, CalOpProc_t op) +{ + int pipeDepth; + CalRequestNode_t *requestNode; + Cal_Bdd_t result; + + BddArrayToRequestNodeListArray(bddManager, calBddArray, numBdds); + CalRequestNodeListArrayOp(bddManager, bddManager->requestNodeListArray, op); + for(pipeDepth = 0; pipeDepth < bddManager->depth-1; pipeDepth++){ + CalRequestNode_t *next; + for(requestNode = bddManager->requestNodeListArray[pipeDepth]; + requestNode != Cal_Nil(CalRequestNode_t); requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], + requestNode); + } + bddManager->requestNodeListArray[pipeDepth] = + Cal_Nil(CalRequestNode_t); + } + requestNode = bddManager->requestNodeListArray[bddManager->depth-1]; + bddManager->requestNodeListArray[bddManager->depth-1] = + Cal_Nil(CalRequestNode_t); + CalRequestNodeGetThenRequest(requestNode, result); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], + requestNode); + return result; +} + + +/**Function******************************************************************** + + Synopsis [Converts an array of BDDs to a list of requests representing BDD + pairs] + + Description [Converts an array of BDDs to a list of requests representing BDD] + + SideEffects [None] + +******************************************************************************/ +static void +BddArrayToRequestNodeListArray( + Cal_BddManager_t * bddManager, + Cal_Bdd_t * calBddArray, + int numBdds) +{ + int i; + Cal_Bdd_t lastBdd; + CalRequestNode_t *even, *odd, *requestNode, *requestNodeList, *head; + + bddManager->depth = CeilLog2(numBdds); + if (bddManager->depth > 10){ + CalBddFatalMessage("Don't be stooopid\n, Use lesser depth\n"); + } + + if (bddManager->depth > bddManager->maxDepth){ + /* Need to reallocate the memory for reqQue and + requestNodeListArray */ + int oldMaxDepth = bddManager->maxDepth; + bddManager->maxDepth = bddManager->depth; + + for (i=0; imaxDepth; i++){ + bddManager->requestNodeListArray[i] = Cal_Nil(CalRequestNode_t); + } + + bddManager->reqQue = Cal_MemRealloc(CalHashTable_t **, bddManager->reqQue, + bddManager->maxDepth); + for (i=oldMaxDepth; imaxDepth; i++){ + int j; + bddManager->reqQue[i] = Cal_MemAlloc(CalHashTable_t *, bddManager->maxNumVars+1); + for (j=0; jnumVars+1; j++){ + bddManager->reqQue[i][j] = CalHashTableInit(bddManager, j); + } + } + } + lastBdd = bddManager->bddNull; + if (numBdds%2 != 0){/* Odd number of Bdd's */ + lastBdd = calBddArray[numBdds-1]; + } + requestNodeList = bddManager->requestNodeListArray[0]; + for (i=0; inodeManagerArray[0], requestNode); + CalRequestNodePutF(requestNode, calBddArray[2*i]); + CalRequestNodePutG(requestNode, calBddArray[2*i+1]); + CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + requestNodeList = requestNode; + } + bddManager->requestNodeListArray[0] = requestNodeList; + + for (i=1; idepth; i++){ + requestNodeList = bddManager->requestNodeListArray[i]; + head = bddManager->requestNodeListArray[i-1]; + while ((odd = head) && (even = head->nextBddNode)){ + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], requestNode); + /* + * We don't have to worry about the Id's attached with + * the requestNode or with the then and else part of it. + */ + CalRequestNodePutThenRequestNode(requestNode, odd); + CalRequestNodePutElseRequestNode(requestNode, even); + CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + requestNodeList = requestNode; + head = CalRequestNodeGetNextRequestNode(even); + } + if (odd != Cal_Nil(CalRequestNode_t)){/* There is an odd node at this + level */ + if (CalBddIsBddNull(bddManager,lastBdd)){ /* There are no odd nodes + * from previous levels, so + * make this an odd node. + */ + CalBddPutBddNode(lastBdd, odd); + } + else{ /* There exists an odd node, so make a pair now. */ + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], requestNode); + CalRequestNodePutThenRequestNode(requestNode, odd); + CalRequestNodePutElseRequest(requestNode, lastBdd); + CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + lastBdd = bddManager->bddNull; + requestNodeList = requestNode; + } + } + bddManager->requestNodeListArray[i] = requestNodeList; + } +} + + + +/**Function******************************************************************** + + Synopsis [Returns the smallest integer greater than or equal to log2 of a + number] + + Description [Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1)] + + SideEffects [None] + +******************************************************************************/ +static int +CeilLog2( + int number) +{ + int num, count; + for (num=number, count=0; num > 1; num >>= 1, count++); + if ((1 << count) != number) count++; + return count; +} + + + + + + diff --git a/calBddReorderTest.c b/calBddReorderTest.c new file mode 100644 index 0000000..6bd2e51 --- /dev/null +++ b/calBddReorderTest.c @@ -0,0 +1,253 @@ +/**CFile*********************************************************************** + + FileName [calBddReorderTest.c] + + PackageName [cal] + + Synopsis [A test routine for checking the functionality of + dynamic reordering.] + + Description [] + + SeeAlso [optional] + + Author [Wilsin Gosti (wilsin@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddReorderTest.c,v 1.1.1.4 1998/05/04 00:58:52 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static CalAddress_t asDoubleSpace[2]; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +#define CalBddReorderBddIsForwarded(bdd) \ + (CAL_BDD_POINTER(CalBddGetElseBddNode(bdd)) == FORWARD_FLAG) + +#define CalBddReorderBddNodeIsForwarded(bddNode) \ + (CAL_BDD_POINTER(CalBddNodeGetElseBddNode(bddNode)) == FORWARD_FLAG) + +#define CalBddReorderForward(bdd) \ +{ \ + CalBddNode_t *_bddNode, *_bddNodeTagged; \ + _bddNodeTagged = CalBddGetBddNode(bdd); \ + _bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + (bdd).bddId = _bddNode->thenBddId; \ + (bdd).bddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(_bddNodeTagged))); \ +} + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static double cpuTime(); +static long elapsedTime(); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +main(int argc, char **argv) +{ + Cal_Bdd expected; + Cal_Bdd a[100]; + Cal_Bdd temp1; + Cal_Bdd temp2; + Cal_Bdd b, c, d, e, f, g, result; + Cal_BddManager_t *bddManager; + CalBddNode_t *bddNode; + int i; + int numVars; + int siftFlag = 0; + + if (argc == 1) { + numVars = 5; + } else if (argc >= 2) { + numVars = atoi(argv[1]); + } + if (argc == 3) { + siftFlag = 1; + } + + bddManager = Cal_BddManagerInit(); + + for (i = 0; i < 2 * numVars; i++) { + a[i] = Cal_BddManagerCreateNewVarLast(bddManager); + } + + result = Cal_BddZero(bddManager); + for (i = 0; i < numVars; i++) { + temp1 = Cal_BddAnd(bddManager, a[i], a[numVars + i]); + temp2 = Cal_BddOr(bddManager, result, temp1); + Cal_BddFree(bddManager, temp1); + Cal_BddFree(bddManager, result); + result = temp2; + } + Cal_BddManagerGC(bddManager); + Cal_BddStats(bddManager, stdout); + cpuTime(); + elapsedTime(); + printf("%%%%%%%%%%%% Reordering %%%%%%%%%%%%%%%%%%%\n"); + if (siftFlag){ + printf("Using Sift Technique\n"); + Cal_BddDynamicReordering(bddManager, CAL_REORDER_SIFT); + } + else{ + printf("Using Window Technique\n"); + Cal_BddDynamicReordering(bddManager, CAL_REORDER_WINDOW); + } + Cal_BddReorder(bddManager); + printf("CPU time: %-8.2f\t Elapsed Time = %-10ld\n", cpuTime(), elapsedTime()); + printf("%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%\n"); + Cal_BddManagerGC(bddManager); + Cal_BddStats(bddManager, stdout); + /*Cal_BddFunctionPrint(bddManager, result, "Result");*/ + temp1 = Cal_BddZero(bddManager); + for (i = 0; i < numVars; i++) { + temp2 = Cal_BddAnd(bddManager, a[i], a[numVars + i]); + expected = Cal_BddOr(bddManager, temp1, temp2); + Cal_BddFree(bddManager, temp1); + Cal_BddFree(bddManager, temp2); + temp1 = expected; + } + + if (!Cal_BddIsEqual(bddManager, result, expected)) { + printf("ERROR: BDDs are not equal\n"); + Cal_BddFunctionPrint(bddManager, result, "Result"); + Cal_BddFunctionPrint(bddManager, expected, "Expected"); + } + printf("\n%%%%%%BDDs are equal\n"); + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + Cal_BddManagerGC(bddManager); + Cal_BddStats(bddManager, stdout); + Cal_BddManagerQuit(bddManager); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static double +cpuTime() +{ + static double timeNew, timeOld; + struct rusage rusage; + static flag = 0; + + getrusage(RUSAGE_SELF, &rusage); + if (flag == 0){ + timeOld = timeNew = rusage.ru_utime.tv_sec+ + ((double)rusage.ru_utime.tv_usec)/1000000; + flag = 1; + } + else { + timeOld = timeNew; + timeNew = rusage.ru_utime.tv_sec+ + ((float)rusage.ru_utime.tv_usec)/1000000; + } + return timeNew - timeOld; +} + +/**Function******************************************************************** + + Synopsis [Computes the time.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static long +elapsedTime() +{ + static long time_new, time_old; + struct timeval t; + struct timezone tz; + static flag = 0; + + gettimeofday(&t, &tz); + if (flag == 0){ + time_old = time_new = t.tv_sec; + flag = 1; + } + else { + time_old = time_new; + time_new = t.tv_sec; + } + return time_new-time_old; +} diff --git a/calBddSatisfy.c b/calBddSatisfy.c new file mode 100644 index 0000000..0a094ae --- /dev/null +++ b/calBddSatisfy.c @@ -0,0 +1,373 @@ +/**CFile*********************************************************************** + + FileName [calBddSatisfy.c] + + PackageName [cal] + + Synopsis [Routines for BDD satisfying valuation.] + + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddSatisfy.c,v 1.1.1.3 1998/05/04 00:58:53 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t BddSatisfyStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f); +static Cal_Bdd_t BddSatisfySupportStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_BddId_t * support); +static int IndexCmp(const void * p1, const void * p2); +static double BddSatisfyingFractionStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, CalHashTable_t * hashTable); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Name [Cal_BddSatisfy] + + Synopsis [Returns a BDD which implies f, true for + some valuation on which f is true, and which has at most + one node at each level] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd +Cal_BddSatisfy(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + Cal_Bdd_t f; + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + if(CalBddIsBddZero(bddManager, f)){ + CalBddWarningMessage("Cal_BddSatisfy: argument is false"); + return (fUserBdd); + } + f = BddSatisfyStep(bddManager, f); + return CalBddGetExternalBdd(bddManager, f); + } + return (Cal_Bdd) 0; +} + + +/**Function******************************************************************** + + Name [Cal_BddSatisfySupport] + + Synopsis [Returns a special cube contained in f.] + + Description [The returned BDD which implies f, is true for some valuation on + which f is true, which has at most one node at each level, + and which has exactly one node corresponding to each variable + which is associated with something in the current variable + association.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd +Cal_BddSatisfySupport(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + Cal_BddId_t *support, *p; + long i; + Cal_Bdd_t result; + Cal_Bdd_t f; + + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + if(CalBddIsBddZero(bddManager, f)){ + CalBddWarningMessage("Cal_BddSatisfySupport: argument is false"); + return (fUserBdd); + } + support = Cal_MemAlloc(Cal_BddId_t, bddManager->numVars+1); + for(i = 1, p = support; i <= bddManager->numVars; i++){ + if(!CalBddIsBddNull(bddManager, + bddManager->currentAssociation->varAssociation[i])){ + *p = bddManager->idToIndex[i]; + ++p; + } + } + *p = 0; + qsort(support, (unsigned)(p - support), sizeof(Cal_BddId_t), IndexCmp); + while(p != support){ + --p; + *p = bddManager->indexToId[*p]; + } + result = BddSatisfySupportStep(bddManager, f, support); + Cal_MemFree(support); + return CalBddGetExternalBdd(bddManager, result); + } + return (Cal_Bdd) 0; +} + +/**Function******************************************************************** + + Synopsis [Returns the fraction of valuations which make f true. (Note that + this fraction is independent of whatever set of variables f is supposed to be + a function of)] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +double +Cal_BddSatisfyingFraction(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + double fraction; + CalHashTable_t *hashTable; + Cal_Bdd_t f; + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + hashTable = CalHashTableOneInit(bddManager, sizeof(double)); + fraction = BddSatisfyingFractionStep(bddManager, f, hashTable); + CalHashTableOneQuit(hashTable); + return fraction; + } + return 0.0; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Name [BddSatisfyStep] + + Synopsis [Returns a BDD which implies f, is true for some valuation + on which f is true, and which has at most one node at each level] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddSatisfyStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f) +{ + Cal_Bdd_t tempBdd; + Cal_Bdd_t result; + + if(CalBddIsBddConst(f)){ + return (f); + } + CalBddGetThenBdd(f, tempBdd); + if(CalBddIsBddZero(bddManager, tempBdd)){ + CalBddGetElseBdd(f, tempBdd); + tempBdd = BddSatisfyStep(bddManager, tempBdd); + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[CalBddGetBddId(f)], + CalBddZero(bddManager), tempBdd, &result)){ + CalBddIcrRefCount(tempBdd); + } + } + else{ + tempBdd = BddSatisfyStep(bddManager, tempBdd); + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[CalBddGetBddId(f)], + tempBdd, CalBddZero(bddManager), &result)){ + CalBddIcrRefCount(tempBdd); + } + } + return (result); +} + + +/**Function******************************************************************** + + Name [BddSatisfySupportStep] + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddSatisfySupportStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + Cal_BddId_t * support) +{ + Cal_Bdd_t tempBdd; + Cal_Bdd_t result; + + if(!*support){ + return BddSatisfyStep(bddManager, f); + } + if(CalBddGetBddIndex(bddManager, f) <= bddManager->idToIndex[*support]){ + if(CalBddGetBddId(f) == *support){ + ++support; + } + CalBddGetThenBdd(f, tempBdd); + if(CalBddIsBddZero(bddManager, tempBdd)){ + CalBddGetElseBdd(f, tempBdd); + tempBdd = BddSatisfySupportStep(bddManager, tempBdd, support); + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[CalBddGetBddId(f)], + CalBddZero(bddManager), tempBdd, &result)){ + CalBddIcrRefCount(tempBdd); + } + } + else{ + tempBdd = BddSatisfySupportStep(bddManager, tempBdd, support); + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[CalBddGetBddId(f)], + tempBdd, CalBddZero(bddManager), &result)){ + CalBddIcrRefCount(tempBdd); + } + } + } + else{ + tempBdd = BddSatisfySupportStep(bddManager, f, support+1); + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[*support], + CalBddZero(bddManager), tempBdd, &result)){ + CalBddIcrRefCount(tempBdd); + } + } + return (result); +} + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +IndexCmp(const void * p1, const void * p2) +{ + Cal_BddIndex_t i1, i2; + + i1 = *(Cal_BddId_t *)p1; + i2 = *(Cal_BddId_t *)p2; + if(i1 < i2){ + return (-1); + } + if(i1 > i2){ + return (1); + } + return (0); +} + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static double +BddSatisfyingFractionStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + CalHashTable_t * hashTable) +{ + double *resultPtr, result; + Cal_Bdd_t thenBdd, elseBdd; + + if(CalBddIsBddConst(f)){ + if(CalBddIsBddZero(bddManager, f)){ + return 0.0; + } + return 1.0; + } + if(CalHashTableOneLookup(hashTable, f, (char **)&resultPtr)){ + return (*resultPtr); + } + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + result = + 0.5 * BddSatisfyingFractionStep(bddManager, thenBdd, hashTable) + + 0.5 * BddSatisfyingFractionStep(bddManager, elseBdd, hashTable); + CalHashTableOneInsert(hashTable, f, (char *)&result); + return (result); +} + diff --git a/calBddSize.c b/calBddSize.c new file mode 100644 index 0000000..be5046d --- /dev/null +++ b/calBddSize.c @@ -0,0 +1,629 @@ +/**CFile*********************************************************************** + + FileName [calBddSize.c] + + PackageName [cal] + + Synopsis [BDD size and profile routines] + + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long. + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddSize.c,v 1.1.1.3 1998/05/04 00:58:53 hsv Exp $] + +******************************************************************************/ +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef int (*CountFn_t)(Cal_Bdd_t); + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void BddMarkBdd(Cal_Bdd_t f); +static int BddCountNoNodes(Cal_Bdd_t f); +static int BddCountNodes(Cal_Bdd_t f); +static long BddSizeStep(Cal_Bdd_t f, CountFn_t countFn); +static void BddProfileStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, long * levelCounts, CountFn_t countFn); +static void BddHighestRefStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, CalHashTable_t * h); +static void BddDominatedStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, long * funcCounts, CalHashTable_t * h); + +/**AutomaticEnd***************************************************************/ + +static +int (*(countingFns[]))(Cal_Bdd_t) = +{ + BddCountNoNodes, + BddCountNodes, +}; + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Returns the number of nodes in f when negout is nonzero. If + negout is zero, we pretend that the BDDs don't have negative-output pointers.] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +long +Cal_BddSize(Cal_BddManager bddManager, Cal_Bdd fUserBdd, int negout) +{ + Cal_Bdd_t f, g; + + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + g = CalBddOne(bddManager); + CalBddPutMark(g, 0); + BddMarkBdd(f); + return BddSizeStep(f, countingFns[!negout]); + } + return (0l); +} + + +/**Function******************************************************************** + + Synopsis [The routine is like Cal_BddSize, but takes a null-terminated + array of BDDs and accounts for sharing of nodes.] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +long +Cal_BddSizeMultiple(Cal_BddManager bddManager, Cal_Bdd *fUserBddArray, + int negout) +{ + long size; + Cal_Bdd_t *f; + Cal_Bdd_t g; + Cal_Bdd_t *fArray; + int i, j; + Cal_Bdd userBdd; + + if (CalBddArrayPreProcessing(bddManager, fUserBddArray) == 0){ + return -1; + } + + for(i = 0; (userBdd = fUserBddArray[i]); ++i); + + fArray = Cal_MemAlloc(Cal_Bdd_t, i+1); + for (j=0; j < i; j++){ + fArray[j] = CalBddGetInternalBdd(bddManager,fUserBddArray[j]); + } + fArray[j] = bddManager->bddNull; + + g = CalBddOne(bddManager); + CalBddPutMark(g, 0); + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + BddMarkBdd(*f); + } + size = 0l; + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + size += BddSizeStep(*f, countingFns[!negout]); + } + Cal_MemFree(fArray); + return size; +} + +/**Function******************************************************************** + + Synopsis [Returns a "node profile" of f, i.e., the number of nodes at each + level in f.] + + Description [negout is as in Cal_BddSize. levelCounts should be an array of + size Cal_BddVars(bddManager)+1 to hold the profile.] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddProfile(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + long * levelCounts, int negout) +{ + Cal_BddIndex_t i; + Cal_Bdd_t f, g; + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + for(i = 0; i <= bddManager->numVars; i++){ + levelCounts[i] = 0l; + } + g = CalBddOne(bddManager); + CalBddPutMark(g, 0); + BddMarkBdd(f); + BddProfileStep(bddManager, f, levelCounts, countingFns[!negout]); + } +} + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddProfileMultiple(Cal_BddManager bddManager, Cal_Bdd *fUserBddArray, + long * levelCounts, int negout) +{ + Cal_Bdd_t *f, *fArray; + Cal_Bdd_t g; + int i, j; + + Cal_Bdd userBdd; + + CalBddArrayPreProcessing(bddManager, fUserBddArray); + + for(i = 0; (userBdd = fUserBddArray[i]); ++i); + + fArray = Cal_MemAlloc(Cal_Bdd_t, i+1); + for (j=0; j < i; j++){ + fArray[j] = CalBddGetInternalBdd(bddManager,fUserBddArray[j]); + } + fArray[j] = bddManager->bddNull; + + for(i = 0; i <= bddManager->numVars; i++){ + levelCounts[i] = 0l; + } + g = CalBddOne(bddManager); + CalBddPutMark(g, 0); + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + BddMarkBdd(*f); + } + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + BddProfileStep(bddManager, *f, levelCounts, countingFns[!negout]); + } + Cal_MemFree(fArray); +} + + +/**Function******************************************************************** + + Synopsis [Returns a "function profile" for f.] + + Description [The nth entry of the function + profile array is the number of subfunctions of f which may be obtained by + restricting the variables whose index is less than n. An entry of zero + indicates that f is independent of the variable with the corresponding index.] + + SideEffects [] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddFunctionProfile(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + long * funcCounts) +{ + long i; + Cal_BddIndex_t j; + CalHashTable_t *h; + Cal_Bdd_t f; + + /* The number of subfunctions obtainable by restricting the */ + /* variables of index < n is the number of subfunctions whose top */ + /* variable has index n plus the number of subfunctions obtainable */ + /* by restricting the variables of index < n+1 minus the number of */ + /* these latter subfunctions whose highest reference is by a node at */ + /* level n. */ + /* The strategy will be to start with the number of subfunctions */ + /* whose top variable has index n. We compute the highest level at */ + /* which each subfunction is referenced. Then we work bottom up; at */ + /* level n we add in the result from level n+1 and subtract the */ + /* number of subfunctions whose highest reference is at level n. */ + + Cal_BddProfile(bddManager, fUserBdd, funcCounts, 0); + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + /* Encode the profile. The low bit of a count will be zero for */ + /* those levels where f actually has a node. */ + for(j = 0; j < bddManager->numVars; ++j){ + if(!funcCounts[j]){ + funcCounts[j] = 1; + } + else{ + funcCounts[j] <<= 1; + } + } + h = CalHashTableOneInit(bddManager, sizeof(int)); + /* For each subfunction in f, compute the highest level where it is */ + /* referenced. f itself is conceptually referenced at the highest */ + /* possible level, which we represent by -1. */ + i = -1; + CalHashTableOneInsert(h, f, (char *)&i); + BddHighestRefStep(bddManager, f, h); + /* Walk through these results. For each subfunction, decrement the */ + /* count at the highest level where it is referenced. */ + BddDominatedStep(bddManager, f, funcCounts, h); + CalHashTableOneQuit(h); + /* Now add each level n+1 result to that of level n. */ + for(i = bddManager->numVars-1, j = i+1; i>= 0; --i){ + if(funcCounts[i] != 1){ + funcCounts[i] = (funcCounts[i] >> 1) + funcCounts[j]; + j = i; + } + else{ + funcCounts[i] = 0; + } + } + } +} + +/**Function******************************************************************** + + Synopsis [Returns a "function profile" for fArray.] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddFunctionProfileMultiple(Cal_BddManager bddManager, Cal_Bdd + *fUserBddArray, long * funcCounts) +{ + long i; + Cal_BddIndex_t j; + Cal_Bdd_t *f, *fArray; + CalHashTable_t *h; + + Cal_Bdd userBdd; + + CalBddArrayPreProcessing(bddManager, fUserBddArray); + + for(i = 0; (userBdd = fUserBddArray[i]); ++i); + + fArray = Cal_MemAlloc(Cal_Bdd_t, i+1); + for (j=0; j < i; j++){ + fArray[j] = CalBddGetInternalBdd(bddManager,fUserBddArray[j]); + } + fArray[j] = bddManager->bddNull; + + /* See cmu_bdd_function_profile for the strategy involved here. */ + Cal_BddProfileMultiple(bddManager, fUserBddArray, funcCounts, 0); + for(j = 0; j < bddManager->numVars; ++j){ + if(!funcCounts[j]){ + funcCounts[j] = 1; + } + else{ + funcCounts[j] <<= 1; + } + } + h = CalHashTableOneInit(bddManager, sizeof(int)); + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + BddHighestRefStep(bddManager, *f, h); + } + i = -1; + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + CalHashTableOneInsert(h, *f, (char *)&i); + } + for(f = fArray; !CalBddIsBddNull(bddManager, *f); ++f){ + BddDominatedStep(bddManager, *f, funcCounts, h); + } + CalHashTableOneQuit(h); + for(i = bddManager->numVars-1, j = i+1; i >= 0; --i){ + if(funcCounts[i] != 1){ + funcCounts[i] = (funcCounts[i] >> 1) + funcCounts[j]; + j = i; + } + else{ + funcCounts[i] = 0; + } + } + Cal_MemFree(fArray); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddMarkBdd(Cal_Bdd_t f) +{ + int currMarking, thisMarking; + Cal_Bdd_t thenBdd, elseBdd; + + currMarking = CalBddGetMark(f); + thisMarking = (1 << CalBddIsComplement(f)); + if(currMarking & thisMarking){ + return; + } + CalBddPutMark(f, currMarking | thisMarking); + if(CalBddIsBddConst(f)){ + return; + } + CalBddGetThenBdd(f, thenBdd); + BddMarkBdd(thenBdd); + CalBddGetElseBdd(f, elseBdd); + BddMarkBdd(elseBdd); +} + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddCountNoNodes( + Cal_Bdd_t f) +{ + return (CalBddGetMark(f) > 0); +} + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddCountNodes( + Cal_Bdd_t f) +{ + int mark; + + mark = CalBddGetMark(f); + return (((mark & 0x1) != 0) + ((mark & 0x2) != 0)); +} + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static long +BddSizeStep( + Cal_Bdd_t f, + CountFn_t countFn) +{ + long result; + Cal_Bdd_t thenBdd, elseBdd; + + if(!CalBddGetMark(f)){ + return (0l); + } + result = (*countFn)(f); + if(!CalBddIsBddConst(f)){ + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + result += + BddSizeStep(thenBdd, countFn) + + BddSizeStep(elseBdd, countFn); + } + CalBddPutMark(f, 0); + return result; +} + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddProfileStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + long * levelCounts, + CountFn_t countFn) +{ + Cal_Bdd_t thenBdd, elseBdd; + if(!CalBddGetMark(f)){ + return; + } + if(CalBddIsBddConst(f)){ + levelCounts[bddManager->numVars] += (*countFn)(f); + } + else{ + levelCounts[CalBddGetBddIndex(bddManager, f)] += (*countFn)(f); + CalBddGetThenBdd(f, thenBdd); + BddProfileStep(bddManager, thenBdd, levelCounts, countFn); + CalBddGetElseBdd(f, elseBdd); + BddProfileStep(bddManager, elseBdd, levelCounts, countFn); + } + CalBddPutMark(f, 0); +} + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddHighestRefStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + CalHashTable_t * h) +{ + int fIndex; + Cal_Bdd_t keyBdd; + int *dataPtr; + + if(CalBddIsBddConst(f)){ + return; + } + fIndex = CalBddGetBddIndex(bddManager, f); + CalBddGetThenBdd(f, keyBdd); + if(CalHashTableOneLookup(h, keyBdd, (char **)&dataPtr)){ + if(*dataPtr > fIndex){ + *dataPtr = fIndex; + } + } + else{ + CalHashTableOneInsert(h, keyBdd, (char *)&fIndex); + BddHighestRefStep(bddManager, keyBdd, h); + } + CalBddGetElseBdd(f, keyBdd); + if(CalHashTableOneLookup(h, keyBdd, (char **)&dataPtr)){ + if(*dataPtr > fIndex){ + *dataPtr = fIndex; + } + } + else{ + CalHashTableOneInsert(h, keyBdd, (char *)&fIndex); + BddHighestRefStep(bddManager, keyBdd, h); + } +} + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddDominatedStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + long * funcCounts, + CalHashTable_t * h) +{ + Cal_Bdd_t thenBdd, elseBdd; + int *dataPtr; + + CalHashTableOneLookup(h, f, (char **)&dataPtr); + if(*dataPtr >= 0) + funcCounts[*dataPtr] -= 2; + if(*dataPtr > -2){ + *dataPtr = -2; + if(!CalBddIsBddConst(f)){ + CalBddGetThenBdd(f, thenBdd); + BddDominatedStep(bddManager, thenBdd, funcCounts, h); + CalBddGetElseBdd(f, elseBdd); + BddDominatedStep(bddManager, elseBdd, funcCounts, h); + } + } +} + + + + + + + + + diff --git a/calBddSubstitute.c b/calBddSubstitute.c new file mode 100644 index 0000000..26b54af --- /dev/null +++ b/calBddSubstitute.c @@ -0,0 +1,407 @@ +/**CFile*********************************************************************** + + FileName [calBddSubstitute.c] + + PackageName [cal] + + Synopsis [Routine for simultaneous substitution of an array of + variables with an array of functions.] + + Description [Routine for simultaneous substitution of an array of + variables with an array of functions.] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddSubstitute.c,v 1.1.1.4 1998/05/04 00:58:54 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalHashTableSubstituteApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, int lastIndex, CalHashTable_t ** reqQueForSubstitute); +static void CalHashTableSubstituteReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** reqQueForITE, CalHashTable_t * uniqueTableForId); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Substitute a set of variables by functions] + + Description [Returns a BDD for f using the substitution defined by current + variable association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously] + + SideEffects [None] + + SeeAlso [Cal_BddCompose] + +******************************************************************************/ +Cal_Bdd +Cal_BddSubstitute(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + CalRequest_t result; + int bddId, bddIndex, lastIndex; + CalHashTable_t *hashTable; + CalHashTable_t *uniqueTableForId; + CalHashTable_t **reqQueForSubstitute = bddManager->reqQue[0]; + CalHashTable_t **reqQueForITE = bddManager->reqQue[1]; + Cal_Bdd_t f; + + if (CalBddPreProcessing(bddManager, 1, fUserBdd) == 0){ + return (Cal_Bdd) 0; + } + f = CalBddGetInternalBdd(bddManager, fUserBdd); + if(CalBddIsBddConst(f)){ + return CalBddGetExternalBdd(bddManager, f); + } + + CalHashTableFindOrAdd(reqQueForSubstitute[CalBddGetBddId(f)], f, + bddManager->bddNull, &result); + + /* ReqQueApply */ + lastIndex = bddManager->currentAssociation->lastBddIndex; + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reqQueForSubstitute[bddId]; + if(hashTable->numEntries){ + CalHashTableSubstituteApply(bddManager, hashTable, lastIndex, + reqQueForSubstitute); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reqQueForSubstitute[bddId]; + if(hashTable->numEntries){ + CalHashTableSubstituteReduce(bddManager, hashTable, + reqQueForITE, uniqueTableForId); + } + } + + CalRequestIsForwardedTo(result); + + /* ReqQueCleanUp */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForSubstitute[bddId]); + } + + return CalBddGetExternalBdd(bddManager, result); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSubstituteApply( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + int lastIndex, + CalHashTable_t ** reqQueForSubstitute) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_BddId_t bddId; + /*Cal_BddIndex_t bddIndex;*/ + int bddIndex; + Cal_Bdd_t f, calBdd; + Cal_Bdd_t nullBdd = bddManager->bddNull; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + /* Process the requestNode */ + CalRequestNodeGetF(requestNode, f); + /* Process Left Cofactor */ + CalBddGetThenBdd(f, calBdd); + bddId = CalBddGetBddId(calBdd); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= lastIndex){ + CalHashTableFindOrAdd(reqQueForSubstitute[bddId], calBdd, nullBdd, + &calBdd); + } + CalBddIcrRefCount(calBdd); + CalRequestNodePutThenRequest(requestNode, calBdd); + /* Process Right Cofactor */ + CalBddGetElseBdd(f, calBdd); + bddId = CalBddGetBddId(calBdd); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= lastIndex){ + CalHashTableFindOrAdd(reqQueForSubstitute[bddId], calBdd, nullBdd, + &calBdd); + } + CalBddIcrRefCount(calBdd); + CalRequestNodePutElseRequest(requestNode, calBdd); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSubstituteReduce( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t ** reqQueForITE, + CalHashTable_t * uniqueTableForId) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + Cal_BddId_t varBddId = hashTable->bddId; + CalNodeManager_t *nodeManager = hashTable->nodeManager; + /*CalRequestNode_t *requestNodeList = hashTable->requestNodeList;*/ + CalRequestNode_t *endNode = hashTable->endNode; + CalRequestNode_t *requestNodeListForITE = Cal_Nil(CalRequestNode_t); + CalRequestNode_t *requestNode, *next; + CalBddNode_t *bddNode; + Cal_Bdd_t varBdd; + Cal_Bdd_t thenBdd, elseBdd, result; + Cal_Bdd_t h; + Cal_BddIndex_t varBddIndex; + Cal_BddRefCount_t refCount; + int bddId, bddIndex; + CalHashTable_t *hashTableForITE; + + varBddIndex = bddManager->idToIndex[varBddId]; + varBdd = bddManager->varBdds[varBddId]; + h = bddManager->currentAssociation->varAssociation[varBddId]; + if(!CalBddIsBddNull(bddManager, h)){ + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else{ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + result = CalOpITE(bddManager, h, thenBdd, elseBdd, reqQueForITE); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + CalRequestNodePutNextRequestNode(requestNode, + requestNodeListForITE); + requestNodeListForITE = requestNode; + } + } + } + } + else{ + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(varBddIndex < CalBddGetBddIndex(bddManager, thenBdd) && + varBddIndex < CalBddGetBddIndex(bddManager, elseBdd)){ + if(CalUniqueTableForIdLookup(bddManager, uniqueTableForId, + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequest(requestNode, elseBdd); + CalHashTableAddDirect(uniqueTableForId, requestNode); + bddManager->numNodes++; + bddManager->gcCheck--; + } + else{ + CalNodeManagerAllocNode(nodeManager, bddNode); + CalBddNodePutThenBddId(bddNode, CalBddGetBddId(thenBdd)); + CalBddNodePutThenBddNode(bddNode, + CalBddGetBddNodeNot(thenBdd)); + CalBddNodePutElseBddId(bddNode, CalBddGetBddId(elseBdd)); + CalBddNodePutElseBddNode(bddNode, + CalBddGetBddNodeNot(elseBdd)); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(uniqueTableForId, bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, varBddId); + CalRequestNodePutThenRequestNode(requestNode, + CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + else{ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + result = CalOpITE(bddManager, varBdd, thenBdd, elseBdd, reqQueForITE); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + CalRequestNodePutNextRequestNode(requestNode, + requestNodeListForITE); + requestNodeListForITE = requestNode; + } + } + } + } + + /* ITE Apply */ + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTableForITE = reqQueForITE[bddId]; + if(hashTableForITE->numEntries){ + CalHashTableITEApply(bddManager, hashTableForITE, reqQueForITE); + } + } + /* ITE Reduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + hashTableForITE = reqQueForITE[bddId]; + if(hashTableForITE->numEntries){ + CalHashTableReduce(bddManager, hashTableForITE, + bddManager->uniqueTable[bddId]); + } + } + + + /*last = Cal_Nil(CalRequestNode_t);*/ + for(requestNode = requestNodeListForITE; + requestNode != Cal_Nil(CalRequestNode_t); + /*last = requestNode, */ + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, result); + CalBddNodeGetRefCount(requestNode, refCount); + CalRequestIsForwardedTo(result); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + } + + /*CalBddNodePutNextBddNode(endNode, requestNodeListForITE);*/ + endNode->nextBddNode = requestNodeListForITE; + hashTable->endNode = endNode; + + /* ITE Cleanup */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForITE[bddId]); + } +} + + + + + + + + + + + + + diff --git a/calBddSupport.c b/calBddSupport.c new file mode 100644 index 0000000..7af2333 --- /dev/null +++ b/calBddSupport.c @@ -0,0 +1,279 @@ +/**CFile*********************************************************************** + + FileName [calBddSupport.c] + + PackageName [cal] + + Synopsis [Routines related to the support of a BDD.] + + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long. + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddSupport.c,v 1.1.1.3 1998/05/04 00:58:54 hsv Exp $] + +******************************************************************************/ +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t * CalBddSupportStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t * support); +static void CalBddUnmarkNodes(Cal_BddManager_t * bddManager, Cal_Bdd_t f); +static int CalBddDependsOnStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_BddIndex_t varIndex, int mark); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Name [Cal_BddSupport] + + Synopsis [returns the support of f as a null-terminated array of variables] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddSupport(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd *support) +{ + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + Cal_Bdd_t *internalSupport = Cal_MemAlloc(Cal_Bdd_t, bddManager->numVars+1); + Cal_Bdd_t *end; + int i = 0; + end = CalBddSupportStep(bddManager, f, internalSupport); + *end = CalBddNull(bddManager); + CalBddUnmarkNodes(bddManager, f); + while (CalBddIsBddNull(bddManager, internalSupport[i]) == 0){ + *support = CalBddGetExternalBdd(bddManager, internalSupport[i]); + support++; + i++; + } + Cal_MemFree(internalSupport); + } + *support = (Cal_Bdd) 0; +} + +/**Function******************************************************************** + + Name [Cal_BddDependsOn] + + Synopsis [Returns 1 if f depends on var and returns 0 otherwise.] + + Description [Returns 1 if f depends on var and returns 0 otherwise.] + + SideEffects [None] + +******************************************************************************/ +int +Cal_BddDependsOn(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd varUserBdd) +{ + Cal_BddIndex_t bddIndex; + Cal_Bdd_t f, var; + + if(CalBddPreProcessing(bddManager, 2, fUserBdd, varUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + var = CalBddGetInternalBdd(bddManager, varUserBdd); + if(CalBddIsBddConst(var)){ + return 1; + } + bddIndex = CalBddGetBddIndex(bddManager, var); + CalBddDependsOnStep(bddManager, f, bddIndex, 1); + return CalBddDependsOnStep(bddManager, f, bddIndex, 0); + } + return (0); +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Name [CalBddSupportStep] + + Synopsis [returns the support of f as a null-terminated array of variables] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t * +CalBddSupportStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + Cal_Bdd_t * support) +{ + Cal_Bdd_t tempBdd; + + if(CalBddIsMarked(f) || CalBddIsBddConst(f)){ + return support; + } + tempBdd = bddManager->varBdds[CalBddGetBddId(f)]; + if(!CalBddIsMarked(tempBdd)){ + CalBddMark(tempBdd); + *support = tempBdd; + ++support; + } + CalBddMark(f); + CalBddGetThenBdd(f, tempBdd); + support = CalBddSupportStep(bddManager, tempBdd, support); + CalBddGetElseBdd(f, tempBdd); + return CalBddSupportStep(bddManager, tempBdd, support); +} + + +/**Function******************************************************************** + + Name [CalBddUnmarkNodes] + + Synopsis [recursively unmarks the nodes] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalBddUnmarkNodes( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f) +{ + Cal_Bdd_t tempBdd; + + if(!CalBddIsMarked(f) || CalBddIsBddConst(f)){ + return; + } + CalBddUnmark(f); + tempBdd = bddManager->varBdds[CalBddGetBddId(f)]; + CalBddUnmark(tempBdd); + CalBddGetThenBdd(f, tempBdd); + CalBddUnmarkNodes(bddManager, tempBdd); + CalBddGetElseBdd(f, tempBdd); + CalBddUnmarkNodes(bddManager, tempBdd); +} + + +/**Function******************************************************************** + + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +CalBddDependsOnStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + Cal_BddIndex_t varIndex, + int mark) +{ + Cal_BddIndex_t fIndex; + Cal_Bdd_t tempBdd; + + fIndex=CalBddGetBddIndex(bddManager, f); + if(fIndex > varIndex){ + return 0; + } + if(fIndex == varIndex){ + return 1; + } + if((mark && CalBddIsMarked(f)) || (!mark && !CalBddIsMarked(f))){ + return (0); + } + if(mark){ + CalBddMark(f); + } + else{ + CalBddUnmark(f); + } + CalBddGetThenBdd(f, tempBdd); + if(CalBddDependsOnStep(bddManager, tempBdd, varIndex, mark)){ + return 1; + } + CalBddGetElseBdd(f, tempBdd); + return CalBddDependsOnStep(bddManager, tempBdd, varIndex, mark); +} + + + + + + + + + + + diff --git a/calBddSwapVars.c b/calBddSwapVars.c new file mode 100644 index 0000000..2f9d482 --- /dev/null +++ b/calBddSwapVars.c @@ -0,0 +1,581 @@ +/**CFile*********************************************************************** + + FileName [calBddSwapVars.c] + + PackageName [cal] + + Synopsis [Routine for swapping two variables.] + + Description [Routine for swapping two variables.] + + SeeAlso [None] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddSwapVars.c,v 1.1.1.3 1998/05/04 00:58:55 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalHashTableSwapVarsApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, Cal_BddIndex_t gIndex, Cal_BddIndex_t hIndex, CalHashTable_t ** reqQueForSwapVars, CalHashTable_t ** reqQueForSwapVarsPlus, CalHashTable_t ** reqQueForSwapVarsMinus, CalHashTable_t ** reqQueForCompose, CalHashTable_t ** reqQueForITE); +static void CalHashTableSwapVarsPlusApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, Cal_BddIndex_t hIndex, CalHashTable_t ** reqQueForSwapVars, CalHashTable_t ** reqQueForSwapVarsPlus, CalHashTable_t ** reqQueForSwapVarsMinus, CalHashTable_t ** reqQueForCompose); +static void CalHashTableSwapVarsMinusApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, Cal_BddIndex_t hIndex, CalHashTable_t ** reqQueForSwapVars, CalHashTable_t ** reqQueForSwapVarsPlus, CalHashTable_t ** reqQueForSwapVarsMinus, CalHashTable_t ** reqQueForCompose); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Return a function obtained by swapping two variables] + + Description [Returns the BDD obtained by simultaneously substituting variable + g by variable h and variable h and variable g in the BDD f] + + SideEffects [None] + + SeeAlso [Cal_BddSubstitute] + +******************************************************************************/ +Cal_Bdd +Cal_BddSwapVars(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd, + Cal_Bdd hUserBdd) +{ + Cal_Bdd_t f,g,h,tmpBdd; + Cal_BddIndex_t gIndex, hIndex; + CalRequest_t result; + int bddId, bddIndex; + CalHashTable_t *hashTable; + CalHashTable_t *uniqueTableForId; + CalHashTable_t **reqQueForSwapVars = bddManager->reqQue[0]; + CalHashTable_t **reqQueForSwapVarsPlus = bddManager->reqQue[1]; + CalHashTable_t **reqQueForSwapVarsMinus = bddManager->reqQue[2]; + CalHashTable_t **reqQueForCompose = bddManager->reqQue[3]; + CalHashTable_t **reqQueForITE = bddManager->reqQue[4]; + + if (CalBddPreProcessing(bddManager, 3, fUserBdd, gUserBdd, hUserBdd) == 0){ + return (Cal_Bdd) 0; + } + f = CalBddGetInternalBdd(bddManager, fUserBdd); + g = CalBddGetInternalBdd(bddManager, gUserBdd); + h = CalBddGetInternalBdd(bddManager, hUserBdd); + + if(CalBddIsBddConst(g) || CalBddIsBddConst(h)){ + CalBddWarningMessage("Unacceptable arguments for Cal_BddSwapVars"); + return (Cal_Bdd) 0; + } + if(CalBddIsEqual(g, h)){ + /* + CalBddIcrRefCount(f); + */ + return CalBddGetExternalBdd(bddManager, f); + } + if(CalBddGetBddIndex(bddManager, g) > CalBddGetBddIndex(bddManager, h)){ + tmpBdd = g; + g = h; + h = tmpBdd; + } + + gIndex = CalBddGetBddIndex(bddManager, g); + hIndex = CalBddGetBddIndex(bddManager, h); + + CalBddGetMinId2(bddManager, f, g, bddId); + CalHashTableFindOrAdd(reqQueForSwapVars[bddId], f, + bddManager->bddNull, &result); + + /* ReqQueApply */ + for(bddIndex = 0; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reqQueForSwapVars[bddId]; + if(hashTable->numEntries){ + CalHashTableSwapVarsApply(bddManager, hashTable, gIndex, hIndex, + reqQueForSwapVars, reqQueForSwapVarsPlus, reqQueForSwapVarsMinus, + reqQueForCompose, reqQueForITE); + } + hashTable = reqQueForSwapVarsPlus[bddId]; + if(hashTable->numEntries){ + CalHashTableSwapVarsPlusApply(bddManager, hashTable, hIndex, + reqQueForSwapVars, reqQueForSwapVarsPlus, reqQueForSwapVarsMinus, + reqQueForCompose); + } + hashTable = reqQueForSwapVarsMinus[bddId]; + if(hashTable->numEntries){ + CalHashTableSwapVarsMinusApply(bddManager, hashTable, hIndex, + reqQueForSwapVars, reqQueForSwapVarsPlus, reqQueForSwapVarsMinus, + reqQueForCompose); + } + hashTable = reqQueForCompose[bddId]; + if(hashTable->numEntries){ + CalHashTableComposeApply(bddManager, hashTable, hIndex, + reqQueForCompose, reqQueForITE); + } + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableITEApply(bddManager, hashTable, reqQueForITE); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= 0; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reqQueForSwapVars[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + hashTable = reqQueForSwapVarsPlus[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + hashTable = reqQueForSwapVarsMinus[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + hashTable = reqQueForCompose[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + hashTable = reqQueForITE[bddId]; + if(hashTable->numEntries){ + CalHashTableReduce(bddManager, hashTable, uniqueTableForId); + } + } + + CalRequestIsForwardedTo(result); + + /* ReqQueCleanUp */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForSwapVars[bddId]); + CalHashTableCleanUp(reqQueForSwapVarsPlus[bddId]); + CalHashTableCleanUp(reqQueForSwapVarsMinus[bddId]); + CalHashTableCleanUp(reqQueForCompose[bddId]); + CalHashTableCleanUp(reqQueForITE[bddId]); + } + return CalBddGetExternalBdd(bddManager, result); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSwapVarsApply( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + Cal_BddIndex_t gIndex, + Cal_BddIndex_t hIndex, + CalHashTable_t ** reqQueForSwapVars, + CalHashTable_t ** reqQueForSwapVarsPlus, + CalHashTable_t ** reqQueForSwapVarsMinus, + CalHashTable_t ** reqQueForCompose, + CalHashTable_t ** reqQueForITE) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_BddId_t bddId; + Cal_BddIndex_t fIndex, bddIndex; + Cal_Bdd_t f, calBdd; + Cal_Bdd_t thenBdd, elseBdd; + Cal_Bdd_t nullBdd = bddManager->bddNull; + Cal_Bdd_t result; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, f); + fIndex = CalBddGetBddIndex(bddManager, f); + if(fIndex < gIndex){ + /* left cofactor */ + CalBddGetThenBdd(f, calBdd); + bddId = CalBddGetBddId(calBdd); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= hIndex){ + if(bddIndex > gIndex){ + bddId = bddManager->indexToId[gIndex]; + } + CalHashTableFindOrAdd(reqQueForSwapVars[bddId], + calBdd, nullBdd, &calBdd); + } + CalBddIcrRefCount(calBdd); + CalRequestNodePutThenRequest(requestNode, calBdd); + /* right cofactor */ + CalBddGetElseBdd(f, calBdd); + bddId = CalBddGetBddId(calBdd); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= hIndex){ + if(bddIndex > gIndex){ + bddId = bddManager->indexToId[gIndex]; + } + CalHashTableFindOrAdd(reqQueForSwapVars[bddId], + calBdd, nullBdd, &calBdd); + } + CalBddIcrRefCount(calBdd); + CalRequestNodePutElseRequest(requestNode, calBdd); + } + else if(fIndex == gIndex){ + /* SwapVarsPlus */ + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + if(CalBddGetBddIndex(bddManager, thenBdd) == hIndex){ + CalBddGetThenBdd(thenBdd, thenBdd); + } + if(CalBddGetBddIndex(bddManager, elseBdd) == hIndex){ + CalBddGetThenBdd(elseBdd, elseBdd); + } + if(CalBddIsEqual(thenBdd, elseBdd)){ + if(hIndex > CalBddGetBddIndex(bddManager, thenBdd)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(thenBdd)], + thenBdd, CalBddOne(bddManager), &result); + } + else{ + result = thenBdd; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, thenBdd) && + hIndex < CalBddGetBddIndex(bddManager, elseBdd)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], thenBdd, elseBdd, &result)){ + CalBddIcrRefCount(thenBdd); + CalBddIcrRefCount(elseBdd); + } + } + else{ + CalBddGetMinId2(bddManager, thenBdd, elseBdd, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsPlus[bddId], + thenBdd, elseBdd, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + /* SwapVarsMinus */ + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + if(CalBddGetBddIndex(bddManager, thenBdd) == hIndex){ + CalBddGetElseBdd(thenBdd, thenBdd); + } + if(CalBddGetBddIndex(bddManager, elseBdd) == hIndex){ + CalBddGetElseBdd(elseBdd, elseBdd); + } + if(CalBddIsEqual(thenBdd, elseBdd)){ + if(hIndex > CalBddGetBddIndex(bddManager, thenBdd)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(thenBdd)], + thenBdd, CalBddZero(bddManager), &result); + } + else{ + result = thenBdd; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, thenBdd) && + hIndex < CalBddGetBddIndex(bddManager, elseBdd)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], thenBdd, elseBdd, &result)){ + CalBddIcrRefCount(thenBdd); + CalBddIcrRefCount(elseBdd); + } + } + else{ + CalBddGetMinId2(bddManager, thenBdd, elseBdd, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsMinus[bddId], + thenBdd, elseBdd, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + else{ /* fIndex > gIndex */ + CalComposeRequestCreate(bddManager, + f, CalBddOne(bddManager), hIndex, + reqQueForCompose, reqQueForITE, &result); + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + CalComposeRequestCreate(bddManager, + f, CalBddZero(bddManager), hIndex, + reqQueForCompose, reqQueForITE, &result); + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } + } +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSwapVarsPlusApply( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + Cal_BddIndex_t hIndex, + CalHashTable_t ** reqQueForSwapVars, + CalHashTable_t ** reqQueForSwapVarsPlus, + CalHashTable_t ** reqQueForSwapVarsMinus, + CalHashTable_t ** reqQueForCompose) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_BddId_t bddId; + Cal_Bdd_t f1, f2, g1, g2; + Cal_Bdd_t result; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetCofactors(bddManager, requestNode, f1, f2, g1, g2); + /* left cofactor */ + if(CalBddGetBddIndex(bddManager, f1) == hIndex){ + CalBddGetThenBdd(f1, f1); + } + if(CalBddGetBddIndex(bddManager, g1) == hIndex){ + CalBddGetThenBdd(g1, g1); + } + if(CalBddIsEqual(f1, g1)){ + if(hIndex > CalBddGetBddIndex(bddManager, f1)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(f1)], + f1, CalBddOne(bddManager), &result); + } + else{ + result = f1; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, f1) && + hIndex < CalBddGetBddIndex(bddManager, g1)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], f1, g1, &result)){ + CalBddIcrRefCount(f1); + CalBddIcrRefCount(g1); + } + } + else{ + CalBddGetMinId2(bddManager, f1, g1, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsPlus[bddId], f1, g1, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + /* right cofactor */ + if(CalBddGetBddIndex(bddManager, f2) == hIndex){ + CalBddGetThenBdd(f2, f2); + } + if(CalBddGetBddIndex(bddManager, g2) == hIndex){ + CalBddGetThenBdd(g2, g2); + } + if(CalBddIsEqual(f2, g2)){ + if(hIndex > CalBddGetBddIndex(bddManager, f2)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(f2)], + f2, CalBddOne(bddManager), &result); + } + else{ + result = f2; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, f2) && + hIndex < CalBddGetBddIndex(bddManager, g2)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], f2, g2, &result)){ + CalBddIcrRefCount(f2); + CalBddIcrRefCount(g2); + } + } + else{ + CalBddGetMinId2(bddManager, f2, g2, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsPlus[bddId], f2, g2, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSwapVarsMinusApply( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + Cal_BddIndex_t hIndex, + CalHashTable_t ** reqQueForSwapVars, + CalHashTable_t ** reqQueForSwapVarsPlus, + CalHashTable_t ** reqQueForSwapVarsMinus, + CalHashTable_t ** reqQueForCompose) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_BddId_t bddId; + Cal_Bdd_t f1, f2, g1, g2; + Cal_Bdd_t result; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetCofactors(bddManager, requestNode, f1, f2, g1, g2); + /* left cofactor */ + if(CalBddGetBddIndex(bddManager, f1) == hIndex){ + CalBddGetElseBdd(f1, f1); + } + if(CalBddGetBddIndex(bddManager, g1) == hIndex){ + CalBddGetElseBdd(g1, g1); + } + if(CalBddIsEqual(f1, g1)){ + if(hIndex > CalBddGetBddIndex(bddManager, f1)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(f1)], + f1, CalBddZero(bddManager), &result); + } + else{ + result = f1; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, f1) && + hIndex < CalBddGetBddIndex(bddManager, g1)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], f1, g1, &result)){ + CalBddIcrRefCount(f1); + CalBddIcrRefCount(g1); + } + } + else{ + CalBddGetMinId2(bddManager, f1, g1, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsMinus[bddId], f1, g1, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + /* right cofactor */ + if(CalBddGetBddIndex(bddManager, f2) == hIndex){ + CalBddGetElseBdd(f2, f2); + } + if(CalBddGetBddIndex(bddManager, g2) == hIndex){ + CalBddGetElseBdd(g2, g2); + } + if(CalBddIsEqual(f2, g2)){ + if(hIndex > CalBddGetBddIndex(bddManager, f2)){ + CalHashTableFindOrAdd(reqQueForCompose[CalBddGetBddId(f2)], + f2, CalBddZero(bddManager), &result); + } + else{ + result = f2; + } + } + else if(hIndex < CalBddGetBddIndex(bddManager, f2) && + hIndex < CalBddGetBddIndex(bddManager, g2)){ + bddId = bddManager->indexToId[hIndex]; + if(!CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[bddId], f2, g2, &result)){ + CalBddIcrRefCount(f2); + CalBddIcrRefCount(g2); + } + } + else{ + CalBddGetMinId2(bddManager, f2, g2, bddId); + CalHashTableFindOrAdd(reqQueForSwapVarsMinus[bddId], f2, g2, &result); + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + + + + + + + + + + + + + + diff --git a/calBddVarSubstitute.c b/calBddVarSubstitute.c new file mode 100644 index 0000000..592677d --- /dev/null +++ b/calBddVarSubstitute.c @@ -0,0 +1,546 @@ +/**CFile*********************************************************************** + + FileName [calBddVarSubstitute.c] + + PackageName [cal] + + Synopsis [Routine for simultaneous substitution of an array of + variables with another array of variables.] + + Description [] + + SeeAlso [optional] + + Author [Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBddVarSubstitute.c,v 1.1.1.3 1998/05/04 00:58:55 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalHashTableSubstituteApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, int lastIndex, CalHashTable_t ** reqQueForSubstitute, unsigned short opCode); +static void CalHashTableSubstituteReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** reqQueForITE, CalHashTable_t * uniqueTableForId, unsigned short opCode); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Substitute a set of variables by set of another variables.] + + Description [Returns a BDD for f using the substitution defined by current + variable association. It is assumed that each variable is replaced + by another variable. For the substitution of a variable by a + function, use Cal_BddSubstitute instead.] + + SideEffects [None] + + SeeAlso [Cal_BddSubstitute] + +******************************************************************************/ +Cal_Bdd +Cal_BddVarSubstitute(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + CalRequest_t result; + Cal_Bdd userResult; + + if (CalBddPreProcessing(bddManager, 1, fUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + CalAssociation_t *assoc = bddManager->currentAssociation; + unsigned short opCode; + if (assoc->id == -1){ + opCode = bddManager->tempOpCode--; + } + else { + opCode = CAL_OP_VAR_SUBSTITUTE + assoc->id; + } + result = CalBddVarSubstitute(bddManager, f, opCode, assoc); + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; + } + return (Cal_Bdd) 0; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Substitute a set of variables by functions] + + Description [Returns a BDD for f using the substitution defined by current + variable association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously] + + SideEffects [None] + + SeeAlso [Cal_BddCompose] + +******************************************************************************/ +Cal_Bdd_t +CalBddVarSubstitute(Cal_BddManager bddManager, Cal_Bdd_t f, unsigned + short opCode, CalAssociation_t *assoc) +{ + CalRequest_t result; + int bddId, bddIndex, lastIndex; + CalHashTable_t *hashTable; + CalHashTable_t *uniqueTableForId; + CalHashTable_t **reqQueForSubstitute = bddManager->reqQue[0]; + CalHashTable_t **reqQueForITE = bddManager->reqQue[1]; + Cal_BddId_t fId = CalBddGetBddId(f); + /*Cal_BddIndex_t fIndex = bddManager->idToIndex[fId];*/ + int fIndex = bddManager->idToIndex[fId]; + + if (CalOpBddVarSubstitute(bddManager, f, &result)){ + return result; + } + + if (CalCacheTableOneLookup(bddManager, f, opCode, &result)){ + return result; + } + CalHashTableFindOrAdd(reqQueForSubstitute[fId], f, + bddManager->bddNull, &result); + + /* ReqQueApply */ + lastIndex = assoc->lastBddIndex; + for(bddIndex = fIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reqQueForSubstitute[bddId]; + if(hashTable->numEntries){ + CalHashTableSubstituteApply(bddManager, hashTable, lastIndex, + reqQueForSubstitute, opCode); + } + } + + /* ReqQueReduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= fIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reqQueForSubstitute[bddId]; + if(hashTable->numEntries){ + CalHashTableSubstituteReduce(bddManager, hashTable, + reqQueForITE, uniqueTableForId, + opCode); + } + } + + CalRequestIsForwardedTo(result); + + /* ReqQueCleanUp */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForSubstitute[bddId]); + } + CalCacheTableTwoFixResultPointers(bddManager); + CalCacheTableOneInsert(bddManager, f, result, opCode, 0); + return result; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpBddVarSubstitute(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t * + resultBddPtr) +{ + if (bddManager->idToIndex[CalBddGetBddId(f)] > + bddManager->currentAssociation->lastBddIndex){ + *resultBddPtr = f; + return 1; + } + return 0; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSubstituteApply( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + int lastIndex, + CalHashTable_t ** reqQueForSubstitute, + unsigned short opCode) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_BddId_t bddId; + /*Cal_BddIndex_t bddIndex;*/ + int bddIndex; + Cal_Bdd_t f, fx, fxBar, result; + Cal_Bdd_t nullBdd = bddManager->bddNull; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + /* Process the requestNode */ + CalRequestNodeGetF(requestNode, f); + /* Process Left Cofactor */ + CalBddGetThenBdd(f, fx); + bddId = CalBddGetBddId(fx); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= lastIndex){ + if (CalCacheTableOneLookup(bddManager, fx, opCode, &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(reqQueForSubstitute[bddId], fx, nullBdd, + &result); + CalCacheTableOneInsert(bddManager, fx, result, + opCode, 1); + } + } + else{ + result = fx; + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + /* Process Right Cofactor */ + CalBddGetElseBdd(f, fxBar); + bddId = CalBddGetBddId(fxBar); + bddIndex = bddManager->idToIndex[bddId]; + if(bddIndex <= lastIndex){ + if (CalCacheTableOneLookup(bddManager, fxBar, opCode, &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(reqQueForSubstitute[bddId], fxBar, nullBdd, + &result); + CalCacheTableOneInsert(bddManager, fxBar, result, + opCode, 1); + } + } + else{ + result = fxBar; + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableSubstituteReduce( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t ** reqQueForITE, + CalHashTable_t * uniqueTableForId, + unsigned short opCode) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + Cal_BddId_t varBddId = hashTable->bddId; + CalNodeManager_t *nodeManager = hashTable->nodeManager; + /*CalRequestNode_t *requestNodeList = hashTable->requestNodeList;*/ + CalRequestNode_t *endNode = hashTable->endNode; + CalRequestNode_t *requestNodeListForITE = Cal_Nil(CalRequestNode_t); + CalRequestNode_t *requestNode, *next, *last; + CalBddNode_t *bddNode; + Cal_Bdd_t varBdd; + Cal_Bdd_t thenBdd, elseBdd, result; + Cal_Bdd_t h; + Cal_BddIndex_t resultIndex, varBddIndex; + int minITEindex = bddManager->numVars; + Cal_BddRefCount_t refCount; + int bddId, bddIndex; + CalHashTable_t *hashTableForITE; + + varBddIndex = bddManager->idToIndex[varBddId]; + varBdd = bddManager->varBdds[varBddId]; + h = bddManager->currentAssociation->varAssociation[varBddId]; + if(!CalBddIsBddNull(bddManager, h)){ + Cal_BddId_t hId = CalBddGetBddId(h); + Cal_BddIndex_t hIndex = bddManager->idToIndex[hId]; + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else{ + if(hIndex < CalBddGetBddIndex(bddManager, thenBdd) && + hIndex < CalBddGetBddIndex(bddManager, elseBdd)){ + if(CalUniqueTableForIdLookup(bddManager, bddManager->uniqueTable[hId], + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + /* Get a node from the node manager of h */ + CalNodeManager_t *hNodeManager = + bddManager->nodeManagerArray[hId]; + CalNodeManagerInitBddNode(hNodeManager, thenBdd, elseBdd, + Cal_Nil(CalBddNode_t), bddNode); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(bddManager->uniqueTable[hId], bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, hId); + CalRequestNodePutThenRequestNode(requestNode, bddNode); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else{ + /* Get a node from the node manager of h */ + CalNodeManager_t *hNodeManager = + bddManager->nodeManagerArray[hId]; + CalBddNot(thenBdd, thenBdd); + CalBddNot(elseBdd, elseBdd); + CalNodeManagerInitBddNode(hNodeManager, thenBdd, elseBdd, + Cal_Nil(CalBddNode_t), bddNode); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(bddManager->uniqueTable[hId], bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, hId); + CalRequestNodePutThenRequestNode(requestNode, + CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + else{ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + result = CalOpITE(bddManager, h, thenBdd, elseBdd, reqQueForITE); + if ((resultIndex = bddManager->idToIndex[CalBddGetBddId(result)]) < minITEindex){ + minITEindex = resultIndex; + } + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + CalRequestNodePutNextRequestNode(requestNode, + requestNodeListForITE); + requestNodeListForITE = requestNode; + } + } + } + } + } + else{ + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else{ + if(varBddIndex < CalBddGetBddIndex(bddManager, thenBdd) && + varBddIndex < CalBddGetBddIndex(bddManager, elseBdd)){ + if(CalUniqueTableForIdLookup(bddManager, uniqueTableForId, + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequest(requestNode, elseBdd); + CalHashTableAddDirect(uniqueTableForId, requestNode); + bddManager->numNodes++; + bddManager->gcCheck--; + } + else{ + CalBddNot(thenBdd, thenBdd); + CalBddNot(elseBdd, elseBdd); + CalNodeManagerInitBddNode(nodeManager, thenBdd, elseBdd, + Cal_Nil(CalBddNode_t), bddNode); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(uniqueTableForId, bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, varBddId); + CalRequestNodePutThenRequestNode(requestNode, + CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + else{ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + result = CalOpITE(bddManager, varBdd, thenBdd, elseBdd, reqQueForITE); + if ((resultIndex = bddManager->idToIndex[CalBddGetBddId(result)]) < minITEindex){ + minITEindex = resultIndex; + } + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + CalRequestNodePutNextRequestNode(requestNode, + requestNodeListForITE); + requestNodeListForITE = requestNode; + } + } + } + } + } + + /* ITE Apply */ + for(bddIndex = minITEindex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTableForITE = reqQueForITE[bddId]; + if(hashTableForITE->numEntries){ + CalHashTableITEApply(bddManager, hashTableForITE, reqQueForITE); + } + } + /* ITE Reduce */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= minITEindex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + hashTableForITE = reqQueForITE[bddId]; + if(hashTableForITE->numEntries){ + CalHashTableReduce(bddManager, hashTableForITE, + bddManager->uniqueTable[bddId]); + } + } + + + last = Cal_Nil(CalRequestNode_t); + for(requestNode = requestNodeListForITE; + requestNode != Cal_Nil(CalRequestNode_t); + last = requestNode, + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetThenRequest(requestNode, result); + CalBddNodeGetRefCount(requestNode, refCount); + CalRequestIsForwardedTo(result); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + } + + endNode->nextBddNode = requestNodeListForITE; + hashTable->endNode = endNode; + /* ITE Cleanup */ + for(bddId = 1; bddId <= bddManager->numVars; bddId++){ + CalHashTableCleanUp(reqQueForITE[bddId]); + } +} + diff --git a/calBlk.c b/calBlk.c new file mode 100644 index 0000000..826bedc --- /dev/null +++ b/calBlk.c @@ -0,0 +1,348 @@ +/**CFile*********************************************************************** + + FileName [calBlk.c] + + PackageName [cal] + + Synopsis [Routines for manipulating blocks of variables.] + + Description [Routines for manipulating blocks of variables.] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu). Modelled on the BDD package + developed by David Long.] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calBlk.c,v 1.1.1.2 1998/05/04 00:59:05 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void AddBlock(Cal_Block b1, Cal_Block b2); + +/**AutomaticEnd***************************************************************/ + +/* BDD variable block routines */ +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Creates and returns a variable block used for + controlling dynamic reordering.] + + Description [The block is specified by passing the first + variable and the length of the block. The "length" number of + consecutive variables starting from "variable" are put in the + block.] + + SideEffects [A new block is created.] + + SeeAlso [] + +******************************************************************************/ +Cal_Block +Cal_BddNewVarBlock(Cal_BddManager bddManager, Cal_Bdd variable, long length) +{ + Cal_Block b; + Cal_Bdd_t calBdd = CalBddGetInternalBdd(bddManager, variable); + + if (CalBddTypeAux(bddManager, calBdd) != CAL_BDD_TYPE_POSVAR) { + CalBddWarningMessage("Cal_BddNewVarBlock: second argument is not a positive variable\n"); + if (CalBddIsBddConst(calBdd)){ + return (Cal_Block) 0; + } + } + + /*b = CAL_BDD_NEW_REC(bddManager, Cal_Block_t);*/ + b = Cal_MemAlloc(Cal_Block_t, 1); + b->reorderable = 0; + b->firstIndex = bddManager->idToIndex[calBdd.bddId]; + if (length <= 0) { + CalBddWarningMessage("Cal_BddNewVarBlock: invalid final argument"); + length = 1; + } + b->lastIndex = b->firstIndex + length - 1; + if (b->lastIndex >= bddManager->numVars) { + CalBddWarningMessage("Cal_BddNewVarBlock: range covers non-existent variables"); + b->lastIndex = bddManager->numVars - 1; + } + AddBlock(bddManager->superBlock, b); + return (b); +} +/**Function******************************************************************** + + Synopsis [Sets the reoderability of a particular block.] + + Description [If a block is reorderable, the child blocks are + recursively involved in swapping.] + + SideEffects [None.] + + SeeAlso [] + +******************************************************************************/ +void +Cal_BddVarBlockReorderable(Cal_BddManager bddManager, Cal_Block block, + int reorderable) +{ + block->reorderable = reorderable; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +long +CalBddFindBlock(Cal_Block block, long index) +{ + long i, j, k; + + i = 0; + j = block->numChildren-1; + while (i <= j) { + k = (i+j)/2; + if (block->children[k]->firstIndex <= index && + block->children[k]->lastIndex >= index){ + return (k); + } + if (block->children[k]->firstIndex > index){ + j = k-1; + } + else { + i = k+1; + } + } + return i; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddBlockDelta(Cal_Block b, long delta) +{ + long i; + b->firstIndex += delta; + b->lastIndex += delta; + for (i=0; i < b->numChildren; ++i) + CalBddBlockDelta(b->children[i], delta); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Block +CalBddShiftBlock(Cal_BddManager_t *bddManager, Cal_Block b, long index) +{ + long i, j; + Cal_Block p; + + if (b->firstIndex >= index) { + CalBddBlockDelta(b, 1l); + return (b); + } + if (b->lastIndex < index) return (b); + b->lastIndex++; + i = CalBddFindBlock(b, index); + if (i == b->numChildren || b->children[i]->firstIndex == index) { + b->children = (Cal_Block *) + Cal_MemRealloc(Cal_Block, b->children, b->numChildren+1); + for (j = b->numChildren-1; j >= i; --j){ + b->children[j+1] = CalBddShiftBlock(bddManager, b->children[j], index); + } + b->numChildren++; + /*p = CAL_BDD_NEW_REC(bddManager, Cal_Block_t);*/ + p = Cal_MemAlloc(Cal_Block_t, 1); + p->reorderable = 0; + p->firstIndex = index; + p->lastIndex = index; + p->numChildren = 0; + p->children = 0; + b->children[i] = p; + } + else{ + while (i < b->numChildren) { + CalBddShiftBlock(bddManager, b->children[i], index); + ++i; + } + } + return (b); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +unsigned long +CalBlockMemoryConsumption(Cal_Block block) +{ + unsigned long totalBytes = 0; + int i; + + totalBytes += sizeof(Cal_Block); + for (i=0; inumChildren; i++){ + totalBytes += CalBlockMemoryConsumption(block->children[i]); + } + return totalBytes; +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalFreeBlockRecursively(Cal_Block block) +{ + int i; + + for (i=0; inumChildren; i++){ + CalFreeBlockRecursively(block->children[i]); + } + Cal_MemFree(block->children); + Cal_MemFree(block); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +AddBlock(Cal_Block b1, Cal_Block b2) +{ + long i, j, k; + Cal_Block start, end; + + if (b1->numChildren){ + i = CalBddFindBlock(b1, b2->firstIndex); + start = b1->children[i]; + j = CalBddFindBlock(b1, b2->lastIndex); + end = b1->children[j]; + if (i == j) { + AddBlock(start, b2); + } + else { + if (start->firstIndex != b2->firstIndex || + end->lastIndex != b2->lastIndex){ + CalBddFatalMessage("AddBlock: illegal block overlap"); + } + b2->numChildren = j-i+1; + b2->children = Cal_MemAlloc(Cal_Block, b2->numChildren); + for (k=0; k < b2->numChildren; ++k){ + b2->children[k] = b1->children[i+k]; + } + b1->children[i] = b2; + ++i; + for (k=j+1; k < b1->numChildren; ++k, ++i){ + b1->children[i] = b1->children[k]; + } + b1->numChildren -= (b2->numChildren-1); + b1->children = (Cal_Block *) + Cal_MemRealloc(Cal_Block, b1->children, b1->numChildren); + } + } + else { + /* b1 and b2 are blocks representing just single variables. */ + b1->numChildren = 1; + b1->children = Cal_MemAlloc(Cal_Block, b1->numChildren); + b1->children[0] = b2; + b2->numChildren = 0; + b2->children = 0; + } +} + + diff --git a/calCacheTableTwo.c b/calCacheTableTwo.c new file mode 100644 index 0000000..1fbc4d3 --- /dev/null +++ b/calCacheTableTwo.c @@ -0,0 +1,751 @@ +/**CFile*********************************************************************** + + FileName [calCacheTableTwo.c] + + PackageName [cal] + + Synopsis [Functions to manage the Cache tables.] + Description [ ] + + SeeAlso [optional] + + Author [ Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calCacheTableTwo.c,v 1.4 1998/09/15 19:02:52 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/* cache table management related constants */ +#define CACHE_TABLE_DEFAULT_SIZE_INDEX 16 +#define CACHE_TABLE_DEFAULT_CACHE_RATIO 4 + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef struct CacheEntryStruct CacheEntry_t; + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ +struct CalCacheTableStruct { + long numBins; + int sizeIndex; + CacheEntry_t *bins; + int cacheRatio; + long numInsertions; + long numEntries; + long numHits; + long numLookups; + long numCollisions; +}; + +struct CacheEntryStruct { + CalBddNode_t *operand1; + CalBddNode_t *operand2; + CalBddNode_t *resultBddNode; + Cal_BddId_t resultBddId; + unsigned short opCode; +}; + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#ifdef USE_POWER_OF_2 +# define CacheTableTwoDoHash(table, operand1, operand2, opCode) \ + (((((((CalAddress_t)(operand1)) + ((CalAddress_t)(operand2))) / NODE_SIZE) << 2) + opCode + ((CalAddress_t)operand1 & 0x1)+ (((CalAddress_t)operand2 & 0x1)<<1)) &((table)->numBins - 1)) +#else +# define CacheTableTwoDoHash(table, operand1, operand2, opCode) \ + ((((((CalAddress_t)(operand1)) + ((CalAddress_t)(operand2))) / NODE_SIZE) + opCode + ((CalAddress_t)operand1 & 0x1)+ ((CalAddress_t)operand2 & 0x1)) %((table)->numBins)) +/*(((((CalAddress_t)(operand1)) + ((CalAddress_t)(operand2))) + opCode) &((table)->numBins - 1)) +((opCode + (((CalAddress_t)(operand1)) << 1) + (((CalAddress_t)(operand2)) <<2)) &((table)->numBins - 1)) +((opCode + ((((CalAddress_t)(operand1)) + ((CalAddress_t)(operand2))) )+(((CalAddress_t)operand1 & 0x1) << (table->sizeIndex-1)) + (((CalAddress_t)operand2 & 0x1) << (table->sizeIndex-2))) &((table)->numBins - 1)) +((opCode + (((CalAddress_t)(operand1)) << 1) + (((CalAddress_t)(operand2)) << 2)) &((table)->numBins - 1)) +*/ +#endif + +#define CacheTableTwoCompareCacheEntry(entry, _operand1, _operand2, _opCode) \ +((((CalBddNode_t *)(((CalAddress_t)((entry)->operand1)) & ~0x2)) == (_operand1))\ + && \ + ((entry)->operand2 == (_operand2))\ + && \ + ((entry)->opCode == _opCode)) + +#define CacheResultNodeIsForwardedTo(resultBddNode, resultBddId) \ +{ \ + CalBddNode_t *__resultBddNode;\ + __resultBddNode = CAL_BDD_POINTER(resultBddNode); \ + if(CalRequestNodeGetElseRequestNode(__resultBddNode) == FORWARD_FLAG){ \ + resultBddId = __resultBddNode->thenBddId; \ + resultBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(__resultBddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(resultBddNode))); \ + } \ +} + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CacheTableTwoRehash(CalCacheTable_t *cacheTable, int grow); +static void CacheTablePrint(CalCacheTable_t *cacheTable); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Initialize a Cache table using default parameters.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +CalCacheTable_t * +CalCacheTableTwoInit(Cal_BddManager_t *bddManager) +{ + CalCacheTable_t *cacheTable; + cacheTable = Cal_MemAlloc(CalCacheTable_t, 1); + if (cacheTable == Cal_Nil(CalCacheTable_t)){ + CalBddFatalMessage("out of memory"); + } + cacheTable->sizeIndex = CACHE_TABLE_DEFAULT_SIZE_INDEX; + cacheTable->numBins = TABLE_SIZE(cacheTable->sizeIndex); + cacheTable->cacheRatio = CACHE_TABLE_DEFAULT_CACHE_RATIO; + cacheTable->bins = Cal_MemAlloc(CacheEntry_t, cacheTable->numBins); + if(cacheTable->bins == Cal_Nil(CacheEntry_t)){ + CalBddFatalMessage("out of memory"); + } + memset((char *)cacheTable->bins, 0, + cacheTable->numBins*sizeof(CacheEntry_t)); + cacheTable->numInsertions = 0; + cacheTable->numEntries = 0; + cacheTable->numHits = 0; + cacheTable->numLookups = 0; + cacheTable->numCollisions = 0; + return cacheTable; +} + + +/**Function******************************************************************** + + Synopsis [Free a Cache table along with the associated storage.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCacheTableTwoQuit(CalCacheTable_t *cacheTable) +{ + if(cacheTable == Cal_Nil(CalCacheTable_t))return 1; + Cal_MemFree(cacheTable->bins); + Cal_MemFree(cacheTable); + return 0; +} + + +/**Function******************************************************************** + + Synopsis [Directly insert a BDD node in the Cache table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableTwoInsert(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + Cal_Bdd_t g, Cal_Bdd_t result, unsigned long + opCode, int cacheLevel) +{ + int hashValue; + CalCacheTable_t *cacheTable; + CacheEntry_t *bin; + CalBddNode_t *operand1Node, *operand2Node; + + cacheTable = bddManager->cacheTable; + cacheTable->numInsertions++; + hashValue = CacheTableTwoDoHash(cacheTable, CalBddGetBddNode(f), + CalBddGetBddNode(g), opCode); + + bin = cacheTable->bins + hashValue; + if (bin->opCode != CAL_OP_INVALID){ + cacheTable->numCollisions++; + } + else{ + cacheTable->numEntries++; + } + + bin->opCode = opCode; + if ((CalAddress_t)CalBddGetBddNode(f) > + (CalAddress_t)CalBddGetBddNode(g)){ + operand1Node = CalBddGetBddNode(g); + operand2Node = CalBddGetBddNode(f); + } + else{ + operand1Node = CalBddGetBddNode(f); + operand2Node = CalBddGetBddNode(g); + } + + if (cacheLevel){ + /* + * Mark this result as temporary node to be forwarded at the end of + * operation. The reason we can use this tagging is because the + * size of the structure is 16 bytes and we are requiring 8 or 16 byte + * alignment (at least last 3 bits should be zero). + */ + bin->operand1 = (CalBddNode_t *) (((CalAddress_t)operand1Node) | 0x2); + } + else { + bin->operand1 = operand1Node; + } + bin->operand2 = operand2Node; + bin->resultBddNode = CalBddGetBddNode(result); + bin->resultBddId = CalBddGetBddId(result); + return; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCacheTableTwoLookup(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + Cal_Bdd_t g, unsigned long opCode, Cal_Bdd_t + *resultBddPtr) +{ + int hashValue; + CalCacheTable_t *cacheTable; + CacheEntry_t *bin; + CalBddNode_t *operand1Node, *operand2Node; + + cacheTable = bddManager->cacheTable; + cacheTable->numLookups++; + hashValue = CacheTableTwoDoHash(cacheTable, CalBddGetBddNode(f), + CalBddGetBddNode(g), opCode); + + bin = cacheTable->bins+hashValue; + + if ((CalAddress_t)CalBddGetBddNode(f) > (CalAddress_t)CalBddGetBddNode(g)){ + operand1Node = CalBddGetBddNode(g); + operand2Node = CalBddGetBddNode(f); + } + else{ + operand1Node = CalBddGetBddNode(f); + operand2Node = CalBddGetBddNode(g); + } + if (CacheTableTwoCompareCacheEntry(bin, operand1Node, operand2Node, + opCode)){ + CalBddPutBddId((*resultBddPtr), bin->resultBddId); + CalBddPutBddNode((*resultBddPtr), bin->resultBddNode); + cacheTable->numHits++; + return 1; + } + *resultBddPtr = bddManager->bddNull; + return 0; +} + +/**Function******************************************************************** + + Synopsis [Free a Cache table along with the associated storage.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableTwoFlush(CalCacheTable_t *cacheTable) +{ + memset((char *)cacheTable->bins, 0, + cacheTable->numBins*sizeof(CacheEntry_t)); + cacheTable->numEntries = 0; +} + +/**Function******************************************************************** + + Synopsis [Free a Cache table along with the associated storage.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCacheTableTwoFlushAll(CalCacheTable_t *cacheTable) +{ + CalCacheTableTwoFlush(cacheTable); + cacheTable->numInsertions = 0; + cacheTable->numCollisions = 0; + cacheTable->numLookups = 0; + cacheTable->numHits = 0; + return 0; +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableTwoGCFlush(CalCacheTable_t *cacheTable) +{ + int i; + CacheEntry_t *bin = cacheTable->bins; + int numBins = cacheTable->numBins; + if (cacheTable->numEntries == 0) return; + for (i=0; iopCode != CAL_OP_INVALID){ + if (CalBddNodeIsMarked((CAL_BDD_POINTER(bin->operand1))) || + CalBddNodeIsMarked((CAL_BDD_POINTER(bin->operand2))) || + CalBddNodeIsMarked((CAL_BDD_POINTER(bin->resultBddNode)))){ + /* This entry needs to be freed */ + cacheTable->numEntries--; + memset((char *)bin, 0, sizeof(CacheEntry_t)); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableTwoRepackUpdate(CalCacheTable_t *cacheTable) +{ + int i; + CacheEntry_t *bin = cacheTable->bins; + int numBins = cacheTable->numBins; + + for (i=0; iopCode != CAL_OP_INVALID){ + if (CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->operand1))){ + CalBddNodeForward(bin->operand1); + } + if (CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->operand2))){ + CalBddNodeForward(bin->operand2); + } + if (CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->resultBddNode))){ + CalBddNodeForward(bin->resultBddNode); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCheckCacheTableValidity(Cal_BddManager bddManager) +{ + CalCacheTable_t *cacheTable = bddManager->cacheTable; + int i; + CacheEntry_t *bin = cacheTable->bins; + int numBins = cacheTable->numBins; + + for (i=0; iopCode != CAL_OP_INVALID){ + Cal_Assert(CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->operand1)) + == 0); + Cal_Assert(CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->operand2)) + == 0); + Cal_Assert(CalBddNodeIsForwarded(CAL_BDD_POINTER(bin->resultBddNode)) + == 0); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableTwoFixResultPointers(Cal_BddManager_t *bddManager) +{ + CalCacheTable_t *cacheTable = bddManager->cacheTable; + int i; + CacheEntry_t *bin = cacheTable->bins; + int numBins = cacheTable->numBins; + + for (i=0; ioperand1 & 0x2){ /* If the result node is temporary + node */ + CacheResultNodeIsForwardedTo(bin->resultBddNode, bin->resultBddId); + bin->operand1 = (CalBddNode_t *)((CalAddress_t)bin->operand1 & + ~0x2); /* It is no longer temporary */ + } + } +} + + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTablePrint(Cal_BddManager_t *bddManager) +{ + CacheTablePrint(bddManager->cacheTable); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddManagerGetCacheTableData(Cal_BddManager_t *bddManager, + unsigned long *cacheSize, + unsigned long *cacheEntries, + unsigned long *cacheInsertions, + unsigned long *cacheLookups, + unsigned long *cacheHits, + unsigned long *cacheCollisions) +{ + CalCacheTable_t *cacheTable = bddManager->cacheTable; + *cacheSize += cacheTable->numBins; + *cacheEntries += cacheTable->numEntries; + *cacheInsertions += cacheTable->numInsertions; + *cacheLookups += cacheTable->numLookups; + *cacheHits += cacheTable->numHits; + *cacheCollisions += cacheTable->numCollisions; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCacheTableRehash(Cal_BddManager_t *bddManager) +{ + CalCacheTable_t *cacheTable = bddManager->cacheTable; + if((3*cacheTable->numBins < cacheTable->cacheRatio*cacheTable->numEntries) && + (32*cacheTable->numBins < + 8*(bddManager->numNodes))){ + CacheTableTwoRehash(cacheTable, 1); + } +} +/**Function******************************************************************** + + Synopsis [Flushes the entries from the cache which + correspond to the given associationId.] + + Description [] + + SideEffects [Cache entries are affected.] + + SeeAlso [] + +******************************************************************************/ +void +CalCacheTableTwoFlushAssociationId(Cal_BddManager_t *bddManager, int + associationId) +{ + CalCacheTable_t *cacheTable = bddManager->cacheTable; + int i; + CacheEntry_t *bin; + + for (i=0; i < cacheTable->numBins; i++){ + bin = cacheTable->bins+i; + if ((bin->opCode == (CAL_OP_QUANT+associationId)) || + (bin->opCode == (CAL_OP_REL_PROD+associationId)) || + (bin->opCode == (CAL_OP_VAR_SUBSTITUTE+associationId))){ + /* This entry needs to be freed */ + cacheTable->numEntries--; + memset((char *)bin, 0, sizeof(CacheEntry_t)); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +unsigned long +CalCacheTableMemoryConsumption(CalCacheTable_t *cacheTable) +{ + return (unsigned long) (sizeof(cacheTable)+cacheTable->numBins*sizeof(CacheEntry_t)); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CacheTableTwoRehash(CalCacheTable_t *cacheTable,int grow) +{ + CacheEntry_t *oldBins = cacheTable->bins; + int i, hashValue; + int oldNumBins = cacheTable->numBins; + CacheEntry_t *bin, *newBin; + + + if(grow){ + cacheTable->sizeIndex++; + } + else{ + if (cacheTable->sizeIndex <= CACHE_TABLE_DEFAULT_SIZE_INDEX){/* No need to Rehash */ + return; + } + cacheTable->sizeIndex--; + } + + cacheTable->numBins = TABLE_SIZE(cacheTable->sizeIndex); + cacheTable->bins = Cal_MemAlloc(CacheEntry_t, cacheTable->numBins); + if(cacheTable->bins == Cal_Nil(CacheEntry_t)){ + CalBddFatalMessage("out of memory"); + } + + memset((char *)cacheTable->bins, 0, + cacheTable->numBins*sizeof(CacheEntry_t)); + + for(i = 0; i < oldNumBins; i++){ + bin = oldBins+i; + if (bin->opCode == CAL_OP_INVALID) continue; + hashValue = CacheTableTwoDoHash(cacheTable, + bin->operand1, + bin->operand2, + bin->opCode); + newBin = cacheTable->bins+hashValue; + if (newBin->opCode != CAL_OP_INVALID){ + cacheTable->numEntries--; + } + newBin->opCode = bin->opCode; + newBin->operand1 = bin->operand1; + newBin->operand2 = bin->operand2; + newBin->resultBddId = bin->resultBddId; + newBin->resultBddNode = bin->resultBddNode; + } + Cal_MemFree(oldBins); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CacheTablePrint(CalCacheTable_t *cacheTable) +{ + int i; + unsigned long opCode; + CacheEntry_t *bin; + + printf("cacheTable entries(%ld) bins(%ld)\n", + cacheTable->numEntries, cacheTable->numBins); + for(i = 0; i < cacheTable->numBins; i++){ + bin = cacheTable->bins+i; + opCode = bin->opCode; + if (opCode != CAL_OP_INVALID){ + fprintf(stdout,"Op = %s O1 = %lx, O2 = %lx RId = %d, RNode = %lx\n", + ((opCode == CAL_OP_OR) ? "OR" : ((opCode == CAL_OP_AND) ? "AND" : + ((opCode == + CAL_OP_QUANT) ? + "QUANT" : + ((opCode == + CAL_OP_REL_PROD) + ? + "RELPROD" + : + "Nothing")))), + (CalAddress_t)bin->operand1, + (CalAddress_t)bin->operand2, bin->resultBddId, + (CalAddress_t)bin->resultBddNode); + } + } +} + + +#ifdef CACHE_TABLE_TWO_TEST +main(int argc, char **argv) +{ + Cal_Bdd_t f1, f2, f3, f4, f5, result; + Cal_BddManager_t *bddManager = Cal_BddManagerInit(); + int i; + CalCacheTable_t *cacheTable; + + for (i=0; i<5; i++){ + Cal_BddManagerCreateNewVarLast(bddManager); + } + + CalCacheTablePrint(bddManager); + + f1 = bddManager->varBdds[1]; + f2 = bddManager->varBdds[2]; + f3 = bddManager->varBdds[3]; + f4 = bddManager->varBdds[4]; + f5 = bddManager->varBdds[5]; + + CalCacheTableTwoInsert(bddManager, f1, f2, f3, CAL_OP_OR, 0); + CalCacheTableTwoInsert(bddManager, f3, f2, f4, CAL_OP_AND,0); + CalCacheTableTwoInsert(bddManager, f3, f4, f5, CAL_OP_REL_PROD,0); + /*CacheTableTwoRehash(bddManager->cacheTableArray[2], 1);*/ + CalCacheTablePrint(bddManager); + + /* Look up */ + CalCacheTableTwoLookup(bddManager, f3, f2, CAL_OP_AND, &result); + assert(CalBddIsEqual(result, f4)); + + CalCacheTableTwoLookup(bddManager, f3, f2, CAL_OP_OR, &result); + assert(CalBddIsEqual(result, bddManager->bddNull)); + + CalCacheTableTwoLookup(bddManager, f3, f1, CAL_OP_OR, &result); + assert(CalBddIsEqual(result, bddManager->bddNull)); + + /* Another look up */ + CalCacheTableTwoLookup(bddManager, f4, f3, CAL_OP_REL_PROD, &result); + assert(CalBddIsEqual(result, f5)); + + /* It will bump off the entry (f2, f2, AND, f4)*/ + CalCacheTableTwoInsert(bddManager, f3, f2, f1, CAL_OP_AND,0); + /* Do lookup and see if that's what happened */ + CalCacheTableTwoLookup(bddManager, f3, f2, CAL_OP_AND, &result); + assert(CalBddIsEqual(result, f1)); + + /* + * Rehashing will visit (f2, f3, AND, f4) first and then (f2, f3, + * AND, f1) + * Hence the we should have (f2, f3, AND, f1) in the first slot + */ + CacheTableTwoRehash(bddManager->cacheTable, 1); + CalCacheTableTwoLookup(bddManager, f3, f2, CAL_OP_AND, &result); + assert(CalBddIsEqual(result, f1)); + Cal_BddManagerQuit(bddManager); + +} +#endif diff --git a/calDesc.html b/calDesc.html new file mode 100644 index 0000000..2d73b56 --- /dev/null +++ b/calDesc.html @@ -0,0 +1,28 @@ + +The cal package: Overview + + +

The cal package

+

Header CAL file for exported data structures and functions.

+

By Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu)

+ + + +
+ + + +
+ +Last updated on 970711 20h11 + + + diff --git a/calDoc.txt b/calDoc.txt new file mode 100644 index 0000000..d1d421a --- /dev/null +++ b/calDoc.txt @@ -0,0 +1,1482 @@ +The cal package + +Header CAL file for exported data structures and functions. + +Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) Jagesh V. Sanghavi +(sanghavi@eecs.berkeley.edu) + +********************************************************************** + +Cal_AssociationInit() Creates or finds a variable association. + +Cal_AssociationQuit() Deletes the variable association given by id + +Cal_AssociationSetCurrent() Sets the current variable association to the + one given by id and returns the ID of the old + association. + +Cal_BddAnd() Returns the BDD for logical AND of argument + BDDs + +Cal_BddBetween() Returns a minimal BDD whose function contains + fMin and is contained in fMax. + +Cal_BddCofactor() Returns the generalized cofactor of BDD f with + respect to BDD c. + +Cal_BddCompose() composition - substitute a BDD variable by a + function + +Cal_BddDependsOn() Returns 1 if f depends on var and returns 0 + otherwise. + +Cal_BddDumpBdd() Write a BDD to a file + +Cal_BddDynamicReordering() Specify dynamic reordering technique. + +Cal_BddElse() Returns the negative cofactor of the argument + BDD with respect to the top variable of the + BDD. + +Cal_BddExists() Returns the result of existentially quantifying + some variables from the given BDD. + +Cal_BddForAll() Returns the result of universally quantifying + some variables from the given BDD. + +Cal_BddFree() Frees the argument BDD. + +Cal_BddFunctionPrint() Prints the function implemented by the argument + BDD + +Cal_BddFunctionProfileMultiple() + Returns a "function profile" for fArray. + +Cal_BddFunctionProfile() Returns a "function profile" for f. + +Cal_BddGetIfId() Returns the id of the top variable of the + argument BDD. + +Cal_BddGetIfIndex() Returns the index of the top variable of the + argument BDD. + +Cal_BddGetRegular() Returns a BDD with positive from a given BDD + with arbitrary phase + +Cal_BddITE() Returns the BDD for logical If-Then-Else + Description [Returns the BDD for the logical + operation IF f THEN g ELSE h - f g + f' h + +Cal_BddIdentity() Returns the duplicate BDD of the argument BDD. + +Cal_BddIf() Returns the BDD corresponding to the top + variable of the argument BDD. + +Cal_BddImplies() Computes a BDD that implies conjunction of f + and Cal_BddNot(g) + +Cal_BddIntersects() Computes a BDD that implies conjunction of f + and g. + +Cal_BddIsBddConst() Returns 1 if the argument BDD is a constant, 0 + otherwise. + +Cal_BddIsBddNull() Returns 1 if the argument BDD is NULL, 0 + otherwise. + +Cal_BddIsBddOne() Returns 1 if the argument BDD is constant one, + 0 otherwise. + +Cal_BddIsBddZero() Returns 1 if the argument BDD is constant zero, + 0 otherwise. + +Cal_BddIsCube() Returns 1 if the argument BDD is a cube, 0 + otherwise + +Cal_BddIsEqual() Returns 1 if argument BDDs are equal, 0 + otherwise. + +Cal_BddIsProvisional() Returns 1, if the given user BDD contains + provisional BDD node. + +Cal_BddManagerCreateNewVarAfter() + Creates and returns a new variable after the + specified one in the variable order. + +Cal_BddManagerCreateNewVarBefore() + Creates and returns a new variable before the + specified one in the variable order. + +Cal_BddManagerCreateNewVarFirst() + Creates and returns a new variable at the start + of the variable order. + +Cal_BddManagerCreateNewVarLast() + Creates and returns a new variable at the end + of the variable order. + +Cal_BddManagerGC() Invokes the garbage collection at the manager + level. + +Cal_BddManagerGetHooks() Returns the hooks field of the manager. + +Cal_BddManagerGetNumNodes() Returns the number of BDD nodes + +Cal_BddManagerGetVarWithId() Returns the variable with the specified id, + null if no such variable exists + +Cal_BddManagerGetVarWithIndex() + Returns the variable with the specified index, + null if no such variable exists + +Cal_BddManagerInit() Creates and initializes a new BDD manager. + +Cal_BddManagerQuit() Frees the BDD manager and all the associated + allocations + +Cal_BddManagerSetGCLimit() Sets the limit of the garbage collection. + +Cal_BddManagerSetHooks() Sets the hooks field of the manager. + +Cal_BddManagerSetParameters() Sets appropriate fields of BDD Manager. + +Cal_BddMultiwayAnd() Returns the BDD for logical AND of argument + BDDs + +Cal_BddMultiwayOr() Returns the BDD for logical OR of argument BDDs + +Cal_BddMultiwayXor() Returns the BDD for logical XOR of argument + BDDs + +Cal_BddNand() Returns the BDD for logical NAND of argument + BDDs + +Cal_BddNewVarBlock() Creates and returns a variable block used for + controlling dynamic reordering. + +Cal_BddNodeLimit() Sets the node limit to new_limit and returns + the old limit. + +Cal_BddNor() Returns the BDD for logical NOR of argument + BDDs + +Cal_BddNot() Returns the complement of the argument BDD. + +Cal_BddOne() Returns the BDD for the constant one + +Cal_BddOr() Returns the BDD for logical OR of argument BDDs + +Cal_BddOverflow() Returns 1 if the node limit has been exceeded, + 0 otherwise. The overflow flag is cleared. + +Cal_BddPairwiseAnd() Returns an array of BDDs obtained by logical + AND of BDD pairs specified by an BDD array in + which a BDD at an even location is paired with + a BDD at an odd location of the array + +Cal_BddPairwiseOr() Returns an array of BDDs obtained by logical OR + of BDD pairs specified by an BDD array in + which a BDD at an even location is paired with + a BDD at an odd location of the array + +Cal_BddPairwiseXor() Returns an array of BDDs obtained by logical + XOR of BDD pairs specified by an BDD array in + which a BDD at an even location is paired with + a BDD at an odd location of the array + +Cal_BddPrintBdd() Prints a BDD in the human readable form. + +Cal_BddPrintFunctionProfileMultiple() + Cal_BddPrintFunctionProfileMultiple is like + Cal_BddPrintFunctionProfile except for multiple + BDDs + +Cal_BddPrintFunctionProfile() Cal_BddPrintFunctionProfile is like + Cal_BddPrintProfile except it + displays a function profile for f + +Cal_BddPrintProfileMultiple() Cal_BddPrintProfileMultiple is like + Cal_BddPrintProfile except it + displays the profile for a set of BDDs + +Cal_BddPrintProfile() Displays the node profile for f on fp. + lineLength specifies the + maximum line length. varNamingFn is as in + Cal_BddPrintBdd. + +Cal_BddProfileMultiple() + +Cal_BddProfile() Returns a "node profile" of f, i.e., the number + of nodes at each level in f. + +Cal_BddReduce() Returns a BDD which agrees with f for all + valuations which satisfy c. + +Cal_BddRelProd() Returns the result of taking the logical AND of + the argument BDDs and existentially + quantifying some variables from the product. + +Cal_BddReorder() Invoke the current dynamic reodering method. + +Cal_BddSatisfySupport() Returns a special cube contained in f. + +Cal_BddSatisfyingFraction() Returns the fraction of valuations which make f + true. (Note that this fraction is independent + of whatever set of variables f is supposed to + be a function of) + +Cal_BddSatisfy() Returns a BDD which implies f, true for + some valuation on which f is true, and which + has at most one node at each + level + +Cal_BddSetGCMode() Sets the garbage collection mode, 0 means the + garbage collection should be turned off, 1 + means garbage collection should be on. + +Cal_BddSizeMultiple() The routine is like Cal_BddSize, but takes a + null-terminated array of BDDs + and accounts for sharing of nodes. + +Cal_BddSize() Returns the number of nodes in f when negout is + nonzero. If negout is zero, we pretend that + the BDDs don't have negative-output pointers. + +Cal_BddStats() Prints miscellaneous BDD statistics + +Cal_BddSubstitute() Substitute a set of variables by functions + +Cal_BddSupport() returns the support of f as a null-terminated + array of variables + +Cal_BddSwapVars() Return a function obtained by swapping two + variables + +Cal_BddThen() Returns the positive cofactor of the argument + BDD with respect to the top variable of the + BDD. + +Cal_BddTotalSize() Returns the number of nodes in the Unique table + +Cal_BddType() Returns type of a BDD ( 0, 1, +var, -var, + ovrflow, nonterminal) + +Cal_BddUnFree() Unfrees the argument BDD. + +Cal_BddUndumpBdd() Reads a BDD from a file + +Cal_BddVarBlockReorderable() Sets the reoderability of a particular block. + +Cal_BddVarSubstitute() Substitute a set of variables by set of another + variables. + +Cal_BddVars() Returns the number of BDD variables + +Cal_BddXnor() Returns the BDD for logical exclusive NOR of + argument BDDs + +Cal_BddXor() Returns the BDD for logical exclusive OR of + argument BDDs + +Cal_BddZero() Returns the BDD for the constant zero + +Cal_MemAllocation() Returns the memory allocated. + +Cal_MemFatal() Prints an error message and exits. + +Cal_MemFreeBlock() Frees the block. + +Cal_MemFreeRecMgr() Frees all the storage associated with the + specified record manager. + +Cal_MemFreeRec() Frees a record managed by the indicated record + manager. + +Cal_MemGetBlock() Allocates a new block of the specified size. + +Cal_MemNewRecMgr() Creates a new record manager with the given + record size. + +Cal_MemNewRec() Allocates a record from the specified record + manager. + +Cal_MemResizeBlock() Expands or contracts the block to a new size. + We try to avoid moving the block if possible. + +Cal_PerformanceTest() Main routine for testing performances of + various routines. + +Cal_PipelineCreateProvisionalBdd() + Create a provisional BDD in the pipeline. + +Cal_PipelineExecute() Executes a pipeline. + +Cal_PipelineInit() Initialize a BDD pipeline. + +Cal_PipelineQuit() Resets the pipeline freeing all resources. + +Cal_PipelineSetDepth() Set depth of a BDD pipeline. + +Cal_PipelineUpdateProvisionalBdd() + Update a provisional Bdd obtained during + pipelining. + +Cal_TempAssociationAugment() Adds to the temporary variable association. + +Cal_TempAssociationInit() Sets the temporary variable association. + +Cal_TempAssociationQuit() Cleans up temporary association + +********************************************************************** + + + +int +Cal_AssociationInit( + Cal_BddManager bddManager, + Cal_Bdd * associationInfoU + int pairs +) + Creates or finds a variable association. The association is specified by + associationInfo, which is a an array of BDD with Cal_BddNull(bddManager) as + the end marker. If pairs is 0, the array is assumed to be an array of + variables. In this case, each variable is paired with constant BDD one. Such + an association may viewed as specifying a set of variables for use with + routines such as Cal_BddExists. If pair is not 0, then the even numbered + array elements should be variables and the odd numbered elements should be + the BDDs which they are mapped to. In both cases, the return value is an + integer identifier for this association. If the given association is + equivalent to one which already exists, the same identifier is used for + both, and the reference count of the association is increased by one. + + Side Effects: None + +void +Cal_AssociationQuit( + Cal_BddManager bddManager, + int associationId +) + Decrements the reference count of the variable association with identifier + id, and frees it if the reference count becomes zero. + + Side Effects: None + +int +Cal_AssociationSetCurrent( + Cal_BddManager bddManager, + int associationId +) + Sets the current variable association to the one given by id and returns the + ID of the old association. An id of -1 indicates the temporary association + + Side Effects: None + +Cal_Bdd +Cal_BddAnd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical AND of f and g + + Side Effects: None + +Cal_Bdd +Cal_BddBetween( + Cal_BddManager bddManager, + Cal_Bdd fMinUserBdd, + Cal_Bdd fMaxUserBdd +) + Returns a minimal BDD f which is contains fMin and is contained in fMax ( + fMin <= f <= fMax). This operation is typically used in state space searches + to simplify the representation for the set of states wich will be expanded + at each step (Rk Rk-1' <= f <= Rk). + + Side Effects: None + +Cal_Bdd +Cal_BddCofactor( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd cUserBdd +) + Returns the generalized cofactor of BDD f with respect to BDD c. The + constrain operator given by Coudert et al (ICCAD90) is used to find the + generalized cofactor. + + Side Effects: None. + +Cal_Bdd +Cal_BddCompose( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd, + Cal_Bdd hUserBdd +) + Returns the BDD obtained by substituting a variable by a function + + Side Effects: None + +int +Cal_BddDependsOn( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd varUserBdd +) + Returns 1 if f depends on var and returns 0 otherwise. + + Side Effects: None + +int +Cal_BddDumpBdd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd * userVars, + FILE * fp +) + Writes an encoded description of the BDD to the file given by fp. The + argument vars should be a null-terminated array of variables that include + the support of f . These variables need not be in order of increasing index. + The function returns a nonzero value if f was written to the file + successfully. + + Side Effects: required + +void +Cal_BddDynamicReordering( + Cal_BddManager bddManager, + int technique +) + Selects the method for dynamic reordering. + + Side Effects: None + +Cal_Bdd +Cal_BddElse( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the negative cofactor of the argument BDD with respect to the top + variable of the BDD. + + Side Effects: The reference count of the returned BDD is increased by 1. + +Cal_Bdd +Cal_BddExists( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns the BDD for f with all the variables that are paired with something + in the current variable association existentially quantified out. + + Side Effects: None. + +Cal_Bdd +Cal_BddForAll( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns the BDD for f with all the variables that are paired with something + in the current variable association universally quantified out. + + Side Effects: None. + +void +Cal_BddFree( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Frees the argument BDD. It is an error to free a BDD more than once. + + Side Effects: The reference count of the argument BDD is decreased by 1. + +void +Cal_BddFunctionPrint( + Cal_BddManager bddManager, + Cal_Bdd userBdd, + char * name +) + Prints the function implemented by the argument BDD + + Side Effects: None + +void +Cal_BddFunctionProfileMultiple( + Cal_BddManager bddManager, + Cal_Bdd * fUserBddArray, + long * funcCounts +) + optional + + Side Effects: None + +void +Cal_BddFunctionProfile( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + long * funcCounts +) + The nth entry of the function profile array is the number of subfunctions of + f which may be obtained by restricting the variables whose index is less + than n. An entry of zero indicates that f is independent of the variable + with the corresponding index. + + +Cal_BddId_t +Cal_BddGetIfId( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the id of the top variable of the argument BDD. + + Side Effects: None + +Cal_BddId_t +Cal_BddGetIfIndex( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the index of the top variable of the argument BDD. + + Side Effects: None + +Cal_Bdd +Cal_BddGetRegular( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns a BDD with positive from a given BDD with arbitrary phase + + Side Effects: None. + +Cal_Bdd +Cal_BddITE( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd, + Cal_Bdd hUserBdd +) + Returns the BDD for logical If-Then-Else Description [Returns the BDD for + the logical operation IF f THEN g ELSE h - f g + f' h + + Side Effects: None + +Cal_Bdd +Cal_BddIdentity( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the duplicate BDD of the argument BDD. + + Side Effects: The reference count of the BDD is increased by 1. + +Cal_Bdd +Cal_BddIf( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the BDD corresponding to the top variable of the argument BDD. + + Side Effects: None. + +Cal_Bdd +Cal_BddImplies( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Computes a BDD that implies conjunction of f and Cal_BddNot(g) + + Side Effects: none + +Cal_Bdd +Cal_BddIntersects( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Computes a BDD that implies conjunction of f and g. + + Side Effects: None + +int +Cal_BddIsBddConst( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns 1 if the argument BDD is either constant one or constant zero, + otherwise returns 0. + + Side Effects: None. + +int +Cal_BddIsBddNull( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns 1 if the argument BDD is NULL, 0 otherwise. + + Side Effects: None. + +int +Cal_BddIsBddOne( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns 1 if the argument BDD is constant one, 0 otherwise. + + Side Effects: None. + +int +Cal_BddIsBddZero( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns 1 if the argument BDD is constant zero, 0 otherwise. + + Side Effects: None. + +int +Cal_BddIsCube( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns 1 if the argument BDD is a cube, 0 otherwise + + Side Effects: None + +int +Cal_BddIsEqual( + Cal_BddManager bddManager, + Cal_Bdd userBdd1, + Cal_Bdd userBdd2 +) + Returns 1 if argument BDDs are equal, 0 otherwise. + + Side Effects: None. + +int +Cal_BddIsProvisional( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns 1, if the given user BDD contains provisional BDD node. + + Side Effects: None. + +Cal_Bdd +Cal_BddManagerCreateNewVarAfter( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Creates and returns a new variable after the specified one in the variable + order. + + Side Effects: None + +Cal_Bdd +Cal_BddManagerCreateNewVarBefore( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Creates and returns a new variable before the specified one in the variable + order. + + Side Effects: None + +Cal_Bdd +Cal_BddManagerCreateNewVarFirst( + Cal_BddManager bddManager +) + Creates and returns a new variable at the start of the variable order. + + Side Effects: None + +Cal_Bdd +Cal_BddManagerCreateNewVarLast( + Cal_BddManager bddManager +) + Creates and returns a new variable at the end of the variable order. + + Side Effects: None + +int +Cal_BddManagerGC( + Cal_BddManager bddManager +) + For each variable in the increasing id free nodes with reference count equal + to zero freeing a node results in decrementing reference count of then and + else nodes by one. + + Side Effects: None. + +void * +Cal_BddManagerGetHooks( + Cal_BddManager bddManager +) + Returns the hooks field of the manager. + + Side Effects: None + +unsigned long +Cal_BddManagerGetNumNodes( + Cal_BddManager bddManager +) + Returns the number of BDD nodes + + Side Effects: None + +Cal_Bdd +Cal_BddManagerGetVarWithId( + Cal_BddManager bddManager, + Cal_BddId_t id +) + Returns the variable with the specified id, null if no such variable exists + + Side Effects: None + +Cal_Bdd +Cal_BddManagerGetVarWithIndex( + Cal_BddManager bddManager, + Cal_BddIndex_t index +) + Returns the variable with the specified index, null if no such variable + exists + + Side Effects: None + +Cal_BddManager +Cal_BddManagerInit( + +) + Initializes and allocates fields of the BDD manager. Some of the fields are + initialized for maxNumVars+1 or numVars+1, whereas some of them are + initialized for maxNumVars or numVars. The first kind of fields are + associated with the id of a variable and the second ones are with the index + of the variable. + + Side Effects: None + +int +Cal_BddManagerQuit( + Cal_BddManager bddManager +) + Frees the BDD manager and all the associated allocations + + Side Effects: None + +void +Cal_BddManagerSetGCLimit( + Cal_BddManager manager +) + It tries to set the limit at twice the number of nodes in the manager at the + current point. However, the limit is not allowed to fall below the + MIN_GC_LIMIT or to exceed the value of node limit (if one exists). + + Side Effects: None. + +void +Cal_BddManagerSetHooks( + Cal_BddManager bddManager, + void * hooks +) + Sets the hooks field of the manager. + + Side Effects: Hooks field changes. + +void +Cal_BddManagerSetParameters( + Cal_BddManager bddManager, + long reorderingThresh + long maxForwardedNode + double repackAfterGCThr + double tableRepackThres +) + This function is used to set the parameters which are used to control the + reordering process. "reorderingThreshold" determines the number of nodes + below which reordering will NOT be invoked, "maxForwardedNodes" determines + the maximum number of forwarded nodes which are allowed (at that point the + cleanup must be done), and "repackingThreshold" determines the fraction of + the page utilized below which repacking has to be invoked. These parameters + have different affect on the computational and memory usage aspects of + reordeing. For instance, higher value of "maxForwardedNodes" will result in + process consuming more memory, and a lower value on the other hand would + invoke the cleanup process repeatedly resulting in increased computation. + + Side Effects: None + +Cal_Bdd +Cal_BddMultiwayAnd( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns the BDD for logical AND of set of BDDs in the bddArray + + Side Effects: None + +Cal_Bdd +Cal_BddMultiwayOr( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns the BDD for logical OR of set of BDDs in the bddArray + + Side Effects: None + +Cal_Bdd +Cal_BddMultiwayXor( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns the BDD for logical XOR of set of BDDs in the bddArray + + Side Effects: None + +Cal_Bdd +Cal_BddNand( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical NAND of f and g + + Side Effects: None + +Cal_Block +Cal_BddNewVarBlock( + Cal_BddManager bddManager, + Cal_Bdd variable, + long length +) + The block is specified by passing the first variable and the length of the + block. The "length" number of consecutive variables starting from "variable" + are put in the block. + + Side Effects: A new block is created. + +long +Cal_BddNodeLimit( + Cal_BddManager bddManager, + long newLimit +) + Sets the node limit to new_limit and returns the old limit. + + Side Effects: Threshold for garbage collection may change + +Cal_Bdd +Cal_BddNor( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical NOR of f and g + + Side Effects: None + +Cal_Bdd +Cal_BddNot( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the complement of the argument BDD. + + Side Effects: The reference count of the argument BDD is increased by 1. + +Cal_Bdd +Cal_BddOne( + Cal_BddManager bddManager +) + Returns the BDD for the constant one + + Side Effects: None + +Cal_Bdd +Cal_BddOr( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical OR of f and g + + Side Effects: None + +int +Cal_BddOverflow( + Cal_BddManager bddManager +) + Returns 1 if the node limit has been exceeded, 0 otherwise. The overflow + flag is cleared. + + Side Effects: None + +Cal_Bdd * +Cal_BddPairwiseAnd( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns an array of BDDs obtained by logical AND of BDD pairs specified by + an BDD array in which a BDD at an even location is paired with a BDD at an + odd location of the array + + Side Effects: None + +Cal_Bdd * +Cal_BddPairwiseOr( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns an array of BDDs obtained by logical OR of BDD pairs specified by an + BDD array in which a BDD at an even location is paired with a BDD at an odd + location of the array + + Side Effects: None + +Cal_Bdd * +Cal_BddPairwiseXor( + Cal_BddManager bddManager, + Cal_Bdd * userBddArray +) + Returns an array of BDDs obtained by logical XOR of BDD pairs specified by + an BDD array in which a BDD at an even location is paired with a BDD at an + odd location of the array + + Side Effects: None + +void +Cal_BddPrintBdd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_VarNamingFn_t VarNamingFn, + Cal_TerminalIdFn_ TerminalIdFn, + Cal_Pointer_t env, + FILE * fp +) + Prints a human-readable representation of the BDD f to the file given by fp. + The namingFn should be a pointer to a function taking a bddManager, a BDD + and the pointer given by env. This function should return either a null + pointer or a srting that is the name of the supplied variable. If it returns + a null pointer, a default name is generated based on the index of the + variable. It is also legal for naminFN to e null; in this case, default + names are generated for all variables. The macro bddNamingFnNone is a null + pointer of suitable type. terminalIdFn should be apointer to a function + taking a bddManager and two longs. plus the pointer given by the env. It + should return either a null pointer. If it returns a null pointer, or if + terminalIdFn is null, then default names are generated for the terminals. + The macro bddTerminalIdFnNone is a null pointer of suitable type. + + Side Effects: None. + +void +Cal_BddPrintFunctionProfileMultiple( + Cal_BddManager bddManager, + Cal_Bdd * userBdds, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp +) + optional + + Side Effects: None + +void +Cal_BddPrintFunctionProfile( + Cal_BddManager bddManager, + Cal_Bdd f, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp +) + optional + + Side Effects: None + +void +Cal_BddPrintProfileMultiple( + Cal_BddManager bddManager, + Cal_Bdd * userBdds, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp +) + optional + + Side Effects: None + +void +Cal_BddPrintProfile( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp +) + optional + + Side Effects: None + +void +Cal_BddProfileMultiple( + Cal_BddManager bddManager, + Cal_Bdd * fUserBddArray, + long * levelCounts, + int negout +) + optional + + Side Effects: None + +void +Cal_BddProfile( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + long * levelCounts, + int negout +) + negout is as in Cal_BddSize. levelCounts should be an array of size + Cal_BddVars(bddManager)+1 to hold the profile. + + Side Effects: None + +Cal_Bdd +Cal_BddReduce( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd cUserBdd +) + Returns a BDD which agrees with f for all valuations which satisfy c. The + result is usually smaller in terms of number of BDD nodes than f. This + operation is typically used in state space searches to simplify the + representation for the set of states wich will be expanded at each step. + + Side Effects: None + +Cal_Bdd +Cal_BddRelProd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for the logical AND of f and g with all the variables that + are paired with something in the current variable association existentially + quantified out. + + Side Effects: None. + +void +Cal_BddReorder( + Cal_BddManager bddManager +) + Invoke the current dynamic reodering method. + + Side Effects: Index of a variable may change due to reodering + +Cal_Bdd +Cal_BddSatisfySupport( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + The returned BDD which implies f, is true for some valuation on which f is + true, which has at most one node at each level, and which has exactly one + node corresponding to each variable which is associated with something in + the current variable association. + + Side Effects: required + +double +Cal_BddSatisfyingFraction( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + optional + + Side Effects: required + +Cal_Bdd +Cal_BddSatisfy( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + optional + + Side Effects: required + +void +Cal_BddSetGCMode( + Cal_BddManager bddManager, + int gcMode +) + Sets the garbage collection mode, 0 means the garbage collection should be + turned off, 1 means garbage collection should be on. + + Side Effects: None. + +long +Cal_BddSizeMultiple( + Cal_BddManager bddManager, + Cal_Bdd * fUserBddArray, + int negout +) + optional + + Side Effects: None + +long +Cal_BddSize( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + int negout +) + optional + + Side Effects: None + +void +Cal_BddStats( + Cal_BddManager bddManager, + FILE * fp +) + Prints miscellaneous BDD statistics + + Side Effects: None + +Cal_Bdd +Cal_BddSubstitute( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns a BDD for f using the substitution defined by current variable + association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously + + Side Effects: None + +void +Cal_BddSupport( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd * support +) + optional + + Side Effects: None + +Cal_Bdd +Cal_BddSwapVars( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd, + Cal_Bdd hUserBdd +) + Returns the BDD obtained by simultaneously substituting variable g by + variable h and variable h and variable g in the BDD f + + Side Effects: None + +Cal_Bdd +Cal_BddThen( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Returns the positive cofactor of the argument BDD with respect to the top + variable of the BDD. + + Side Effects: The reference count of the returned BDD is increased by 1. + +unsigned long +Cal_BddTotalSize( + Cal_BddManager bddManager +) + Returns the number of nodes in the Unique table + + Side Effects: None + +int +Cal_BddType( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns BDD_TYPE_ZERO if f is false, BDD_TYPE_ONE if f is true, + BDD_TYPE_POSVAR is f is an unnegated variable, BDD_TYPE_NEGVAR if f is a + negated variable, BDD_TYPE_OVERFLOW if f is null, and BDD_TYPE_NONTERMINAL + otherwise. + + Side Effects: None + +void +Cal_BddUnFree( + Cal_BddManager bddManager, + Cal_Bdd userBdd +) + Unfrees the argument BDD. It is an error to pass a BDD with reference count + of zero to be unfreed. + + Side Effects: The reference count of the argument BDD is increased by 1. + +Cal_Bdd +Cal_BddUndumpBdd( + Cal_BddManager bddManager, + Cal_Bdd * userVars, + FILE * fp, + int * error +) + Loads an encoded description of a BDD from the file given by fp. The + argument vars should be a null terminated array of variables that will + become the support of the BDD. As in Cal_BddDumpBdd, these need not be in + the order of increasing index. If the same array of variables in used in + dumping and undumping, the BDD returned will be equal to the one that was + dumped. More generally, if array v1 is used when dumping, and the array v2 + is used when undumping, the BDD returned will be equal to the original BDD + with the ith variable in v2 substituted for the ith variable in v1 for all + i. Null BDD is returned in the operation fails for reason (node limit + reached, I/O error, invalid file format, etc.). In this case, an error code + is stored in error. the code will be one of the following. + CAL_BDD_UNDUMP_FORMAT Invalid file format CAL_BDD_UNDUMP_OVERFLOW Node limit + exceeded CAL_BDD_UNDUMP_IOERROR File I/O error CAL_BDD_UNDUMP_EOF Unexpected + EOF + + Side Effects: required + +void +Cal_BddVarBlockReorderable( + Cal_BddManager bddManager, + Cal_Block block, + int reorderable +) + If a block is reorderable, the child blocks are recursively involved in + swapping. + + Side Effects: None. + +Cal_Bdd +Cal_BddVarSubstitute( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd +) + Returns a BDD for f using the substitution defined by current variable + association. It is assumed that each variable is replaced by another + variable. For the substitution of a variable by a function, use + Cal_BddSubstitute instead. + + Side Effects: None + +long +Cal_BddVars( + Cal_BddManager bddManager +) + Returns the number of BDD variables + + Side Effects: None + +Cal_Bdd +Cal_BddXnor( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical exclusive NOR of f and g + + Side Effects: None + +Cal_Bdd +Cal_BddXor( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + Returns the BDD for logical exclusive OR of f and g + + Side Effects: None + +Cal_Bdd +Cal_BddZero( + Cal_BddManager bddManager +) + Returns the BDD for the constant zero + + Side Effects: None + +Cal_Address_t +Cal_MemAllocation( + +) + Returns the memory allocated. + + Side Effects: required + +void +Cal_MemFatal( + char * message +) + Prints an error message and exits. + + Side Effects: required + +void +Cal_MemFreeBlock( + Cal_Pointer_t p +) + Frees the block. + + Side Effects: required + +void +Cal_MemFreeRecMgr( + Cal_RecMgr mgr +) + Frees all the storage associated with the specified record manager. + + Side Effects: required + +void +Cal_MemFreeRec( + Cal_RecMgr mgr, + Cal_Pointer_t rec +) + Frees a record managed by the indicated record manager. + + Side Effects: required + +Cal_Pointer_t +Cal_MemGetBlock( + Cal_Address_t size +) + Allocates a new block of the specified size. + + Side Effects: required + +Cal_RecMgr +Cal_MemNewRecMgr( + int size +) + Creates a new record manager with the given record size. + + Side Effects: required + +Cal_Pointer_t +Cal_MemNewRec( + Cal_RecMgr mgr +) + Allocates a record from the specified record manager. + + Side Effects: required + +Cal_Pointer_t +Cal_MemResizeBlock( + Cal_Pointer_t p, + Cal_Address_t newSize +) + Expands or contracts the block to a new size. We try to avoid moving the + block if possible. + + Side Effects: required + +int +Cal_PerformanceTest( + Cal_BddManager bddManager, + Cal_Bdd * outputBddArray, + int numFunctions, + int iteration, + int seed, + int andPerformanceFl + int multiwayPerforma + int onewayPerformanc + int quantifyPerforma + int composePerforman + int relprodPerforman + int swapPerformanceF + int substitutePerfor + int sanityCheckFlag, + int computeMemoryOve + int superscalarFlag +) + optional + + Side Effects: required + +Cal_Bdd +Cal_PipelineCreateProvisionalBdd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd +) + The provisional BDD is automatically freed once the pipeline is quitted. + + +int +Cal_PipelineExecute( + Cal_BddManager bddManager +) + All the results are computed. User should update the BDDs of interest. + Eventually this feature would become transparent. + + Side Effects: required + +int +Cal_PipelineInit( + Cal_BddManager bddManager, + Cal_BddOp_t bddOp +) + All the operations for this pipeline must be of the same kind. + + Side Effects: None. + +void +Cal_PipelineQuit( + Cal_BddManager bddManager +) + The user must make sure to update all provisional BDDs of interest before + calling this routine. + + +void +Cal_PipelineSetDepth( + Cal_BddManager bddManager, + int depth +) + The "depth" determines the amount of dependency we would allow in pipelined + computation. + + Side Effects: None. + +Cal_Bdd +Cal_PipelineUpdateProvisionalBdd( + Cal_BddManager bddManager, + Cal_Bdd provisionalBdd +) + The provisional BDD is automatically freed after quitting pipeline. + + +void +Cal_TempAssociationAugment( + Cal_BddManager bddManager, + Cal_Bdd * associationInfoU + int pairs +) + Pairs is 0 if the information represents only a list of variables rather + than a full association. + + Side Effects: None + +void +Cal_TempAssociationInit( + Cal_BddManager bddManager, + Cal_Bdd * associationInfoU + int pairs +) + Pairs is 0 if the information represents only a list of variables rather + than a full association. + + Side Effects: None + +void +Cal_TempAssociationQuit( + Cal_BddManager bddManager +) + Cleans up temporary associationoptional + + Side Effects: None + diff --git a/calDump.c b/calDump.c new file mode 100644 index 0000000..0c0c09e --- /dev/null +++ b/calDump.c @@ -0,0 +1,628 @@ +/**CFile*********************************************************************** + + FileName [calDump.c] + + PackageName [cal] + + Synopsis [BDD library dump/undump routines] + + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long. + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calDump.c,v 1.1.1.3 1998/05/04 00:58:56 hsv Exp $] + +******************************************************************************/ +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +#define MAGIC_COOKIE 0x5e02f795l +#define CAL_BDD_IOERROR 100 + +#define TRUE_ENCODING 0xffffff00l +#define FALSE_ENCODING 0xffffff01l +#define POSVAR_ENCODING 0xffffff02l +#define NEGVAR_ENCODING 0xffffff03l +#define POSNODE_ENCODING 0xffffff04l +#define NEGNODE_ENCODING 0xffffff05l +#define NODELABEL_ENCODING 0xffffff06l +#define CONSTANT_ENCODING 0xffffff07l + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +static long indexMask[] = {0xffl, 0xffffl, 0xffffffl}; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void Write(Cal_BddManager_t * bddManager, unsigned long n, int bytes, FILE * fp); +static void BddDumpBddStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, FILE * fp, CalHashTable_t * h, Cal_BddIndex_t * normalizedIndexes, int indexSize, int nodeNumberSize); +static unsigned long Read(int * error, int bytes, FILE * fp); +static Cal_Bdd_t BddUndumpBddStep(Cal_BddManager_t * bddManager, Cal_Bdd_t * vars, FILE * fp, Cal_BddIndex_t numberVars, Cal_Bdd_t * shared, long numberShared, long * sharedSoFar, int indexSize, int nodeNumberSize, int * error); +static int BytesNeeded(long n); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Reads a BDD from a file] + + Description [Loads an encoded description of a BDD from the file given by + fp. The argument vars should be a null terminated array of variables that will + become the support of the BDD. As in Cal_BddDumpBdd, these need not be in + the order of increasing index. If the same array of variables in used in + dumping and undumping, the BDD returned will be equal to the one that was + dumped. More generally, if array v1 is used when dumping, and the array v2 + is used when undumping, the BDD returned will be equal to the original BDD + with the ith variable in v2 substituted for the ith variable in v1 for all i. + Null BDD is returned in the operation fails for reason (node limit reached, + I/O error, invalid file format, etc.). In this case, an error code is stored + in error. the code will be one of the following. + CAL_BDD_UNDUMP_FORMAT Invalid file format + CAL_BDD_UNDUMP_OVERFLOW Node limit exceeded + CAL_BDD_UNDUMP_IOERROR File I/O error + CAL_BDD_UNDUMP_EOF Unexpected EOF] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd +Cal_BddUndumpBdd( + Cal_BddManager bddManager, + Cal_Bdd * userVars, + FILE * fp, + int * error) +{ + long i,j; + Cal_BddIndex_t numberVars; + long numberShared; + int indexSize; + int nodeNumberSize; + Cal_Bdd_t *shared; + long sharedSoFar; + Cal_Bdd_t v; + Cal_Bdd_t result; + Cal_Bdd_t *vars; + + *error = 0; + for(i = 0; userVars[i]; ++i){ + if(Cal_BddType(bddManager, userVars[i]) != CAL_BDD_TYPE_POSVAR){ + CalBddWarningMessage("Cal_BddUndumpBdd: support is not all positive variables"); + return (Cal_Bdd) 0; + } + } + vars = Cal_MemAlloc(Cal_Bdd_t, i); + for (j=0; j < i; j++){ + vars[j] = CalBddGetInternalBdd(bddManager,userVars[j]); + } + + if(Read(error, sizeof(long), fp) != MAGIC_COOKIE){ + if(!*error){ + *error = CAL_BDD_UNDUMP_FORMAT; + } + Cal_MemFree(vars); + return (Cal_Bdd) 0; + } + numberVars = Read(error, sizeof(Cal_BddIndex_t), fp); + if(*error){ + Cal_MemFree(vars); + return (Cal_Bdd) 0; + } + if(numberVars != i){ + *error = CAL_BDD_UNDUMP_FORMAT; + Cal_MemFree(vars); + return (Cal_Bdd) 0; + } + numberShared = Read(error, sizeof(long), fp); + if(*error){ + Cal_MemFree(vars); + return (Cal_Bdd) 0; + } + indexSize = BytesNeeded(numberVars+1); + nodeNumberSize = BytesNeeded(numberShared); + if(numberShared < 0){ + *error = CAL_BDD_UNDUMP_FORMAT; + Cal_MemFree(vars); + return (Cal_Bdd) 0; + } + shared = Cal_MemAlloc(Cal_Bdd_t, numberShared); + for(i = 0; i < numberShared; ++i){ + shared[i] = CalBddNull(bddManager); + } + sharedSoFar = 0; + result = BddUndumpBddStep(bddManager, vars, fp, numberVars, shared, + numberShared, &sharedSoFar, indexSize, nodeNumberSize, error); + Cal_MemFree(vars); + + for(i = 0; i < numberShared; ++i){ + v = shared[i]; + if(!CalBddIsBddNull(bddManager, v)){ + CalBddFree(v); + } + } + if(!*error && sharedSoFar != numberShared){ + *error = CAL_BDD_UNDUMP_FORMAT; + } + Cal_MemFree(shared); + if(*error){ + if(!CalBddIsBddNull(bddManager, result)){ + CalBddFree(result); + } + return (Cal_Bdd) 0; + } + /* + * Decrement the reference count of result by 1. Since it has + * already been incremented in BddUndumpBddStep. + */ + CalBddDcrRefCount(result); + return CalBddGetExternalBdd(bddManager, result); +} + + +/**Function******************************************************************** + + Synopsis [Write a BDD to a file] + + Description [Writes an encoded description of the BDD to the file given by fp. + The argument vars should be a null-terminated array of variables that include + the support of f . These variables need not be in order of increasing index. + The function returns a nonzero value if f was written to the file successfully. + ] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +Cal_BddDumpBdd( + Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_Bdd * userVars, + FILE * fp) +{ + long i; + Cal_BddIndex_t *normalizedIndexes; + Cal_BddIndex_t vIndex; + Cal_Bdd_t f; + Cal_BddIndex_t numberVars; + Cal_Bdd *support; + int ok; + CalHashTable_t *h; + int indexSize; + long next; + int nodeNumberSize; + + if(CalBddPreProcessing(bddManager, 1, fUserBdd)){ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + for(i = 0; userVars[i]; ++i){ + if(Cal_BddType(bddManager, userVars[i]) != CAL_BDD_TYPE_POSVAR){ + CalBddWarningMessage("Cal_BddDumpBdd: support is not all positive variables"); + return (0); + } + } + normalizedIndexes = Cal_MemAlloc(Cal_BddIndex_t, bddManager->numVars); + for(i = 0; i < bddManager->numVars; ++i){ + normalizedIndexes[i] = CAL_BDD_CONST_INDEX; + } + for(i = 0; userVars[i]; ++i){ + vIndex = Cal_BddGetIfIndex(bddManager, userVars[i]); + if(normalizedIndexes[vIndex] != CAL_BDD_CONST_INDEX){ + CalBddWarningMessage("Cal_BddDumpBdd: variables duplicated in support"); + Cal_MemFree(normalizedIndexes); + return 0; + } + normalizedIndexes[vIndex] = i; + } + numberVars = i; + support = Cal_MemAlloc(Cal_Bdd, bddManager->numVars+1); + Cal_BddSupport(bddManager, fUserBdd, support); + ok = 1; + for(i = 0; ok && support[i]; ++i){ + if(normalizedIndexes[Cal_BddGetIfIndex(bddManager, support[i])] == CAL_BDD_CONST_INDEX){ + CalBddWarningMessage("Cal_BddDumpBdd: incomplete support specified"); + ok = 0; + } + } + if(!ok){ + Cal_MemFree(normalizedIndexes); + Cal_MemFree(support); + return 0; + } + Cal_MemFree(support); + /* Everything checked now; barring I/O errors, we should be able to */ + /* Write a valid output file. */ + f = CalBddGetInternalBdd(bddManager, fUserBdd); + h = CalHashTableOneInit(bddManager, sizeof(long)); + indexSize = BytesNeeded(numberVars+1); + CalBddMarkSharedNodes(bddManager, f); + next = 0; + CalBddNumberSharedNodes(bddManager, f, h, &next); + nodeNumberSize = BytesNeeded(next); + Write(bddManager, MAGIC_COOKIE, sizeof(long), fp); + Write(bddManager, (unsigned long)numberVars, sizeof(Cal_BddIndex_t), fp); + Write(bddManager, (unsigned long)next, sizeof(long), fp); + BddDumpBddStep(bddManager, f, fp, h, normalizedIndexes, indexSize, nodeNumberSize); + CalHashTableOneQuit(h); + Cal_MemFree(normalizedIndexes); + return (1); + } + return (0); +} + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +Write( + Cal_BddManager_t * bddManager, + unsigned long n, + int bytes, + FILE * fp) +{ + while(bytes){ + if(fputc((char)(n >> (8*(bytes-1)) & 0xff), fp) == EOF){ + } + --bytes; + } +} + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddDumpBddStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + FILE * fp, + CalHashTable_t * h, + Cal_BddIndex_t * normalizedIndexes, + int indexSize, + int nodeNumberSize) +{ + int negated; + long *number; + Cal_Bdd_t thenBdd, elseBdd; + + switch(CalBddTypeAux(bddManager, f)){ + case CAL_BDD_TYPE_ZERO: + Write(bddManager, FALSE_ENCODING, indexSize+1, fp); + break; + case CAL_BDD_TYPE_ONE: + Write(bddManager, TRUE_ENCODING, indexSize+1, fp); + break; + case CAL_BDD_TYPE_CONSTANT: + Write(bddManager, CONSTANT_ENCODING, indexSize+1, fp); +#ifdef JAGESH + Write(bddManager, (unsigned long)BDD_DATA(f)[0], sizeof(long), fp); + Write(bddManager, (unsigned long)BDD_DATA(f)[1], sizeof(long), fp); +#endif + break; + case CAL_BDD_TYPE_POSVAR: + Write(bddManager, POSVAR_ENCODING, indexSize+1, fp); + Write(bddManager, + (unsigned long)normalizedIndexes[CalBddGetBddIndex(bddManager, f)], + indexSize, fp); + break; + case CAL_BDD_TYPE_NEGVAR: + Write(bddManager, NEGVAR_ENCODING, indexSize+1, fp); + Write(bddManager, + (unsigned long)normalizedIndexes[CalBddGetBddIndex(bddManager, f)], + indexSize, fp); + break; + case CAL_BDD_TYPE_NONTERMINAL: + CalBddNot(f, f); + if(CalHashTableOneLookup(h, f, (char **)0)){ + negated = 1; + } + else{ + CalBddNot(f, f); + negated = 0; + } + CalHashTableOneLookup(h, f, (char **)&number); + if(number && *number < 0){ + if(negated) + Write(bddManager, NEGNODE_ENCODING, indexSize+1, fp); + else + Write(bddManager, POSNODE_ENCODING, indexSize+1, fp); + Write(bddManager, (unsigned long)(-*number-1), nodeNumberSize, fp); + } + else{ + if(number){ + Write(bddManager, NODELABEL_ENCODING, indexSize+1, fp); + *number = -*number-1; + } + Write(bddManager, + (unsigned long)normalizedIndexes[CalBddGetBddIndex(bddManager, f)], + indexSize, fp); + CalBddGetThenBdd(f, thenBdd); + BddDumpBddStep(bddManager, thenBdd, fp, h, normalizedIndexes, + indexSize, nodeNumberSize); + CalBddGetElseBdd(f, elseBdd); + BddDumpBddStep(bddManager, elseBdd, fp, h, normalizedIndexes, + indexSize, nodeNumberSize); + } + break; + default: + CalBddFatalMessage("BddDumpBddStep: unknown type returned by CalBddType"); + } +} + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static unsigned long +Read( + int * error, + int bytes, + FILE * fp) +{ + int c; + long result; + + result = 0; + if(*error){ + return (result); + } + while(bytes){ + c = fgetc(fp); + if(c == EOF){ + if(ferror(fp)){ + *error = CAL_BDD_UNDUMP_IOERROR; + } + else{ + *error = CAL_BDD_UNDUMP_EOF; + } + return (0l); + } + result = (result << 8)+c; + --bytes; + } + return (result); +} + + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddUndumpBddStep( + Cal_BddManager_t * bddManager, + Cal_Bdd_t * vars, + FILE * fp, + Cal_BddIndex_t numberVars, + Cal_Bdd_t * shared, + long numberShared, + long * sharedSoFar, + int indexSize, + int nodeNumberSize, + int * error) +{ + long nodeNumber; + long encoding; + Cal_BddIndex_t i; + CalAddress_t value1, value2; + Cal_Bdd_t v; + Cal_Bdd_t temp1, temp2; + Cal_Bdd_t result; + + i = Read(error, indexSize, fp); + if(*error){ + return CalBddNull(bddManager); + } + if(i == indexMask[indexSize-1]){ + encoding = 0xffffff00l+Read(error, 1, fp); + if(*error){ + return CalBddNull(bddManager); + } + switch(encoding){ + case TRUE_ENCODING: + return (CalBddOne(bddManager)); + case FALSE_ENCODING: + return (CalBddZero(bddManager)); + case CONSTANT_ENCODING: + value1 = Read(error, sizeof(long), fp); + value2 = Read(error, sizeof(long), fp); + if(*error){ + return CalBddNull(bddManager); + } + *error = CAL_BDD_UNDUMP_OVERFLOW; + return CalBddNull(bddManager); + case POSVAR_ENCODING: + case NEGVAR_ENCODING: + i = Read(error, indexSize, fp); + if(!*error && i >= numberVars){ + *error = CAL_BDD_UNDUMP_FORMAT; + } + if(*error){ + return CalBddNull(bddManager); + } + v = vars[i]; + if(encoding == POSVAR_ENCODING){ + return (v); + } + else{ + CalBddNot(v, v); + return (v); + } + case POSNODE_ENCODING: + case NEGNODE_ENCODING: + nodeNumber = Read(error, nodeNumberSize, fp); + if(!*error && (nodeNumber >= numberShared || + CalBddIsBddNull(bddManager, shared[nodeNumber]))){ + *error = CAL_BDD_UNDUMP_FORMAT; + } + if(*error){ + return CalBddNull(bddManager); + } + v = shared[nodeNumber]; + v = CalBddIdentity(bddManager, v); + if(encoding == POSNODE_ENCODING){ + return (v); + } + else{ + CalBddNot(v, v); + return (v); + } + case NODELABEL_ENCODING: + nodeNumber = *sharedSoFar; + ++*sharedSoFar; + v = BddUndumpBddStep(bddManager, vars, fp, numberVars, shared, + numberShared, sharedSoFar, indexSize, nodeNumberSize, error); + shared[nodeNumber] = v; + v = CalBddIdentity(bddManager, v); + return (v); + default: + *error = CAL_BDD_UNDUMP_FORMAT; + return CalBddNull(bddManager); + } + } + if(i >= numberVars){ + *error = CAL_BDD_UNDUMP_FORMAT; + return CalBddNull(bddManager); + } + temp1 = BddUndumpBddStep(bddManager, vars, fp, numberVars, shared, + numberShared, sharedSoFar, indexSize, nodeNumberSize, error); + temp2 = BddUndumpBddStep(bddManager, vars, fp, numberVars, shared, + numberShared, sharedSoFar, indexSize, nodeNumberSize, error); + if(*error){ + CalBddFree(temp1); + return CalBddNull(bddManager); + } + result = CalBddITE(bddManager, vars[i], temp1, temp2); + CalBddFree(temp1); + CalBddFree(temp2); + if(CalBddIsBddNull(bddManager, result)){ + *error = CAL_BDD_UNDUMP_OVERFLOW; + } + return (result); +} + + + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BytesNeeded( + long n) +{ + if(n <= 0x100l){ + return (1); + } + if(n <= 0x10000l){ + return (2); + } + if(n <= 0x1000000l){ + return (3); + } + return (4); +} + + + + + + + + + + + + diff --git a/calExt.html b/calExt.html new file mode 100644 index 0000000..3bb7744 --- /dev/null +++ b/calExt.html @@ -0,0 +1,13 @@ + +The cal Package for Programmers + + + + + + + + + + + diff --git a/calExtAbs.html b/calExtAbs.html new file mode 100644 index 0000000..35eb4c4 --- /dev/null +++ b/calExtAbs.html @@ -0,0 +1,388 @@ + +cal package abstract + + + + + +
+
Cal_AssociationInit() +
Creates or finds a variable association. + +
Cal_AssociationQuit() +
Deletes the variable association given by id + +
Cal_AssociationSetCurrent() +
Sets the current variable association to the one given by id and + returns the ID of the old association. + +
Cal_BddAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddBetween() +
Returns a minimal BDD whose function contains fMin and is + contained in fMax. + +
Cal_BddCofactor() +
Returns the generalized cofactor of BDD f with respect + to BDD c. + +
Cal_BddCompose() +
composition - substitute a BDD variable by a function + +
Cal_BddDependsOn() +
Returns 1 if f depends on var and returns 0 otherwise. + +
Cal_BddDumpBdd() +
Write a BDD to a file + +
Cal_BddDynamicReordering() +
Specify dynamic reordering technique. + +
Cal_BddElse() +
Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddExists() +
Returns the result of existentially quantifying some + variables from the given BDD. + +
Cal_BddForAll() +
Returns the result of universally quantifying some + variables from the given BDD. + +
Cal_BddFree() +
Frees the argument BDD. + +
Cal_BddFunctionPrint() +
Prints the function implemented by the argument BDD + +
Cal_BddFunctionProfileMultiple() +
Returns a "function profile" for fArray. + +
Cal_BddFunctionProfile() +
Returns a "function profile" for f. + +
Cal_BddGetIfId() +
Returns the id of the top variable of the argument BDD. + +
Cal_BddGetIfIndex() +
Returns the index of the top variable of the argument BDD. + +
Cal_BddGetRegular() +
Returns a BDD with positive from a given BDD with arbitrary phase + +
Cal_BddITE() +
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h + +
Cal_BddIdentity() +
Returns the duplicate BDD of the argument BDD. + +
Cal_BddIf() +
Returns the BDD corresponding to the top variable of + the argument BDD. + +
Cal_BddImplies() +
Computes a BDD that implies conjunction of f and Cal_BddNot(g) + +
Cal_BddIntersects() +
Computes a BDD that implies conjunction of f and g. + +
Cal_BddIsBddConst() +
Returns 1 if the argument BDD is a constant, 0 otherwise. + +
Cal_BddIsBddNull() +
Returns 1 if the argument BDD is NULL, 0 otherwise. + +
Cal_BddIsBddOne() +
Returns 1 if the argument BDD is constant one, 0 otherwise. + +
Cal_BddIsBddZero() +
Returns 1 if the argument BDD is constant zero, 0 otherwise. + +
Cal_BddIsCube() +
Returns 1 if the argument BDD is a cube, 0 otherwise + +
Cal_BddIsEqual() +
Returns 1 if argument BDDs are equal, 0 otherwise. + +
Cal_BddIsProvisional() +
Returns 1, if the given user BDD contains + provisional BDD node. + +
Cal_BddManagerCreateNewVarAfter() +
Creates and returns a new variable after the specified one in + the variable order. + +
Cal_BddManagerCreateNewVarBefore() +
Creates and returns a new variable before the specified one in + the variable order. + +
Cal_BddManagerCreateNewVarFirst() +
Creates and returns a new variable at the start of the variable + order. + +
Cal_BddManagerCreateNewVarLast() +
Creates and returns a new variable at the end of the variable + order. + +
Cal_BddManagerGC() +
Invokes the garbage collection at the manager level. + +
Cal_BddManagerGetHooks() +
Returns the hooks field of the manager. + +
Cal_BddManagerGetNumNodes() +
Returns the number of BDD nodes + +
Cal_BddManagerGetVarWithId() +
Returns the variable with the specified id, null if no + such variable exists + +
Cal_BddManagerGetVarWithIndex() +
Returns the variable with the specified index, null if no + such variable exists + +
Cal_BddManagerInit() +
Creates and initializes a new BDD manager. + +
Cal_BddManagerQuit() +
Frees the BDD manager and all the associated allocations + +
Cal_BddManagerSetGCLimit() +
Sets the limit of the garbage collection. + +
Cal_BddManagerSetHooks() +
Sets the hooks field of the manager. + +
Cal_BddManagerSetParameters() +
Sets appropriate fields of BDD Manager. + +
Cal_BddMultiwayAnd() +
Returns the BDD for logical AND of argument BDDs + +
Cal_BddMultiwayOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddMultiwayXor() +
Returns the BDD for logical XOR of argument BDDs + +
Cal_BddNand() +
Returns the BDD for logical NAND of argument BDDs + +
Cal_BddNewVarBlock() +
Creates and returns a variable block used for + controlling dynamic reordering. + +
Cal_BddNodeLimit() +
Sets the node limit to new_limit and returns the old limit. + +
Cal_BddNor() +
Returns the BDD for logical NOR of argument BDDs + +
Cal_BddNot() +
Returns the complement of the argument BDD. + +
Cal_BddOne() +
Returns the BDD for the constant one + +
Cal_BddOr() +
Returns the BDD for logical OR of argument BDDs + +
Cal_BddOverflow() +
Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared. + +
Cal_BddPairwiseAnd() +
Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseOr() +
Returns an array of BDDs obtained by logical OR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPairwiseXor() +
Returns an array of BDDs obtained by logical XOR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array + +
Cal_BddPrintBdd() +
Prints a BDD in the human readable form. + +
Cal_BddPrintFunctionProfileMultiple() +
Cal_BddPrintFunctionProfileMultiple is like + Cal_BddPrintFunctionProfile except for multiple BDDs + +
Cal_BddPrintFunctionProfile() +
Cal_BddPrintFunctionProfile is like Cal_BddPrintProfile except + it displays a function profile for f + +
Cal_BddPrintProfileMultiple() +
Cal_BddPrintProfileMultiple is like Cal_BddPrintProfile except + it displays the profile for a set of BDDs + +
Cal_BddPrintProfile() +
Displays the node profile for f on fp. lineLength specifies + the maximum line length. varNamingFn is as in + Cal_BddPrintBdd. + +
Cal_BddProfileMultiple() +
+ +
Cal_BddProfile() +
Returns a "node profile" of f, i.e., the number of nodes at each + level in f. + +
Cal_BddReduce() +
Returns a BDD which agrees with f for all valuations + which satisfy c. + +
Cal_BddRelProd() +
Returns the result of taking the logical AND of the + argument BDDs and existentially quantifying some variables from the + product. + +
Cal_BddReorder() +
Invoke the current dynamic reodering method. + +
Cal_BddSatisfySupport() +
Returns a special cube contained in f. + +
Cal_BddSatisfyingFraction() +
Returns the fraction of valuations which make f true. (Note that + this fraction is independent of whatever set of variables f is supposed to be + a function of) + +
Cal_BddSatisfy() +
Returns a BDD which implies f, true for + some valuation on which f is true, and which has at most + one node at each level + +
Cal_BddSetGCMode() +
Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on. + +
Cal_BddSizeMultiple() +
The routine is like Cal_BddSize, but takes a null-terminated + array of BDDs and accounts for sharing of nodes. + +
Cal_BddSize() +
Returns the number of nodes in f when negout is nonzero. If + negout is zero, we pretend that the BDDs don't have negative-output pointers. + +
Cal_BddStats() +
Prints miscellaneous BDD statistics + +
Cal_BddSubstitute() +
Substitute a set of variables by functions + +
Cal_BddSupport() +
returns the support of f as a null-terminated array of variables + +
Cal_BddSwapVars() +
Return a function obtained by swapping two variables + +
Cal_BddThen() +
Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD. + +
Cal_BddTotalSize() +
Returns the number of nodes in the Unique table + +
Cal_BddType() +
Returns type of a BDD ( 0, 1, +var, -var, ovrflow, nonterminal) + +
Cal_BddUnFree() +
Unfrees the argument BDD. + +
Cal_BddUndumpBdd() +
Reads a BDD from a file + +
Cal_BddVarBlockReorderable() +
Sets the reoderability of a particular block. + +
Cal_BddVarSubstitute() +
Substitute a set of variables by set of another variables. + +
Cal_BddVars() +
Returns the number of BDD variables + +
Cal_BddXnor() +
Returns the BDD for logical exclusive NOR of argument BDDs + +
Cal_BddXor() +
Returns the BDD for logical exclusive OR of argument BDDs + +
Cal_BddZero() +
Returns the BDD for the constant zero + +
Cal_MemAllocation() +
Returns the memory allocated. + +
Cal_MemFatal() +
Prints an error message and exits. + +
Cal_MemFreeBlock() +
Frees the block. + +
Cal_MemFreeRecMgr() +
Frees all the storage associated with the specified record manager. + +
Cal_MemFreeRec() +
Frees a record managed by the indicated record manager. + +
Cal_MemGetBlock() +
Allocates a new block of the specified size. + +
Cal_MemNewRecMgr() +
Creates a new record manager with the given record size. + +
Cal_MemNewRec() +
Allocates a record from the specified record manager. + +
Cal_MemResizeBlock() +
Expands or contracts the block to a new size. + We try to avoid moving the block if possible. + +
Cal_PerformanceTest() +
Main routine for testing performances of various routines. + +
Cal_PipelineCreateProvisionalBdd() +
Create a provisional BDD in the pipeline. + +
Cal_PipelineExecute() +
Executes a pipeline. + +
Cal_PipelineInit() +
Initialize a BDD pipeline. + +
Cal_PipelineQuit() +
Resets the pipeline freeing all resources. + +
Cal_PipelineSetDepth() +
Set depth of a BDD pipeline. + +
Cal_PipelineUpdateProvisionalBdd() +
Update a provisional Bdd obtained during pipelining. + +
Cal_TempAssociationAugment() +
Adds to the temporary variable association. + +
Cal_TempAssociationInit() +
Sets the temporary variable association. + +
Cal_TempAssociationQuit() +
Cleans up temporary association + +
+ +
+ +Last updated on 970711 20h11 + diff --git a/calExtDet.html b/calExtDet.html new file mode 100644 index 0000000..ad06766 --- /dev/null +++ b/calExtDet.html @@ -0,0 +1,1924 @@ + +The cal package + + +
+
+
+int 
+Cal_AssociationInit(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Creates or finds a variable association. The association is + specified by associationInfo, which is a an array of BDD with + Cal_BddNull(bddManager) as the end marker. If pairs is 0, the array is + assumed to be an array of variables. In this case, each variable is paired + with constant BDD one. Such an association may viewed as specifying a set + of variables for use with routines such as Cal_BddExists. If pair is not 0, + then the even numbered array elements should be variables and the odd numbered + elements should be the BDDs which they are mapped to. In both cases, the + return value is an integer identifier for this association. If the given + association is equivalent to one which already exists, the same identifier + is used for both, and the reference count of the association is increased by + one. +

+ +

Side Effects None +

+ +

See Also Cal_AssociationQuit + + +
+
+void 
+Cal_AssociationQuit(
+  Cal_BddManager  bddManager, 
+  int  associationId 
+)
+
+
Decrements the reference count of the variable association with + identifier id, and frees it if the reference count becomes zero. +

+ +

Side Effects None +

+ +

See Also Cal_AssociationInit + + +
+
+int 
+Cal_AssociationSetCurrent(
+  Cal_BddManager  bddManager, 
+  int  associationId 
+)
+
+
Sets the current variable association to the one given by id and + returns the ID of the old association. An id of -1 indicates the temporary + association +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical AND of f and g +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddBetween(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fMinUserBdd, 
+  Cal_Bdd  fMaxUserBdd 
+)
+
+
Returns a minimal BDD f which is contains fMin and is + contained in fMax ( fMin <= f <= fMax). + This operation is typically used in state space searches to simplify + the representation for the set of states wich will be expanded at + each step (Rk Rk-1' <= f <= Rk). +

+ +

Side Effects None +

+ +

See Also Cal_BddReduce + + +
+
+Cal_Bdd 
+Cal_BddCofactor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  cUserBdd 
+)
+
+
Returns the generalized cofactor of BDD f with respect + to BDD c. The constrain operator given by Coudert et al (ICCAD90) is + used to find the generalized cofactor. +

+ +

Side Effects None. +

+ +

See Also Cal_BddReduce + + +
+
+Cal_Bdd 
+Cal_BddCompose(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD obtained by substituting a variable by a function +

+ +

Side Effects None +

+ +

+
+int 
+Cal_BddDependsOn(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  varUserBdd 
+)
+
+
Returns 1 if f depends on var and returns 0 otherwise. +

+ +

Side Effects None +

+ +

+
+int 
+Cal_BddDumpBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd * userVars, 
+  FILE * fp 
+)
+
+
Writes an encoded description of the BDD to the file given by fp. + The argument vars should be a null-terminated array of variables that include + the support of f . These variables need not be in order of increasing index. + The function returns a nonzero value if f was written to the file successfully. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_BddDynamicReordering(
+  Cal_BddManager  bddManager, 
+  int  technique 
+)
+
+
Selects the method for dynamic reordering. +

+ +

Side Effects None +

+ +

See Also Cal_BddReorder + + +
+
+Cal_Bdd 
+Cal_BddElse(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the negative cofactor of the argument BDD with + respect to the top variable of the BDD. +

+ +

Side Effects The reference count of the returned BDD is increased by 1. +

+ +

See Also Cal_BddThen + + +
+
+Cal_Bdd 
+Cal_BddExists(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns the BDD for f with all the variables that are + paired with something in the current variable association + existentially quantified out. +

+ +

Side Effects None. +

+ +

See Also Cal_BddRelProd + + +
+
+Cal_Bdd 
+Cal_BddForAll(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns the BDD for f with all the variables that are + paired with something in the current variable association + universally quantified out. +

+ +

Side Effects None. +

+ +

+
+void 
+Cal_BddFree(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Frees the argument BDD. It is an error to free a BDD + more than once. +

+ +

Side Effects The reference count of the argument BDD is decreased by 1. +

+ +

See Also Cal_BddUnFree + + +
+
+void 
+Cal_BddFunctionPrint(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd, 
+  char * name 
+)
+
+
Prints the function implemented by the argument BDD +

+ +

Side Effects None +

+ +

+
+void 
+Cal_BddFunctionProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  long * funcCounts 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddFunctionProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  long * funcCounts 
+)
+
+
The nth entry of the function + profile array is the number of subfunctions of f which may be obtained by + restricting the variables whose index is less than n. An entry of zero + indicates that f is independent of the variable with the corresponding index. +

+ +

See Also optional + + +
+
+Cal_BddId_t 
+Cal_BddGetIfId(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the id of the top variable of the argument BDD. +

+ +

Side Effects None +

+ +

See Also Cal_BddGetIfIndex + + +
+
+Cal_BddId_t 
+Cal_BddGetIfIndex(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the index of the top variable of the argument BDD. +

+ +

Side Effects None +

+ +

See Also Cal_BddGetIfId + + +
+
+Cal_Bdd 
+Cal_BddGetRegular(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns a BDD with positive from a given BDD with arbitrary phase +

+ +

Side Effects None. +

+ +

+
+Cal_Bdd 
+Cal_BddITE(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD for logical If-Then-Else + + Description [Returns the BDD for the logical operation IF f THEN g ELSE h + - f g + f' h +

+ +

Side Effects None +

+ +

See Also Cal_BddAnd +Cal_BddNand +Cal_BddOr +Cal_BddNor +Cal_BddXor +Cal_BddXnor + + +
+
+Cal_Bdd 
+Cal_BddIdentity(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the duplicate BDD of the argument BDD. +

+ +

Side Effects The reference count of the BDD is increased by 1. +

+ +

See Also Cal_BddNot + + +
+
+Cal_Bdd 
+Cal_BddIf(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the BDD corresponding to the top variable of + the argument BDD. +

+ +

Side Effects None. +

+ +

+
+Cal_Bdd 
+Cal_BddImplies(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Computes a BDD that implies conjunction of f and Cal_BddNot(g) +

+ +

Side Effects none +

+ +

See Also Cal_BddIntersects + + +
+
+Cal_Bdd 
+Cal_BddIntersects(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Computes a BDD that implies conjunction of f and g. +

+ +

Side Effects None +

+ +

See Also Cal_BddImplies + + +
+
+int 
+Cal_BddIsBddConst(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is either constant one or + constant zero, otherwise returns 0. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddOne +Cal_BddIsBddZero + + +
+
+int 
+Cal_BddIsBddNull(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is NULL, 0 otherwise. +

+ +

Side Effects None. +

+ +

+
+int 
+Cal_BddIsBddOne(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is constant one, 0 otherwise. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddZero + + +
+
+int 
+Cal_BddIsBddZero(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1 if the argument BDD is constant zero, 0 otherwise. +

+ +

Side Effects None. +

+ +

See Also Cal_BddIsBddOne + + +
+
+int 
+Cal_BddIsCube(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns 1 if the argument BDD is a cube, 0 otherwise +

+ +

Side Effects None +

+ +

+
+int 
+Cal_BddIsEqual(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd1, 
+  Cal_Bdd  userBdd2 
+)
+
+
Returns 1 if argument BDDs are equal, 0 otherwise. +

+ +

Side Effects None. +

+ +

+
+int 
+Cal_BddIsProvisional(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns 1, if the given user BDD contains + provisional BDD node. +

+ +

Side Effects None. +

+ +

+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarAfter(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Creates and returns a new variable after the specified one in + the variable order. +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarBefore(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Creates and returns a new variable before the specified one in + the variable order. +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarFirst(
+  Cal_BddManager  bddManager 
+)
+
+
Creates and returns a new variable at the start of the + variable order. +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddManagerCreateNewVarLast(
+  Cal_BddManager  bddManager 
+)
+
+
Creates and returns a new variable at the end of the variable + order. +

+ +

Side Effects None +

+ +

+
+int 
+Cal_BddManagerGC(
+  Cal_BddManager  bddManager 
+)
+
+
For each variable in the increasing id free nodes with reference + count equal to zero freeing a node results in decrementing reference count of + then and else nodes by one. +

+ +

Side Effects None. +

+ +

+
+void * 
+Cal_BddManagerGetHooks(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the hooks field of the manager. +

+ +

Side Effects None +

+ +

+
+unsigned long 
+Cal_BddManagerGetNumNodes(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of BDD nodes +

+ +

Side Effects None +

+ +

See Also Cal_BddTotalSize + + +
+
+Cal_Bdd 
+Cal_BddManagerGetVarWithId(
+  Cal_BddManager  bddManager, 
+  Cal_BddId_t  id 
+)
+
+
Returns the variable with the specified id, null if no + such variable exists +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+Cal_Bdd 
+Cal_BddManagerGetVarWithIndex(
+  Cal_BddManager  bddManager, 
+  Cal_BddIndex_t  index 
+)
+
+
Returns the variable with the specified index, null if no + such variable exists +

+ +

Side Effects None +

+ +

+
+Cal_BddManager 
+Cal_BddManagerInit(
+    
+)
+
+
Initializes and allocates fields of the BDD manager. Some of the + fields are initialized for maxNumVars+1 or numVars+1, whereas some of them are + initialized for maxNumVars or numVars. The first kind of fields are associated + with the id of a variable and the second ones are with the index of the + variable. +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerQuit + + +
+
+int 
+Cal_BddManagerQuit(
+  Cal_BddManager  bddManager 
+)
+
+
Frees the BDD manager and all the associated allocations +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerInit + + +
+
+void 
+Cal_BddManagerSetGCLimit(
+  Cal_BddManager  manager 
+)
+
+
It tries to set the limit at twice the number of nodes + in the manager at the current point. However, the limit is not + allowed to fall below the MIN_GC_LIMIT or to exceed the value of + node limit (if one exists). +

+ +

Side Effects None. +

+ +

+
+void 
+Cal_BddManagerSetHooks(
+  Cal_BddManager  bddManager, 
+  void * hooks 
+)
+
+
Sets the hooks field of the manager. +

+ +

Side Effects Hooks field changes. +

+ +

+
+void 
+Cal_BddManagerSetParameters(
+  Cal_BddManager  bddManager, 
+  long  reorderingThreshold, 
+  long  maxForwardedNodes, 
+  double  repackAfterGCThreshold, 
+  double  tableRepackThreshold 
+)
+
+
This function is used to set the parameters which are + used to control the reordering process. "reorderingThreshold" + determines the number of nodes below which reordering will NOT be + invoked, "maxForwardedNodes" determines the maximum number of + forwarded nodes which are allowed (at that point the cleanup must be + done), and "repackingThreshold" determines the fraction of the page + utilized below which repacking has to be invoked. These parameters + have different affect on the computational and memory usage aspects + of reordeing. For instance, higher value of "maxForwardedNodes" will + result in process consuming more memory, and a lower value on the + other hand would invoke the cleanup process repeatedly resulting in + increased computation. +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddMultiwayAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical AND of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddMultiwayOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical OR of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddMultiwayXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns the BDD for logical XOR of set of BDDs in the bddArray +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddNand(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical NAND of f and g +

+ +

Side Effects None +

+ +

+
+Cal_Block 
+Cal_BddNewVarBlock(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  variable, 
+  long  length 
+)
+
+
The block is specified by passing the first + variable and the length of the block. The "length" number of + consecutive variables starting from "variable" are put in the + block. +

+ +

Side Effects A new block is created. +

+ +

+
+long 
+Cal_BddNodeLimit(
+  Cal_BddManager  bddManager, 
+  long  newLimit 
+)
+
+
Sets the node limit to new_limit and returns the old limit. +

+ +

Side Effects Threshold for garbage collection may change +

+ +

See Also Cal_BddManagerGC + + +
+
+Cal_Bdd 
+Cal_BddNor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical NOR of f and g +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddNot(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the complement of the argument BDD. +

+ +

Side Effects The reference count of the argument BDD is increased by 1. +

+ +

See Also Cal_BddIdentity + + +
+
+Cal_Bdd 
+Cal_BddOne(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the BDD for the constant one +

+ +

Side Effects None +

+ +

See Also Cal_BddZero + + +
+
+Cal_Bdd 
+Cal_BddOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical OR of f and g +

+ +

Side Effects None +

+ +

+
+int 
+Cal_BddOverflow(
+  Cal_BddManager  bddManager 
+)
+
+
Returns 1 if the node limit has been exceeded, 0 otherwise. The + overflow flag is cleared. +

+ +

Side Effects None +

+ +

See Also Cal_BddNodeLimit + + +
+
+Cal_Bdd * 
+Cal_BddPairwiseAnd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical AND of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseOr + + +
+
+Cal_Bdd * 
+Cal_BddPairwiseOr(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical OR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseAnd + + +
+
+Cal_Bdd * 
+Cal_BddPairwiseXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBddArray 
+)
+
+
Returns an array of BDDs obtained by logical XOR of BDD pairs + specified by an BDD array in which a BDD at an even location is paired with + a BDD at an odd location of the array +

+ +

Side Effects None +

+ +

See Also Cal_BddPairwiseAnd + + +
+
+void 
+Cal_BddPrintBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_VarNamingFn_t  VarNamingFn, 
+  Cal_TerminalIdFn_t  TerminalIdFn, 
+  Cal_Pointer_t  env, 
+  FILE * fp 
+)
+
+
Prints a human-readable representation of the BDD f to + the file given by fp. The namingFn should be a pointer to a function + taking a bddManager, a BDD and the pointer given by env. This + function should return either a null pointer or a srting that is the + name of the supplied variable. If it returns a null pointer, a + default name is generated based on the index of the variable. It is + also legal for naminFN to e null; in this case, default names are + generated for all variables. The macro bddNamingFnNone is a null + pointer of suitable type. terminalIdFn should be apointer to a + function taking a bddManager and two longs. plus the pointer given + by the env. It should return either a null pointer. If it returns a + null pointer, or if terminalIdFn is null, then default names are + generated for the terminals. The macro bddTerminalIdFnNone is a null + pointer of suitable type. +

+ +

Side Effects None. +

+ +

+
+void 
+Cal_BddPrintFunctionProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBdds, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddPrintFunctionProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  f, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddPrintProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userBdds, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddPrintProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_VarNamingFn_t  varNamingProc, 
+  char * env, 
+  int  lineLength, 
+  FILE * fp 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddProfileMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  long * levelCounts, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddProfile(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  long * levelCounts, 
+  int  negout 
+)
+
+
negout is as in Cal_BddSize. levelCounts should be an array of + size Cal_BddVars(bddManager)+1 to hold the profile. +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+Cal_Bdd 
+Cal_BddReduce(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  cUserBdd 
+)
+
+
Returns a BDD which agrees with f for all valuations + which satisfy c. The result is usually smaller in terms of number of + BDD nodes than f. This operation is typically used in state space + searches to simplify the representation for the set of states wich + will be expanded at each step. +

+ +

Side Effects None +

+ +

See Also Cal_BddCofactor + + +
+
+Cal_Bdd 
+Cal_BddRelProd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for the logical AND of f and g with all + the variables that are paired with something in the current variable + association existentially quantified out. +

+ +

Side Effects None. +

+ +

+
+void 
+Cal_BddReorder(
+  Cal_BddManager  bddManager 
+)
+
+
Invoke the current dynamic reodering method. +

+ +

Side Effects Index of a variable may change due to reodering +

+ +

See Also Cal_BddDynamicReordering + + +
+
+Cal_Bdd 
+Cal_BddSatisfySupport(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
The returned BDD which implies f, is true for some valuation on + which f is true, which has at most one node at each level, + and which has exactly one node corresponding to each variable + which is associated with something in the current variable + association. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+double 
+Cal_BddSatisfyingFraction(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_Bdd 
+Cal_BddSatisfy(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_BddSetGCMode(
+  Cal_BddManager  bddManager, 
+  int  gcMode 
+)
+
+
Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on. +

+ +

Side Effects None. +

+ +

+
+long 
+Cal_BddSizeMultiple(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * fUserBddArray, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+long 
+Cal_BddSize(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  int  negout 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+void 
+Cal_BddStats(
+  Cal_BddManager  bddManager, 
+  FILE * fp 
+)
+
+
Prints miscellaneous BDD statistics +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns a BDD for f using the substitution defined by current + variable association. Each variable is replaced by its associated BDDs. The + substitution is effective simultaneously +

+ +

Side Effects None +

+ +

See Also Cal_BddCompose + + +
+
+void 
+Cal_BddSupport(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd * support 
+)
+
+
optional +

+ +

Side Effects None +

+ +

See Also optional + + +
+
+Cal_Bdd 
+Cal_BddSwapVars(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd, 
+  Cal_Bdd  hUserBdd 
+)
+
+
Returns the BDD obtained by simultaneously substituting variable + g by variable h and variable h and variable g in the BDD f +

+ +

Side Effects None +

+ +

See Also Cal_BddSubstitute + + +
+
+Cal_Bdd 
+Cal_BddThen(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Returns the positive cofactor of the argument BDD with + respect to the top variable of the BDD. +

+ +

Side Effects The reference count of the returned BDD is increased by 1. +

+ +

See Also Cal_BddElse + + +
+
+unsigned long 
+Cal_BddTotalSize(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of nodes in the Unique table +

+ +

Side Effects None +

+ +

See Also Cal_BddManagerGetNumNodes + + +
+
+int 
+Cal_BddType(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns BDD_TYPE_ZERO if f is false, BDD_TYPE_ONE + if f is true, BDD_TYPE_POSVAR is f is an unnegated variable, + BDD_TYPE_NEGVAR if f is a negated variable, BDD_TYPE_OVERFLOW if f + is null, and BDD_TYPE_NONTERMINAL otherwise. +

+ +

Side Effects None +

+ +

+
+void 
+Cal_BddUnFree(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  userBdd 
+)
+
+
Unfrees the argument BDD. It is an error to pass a BDD + with reference count of zero to be unfreed. +

+ +

Side Effects The reference count of the argument BDD is increased by 1. +

+ +

See Also Cal_BddFree + + +
+
+Cal_Bdd 
+Cal_BddUndumpBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * userVars, 
+  FILE * fp, 
+  int * error 
+)
+
+
Loads an encoded description of a BDD from the file given by + fp. The argument vars should be a null terminated array of variables that will + become the support of the BDD. As in Cal_BddDumpBdd, these need not be in + the order of increasing index. If the same array of variables in used in + dumping and undumping, the BDD returned will be equal to the one that was + dumped. More generally, if array v1 is used when dumping, and the array v2 + is used when undumping, the BDD returned will be equal to the original BDD + with the ith variable in v2 substituted for the ith variable in v1 for all i. + Null BDD is returned in the operation fails for reason (node limit reached, + I/O error, invalid file format, etc.). In this case, an error code is stored + in error. the code will be one of the following. + CAL_BDD_UNDUMP_FORMAT Invalid file format + CAL_BDD_UNDUMP_OVERFLOW Node limit exceeded + CAL_BDD_UNDUMP_IOERROR File I/O error + CAL_BDD_UNDUMP_EOF Unexpected EOF +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_BddVarBlockReorderable(
+  Cal_BddManager  bddManager, 
+  Cal_Block  block, 
+  int  reorderable 
+)
+
+
If a block is reorderable, the child blocks are + recursively involved in swapping. +

+ +

Side Effects None. +

+ +

+
+Cal_Bdd 
+Cal_BddVarSubstitute(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd 
+)
+
+
Returns a BDD for f using the substitution defined by current + variable association. It is assumed that each variable is replaced + by another variable. For the substitution of a variable by a + function, use Cal_BddSubstitute instead. +

+ +

Side Effects None +

+ +

See Also Cal_BddSubstitute + + +
+
+long 
+Cal_BddVars(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the number of BDD variables +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddXnor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical exclusive NOR of f and g +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddXor(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
Returns the BDD for logical exclusive OR of f and g +

+ +

Side Effects None +

+ +

+
+Cal_Bdd 
+Cal_BddZero(
+  Cal_BddManager  bddManager 
+)
+
+
Returns the BDD for the constant zero +

+ +

Side Effects None +

+ +

See Also Cal_BddOne + + +
+
+Cal_Address_t 
+Cal_MemAllocation(
+    
+)
+
+
Returns the memory allocated. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_MemFatal(
+  char * message 
+)
+
+
Prints an error message and exits. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_MemFreeBlock(
+  Cal_Pointer_t  p 
+)
+
+
Frees the block. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_MemFreeRecMgr(
+  Cal_RecMgr  mgr 
+)
+
+
Frees all the storage associated with the specified record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+void 
+Cal_MemFreeRec(
+  Cal_RecMgr  mgr, 
+  Cal_Pointer_t  rec 
+)
+
+
Frees a record managed by the indicated record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_Pointer_t 
+Cal_MemGetBlock(
+  Cal_Address_t  size 
+)
+
+
Allocates a new block of the specified size. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_RecMgr 
+Cal_MemNewRecMgr(
+  int  size 
+)
+
+
Creates a new record manager with the given record size. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_Pointer_t 
+Cal_MemNewRec(
+  Cal_RecMgr  mgr 
+)
+
+
Allocates a record from the specified record manager. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_Pointer_t 
+Cal_MemResizeBlock(
+  Cal_Pointer_t  p, 
+  Cal_Address_t  newSize 
+)
+
+
Expands or contracts the block to a new size. + We try to avoid moving the block if possible. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+int 
+Cal_PerformanceTest(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * outputBddArray, 
+  int  numFunctions, 
+  int  iteration, 
+  int  seed, 
+  int  andPerformanceFlag, 
+  int  multiwayPerformanceFlag, 
+  int  onewayPerformanceFlag, 
+  int  quantifyPerformanceFlag, 
+  int  composePerformanceFlag, 
+  int  relprodPerformanceFlag, 
+  int  swapPerformanceFlag, 
+  int  substitutePerformanceFlag, 
+  int  sanityCheckFlag, 
+  int  computeMemoryOverheadFlag, 
+  int  superscalarFlag 
+)
+
+
optional +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+Cal_Bdd 
+Cal_PipelineCreateProvisionalBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  fUserBdd, 
+  Cal_Bdd  gUserBdd 
+)
+
+
The provisional BDD is automatically freed once the + pipeline is quitted. +

+ +

+
+int 
+Cal_PipelineExecute(
+  Cal_BddManager  bddManager 
+)
+
+
All the results are computed. User should update the + BDDs of interest. Eventually this feature would become transparent. +

+ +

Side Effects required +

+ +

See Also optional + + +
+
+int 
+Cal_PipelineInit(
+  Cal_BddManager  bddManager, 
+  Cal_BddOp_t  bddOp 
+)
+
+
All the operations for this pipeline must be of the + same kind. +

+ +

Side Effects None. +

+ +

+
+void 
+Cal_PipelineQuit(
+  Cal_BddManager  bddManager 
+)
+
+
The user must make sure to update all provisional BDDs + of interest before calling this routine. +

+ +

+
+void 
+Cal_PipelineSetDepth(
+  Cal_BddManager  bddManager, 
+  int  depth 
+)
+
+
The "depth" determines the amount of dependency we + would allow in pipelined computation. +

+ +

Side Effects None. +

+ +

+
+Cal_Bdd 
+Cal_PipelineUpdateProvisionalBdd(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd  provisionalBdd 
+)
+
+
The provisional BDD is automatically freed after + quitting pipeline. +

+ +

+
+void 
+Cal_TempAssociationAugment(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Pairs is 0 if the information represents only a list of + variables rather than a full association. +

+ +

Side Effects None +

+ +

+
+void 
+Cal_TempAssociationInit(
+  Cal_BddManager  bddManager, 
+  Cal_Bdd * associationInfoUserBdds, 
+  int  pairs 
+)
+
+
Pairs is 0 if the information represents only a list of + variables rather than a full association. +

+ +

Side Effects None +

+ +

+
+void 
+Cal_TempAssociationQuit(
+  Cal_BddManager  bddManager 
+)
+
+
Cleans up temporary associationoptional +

+ +

Side Effects None +

+ + +

+
+Last updated on 970711 20h11 + diff --git a/calGC.c b/calGC.c new file mode 100644 index 0000000..aee7fce --- /dev/null +++ b/calGC.c @@ -0,0 +1,448 @@ +/**CFile*********************************************************************** + + FileName [calGC.c] + + PackageName [cal] + + Synopsis [Garbage collection routines] + + Description [optional] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calGC.c,v 1.2 1998/09/16 16:08:40 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int CeilLog2(int number); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on.] + + Description [Sets the garbage collection mode, 0 means the garbage + collection should be turned off, 1 means garbage collection should + be on.] + + SideEffects [None.] + +******************************************************************************/ +void +Cal_BddSetGCMode( + Cal_BddManager bddManager, + int gcMode) +{ + bddManager->gcMode = gcMode; +} + + +/**Function******************************************************************** + + Synopsis [Invokes the garbage collection at the manager level.] + + Description [For each variable in the increasing id free nodes with reference + count equal to zero freeing a node results in decrementing reference count of + then and else nodes by one.] + + SideEffects [None.] + +******************************************************************************/ +int +Cal_BddManagerGC(Cal_BddManager bddManager) +{ + Cal_BddIndex_t index; + Cal_BddId_t id; + int numNodesFreed; + /* unsigned long origNodes = bddManager->numNodes; */ + + if (bddManager->numPeakNodes < (bddManager->numNodes + + bddManager->numForwardedNodes)){ + bddManager->numPeakNodes = bddManager->numNodes + + bddManager->numForwardedNodes ; + } + + CalHashTableGC(bddManager, bddManager->uniqueTable[0]); + for(index = 0; index < bddManager->numVars; index++){ + id = bddManager->indexToId[index]; + numNodesFreed = CalHashTableGC(bddManager, bddManager->uniqueTable[id]); + bddManager->numNodes -= numNodesFreed; + bddManager->numNodesFreed += numNodesFreed; + } + /* Free the cache entries related to unused BDD nodes */ + /* The assumption is that during CalHashTableGC, the freed BDD nodes + are marked. However, since they are not touched after being put + on the free list, the mark should be unaffected and can be used + for cleaning up the cache table. + */ + CalCacheTableTwoGCFlush(bddManager->cacheTable); + bddManager->numGC++; + return 0; +} + +/**Function******************************************************************** + + Synopsis [Sets the limit of the garbage collection.] + + Description [It tries to set the limit at twice the number of nodes + in the manager at the current point. However, the limit is not + allowed to fall below the MIN_GC_LIMIT or to exceed the value of + node limit (if one exists).] + + SideEffects [None.] + +******************************************************************************/ +void +Cal_BddManagerSetGCLimit(Cal_BddManager manager) +{ + manager->uniqueTableGCLimit = ((manager->numNodes) << 1); + if(manager->uniqueTableGCLimit < CAL_MIN_GC_LIMIT){ + manager->uniqueTableGCLimit = CAL_MIN_GC_LIMIT; + } + if (manager->nodeLimit && (manager->uniqueTableGCLimit > + manager->nodeLimit)){ + manager->uniqueTableGCLimit = manager->nodeLimit; + } +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddManagerGCCheck(Cal_BddManager_t * bddManager) +{ + if (bddManager->gcMode == 0) return; + if (bddManager->gcCheck > 0) return; + bddManager->gcCheck = CAL_GC_CHECK; + if(bddManager->numNodes > bddManager->uniqueTableGCLimit){ + Cal_BddManagerGC(bddManager); + Cal_BddManagerSetGCLimit(bddManager); + } +} + +/**Function******************************************************************** + + Synopsis [This function performs the garbage collection operation + for a particular index.] + + Description [The input is the hash table containing the nodes + belonging to that level. Each bin of the hash table is traversed and + the Bdd nodes with 0 reference count are put at the appropriate + level in the processing que of the manager.] + + SideEffects [The number of nodes in the hash table can possibly decrease.] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableGC(Cal_BddManager_t *bddManager, CalHashTable_t *hashTable) +{ + CalBddNode_t *last, *next, *ptr, *thenBddNode, *elseBddNode; + int i; + int oldNumEntries; + + oldNumEntries = hashTable->numEntries; + for(i = 0; i < hashTable->numBins; i++){ + last = NULL; + ptr = hashTable->bins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + if(CalBddNodeIsRefCountZero(ptr)){ + if (last == NULL){ + hashTable->bins[i] = next; + } + else{ + CalBddNodePutNextBddNode(last,next); + } + thenBddNode = CAL_BDD_POINTER(CalBddNodeGetThenBddNode(ptr)); + elseBddNode = CAL_BDD_POINTER(CalBddNodeGetElseBddNode(ptr)); + CalBddNodeDcrRefCount(thenBddNode); + CalBddNodeDcrRefCount(elseBddNode); + CalNodeManagerFreeNode(hashTable->nodeManager, ptr); + /* Mark the freed node for cache table clean up */ + /* We have to make sure that the clean up routine is called */ + /* right after this function (so that the marking remains */ + /* valid) */ + CalBddNodeMark(ptr); + hashTable->numEntries--; + } + else { + last = ptr; + } + ptr = next; + } + } + return oldNumEntries - hashTable->numEntries; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalRepackNodesAfterGC(Cal_BddManager_t *bddManager) +{ + int index, id, numPagesRequired, packingFlag, pageNum, nodeNum; + int rehashFlag = 0; + int newSizeIndex, hashValue; + CalNodeManager_t *nodeManager; + CalHashTable_t *uniqueTableForId; + CalBddNode_t *bddNode, *thenBddNode, *elseBddNode, *freeNodeList; + CalBddNode_t *newNode; + Cal_Bdd_t thenBdd, elseBdd; + + packingFlag = 0; + + for (index = bddManager->numVars-1; index >= 0; index--){ + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + nodeManager = uniqueTableForId->nodeManager; + if (CalBddIdNeedsRepacking(bddManager, id) == 0){ + if (packingFlag == 0) continue; /* nothing needs to be done */ + /* We just need to update the cofactors and continue; */ + for (pageNum=0; pageNum < nodeManager->numPages; pageNum++){ + for(nodeNum = 0, + bddNode = (CalBddNode_t *)nodeManager->pageList[pageNum]; + nodeNum < NUM_NODES_PER_PAGE; nodeNum++, bddNode += 1){ + if (CalBddNodeIsRefCountZero(bddNode) || + CalBddNodeIsForwarded(bddNode)) continue; + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + if (CalBddIsForwarded(thenBdd)){ + CalBddForward(thenBdd); + CalBddNodePutThenBdd(bddNode, thenBdd); + rehashFlag = 1; + } + if (CalBddIsForwarded(elseBdd)){ + CalBddForward(elseBdd); + CalBddNodePutElseBdd(bddNode, elseBdd); + rehashFlag = 1; + } + Cal_Assert(!CalBddIsRefCountZero(thenBdd)); + Cal_Assert(!CalBddIsRefCountZero(elseBdd)); + Cal_Assert(bddManager->idToIndex[id] < + bddManager->idToIndex[bddNode->thenBddId]); + Cal_Assert(bddManager->idToIndex[id] < + bddManager->idToIndex[bddNode->elseBddId]); + if (rehashFlag){ + CalUniqueTableForIdRehashNode(uniqueTableForId, bddNode, + thenBddNode, elseBddNode); + } + } + } + continue; /* move to next higher index */ + } + packingFlag = 1; + if ((uniqueTableForId->numBins > uniqueTableForId->numEntries) && + (uniqueTableForId->sizeIndex > HASH_TABLE_DEFAULT_SIZE_INDEX)){ + /* Free the old bins */ + Cal_MemFree(uniqueTableForId->bins); + /* Create the new set of bins */ + newSizeIndex = + CeilLog2(uniqueTableForId->numEntries/HASH_TABLE_DEFAULT_MAX_DENSITY); + if (newSizeIndex < HASH_TABLE_DEFAULT_SIZE_INDEX){ + newSizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + } + uniqueTableForId->sizeIndex = newSizeIndex; + uniqueTableForId->numBins = TABLE_SIZE(uniqueTableForId->sizeIndex); + uniqueTableForId->maxCapacity = + uniqueTableForId->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + uniqueTableForId->bins = Cal_MemAlloc(CalBddNode_t *, + uniqueTableForId->numBins); + if(uniqueTableForId->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + } + /* Clear the unique table bins */ + memset((char *)uniqueTableForId->bins, 0, + uniqueTableForId->numBins*sizeof(CalBddNode_t *)); + numPagesRequired = + uniqueTableForId->numEntries/NUM_NODES_PER_PAGE+1; + /* Traverse the first numPagesRequired pages of this nodeManager */ + /* Create the new free list */ + nodeManager->freeNodeList = freeNodeList = Cal_Nil(CalBddNode_t); + for (pageNum = 0; pageNum < nodeManager->numPages; pageNum++){ + for(nodeNum = 0, + bddNode = (CalBddNode_t *)nodeManager->pageList[pageNum]; + nodeNum < NUM_NODES_PER_PAGE; nodeNum++, bddNode += 1){ + if(CalBddNodeIsRefCountZero(bddNode) || + CalBddNodeIsForwarded(bddNode)){ + if (pageNum < numPagesRequired){ + bddNode->nextBddNode = freeNodeList; + freeNodeList = bddNode; + } + continue; + } + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + if (CalBddIsForwarded(thenBdd)){ + CalBddForward(thenBdd); + CalBddNodePutThenBdd(bddNode, thenBdd); + } + if (CalBddIsForwarded(elseBdd)){ + CalBddForward(elseBdd); + CalBddNodePutElseBdd(bddNode, elseBdd); + } + if (pageNum < numPagesRequired){ + /* Simply insert the node in the unique table */ + hashValue = CalDoHash2(thenBdd.bddNode, elseBdd.bddNode, + uniqueTableForId); + CalBddNodePutNextBddNode(bddNode, uniqueTableForId->bins[hashValue]); + uniqueTableForId->bins[hashValue] = bddNode; + } + else { + /* Create a new node */ + newNode = freeNodeList; + freeNodeList = newNode->nextBddNode; + newNode->thenBddNode = bddNode->thenBddNode; + newNode->elseBddNode = bddNode->elseBddNode; + newNode->thenBddId = bddNode->thenBddId; + newNode->elseBddId = bddNode->elseBddId; + newNode->nextBddNode = bddNode->nextBddNode; + bddNode->elseBddNode = FORWARD_FLAG; + bddNode->thenBddId = id; + bddNode->thenBddNode = newNode; + hashValue = CalDoHash2(thenBdd.bddNode, elseBdd.bddNode, + uniqueTableForId); + CalBddNodePutNextBddNode(newNode, uniqueTableForId->bins[hashValue]); + uniqueTableForId->bins[hashValue] = newNode; + } + } + if (pageNum >= numPagesRequired){ + /* Free this page. I am assuming that there would not be any + call to PageManagerAllocPage, until this function finishes */ + /* Also, CalPageManagerFreePage overwrites only the first field of + the bdd node (the nextBddNode field), hence no relevant + information is lost */ + CalPageManagerFreePage(nodeManager->pageManager, + nodeManager->pageList[pageNum]); + nodeManager->pageList[pageNum] = 0; + } + } +#ifdef _CAL_VERBOSE + printf("Recycled %4d pages for %3d id\n", + nodeManager->numPages-numPagesRequired, id); +#endif + nodeManager->numPages = numPagesRequired; + nodeManager->freeNodeList = freeNodeList; + } + /* Need to update the handles to the nodes being moved */ + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + + CalCacheTableTwoRepackUpdate(bddManager->cacheTable); + + /* Fix the user BDDs */ + CalBddReorderFixUserBddPtrs(bddManager); + + /* Fix the association */ + CalReorderAssociationFix(bddManager); + + Cal_Assert(CalCheckAssoc(bddManager)); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Returns the smallest integer greater than or equal to log2 of a + number] + + Description [Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1)] + + SideEffects [None] + +******************************************************************************/ +static int +CeilLog2(int number) +{ + int num, count; + for (num=number, count=0; num > 1; num >>= 1, count++); + if ((1 << count) != number) count++; + return count; +} diff --git a/calHashTable.c b/calHashTable.c new file mode 100644 index 0000000..375d239 --- /dev/null +++ b/calHashTable.c @@ -0,0 +1,1052 @@ +/**CFile*********************************************************************** + + FileName [calHashTable.c] + + PackageName [cal] + + Synopsis [Functions to manage the hash tables that are a part of + 1. unique table + 2. request queue + ] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calHashTable.c,v 1.8 1998/09/16 00:32:36 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int CeilLog2(int number); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Initialize a hash table using default parameters.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +CalHashTable_t * +CalHashTableInit(Cal_BddManager_t *bddManager, Cal_BddId_t bddId) +{ + CalHashTable_t *hashTable; + + hashTable = Cal_MemAlloc(CalHashTable_t, 1); + /*hashTable = CAL_BDD_NEW_REC(bddManager, CalHashTable_t);*/ + if(hashTable == Cal_Nil(CalHashTable_t)){ + CalBddFatalMessage("out of memory"); + } + hashTable->sizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + hashTable->numBins = TABLE_SIZE(hashTable->sizeIndex); + hashTable->maxCapacity = hashTable->numBins*HASH_TABLE_DEFAULT_MAX_DENSITY; + hashTable->bins = Cal_MemAlloc(CalBddNode_t *, hashTable->numBins); + if(hashTable->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + memset((char *)hashTable->bins, 0, + hashTable->numBins*sizeof(CalBddNode_t *)); + hashTable->bddId = bddId; + hashTable->nodeManager = bddManager->nodeManagerArray[bddId]; + hashTable->requestNodeList = Cal_Nil(CalRequestNode_t); + memset((char *)(&(hashTable->startNode)), 0, sizeof(CalBddNode_t)); + hashTable->endNode = &(hashTable->startNode); + hashTable->numEntries = 0; + return hashTable; +} + + +/**Function******************************************************************** + + Synopsis [Free a hash table along with the associated storage.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableQuit(Cal_BddManager_t *bddManager, CalHashTable_t * hashTable) +{ + if(hashTable == Cal_Nil(CalHashTable_t))return 1; + /* + for(i = 0; i < hashTable->numBins; i++){ + ptr = hashTable->bins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + CalNodeManagerFreeNode(hashTable->nodeManager, ptr); + ptr = next; + } + } + There is no need to free the nodes individually. They will be taken + care of by the PageManagerQuit. + We need to make sure that this function is called only during the global quitting. + If it need be called at some intermediate point, we need to free the BDD nodes + appropriately. + */ + + Cal_MemFree(hashTable->bins); + Cal_MemFree(hashTable); + /*CAL_BDD_FREE_REC(bddManager, hashTable, CalHashTable_t);*/ + return 0; +} + + + +/**Function******************************************************************** + + Synopsis [Directly insert a BDD node in the hash table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableAddDirect(CalHashTable_t * hashTable, CalBddNode_t * bddNode) +{ + int hashValue; + CalBddNode_t *thenBddNode, *elseBddNode; + + hashTable->numEntries++; + if(hashTable->numEntries >= hashTable->maxCapacity){ + CalHashTableRehash(hashTable, 1); + } + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + hashValue = CalDoHash2(thenBddNode, elseBddNode, hashTable); + CalBddNodePutNextBddNode(bddNode, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = bddNode; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableFindOrAdd(CalHashTable_t * hashTable, + Cal_Bdd_t thenBdd, + Cal_Bdd_t elseBdd, + Cal_Bdd_t * bddPtr) +{ + CalBddNode_t *ptr; + Cal_Bdd_t tmpBdd; + int hashValue; + + hashValue = CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), hashTable); + ptr = hashTable->bins[hashValue]; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(thenBdd, tmpBdd)){ + CalBddNodeGetElseBdd(ptr, tmpBdd); + if(CalBddIsEqual(elseBdd, tmpBdd)){ + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 1; + } + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + hashTable->numEntries++; + if(hashTable->numEntries > hashTable->maxCapacity){ + CalHashTableRehash(hashTable,1); + hashValue = CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), hashTable); + } + CalNodeManagerInitBddNode(hashTable->nodeManager, thenBdd, elseBdd, + hashTable->bins[hashValue], ptr); + hashTable->bins[hashValue] = ptr; + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 0; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableAddDirectAux(CalHashTable_t * hashTable, Cal_Bdd_t + thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * + bddPtr) +{ + CalBddNode_t *ptr; + int hashValue; + + hashTable->numEntries++; + if(hashTable->numEntries >= hashTable->maxCapacity){ + CalHashTableRehash(hashTable, 1); + } + hashValue = CalDoHash2(CalBddGetBddNode(thenBdd), CalBddGetBddNode(elseBdd), + hashTable); + CalNodeManagerInitBddNode(hashTable->nodeManager, thenBdd, elseBdd, + hashTable->bins[hashValue], ptr); + hashTable->bins[hashValue] = ptr; + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 0; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableCleanUp(CalHashTable_t * hashTable) +{ + CalNodeManager_t *nodeManager; + + nodeManager = hashTable->nodeManager; + hashTable->endNode->nextBddNode = nodeManager->freeNodeList; + nodeManager->freeNodeList = hashTable->startNode.nextBddNode; + hashTable->endNode = &(hashTable->startNode); + hashTable->numEntries = 0; + hashTable->startNode.nextBddNode = NULL; + Cal_Assert(!(hashTable->requestNodeList)); + hashTable->requestNodeList = Cal_Nil(CalRequestNode_t); + return; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableLookup( + CalHashTable_t * hashTable, + Cal_Bdd_t thenBdd, + Cal_Bdd_t elseBdd, + Cal_Bdd_t * bddPtr) +{ + CalBddNode_t *ptr; + Cal_Bdd_t tmpBdd; + int hashValue; + + hashValue = CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), hashTable); + ptr = hashTable->bins[hashValue]; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(thenBdd, tmpBdd)){ + CalBddNodeGetElseBdd(ptr, tmpBdd); + if(CalBddIsEqual(elseBdd, tmpBdd)){ + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 1; + } + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + return 0; +} + +/**Function******************************************************************** + + Synopsis [Deletes a BDD node in the hash table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableDelete(CalHashTable_t * hashTable, CalBddNode_t * bddNode) +{ + int hashValue; + Cal_Bdd_t thenBdd, elseBdd; + CalBddNode_t *ptr, *last; + + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + hashValue = + CalDoHash2(CalBddGetBddNode(thenBdd), CalBddGetBddNode(elseBdd), hashTable); + + last = Cal_Nil(CalBddNode_t); + ptr = hashTable->bins[hashValue]; + while(ptr != Cal_Nil(CalBddNode_t)){ + if(ptr == bddNode){ + if(last == Cal_Nil(CalBddNode_t)){ + hashTable->bins[hashValue] = CalBddNodeGetNextBddNode(ptr); + } + else{ + CalBddNodePutNextBddNode(last, CalBddNodeGetNextBddNode(ptr)); + } + hashTable->numEntries--; + CalNodeManagerFreeNode(hashTable->nodeManager, ptr); + return; + } + last = ptr; + ptr = CalBddNodeGetNextBddNode(ptr); + } + CalBddWarningMessage("Trying to delete a non-existent node\n"); +} + + +/**Function******************************************************************** + + Synopsis [Lookup unique table for id.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalUniqueTableForIdLookup( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + Cal_Bdd_t thenBdd, + Cal_Bdd_t elseBdd, + Cal_Bdd_t * bddPtr) +{ + CalBddNode_t *ptr; + Cal_Bdd_t tmpBdd; + int hashValue; + + hashValue = CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), hashTable); + ptr = hashTable->bins[hashValue]; + if(CalBddIsOutPos(thenBdd)){ + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(thenBdd, tmpBdd)){ + CalBddNodeGetElseBdd(ptr, tmpBdd); + if(CalBddIsEqual(elseBdd, tmpBdd)){ + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 1; + } + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + } + else{ + CalBddNot(thenBdd, thenBdd); + CalBddNot(elseBdd, elseBdd); + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(thenBdd, tmpBdd)){ + CalBddNodeGetElseBdd(ptr, tmpBdd); + if(CalBddIsEqual(elseBdd, tmpBdd)){ + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, CalBddNodeNot(ptr)); + return 1; + } + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + } + return 0; +} + + +/**Function******************************************************************** + + Synopsis [find or add in the unique table for id.] + + Description [optional] + + SideEffects [If a new BDD node is created (found == false), then the + numNodes field of the manager needs to be incremented.] + + SeeAlso [optional] + +******************************************************************************/ +int +CalUniqueTableForIdFindOrAdd( + Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + Cal_Bdd_t thenBdd, + Cal_Bdd_t elseBdd, + Cal_Bdd_t * bddPtr) +{ + int found = 0; + if (CalBddIsEqual(thenBdd, elseBdd)){ + *bddPtr = thenBdd; + found = 1; + } + else if(CalBddIsOutPos(thenBdd)){ + found = CalHashTableFindOrAdd(hashTable, thenBdd, elseBdd, bddPtr); + } + else{ + CalBddNot(thenBdd, thenBdd); + CalBddNot(elseBdd, elseBdd); + found = CalHashTableFindOrAdd(hashTable, thenBdd, elseBdd, bddPtr); + CalBddNot(*bddPtr, *bddPtr); + } + if (!found) bddManager->numNodes++; + return found; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ + +void +CalHashTableRehash(CalHashTable_t *hashTable,int grow) +{ + CalBddNode_t *ptr, *next; + CalBddNode_t **oldBins = hashTable->bins; + int i, hashValue; + int oldNumBins = hashTable->numBins; + + if(grow){ + hashTable->sizeIndex++; + } + else{ + if (hashTable->sizeIndex <= HASH_TABLE_DEFAULT_SIZE_INDEX){/* No need to rehash */ + return; + } + hashTable->sizeIndex--; + } + + hashTable->numBins = TABLE_SIZE(hashTable->sizeIndex); + hashTable->maxCapacity = hashTable->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + hashTable->bins = Cal_MemAlloc(CalBddNode_t *, hashTable->numBins); + if(hashTable->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + /* + for(i = 0; i < hashTable->numBins; i++){ + hashTable->bins[i] = Cal_Nil(CalBddNode_t); + } + */ + memset((char *)hashTable->bins, 0, + hashTable->numBins*sizeof(CalBddNode_t *)); + + for(i = 0; i < oldNumBins; i++){ + ptr = oldBins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + hashValue = CalDoHash2(CalBddNodeGetThenBddNode(ptr), + CalBddNodeGetElseBddNode(ptr), hashTable); + CalBddNodePutNextBddNode(ptr, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = ptr; + ptr = next; + } + } + Cal_MemFree(oldBins); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalUniqueTableForIdRehashNode(CalHashTable_t *hashTable, CalBddNode_t *bddNode, + CalBddNode_t *thenBddNode, + CalBddNode_t *elseBddNode) + +{ + CalBddNode_t *nextBddNode; + CalBddNode_t *ptr; + int found; + int hashValue; + int oldHashValue; + Cal_Bdd_t thenBdd; + + oldHashValue = CalDoHash2(thenBddNode, elseBddNode, hashTable); + hashValue = CalDoHash2(CalBddNodeGetThenBddNode(bddNode), + CalBddNodeGetElseBddNode(bddNode), + hashTable); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddIsComplement(thenBdd)) { + CalBddFatalMessage("Complement edge on then pointer"); + } + if (oldHashValue == hashValue) { + return; + } + + found = 0; + ptr = hashTable->bins[oldHashValue]; + if ((ptr != Cal_Nil(CalBddNode_t)) && (ptr == bddNode)) { + hashTable->bins[oldHashValue] = CalBddNodeGetNextBddNode(bddNode); + found = 1; + } else { + while (ptr != Cal_Nil(CalBddNode_t)) { + nextBddNode = CalBddNodeGetNextBddNode(ptr); + if (nextBddNode == bddNode) { + CalBddNodePutNextBddNode(ptr, CalBddNodeGetNextBddNode(bddNode)); + found = 1; + break; + } + ptr = nextBddNode; + } + } + + if (!found) { + CalBddFatalMessage("Node not found in the unique table"); + } else { + CalBddNodePutNextBddNode(bddNode, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = bddNode; + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ + +unsigned long +CalBddUniqueTableNumLockedNodes(Cal_BddManager_t *bddManager, + CalHashTable_t *uniqueTableForId) +{ + CalBddNode_t *bddNode; + long i; + unsigned long numLockedNodes = 0; + + for(i=0; inumBins; i++){ + bddNode = uniqueTableForId->bins[i]; + while (bddNode){ + numLockedNodes += CalBddNodeIsRefCountMax(bddNode); + bddNode = CalBddNodeGetNextBddNode(bddNode); + } + } + return numLockedNodes; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalPackNodes(Cal_BddManager_t *bddManager) +{ + int index, id; + CalNodeManager_t *nodeManager; + CalHashTable_t *uniqueTableForId; + + for (index = bddManager->numVars-1; index >= 0; index--){ + id = bddManager->indexToId[index]; + nodeManager = bddManager->nodeManagerArray[id]; + uniqueTableForId = bddManager->uniqueTable[id]; + CalBddPackNodesForSingleId(bddManager, id); + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddPackNodesForSingleId(Cal_BddManager_t *bddManager, + Cal_BddId_t id) +{ + /* Need to copy the one for "AfterReorder" and suitably modify. */ +} + +/**Function******************************************************************** + + Synopsis [Packs the nodes if the variables which has just + been sifted.] + + Description [fixForwardedNodesFlag: Whether we need to fix + the forwarded nodes of variables corresponding to bestIndex through + bottomIndex. If this flag is set, then the forwarded nodes of these + variables are traversed and updated after the nodes of the bestIndex + have been copied. At the end the forwarded nodes are freed. If this + flag is not set, it is assumed that the cleanup pass has already + been performed.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddPackNodesAfterReorderForSingleId(Cal_BddManager_t *bddManager, + int fixForwardedNodesFlag, + int bestIndex, + int bottomIndex) +{ + /* We need to pack the nodes for this id and fix the cofactors of + the upper indices. + */ + CalBddNode_t *node, *nextBddNode, *dupNode, **oldBins; + CalBddNode_t *thenBddNode, *elseBddNode, *bddNode; + Cal_Bdd_t thenBdd; + CalAddress_t *page; + int id = bddManager->indexToId[bestIndex]; + CalNodeManager_t *nodeManager = bddManager->nodeManagerArray[id]; + CalAddress_t **oldPageList = nodeManager->pageList; + int oldNumPages = nodeManager->numPages; + CalHashTable_t *uniqueTableForId = bddManager->uniqueTable[id]; + int numPagesRequired, newSizeIndex, index, i; + long oldNumBins, hashValue; + + +#ifdef _CAL_VERBOSE + fprintf(stdout,"Repacking id %3d\n", id); +#endif + + + nodeManager->freeNodeList = Cal_Nil(CalBddNode_t); + nodeManager->numPages = 0; + numPagesRequired = uniqueTableForId->numEntries/NUM_NODES_PER_PAGE; + nodeManager->maxNumPages = + 2*(numPagesRequired ? numPagesRequired : 1); + + nodeManager->pageList = Cal_MemAlloc(CalAddress_t *, + nodeManager->maxNumPages); + + oldBins = uniqueTableForId->bins; + oldNumBins = uniqueTableForId->numBins; + /* Create the new set of bins */ + newSizeIndex = + CeilLog2(uniqueTableForId->numEntries/HASH_TABLE_DEFAULT_MAX_DENSITY); + + if (newSizeIndex < HASH_TABLE_DEFAULT_SIZE_INDEX){ + newSizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + } + + uniqueTableForId->sizeIndex = newSizeIndex; + uniqueTableForId->numBins = TABLE_SIZE(uniqueTableForId->sizeIndex); + uniqueTableForId->maxCapacity = + uniqueTableForId->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + + uniqueTableForId->bins = Cal_MemAlloc(CalBddNode_t *, + uniqueTableForId->numBins); + if(uniqueTableForId->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + + memset((char *)uniqueTableForId->bins, 0, + uniqueTableForId->numBins*sizeof(CalBddNode_t *)); + + for (i = 0; i < oldNumBins; i++){ + node = oldBins[i]; + while (node){ + nextBddNode = CalBddNodeGetNextBddNode(node); + CalNodeManagerCreateAndDupBddNode(nodeManager, node, dupNode); + thenBddNode = CalBddNodeGetThenBddNode(dupNode); + elseBddNode = CalBddNodeGetElseBddNode(dupNode); + hashValue = CalDoHash2(thenBddNode, elseBddNode, uniqueTableForId); + CalBddNodePutNextBddNode(dupNode, uniqueTableForId->bins[hashValue]); + uniqueTableForId->bins[hashValue] = dupNode; + CalBddNodePutThenBddNode(node, dupNode); + CalBddNodePutThenBddId(node, id); + CalBddNodePutElseBddNode(node, FORWARD_FLAG); + node = nextBddNode; + Cal_Assert(!(CalBddNodeIsRefCountZero(dupNode))); + } + } + + if (fixForwardedNodesFlag){ + CalBddNode_t *requestNodeList = + bddManager->uniqueTable[id]->startNode.nextBddNode; + for (bddNode = requestNodeList; bddNode; bddNode = nextBddNode){ + Cal_Assert(CalBddNodeIsForwarded(bddNode)); + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddGetBddId(thenBdd) == id){ + if (CalBddIsForwarded(thenBdd)) { + CalBddForward(thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + CalBddNodePutThenBdd(bddNode, thenBdd); + } + } + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + for (index = bestIndex+1; index <= bottomIndex; index++){ + int varId = bddManager->indexToId[index]; + requestNodeList = + bddManager->uniqueTable[varId]->startNode.nextBddNode; + for (bddNode = requestNodeList; bddNode; bddNode = nextBddNode){ + Cal_Assert(CalBddNodeIsForwarded(bddNode)); + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddIsForwarded(thenBdd)) { + CalBddForward(thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + CalBddNodePutThenBdd(bddNode, thenBdd); + } + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + } + } + +/* Traverse the upper indices fixing the cofactors */ + for (index = bestIndex-1; index >= 0; index--){ + CalBddReorderFixCofactors(bddManager, + bddManager->indexToId[index]); + } + + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + + /* Fix the user BDDs */ + CalBddReorderFixUserBddPtrs(bddManager); + + CalBddIsForwardedTo(bddManager->varBdds[id]); + + /* Fix the association */ + CalReorderAssociationFix(bddManager); + + /* Free the old bins */ + Cal_MemFree(oldBins); + + uniqueTableForId->endNode = &(uniqueTableForId->startNode); + uniqueTableForId->startNode.nextBddNode = NULL; + if (fixForwardedNodesFlag){ + CalBddReorderReclaimForwardedNodes(bddManager, bestIndex+1, + bottomIndex); + } + /* Free the old pages */ + for (i = 0; i < oldNumPages; i++){ + page = oldPageList[i]; + CalPageManagerFreePage(nodeManager->pageManager, page); + } + Cal_MemFree(oldPageList); + Cal_Assert(CalCheckAllValidity(bddManager)); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddPackNodesForMultipleIds(Cal_BddManager_t *bddManager, + Cal_BddId_t beginId, int numLevels) +{ + /* We need to pack the nodes for this id and fix the cofactors of + the upper indices. + */ + int index = bddManager->idToIndex[beginId]; + int level, id; + long i, j; + CalBddNode_t *node, *nextBddNode, *dupNode, *thenBddNode; + CalBddNode_t *elseBddNode, **oldBins; + Cal_Bdd_t thenBdd, elseBdd; + CalNodeManager_t *nodeManager; + CalHashTable_t *uniqueTableForId; + int someRepackingDone = 0; + long oldNumBins, hashValue; + int newSizeIndex; + + + CalAddress_t *page, ***oldPageListArray, **oldPageList; + int *oldNumPagesArray; + int numPagesRequired; + + oldPageListArray = Cal_MemAlloc(CalAddress_t **, numLevels); + + oldNumPagesArray = Cal_MemAlloc(int, numLevels); + + for (level = numLevels-1; level >= 0; level--){ + id = bddManager->indexToId[index+level]; + oldNumPagesArray[level] = 0; + oldPageListArray[level] = Cal_Nil(CalAddress_t *); + if (CalBddIdNeedsRepacking(bddManager, id)){ + nodeManager = bddManager->nodeManagerArray[id]; + uniqueTableForId = bddManager->uniqueTable[id]; + oldPageListArray[level] = nodeManager->pageList; + oldNumPagesArray[level] = nodeManager->numPages; + nodeManager->freeNodeList = Cal_Nil(CalBddNode_t); + nodeManager->numPages = 0; + numPagesRequired = uniqueTableForId->numEntries/NUM_NODES_PER_PAGE; + nodeManager->maxNumPages = + 2*(numPagesRequired ? numPagesRequired : 1); + nodeManager->pageList = Cal_MemAlloc(CalAddress_t *, + nodeManager->maxNumPages); + oldBins = uniqueTableForId->bins; + oldNumBins = uniqueTableForId->numBins; + /* Create the new set of bins */ + newSizeIndex = + CeilLog2(uniqueTableForId->numEntries / + HASH_TABLE_DEFAULT_MAX_DENSITY); + if (newSizeIndex < HASH_TABLE_DEFAULT_SIZE_INDEX){ + newSizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + } + uniqueTableForId->sizeIndex = newSizeIndex; + uniqueTableForId->numBins = TABLE_SIZE(uniqueTableForId->sizeIndex); + uniqueTableForId->maxCapacity = + uniqueTableForId->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + + uniqueTableForId->bins = Cal_MemAlloc(CalBddNode_t *, + uniqueTableForId->numBins); + if(uniqueTableForId->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + memset((char *)uniqueTableForId->bins, 0, + uniqueTableForId->numBins*sizeof(CalBddNode_t *)); + + for (i = 0; i < oldNumBins; i++){ + node = oldBins[i]; + while (node){ + nextBddNode = CalBddNodeGetNextBddNode(node); + CalBddNodeGetThenBdd(node, thenBdd); + CalBddNodeGetElseBdd(node, elseBdd); + if (CalBddIsForwarded(thenBdd)){ + CalBddForward(thenBdd); + CalBddNodePutThenBdd(node, thenBdd); + } + if (CalBddIsForwarded(elseBdd)){ + CalBddForward(elseBdd); + CalBddNodePutElseBdd(node, elseBdd); + } + CalNodeManagerCreateAndDupBddNode(nodeManager, node, dupNode); + thenBddNode = CalBddNodeGetThenBddNode(dupNode); + elseBddNode = CalBddNodeGetElseBddNode(dupNode); + hashValue = CalDoHash2(thenBddNode, elseBddNode, uniqueTableForId); + CalBddNodePutNextBddNode(dupNode, uniqueTableForId->bins[hashValue]); + uniqueTableForId->bins[hashValue] = dupNode; + CalBddNodePutThenBddNode(node, dupNode); + CalBddNodePutThenBddId(node, id); + CalBddNodePutElseBddNode(node, FORWARD_FLAG); + node = nextBddNode; + Cal_Assert(!(CalBddNodeIsRefCountZero(dupNode))); + } + } + +#ifdef __FOO__ + /*fprintf(stdout,"Repacking id = %d, index = %d\n", id, index+level);*/ + /* First put all the nodes in that list */ + nodeList = Cal_Nil(CalBddNode_t); + for (i = 0; i < uniqueTableForId->numBins; i++){ + node = uniqueTableForId->bins[i]; + while (node){ + nextBddNode = CalBddNodeGetNextBddNode(node); + /* The "then" and "else" pointers could be forwarded */ + CalBddNodeGetThenBdd(node, thenBdd); + CalBddNodeGetElseBdd(node, elseBdd); + if (CalBddIsForwarded(thenBdd)){ + CalBddForward(thenBdd); + CalBddNodePutThenBdd(node, thenBdd); + } + if (CalBddIsForwarded(elseBdd)){ + CalBddForward(elseBdd); + CalBddNodePutElseBdd(node, elseBdd); + } + CalBddNodePutNextBddNode(node, nodeList); + nodeList = node; + node = nextBddNode; + } + uniqueTableForId->bins[i] = Cal_Nil(CalBddNode_t); + } + uniqueTableForId->numEntries = 0; + + for (node = nodeList; node; node = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(node); + CalNodeManagerCreateAndDupBddNode(nodeManager, node, dupNode); + /* Hash the dupNode */ + CalHashTableAddDirect(uniqueTableForId, dupNode); + /* Make the original node a forwarding node */ + CalBddNodePutThenBddNode(node, dupNode); + CalBddNodePutThenBddId(node, id); + CalBddNodePutElseBddNode(node, FORWARD_FLAG); + } +#endif + someRepackingDone = 1; + } + else if (someRepackingDone){ /* Still need to fix the cofactors */ + CalBddReorderFixCofactors(bddManager, id); + } + } + + + /* Traverse the upper indices fixing the cofactors */ + for (i = index-1; i >= 0; i--){ + CalBddReorderFixCofactors(bddManager, + bddManager->indexToId[i]); + } + + /* Fix the user BDDs */ + CalBddReorderFixUserBddPtrs(bddManager); + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + /* Fix Cache Tables */ + (void)CalCacheTableTwoRepackUpdate(bddManager->cacheTable); + + for (level = numLevels - 1 ; level >= 0; level--){ + id = bddManager->indexToId[index+level]; + /* Update varBdd field of bdd manager */ + CalBddIsForwardedTo(bddManager->varBdds[id]); + /* Fix associations */ + CalVarAssociationRepackUpdate(bddManager, id); + /* Free the old pages */ + nodeManager = bddManager->nodeManagerArray[id]; + oldPageList = oldPageListArray[level]; + for (j = 0; j < oldNumPagesArray[level]; j++){ + page = oldPageList[j]; + CalPageManagerFreePage(nodeManager->pageManager, page); + } + if ((unsigned long)oldPageList) Cal_MemFree(oldPageList); + } + Cal_MemFree(oldPageListArray); + Cal_MemFree(oldNumPagesArray); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the smallest integer greater than or equal to log2 of a + number] + + Description [Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1)] + + SideEffects [None] + +******************************************************************************/ +static int +CeilLog2( + int number) +{ + int num, count; + for (num=number, count=0; num > 1; num >>= 1, count++); + if ((1 << count) != number) count++; + return count; +} diff --git a/calHashTableOne.c b/calHashTableOne.c new file mode 100644 index 0000000..5beba1d --- /dev/null +++ b/calHashTableOne.c @@ -0,0 +1,298 @@ +/**CFile*********************************************************************** + + FileName [calHashTableOne.c] + + PackageName [cal] + + Synopsis [Routines for managing hash table with Bdd is a key and + int, long, or double as a value] + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calHashTableOne.c,v 1.1.1.3 1998/05/04 00:58:57 hsv Exp $] + +******************************************************************************/ +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#ifdef USE_POWER_OF_2 +# define HashTableOneDoHash(hashTable, keyBdd) \ + (((CalAddress_t)(CalBddGetBddNode(keyBdd)) / NODE_SIZE) & ((hashTable)->numBins - 1)) +#else +# define HashTableOneDoHash(hashTable, keyBdd) \ + (((CalAddress_t)(CalBddGetBddNode(keyBdd)) / NODE_SIZE) % hashTable->numBins) +#endif + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void HashTableOneRehash(CalHashTable_t * hashTable, int grow); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Initialize a hash table using default parameters.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +CalHashTable_t * +CalHashTableOneInit(Cal_BddManager_t * bddManager, int itemSize) +{ + int i; + CalHashTable_t *hashTable; + + hashTable = Cal_MemAlloc(CalHashTable_t, 1); + if(hashTable == Cal_Nil(CalHashTable_t)){ + CalBddFatalMessage("out of memory"); + } + hashTable->sizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + hashTable->numBins = TABLE_SIZE(hashTable->sizeIndex); + hashTable->maxCapacity = hashTable->numBins*HASH_TABLE_DEFAULT_MAX_DENSITY; + hashTable->bins = Cal_MemAlloc(CalBddNode_t *, hashTable->numBins); + if(hashTable->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + for(i = 0; i < hashTable->numBins; i++){ + hashTable->bins[i] = Cal_Nil(CalBddNode_t); + } + hashTable->numEntries = 0; + hashTable->bddId = (Cal_BddId_t)itemSize; + if(itemSize > NODE_SIZE){ + CalBddFatalMessage("CalHashTableOneInit: itemSize exceeds NODE_SIZE"); + } + hashTable->nodeManager = bddManager->nodeManagerArray[0]; + hashTable->requestNodeList = Cal_Nil(CalRequestNode_t); + return hashTable; +} + + +/**Function******************************************************************** + + Synopsis [Free a hash table along with the associated storage.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableOneQuit( + CalHashTable_t * hashTable) +{ + CalBddNode_t *ptr, *next, *node; + int i; + if(hashTable == Cal_Nil(CalHashTable_t))return; + for(i = 0; i < hashTable->numBins; i++){ + ptr = hashTable->bins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + node = CalBddNodeGetElseBddNode(ptr); + CalNodeManagerFreeNode(hashTable->nodeManager, node); + CalNodeManagerFreeNode(hashTable->nodeManager, ptr); + ptr = next; + } + } + Cal_MemFree(hashTable->bins); + Cal_MemFree(hashTable); +} + + +/**Function******************************************************************** + + Synopsis [Directly insert a BDD node in the hash table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableOneInsert(CalHashTable_t * hashTable, Cal_Bdd_t keyBdd, + char * valuePtr) +{ + int hashValue; + CalBddNode_t *bddNode, *dataPtr; + + hashValue = HashTableOneDoHash(hashTable, keyBdd); + hashTable->numEntries++; + if(hashTable->numEntries >= hashTable->maxCapacity){ + HashTableOneRehash(hashTable, 1); + hashValue = HashTableOneDoHash(hashTable, keyBdd); + } + CalNodeManagerAllocNode(hashTable->nodeManager, dataPtr); + memcpy(dataPtr, valuePtr, (size_t)hashTable->bddId); + CalNodeManagerAllocNode(hashTable->nodeManager, bddNode); + CalBddNodePutThenBdd(bddNode, keyBdd); + CalBddNodePutElseBddNode(bddNode, dataPtr); + CalBddNodePutNextBddNode(bddNode, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = bddNode; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableOneLookup(CalHashTable_t * hashTable, Cal_Bdd_t keyBdd, + char ** valuePtrPtr) +{ + CalBddNode_t *ptr; + Cal_Bdd_t tmpBdd; + int hashValue; + + hashValue = HashTableOneDoHash(hashTable, keyBdd); + ptr = hashTable->bins[hashValue]; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(keyBdd, tmpBdd)){ + if(valuePtrPtr){ + *valuePtrPtr = (char *)CalBddNodeGetElseBddNode(ptr); + } + return 1; + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + if(valuePtrPtr){ + *valuePtrPtr = Cal_Nil(char); + } + return 0; +} +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableOneRehash( + CalHashTable_t * hashTable, + int grow) +{ + CalBddNode_t *ptr, *next; + CalBddNode_t **oldBins = hashTable->bins; + int i, hashValue; + int oldNumBins = hashTable->numBins; + Cal_Bdd_t keyBdd; + + if(grow){ + hashTable->sizeIndex++; + } + else{ + if (hashTable->sizeIndex <= HASH_TABLE_DEFAULT_SIZE_INDEX){/* No need to rehash */ + return; + } + hashTable->sizeIndex--; + } + + hashTable->numBins = TABLE_SIZE(hashTable->sizeIndex); + hashTable->maxCapacity = hashTable->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + hashTable->bins = Cal_MemAlloc(CalBddNode_t *, hashTable->numBins); + if(hashTable->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + for(i = 0; i < hashTable->numBins; i++){ + hashTable->bins[i] = Cal_Nil(CalBddNode_t); + } + + for(i = 0; i < oldNumBins; i++){ + ptr = oldBins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + CalBddNodeGetThenBdd(ptr, keyBdd); + hashValue = HashTableOneDoHash(hashTable, keyBdd); + CalBddNodePutNextBddNode(ptr, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = ptr; + ptr = next; + } + } + Cal_MemFree(oldBins); +} + + + + + + + + + + diff --git a/calHashTableThree.c b/calHashTableThree.c new file mode 100644 index 0000000..9290094 --- /dev/null +++ b/calHashTableThree.c @@ -0,0 +1,221 @@ +/**CFile*********************************************************************** + + FileName [calHashTableThree.c] + + PackageName [cal] + + Synopsis [Functions to manage the hash tables that are a part of + ITE operation] + + Description [CalHashTableThreeFindOrAdd] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calHashTableThree.c,v 1.1.1.3 1998/05/04 00:58:58 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#ifdef USE_POWER_OF_2 +#define CalDoHash3(fBddNode, gBddNode, hBddNode,table) \ +((((CalAddress_t)fBddNode + \ + (CalAddress_t)gBddNode + \ + (CalAddress_t) hBddNode) \ + / NODE_SIZE) & ((table)->numBins-1)) +#else +#define CalDoHash3(fBddNode, gBddNode, hBddNode,table) \ + ((((CalAddress_t)fBddNode + \ + (CalAddress_t)gBddNode + \ + (CalAddress_t) hBddNode) \ + / NODE_SIZE)% table->numBins) +#endif +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalHashTableThreeRehash(CalHashTable_t *hashTable, int grow); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalHashTableThreeFindOrAdd(CalHashTable_t * hashTable, + Cal_Bdd_t f, + Cal_Bdd_t g, + Cal_Bdd_t h, + Cal_Bdd_t * bddPtr) +{ + CalBddNode_t *ptr, *ptrIndirect; + Cal_Bdd_t tmpBdd; + int hashValue; + + hashValue = CalDoHash3(CalBddGetBddNode(f), + CalBddGetBddNode(g), CalBddGetBddNode(h), hashTable); + ptr = hashTable->bins[hashValue]; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, tmpBdd); + if(CalBddIsEqual(f, tmpBdd)){ + ptrIndirect = CalBddNodeGetElseBddNode(ptr); + CalBddNodeGetThenBdd(ptrIndirect, tmpBdd); + if(CalBddIsEqual(g, tmpBdd)){ + CalBddNodeGetElseBdd(ptrIndirect, tmpBdd); + if(CalBddIsEqual(h, tmpBdd)){ + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 1; + } + } + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + hashTable->numEntries++; + if(hashTable->numEntries > hashTable->maxCapacity){ + CalHashTableThreeRehash(hashTable,1); + hashValue = CalDoHash3(CalBddGetBddNode(f), + CalBddGetBddNode(g), CalBddGetBddNode(h), hashTable); + } + CalNodeManagerAllocNode(hashTable->nodeManager, ptr); + CalNodeManagerAllocNode(hashTable->nodeManager, ptrIndirect); + CalBddNodePutThenBdd(ptr, f); + CalBddNodePutThenBdd(ptrIndirect, g); + CalBddNodePutElseBdd(ptrIndirect, h); + CalBddNodePutElseBddNode(ptr, ptrIndirect); + CalBddNodePutNextBddNode(ptr, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = ptr; + CalBddPutBddId(*bddPtr, hashTable->bddId); + CalBddPutBddNode(*bddPtr, ptr); + return 0; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalHashTableThreeRehash(CalHashTable_t *hashTable, int grow) +{ + CalBddNode_t *ptr, *ptrIndirect, *next; + CalBddNode_t **oldBins = hashTable->bins; + int i, hashValue; + int oldNumBins = hashTable->numBins; + + if(grow){ + hashTable->sizeIndex++; + } + else{ + if (hashTable->sizeIndex <= HASH_TABLE_DEFAULT_SIZE_INDEX){/* No need to rehash */ + return; + } + hashTable->sizeIndex--; + } + + hashTable->numBins = TABLE_SIZE(hashTable->sizeIndex); + hashTable->numBins = hashTable->numBins; + hashTable->maxCapacity = hashTable->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + hashTable->bins = Cal_MemAlloc(CalBddNode_t *, hashTable->numBins); + if(hashTable->bins == Cal_Nil(CalBddNode_t *)){ + CalBddFatalMessage("out of memory"); + } + for(i = 0; i < hashTable->numBins; i++){ + hashTable->bins[i] = Cal_Nil(CalBddNode_t); + } + + for(i = 0; i < oldNumBins; i++){ + ptr = oldBins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(ptr); + ptrIndirect = CalBddNodeGetElseBddNode(ptr); + hashValue = CalDoHash3(CalBddNodeGetThenBddNode(ptr), + CalBddNodeGetThenBddNode(ptrIndirect), + CalBddNodeGetElseBddNode(ptrIndirect), hashTable); + CalBddNodePutNextBddNode(ptr, hashTable->bins[hashValue]); + hashTable->bins[hashValue] = ptr; + ptr = next; + } + } + Cal_MemFree(oldBins); +} + + + + + + + + diff --git a/calInt.h b/calInt.h new file mode 100644 index 0000000..75fd816 --- /dev/null +++ b/calInt.h @@ -0,0 +1,1578 @@ +/**CHeaderFile***************************************************************** + + FileName [calInt.h] + + PackageName [cal] + + Synopsis [The internal data structures, macros and function declarations] + + Description [] + + SeeAlso [cal.h] + + Author [Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu + Jagesh Sanghavi (sanghavi@ic.eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calInt.h,v 1.9 1998/09/15 19:02:53 ravi Exp $] + +******************************************************************************/ + +#ifndef _CALINT +#define _CALINT + +#include "cal.h" + +/* Make sure variable argument lists work */ +#if HAVE_STDARG_H +# include +#else +# if HAVE_VARARGS_H +# include +# else +# error "Need to have HAVE_STDARG_H or HAVE_VARARGS_H defined for variable arguments" +# endif +#endif + + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/* Begin Performance Related Constants */ + +/* Garbage collection and reordering related constants */ +/* The following constants could significantly affect the + performance of the package */ + + +#define CAL_MIN_GC_LIMIT 10000 /* minimum number of nodes in the unique table + before performing garbage collection. It can + be overridden by user define node limit */ + + + + +#define CAL_REPACK_AFTER_GC_THRESHOLD 0.75 /* If the number of nodes fall below + this factor after garbage + collection, repacking should be + done */ +/* A note about repacking after garbage collection: Since repacking +** moves the node pointers, it is important that "user" does not have +** access to internal node pointers during such times. If for some +** purposes the node handle is needed and also there is a possibility of +** garbage collection being invoked, this field (repackAfterGCThreshold) of +** the bdd manager should be set to 0. +*/ + +#define CAL_TABLE_REPACK_THRESHOLD 0.9 /* If the page utility of a unique + table (for some id) goes below this, repacking + would be done */ + +#define CAL_BDD_REORDER_THRESHOLD 10000 /* Don't perform reordering below these + many nodes */ + +#define CAL_NUM_PAGES_THRESHOLD 3 + +#define CAL_NUM_FORWARDED_NODES_LIMIT 50000 /* maximum number of forwarded nodes + allowed during BF reordering */ + +#define CAL_GC_CHECK 100 /* garbage collection check performed after + addition of every GC_CHECK number of nodes to + the unique table */ + +/* End Performance Related Constants */ + +/* Memory Management related constants */ +#define NODE_SIZE sizeof(CalBddNode_t) /* sizeof(CalBddNode_t) */ + +#ifndef PAGE_SIZE +# define PAGE_SIZE 4096 /* size of a virtual memory page */ +#endif +#ifndef LG_PAGE_SIZE +# define LG_PAGE_SIZE 12 /* log2 of the page size */ +#endif + +#define NUM_NODES_PER_PAGE (PAGE_SIZE/NODE_SIZE) + +#define MAX_NUM_SEGMENTS 32 +#define NUM_PAGES_PER_SEGMENT 64 /* We start with grabbing 64 pages at a time */ +#define MIN_NUM_PAGES_PER_SEGMENT 4 +#define MAX_NUM_PAGES 10 + +#define MIN_REC_SIZE CAL_ALLOC_ALIGNMENT +#define MAX_REC_SIZE (sizeof(CalHashTable_t)) /* size of hash table */ +#define NUM_REC_MGRS (((MAX_REC_SIZE-MIN_REC_SIZE)/CAL_ALLOC_ALIGNMENT)+1) + + + + +/* true / false */ +#ifndef TRUE +#define TRUE 1 +#endif +#ifndef FALSE +#define FALSE 0 +#endif + + + + +/* Error Codes */ +#define CAL_BDD_OK 0 +#define CAL_BDD_OVERFLOWED 1 + +/* bdd variable id and index related constants */ +#define CAL_BDD_NULL_ID ((unsigned short) ((1 << 8*sizeof(unsigned short)) - 1)) +#define CAL_BDD_CONST_ID 0 +#define CAL_MAX_VAR_ID ((unsigned short) (CAL_BDD_NULL_ID - 1)) +#define CAL_BDD_NULL_INDEX (unsigned short) ((1 << 8*sizeof(unsigned short)) - 1) +#define CAL_BDD_CONST_INDEX CAL_BDD_NULL_INDEX +#define CAL_MAX_VAR_INDEX (CAL_BDD_NULL_INDEX - 1) +#define CAL_MAX_REF_COUNT (unsigned short)((1 << 8*sizeof(char)) - 1) +#define CAL_INFINITY (1 << 20) + +/* Pipeline related constants */ +#define MAX_INSERT_DEPTH 256 +#define PIPELINE_EXECUTION_DEPTH 1 +#define DEFAULT_DEPTH 4 +#define DEFAULT_MAX_DEPTH 6 + + +#define FORWARD_FLAG 0 /* Flag used to identify redundant nodes */ + + +/* Hash table management related constants. */ +#define HASH_TABLE_DEFAULT_MAX_DENSITY 5 +#define HASH_TABLE_DEFAULT_SIZE_INDEX 8 +#define HASH_TABLE_DEFAULT_NUM_BINS TABLE_SIZE(HASH_TABLE_DEFAULT_SIZE_INDEX) +#define HASH_TABLE_DEFAULT_MAX_CAPACITY HASH_TABLE_DEFAULT_NUM_BINS*HASH_TABLE_DEFAULT_MAX_DENSITY +extern unsigned long calPrimes[]; + +#define USE_POWER_OF_2 +#ifdef USE_POWER_OF_2 +#define TABLE_SIZE(sizeIndex) (1<freeNodeList != Cal_Nil(CalBddNode_t)){ \ + node = nodeManager->freeNodeList; \ + nodeManager->freeNodeList = ((CalBddNode_t *)(node))->nextBddNode; \ + Cal_Assert(!((CalAddress_t)nodeManager->freeNodeList & 0xf));\ + } \ + else{ \ + CalBddNode_t *_freeNodeList, *_nextNode, *_node; \ + _freeNodeList = \ + (CalBddNode_t *)CalPageManagerAllocPage(nodeManager->pageManager); \ + for(_node = _freeNodeList + NUM_NODES_PER_PAGE - 1, _nextNode =0; \ + _node != _freeNodeList; _nextNode = _node--){ \ + _node->nextBddNode = _nextNode; \ + } \ + nodeManager->freeNodeList = _freeNodeList + 1; \ + node = _node; \ + if ((nodeManager)->numPages == (nodeManager)->maxNumPages){ \ + (nodeManager)->maxNumPages *= 2; \ + (nodeManager)->pageList = \ + Cal_MemRealloc(CalAddress_t *, (nodeManager)->pageList, \ + (nodeManager)->maxNumPages); \ + } \ + (nodeManager)->pageList[(nodeManager)->numPages++] = (CalAddress_t *)_freeNodeList; \ + } \ + ((CalBddNode_t *)(node))->nextBddNode = 0; \ + ((CalBddNode_t *)(node))->thenBddId = 0; \ + ((CalBddNode_t *)(node))->elseBddId = 0; \ + ((CalBddNode_t *)(node))->thenBddNode = 0; \ + ((CalBddNode_t *)(node))->elseBddNode = 0; \ +} + +#define CalNodeManagerFreeNode(nodeManager, node) \ +{ \ + (node)->nextBddNode = (nodeManager)->freeNodeList; \ + (nodeManager)->freeNodeList = node; \ +} +#define CalNodeManagerInitBddNode(nodeManager, thenBdd, elseBdd, next, node) \ +{ \ + if((nodeManager)->freeNodeList != Cal_Nil(CalBddNode_t)){ \ + node = nodeManager->freeNodeList; \ + nodeManager->freeNodeList = ((CalBddNode_t *)(node))->nextBddNode; \ + Cal_Assert(!((CalAddress_t)nodeManager->freeNodeList & 0xf));\ + } \ + else{ \ + CalBddNode_t *_freeNodeList, *_nextNode, *_node; \ + _freeNodeList = \ + (CalBddNode_t *)CalPageManagerAllocPage(nodeManager->pageManager); \ + for(_node = _freeNodeList + NUM_NODES_PER_PAGE - 1, _nextNode =0; \ + _node != _freeNodeList; _nextNode = _node--){ \ + _node->nextBddNode = _nextNode; \ + } \ + nodeManager->freeNodeList = _freeNodeList + 1; \ + node = _node; \ + if ((nodeManager)->numPages == (nodeManager)->maxNumPages){ \ + (nodeManager)->maxNumPages *= 2; \ + (nodeManager)->pageList = \ + Cal_MemRealloc(CalAddress_t *, (nodeManager)->pageList, \ + (nodeManager)->maxNumPages); \ + } \ + (nodeManager)->pageList[(nodeManager)->numPages++] = (CalAddress_t *)_freeNodeList; \ + } \ + ((CalBddNode_t *)(node))->nextBddNode = next; \ + ((CalBddNode_t *)(node))->thenBddId = CalBddGetBddId(thenBdd); \ + ((CalBddNode_t *)(node))->elseBddId = CalBddGetBddId(elseBdd); \ + ((CalBddNode_t *)(node))->thenBddNode = CalBddGetBddNode(thenBdd); \ + ((CalBddNode_t *)(node))->elseBddNode = CalBddGetBddNode(elseBdd); \ +} + +#define CalNodeManagerCreateAndDupBddNode(nodeManager, node, dupNode)\ +{ \ + if((nodeManager)->freeNodeList != Cal_Nil(CalBddNode_t)){ \ + dupNode = nodeManager->freeNodeList; \ + nodeManager->freeNodeList = ((CalBddNode_t *)(dupNode))->nextBddNode; \ + } \ + else{ \ + CalBddNode_t *_freeNodeList, *_nextNode, *_node; \ + _freeNodeList = \ + (CalBddNode_t *)CalPageManagerAllocPage(nodeManager->pageManager); \ + for(_node = _freeNodeList + NUM_NODES_PER_PAGE - 1, _nextNode =0; \ + _node != _freeNodeList; _nextNode = _node--){ \ + _node->nextBddNode = _nextNode; \ + } \ + nodeManager->freeNodeList = _freeNodeList + 1; \ + dupNode = _node; \ + if ((nodeManager)->numPages == (nodeManager)->maxNumPages){ \ + (nodeManager)->maxNumPages *= 2; \ + (nodeManager)->pageList = \ + Cal_MemRealloc(CalAddress_t *, (nodeManager)->pageList, \ + (nodeManager)->maxNumPages); \ + } \ + (nodeManager)->pageList[(nodeManager)->numPages++] = (CalAddress_t *)_freeNodeList; \ + } \ + ((CalBddNode_t *)(dupNode))->nextBddNode = (node)->nextBddNode; \ + ((CalBddNode_t *)(dupNode))->thenBddId = (node)->thenBddId;\ + ((CalBddNode_t *)(dupNode))->elseBddId = (node)->elseBddId;\ + ((CalBddNode_t *)(dupNode))->thenBddNode = (node)->thenBddNode;\ + ((CalBddNode_t *)(dupNode))->elseBddNode = (node)->elseBddNode; \ +} + +/* Record manager size range stuff */ + +#define CAL_BDD_NEW_REC(bddManager, type) ((type *)Cal_MemNewRec((bddManager)->recordMgrArray[(CAL_ROUNDUP(sizeof(type))-MIN_REC_SIZE)/CAL_ALLOC_ALIGNMENT])) +#define CAL_BDD_FREE_REC(bddManager, rec, type) Cal_MemFreeRec((bddManager)->recordMgrArray[(CAL_ROUNDUP(sizeof(type))-MIN_REC_SIZE)/CAL_ALLOC_ALIGNMENT], (rec)) + +/* +** We would like to do repacking if : +** i) The id has more than minimum number of pages. +** ii) The ratio between the actual number of entries and the capacity is +** less than a threshold. +*/ +#define CalBddIdNeedsRepacking(bddManager, id) \ +((bddManager->nodeManagerArray[id]->numPages > CAL_NUM_PAGES_THRESHOLD) && (bddManager->uniqueTable[id]->numEntries < bddManager->tableRepackThreshold * \ + bddManager->nodeManagerArray[id]->numPages * NUM_NODES_PER_PAGE)) + + +/* + * Macros for managing Cal_Bdd_t and CalBddNode_t. + * INTERNAL FUNCTIONS SHOULD NOT TOUCH THE INTERNAL FIELDS + * FUNCTIONS IN calTerminal.c ARE EXCEPTION TO THIS GENERAL RULE + * + * {CalBdd} X {Get, Put} X {ThenBddId, ElseBddId, ThenBddNode, ElseBddNode, + * ThenBdd, ElseBdd, BddId, BddNode, NextBddNode} + * {CalBdd} X {Get, Put, Icr, Dcr, Add} X {RefCount} + * {CalBdd,CalBddNode} X {Get} X {BddIndex} + * {CalBdd} X {Is} X {RefCountZero, OutPos, BddOne, BddZero, BddNull, BddConst} + * {CalBddManager} X {Get} X {BddZero, BddOne, BddNull} + * {CalBddNode} X {Get, Put} X {ThenBddId, ElseBddId, ThenBddNode, ElseBddNode, + * ThenBdd, ElseBdd, NextBddNode} + * {CalBddNode} X {Get, Put, Icr, Dcr, Add} X {RefCount} + * {CalBddNode} X {Is} X {RefCountZero, OutPos} + * {CalBddEqual, CalBddNodeEqual} + * + * {CalRequest} X {Get, Put} X {ThenRequestId, ElseRequestId, ThenRequestNode, + * ElseRequestNode, ThenRequest, ElseRequest, RequestId, RequestNode, + * F, G, Next} + * {CalRequest} X {Is} X {Null} + * {CalRequestNode} X {Get, Put} X {ThenRequestId, ElseRequestId, + * ThenRequestNode, ElseRequestNode, ThenRequest, ElseRequest, F, G, Next} + */ + +#define CAL_BDD_POINTER(f) ((CalBddNode_t *)(((CalAddress_t)f) & ~0xf)) +#define CAL_TAG0(pointer) ((int)((CalAddress_t)(pointer) & 0x1)) +#define CalBddIsComplement(calBdd) CAL_TAG0((calBdd).bddNode) +#define CalBddUpdatePhase(calBdd, complement) \ + ((calBdd).bddNode = \ + (CalBddNode_t *)((CalAddress_t)((calBdd).bddNode) ^ complement)) + +#define CalBddZero(bddManager) ((bddManager)->bddZero) +#define CalBddOne(bddManager) ((bddManager)->bddOne) +#define CalBddNull(bddManager) ((bddManager)->bddNull) +#define CalBddIsBddConst(calBdd) ((calBdd).bddId == 0) +/* We are cheating here. Ideally we should compare both the id as well as the bdd node */ +#define CalBddNodeIsBddNodeConst(bddNode) (((CalAddress_t)(bddNode)&~01) == ((CalAddress_t) bddManager->bddOne.bddNode & ~01)) +#define CalBddIsEqual(calBdd1, calBdd2)\ + (((calBdd1).bddNode == (calBdd2).bddNode)) +#define CalBddIsComplementEqual(calBdd1, calBdd2) \ + (((calBdd1).bddNode == \ + (CalBddNode_t *)(((CalAddress_t)(calBdd2).bddNode) ^ 0x1))) +#define CalBddSameOrNegation(calBdd1, calBdd2) \ + (CAL_BDD_POINTER((calBdd1).bddNode) == CAL_BDD_POINTER((calBdd2).bddNode)) + +/* CAUTION: MACRO ASSUMES THAT THE INDEX CORRESPONDING TO varId IS LESS THAN OR + * EQUAL TO THE INDEX OF calBdd */ +#define CalBddGetCofactors(calBdd, varId, fx, fxbar) \ +{ \ + if(varId == (calBdd).bddId){ \ + CalBddGetThenBdd(calBdd, fx); \ + CalBddGetElseBdd(calBdd, fxbar); \ + } \ + else{ \ + fx = calBdd; \ + fxbar = calBdd; \ + } \ +} + +#define CalBddGetThenBddId(calBdd) CAL_BDD_POINTER((calBdd).bddNode)->thenBddId +#define CalBddGetElseBddId(calBdd) CAL_BDD_POINTER((calBdd).bddNode)->elseBddId +#define CalBddGetThenBddIndex(bddManager, calBdd) \ + (bddManager->idToIndex[CAL_BDD_POINTER((calBdd).bddNode)->thenBddId]) +#define CalBddGetElseBddIndex(bddManager, calBdd) \ + (bddManager->idToIndex[CAL_BDD_POINTER((calBdd).bddNode)->elseBddId]) + +#define CalBddGetThenBddNode(calBdd) \ + ((CalBddNode_t*) \ + (((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->thenBddNode) \ + & ~0xe) ^ (CAL_TAG0((calBdd).bddNode)))) + +#define CalBddGetElseBddNode(calBdd) \ + ((CalBddNode_t*) \ + (((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->elseBddNode) \ + & ~0xe) ^ (CAL_TAG0((calBdd).bddNode)))) + +#define CalBddGetThenBdd(calBdd, _thenBdd) \ +{ \ + CalBddNode_t *_bddNode, *_bddNodeTagged; \ + _bddNodeTagged = (calBdd).bddNode; \ + _bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + (_thenBdd).bddId = _bddNode->thenBddId; \ + (_thenBdd).bddNode = (CalBddNode_t*) (((CalAddress_t) (_bddNode->thenBddNode) \ + & ~0xe)^(CAL_TAG0(_bddNodeTagged))); \ +} + +#define CalBddGetElseBdd(calBdd, _elseBdd) \ +{ \ + CalBddNode_t *_bddNode, *_bddNodeTagged; \ + _bddNodeTagged = (calBdd).bddNode; \ + _bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + (_elseBdd).bddId = _bddNode->elseBddId; \ + (_elseBdd).bddNode = (CalBddNode_t*) (((CalAddress_t) (_bddNode->elseBddNode) \ + & ~0xe)^(CAL_TAG0(_bddNodeTagged)));\ +} + + +#define CalBddGetBddId(calBdd) ((calBdd).bddId) +#define CalBddGetBddIndex(bddManager, calBdd) \ + (bddManager->idToIndex[(calBdd).bddId]) +#define CalBddGetBddNode(calBdd) ((calBdd).bddNode) +#define CalBddGetBddNodeNot(calBdd) \ + ((CalBddNode_t*)(((CalAddress_t)((calBdd).bddNode))^0x1)) + +#define CalBddGetNextBddNode(calBdd) \ + ((CalBddNode_t *)(((CalAddress_t) \ + (CAL_BDD_POINTER((calBdd).bddNode)->nextBddNode)) & ~0xf)) + +#define CalBddPutThenBddId(calBdd, _thenBddId) \ + (CAL_BDD_POINTER((calBdd).bddNode)->thenBddId = _thenBddId) +#define CalBddPutElseBddId(calBdd, _elseBddId) \ + (CAL_BDD_POINTER((calBdd).bddNode)->elseBddId = _elseBddId) + +#define CalBddPutThenBddNode(calBdd, _thenBddNode) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _bddNode->thenBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->thenBddNode) & 0xe)| \ + (((CalAddress_t) _thenBddNode) & ~0xe)); \ +} + +#define CalBddPutElseBddNode(calBdd, _elseBddNode) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _bddNode->elseBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->elseBddNode) & 0xe)| \ + (((CalAddress_t) _elseBddNode) & ~0xe)); \ +} + +#define CalBddPutThenBdd(calBdd, thenBdd) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _bddNode->thenBddId = (thenBdd).bddId; \ + _bddNode->thenBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->thenBddNode) & 0xe)| \ + (((CalAddress_t)(thenBdd).bddNode) & ~0xe)); \ +} + +#define CalBddPutElseBdd(calBdd, elseBdd) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _bddNode->elseBddId = (elseBdd).bddId; \ + _bddNode->elseBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->elseBddNode) & 0xe)| \ + (((CalAddress_t)(elseBdd).bddNode) & ~0xe)); \ +} + +#define CalBddPutBddId(calBdd, _bddId) ((calBdd).bddId = _bddId) +#define CalBddPutBddNode(calBdd, _bddNode) ((calBdd).bddNode = _bddNode) +#define CalBddPutNextBddNode(calBdd, _nextBddNode) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _bddNode->nextBddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->nextBddNode) & 0xf)| \ + (((CalAddress_t) _nextBddNode) & ~0xf)); \ +} + +#define CalBddGetRefCount(calBdd, refCount) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + refCount = ((CalAddress_t)(_bddNode->thenBddNode) & 0x2); \ + refCount <<= 3; \ + refCount |= ((CalAddress_t)(_bddNode->elseBddNode) & 0xe); \ + refCount <<= 3; \ + refCount |= ((CalAddress_t)(_bddNode->nextBddNode) & 0xf); \ +} + +#define CalBddPutRefCount(calBdd, count) \ +{ \ + Cal_BddRefCount_t _nextTag, _thenTag, _elseTag; \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + _nextTag = (count & 0xf); \ + _thenTag = ((count >> 6) & 0x2); \ + _elseTag = ((count >> 3) & 0xe); \ + _bddNode->nextBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->nextBddNode)) & ~0xf) | _nextTag); \ + _bddNode->thenBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->thenBddNode)) & ~0x2) | _thenTag); \ + _bddNode->elseBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->elseBddNode)) & ~0xe) | _elseTag); \ +} + +#define CalBddIcrRefCount(calBdd) \ +{ CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) != 0xf){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) + 1); \ + } \ + else{ \ + if(((CalAddress_t)(_bddNode->elseBddNode) & 0xe) != 0xe){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) & ~0xf); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) + 0x2); \ + } \ + else{ \ + if(((CalAddress_t)(_bddNode->thenBddNode) & 0x2) == 0){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) & ~0xf); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) & ~0xe); \ + _bddNode->thenBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->thenBddNode) | 0x2); \ + } \ + } \ + } \ +} + +#define CalBddDcrRefCount(calBdd) \ +{ CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER((calBdd).bddNode); \ + if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) == 0x0){ \ + if(((CalAddress_t)(_bddNode->elseBddNode) & 0xe) == 0x0){ \ + if(((CalAddress_t)(_bddNode->thenBddNode) & 0x2) == 0x0){ \ + CalBddWarningMessage("Trying to decrement reference count below zero"); \ + } \ + else{ \ + _bddNode->thenBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->thenBddNode) & ~0x2); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) | 0xe); \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) | 0xf); \ + } \ + } \ + else{ \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) - 0x2); \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) | 0xf); \ + } \ + } \ + else if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) != 0xf \ + || ((CalAddress_t)(_bddNode->elseBddNode) & 0xe) != 0xe \ + || ((CalAddress_t)(_bddNode->thenBddNode) & 0x2) != 0x2){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) - 1); \ + } \ +} + +#define CalBddAddRefCount(calBdd, num) \ +{ \ + Cal_BddRefCount_t _count; \ + CalBddGetRefCount(calBdd, _count); \ + if(_count < CAL_MAX_REF_COUNT){ \ + _count += num; \ + if(_count > CAL_MAX_REF_COUNT){ \ + _count = CAL_MAX_REF_COUNT; \ + } \ + CalBddPutRefCount(calBdd, _count); \ + } \ +} + +#define CalBddIsRefCountZero(calBdd) \ + (((((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->thenBddNode)) & 0x2) \ + || (((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->elseBddNode)) & 0xe)\ + || (((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->nextBddNode)) & 0xf))\ + ? 0 : 1) + +#define CalBddIsRefCountMax(calBdd) \ + ((((((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->thenBddNode)) & 0x2) == 0x2) \ + && ((((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->elseBddNode)) & 0xe) == 0xe)\ + && ((((CalAddress_t)(CAL_BDD_POINTER((calBdd).bddNode)->nextBddNode)) & 0xf) == 0xf))\ + ? 1 : 0) + +#define CalBddFree(calBdd) CalBddDcrRefCount(calBdd) + +#define CalBddIsOutPos(calBdd) (!(((CalAddress_t)(calBdd).bddNode) & 0x1)) + +#define CalBddIsBddOne(manager, calBdd) CalBddIsEqual(calBdd, (manager)->bddOne) +#define CalBddIsBddZero(manager, calBdd) CalBddIsEqual(calBdd, (manager)->bddZero) +#define CalBddIsBddNull(manager, calBdd) CalBddIsEqual(calBdd,(manager)->bddNull) +#define CalBddManagerGetBddOne(manager) ((manager)->bddOne) +#define CalBddManagerGetBddZero(manager) ((manager)->bddZero) +#define CalBddManagerGetBddNull(manager) (manager)->bddNull + + + +#define CalBddGetMinId2(bddManager, calBdd1, calBdd2, topId) \ +{ \ + Cal_BddId_t _id1, _id2; \ + Cal_BddIndex_t _index1, _index2; \ + _id1 = CalBddGetBddId((calBdd1)); \ + _id2 = CalBddGetBddId((calBdd2)); \ + _index1 = (bddManager)->idToIndex[_id1]; \ + _index2 = (bddManager)->idToIndex[_id2]; \ + if (_index1 < _index2) topId = _id1; \ + else topId = _id2; \ +} + +#define CalBddGetMinId3(bddManager, calBdd1, calBdd2, calBdd3, topId) \ +{ \ + Cal_BddId_t _id1, _id2, _id3; \ + Cal_BddIndex_t _index1, _index2, _index3; \ + _id1 = CalBddGetBddId((calBdd1)); \ + _id2 = CalBddGetBddId((calBdd2)); \ + _id3 = CalBddGetBddId((calBdd3)); \ + _index1 = (bddManager)->idToIndex[_id1]; \ + _index2 = (bddManager)->idToIndex[_id2]; \ + _index3 = (bddManager)->idToIndex[_id3]; \ + if(_index1 <= _index2){ \ + if(_index1 <= _index3){ \ + topId = _id1; \ + } \ + else{ \ + topId = _id3; \ + } \ + } \ + else{ \ + if(_index2 <= _index3){ \ + topId = _id2; \ + } \ + else{ \ + topId = _id3; \ + } \ + } \ +} + +#define CalBddGetMinIndex2(bddManager, calBdd1, calBdd2, topIndex) \ +{ \ + Cal_BddIndex_t _index1, _index2; \ + _index1 = bddManager->idToIndex[CalBddGetBddId(calBdd1)]; \ + _index2 = bddManager->idToIndex[CalBddGetBddId(calBdd2)]; \ + if (_index1 < _index2) topIndex = _index1; \ + else topIndex = _index2; \ +} + +#define CalBddGetMinIndex3(bddManager, calBdd1, calBdd2, calBdd3, topIndex) \ +{ \ + Cal_BddId_t _id1, _id2, _id3; \ + Cal_BddIndex_t _index1, _index2, _index3; \ + _id1 = CalBddGetBddId((calBdd1)); \ + _id2 = CalBddGetBddId((calBdd2)); \ + _id3 = CalBddGetBddId((calBdd3)); \ + _index1 = (bddManager)->idToIndex[_id1]; \ + _index2 = (bddManager)->idToIndex[_id2]; \ + _index3 = (bddManager)->idToIndex[_id3]; \ + if(_index1 <= _index2){ \ + if(_index1 <= _index3){ \ + topIndex = _index1; \ + } \ + else{ \ + topIndex = _index3; \ + } \ + } \ + else{ \ + if(_index2 <= _index3){ \ + topIndex = _index2; \ + } \ + else{ \ + topIndex = _index3; \ + } \ + } \ +} + +#define CalBddGetMinIdAndMinIndex(bddManager, calBdd1, calBdd2, topId, topIndex)\ +{ \ + Cal_BddId_t _id1, _id2; \ + Cal_BddIndex_t _index1, _index2; \ + _id1 = CalBddGetBddId((calBdd1)); \ + _id2 = CalBddGetBddId((calBdd2)); \ + _index1 = (bddManager)->idToIndex[_id1]; \ + _index2 = (bddManager)->idToIndex[_id2]; \ + if (_index1 < _index2){ \ + topId = _id1; \ + topIndex = _index1; \ + } \ + else { \ + topId = _id2; \ + topIndex = _index2; \ + } \ +} + +#define CalBddNot(calBdd1, calBdd2) \ +{ \ + (calBdd2).bddId = (calBdd1).bddId; \ + (calBdd2).bddNode = (CalBddNode_t *)((CalAddress_t)(calBdd1).bddNode ^ 0x1); \ +} + +#define CAL_BDD_OUT_OF_ORDER(f, g) \ + ((CalAddress_t)CalBddGetBddNode(f) > (CalAddress_t)CalBddGetBddNode(g)) + +#define CAL_BDD_SWAP(f, g) \ +{ \ + Cal_Bdd_t _tmp; \ + _tmp = f; \ + f = g; \ + g = _tmp; \ +} + + +/* BddNode related Macros */ +#define CalBddNodeGetThenBddId(_bddNode) ((_bddNode)->thenBddId) +#define CalBddNodeGetElseBddId(_bddNode) ((_bddNode)->elseBddId) +#define CalBddNodeGetThenBddIndex(bddManager, _bddNode) \ + bddManager->idToIndex[((_bddNode)->thenBddId)] +#define CalBddNodeGetElseBddIndex(bddManager, _bddNode) \ + bddManager->idToIndex[((_bddNode)->elseBddId)] +#define CalBddNodeGetThenBddNode(_bddNode) \ + ((CalBddNode_t *)((CalAddress_t)((_bddNode)->thenBddNode) & ~0xe)) +#define CalBddNodeGetElseBddNode(_bddNode) \ + ((CalBddNode_t *)((CalAddress_t)((_bddNode)->elseBddNode) & ~0xe)) + +#define CalBddNodeGetThenBdd(_bddNode, _thenBdd) \ +{ \ + (_thenBdd).bddId = (_bddNode)->thenBddId; \ + (_thenBdd).bddNode = \ + (CalBddNode_t*) (((CalAddress_t) ((_bddNode)->thenBddNode) & ~0xe)); \ +} + +#define CalBddNodeGetElseBdd(_bddNode, _elseBdd) \ +{ \ + (_elseBdd).bddId = (_bddNode)->elseBddId; \ + (_elseBdd).bddNode = \ + (CalBddNode_t*) (((CalAddress_t) ((_bddNode)->elseBddNode) & ~0xe)); \ +} + +#define CalBddNodeGetNextBddNode(_bddNode) \ + ((CalBddNode_t *)(((CalAddress_t) ((_bddNode)->nextBddNode)) & ~0xf)) + +#define CalBddNodePutThenBddId(_bddNode, _thenBddId) \ + ((_bddNode)->thenBddId = _thenBddId) + +#define CalBddNodePutElseBddId(_bddNode, _elseBddId) \ + ((_bddNode)->elseBddId = _elseBddId) + +#define CalBddNodePutThenBddNode(_bddNode, _thenBddNode) \ +{ \ + (_bddNode)->thenBddNode = (CalBddNode_t*) \ + (((CalAddress_t)((_bddNode)->thenBddNode) & 0xe)| \ + (((CalAddress_t) _thenBddNode) & ~0xe)); \ +} + +#define CalBddNodePutElseBddNode(_bddNode, _elseBddNode) \ +{ \ + (_bddNode)->elseBddNode = (CalBddNode_t*) \ + (((CalAddress_t)((_bddNode)->elseBddNode) & 0xe)| \ + (((CalAddress_t) _elseBddNode) & ~0xe)); \ +} + +#define CalBddNodePutThenBdd(_bddNode, _thenBdd) \ +{ \ + (_bddNode)->thenBddId = (_thenBdd).bddId; \ + (_bddNode)->thenBddNode = (CalBddNode_t*) \ + (((CalAddress_t)((_bddNode)->thenBddNode) & 0xe)| \ + (((CalAddress_t)(_thenBdd).bddNode) & ~0xe)); \ +} + +#define CalBddNodePutElseBdd(_bddNode, _elseBdd) \ +{ \ + (_bddNode)->elseBddId = (_elseBdd).bddId; \ + (_bddNode)->elseBddNode = (CalBddNode_t*) \ + (((CalAddress_t)((_bddNode)->elseBddNode) & 0xe)| \ + (((CalAddress_t) (_elseBdd).bddNode) & ~0xe)); \ +} + +#define CalBddNodePutNextBddNode(_bddNode, _nextBddNode) \ +{ \ + (_bddNode)->nextBddNode = (CalBddNode_t*) \ + (((CalAddress_t)((_bddNode)->nextBddNode) & 0xf)| \ + (((CalAddress_t) _nextBddNode) & ~0xf)); \ +} + + +#define CalBddNodeGetRefCount(_bddNode, refCount) \ +{ \ + refCount = ((CalAddress_t)(_bddNode->thenBddNode) & 0x2); \ + refCount <<= 3; \ + refCount |= ((CalAddress_t)(_bddNode->elseBddNode) & 0xe); \ + refCount <<= 3; \ + refCount |= ((CalAddress_t)(_bddNode->nextBddNode) & 0xf); \ +} + +#define CalBddNodePutRefCount(_bddNode, count) \ +{ \ + Cal_BddRefCount_t _nextTag, _thenTag, _elseTag; \ + _nextTag = (count & 0xf); \ + _thenTag = ((count >> 6) & 0x2); \ + _elseTag = ((count >> 3) & 0xe); \ + _bddNode->nextBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->nextBddNode)) & ~0xf) | _nextTag); \ + _bddNode->thenBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->thenBddNode)) & ~0x2) | _thenTag); \ + _bddNode->elseBddNode = (CalBddNode_t*) \ + ((((CalAddress_t)(_bddNode->elseBddNode)) & ~0xe) | _elseTag); \ +} + +#define CalBddNodeDcrRefCount(_bddNode) \ +{ \ + if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) == 0x0){ \ + if(((CalAddress_t)(_bddNode->elseBddNode) & 0xe) == 0x0){ \ + if(((CalAddress_t)(_bddNode->thenBddNode) & 0x2) == 0x0){ \ + CalBddWarningMessage("Trying to decrement reference count below zero"); \ + } \ + else{ \ + _bddNode->thenBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->thenBddNode) & ~0x2); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) | 0xe); \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) | 0xf); \ + } \ + } \ + else{ \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) - 0x2); \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) | 0xf); \ + } \ + } \ + else if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) != 0xf \ + || ((CalAddress_t)(_bddNode->elseBddNode) & 0xe) != 0xe \ + || ((CalAddress_t)(_bddNode->thenBddNode) & 0x2) != 0x2){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) - 1); \ + } \ +} + +#define CalBddNodeIcrRefCount(_bddNode) \ +{ \ + if(((CalAddress_t)(_bddNode->nextBddNode) & 0xf) != 0xf){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) + 1); \ + } \ + else{ \ + if(((CalAddress_t)(_bddNode->elseBddNode) & 0xe) != 0xe){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) & ~0xf); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) + 0x2); \ + } \ + else{ \ + if(((CalAddress_t)(_bddNode->thenBddNode) & 0x2) == 0){ \ + _bddNode->nextBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->nextBddNode) & ~0xf); \ + _bddNode->elseBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->elseBddNode) & ~0xe); \ + _bddNode->thenBddNode = \ + (CalBddNode_t *)((CalAddress_t)(_bddNode->thenBddNode) | 0x2); \ + } \ + } \ + } \ +} + +#define CalBddNodeAddRefCount(__bddNode, num) \ +{ \ + Cal_BddRefCount_t _count; \ + CalBddNodeGetRefCount(__bddNode, _count); \ + _count += num; \ + if(_count > CAL_MAX_REF_COUNT){ \ + _count = CAL_MAX_REF_COUNT; \ + } \ + CalBddNodePutRefCount(__bddNode, _count); \ +} + +#define CalBddNodeIsRefCountZero(_bddNode) \ + (((((CalAddress_t) ((_bddNode)->thenBddNode)) & 0x2) || \ + (((CalAddress_t) ((_bddNode)->elseBddNode)) & 0xe) || \ + (((CalAddress_t) ((_bddNode)->nextBddNode)) & 0xf)) \ + ? 0 : 1) + +#define CalBddNodeIsRefCountMax(_bddNode) \ + ((((((CalAddress_t) ((_bddNode)->thenBddNode)) & 0x2) == 0x2)&& \ + ((((CalAddress_t) ((_bddNode)->elseBddNode)) & 0xe) == 0xe)&& \ + ((((CalAddress_t) ((_bddNode)->nextBddNode)) & 0xf) == 0xf)) \ + ? 1 : 0) + +#define CalBddNodeIsOutPos(bddNode) (!(((CalAddress_t)bddNode) & 0x1)) +#define CalBddNodeRegular(bddNode) ((CalBddNode_t *)(((unsigned long)(bddNode)) & ~01)) +#define CalBddRegular(calBdd1, calBdd2) \ +{ \ + calBdd2.bddId = calBdd1.bddId; \ + calBdd2.bddNode = CalBddNodeRegular(calBdd1.bddNode); \ +} + +#define CalBddNodeEqual(calBddNode1, calBddNode2)\ + ((CalAddress_t)calBddNode1 == (CalAddress_t)calBddNode2) + +#define CalBddNodeNot(bddNode) ((CalBddNode_t*)(((CalAddress_t)(bddNode))^0x1)) + +/* Mark / Unmark */ +#define CalBddIsMarked(calBdd) \ + CalBddNodeIsMarked(CAL_BDD_POINTER((calBdd).bddNode)) + +#define CalBddMark(calBdd) \ + CalBddNodeMark(CAL_BDD_POINTER((calBdd).bddNode)) + +#define CalBddUnmark(calBdd) \ + CalBddNodeUnmark(CAL_BDD_POINTER((calBdd).bddNode)) + +#define CalBddGetMark(calBdd) \ + CalBddNodeGetMark(CAL_BDD_POINTER((calBdd).bddNode)) + +#define CalBddPutMark(calBdd, mark) \ + CalBddNodePutMark(CAL_BDD_POINTER((calBdd).bddNode), (mark)) + +#define CalBddNodeIsMarked(bddNode) \ + ((((CalAddress_t)((bddNode)->thenBddNode)) & 0x4) >> 2) + +#define CalBddNodeMark(bddNode) \ + ((bddNode)->thenBddNode = \ + (CalBddNode_t *)(((CalAddress_t)(bddNode)->thenBddNode) | 0x4)) + +#define CalBddNodeUnmark(bddNode) \ + ((bddNode)->thenBddNode = \ + (CalBddNode_t *)(((CalAddress_t)(bddNode)->thenBddNode) & ~0x4)) + +#define CalBddNodeGetMark(bddNode) \ + ((((CalAddress_t)((bddNode)->thenBddNode)) & 0xc) >> 2) + +#define CalBddNodePutMark(bddNode, mark) \ + ((bddNode)->thenBddNode = (CalBddNode_t *) \ + ((((CalAddress_t)(bddNode)->thenBddNode) & ~0xc) | ((mark) << 2))) + + +/* THIS SHOULD BE CHANGED TO MACROS WITH ARGUMENTS */ +#define CalRequestGetThenRequestId CalBddGetThenBddId +#define CalRequestGetElseRequestId CalBddGetElseBddId +#define CalRequestGetThenRequestNode CalBddGetThenBddNode +#define CalRequestGetElseRequestNode CalBddGetElseBddNode +#define CalRequestGetThenRequest CalBddGetThenBdd +#define CalRequestGetElseRequest CalBddGetElseBdd +#define CalRequestGetRequestId CalBddGetBddId +#define CalRequestGetRequestNode CalBddGetBddNode +#define CalRequestGetF CalBddGetThenBdd +#define CalRequestGetG CalBddGetElseBdd +#define CalRequestGetNextNode CalBddGetNextBddNode + +#define CalRequestPutThenRequestId CalBddPutThenBddId +#define CalRequestPutElseRequestId CalBddPutElseBddId +#define CalRequestPutThenRequestNode CalBddPutThenBddNode +#define CalRequestPutElseRequestNode CalBddPutElseBddNode +#define CalRequestPutThenRequest CalBddPutThenBdd +#define CalRequestPutElseRequest CalBddPutElseBdd +#define CalRequestPutRequestId CalBddPutBddId +#define CalRequestPutRequestNode CalBddPutBddNode +#define CalRequestPutF CalBddPutThenBdd +#define CalRequestPutG CalBddPutElseBdd +#define CalRequestPutNextNode CalBddPutNextBddNode + +/* Macros related to the CalRequestNode */ + +#define CalRequestNodeGetThenRequestId CalBddNodeGetThenBddId +#define CalRequestNodeGetElseRequestId CalBddNodeGetElseBddId +#define CalRequestNodeGetThenRequestNode CalBddNodeGetThenBddNode +#define CalRequestNodeGetElseRequestNode CalBddNodeGetElseBddNode +#define CalRequestNodeGetThenRequest CalBddNodeGetThenBdd +#define CalRequestNodeGetElseRequest CalBddNodeGetElseBdd +#define CalRequestNodeGetF CalBddNodeGetThenBdd +#define CalRequestNodeGetG CalBddNodeGetElseBdd +#define CalRequestNodeGetNextRequestNode CalBddNodeGetNextBddNode + +#define CalRequestNodePutThenRequestId CalBddNodePutThenBddId +#define CalRequestNodePutElseRequestId CalBddNodePutElseBddId +#define CalRequestNodePutThenRequestNode CalBddNodePutThenBddNode +#define CalRequestNodePutElseRequestNode CalBddNodePutElseBddNode +#define CalRequestNodePutThenRequest CalBddNodePutThenBdd +#define CalRequestNodePutElseRequest CalBddNodePutElseBdd +#define CalRequestNodePutF CalBddNodePutThenBdd +#define CalRequestNodePutG CalBddNodePutElseBdd +#define CalRequestNodePutNextRequestNode CalBddNodePutNextBddNode +#define CalRequestIsNull(calRequest) \ + ((CalRequestGetRequestId(calRequest) == 0) \ + && (CalRequestGetRequestNode(calRequest) == 0)) + +#define CalRequestIsMarked CalBddIsMarked +#define CalRequestMark CalBddMark +#define CalRequestUnmark CalBddUnmark +#define CalRequestGetMark CalBddGetMark +#define CalRequestPutMark CalBddPutMark +#define CalRequestNodeIsMarked CalBddNodeIsMarked +#define CalRequestNodeMark CalBddNodeMark +#define CalRequestNodeUnmark CalBddNodeUnmark +#define CalRequestNodeGetMark CalBddNodeGetMark +#define CalRequestNodePutMark CalBddNodePutMark + +#define CalRequestNodeGetCofactors(bddManager,requestNode,fx,fxbar,gx,gxbar) \ +{ \ + Cal_Bdd_t __f, __g; \ + Cal_BddIndex_t __index1, __index2; \ + CalRequestNodeGetF(requestNode, __f); \ + CalRequestNodeGetG(requestNode, __g); \ + __index1 = (bddManager)->idToIndex[CalBddGetBddId(__f)]; \ + __index2 = (bddManager)->idToIndex[CalBddGetBddId(__g)]; \ + if(__index1 == __index2){ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + } \ + else if(__index1 < __index2){ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + gx = gxbar = __g; \ + } \ + else{ \ + fx = fxbar = __f; \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + } \ +} + +#define CalBddPairGetCofactors(bddManager,f,g,fx,fxbar,gx,gxbar) \ +{ \ + Cal_BddIndex_t __index1, __index2; \ + __index1 = (bddManager)->idToIndex[CalBddGetBddId(f)]; \ + __index2 = (bddManager)->idToIndex[CalBddGetBddId(g)]; \ + if(__index1 == __index2){ \ + CalBddGetThenBdd(f, fx); \ + CalBddGetElseBdd(f, fxbar); \ + CalBddGetThenBdd(g, gx); \ + CalBddGetElseBdd(g, gxbar); \ + } \ + else if(__index1 < __index2){ \ + CalBddGetThenBdd(f, fx); \ + CalBddGetElseBdd(f, fxbar); \ + gx = gxbar = g; \ + } \ + else{ \ + fx = fxbar = f; \ + CalBddGetThenBdd(g, gx); \ + CalBddGetElseBdd(g, gxbar); \ + } \ +} + +#define CalBddIsForwarded(bdd) \ + (CAL_BDD_POINTER(CalBddGetElseBddNode(bdd)) == FORWARD_FLAG) + +#define CalBddNodeIsForwarded(bddNode) \ + (((CalAddress_t)(CAL_BDD_POINTER(CalBddNodeGetElseBddNode(bddNode)))) == FORWARD_FLAG) + +#define CalBddForward(bdd) \ +{ \ + CalBddNode_t *_bddNode, *_bddNodeTagged; \ + _bddNodeTagged = CalBddGetBddNode(bdd); \ + _bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + (bdd).bddId = _bddNode->thenBddId; \ + (bdd).bddNode = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(_bddNodeTagged))); \ +} + +#define CalBddNodeForward(_bddNodeTagged) \ +{ \ + CalBddNode_t *_bddNode; \ + _bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + _bddNodeTagged = (CalBddNode_t*) \ + (((CalAddress_t)(_bddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(_bddNodeTagged))); \ +} + +#define CalBddNodeIsForwardedTo(_bddNodeTagged) \ +{ \ + CalBddNode_t *__bddNode;\ + __bddNode = CAL_BDD_POINTER(_bddNodeTagged); \ + if(CalBddNodeGetElseBddNode(__bddNode) == FORWARD_FLAG){ \ + _bddNodeTagged = (CalBddNode_t*) \ + (((CalAddress_t)(__bddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(_bddNodeTagged))); \ + } \ +} + +#define CalRequestIsForwardedTo(request) \ +{ \ + CalBddNode_t *__bddNode, *__bddNodeTagged; \ + __bddNodeTagged = (request).bddNode; \ + __bddNode = CAL_BDD_POINTER(__bddNodeTagged); \ + if(CalRequestNodeGetElseRequestNode(__bddNode) == FORWARD_FLAG){ \ + (request).bddId = __bddNode->thenBddId; \ + (request).bddNode = (CalBddNode_t*) \ + (((CalAddress_t)(__bddNode->thenBddNode) & ~0xe) \ + ^(CAL_TAG0(__bddNodeTagged))); \ + } \ +} + +#define CalBddIsForwardedTo CalRequestIsForwardedTo + +#define CalBddNormalize(fBdd, gBdd) \ +{ \ + Cal_Bdd_t _tmpBdd; \ + if((unsigned long)CAL_BDD_POINTER(CalBddGetBddNode(gBdd)) < \ + (unsigned long)CAL_BDD_POINTER(CalBddGetBddNode(fBdd))){ \ + _tmpBdd = fBdd; \ + fBdd = gBdd; \ + gBdd = _tmpBdd; \ + } \ +} + +/* Depth aliased as RefCount */ +#define CalBddGetDepth CalBddGetRefCount +#define CalBddPutDepth CalBddPutRefCount +#define CalRequestNodeGetDepth CalBddNodeGetRefCount +#define CalRequestNodeGetRefCount CalBddNodeGetRefCount +#define CalRequestNodeAddRefCount CalBddNodeAddRefCount +#define CalRequestAddRefCount CalBddAddRefCount +#define CalRequestNodePutDepth CalBddNodePutRefCount + +#define CalITERequestNodeGetCofactors(bddManager, requestNode, fx, fxbar, gx, gxbar, hx, hxbar) \ +{ \ + Cal_Bdd_t __f, __g, __h; \ + Cal_BddIndex_t __index1, __index2, __index3; \ + CalBddNode_t *__ptrIndirect; \ + CalRequestNodeGetThenRequest(requestNode, __f); \ + __ptrIndirect = CalRequestNodeGetElseRequestNode(requestNode); \ + CalRequestNodeGetThenRequest(__ptrIndirect, __g); \ + CalRequestNodeGetElseRequest(__ptrIndirect, __h); \ + __index1 = (bddManager)->idToIndex[CalBddGetBddId(__f)]; \ + __index2 = (bddManager)->idToIndex[CalBddGetBddId(__g)]; \ + __index3 = (bddManager)->idToIndex[CalBddGetBddId(__h)]; \ + if(__index1 == __index2){ \ + if(__index3 == __index1){ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else if(__index3 < __index1){ \ + fx = fxbar = __f; \ + gx = gxbar = __g; \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else{ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + hx = hxbar = __h; \ + } \ + } \ + else if(__index1 < __index2){ \ + if(__index3 == __index1){ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + gx = gxbar = __g; \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else if(__index3 < __index1){ \ + fx = fxbar = __f; \ + gx = gxbar = __g; \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else{ \ + CalBddGetThenBdd(__f, fx); \ + CalBddGetElseBdd(__f, fxbar); \ + gx = gxbar = __g; \ + hx = hxbar = __h; \ + } \ + } \ + else{ \ + if(__index3 == __index2){ \ + fx = fxbar = __f; \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else if(__index3 < __index2){ \ + fx = fxbar = __f; \ + gx = gxbar = __g; \ + CalBddGetThenBdd(__h, hx); \ + CalBddGetElseBdd(__h, hxbar); \ + } \ + else{ \ + fx = fxbar = __f; \ + CalBddGetThenBdd(__g, gx); \ + CalBddGetElseBdd(__g, gxbar); \ + hx = hxbar = __h; \ + } \ + } \ +} + + +#define CalCacheTableOneInsert(bddManager, f, result, opCode, cacheLevel) CalCacheTableTwoInsert(bddManager, f, (bddManager)->bddOne, result, opCode, cacheLevel) + +#define CalCacheTableOneLookup(bddManager, f, opCode, resultPtr) CalCacheTableTwoLookup(bddManager, f, (bddManager)->bddOne, opCode, resultPtr) + +#ifdef USE_POWER_OF_2 +#define CalDoHash2(thenBddNode, elseBddNode, table) \ + (((((CalAddress_t)thenBddNode) + ((CalAddress_t)elseBddNode)) / NODE_SIZE) & ((table)->numBins - 1)) +#else +#define CalDoHash2(thenBddNode, elseBddNode, table) \ + (((((CalAddress_t)thenBddNode) + \ + ((CalAddress_t)elseBddNode)) / NODE_SIZE)% \ + (table)->numBins) +#endif + +#if HAVE_STDARG_H +EXTERN int CalBddPreProcessing(Cal_BddManager_t *bddManager, int count, ...); +#else +EXTERN int CalBddPreProcessing(); +#endif + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Function prototypes */ +/*---------------------------------------------------------------------------*/ + +EXTERN Cal_Bdd_t CalBddIf(Cal_BddManager bddManager, Cal_Bdd_t F); +EXTERN int CalBddIsCubeStep(Cal_BddManager bddManager, Cal_Bdd_t f); +EXTERN int CalBddTypeAux(Cal_BddManager_t * bddManager, Cal_Bdd_t f); +EXTERN Cal_Bdd_t CalBddIdentity(Cal_BddManager_t *bddManager, Cal_Bdd_t calBdd); +EXTERN void CalHashTableApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** reqQueAtPipeDepth, CalOpProc_t calOpProc); +EXTERN void CalHashTableReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t * uniqueTableForId); +EXTERN void CalAssociationListFree(Cal_BddManager_t * bddManager); +EXTERN void CalVarAssociationRepackUpdate(Cal_BddManager_t * bddManager, Cal_BddId_t id); +EXTERN void CalCheckAssociationValidity(Cal_BddManager_t * bddManager); +EXTERN void CalReorderAssociationFix(Cal_BddManager_t *bddManager); +EXTERN void CalRequestNodeListCompose(Cal_BddManager_t * bddManager, CalRequestNode_t * requestNodeList, Cal_BddIndex_t composeIndex); +EXTERN void CalHashTableComposeApply(Cal_BddManager_t *bddManager, CalHashTable_t *hashTable, Cal_BddIndex_t gIndex, CalHashTable_t **reqQueForCompose, CalHashTable_t **reqQueForITE); +EXTERN void CalComposeRequestCreate(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t h, Cal_BddIndex_t composeIndex, CalHashTable_t **reqQueForCompose, CalHashTable_t **reqQueForITE, Cal_Bdd_t *resultPtr); +EXTERN void CalRequestNodeListArrayITE(Cal_BddManager_t *bddManager, CalRequestNode_t **requestNodeListArray); +EXTERN Cal_Bdd_t CalBddOpITEBF(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_Bdd_t g, Cal_Bdd_t h); +EXTERN void CalHashTableITEApply(Cal_BddManager_t *bddManager, CalHashTable_t *hashTable, CalHashTable_t **reqQueAtPipeDepth); +EXTERN Cal_Bdd_t CalBddITE(Cal_BddManager_t *bddManager, Cal_Bdd_t F, Cal_Bdd_t G, Cal_Bdd_t H); +EXTERN Cal_Bdd_t CalBddManagerCreateNewVar(Cal_BddManager_t * bddManager, Cal_BddIndex_t index); +EXTERN void CalRequestNodeListArrayOp(Cal_BddManager_t * bddManager, CalRequestNode_t ** requestNodeListArray, CalOpProc_t calOpProc); +EXTERN Cal_Bdd_t CalBddOpBF(Cal_BddManager_t * bddManager, CalOpProc_t calOpProc, Cal_Bdd_t F, Cal_Bdd_t G); +EXTERN int main(int argc, char **argv); +EXTERN Cal_Bdd_t CalBddVarSubstitute(Cal_BddManager bddManager, Cal_Bdd_t f, unsigned short opCode, CalAssociation_t *assoc); +EXTERN int CalOpBddVarSubstitute(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t * resultBddPtr); +EXTERN long CalBddFindBlock(Cal_Block block, long index); +EXTERN void CalBddBlockDelta(Cal_Block b, long delta); +EXTERN Cal_Block CalBddShiftBlock(Cal_BddManager_t *bddManager, Cal_Block b, long index); +EXTERN unsigned long CalBlockMemoryConsumption(Cal_Block block); +EXTERN void CalFreeBlockRecursively(Cal_Block block); +EXTERN CalCacheTable_t * CalCacheTableTwoInit(Cal_BddManager_t *bddManager); +EXTERN int CalCacheTableTwoQuit(CalCacheTable_t *cacheTable); +EXTERN void CalCacheTableTwoInsert(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_Bdd_t g, Cal_Bdd_t result, unsigned long opCode, int cacheLevel); +EXTERN int CalCacheTableTwoLookup(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_Bdd_t g, unsigned long opCode, Cal_Bdd_t *resultBddPtr); +EXTERN void CalCacheTableTwoFlush(CalCacheTable_t *cacheTable); +EXTERN int CalCacheTableTwoFlushAll(CalCacheTable_t *cacheTable); +EXTERN void CalCacheTableTwoGCFlush(CalCacheTable_t *cacheTable); +EXTERN void CalCacheTableTwoRepackUpdate(CalCacheTable_t *cacheTable); +EXTERN void CalCheckCacheTableValidity(Cal_BddManager bddManager); +EXTERN void CalCacheTableTwoFixResultPointers(Cal_BddManager_t *bddManager); +EXTERN void CalCacheTablePrint(Cal_BddManager_t *bddManager); +EXTERN void CalBddManagerGetCacheTableData(Cal_BddManager_t *bddManager, unsigned long *cacheSize, unsigned long *cacheEntries, unsigned long *cacheInsertions, unsigned long *cacheLookups, unsigned long *cacheHits, unsigned long *cacheCollisions); +EXTERN void CalCacheTableRehash(Cal_BddManager_t *bddManager); +EXTERN void CalCacheTableTwoFlushAssociationId(Cal_BddManager_t *bddManager, int associationId); +EXTERN unsigned long CalCacheTableMemoryConsumption(CalCacheTable_t *cacheTable); +EXTERN void CalBddManagerGCCheck(Cal_BddManager_t * bddManager); +EXTERN int CalHashTableGC(Cal_BddManager_t *bddManager, CalHashTable_t *hashTable); +EXTERN void CalRepackNodesAfterGC(Cal_BddManager_t *bddManager); +EXTERN CalHashTable_t * CalHashTableInit(Cal_BddManager_t *bddManager, Cal_BddId_t bddId); +EXTERN int CalHashTableQuit(Cal_BddManager_t *bddManager, CalHashTable_t * hashTable); +EXTERN void CalHashTableAddDirect(CalHashTable_t * hashTable, CalBddNode_t * bddNode); +EXTERN int CalHashTableFindOrAdd(CalHashTable_t * hashTable, Cal_Bdd_t thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * bddPtr); +EXTERN int CalHashTableAddDirectAux(CalHashTable_t * hashTable, Cal_Bdd_t thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * bddPtr); +EXTERN void CalHashTableCleanUp(CalHashTable_t * hashTable); +EXTERN int CalHashTableLookup(CalHashTable_t * hashTable, Cal_Bdd_t thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * bddPtr); +EXTERN void CalHashTableDelete(CalHashTable_t * hashTable, CalBddNode_t * bddNode); +EXTERN int CalUniqueTableForIdLookup(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, Cal_Bdd_t thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * bddPtr); +EXTERN int CalUniqueTableForIdFindOrAdd(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, Cal_Bdd_t thenBdd, Cal_Bdd_t elseBdd, Cal_Bdd_t * bddPtr); +EXTERN void CalHashTableRehash(CalHashTable_t *hashTable, int grow); +EXTERN void CalUniqueTableForIdRehashNode(CalHashTable_t *hashTable, CalBddNode_t *bddNode, CalBddNode_t *thenBddNode, CalBddNode_t *elseBddNode); +EXTERN unsigned long CalBddUniqueTableNumLockedNodes(Cal_BddManager_t *bddManager, CalHashTable_t *uniqueTableForId); +EXTERN void CalPackNodes(Cal_BddManager_t *bddManager); +EXTERN void CalBddPackNodesForSingleId(Cal_BddManager_t *bddManager, Cal_BddId_t id); +EXTERN void CalBddPackNodesAfterReorderForSingleId(Cal_BddManager_t *bddManager, int fixForwardedNodesFlag, int bestIndex, int bottomIndex); +EXTERN void CalBddPackNodesForMultipleIds(Cal_BddManager_t *bddManager, Cal_BddId_t beginId, int numLevels); +EXTERN CalHashTable_t * CalHashTableOneInit(Cal_BddManager_t * bddManager, int itemSize); +EXTERN void CalHashTableOneQuit(CalHashTable_t * hashTable); +EXTERN void CalHashTableOneInsert(CalHashTable_t * hashTable, Cal_Bdd_t keyBdd, char * valuePtr); +EXTERN int CalHashTableOneLookup(CalHashTable_t * hashTable, Cal_Bdd_t keyBdd, char ** valuePtrPtr); +EXTERN int CalHashTableThreeFindOrAdd(CalHashTable_t * hashTable, Cal_Bdd_t f, Cal_Bdd_t g, Cal_Bdd_t h, Cal_Bdd_t * bddPtr); +EXTERN void CalSetInteract(Cal_BddManager_t *bddManager, int x, int y); +EXTERN int CalTestInteract(Cal_BddManager_t *bddManager, int x, int y); +EXTERN int CalInitInteract(Cal_BddManager_t *bddManager); +EXTERN CalPageManager_t * CalPageManagerInit(int numPagesPerSegment); +EXTERN int CalPageManagerQuit(CalPageManager_t * pageManager); +EXTERN void CalPageManagerPrint(CalPageManager_t * pageManager); +EXTERN CalNodeManager_t * CalNodeManagerInit(CalPageManager_t * pageManager); +EXTERN int CalNodeManagerQuit(CalNodeManager_t * nodeManager); +EXTERN void CalNodeManagerPrint(CalNodeManager_t * nodeManager); +EXTERN CalAddress_t * CalPageManagerAllocPage(CalPageManager_t * pageManager); +EXTERN void CalPageManagerFreePage(CalPageManager_t * pageManager, CalAddress_t * page); +EXTERN int CalIncreasingOrderCompare(const void *a, const void *b); +EXTERN int CalDecreasingOrderCompare(const void *a, const void *b); +EXTERN void CalBddReorderFixProvisionalNodes(Cal_BddManager_t *bddManager); +EXTERN void CalCheckPipelineValidity(Cal_BddManager_t *bddManager); +EXTERN char * CalBddVarName(Cal_BddManager_t *bddManager, Cal_Bdd_t v, Cal_VarNamingFn_t VarNamingFn, Cal_Pointer_t env); +EXTERN void CalBddNumberSharedNodes(Cal_BddManager_t *bddManager, Cal_Bdd_t f, CalHashTable_t *hashTable, long *next); +EXTERN void CalBddMarkSharedNodes(Cal_BddManager_t *bddManager, Cal_Bdd_t f); +EXTERN int CalOpExists(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t * resultBddPtr); +EXTERN int CalOpRelProd(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, Cal_Bdd_t * resultBddPtr); +EXTERN int CalOpCofactor(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t c, Cal_Bdd_t * resultBddPtr); +EXTERN void CalBddReorderAuxBF(Cal_BddManager_t * bddManager); +EXTERN void CalBddReorderFixCofactors(Cal_BddManager bddManager, Cal_BddId_t id); +EXTERN void CalFixupAssoc(Cal_BddManager_t *bddManager, long id1, long id2, CalAssociation_t *assoc); +EXTERN void CalBddReorderReclaimForwardedNodes(Cal_BddManager bddManager, int startIndex, int endIndex); +EXTERN void CalBddReorderBlockSift(Cal_BddManager_t *bddManager, double maxSizeFactor); +EXTERN void CalBddReorderBlockWindow(Cal_BddManager bddManager, Cal_Block block, char *levels); +EXTERN void CalBddReorderAuxDF(Cal_BddManager_t *bddManager); +EXTERN void CalAlignCollisionChains(Cal_BddManager_t *bddManager); +EXTERN void CalBddReorderFixUserBddPtrs(Cal_BddManager bddManager); +EXTERN int CalCheckAllValidity(Cal_BddManager bddManager); +EXTERN int CalCheckValidityOfNodesForId(Cal_BddManager bddManager, int id); +EXTERN int CalCheckValidityOfNodesForWindow(Cal_BddManager bddManager, Cal_BddIndex_t index, int numLevels); +EXTERN int CalCheckValidityOfANode(Cal_BddManager_t *bddManager, CalBddNode_t *bddNode, int id); +EXTERN void CalCheckRefCountValidity(Cal_BddManager_t *bddManager); +EXTERN int CalCheckAssoc(Cal_BddManager_t *bddManager); +EXTERN void CalBddReorderVarSift(Cal_BddManager bddManager, double maxSizeFactor); +EXTERN void CalBddReorderVarWindow(Cal_BddManager bddManager, char *levels); +EXTERN int CalOpAnd(Cal_BddManager_t * bddManager, Cal_Bdd_t F, Cal_Bdd_t G, Cal_Bdd_t * resultBddPtr); +EXTERN int CalOpNand(Cal_BddManager_t * bddManager, Cal_Bdd_t F, Cal_Bdd_t G, Cal_Bdd_t * resultBddPtr); +EXTERN int CalOpOr(Cal_BddManager_t * bddManager, Cal_Bdd_t F, Cal_Bdd_t G, Cal_Bdd_t * resultBddPtr); +EXTERN int CalOpXor(Cal_BddManager_t * bddManager, Cal_Bdd_t F, Cal_Bdd_t G, Cal_Bdd_t * resultBddPtr); +EXTERN Cal_Bdd_t CalOpITE(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_Bdd_t g, Cal_Bdd_t h, CalHashTable_t **reqQueForITE); +EXTERN int main(int argc, char ** argv); +EXTERN void CalUniqueTablePrint(Cal_BddManager_t *bddManager); +EXTERN void CalBddFunctionPrint(Cal_BddManager_t * bddManager, Cal_Bdd_t calBdd, char * name); +EXTERN int CalBddPreProcessing(Cal_BddManager_t *bddManager, int count, ...); +EXTERN int CalBddPostProcessing(Cal_BddManager_t *bddManager); +EXTERN int CalBddArrayPreProcessing(Cal_BddManager_t *bddManager, Cal_Bdd *userBddArray); +EXTERN Cal_Bdd_t CalBddGetInternalBdd(Cal_BddManager bddManager, Cal_Bdd userBdd); +EXTERN Cal_Bdd CalBddGetExternalBdd(Cal_BddManager_t *bddManager, Cal_Bdd_t internalBdd); +EXTERN void CalBddFatalMessage(char *string); +EXTERN void CalBddWarningMessage(char *string); +EXTERN void CalBddNodePrint(CalBddNode_t *bddNode); +EXTERN void CalBddPrint(Cal_Bdd_t calBdd); +EXTERN void CalHashTablePrint(CalHashTable_t *hashTable); +EXTERN void CalHashTableOnePrint(CalHashTable_t *hashTable, int flag); +EXTERN void CalUtilSRandom(long seed); +EXTERN long CalUtilRandom(); + +/**AutomaticEnd***************************************************************/ + +#endif /* _INT */ diff --git a/calInteract.c b/calInteract.c new file mode 100644 index 0000000..71c5699 --- /dev/null +++ b/calInteract.c @@ -0,0 +1,348 @@ +/**CFile*********************************************************************** + + FileName [calInteract.c] + + PackageName [cal] + + Synopsis [Functions to manipulate the variable interaction matrix.] + + Description [ + The interaction matrix tells whether two variables are + both in the support of some function of the DD. The main use of the + interaction matrix is in the in-place swapping. Indeed, if two + variables do not interact, there is no arc connecting the two layers; + therefore, the swap can be performed in constant time, without + scanning the subtables. Another use of the interaction matrix is in + the computation of the lower bounds for sifting. Finally, the + interaction matrix can be used to speed up aggregation checks in + symmetric and group sifting.

+ The computation of the interaction matrix is done with a series of + depth-first searches. The searches start from those nodes that have + only external references. The matrix is stored as a packed array of bits; + since it is symmetric, only the upper triangle is kept in memory. + As a final remark, we note that there may be variables that do + intercat, but that for a given variable order have no arc connecting + their layers when they are adjacent.] + + SeeAlso [] + + Author [Original author:Fabio Somenzi. Modified for CAL package + by Rajeev K. Ranjan] + + Copyright [ This file was created at the University of Colorado at + Boulder. The University of Colorado at Boulder makes no warranty + about the suitability of this software for any purpose. It is + presented on an AS IS basis.] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +#if SIZEOF_LONG == 8 +#define BPL 64 +#define LOGBPL 6 +#else +#define BPL 32 +#define LOGBPL 5 +#endif + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void ddSuppInteract(Cal_BddManager_t *bddManager, Cal_Bdd_t f, int *support); +static void ddClearLocal(Cal_Bdd_t f); +static void ddUpdateInteract(Cal_BddManager_t *bddManager, int *support); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + + +/**Function******************************************************************** + + Synopsis [Set interaction matrix entries.] + + Description [Given a pair of variables 0 <= x < y < table->size, + sets the corresponding bit of the interaction matrix to 1.] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +void +CalSetInteract(Cal_BddManager_t *bddManager, int x, int y) +{ + int posn, word, bit; + + Cal_Assert(x < y); + Cal_Assert(y < bddManager->numVars); + Cal_Assert(x >= 0); + + posn = ((((bddManager->numVars << 1) - x - 3) * x) >> 1) + y - 1; + word = posn >> LOGBPL; + bit = posn & (BPL-1); + bddManager->interact[word] |= 1 << bit; + +} /* end of CalSetInteract */ + + +/**Function******************************************************************** + + Synopsis [Test interaction matrix entries.] + + Description [Given a pair of variables 0 <= x < y < bddManager->numVars, + tests whether the corresponding bit of the interaction matrix is 1. + Returns the value of the bit.] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +int +CalTestInteract(Cal_BddManager_t *bddManager, int x, int y) +{ + int posn, word, bit, result; + + x -= 1; + y -= 1; + + if (x > y) { + int tmp = x; + x = y; + y = tmp; + } + Cal_Assert(x < y); + Cal_Assert(y < bddManager->numVars); + Cal_Assert(x >= 0); + + posn = ((((bddManager->numVars << 1) - x - 3) * x) >> 1) + y - 1; + word = posn >> LOGBPL; + bit = posn & (BPL-1); + result = (bddManager->interact[word] >> bit) & 1; + return(result); + +} /* end of CalTestInteract */ + + +/**Function******************************************************************** + + Synopsis [Initializes the interaction matrix.] + + Description [Initializes the interaction matrix. The interaction + matrix is implemented as a bit vector storing the upper triangle of + the symmetric interaction matrix. The bit vector is kept in an array + of long integers. The computation is based on a series of depth-first + searches, one for each root of the DAG. A local flag (the mark bits) + is used.] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +int +CalInitInteract(Cal_BddManager_t *bddManager) +{ + int i,k; + int words; + long *interact; + int *support; + long numBins; + CalBddNode_t **bins, *bddNode, *nextBddNode; + + int n = bddManager->numVars; + + words = ((n * (n-1)) >> (1 + LOGBPL)) + 1; + bddManager->interact = interact = Cal_MemAlloc(long, words); + if (interact == NULL) return(0); + for (i = 0; i < words; i++) { + interact[i] = 0; + } + + support = Cal_MemAlloc(int, n); + if (support == Cal_Nil(int)) { + Cal_MemFree(interact); + return(0); + } + bins = bddManager->uniqueTable[0]->bins; + numBins = bddManager->uniqueTable[0]->numBins; + for (i=0; ipipelineState == CREATE){ + CalRequestNode_t **requestNodeListArray = + bddManager->requestNodeListArray; + Cal_Bdd_t resultBdd; + for (i=0; + ipipelineDepth-bddManager->currentPipelineDepth; + i++){ + for (bddNode = *requestNodeListArray; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + Cal_Assert(CalBddNodeIsForwarded(bddNode)); + CalBddNodeGetThenBdd(bddNode, resultBdd); + Cal_Assert(CalBddIsForwarded(resultBdd) == 0); + for (k = 0; k < n; k++) { + support[k] = 0; + } + ddSuppInteract(bddManager, resultBdd, support); + ddClearLocal(resultBdd); + ddUpdateInteract(bddManager, support); + } + requestNodeListArray++; + } + } + + + Cal_MemFree(support); + return(1); + +} /* end of CalInitInteract */ + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + + +/**Function******************************************************************** + + Synopsis [Find the support of f.] + + Description [Performs a DFS from f. Uses the LSB of the then pointer + as visited flag.] + + SideEffects [Accumulates in support the variables on which f depends.] + + SeeAlso [] + +******************************************************************************/ +static void +ddSuppInteract(Cal_BddManager_t *bddManager, Cal_Bdd_t f, int *support) +{ + Cal_Bdd_t thenBdd, elseBdd; + + if (CalBddIsBddConst(f) || CalBddIsMarked(f)){ + return; + } + support[f.bddId-1] = 1; + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + ddSuppInteract(bddManager, thenBdd, support); + ddSuppInteract(bddManager, elseBdd, support); + CalBddMark(f); + return; +} /* end of ddSuppInteract */ + + +/**Function******************************************************************** + + Synopsis [Performs a DFS from f, clearing the LSB of the then pointers.] + + Description [] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +static void +ddClearLocal(Cal_Bdd_t f) +{ + Cal_Bdd_t thenBdd; + Cal_Bdd_t elseBdd; + CalBddGetElseBdd(f, elseBdd); + if (CalBddIsBddConst(f) || !CalBddIsMarked(f)){ + return; + } + /* clear visited flag */ + CalBddUnmark(f); + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + ddClearLocal(thenBdd); + ddClearLocal(elseBdd); + return; +} /* end of ddClearLocal */ + + +/**Function******************************************************************** + + Synopsis [Marks as interacting all pairs of variables that appear in + support.] + + Description [If support[i] == support[j] == 1, sets the (i,j) entry + of the interaction matrix to 1.] + + SideEffects [None] + + SeeAlso [] + +******************************************************************************/ +static void +ddUpdateInteract(Cal_BddManager_t *bddManager, int *support) +{ + int i,j; + int n = bddManager->numVars; + + for (i = 0; i < n-1; i++) { + if (support[i] == 1) { + for (j = i+1; j < n; j++) { + if (support[j] == 1) { + CalSetInteract(bddManager, i, j); + } + } + } + } +} /* end of ddUpdateInteract */ + + diff --git a/calMem.c b/calMem.c new file mode 100644 index 0000000..f6954c9 --- /dev/null +++ b/calMem.c @@ -0,0 +1,717 @@ +/**CFile***************************************************************** + + FileName [calMem.c] + + PackageName [cal] + + Synopsis [Routines for memory management.] + + Description [Contains allocation, free, resize routines. Also has + routines for managing records of fixed size.] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu). Originally + written by David Long.] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calMem.c,v 1.1.1.3 1998/05/04 00:58:59 hsv Exp $] + +******************************************************************************/ + +#include +#include "calMem.h" +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef struct BlockStruct *Block; +typedef struct BlockStruct Block_t; +typedef struct SegmentStruct *Segment; +typedef struct SegmentStruct Segment_t; +typedef struct ListStruct *List; +typedef struct ListStruct List_t; +typedef struct Cal_RecMgrStruct Cal_RecMgr_t; + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/* #define DEBUG_MEM */ +#define MAGIC_COOKIE 0x34f21ab3l +#define MAGIC_COOKIE1 0x432fa13bl +struct SegmentStruct +{ + Cal_Pointer_t baseAddress; + Cal_Address_t limit; +}; + +struct BlockStruct +{ + int used; + int sizeIndex; + unsigned long dummy; + Block_t *next; + Block_t *prev; + Segment seg; +}; +#define HEADER_SIZE ((Cal_Address_t)CAL_ROUNDUP(sizeof(Block_t))) +#define MAX_SIZEINDEX (8*sizeof(Cal_Address_t)-2) +#define MAX_SEG_SIZE ((Cal_Address_t)1 << MAX_SIZEINDEX) +#define MAX_SIZE ((Cal_Address_t)(MAX_SEG_SIZE-HEADER_SIZE)) +#define NICE_BLOCK_SIZE ((Cal_Address_t)PAGE_SIZE-CAL_ROUNDUP(sizeof(Block_t))) +#define ALLOC_SIZE NICE_BLOCK_SIZE +#define MIN_ALLOC_SIZEINDEX 15 + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ +struct ListStruct +{ + List_t *next; +}; + +struct Cal_RecMgrStruct +{ + int size; + int recsPerBlock; + List free; + List blocks; + int numBlocks; +}; + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static Cal_Address_t blockAllocation; +static Block avail[MAX_SIZEINDEX+1]; + + +/* Bogus segment for initialization */ + +static Segment_t dummySeg={(Cal_Pointer_t)0, (Cal_Address_t)0}; + + +/* Current segment */ + +static Segment currSeg= &dummySeg; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#define SBRK(size) ((Cal_Pointer_t)sbrk((long)(size))) + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int CeilingLog2(Cal_Address_t i); +static int BlockSizeIndex(Cal_Address_t size); +static void AddToFreeList(Block b); +static Block RemoveFromFreeList(Block b); +static Block Buddy(Block b); +static void TrimToSize(Block b, int sizeIndex); +static void MergeAndFree(Block b); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + + + +/**Function******************************************************************** + + Synopsis [Prints an error message and exits.] + + Description [Prints an error message and exits.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_MemFatal(char *message) +{ + fprintf(stderr, "Memory management library: error: %s\n", message); + exit(1); +} + +/**Function******************************************************************** + + Synopsis [Returns the memory allocated.] + + Description [Returns the memory allocated.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Address_t +Cal_MemAllocation(void) +{ + return (blockAllocation); +} + +/**Function******************************************************************** + + Synopsis [Allocates a new block of the specified size.] + + Description [Allocates a new block of the specified size.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Pointer_t +Cal_MemGetBlock(Cal_Address_t size) +{ + int i; + int sizeIndex; + int allocSizeIndex; + int newSeg; + Cal_Address_t allocSize; + Cal_Pointer_t sbrkRet; + Block b; + + if ((sizeIndex = BlockSizeIndex(size)) < 0) return ((Cal_Pointer_t)0); + + /* Find smallest free block which is large enough. */ + for (i = sizeIndex; i <= MAX_SIZEINDEX && !avail[i]; ++i); + if (i > MAX_SIZEINDEX) { + /* We must get more storage; don't allocate less than */ + /* 2^MIN_ALLOC_SIZE_INDEX */ + if (sizeIndex < MIN_ALLOC_SIZEINDEX) allocSizeIndex=MIN_ALLOC_SIZEINDEX; + else allocSizeIndex=sizeIndex; + allocSize=((Cal_Address_t)1 << allocSizeIndex); + + /* Pad current segment to be a multiple of 2^allocSizeIndex in */ + /* length. */ + allocSize += ((currSeg->limit + allocSize - 1) & + ~(allocSize - 1)) - currSeg->limit; + if ((sbrkRet=(Cal_Pointer_t)SBRK(0)) != + (Cal_Pointer_t)((Cal_Address_t)currSeg->baseAddress+currSeg->limit) || + allocSize+currSeg->limit > MAX_SEG_SIZE) { + + /* Segment is too large or someone else has moved the break. */ + /* Pad to get to appropriate boundary. */ + allocSize=CAL_ROUNDUP((Cal_Address_t)sbrkRet)-(Cal_Address_t)sbrkRet; + + /* Pad allocation request with storage for new segment */ + /* information and indicate that a new segment must be */ + /* created. */ + allocSize+=((Cal_Address_t)1 << allocSizeIndex)+CAL_ROUNDUP(sizeof(Segment_t)); + newSeg=1; + } + else newSeg=0; + sbrkRet=(Cal_Pointer_t)SBRK(allocSize); + if (sbrkRet == (Cal_Pointer_t) -1) Cal_MemFatal("Cal_MemGetBlock: allocation failed"); + blockAllocation += allocSize; + if (newSeg){ + currSeg = (Segment) CAL_ROUNDUP((Cal_Address_t)sbrkRet); + currSeg->baseAddress=(Cal_Pointer_t)((Cal_Address_t)currSeg+CAL_ROUNDUP(sizeof(Segment_t))); + currSeg->limit=0; + /* Readjust allocation size. */ + allocSize=(1l << allocSizeIndex); + } + /* Carve allocated space up into blocks and add to free lists. */ + while (allocSize){ + size = allocSize - (allocSize & (allocSize-1)); + b = (Block) ((Cal_Address_t)currSeg->baseAddress+currSeg->limit); + b->sizeIndex = CeilingLog2(size); + b->seg = currSeg; + AddToFreeList(b); + currSeg->limit += size; + allocSize -= size; + } + /* Find free block of appropriate size. */ + for (i=sizeIndex; i <= MAX_SIZEINDEX && !avail[i]; ++i); + } + b = RemoveFromFreeList(avail[i]); + TrimToSize(b, sizeIndex); + return ((Cal_Pointer_t)((Cal_Address_t)b + HEADER_SIZE)); +} + + +/**Function******************************************************************** + + Synopsis [Frees the block.] + + Description [Frees the block.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/void +Cal_MemFreeBlock(Cal_Pointer_t p) +{ + Block b; + + if (!p) return; + b = (Block) ((Cal_Address_t)p-HEADER_SIZE); + if (!b->used) Cal_MemFatal("Cal_MemFreeBlock: block not in use"); + if (b->sizeIndex < 0 || b->sizeIndex > MAX_SIZEINDEX) Cal_MemFatal("Cal_MemFreeBlock: invalid block header"); + MergeAndFree(b); +} + + + +/**Function******************************************************************** + + Synopsis [Expands or contracts the block to a new size. + We try to avoid moving the block if possible. ] + + Description [Expands or contracts the block to a new size. + We try to avoid moving the block if possible. ] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Pointer_t +Cal_MemResizeBlock(Cal_Pointer_t p, Cal_Address_t newSize) +{ + int newSizeIndex; + Block b; + Block bb; + Cal_Pointer_t q; + Cal_Address_t oldSize; + + if (!p) return (Cal_MemGetBlock(newSize)); + b = (Block) ((Cal_Address_t)p - HEADER_SIZE); + if (!b->used) Cal_MemFatal("Cal_MemResizeBlock: block not in use"); + if (b->sizeIndex < 0 || b->sizeIndex > MAX_SIZEINDEX){ + Cal_MemFatal("Cal_MemResizeBlock: invalid block header"); + } + if ((newSizeIndex = BlockSizeIndex(newSize)) < 0){ + Cal_MemFreeBlock(p); + return ((Cal_Pointer_t)0); + } + if (b->sizeIndex >= newSizeIndex){ + /* Shrink block. */ + TrimToSize(b, newSizeIndex); + return (p); + } + oldSize=(1l << b->sizeIndex) - HEADER_SIZE; + /* Try to expand by adding buddies at higher addresses. */ + for (bb=Buddy(b); + bb && (Cal_Address_t)b < (Cal_Address_t)bb && !bb->used && bb->sizeIndex == b->sizeIndex; + bb=Buddy(b)) { + RemoveFromFreeList(bb); + if (++(b->sizeIndex) == newSizeIndex) return (p); + } + /* Couldn't expand all the way to needed size; allocate a new block */ + /* and move the contents of the old one. */ + q = (Cal_Pointer_t) Cal_MemGetBlock(newSize); + Cal_MemCopy(q, p, oldSize); + MergeAndFree(b); + return (q); +} + +/**Function******************************************************************** + + Synopsis [Allocates a record from the specified record manager. ] + + Description [Allocates a record from the specified record manager. ] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Pointer_t +Cal_MemNewRec(Cal_RecMgr mgr) +{ + int i; + Cal_Pointer_t p; + List new; + + if (!mgr->free) { + /* Allocate a new block. */ + new = (List) Cal_MemGetBlock(ALLOC_SIZE); + mgr->numBlocks++; + new->next=mgr->blocks; + mgr->blocks=new; + mgr->free=(List)((Cal_Address_t)new+CAL_ROUNDUP(sizeof(List_t))); + p=(Cal_Pointer_t)(mgr->free); + /* Carve the block into pieces. */ + for (i=1; i < mgr->recsPerBlock; ++i) { + ((List)p)->next=(List)((Cal_Address_t)p+mgr->size); +#if defined(DEBUG_MEM) + if (mgr->size >= sizeof(long)+sizeof(List_t)) + *(long *)(sizeof(List_t)+(Cal_Address_t)p)=MAGIC_COOKIE; +#endif + p=(Cal_Pointer_t)((Cal_Address_t)p+mgr->size); + } + ((List)p)->next=0; +#if defined(DEBUG_MEM) + if (mgr->size >= sizeof(long)+sizeof(List_t)){ + *(long *)(sizeof(List_t)+(Cal_Address_t)p)=MAGIC_COOKIE; + } +#endif + } + new = mgr->free; +#if defined(DEBUG_MEM) + if (mgr->size >= sizeof(long)+sizeof(List_t)){ + if (*(long *)(sizeof(List_t)+(Cal_Address_t)new) != MAGIC_COOKIE) + fprintf(stderr, "record at 0x%lx may be in use\n", (Cal_Address_t)new); + else + *(long *)(sizeof(struct + list_)+(Cal_Address_t)new)=MAGIC_COOKIE1; + } +#endif + mgr->free = mgr->free->next; + return ((Cal_Pointer_t)new); +} + + +/**Function******************************************************************** + + Synopsis [Frees a record managed by the indicated record manager. ] + + Description [Frees a record managed by the indicated record manager. ] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_MemFreeRec(Cal_RecMgr mgr, Cal_Pointer_t rec) +{ +#if defined(DEBUG_MEM) + if (mgr->size >= sizeof(long)+sizeof(List_t)) + if (*(long *)(sizeof(List_t)+(Cal_Address_t)rec) == MAGIC_COOKIE) + fprintf(stderr, "record at 0x%lx may already be freed\n", (Cal_Address_t)rec); +#endif + ((List)rec)->next=mgr->free; +#if defined(DEBUG_MEM) + if (mgr->size >= sizeof(long)+sizeof(List_t)) + *(long *)(sizeof(List_t)+(Cal_Address_t)rec)=MAGIC_COOKIE; +#endif + mgr->free=(List)rec; +} + + + +/**Function******************************************************************** + + Synopsis [Creates a new record manager with the given record size.] + + Description [Creates a new record manager with the given record size.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_RecMgr +Cal_MemNewRecMgr(int size) +{ + Cal_RecMgr mgr; + + if (size < sizeof(List_t)) size=sizeof(List_t); + size=CAL_ROUNDUP(size); + if (size > ALLOC_SIZE-CAL_ROUNDUP(sizeof(List_t))) + Cal_MemFatal("Cal_MemNewRecMgr: record size too large"); + mgr = (Cal_RecMgr)Cal_MemGetBlock((Cal_Address_t)sizeof(Cal_RecMgr_t)); + mgr->size=size; + mgr->recsPerBlock=(ALLOC_SIZE-CAL_ROUNDUP(sizeof(List_t)))/size; + mgr->free=0; + mgr->blocks=0; + mgr->numBlocks = 0; + return (mgr); +} + +/**Function******************************************************************** + + Synopsis [Frees all the storage associated with the specified record manager.] + + Description [Frees all the storage associated with the specified record manager.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_MemFreeRecMgr(Cal_RecMgr mgr) +{ + List p, q; + for (p=mgr->blocks; p; p=q){ + q=p->next; + Cal_MemFreeBlock((Cal_Pointer_t)p); + } + Cal_MemFreeBlock((Cal_Pointer_t)mgr); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static int +CeilingLog2(Cal_Address_t i) +{ + Cal_Address_t j; + int result; + + for (result=0, j=1; j < i; ++result, j*=2); + return (result); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [BlockSizeIndex(size) return the coded size for a block. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static int +BlockSizeIndex(Cal_Address_t size) +{ + if (size < 1) + return (-1); + if (size > MAX_SIZE) + Cal_MemFatal("BlockSizeIndex: block size too large"); + else + size+=HEADER_SIZE; + return (CeilingLog2(size)); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [AddToFreeList(b) adds b to the appropriate free list. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static void +AddToFreeList(Block b) +{ + int i; + + i=b->sizeIndex; + if (!avail[i]){ + b->next=b; + b->prev=b; + avail[i]=b; + } + else { + b->next=avail[i]->next; + avail[i]->next->prev=b; + avail[i]->next=b; + b->prev=avail[i]; + } + b->used=0; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [RemoveFromFreeList(b) removes b from the free list which it is on. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static Block +RemoveFromFreeList(Block b) +{ + int i; + + i=b->sizeIndex; + if (b->next == b) + avail[i]=0; + else { + b->next->prev=b->prev; + b->prev->next=b->next; + if (avail[i] == b) avail[i]=b->next; + } + b->used=1; + return (b); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [Buddy(b) returns the Buddy block of b, or null if there is no Buddy. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ + +static Block +Buddy(Block b) +{ + Cal_Address_t Buddy_offset; + + Buddy_offset=(Cal_Address_t)(((Cal_Address_t)b-(Cal_Address_t)b->seg->baseAddress) ^ + ((Cal_Address_t)1 << b->sizeIndex)); + if (Buddy_offset < b->seg->limit) + return ((Block)((Cal_Address_t)b->seg->baseAddress+Buddy_offset)); + else + return ((Block)0); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [TrimToSize(b, sizeIndex) repeatedly splits b until it has the indicated size. Blocks which are split off are added to the appropriate free list. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static void +TrimToSize(Block b, int sizeIndex) +{ + Block bb; + + while (b->sizeIndex > sizeIndex) { + b->sizeIndex--; + bb=Buddy(b); + bb->sizeIndex=b->sizeIndex; + bb->seg=b->seg; + AddToFreeList(bb); + } +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [MergeAndFree(b) repeatedly merges b its Buddy until b has no Buddy or the Buddy isn't free, then adds the result to the appropriate free list. ] + + SideEffects [required] + + SeeAlso [optional] + + CommandName [optional] + + CommandSynopsis [optional] + + CommandArguments [optional] + + CommandDescription [optional] + +******************************************************************************/ +static void +MergeAndFree(Block b) +{ + Block bb; + + for (bb=Buddy(b); bb && !bb->used && bb->sizeIndex == b->sizeIndex; + bb=Buddy(b)) { + RemoveFromFreeList(bb); + if ((Cal_Address_t)bb < (Cal_Address_t)b) b=bb; + b->sizeIndex++; + } + AddToFreeList(b); +} diff --git a/calMem.h b/calMem.h new file mode 100644 index 0000000..8b23196 --- /dev/null +++ b/calMem.h @@ -0,0 +1,112 @@ +/**CHeaderFile***************************************************************** + + FileName [calMem.h] + + PackageName [cal] + + Synopsis [Header file for memory management] + + Description [ ] + + SeeAlso [] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu). Originally written by David Long. ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calMem.h,v 1.2 1998/09/17 03:19:18 ravi Exp $] + +******************************************************************************/ + +#ifndef _CAL_MEM +#define _CAL_MEM + +#include + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/* CAL_ALLOC_ALIGNMENT is the alignment for all storage returned by the */ +/* storage allocation routines. */ +/* was 16 for __osf__ systems, 8 otherwise */ + +#define CAL_ALLOC_ALIGNMENT sizeof(void *) + + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef struct Cal_RecMgrStruct * Cal_RecMgr; +typedef void *Cal_Pointer_t; +typedef size_t Cal_Address_t; +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#ifndef EXTERN +#define EXTERN extern +#endif +#define Cal_Nil(obj) ((obj *)0) +#define USE_OS_MEMORY_MANAGEMENT +#ifdef USE_OS_MEMORY_MANAGEMENT +#define Cal_MemAlloc(type, num) ((type *) malloc(sizeof(type) * (num))) +#define Cal_MemRealloc(type, obj, num) \ + (obj) ? ((type *) realloc((char *) obj, sizeof(type) * (num))) : \ + ((type *) malloc(sizeof(type) * (num))) +#define Cal_MemFree(obj) ((obj) ? (free((char *) (obj)), (obj) = 0) : 0) +#else +#define Cal_MemAlloc(type, num) ((type *) Cal_MemGetBlock(sizeof(type) * (num))) +#define Cal_MemRealloc(type, obj, num) \ + (obj) ? ((type *) Cal_MemResizeBlock((Cal_Pointer_t) obj, sizeof(type) * (num))) : \ + ((type *) Cal_MemGetBlock(sizeof(type) * (num))) +#define Cal_MemFree(obj) ((obj) ? (Cal_MemFreeBlock((Cal_Pointer_t) (obj)), (obj) = 0) : 0) +#endif +#define Cal_MemCopy(dest, src, size) ((void *) memcpy((void *)dest, (const void *)src, (size_t)size)); +#define Cal_MemZero(ptr, size) ((void)memset((void *)(ptr), 0, (Cal_Address_t)(size))) + +/* Round a size up for alignment */ + +#define CAL_ROUNDUP(size) ((((size)+CAL_ALLOC_ALIGNMENT-1)/CAL_ALLOC_ALIGNMENT)*CAL_ALLOC_ALIGNMENT) + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Function prototypes */ +/*---------------------------------------------------------------------------*/ +EXTERN void Cal_MemFatal(char *message); +EXTERN Cal_Address_t Cal_MemAllocation(void); +EXTERN Cal_Pointer_t Cal_MemGetBlock(Cal_Address_t size); +EXTERN void Cal_MemFreeBlock(Cal_Pointer_t p); +EXTERN Cal_Pointer_t Cal_MemResizeBlock(Cal_Pointer_t p, Cal_Address_t newSize); +EXTERN Cal_Pointer_t Cal_MemNewRec(Cal_RecMgr mgr); +EXTERN void Cal_MemFreeRec(Cal_RecMgr mgr, Cal_Pointer_t rec); +EXTERN Cal_RecMgr Cal_MemNewRecMgr(int size); +EXTERN void Cal_MemFreeRecMgr(Cal_RecMgr mgr); + +/**AutomaticEnd***************************************************************/ + +#endif /* _CAL */ diff --git a/calMemoryManagement.c b/calMemoryManagement.c new file mode 100644 index 0000000..213669e --- /dev/null +++ b/calMemoryManagement.c @@ -0,0 +1,592 @@ +/**CFile*********************************************************************** + + FileName [calMemoryManagement.c] + + PackageName [cal] + + Synopsis [Special memory management routines specific to CAL.] + + Description [Functions for managing the system memory using a set of + nodeManagers. Each nodeManager manages a set of fixed size + nodes obtained from a set of pages. When additional memory + is required, nodeManager obtains a new page from the pageManager. + The new page is divided into ( PAGE_SIZE/NODE_SIZE ) number of + nodes.] + + SeeAlso [] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calMemoryManagement.c,v 1.3 1998/09/18 15:34:37 fabio Exp $] + +******************************************************************************/ +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#ifndef HAVE_VALLOC +#define __NOVALLOC__ +#else +#if HAVE_VALLOC != 1 +#define __NOVALLOC__ +#endif +#endif + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int PageManagerExpandStorage(CalPageManager_t * pageManager); +static CalAddress_t * PageAlign(CalAddress_t * p); +static int SegmentToPageList(CalAddress_t * segment, int numPages, CalAddress_t * lastPointer); + +/**AutomaticEnd***************************************************************/ + +/* + * object: pageManager + * operations: Init, Quit, AllocPage, FreePage, Print + */ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Name [CalPageMangerInit] + + Synopsis [Initializes a pageManager.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +CalPageManager_t * +CalPageManagerInit(int numPagesPerSegment) +{ + CalPageManager_t *pageManager; + pageManager = Cal_MemAlloc(CalPageManager_t, 1); + pageManager->totalNumPages = 0; + pageManager->numSegments = 0; + pageManager->numPagesPerSegment = numPagesPerSegment; + pageManager->maxNumSegments = MAX_NUM_SEGMENTS; + pageManager->pageSegmentArray + = Cal_MemAlloc(CalAddress_t *, pageManager->maxNumSegments); + pageManager->numPagesArray + = Cal_MemAlloc(int, pageManager->maxNumSegments); + pageManager->freePageList = Cal_Nil(CalAddress_t); + if(PageManagerExpandStorage(pageManager) == FALSE){ + Cal_MemFree(pageManager->pageSegmentArray); + Cal_MemFree(pageManager); + return Cal_Nil(CalPageManager_t); + } + return pageManager; +} + + +/**Function******************************************************************** + + Name [CalPageMangerQuit] + + Synopsis [Frees pageManager and associated pages.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalPageManagerQuit( + CalPageManager_t * pageManager) +{ + int i; + if(pageManager == Cal_Nil(CalPageManager_t)){ + return 1; + } + for(i = 0; i < pageManager->numSegments; i++){ + free(pageManager->pageSegmentArray[i]); + } + Cal_MemFree(pageManager->pageSegmentArray); + Cal_MemFree(pageManager->numPagesArray); + Cal_MemFree(pageManager); + return 0; +} + + +/**Function******************************************************************** + + Name [CalPageMangerPrint] + + Synopsis [Prints address of each memory segment and address of each page.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalPageManagerPrint( + CalPageManager_t * pageManager) +{ + int i; + CalAddress_t *page; + printf("****************** pageManager ********************\n"); + printf("allocationList:\n"); + for(i = 0; i < pageManager->numSegments; i++){ + page = pageManager->pageSegmentArray[i]; + printf("%lx%c", (CalAddress_t)page, (i+1)%5?' ':'\n'); + } + printf("\n"); + printf("freePageList:\n"); + i = 0; + page = pageManager->freePageList; + while(page){ + printf("%lx%c", (CalAddress_t)page, (i+1)%5?' ':'\n'); + i++; + page = (CalAddress_t *)*page; + } + printf("\n"); +} + + +/**Function******************************************************************** + + Name [CalNodeManagerInit] + + Synopsis [Initializes a node manager.] + + Description [optional] + + SideEffects [] + + SeeAlso [optional] + +******************************************************************************/ +CalNodeManager_t * +CalNodeManagerInit(CalPageManager_t * pageManager) +{ + CalNodeManager_t *nodeManager; + nodeManager = Cal_MemAlloc(CalNodeManager_t, 1); + nodeManager->freeNodeList = Cal_Nil(CalBddNode_t); + nodeManager->pageManager = pageManager; + nodeManager->numPages = 0; + nodeManager->maxNumPages = 10; + nodeManager->pageList = Cal_MemAlloc(CalAddress_t *, + nodeManager->maxNumPages); + return nodeManager; +} + + +/**Function******************************************************************** + + Name [CalNodeManagerQuit] + + Synopsis [Frees a node manager.] + + Description [optional] + + SideEffects [The associated nodes are lost.] + + SeeAlso [optional] + +******************************************************************************/ +int +CalNodeManagerQuit(CalNodeManager_t * nodeManager) +{ + if(nodeManager == Cal_Nil(CalNodeManager_t)){ + return 1; + } + else{ + int i; + for (i = 0; i < nodeManager->numPages; i++){ + CalPageManagerFreePage(nodeManager->pageManager, + nodeManager->pageList[i]); + } + Cal_MemFree(nodeManager->pageList); + Cal_MemFree(nodeManager); + return 0; + } +} + + + +/**Function******************************************************************** + + Name [CalNodeManagerPrint] + + Synopsis [Prints address of each free node.] + + Description [optional] + + SideEffects [] + + SeeAlso [optional] + +******************************************************************************/ +void +CalNodeManagerPrint( + CalNodeManager_t * nodeManager) +{ + int i; + CalBddNode_t *node; + printf("****************** nodeManager ********************\n"); + printf("freeNodeList:\n"); + i = 0; + node = nodeManager->freeNodeList; + while(node){ + printf("%lx%c", (CalAddress_t)node, (i+1)%5?' ':'\n'); + i++; + node = node->nextBddNode; + } + printf("\n"); +} + + +/**Function******************************************************************** + + Name [PageMangerAllocPage] + + Synopsis [Allocs a new page.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +CalAddress_t * +CalPageManagerAllocPage(CalPageManager_t * pageManager) +{ + CalAddress_t *page; + char buffer[512]; + if(pageManager->freePageList == Cal_Nil(CalAddress_t)){ + if(PageManagerExpandStorage(pageManager) == FALSE){ + sprintf(buffer, + "out of memory : Number of pages allocated = %d\n", + pageManager->totalNumPages); + CalBddFatalMessage(buffer); + } + } + page = pageManager->freePageList; + pageManager->freePageList = (CalAddress_t *)*page; + return page; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Name [PageMangerFreePage] + + Synopsis [Free a page.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalPageManagerFreePage(CalPageManager_t * pageManager, CalAddress_t * page) +{ + *page = (CalAddress_t)(pageManager->freePageList); + pageManager->freePageList = page; +} + + +/**Function******************************************************************** + + Name [PageManagerExpandStorage] + + Synopsis [Allocates a segment of memory to expand the storage managed by + pageManager. The allocated segment is divided into free pages + which are linked as a freePageList.] + + Description [optional] + + SideEffects [The size of the segment is stored in one of the fields + of page manager - numPagesPerSegment. If a memory + segment of a specific size cannot be allocated, the + routine calls itself recursively by reducing + numPagesPerSegment by a factor of 2.] + + SeeAlso [optional] + +******************************************************************************/ +static int +PageManagerExpandStorage(CalPageManager_t * pageManager) +{ + CalAddress_t *p; + CalAddress_t *segment; + int numUsefulPages; + + int numPagesPerSegment = pageManager->numPagesPerSegment; + +#ifdef __NOVALLOC__ + p = (CalAddress_t *) malloc(numPagesPerSegment*PAGE_SIZE); +#else + p = (CalAddress_t *) valloc(numPagesPerSegment*PAGE_SIZE); +#endif + /* Just check the page boundary correctness */ + Cal_Assert(((CalAddress_t)p & ((1 << LG_PAGE_SIZE)-1)) == 0); + if(p == Cal_Nil(CalAddress_t)){ + numPagesPerSegment = numPagesPerSegment / 2; + if(numPagesPerSegment < MIN_NUM_PAGES_PER_SEGMENT){ + return FALSE; + } + pageManager->numPagesPerSegment = numPagesPerSegment; + return PageManagerExpandStorage(pageManager); + } + +#ifdef __NOVALLOC__ + /* No need to do it anymore, since I am using valloc */ + /* align the memory segment to a page boundary */ + segment = PageAlign(p); + + /* if memory segment is already page aligned, all pages in the memory + * segment are useful, otherwise, one page is wasted + */ + if(segment == p){ + numUsefulPages = numPagesPerSegment; + } + else{ + numUsefulPages = numPagesPerSegment - 1; + } +#else + segment = p; + numUsefulPages = numPagesPerSegment; +#endif + + /* Initialize the pages */ + memset((char *)segment, 0, numUsefulPages*PAGE_SIZE); + + /* Keep track of the number of pages allocated */ + pageManager->totalNumPages += numUsefulPages; + + /* increase the size of the allocation list if neccessary */ + if(pageManager->numSegments == pageManager->maxNumSegments){ + pageManager->maxNumSegments = pageManager->maxNumSegments * 2; + pageManager->pageSegmentArray = Cal_MemRealloc(CalAddress_t *, + pageManager->pageSegmentArray, + pageManager->maxNumSegments); + pageManager->numPagesArray = Cal_MemRealloc(int, + pageManager->numPagesArray, + pageManager->maxNumSegments); + + } + + pageManager->pageSegmentArray[pageManager->numSegments] = segment; + pageManager->numPagesArray[pageManager->numSegments++] = + numUsefulPages; + + SegmentToPageList(segment, numUsefulPages, pageManager->freePageList); + pageManager->freePageList = segment; + return TRUE; +} + + +/**Function******************************************************************** + + Name [PageAlign] + + Synopsis [Return page aligned address greater than or equal to + the pointer.] + + Description [optional] + + SideEffects [] + + SeeAlso [optional] + +******************************************************************************/ +static CalAddress_t * +PageAlign( + CalAddress_t * p) +{ + if((CalAddress_t)p & (PAGE_SIZE - 1)){ + p = (CalAddress_t *)( (CalAddress_t)p >> LG_PAGE_SIZE ); + p = (CalAddress_t *)( ((CalAddress_t)p << LG_PAGE_SIZE) + PAGE_SIZE ); + } + return p; +} + + +/**Function******************************************************************** + + Name [SegmentToPageList] + + Synopsis [Converts a memory segment into a linked list of pages. + if p is a pointer to a page, *p contains address of the next page + if p is a pointer to the last page, *p contains lastPointer.] + + Description [optional] + + SideEffects [] + + SeeAlso [optional] + +******************************************************************************/ +static int +SegmentToPageList(CalAddress_t * segment, + int numPages, + CalAddress_t * lastPointer) +{ + int i; + unsigned long thisPageOffset, nextPageOffset; + + if(numPages > 0){ + for(i = 0; i < numPages - 1; i++){ + thisPageOffset = (i< +#include + + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static int ITERATION; + + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalPerformanceTestAnd(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +#ifdef COMPUTE_MEMORY_OVERHEAD +static void CalPerformanceMemoryOverhead(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +#endif +static void CalPerformaceTestSuperscalar(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestNonSuperscalar(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestMultiway(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestOneway(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestCompose(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestQuantifyAllTogether(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions, int bfZeroBFPlusDFOne, int cacheExistsResultsFlag, int cacheOrResultsFlag); +static void CalQuantifySanityCheck(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestRelProd(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions, int bfZeroBFPlusDFOne, int cacheRelProdResultsFlag, int cacheAndResultsFlag, int cacheOrResultsFlag); +static void CalPerformanceTestSubstitute(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static void CalPerformanceTestSwapVars(Cal_BddManager bddManager, Cal_Bdd *outputBddArray, int numFunctions); +static long elapsedTime(); +static double cpuTime(); +static long pageFaults(); +static void GetRandomNumbers(int lowerBound, int upperBound, int count, int *resultVector); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Main routine for testing performances of various routines.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +Cal_PerformanceTest(Cal_BddManager bddManager, Cal_Bdd + *outputBddArray, int numFunctions, int iteration, int seed, + int andPerformanceFlag, int + multiwayPerformanceFlag, int + onewayPerformanceFlag, int + quantifyPerformanceFlag, + int composePerformanceFlag, int relprodPerformanceFlag, + int swapPerformanceFlag, + int substitutePerformanceFlag, int + sanityCheckFlag, int computeMemoryOverheadFlag, + int superscalarFlag) +{ + + CalUtilSRandom((long)seed); + + ITERATION = iteration; + fprintf(stdout,"%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"); + fprintf(stdout, "Performing %d iterations for each function\n", iteration); + Cal_BddSetGCMode(bddManager, 0); +#ifdef QUANTIFY + quantify_start_recording_data(); +#endif + +#ifdef PURECOV + purecov_clear_data(); +#endif + + if (relprodPerformanceFlag){ + CalPerformanceTestRelProd(bddManager, outputBddArray, numFunctions, 1, 1, + 1, 1); + CalUtilSRandom((long)seed); + + } + if (sanityCheckFlag == 1){ + CalQuantifySanityCheck(bddManager, outputBddArray, + numFunctions); + CalUtilSRandom((long)seed); + } + if (quantifyPerformanceFlag){ + CalPerformanceTestQuantifyAllTogether(bddManager, outputBddArray, + numFunctions, 1, 1, 1); + CalUtilSRandom((long)seed); + /* + CalPerformanceTestNonSuperscalarQuant(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + */ + } + + if (multiwayPerformanceFlag){ + CalPerformanceTestMultiway(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } + if (onewayPerformanceFlag){ + CalPerformanceTestOneway(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } + if (andPerformanceFlag){ + CalPerformanceTestAnd(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } + if (composePerformanceFlag){ + CalPerformanceTestCompose(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } + if (swapPerformanceFlag){ + CalPerformanceTestSwapVars(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } + if (substitutePerformanceFlag){ + CalPerformanceTestSubstitute(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } +#ifdef COMPUTE_MEMORY_OVERHEAD + if (computeMemoryOverheadFlag){ + CalPerformaceMemoryOverhead(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } +#endif + if (superscalarFlag){ + CalPerformaceTestSuperscalar(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + CalPerformanceTestNonSuperscalar(bddManager, outputBddArray, numFunctions); + CalUtilSRandom((long)seed); + } +#ifdef QUANTIFY + quantify_stop_recording_data(); +#endif +#ifdef PURECOV + purecov_save_data(); + purecov_disable_save(); +#endif + fprintf(stdout,"%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"); + Cal_BddSetGCMode(bddManager, 1); + return 0; +} +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalIncreasingOrderCompare(const void *a, const void *b) +{ + return (*(int *)b-*(int *)a); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalDecreasingOrderCompare(const void *a, const void *b) +{ + return (*(int *)a-*(int *)b); +} +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Performance test routine for quantify (all variables at the same + time).] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalPerformanceTestAnd(Cal_BddManager bddManager, Cal_Bdd + *outputBddArray, int numFunctions) +{ + int i; + Cal_Bdd function1, function2; + Cal_Bdd result; + + + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i numFunctions) return; + varIdArray = Cal_MemAlloc(int, num); + bddArray = Cal_MemAlloc(Cal_Bdd, num+1); + bddArray[num] = Cal_BddGetNullBdd(bddManager); + + maxReduceToApplyRatio = 0; + maxReduceToUniqueTableRatio = 0; + + for (i=0; i 100) num = 100; + varIdArray = Cal_MemAlloc(int, num); + bddArray = Cal_MemAlloc(Cal_Bdd, num+1); + bddArray[num] = (Cal_Bdd) 0; + + + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i 100) num = 100; + + varIdArray = Cal_MemAlloc(int, num); + bddArray = Cal_MemAlloc(Cal_Bdd, num+1); + bddArray[num] = (Cal_Bdd) 0; + resultArray = Cal_MemAlloc(Cal_Bdd, num/2); + + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i numFunctions) return; + varIdArray = Cal_MemAlloc(int, num); + bddArray = Cal_MemAlloc(Cal_Bdd, num+1); + bddArray[num] = (Cal_Bdd) 0; + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i numFunctions) return; + varIdArray = Cal_MemAlloc(int, num); + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i numFunctions/2) ? numFunctions/2 + : numVars/2); + int *varIdArray = Cal_MemAlloc(int, numQuantifyVars); + Cal_Bdd *assoc = Cal_MemAlloc(Cal_Bdd, 2*numQuantifyVars+1); + Cal_Bdd function, result; + + for (i=0; i <= 2*numQuantifyVars; i++){ + assoc[i] = (Cal_Bdd) 0; + } + (void) elapsedTime(); + cpuTime(); + pageFaults(); + for (i=0; i= count.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +GetRandomNumbers(int lowerBound, int upperBound, int count, int *resultVector) +{ + int i,j, tempVector[2048], number; + int range = (upperBound - lowerBound + 1); + + for (i=0; i 6){ + CalBddWarningMessage("PipelineDepth can not exceed 6\n"); + CalBddWarningMessage("setting PipelineDepth to 6\n"); + depth = 6; + } + if(bddManager->maxDepth < depth){ + int oldMaxDepth = bddManager->maxDepth; + bddManager->depth = bddManager->maxDepth = depth; + bddManager->reqQue = Cal_MemRealloc(CalHashTable_t **, bddManager->reqQue, + bddManager->maxDepth); + for(i = oldMaxDepth; i < bddManager->maxDepth; i++){ + bddManager->reqQue[i] = Cal_MemAlloc(CalHashTable_t *, bddManager->maxNumVars+1); + for(j = 0; j < bddManager->numVars+1; j++){ + bddManager->reqQue[i][j] = + CalHashTableInit(bddManager, j); + } + } + } + else{ + bddManager->depth = depth; + } +} + +/**Function******************************************************************** + + Synopsis [Initialize a BDD pipeline.] + + Description [All the operations for this pipeline must be of the + same kind.] + + SideEffects [None.] + + SeeAlso [] + +******************************************************************************/ +int +Cal_PipelineInit(Cal_BddManager bddManager, Cal_BddOp_t bddOp) +{ + CalBddPostProcessing(bddManager); + if(bddManager->pipelineState != READY){ + CalBddWarningMessage("Pipeline cannot be initialized"); + return 0; + } + else{ + bddManager->pipelineState = CREATE; + switch(bddOp){ + case CAL_AND : + bddManager->pipelineFn = CalOpAnd; + break; + case CAL_OR : + bddManager->pipelineFn = CalOpOr; + break; + case CAL_XOR : + bddManager->pipelineFn = CalOpXor; + break; + default : + CalBddWarningMessage("Unknown Bdd Operation type"); + return 0; + } + return 1; + } +} + +/**Function******************************************************************** + + Synopsis [Create a provisional BDD in the pipeline.] + + Description [The provisional BDD is automatically freed once the + pipeline is quitted.] + + SideEffects [] + + SeeAlso [] + +******************************************************************************/ +Cal_Bdd +Cal_PipelineCreateProvisionalBdd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd gUserBdd) +{ + int insertDepth, operandDepth; + CalRequestNode_t *requestNode; + Cal_Bdd_t provisionalBdd, f, g; + Cal_BddId_t bddId; + Cal_Bdd userNode; + + insertDepth = 0; + + f = CalBddGetInternalBdd(bddManager, fUserBdd); + g = CalBddGetInternalBdd(bddManager, gUserBdd); + if(bddManager->pipelineState != CREATE){ + CalBddWarningMessage("Provisional Bdd not created: Pipeline is not initialized"); + return (Cal_Bdd) 0; + } + if(CalBddIsMarked(f)){ + CalBddGetDepth(f, operandDepth); + if(insertDepth <= operandDepth){ + insertDepth = operandDepth + 1; + } + } + if(CalBddIsMarked(g)){ + CalBddGetDepth(g, operandDepth); + if(insertDepth <= operandDepth){ + insertDepth = operandDepth + 1; + } + } + if (bddManager->pipelineDepth <= insertDepth){ + bddManager->pipelineDepth = insertDepth + 1; + } + if (insertDepth >= MAX_INSERT_DEPTH){ + CalBddWarningMessage("Provisional Bdd not created"); + CalBddWarningMessage("Maximum pipeline depth is reached"); + return (Cal_Bdd) 0; + } + + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], requestNode); + CalRequestNodePutF(requestNode, f); + CalRequestNodePutG(requestNode, g); + CalRequestNodeMark(requestNode); + CalRequestNodePutDepth(requestNode, insertDepth); + CalRequestNodePutNextRequestNode(requestNode, + bddManager->requestNodeListArray[insertDepth]); + bddManager->requestNodeListArray[insertDepth] = requestNode; + + CalBddGetMinId2(bddManager, f, g, bddId); + CalBddPutBddId(provisionalBdd, bddId); + CalBddPutBddNode(provisionalBdd, (CalBddNode_t *)requestNode); + + CalNodeManagerAllocNode(bddManager->nodeManagerArray[0], userNode); + CalBddNodePutThenBdd(userNode, provisionalBdd); + CalBddNodePutElseBdd(userNode, bddManager->bddOne); + CalBddNodePutNextBddNode(userNode, + bddManager->userProvisionalNodeList); + bddManager->userProvisionalNodeList = userNode; + CalBddNodeIcrRefCount(userNode); + return userNode; +} + +/**Function******************************************************************** + + Synopsis [Executes a pipeline.] + + Description [All the results are computed. User should update the + BDDs of interest. Eventually this feature would become transparent.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +Cal_PipelineExecute(Cal_BddManager bddManager) +{ + CalRequestNode_t **requestNodeListArray, *node, *nextNode; + int i; + Cal_Bdd_t thenBdd; + int automaticDepthControlFlag = 0; + int pipelineDepth; + + if(bddManager->pipelineState != CREATE){ + CalBddWarningMessage("Pipeline cannot be executed"); + return 0; + } + + /* Check if we need to control the depth value using some heuristic */ + if (bddManager->depth == 0) automaticDepthControlFlag = 1; + + requestNodeListArray = bddManager->requestNodeListArray; + pipelineDepth = bddManager->pipelineDepth; + while(pipelineDepth){ + if (automaticDepthControlFlag){ + if (bddManager->numNodes < 10000) bddManager->depth = 4; + else if (bddManager->numNodes < 100000) bddManager->depth = 2; + else bddManager->depth = 1; + } + if(bddManager->depth > pipelineDepth){ + bddManager->depth = pipelineDepth; + } + CalRequestNodeListArrayOp(bddManager, requestNodeListArray, + bddManager->pipelineFn); + pipelineDepth -= bddManager->depth; + + /* Lock the results, in case garbage collection needs to be + invoked */ + for (i=0; idepth; i++){ + for (node = requestNodeListArray[i]; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + CalBddNodeGetThenBdd(node, thenBdd); + CalBddIcrRefCount(thenBdd); + } + } + /* Save the current pipelineDepth */ + bddManager->currentPipelineDepth = pipelineDepth; + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + /* Abort, may be we should clean up a little bit */ + fprintf(stderr,"Bdd Overflow: Aborting\n"); + return 0; + } + requestNodeListArray += bddManager->depth; + } + /* Need to decrement the reference counts */ + for (i=0; ipipelineDepth; i++){ + for (node=bddManager->requestNodeListArray[i]; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + CalBddNodeGetThenBdd(node, thenBdd); + CalBddDcrRefCount(thenBdd); + } + } + bddManager->pipelineState = UPDATE; + return 1; +} + +/**Function******************************************************************** + + Synopsis [Update a provisional Bdd obtained during pipelining.] + + Description [The provisional BDD is automatically freed after + quitting pipeline.] + + SideEffects [] + + SeeAlso [] + +******************************************************************************/ +Cal_Bdd +Cal_PipelineUpdateProvisionalBdd(Cal_BddManager bddManager, + Cal_Bdd provisionalBdd) +{ + Cal_Bdd_t calBdd = CalBddGetInternalBdd(bddManager, provisionalBdd); + if(bddManager->pipelineState != UPDATE){ + CalBddWarningMessage("Provisional Bdd cannot be updated"); + return (Cal_Bdd) 0; + } + CalBddGetThenBdd(calBdd, calBdd); + return CalBddGetExternalBdd(bddManager, calBdd); +} + +/**Function******************************************************************** + + Synopsis [Returns 1, if the given user BDD contains + provisional BDD node.] + + Description [Returns 1, if the given user BDD contains + provisional BDD node.] + + SideEffects [None.] + + SeeAlso [] + +******************************************************************************/ +int +Cal_BddIsProvisional(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t internalBdd = CalBddGetInternalBdd(bddManager, userBdd); + return CalBddIsMarked(internalBdd); +} + +/**Function******************************************************************** + + Synopsis [Resets the pipeline freeing all resources.] + + Description [The user must make sure to update all provisional BDDs + of interest before calling this routine.] + + SideEffects [] + + SeeAlso [] + +******************************************************************************/ +void +Cal_PipelineQuit(Cal_BddManager bddManager) +{ + CalRequestNode_t *requestNode, *next; + int i; + + bddManager->pipelineState = READY; + for(i = 0; i < bddManager->pipelineDepth; i++){ + for(requestNode = bddManager->requestNodeListArray[i], + bddManager->requestNodeListArray[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], requestNode); + } + bddManager->requestNodeListArray[i] = Cal_Nil(CalRequestNode_t); + } + bddManager->pipelineDepth = 0; + for (requestNode = bddManager->userProvisionalNodeList; requestNode; + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[0], + requestNode); + } + bddManager->userProvisionalNodeList = Cal_Nil(CalRequestNode_t); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderFixProvisionalNodes(Cal_BddManager_t *bddManager) +{ + CalRequestNode_t **requestNodeListArray = + bddManager->requestNodeListArray; + CalRequestNode_t *node, *nextNode; + int i; + Cal_Bdd_t thenBdd, elseBdd; + + for (i=0; + ipipelineDepth-bddManager->currentPipelineDepth; + i++){ + for (node = *requestNodeListArray; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + Cal_Assert(CalBddNodeIsForwarded(node)); + CalBddNodeGetThenBdd(node, thenBdd); + if (CalBddIsForwarded(thenBdd)) { + CalBddForward(thenBdd); + } + CalBddNodePutThenBdd(node, thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + requestNodeListArray++; + } + for (; ipipelineDepth; i++){ + for (node = *requestNodeListArray; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + Cal_Assert(CalBddNodeIsForwarded(node) == 0); + CalBddNodeGetThenBdd(node, thenBdd); + if (CalBddIsForwarded(thenBdd)) { + CalBddForward(thenBdd); + } + CalBddNodePutThenBdd(node, thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + CalBddNodeGetElseBdd(node, elseBdd); + if (CalBddIsForwarded(elseBdd)) { + CalBddForward(elseBdd); + } + CalBddNodePutElseBdd(node, elseBdd); + Cal_Assert(CalBddIsForwarded(elseBdd) == 0); + } + requestNodeListArray++; + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCheckPipelineValidity(Cal_BddManager_t *bddManager) +{ + CalRequestNode_t **requestNodeListArray = + bddManager->requestNodeListArray; + CalRequestNode_t *node, *nextNode; + int i; + Cal_Bdd_t thenBdd, elseBdd; + + for (i=0; + ipipelineDepth-bddManager->currentPipelineDepth; + i++){ + for (node = *requestNodeListArray; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + Cal_Assert(CalBddNodeIsForwarded(node)); + CalBddNodeGetThenBdd(node, thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + requestNodeListArray++; + } + for (; ipipelineDepth; i++){ + for (node = *requestNodeListArray; node; node = nextNode){ + nextNode = CalBddNodeGetNextBddNode(node); + Cal_Assert(CalBddNodeIsForwarded(node) == 0); + CalBddNodeGetThenBdd(node, thenBdd); + /*Cal_Assert(CalBddIsForwarded(thenBdd) == 0);*/ + /* This is possible since the actual BDD of thenBdd could have been + computed and it is forwarded, however this node is not yet + updated with the result */ + CalBddNodeGetElseBdd(node, elseBdd); + /*Cal_Assert(CalBddIsForwarded(elseBdd) == 0);*/ + } + requestNodeListArray++; + } +} +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + diff --git a/calPrint.c b/calPrint.c new file mode 100644 index 0000000..184d0d5 --- /dev/null +++ b/calPrint.c @@ -0,0 +1,418 @@ +/**CFile*********************************************************************** + + FileName [calPrint.c] + + PackageName [cal] + + Synopsis [Routine for printing a BDD.] + + Description [] + + SeeAlso [None] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu) + Originally written by David Long. + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calPrint.c,v 1.2 1998/09/16 16:40:41 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static char defaultTerminalId[]="terminal XXXXXXXXXX XXXXXXXXXX"; +static char defaultVarName[]="var.XXXXXXXXXX"; + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void Chars(char c, int n, FILE *fp); +static void BddPrintTopVar(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_VarNamingFn_t VarNamingFn, Cal_Pointer_t env, FILE *fp); +static void BddPrintBddStep(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_VarNamingFn_t VarNamingFn, Cal_TerminalIdFn_t TerminalIdFn, Cal_Pointer_t env, FILE *fp, CalHashTable_t* hashTable, int indentation); +static char * BddTerminalId(Cal_BddManager_t *bddManager, Cal_Bdd_t f, Cal_TerminalIdFn_t TerminalIdFn, Cal_Pointer_t env); +static void BddTerminalValueAux(Cal_BddManager_t *bddManager, Cal_Bdd_t f, CalAddress_t *value1, CalAddress_t *value2); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Prints a BDD in the human readable form.] + + Description [Prints a human-readable representation of the BDD f to + the file given by fp. The namingFn should be a pointer to a function + taking a bddManager, a BDD and the pointer given by env. This + function should return either a null pointer or a srting that is the + name of the supplied variable. If it returns a null pointer, a + default name is generated based on the index of the variable. It is + also legal for naminFN to e null; in this case, default names are + generated for all variables. The macro bddNamingFnNone is a null + pointer of suitable type. terminalIdFn should be apointer to a + function taking a bddManager and two longs. plus the pointer given + by the env. It should return either a null pointer. If it returns a + null pointer, or if terminalIdFn is null, then default names are + generated for the terminals. The macro bddTerminalIdFnNone is a null + pointer of suitable type.] + + SideEffects [None.] + +******************************************************************************/ +void +Cal_BddPrintBdd(Cal_BddManager bddManager, + Cal_Bdd fUserBdd, Cal_VarNamingFn_t VarNamingFn, + Cal_TerminalIdFn_t TerminalIdFn, + Cal_Pointer_t env, FILE *fp) +{ + long next; + CalHashTable_t *hashTable; + + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager,fUserBdd); + CalBddMarkSharedNodes(bddManager, f); + hashTable = CalHashTableOneInit(bddManager, sizeof(long)); + next = 0; + CalBddNumberSharedNodes(bddManager, f, hashTable, &next); + BddPrintBddStep(bddManager, f, VarNamingFn, TerminalIdFn, env, fp, + hashTable, 0); + CalHashTableOneQuit(hashTable); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +char * +CalBddVarName(Cal_BddManager_t *bddManager, Cal_Bdd_t v, + Cal_VarNamingFn_t VarNamingFn, Cal_Pointer_t env) +{ + char *name; + if (VarNamingFn){ + Cal_Bdd userV = CalBddGetExternalBdd(bddManager, v); + name = (*VarNamingFn)(bddManager, userV, env); + Cal_BddFree(bddManager, userV); + } + else + name=0; + if (!name){ + sprintf(defaultVarName, "var.%d", CalBddGetBddIndex(bddManager, v)); + name = defaultVarName; + } + return (name); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddNumberSharedNodes(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + CalHashTable_t *hashTable, long *next) +{ + Cal_Bdd_t thenBdd, elseBdd; + int mark; + + if (CalBddIsBddConst(f) || ((1 << CalBddTypeAux(bddManager, f)) & + ((1 << CAL_BDD_TYPE_POSVAR) | + (1 << CAL_BDD_TYPE_NEGVAR)))) + return; + mark = CalBddGetMark(f); + if (mark == 0) return; + if (mark == 2) { + CalHashTableOneInsert(hashTable, f, (char *)next); + ++*next; + } + CalBddPutMark(f, 0); + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + CalBddNumberSharedNodes(bddManager, thenBdd, hashTable, next); + CalBddNumberSharedNodes(bddManager, elseBdd, hashTable, next); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddMarkSharedNodes(Cal_BddManager_t *bddManager, Cal_Bdd_t f) +{ + int mark; + Cal_Bdd_t thenBdd, elseBdd; + + if (CalBddIsOutPos(f) == 0){ + CalBddNot(f,f); + } + if (CalBddIsBddConst(f) || CalBddTypeAux(bddManager, f) == + CAL_BDD_TYPE_POSVAR) + return; + if ((mark = CalBddGetMark(f))){ + if (mark == 1){ + CalBddPutMark(f, 2); + return; + } + } + CalBddPutMark(f, 1); + CalBddGetThenBdd(f, thenBdd); + CalBddGetElseBdd(f, elseBdd); + CalBddMarkSharedNodes(bddManager, thenBdd); + CalBddMarkSharedNodes(bddManager, elseBdd); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +Chars(char c, int n,FILE *fp) +{ + int i; + for (i=0; i < n; ++i){ + fputc(c, fp); + } +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddPrintTopVar(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + Cal_VarNamingFn_t VarNamingFn, Cal_Pointer_t env, FILE *fp) +{ + Cal_Bdd_t ifVar; + ifVar = CalBddIf(bddManager, f); + fputs(CalBddVarName(bddManager, ifVar, VarNamingFn, env), fp); + fputc('\n', fp); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/static void +BddPrintBddStep(Cal_BddManager_t *bddManager, + Cal_Bdd_t f, Cal_VarNamingFn_t VarNamingFn, + Cal_TerminalIdFn_t TerminalIdFn, + Cal_Pointer_t env, FILE *fp, CalHashTable_t* hashTable, + int indentation) +{ + int negated; + long *number; + Cal_Bdd_t fNot, thenBdd, elseBdd; + + Chars(' ', indentation, fp); + switch (CalBddTypeAux(bddManager, f)){ + case CAL_BDD_TYPE_ZERO: + case CAL_BDD_TYPE_ONE: + fputs(BddTerminalId(bddManager, f, TerminalIdFn, env), fp); + fputc('\n', fp); + break; + case CAL_BDD_TYPE_NEGVAR: + fputc('!', fp); + /* fall through */ + case CAL_BDD_TYPE_POSVAR: + BddPrintTopVar(bddManager, f, VarNamingFn, env, fp); + break; + case CAL_BDD_TYPE_NONTERMINAL: + CalBddNot(f, fNot); + if (CalHashTableOneLookup(hashTable, fNot, Cal_Nil(char *))){ + f = fNot; + negated = 1; + } + else { + negated=0; + } + CalHashTableOneLookup(hashTable, f, (char **)&number); + if (number && *number < 0){ + if (negated) + fputc('!', fp); + fprintf(fp, "subformula %d\n", (int)-*number-1); + } + else { + if (number){ + fprintf(fp, "%d: ", (int) *number); + *number= -*number-1; + } + fputs("if ", fp); + BddPrintTopVar(bddManager, f, VarNamingFn, env, fp); + CalBddGetThenBdd(f, thenBdd); + BddPrintBddStep(bddManager, thenBdd, VarNamingFn, + TerminalIdFn, env, fp, hashTable, indentation+2); + Chars(' ', indentation, fp); + fputs("else if !", fp); + BddPrintTopVar(bddManager, f, VarNamingFn, env, fp); + CalBddGetElseBdd(f, elseBdd); + BddPrintBddStep(bddManager, elseBdd, VarNamingFn, + TerminalIdFn, env, fp, hashTable, indentation+2); + Chars(' ', indentation, fp); + fputs("endif ", fp); + BddPrintTopVar(bddManager, f, VarNamingFn, env, fp); + } + break; + default: + CalBddFatalMessage("BddPrintBddStep: unknown type returned by Cal_BddType"); + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static char * +BddTerminalId(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + Cal_TerminalIdFn_t TerminalIdFn, Cal_Pointer_t env) +{ + char *id; + CalAddress_t v1, v2; + BddTerminalValueAux(bddManager, f, &v1, &v2); + if (TerminalIdFn) id = (*TerminalIdFn)(bddManager, v1, v2, env); + else id=0; + if (!id){ + if (CalBddIsBddOne(bddManager, f)) return ("1"); + if (CalBddIsBddZero(bddManager, f)) return ("0"); + sprintf(defaultTerminalId, "terminal %ld %ld", (long)v1, (long)v2); + id = defaultTerminalId; + } + return (id); +} + + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddTerminalValueAux(Cal_BddManager_t *bddManager, Cal_Bdd_t f, + CalAddress_t *value1, CalAddress_t *value2) +{ + if (CalBddIsOutPos(f)){ + *value1 = (CalAddress_t)CalBddGetThenBddNode(f); + *value2 = (CalAddress_t)CalBddGetElseBddNode(f); + } + else + (*bddManager->TransformFn)(bddManager, + (CalAddress_t)CalBddGetThenBddNode(f), + (CalAddress_t)CalBddGetElseBddNode(f), + value1, value2, bddManager->transformEnv); +} + + + + + + + + diff --git a/calPrintProfile.c b/calPrintProfile.c new file mode 100644 index 0000000..6a4b00a --- /dev/null +++ b/calPrintProfile.c @@ -0,0 +1,334 @@ +/**CFile*********************************************************************** + + FileName [calPrintProfile.c] + + PackageName [cal] + + Synopsis [Routines for printing various profiles for a BDD.] + + Description [ ] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev Ranjan (rajeev@eecs.berkeley.edu) + Originally written by David Long. + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calPrintProfile.c,v 1.1.1.3 1998/05/04 00:59:01 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +static char profileWidth[] = "XXXXXXXXX"; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void CalBddPrintProfileAux(Cal_BddManager_t * bddManager, long * levelCounts, Cal_VarNamingFn_t varNamingProc, char * env, int lineLength, FILE * fp); +static void chars(char c, int n, FILE * fp); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Displays the node profile for f on fp. lineLength specifies + the maximum line length. varNamingFn is as in + Cal_BddPrintBdd.] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddPrintProfile(Cal_BddManager bddManager, + Cal_Bdd fUserBdd, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp) +{ + long *levelCounts; + + if (CalBddPreProcessing(bddManager, 1, fUserBdd) == 0){ + return; + } + levelCounts = Cal_MemAlloc(long, bddManager->numVars+1); + Cal_BddProfile(bddManager, fUserBdd, levelCounts, 1); + CalBddPrintProfileAux(bddManager, levelCounts, varNamingProc, env, + lineLength, fp); + Cal_MemFree(levelCounts); +} + +/**Function******************************************************************** + + Synopsis [Cal_BddPrintProfileMultiple is like Cal_BddPrintProfile except + it displays the profile for a set of BDDs] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddPrintProfileMultiple( + Cal_BddManager bddManager, + Cal_Bdd *userBdds, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp) +{ + long *levelCounts; + + if (CalBddArrayPreProcessing(bddManager, userBdds) == 0){ + return; + } + levelCounts = Cal_MemAlloc(long, bddManager->numVars+1); + Cal_BddProfileMultiple(bddManager, userBdds, levelCounts, 1); + CalBddPrintProfileAux(bddManager, levelCounts, varNamingProc, env, lineLength, fp); + Cal_MemFree(levelCounts); +} + + + +/**Function******************************************************************** + + Synopsis [Cal_BddPrintFunctionProfile is like Cal_BddPrintProfile except + it displays a function profile for f] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddPrintFunctionProfile(Cal_BddManager bddManager, + Cal_Bdd f, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp) +{ + long *levelCounts; + if (CalBddPreProcessing(bddManager, 1, f)){ + return; + } + levelCounts = Cal_MemAlloc(long, bddManager->numVars+1); + Cal_BddFunctionProfile(bddManager, f, levelCounts); + CalBddPrintProfileAux(bddManager, levelCounts, varNamingProc, env, + lineLength, fp); + Cal_MemFree(levelCounts); +} + + +/**Function******************************************************************** + + Synopsis [Cal_BddPrintFunctionProfileMultiple is like + Cal_BddPrintFunctionProfile except for multiple BDDs] + + Description [optional] + + SideEffects [None] + + SeeAlso [optional] + +******************************************************************************/ +void +Cal_BddPrintFunctionProfileMultiple(Cal_BddManager bddManager, + Cal_Bdd *userBdds, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp) +{ + long *levelCounts; + if (CalBddArrayPreProcessing(bddManager, userBdds) == 0){ + return; + } + levelCounts = Cal_MemAlloc(long, bddManager->numVars+1); + Cal_BddFunctionProfileMultiple(bddManager, userBdds, levelCounts); + CalBddPrintProfileAux(bddManager, levelCounts, varNamingProc, env, lineLength, fp); + Cal_MemFree(levelCounts); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Prints a profile to the file given by fp. The varNamingProc + is as in Cal_BddPrintBdd. lineLength gives the line width to scale + the profile to.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +CalBddPrintProfileAux( + Cal_BddManager_t * bddManager, + long * levelCounts, + Cal_VarNamingFn_t varNamingProc, + char * env, + int lineLength, + FILE * fp) +{ + long i, n; + int l; + char *name; + int maxPrefixLen; + int maxProfileWidth; + int histogramColumn; + int histogramWidth; + int profileScale; + long total; + + n = bddManager->numVars; + /* max_... initialized with values for leaf nodes */ + maxPrefixLen = 5; + maxProfileWidth = levelCounts[n]; + total = levelCounts[n]; + for(i = 0; i < n; i++){ + if(levelCounts[i]){ + sprintf(profileWidth, "%ld", levelCounts[i]); + l = strlen(CalBddVarName(bddManager, + bddManager->varBdds[bddManager->indexToId[i]], + varNamingProc, env)) + strlen((char *)profileWidth); + if(l > maxPrefixLen){ + maxPrefixLen = l; + } + if(levelCounts[i] > maxProfileWidth){ + maxProfileWidth = levelCounts[i]; + } + total += levelCounts[i]; + } + } + histogramColumn = maxPrefixLen+3; + histogramWidth = lineLength-histogramColumn-1; + if(histogramWidth < 20) + histogramWidth = 20; /* Random minimum width */ + if(histogramWidth >= maxProfileWidth){ + profileScale = 1; + } + else{ + profileScale = (maxProfileWidth+histogramWidth-1)/histogramWidth; + } + for(i = 0; i < n; ++i){ + if(levelCounts[i]){ + name = CalBddVarName(bddManager, + bddManager->varBdds[bddManager->indexToId[i]], + varNamingProc, env); + fputs(name, fp); + fputc(':', fp); + sprintf(profileWidth, "%ld", levelCounts[i]); + chars(' ', (int)(maxPrefixLen-strlen(name)-strlen(profileWidth)+1), fp); + fputs(profileWidth, fp); + fputc(' ', fp); + chars('#', levelCounts[i]/profileScale, fp); + fputc('\n', fp); + } + } + fputs("leaf:", fp); + sprintf(profileWidth, "%ld", levelCounts[n]); + chars(' ', (int)(maxPrefixLen-4-strlen(profileWidth)+1), fp); + fputs(profileWidth, fp); + fputc(' ', fp); + chars('#', levelCounts[n]/profileScale, fp); + fputc('\n', fp); + fprintf(fp, "Total: %ld\n", total); +} + +/**Function******************************************************************** + + Synopsis [] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +chars( + char c, + int n, + FILE * fp) +{ + int i; + + for(i = 0; i < n; ++i){ + fputc(c, fp); + } +} + + + + + + + + + + + + diff --git a/calQuant.c b/calQuant.c new file mode 100644 index 0000000..09f50f3 --- /dev/null +++ b/calQuant.c @@ -0,0 +1,1492 @@ +/**CFile*********************************************************************** + + FileName [calQuant.c] + + PackageName [cal] + + Synopsis [Routines for existential/universal quantification and + relational product.] + + Description [] + + SeeAlso [None] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calQuant.c,v 1.1.1.4 1998/05/04 00:59:02 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +#define DEFAULT_EXIST_HASH_TABLE_SIZE_INDEX 4 +#define DEFAULT_EXIST_HASH_TABLE_SIZE 16 + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t BddExistsStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, unsigned short opCode, CalAssociation_t *association); +static Cal_Bdd_t BddRelProdStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, unsigned short opCode, CalAssociation_t *assoc); +static Cal_Bdd_t BddDFStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, CalOpProc_t calOpProc, unsigned short opCode); +static void HashTableApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** reqQueAtPipeDepth, CalOpProc_t calOpProc, unsigned long opCode); +static void HashTableReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t * uniqueTableForId); +static void BddExistsApply(Cal_BddManager_t *bddManager, int quantifying, CalHashTable_t *existHashTable, CalHashTable_t **existHashTableArray, CalOpProc1_t calOpProc, unsigned short opCode, CalAssociation_t *assoc); +static void BddExistsBFAux(Cal_BddManager_t *bddManager, int minIndex, CalHashTable_t **existHashTableArray, CalHashTable_t **orHashTableArray, CalOpProc1_t calOpProc, unsigned short opCode, CalAssociation_t *assoc); +static void BddExistsReduce(Cal_BddManager_t *bddManager, CalHashTable_t *existHashTable, CalHashTable_t **existHashTableArray, CalHashTable_t **orHashTableArray, unsigned short opCode, CalAssociation_t *association); +static Cal_Bdd_t BddExistsBFPlusDF(Cal_BddManager_t *bddManager, Cal_Bdd_t f, unsigned short opCode, CalAssociation_t *association); +static void BddRelProdApply(Cal_BddManager_t *bddManager, int quantifying, CalHashTable_t *relProdHashTable, CalHashTable_t **relProdHashTableArray, CalHashTable_t **andHashTableArray, CalOpProc_t calOpProc, unsigned short opCode, CalAssociation_t *assoc); +static void BddRelProdReduce(Cal_BddManager_t *bddManager, CalHashTable_t *relProdHashTable, CalHashTable_t **relProdHashTableArray, CalHashTable_t **andHashTableArray, CalHashTable_t **orHashTableArray, unsigned short opCode, CalAssociation_t *assoc); +static void BddRelProdBFAux(Cal_BddManager_t *bddManager, int minIndex, CalHashTable_t **relProdHashTableArray, CalHashTable_t **andHashTableArray, CalHashTable_t **orHashTableArray, unsigned short opCode, CalAssociation_t *assoc); +static Cal_Bdd_t BddRelProdBFPlusDF(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, unsigned short opCode, CalAssociation_t *association); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the result of existentially quantifying some + variables from the given BDD.] + + Description [Returns the BDD for f with all the variables that are + paired with something in the current variable association + existentially quantified out.] + + SideEffects [None.] + + SeeAlso [Cal_BddRelProd] + +******************************************************************************/ +Cal_Bdd +Cal_BddExists(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + + if (CalBddPreProcessing(bddManager, 1, fUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + CalAssociation_t *assoc = bddManager->currentAssociation; + unsigned short opCode; + + if (assoc->id == -1){ + opCode = bddManager->tempOpCode--; + } + else { + opCode = CAL_OP_QUANT + assoc->id; + } + if (bddManager->numNodes <= CAL_LARGE_BDD){ + /* If number of nodes is small, call depth first routine. */ + result = BddExistsStep(bddManager, f, opCode, assoc); + } + else { + result = BddExistsBFPlusDF(bddManager, f, opCode, assoc); + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; + } + return (Cal_Bdd) 0; +} + + +/**Function******************************************************************** + + Synopsis [Returns the result of taking the logical AND of the + argument BDDs and existentially quantifying some variables from the + product.] + + Description [Returns the BDD for the logical AND of f and g with all + the variables that are paired with something in the current variable + association existentially quantified out.] + + SideEffects [None.] + +******************************************************************************/ +Cal_Bdd +Cal_BddRelProd(Cal_BddManager bddManager, Cal_Bdd fUserBdd, Cal_Bdd gUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + + if (CalBddPreProcessing(bddManager, 2, fUserBdd, gUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + Cal_Bdd_t g = CalBddGetInternalBdd(bddManager, gUserBdd); + CalAssociation_t *assoc = bddManager->currentAssociation; + unsigned short opCode; + + if (bddManager->currentAssociation->id == -1){ + opCode = bddManager->tempOpCode--; + bddManager->tempOpCode--; + } + else { + opCode = CAL_OP_REL_PROD + assoc->id; + } + if (bddManager->numNodes <= CAL_LARGE_BDD){ + /* If number of nodes is small, call depth first routine. */ + result = BddRelProdStep(bddManager, f, g, opCode, assoc); + } + else { + result = BddRelProdBFPlusDF(bddManager, f, g, opCode, assoc); + } + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; + } + return (Cal_Bdd) 0; +} + +/**Function******************************************************************** + + Synopsis [Returns the result of universally quantifying some + variables from the given BDD.] + + Description [Returns the BDD for f with all the variables that are + paired with something in the current variable association + universally quantified out.] + + SideEffects [None.] + +******************************************************************************/ +Cal_Bdd +Cal_BddForAll(Cal_BddManager bddManager, Cal_Bdd fUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + + if (CalBddPreProcessing(bddManager, 1, fUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + CalAssociation_t *assoc = bddManager->currentAssociation; + unsigned short opCode; + + CalBddNot(f, f); + if (assoc->id == -1){ + opCode = bddManager->tempOpCode--; + } + else { + opCode = CAL_OP_QUANT + assoc->id; + } + if (bddManager->numNodes <= CAL_LARGE_BDD){ + /* If number of nodes is small, call depth first routine. */ + result = BddExistsStep(bddManager, f, opCode, assoc); + } + else { + result = BddExistsBFPlusDF(bddManager, f, opCode, assoc); + } + CalBddNot(result, result); + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; + } + return (Cal_Bdd) 0; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpExists(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t * + resultBddPtr) +{ + if (((int)bddManager->idToIndex[CalBddGetBddId(f)]) > + bddManager->currentAssociation->lastBddIndex){ + *resultBddPtr = f; + return 1; + } + return 0; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpRelProd(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, + Cal_Bdd_t * resultBddPtr) +{ + if (CalBddIsBddZero(bddManager, f) || CalBddIsBddZero(bddManager, g) || + CalBddIsComplementEqual(f, g)){ + *resultBddPtr = bddManager->bddZero; + return 1; + } + else if (CalBddIsBddOne(bddManager, f) && CalBddIsBddOne(bddManager, g)){ + *resultBddPtr = bddManager->bddOne; + return 1; + } + return 0; +} +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddExistsStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, unsigned + short opCode, CalAssociation_t *association) +{ + Cal_Bdd_t temp1, temp2; + Cal_Bdd_t f1, f2; + Cal_Bdd_t result; + Cal_BddId_t topId; + int quantifying; + + if (((int)CalBddGetBddIndex(bddManager, f)) > association->lastBddIndex){ + return f; + } + if (CalCacheTableOneLookup(bddManager, f, opCode, &result)){ + return result; + } + + topId = CalBddGetBddId(f); + quantifying = (CalBddIsBddNull(bddManager, + association->varAssociation[topId]) ? 0 : 1); + CalBddGetCofactors(f, topId, f1, f2); + temp1 = BddExistsStep(bddManager, f1, opCode, association); + if (quantifying && CalBddIsEqual(temp1, bddManager->bddOne)){ + result=temp1; + } + else { + temp2 = BddExistsStep(bddManager, f2, opCode, association); + if (quantifying){ + CalBddNot(temp1, temp1); + CalBddNot(temp2, temp2); + result = BddDFStep(bddManager, temp1, temp2, CalOpNand, CAL_OP_NAND); + } + else { + Cal_BddId_t id = CalBddGetBddId(f); + if (CalUniqueTableForIdFindOrAdd(bddManager, bddManager->uniqueTable[id], + temp1, temp2, &result) == 0){ + CalBddIcrRefCount(temp1); + CalBddIcrRefCount(temp2); + } + } + } + CalCacheTableOneInsert(bddManager, f, result, opCode, 0); + return (result); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddRelProdStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t + g, unsigned short opCode, CalAssociation_t *assoc) +{ + Cal_BddId_t topId; + Cal_Bdd_t f1, f2, g1, g2; + Cal_Bdd_t temp1, temp2; + Cal_Bdd_t result; + int quantifying; + + if (CalBddIsBddConst(f) || CalBddIsBddConst(g)){ + if (CalBddIsBddZero(bddManager, f) || CalBddIsBddZero(bddManager, g)){ + return bddManager->bddZero; + } + if (assoc->id != -1){ + opCode = CAL_OP_QUANT+assoc->id; + } + else{ + opCode--; + } + if (CalBddIsBddOne(bddManager, f)){ + return (BddExistsStep(bddManager, g, opCode, assoc)); + } + return (BddExistsStep(bddManager, f, opCode, assoc)); + } + if ((((int)CalBddGetBddIndex(bddManager, f)) > assoc->lastBddIndex) && + (((int)CalBddGetBddIndex(bddManager, g)) > assoc->lastBddIndex)){ + result = BddDFStep(bddManager, f, g, CalOpNand, CAL_OP_NAND); + CalBddNot(result, result); + return result; + } + if(CalOpRelProd(bddManager, f, g, &result) == 1){ + return result; + } + CalBddNormalize(f, g); + if(CalCacheTableTwoLookup(bddManager, f, g, opCode, &result)){ + return result; + } + CalBddGetMinId2(bddManager, f, g, topId); + + quantifying = (CalBddIsBddNull(bddManager, assoc->varAssociation[topId]) ? 0 + : 1); + CalBddGetCofactors(f, topId, f1, f2); + CalBddGetCofactors(g, topId, g1, g2); + + temp1 = BddRelProdStep(bddManager, f1, g1, opCode, assoc); + if (quantifying && CalBddIsBddOne(bddManager, temp1)){ + result=temp1; + } + else { + temp2 = BddRelProdStep(bddManager, f2, g2, opCode, assoc); + if (quantifying) { + CalBddNot(temp1, temp1); + CalBddNot(temp2, temp2); + result = BddDFStep(bddManager, temp1, temp2, CalOpNand, CAL_OP_NAND); + /*result = BddDFStep(bddManager, temp1, temp2, CalOpOr, CAL_OP_OR);*/ + } + else { + if (CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[topId], + temp1, temp2, &result) == 0){ + CalBddIcrRefCount(temp1); + CalBddIcrRefCount(temp2); + } + } + } + CalCacheTableTwoInsert(bddManager, f, g, result, opCode, 0); + return (result); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddDFStep(Cal_BddManager_t * bddManager, Cal_Bdd_t f, Cal_Bdd_t g, + CalOpProc_t calOpProc, unsigned short opCode) +{ + Cal_BddId_t topId; + Cal_Bdd_t temp1, temp2, fx, fxbar, gx, gxbar; + Cal_Bdd_t result; + + if((*calOpProc)(bddManager, f, g, &result) == 1){ + return result; + } + CalBddNormalize(f, g); + if(CalCacheTableTwoLookup(bddManager, f, g, opCode, &result)){ + return result; + } + CalBddGetMinId2(bddManager, f, g, topId); + CalBddGetCofactors(f, topId, fx, fxbar); + CalBddGetCofactors(g, topId, gx, gxbar); + temp1 = BddDFStep(bddManager, fx, gx, calOpProc, opCode); + temp2 = BddDFStep(bddManager, fxbar, gxbar, calOpProc, opCode); + + if (CalUniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[topId], + temp1, temp2, &result) == 0){ + CalBddIcrRefCount(temp1); + CalBddIcrRefCount(temp2); + } + CalCacheTableTwoInsert(bddManager, f, g, result, opCode, 0); + return (result); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, + CalHashTable_t ** reqQueAtPipeDepth, CalOpProc_t calOpProc, + unsigned long opCode) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_Bdd_t fx, gx, fxbar, gxbar, result; + Cal_BddId_t bddId; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetCofactors(bddManager, requestNode, fx, fxbar, gx, gxbar); + CalBddNormalize(fx, gx); + if((*calOpProc)(bddManager, fx, gx, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fx, gx, opCode, &result) == 0){ + CalBddGetMinId2(bddManager, fx, gx, bddId); + CalHashTableFindOrAdd(reqQueAtPipeDepth[bddId], fx, gx, &result); + CalCacheTableTwoInsert(bddManager, fx, gx, result, opCode, 1); + } + else { + CalRequestIsForwardedTo(result); + } + } + CalBddIcrRefCount(result); + CalRequestNodePutThenRequest(requestNode, result); + CalBddNormalize(fxbar, gxbar); + if((*calOpProc)(bddManager, fxbar, gxbar, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fxbar, gxbar, opCode, &result) + == 0){ + CalBddGetMinId2(bddManager, fxbar, gxbar, bddId); + CalHashTableFindOrAdd(reqQueAtPipeDepth[bddId], fxbar, gxbar, + &result); + CalCacheTableTwoInsert(bddManager, fxbar, gxbar, result, + opCode, 1); + } + else { + CalRequestIsForwardedTo(result); + } + } + CalBddIcrRefCount(result); + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, + CalHashTable_t * uniqueTableForId) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + Cal_BddId_t currentBddId = uniqueTableForId->bddId; + CalNodeManager_t *nodeManager = uniqueTableForId->nodeManager; + CalRequestNode_t *requestNode, *next; + CalBddNode_t *bddNode, *endNode; + Cal_Bdd_t thenBdd, elseBdd, result; + Cal_BddRefCount_t refCount; + + /*requestNodeList = hashTable->requestNodeList;*/ + endNode = hashTable->endNode; + hashTable->numEntries = 0; + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalUniqueTableForIdLookup(bddManager, uniqueTableForId, + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequest(requestNode, elseBdd); + CalHashTableAddDirect(uniqueTableForId, requestNode); + bddManager->numNodes++; + bddManager->gcCheck--; + } + else{ + CalNodeManagerAllocNode(nodeManager, bddNode); + CalBddNodePutThenBddId(bddNode, CalBddGetBddId(thenBdd)); + CalBddNodePutThenBddNode(bddNode, CalBddGetBddNodeNot(thenBdd)); + CalBddNodePutElseBddId(bddNode, CalBddGetBddId(elseBdd)); + CalBddNodePutElseBddNode(bddNode, CalBddGetBddNodeNot(elseBdd)); + /* + CalNodeManagerInitBddNode(nodeManager, thenBdd, elseBdd, + Cal_Nil(CalBddNode_t), bddNode); + */ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(uniqueTableForId, bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, currentBddId); + CalRequestNodePutThenRequestNode(requestNode, CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + } + /* hashTable->requestNodeList = requestNodeList; */ + hashTable->endNode = endNode; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExistsApply(Cal_BddManager_t *bddManager, int quantifying, + CalHashTable_t *existHashTable, CalHashTable_t + **existHashTableArray, CalOpProc1_t calOpProc, + unsigned short opCode, CalAssociation_t *assoc) +{ + int i, numBins = existHashTable->numBins; + CalBddNode_t **bins = existHashTable->bins; + CalRequestNode_t *requestNode; + Cal_Bdd_t f, fx, fxbar, result, resultBar; + int lastBddIndex = assoc->lastBddIndex; + + if (quantifying){ + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, f); + CalBddGetThenBdd(f, fx); + CalBddGetElseBdd(f, fxbar); + + /*if(calOpProc(bddManager, fx, &result) == 0){*/ + if (((int)bddManager->idToIndex[CalBddGetBddId(fx)]) <= lastBddIndex){ + if (CalCacheTableOneLookup(bddManager, fx, opCode, &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(existHashTableArray[CalBddGetBddId(fx)], fx, + bddManager->bddOne, &result); + CalCacheTableOneInsert(bddManager, fx, result, + opCode, 1); + } + } + else { + result = fx; + } + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequest(requestNode, fxbar); + } + } + } + else { + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, f); + CalBddGetThenBdd(f, fx); + CalBddGetElseBdd(f, fxbar); + + if (((int)bddManager->idToIndex[CalBddGetBddId(fx)]) <= lastBddIndex){ + if (CalCacheTableOneLookup(bddManager, fx, opCode, &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(existHashTableArray[CalBddGetBddId(fx)], fx, + bddManager->bddOne, &result); + CalCacheTableOneInsert(bddManager, fx, result, + opCode, 1); + } + } + else { + result = fx; + } + CalRequestNodePutThenRequest(requestNode, result); + CalBddIcrRefCount(result); + /*if(calOpProc(bddManager, fxbar, &resultBar) == 0){*/ + if (((int)bddManager->idToIndex[CalBddGetBddId(fxbar)]) <= lastBddIndex){ + if (CalCacheTableOneLookup(bddManager, fxbar, opCode, + &resultBar)){ + CalRequestIsForwardedTo(resultBar); + } + else { + CalHashTableFindOrAdd(existHashTableArray[CalBddGetBddId(fxbar)], fxbar, + bddManager->bddOne, &resultBar); + CalCacheTableOneInsert(bddManager, fxbar, resultBar, + opCode, 1); + } + } + else{ + resultBar = fxbar; + } + CalBddIcrRefCount(resultBar); + CalRequestNodePutElseRequest(requestNode, resultBar); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExistsBFAux(Cal_BddManager_t *bddManager, int minIndex, + CalHashTable_t **existHashTableArray, CalHashTable_t + **orHashTableArray, CalOpProc1_t calOpProc, unsigned + short opCode, CalAssociation_t *assoc) +{ + int index; + Cal_BddId_t bddId; + int quantifying; + + /* Apply phase */ + for (index = minIndex; index < bddManager->numVars; index++){ + bddId = bddManager->indexToId[index]; + if (existHashTableArray[bddId]->numEntries){ + quantifying = (CalBddIsBddNull(bddManager, + assoc->varAssociation[bddId]) ? 0 : 1); + BddExistsApply(bddManager, quantifying, + existHashTableArray[bddId], existHashTableArray, + calOpProc, opCode, assoc); + } + } + + /* Reduce phase */ + for (index = bddManager->numVars-1; index >= minIndex; index--){ + bddId = bddManager->indexToId[index]; + if (existHashTableArray[bddId]->numEntries){ + quantifying = (CalBddIsBddNull(bddManager, + assoc->varAssociation[bddId]) ? 0 : 1); + if (quantifying){ + BddExistsReduce(bddManager, existHashTableArray[bddId], + existHashTableArray, orHashTableArray, + opCode, assoc); + } + else { + HashTableReduce(bddManager, existHashTableArray[bddId], + bddManager->uniqueTable[bddId]); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExistsReduce(Cal_BddManager_t *bddManager, CalHashTable_t + *existHashTable, CalHashTable_t **existHashTableArray, + CalHashTable_t **orHashTableArray, unsigned short + opCode, CalAssociation_t *association) +{ + int i, numBins = existHashTable->numBins; + CalBddNode_t **bins = existHashTable->bins; + CalRequestNode_t *requestNode, *next, *requestNodeListAux; + CalBddNode_t *endNode; + + int bddIndex; + /*Cal_BddIndex_t minIndex, elseIndex;*/ + int minIndex, elseIndex; + Cal_BddId_t bddId, minId; + Cal_Bdd_t thenBdd, elseBdd, result, orResult; + Cal_BddRefCount_t refCount; + int lastBddIndex = association->lastBddIndex; + + + /* For those nodes which get processed in the first pass */ + /* requestNodeList = existHashTable->requestNodeList; */ + endNode = existHashTable->endNode; + + /* For the other ones. This list is merged with the requestNodeList + * after processing is complete. + */ + requestNodeListAux = Cal_Nil(CalRequestNode_t); + existHashTable->numEntries = 0; + + minIndex = bddManager->numVars; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(thenBdd); + CalRequestNodePutThenRequest(requestNode, thenBdd); + if (CalBddIsBddOne(bddManager, thenBdd)){ + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + continue; + } + + CalRequestNodePutNextRequestNode(requestNode, requestNodeListAux); + requestNodeListAux = requestNode; + + /*if(CalOpExists(bddManager, elseBdd, &result) == 0){*/ + if (((int)bddManager->idToIndex[CalBddGetBddId(elseBdd)]) <= lastBddIndex){ + if (CalCacheTableOneLookup(bddManager, elseBdd, opCode, + &result)){ + CalRequestIsForwardedTo(result); + } + else{ + CalHashTableFindOrAdd(existHashTableArray[CalBddGetBddId(elseBdd)], elseBdd, + bddManager->bddOne, &result); + CalCacheTableOneInsert(bddManager, elseBdd, result, + opCode, 1); + if (minIndex > (elseIndex = CalBddGetBddIndex(bddManager, + elseBdd))){ + minIndex = elseIndex; + } + } + } + else{ + result = elseBdd; + } + CalRequestNodePutElseRequest(requestNode, result); + } + } + + if (!requestNodeListAux){ + /* requestNodeList = requestNodeList; */ + existHashTable->endNode = endNode; + return; + } + + BddExistsBFAux(bddManager, minIndex, existHashTableArray, + orHashTableArray, CalOpExists, opCode, association); + minIndex = bddManager->numVars; + for (requestNode = requestNodeListAux; requestNode; requestNode = next){ + Cal_Bdd_t thenResult, elseResult; + Cal_BddIndex_t orResultIndex; + + next = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetThenRequest(requestNode, thenResult); + CalRequestNodeGetElseRequest(requestNode, elseResult); + CalRequestIsForwardedTo(elseResult); + if (CalOpOr(bddManager, thenResult, elseResult, &orResult) == 0){ + CalBddNormalize(thenResult, elseResult); + CalBddNot(thenResult, thenResult); + CalBddNot(elseResult, elseResult); + if (CalCacheTableTwoLookup(bddManager, thenResult,elseResult, + CAL_OP_NAND, &orResult)){ + CalRequestIsForwardedTo(orResult); + } + else { + CalBddGetMinIdAndMinIndex(bddManager, thenResult, elseResult, + minId, orResultIndex); + CalHashTableFindOrAdd(orHashTableArray[minId], thenResult, elseResult, + &orResult); + CalCacheTableTwoInsert(bddManager, thenResult, elseResult, orResult, + CAL_OP_NAND, 1); + if (minIndex > orResultIndex) minIndex = orResultIndex; + } + } + CalRequestNodePutThenRequest(requestNode, orResult); + } + + + /* Call "OR" apply and reduce */ + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + if(orHashTableArray[bddId]->numEntries){ + HashTableApply(bddManager, orHashTableArray[bddId], orHashTableArray, + CalOpNand, CAL_OP_NAND); + } + } + + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + CalHashTable_t *uniqueTableForId; + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + if(orHashTableArray[bddId]->numEntries){ + HashTableReduce(bddManager, orHashTableArray[bddId], uniqueTableForId); + } + } + + for (requestNode = requestNodeListAux; requestNode; requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetThenRequest(requestNode, result); + CalRequestIsForwardedTo(result); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + /*existHashTable->requestNodeList = requestNodeList;*/ + existHashTable->endNode = endNode; + +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddExistsBFPlusDF(Cal_BddManager_t *bddManager, Cal_Bdd_t f, unsigned + short opCode, CalAssociation_t *association) +{ + Cal_BddId_t fId = CalBddGetBddId(f); + Cal_BddIndex_t bddIndex; + Cal_BddId_t bddId; + + Cal_BddIndex_t fIndex = bddManager->idToIndex[fId]; + CalHashTable_t **orHashTableArray = bddManager->reqQue[4]; + CalHashTable_t **existHashTableArray = bddManager->reqQue[5]; + Cal_Bdd_t result; + + if (CalOpExists(bddManager, f, &result) == 1){ + return result; + } + + if (CalCacheTableOneLookup(bddManager, f, opCode, &result)){ + return result; + } + + /* + * Change the size of the exist hash table to min. size + */ + for (bddIndex = fIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + existHashTableArray[bddId]->sizeIndex = + DEFAULT_EXIST_HASH_TABLE_SIZE_INDEX; + existHashTableArray[bddId]->numBins = DEFAULT_EXIST_HASH_TABLE_SIZE; + Cal_MemFree(existHashTableArray[bddId]->bins); + existHashTableArray[bddId]->bins = Cal_MemAlloc(CalBddNode_t*, + DEFAULT_EXIST_HASH_TABLE_SIZE); + memset((char *)existHashTableArray[bddId]->bins, 0, + existHashTableArray[bddId]->numBins*sizeof(CalBddNode_t*)); + } + + CalHashTableFindOrAdd(existHashTableArray[fId], f, bddManager->bddOne, + &result); + + + BddExistsBFAux(bddManager, fIndex, existHashTableArray, orHashTableArray, + CalOpExists, opCode, association); + + CalRequestIsForwardedTo(result); + + CalCacheTableTwoFixResultPointers(bddManager); + CalCacheTableOneInsert(bddManager, f, result, opCode, 0); + for (bddIndex = fIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(existHashTableArray[bddId]); + CalHashTableCleanUp(orHashTableArray[bddId]); + } + return result; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddRelProdApply(Cal_BddManager_t *bddManager, int quantifying, CalHashTable_t + *relProdHashTable, CalHashTable_t **relProdHashTableArray, + CalHashTable_t **andHashTableArray, CalOpProc_t + calOpProc, unsigned short opCode, CalAssociation_t *assoc) +{ + int i, numBins = relProdHashTable->numBins; + CalBddNode_t **bins = relProdHashTable->bins; + Cal_BddId_t minId; + CalRequestNode_t *requestNode; + Cal_Bdd_t fx, fxbar, gx, gxbar, result, resultBar; + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetCofactors(bddManager, requestNode, fx, fxbar, gx, gxbar); + CalBddNormalize(fx, gx); + CalBddGetMinIdAndMinIndex(bddManager, fx, gx, minId, minIndex); + if (minIndex > assoc->lastBddIndex){ + if (CalOpAnd(bddManager, fx, gx, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fx, gx, CAL_OP_NAND, + &result)){ + CalRequestIsForwardedTo(result); + } + else{ + CalHashTableFindOrAdd(andHashTableArray[minId], fx, gx, &result); + CalCacheTableTwoInsert(bddManager, fx, gx, result, + CAL_OP_NAND, 1); + } + CalBddNot(result, result); + } + } + else { + if(calOpProc(bddManager, fx, gx, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fx, gx, opCode, + &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(relProdHashTableArray[minId], fx, gx, + &result); + CalCacheTableTwoInsert(bddManager, fx, gx, result, opCode, 1); + } + } + } + CalRequestNodePutThenRequest(requestNode, result); + if (quantifying){ + Cal_Bdd_t elseRequest; + Cal_BddId_t elseRequestId; + CalBddNode_t *elseRequestNode; + + CalBddGetMinId2(bddManager, fxbar, gxbar, elseRequestId); + CalNodeManagerInitBddNode(bddManager->nodeManagerArray[elseRequestId], + fxbar, gxbar, Cal_Nil(CalBddNode_t), + elseRequestNode); + /* + CalNodeManagerAllocNode(bddManager->nodeManagerArray[elseRequestId], + elseRequestNode); + CalRequestNodePutF(elseRequestNode, fxbar); + CalRequestNodePutG(elseRequestNode, gxbar); + */ + CalRequestPutRequestId(elseRequest, elseRequestId); + CalRequestPutRequestNode(elseRequest, elseRequestNode); + CalRequestNodePutElseRequest(requestNode, elseRequest); + } + else { + CalBddIcrRefCount(result); + CalBddNormalize(fxbar, gxbar); + CalBddGetMinIdAndMinIndex(bddManager, fxbar, gxbar, minId, minIndex); + if (minIndex > assoc->lastBddIndex){ + if (CalOpAnd(bddManager, fxbar, gxbar, &resultBar) == 0){ + if( CalCacheTableTwoLookup(bddManager, fxbar, gxbar, + CAL_OP_NAND, &resultBar)){ + CalRequestIsForwardedTo(resultBar); + } + else{ + CalHashTableFindOrAdd(andHashTableArray[minId], fxbar, gxbar, + &resultBar); + CalCacheTableTwoInsert(bddManager, fxbar, gxbar, resultBar, + CAL_OP_NAND, 1); + } + CalBddNot(resultBar, resultBar); + } + } + else { + if(calOpProc(bddManager, fxbar, gxbar, &resultBar) == 0){ + if (CalCacheTableTwoLookup(bddManager, fxbar, gxbar, opCode, + &resultBar)){ + CalRequestIsForwardedTo(resultBar); + } + else { + CalHashTableFindOrAdd(relProdHashTableArray[minId], + fxbar, gxbar, &resultBar); + CalCacheTableTwoInsert(bddManager, fxbar, gxbar, + resultBar, opCode, 1); + } + } + } + CalBddIcrRefCount(resultBar); + CalRequestNodePutElseRequest(requestNode, resultBar); + } + } + } +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddRelProdReduce(Cal_BddManager_t *bddManager, CalHashTable_t + *relProdHashTable, CalHashTable_t + **relProdHashTableArray, CalHashTable_t + **andHashTableArray, CalHashTable_t + **orHashTableArray, unsigned short opCode, + CalAssociation_t *assoc) +{ + int i, numBins = relProdHashTable->numBins; + CalBddNode_t **bins = relProdHashTable->bins; + CalRequestNode_t *requestNode, *next, *requestNodeListAux; + CalBddNode_t *elseRequestNode; + int bddIndex; + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + Cal_BddId_t bddId, minId, elseRequestId; + Cal_Bdd_t thenBdd, elseBdd, result, orResult; + Cal_BddRefCount_t refCount; + Cal_Bdd_t fxbar, gxbar; + CalBddNode_t *endNode; + + + /* For those nodes which get processed in the first pass */ + /*requestNodeList = relProdHashTable->requestNodeList;*/ + endNode = relProdHashTable->endNode; + + /* For the other ones. This list is merged with the requestNodeList + * after processing is complete. + */ + requestNodeListAux = Cal_Nil(CalRequestNode_t); + + minIndex = bddManager->numVars; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestIsForwardedTo(thenBdd); + /*CalRequestNodePutThenRequest(requestNode, thenBdd);*/ + CalRequestNodeGetElseRequest(requestNode, elseBdd); + CalRequestIsForwardedTo(elseBdd); + CalRequestGetF(elseBdd, fxbar); + CalRequestGetG(elseBdd, gxbar); + + /* Free the else request node because it is not needed */ + elseRequestNode = CalRequestNodeGetElseRequestNode(requestNode); + elseRequestId = CalRequestNodeGetElseRequestId(requestNode); + CalNodeManagerFreeNode(bddManager->nodeManagerArray[elseRequestId], + elseRequestNode); + if (CalBddIsBddOne(bddManager, thenBdd)){ + CalRequestNodePutThenRequest(requestNode, bddManager->bddOne); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + continue; + } + + CalRequestNodePutNextRequestNode(requestNode, requestNodeListAux); + requestNodeListAux = requestNode; + + CalBddGetMinIdAndMinIndex(bddManager, fxbar, gxbar, bddId, bddIndex); + CalBddNormalize(fxbar, gxbar); + if (bddIndex > assoc->lastBddIndex){ + if (CalOpAnd(bddManager, fxbar, gxbar, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fxbar, gxbar, + CAL_OP_NAND, &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(andHashTableArray[bddId], fxbar, + gxbar, &result); + CalCacheTableTwoInsert(bddManager, fxbar, gxbar, result, + CAL_OP_NAND, 1); + if (minIndex > bddIndex) minIndex = bddIndex; + } + CalBddNot(result, result); + } + } + else { + if(CalOpRelProd(bddManager, fxbar, gxbar, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, fxbar, gxbar, opCode, + &result)){ + CalRequestIsForwardedTo(result); + } + else { + CalHashTableFindOrAdd(relProdHashTableArray[bddId], fxbar, gxbar, + &result); + CalCacheTableTwoInsert(bddManager, fxbar, gxbar, result, + opCode, 1); + if (minIndex > bddIndex) minIndex = bddIndex; + } + } + } + CalRequestNodePutElseRequest(requestNode, result); + } + } + + if (!requestNodeListAux){ + /*relProdHashTable->requestNodeList = requestNodeList;*/ + relProdHashTable->endNode = endNode; + return; + } + + BddRelProdBFAux(bddManager, minIndex, relProdHashTableArray, + andHashTableArray, orHashTableArray, opCode, assoc); + + minIndex = bddManager->numVars; + for (requestNode = requestNodeListAux; requestNode; requestNode = next){ + Cal_Bdd_t thenResult, elseResult; + Cal_BddIndex_t orResultIndex; + + next = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetThenRequest(requestNode, thenResult); + CalRequestNodeGetElseRequest(requestNode, elseResult); + CalRequestIsForwardedTo(elseResult); + CalRequestIsForwardedTo(thenResult); + CalBddNormalize(thenResult, elseResult); + if (CalOpOr(bddManager, thenResult, elseResult, &orResult) == 0){ + CalBddNot(thenResult, thenResult); + CalBddNot(elseResult, elseResult); + if (CalCacheTableTwoLookup(bddManager, thenResult, elseResult, + CAL_OP_NAND, &orResult)){ + CalRequestIsForwardedTo(orResult); + } + else { + CalBddGetMinIdAndMinIndex(bddManager, thenResult, elseResult, + minId, orResultIndex); + CalHashTableFindOrAdd(orHashTableArray[minId], thenResult, elseResult, + &orResult); + CalCacheTableTwoInsert(bddManager, thenResult, elseResult, orResult, + CAL_OP_NAND, 1); + if (minIndex > orResultIndex) minIndex = orResultIndex; + } + } + CalRequestNodePutThenRequest(requestNode, orResult); + } + + /* Call "OR" apply and reduce */ + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + if(orHashTableArray[bddId]->numEntries){ + HashTableApply(bddManager, orHashTableArray[bddId], orHashTableArray, + CalOpNand, CAL_OP_NAND); + } + } + + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + CalHashTable_t *uniqueTableForId; + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + if(orHashTableArray[bddId]->numEntries){ + HashTableReduce(bddManager, orHashTableArray[bddId], uniqueTableForId); + } + } + for (requestNode = requestNodeListAux; requestNode; requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetThenRequest(requestNode, result); + CalRequestIsForwardedTo(result); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + /* + ** CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + ** requestNodeList = requestNode; + */ + /*CalRequestNodePutNextRequestNode(endNode, requestNode);*/ + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + + /*relProdHashTable->requestNodeList = requestNodeList;*/ + relProdHashTable->endNode = endNode; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddRelProdBFAux(Cal_BddManager_t *bddManager, int minIndex, + CalHashTable_t **relProdHashTableArray, CalHashTable_t + **andHashTableArray, CalHashTable_t + **orHashTableArray, unsigned short opCode, + CalAssociation_t *assoc) +{ + Cal_BddIndex_t bddIndex; + int quantifying; + int index; + Cal_BddId_t bddId; + CalHashTable_t *hashTable; + + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = andHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableApply(bddManager, hashTable, andHashTableArray, CalOpNand, + CAL_OP_NAND); + } + hashTable = relProdHashTableArray[bddId]; + if(hashTable->numEntries){ + quantifying = (CalBddIsBddNull(bddManager, + assoc->varAssociation[bddId]) ? 0 : 1); + BddRelProdApply(bddManager, quantifying, hashTable, + relProdHashTableArray, andHashTableArray, + CalOpRelProd, opCode, assoc); + } + } + + /* Reduce phase */ + for (index = bddManager->numVars-1; index >= minIndex; index--){ + CalHashTable_t *uniqueTableForId; + bddId = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = andHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableReduce(bddManager, hashTable, uniqueTableForId); + } + if (relProdHashTableArray[bddId]->numEntries){ + quantifying = (CalBddIsBddNull(bddManager, + assoc->varAssociation[bddId]) ? 0 : 1); + if (quantifying){ + BddRelProdReduce(bddManager, relProdHashTableArray[bddId], + relProdHashTableArray, andHashTableArray, + orHashTableArray, opCode, assoc); + } + else { + HashTableReduce(bddManager, relProdHashTableArray[bddId], + bddManager->uniqueTable[bddId]); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddRelProdBFPlusDF(Cal_BddManager_t * bddManager, Cal_Bdd_t f, + Cal_Bdd_t g, unsigned short opCode, + CalAssociation_t *association) +{ + Cal_Bdd_t result; + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + int bddIndex; + CalHashTable_t **andHashTableArray = bddManager->reqQue[3]; + CalHashTable_t **relProdHashTableArray = bddManager->reqQue[4]; + CalHashTable_t **orHashTableArray = bddManager->reqQue[5]; + Cal_BddId_t bddId, minId; + + if(CalOpRelProd(bddManager, f, g, &result) == 1){ + return result; + } + CalBddNormalize(f, g); + if(CalCacheTableTwoLookup(bddManager, f, g, opCode, &result)){ + return result; + } + + CalBddGetMinIdAndMinIndex(bddManager, f, g, minId, minIndex); + + /* + * Change the size of the exist hash table to min. size + */ + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + relProdHashTableArray[bddId]->sizeIndex = + DEFAULT_EXIST_HASH_TABLE_SIZE_INDEX; + relProdHashTableArray[bddId]->numBins = DEFAULT_EXIST_HASH_TABLE_SIZE; + Cal_MemFree(relProdHashTableArray[bddId]->bins); + relProdHashTableArray[bddId]->bins = Cal_MemAlloc(CalBddNode_t*, + DEFAULT_EXIST_HASH_TABLE_SIZE); + memset((char *)relProdHashTableArray[bddId]->bins, 0, + relProdHashTableArray[bddId]->numBins*sizeof(CalBddNode_t*)); + } + + if (minIndex > association->lastBddIndex) { + if (CalOpAnd(bddManager, f, g, &result) == 0){ + if (CalCacheTableTwoLookup(bddManager, f, g, CAL_OP_NAND, &result) + == 0){ + CalHashTableFindOrAdd(andHashTableArray[minId], f, g, &result); + } + else{ + CalCacheTableTwoInsert(bddManager, f, g, result, CAL_OP_NAND, + 1); + } + CalBddNot(result, result); + } + } + else { + CalHashTableFindOrAdd(relProdHashTableArray[minId], f, g, &result); + } + + BddRelProdBFAux(bddManager, minIndex, relProdHashTableArray, + andHashTableArray, orHashTableArray, opCode, association); + CalRequestIsForwardedTo(result); + CalCacheTableTwoFixResultPointers(bddManager); + CalCacheTableTwoInsert(bddManager, f, g, result, opCode, 0); + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(relProdHashTableArray[bddId]); + CalHashTableCleanUp(andHashTableArray[bddId]); + CalHashTableCleanUp(orHashTableArray[bddId]); + } + return result; +} + diff --git a/calReduce.c b/calReduce.c new file mode 100644 index 0000000..9598b3b --- /dev/null +++ b/calReduce.c @@ -0,0 +1,680 @@ +/**CFile*********************************************************************** + + FileName [calReduce.c] + + PackageName [cal] + + Synopsis [Routines for optimizing a BDD with respect to a don't + care set (cofactor and restrict).] + + Description [] + + SeeAlso [None] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calReduce.c,v 1.1.1.4 1998/05/04 00:59:02 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static Cal_Bdd_t BddReduceBF(Cal_BddManager_t * bddManager, CalOpProc_t calOpProc, Cal_Bdd_t f, Cal_Bdd_t c); +static Cal_Bdd_t BddCofactorBF(Cal_BddManager_t * bddManager, CalOpProc_t calOpProc, Cal_Bdd_t f, Cal_Bdd_t c); +static void HashTableReduceApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** reduceHashTableArray, CalHashTable_t ** orHashTableArray, CalOpProc_t calOpProc); +static void HashTableCofactorApply(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t ** cofactorHashTableArray, CalOpProc_t calOpProc); +static void HashTableCofactorReduce(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalHashTable_t * uniqueTableForId); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [Returns the generalized cofactor of BDD f with respect + to BDD c.] + + Description [Returns the generalized cofactor of BDD f with respect + to BDD c. The constrain operator given by Coudert et al (ICCAD90) is + used to find the generalized cofactor.] + + SideEffects [None.] + + SeeAlso [Cal_BddReduce] + +******************************************************************************/ +Cal_Bdd +Cal_BddCofactor(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd cUserBdd) +{ + Cal_Bdd_t result; + Cal_Bdd userResult; + if (CalBddPreProcessing(bddManager, 2, fUserBdd, cUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + Cal_Bdd_t c = CalBddGetInternalBdd(bddManager, cUserBdd); + result = BddCofactorBF(bddManager, CalOpCofactor, f, c); + userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + return userResult; + } + return (Cal_Bdd) 0; +} + + +/**Function******************************************************************** + + Synopsis [Returns a BDD which agrees with f for all valuations + which satisfy c.] + + Description [Returns a BDD which agrees with f for all valuations + which satisfy c. The result is usually smaller in terms of number of + BDD nodes than f. This operation is typically used in state space + searches to simplify the representation for the set of states wich + will be expanded at each step.] + + SideEffects [None] + + SeeAlso [Cal_BddCofactor] + +******************************************************************************/ +Cal_Bdd +Cal_BddReduce(Cal_BddManager bddManager, Cal_Bdd fUserBdd, + Cal_Bdd cUserBdd) +{ + if (CalBddPreProcessing(bddManager, 2, fUserBdd, cUserBdd)){ + Cal_Bdd_t f = CalBddGetInternalBdd(bddManager, fUserBdd); + Cal_Bdd_t c = CalBddGetInternalBdd(bddManager, cUserBdd); + Cal_Bdd_t result = BddReduceBF(bddManager, CalOpCofactor, f, c); + Cal_Bdd userResult = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, userResult); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + if (Cal_BddSize(bddManager, userResult, 1) < + Cal_BddSize(bddManager, fUserBdd, 1)){ + return userResult; + } + else{ + Cal_BddFree(bddManager, userResult); + return Cal_BddIdentity(bddManager, fUserBdd); + } + } + return (Cal_Bdd) 0; +} + + +/**Function******************************************************************** + + Synopsis [Returns a minimal BDD whose function contains fMin and is + contained in fMax.] + + Description [Returns a minimal BDD f which is contains fMin and is + contained in fMax ( fMin <= f <= fMax). + This operation is typically used in state space searches to simplify + the representation for the set of states wich will be expanded at + each step (Rk Rk-1' <= f <= Rk).] + + SideEffects [None] + + SeeAlso [Cal_BddReduce] + +******************************************************************************/ +Cal_Bdd +Cal_BddBetween(Cal_BddManager bddManager, Cal_Bdd fMinUserBdd, + Cal_Bdd fMaxUserBdd) +{ + if (CalBddPreProcessing(bddManager, 2, fMinUserBdd, fMaxUserBdd)){ + Cal_Bdd_t fMin = CalBddGetInternalBdd(bddManager, fMinUserBdd); + Cal_Bdd_t fMax = CalBddGetInternalBdd(bddManager, fMaxUserBdd); + Cal_Bdd_t fMaxNot, careSet, result; + Cal_Bdd resultUserBdd; + long fMinSize, fMaxSize, resultSize; + + CalBddNot(fMax, fMaxNot); + careSet = CalBddOpBF(bddManager, CalOpOr, fMin, fMaxNot); + result = BddReduceBF(bddManager, CalOpCofactor, fMin, careSet); + resultUserBdd = CalBddGetExternalBdd(bddManager, result); + if (CalBddPostProcessing(bddManager) == CAL_BDD_OVERFLOWED){ + Cal_BddFree(bddManager, resultUserBdd); + Cal_BddManagerGC(bddManager); + return (Cal_Bdd) 0; + } + fMinSize = Cal_BddSize(bddManager, fMinUserBdd, 1); + fMaxSize = Cal_BddSize(bddManager, fMaxUserBdd, 1); + resultSize = Cal_BddSize(bddManager, resultUserBdd, 1); + if (resultSize < fMinSize){ + if (resultSize < fMaxSize){ + return resultUserBdd; + } + else { + Cal_BddFree(bddManager, resultUserBdd); + return Cal_BddIdentity(bddManager, fMaxUserBdd); + } + } + Cal_BddFree(bddManager, resultUserBdd); + if (fMinSize < fMaxSize){ + return Cal_BddIdentity(bddManager, fMinUserBdd); + } + else{ + return Cal_BddIdentity(bddManager, fMaxUserBdd); + } + } + return (Cal_Bdd) 0; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpCofactor( + Cal_BddManager_t * bddManager, + Cal_Bdd_t f, + Cal_Bdd_t c, + Cal_Bdd_t * resultBddPtr) +{ + if (CalBddIsBddConst(c)){ + if (CalBddIsBddZero(bddManager, c)){ + *resultBddPtr = bddManager->bddNull; + } + else { + *resultBddPtr = f; + } + return 1; + } + if (CalBddIsBddConst(f)){ + *resultBddPtr = f; + return 1; + } + return 0; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddReduceBF( + Cal_BddManager_t * bddManager, + CalOpProc_t calOpProc, + Cal_Bdd_t f, + Cal_Bdd_t c) +{ + Cal_Bdd_t result; + CalHashTable_t *hashTable; + CalHashTable_t **orHashTableArray = bddManager->reqQue[0]; + CalHashTable_t **reduceHashTableArray = bddManager->reqQue[1]; + CalHashTable_t *uniqueTableForId; + + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + int bddIndex; + Cal_BddId_t bddId, minId; + + + if ((*calOpProc)(bddManager, f, c, &result) == 1){ + return result; + } + + CalBddGetMinIdAndMinIndex(bddManager, f, c, minId, minIndex); + CalHashTableFindOrAdd(reduceHashTableArray[minId], f, c, &result); + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = reduceHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableReduceApply(bddManager, hashTable, reduceHashTableArray, + orHashTableArray, CalOpCofactor); + } + } + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = reduceHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableCofactorReduce(bddManager, hashTable, uniqueTableForId); + } + } + CalRequestIsForwardedTo(result); + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(reduceHashTableArray[bddId]); + } + return result; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd_t +BddCofactorBF(Cal_BddManager_t * bddManager, + CalOpProc_t calOpProc, + Cal_Bdd_t f, + Cal_Bdd_t c) +{ + Cal_Bdd_t result; + CalHashTable_t *hashTable; + CalHashTable_t **cofactorHashTableArray = bddManager->reqQue[0]; + CalHashTable_t *uniqueTableForId; + +/*Cal_BddIndex_t minIndex;*/ + int minIndex; + int bddIndex; + Cal_BddId_t bddId, minId; + + if (CalBddIsBddZero(bddManager, c)){ + CalBddWarningMessage("Bdd Cofactor Called with zero care set"); + return bddManager->bddOne; + } + + if (calOpProc(bddManager, f, c, &result) == 1){ + return result; + } + + CalBddGetMinIdAndMinIndex(bddManager, f, c, minId, minIndex); + CalHashTableFindOrAdd(cofactorHashTableArray[minId], f, c, &result); + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + hashTable = cofactorHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableCofactorApply(bddManager, hashTable, cofactorHashTableArray, + calOpProc); + } + } + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + hashTable = cofactorHashTableArray[bddId]; + if(hashTable->numEntries){ + HashTableCofactorReduce(bddManager, hashTable, uniqueTableForId); + } + } + CalRequestIsForwardedTo(result); + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(cofactorHashTableArray[bddId]); + } + return result; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableReduceApply(Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t ** reduceHashTableArray, + CalHashTable_t ** orHashTableArray, + CalOpProc_t calOpProc) +{ + int i, numBins = hashTable->numBins; + CalRequestNode_t *requestNode, *last, *nextRequestNode, *requestNodeList; + Cal_Bdd_t f, c, fx, cx, fxbar, cxbar, result, orResult; + Cal_BddId_t bddId, minId; + /*Cal_BddIndex_t minIndex;*/ + int minIndex; + int bddIndex; + CalHashTable_t *orHashTable; + + requestNodeList = Cal_Nil(CalRequestNode_t); + for(i = 0; i < numBins; i++){ + last = Cal_Nil(CalRequestNode_t); + for (requestNode = hashTable->bins[i]; requestNode != + Cal_Nil(CalRequestNode_t); + requestNode = nextRequestNode){ + nextRequestNode = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetF(requestNode, f); + CalRequestNodeGetG(requestNode, c); + CalBddGetMinId2(bddManager, f, c, minId); + CalBddGetCofactors(c, minId, cx, cxbar); + if (CalBddGetBddId(f) != minId){ + if (CalOpOr(bddManager, cx, cxbar, &orResult) == 0){ + CalBddNormalize(cx, cxbar); + CalBddGetMinId2(bddManager, cx, cxbar, minId); + CalHashTableFindOrAdd(orHashTableArray[minId], cx, cxbar, &orResult); + } + CalRequestNodePutElseRequest(requestNode, orResult); + if (last == Cal_Nil(CalRequestNode_t)){ + hashTable->bins[i] = nextRequestNode; + } + else { + CalRequestNodePutNextRequestNode(last, nextRequestNode); + } + CalRequestNodePutNextRequestNode(requestNode, requestNodeList); + requestNodeList = requestNode; + } + else{ + last = requestNode; + CalBddGetCofactors(f, minId, fx, fxbar); + if((*calOpProc)(bddManager, fx, cx, &result) == 0){ + CalBddGetMinId2(bddManager, fx, cx, bddId); + CalHashTableFindOrAdd(reduceHashTableArray[bddId], fx, cx, &result); + } + if (CalBddIsBddNull(bddManager, result) == 0){ + CalBddIcrRefCount(result); + } + CalRequestNodePutThenRequest(requestNode, result); + if((*calOpProc)(bddManager, fxbar, cxbar, &result) == 0){ + CalBddGetMinId2(bddManager, fxbar, cxbar, bddId); + CalHashTableFindOrAdd(reduceHashTableArray[bddId], fxbar, cxbar, + &result); + } + if (CalBddIsBddNull(bddManager, result) == 0){ + CalBddIcrRefCount(result); + } + CalRequestNodePutElseRequest(requestNode, result); + } + } + } + minIndex = bddManager->idToIndex[hashTable->bddId]; + for (bddIndex = minIndex; bddIndex < bddManager->numVars; bddIndex++){ + bddId = bddManager->indexToId[bddIndex]; + orHashTable = orHashTableArray[bddId]; + if(orHashTable->numEntries){ + CalHashTableApply(bddManager, orHashTable, orHashTableArray, CalOpOr); + } + } + + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + CalHashTable_t *uniqueTableForId; + bddId = bddManager->indexToId[bddIndex]; + uniqueTableForId = bddManager->uniqueTable[bddId]; + orHashTable = orHashTableArray[bddId]; + if(orHashTable->numEntries){ + CalHashTableReduce(bddManager, orHashTable, uniqueTableForId); + } + } + for (requestNode = requestNodeList; requestNode; requestNode = + nextRequestNode){ + nextRequestNode = CalRequestNodeGetNextRequestNode(requestNode); + CalRequestNodeGetElseRequest(requestNode, orResult); + CalRequestIsForwardedTo(orResult); + CalRequestNodeGetThenRequest(requestNode, f); + CalBddGetMinId2(bddManager, f, orResult, minId); + CalHashTableFindOrAdd(reduceHashTableArray[minId], f, orResult, + &result); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequest(requestNode, result); + CalBddAddRefCount(result, 2); + CalHashTableAddDirect(hashTable, requestNode); + } + + /* Clean up the orHashTableArray */ + for(bddIndex = bddManager->numVars - 1; bddIndex >= minIndex; bddIndex--){ + bddId = bddManager->indexToId[bddIndex]; + CalHashTableCleanUp(orHashTableArray[bddId]); + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableCofactorApply(Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t ** cofactorHashTableArray, + CalOpProc_t calOpProc) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + CalRequestNode_t *requestNode; + Cal_Bdd_t f, c, fx, cx, fxbar, cxbar, result; + Cal_BddId_t bddId, minId; + + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i]; + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = CalRequestNodeGetNextRequestNode(requestNode)){ + CalRequestNodeGetF(requestNode, f); + CalRequestNodeGetG(requestNode, c); + CalBddGetMinId2(bddManager, f, c, minId); + CalBddGetCofactors(f, minId, fx, fxbar); + CalBddGetCofactors(c, minId, cx, cxbar); + if((*calOpProc)(bddManager, fx, cx, &result) == 0){ + CalBddGetMinId2(bddManager, fx, cx, bddId); + CalHashTableFindOrAdd(cofactorHashTableArray[bddId], fx, cx, &result); + } + if (CalBddIsBddNull(bddManager, result) == 0){ + CalBddIcrRefCount(result); + } + CalRequestNodePutThenRequest(requestNode, result); + if((*calOpProc)(bddManager, fxbar, cxbar, &result) == 0){ + CalBddGetMinId2(bddManager, fxbar, cxbar, bddId); + CalHashTableFindOrAdd(cofactorHashTableArray[bddId], fxbar, cxbar, + &result); + } + if (CalBddIsBddNull(bddManager, result) == 0){ + CalBddIcrRefCount(result); + } + CalRequestNodePutElseRequest(requestNode, result); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableCofactorReduce(Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalHashTable_t * uniqueTableForId) +{ + int i, numBins = hashTable->numBins; + CalBddNode_t **bins = hashTable->bins; + Cal_BddId_t currentBddId = uniqueTableForId->bddId; + CalNodeManager_t *nodeManager = uniqueTableForId->nodeManager; + CalRequestNode_t *requestNode, *next, *endNode; + CalBddNode_t *bddNode; + Cal_Bdd_t thenBdd, elseBdd, result; + Cal_BddRefCount_t refCount; + + endNode = hashTable->endNode; + for(i = 0; i < numBins; i++){ + for(requestNode = bins[i], bins[i] = Cal_Nil(CalRequestNode_t); + requestNode != Cal_Nil(CalRequestNode_t); + requestNode = next){ + next = CalRequestNodeGetNextRequestNode(requestNode); + /* Process the requestNode */ + CalRequestNodeGetThenRequest(requestNode, thenBdd); + CalRequestNodeGetElseRequest(requestNode, elseBdd); + if (CalBddIsBddNull(bddManager, thenBdd)){ + CalRequestIsForwardedTo(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(elseBdd, refCount - 1); + CalRequestNodePutThenRequest(requestNode, elseBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + continue; + } + else if (CalBddIsBddNull(bddManager, elseBdd)){ + CalRequestIsForwardedTo(thenBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 1); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + continue; + } + CalRequestIsForwardedTo(thenBdd); + CalRequestIsForwardedTo(elseBdd); + if(CalBddIsEqual(thenBdd, elseBdd)){ + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(thenBdd, refCount - 2); + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalUniqueTableForIdLookup(bddManager, uniqueTableForId, + thenBdd, elseBdd, &result) == 1){ + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddAddRefCount(result, refCount); + CalRequestNodePutThenRequest(requestNode, result); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + else if(CalBddIsOutPos(thenBdd)){ + CalRequestNodePutThenRequest(requestNode, thenBdd); + CalRequestNodePutElseRequest(requestNode, elseBdd); + CalHashTableAddDirect(uniqueTableForId, requestNode); + bddManager->numNodes++; + bddManager->gcCheck--; + } + else{ + CalNodeManagerAllocNode(nodeManager, bddNode); + CalBddNodePutThenBddId(bddNode, CalBddGetBddId(thenBdd)); + CalBddNodePutThenBddNode(bddNode, CalBddGetBddNodeNot(thenBdd)); + CalBddNodePutElseBddId(bddNode, CalBddGetBddId(elseBdd)); + CalBddNodePutElseBddNode(bddNode, CalBddGetBddNodeNot(elseBdd)); + CalBddNodeGetRefCount(requestNode, refCount); + CalBddNodePutRefCount(bddNode, refCount); + CalHashTableAddDirect(uniqueTableForId, bddNode); + bddManager->numNodes++; + bddManager->gcCheck--; + CalRequestNodePutThenRequestId(requestNode, currentBddId); + CalRequestNodePutThenRequestNode(requestNode, CalBddNodeNot(bddNode)); + CalRequestNodePutElseRequestNode(requestNode, FORWARD_FLAG); + endNode->nextBddNode = requestNode; + endNode = requestNode; + } + } + } + hashTable->endNode = endNode; +} + + + + + + + + + + + + + + + + + + + + + + diff --git a/calReorderBF.c b/calReorderBF.c new file mode 100644 index 0000000..3b957d7 --- /dev/null +++ b/calReorderBF.c @@ -0,0 +1,1490 @@ +/**CFile*********************************************************************** + + FileName [calReorderBF.c] + + PackageName [cal] + + Synopsis [Routines for dynamic reordering of variables.] + + Description [This method dynamically reorders variables while + preserving their locality. This entails both memory and + computational overheads. Conceptually and experimentally it has + been observed that these overheads lead to poorer performance + compared to the traditional reordering methods. For details, please + refer to the work by Rajeev K. Ranjan et al - "Dynamic variable + reordering in a breadth-first manipulation based package: Challenges + and Solutions"- Proceedings of ICCD'97.] + + SeeAlso [calReorderDF.c calReorderUtil.c] + + Author [Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu) + Wilsin Gosti (wilsin@ic.eecs.berkeley.edu)] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calReorderBF.c,v 1.2 1998/09/17 02:30:21 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static void BddReorderFixForwardingNodes(Cal_BddManager bddManager, Cal_BddId_t id); +static void BddReorderFixAndFreeForwardingNodes(Cal_BddManager bddManager, Cal_BddId_t id, int numLevels); +static void BddReorderSwapVarIndex(Cal_BddManager_t * bddManager, int varIndex, int forwardCheckFlag); +static int CofactorFixAndReclaimForwardedNodes(Cal_BddManager_t *bddManager, int cofactorCheckStartIndex, int cofactorCheckEndIndex, int reclaimStartIndex, int reclaimEndIndex); +static void BddReorderFreeNodes(Cal_BddManager_t * bddManager, int varId); +#ifdef _CAL_VERBOSE +static void PrintBddProfileAfterReorder(Cal_BddManager_t *bddManager); +#endif +static void BddReorderVarSift(Cal_BddManager bddManager, double maxSizeFactor); +static int BddReorderSiftToBestPos(Cal_BddManager_t * bddManager, int varStartIndex, double maxSizeFactor); +static void BddSiftPerfromPhaseIV(Cal_BddManager_t *bddManager, int varStartIndex, int bestIndex, int bottomMostSwapIndex); +static void BddReorderVarWindow(Cal_BddManager bddManager, char *levels); +static int BddReorderWindow2(Cal_BddManager bddManager, long index, int directionFlag); +static int BddReorderWindow3(Cal_BddManager bddManager, long index, int directionFlag); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderAuxBF(Cal_BddManager_t * bddManager) +{ + Cal_Assert(CalCheckAllValidity(bddManager)); + CalInitInteract(bddManager); +#ifdef _CAL_QUANTIFY_ + quantify_start_recording_data(); +#endif + if (bddManager->reorderTechnique == CAL_REORDER_WINDOW){ + char *levels = Cal_MemAlloc(char, bddManager->numVars); + BddReorderVarWindow(bddManager, levels); + Cal_MemFree(levels); + } + else { + BddReorderVarSift(bddManager, bddManager->maxSiftingGrowth); + } +#ifdef _CAL_QUANTIFY_ + quantify_stop_recording_data(); +#endif + Cal_Assert(CalCheckAllValidity(bddManager)); + Cal_MemFree(bddManager->interact); + bddManager->numReorderings++; +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [Fixes the forwarding nodes in a unique table.] + + Description [As opposed to CalBddReorderFixCofactors, which fixes + the cofactors of the non-forwarding nodes, this routine traverses + the list of forwarding nodes and removes the intermediate level of + forwarding. Number of levels should be 1 or 2.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderFixForwardingNodes(Cal_BddManager bddManager, + Cal_BddId_t id) +{ + CalHashTable_t *uniqueTableForId = + bddManager->uniqueTable[id]; + CalBddNode_t *bddNode, *nextBddNode; + Cal_Bdd_t thenBdd; + + /* These are the forwarding nodes. */ + CalBddNode_t *requestNodeList = + uniqueTableForId->startNode.nextBddNode; + for (bddNode = requestNodeList; bddNode; bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddIsForwarded(thenBdd)) { + CalBddForward(thenBdd); + CalBddNodePutThenBdd(bddNode, thenBdd); + } + else { + /* there should not be anymore double forwarding */ + break; + } + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + /* Adjust the list */ + uniqueTableForId->endNode->nextBddNode = + uniqueTableForId->startNode.nextBddNode; + uniqueTableForId->startNode.nextBddNode = bddNode; +} + +/**Function******************************************************************** + + Synopsis [Traverses the forwarding node lists of index, + index+1 .. up to index+level. Frees the intermediate forwarding nodes.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderFixAndFreeForwardingNodes(Cal_BddManager bddManager, + Cal_BddId_t id, int numLevels) +{ + CalHashTable_t *uniqueTableForId; + Cal_BddIndex_t index = bddManager->idToIndex[id]; + CalBddNode_t *nextBddNode, *bddNode, *endNode; + Cal_Bdd_t thenBdd; + CalNodeManager_t *nodeManager; + int i; + + /* Fixing */ + for (i=numLevels-1; i >= 0; i--){ + uniqueTableForId = + bddManager->uniqueTable[bddManager->indexToId[index+i]]; + for (bddNode = uniqueTableForId->startNode.nextBddNode; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddIsForwarded(thenBdd)){ + do{ + CalBddMark(thenBdd); + CalBddForward(thenBdd); + } while (CalBddIsForwarded(thenBdd)); + CalBddNodePutThenBdd(bddNode, thenBdd); + } + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + } + /* Freeing */ + for (i=numLevels-1; i >= 0; i--){ + uniqueTableForId = + bddManager->uniqueTable[bddManager->indexToId[index+i]]; + endNode = &(uniqueTableForId->startNode); + for (bddNode = uniqueTableForId->startNode.nextBddNode; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + if (CalBddIsMarked(thenBdd)){ + do{ + /* Free the node */ + nodeManager = bddManager->nodeManagerArray[CalBddGetBddId(thenBdd)]; + CalNodeManagerFreeNode(nodeManager, CalBddGetBddNode(thenBdd)); + bddManager->numForwardedNodes--; + } while (CalBddIsMarked(thenBdd)); + } + else{ + endNode->nextBddNode = bddNode; + endNode = bddNode; + } + } + uniqueTableForId->endNode = endNode; + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [Traversesoptional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderSwapVarIndex(Cal_BddManager_t * bddManager, int varIndex, + int forwardCheckFlag) +{ + int thenVarIndex; + int elseVarIndex; + int varId; + int nextVarId; + int i; + int numBins; + int curSize1; + int curSize2; + int refCount; + int f0Found; + int f1Found; + CalHashTable_t *uniqueTableForId; + CalHashTable_t *nextUniqueTableForId; + CalBddNode_t **bins; + CalBddNode_t *bddNode, *startNode; + CalBddNode_t *nextBddNode, *processingNodeList; + CalBddNode_t *prevBddNode = Cal_Nil(CalBddNode_t); + Cal_Bdd_t newF; + Cal_Bdd_t f0; + Cal_Bdd_t f1; + Cal_Bdd_t newF0; + Cal_Bdd_t newF1; + Cal_Bdd_t f00; + Cal_Bdd_t f01; + Cal_Bdd_t f10; + Cal_Bdd_t f11; + CalAssociation_t *assoc; + + varId = bddManager->indexToId[varIndex]; + nextVarId = bddManager->indexToId[varIndex + 1]; + + if (CalTestInteract(bddManager, varId, nextVarId)){ + bddManager->numSwaps++; +#ifdef _CAL_VERBOSE + /*fprintf(stdout," %3d(%3d) going down, %3d(%3d) going up\n", + varId, varIndex, nextVarId, varIndex+1);*/ +#endif + uniqueTableForId = bddManager->uniqueTable[varId]; + nextUniqueTableForId = bddManager->uniqueTable[nextVarId]; + curSize1 = bddManager->uniqueTable[varId]->numEntries; + curSize2 = bddManager->uniqueTable[nextVarId]->numEntries; + + /*uniqueTableForId->requestNodeList = Cal_Nil(CalBddNode_t);*/ + processingNodeList = Cal_Nil(CalBddNode_t); + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + if (forwardCheckFlag){ + for(i = 0; i < numBins; ++i) { + prevBddNode = Cal_Nil(CalBddNode_t); + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + /* + * Process one bddNode at a time + */ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + /* The node should not be forwarded */ + Cal_Assert(CalBddNodeIsForwarded(bddNode) == 0); + /* + ** We don't know for sure if the reference count of the node + ** could be 0. Let us use the assertion at this point. + */ + Cal_Assert(CalBddNodeIsRefCountZero(bddNode) == 0); + /* + ** If ever the above assetion fails, or if we can convince + ** ourselves that the reference count could be zero, we need + ** to uncomment the following code. + */ + /* + if (CalBddNodeIsRefCountZero(bddNode)){ + thenBddNode = CAL_BDD_POINTER(CalBddNodeGetThenBddNode(bddNode)); + elseBddNode = CAL_BDD_POINTER(CalBddNodeGetElseBddNode(bddNode)); + CalBddNodeDcrRefCount(thenBddNode); + CalBddNodeDcrRefCount(elseBddNode); + if (prevBddNode){ + CalBddNodePutNextBddNode(prevBddNode, nextBddNode); + } + else{ + bins[i] = nextBddNode; + } + uniqueTableForId->numEntries--; + bddManager->numNodes--; + bddManager->numNodesFreed++; + CalNodeManagerFreeNode(uniqueTableForId->nodeManager, bddNode); + continue; + } + */ + CalBddNodeGetElseBdd(bddNode, f0); + CalBddNodeGetThenBdd(bddNode, f1); + + if (CalBddIsForwarded(f1)) { + CalBddForward(f1); + CalBddNodePutThenBdd(bddNode, f1); + } + Cal_Assert(CalBddIsForwarded(f1) == 0); + + if (CalBddIsForwarded(f0)) { + CalBddForward(f0); + CalBddNodePutElseBdd(bddNode, f0); + } + Cal_Assert(CalBddIsForwarded(f0) == 0); + /* + ** Get the index of f0 and f1 and create newF0 and newF1 if necessary + */ + elseVarIndex = CalBddNodeGetElseBddIndex(bddManager, bddNode); + thenVarIndex = CalBddNodeGetThenBddIndex(bddManager, bddNode); + + if ((elseVarIndex > (varIndex + 1)) + && (thenVarIndex > (varIndex + 1))) { + prevBddNode = bddNode; + Cal_Assert(CalDoHash2(CalBddGetBddNode(f1), + CalBddGetBddNode(f0), + uniqueTableForId) == i); + continue; + } + + /* This node is going to be forwared */ + CalBddNodePutNextBddNode(bddNode, processingNodeList); + processingNodeList = bddNode; + + /* Update the unique table appropriately */ + if (prevBddNode){ + CalBddNodePutNextBddNode(prevBddNode, nextBddNode); + } + else{ + bins[i] = nextBddNode; + } + uniqueTableForId->numEntries--; + bddManager->numNodes--; + } + } + } + else{ + for(i = 0; i < numBins; i++) { + prevBddNode = Cal_Nil(CalBddNode_t); + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + /* + * Process one bddNode at a time + */ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + /* The node should not be forwarded */ + Cal_Assert(CalBddNodeIsForwarded(bddNode) == 0); + + /* + ** We don't know for sure if the reference count of the node + ** could be 0. Let us use the assertion at this point. + */ + Cal_Assert(CalBddNodeIsRefCountZero(bddNode) == 0); + /* + ** If ever the above assetion fails, or if we can convince + ** ourselves that the reference count could be zero, we need + ** to uncomment the following code. + */ + /* + if (CalBddNodeIsRefCountZero(bddNode)){ + thenBddNode = CAL_BDD_POINTER(CalBddNodeGetThenBddNode(bddNode)); + elseBddNode = CAL_BDD_POINTER(CalBddNodeGetElseBddNode(bddNode)); + CalBddNodeDcrRefCount(thenBddNode); + CalBddNodeDcrRefCount(elseBddNode); + if (prevBddNode){ + CalBddNodePutNextBddNode(prevBddNode, nextBddNode); + } + else{ + bins[i] = nextBddNode; + } + uniqueTableForId->numEntries--; + bddManager->numNodes--; + bddManager->numNodesFreed++; + CalNodeManagerFreeNode(uniqueTableForId->nodeManager, bddNode); + continue; + } + */ + CalBddNodeGetThenBdd(bddNode, f1); + Cal_Assert(CalBddIsForwarded(f1) == 0); + CalBddNodeGetElseBdd(bddNode, f0); + Cal_Assert(CalBddIsForwarded(f0) == 0); + /* + ** Get the index of f0 and f1 and create newF0 and newF1 if necessary + */ + + elseVarIndex = CalBddNodeGetElseBddIndex(bddManager, bddNode); + thenVarIndex = CalBddNodeGetThenBddIndex(bddManager, bddNode); + + if ((elseVarIndex > (varIndex + 1)) + && (thenVarIndex > (varIndex + 1))) { + prevBddNode = bddNode; + continue; + } + + /* This node is going to be forwared */ + CalBddNodePutNextBddNode(bddNode, processingNodeList); + processingNodeList = bddNode; + + /* Update the unique table appropriately */ + if (prevBddNode){ + CalBddNodePutNextBddNode(prevBddNode, nextBddNode); + } + else{ + bins[i] = nextBddNode; + } + uniqueTableForId->numEntries--; + bddManager->numNodes--; + } + } + } + bddNode = processingNodeList; + /*endNode = uniqueTableForId->endNode;*/ + startNode = uniqueTableForId->startNode.nextBddNode; + while (bddNode != Cal_Nil(CalBddNode_t)) { + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + + /* + * Get the index of f0 and f1 and create newF0 and newF1 if necessary + */ + + CalBddNodeGetElseBdd(bddNode, f0); + CalBddNodeGetThenBdd(bddNode, f1); + elseVarIndex = CalBddNodeGetElseBddIndex(bddManager, bddNode); + thenVarIndex = CalBddNodeGetThenBddIndex(bddManager, bddNode); + + if (elseVarIndex > (varIndex + 1)) { + f00 = f0; + f01 = f0; + CalBddGetElseBdd(f1, f10); + CalBddGetThenBdd(f1, f11); + } else if (thenVarIndex > (varIndex + 1)) { + f10 = f1; + f11 = f1; + CalBddGetElseBdd(f0, f00); + CalBddGetThenBdd(f0, f01); + }else{ + CalBddGetElseBdd(f1, f10); + CalBddGetThenBdd(f1, f11); + CalBddGetElseBdd(f0, f00); + CalBddGetThenBdd(f0, f01); + } + Cal_Assert(CalBddIsForwarded(f10) == 0); + Cal_Assert(CalBddIsForwarded(f11) == 0); + Cal_Assert(CalBddIsForwarded(f00) == 0); + Cal_Assert(CalBddIsForwarded(f01) == 0); + + if (CalBddIsEqual(f10,f00)) { + newF0 = f00; + f0Found = 1; + } + else { + f0Found = CalUniqueTableForIdFindOrAdd(bddManager, uniqueTableForId, f10, + f00, &newF0); + } + CalBddIcrRefCount(newF0); + if (CalBddIsEqual(f11, f01)) { + newF1 = f01; + f1Found = 1; + } + else { + f1Found = CalUniqueTableForIdFindOrAdd(bddManager, uniqueTableForId, f11, + f01, &newF1); + } + CalBddIcrRefCount(newF1); + + if (!f0Found){ + CalBddIcrRefCount(f10); + CalBddIcrRefCount(f00); + } + + if (!f1Found){ + CalBddIcrRefCount(f11); + CalBddIcrRefCount(f01); + } + + CalBddDcrRefCount(f0); + CalBddDcrRefCount(f1); + /* + * Create the new node for f. It cannot exist before, since at + * least one of newF0 and newF1 must be dependent on currentIndex. + * Otherwise, f00 == f10 and f01 == f11 (redundant nodes). + */ + CalHashTableAddDirectAux(nextUniqueTableForId, newF1, newF0, &newF); + bddManager->numNodes++; + CalBddNodePutThenBdd(bddNode, newF); + CalBddNodePutElseBddNode(bddNode, FORWARD_FLAG); + bddManager->numForwardedNodes++; + CalBddNodeGetRefCount(bddNode, refCount); + CalBddAddRefCount(newF, refCount); + Cal_Assert(!CalBddIsRefCountZero(newF)); + /* Put it in the forwarded list of the unique table */ + /* + endNode->nextBddNode = bddNode; + endNode = bddNode; + */ + bddNode->nextBddNode = startNode; + startNode = bddNode; + + bddNode = nextBddNode; + } + /*uniqueTableForId->endNode = endNode;*/ + uniqueTableForId->startNode.nextBddNode = startNode; + + BddReorderFreeNodes(bddManager, nextVarId); + + } + else{ + bddManager->numTrivialSwaps++; + } + + CalFixupAssoc(bddManager, varId, nextVarId, bddManager->tempAssociation); + for(assoc = bddManager->associationList; assoc; assoc = assoc->next){ + CalFixupAssoc(bddManager, varId, nextVarId, assoc); + } + + bddManager->idToIndex[varId] = varIndex + 1; + bddManager->idToIndex[nextVarId] = varIndex; + bddManager->indexToId[varIndex] = nextVarId; + bddManager->indexToId[varIndex + 1] = varId; + + Cal_Assert(CalCheckAssoc(bddManager)); + +#ifdef _CAL_VERBOSE + /*fprintf(stdout,"Variable order after swap:\n");*/ + for (i=0; inumVars; i++){ + fprintf(stdout, "%3d ", bddManager->indexToId[i]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +CofactorFixAndReclaimForwardedNodes(Cal_BddManager_t *bddManager, int + cofactorCheckStartIndex, int + cofactorCheckEndIndex, int + reclaimStartIndex, int reclaimEndIndex) +{ + int index, varId; + /* Clean up : Need to fix the cofactors of userBDDs and the + indices above the varStartIndex only. */ + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalBddReorderFixUserBddPtrs(bddManager); + CalReorderAssociationFix(bddManager); + for (index = cofactorCheckStartIndex; + index <= cofactorCheckEndIndex; index++){ + varId = bddManager->indexToId[index]; + CalBddReorderFixCofactors(bddManager, varId); + } + CalBddReorderReclaimForwardedNodes(bddManager, reclaimStartIndex, + reclaimEndIndex); + Cal_Assert(CalCheckAllValidity(bddManager)); + return 0; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderFreeNodes(Cal_BddManager_t * bddManager, int varId) +{ + CalBddNode_t *prevNode, *bddNode, *nextBddNode; + CalBddNode_t *elseBddNode; + CalBddNode_t *thenBddNode; + CalHashTable_t *uniqueTableForId; + CalBddNode_t **bins; + int numBins; + int i; + long oldNumEntries, numNodesFreed; + + uniqueTableForId = bddManager->uniqueTable[varId]; + bins = uniqueTableForId->bins; + numBins = uniqueTableForId->numBins; + oldNumEntries = uniqueTableForId->numEntries; + + if (bddManager->numPeakNodes < (bddManager->numNodes + + bddManager->numForwardedNodes)){ + bddManager->numPeakNodes = bddManager->numNodes + + bddManager->numForwardedNodes ; + } + + for(i = 0; i < numBins; i++){ + prevNode = NULL; + bddNode = bins[i]; + while(bddNode != Cal_Nil(CalBddNode_t)){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + Cal_Assert(CalBddNodeIsForwarded(bddNode) == 0); + if(CalBddNodeIsRefCountZero(bddNode)){ + thenBddNode = CAL_BDD_POINTER(CalBddNodeGetThenBddNode(bddNode)); + elseBddNode = CAL_BDD_POINTER(CalBddNodeGetElseBddNode(bddNode)); + Cal_Assert(CalBddNodeIsForwarded(thenBddNode) == 0); + Cal_Assert(CalBddNodeIsForwarded(elseBddNode) == 0); + CalBddNodeDcrRefCount(thenBddNode); + CalBddNodeDcrRefCount(elseBddNode); + if (prevNode == NULL) { + bins[i] = nextBddNode; + } else { + CalBddNodePutNextBddNode(prevNode, nextBddNode); + } + CalNodeManagerFreeNode(uniqueTableForId->nodeManager, bddNode); + uniqueTableForId->numEntries--; + } else { + prevNode = bddNode; + } + bddNode = nextBddNode; + } + } + numNodesFreed = oldNumEntries - uniqueTableForId->numEntries; + bddManager->numNodes -= numNodesFreed; + bddManager->numNodesFreed += numNodesFreed; +} + +#ifdef _CAL_VERBOSE + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +PrintBddProfileAfterReorder(Cal_BddManager_t *bddManager) +{ + int i, index, numBins, j; + CalHashTable_t *uniqueTableForId; + CalBddNode_t *bddNode, *nextBddNode; + char *levels = Cal_MemAlloc(char, bddManager->numVars+1); + CalBddNode_t *requestNodeList; + Cal_Bdd_t thenBdd, elseBdd; + + /* Now traverse all the nodes in order */ + for (index = 0; index < bddManager->numVars; index++){ + fprintf(stdout,"**** %3d ****\n", bddManager->indexToId[index]); + uniqueTableForId = bddManager->uniqueTable[bddManager->indexToId[index]]; + numBins = uniqueTableForId->numBins; + for (i=1; i<=bddManager->numVars; i++) { + levels[i] = 0; + } + j = 0; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + if (CalBddIsForwarded(thenBdd) || + CalBddIsForwarded(elseBdd)){ + j++; + } + if (CalBddIsForwarded(thenBdd)) { + levels[CalBddGetThenBddId(thenBdd)]++; + } + if (CalBddIsForwarded(elseBdd)) { + levels[CalBddGetThenBddId(elseBdd)]++; + } + } + } + fprintf(stdout,"\tCofactors (%3d): ", j); + for (i=1; i<=bddManager->numVars; i++){ + if (levels[i]) { + fprintf(stdout,"%3d->%3d ", i, levels[i]); + } + } + fprintf(stdout,"\n"); + for (i=1; i<=bddManager->numVars; i++) { + levels[i] = 0; + } + j = 0; + requestNodeList = uniqueTableForId->startNode.nextBddNode; + for (bddNode = requestNodeList; bddNode; bddNode = nextBddNode){ + Cal_Assert(CalBddNodeIsForwarded(bddNode)); + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + Cal_Assert(!CalBddIsForwarded(thenBdd)); + levels[CalBddGetBddId(thenBdd)]++; + j++; + } + fprintf(stdout,"\tForwarded nodes (%3d): ", j); + for (i=1; i<=bddManager->numVars; i++){ + if (levels[i]) { + fprintf(stdout,"%3d->%3d ", i, levels[i]); + } + } + fprintf(stdout,"\n"); + } + Cal_MemFree(levels); +} +#endif + +/**Function******************************************************************** + + Synopsis [Reorder variables using "sift" algorithm.] + + Description [Reorder variables using "sift" algorithm.] + + SideEffects [None] + +******************************************************************************/ +static void +BddReorderVarSift(Cal_BddManager bddManager, double maxSizeFactor) +{ + int i,j; + int mostNodesId = -1; + long mostNodes, varNodes; + int *idArray; + long numVarsShifted = 0; + bddManager->numSwaps = 0; + + idArray = Cal_MemAlloc(int, bddManager->numVars); + for (i = 0; i < bddManager->numVars; i++) { + idArray[i] = bddManager->indexToId[i]; + } + + while (i && + (numVarsShifted <= + bddManager->maxNumVarsSiftedPerReordering) && + (bddManager->numSwaps <= + bddManager->maxNumSwapsPerReordering)){ + i--; + numVarsShifted++; +/* + * Find var with the most number of nodes and do sifting on it. + * idArray is used to make sure that a var is not sifted more than + * once. + */ + mostNodes = 0; + for (j = 0; j <= i; j++){ + varNodes = bddManager->uniqueTable[idArray[j]]->numEntries; + if (varNodes > mostNodes) { + mostNodes = varNodes; + mostNodesId = j; + } + } + + if (mostNodes <= 1) { /* I can put a different stopping criterion */ + /* + * Most number of nodes among the vars not sifted yet is 0. Stop. + */ + break; + } + + BddReorderSiftToBestPos(bddManager, + bddManager->idToIndex[idArray[mostNodesId]], + maxSizeFactor); + Cal_Assert(CalCheckAllValidity(bddManager)); + idArray[mostNodesId] = idArray[i]; + } + + Cal_MemFree(idArray); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddReorderSiftToBestPos(Cal_BddManager_t * bddManager, int + varStartIndex, double maxSizeFactor) +{ + long curSize; + long bestSize; + int bestIndex; + int varCurIndex; + int varId, i; + int lastIndex = bddManager->numVars - 1; + int numVars = bddManager->numVars; + long startSize = bddManager->numNodes; + long maxSize = startSize * maxSizeFactor; + int origId = bddManager->indexToId[varStartIndex]; + + int topMostSwapIndex = 0; /* the variable has been swapped upto this + index */ + int bottomMostSwapIndex = lastIndex; /* the variable has been + swapped upto this index */ + + int swapFlag = 0; /* If a swap has taken place after last cleaning + up */ + + + curSize = bestSize = bddManager->numNodes; + bestIndex = varStartIndex; + +#ifdef _CAL_VERBOSE + for (i=0; inumVars; i++){ + fprintf(stdout, "%3d ", bddManager->indexToId[i]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif + + /* + ** If varStartIndex > numVars/2, do: Down, Up, Down. + ** If varStartIndex < numVars/2, do: Up, Down, Up + ** Followed by a cleanup phase in either case. + */ + + if (varStartIndex >= (numVars >> 1)){ + /* Phase I: Downward swap, no forwarding check. */ + varCurIndex = varStartIndex; + while (varCurIndex < lastIndex) { + BddReorderSwapVarIndex(bddManager, varCurIndex, 0); + swapFlag = 1; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex+1, + varCurIndex+1); + swapFlag = 0; + } + varCurIndex++; + curSize = bddManager->numNodes; + /*if (curSize > maxSize){*/ + if (curSize >= (bestSize << 1)){ + bottomMostSwapIndex = varCurIndex; + break; + } + if (curSize < bestSize) { + bestSize = curSize; + bestIndex = varCurIndex; + } + } + + /* Phase II : Two parts */ + /* + ** Part One: Upward swap until varStartIndex. Fix cofactors and + ** fix double pointers. + */ + + while (varCurIndex > varStartIndex) { + varCurIndex--; + BddReorderSwapVarIndex(bddManager, varCurIndex, 1); + swapFlag = 1; + varId = bddManager->indexToId[varCurIndex]; + BddReorderFixForwardingNodes(bddManager, varId); + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex, + bottomMostSwapIndex); + swapFlag = 0; + } + } + curSize = startSize; + + /* + ** Part two: Upward swap all the way to the top. Fix cofactors. + */ + while (varCurIndex > 0) { + varCurIndex--; + BddReorderSwapVarIndex(bddManager, varCurIndex, 1); + swapFlag = 1; + curSize = bddManager->numNodes; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex, + bottomMostSwapIndex); + swapFlag = 0; + } + if (curSize > maxSize){ + topMostSwapIndex = varCurIndex; + break; + } + if (curSize <= bestSize) { + bestSize = curSize; + bestIndex = varCurIndex; + } + } + + if (swapFlag){ + /* Fix user BDD pointers and reclaim forwarding nodes */ + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalBddReorderFixUserBddPtrs(bddManager); + CalReorderAssociationFix(bddManager); + + /* The upward swapping might have stopped short */ + for (i = 0; i < topMostSwapIndex; i++){ + varId = bddManager->indexToId[i]; + CalBddReorderFixCofactors(bddManager, varId); + } + + CalBddReorderReclaimForwardedNodes(bddManager, topMostSwapIndex, + bottomMostSwapIndex); + swapFlag = 0; + } + + Cal_Assert(CalCheckAllValidity(bddManager)); + + /* Phase III : Swap to the min position */ + + while (varCurIndex < bestIndex) { + BddReorderSwapVarIndex(bddManager, varCurIndex, 0); + swapFlag = 1; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex+1, + varCurIndex+1); + swapFlag = 0; + } + varCurIndex++; + } + } + else{ + /* Phase I: Upward swap, fix cofactors. */ + varCurIndex = varStartIndex; + while (varCurIndex > 0) { + varCurIndex--; + BddReorderSwapVarIndex(bddManager, varCurIndex, 1); + swapFlag = 1; + curSize = bddManager->numNodes; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex+1, + varStartIndex); + swapFlag = 0; + } + if (curSize > maxSize){ + topMostSwapIndex = varCurIndex; + break; + } + if (curSize < bestSize) { + bestSize = curSize; + bestIndex = varCurIndex; + } + } + + if (swapFlag){ + /* Fix user BDD pointers and reclaim forwarding nodes */ + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalBddReorderFixUserBddPtrs(bddManager); + CalReorderAssociationFix(bddManager); + /* The upward swapping might have stopped short */ + for (i = 0; i < topMostSwapIndex; i++){ + varId = bddManager->indexToId[i]; + CalBddReorderFixCofactors(bddManager, varId); + } + CalBddReorderReclaimForwardedNodes(bddManager, topMostSwapIndex, + varStartIndex); + swapFlag = 0; + } + + Cal_Assert(CalCheckAllValidity(bddManager)); + + /* Phase II : Move all the way down : two parts */ + + /* Swap it to the original position, no cofactor fixing, fix + double pointers of the variable moving up.*/ + while (varCurIndex < varStartIndex){ + BddReorderSwapVarIndex(bddManager, varCurIndex, 0); + swapFlag = 1; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex+1, + varCurIndex+1); + swapFlag = 0; + } + varCurIndex++; + } + /* Swap to the bottom */ + while (varCurIndex < lastIndex){ + BddReorderSwapVarIndex(bddManager, varCurIndex, 0); + swapFlag = 1; + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + varCurIndex-1, + varCurIndex+1, + varCurIndex+1); + swapFlag = 0; + } + varCurIndex++; + curSize = bddManager->numNodes; + /* if (curSize > maxSize){ */ + if (curSize >= (bestSize << 1)){ + bottomMostSwapIndex = varCurIndex; + break; + } + if (curSize <= bestSize) { + bestSize = curSize; + bestIndex = varCurIndex; + } + } + + /* Phase III : Move up to the best position */ + while (varCurIndex > bestIndex){ + varCurIndex--; + BddReorderSwapVarIndex(bddManager, varCurIndex, 1); + swapFlag = 1; + varId = bddManager->indexToId[varCurIndex]; + BddReorderFixForwardingNodes(bddManager, varId); + if (bddManager->numForwardedNodes > bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, varCurIndex-1, + varCurIndex, + bottomMostSwapIndex); + swapFlag = 0; + } + } + } /* End of else clause (varStartIndex < numVars/2) */ + +#ifdef _CAL_VERBOSE + PrintBddProfileAfterReorder(bddManager); +#endif + + if (CalBddIdNeedsRepacking(bddManager, origId)){ + if (swapFlag){ + if (varStartIndex >= (numVars >> 1)){ + CalBddPackNodesAfterReorderForSingleId(bddManager, 0, + bestIndex, bestIndex); + } + /* + else if (bestIndex >= (numVars >> 1)){ + int i; + int nodeCounter = 0; + for (i=bestIndex; iuniqueTable[bddManager->indexToId[i]]->numEntries; + } + if ((bddManager->numNodes - nodeCounter) > + bddManager->numForwardedNodes){ + BddPackNodesAfterReorderForSingleId(bddManager, 1, bestIndex, + bottomMostSwapIndex); + } + else { + BddSiftPerfromPhaseIV(bddManager, varStartIndex, bestIndex, + bottomMostSwapIndex); + BddPackNodesAfterReorderForSingleId(bddManager, 0, + bestIndex, bestIndex); + } + } + */ + else { + /* Clean up - phase IV */ + BddSiftPerfromPhaseIV(bddManager, varStartIndex, bestIndex, + bottomMostSwapIndex); + CalBddPackNodesAfterReorderForSingleId(bddManager, 0, + bestIndex, bestIndex); + } + } + else { + CalBddPackNodesAfterReorderForSingleId(bddManager, 0, bestIndex, + bestIndex); + } + } + else if (swapFlag) { + /* clean up - phase IV */ + BddSiftPerfromPhaseIV(bddManager, varStartIndex, bestIndex, + bottomMostSwapIndex); + } + Cal_Assert(CalCheckAllValidity(bddManager)); + +#ifdef _CAL_VERBOSE + printf("ID = %3d SI = %3d EI = %3d Nodes = %7d\n", origId, + varStartIndex, bestIndex, bddManager->numNodes); +#endif + return bestIndex; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddSiftPerfromPhaseIV(Cal_BddManager_t *bddManager, int varStartIndex, + int bestIndex, int bottomMostSwapIndex) +{ + int varCurIndex, varId; + + +/* We need to perform phase IV */ + varCurIndex = bestIndex-1; + while (varCurIndex >= 0) { + varId = bddManager->indexToId[varCurIndex]; + CalBddReorderFixCofactors(bddManager, varId); + varCurIndex--; + } + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalBddReorderFixUserBddPtrs(bddManager); + CalReorderAssociationFix(bddManager); + if (varStartIndex >= (bddManager->numVars >> 1)){ + CalBddReorderReclaimForwardedNodes(bddManager, bestIndex, bestIndex); + } + else { + CalBddReorderReclaimForwardedNodes(bddManager, bestIndex, + bottomMostSwapIndex); + } +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderVarWindow(Cal_BddManager bddManager, char *levels) +{ + long i; + int moved; + int anySwapped; + int even; + int lastIndex = bddManager->numVars-1; + +#ifdef _CAL_VERBOSE + for (i=0; inumVars; i++){ + fprintf(stdout, "%3d ", bddManager->indexToId[i]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif + for (i=0; i < bddManager->numVars-1; i++) levels[i]=1; + even = 1; + do { + anySwapped=0; + if (even){ + /*fprintf(stdout, "Downward Swap\n");*/ + for (i=0; i < bddManager->numVars-1; i++){ + if (levels[i]) { + if (i < bddManager->numVars-2) { + moved = BddReorderWindow3(bddManager, i, 0); + if (bddManager->numForwardedNodes > + bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + i-1, 0, i+2); + CalBddPackNodesForMultipleIds(bddManager, + bddManager->indexToId[i], 3); + } + } + else { + moved = BddReorderWindow2(bddManager, i, 0); + } + if (moved){ + if (i > 0) { + levels[i-1]=1; + if (i > 1) levels[i-2]=1; + } + levels[i]=1; + levels[i+1]=1; + if (i < bddManager->numVars-2) { + levels[i+2]=1; + if (i < bddManager->numVars-3) { + levels[i+3]=1; + if (i < bddManager->numVars-4) levels[i+4]=1; + } + } + anySwapped=1; + } + else { + levels[i]=0; + } + } + } + /* new code added */ + for (i = bddManager->numVars-1; i >= 0; i--){ + CalBddReorderFixCofactors(bddManager, bddManager->indexToId[i]); + } + CalBddReorderFixUserBddPtrs(bddManager); + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalReorderAssociationFix(bddManager); + CalBddReorderReclaimForwardedNodes(bddManager, 0, lastIndex); + /*even = 0;*/ + } + else{ + /*fprintf(stdout, "Upward Swap\n");*/ + for (i=bddManager->numVars-1; i > 0; i--){ + /* + * Fix the then and else cofactors. We need to fix it, even + * if this level is not supposed to be moved. + */ + if (i > 1) { + CalBddReorderFixCofactors(bddManager, + bddManager->indexToId[i-2]); + } + else { + CalBddReorderFixCofactors(bddManager, + bddManager->indexToId[i-1]); + } + if (levels[i]) { + if (i > 1) { + moved = BddReorderWindow3(bddManager, i-2, 1); + if (bddManager->numForwardedNodes > + bddManager->maxForwardedNodes){ + CofactorFixAndReclaimForwardedNodes(bddManager, 0, + i-3, 0, + lastIndex); + CalBddPackNodesForMultipleIds(bddManager, + bddManager->indexToId[i-2], 3); + } + } + else { + moved = BddReorderWindow2(bddManager, i-1, 1); + } + if (moved){ + if (i < bddManager->numVars-1) { + levels[i+1]=1; + if (i < bddManager->numVars-2) { + levels[i+2]=1; + if (i < bddManager->numVars-3) { + levels[i+3]=1; + if (i < bddManager->numVars-4) { + levels[i+4]=1; + } + } + } + } + levels[i]=1; + levels[i-1]=1; + if (i > 1) { + levels[i-2]=1; + } + anySwapped=1; + } + else { + levels[i]=0; + } + } + } + even = 1; + CalBddReorderFixUserBddPtrs(bddManager); + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalReorderAssociationFix(bddManager); + CalBddReorderReclaimForwardedNodes(bddManager, 0, lastIndex); + } + } + while (anySwapped); + if (!even){ /* Need to do pointer fixing */ + for (i = bddManager->numVars-1; i >= 0; i--){ + CalBddReorderFixCofactors(bddManager, bddManager->indexToId[i]); + } + CalBddReorderFixUserBddPtrs(bddManager); + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + CalReorderAssociationFix(bddManager); + CalBddReorderReclaimForwardedNodes(bddManager, 0, lastIndex); + } + Cal_Assert(CalCheckAllValidity(bddManager)); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddReorderWindow2(Cal_BddManager bddManager, long index, int directionFlag) +{ + long curSize, startSize; + + startSize = bddManager->numNodes; + BddReorderSwapVarIndex(bddManager, index, 0); + curSize = bddManager->numNodes; + if (curSize > startSize){ + BddReorderSwapVarIndex(bddManager, index, 0); + } + if (directionFlag){/* Upward window swap */ + BddReorderFixAndFreeForwardingNodes(bddManager, + bddManager->indexToId[index], + bddManager->numVars-index); + } + else{ + BddReorderFixAndFreeForwardingNodes(bddManager, + bddManager->indexToId[index], 2); + } + Cal_Assert(CalCheckValidityOfNodesForWindow(bddManager, index, 2)); + return (curSize < startSize); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddReorderWindow3(Cal_BddManager bddManager, long index, int directionFlag) +{ + int best; + long curSize, bestSize; + long origSize = bddManager->numNodes; + + /* 1 2 3 */ + best = 0; + bestSize = bddManager->numNodes; + BddReorderSwapVarIndex(bddManager, index, 0); + /* 2 1 3 */ + curSize = bddManager->numNodes; + if (curSize < bestSize){ + best = 1; + bestSize = curSize; + } + BddReorderSwapVarIndex(bddManager, index+1, 0); + /* 2 3 1 */ + curSize = bddManager->numNodes; + if (curSize < bestSize){ + best = 2; + bestSize = curSize; + } + BddReorderSwapVarIndex(bddManager, index, 1); + /* 3 2 1 */ + curSize = bddManager->numNodes; + if (curSize <= bestSize){ + best = 3; + bestSize = curSize; + } + BddReorderSwapVarIndex(bddManager, index+1, 0); + /* 3 1 2 */ + curSize = bddManager->numNodes; + if (curSize <= bestSize){ + best = 4; + bestSize = curSize; + } + BddReorderSwapVarIndex(bddManager, index, 1); + /* 1 3 2 */ + curSize = bddManager->numNodes; + if (curSize <= bestSize){ + best = 5; + bestSize = curSize; + } + switch (best) { + case 0: + BddReorderSwapVarIndex(bddManager, index+1, 0); + break; + case 1: + BddReorderSwapVarIndex(bddManager, index+1, 0); + BddReorderSwapVarIndex(bddManager, index, 1); + break; + case 2: + BddReorderSwapVarIndex(bddManager, index, 0); + BddReorderSwapVarIndex(bddManager, index+1, 0); + BddReorderSwapVarIndex(bddManager, index, 1); + break; + case 3: + BddReorderSwapVarIndex(bddManager, index, 0); + BddReorderSwapVarIndex(bddManager, index+1, 0); + break; + case 4: + BddReorderSwapVarIndex(bddManager, index, 0); + break; + case 5: + break; + } + if ((best == 0) || (best == 3)){ + CalBddReorderFixCofactors(bddManager, bddManager->indexToId[index]); + } + if (directionFlag){/* Upward window swap */ + BddReorderFixAndFreeForwardingNodes(bddManager, + bddManager->indexToId[index], + bddManager->numVars-index); + } + else{ + BddReorderFixAndFreeForwardingNodes(bddManager, + bddManager->indexToId[index], 3); + } + Cal_Assert(CalCheckValidityOfNodesForWindow(bddManager, index, 3)); + return ((best > 0) && (origSize > bestSize)); +} + diff --git a/calReorderDF.c b/calReorderDF.c new file mode 100644 index 0000000..af8bf45 --- /dev/null +++ b/calReorderDF.c @@ -0,0 +1,1584 @@ +/**CFile*********************************************************************** + + FileName [calReorderDF.c] + + PackageName [cal] + + Synopsis [Routines for dynamic reordering of variables.] + + Description [This method is based on traditional dynamic reordering + technique found in depth-first based packages. The data structure is + first converted to conform to traditional one and then reordering is + performed. At the end the nodes are arranged back on the pages. The + computational overheads are in terms of converting the data + structure back and forth and the memory overhead due to the extra + space needed to arrange the nodes. This overhead can be eliminated + by proper implementation. For details, please refer to the work by + Rajeev K. Ranjan et al - "Dynamic variable reordering in a + breadth-first manipulation based package: Challenges and Solutions"- + Proceedings of ICCD'97.] + + SeeAlso [calReorderBF.c calReorderUtil.c] + + Author [Rajeev K. Ranjan (rajeev@@ic. eecs.berkeley.edu)] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static CalNodeManager_t *nodeManager; +static int freeListId; + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +/* These macros are needed because we are dealing with a new data + structures of the BDD nodes */ + +#define BddNodeIcrRefCount(f) \ +{ \ + CalBddNode_t *_bddNode = CAL_BDD_POINTER(f); \ + if (_bddNode->elseBddId < CAL_MAX_REF_COUNT){ \ + _bddNode->elseBddId++; \ + } \ +} + +#define BddNodeDcrRefCount(f) \ +{ \ + CalBddNode_t *_bddNode = CAL_BDD_POINTER(f); \ + if ((_bddNode->elseBddId < CAL_MAX_REF_COUNT) && (_bddNode->elseBddId)){ \ + _bddNode->elseBddId--; \ + } \ + else if (_bddNode->elseBddId == 0){ \ + CalBddWarningMessage("Trying to decrement reference count below zero"); \ + } \ +} + +#define BddGetCofactors(bddManager, f, id, fThen, fElse) \ +{ \ + CalBddNode_t *_bddNode = CAL_BDD_POINTER(f); \ + Cal_Assert(bddManager->idToIndex[_bddNode->thenBddId] <= \ + bddManager->idToIndex[id]); \ + if (bddManager->idToIndex[_bddNode->thenBddId] == \ + bddManager->idToIndex[id]){ \ + fThen = _bddNode->thenBddNode; \ + fElse = _bddNode->elseBddNode; \ + } \ + else{ \ + fThen = fElse = f; \ + } \ +} + +#define BddNodeGetThenBddNode(bddNode) \ +((CalBddNode_t*) ((CalAddress_t) \ + (CAL_BDD_POINTER(bddNode)->thenBddNode) \ + ^ (CAL_TAG0(bddNode)))) + +#define BddNodeGetElseBddNode(bddNode) \ +((CalBddNode_t*) ((CalAddress_t) \ + (CAL_BDD_POINTER(bddNode)->elseBddNode) \ + ^ (CAL_TAG0(bddNode)))) + + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static int UniqueTableForIdFindOrAdd(Cal_BddManager_t * bddManager, CalHashTable_t * hashTable, CalBddNode_t *thenBdd, CalBddNode_t *elseBdd, CalBddNode_t **bddPtr); +static void HashTableAddDirect(CalHashTable_t * hashTable, CalBddNode_t *bddNode); +static int HashTableFindOrAdd(Cal_BddManager_t *bddManager, CalHashTable_t *hashTable, CalBddNode_t *thenBdd, CalBddNode_t *elseBdd, CalBddNode_t **bddPtr); +static void BddConvertDataStruct(Cal_BddManager_t *bddManager); +static void BddConvertDataStructBack(Cal_BddManager_t *bddManager); +static void BddReallocateNodes(Cal_BddManager_t *bddManager); +static void BddExchangeAux(Cal_BddManager_t *bddManager, CalBddNode_t *f, int id, int nextId); +static int CheckValidityOfNodes(Cal_BddManager_t *bddManager, long id); +static void SweepVarTable(Cal_BddManager_t *bddManager, long id); +static void BddExchange(Cal_BddManager_t *bddManager, long id); +static void BddExchangeVarBlocks(Cal_BddManager_t *bddManager, Cal_Block parent, long blockIndex); +static int BddReorderWindow2(Cal_BddManager_t *bddManager, Cal_Block block, long i); +static int BddReorderWindow3(Cal_BddManager_t *bddManager, Cal_Block block, long i); +static void BddReorderStableWindow3Aux(Cal_BddManager_t *bddManager, Cal_Block block, char *levels); +static void BddReorderStableWindow3(Cal_BddManager_t *bddManager); +static void BddSiftBlock(Cal_BddManager_t *bddManager, Cal_Block block, long startPosition, double maxSizeFactor); +static void BddReorderSiftAux(Cal_BddManager_t *bddManager, Cal_Block block, Cal_Block *toSift, double maxSizeFactor); +static void BddReorderSift(Cal_BddManager_t *bddManager, double maxSizeFactor); +static int CeilLog2(int number); + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderAuxDF(Cal_BddManager_t *bddManager) +{ + CalHashTableGC(bddManager, bddManager->uniqueTable[0]); + /*Cal_BddManagerGC(bddManager);Cal_Assert(CalCheckAllValidity(bddManager));*/ + /* If we want to check the validity, we need to garbage collect */ + CalInitInteract(bddManager); /* Initialize the interaction matrix + before changing the data structure */ + nodeManager = CalNodeManagerInit(bddManager->pageManager2); + freeListId = 1; +#ifdef _CAL_QUANTIFY_ + quantify_start_recording_data(); +#endif + BddConvertDataStruct(bddManager); + if (bddManager->reorderTechnique == CAL_REORDER_WINDOW){ + BddReorderStableWindow3(bddManager); + } + else { + BddReorderSift(bddManager, bddManager->maxSiftingGrowth); + } + BddReallocateNodes(bddManager); + BddConvertDataStructBack(bddManager); +#ifdef _CAL_QUANTIFY_ + quantify_stop_recording_data(); +#endif + nodeManager->numPages = 0; /* Since these pages have already been + freed */ + CalNodeManagerQuit(nodeManager); + Cal_Assert(CalCheckAllValidity(bddManager)); + Cal_MemFree(bddManager->interact); + bddManager->numReorderings++; +} + + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +static void +NodeManagerAllocNode(Cal_BddManager_t *bddManager, CalBddNode_t **nodePtr) +{ + /* First check the free list of bddManager */ + if (nodeManager->freeNodeList){ + *nodePtr = nodeManager->freeNodeList; + nodeManager->freeNodeList = + ((CalBddNode_t *)(*nodePtr))->nextBddNode; + } + else{ + if (freeListId < bddManager->numVars){ + /* Find the next id with free list */ + for (; freeListId <= bddManager->numVars; freeListId++){ + CalNodeManager_t *nodeManagerForId = + bddManager->nodeManagerArray[freeListId]; + if (nodeManagerForId->freeNodeList){ + *nodePtr = nodeManagerForId->freeNodeList; + nodeManagerForId->freeNodeList = (CalBddNode_t *)0; + nodeManager->freeNodeList = + ((CalBddNode_t *)(*nodePtr))->nextBddNode; + break; + } + } + } + } + if (!(*nodePtr)){ + /* Create a new page */ + CalBddNode_t *_freeNodeList, *_nextNode, *_node; + _freeNodeList = + (CalBddNode_t *)CalPageManagerAllocPage(nodeManager->pageManager); + for(_node = _freeNodeList + NUM_NODES_PER_PAGE - 1, _nextNode =0; + _node != _freeNodeList; _nextNode = _node--){ + _node->nextBddNode = _nextNode; + } + nodeManager->freeNodeList = _freeNodeList + 1; + *nodePtr = _node; + if (nodeManager->numPages == nodeManager->maxNumPages){ + nodeManager->maxNumPages *= 2; + nodeManager->pageList = + Cal_MemRealloc(CalAddress_t *, nodeManager->pageList, + nodeManager->maxNumPages); + } + nodeManager->pageList[nodeManager->numPages++] = + (CalAddress_t *)_freeNodeList; + } +} + +/**Function******************************************************************** + + Synopsis [find or add in the unique table for id.] + + Description [optional] + + SideEffects [If a new BDD node is created (found == false), then the + numNodes field of the manager needs to be incremented.] + + SeeAlso [optional] + +******************************************************************************/ +static int +UniqueTableForIdFindOrAdd(Cal_BddManager_t * bddManager, + CalHashTable_t * hashTable, + CalBddNode_t *thenBdd, + CalBddNode_t *elseBdd, + CalBddNode_t **bddPtr) +{ + int found = 0; + if (thenBdd == elseBdd){ + *bddPtr = thenBdd; + found = 1; + } + else if(CalBddNodeIsOutPos(thenBdd)){ + found = HashTableFindOrAdd(bddManager, hashTable, thenBdd, elseBdd, bddPtr); + } + else{ + found = HashTableFindOrAdd(bddManager, hashTable, + CalBddNodeNot(thenBdd), + CalBddNodeNot(elseBdd), bddPtr); + *bddPtr = CalBddNodeNot(*bddPtr); + } + if (!found) bddManager->numNodes++; + return found; +} + +/**Function******************************************************************** + + Synopsis [Directly insert a BDD node in the hash table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +HashTableAddDirect(CalHashTable_t * hashTable, CalBddNode_t *bddNode) +{ + int hashValue; + CalBddNode_t *thenBddNode, *elseBddNode; + + hashTable->numEntries++; + if(hashTable->numEntries >= hashTable->maxCapacity){ + CalHashTableRehash(hashTable, 1); + } + thenBddNode = bddNode->thenBddNode; + Cal_Assert(CalBddNodeIsOutPos(thenBddNode)); + elseBddNode = bddNode->elseBddNode; + hashValue = CalDoHash2(thenBddNode, elseBddNode, hashTable); + bddNode->nextBddNode = hashTable->bins[hashValue]; + hashTable->bins[hashValue] = bddNode; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +HashTableFindOrAdd(Cal_BddManager_t *bddManager, CalHashTable_t + *hashTable, CalBddNode_t *thenBdd, + CalBddNode_t *elseBdd, CalBddNode_t **bddPtr) +{ + CalBddNode_t *ptr; + int hashValue; + + Cal_Assert(CalBddNodeIsOutPos(thenBdd)); + hashValue = CalDoHash2(thenBdd, elseBdd, hashTable); + for (ptr = hashTable->bins[hashValue]; ptr; ptr = ptr->nextBddNode){ + if ((ptr->thenBddNode == thenBdd) && + (ptr->elseBddNode == elseBdd)){ + *bddPtr = ptr; + return 1; + } + } + hashTable->numEntries++; + if(hashTable->numEntries > hashTable->maxCapacity){ + CalHashTableRehash(hashTable,1); + hashValue = CalDoHash2(thenBdd, elseBdd, hashTable); + } + + NodeManagerAllocNode(bddManager, &ptr); + + ptr->thenBddNode = thenBdd; + ptr->elseBddNode = elseBdd; + ptr->nextBddNode = hashTable->bins[hashValue]; + ptr->thenBddId = hashTable->bddId; + ptr->elseBddId = 0; + hashTable->bins[hashValue] = ptr; + *bddPtr = ptr; + return 0; +} + + +/**Function******************************************************************** + + Synopsis [Changes the data structure of the bdd nodes.] + + Description [New data structure: thenBddId -> id + elseBddId -> ref count] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddConvertDataStruct(Cal_BddManager_t *bddManager) +{ + CalBddNode_t *bddNode, **bins, *thenBddNode, *elseBddNode, + *next = Cal_Nil(CalBddNode_t); + CalBddNode_t *last; + long numBins; + int i, refCount, id, index; + long oldNumEntries; + CalHashTable_t *uniqueTableForId; + + if (bddManager->numPeakNodes < bddManager->numNodes){ + bddManager->numPeakNodes = bddManager->numNodes; + } + + for(index = 0; index < bddManager->numVars; index++){ + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + oldNumEntries = uniqueTableForId->numEntries; + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + for(i = 0; i < numBins; i++){ + last = NULL; + bddNode = uniqueTableForId->bins[i]; + while(bddNode != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetRefCount(bddNode, refCount); + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + if(refCount == 0){ + if (last == NULL){ + uniqueTableForId->bins[i] = next; + } + else{ + last->nextBddNode = next; + } + CalBddNodeDcrRefCount(CAL_BDD_POINTER(thenBddNode)); + CalBddNodeDcrRefCount(CAL_BDD_POINTER(elseBddNode)); + CalNodeManagerFreeNode(nodeManager, bddNode); + uniqueTableForId->numEntries--; + } + else { + bddNode->thenBddId = id; + bddNode->elseBddId = refCount; + bddNode->nextBddNode = next; + bddNode->thenBddNode = thenBddNode; + bddNode->elseBddNode = elseBddNode; + last = bddNode; + } + bddNode = next; + } + } + if ((uniqueTableForId->numBins > uniqueTableForId->numEntries) && + (uniqueTableForId->sizeIndex > HASH_TABLE_DEFAULT_SIZE_INDEX)){ + CalHashTableRehash(uniqueTableForId, 0); + } + bddManager->numNodes -= oldNumEntries - uniqueTableForId->numEntries; + bddManager->numNodesFreed += oldNumEntries - uniqueTableForId->numEntries; + } + id = 0; + uniqueTableForId = bddManager->uniqueTable[id]; + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + for(i = 0; i < numBins; i++){ + bddNode = uniqueTableForId->bins[i]; + while(bddNode != Cal_Nil(CalBddNode_t)){ + next = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetRefCount(bddNode, refCount); + Cal_Assert(refCount); + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + bddNode->thenBddId = id; + bddNode->elseBddId = refCount; + bddNode->nextBddNode = next; + bddNode->thenBddNode = thenBddNode; + bddNode->elseBddNode = elseBddNode; + bddNode = next; + } + } + bddNode = bddManager->bddOne.bddNode; + CalBddNodeGetRefCount(bddNode, refCount); + Cal_Assert(refCount); + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + bddNode->thenBddId = id; + bddNode->elseBddId = refCount; + bddNode->nextBddNode = next; + bddNode->thenBddNode = thenBddNode; + bddNode->elseBddNode = elseBddNode; +} + + +/**Function******************************************************************** + + Synopsis [Changes the data structure of the bdd nodes to + the original one.] + + Description [Data structure conversion: thenBddId -> id + elseBddId -> ref count] + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddConvertDataStructBack(Cal_BddManager_t *bddManager) +{ + Cal_Bdd_t thenBdd, elseBdd; + + CalBddNode_t *bddNode, *nextBddNode, **bins; + long numBins; + int i, id, index; + CalHashTable_t *uniqueTableForId; + uniqueTableForId = bddManager->uniqueTable[0]; + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + for(i = 0; i < numBins; i++) { + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodePutRefCount(bddNode, bddNode->elseBddId); + bddNode->thenBddId = CAL_BDD_POINTER(bddNode->thenBddNode)->thenBddId; + bddNode->elseBddId = CAL_BDD_POINTER(bddNode->elseBddNode)->thenBddId; + } + } + for(index = 0; index < bddManager->numVars; index++){ + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + for(i = 0; i < numBins; i++) { + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodePutRefCount(bddNode, bddNode->elseBddId); + bddNode->thenBddId = CAL_BDD_POINTER(bddNode->thenBddNode)->thenBddId; + bddNode->elseBddId = CAL_BDD_POINTER(bddNode->elseBddNode)->thenBddId; + Cal_Assert(!CalBddNodeIsForwarded(bddNode)); + Cal_Assert(!CalBddNodeIsRefCountZero(bddNode)); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + Cal_Assert(CalBddIsForwarded(elseBdd) == 0); + } + } + } + bddNode = bddManager->bddOne.bddNode; + CalBddNodePutRefCount(bddNode, bddNode->elseBddId); + bddNode->thenBddId = 0; + bddNode->elseBddId = 0; +} + +#ifdef _FOO_ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReallocateNodesInPlace(Cal_BddManager_t *bddManager) +{ + Cal_Address_t *pageSegment; + CalPageManager_t *pageManager; + CalHashTable_t *uniqueTable; + CalNodeManager_t *nodeManager; + int index, id, i, pageCounter, numUsefulSegments, segmentCounter; + + /* Initialize and set up few things */ + pageManager = bddManager->pageManager; + uniqueTable = bddManager->uniqueTable; + for (id = 1; id <= bddManager->numVars; id++){ + numPagesRequired = + uniqueTable[id]->numEntries/NUM_NODES_PER_PAGE+1; + nodeManager = uniqueTable[id]->nodeManager; + /* Clear out the page list of the node manager */ + for (i=0; imaxNumPages; i++){ + nodeManager->pageList[i] = 0; + } + nodeManager->freeNodeList = (CalBddNode_t *)0; + nodeManager->numPages = numPagesRequired; + Cal_Assert(nodeManager->maxNumPages >= numPagesRequired); + for (i = 0; inumPagesArray[segmentCounter]){ + pageCounter = 0; + segmentCounter++; + pageSegment = pageManager->pageSegmentArray[segmentCounter]; + } + nodeManager->pageList[i] = pageSegment[pageCounter]; + } + } + numUsefulSegments = segmentCounter+1; + numUsefulPagesInLastSegment = pageCounter+1; + + /* Traverse all the nodes belonging in each page */ + /* Put the destination addresses in the next pointer */ + for (numSegment=0; numSegment < pageManager->numSegments; + numSegment++){ + for (numPage = 0, page = pageManager->pageSegmentArray[numSegment]; + numPage < pageManager->numPagesArray[numSegment]; + page += PAGE_SIZE, numPage++){ + for (bddNode = (CalBddNode_t*) page, numNode = 0; + numNode < NUM_NODES_PER_PAGE; numNode++, bddNode += 1){ + /* If the node is not useful, continue */ + if (bddNode->elseBddId == 0) continue; + /* Find out the destination address */ + bddId = bddNode->thenBddId; + nodeCounter[bddId]++; + if (nodeCounter[bddId] == NUM_NODES_PER_PAGE){ + pageCounter[bddId]++; + nodePointerArray[bddId] = + pageListArray[bddId][pageCounter[bddId]]; + nodeCounter[bddId] = 0; + } + bddNode->nextBddNode = nodePointerArray[bddId]; + nodePointerArray[bddId] += 1; + } + } + } + /* Traverse all the nodes belonging in each page */ + /* Update the contents */ + for (numSegment=0; numSegment < pageManager->totalNumSegments; + numSegment++){ + for (numPage = 0, page = pageManager->pageSegmentArray[numSegment]; + numPage < pageManager->numPagesArray[numSegment]; + page += PAGE_SIZE, numPage++){ + for (bddNode = (CalBddNode_t*) page, numNode = 0; + numNode < NUM_NODES_PER_PAGE; numNode++, bddNode += 1){ + /* If the node is not useful, continue */ + if (bddNode->elseBddId == 0) continue; + /* If the node has been visited, continue */ + if ((CalAddress_t)bddNode->nextBddNode & 01) continue; + /* If the nodes is supposed to remain at the same place, + update the then and else pointers and continue */ + if (((CalAddress_t) bddNode->nextBddNode &~01) == + ((CalAddress_t) bddNode & ~01)){ + CalBddNodeUpdatebddNode(bddNode); + continue; + } + origNode = bddNode; /* Remember the address */ + /* Update the contents */ + thenBddNode = bddNode->thenBddNode; + elseBddNode = bddNode->elseBddNode; + thenBddId = bddNode->thenBddId; + elseBddId = bddNode->elseBddId; + do{ + thenBddNode = UpdateThenBddNode(thenBddNode); + elseBddNode = UpdateElseBddNode(elseBddNode); + destinationNode = bddNode->nextBddNode; + /* Mark the node visited */ + bddNode->nextBddNode = (CalBddNode_t *) + ((CalAddress_t)bddNode->nextBddNode | 01); + thenBddNode2 = destinationNode->thenBddNode; + elseBddNode2 = destinationNode->elseBddNode; + thenBddId2 = destinationNode->thenBddId; + elseBddId2 = destinationNode->elseBddId; + destinationNode->thenBddNode = thenBddNode; + destinationNode->elseBddNode = elseBddNode; + destinationNode->thenBddId = thenBddId; + destinationNode->elseBddId = elseBddId; + bddNode = destinationNode; + thenBddNode = thenBddNode2; + elseBddNode = elseBddNode2; + thenBddId = thenBddId2; + elseBddId = elseBddId2; + } while ((elseBddId != 0) && (bddNode != origNode) && + !((CalAddress_t)(bddNode->nextBddNode) & 01)); + } + } + } + /* Fix the handles to the nodes being moved */ + for (id = 1; id <= bddManager->numVars; id++){ + /* Fix the varBdd array */ + } +/* Need to update the handles to the nodes being moved */ + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodesAfterReallocation(bddManager); + } + + /* Fix the user BDDs */ + CalBddReorderFixUserBddPtrsAfterReallocation(bddManager); + + /* Fix the association */ + CalReorderAssociationFixAfterReallocation(bddManager); + + Cal_Assert(CalCheckAssoc(bddManager)); + + + /* Update the next pointers */ + /* Since the pages for the ids are distributed in the uniform + manner, we can scan the pages on id by id basis without any + disadvantage */ + for (id = 1; id <= bddManager->numVars; id++){ + nodeManager = uniqueTable[id]->nodeManager; + freeNodeList = Cal_Nil(CalBddNode_t); + for (i=0; inumPages; i++){ + page = nodeManager->pageList[i]; + for (bddNode = (CalBddNode_t*) page, numNode = 0; + numNode < NUM_NODES_PER_PAGE; numNode++, bddNode += 1){ + /* If the node is not useful, put it in the free list */ + if ((bddNode->elseBddId == 0) || (bddNode->elseBddNode == 0)){ + bddNode->nextBddNode = freeNodeList; + freeNodeList = bddNode; + } + } + } + nodeManager->freeNodeList = freeNodeList; + } + /* We should put the unused pages in the free page list */ + pageSegment = pageManager->pageSegmentArray[numUsefulSegments-1]; + for (pageCounter = numUsefulPagesInLastSegment; + pageCounter < pageSegment->numPages ; pageCounter++){ + CalPageManagerFreePage(pageManager, pageSegment[pageCounter]); + } + /* We have to free up the unnecessary page segments;*/ + for (i = numUsefulSegments; i < pageManager->numSegments; i++){ + free(pageManager->pageSegmentArray[i]); + pageManager->pageSegmentArray[i] = 0; + } + pageManager->numSegments = numUsefulSegments; +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalAlignCollisionChains(Cal_BddManager_t *bddManager) +{ + /* First find out the pages corresponding to each variable */ + Cal_Address_t ***pageListArray = Cal_MemAlloc(Cal_Address_t **, + bddManager->numVars+1); + for (id = 1; id <= bddManager->numVars; id++){ + nodeManager = bddManager->nodeManagerArray[id]; + numPages = nodeManager->numPages; + pageListArray[id] = Cal_MemAlloc(Cal_Address_t *, numPages); + for (i=0; ipageList[i]; + } + } + + /* Bottom up traversal */ + for (index = bddManager->numVars-1; index >= 0; index--){ + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + nodeManager = uniqueTableForId->nodeManager; + /* Calculate the collision lengths */ + collisionLengthArray = CalculateCollisionLength(uniqueTableForId); + /* Initialize the bins */ + bins = uniqueTableForId->bins; + numBins = uniqueTableForId->numBins; + numNodes = 0; + pageNum = 0; + for (i=0; inextBddNode = nodeManager->freeNodeList; + nodeManager->freeNodeList = nodePointer; + nodePointer[i] = pageListArray[id][++pageNum]+collisionLengthArray[i]; + numNodes = collisionLengthArray[i]; + } + } + } +} +#endif + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReallocateNodes(Cal_BddManager_t *bddManager) +{ + int i; + int index; + CalNodeManager_t *nodeManager; + CalPageManager_t *pageManager; + int numSegments; + CalAddress_t **pageSegmentArray; + + pageManager = bddManager->pageManager2; + numSegments = pageManager->numSegments; + pageSegmentArray = pageManager->pageSegmentArray; + + /* Reinitialize the page manager */ + pageManager->totalNumPages = 0; + pageManager->numSegments = 0; + pageManager->maxNumSegments = MAX_NUM_SEGMENTS; + pageManager->pageSegmentArray + = Cal_MemAlloc(CalAddress_t *, pageManager->maxNumSegments); + pageManager->freePageList = Cal_Nil(CalAddress_t); + + /* Do a bottom up traversal */ + + for (index = bddManager->numVars-1; index >= 0; index--){ + int id; + CalHashTable_t *uniqueTableForId; + int numPagesRequired, newSizeIndex; + CalBddNode_t *bddNode, *dupNode, *thenNode, *elseNode, **oldBins; + long hashValue, oldNumBins; + + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + nodeManager = bddManager->nodeManagerArray[id]; + oldBins = uniqueTableForId->bins; + oldNumBins = uniqueTableForId->numBins; + nodeManager->freeNodeList = Cal_Nil(CalBddNode_t); + nodeManager->numPages = 0; + numPagesRequired = + uniqueTableForId->numEntries/NUM_NODES_PER_PAGE; + nodeManager->maxNumPages = + 2*(numPagesRequired ? numPagesRequired : 1); + Cal_MemFree(nodeManager->pageList); + nodeManager->pageList = Cal_MemAlloc(CalAddress_t *, + nodeManager->maxNumPages); + /* Create the new set of bins */ + newSizeIndex = + CeilLog2(uniqueTableForId->numEntries/HASH_TABLE_DEFAULT_MAX_DENSITY); + if (newSizeIndex < HASH_TABLE_DEFAULT_SIZE_INDEX){ + newSizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; + } + uniqueTableForId->sizeIndex = newSizeIndex; + uniqueTableForId->numBins = TABLE_SIZE(uniqueTableForId->sizeIndex); + uniqueTableForId->maxCapacity = + uniqueTableForId->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; + + uniqueTableForId->bins = Cal_MemAlloc(CalBddNode_t *, + uniqueTableForId->numBins); + memset((char *)uniqueTableForId->bins, 0, + uniqueTableForId->numBins*sizeof(CalBddNode_t *)); + for (i=0; inextBddNode){ + CalNodeManagerAllocNode(nodeManager, dupNode); + thenNode = bddNode->thenBddNode; + CalBddNodeIsForwardedTo(thenNode); + Cal_Assert(thenNode); + Cal_Assert(!CalBddNodeIsForwarded(thenNode)); + elseNode = bddNode->elseBddNode; + CalBddNodeIsForwardedTo(elseNode); + Cal_Assert(elseNode); + Cal_Assert(!CalBddNodeIsForwarded(CAL_BDD_POINTER(elseNode))); + Cal_Assert(bddManager->idToIndex[bddNode->thenBddId] < + bddManager->idToIndex[thenNode->thenBddId]); + Cal_Assert(bddManager->idToIndex[bddNode->thenBddId] < + bddManager->idToIndex[CAL_BDD_POINTER(elseNode)->thenBddId]); + dupNode->thenBddNode = thenNode; + dupNode->elseBddNode = elseNode; + dupNode->thenBddId = bddNode->thenBddId; + dupNode->elseBddId = bddNode->elseBddId; + hashValue = CalDoHash2(thenNode, elseNode, uniqueTableForId); + dupNode->nextBddNode = uniqueTableForId->bins[hashValue]; + uniqueTableForId->bins[hashValue] = dupNode; + bddNode->thenBddNode = dupNode; + bddNode->elseBddNode = (CalBddNode_t *)0; + bddNode->thenBddId = id; + Cal_Assert(bddManager->idToIndex[dupNode->thenBddId] < + bddManager->idToIndex[thenNode->thenBddId]); + Cal_Assert(bddManager->idToIndex[dupNode->thenBddId] < + bddManager->idToIndex[CAL_BDD_POINTER(elseNode)->thenBddId]); + } + } + Cal_MemFree(oldBins); + CalBddIsForwardedTo(bddManager->varBdds[id]); + } + + if (bddManager->pipelineState == CREATE){ + /* There are some results computed in pipeline */ + CalBddReorderFixProvisionalNodes(bddManager); + } + + /* Fix the user BDDs */ + CalBddReorderFixUserBddPtrs(bddManager); + + /* Fix the association */ + CalReorderAssociationFix(bddManager); + + Cal_Assert(CalCheckAssoc(bddManager)); + + /* Free the page manager related stuff*/ + for(i = 0; i < numSegments; i++){ + free(pageSegmentArray[i]); + } + Cal_MemFree(pageSegmentArray); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExchangeAux(Cal_BddManager_t *bddManager, CalBddNode_t *f, + int id, int nextId) +{ + CalBddNode_t *f0, *f1; + CalBddNode_t *f00, *f01, *f10, *f11; + CalBddNode_t *newF0, *newF1; + int f0Found, f1Found; + int fIndex; + + f0 = f->elseBddNode; + f1 = f->thenBddNode; + + if (CAL_BDD_POINTER(f0)->thenBddId == nextId){ + f00 = BddNodeGetElseBddNode(f0); + f01 = BddNodeGetThenBddNode(f0); + } + else { + f00 = f01 = f0; + } + if (CAL_BDD_POINTER(f1)->thenBddId == nextId){ + f10 = BddNodeGetElseBddNode(f1); + f11 = BddNodeGetThenBddNode(f1); + } + else { + f10 = f11 = f1; + } + + if (f00 == f10){ + newF0 = f00; + f0Found = 1; + } + else{ + f0Found = UniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[id], f10, + f00, &newF0); + } + BddNodeIcrRefCount(newF0); + if (f01 == f11){ + newF1 = f11; + f1Found = 1; + } + else{ + f1Found = UniqueTableForIdFindOrAdd(bddManager, + bddManager->uniqueTable[id], f11, + f01, &newF1); + } + BddNodeIcrRefCount(newF1); + + f->thenBddId = nextId; + f->elseBddNode = newF0; + f->thenBddNode = newF1; + + fIndex = bddManager->idToIndex[id]; + Cal_Assert(fIndex < + bddManager->idToIndex[CAL_BDD_POINTER(f00)->thenBddId]); + Cal_Assert(fIndex < + bddManager->idToIndex[CAL_BDD_POINTER(f10)->thenBddId]); + Cal_Assert(fIndex < + bddManager->idToIndex[CAL_BDD_POINTER(f01)->thenBddId]); + Cal_Assert(fIndex < + bddManager->idToIndex[CAL_BDD_POINTER(f11)->thenBddId]); + Cal_Assert(CAL_BDD_POINTER(f00)->thenBddId != nextId); + Cal_Assert(CAL_BDD_POINTER(f01)->thenBddId != nextId); + Cal_Assert(CAL_BDD_POINTER(f10)->thenBddId != nextId); + Cal_Assert(CAL_BDD_POINTER(f11)->thenBddId != nextId); + + if (!f0Found){ + BddNodeIcrRefCount(f00); + BddNodeIcrRefCount(f10); + } + + if (!f1Found){ + BddNodeIcrRefCount(f01); + BddNodeIcrRefCount(f11); + } + + BddNodeDcrRefCount(f0); + BddNodeDcrRefCount(f1); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +CheckValidityOfNodes(Cal_BddManager_t *bddManager, long id) +{ + CalHashTable_t *table = bddManager->uniqueTable[id]; + int i; + CalBddNode_t *bddNode; + int index = bddManager->idToIndex[id]; + for(i = 0; i < table->numBins; ++i){ + for (bddNode = table->bins[i]; bddNode; bddNode = bddNode->nextBddNode){ + int thenIndex = bddManager->idToIndex[bddNode->thenBddNode->thenBddId]; + int elseIndex = + bddManager->idToIndex[CAL_BDD_POINTER(bddNode->elseBddNode)->thenBddId]; + assert((thenIndex > index) && (elseIndex > index)); + } + } + return 1; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +SweepVarTable(Cal_BddManager_t *bddManager, long id) +{ + CalHashTable_t *table = bddManager->uniqueTable[id]; + long numNodesFreed, oldNumEntries; + CalBddNode_t **ptr, *bddNode; + int i; + + oldNumEntries = table->numEntries; + for(i = 0; i < table->numBins; ++i){ + for (ptr = &table->bins[i], bddNode = *ptr; bddNode; + bddNode = *ptr){ + if (bddNode->elseBddId == 0){ + *ptr = bddNode->nextBddNode; + CalNodeManagerFreeNode(nodeManager, bddNode); + BddNodeDcrRefCount(bddNode->thenBddNode); + BddNodeDcrRefCount(bddNode->elseBddNode); + table->numEntries--; + } + else{ + ptr = &bddNode->nextBddNode; + } + } + } + numNodesFreed = oldNumEntries - table->numEntries; + bddManager->numNodes -= numNodesFreed; + bddManager->numNodesFreed += numNodesFreed; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExchange(Cal_BddManager_t *bddManager, long id) +{ + Cal_BddId_t nextId; + CalBddNode_t **ptr, *bddNode, *nodeList; + CalHashTable_t *table, *nextTable; + Cal_BddIndex_t index, nextIndex; + int i; + CalBddNode_t *f1, *f2; + CalAssociation_t *p; + CalNodeManager_t *nodeManager; + + index = bddManager->idToIndex[id]; + nextIndex = index+1; + nextId = bddManager->indexToId[nextIndex]; + + if (CalTestInteract(bddManager, id, nextId)){ + bddManager->numSwaps++; + nodeManager = bddManager->nodeManagerArray[id]; + table = bddManager->uniqueTable[id]; + nextTable = bddManager->uniqueTable[nextId]; + nodeList = (CalBddNode_t*)0; + for(i = 0; i < table->numBins; i++){ + for (ptr = &table->bins[i], bddNode = *ptr; bddNode; + bddNode = *ptr){ + Cal_Assert(bddNode->elseBddId != 0); + f1 = bddNode->elseBddNode; + f2 = bddNode->thenBddNode; + if ((CAL_BDD_POINTER(f1)->thenBddId != nextId) && + (CAL_BDD_POINTER(f2)->thenBddId != nextId)){ + ptr = &bddNode->nextBddNode; + } + else{ + *ptr = bddNode->nextBddNode; + bddNode->nextBddNode = nodeList; + nodeList = bddNode; + } + } + } + for (bddNode = nodeList; bddNode ; bddNode = nodeList){ + BddExchangeAux(bddManager, bddNode, id, nextId); + nodeList = bddNode->nextBddNode; + HashTableAddDirect(nextTable, bddNode); + table->numEntries--; + } + SweepVarTable(bddManager, nextId); + } + else { + bddManager->numTrivialSwaps++; + } + + CalFixupAssoc(bddManager, id, nextId, bddManager->tempAssociation); + for(p = bddManager->associationList; p; p = p->next){ + CalFixupAssoc(bddManager, id, nextId, p); + } + + bddManager->idToIndex[id] = nextIndex; + bddManager->idToIndex[nextId] = index; + bddManager->indexToId[index] = nextId; + bddManager->indexToId[nextIndex] = id; + + Cal_Assert(CheckValidityOfNodes(bddManager, id)); + Cal_Assert(CheckValidityOfNodes(bddManager, nextId)); + Cal_Assert(CalCheckAssoc(bddManager)); +#ifdef _CAL_VERBOSE + /*fprintf(stdout,"Variable order after swap:\n");*/ + for (i=0; inumVars; i++){ + fprintf(stdout, "%3d ", bddManager->indexToId[i]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddExchangeVarBlocks(Cal_BddManager_t *bddManager, Cal_Block parent, + long blockIndex) +{ + Cal_Block b1, b2, temp; + long i, j, k, l, firstBlockWidth, secondBlockWidth; + + b1 = parent->children[blockIndex]; + b2 = parent->children[blockIndex+1]; + /* This slides the blocks past each other in a kind of interleaving */ + /* fashion. */ + firstBlockWidth = b1->lastIndex - b1->firstIndex; + secondBlockWidth = b2->lastIndex - b2->firstIndex; + + for (i=0; i <= firstBlockWidth + secondBlockWidth; i++){ + j = i - firstBlockWidth; + if (j < 0) j=0; + k = ((i > secondBlockWidth) ? secondBlockWidth : i); + while (j <= k) { + l = b2->firstIndex + j - i + j; + BddExchange(bddManager, bddManager->indexToId[l-1]); + ++j; + } + } + CalBddBlockDelta(b1, secondBlockWidth+1); + CalBddBlockDelta(b2, -(firstBlockWidth+1)); + temp = parent->children[blockIndex]; + parent->children[blockIndex] = parent->children[blockIndex+1]; + parent->children[blockIndex+1] = temp; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddReorderWindow2(Cal_BddManager_t *bddManager, Cal_Block block, long i) +{ + long size, bestSize; + + /* 1 2 */ + bestSize = bddManager->numNodes; + BddExchangeVarBlocks(bddManager, block, i); + /* 2 1 */ + size = bddManager->numNodes; + if (size < bestSize) return (1); + BddExchangeVarBlocks(bddManager, block, i); + return (0); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static int +BddReorderWindow3(Cal_BddManager_t *bddManager, Cal_Block block, long i) +{ + int best; + long size, bestSize; + long origSize; + + origSize = bddManager->numNodes; + best = 0; + /* 1 2 3 */ + bestSize = bddManager->numNodes; + BddExchangeVarBlocks(bddManager, block, i); + /* 2 1 3 */ + size=bddManager->numNodes; + if (size < bestSize) { + best=1; + bestSize=size; + } + BddExchangeVarBlocks(bddManager, block, i+1); + /* 2 3 1 */ + size=bddManager->numNodes; + if (size < bestSize) { + best=2; + bestSize=size; + } + BddExchangeVarBlocks(bddManager, block, i); + /* 3 2 1 */ + size=bddManager->numNodes; + if (size <= bestSize) { + best=3; + bestSize=size; + } + BddExchangeVarBlocks(bddManager, block, i+1); + /* 3 1 2 */ + size=bddManager->numNodes; + if (size <= bestSize) { + best=4; + bestSize=size; + } + BddExchangeVarBlocks(bddManager, block, i); + /* 1 3 2 */ + size=bddManager->numNodes; + if (size <= bestSize) { + best=5; + bestSize=size; + } + switch (best){ + case 0: + BddExchangeVarBlocks(bddManager, block, i+1); + break; + case 1: + BddExchangeVarBlocks(bddManager, block, i+1); + BddExchangeVarBlocks(bddManager, block, i); + break; + case 2: + BddExchangeVarBlocks(bddManager, block, i+1); + BddExchangeVarBlocks(bddManager, block, i); + BddExchangeVarBlocks(bddManager, block, i+1); + break; + case 3: + BddExchangeVarBlocks(bddManager, block, i); + BddExchangeVarBlocks(bddManager, block, i+1); + break; + case 4: + BddExchangeVarBlocks(bddManager, block, i); + break; + case 5: + break; + } + return ((best > 0) && (origSize > bestSize)); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderStableWindow3Aux(Cal_BddManager_t *bddManager, Cal_Block block, + char *levels) +{ + long i; + int moved; + int anySwapped; + + if (block->reorderable) { + for (i=0; i < block->numChildren-1; ++i) levels[i]=1; + do { + anySwapped=0; + for (i=0; i < block->numChildren-1; i++){ + if (levels[i]){ +#ifdef _CAL_VERBOSE + fprintf(stdout,"Moving block %3d -- %3d\n", + bddManager->indexToId[block->children[i]-> firstIndex], + bddManager->indexToId[block->children[i]->lastIndex]); + fflush(stdout); + for (j=0; jnumVars; j++){ + fprintf(stdout, "%3d ", bddManager->indexToId[j]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif + if (i < block->numChildren-2){ + moved = BddReorderWindow3(bddManager, block, i); + } + else{ + moved = BddReorderWindow2(bddManager, block, i); + } + if (moved){ + if (i > 0) { + levels[i-1]=1; + if (i > 1) + levels[i-2]=1; + } + levels[i]=1; + levels[i+1]=1; + if (i < block->numChildren-2){ + levels[i+2]=1; + if (i < block->numChildren-3) { + levels[i+3]=1; + if (i < block->numChildren-4) levels[i+4]=1; + } + } + anySwapped=1; + } + else levels[i]=0; + } + } + } while (anySwapped); + } + for (i=0; i < block->numChildren; ++i){ + BddReorderStableWindow3Aux(bddManager, block->children[i], levels); + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderStableWindow3(Cal_BddManager_t *bddManager) +{ + char *levels; + levels = Cal_MemAlloc(char, bddManager->numVars); + bddManager->numSwaps = 0; + BddReorderStableWindow3Aux(bddManager, bddManager->superBlock, levels); + Cal_MemFree(levels); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddSiftBlock(Cal_BddManager_t *bddManager, Cal_Block block, long + startPosition, double maxSizeFactor) +{ + long startSize; + long bestSize; + long bestPosition; + long currentSize; + long currentPosition; + long maxSize; + + startSize = bddManager->numNodes; + bestSize = startSize; + bestPosition = startPosition; + currentSize = startSize; + currentPosition = startPosition; + maxSize = maxSizeFactor*startSize; + if (bddManager->nodeLimit && maxSize > bddManager->nodeLimit) + maxSize = bddManager->nodeLimit; + + /* Need to do optimization here */ + if (startPosition > (block->numChildren >> 1)){ + while (currentPosition < block->numChildren-1 && currentSize <= maxSize){ + BddExchangeVarBlocks(bddManager, block, currentPosition); + ++currentPosition; + currentSize = bddManager->numNodes; + if (currentSize < bestSize){ + bestSize = currentSize; + bestPosition=currentPosition; + } + } + while (currentPosition != startPosition){ + --currentPosition; + BddExchangeVarBlocks(bddManager, block, currentPosition); + } + currentSize = startSize; + while (currentPosition && currentSize <= maxSize){ + --currentPosition; + BddExchangeVarBlocks(bddManager, block, currentPosition); + currentSize = bddManager->numNodes; + if (currentSize <= bestSize){ + bestSize = currentSize; + bestPosition = currentPosition; + } + } + while (currentPosition != bestPosition){ + BddExchangeVarBlocks(bddManager, block, currentPosition); + ++currentPosition; + } + } + else{ + while (currentPosition && currentSize <= maxSize){ + --currentPosition; + BddExchangeVarBlocks(bddManager, block, currentPosition); + currentSize = bddManager->numNodes; + if (currentSize < bestSize){ + bestSize = currentSize; + bestPosition = currentPosition; + } + } + while (currentPosition != startPosition){ + BddExchangeVarBlocks(bddManager, block, currentPosition); + ++currentPosition; + } + currentSize = startSize; + while (currentPosition < block->numChildren-1 && currentSize <= maxSize){ + BddExchangeVarBlocks(bddManager, block, currentPosition); + currentSize = bddManager->numNodes; + ++currentPosition; + if (currentSize <= bestSize){ + bestSize = currentSize; + bestPosition = currentPosition; + } + } + while (currentPosition != bestPosition){ + --currentPosition; + BddExchangeVarBlocks(bddManager, block, currentPosition); + } + } +} + + + +/**Function******************************************************************** + + Synopsis [Reorder variables using "sift" algorithm.] + + Description [Reorder variables using "sift" algorithm.] + + SideEffects [None] + +******************************************************************************/ +static void +BddReorderSiftAux(Cal_BddManager_t *bddManager, Cal_Block block, + Cal_Block *toSift, double maxSizeFactor) +{ + long i, j, k; + long width; + long maxWidth; + long widest; + long numVarsShifted = 0; + bddManager->numSwaps = 0; + if (block->reorderable) { + for (i=0; i < block->numChildren; ++i){ + toSift[i] = block->children[i]; + } + while (i && + (numVarsShifted <= + bddManager->maxNumVarsSiftedPerReordering) && + (bddManager->numSwaps <= + bddManager->maxNumSwapsPerReordering)){ + i--; + numVarsShifted++; + maxWidth = 0; + widest = 0; + for (j=0; j <= i; ++j) { + for (width=0, k=toSift[j]->firstIndex; k <= toSift[j]->lastIndex; ++k){ + width += + bddManager->uniqueTable[bddManager->indexToId[k]]->numEntries; + } + width /= toSift[j]->lastIndex - toSift[j]->firstIndex+1; + if (width > maxWidth) { + maxWidth = width; + widest = j; + } + } + if (maxWidth > 1) { + for (j=0; block->children[j] != toSift[widest]; ++j); +#ifdef _CAL_VERBOSE + fprintf(stdout,"Moving block %3d -- %3d\n", + bddManager->indexToId[block->children[j]-> firstIndex], + bddManager->indexToId[block->children[j]->lastIndex]); + fflush(stdout); + for (l=0; lnumVars; l++){ + fprintf(stdout, "%3d ", bddManager->indexToId[l]); + } + fprintf(stdout, "%8d\n", bddManager->numNodes); +#endif + BddSiftBlock(bddManager, block, j, maxSizeFactor); + toSift[widest] = toSift[i]; + } + else { + break; + } + } + } + for (i=0; i < block->numChildren; ++i) + BddReorderSiftAux(bddManager, block->children[i], toSift, + maxSizeFactor); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +BddReorderSift(Cal_BddManager_t *bddManager, double maxSizeFactor) +{ + Cal_Block *toSift; + + toSift = Cal_MemAlloc(Cal_Block, bddManager->numVars); + BddReorderSiftAux(bddManager, bddManager->superBlock, toSift, + maxSizeFactor); + Cal_MemFree(toSift); +} + + + + +/**Function******************************************************************** + + Synopsis [Returns the smallest integer greater than or equal to log2 of a + number] + + Description [Returns the smallest integer greater than or equal to log2 of a + number (The assumption is that the number is >= 1)] + + SideEffects [None] + +******************************************************************************/ +static int +CeilLog2(int number) +{ + int num, count; + for (num=number, count=0; num > 1; num >>= 1, count++); + if ((1 << count) != number) count++; + return count; +} diff --git a/calReorderUtil.c b/calReorderUtil.c new file mode 100644 index 0000000..a371945 --- /dev/null +++ b/calReorderUtil.c @@ -0,0 +1,617 @@ +/**CFile*********************************************************************** + + FileName [calReorderUtil.c] + + PackageName [cal] + + Synopsis [Some utility routines used by both breadth-first and + depth-first reordering techniques.] + + Description [] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@ic.eecs.berkeley.edu) + Wilsin Gosti (wilsin@ic.eecs.berkeley.edu)] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calReorderUtil.c,v 1.2 1998/09/17 02:37:15 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderFixUserBddPtrs(Cal_BddManager bddManager) +{ + CalHashTable_t *userBddUniqueTable = bddManager->uniqueTable[0]; + int i; + int numBins; + int rehashFlag; + CalBddNode_t **bins; + CalBddNode_t *bddNode; + CalBddNode_t *nextBddNode; + CalBddNode_t *thenBddNode; + CalBddNode_t *elseBddNode; + Cal_Bdd_t internalBdd; + + numBins = userBddUniqueTable->numBins; + bins = userBddUniqueTable->bins; + + for(i = 0; i < numBins; i++) { + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + /* + * Process one bddNode at a time + */ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + rehashFlag = 0; + + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, internalBdd); + if (CalBddIsForwarded(internalBdd)) { + CalBddForward(internalBdd); + CalBddNodePutThenBdd(bddNode, internalBdd); + rehashFlag = 1; + } + Cal_Assert(CalBddIsForwarded(internalBdd) == 0); + /*Cal_Assert(!CalBddIsRefCountZero(internalBdd));*/ + /* + * Rehash if necessary + */ + if (rehashFlag) { + CalUniqueTableForIdRehashNode(userBddUniqueTable, bddNode, + thenBddNode, elseBddNode); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCheckAllValidity(Cal_BddManager bddManager) +{ + int id; + for(id = 0; id <= bddManager->numVars; id++){ + CalCheckValidityOfNodesForId(bddManager, id); + } + CalCheckAssociationValidity(bddManager); + if (bddManager->pipelineState == CREATE){ + CalCheckPipelineValidity(bddManager); + } + CalCheckRefCountValidity(bddManager); + CalCheckCacheTableValidity(bddManager); + return 1; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCheckValidityOfNodesForId(Cal_BddManager bddManager, int id) +{ + int i, numBins; + CalHashTable_t *uniqueTableForId; + CalBddNode_t *bddNode, *nextBddNode; + Cal_Bdd_t thenBdd, elseBdd; + + uniqueTableForId = bddManager->uniqueTable[id]; + Cal_Assert(uniqueTableForId->startNode.nextBddNode == NULL); + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalCheckValidityOfANode(bddManager, bddNode, id); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + Cal_Assert(CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), + uniqueTableForId) == i); + } + } + return 1; +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCheckValidityOfNodesForWindow(Cal_BddManager bddManager, + Cal_BddIndex_t index, int numLevels) +{ + int i, numBins, j; + CalHashTable_t *uniqueTableForId; + CalBddNode_t *bddNode, *nextBddNode; + Cal_Bdd_t thenBdd, elseBdd; + + for (i = 0; i < numLevels; i++){ + uniqueTableForId = + bddManager->uniqueTable[bddManager->indexToId[index+i]]; + numBins = uniqueTableForId->numBins; + for (j = 0; j < numBins; j++){ + for (bddNode = uniqueTableForId->bins[j]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + Cal_Assert(CalBddNodeIsForwarded(bddNode) == 0); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + Cal_Assert(CalBddIsForwarded(elseBdd) == 0); + Cal_Assert(CalDoHash2(CalBddGetBddNode(thenBdd), + CalBddGetBddNode(elseBdd), + uniqueTableForId) == j); + } + } + for (bddNode = uniqueTableForId->startNode.nextBddNode; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + } + } + return 1; +} + + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCheckValidityOfANode(Cal_BddManager_t *bddManager, CalBddNode_t + *bddNode, int id) +{ + Cal_Bdd_t thenBdd, elseBdd, thenBdd_, elseBdd_; + if (id != 0){ + /* id = 0 corresponds to the constants and the user BDDs */ + Cal_Assert(bddManager->idToIndex[id] < + bddManager->idToIndex[bddNode->thenBddId]); + Cal_Assert(bddManager->idToIndex[id] < + bddManager->idToIndex[bddNode->elseBddId]); + } + Cal_Assert(!CalBddNodeIsForwarded(bddNode)); + Cal_Assert(!CalBddNodeIsRefCountZero(bddNode)); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + Cal_Assert(CalBddIsForwarded(thenBdd) == 0); + Cal_Assert(CalBddIsForwarded(elseBdd) == 0); + Cal_Assert(!CalBddIsRefCountZero(thenBdd)); + Cal_Assert(!CalBddIsRefCountZero(elseBdd)); + /* Make sure that the then and else bdd nodes are part of the + respective unique tables */ + if (bddNode->thenBddId != 0){ + CalBddGetThenBdd(thenBdd, thenBdd_); + CalBddGetElseBdd(thenBdd, elseBdd_); + Cal_Assert( + CalUniqueTableForIdLookup(bddManager, + bddManager->uniqueTable[bddNode->thenBddId], + thenBdd_, elseBdd_, &bdd)); + } + if (bddNode->elseBddId != 0){ + CalBddGetThenBdd(elseBdd, thenBdd_); + CalBddGetElseBdd(elseBdd, elseBdd_); + Cal_Assert( + CalUniqueTableForIdLookup(bddManager, + bddManager->uniqueTable[bddNode->elseBddId], + thenBdd_, elseBdd_, &bdd)); + } + return 1; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalCheckRefCountValidity(Cal_BddManager_t *bddManager) +{ + int i, numBins, index; + CalHashTable_t *uniqueTableForId; + CalBddNode_t *bddNode, *nextBddNode; + Cal_Bdd_t thenBdd, elseBdd, internalBdd; + CalAssociation_t *assoc, *nextAssoc; + + /* First traverse the user BDDs */ + uniqueTableForId = bddManager->uniqueTable[0]; + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, internalBdd); + CalBddDcrRefCount(internalBdd); + } + } + /* Traverse the associations */ + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddDcrRefCount(assoc->varAssociation[i]); + } + } + } + /* temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddDcrRefCount(assoc->varAssociation[i]); + } + } + + + /* Now traverse all the nodes in order */ + for (index = 0; index < bddManager->numVars; index++){ + uniqueTableForId = bddManager->uniqueTable[bddManager->indexToId[index]]; + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + CalBddDcrRefCount(thenBdd); + CalBddDcrRefCount(elseBdd); + } + } + } + + /* All the reference count must be zero or max */ + for (index = 0; index < bddManager->numVars; index++){ + uniqueTableForId = bddManager->uniqueTable[bddManager->indexToId[index]]; + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + /* If the pipeline execution is going on, the following + assertion will not hold */ + if (bddManager->pipelineState != CREATE){ + Cal_Assert(CalBddNodeIsRefCountZero(bddNode) || + CalBddNodeIsRefCountMax(bddNode)); + } + } + } + } + + /* Put back the ref count */ + /* traverse all the nodes in order */ + for (index = 0; index < bddManager->numVars; index++){ + uniqueTableForId = bddManager->uniqueTable[bddManager->indexToId[index]]; + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, thenBdd); + CalBddNodeGetElseBdd(bddNode, elseBdd); + CalBddIcrRefCount(thenBdd); + CalBddIcrRefCount(elseBdd); + } + } + } + /* Traverse the associations */ + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddIcrRefCount(assoc->varAssociation[i]); + } + } + } + /* temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddGetBddId(assoc->varAssociation[i]) != CAL_BDD_NULL_ID){ + CalBddIcrRefCount(assoc->varAssociation[i]); + } + } + + /* Traverse the user BDDs */ + uniqueTableForId = bddManager->uniqueTable[0]; + numBins = uniqueTableForId->numBins; + for (i = 0; i < numBins; i++){ + for (bddNode = uniqueTableForId->bins[i]; bddNode; + bddNode = nextBddNode){ + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + CalBddNodeGetThenBdd(bddNode, internalBdd); + CalBddIcrRefCount(internalBdd); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalCheckAssoc(Cal_BddManager_t *bddManager) +{ + CalAssociation_t *assoc, *nextAssoc; + int i; + int expectedLastBddIndex, bddIndex; + + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + expectedLastBddIndex = -1; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddIsBddNull(bddManager, assoc->varAssociation[i]) == 0){ + bddIndex = bddManager->idToIndex[i]; + if (expectedLastBddIndex < bddIndex){ + expectedLastBddIndex = bddIndex; + } + } + } + Cal_Assert(expectedLastBddIndex == assoc->lastBddIndex); + } + /* fix temporary association */ + assoc = bddManager->tempAssociation; + expectedLastBddIndex = -1; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddIsBddNull(bddManager, assoc->varAssociation[i]) == 0){ + bddIndex = bddManager->idToIndex[i]; + if (expectedLastBddIndex < bddIndex){ + expectedLastBddIndex = bddIndex; + } + } + } + Cal_Assert(expectedLastBddIndex == assoc->lastBddIndex); + return 1; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalFixupAssoc(Cal_BddManager_t *bddManager, long id1, long id2, + CalAssociation_t *assoc) +{ + if (assoc->lastBddIndex == -1) return; + /* Variable with id1 is moving down a spot. */ + if ((CalBddIsBddNull(bddManager, assoc->varAssociation[id1]) == 0) + && (assoc->lastBddIndex == bddManager->idToIndex[id1])){ + assoc->lastBddIndex++; + } + else if ((CalBddIsBddNull(bddManager, assoc->varAssociation[id1])) && + (CalBddIsBddNull(bddManager, assoc->varAssociation[id2]) == + 0) && + (assoc->lastBddIndex == bddManager->idToIndex[id2])){ + assoc->lastBddIndex--; + } + Cal_Assert((assoc->lastBddIndex >= 0) && (assoc->lastBddIndex <= + CAL_BDD_CONST_INDEX)); + +} +/**Function******************************************************************** + + Synopsis [Fixes the cofactors of the nodes belonging to + the given index.] + + Description [This routine traverses the unique table and for + each node, looks at the then and else cofactors. If needed fixes the + cofactors.] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderFixCofactors(Cal_BddManager bddManager, Cal_BddId_t id) +{ + CalHashTable_t *uniqueTableForId = + bddManager->uniqueTable[id]; + CalBddNode_t *bddNode, *nextBddNode, **bins, *thenBddNode, *elseBddNode; + Cal_Bdd_t f0, f1; + long numBins; + int i, rehashFlag; + + numBins = uniqueTableForId->numBins; + bins = uniqueTableForId->bins; + + for(i = 0; i < numBins; i++) { + for(bddNode = bins[i]; + bddNode != Cal_Nil(CalBddNode_t); + bddNode = nextBddNode) { + nextBddNode = CalBddNodeGetNextBddNode(bddNode); + /* + * Process one bddNode at a time + */ + /* + ** Because we have kept all the forwarding nodes in the list, + ** this should not be a forwarding node. + */ + Cal_Assert(CalBddNodeIsForwarded(bddNode) == 0); + Cal_Assert(CalBddNodeIsRefCountZero(bddNode) == 0); + thenBddNode = CalBddNodeGetThenBddNode(bddNode); + elseBddNode = CalBddNodeGetElseBddNode(bddNode); + rehashFlag = 0; + CalBddNodeGetThenBdd(bddNode, f1); + CalBddNodeGetElseBdd(bddNode, f0); + if (CalBddIsForwarded(f1)) { + CalBddForward(f1); + CalBddNodePutThenBdd(bddNode, f1); + rehashFlag = 1; + } + Cal_Assert(CalBddIsForwarded(f1) == 0); + if (CalBddIsForwarded(f0)) { + CalBddForward(f0); + CalBddNodePutElseBdd(bddNode, f0); + rehashFlag = 1; + } + Cal_Assert(CalBddIsForwarded(f0) == 0); + /* Rehash if necessary */ + if (rehashFlag) { + CalUniqueTableForIdRehashNode(uniqueTableForId, bddNode, thenBddNode, + elseBddNode); + } + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddReorderReclaimForwardedNodes(Cal_BddManager bddManager, int + startIndex, int endIndex) +{ + Cal_BddIndex_t index; + Cal_BddId_t id; + CalHashTable_t *uniqueTableForId; + CalNodeManager_t *nodeManager; + + for(index = startIndex; index <= endIndex; index++){ + id = bddManager->indexToId[index]; + uniqueTableForId = bddManager->uniqueTable[id]; + nodeManager = uniqueTableForId->nodeManager; + uniqueTableForId->endNode->nextBddNode = nodeManager->freeNodeList; + nodeManager->freeNodeList = uniqueTableForId->startNode.nextBddNode; + uniqueTableForId->endNode = &(uniqueTableForId->startNode); + uniqueTableForId->startNode.nextBddNode = NULL; + } + bddManager->numForwardedNodes = 0; +} + + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + diff --git a/calTerminal.c b/calTerminal.c new file mode 100644 index 0000000..79e18f1 --- /dev/null +++ b/calTerminal.c @@ -0,0 +1,421 @@ +/**CFile*********************************************************************** + + FileName [calTerminal.c] + + PackageName [cal] + + Synopsis [Contains the terminal function for various BDD operations.] + + Description [] + + SeeAlso [] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) and + Jagesh V. Sanghavi (sanghavi@eecs.berkeley.edu] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calTerminal.c,v 1.1.1.2 1997/02/12 21:11:30 hsv Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpAnd(Cal_BddManager_t * bddManager, + Cal_Bdd_t F, + Cal_Bdd_t G, + Cal_Bdd_t * resultBddPtr) +{ + if(CalBddIsBddConst(F)){ + if(CalBddIsBddOne(bddManager, F)){ + *resultBddPtr = G; + } + else{ + *resultBddPtr = F; + } + return 1; + } + else if(CalBddIsBddConst(G)){ + if(CalBddIsBddOne(bddManager, G)){ + *resultBddPtr = F; + } + else{ + *resultBddPtr = G; + } + return 1; + } + else{ + CalBddNode_t *bddNodeF, *bddNodeG; + bddNodeF = CalBddGetBddNode(F); + bddNodeG = CalBddGetBddNode(G); + if((CAL_BDD_POINTER(bddNodeF) == CAL_BDD_POINTER(bddNodeG))){ + if((CalAddress_t)bddNodeF ^ (CalAddress_t)bddNodeG){ + *resultBddPtr = CalBddZero(bddManager); + } + else{ + *resultBddPtr = F; + } + return 1; + } + else{ + return 0; + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpNand(Cal_BddManager_t * bddManager, + Cal_Bdd_t F, + Cal_Bdd_t G, + Cal_Bdd_t * resultBddPtr) +{ + if(CalBddIsBddConst(F)){ + if(CalBddIsBddOne(bddManager, F)){ + CalBddNot(G, *resultBddPtr); + } + else{ + CalBddNot(F, *resultBddPtr); + } + return 1; + } + else if(CalBddIsBddConst(G)){ + if(CalBddIsBddOne(bddManager, G)){ + CalBddNot(F, *resultBddPtr); + } + else{ + CalBddNot(G, *resultBddPtr); + } + return 1; + } + else{ + CalBddNode_t *bddNodeF, *bddNodeG; + bddNodeF = CalBddGetBddNode(F); + bddNodeG = CalBddGetBddNode(G); + if((CAL_BDD_POINTER(bddNodeF) == CAL_BDD_POINTER(bddNodeG))){ + if((CalAddress_t)bddNodeF ^ (CalAddress_t)bddNodeG){ + *resultBddPtr = CalBddOne(bddManager); + } + else{ + CalBddNot(F, *resultBddPtr); + } + return 1; + } + else{ + return 0; + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpOr( + Cal_BddManager_t * bddManager, + Cal_Bdd_t F, + Cal_Bdd_t G, + Cal_Bdd_t * resultBddPtr) +{ + if(CalBddIsBddConst(F)){ + if(CalBddIsBddOne(bddManager, F)){ + *resultBddPtr = F; + } + else{ + *resultBddPtr = G; + } + return 1; + } + else if(CalBddIsBddConst(G)){ + if(CalBddIsBddOne(bddManager, G)){ + *resultBddPtr = G; + } + else{ + *resultBddPtr = F; + } + return 1; + } + else{ + CalBddNode_t *bddNodeF, *bddNodeG; + bddNodeF = CalBddGetBddNode(F); + bddNodeG = CalBddGetBddNode(G); + if((CAL_BDD_POINTER(bddNodeF) == CAL_BDD_POINTER(bddNodeG))){ + if((CalAddress_t)bddNodeF ^ (CalAddress_t)bddNodeG){ + *resultBddPtr = CalBddOne(bddManager); + } + else{ + *resultBddPtr = F; + } + return 1; + } + else{ + return 0; + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalOpXor( + Cal_BddManager_t * bddManager, + Cal_Bdd_t F, + Cal_Bdd_t G, + Cal_Bdd_t * resultBddPtr) +{ + if(CalBddIsBddConst(F)){ + if(CalBddIsBddOne(bddManager, F)){ + CalBddNot(G, *resultBddPtr); + } + else{ + *resultBddPtr = G; + } + return 1; + } + else if(CalBddIsBddConst(G)){ + if(CalBddIsBddOne(bddManager, G)){ + CalBddNot(F, *resultBddPtr); + } + else{ + *resultBddPtr = F; + } + return 1; + } + else{ + CalBddNode_t *bddNodeF, *bddNodeG; + bddNodeF = CalBddGetBddNode(F); + bddNodeG = CalBddGetBddNode(G); + if((CAL_BDD_POINTER(bddNodeF) == CAL_BDD_POINTER(bddNodeG))){ + if((CalAddress_t)bddNodeF ^ (CalAddress_t)bddNodeG){ + *resultBddPtr = CalBddOne(bddManager); + } + else{ + *resultBddPtr = CalBddZero(bddManager); + } + return 1; + } + else{ + return 0; + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd_t +CalOpITE( + Cal_BddManager_t *bddManager, + Cal_Bdd_t f, + Cal_Bdd_t g, + Cal_Bdd_t h, + CalHashTable_t **reqQueForITE) +{ + CalBddNode_t *bddNode1, *bddNode2; + int complementFlag = 0; + + /* + * First phase: Make substitutions + * ITE(F,F,H) = ITE(F,1,H) + * ITE(F,F',H) = ITE(F,0,H) + * ITE(F,G,F) = ITE(F,G,0) + * ITE(F,G,F') = ITE(F,G,1) + */ + bddNode1 = CalBddGetBddNode(f); + bddNode2 = CalBddGetBddNode(g); + if((CAL_BDD_POINTER(bddNode1) == CAL_BDD_POINTER(bddNode2))){ + if((CalAddress_t)bddNode1 ^ (CalAddress_t)bddNode2){ + g = CalBddZero(bddManager); + } + else{ + g = CalBddOne(bddManager); + } + } + bddNode2 = CalBddGetBddNode(h); + if((CAL_BDD_POINTER(bddNode1) == CAL_BDD_POINTER(bddNode2))){ + if((CalAddress_t)bddNode1 ^ (CalAddress_t)bddNode2){ + h = CalBddOne(bddManager); + } + else{ + h = CalBddZero(bddManager); + } + } + + /* + * Second phase: Fix the complement pointers. + * There are 3 possible cases: + * F +ve G -ve: ITE(F ,G',H ) = ITE(F ,G ,H')' + * F -ve H +ve: ITE(F',G ,H ) = ITE(F ,H ,G) + * F -ve H -ve: ITE(F',G ,H') = ITE(F ,H ,G')' + */ + if(CalBddIsOutPos(f)){ + if(!CalBddIsOutPos(g)){ + CalBddNot(g, g); + CalBddNot(h, h); + complementFlag = 1; + } + } + else{ + Cal_Bdd_t tmpBdd; + CalBddNot(f, f); + if(CalBddIsOutPos(h)){ + tmpBdd = g; + g = h; + h = tmpBdd; + } + else{ + tmpBdd = g; + CalBddNot(h, g); + CalBddNot(tmpBdd, h); + complementFlag = 1; + } + } + + /* + * Third phase: Check for the terminal cases; create new request if needed + * ite(1,G,H) = G + * ite(0,G,H) = H (impossible by construction in second phase) + * ite(F,G,G) = G + * ite(F,1,0) = F + * ite(F,0,1) = F'(impossible by construction in second phase) + */ + if(CalBddIsBddConst(f) || CalBddIsEqual(g, h)){ + CalBddUpdatePhase(g, complementFlag); + return g; + } + else if(CalBddIsBddConst(g) && CalBddIsBddConst(h)){ + CalBddUpdatePhase(f, complementFlag); + return f; + } + else{ + Cal_BddId_t bddId; + Cal_Bdd_t result; + CalBddGetMinId3(bddManager, f, g, h, bddId); + CalHashTableThreeFindOrAdd(reqQueForITE[bddId], f, g, h, &result); + CalBddUpdatePhase(result, complementFlag); + return result; + } +} + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ + + + + + + + + + + + + + diff --git a/calTest.c b/calTest.c new file mode 100644 index 0000000..a9f19cd --- /dev/null +++ b/calTest.c @@ -0,0 +1,1816 @@ +/**CFile*********************************************************************** + + FileName [calTest.c] + + PackageName [cal] + + Synopsis [This file contains the test routines for the CAL package.] + + Description [optional] + + SeeAlso [optional] + + Author [Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Modified and extended from the original version written + by David Long. + ] + + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calTest.c,v 1.4 1998/09/17 08:51:30 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" +#include "time.h" +#include + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +#define VARS 50 +#define TT_BITS 32 /* Size of tt in bits */ +#define MAX_TT_VARS 20 +#define ITERATIONS 50 /* Number of trials to run */ +#define BITS_PER_INT 32 +#define LG_BITS_PER_INT 5 + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ +typedef unsigned long TruthTable_t; /* "Truth table" */ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static Cal_BddManager bddManager; +static Cal_Bdd vars[VARS]; +static TruthTable_t cofactorMasks[]= +{ + 0xffff0000, + 0xff00ff00, + 0xf0f0f0f0, + 0xcccccccc, + 0xaaaaaaaa, +}; +static int TT_VARS; +static CalAddress_t asDoubleSpace[2]; +/*static char filename[]="/tmp/tmpXXXXXX";*/ +static char filename[1024]; + + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ +#define EncodingToBdd(table) (Decode(0, (table))) + +#if HAVE_STDARG_H +static void Error(char *op, Cal_BddManager bddManager, Cal_Bdd result, Cal_Bdd expected, ...); +#else +static void Error(); +#endif + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + +static double asDouble(CalAddress_t v1, CalAddress_t v2); +static void asAddress(double n, CalAddress_t * r1, CalAddress_t * r2); +static char * terminalIdFn(Cal_BddManager bddManager, CalAddress_t v1, CalAddress_t v2, Cal_Pointer_t pointer); +static void PrintBdd(Cal_BddManager bddManager, Cal_Bdd f); +static void Error(char *op, Cal_BddManager bddManager, Cal_Bdd result, Cal_Bdd expected, ...); +static TruthTable_t Cofactor(TruthTable_t table, int var, int value); +static Cal_Bdd Decode(int var, TruthTable_t table); +static void TestAnd(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestNand(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestOr(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestITE(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestXor(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestIdNot(Cal_BddManager bddManager, Cal_Bdd f, TruthTable_t table); +static void TestCompose(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestSubstitute(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestVarSubstitute(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestSwapVars(Cal_BddManager bddManager, Cal_Bdd f, TruthTable_t table); +static void TestMultiwayAnd(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestMultiwayOr(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestMultiwayLarge(Cal_BddManager bddManager, int numBdds); +static void TestArrayOp(Cal_BddManager bddManager, int numBdds); +static void TestInterImpl(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestQnt(Cal_BddManager bddManager, Cal_Bdd f, TruthTable_t table, int bfZeroBFPlusDFOne, int cacheExistsResultsFlag, int cacheOrResultsFlag); +static void TestAssoc(Cal_BddManager bddManager, Cal_Bdd f, TruthTable_t table); +static void TestRelProd(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, int bfZeroBFPlusDFOne, int cacheRelProdResultsFlag, int cacheAndResultsFlag, int cacheOrResultsFlag); +static void TestReduce(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestGenCof(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestSize(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2); +static void TestSatisfy(Cal_BddManager bddManager, Cal_Bdd f, TruthTable_t table); +static void TestPipeline(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, Cal_Bdd f2, TruthTable_t table2, Cal_Bdd f3, TruthTable_t table3); +static void TestDump(Cal_BddManager bddManager, Cal_Bdd f); +static void TestReorderBlock(Cal_BddManager bddManager, TruthTable_t table, Cal_Bdd f); +static void TestReorder(Cal_BddManager bddManager, TruthTable_t table, Cal_Bdd f); +static void handler(int ignored); +static void RandomTests(int numVars, int iterations); + +/**AutomaticEnd***************************************************************/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +#ifdef TEST +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +main(int argc, char ** argv) +{ + int numVars, iterations; + if(argc < 2){ + iterations = ITERATIONS; + } + else{ + iterations = atoi(argv[1]); + } + if(argc < 3){ + TT_VARS = 5; + } + else { + TT_VARS = atoi(argv[2]); + } + + CalUtilSRandom((long)1); + numVars = TT_VARS; + RandomTests(numVars, iterations); + return 0; +} +#endif +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Definition of static functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static double +asDouble( + CalAddress_t v1, + CalAddress_t v2) +{ + asDoubleSpace[0] = v1; + asDoubleSpace[1] = v2; + return (*(double *)asDoubleSpace); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +asAddress( + double n, + CalAddress_t * r1, + CalAddress_t * r2) +{ + (*(double *)asDoubleSpace)=n; + *r1 = asDoubleSpace[0]; + *r2 = asDoubleSpace[1]; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static char * +terminalIdFn( + Cal_BddManager bddManager, + CalAddress_t v1, + CalAddress_t v2, + Cal_Pointer_t pointer) +{ + static char result[100]; + sprintf(result, "%g", asDouble(v1, v2)); + return (result); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +PrintBdd( + Cal_BddManager bddManager, + Cal_Bdd f) +{ + Cal_BddPrintBdd(bddManager, f, Cal_BddNamingFnNone, + (Cal_TerminalIdFn_t) terminalIdFn, + (Cal_Pointer_t)0, stderr); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +#if HAVE_STDARG_H +static void +Error(char *op, Cal_BddManager bddManager, Cal_Bdd result, + Cal_Bdd expected, ...) +{ + int i; + va_list ap; + Cal_Bdd userBdd; + Cal_Bdd_t f; + + va_start(ap, expected); +#else +static void +Error(va_alist) +va_dcl +{ + va_list ap; + Cal_BddRefCount_t refCount; + Cal_BddManager_t *bddManager; + Cal_Bdd result, expected; + Cal_Bdd userBdd; + char *op; + int i; + + va_start(ap); + op = va_arg(ap, char *); + bddManager = va_arg(ap, Cal_BddManager_t *); + result = va_arg(ap, Cal_Bdd); + expected = va_arg(ap, Cal_Bdd); +#endif + + fprintf(stderr, "\nError: operation %s:\n", op); + i=0; + while (1) { + if (userBdd = va_arg(ap, Cal_Bdd)){ + ++i; + fprintf(stderr, "Argument %d:\n", i); + Cal_BddFunctionPrint(bddManager, userBdd, "a"); + } + else + break; + } + fprintf(stderr, "Expected result:\n"); + Cal_BddFunctionPrint(bddManager, expected, "a"); + fprintf(stderr, "Result:\n"); + Cal_BddFunctionPrint(bddManager, result, "a"); + va_end(ap); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static TruthTable_t +Cofactor(TruthTable_t table, int var, int value) +{ + int shift; + + shift = 1 << (TT_VARS-var-1); + if(value) { + table &= cofactorMasks[var]; + table |= table >> shift; + } + else { + table &= ~cofactorMasks[var]; + table |= table << shift; + } + return (table); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static Cal_Bdd +Decode(int var, TruthTable_t table) +{ + Cal_Bdd temp1, temp2; + Cal_Bdd result; + Cal_Bdd left, right; + Cal_Bdd varBdd; + + if(var == TT_VARS){ + if(table & 0x1){ + result = Cal_BddOne(bddManager); + } + else{ + result = Cal_BddZero(bddManager); + } + } + else{ + temp1 = Decode(var+1, table >> (1 << (TT_VARS-var-1))); + temp2 = Decode(var+1, table); + left = Cal_BddAnd(bddManager, vars[var], temp1); + varBdd = Cal_BddNot(bddManager, vars[var]); + right = Cal_BddAnd(bddManager, varBdd, temp2); + result = Cal_BddOr(bddManager, left, right); + /* + result = Cal_BddITE(bddManager, vars[var], temp1, temp2); + */ + Cal_BddFree(bddManager, left); + Cal_BddFree(bddManager, right); + Cal_BddFree(bddManager, temp1); + Cal_BddFree(bddManager, temp2); + Cal_BddFree(bddManager, varBdd); + } + return (result); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestAnd(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, + Cal_Bdd f2, TruthTable_t table2) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + + result = Cal_BddAnd(bddManager, f1, f2); + resulttable = table1 & table2; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("AND", bddManager, result, expected, f1, f2, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestNand(Cal_BddManager bddManager, Cal_Bdd f1, TruthTable_t table1, + Cal_Bdd f2, TruthTable_t table2) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + + result = Cal_BddNand(bddManager, f1, f2); + resulttable = ~(table1 & table2); + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("NAND", bddManager, result, expected, f1, f2, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestOr( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + + result = Cal_BddOr(bddManager, f1, f2); + resulttable = table1 | table2; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("OR", bddManager,result, expected, f1, f2, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestITE( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2, + Cal_Bdd f3, + TruthTable_t table3) +{ + Cal_Bdd result; + TruthTable_t resultTable; + Cal_Bdd expected; + + result = Cal_BddITE(bddManager, f1, f2, f3); + resultTable = (table1 & table2) | (~table1 & table3); + expected = EncodingToBdd(resultTable); + if(Cal_BddIsEqual(bddManager, result, expected) == 0){ + Error("ITE", bddManager, result, expected, f1, f2, f3, + (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestXor( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + + result = Cal_BddXor(bddManager, f1, f2); + resulttable = table1 ^ table2; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("XOR", bddManager, result, expected, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestIdNot( + Cal_BddManager bddManager, + Cal_Bdd f, + TruthTable_t table) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + + result = Cal_BddNot(bddManager, f); + resulttable = ~table; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Not", bddManager, result, expected, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + result = Cal_BddIdentity(bddManager, f); + resulttable = table; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Identity", bddManager, result, expected, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestCompose( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2) +{ + int var; + Cal_Bdd result, expected; + TruthTable_t resulttable; + + + var = (int)(((long)CalUtilRandom())%TT_VARS); + + result = Cal_BddCompose(bddManager, vars[var], vars[var], Cal_BddOne(bddManager)); + if(!Cal_BddIsEqual(bddManager, result, Cal_BddOne(bddManager))){ + Cal_BddFunctionPrint(bddManager, result, "Compose"); + } + + result = Cal_BddCompose(bddManager, vars[var], vars[var], Cal_BddZero(bddManager)); + if(!Cal_BddIsEqual(bddManager, result, Cal_BddZero(bddManager))){ + Cal_BddFunctionPrint(bddManager, result, "Compose"); + } + + result = Cal_BddCompose(bddManager, f1, vars[var], Cal_BddOne(bddManager)); + resulttable = Cofactor(table1, var, 1); + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result,expected)){ + Error("Restrict 1", bddManager, result, expected, f1, vars[var], + (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + + result = Cal_BddCompose(bddManager, f1, vars[var], Cal_BddZero(bddManager)); + resulttable = Cofactor(table1, var, 0); + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Restrict 0", bddManager, result, expected, f1, vars[var], + (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + + result = Cal_BddCompose(bddManager, f1, vars[var], f2); + resulttable = (table2 & Cofactor(table1, var, 1)) | + (~table2 & Cofactor(table1, var, 0)); + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Compose", bddManager, result, expected, f1, vars[var], + f2, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestSubstitute( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2, + Cal_Bdd f3, + TruthTable_t table3) +{ + int var1, var2; + Cal_Bdd associationInfo[6]; + Cal_Bdd result; + TruthTable_t resulttable; + TruthTable_t temp1, temp2, temp3, temp4; + Cal_Bdd expected; + int assocId; + + var1 = (int)(((long)CalUtilRandom())%TT_VARS); + do{ + var2 = (int)(((long)CalUtilRandom())%TT_VARS); + }while (var1 == var2); + + associationInfo[0] = vars[var1]; + associationInfo[1] = f2; + associationInfo[2] = vars[var2]; + associationInfo[3] = f3; + associationInfo[4] = (Cal_Bdd) 0; + associationInfo[5] = (Cal_Bdd) 0; + + assocId = Cal_AssociationInit(bddManager, associationInfo, 1); + Cal_AssociationSetCurrent(bddManager, assocId); + + result = Cal_BddSubstitute(bddManager, f1); + temp1 = Cofactor(Cofactor(table1, var1, 1), var2, 1); + temp2 = Cofactor(Cofactor(table1, var1, 1), var2, 0); + temp3 = Cofactor(Cofactor(table1, var1, 0), var2, 1); + temp4 = Cofactor(Cofactor(table1, var1, 0), var2, 0); + resulttable = table2 & table3 & temp1; + resulttable |= table2 & ~table3 & temp2; + resulttable |= ~table2 & table3 & temp3; + resulttable |= ~table2 & ~table3 & temp4; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("substitute", bddManager, result, expected, + f1, vars[var1], f2, vars[var2], f3, (Cal_Bdd) 0); + } + /*Cal_AssociationQuit(bddManager, assocId);*/ + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestVarSubstitute( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2, + Cal_Bdd f3, + TruthTable_t table3) +{ + int var1, var2, var3, var4; + Cal_Bdd associationInfo[6]; + Cal_Bdd result1, result2; + TruthTable_t resulttable; + TruthTable_t temp1, temp2, temp3, temp4; + Cal_Bdd expected; + int assocId; + + var1 = (int)(((long)CalUtilRandom())%TT_VARS); + do{ + var3 = (int)(((long)CalUtilRandom())%TT_VARS); + }while (var1 == var3); + + var2 = (int)(((long)CalUtilRandom())%TT_VARS); + do{ + var4 = (int)(((long)CalUtilRandom())%TT_VARS); + }while (var2 == var4); + + /* + f1 = vars[0]; + table1 = cofactorMasks[0]; + */ + associationInfo[0] = vars[var1]; + associationInfo[1] = vars[var3]; + associationInfo[2] = vars[var2]; + associationInfo[3] = vars[var4]; + associationInfo[4] = (Cal_Bdd) 0; + associationInfo[5] = (Cal_Bdd) 0; + + assocId = Cal_AssociationInit(bddManager, associationInfo, 1); + Cal_AssociationSetCurrent(bddManager, assocId); + + result1 = Cal_BddVarSubstitute(bddManager, f1); + result2 = Cal_BddSubstitute(bddManager, f1); + temp1 = Cofactor(Cofactor(table1, var2, 1), var1, 1); + temp2 = Cofactor(Cofactor(table1, var2, 1), var1, 0); + temp3 = Cofactor(Cofactor(table1, var2, 0), var1, 1); + temp4 = Cofactor(Cofactor(table1, var2, 0), var1, 0); + resulttable = cofactorMasks[var3] & cofactorMasks[var4] & temp1; + resulttable |= ~cofactorMasks[var3] & cofactorMasks[var4] & temp2; + resulttable |= cofactorMasks[var3] & ~cofactorMasks[var4] & temp3; + resulttable |= ~cofactorMasks[var3] & ~cofactorMasks[var4] & temp4; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result1, result2)){ + Error("var substitute and substitute differ", bddManager, result1, result2, + f1, vars[var1], vars[var3], vars[var2], vars[var4], + (Cal_Bdd) 0); + } + if(!Cal_BddIsEqual(bddManager, result1, expected)){ + Error("var substitute", bddManager, result1, expected, + f1, vars[var1], vars[var3], vars[var2], vars[var4], + (Cal_Bdd) 0); + } + /*Cal_AssociationQuit(bddManager, assocId);*/ + Cal_BddFree(bddManager, result1); + Cal_BddFree(bddManager, result2); + Cal_BddFree(bddManager, expected); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestSwapVars( + Cal_BddManager bddManager, + Cal_Bdd f, + TruthTable_t table) +{ + int var1, var2; + Cal_Bdd result; + TruthTable_t resulttable; + TruthTable_t temp1, temp2, temp3, temp4; + Cal_Bdd expected; + + var1 = (int)(((long)CalUtilRandom())%TT_VARS); + var2 = (int)(((long)CalUtilRandom())%TT_VARS); + result = Cal_BddSwapVars(bddManager, f, vars[var1], vars[var2]); + temp1 = Cofactor(Cofactor(table, var1, 1), var2, 1); + temp2 = Cofactor(Cofactor(table, var1, 1), var2, 0); + temp3 = Cofactor(Cofactor(table, var1, 0), var2, 1); + temp4 = Cofactor(Cofactor(table, var1, 0), var2, 0); + resulttable = cofactorMasks[var2] & cofactorMasks[var1] & temp1; + resulttable |= cofactorMasks[var2] & ~cofactorMasks[var1] & temp2; + resulttable |= ~cofactorMasks[var2] & cofactorMasks[var1] & temp3; + resulttable |= ~cofactorMasks[var2] & ~cofactorMasks[var1] & temp4; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("swap variables", bddManager, result, expected, + f, vars[var1], vars[var2], (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestMultiwayAnd( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2, + Cal_Bdd f3, + TruthTable_t table3) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + Cal_Bdd *calBddArray; + + calBddArray = Cal_MemAlloc(Cal_Bdd, 4); + calBddArray[0] = f1; + calBddArray[1] = f2; + calBddArray[2] = f3; + calBddArray[3] = (Cal_Bdd) 0; + result = Cal_BddMultiwayAnd(bddManager, calBddArray); + resulttable = table1 & table2 & table3; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Multiway And", bddManager, result, expected, + (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + Cal_MemFree(calBddArray); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestMultiwayOr( + Cal_BddManager bddManager, + Cal_Bdd f1, + TruthTable_t table1, + Cal_Bdd f2, + TruthTable_t table2, + Cal_Bdd f3, + TruthTable_t table3) +{ + Cal_Bdd result; + TruthTable_t resulttable; + Cal_Bdd expected; + Cal_Bdd *calBddArray; + + calBddArray = Cal_MemAlloc(Cal_Bdd, 4); + calBddArray[0] = f1; + calBddArray[1] = f2; + calBddArray[2] = f3; + calBddArray[3] = (Cal_Bdd) 0; + result = Cal_BddMultiwayOr(bddManager, calBddArray); + resulttable = table1 | table2 | table3; + expected = EncodingToBdd(resulttable); + if(!Cal_BddIsEqual(bddManager, result, expected)){ + Error("Multiway Or", bddManager, result, expected, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, result); + Cal_BddFree(bddManager, expected); + Cal_MemFree(calBddArray); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestMultiwayLarge( + Cal_BddManager bddManager, + int numBdds) +{ + TruthTable_t table, andResulttable, orResulttable; + Cal_Bdd f, andResult, orResult, andExpected, orExpected; + int i; + Cal_Bdd *calBddArray; + + andResulttable = ~0x0; + orResulttable = 0x0; + calBddArray = Cal_MemAlloc(Cal_Bdd, numBdds+1); + for (i=0; iindexToId[0]-1], + 4); + block2 = Cal_BddNewVarBlock(bddManager, + vars[bddManager->indexToId[4]-1], + 4); + block3 = Cal_BddNewVarBlock(bddManager, + vars[bddManager->indexToId[8]-1], + 4); + Cal_BddVarBlockReorderable(bddManager, block2, 1); + Cal_BddReorder(bddManager); + newFunction = EncodingToBdd(table); + if (Cal_BddIsEqual(bddManager, f, newFunction) == 0){ + Error("Reordering (window)", bddManager, newFunction, f, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, newFunction); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +TestReorder(Cal_BddManager bddManager, TruthTable_t table, Cal_Bdd f) +{ + Cal_Bdd newFunction; + + if (CalUtilRandom()&0x1){ + fprintf(stdout, "Using Window\n"); + Cal_BddDynamicReordering(bddManager, CAL_REORDER_WINDOW); + } + else{ + fprintf(stdout, "Using Sift\n"); + Cal_BddDynamicReordering(bddManager, CAL_REORDER_SIFT); + } + if (CalUtilRandom()&0x1){ + bddManager->reorderMethod = CAL_REORDER_METHOD_BF; + } + else{ + bddManager->reorderMethod = CAL_REORDER_METHOD_DF; + } + Cal_BddReorder(bddManager); + newFunction = EncodingToBdd(table); + if (Cal_BddIsEqual(bddManager, f, newFunction) == 0){ + Error("Reordering (window)", bddManager, newFunction, f, (Cal_Bdd) 0); + } + Cal_BddFree(bddManager, newFunction); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +handler(int ignored) +{ + printf("arthimetic exception ############\n"); +} + + + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +static void +RandomTests(int numVars, int iterations) +{ + int i, j, seed; + TruthTable_t table1, table2, table3, table; + Cal_Bdd f1, f2, f3, f4, result, f, g; + Cal_Bdd *outputBddArray; + int associationId; + CalAssociation_t *assoc, *nextAssoc; + Cal_Block block1, block2; + + signal(SIGFPE, handler); + + printf("Random operation tests...\n"); + bddManager = Cal_BddManagerInit(); + seed = 1; + /* + (void) time((time_t *)&seed); + */ + CalUtilSRandom((long)seed); + + for(i = 0; i < numVars; ++i){ + vars[i] = Cal_BddManagerCreateNewVarLast(bddManager); + } + + /* + f1 = Cal_BddAnd(bddManager, vars[1], vars[2]); + f2 = Cal_BddAnd(bddManager, vars[1], vars[0]); + f3 = Cal_BddOr(bddManager, f1, f2); + Cal_BddFree(bddManager, f1); + Cal_BddFree(bddManager, f2); + Cal_BddDynamicReordering(bddManager, Cal_BddReorderSift); + fprintf(stdout,"Original function:\n"); + Cal_BddFunctionPrint(bddManager, f3, "a"); + Cal_BddReorderNew(bddManager); + f1 = Cal_BddAnd(bddManager, vars[1], vars[2]); + f2 = Cal_BddAnd(bddManager, vars[1], vars[0]); + f4 = Cal_BddOr(bddManager, f1, f2); + Cal_BddFree(bddManager, f1); + Cal_BddFree(bddManager, f2); + fprintf(stdout,"New function:\n"); + Cal_BddFunctionPrint(bddManager, f4, "a"); + Cal_Assert(Cal_BddIsEqual(bddManager, f3, f4)); + Cal_BddFree(bddManager, f3); + Cal_BddFree(bddManager, f4); + */ + +/* + block1 = Cal_BddNewVarBlock(bddManager, + vars[0], 2); + block2 = Cal_BddNewVarBlock(bddManager, vars[3], 2); + Cal_BddVarBlockReorderable(bddManager, block2, 1); + */ + for (i = 0; i < iterations; i++){ + Cal_Bdd result; + printf("Iteration %3d\n", i); + table1 = (TruthTable_t)CalUtilRandom(); + table2 = (TruthTable_t)CalUtilRandom(); + table3 = (TruthTable_t)CalUtilRandom(); + f1 = EncodingToBdd(table1); + f2 = EncodingToBdd(table2); + f3 = EncodingToBdd(table3); + + /* The following tests will fail if you do not use 5 variables */ + if (numVars == 5){ + TestGenCof(bddManager, f1, table1, f2, table2); + TestSubstitute(bddManager, f1, table1, f2, table2, f3, table3); + TestSwapVars(bddManager, f1, table1); + TestCompose(bddManager, f1, table1, f2, table2); + TestRelProd(bddManager, f1, table1, f2, table2, 0, 0, 0, 0); + TestQnt(bddManager, f1, table1, 1, 1, 1); + TestVarSubstitute(bddManager, f1, table1, f2, table2, f3, + table3); + } + /* The following can be tested for larger number of variables */ + TestAnd(bddManager,f1, table1, f2, table2); + TestIdNot(bddManager, f1, table1); + TestITE(bddManager, f1, table1, f2, table2, f3, table3); + TestNand(bddManager,f1, table1, f2, table2); + TestOr(bddManager, f1, table1, f2, table2); + TestXor(bddManager,f1, table1, f2, table2); + TestMultiwayOr(bddManager, f1, table1, f2, table2, f3, table3); + TestMultiwayAnd(bddManager, f1, table1, f2, table2, f3, table3); + TestArrayOp(bddManager, 10); + TestInterImpl(bddManager, f1, table1, f2, table2); + TestReduce(bddManager, f1, table1, f2, table2); + TestSize(bddManager, f1, table1, f2, table2); + TestSatisfy(bddManager, f1, table1); + TestAssoc(bddManager, f1, table1); + TestDump(bddManager, f1); + TestPipeline(bddManager, f1, table1, f2, table2, f3, table3); + TestReorder(bddManager, table1, f1); + Cal_BddFree(bddManager, f1); + Cal_BddFree(bddManager, f2); + Cal_BddFree(bddManager, f3); + if (i && (i % 10 == 0)) { + Cal_BddManagerGC(bddManager); + (void)CalPackNodes(bddManager); + } + } + for(i = 0; i < numVars; ++i){ + Cal_BddFree(bddManager, vars[i]); + } + Cal_BddStats(bddManager, stdout); + for(assoc = bddManager->associationList; + assoc != Cal_Nil(CalAssociation_t); assoc = nextAssoc){ + nextAssoc = assoc->next; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddIsBddNull(bddManager, assoc->varAssociation[i]) == 0){ + CalBddDcrRefCount(assoc->varAssociation[i]); + assoc->varAssociation[i] = bddManager->bddNull; + assoc->lastBddIndex = -1; + } + } + } + /* fix temporary association */ + assoc = bddManager->tempAssociation; + for (i=1; i <= bddManager->numVars; i++){ + if (CalBddIsBddNull(bddManager, assoc->varAssociation[i]) == 0){ + CalBddDcrRefCount(assoc->varAssociation[i]); + assoc->varAssociation[i] = bddManager->bddNull; + assoc->lastBddIndex = -1; + } + } + + Cal_BddManagerGC(bddManager); + Cal_BddStats(bddManager, stdout); + /*CalUniqueTablePrint(bddManager);*/ + Cal_BddManagerQuit(bddManager); +} diff --git a/calTitle.html b/calTitle.html new file mode 100644 index 0000000..c960406 --- /dev/null +++ b/calTitle.html @@ -0,0 +1,17 @@ + +The cal package: Title + + + + + + + + +
+ Programmer view + Maintainer by function + Maintainer by file
+ + + diff --git a/calUtil.c b/calUtil.c new file mode 100644 index 0000000..951f911 --- /dev/null +++ b/calUtil.c @@ -0,0 +1,698 @@ +/**CFile*********************************************************************** + + FileName [calUtil.c] + + PackageName [cal] + + Synopsis [Utility functions for the Cal package.] + + Description [Utility functions used in the Cal package.] + + SeeAlso [optional] + + Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) + Rajeev K. Ranjan (rajeev@eecs.berkeley.edu) + ] + Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. + All rights reserved. + + Permission is hereby granted, without written agreement and without license + or royalty fees, to use, copy, modify, and distribute this software and its + documentation for any purpose, provided that the above copyright notice and + the following two paragraphs appear in all copies of this software. + + IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + + THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN + "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE + MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.] + + Revision [$Id: calUtil.c,v 1.3 1998/09/15 19:02:54 ravi Exp $] + +******************************************************************************/ + +#include "calInt.h" + +/*---------------------------------------------------------------------------*/ +/* Constant declarations */ +/*---------------------------------------------------------------------------*/ +/* Random generator constants. */ +#define CAL_MODULUS1 2147483563 +#define CAL_LEQA1 40014 +#define CAL_LEQQ1 53668 +#define CAL_LEQR1 12211 +#define CAL_MODULUS2 2147483399 +#define CAL_LEQA2 40692 +#define CAL_LEQQ2 52774 +#define CAL_LEQR2 3791 +#define CAL_STAB_SIZE 64 +#define CAL_STAB_DIV (1 + (CAL_MODULUS1 - 1) / CAL_STAB_SIZE) + +/*---------------------------------------------------------------------------*/ +/* Type declarations */ +/*---------------------------------------------------------------------------*/ + + +/*---------------------------------------------------------------------------*/ +/* Stucture declarations */ +/*---------------------------------------------------------------------------*/ + +/*---------------------------------------------------------------------------*/ +/* Variable declarations */ +/*---------------------------------------------------------------------------*/ +static long utilRand = 0; +static long utilRand2; +static long shuffleSelect; +static long shuffleTable[CAL_STAB_SIZE]; + +/*---------------------------------------------------------------------------*/ +/* Macro declarations */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticStart*************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Static function prototypes */ +/*---------------------------------------------------------------------------*/ + + +/**AutomaticEnd***************************************************************/ + +/*---------------------------------------------------------------------------*/ +/* Definition of exported functions */ +/*---------------------------------------------------------------------------*/ +void +Cal_ImageDump(Cal_BddManager_t *bddManager, FILE *fp) +{ + + CalPageManager_t *pageManager; + int i, j; + char *segment, c; + int count = NUM_PAGES_PER_SEGMENT * PAGE_SIZE; + + pageManager = bddManager->pageManager1; + for(i = 0; i < pageManager->numSegments; i++){ + segment = (char *) pageManager->pageSegmentArray[i]; + for(j = 1; j <= count; j++){ + c = segment[j]; + fprintf(fp, "%c", j%64?c:'\n'); + } + } + pageManager = bddManager->pageManager2; + for(i = 0; i < pageManager->numSegments; i++){ + segment = (char *) pageManager->pageSegmentArray[i]; + for(j = 1; j <= count; j++){ + c = segment[j]; + fprintf(fp, "%c", j%64?c:'\n'); + } + } +} + + +/**Function******************************************************************** + + Synopsis [Prints the function implemented by the argument BDD] + + Description [Prints the function implemented by the argument BDD] + + SideEffects [None] + +******************************************************************************/ +void +Cal_BddFunctionPrint(Cal_BddManager bddManager, Cal_Bdd userBdd, + char *name) +{ + Cal_Bdd_t calBdd; + calBdd = CalBddGetInternalBdd(bddManager, userBdd); + CalBddFunctionPrint(bddManager, calBdd, name); +} + +/*---------------------------------------------------------------------------*/ +/* Definition of internal functions */ +/*---------------------------------------------------------------------------*/ +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalUniqueTablePrint(Cal_BddManager_t *bddManager) +{ + int i; + for(i = 0; i <= bddManager->numVars; i++){ + CalHashTablePrint(bddManager->uniqueTable[i]); + } +} + +/**Function******************************************************************** + + Synopsis [Prints the function implemented by the argument BDD] + + Description [Prints the function implemented by the argument BDD] + + SideEffects [None] + +******************************************************************************/ +void +CalBddFunctionPrint(Cal_BddManager_t * bddManager, + Cal_Bdd_t calBdd, + char * name) +{ + Cal_Bdd_t T,E; + Cal_BddId_t id; + char c; + static int level; + + if(level == 0)printf("%s = ",name); + level++; + printf("( "); + if(CalBddIsBddZero(bddManager, calBdd)){ + printf("0 "); + } + else if(CalBddIsBddOne(bddManager, calBdd)){ + printf("1 "); + } + else{ + id = CalBddGetBddId(calBdd); + c = (char)((int)'a' + id - 1); + printf("%c ", c); + CalBddGetCofactors(calBdd, id, T, E); + CalBddFunctionPrint(bddManager, T, " "); + printf("+ %c' ", c); + CalBddFunctionPrint(bddManager, E, " "); + } + level--; + printf(") "); + if(level == 0)printf("\n"); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +#if HAVE_STDARG_H +int +CalBddPreProcessing(Cal_BddManager_t *bddManager, int count, ...) +{ + int allValid; + va_list ap; + Cal_Bdd fUserBdd; + Cal_Bdd_t f; + + va_start(ap, count); +#else +# if HAVE_VARARGS_H +int +CalBddPreProcessing(va_alist) +va_dcl +{ + int allValid; + va_list ap; + Cal_Bdd *fUserBdd; + int count; + Cal_BddManager_t *bddManager; + Cal_Bdd_t f; + + va_start(ap); + bddManager = va_arg(ap, Cal_BddManager_t *); + count = va_arg(ap, int); +# endif +#endif + + allValid=1; + while (count){ + fUserBdd = va_arg(ap, Cal_Bdd); + if (fUserBdd == 0){ + allValid=0; + } + else { + f = CalBddGetInternalBdd(bddManager, fUserBdd); + if (CalBddIsRefCountZero(f)){ + CalBddFatalMessage("Bdd With Zero Reference Count Used."); + } + } + --count; + } + if (allValid) { + CalBddPostProcessing(bddManager); + } + va_end(ap); + return (allValid); +} + + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalBddPostProcessing(Cal_BddManager_t *bddManager) +{ + if (bddManager->gcCheck > 0) return CAL_BDD_OK; + bddManager->gcCheck = CAL_GC_CHECK; + if(bddManager->numNodes > bddManager->uniqueTableGCLimit){ + long origNodes = bddManager->numNodes; + Cal_BddManagerGC(bddManager); + if ((bddManager->numNodes > bddManager->reorderingThreshold) && + (3*bddManager->numNodes > 2* bddManager->uniqueTableGCLimit) && + (bddManager->dynamicReorderingEnableFlag) && + (bddManager->reorderTechnique != CAL_REORDER_NONE)){ + CalCacheTableTwoFlush(bddManager->cacheTable); + if (bddManager->reorderMethod == CAL_REORDER_METHOD_BF){ + CalBddReorderAuxBF(bddManager); + } + else{ + CalBddReorderAuxDF(bddManager); + } + } + else { + /* Check if we should repack */ + Cal_Assert(CalCheckAllValidity(bddManager)); + if (bddManager->numNodes < + bddManager->repackAfterGCThreshold*origNodes){ + CalRepackNodesAfterGC(bddManager); + } + Cal_Assert(CalCheckAllValidity(bddManager)); + } + Cal_BddManagerSetGCLimit(bddManager); + if (bddManager->nodeLimit && (bddManager->numNodes > + bddManager->nodeLimit)){ + CalBddWarningMessage("Overflow: Node Limit Exceeded"); + bddManager->overflow = 1; + return CAL_BDD_OVERFLOWED; + } + /* + * Check to see if the cache table needs to be rehashed. + */ + CalCacheTableRehash(bddManager); + } + return CAL_BDD_OK; +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +int +CalBddArrayPreProcessing(Cal_BddManager_t *bddManager, Cal_Bdd *userBddArray) +{ + int i = 0; + Cal_Bdd userBdd; + while ((userBdd = userBddArray[i++])){ + if (CalBddPreProcessing(bddManager, 1, userBdd) == 0){ + return 0; + } + } + return 1; +} + + +/**Function******************************************************************** + + Name [CalBddFatalMessage] + + Synopsis [Prints fatal message and exits.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd_t +CalBddGetInternalBdd(Cal_BddManager bddManager, Cal_Bdd userBdd) +{ + Cal_Bdd_t resultBdd; + if (CalBddNodeIsOutPos(userBdd)){ + CalBddNodeGetThenBdd(userBdd, resultBdd); + } + else { + Cal_Bdd userBddNot = CalBddNodeNot(userBdd); + Cal_Bdd_t internalBdd; + CalBddNodeGetThenBdd(userBddNot,internalBdd); + CalBddNot(internalBdd, resultBdd); + } + return resultBdd; +} + +/**Function******************************************************************** + + Name [CalBddFatalMessage] + + Synopsis [Prints fatal message and exits.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +Cal_Bdd +CalBddGetExternalBdd(Cal_BddManager_t *bddManager, Cal_Bdd_t internalBdd) +{ + CalHashTable_t *hashTableForUserBdd = bddManager->uniqueTable[0]; + Cal_Bdd_t resultBdd; + int found; + + if(CalBddIsOutPos(internalBdd)){ + found = CalHashTableFindOrAdd(hashTableForUserBdd, internalBdd, + bddManager->bddOne, &resultBdd); + } + else { + Cal_Bdd_t internalBddNot; + CalBddNot(internalBdd, internalBddNot); + found = CalHashTableFindOrAdd(hashTableForUserBdd, internalBddNot, + bddManager->bddOne, &resultBdd); + CalBddNot(resultBdd, resultBdd); + } + if (found == 0){ + CalBddIcrRefCount(internalBdd); + } + CalBddIcrRefCount(resultBdd); + return CalBddGetBddNode(resultBdd); +} + + +/**Function******************************************************************** + + Name [CalBddFatalMessage] + + Synopsis [Prints fatal message and exits.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddFatalMessage(char *string) +{ + (void) fprintf(stderr,"Fatal: %s\n", string); + exit(-1); +} +/**Function******************************************************************** + + Name [CalBddWarningMessage] + + Synopsis [Prints warning message.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddWarningMessage(char *string) +{ + (void) fprintf(stderr,"Warning: %s\n", string); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalBddNodePrint(CalBddNode_t *bddNode) +{ + int refCount; + CalBddNodeGetRefCount(bddNode, refCount); + printf("Node (%lx) thenBdd(%2d %lx) elseBdd(%2d %lx) ref_count (%d) next (%lx)\n", + (CalAddress_t)bddNode, + CalBddNodeGetThenBddId(bddNode), + (CalAddress_t) CalBddNodeGetThenBddNode(bddNode), + CalBddNodeGetElseBddId(bddNode), + (CalAddress_t) CalBddNodeGetElseBddNode(bddNode), + refCount, (CalAddress_t)bddNode->nextBddNode); +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ + +void +CalBddPrint(Cal_Bdd_t calBdd) +{ + printf("Id(%2d) node(%lx) ", + CalBddGetBddId(calBdd), (CalAddress_t) CalBddGetBddNode(calBdd)); + printf("thenBdd(%2d %lx) elseBdd(%2d %lx)\n", + CalBddGetThenBddId(calBdd), + (CalAddress_t) CalBddGetThenBddNode(calBdd), + CalBddGetElseBddId(calBdd), + (CalAddress_t) CalBddGetElseBddNode(calBdd)); +} + +#ifdef TEST_CALBDDNODE +main(int argc, char **argv) +{ + CalBddNode_t *bddNode, *thenBddNode, *elseBddNode; + + bddNode = Cal_MemAlloc(CalBddNode_t, 1); + thenBddNode = Cal_MemAlloc(CalBddNode_t, 1); + elseBddNode = Cal_MemAlloc(CalBddNode_t, 1); + + CalBddNodePutThenBddId(bddNode, 1); + CalBddNodePutThenBddNode(bddNode, thenBddNode); + CalBddNodePutElseBddId(bddNode, 2); + CalBddNodePutElseBddNode(bddNode, elseBddNode); + + printf("then( 1 %x) else( 2 %x)\n", thenBddNode, elseBddNode); + CalBddNodePrint(bddNode); +} +#endif + + +/**Function******************************************************************** + + Synopsis [Prints a hash table.] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTablePrint(CalHashTable_t *hashTable) +{ + int i; + CalBddNode_t *ptr; + Cal_Bdd_t calBdd, T, E; + int refCount, firstFlag; + + printf("HashTable bddId(%d) entries(%ld) bins(%ld) capacity(%ld)\n", + hashTable->bddId, hashTable->numEntries, hashTable->numBins, + hashTable->maxCapacity); + for(i = 0; i < hashTable->numBins; i++){ + ptr = hashTable->bins[i]; + firstFlag = 1; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddPutBddNode(calBdd, ptr); + CalBddNodeGetThenBdd(ptr, T); + CalBddNodeGetElseBdd(ptr, E); + if (firstFlag){ + printf("\tbin = (%d) ", i); + firstFlag = 0; + } + printf("\t\tbddNode(%lx) ", (CalAddress_t)ptr); + printf("thenId(%d) ", CalBddGetBddId(T)); + printf("thenBddNode(%lx) ", (CalAddress_t) CalBddGetBddNode(T)); + printf("elseId(%d) ", CalBddGetBddId(E)); + printf("elseBddNode(%lx) ", (unsigned long)CalBddGetBddNode(E)); + CalBddGetRefCount(calBdd, refCount); + printf("refCount(%d)\n", refCount); + ptr = CalBddNodeGetNextBddNode(ptr); + } + } +} + +/**Function******************************************************************** + + Synopsis [required] + + Description [optional] + + SideEffects [required] + + SeeAlso [optional] + +******************************************************************************/ +void +CalHashTableOnePrint(CalHashTable_t *hashTable, int flag) +{ + int i; + CalBddNode_t *ptr, *node; + Cal_Bdd_t keyBdd; + + printf("*************************************************\n"); + for(i = 0; i < hashTable->numBins; i++){ + ptr = hashTable->bins[i]; + while(ptr != Cal_Nil(CalBddNode_t)){ + CalBddNodeGetThenBdd(ptr, keyBdd); + node = CalBddNodeGetElseBddNode(ptr); + if(flag == 1){ + printf("Key(%d %lx) Value(%f)\n", + CalBddGetBddId(keyBdd), (CalAddress_t)CalBddGetBddNode(keyBdd), *(double *)node); + } + else{ + printf("Key(%d %lx) Value(%d)\n", + CalBddGetBddId(keyBdd), (CalAddress_t)CalBddGetBddNode(keyBdd), *(int *)node); + } + ptr = CalBddNodeGetNextBddNode(ptr); + } + } +} + +/**Function******************************************************************** + + Synopsis [Initializer for the portable random number generator.] + + Description [Initializer for the portable number generator based on + ran2 in "Numerical Recipes in C." The input is the seed for the + generator. If it is negative, its absolute value is taken as seed. + If it is 0, then 1 is taken as seed. The initialized sets up the two + recurrences used to generate a long-period stream, and sets up the + shuffle table.] + + SideEffects [None] + + SeeAlso [CalUtilRandom] + +******************************************************************************/ +void +CalUtilSRandom(long seed) +{ + int i; + + if (seed < 0) utilRand = -seed; + else if (seed == 0) utilRand = 1; + else utilRand = seed; + utilRand2 = utilRand; + /* Load the shuffle table (after 11 warm-ups). */ + for (i = 0; i < CAL_STAB_SIZE + 11; i++) { + long int w; + w = utilRand / CAL_LEQQ1; + utilRand = CAL_LEQA1 * (utilRand - w * CAL_LEQQ1) - w * CAL_LEQR1; + utilRand += (utilRand < 0) * CAL_MODULUS1; + shuffleTable[i % CAL_STAB_SIZE] = utilRand; + } + shuffleSelect = shuffleTable[1 % CAL_STAB_SIZE]; +} /* end of CalUtilSRandom */ + +/**Function******************************************************************** + + Synopsis [Portable random number generator.] + + Description [Portable number generator based on ran2 from "Numerical + Recipes in C." It is a long period (> 2 * 10^18) random number generator + of L'Ecuyer with Bays-Durham shuffle. Returns a long integer uniformly + distributed between 0 and 2147483561 (inclusive of the endpoint values). + The random generator can be explicitly initialized by calling + CalUtilSRandom. If no explicit initialization is performed, then the + seed 1 is assumed.] + + SideEffects [] + + SeeAlso [CalUtilSRandom] + +******************************************************************************/ +long +CalUtilRandom() +{ + int i; /* index in the shuffle table */ + long int w; /* work variable */ + + /* utilRand == 0 if the geneartor has not been initialized yet. */ + if (utilRand == 0) CalUtilSRandom((long)1); + + /* Compute utilRand = (utilRand * CAL_LEQA1) % CAL_MODULUS1 avoiding + ** overflows by Schrage's method. + */ + w = utilRand / CAL_LEQQ1; + utilRand = CAL_LEQA1 * (utilRand - w * CAL_LEQQ1) - w * CAL_LEQR1; + utilRand += (utilRand < 0) * CAL_MODULUS1; + + /* Compute utilRand2 = (utilRand2 * CAL_LEQA2) % CAL_MODULUS2 avoiding + ** overflows by Schrage's method. + */ + w = utilRand2 / CAL_LEQQ2; + utilRand2 = CAL_LEQA2 * (utilRand2 - w * CAL_LEQQ2) - w * CAL_LEQR2; + utilRand2 += (utilRand2 < 0) * CAL_MODULUS2; + + /* utilRand is shuffled with the Bays-Durham algorithm. + ** shuffleSelect and utilRand2 are combined to generate the output. + */ + + /* Pick one element from the shuffle table; "i" will be in the range + ** from 0 to CAL_STAB_SIZE-1. + */ + i = shuffleSelect / CAL_STAB_DIV; + /* Mix the element of the shuffle table with the current iterate of + ** the second sub-generator, and replace the chosen element of the + ** shuffle table with the current iterate of the first sub-generator. + */ + shuffleSelect = shuffleTable[i] - utilRand2; + shuffleTable[i] = utilRand; + shuffleSelect += (shuffleSelect < 1) * (CAL_MODULUS1 - 1); + /* Since shuffleSelect != 0, and we want to be able to return 0, + ** here we subtract 1 before returning. + */ + return(shuffleSelect - 1); + +} /* end of CalUtilRandom */ + + diff --git a/config.guess b/config.guess new file mode 100644 index 0000000..e9e4455 --- /dev/null +++ b/config.guess @@ -0,0 +1,693 @@ +#! /bin/sh +# Attempt to guess a canonical system name. +# Copyright (C) 1992, 93, 94, 95, 1996 Free Software Foundation, Inc. +# +# This file is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Written by Per Bothner . +# The master version of this file is at the FSF in /home/gd/gnu/lib. +# +# This script attempts to guess a canonical system name similar to +# config.sub. If it succeeds, it prints the system name on stdout, and +# exits with 0. Otherwise, it exits with 1. +# +# The plan is that this can be called by configure scripts if you +# don't specify an explicit system type (host/target name). +# +# Only a few systems have been added to this list; please add others +# (but try to keep the structure clean). +# + +# This is needed to find uname on a Pyramid OSx when run in the BSD universe. +# (ghazi@noc.rutgers.edu 8/24/94.) +if (test -f /.attbin/uname) >/dev/null 2>&1 ; then + PATH=$PATH:/.attbin ; export PATH +fi + +UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown +UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown +UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown +UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown + +trap 'rm -f dummy.c dummy.o dummy; exit 1' 1 2 15 + +# Note: order is significant - the case branches are not exclusive. + +case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in + alpha:OSF1:*:*) + # A Vn.n version is a released version. + # A Tn.n version is a released field test version. + # A Xn.n version is an unreleased experimental baselevel. + # 1.2 uses "1.2" for uname -r. + echo alpha-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[VTX]//'` + exit 0 ;; + 21064:Windows_NT:50:3) + echo alpha-dec-winnt3.5 + exit 0 ;; + Amiga*:UNIX_System_V:4.0:*) + echo m68k-cbm-sysv4 + exit 0;; + amiga:NetBSD:*:*) + echo m68k-cbm-netbsd${UNAME_RELEASE} + exit 0 ;; + amiga:OpenBSD:*:*) + echo m68k-cbm-openbsd${UNAME_RELEASE} + exit 0 ;; + arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) + echo arm-acorn-riscix${UNAME_RELEASE} + exit 0;; + Pyramid*:OSx*:*:*|MIS*:OSx*:*:*) + # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE. + if test "`(/bin/universe) 2>/dev/null`" = att ; then + echo pyramid-pyramid-sysv3 + else + echo pyramid-pyramid-bsd + fi + exit 0 ;; + NILE:*:*:dcosx) + echo pyramid-pyramid-svr4 + exit 0 ;; + sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*) + echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + i86pc:SunOS:5.*:*) + echo i386-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + sun4*:SunOS:6*:*) + # According to config.sub, this is the proper way to canonicalize + # SunOS6. Hard to guess exactly what SunOS6 will be like, but + # it's likely to be more like Solaris than SunOS4. + echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + sun4*:SunOS:*:*) + case "`/usr/bin/arch -k`" in + Series*|S4*) + UNAME_RELEASE=`uname -v` + ;; + esac + # Japanese Language versions have a version number like `4.1.3-JL'. + echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'` + exit 0 ;; + sun3*:SunOS:*:*) + echo m68k-sun-sunos${UNAME_RELEASE} + exit 0 ;; + aushp:SunOS:*:*) + echo sparc-auspex-sunos${UNAME_RELEASE} + exit 0 ;; + atari*:NetBSD:*:*) + echo m68k-atari-netbsd${UNAME_RELEASE} + exit 0 ;; + atari*:OpenBSD:*:*) + echo m68k-atari-openbsd${UNAME_RELEASE} + exit 0 ;; + sun3*:NetBSD:*:*) + echo m68k-sun-netbsd${UNAME_RELEASE} + exit 0 ;; + sun3*:OpenBSD:*:*) + echo m68k-sun-openbsd${UNAME_RELEASE} + exit 0 ;; + mac68k:NetBSD:*:*) + echo m68k-apple-netbsd${UNAME_RELEASE} + exit 0 ;; + mac68k:OpenBSD:*:*) + echo m68k-apple-openbsd${UNAME_RELEASE} + exit 0 ;; + powerpc:machten:*:*) + echo powerpc-apple-machten${UNAME_RELEASE} + exit 0 ;; + RISC*:Mach:*:*) + echo mips-dec-mach_bsd4.3 + exit 0 ;; + RISC*:ULTRIX:*:*) + echo mips-dec-ultrix${UNAME_RELEASE} + exit 0 ;; + VAX*:ULTRIX*:*:*) + echo vax-dec-ultrix${UNAME_RELEASE} + exit 0 ;; + mips:*:*:UMIPS | mips:*:*:RISCos) + sed 's/^ //' << EOF >dummy.c + int main (argc, argv) int argc; char **argv; { + #if defined (host_mips) && defined (MIPSEB) + #if defined (SYSTYPE_SYSV) + printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_SVR4) + printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD) + printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0); + #endif + #endif + exit (-1); + } +EOF + ${CC-cc} dummy.c -o dummy \ + && ./dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \ + && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo mips-mips-riscos${UNAME_RELEASE} + exit 0 ;; + Night_Hawk:Power_UNIX:*:*) + echo powerpc-harris-powerunix + exit 0 ;; + m88k:CX/UX:7*:*) + echo m88k-harris-cxux7 + exit 0 ;; + m88k:*:4*:R4*) + echo m88k-motorola-sysv4 + exit 0 ;; + m88k:*:3*:R3*) + echo m88k-motorola-sysv3 + exit 0 ;; + AViiON:dgux:*:*) + # DG/UX returns AViiON for all architectures + UNAME_PROCESSOR=`/usr/bin/uname -p` + if [ $UNAME_PROCESSOR = mc88100 -o $UNAME_PROCESSOR = mc88110 ] ; then + if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx \ + -o ${TARGET_BINARY_INTERFACE}x = x ] ; then + echo m88k-dg-dgux${UNAME_RELEASE} + else + echo m88k-dg-dguxbcs${UNAME_RELEASE} + fi + else echo i586-dg-dgux${UNAME_RELEASE} + fi + exit 0 ;; + M88*:DolphinOS:*:*) # DolphinOS (SVR3) + echo m88k-dolphin-sysv3 + exit 0 ;; + M88*:*:R3*:*) + # Delta 88k system running SVR3 + echo m88k-motorola-sysv3 + exit 0 ;; + XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3) + echo m88k-tektronix-sysv3 + exit 0 ;; + Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD) + echo m68k-tektronix-bsd + exit 0 ;; + *:IRIX*:*:*) + echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'` + exit 0 ;; + ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX. + echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id + exit 0 ;; # Note that: echo "'`uname -s`'" gives 'AIX ' + i?86:AIX:*:*) + echo i386-ibm-aix + exit 0 ;; + *:AIX:2:3) + if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then + sed 's/^ //' << EOF >dummy.c + #include + + main() + { + if (!__power_pc()) + exit(1); + puts("powerpc-ibm-aix3.2.5"); + exit(0); + } +EOF + ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo rs6000-ibm-aix3.2.5 + elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then + echo rs6000-ibm-aix3.2.4 + else + echo rs6000-ibm-aix3.2 + fi + exit 0 ;; + *:AIX:*:4) + if /usr/sbin/lsattr -EHl proc0 | grep POWER >/dev/null 2>&1; then + IBM_ARCH=rs6000 + else + IBM_ARCH=powerpc + fi + if [ -x /usr/bin/oslevel ] ; then + IBM_REV=`/usr/bin/oslevel` + else + IBM_REV=4.${UNAME_RELEASE} + fi + echo ${IBM_ARCH}-ibm-aix${IBM_REV} + exit 0 ;; + *:AIX:*:*) + echo rs6000-ibm-aix + exit 0 ;; + ibmrt:4.4BSD:*|romp-ibm:BSD:*) + echo romp-ibm-bsd4.4 + exit 0 ;; + ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC NetBSD and + echo romp-ibm-bsd${UNAME_RELEASE} # 4.3 with uname added to + exit 0 ;; # report: romp-ibm BSD 4.3 + *:BOSX:*:*) + echo rs6000-bull-bosx + exit 0 ;; + DPX/2?00:B.O.S.:*:*) + echo m68k-bull-sysv3 + exit 0 ;; + 9000/[34]??:4.3bsd:1.*:*) + echo m68k-hp-bsd + exit 0 ;; + hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*) + echo m68k-hp-bsd4.4 + exit 0 ;; + 9000/[3478]??:HP-UX:*:*) + case "${UNAME_MACHINE}" in + 9000/31? ) HP_ARCH=m68000 ;; + 9000/[34]?? ) HP_ARCH=m68k ;; + 9000/7?? | 9000/8?[1679] ) HP_ARCH=hppa1.1 ;; + 9000/8?? ) HP_ARCH=hppa1.0 ;; + esac + HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'` + echo ${HP_ARCH}-hp-hpux${HPUX_REV} + exit 0 ;; + 3050*:HI-UX:*:*) + sed 's/^ //' << EOF >dummy.c + #include + int + main () + { + long cpu = sysconf (_SC_CPU_VERSION); + /* The order matters, because CPU_IS_HP_MC68K erroneously returns + true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct + results, however. */ + if (CPU_IS_PA_RISC (cpu)) + { + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break; + case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break; + default: puts ("hppa-hitachi-hiuxwe2"); break; + } + } + else if (CPU_IS_HP_MC68K (cpu)) + puts ("m68k-hitachi-hiuxwe2"); + else puts ("unknown-hitachi-hiuxwe2"); + exit (0); + } +EOF + ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo unknown-hitachi-hiuxwe2 + exit 0 ;; + 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* ) + echo hppa1.1-hp-bsd + exit 0 ;; + 9000/8??:4.3bsd:*:*) + echo hppa1.0-hp-bsd + exit 0 ;; + hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* ) + echo hppa1.1-hp-osf + exit 0 ;; + hp8??:OSF1:*:*) + echo hppa1.0-hp-osf + exit 0 ;; + i?86:OSF1:*:*) + if [ -x /usr/sbin/sysversion ] ; then + echo ${UNAME_MACHINE}-unknown-osf1mk + else + echo ${UNAME_MACHINE}-unknown-osf1 + fi + exit 0 ;; + parisc*:Lites*:*:*) + echo hppa1.1-hp-lites + exit 0 ;; + C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) + echo c1-convex-bsd + exit 0 ;; + C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit 0 ;; + C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) + echo c34-convex-bsd + exit 0 ;; + C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) + echo c38-convex-bsd + exit 0 ;; + C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) + echo c4-convex-bsd + exit 0 ;; + CRAY*X-MP:*:*:*) + echo xmp-cray-unicos + exit 0 ;; + CRAY*Y-MP:*:*:*) + echo ymp-cray-unicos${UNAME_RELEASE} + exit 0 ;; + CRAY*[A-Z]90:*:*:*) + echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \ + | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \ + -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ + exit 0 ;; + CRAY*TS:*:*:*) + echo t90-cray-unicos${UNAME_RELEASE} + exit 0 ;; + CRAY-2:*:*:*) + echo cray2-cray-unicos + exit 0 ;; + F300:UNIX_System_V:*:*) + FUJITSU_SYS=`uname -p | tr [A-Z] [a-z] | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` + echo "f300-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + exit 0 ;; + F301:UNIX_System_V:*:*) + echo f301-fujitsu-uxpv`echo $UNAME_RELEASE | sed 's/ .*//'` + exit 0 ;; + hp3[0-9][05]:NetBSD:*:*) + echo m68k-hp-netbsd${UNAME_RELEASE} + exit 0 ;; + hp3[0-9][05]:OpenBSD:*:*) + echo m68k-hp-openbsd${UNAME_RELEASE} + exit 0 ;; + i?86:BSD/386:*:* | *:BSD/OS:*:*) + echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE} + exit 0 ;; + *:FreeBSD:*:*) + echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` + exit 0 ;; + *:NetBSD:*:*) + echo ${UNAME_MACHINE}-unknown-netbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` + exit 0 ;; + *:OpenBSD:*:*) + echo ${UNAME_MACHINE}-unknown-openbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` + exit 0 ;; + i*:CYGWIN*:*) + echo i386-pc-cygwin32 + exit 0 ;; + p*:CYGWIN*:*) + echo powerpcle-unknown-cygwin32 + exit 0 ;; + prep*:SunOS:5.*:*) + echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + *:GNU:*:*) + echo `echo ${UNAME_MACHINE}|sed -e 's,/.*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'` + exit 0 ;; + *:Linux:*:*) + # The BFD linker knows what the default object file format is, so + # first see if it will tell us. + ld_help_string=`ld --help 2>&1` + if echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: elf_i.86"; then + echo "${UNAME_MACHINE}-pc-linux-gnu" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: i.86linux"; then + echo "${UNAME_MACHINE}-pc-linux-gnuaout" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: i.86coff"; then + echo "${UNAME_MACHINE}-pc-linux-gnucoff" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: m68kelf"; then + echo "${UNAME_MACHINE}-unknown-linux-gnu" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: m68klinux"; then + echo "${UNAME_MACHINE}-unknown-linux-gnuaout" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: elf32ppc"; then + echo "powerpc-unknown-linux-gnu" ; exit 0 + elif test "${UNAME_MACHINE}" = "alpha" ; then + echo alpha-unknown-linux-gnu ; exit 0 + elif test "${UNAME_MACHINE}" = "sparc" ; then + echo sparc-unknown-linux-gnu ; exit 0 + else + # Either a pre-BFD a.out linker (linux-gnuoldld) or one that does not give us + # useful --help. Gcc wants to distinguish between linux-gnuoldld and linux-gnuaout. + test ! -d /usr/lib/ldscripts/. \ + && echo "${UNAME_MACHINE}-pc-linux-gnuoldld" && exit 0 + # Determine whether the default compiler is a.out or elf + cat >dummy.c </dev/null && ./dummy "${UNAME_MACHINE}" && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + fi ;; +# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. earlier versions +# are messed up and put the nodename in both sysname and nodename. + i?86:DYNIX/ptx:4*:*) + echo i386-sequent-sysv4 + exit 0 ;; + i?86:*:4.*:* | i?86:SYSTEM_V:4.*:*) + if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then + echo ${UNAME_MACHINE}-univel-sysv${UNAME_RELEASE} + else + echo ${UNAME_MACHINE}-pc-sysv${UNAME_RELEASE} + fi + exit 0 ;; + i?86:*:3.2:*) + if test -f /usr/options/cb.name; then + UNAME_REL=`sed -n 's/.*Version //p' /dev/null >/dev/null ; then + UNAME_REL=`(/bin/uname -X|egrep Release|sed -e 's/.*= //')` + (/bin/uname -X|egrep i80486 >/dev/null) && UNAME_MACHINE=i486 + (/bin/uname -X|egrep '^Machine.*Pentium' >/dev/null) \ + && UNAME_MACHINE=i586 + echo ${UNAME_MACHINE}-pc-sco$UNAME_REL + else + echo ${UNAME_MACHINE}-pc-sysv32 + fi + exit 0 ;; + Intel:Mach:3*:*) + echo i386-pc-mach3 + exit 0 ;; + paragon:*:*:*) + echo i860-intel-osf1 + exit 0 ;; + i860:*:4.*:*) # i860-SVR4 + if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then + echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4 + else # Add other i860-SVR4 vendors below as they are discovered. + echo i860-unknown-sysv${UNAME_RELEASE} # Unknown i860-SVR4 + fi + exit 0 ;; + mini*:CTIX:SYS*5:*) + # "miniframe" + echo m68010-convergent-sysv + exit 0 ;; + M68*:*:R3V[567]*:*) + test -r /sysV68 && echo 'm68k-motorola-sysv' && exit 0 ;; + 3[34]??:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 4850:*:4.0:3.0) + OS_REL='' + test -r /etc/.relid \ + && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && echo i486-ncr-sysv4.3${OS_REL} && exit 0 + /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ + && echo i586-ncr-sysv4.3${OS_REL} && exit 0 ;; + 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && echo i486-ncr-sysv4 && exit 0 ;; + m68*:LynxOS:2.*:*) + echo m68k-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + mc68030:UNIX_System_V:4.*:*) + echo m68k-atari-sysv4 + exit 0 ;; + i?86:LynxOS:2.*:*) + echo i386-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + TSUNAMI:LynxOS:2.*:*) + echo sparc-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + rs6000:LynxOS:2.*:* | PowerPC:LynxOS:2.*:*) + echo rs6000-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + SM[BE]S:UNIX_SV:*:*) + echo mips-dde-sysv${UNAME_RELEASE} + exit 0 ;; + RM*:SINIX-*:*:*) + echo mips-sni-sysv4 + exit 0 ;; + *:SINIX-*:*:*) + if uname -p 2>/dev/null >/dev/null ; then + UNAME_MACHINE=`(uname -p) 2>/dev/null` + echo ${UNAME_MACHINE}-sni-sysv4 + else + echo ns32k-sni-sysv + fi + exit 0 ;; + *:UNIX_System_V:4*:FTX*) + # From Gerald Hewes . + # How about differentiating between stratus architectures? -djm + echo hppa1.1-stratus-sysv4 + exit 0 ;; + *:*:*:FTX*) + # From seanf@swdc.stratus.com. + echo i860-stratus-sysv4 + exit 0 ;; + mc68*:A/UX:*:*) + echo m68k-apple-aux${UNAME_RELEASE} + exit 0 ;; + R3000:*System_V*:*:* | R4000:UNIX_SYSV:*:*) + if [ -d /usr/nec ]; then + echo mips-nec-sysv${UNAME_RELEASE} + else + echo mips-unknown-sysv${UNAME_RELEASE} + fi + exit 0 ;; + PENTIUM:CPunix:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort + # says + echo i586-unisys-sysv4 + exit 0 ;; +esac + +#echo '(No uname command or uname output not recognized.)' 1>&2 +#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2 + +cat >dummy.c < +# include +#endif +main () +{ +#if defined (sony) +#if defined (MIPSEB) + /* BFD wants "bsd" instead of "newsos". Perhaps BFD should be changed, + I don't know.... */ + printf ("mips-sony-bsd\n"); exit (0); +#else +#include + printf ("m68k-sony-newsos%s\n", +#ifdef NEWSOS4 + "4" +#else + "" +#endif + ); exit (0); +#endif +#endif + +#if defined (__arm) && defined (__acorn) && defined (__unix) + printf ("arm-acorn-riscix"); exit (0); +#endif + +#if defined (hp300) && !defined (hpux) + printf ("m68k-hp-bsd\n"); exit (0); +#endif + +#if defined (NeXT) +#if !defined (__ARCHITECTURE__) +#define __ARCHITECTURE__ "m68k" +#endif + int version; + version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`; + printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version); + exit (0); +#endif + +#if defined (MULTIMAX) || defined (n16) +#if defined (UMAXV) + printf ("ns32k-encore-sysv\n"); exit (0); +#else +#if defined (CMU) + printf ("ns32k-encore-mach\n"); exit (0); +#else + printf ("ns32k-encore-bsd\n"); exit (0); +#endif +#endif +#endif + +#if defined (__386BSD__) + printf ("i386-pc-bsd\n"); exit (0); +#endif + +#if defined (sequent) +#if defined (i386) + printf ("i386-sequent-dynix\n"); exit (0); +#endif +#if defined (ns32000) + printf ("ns32k-sequent-dynix\n"); exit (0); +#endif +#endif + +#if defined (_SEQUENT_) + struct utsname un; + + uname(&un); + + if (strncmp(un.version, "V2", 2) == 0) { + printf ("i386-sequent-ptx2\n"); exit (0); + } + if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */ + printf ("i386-sequent-ptx1\n"); exit (0); + } + printf ("i386-sequent-ptx\n"); exit (0); + +#endif + +#if defined (vax) +#if !defined (ultrix) + printf ("vax-dec-bsd\n"); exit (0); +#else + printf ("vax-dec-ultrix\n"); exit (0); +#endif +#endif + +#if defined (alliant) && defined (i860) + printf ("i860-alliant-bsd\n"); exit (0); +#endif + + exit (1); +} +EOF + +${CC-cc} dummy.c -o dummy 2>/dev/null && ./dummy && rm dummy.c dummy && exit 0 +rm -f dummy.c dummy + +# Apollos put the system type in the environment. + +test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit 0; } + +# Convex versions that predate uname can use getsysinfo(1) + +if [ -x /usr/convex/getsysinfo ] +then + case `getsysinfo -f cpu_type` in + c1*) + echo c1-convex-bsd + exit 0 ;; + c2*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit 0 ;; + c34*) + echo c34-convex-bsd + exit 0 ;; + c38*) + echo c38-convex-bsd + exit 0 ;; + c4*) + echo c4-convex-bsd + exit 0 ;; + esac +fi + +#echo '(Unable to guess system type)' 1>&2 + +exit 1 diff --git a/config.log b/config.log new file mode 100644 index 0000000..3ba549d --- /dev/null +++ b/config.log @@ -0,0 +1,120 @@ +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. + +configure:623: checking for ar +configure:655: checking for ranlib +configure:710: checking host system type +configure:731: checking target system type +configure:749: checking build system type +configure:799: checking for gcc +configure:876: checking whether the C compiler (cc ) works +configure:890: cc -o conftest conftest.c 1>&5 +configure:910: checking whether the C compiler (cc ) is a cross-compiler +configure:915: checking whether we are using GNU C +configure:924: cc -E conftest.c +configure:1003: checking for a BSD compatible install +configure:1184: checking how to run the C preprocessor +configure:1205: cc -E conftest.c >/dev/null 2>conftest.out +configure:1245: checking for ANSI C header files +configure:1258: cc -E conftest.c >/dev/null 2>conftest.out +configure:1325: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1351: checking for sys/wait.h that is POSIX.1 compatible +configure:1372: cc -c -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1398: checking for sys/file.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/stat.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for unistd.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for errno.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for assert.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/wait.h +configure:1398: checking for pwd.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/types.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/times.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/time.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1398: checking for sys/resource.h +configure:1408: cc -E conftest.c >/dev/null 2>conftest.out +configure:1445: checking for stdarg.h +configure:1455: cc -E conftest.c >/dev/null 2>conftest.out +configure:1445: checking for varargs.h +configure:1455: cc -E conftest.c >/dev/null 2>conftest.out +configure:1489: checking for working const +configure:1543: cc -c -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1568: checking size of void * +configure:1587: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1608: checking size of int +configure:1627: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1650: checking for +Infinity (IEEE 754 floating point) +configure:1669: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1701: checking the size of the virtual memory system's page +configure:1726: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1797: checking for 8-bit clean memcmp +configure:1815: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +"configure", line 1809: warning: initializer does not fit: 128 +"configure", line 1809: warning: initializer does not fit: 129 +configure:1836: checking return type of signal handlers +configure:1858: cc -c -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1879: checking for working strcoll +configure:1897: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:1923: checking for pid_t +configure:1957: checking for vfork.h +configure:1967: cc -E conftest.c >/dev/null 2>conftest.out +"configure", line 1963: cannot find include file: +cc: acomp failed for conftest.c +configure: failed program was: +#line 1962 "configure" +#include "confdefs.h" +#include +configure:1992: checking for working vfork +configure:2142: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for sysconf +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for gethostname +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for strcspn +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for strerror +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for strspn +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for strstr +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for getenv +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for strchr +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for getrlimit +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for getrusage +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 +configure:2169: checking for valloc +configure:2197: cc -o conftest -xO5 -native -dalign conftest.c 1>&5 +cc: Warning illegal option -xO5 diff --git a/config.sub b/config.sub new file mode 100644 index 0000000..0432524 --- /dev/null +++ b/config.sub @@ -0,0 +1,927 @@ +#! /bin/sh +# Configuration validation subroutine script, version 1.1. +# Copyright (C) 1991, 92, 93, 94, 95, 1996 Free Software Foundation, Inc. +# This file is (in principle) common to ALL GNU software. +# The presence of a machine in this file suggests that SOME GNU software +# can handle that machine. It does not imply ALL GNU software can. +# +# This file is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, +# Boston, MA 02111-1307, USA. + +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Configuration subroutine to validate and canonicalize a configuration type. +# Supply the specified configuration type as an argument. +# If it is invalid, we print an error message on stderr and exit with code 1. +# Otherwise, we print the canonical config type on stdout and succeed. + +# This file is supposed to be the same for all GNU packages +# and recognize all the CPU types, system types and aliases +# that are meaningful with *any* GNU software. +# Each package is responsible for reporting which valid configurations +# it does not support. The user should be able to distinguish +# a failure to support a valid configuration from a meaningless +# configuration. + +# The goal of this file is to map all the various variations of a given +# machine specification into a single specification in the form: +# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM +# or in some cases, the newer four-part form: +# CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM +# It is wrong to echo any other type of specification. + +if [ x$1 = x ] +then + echo Configuration name missing. 1>&2 + echo "Usage: $0 CPU-MFR-OPSYS" 1>&2 + echo "or $0 ALIAS" 1>&2 + echo where ALIAS is a recognized configuration type. 1>&2 + exit 1 +fi + +# First pass through any local machine types. +case $1 in + *local*) + echo $1 + exit 0 + ;; + *) + ;; +esac + +# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any). +# Here we must recognize all the valid KERNEL-OS combinations. +maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'` +case $maybe_os in + linux-gnu*) + os=-$maybe_os + basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'` + ;; + *) + basic_machine=`echo $1 | sed 's/-[^-]*$//'` + if [ $basic_machine != $1 ] + then os=`echo $1 | sed 's/.*-/-/'` + else os=; fi + ;; +esac + +### Let's recognize common machines as not being operating systems so +### that things like config.sub decstation-3100 work. We also +### recognize some manufacturers as not being operating systems, so we +### can provide default operating systems below. +case $os in + -sun*os*) + # Prevent following clause from handling this invalid input. + ;; + -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \ + -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \ + -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \ + -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\ + -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \ + -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \ + -apple) + os= + basic_machine=$1 + ;; + -hiux*) + os=-hiuxwe2 + ;; + -sco5) + os=sco3.2v5 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco4) + os=-sco3.2v4 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2.[4-9]*) + os=`echo $os | sed -e 's/sco3.2./sco3.2v/'` + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2v[4-9]*) + # Don't forget version if it is 3.2v4 or newer. + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco*) + os=-sco3.2v2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -isc) + os=-isc2.2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -clix*) + basic_machine=clipper-intergraph + ;; + -isc*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -lynx*) + os=-lynxos + ;; + -ptx*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'` + ;; + -windowsnt*) + os=`echo $os | sed -e 's/windowsnt/winnt/'` + ;; + -psos*) + os=-psos + ;; +esac + +# Decode aliases for certain CPU-COMPANY combinations. +case $basic_machine in + # Recognize the basic CPU types without company name. + # Some are omitted here because they have special meanings below. + tahoe | i860 | m68k | m68000 | m88k | ns32k | arm \ + | arme[lb] | pyramid \ + | tron | a29k | 580 | i960 | h8300 | hppa | hppa1.0 | hppa1.1 \ + | alpha | we32k | ns16k | clipper | i370 | sh \ + | powerpc | powerpcle | 1750a | dsp16xx | mips64 | mipsel \ + | pdp11 | mips64el | mips64orion | mips64orionel \ + | sparc | sparclet | sparclite | sparc64) + basic_machine=$basic_machine-unknown + ;; + # We use `pc' rather than `unknown' + # because (1) that's what they normally are, and + # (2) the word "unknown" tends to confuse beginning users. + i[3456]86) + basic_machine=$basic_machine-pc + ;; + # Object if more than one company name word. + *-*-*) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; + # Recognize the basic CPU types with company name. + vax-* | tahoe-* | i[3456]86-* | i860-* | m68k-* | m68000-* | m88k-* \ + | sparc-* | ns32k-* | fx80-* | arm-* | c[123]* \ + | mips-* | pyramid-* | tron-* | a29k-* | romp-* | rs6000-* | power-* \ + | none-* | 580-* | cray2-* | h8300-* | i960-* | xmp-* | ymp-* \ + | hppa-* | hppa1.0-* | hppa1.1-* | alpha-* | we32k-* | cydra-* | ns16k-* \ + | pn-* | np1-* | xps100-* | clipper-* | orion-* | sparclite-* \ + | pdp11-* | sh-* | powerpc-* | powerpcle-* | sparc64-* | mips64-* | mipsel-* \ + | mips64el-* | mips64orion-* | mips64orionel-* | f301-*) + ;; + # Recognize the various machine names and aliases which stand + # for a CPU type and a company and sometimes even an OS. + 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc) + basic_machine=m68000-att + ;; + 3b*) + basic_machine=we32k-att + ;; + alliant | fx80) + basic_machine=fx80-alliant + ;; + altos | altos3068) + basic_machine=m68k-altos + ;; + am29k) + basic_machine=a29k-none + os=-bsd + ;; + amdahl) + basic_machine=580-amdahl + os=-sysv + ;; + amiga | amiga-*) + basic_machine=m68k-cbm + ;; + amigados) + basic_machine=m68k-cbm + os=-amigados + ;; + amigaunix | amix) + basic_machine=m68k-cbm + os=-sysv4 + ;; + apollo68) + basic_machine=m68k-apollo + os=-sysv + ;; + aux) + basic_machine=m68k-apple + os=-aux + ;; + balance) + basic_machine=ns32k-sequent + os=-dynix + ;; + convex-c1) + basic_machine=c1-convex + os=-bsd + ;; + convex-c2) + basic_machine=c2-convex + os=-bsd + ;; + convex-c32) + basic_machine=c32-convex + os=-bsd + ;; + convex-c34) + basic_machine=c34-convex + os=-bsd + ;; + convex-c38) + basic_machine=c38-convex + os=-bsd + ;; + cray | ymp) + basic_machine=ymp-cray + os=-unicos + ;; + cray2) + basic_machine=cray2-cray + os=-unicos + ;; + [ctj]90-cray) + basic_machine=c90-cray + os=-unicos + ;; + crds | unos) + basic_machine=m68k-crds + ;; + da30 | da30-*) + basic_machine=m68k-da30 + ;; + decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn) + basic_machine=mips-dec + ;; + delta | 3300 | motorola-3300 | motorola-delta \ + | 3300-motorola | delta-motorola) + basic_machine=m68k-motorola + ;; + delta88) + basic_machine=m88k-motorola + os=-sysv3 + ;; + dpx20 | dpx20-*) + basic_machine=rs6000-bull + os=-bosx + ;; + dpx2* | dpx2*-bull) + basic_machine=m68k-bull + os=-sysv3 + ;; + ebmon29k) + basic_machine=a29k-amd + os=-ebmon + ;; + elxsi) + basic_machine=elxsi-elxsi + os=-bsd + ;; + encore | umax | mmax) + basic_machine=ns32k-encore + ;; + fx2800) + basic_machine=i860-alliant + ;; + genix) + basic_machine=ns32k-ns + ;; + gmicro) + basic_machine=tron-gmicro + os=-sysv + ;; + h3050r* | hiux*) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + h8300hms) + basic_machine=h8300-hitachi + os=-hms + ;; + harris) + basic_machine=m88k-harris + os=-sysv3 + ;; + hp300-*) + basic_machine=m68k-hp + ;; + hp300bsd) + basic_machine=m68k-hp + os=-bsd + ;; + hp300hpux) + basic_machine=m68k-hp + os=-hpux + ;; + hp9k2[0-9][0-9] | hp9k31[0-9]) + basic_machine=m68000-hp + ;; + hp9k3[2-9][0-9]) + basic_machine=m68k-hp + ;; + hp9k7[0-9][0-9] | hp7[0-9][0-9] | hp9k8[0-9]7 | hp8[0-9]7) + basic_machine=hppa1.1-hp + ;; + hp9k8[0-9][0-9] | hp8[0-9][0-9]) + basic_machine=hppa1.0-hp + ;; + hppa-next) + os=-nextstep3 + ;; + i370-ibm* | ibm*) + basic_machine=i370-ibm + os=-mvs + ;; +# I'm not sure what "Sysv32" means. Should this be sysv3.2? + i[3456]86v32) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv32 + ;; + i[3456]86v4*) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv4 + ;; + i[3456]86v) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv + ;; + i[3456]86sol2) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-solaris2 + ;; + iris | iris4d) + basic_machine=mips-sgi + case $os in + -irix*) + ;; + *) + os=-irix4 + ;; + esac + ;; + isi68 | isi) + basic_machine=m68k-isi + os=-sysv + ;; + m88k-omron*) + basic_machine=m88k-omron + ;; + magnum | m3230) + basic_machine=mips-mips + os=-sysv + ;; + merlin) + basic_machine=ns32k-utek + os=-sysv + ;; + miniframe) + basic_machine=m68000-convergent + ;; + mips3*-*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'` + ;; + mips3*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown + ;; + ncr3000) + basic_machine=i486-ncr + os=-sysv4 + ;; + news | news700 | news800 | news900) + basic_machine=m68k-sony + os=-newsos + ;; + news1000) + basic_machine=m68030-sony + os=-newsos + ;; + news-3600 | risc-news) + basic_machine=mips-sony + os=-newsos + ;; + next | m*-next ) + basic_machine=m68k-next + case $os in + -nextstep* ) + ;; + -ns2*) + os=-nextstep2 + ;; + *) + os=-nextstep3 + ;; + esac + ;; + nh3000) + basic_machine=m68k-harris + os=-cxux + ;; + nh[45]000) + basic_machine=m88k-harris + os=-cxux + ;; + nindy960) + basic_machine=i960-intel + os=-nindy + ;; + np1) + basic_machine=np1-gould + ;; + pa-hitachi) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + paragon) + basic_machine=i860-intel + os=-osf + ;; + pbd) + basic_machine=sparc-tti + ;; + pbb) + basic_machine=m68k-tti + ;; + pc532 | pc532-*) + basic_machine=ns32k-pc532 + ;; + pentium | p5) + basic_machine=i586-intel + ;; + pentiumpro | p6) + basic_machine=i686-intel + ;; + pentium-* | p5-*) + basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentiumpro-* | p6-*) + basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + k5) + # We don't have specific support for AMD's K5 yet, so just call it a Pentium + basic_machine=i586-amd + ;; + nexen) + # We don't have specific support for Nexgen yet, so just call it a Pentium + basic_machine=i586-nexgen + ;; + pn) + basic_machine=pn-gould + ;; + power) basic_machine=rs6000-ibm + ;; + ppc) basic_machine=powerpc-unknown + ;; + ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ppcle | powerpclittle | ppc-le | powerpc-little) + basic_machine=powerpcle-unknown + ;; + ppcle-* | powerpclittle-*) + basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ps2) + basic_machine=i386-ibm + ;; + rm[46]00) + basic_machine=mips-siemens + ;; + rtpc | rtpc-*) + basic_machine=romp-ibm + ;; + sequent) + basic_machine=i386-sequent + ;; + sh) + basic_machine=sh-hitachi + os=-hms + ;; + sps7) + basic_machine=m68k-bull + os=-sysv2 + ;; + spur) + basic_machine=spur-unknown + ;; + sun2) + basic_machine=m68000-sun + ;; + sun2os3) + basic_machine=m68000-sun + os=-sunos3 + ;; + sun2os4) + basic_machine=m68000-sun + os=-sunos4 + ;; + sun3os3) + basic_machine=m68k-sun + os=-sunos3 + ;; + sun3os4) + basic_machine=m68k-sun + os=-sunos4 + ;; + sun4os3) + basic_machine=sparc-sun + os=-sunos3 + ;; + sun4os4) + basic_machine=sparc-sun + os=-sunos4 + ;; + sun4sol2) + basic_machine=sparc-sun + os=-solaris2 + ;; + sun3 | sun3-*) + basic_machine=m68k-sun + ;; + sun4) + basic_machine=sparc-sun + ;; + sun386 | sun386i | roadrunner) + basic_machine=i386-sun + ;; + symmetry) + basic_machine=i386-sequent + os=-dynix + ;; + tower | tower-32) + basic_machine=m68k-ncr + ;; + udi29k) + basic_machine=a29k-amd + os=-udi + ;; + ultra3) + basic_machine=a29k-nyu + os=-sym1 + ;; + vaxv) + basic_machine=vax-dec + os=-sysv + ;; + vms) + basic_machine=vax-dec + os=-vms + ;; + vpp*|vx|vx-*) + basic_machine=f301-fujitsu + ;; + vxworks960) + basic_machine=i960-wrs + os=-vxworks + ;; + vxworks68) + basic_machine=m68k-wrs + os=-vxworks + ;; + vxworks29k) + basic_machine=a29k-wrs + os=-vxworks + ;; + xmp) + basic_machine=xmp-cray + os=-unicos + ;; + xps | xps100) + basic_machine=xps100-honeywell + ;; + none) + basic_machine=none-none + os=-none + ;; + +# Here we handle the default manufacturer of certain CPU types. It is in +# some cases the only manufacturer, in others, it is the most popular. + mips) + basic_machine=mips-mips + ;; + romp) + basic_machine=romp-ibm + ;; + rs6000) + basic_machine=rs6000-ibm + ;; + vax) + basic_machine=vax-dec + ;; + pdp11) + basic_machine=pdp11-dec + ;; + we32k) + basic_machine=we32k-att + ;; + sparc) + basic_machine=sparc-sun + ;; + cydra) + basic_machine=cydra-cydrome + ;; + orion) + basic_machine=orion-highlevel + ;; + orion105) + basic_machine=clipper-highlevel + ;; + *) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; +esac + +# Here we canonicalize certain aliases for manufacturers. +case $basic_machine in + *-digital*) + basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'` + ;; + *-commodore*) + basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'` + ;; + *) + ;; +esac + +# Decode manufacturer-specific aliases for certain operating systems. + +if [ x"$os" != x"" ] +then +case $os in + # First match some system type aliases + # that might get confused with valid system types. + # -solaris* is a basic system type, with this one exception. + -solaris1 | -solaris1.*) + os=`echo $os | sed -e 's|solaris1|sunos4|'` + ;; + -solaris) + os=-solaris2 + ;; + -unixware* | svr4*) + os=-sysv4 + ;; + -gnu/linux*) + os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'` + ;; + # First accept the basic system types. + # The portable systems comes first. + # Each alternative MUST END IN A *, to match a version number. + # -sysv* is not here because it comes later, after sysvr4. + -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \ + | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\ + | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \ + | -amigados* | -msdos* | -newsos* | -unicos* | -aof* | -aos* \ + | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \ + | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \ + | -hiux* | -386bsd* | -netbsd* | -openbsd* | -freebsd* | -riscix* \ + | -lynxos* | -bosx* | -nextstep* | -cxux* | -aout* | -elf* \ + | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \ + | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \ + | -cygwin32* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ + | -linux-gnu* | -uxpv*) + # Remember, each alternative MUST END IN *, to match a version number. + ;; + -linux*) + os=`echo $os | sed -e 's|linux|linux-gnu|'` + ;; + -sunos5*) + os=`echo $os | sed -e 's|sunos5|solaris2|'` + ;; + -sunos6*) + os=`echo $os | sed -e 's|sunos6|solaris3|'` + ;; + -osfrose*) + os=-osfrose + ;; + -osf*) + os=-osf + ;; + -utek*) + os=-bsd + ;; + -dynix*) + os=-bsd + ;; + -acis*) + os=-aos + ;; + -ctix* | -uts*) + os=-sysv + ;; + -ns2 ) + os=-nextstep2 + ;; + # Preserve the version number of sinix5. + -sinix5.*) + os=`echo $os | sed -e 's|sinix|sysv|'` + ;; + -sinix*) + os=-sysv4 + ;; + -triton*) + os=-sysv3 + ;; + -oss*) + os=-sysv3 + ;; + -svr4) + os=-sysv4 + ;; + -svr3) + os=-sysv3 + ;; + -sysvr4) + os=-sysv4 + ;; + # This must come after -sysvr4. + -sysv*) + ;; + -xenix) + os=-xenix + ;; + -none) + ;; + *) + # Get rid of the `-' at the beginning of $os. + os=`echo $os | sed 's/[^-]*-//'` + echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2 + exit 1 + ;; +esac +else + +# Here we handle the default operating systems that come with various machines. +# The value should be what the vendor currently ships out the door with their +# machine or put another way, the most popular os provided with the machine. + +# Note that if you're going to try to match "-MANUFACTURER" here (say, +# "-sun"), then you have to tell the case statement up towards the top +# that MANUFACTURER isn't an operating system. Otherwise, code above +# will signal an error saying that MANUFACTURER isn't an operating +# system, and we'll never get to this point. + +case $basic_machine in + *-acorn) + os=-riscix1.2 + ;; + arm*-semi) + os=-aout + ;; + pdp11-*) + os=-none + ;; + *-dec | vax-*) + os=-ultrix4.2 + ;; + m68*-apollo) + os=-domain + ;; + i386-sun) + os=-sunos4.0.2 + ;; + m68000-sun) + os=-sunos3 + # This also exists in the configure program, but was not the + # default. + # os=-sunos4 + ;; + *-tti) # must be before sparc entry or we get the wrong os. + os=-sysv3 + ;; + sparc-* | *-sun) + os=-sunos4.1.1 + ;; + *-ibm) + os=-aix + ;; + *-hp) + os=-hpux + ;; + *-hitachi) + os=-hiux + ;; + i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent) + os=-sysv + ;; + *-cbm) + os=-amigados + ;; + *-dg) + os=-dgux + ;; + *-dolphin) + os=-sysv3 + ;; + m68k-ccur) + os=-rtu + ;; + m88k-omron*) + os=-luna + ;; + *-next ) + os=-nextstep + ;; + *-sequent) + os=-ptx + ;; + *-crds) + os=-unos + ;; + *-ns) + os=-genix + ;; + i370-*) + os=-mvs + ;; + *-next) + os=-nextstep3 + ;; + *-gould) + os=-sysv + ;; + *-highlevel) + os=-bsd + ;; + *-encore) + os=-bsd + ;; + *-sgi) + os=-irix + ;; + *-siemens) + os=-sysv4 + ;; + *-masscomp) + os=-rtu + ;; + f301-fujitsu) + os=-uxpv + ;; + *) + os=-none + ;; +esac +fi + +# Here we handle the case where we know the os, and the CPU type, but not the +# manufacturer. We pick the logical manufacturer. +vendor=unknown +case $basic_machine in + *-unknown) + case $os in + -riscix*) + vendor=acorn + ;; + -sunos*) + vendor=sun + ;; + -aix*) + vendor=ibm + ;; + -hpux*) + vendor=hp + ;; + -hiux*) + vendor=hitachi + ;; + -unos*) + vendor=crds + ;; + -dgux*) + vendor=dg + ;; + -luna*) + vendor=omron + ;; + -genix*) + vendor=ns + ;; + -mvs*) + vendor=ibm + ;; + -ptx*) + vendor=sequent + ;; + -vxsim* | -vxworks*) + vendor=wrs + ;; + -aux*) + vendor=apple + ;; + esac + basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"` + ;; +esac + +echo $basic_machine$os diff --git a/configure b/configure new file mode 100644 index 0000000..187a437 --- /dev/null +++ b/configure @@ -0,0 +1,2504 @@ +#! /bin/sh + +# Guess values for system-dependent variables and create Makefiles. +# Generated automatically using autoconf version 2.12 +# Copyright (C) 1992, 93, 94, 95, 96 Free Software Foundation, Inc. +# +# This configure script is free software; the Free Software Foundation +# gives unlimited permission to copy, distribute and modify it. + +# Defaults: +ac_help= +ac_default_prefix=/usr/local +# Any additions from configure.in: +ac_help="$ac_help + --enable-times-resolution= + Set the resolution of the times() function (only + necessary for non-POSIX systems)." +ac_help="$ac_help + --with-local-srcdir= Specify the root directory to search for + source for packages (the PKGS list). + Expects to find, e.g., /array/array.c" +ac_help="$ac_help + --with-datasize= (Default: 16777216.) Specify maximum datasize in + bytes for systems without working getrlimit. + The application may use this value to size some + data structures, but may still try to exceed it." +ac_help="$ac_help + --enable-gcc Allow use of gcc if available" +ac_help="$ac_help + --enable-64 Use 64-bit pointers on 64-bit Alpha machines" +ac_help="$ac_help + --with-comp-mode= Specify a special compilation mode: + optimize (the default): Produce optimized + code, with symbol table information + if supported on the platform/compiler, + and without asserts. + debug: Produce unoptimized code with symbol table + information and asserts enabled + purify: Unoptimized code linked with purify + quantify: Optimized code without asserts + linked with quantify" + +# Initialize some variables set by options. +# The variables have the same names as the options, with +# dashes changed to underlines. +build=NONE +cache_file=./config.cache +exec_prefix=NONE +host=NONE +no_create= +nonopt=NONE +no_recursion= +prefix=NONE +program_prefix=NONE +program_suffix=NONE +program_transform_name=s,x,x, +silent= +site= +srcdir= +target=NONE +verbose= +x_includes=NONE +x_libraries=NONE +bindir='${exec_prefix}/bin' +sbindir='${exec_prefix}/sbin' +libexecdir='${exec_prefix}/libexec' +datadir='${prefix}/share' +sysconfdir='${prefix}/etc' +sharedstatedir='${prefix}/com' +localstatedir='${prefix}/var' +libdir='${exec_prefix}/lib' +includedir='${prefix}/include' +oldincludedir='/usr/include' +infodir='${prefix}/info' +mandir='${prefix}/man' + +# Initialize some other variables. +subdirs= +MFLAGS= MAKEFLAGS= +# Maximum number of lines to put in a shell here document. +ac_max_here_lines=12 + +ac_prev= +for ac_option +do + + # If the previous option needs an argument, assign it. + if test -n "$ac_prev"; then + eval "$ac_prev=\$ac_option" + ac_prev= + continue + fi + + case "$ac_option" in + -*=*) ac_optarg=`echo "$ac_option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; + *) ac_optarg= ;; + esac + + # Accept the important Cygnus configure options, so we can diagnose typos. + + case "$ac_option" in + + -bindir | --bindir | --bindi | --bind | --bin | --bi) + ac_prev=bindir ;; + -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) + bindir="$ac_optarg" ;; + + -build | --build | --buil | --bui | --bu) + ac_prev=build ;; + -build=* | --build=* | --buil=* | --bui=* | --bu=*) + build="$ac_optarg" ;; + + -cache-file | --cache-file | --cache-fil | --cache-fi \ + | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) + ac_prev=cache_file ;; + -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ + | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) + cache_file="$ac_optarg" ;; + + -datadir | --datadir | --datadi | --datad | --data | --dat | --da) + ac_prev=datadir ;; + -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \ + | --da=*) + datadir="$ac_optarg" ;; + + -disable-* | --disable-*) + ac_feature=`echo $ac_option|sed -e 's/-*disable-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + eval "enable_${ac_feature}=no" ;; + + -enable-* | --enable-*) + ac_feature=`echo $ac_option|sed -e 's/-*enable-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "enable_${ac_feature}='$ac_optarg'" ;; + + -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ + | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ + | --exec | --exe | --ex) + ac_prev=exec_prefix ;; + -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ + | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ + | --exec=* | --exe=* | --ex=*) + exec_prefix="$ac_optarg" ;; + + -gas | --gas | --ga | --g) + # Obsolete; use --with-gas. + with_gas=yes ;; + + -help | --help | --hel | --he) + # Omit some internal or obsolete options to make the list less imposing. + # This message is too long to be a string in the A/UX 3.1 sh. + cat << EOF +Usage: configure [options] [host] +Options: [defaults in brackets after descriptions] +Configuration: + --cache-file=FILE cache test results in FILE + --help print this message + --no-create do not create output files + --quiet, --silent do not print \`checking...' messages + --version print the version of autoconf that created configure +Directory and file names: + --prefix=PREFIX install architecture-independent files in PREFIX + [$ac_default_prefix] + --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX + [same as prefix] + --bindir=DIR user executables in DIR [EPREFIX/bin] + --sbindir=DIR system admin executables in DIR [EPREFIX/sbin] + --libexecdir=DIR program executables in DIR [EPREFIX/libexec] + --datadir=DIR read-only architecture-independent data in DIR + [PREFIX/share] + --sysconfdir=DIR read-only single-machine data in DIR [PREFIX/etc] + --sharedstatedir=DIR modifiable architecture-independent data in DIR + [PREFIX/com] + --localstatedir=DIR modifiable single-machine data in DIR [PREFIX/var] + --libdir=DIR object code libraries in DIR [EPREFIX/lib] + --includedir=DIR C header files in DIR [PREFIX/include] + --oldincludedir=DIR C header files for non-gcc in DIR [/usr/include] + --infodir=DIR info documentation in DIR [PREFIX/info] + --mandir=DIR man documentation in DIR [PREFIX/man] + --srcdir=DIR find the sources in DIR [configure dir or ..] + --program-prefix=PREFIX prepend PREFIX to installed program names + --program-suffix=SUFFIX append SUFFIX to installed program names + --program-transform-name=PROGRAM + run sed PROGRAM on installed program names +EOF + cat << EOF +Host type: + --build=BUILD configure for building on BUILD [BUILD=HOST] + --host=HOST configure for HOST [guessed] + --target=TARGET configure for TARGET [TARGET=HOST] +Features and packages: + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] + --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) + --x-includes=DIR X include files are in DIR + --x-libraries=DIR X library files are in DIR +EOF + if test -n "$ac_help"; then + echo "--enable and --with options recognized:$ac_help" + fi + exit 0 ;; + + -host | --host | --hos | --ho) + ac_prev=host ;; + -host=* | --host=* | --hos=* | --ho=*) + host="$ac_optarg" ;; + + -includedir | --includedir | --includedi | --included | --include \ + | --includ | --inclu | --incl | --inc) + ac_prev=includedir ;; + -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ + | --includ=* | --inclu=* | --incl=* | --inc=*) + includedir="$ac_optarg" ;; + + -infodir | --infodir | --infodi | --infod | --info | --inf) + ac_prev=infodir ;; + -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) + infodir="$ac_optarg" ;; + + -libdir | --libdir | --libdi | --libd) + ac_prev=libdir ;; + -libdir=* | --libdir=* | --libdi=* | --libd=*) + libdir="$ac_optarg" ;; + + -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ + | --libexe | --libex | --libe) + ac_prev=libexecdir ;; + -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ + | --libexe=* | --libex=* | --libe=*) + libexecdir="$ac_optarg" ;; + + -localstatedir | --localstatedir | --localstatedi | --localstated \ + | --localstate | --localstat | --localsta | --localst \ + | --locals | --local | --loca | --loc | --lo) + ac_prev=localstatedir ;; + -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ + | --localstate=* | --localstat=* | --localsta=* | --localst=* \ + | --locals=* | --local=* | --loca=* | --loc=* | --lo=*) + localstatedir="$ac_optarg" ;; + + -mandir | --mandir | --mandi | --mand | --man | --ma | --m) + ac_prev=mandir ;; + -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) + mandir="$ac_optarg" ;; + + -nfp | --nfp | --nf) + # Obsolete; use --without-fp. + with_fp=no ;; + + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) + no_create=yes ;; + + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) + no_recursion=yes ;; + + -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ + | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ + | --oldin | --oldi | --old | --ol | --o) + ac_prev=oldincludedir ;; + -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ + | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ + | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) + oldincludedir="$ac_optarg" ;; + + -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) + ac_prev=prefix ;; + -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) + prefix="$ac_optarg" ;; + + -program-prefix | --program-prefix | --program-prefi | --program-pref \ + | --program-pre | --program-pr | --program-p) + ac_prev=program_prefix ;; + -program-prefix=* | --program-prefix=* | --program-prefi=* \ + | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) + program_prefix="$ac_optarg" ;; + + -program-suffix | --program-suffix | --program-suffi | --program-suff \ + | --program-suf | --program-su | --program-s) + ac_prev=program_suffix ;; + -program-suffix=* | --program-suffix=* | --program-suffi=* \ + | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) + program_suffix="$ac_optarg" ;; + + -program-transform-name | --program-transform-name \ + | --program-transform-nam | --program-transform-na \ + | --program-transform-n | --program-transform- \ + | --program-transform | --program-transfor \ + | --program-transfo | --program-transf \ + | --program-trans | --program-tran \ + | --progr-tra | --program-tr | --program-t) + ac_prev=program_transform_name ;; + -program-transform-name=* | --program-transform-name=* \ + | --program-transform-nam=* | --program-transform-na=* \ + | --program-transform-n=* | --program-transform-=* \ + | --program-transform=* | --program-transfor=* \ + | --program-transfo=* | --program-transf=* \ + | --program-trans=* | --program-tran=* \ + | --progr-tra=* | --program-tr=* | --program-t=*) + program_transform_name="$ac_optarg" ;; + + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + silent=yes ;; + + -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) + ac_prev=sbindir ;; + -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ + | --sbi=* | --sb=*) + sbindir="$ac_optarg" ;; + + -sharedstatedir | --sharedstatedir | --sharedstatedi \ + | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ + | --sharedst | --shareds | --shared | --share | --shar \ + | --sha | --sh) + ac_prev=sharedstatedir ;; + -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ + | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ + | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ + | --sha=* | --sh=*) + sharedstatedir="$ac_optarg" ;; + + -site | --site | --sit) + ac_prev=site ;; + -site=* | --site=* | --sit=*) + site="$ac_optarg" ;; + + -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) + ac_prev=srcdir ;; + -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) + srcdir="$ac_optarg" ;; + + -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ + | --syscon | --sysco | --sysc | --sys | --sy) + ac_prev=sysconfdir ;; + -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ + | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) + sysconfdir="$ac_optarg" ;; + + -target | --target | --targe | --targ | --tar | --ta | --t) + ac_prev=target ;; + -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) + target="$ac_optarg" ;; + + -v | -verbose | --verbose | --verbos | --verbo | --verb) + verbose=yes ;; + + -version | --version | --versio | --versi | --vers) + echo "configure generated by autoconf version 2.12" + exit 0 ;; + + -with-* | --with-*) + ac_package=`echo $ac_option|sed -e 's/-*with-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "with_${ac_package}='$ac_optarg'" ;; + + -without-* | --without-*) + ac_package=`echo $ac_option|sed -e 's/-*without-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + eval "with_${ac_package}=no" ;; + + --x) + # Obsolete; use --with-x. + with_x=yes ;; + + -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ + | --x-incl | --x-inc | --x-in | --x-i) + ac_prev=x_includes ;; + -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ + | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) + x_includes="$ac_optarg" ;; + + -x-libraries | --x-libraries | --x-librarie | --x-librari \ + | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) + ac_prev=x_libraries ;; + -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ + | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) + x_libraries="$ac_optarg" ;; + + -*) { echo "configure: error: $ac_option: invalid option; use --help to show usage" 1>&2; exit 1; } + ;; + + *) + if test -n "`echo $ac_option| sed 's/[-a-z0-9.]//g'`"; then + echo "configure: warning: $ac_option: invalid host type" 1>&2 + fi + if test "x$nonopt" != xNONE; then + { echo "configure: error: can only configure for one host and one target at a time" 1>&2; exit 1; } + fi + nonopt="$ac_option" + ;; + + esac +done + +if test -n "$ac_prev"; then + { echo "configure: error: missing argument to --`echo $ac_prev | sed 's/_/-/g'`" 1>&2; exit 1; } +fi + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +# File descriptor usage: +# 0 standard input +# 1 file creation +# 2 errors and warnings +# 3 some systems may open it to /dev/tty +# 4 used on the Kubota Titan +# 6 checking for... messages and results +# 5 compiler messages saved in config.log +if test "$silent" = yes; then + exec 6>/dev/null +else + exec 6>&1 +fi +exec 5>./config.log + +echo "\ +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. +" 1>&5 + +# Strip out --no-create and --no-recursion so they do not pile up. +# Also quote any args containing shell metacharacters. +ac_configure_args= +for ac_arg +do + case "$ac_arg" in + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) ;; + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) ;; + *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?]*) + ac_configure_args="$ac_configure_args '$ac_arg'" ;; + *) ac_configure_args="$ac_configure_args $ac_arg" ;; + esac +done + +# NLS nuisances. +# Only set these to C if already set. These must not be set unconditionally +# because not all systems understand e.g. LANG=C (notably SCO). +# Fixing LC_MESSAGES prevents Solaris sh from translating var values in `set'! +# Non-C LC_CTYPE values break the ctype check. +if test "${LANG+set}" = set; then LANG=C; export LANG; fi +if test "${LC_ALL+set}" = set; then LC_ALL=C; export LC_ALL; fi +if test "${LC_MESSAGES+set}" = set; then LC_MESSAGES=C; export LC_MESSAGES; fi +if test "${LC_CTYPE+set}" = set; then LC_CTYPE=C; export LC_CTYPE; fi + +# confdefs.h avoids OS command line length limits that DEFS can exceed. +rm -rf conftest* confdefs.h +# AIX cpp loses on an empty file, so make sure it contains at least a newline. +echo > confdefs.h + +# A filename unique to this package, relative to the directory that +# configure is in, which we can look for to find out if srcdir is correct. +ac_unique_file=cal.c + +# Find the source files, if location was not specified. +if test -z "$srcdir"; then + ac_srcdir_defaulted=yes + # Try the directory containing this script, then its parent. + ac_prog=$0 + ac_confdir=`echo $ac_prog|sed 's%/[^/][^/]*$%%'` + test "x$ac_confdir" = "x$ac_prog" && ac_confdir=. + srcdir=$ac_confdir + if test ! -r $srcdir/$ac_unique_file; then + srcdir=.. + fi +else + ac_srcdir_defaulted=no +fi +if test ! -r $srcdir/$ac_unique_file; then + if test "$ac_srcdir_defaulted" = yes; then + { echo "configure: error: can not find sources in $ac_confdir or .." 1>&2; exit 1; } + else + { echo "configure: error: can not find sources in $srcdir" 1>&2; exit 1; } + fi +fi +srcdir=`echo "${srcdir}" | sed 's%\([^/]\)/*$%\1%'` + +# Prefer explicitly selected file to automatically selected ones. +if test -z "$CONFIG_SITE"; then + if test "x$prefix" != xNONE; then + CONFIG_SITE="$prefix/share/config.site $prefix/etc/config.site" + else + CONFIG_SITE="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" + fi +fi +for ac_site_file in $CONFIG_SITE; do + if test -r "$ac_site_file"; then + echo "loading site script $ac_site_file" + . "$ac_site_file" + fi +done + +if test -r "$cache_file"; then + echo "loading cache $cache_file" + . $cache_file +else + echo "creating cache $cache_file" + > $cache_file +fi + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then + # Stardent Vistra SVR4 grep lacks -e, says ghazi@caip.rutgers.edu. + if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then + ac_n= ac_c=' +' ac_t=' ' + else + ac_n=-n ac_c= ac_t= + fi +else + ac_n= ac_c='\c' ac_t= +fi + + + +ac_aux_dir= +for ac_dir in . $srcdir/.; do + if test -f $ac_dir/install-sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install-sh -c" + break + elif test -f $ac_dir/install.sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install.sh -c" + break + fi +done +if test -z "$ac_aux_dir"; then + { echo "configure: error: can not find install-sh or install.sh in . $srcdir/." 1>&2; exit 1; } +fi +ac_config_guess=$ac_aux_dir/config.guess +ac_config_sub=$ac_aux_dir/config.sub +ac_configure=$ac_aux_dir/configure # This should be Cygnus configure. + + +# Check whether --enable-times-resolution or --disable-times-resolution was given. +if test "${enable_times_resolution+set}" = set; then + enableval="$enable_times_resolution" + cat >> confdefs.h <> confdefs.h <> confdefs.h <&6 +echo "configure:623: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_path_AR'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + case "$AR" in + /*) + ac_cv_path_AR="$AR" # Let the user override the test with a path. + ;; + *) + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_path_AR="$ac_dir/$ac_word" + break + fi + done + IFS="$ac_save_ifs" + test -z "$ac_cv_path_AR" && ac_cv_path_AR="ar" + ;; +esac +fi +AR="$ac_cv_path_AR" +if test -n "$AR"; then + echo "$ac_t""$AR" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +# Extract the first word of "ranlib", so it can be a program name with args. +set dummy ranlib; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:655: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_RANLIB'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$RANLIB"; then + ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_RANLIB="ranlib" + break + fi + done + IFS="$ac_save_ifs" + test -z "$ac_cv_prog_RANLIB" && ac_cv_prog_RANLIB=":" +fi +fi +RANLIB="$ac_cv_prog_RANLIB" +if test -n "$RANLIB"; then + echo "$ac_t""$RANLIB" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + + + +# Do some error checking and defaulting for the host and target type. +# The inputs are: +# configure --host=HOST --target=TARGET --build=BUILD NONOPT +# +# The rules are: +# 1. You are not allowed to specify --host, --target, and nonopt at the +# same time. +# 2. Host defaults to nonopt. +# 3. If nonopt is not specified, then host defaults to the current host, +# as determined by config.guess. +# 4. Target and build default to nonopt. +# 5. If nonopt is not specified, then target and build default to host. + +# The aliases save the names the user supplied, while $host etc. +# will get canonicalized. +case $host---$target---$nonopt in +NONE---*---* | *---NONE---* | *---*---NONE) ;; +*) { echo "configure: error: can only configure for one host and one target at a time" 1>&2; exit 1; } ;; +esac + + +# Make sure we can run config.sub. +if $ac_config_sub sun4 >/dev/null 2>&1; then : +else { echo "configure: error: can not run $ac_config_sub" 1>&2; exit 1; } +fi + +echo $ac_n "checking host system type""... $ac_c" 1>&6 +echo "configure:710: checking host system type" >&5 + +host_alias=$host +case "$host_alias" in +NONE) + case $nonopt in + NONE) + if host_alias=`$ac_config_guess`; then : + else { echo "configure: error: can not guess host type; you must specify one" 1>&2; exit 1; } + fi ;; + *) host_alias=$nonopt ;; + esac ;; +esac + +host=`$ac_config_sub $host_alias` +host_cpu=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +host_vendor=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +host_os=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` +echo "$ac_t""$host" 1>&6 + +echo $ac_n "checking target system type""... $ac_c" 1>&6 +echo "configure:731: checking target system type" >&5 + +target_alias=$target +case "$target_alias" in +NONE) + case $nonopt in + NONE) target_alias=$host_alias ;; + *) target_alias=$nonopt ;; + esac ;; +esac + +target=`$ac_config_sub $target_alias` +target_cpu=`echo $target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +target_vendor=`echo $target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +target_os=`echo $target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` +echo "$ac_t""$target" 1>&6 + +echo $ac_n "checking build system type""... $ac_c" 1>&6 +echo "configure:749: checking build system type" >&5 + +build_alias=$build +case "$build_alias" in +NONE) + case $nonopt in + NONE) build_alias=$host_alias ;; + *) build_alias=$nonopt ;; + esac ;; +esac + +build=`$ac_config_sub $build_alias` +build_cpu=`echo $build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +build_vendor=`echo $build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +build_os=`echo $build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` +echo "$ac_t""$build" 1>&6 + +test "$host_alias" != "$target_alias" && + test "$program_prefix$program_suffix$program_transform_name" = \ + NONENONEs,x,x, && + program_prefix=${target_alias}- + + + +# Determine the name of the C compiler we're going to use + +# Check whether --enable-gcc or --disable-gcc was given. +if test "${enable_gcc+set}" = set; then + enableval="$enable_gcc" + gcc_ok=$enableval +else + gcc_ok=no +fi + + +if test "$gcc_ok" = "yes"; then + CC=gcc +else +# Balakrishna Kumthekar +# As we do not support cc on RS6000, Cygwin and SunOS. + case "$target" in + rs6000-ibm-aix* | *-pc-cygwin32 | sparc-sun-sunos*) + CC=gcc ;; + *) + CC=cc ;; + esac +fi +# Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:799: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_CC="gcc" + break + fi + done + IFS="$ac_save_ifs" +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +if test -z "$CC"; then + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:828: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + ac_prog_rejected=no + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + if test "$ac_dir/$ac_word" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC="cc" + break + fi + done + IFS="$ac_save_ifs" +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC + shift + if test $# -gt 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC to just the basename; use the full file name. + shift + set dummy "$ac_dir/$ac_word" "$@" + shift + ac_cv_prog_CC="$@" + fi +fi +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + + test -z "$CC" && { echo "configure: error: no acceptable cc found in \$PATH" 1>&2; exit 1; } +fi + +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 +echo "configure:876: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then + ac_cv_prog_cc_works=yes + # If we can't run a trivial program, we are probably using a cross compiler. + if (./conftest; exit) 2>/dev/null; then + ac_cv_prog_cc_cross=no + else + ac_cv_prog_cc_cross=yes + fi +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + ac_cv_prog_cc_works=no +fi +rm -fr conftest* + +echo "$ac_t""$ac_cv_prog_cc_works" 1>&6 +if test $ac_cv_prog_cc_works = no; then + { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } +fi +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 +echo "configure:910: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 +cross_compiling=$ac_cv_prog_cc_cross + +echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 +echo "configure:915: checking whether we are using GNU C" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then + ac_cv_prog_gcc=yes +else + ac_cv_prog_gcc=no +fi +fi + +echo "$ac_t""$ac_cv_prog_gcc" 1>&6 + +if test $ac_cv_prog_gcc = yes; then + GCC=yes + ac_test_CFLAGS="${CFLAGS+set}" + ac_save_CFLAGS="$CFLAGS" + CFLAGS= + echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 +echo "configure:939: checking whether ${CC-cc} accepts -g" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + echo 'void f(){}' > conftest.c +if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then + ac_cv_prog_cc_g=yes +else + ac_cv_prog_cc_g=no +fi +rm -f conftest* + +fi + +echo "$ac_t""$ac_cv_prog_cc_g" 1>&6 + if test "$ac_test_CFLAGS" = set; then + CFLAGS="$ac_save_CFLAGS" + elif test $ac_cv_prog_cc_g = yes; then + CFLAGS="-g -O2" + else + CFLAGS="-O2" + fi +else + GCC= + test "${CFLAGS+set}" = set || CFLAGS="-g" +fi + + +# Check whether --enable-64 or --disable-64 was given. +if test "${enable_64+set}" = set; then + enableval="$enable_64" + use_sixty_four=$enableval +else + use_sixty_four=no +fi + + +if test "$gcc_ok" = "yes"; then + use_sixty_four="yes" +fi + + +# Determine the compiler flags to use + +# Balakrisha Kumthekar (kumtheka@colorado.edu): making a special case for ultrix install, +# since its annoying about setting groupids. +case "$target" in + mips-dec-ultrix*) + INSTALL="helpers/install-sh -c" + INSTALL_PROGRAM="\${INSTALL}" + INSTALL_DATA="\${INSTALL} -m 644";; + + *) + # Find a good install program. We prefer a C program (faster), +# so one script is as good as another. But avoid the broken or +# incompatible versions: +# SysV /etc/install, /usr/sbin/install +# SunOS /usr/etc/install +# IRIX /sbin/install +# AIX /bin/install +# AFS /usr/afsws/bin/install, which mishandles nonexistent args +# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" +# ./install, which can be erroneously created by make from ./install.sh. +echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 +echo "configure:1003: checking for a BSD compatible install" >&5 +if test -z "$INSTALL"; then +if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + # Account for people who put trailing slashes in PATH elements. + case "$ac_dir/" in + /|./|.//|/etc/*|/usr/sbin/*|/usr/etc/*|/sbin/*|/usr/afsws/bin/*|/usr/ucb/*) ;; + *) + # OSF1 and SCO ODT 3.0 have their own names for install. + for ac_prog in ginstall installbsd scoinst install; do + if test -f $ac_dir/$ac_prog; then + if test $ac_prog = install && + grep dspmsg $ac_dir/$ac_prog >/dev/null 2>&1; then + # AIX install. It has an incompatible calling convention. + # OSF/1 installbsd also uses dspmsg, but is usable. + : + else + ac_cv_path_install="$ac_dir/$ac_prog -c" + break 2 + fi + fi + done + ;; + esac + done + IFS="$ac_save_IFS" + +fi + if test "${ac_cv_path_install+set}" = set; then + INSTALL="$ac_cv_path_install" + else + # As a last resort, use the slow shell script. We don't cache a + # path for INSTALL within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the path is relative. + INSTALL="$ac_install_sh" + fi +fi +echo "$ac_t""$INSTALL" 1>&6 + +# Use test -z because SunOS4 sh mishandles braces in ${var-val}. +# It thinks the first close brace ends the variable substitution. +test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' + +test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' + ;; +esac + + +DEBUG_CFLAGS="-g" +DEBUG_LDFLAGS="" + +case "$target" in + + sparc-sun-solaris*) + # Sparc Solaris: + # -xO5: Highest level of optimization + # -native: Optimize for the native processor + # -dalign: Generate double-word load/store for performance + OPTIMIZE_CFLAGS="-xO5 -native -dalign" ;; + + mips-dec-ultrix*) + # MIPS-based DECstations running Ultrix: + # -std1: Produce non-ANSI code warnings, and define __STDC__ + # -O: Use the global "ucode" optimizer + # -Olimit 5000: Don't optimize routines bigger than 5000 basic blocks + OPTIMIZE_CFLAGS="-std1 -O -Olimit 5000" ;; + + alpha-dec-osf*) + # DEC Alpha running OSF: + + # 64-bit mode: + # -g3: Produce symbol table information for optimized code + # -O4: Enable every optimization + # -std: Enforce the ANSI standard with extensions, define __STDC__ + # -ieee_with_no_inexact: Disable (potentially slow) signaling + # for inexact floating-point results + # -tune host: Tune instructions for the compilation host machine + + OPTIMIZE_CFLAGS="-g3 -O4 -std -ieee_with_no_inexact -tune host" + DEBUG_CFLAGS="-g -std -ieee_with_no_inexact" + + # -non_shared: Do not use shared libraries + # -om: Generate an OMAGIC file for the om optimizer + OPTIMIZE_LDFLAGS="-non_shared -om" + + if test "$use_sixty_four" = "no"; then + # 32-bit mode: + # -xtaso: Make the compiler respond to #pragma pointer_size directives + OPTIMIZE_CFLAGS="$OPTIMIZE_CFLAGS -xtaso" + DEBUG_CFLAGS="$DEBUG_CFLAGS -xtaso" + + # -taso: Load the executable into the lower 31-bit address space + OPTIMIZE_LDFLAGS="$OPTIMIZE_LDFLAGS -taso" + DEBUG_LDFLAGS="$DEBUG_LDFLAGS -taso" + + cat >> confdefs.h <<\EOF +#define SIZEOF_VOID_P 4 +EOF + + ac_sizeof_voidp=4 + fi + ;; + + hppa*-*-hpux*) + # HP running HPUX + # -Aa: Behave as an ANSI compiler + # -D_HPUX_SOURCE: Include "HP-specific" symbols in the header + # files (e.g., this means sys/resource.h has struct rusage) + OPTIMIZE_CFLAGS="-O -Aa -D_HPUX_SOURCE" + DEBUG_CFLAGS="-g -Aa -D_HPUX_SOURCE" ;; + + *) + # Other systems: + OPTIMIZE_CFLAGS="-O" ;; + +esac + +if test "$CC" = "gcc" ; then + OPTIMIZE_CFLAGS="-g -O3" + OPTIMIZE_LDFLAGS="" + DEBUG_CFLAGS="-g" + DEBUG_LDFLAGS="" +fi + +# Check whether --with-comp-mode or --without-comp-mode was given. +if test "${with_comp_mode+set}" = set; then + withval="$with_comp_mode" + comp_mode=$withval +else + comp_mode=optimize +fi + + + + +LINKER="$CC" + +case "$comp_mode" in + debug) + CFLAGS="$DEBUG_CFLAGS" + LDFLAGS="$DEBUG_LDFLAGS" ;; + purify) + CFLAGS="$DEBUG_CFLAGS" + LDFLAGS="$DEBUG_LDFLAGS" + cat >> confdefs.h <<\EOF +#define PURIFY 1 +EOF + + LINKER="purify -cache-dir=/tmp $CC" + PLINKER="purify -log-file=./purify.log -cachedir=/tmp $CC" ;; + quantify) + CFLAGS="$OPTIMIZE_CFLAGS" + LDFLAGS="$OPTIMIZE_LDFLAGS" + cat >> confdefs.h <<\EOF +#define QUANTIFY 1 +EOF + + cat >> confdefs.h <<\EOF +#define NDEBUG 1 +EOF + + LINKER="quantify $CC" ;; + optimize | *) + CFLAGS="$OPTIMIZE_CFLAGS" + LDFLAGS="$OPTIMIZE_LDFLAGS" + cat >> confdefs.h <<\EOF +#define NDEBUG 1 +EOF + ;; +esac + +#---------------------------------------------------------------------- +# Checks for libraries +#---------------------------------------------------------------------- + +# Define STDC_HEADERS if the system has ANSI C header files +echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 +echo "configure:1184: checking how to run the C preprocessor" >&5 +# On Suns, sometimes $CPP names a directory. +if test -n "$CPP" && test -d "$CPP"; then + CPP= +fi +if test -z "$CPP"; then +if eval "test \"`echo '$''{'ac_cv_prog_CPP'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + # This must be in double quotes, not single quotes, because CPP may get + # substituted into the Makefile and "${CC-cc}" will confuse make. + CPP="${CC-cc} -E" + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. + cat > conftest.$ac_ext < +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1205: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP="${CC-cc} -E -traditional-cpp" + cat > conftest.$ac_ext < +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1222: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP=/lib/cpp +fi +rm -f conftest* +fi +rm -f conftest* + ac_cv_prog_CPP="$CPP" +fi + CPP="$ac_cv_prog_CPP" +else + ac_cv_prog_CPP="$CPP" +fi +echo "$ac_t""$CPP" 1>&6 + +echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 +echo "configure:1245: checking for ANSI C header files" >&5 +if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +#include +#include +#include +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1258: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + ac_cv_header_stdc=yes +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +if test $ac_cv_header_stdc = yes; then + # SunOS 4.x string.h does not declare mem*, contrary to ANSI. +cat > conftest.$ac_ext < +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "memchr" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. +cat > conftest.$ac_ext < +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "free" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. +if test "$cross_compiling" = yes; then + : +else + cat > conftest.$ac_ext < +#define ISLOWER(c) ('a' <= (c) && (c) <= 'z') +#define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) +#define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) +int main () { int i; for (i = 0; i < 256; i++) +if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) exit(2); +exit (0); } + +EOF +if { (eval echo configure:1325: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + : +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_header_stdc=no +fi +rm -fr conftest* +fi + +fi +fi + +echo "$ac_t""$ac_cv_header_stdc" 1>&6 +if test $ac_cv_header_stdc = yes; then + cat >> confdefs.h <<\EOF +#define STDC_HEADERS 1 +EOF + +fi + + +# Define HAVE_SYS_WAIT_H if sys/wait.h exists and is POSIX-compliant +echo $ac_n "checking for sys/wait.h that is POSIX.1 compatible""... $ac_c" 1>&6 +echo "configure:1351: checking for sys/wait.h that is POSIX.1 compatible" >&5 +if eval "test \"`echo '$''{'ac_cv_header_sys_wait_h'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +#include +#ifndef WEXITSTATUS +#define WEXITSTATUS(stat_val) ((unsigned)(stat_val) >> 8) +#endif +#ifndef WIFEXITED +#define WIFEXITED(stat_val) (((stat_val) & 255) == 0) +#endif +int main() { +int s; +wait (&s); +s = WIFEXITED (s) ? WEXITSTATUS (s) : 1; +; return 0; } +EOF +if { (eval echo configure:1372: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_header_sys_wait_h=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_header_sys_wait_h=no +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_header_sys_wait_h" 1>&6 +if test $ac_cv_header_sys_wait_h = yes; then + cat >> confdefs.h <<\EOF +#define HAVE_SYS_WAIT_H 1 +EOF + +fi + + +# Check for these system header files +for ac_hdr in sys/file.h sys/stat.h unistd.h errno.h assert.h sys/wait.h pwd.h sys/types.h sys/times.h sys/time.h sys/resource.h +do +ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 +echo "configure:1398: checking for $ac_hdr" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1408: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` + cat >> confdefs.h <&6 +fi +done + + +# Check how the compiler handles functions with variable argument lists +# +# If there's a , this is probably an ANSI compiler and the "..." +# notation will probably work. If not, there may be another version +# called , that uses an argument of the type "va_alist" +# (see, e.g., Ultrix, Digital Unix) +for ac_hdr in stdarg.h varargs.h +do +ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 +echo "configure:1445: checking for $ac_hdr" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1455: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` + cat >> confdefs.h <&6 +fi +done + + +#---------------------------------------------------------------------- +# Checks for typedefs, structures, and compiler characteristics. +#---------------------------------------------------------------------- + +# Check to see if the compiler understands "const" +# #define it empty otherwise +echo $ac_n "checking for working const""... $ac_c" 1>&6 +echo "configure:1489: checking for working const" >&5 +if eval "test \"`echo '$''{'ac_cv_c_const'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <j = 5; +} +{ /* ULTRIX-32 V3.1 (Rev 9) vcc rejects this */ + const int foo = 10; +} + +; return 0; } +EOF +if { (eval echo configure:1543: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_c_const=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_c_const=no +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_c_const" 1>&6 +if test $ac_cv_c_const = no; then + cat >> confdefs.h <<\EOF +#define const +EOF + +fi + + +# Check the size of pointers and ints + +if test -z "$ac_sizeof_voidp"; then + echo $ac_n "checking size of void *""... $ac_c" 1>&6 +echo "configure:1568: checking size of void *" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_void_p'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext < +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(void *)); + exit(0); +} +EOF +if { (eval echo configure:1587: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_void_p=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_void_p=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_void_p" 1>&6 +cat >> confdefs.h <&6 +echo "configure:1608: checking size of int" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_int'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext < +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(int)); + exit(0); +} +EOF +if { (eval echo configure:1627: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_int=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_int=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_int" 1>&6 +cat >> confdefs.h <&6 +echo "configure:1650: checking for +Infinity (IEEE 754 floating point)" >&5 +if eval "test \"`echo '$''{'ac_cv_have_ieee_754'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + ac_cv_have_ieee_754=no +else + cat > conftest.$ac_ext < +main() +{ + if (HUGE_VAL != HUGE_VAL * 3 || HUGE_VAL != HUGE_VAL / 3) exit(1); + exit(0); +} + +EOF +if { (eval echo configure:1669: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_have_ieee_754=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_have_ieee_754=no +fi +rm -fr conftest* +fi + +fi + +if test $ac_cv_have_ieee_754 = yes ; then + echo "$ac_t""working" 1>&6 + cat >> confdefs.h <<\EOF +#define HAVE_IEEE_754 1 +EOF + +else + echo "$ac_t""broken" 1>&6 +fi + +# Check the size of the virtual memory page +# +# The Cal BDD package uses this +# +# This compiles and runs a small program that gets the pagesize from +# the "getpagesize()" UNIX system function. + +echo $ac_n "checking the size of the virtual memory system's page""... $ac_c" 1>&6 +echo "configure:1701: checking the size of the virtual memory system's page" >&5 +if eval "test \"`echo '$''{'ac_cv_sys_pagesize'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext < +#ifdef HAVE_UNISTD_H +# include +#endif + +main() { + FILE * f = fopen( "conftestval", "w" ); + if ( f == NULL ) exit(1); + fprintf( f, "%d\n", (int) getpagesize() ); + exit(0); +} + +EOF +if { (eval echo configure:1726: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_sys_pagesize=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sys_pagesize=unknown +fi +rm -fr conftest* +fi + +fi + +case "$ac_cv_sys_pagesize" in + 512) + echo "$ac_t""512" 1>&6 + PAGE_SIZE=512 + LG_PAGE_SIZE=9 ;; + 1024) + echo "$ac_t""1K" 1>&6 + PAGE_SIZE=1024 + LG_PAGE_SIZE=10 ;; + 2048) + echo "$ac_t""2K" 1>&6 + PAGE_SIZE=2048 + LG_PAGE_SIZE=11 ;; + 4096) + echo "$ac_t""4K" 1>&6 + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; + 8192) + echo "$ac_t""8K" 1>&6 + PAGE_SIZE=8192 + LG_PAGE_SIZE=13 ;; + 16384) + echo "$ac_t""16K" 1>&6 + PAGE_SIZE=16384 + LG_PAGE_SIZE=14 ;; + 32768) + echo "$ac_t""32K" 1>&6 + PAGE_SIZE=32768 + LG_PAGE_SIZE=15 ;; + 65536) + echo "$ac_t""64K" 1>&6 + PAGE_SIZE=65536 + LG_PAGE_SIZE=16 ;; + unknown) + echo "$ac_t""could not determine -- assuming 4K" 1>&6 + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; + *) + echo "$ac_t""Invalid page size $ac_cv_sys_pagesize -- assuming 4K" 1>&6 + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; +esac +cat >> confdefs.h <> confdefs.h <&6 +echo "configure:1797: checking for 8-bit clean memcmp" >&5 +if eval "test \"`echo '$''{'ac_cv_func_memcmp_clean'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + ac_cv_func_memcmp_clean=no +else + cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_func_memcmp_clean=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_func_memcmp_clean=no +fi +rm -fr conftest* +fi + +fi + +echo "$ac_t""$ac_cv_func_memcmp_clean" 1>&6 +test $ac_cv_func_memcmp_clean = no && LIBOBJS="$LIBOBJS memcmp.o" + + +# Define RETSIGTYPE to be void or int depending on the expected return type of +# a signal handler +echo $ac_n "checking return type of signal handlers""... $ac_c" 1>&6 +echo "configure:1836: checking return type of signal handlers" >&5 +if eval "test \"`echo '$''{'ac_cv_type_signal'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +#include +#ifdef signal +#undef signal +#endif +#ifdef __cplusplus +extern "C" void (*signal (int, void (*)(int)))(int); +#else +void (*signal ()) (); +#endif + +int main() { +int i; +; return 0; } +EOF +if { (eval echo configure:1858: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_type_signal=void +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_type_signal=int +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_type_signal" 1>&6 +cat >> confdefs.h <&6 +echo "configure:1879: checking for working strcoll" >&5 +if eval "test \"`echo '$''{'ac_cv_func_strcoll_works'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + ac_cv_func_strcoll_works=no +else + cat > conftest.$ac_ext < +main () +{ + exit (strcoll ("abc", "def") >= 0 || + strcoll ("ABC", "DEF") >= 0 || + strcoll ("123", "456") >= 0); +} +EOF +if { (eval echo configure:1897: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_func_strcoll_works=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_func_strcoll_works=no +fi +rm -fr conftest* +fi + +fi + +echo "$ac_t""$ac_cv_func_strcoll_works" 1>&6 +if test $ac_cv_func_strcoll_works = yes; then + cat >> confdefs.h <<\EOF +#define HAVE_STRCOLL 1 +EOF + +fi + + +# Define HAVE_VFORK_H if vfork.h is present, otherwise define "vfork" to be +# "fork" +echo $ac_n "checking for pid_t""... $ac_c" 1>&6 +echo "configure:1923: checking for pid_t" >&5 +if eval "test \"`echo '$''{'ac_cv_type_pid_t'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +#if STDC_HEADERS +#include +#include +#endif +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "pid_t[^a-zA-Z_0-9]" >/dev/null 2>&1; then + rm -rf conftest* + ac_cv_type_pid_t=yes +else + rm -rf conftest* + ac_cv_type_pid_t=no +fi +rm -f conftest* + +fi +echo "$ac_t""$ac_cv_type_pid_t" 1>&6 +if test $ac_cv_type_pid_t = no; then + cat >> confdefs.h <<\EOF +#define pid_t int +EOF + +fi + +ac_safe=`echo "vfork.h" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for vfork.h""... $ac_c" 1>&6 +echo "configure:1957: checking for vfork.h" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1967: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + cat >> confdefs.h <<\EOF +#define HAVE_VFORK_H 1 +EOF + +else + echo "$ac_t""no" 1>&6 +fi + +echo $ac_n "checking for working vfork""... $ac_c" 1>&6 +echo "configure:1992: checking for working vfork" >&5 +if eval "test \"`echo '$''{'ac_cv_func_vfork_works'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + echo $ac_n "checking for vfork""... $ac_c" 1>&6 +echo "configure:1998: checking for vfork" >&5 +if eval "test \"`echo '$''{'ac_cv_func_vfork'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char vfork(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_vfork) || defined (__stub___vfork) +choke me +#else +vfork(); +#endif + +; return 0; } +EOF +if { (eval echo configure:2026: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_func_vfork=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_vfork=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'vfork`\" = yes"; then + echo "$ac_t""yes" 1>&6 + : +else + echo "$ac_t""no" 1>&6 +fi + +else + cat > conftest.$ac_ext < +#include +#include +#ifdef HAVE_UNISTD_H +#include +#endif +#ifdef HAVE_VFORK_H +#include +#endif +/* On some sparc systems, changes by the child to local and incoming + argument registers are propagated back to the parent. + The compiler is told about this with #include , + but some compilers (e.g. gcc -O) don't grok . + Test for this by using a static variable whose address + is put into a register that is clobbered by the vfork. */ +static +#ifdef __cplusplus +sparc_address_test (int arg) +#else +sparc_address_test (arg) int arg; +#endif +{ + static pid_t child; + if (!child) { + child = vfork (); + if (child < 0) { + perror ("vfork"); + _exit(2); + } + if (!child) { + arg = getpid(); + write(-1, "", 0); + _exit (arg); + } + } +} +main() { + pid_t parent = getpid (); + pid_t child; + + sparc_address_test (); + + child = vfork (); + + if (child == 0) { + /* Here is another test for sparc vfork register problems. + This test uses lots of local variables, at least + as many local variables as main has allocated so far + including compiler temporaries. 4 locals are enough for + gcc 1.40.3 on a Solaris 4.1.3 sparc, but we use 8 to be safe. + A buggy compiler should reuse the register of parent + for one of the local variables, since it will think that + parent can't possibly be used any more in this routine. + Assigning to the local variable will thus munge parent + in the parent process. */ + pid_t + p = getpid(), p1 = getpid(), p2 = getpid(), p3 = getpid(), + p4 = getpid(), p5 = getpid(), p6 = getpid(), p7 = getpid(); + /* Convince the compiler that p..p7 are live; otherwise, it might + use the same hardware register for all 8 local variables. */ + if (p != p1 || p != p2 || p != p3 || p != p4 + || p != p5 || p != p6 || p != p7) + _exit(1); + + /* On some systems (e.g. IRIX 3.3), + vfork doesn't separate parent from child file descriptors. + If the child closes a descriptor before it execs or exits, + this munges the parent's descriptor as well. + Test for this by closing stdout in the child. */ + _exit(close(fileno(stdout)) != 0); + } else { + int status; + struct stat st; + + while (wait(&status) != child) + ; + exit( + /* Was there some problem with vforking? */ + child < 0 + + /* Did the child fail? (This shouldn't happen.) */ + || status + + /* Did the vfork/compiler bug occur? */ + || parent != getpid() + + /* Did the file descriptor bug occur? */ + || fstat(fileno(stdout), &st) != 0 + ); + } +} +EOF +if { (eval echo configure:2142: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + ac_cv_func_vfork_works=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_func_vfork_works=no +fi +rm -fr conftest* +fi + +fi + +echo "$ac_t""$ac_cv_func_vfork_works" 1>&6 +if test $ac_cv_func_vfork_works = no; then + cat >> confdefs.h <<\EOF +#define vfork fork +EOF + +fi + + +# Look for these functions and define HAVE_... for each if present +for ac_func in sysconf gethostname strcspn strerror strspn strstr getenv strchr getrlimit getrusage valloc +do +echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 +echo "configure:2169: checking for $ac_func" >&5 +if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +$ac_func(); +#endif + +; return 0; } +EOF +if { (eval echo configure:2197: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_func_$ac_func=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_$ac_func=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'$ac_func`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_func=HAVE_`echo $ac_func | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'` + cat >> confdefs.h <&6 +fi +done + + +#---------------------------------------------------------------------- +# Create the Makefile from Makefile.in +#---------------------------------------------------------------------- +trap '' 1 2 15 +cat > confcache <<\EOF +# This file is a shell script that caches the results of configure +# tests run on this system so they can be shared between configure +# scripts and configure runs. It is not useful on other systems. +# If it contains results you don't want to keep, you may remove or edit it. +# +# By default, configure uses ./config.cache as the cache file, +# creating it if it does not exist already. You can give configure +# the --cache-file=FILE option to use a different cache file; that is +# what configure does when it calls configure scripts in +# subdirectories, so they share the cache. +# Giving --cache-file=/dev/null disables caching, for debugging configure. +# config.status only pays attention to the cache file if you give it the +# --recheck option to rerun configure. +# +EOF +# The following way of writing the cache mishandles newlines in values, +# but we know of no workaround that is simple, portable, and efficient. +# So, don't put newlines in cache variables' values. +# Ultrix sh set writes to stderr and can't be redirected directly, +# and sets the high bit in the cache file unless we assign to the vars. +(set) 2>&1 | + case `(ac_space=' '; set) 2>&1` in + *ac_space=\ *) + # `set' does not quote correctly, so add quotes (double-quote substitution + # turns \\\\ into \\, and sed turns \\ into \). + sed -n \ + -e "s/'/'\\\\''/g" \ + -e "s/^\\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\\)=\\(.*\\)/\\1=\${\\1='\\2'}/p" + ;; + *) + # `set' quotes correctly as required by POSIX, so do not add quotes. + sed -n -e 's/^\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\)=\(.*\)/\1=${\1=\2}/p' + ;; + esac >> confcache +if cmp -s $cache_file confcache; then + : +else + if test -w $cache_file; then + echo "updating cache $cache_file" + cat confcache > $cache_file + else + echo "not updating unwritable cache $cache_file" + fi +fi +rm -f confcache + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +test "x$prefix" = xNONE && prefix=$ac_default_prefix +# Let make expand exec_prefix. +test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' + +# Any assignment to VPATH causes Sun make to only execute +# the first set of double-colon rules, so remove it if not needed. +# If there is a colon in the path, we need to keep it. +if test "x$srcdir" = x.; then + ac_vpsub='/^[ ]*VPATH[ ]*=[^:]*$/d' +fi + +trap 'rm -f $CONFIG_STATUS conftest*; exit 1' 1 2 15 + +# Transform confdefs.h into DEFS. +# Protect against shell expansion while executing Makefile rules. +# Protect against Makefile macro expansion. +cat > conftest.defs <<\EOF +s%#define \([A-Za-z_][A-Za-z0-9_]*\) *\(.*\)%-D\1=\2%g +s%[ `~#$^&*(){}\\|;'"<>?]%\\&%g +s%\[%\\&%g +s%\]%\\&%g +s%\$%$$%g +EOF +DEFS=`sed -f conftest.defs confdefs.h | tr '\012' ' '` +rm -f conftest.defs + + +# Without the "./", some shells look in PATH for config.status. +: ${CONFIG_STATUS=./config.status} + +echo creating $CONFIG_STATUS +rm -f $CONFIG_STATUS +cat > $CONFIG_STATUS </dev/null | sed 1q`: +# +# $0 $ac_configure_args +# +# Compiler output produced by configure, useful for debugging +# configure, is in ./config.log if it exists. + +ac_cs_usage="Usage: $CONFIG_STATUS [--recheck] [--version] [--help]" +for ac_option +do + case "\$ac_option" in + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + echo "running \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion" + exec \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion ;; + -version | --version | --versio | --versi | --vers | --ver | --ve | --v) + echo "$CONFIG_STATUS generated by autoconf version 2.12" + exit 0 ;; + -help | --help | --hel | --he | --h) + echo "\$ac_cs_usage"; exit 0 ;; + *) echo "\$ac_cs_usage"; exit 1 ;; + esac +done + +ac_given_srcdir=$srcdir +ac_given_INSTALL="$INSTALL" + +trap 'rm -fr `echo "Makefile" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 +EOF +cat >> $CONFIG_STATUS < conftest.subs <<\\CEOF +$ac_vpsub +$extrasub +s%@CFLAGS@%$CFLAGS%g +s%@CPPFLAGS@%$CPPFLAGS%g +s%@CXXFLAGS@%$CXXFLAGS%g +s%@DEFS@%$DEFS%g +s%@LDFLAGS@%$LDFLAGS%g +s%@LIBS@%$LIBS%g +s%@exec_prefix@%$exec_prefix%g +s%@prefix@%$prefix%g +s%@program_transform_name@%$program_transform_name%g +s%@bindir@%$bindir%g +s%@sbindir@%$sbindir%g +s%@libexecdir@%$libexecdir%g +s%@datadir@%$datadir%g +s%@sysconfdir@%$sysconfdir%g +s%@sharedstatedir@%$sharedstatedir%g +s%@localstatedir@%$localstatedir%g +s%@libdir@%$libdir%g +s%@includedir@%$includedir%g +s%@oldincludedir@%$oldincludedir%g +s%@infodir@%$infodir%g +s%@mandir@%$mandir%g +s%@local_srcdir@%$local_srcdir%g +s%@AR@%$AR%g +s%@RANLIB@%$RANLIB%g +s%@host@%$host%g +s%@host_alias@%$host_alias%g +s%@host_cpu@%$host_cpu%g +s%@host_vendor@%$host_vendor%g +s%@host_os@%$host_os%g +s%@target@%$target%g +s%@target_alias@%$target_alias%g +s%@target_cpu@%$target_cpu%g +s%@target_vendor@%$target_vendor%g +s%@target_os@%$target_os%g +s%@build@%$build%g +s%@build_alias@%$build_alias%g +s%@build_cpu@%$build_cpu%g +s%@build_vendor@%$build_vendor%g +s%@build_os@%$build_os%g +s%@CC@%$CC%g +s%@INSTALL_PROGRAM@%$INSTALL_PROGRAM%g +s%@INSTALL_DATA@%$INSTALL_DATA%g +s%@LINKER@%$LINKER%g +s%@PLINKER@%$PLINKER%g +s%@CPP@%$CPP%g +s%@LIBOBJS@%$LIBOBJS%g + +CEOF +EOF + +cat >> $CONFIG_STATUS <<\EOF + +# Split the substitutions into bite-sized pieces for seds with +# small command number limits, like on Digital OSF/1 and HP-UX. +ac_max_sed_cmds=90 # Maximum number of lines to put in a sed script. +ac_file=1 # Number of current file. +ac_beg=1 # First line for current file. +ac_end=$ac_max_sed_cmds # Line after last line for current file. +ac_more_lines=: +ac_sed_cmds="" +while $ac_more_lines; do + if test $ac_beg -gt 1; then + sed "1,${ac_beg}d; ${ac_end}q" conftest.subs > conftest.s$ac_file + else + sed "${ac_end}q" conftest.subs > conftest.s$ac_file + fi + if test ! -s conftest.s$ac_file; then + ac_more_lines=false + rm -f conftest.s$ac_file + else + if test -z "$ac_sed_cmds"; then + ac_sed_cmds="sed -f conftest.s$ac_file" + else + ac_sed_cmds="$ac_sed_cmds | sed -f conftest.s$ac_file" + fi + ac_file=`expr $ac_file + 1` + ac_beg=$ac_end + ac_end=`expr $ac_end + $ac_max_sed_cmds` + fi +done +if test -z "$ac_sed_cmds"; then + ac_sed_cmds=cat +fi +EOF + +cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF +for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + # Adjust a relative srcdir, top_srcdir, and INSTALL for subdirectories. + + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + ac_dir_suffix="/`echo $ac_dir|sed 's%^\./%%'`" + # A "../" for each directory in $ac_dir_suffix. + ac_dots=`echo $ac_dir_suffix|sed 's%/[^/]*%../%g'` + else + ac_dir_suffix= ac_dots= + fi + + case "$ac_given_srcdir" in + .) srcdir=. + if test -z "$ac_dots"; then top_srcdir=. + else top_srcdir=`echo $ac_dots|sed 's%/$%%'`; fi ;; + /*) srcdir="$ac_given_srcdir$ac_dir_suffix"; top_srcdir="$ac_given_srcdir" ;; + *) # Relative path. + srcdir="$ac_dots$ac_given_srcdir$ac_dir_suffix" + top_srcdir="$ac_dots$ac_given_srcdir" ;; + esac + + case "$ac_given_INSTALL" in + [/$]*) INSTALL="$ac_given_INSTALL" ;; + *) INSTALL="$ac_dots$ac_given_INSTALL" ;; + esac + + echo creating "$ac_file" + rm -f "$ac_file" + configure_input="Generated automatically from `echo $ac_file_in|sed 's%.*/%%'` by configure." + case "$ac_file" in + *Makefile*) ac_comsub="1i\\ +# $configure_input" ;; + *) ac_comsub= ;; + esac + + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + sed -e "$ac_comsub +s%@configure_input@%$configure_input%g +s%@srcdir@%$srcdir%g +s%@top_srcdir@%$top_srcdir%g +s%@INSTALL@%$INSTALL%g +" $ac_file_inputs | (eval "$ac_sed_cmds") > $ac_file +fi; done +rm -f conftest.s* + +EOF +cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF + +exit 0 +EOF +chmod +x $CONFIG_STATUS +rm -fr confdefs* $ac_clean_files +test "$no_create" = yes || ${CONFIG_SHELL-/bin/sh} $CONFIG_STATUS || exit 1 + + diff --git a/configure.in b/configure.in new file mode 100644 index 0000000..a04541a --- /dev/null +++ b/configure.in @@ -0,0 +1,391 @@ +dnl Run autoconf on this file to produce the system configuration +dnl script "configure" + +# FileName [ configure.in ] +# +# PackageName [ glu ] +# +# Synopsis [ System configuration script for autoconf ] +# +# SeeAlso [ Makefile.in ] +# +# Author [ Stephen Edwards ] +# +# Copyright [ +# Copyright (c) 1994-1996 The Regents of the Univ. of California. +# All rights reserved. +# +# Permission is hereby granted, without written agreement and without license +# or royalty fees, to use, copy, modify, and distribute this software and its +# documentation for any purpose, provided that the above copyright notice and +# the following two paragraphs appear in all copies of this software. +# +# IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR +# DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT +# OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF +# CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +# THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, +# INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND +# FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN +# "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE +# MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. +# ] +# +# Revision [$Id: configure.in,v 1.31 1998/09/25 03:47:09 kumtheka Exp $] + +# Require version 2.11 or above -- it checks to see if the C compiler +# actually works! + +AC_PREREQ(2.11) + +AC_INIT(cal.c) + +AC_CONFIG_AUX_DIR(.) + +AC_ARG_ENABLE(times-resolution, [ --enable-times-resolution= + Set the resolution of the times() function (only + necessary for non-POSIX systems).], + [AC_DEFINE_UNQUOTED(CLOCK_RESOLUTION,$enableval)], + [AC_DEFINE_UNQUOTED(CLOCK_RESOLUTION,60)]) + +#---------------------------------------------------------------------- +# Set local_srcdir +#---------------------------------------------------------------------- +# Give the configurer a chance to set a different location for the GLU +# source. When specified, "srcdir" points to "master" source, and +# "local_srcdir" points to the source under local development. + +AC_SUBST(local_srcdir) +AC_ARG_WITH(local-srcdir, +[ --with-local-srcdir= Specify the root directory to search for + source for packages (the PKGS list). + Expects to find, e.g., /array/array.c], +[local_srcdir=$withval], +[local_srcdir=$srcdir]) + +AC_ARG_WITH(datasize, +[ --with-datasize= (Default: 16777216.) Specify maximum datasize in + bytes for systems without working getrlimit. + The application may use this value to size some + data structures, but may still try to exceed it.], +[datasize=$withval], +[datasize=16777216]) +AC_DEFINE_UNQUOTED(RLIMIT_DATA_DEFAULT,$datasize) + +#---------------------------------------------------------------------- +# Checks for programs we need +#---------------------------------------------------------------------- + +AC_PATH_PROG(AR, ar, ar) +AC_PROG_RANLIB + +AC_CANONICAL_SYSTEM +AC_SUBST(target) + +# Determine the name of the C compiler we're going to use + +AC_ARG_ENABLE(gcc, + [ --enable-gcc Allow use of gcc if available], + [gcc_ok=$enableval], [gcc_ok=no]) + +if test "$gcc_ok" = "yes"; then + CC=gcc +else +# Balakrishna Kumthekar +# As we do not support cc on RS6000, Cygwin and SunOS. + case "$target" in + rs6000-ibm-aix* | *-pc-cygwin32 | sparc-sun-sunos*) + CC=gcc ;; + *) + CC=cc ;; + esac +fi +AC_PROG_CC + +AC_ARG_ENABLE(64, + [ --enable-64 Use 64-bit pointers on 64-bit Alpha machines], + [use_sixty_four=$enableval], [use_sixty_four=no]) + +if test "$gcc_ok" = "yes"; then + use_sixty_four="yes" +fi + + +# Determine the compiler flags to use + +# Balakrisha Kumthekar (kumtheka@colorado.edu): making a special case for ultrix install, +# since its annoying about setting groupids. +case "$target" in + mips-dec-ultrix*) + INSTALL="helpers/install-sh -c" + INSTALL_PROGRAM="\${INSTALL}" + INSTALL_DATA="\${INSTALL} -m 644";; + + *) + AC_PROG_INSTALL ;; +esac + + +DEBUG_CFLAGS="-g" +DEBUG_LDFLAGS="" + +case "$target" in + + sparc-sun-solaris*) + # Sparc Solaris: + # -xO5: Highest level of optimization + # -native: Optimize for the native processor + # -dalign: Generate double-word load/store for performance + OPTIMIZE_CFLAGS="-xO5 -native -dalign" ;; + + mips-dec-ultrix*) + # MIPS-based DECstations running Ultrix: + # -std1: Produce non-ANSI code warnings, and define __STDC__ + # -O: Use the global "ucode" optimizer + # -Olimit 5000: Don't optimize routines bigger than 5000 basic blocks + OPTIMIZE_CFLAGS="-std1 -O -Olimit 5000" ;; + + alpha-dec-osf*) + # DEC Alpha running OSF: + + # 64-bit mode: + # -g3: Produce symbol table information for optimized code + # -O4: Enable every optimization + # -std: Enforce the ANSI standard with extensions, define __STDC__ + # -ieee_with_no_inexact: Disable (potentially slow) signaling + # for inexact floating-point results + # -tune host: Tune instructions for the compilation host machine + + OPTIMIZE_CFLAGS="-g3 -O4 -std -ieee_with_no_inexact -tune host" + DEBUG_CFLAGS="-g -std -ieee_with_no_inexact" + + # -non_shared: Do not use shared libraries + # -om: Generate an OMAGIC file for the om optimizer + OPTIMIZE_LDFLAGS="-non_shared -om" + + if test "$use_sixty_four" = "no"; then + # 32-bit mode: + # -xtaso: Make the compiler respond to #pragma pointer_size directives + OPTIMIZE_CFLAGS="$OPTIMIZE_CFLAGS -xtaso" + DEBUG_CFLAGS="$DEBUG_CFLAGS -xtaso" + + # -taso: Load the executable into the lower 31-bit address space + OPTIMIZE_LDFLAGS="$OPTIMIZE_LDFLAGS -taso" + DEBUG_LDFLAGS="$DEBUG_LDFLAGS -taso" + + AC_DEFINE(SIZEOF_VOID_P, 4) + ac_sizeof_voidp=4 + fi + ;; + + hppa*-*-hpux*) + # HP running HPUX + # -Aa: Behave as an ANSI compiler + # -D_HPUX_SOURCE: Include "HP-specific" symbols in the header + # files (e.g., this means sys/resource.h has struct rusage) + OPTIMIZE_CFLAGS="-O -Aa -D_HPUX_SOURCE" + DEBUG_CFLAGS="-g -Aa -D_HPUX_SOURCE" ;; + + *) + # Other systems: + OPTIMIZE_CFLAGS="-O" ;; + +esac + +if test "$CC" = "gcc" ; then + OPTIMIZE_CFLAGS="-g -O3" + OPTIMIZE_LDFLAGS="" + DEBUG_CFLAGS="-g" + DEBUG_LDFLAGS="" +fi + +AC_ARG_WITH(comp-mode, +[ --with-comp-mode= Specify a special compilation mode: + optimize (the default): Produce optimized + code, with symbol table information + if supported on the platform/compiler, + and without asserts. + debug: Produce unoptimized code with symbol table + information and asserts enabled + purify: Unoptimized code linked with purify + quantify: Optimized code without asserts + linked with quantify], +[comp_mode=$withval], +[comp_mode=optimize]) +AC_SUBST(LINKER) +AC_SUBST(PLINKER) + +LINKER="$CC" + +case "$comp_mode" in + debug) + CFLAGS="$DEBUG_CFLAGS" + LDFLAGS="$DEBUG_LDFLAGS" ;; + purify) + CFLAGS="$DEBUG_CFLAGS" + LDFLAGS="$DEBUG_LDFLAGS" + AC_DEFINE(PURIFY) + LINKER="purify -cache-dir=/tmp $CC" + PLINKER="purify -log-file=./purify.log -cachedir=/tmp $CC" ;; + quantify) + CFLAGS="$OPTIMIZE_CFLAGS" + LDFLAGS="$OPTIMIZE_LDFLAGS" + AC_DEFINE(QUANTIFY) + AC_DEFINE(NDEBUG) + LINKER="quantify $CC" ;; + optimize | *) + CFLAGS="$OPTIMIZE_CFLAGS" + LDFLAGS="$OPTIMIZE_LDFLAGS" + AC_DEFINE(NDEBUG) ;; +esac + +#---------------------------------------------------------------------- +# Checks for libraries +#---------------------------------------------------------------------- + +# Define STDC_HEADERS if the system has ANSI C header files +AC_HEADER_STDC + +# Define HAVE_SYS_WAIT_H if sys/wait.h exists and is POSIX-compliant +AC_HEADER_SYS_WAIT + +# Check for these system header files +AC_CHECK_HEADERS(sys/file.h sys/stat.h unistd.h errno.h assert.h sys/wait.h pwd.h sys/types.h sys/times.h sys/time.h sys/resource.h) + +# Check how the compiler handles functions with variable argument lists +# +# If there's a , this is probably an ANSI compiler and the "..." +# notation will probably work. If not, there may be another version +# called , that uses an argument of the type "va_alist" +# (see, e.g., Ultrix, Digital Unix) +AC_CHECK_HEADERS(stdarg.h varargs.h) + +#---------------------------------------------------------------------- +# Checks for typedefs, structures, and compiler characteristics. +#---------------------------------------------------------------------- + +# Check to see if the compiler understands "const" +# #define it empty otherwise +AC_C_CONST + +# Check the size of pointers and ints + +if test -z "$ac_sizeof_voidp"; then + AC_CHECK_SIZEOF(void *) +fi +AC_CHECK_SIZEOF(int) + +# Check for a working implementation of IEEE 754 floating point +# Specifically, check for correct treatment of +Infinity +AC_MSG_CHECKING([for +Infinity (IEEE 754 floating point)]) +AC_CACHE_VAL(ac_cv_have_ieee_754, +[ AC_TRY_RUN([ +#include +main() +{ + if (HUGE_VAL != HUGE_VAL * 3 || HUGE_VAL != HUGE_VAL / 3) exit(1); + exit(0); +} +],ac_cv_have_ieee_754=yes,ac_cv_have_ieee_754=no,ac_cv_have_ieee_754=no)]) +if test $ac_cv_have_ieee_754 = yes ; then + AC_MSG_RESULT(working) + AC_DEFINE(HAVE_IEEE_754) +else + AC_MSG_RESULT(broken) +fi + +# Check the size of the virtual memory page +# +# The Cal BDD package uses this +# +# This compiles and runs a small program that gets the pagesize from +# the "getpagesize()" UNIX system function. + +AC_MSG_CHECKING([the size of the virtual memory system's page]) +AC_CACHE_VAL(ac_cv_sys_pagesize, +[ AC_TRY_RUN([ + +#include +#ifdef HAVE_UNISTD_H +# include +#endif + +main() { + FILE * f = fopen( "conftestval", "w" ); + if ( f == NULL ) exit(1); + fprintf( f, "%d\n", (int) getpagesize() ); + exit(0); +} +], ac_cv_sys_pagesize=`cat conftestval`, ac_cv_sys_pagesize=unknown)]) +case "$ac_cv_sys_pagesize" in + 512) + AC_MSG_RESULT(512) + PAGE_SIZE=512 + LG_PAGE_SIZE=9 ;; + 1024) + AC_MSG_RESULT(1K) + PAGE_SIZE=1024 + LG_PAGE_SIZE=10 ;; + 2048) + AC_MSG_RESULT(2K) + PAGE_SIZE=2048 + LG_PAGE_SIZE=11 ;; + 4096) + AC_MSG_RESULT(4K) + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; + 8192) + AC_MSG_RESULT(8K) + PAGE_SIZE=8192 + LG_PAGE_SIZE=13 ;; + 16384) + AC_MSG_RESULT(16K) + PAGE_SIZE=16384 + LG_PAGE_SIZE=14 ;; + 32768) + AC_MSG_RESULT(32K) + PAGE_SIZE=32768 + LG_PAGE_SIZE=15 ;; + 65536) + AC_MSG_RESULT(64K) + PAGE_SIZE=65536 + LG_PAGE_SIZE=16 ;; + unknown) + AC_MSG_RESULT([could not determine -- assuming 4K]) + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; + *) + AC_MSG_RESULT(Invalid page size $ac_cv_sys_pagesize -- assuming 4K) + PAGE_SIZE=4096 + LG_PAGE_SIZE=12 ;; +esac +AC_DEFINE_UNQUOTED(PAGE_SIZE, $PAGE_SIZE) +AC_DEFINE_UNQUOTED(LG_PAGE_SIZE, $LG_PAGE_SIZE) + +#---------------------------------------------------------------------- +# Checks for library functions. +#---------------------------------------------------------------------- + +# Add memcmp.o to LIBOBJS if the memcmp() function is unavailable or broken +AC_FUNC_MEMCMP + +# Define RETSIGTYPE to be void or int depending on the expected return type of +# a signal handler +AC_TYPE_SIGNAL + +# Define HAVE_STRCOLL if the strcoll function exists and works +AC_FUNC_STRCOLL + +# Define HAVE_VFORK_H if vfork.h is present, otherwise define "vfork" to be +# "fork" +AC_FUNC_VFORK + +# Look for these functions and define HAVE_... for each if present +AC_CHECK_FUNCS(sysconf gethostname strcspn strerror strspn strstr getenv strchr getrlimit getrusage valloc) + +#---------------------------------------------------------------------- +# Create the Makefile from Makefile.in +#---------------------------------------------------------------------- +AC_OUTPUT(Makefile) + diff --git a/credit.html b/credit.html new file mode 100644 index 0000000..868097b --- /dev/null +++ b/credit.html @@ -0,0 +1,15 @@ + +Credit + + + + + + + +
+ Command Documentation + Package Documentation Generated by + the Ext system
+ + diff --git a/dependency.make b/dependency.make new file mode 100644 index 0000000..f72ed5f --- /dev/null +++ b/dependency.make @@ -0,0 +1,32 @@ +# FileName [dependency.make] +# +# PackageName [vis] +# +# Synopsis [Makefile to automatically create the dependency files.] +# +# Description [This file is called from the main Makefile.] +# +# SeeAlso [Makefile.in] +# +# Author [Abelardo Pardo ] +# +# Copyright [This file was created at the University of Colorado at Boulder. +# The University of Colorado at Boulder makes no warranty about the suitability +# of this software for any purpose. It is presented on an AS IS basis.] +# +# Revision [$Id: dependency.make,v 1.3 1998/09/18 18:30:23 hsv Exp $] + +include $(PKGNAME).make + +ifdef DEPENDENCYFILES +$(PKGNAME).d : $(DEPENDENCYFILES) $(HEADERS) $(PKGNAME).make + @echo -n "Dependency file $(PKGNAME).d->" + @$(CC) -MM $(CFLAGS) $(AC_FLAGS) $(INCLUDEDIRS) \ + $(filter %.c, $^) | \ + sed 's/^[a-zA-Z0-9_]*\.o[ :]*/$(objectdir)\/&/g' > $@ + @echo "Created." +else +$(PKGNAME).d : + @echo "No dependency files given in $(PKGNAME).make" + @echo "Define the variable DEPENDENCYFILES to create the dependencies" +endif diff --git a/install-sh b/install-sh new file mode 100644 index 0000000..89fc9b0 --- /dev/null +++ b/install-sh @@ -0,0 +1,238 @@ +#! /bin/sh +# +# install - install a program, script, or datafile +# This comes from X11R5. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# `make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. +# + + +# set DOITPROG to echo to test this script + +# Don't use :- since 4.3BSD and earlier shells don't like it. +doit="${DOITPROG-}" + + +# put in absolute paths if you don't have them in your path; or use env. vars. + +mvprog="${MVPROG-mv}" +cpprog="${CPPROG-cp}" +chmodprog="${CHMODPROG-chmod}" +chownprog="${CHOWNPROG-chown}" +chgrpprog="${CHGRPPROG-chgrp}" +stripprog="${STRIPPROG-strip}" +rmprog="${RMPROG-rm}" +mkdirprog="${MKDIRPROG-mkdir}" + +tranformbasename="" +transform_arg="" +instcmd="$mvprog" +chmodcmd="$chmodprog 0755" +chowncmd="" +chgrpcmd="" +stripcmd="" +rmcmd="$rmprog -f" +mvcmd="$mvprog" +src="" +dst="" +dir_arg="" + +while [ x"$1" != x ]; do + case $1 in + -c) instcmd="$cpprog" + shift + continue;; + + -d) dir_arg=true + shift + continue;; + + -m) chmodcmd="$chmodprog $2" + shift + shift + continue;; + + -o) chowncmd="$chownprog $2" + shift + shift + continue;; + + -g) chgrpcmd="$chgrpprog $2" + shift + shift + continue;; + + -s) stripcmd="$stripprog" + shift + continue;; + + -t=*) transformarg=`echo $1 | sed 's/-t=//'` + shift + continue;; + + -b=*) transformbasename=`echo $1 | sed 's/-b=//'` + shift + continue;; + + *) if [ x"$src" = x ] + then + src=$1 + else + # this colon is to work around a 386BSD /bin/sh bug + : + dst=$1 + fi + shift + continue;; + esac +done + +if [ x"$src" = x ] +then + echo "install: no input file specified" + exit 1 +else + true +fi + +if [ x"$dir_arg" != x ]; then + dst=$src + src="" + + if [ -d $dst ]; then + instcmd=: + else + instcmd=mkdir + fi +else + +# Waiting for this to be detected by the "$instcmd $src $dsttmp" command +# might cause directories to be created, which would be especially bad +# if $src (and thus $dsttmp) contains '*'. + + if [ -f $src -o -d $src ] + then + true + else + echo "install: $src does not exist" + exit 1 + fi + + if [ x"$dst" = x ] + then + echo "install: no destination specified" + exit 1 + else + true + fi + +# If destination is a directory, append the input filename; if your system +# does not like double slashes in filenames, you may need to add some logic + + if [ -d $dst ] + then + dst="$dst"/`basename $src` + else + true + fi +fi + +## this sed command emulates the dirname command +dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` + +# Make sure that the destination directory exists. +# this part is taken from Noah Friedman's mkinstalldirs script + +# Skip lots of stat calls in the usual case. +if [ ! -d "$dstdir" ]; then +defaultIFS=' +' +IFS="${IFS-${defaultIFS}}" + +oIFS="${IFS}" +# Some sh's can't handle IFS=/ for some reason. +IFS='%' +set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` +IFS="${oIFS}" + +pathcomp='' + +while [ $# -ne 0 ] ; do + pathcomp="${pathcomp}${1}" + shift + + if [ ! -d "${pathcomp}" ] ; + then + $mkdirprog "${pathcomp}" + else + true + fi + + pathcomp="${pathcomp}/" +done +fi + +if [ x"$dir_arg" != x ] +then + $doit $instcmd $dst && + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi +else + +# If we're going to rename the final executable, determine the name now. + + if [ x"$transformarg" = x ] + then + dstfile=`basename $dst` + else + dstfile=`basename $dst $transformbasename | + sed $transformarg`$transformbasename + fi + +# don't allow the sed command to completely eliminate the filename + + if [ x"$dstfile" = x ] + then + dstfile=`basename $dst` + else + true + fi + +# Make a temp file name in the proper directory. + + dsttmp=$dstdir/#inst.$$# + +# Move or copy the file name to the temp name + + $doit $instcmd $src $dsttmp && + + trap "rm -f ${dsttmp}" 0 && + +# and set any options; do chmod last to preserve setuid bits + +# If any of these fail, we abort the whole thing. If we want to +# ignore errors from any of these, just make sure not to ignore +# errors from the above "$doit $instcmd $src $dsttmp" command. + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && + +# Now rename the file to the real destination. + + $doit $rmcmd -f $dstdir/$dstfile && + $doit $mvcmd $dsttmp $dstdir/$dstfile + +fi && + + +exit 0 diff --git a/mkinstalldirs b/mkinstalldirs new file mode 100644 index 0000000..91f6d04 --- /dev/null +++ b/mkinstalldirs @@ -0,0 +1,32 @@ +#!/bin/sh +# mkinstalldirs --- make directory hierarchy +# Author: Noah Friedman +# Created: 1993-05-16 +# Last modified: 1994-03-25 +# Public domain + +errstatus=0 + +for file in ${1+"$@"} ; do + set fnord `echo ":$file" | sed -ne 's/^:\//#/;s/^://;s/\// /g;s/^#/\//;p'` + shift + + pathcomp= + for d in ${1+"$@"} ; do + pathcomp="$pathcomp$d" + case "$pathcomp" in + -* ) pathcomp=./$pathcomp ;; + esac + + if test ! -d "$pathcomp"; then + echo "mkdir $pathcomp" 1>&2 + mkdir "$pathcomp" || errstatus=$? + fi + + pathcomp="$pathcomp/" + done +done + +exit $errstatus + +# mkinstalldirs ends here