mirror of
https://github.com/Mercury-Language/mercury.git
synced 2025-12-12 20:34:19 +00:00
Estimated hours taken: unknown (but probably several weeks by dmo)
Branches: main
Move changes in the library on the mode-constraints branch onto the trunk.
library/eqvclass.m:
Add some utility functions and predicates.
library/map.m:
Add some utility functions and predicates, and some type
specialization directives.
library/tree234.m:
Add some utility functions and predicates.
library/robdd.m:
Add this module, which provides a Mercury interface to the C code in
robdd/bryant.c. In some places, robustness has been sacrificed for
speed, and the module is not (yet) as well documented as it could be;
therefore it is not (yet) included in the documentation.
library/pprint.m:
Print robdds nicely, since this is essential to debugging code handling
robdds. (This is why adding robdd.m in some other directory, e.g. the
compiler, wouldn't really work.)
library/term.m:
Add a function that returns the highest numbered vars created from
a var_supply.
library/varset.m:
Add a function that returns the highest numbered vars created from
a varset.
library/unsafe.m:
Add this module here, since it may be needed to debug code in the
library (e.g. in robdd.m.).
library/library.m:
Add a reference to the robdd module, and a commented out reference
to the unsafe module. If a developer needs to use unsafe.m anywhere
in the Mercury implementation, they can uncomment this reference
in the relevant workspace.
Make the list of modules easier to maintain (especially in the case
of CVS conflicts) by listing one module per line.
Fix formatting of some foreign_procs.
NEWS:
Mention the new predicates and functions.
Mmake.workspace:
Add a new make variable that specifies the location of the robdd
subdirectory.
Mmakefile:
Add rules for handling the robdd subdirectory.
configure.in:
Check whether the compiler can handle local foreign_decls, since
robdd.m now needs this.
tools/bootcheck:
Add the robdd subdirectory to the stage 2 & 3 directories.
deep_profiler/unsafe.m:
Remove this module from this directory.
doc/Mmakefile:
Do not include the robdd and unsafe modules in the documentation.
The robdd module because (in its present state) it is not stable
enough, the unsafe module because it is not enabled in installed
versions of the library.
robdd/Makefile:
Update the set of default compilation flags. The main code in this
directory, bryant.c, is #included in library/robdd.m, and the only
other programs in this directory are test programs.
robdd/Mmakefile:
New file. Includes a mechanism to compile bryant.c in the robdd
subdirectory, since this can give cleaner error messages than
compiling library/robdd.m.
robdd/bryant.[ch]:
Huge cleanup of these files. Add MR_ROBDD_ prefixes to global symbols,
make the formatting conform to our standards, and fix irregularities
in the uses of the macros that control the use of optional facilities.
robdd/bryantPrint.[ch]:
robdd/table.[ch]:
robdd/test_abexit.c:
robdd/test_abunify.c:
robdd/test_abglb.c:
robdd/test_iff.c:
robdd/test_rename.c:
robdd/test_restrict.c:
robdd/test_rglb.c:
robdd/test_upclose.c:
robdd/test_var.c:
robdd/test_vars.c:
robdd/timing.[ch]:
robdd/var.h:
Conform to the changes in bryant.h. Note that since the code in these
files won't end up in Mercury program code, they don't need to be
namespace clean.
runtime/mercury.h:
runtime/mercury_heap.h:
runtime/mercury_init.h:
runtime/mercury_memory.h:
#define GC_I_HIDE_POINTERS before each #include of gc.h (bryant.c
hides pointers). This impact of this #define is so small that it is
not measurable.
runtime/RESERVED_MACRO_NAMES:
library/RESERVED_MACRO_NAMES:
Add HIDE_POINTER and REVEAL_POINTER, since defining GC_I_HIDE_POINTERS
makes these macros from gc.h visible.
runtime/mercury_reg_workarounds.[ch]:
Add the MR_memset function.
tests/debugger/declarative/if_then_else.{inp,exp}:
tests/debugger/declarative/ite_2.{inp,exp,exp2}:
Avoid a name conflict with the predicate ite in robdd.m.
195 lines
4.7 KiB
C
195 lines
4.7 KiB
C
/*
|
|
** Copyright (C) 1995,2003-2004 Peter Schachte and The University of Melbourne.
|
|
** This file may only be copied under the terms of the GNU Library General
|
|
** Public License - see the file COPYING.LIB in the Mercury distribution.
|
|
*/
|
|
|
|
/*****************************************************************
|
|
File : test_var.c
|
|
Author : Peter Schachte
|
|
Origin : Tue Jul 18 14:28:15 1995
|
|
Purpose : Timing test for bryant graph MR_ROBDD_var_entailed function
|
|
|
|
*****************************************************************/
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include "bryant.h"
|
|
#include "timing.h"
|
|
|
|
|
|
#define VARLIMIT 1024
|
|
|
|
int opcount;
|
|
|
|
void usage(char *progname)
|
|
{
|
|
printf("usage: %s size maxvar [repetitions]\n", progname);
|
|
printf(" creates all possible v <-> v1 & v2 & ... & vsize functions and conjoins this\n");
|
|
printf(" with each variable between 0 and maxvar, and then determines for each variable\n");
|
|
printf(" between 0 and maxvar if that variable is MR_ROBDD_entailed by this function.\n");
|
|
printf(" V and the vi are between 0 and maxvar inclusive. If repetitions is >0,\n");
|
|
printf(" this will be done that many times.\n");
|
|
}
|
|
|
|
|
|
void init_array(int top, int v0, int array[])
|
|
{
|
|
int i, val;
|
|
|
|
for (i=0, val=0; i<top; ++i, ++val) {
|
|
if (val==v0) ++val;
|
|
array[i] = val;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
int next_array(int n, int varmax, int v0, int array[])
|
|
{
|
|
int i;
|
|
int limit;
|
|
int val;
|
|
|
|
/* Search backward for first cell with "room" to be
|
|
* incremented. This is complicated by the need to avoid
|
|
* using the value v0.
|
|
*/
|
|
for (i=n-1, limit=varmax-1;; --i, --limit) {
|
|
if (i<0) return 0; /* no more combinations possible */
|
|
if (limit==v0) --limit;
|
|
if (++array[i]==v0) ++array[i];
|
|
if (array[i]<=limit) break;
|
|
}
|
|
/* Now we've incremented array[i], and must set
|
|
* array[i+1..n-1] to successive values (avoiding v0).
|
|
*/
|
|
for (val=array[i]+1, ++i; i<n; ++i, ++val) {
|
|
if (val==v0) ++val;
|
|
array[i] = val;
|
|
}
|
|
return 1;
|
|
}
|
|
|
|
|
|
void doit(int w, MR_ROBDD_type *f)
|
|
{
|
|
int result;
|
|
|
|
#ifdef DEBUGALL
|
|
printf("MR_ROBDD_var_entailed(");
|
|
printOut(f),
|
|
printf(", %d) = ", w);
|
|
fflush(stdout);
|
|
#endif /* DEBUGALL */
|
|
#ifndef OVERHEAD
|
|
result = MR_ROBDD_var_entailed(f, w);
|
|
#ifdef DEBUGALL
|
|
printf("%s\n", (result ? "true" : "false"));
|
|
#endif /* DEBUGALL */
|
|
#endif /* !OVERHEAD */
|
|
++opcount;
|
|
}
|
|
|
|
|
|
void dont_doit(int w, MR_ROBDD_type *f)
|
|
{
|
|
}
|
|
|
|
|
|
void inner_loop(int varmax, MR_ROBDD_type *f)
|
|
{
|
|
MR_ROBDD_type *g;
|
|
int v, w;
|
|
|
|
for (v=0; v<varmax; ++v) {
|
|
g = MR_ROBDD_glb(MR_ROBDD_variableRep(v), f);
|
|
for (w=0; w<varmax; ++w) {
|
|
doit(w, g);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
void dont_inner_loop(int varmax, MR_ROBDD_type *f)
|
|
{
|
|
MR_ROBDD_type *g;
|
|
int v, w;
|
|
|
|
for (v=0; v<varmax; ++v) {
|
|
g = MR_ROBDD_glb(MR_ROBDD_variableRep(v), f);
|
|
for (w=0; w<varmax; ++w) {
|
|
dont_doit(w, g);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
int main(int argc, char **argv)
|
|
{
|
|
int varmax, size, repetitions;
|
|
int array[VARLIMIT];
|
|
int reps, v0;
|
|
MR_ROBDD_type *f;
|
|
millisec clock0, clock1, clock2, clock3;
|
|
float runtime, overhead, rate;
|
|
int test_nodes, overhead_nodes;
|
|
|
|
if (argc < 3) {
|
|
usage(argv[0]);
|
|
return 20;
|
|
}
|
|
if ((varmax=atoi(argv[2]))<1 || varmax>=VARLIMIT) {
|
|
usage(argv[0]);
|
|
printf("\n varmax must be between 1 <= varmax < %d\n", VARLIMIT);
|
|
return 20;
|
|
}
|
|
if ((size=atoi(argv[1]))<0 || size>=varmax) {
|
|
usage(argv[0]);
|
|
printf("\n size must be between 0 <= size < varmax\n");
|
|
return 20;
|
|
}
|
|
repetitions=(argc>3 ? atoi(argv[3]) : 1);
|
|
if (repetitions <= 0) repetitions = 1;
|
|
|
|
opcount = 0;
|
|
clock0 = milli_time();
|
|
for (reps=repetitions; reps>0; --reps) {
|
|
for (v0=0; v0<varmax; ++v0) {
|
|
init_array(size, v0, array);
|
|
f = MR_ROBDD_testing_iff_conj_array(v0, size, array);
|
|
inner_loop(varmax, f);
|
|
while (next_array(size, varmax, v0, array)) {
|
|
f = MR_ROBDD_testing_iff_conj_array(v0, size, array);
|
|
inner_loop(varmax, f);
|
|
}
|
|
}
|
|
}
|
|
clock1 = milli_time();
|
|
test_nodes = MR_ROBDD_nodes_in_use();
|
|
MR_ROBDD_initRep();
|
|
clock2 = milli_time();
|
|
for (reps=repetitions; reps>0; --reps) {
|
|
for (v0=0; v0<varmax; ++v0) {
|
|
init_array(size, v0, array);
|
|
f = MR_ROBDD_testing_iff_conj_array(v0, size, array);
|
|
dont_inner_loop(varmax, f);
|
|
while (next_array(size, varmax, v0, array)) {
|
|
f = MR_ROBDD_testing_iff_conj_array(v0, size, array);
|
|
dont_inner_loop(varmax, f);
|
|
}
|
|
}
|
|
}
|
|
clock3 = milli_time();
|
|
overhead_nodes = MR_ROBDD_nodes_in_use();
|
|
runtime = (float)(clock1-clock0)/1000;
|
|
overhead = (float)(clock3-clock2)/1000;
|
|
rate = ((float)opcount)/(runtime-overhead);
|
|
printf("%s %d %d %d: %.3f - %.3f = %.3f secs, %d ops, %d nodes, %.1f ops/sec\n",
|
|
argv[0], size, varmax, repetitions,
|
|
runtime, overhead, (runtime-overhead), opcount,
|
|
test_nodes-overhead_nodes, rate);
|
|
return 0;
|
|
}
|