mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
Creation of OpenFOAM-dev repository 15/04/2008
This commit is contained in:
@ -0,0 +1,147 @@
|
||||
include ../Makefile.in
|
||||
|
||||
CURBUILDDIR = $(PRGBUILDDIR)
|
||||
|
||||
|
||||
METISSRC = metis.c io.c smbfactor.c
|
||||
PMETISSRC = pmetis.c io.c cmdline_pmetis.c
|
||||
KMETISSRC = kmetis.c io.c
|
||||
OEMETISSRC = oemetis.c io.c smbfactor.c
|
||||
ONMETISSRC = onmetis.c io.c smbfactor.c
|
||||
MESH2DUALSRC = mesh2dual.c io.c
|
||||
MESH2NODALSRC = mesh2nodal.c io.c
|
||||
PARTDMESHSRC = partdmesh.c io.c
|
||||
PARTNMESHSRC = partnmesh.c io.c
|
||||
GRAPHCHKSRC = graphchk.c io.c
|
||||
KFMETISSRC = kfmetis.c io.c cmdline_kfmetis.c smbfactor.c
|
||||
CMETISSRC = cmetis.c io.c cmdline_cmetis.c
|
||||
|
||||
METISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(METISSRC))
|
||||
PMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(PMETISSRC))
|
||||
KMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(KMETISSRC))
|
||||
OEMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(OEMETISSRC))
|
||||
ONMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(ONMETISSRC))
|
||||
MESH2DUALOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(MESH2DUALSRC))
|
||||
MESH2NODALOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(MESH2NODALSRC))
|
||||
PARTDMESHOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(PARTDMESHSRC))
|
||||
PARTNMESHOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(PARTNMESHSRC))
|
||||
GRAPHCHKOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(GRAPHCHKSRC))
|
||||
KFMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(KFMETISSRC))
|
||||
CMETISOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(CMETISSRC))
|
||||
|
||||
ALLOBJS = $(patsubst %.c, $(CURBUILDDIR)/%$(OBJEXT), $(wildcard *.c))
|
||||
HEADERS = $(wildcard *.h) $(TOPDIR)/include/metis.h $(wildcard $(GKLIBINCDIR)/*.h)
|
||||
|
||||
LIBRARIES = $(BUILDDIR)/libmetis$(LIBEXT)
|
||||
|
||||
|
||||
TARGETS = $(BUILDDIR)/metis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/pmetis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/kmetis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/oemetis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/onmetis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/mesh2dual$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/mesh2nodal$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/partdmesh$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/partnmesh$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/graphchk$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/kfmetis$(VERNUM)$(EXEEXT) \
|
||||
$(BUILDDIR)/cmetis$(VERNUM)$(EXEEXT)
|
||||
|
||||
|
||||
default: $(TARGETS)
|
||||
|
||||
|
||||
$(BUILDDIR)/metis$(VERNUM)$(EXEEXT): $(METISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(METISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/pmetis$(VERNUM)$(EXEEXT): $(PMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(PMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/kmetis$(VERNUM)$(EXEEXT): $(KMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(KMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/oemetis$(VERNUM)$(EXEEXT): $(OEMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(OEMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/onmetis$(VERNUM)$(EXEEXT): $(ONMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(ONMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/mesh2dual$(VERNUM)$(EXEEXT): $(MESH2DUALOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(MESH2DUALOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/mesh2nodal$(VERNUM)$(EXEEXT): $(MESH2NODALOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(MESH2NODALOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/partdmesh$(VERNUM)$(EXEEXT): $(PARTDMESHOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(PARTDMESHOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/partnmesh$(VERNUM)$(EXEEXT): $(PARTNMESHOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(PARTNMESHOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/graphchk$(VERNUM)$(EXEEXT): $(GRAPHCHKOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(GRAPHCHKOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/kfmetis$(VERNUM)$(EXEEXT): $(KFMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(KFMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/cmetis$(VERNUM)$(EXEEXT): $(CMETISOBJS) $(LIBRARIES)
|
||||
$(LD) $(LDOPTIONS) $(EXEOUTPUTFILE) $(CMETISOBJS) $(LIBSDIR) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
|
||||
|
||||
$(BUILDDIR)/cepic$(VERNUM)$(EXEEXT): $(CEPICOBJS) $(LIBRARIES)
|
||||
$(LD) -o $@ $(CEPICOBJ) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/cepic-rcb$(VERNUM)$(EXEEXT): $(CEPICRCBOBJS) $(LIBRARIES)
|
||||
$(LD) -o $@ $(CEPICRCBOBJ) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
$(BUILDDIR)/mmetis$(VERNUM)$(EXEEXT): $(MMETISOBJS) $(LIBRARIES)
|
||||
$(LD) -o $@ $(MMETISOBJS) $(LIBS)
|
||||
chmod 744 $@
|
||||
@if [ "$(BINDIR)" ]; then cp $@* $(BINDIR); fi
|
||||
|
||||
|
||||
|
||||
clean:
|
||||
rm -f $(ALLOBJS)
|
||||
|
||||
realclean:
|
||||
rm -f $(ALLOBJS) $(TARGETS)
|
||||
|
||||
|
||||
|
||||
$(ALLOBJS) : $(HEADERS) ../Makefile.in Makefile
|
||||
|
||||
$(CURBUILDDIR)/%$(OBJEXT) : %.c
|
||||
$(CC) $(CFLAGS) $(SOURCEFILE) $(OUTPUTFILE)
|
||||
|
||||
|
||||
@ -0,0 +1,336 @@
|
||||
/*
|
||||
* Copyright 2003, Regents of the University of Minnesota
|
||||
*
|
||||
* cepic.c
|
||||
*
|
||||
* This file contains the driving routine for contact/impact simulations
|
||||
* for EPIC meshes
|
||||
*
|
||||
* Started 4/12/03
|
||||
* George
|
||||
*
|
||||
* $Id: cepic-rcb.c,v 1.3 2003/05/03 16:10:48 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
#define Flip_int32(type) (((type >>24) & 0x000000ff) | \
|
||||
((type >> 8) & 0x0000ff00) | \
|
||||
((type << 8) & 0x00ff0000) | \
|
||||
((type <<24) & 0xff000000) )
|
||||
|
||||
#define Flip_int64(type) (((type >>56) & 0x00000000000000ff) | \
|
||||
((type >>40) & 0x000000000000ff00) | \
|
||||
((type >>24) & 0x0000000000ff0000) | \
|
||||
((type >>8) & 0x00000000ff000000) | \
|
||||
((type <<8) & 0x000000ff00000000) | \
|
||||
((type <<24) & 0x0000ff0000000000) | \
|
||||
((type <<40) & 0x00ff000000000000) | \
|
||||
((type <<56) & 0xff00000000000000))
|
||||
|
||||
|
||||
int ComputeMapCost(idxtype nvtxs, idxtype nparts, idxtype *fepart, idxtype *cpart);
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, istep, options[10], nn, ne, fstep, lstep, nparts, nboxes, u[3], dim, nchanges, ncomm;
|
||||
char filename[256];
|
||||
idxtype *mien, *mrng, *part, *oldpart, *sflag, *bestdims, *fepart;
|
||||
double *mxyz, *bxyz;
|
||||
idxtype *xadj, *adjncy, *cntptr, *cntind;
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut, etype=2;
|
||||
void *cinfo;
|
||||
FILE *fpin;
|
||||
long long int *ltmp;
|
||||
|
||||
if (argc != 6) {
|
||||
mfprintf(stderr, "Usage: %s <nn> <ne> <fstep> <lstep> <nparts>\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
nn = atoi(argv[1]);
|
||||
ne = atoi(argv[2]);
|
||||
fstep = atoi(argv[3]);
|
||||
lstep = atoi(argv[4]);
|
||||
nparts = atoi(argv[5]);
|
||||
|
||||
mprintf("Reading %s, nn: %D, ne: %D, fstep: %D, lstep: %D, nparts: %D\n", filename, nn, ne, fstep, lstep, nparts);
|
||||
|
||||
mien = idxmalloc(4*ne, "main: mien");
|
||||
mxyz = gk_dmalloc(3*nn, "main: mxyz");
|
||||
mrng = idxmalloc(4*ne, "main: mrng");
|
||||
bxyz = gk_dmalloc(6*ne*4, "main: bxyz");
|
||||
|
||||
fepart = idxmalloc(nn, "main: fepart");
|
||||
part = idxmalloc(nn, "main: part");
|
||||
oldpart = idxmalloc(nn, "main: oldpart");
|
||||
sflag = idxmalloc(nn, "main: sflag");
|
||||
|
||||
bestdims = idxsmalloc(2*nparts, -1, "main: bestdims");
|
||||
|
||||
xadj = idxmalloc(nn+1, "main: xadj");
|
||||
adjncy = idxmalloc(50*nn, "main: adjncy");
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Read the initial mesh and setup the graph and contact information
|
||||
*========================================================================*/
|
||||
msprintf(filename, "mien.%04D", fstep);
|
||||
fpin = GKfopen(filename, "rb", "main: mien");
|
||||
fread(mien, sizeof(int), 4*ne, fpin);
|
||||
for (i=0; i<4*ne; i++)
|
||||
mien[i] = Flip_int32(mien[i]);
|
||||
GKfclose(fpin);
|
||||
|
||||
msprintf(filename, "mxyz.%04D", fstep);
|
||||
fpin = GKfopen(filename, "rb", "main: mxyz");
|
||||
fread(mxyz, sizeof(double), 3*nn, fpin);
|
||||
for (i=0; i<3*nn; i++) {
|
||||
ltmp = (long long int *)(mxyz+i);
|
||||
*ltmp = Flip_int64(*ltmp);
|
||||
}
|
||||
GKfclose(fpin);
|
||||
mprintf("%e %e %e\n", mxyz[3*0+0], mxyz[3*0+1], mxyz[3*0+2]);
|
||||
|
||||
msprintf(filename, "mrng.%04D", fstep);
|
||||
fpin = GKfopen(filename, "rb", "main: mrng");
|
||||
fread(mrng, sizeof(int), 4*ne, fpin);
|
||||
for (i=0; i<4*ne; i++)
|
||||
mrng[i] = Flip_int32(mrng[i]);
|
||||
GKfclose(fpin);
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Determine which nodes are in the surface
|
||||
*========================================================================*/
|
||||
iset(nn, 0, sflag);
|
||||
for (i=0; i<ne; i++) {
|
||||
if (mrng[4*i+0] > 0) { /* 1, 2, 3 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+1] > 0) { /* 1, 2, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+2] > 0) { /* 2, 3, 4 */
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+3] > 0) { /* 1, 3, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
}
|
||||
|
||||
mprintf("Contact Nodes: %D of %D\n", isum(nn, sflag), nn);
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Compute the FE partition
|
||||
*========================================================================*/
|
||||
numflag = mien[idxargmin(4*ne, mien)];
|
||||
METIS_MeshToNodal(&ne, &nn, mien, &etype, &numflag, xadj, adjncy);
|
||||
|
||||
options[0] = 0;
|
||||
METIS_PartGraphVKway(&nn, xadj, adjncy, NULL, NULL, &wgtflag, &numflag, &nparts,
|
||||
options, &edgecut, fepart);
|
||||
|
||||
mprintf("K-way partitioning Volume: %D\n", edgecut);
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Get into the loop in which you go over the different configurations
|
||||
*========================================================================*/
|
||||
for (istep=fstep; istep<=lstep; istep++) {
|
||||
msprintf(filename, "mxyz.%04D", istep);
|
||||
mprintf("Reading %s...............................................................\n", filename);
|
||||
fpin = GKfopen(filename, "rb", "main: mxyz");
|
||||
fread(mxyz, sizeof(double), 3*nn, fpin);
|
||||
for (i=0; i<3*nn; i++) {
|
||||
ltmp = (long long int *)(mxyz+i);
|
||||
*ltmp = Flip_int64(*ltmp);
|
||||
}
|
||||
GKfclose(fpin);
|
||||
|
||||
msprintf(filename, "mrng.%04D", istep);
|
||||
fpin = GKfopen(filename, "rb", "main: mrng");
|
||||
fread(mrng, sizeof(int), 4*ne, fpin);
|
||||
for (i=0; i<4*ne; i++)
|
||||
mrng[i] = Flip_int32(mrng[i]);
|
||||
GKfclose(fpin);
|
||||
|
||||
/* Determine which nodes are in the surface */
|
||||
iset(nn, 0, sflag);
|
||||
for (i=0; i<ne; i++) {
|
||||
if (mrng[4*i+0] > 0) { /* 1, 2, 3 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+1] > 0) { /* 1, 2, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+2] > 0) { /* 2, 3, 4 */
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+3] > 0) { /* 1, 3, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
}
|
||||
|
||||
mprintf("Contact Nodes: %D of %D\n", isum(nn, sflag), nn);
|
||||
|
||||
/* Determine the bounding boxes of the surface elements */
|
||||
for (nboxes=0, i=0; i<ne; i++) {
|
||||
if (mrng[4*i+0] > 0) { /* 1, 2, 3 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+1]-1;
|
||||
u[2] = mien[4*i+2]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
}
|
||||
if (mrng[4*i+1] > 0) { /* 1, 2, 4 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+1]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
}
|
||||
if (mrng[4*i+2] > 0) { /* 2, 3, 4 */
|
||||
u[0] = mien[4*i+1]-1;
|
||||
u[1] = mien[4*i+2]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
}
|
||||
if (mrng[4*i+3] > 0) { /* 1, 3, 4 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+2]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
}
|
||||
}
|
||||
|
||||
cinfo = METIS_PartSurfForContactRCB(&nn, mxyz, sflag, &nparts, part, bestdims);
|
||||
|
||||
METIS_FindContacts(cinfo, &nboxes, bxyz, &nparts, &cntptr, &cntind);
|
||||
|
||||
METIS_FreeContactInfo(cinfo);
|
||||
|
||||
nchanges = 0;
|
||||
if (istep > fstep) {
|
||||
for (i=0; i<nn; i++)
|
||||
nchanges += (part[i] != oldpart[i] ? 1 : 0);
|
||||
}
|
||||
idxcopy(nn, part, oldpart);
|
||||
|
||||
ncomm = ComputeMapCost(nn, nparts, fepart, part);
|
||||
|
||||
mprintf("Contacting Elements: %D Indices: %D Nchanges: %D MapCost: %D\n", nboxes, cntptr[nboxes]-nboxes, nchanges, ncomm);
|
||||
|
||||
gk_free((void **)&cntptr, &cntind, LTERM);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************
|
||||
* This function determines the cost of moving data between the two meshes assuming
|
||||
* that a good matching between the two partitions was done!
|
||||
************************************************************************************/
|
||||
int ComputeMapCost(idxtype nvtxs, idxtype nparts, idxtype *fepart, idxtype *cpart)
|
||||
{
|
||||
idxtype i, j, k, n, ncomm;
|
||||
KeyValueType cand[nparts*nparts];
|
||||
idxtype fmatched[nparts], cmatched[nparts];
|
||||
|
||||
/* Compute the overlap */
|
||||
for (i=0; i<nparts; i++) {
|
||||
for (j=0; j<nparts; j++) {
|
||||
cand[i*nparts+j].key = 0;
|
||||
cand[i*nparts+j].val = i*nparts+j;
|
||||
}
|
||||
}
|
||||
|
||||
for (k=0, i=0; i<nvtxs; i++) {
|
||||
if (cpart[i] >= 0) {
|
||||
cand[(fepart[i]-1)*nparts+(cpart[i]-1)].key++;
|
||||
k++;
|
||||
}
|
||||
}
|
||||
|
||||
mprintf("Contact points: %D\n", k);
|
||||
|
||||
ikeysort(nparts*nparts, cand);
|
||||
|
||||
iset(nparts, -1, fmatched);
|
||||
iset(nparts, -1, cmatched);
|
||||
|
||||
|
||||
for (ncomm=0, k=nparts*nparts-1; k>=0; k--) {
|
||||
i = cand[k].val/nparts;
|
||||
j = cand[k].val%nparts;
|
||||
|
||||
if (fmatched[i] == -1 && cmatched[j] == -1) {
|
||||
fmatched[i] = j;
|
||||
cmatched[j] = i;
|
||||
}
|
||||
else
|
||||
ncomm += cand[k].key;
|
||||
}
|
||||
|
||||
mprintf("Ncomm: %D\n", ncomm);
|
||||
|
||||
return ncomm;
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,256 @@
|
||||
/*
|
||||
* Copyright 2003, Regents of the University of Minnesota
|
||||
*
|
||||
* cepic.c
|
||||
*
|
||||
* This file contains the driving routine for contact/impact simulations
|
||||
* for EPIC meshes
|
||||
*
|
||||
* Started 4/12/03
|
||||
* George
|
||||
*
|
||||
* $Id: cepic.c,v 1.15 2003/05/03 16:10:48 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
#define Flip_int32(type) (((type >>24) & 0x000000ff) | \
|
||||
((type >> 8) & 0x0000ff00) | \
|
||||
((type << 8) & 0x00ff0000) | \
|
||||
((type <<24) & 0xff000000) )
|
||||
|
||||
#define Flip_int64(type) (((type >>56) & 0x00000000000000ff) | \
|
||||
((type >>40) & 0x000000000000ff00) | \
|
||||
((type >>24) & 0x0000000000ff0000) | \
|
||||
((type >>8) & 0x00000000ff000000) | \
|
||||
((type <<8) & 0x000000ff00000000) | \
|
||||
((type <<24) & 0x0000ff0000000000) | \
|
||||
((type <<40) & 0x00ff000000000000) | \
|
||||
((type <<56) & 0xff00000000000000))
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, k, istep, options[10], nn, ne, fstep, lstep, nparts, nboxes, u[3], dim, nsplit, flags=0, NSKIP=1;
|
||||
char filename[256];
|
||||
idxtype *mien, *mrng, *part, *sflag;
|
||||
double *mxyz, *bxyz;
|
||||
idxtype *xadj, *adjncy, *cntptr, *cntind;
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut, etype=2;
|
||||
void *cinfo=NULL;
|
||||
FILE *fpin;
|
||||
long long int *ltmp;
|
||||
|
||||
if (argc <= 6) {
|
||||
mfprintf(stderr, "Usage: %s <nn> <ne> <fstep> <lstep> <nparts> [flags] [NSKIP]\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
nn = atoi(argv[1]);
|
||||
ne = atoi(argv[2]);
|
||||
fstep = atoi(argv[3]);
|
||||
lstep = atoi(argv[4]);
|
||||
nparts = atoi(argv[5]);
|
||||
if (argc > 6)
|
||||
flags = atoi(argv[6]);
|
||||
if (argc > 7)
|
||||
NSKIP = atoi(argv[7]);
|
||||
|
||||
mprintf("\n\n------------------------------------------------------------------------------------------\n");
|
||||
mprintf("Reading nn: %D, ne: %D, fstep: %D, lstep: %D, nparts: %D\n", nn, ne, fstep, lstep, nparts);
|
||||
|
||||
mien = idxmalloc(4*ne, "main: mien");
|
||||
mxyz = gk_dmalloc(3*nn, "main: mxyz");
|
||||
mrng = idxmalloc(4*ne, "main: mrng");
|
||||
bxyz = gk_dmalloc(6*ne*4, "main: bxyz");
|
||||
|
||||
part = idxmalloc(nn, "main: part");
|
||||
sflag = idxmalloc(nn, "main: sflag");
|
||||
|
||||
xadj = idxmalloc(nn+1, "main: xadj");
|
||||
adjncy = idxmalloc(50*nn, "main: adjncy");
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Read the initial mesh and setup the graph and contact information
|
||||
*========================================================================*/
|
||||
msprintf(filename, "mien.%04D", fstep);
|
||||
fpin = GKfopen(filename, "rb", "main: mien");
|
||||
fread(mien, sizeof(int), 4*ne, fpin);
|
||||
for (i=0; i<4*ne; i++)
|
||||
mien[i] = Flip_int32(mien[i]);
|
||||
GKfclose(fpin);
|
||||
|
||||
/*========================================================================
|
||||
* Create the nodal graph
|
||||
*========================================================================*/
|
||||
numflag = mien[idxargmin(4*ne, mien)];
|
||||
METIS_MeshToNodal(&ne, &nn, mien, &etype, &numflag, xadj, adjncy);
|
||||
|
||||
|
||||
|
||||
/*========================================================================
|
||||
* Get into the loop in which you go over the different configurations
|
||||
*========================================================================*/
|
||||
for (k=0, istep=fstep; istep<=lstep; istep++, k++) {
|
||||
msprintf(filename, "mxyz.%04D", istep);
|
||||
mprintf("Reading %s...............................................................\n", filename);
|
||||
fpin = GKfopen(filename, "rb", "main: mxyz");
|
||||
fread(mxyz, sizeof(double), 3*nn, fpin);
|
||||
for (i=0; i<3*nn; i++) {
|
||||
ltmp = (long long int *)(mxyz+i);
|
||||
*ltmp = Flip_int64(*ltmp);
|
||||
}
|
||||
GKfclose(fpin);
|
||||
|
||||
msprintf(filename, "mrng.%04D", istep);
|
||||
fpin = GKfopen(filename, "rb", "main: mrng");
|
||||
fread(mrng, sizeof(int), 4*ne, fpin);
|
||||
for (i=0; i<4*ne; i++)
|
||||
mrng[i] = Flip_int32(mrng[i]);
|
||||
GKfclose(fpin);
|
||||
|
||||
/* Determine which nodes are in the surface */
|
||||
iset(nn, 0, sflag);
|
||||
for (i=0; i<ne; i++) {
|
||||
if (mrng[4*i+0] > 0) { /* 1, 2, 3 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+1] > 0) { /* 1, 2, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+2] > 0) { /* 2, 3, 4 */
|
||||
sflag[mien[4*i+1]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
if (mrng[4*i+3] > 0) { /* 1, 3, 4 */
|
||||
sflag[mien[4*i+0]-1] = 1;
|
||||
sflag[mien[4*i+2]-1] = 1;
|
||||
sflag[mien[4*i+3]-1] = 1;
|
||||
}
|
||||
}
|
||||
|
||||
mprintf("Contact Nodes: %D of %D\n", isum(nn, sflag), nn);
|
||||
|
||||
/* Compute/Update the partitioning */
|
||||
if (k%NSKIP == 0) {
|
||||
if (cinfo != NULL)
|
||||
METIS_FreeContactInfo(cinfo);
|
||||
|
||||
options[0] = 0;
|
||||
cinfo = METIS_PartGraphForContact(&nn, xadj, adjncy, mxyz, sflag, &numflag, &nparts,
|
||||
options, &edgecut, part);
|
||||
for (i=0; i<nn; i++)
|
||||
part[i]--;
|
||||
}
|
||||
|
||||
switch (flags) {
|
||||
case 1:
|
||||
if (cinfo != NULL)
|
||||
METIS_FreeContactInfo(cinfo);
|
||||
|
||||
cinfo = METIS_SetupContact(&nn, mxyz, sflag, &nparts, part);
|
||||
break;
|
||||
case 2:
|
||||
if (cinfo != NULL)
|
||||
METIS_FreeContactInfo(cinfo);
|
||||
|
||||
cinfo = METIS_SetupContact0(&nn, mxyz, sflag, &nparts, part);
|
||||
break;
|
||||
default:
|
||||
METIS_UpdateContactInfo(cinfo, &nn, mxyz, sflag);
|
||||
}
|
||||
|
||||
|
||||
/* Determine the bounding boxes of the surface elements */
|
||||
for (nsplit=0, nboxes=0, i=0; i<ne; i++) {
|
||||
if (mrng[4*i+0] > 0) { /* 1, 2, 3 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+1]-1;
|
||||
u[2] = mien[4*i+2]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
if (part[u[0]] != part[u[1]] || part[u[0]] != part[u[2]])
|
||||
nsplit++;
|
||||
}
|
||||
if (mrng[4*i+1] > 0) { /* 1, 2, 4 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+1]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
if (part[u[0]] != part[u[1]] || part[u[0]] != part[u[2]])
|
||||
nsplit++;
|
||||
}
|
||||
if (mrng[4*i+2] > 0) { /* 2, 3, 4 */
|
||||
u[0] = mien[4*i+1]-1;
|
||||
u[1] = mien[4*i+2]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
if (part[u[0]] != part[u[1]] || part[u[0]] != part[u[2]])
|
||||
nsplit++;
|
||||
}
|
||||
if (mrng[4*i+3] > 0) { /* 1, 3, 4 */
|
||||
u[0] = mien[4*i+0]-1;
|
||||
u[1] = mien[4*i+2]-1;
|
||||
u[2] = mien[4*i+3]-1;
|
||||
bxyz[6*nboxes+0] = bxyz[6*nboxes+3] = mxyz[3*u[0]+0];
|
||||
bxyz[6*nboxes+1] = bxyz[6*nboxes+4] = mxyz[3*u[0]+1];
|
||||
bxyz[6*nboxes+2] = bxyz[6*nboxes+5] = mxyz[3*u[0]+2];
|
||||
for (j=1; j<3; j++) {
|
||||
for (dim=0; dim<3; dim++) {
|
||||
bxyz[6*nboxes+dim] = (bxyz[6*nboxes+dim] > mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+dim]);
|
||||
bxyz[6*nboxes+3+dim] = (bxyz[6*nboxes+3+dim] < mxyz[3*u[j]+dim] ? mxyz[3*u[j]+dim] : bxyz[6*nboxes+3+dim]);
|
||||
}
|
||||
}
|
||||
nboxes++;
|
||||
if (part[u[0]] != part[u[1]] || part[u[0]] != part[u[2]])
|
||||
nsplit++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
METIS_FindContacts(cinfo, &nboxes, bxyz, &nparts, &cntptr, &cntind);
|
||||
|
||||
mprintf("Contacting Elements: %D Indices: %D Nsplit: %D\n", nboxes, cntptr[nboxes]-nboxes, nsplit);
|
||||
|
||||
gk_free((void **)&cntptr, &cntind, LTERM);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -0,0 +1,208 @@
|
||||
/*
|
||||
* cmdline_cpmetis.c
|
||||
*
|
||||
* This file parses the command line arguments
|
||||
*
|
||||
* Started 3/25/03
|
||||
* George
|
||||
*
|
||||
* $Id: cmdline_cmetis.c,v 1.1 2003/04/04 23:22:47 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Command-line options
|
||||
*-------------------------------------------------------------------*/
|
||||
static struct gk_option long_options[] = {
|
||||
{"mtype", 1, 0, CMD_MTYPE},
|
||||
{"itype", 1, 0, CMD_ITYPE},
|
||||
{"rtype", 1, 0, CMD_RTYPE},
|
||||
|
||||
{"balanced", 0, 0, CMD_BALANCE},
|
||||
|
||||
{"niter", 1, 0, CMD_NITER},
|
||||
|
||||
{"tpwgts", 1, 0, CMD_TPWGTS},
|
||||
|
||||
{"seed", 1, 0, CMD_SEED},
|
||||
|
||||
{"dbglvl", 1, 0, CMD_DBGLVL},
|
||||
|
||||
{"help", 0, 0, CMD_HELP},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mappings for the various parameter values
|
||||
*-------------------------------------------------------------------*/
|
||||
static gk_StringMap_t mtype_options[] = {
|
||||
{"rm", MTYPE_RM},
|
||||
{"hem", MTYPE_HEM},
|
||||
{"shem", MTYPE_SHEM},
|
||||
{"shebm", MTYPE_SHEBM_ONENORM},
|
||||
{"sbhem", MTYPE_SBHEM_ONENORM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t itype_options[] = {
|
||||
{"greedy", ITYPE_GGPKL},
|
||||
{"random", ITYPE_RANDOM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t rtype_options[] = {
|
||||
{"fm", RTYPE_FM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mini help
|
||||
*-------------------------------------------------------------------*/
|
||||
static char helpstr[][100] =
|
||||
{
|
||||
" ",
|
||||
"Usage: cpmetis [options] <graph filename> <coord filename> <nparts>",
|
||||
" ",
|
||||
" Required parameters",
|
||||
" filename Stores the graph to be partitioned.",
|
||||
" nparts The number of partitions to split the graph.",
|
||||
" ",
|
||||
" Optional parameters",
|
||||
" -mtyep=string",
|
||||
" Specifies the scheme to be used to match the vertices of the graph",
|
||||
" during the coarsening.",
|
||||
" The possible values are:",
|
||||
" rm - Random matching",
|
||||
" hem - Heavy-edge matching",
|
||||
" shem - Sorted heavy-edge matching [default]",
|
||||
" shebm - Combination of shem and balanced matching for",
|
||||
" multi-constraint.",
|
||||
" sbhem - Similar as shebm but priority is given to balance",
|
||||
" ",
|
||||
" -itype=string",
|
||||
" Specifies the scheme to be used to compute the initial partitioning",
|
||||
" of the graph.",
|
||||
" The possible values are:",
|
||||
" greedy - Grow a bisection using a greedy strategy [default]",
|
||||
" random - Compute a bisection at random",
|
||||
" ",
|
||||
" -rtype=string",
|
||||
" Specifies the scheme to be used for refinement",
|
||||
" The possible values are:",
|
||||
" fm - FM refinement",
|
||||
" ",
|
||||
" -balance",
|
||||
" Specifies that the final partitioning should contain nparts-1 equal",
|
||||
" size partitions with the last partition having upto nparts-1 fewer",
|
||||
" vertices.",
|
||||
" ",
|
||||
" -seed=int ",
|
||||
" Selects the seed of the random number generator. ",
|
||||
" ",
|
||||
" -dbglvl=int ",
|
||||
" Selects the dbglvl. ",
|
||||
" ",
|
||||
" -help",
|
||||
" Prints this message.",
|
||||
""
|
||||
};
|
||||
|
||||
static char shorthelpstr[][100] = {
|
||||
" ",
|
||||
" Usage: cpmetis [options] <graph filename> <coord filename> <nparts>",
|
||||
" use 'cpmetis -help' for a summary of the options.",
|
||||
""
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This is the entry point of the command-line argument parser
|
||||
**************************************************************************/
|
||||
void parse_cmdline(ParamType *params, int argc, char *argv[])
|
||||
{
|
||||
int i, j, k;
|
||||
int c, option_index;
|
||||
|
||||
/* initialize the params data structure */
|
||||
params->mtype = PMETIS_CTYPE;
|
||||
params->itype = PMETIS_ITYPE;
|
||||
params->rtype = PMETIS_RTYPE;
|
||||
params->dbglvl = PMETIS_DBGLVL;
|
||||
|
||||
params->balance = 0;
|
||||
params->seed = -1;
|
||||
params->dbglvl = 0;
|
||||
params->filename = NULL;
|
||||
params->xyzfilename = NULL;
|
||||
params->nparts = 1;
|
||||
|
||||
|
||||
/* Parse the command line arguments */
|
||||
while ((c = gk_getopt_long_only(argc, argv, "", long_options, &option_index)) != -1) {
|
||||
switch (c) {
|
||||
case CMD_MTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->mtype = gk_GetStringID(mtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_ITYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->itype = gk_GetStringID(itype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_RTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->rtype = gk_GetStringID(rtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_BALANCE:
|
||||
params->balance = 1;
|
||||
break;
|
||||
|
||||
|
||||
case CMD_SEED:
|
||||
if (gk_optarg) params->seed = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_DBGLVL:
|
||||
if (gk_optarg) params->dbglvl = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_HELP:
|
||||
for (i=0; strlen(helpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", helpstr[i]);
|
||||
exit(0);
|
||||
break;
|
||||
case '?':
|
||||
default:
|
||||
mprintf("Illegal command-line option(s)\nUse %s -help for a summary of the options.\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
if (argc-gk_optind != 3) {
|
||||
mprintf("Missing parameters.");
|
||||
for (i=0; strlen(shorthelpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", shorthelpstr[i]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
params->filename = strdup(argv[gk_optind++]);
|
||||
params->xyzfilename = strdup(argv[gk_optind++]);
|
||||
params->nparts = atoi(argv[gk_optind++]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,206 @@
|
||||
/*
|
||||
* cmdline_kfmetis.c
|
||||
*
|
||||
* This file parses the command line arguments
|
||||
*
|
||||
* Started 8/9/02
|
||||
* George
|
||||
*
|
||||
* $Id: cmdline_kfmetis.c,v 1.1 2002/08/12 15:20:50 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Command-line options
|
||||
*-------------------------------------------------------------------*/
|
||||
static struct gk_option long_options[] = {
|
||||
{"mtype", 1, 0, CMD_MTYPE},
|
||||
{"itype", 1, 0, CMD_ITYPE},
|
||||
{"rtype", 1, 0, CMD_RTYPE},
|
||||
|
||||
{"balanced", 0, 0, CMD_BALANCE},
|
||||
|
||||
{"niter", 1, 0, CMD_NITER},
|
||||
|
||||
{"tpwgts", 1, 0, CMD_TPWGTS},
|
||||
|
||||
{"seed", 1, 0, CMD_SEED},
|
||||
|
||||
{"dbglvl", 1, 0, CMD_DBGLVL},
|
||||
|
||||
{"help", 0, 0, CMD_HELP},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mappings for the various parameter values
|
||||
*-------------------------------------------------------------------*/
|
||||
static gk_StringMap_t mtype_options[] = {
|
||||
{"rm", MTYPE_RM},
|
||||
{"hem", MTYPE_HEM},
|
||||
{"shem", MTYPE_SHEM},
|
||||
{"shebm", MTYPE_SHEBM_ONENORM},
|
||||
{"sbhem", MTYPE_SBHEM_ONENORM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t itype_options[] = {
|
||||
{"greedy", ITYPE_GGPKL},
|
||||
{"random", ITYPE_RANDOM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t rtype_options[] = {
|
||||
{"fm", RTYPE_FM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mini help
|
||||
*-------------------------------------------------------------------*/
|
||||
static char helpstr[][100] =
|
||||
{
|
||||
" ",
|
||||
"Usage: pmetis [options] <filename> <nparts>",
|
||||
" ",
|
||||
" Required parameters",
|
||||
" filename Stores the graph to be partitioned.",
|
||||
" nparts The number of partitions to split the graph.",
|
||||
" ",
|
||||
" Optional parameters",
|
||||
" -mtyep=string",
|
||||
" Specifies the scheme to be used to match the vertices of the graph",
|
||||
" during the coarsening.",
|
||||
" The possible values are:",
|
||||
" rm - Random matching",
|
||||
" hem - Heavy-edge matching",
|
||||
" shem - Sorted heavy-edge matching [default]",
|
||||
" shebm - Combination of shem and balanced matching for",
|
||||
" multi-constraint.",
|
||||
" sbhem - Similar as shebm but priority is given to balance",
|
||||
" ",
|
||||
" -itype=string",
|
||||
" Specifies the scheme to be used to compute the initial partitioning",
|
||||
" of the graph.",
|
||||
" The possible values are:",
|
||||
" greedy - Grow a bisection using a greedy strategy [default]",
|
||||
" random - Compute a bisection at random",
|
||||
" ",
|
||||
" -rtype=string",
|
||||
" Specifies the scheme to be used for refinement",
|
||||
" The possible values are:",
|
||||
" fm - FM refinement",
|
||||
" ",
|
||||
" -balance",
|
||||
" Specifies that the final partitioning should contain nparts-1 equal",
|
||||
" size partitions with the last partition having upto nparts-1 fewer",
|
||||
" vertices.",
|
||||
" ",
|
||||
" -seed=int ",
|
||||
" Selects the seed of the random number generator. ",
|
||||
" ",
|
||||
" -dbglvl=int ",
|
||||
" Selects the dbglvl. ",
|
||||
" ",
|
||||
" -help",
|
||||
" Prints this message.",
|
||||
""
|
||||
};
|
||||
|
||||
static char shorthelpstr[][100] = {
|
||||
" ",
|
||||
" Usage: pmetis [options] <filename> <nparts>",
|
||||
" use 'pmetis -help' for a summary of the options.",
|
||||
""
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This is the entry point of the command-line argument parser
|
||||
**************************************************************************/
|
||||
void parse_cmdline(ParamType *params, int argc, char *argv[])
|
||||
{
|
||||
int i, j, k;
|
||||
int c, option_index;
|
||||
|
||||
/* initialize the params data structure */
|
||||
params->mtype = PMETIS_CTYPE;
|
||||
params->itype = PMETIS_ITYPE;
|
||||
params->rtype = PMETIS_RTYPE;
|
||||
params->dbglvl = PMETIS_DBGLVL;
|
||||
|
||||
params->balance = 0;
|
||||
params->seed = -1;
|
||||
params->dbglvl = 0;
|
||||
params->filename = NULL;
|
||||
params->nparts = 1;
|
||||
|
||||
|
||||
/* Parse the command line arguments */
|
||||
while ((c = gk_getopt_long_only(argc, argv, "", long_options, &option_index)) != -1) {
|
||||
switch (c) {
|
||||
case CMD_MTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->mtype = gk_GetStringID(mtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_ITYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->itype = gk_GetStringID(itype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_RTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->rtype = gk_GetStringID(rtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_BALANCE:
|
||||
params->balance = 1;
|
||||
break;
|
||||
|
||||
|
||||
case CMD_SEED:
|
||||
if (gk_optarg) params->seed = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_DBGLVL:
|
||||
if (gk_optarg) params->dbglvl = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_HELP:
|
||||
for (i=0; strlen(helpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", helpstr[i]);
|
||||
exit(0);
|
||||
break;
|
||||
case '?':
|
||||
default:
|
||||
mprintf("Illegal command-line option(s)\nUse %s -help for a summary of the options.\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
if (argc-gk_optind != 2) {
|
||||
mprintf("Missing parameters.");
|
||||
for (i=0; strlen(shorthelpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", shorthelpstr[i]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
params->filename = strdup(argv[gk_optind++]);
|
||||
params->nparts = atoi(argv[gk_optind++]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,206 @@
|
||||
/*
|
||||
* cmdline_pmetis.c
|
||||
*
|
||||
* This file parses the command line arguments
|
||||
*
|
||||
* Started 8/9/02
|
||||
* George
|
||||
*
|
||||
* $Id: cmdline_pmetis.c,v 1.4 2002/08/12 15:20:51 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Command-line options
|
||||
*-------------------------------------------------------------------*/
|
||||
static struct gk_option long_options[] = {
|
||||
{"mtype", 1, 0, CMD_MTYPE},
|
||||
{"itype", 1, 0, CMD_ITYPE},
|
||||
{"rtype", 1, 0, CMD_RTYPE},
|
||||
|
||||
{"balanced", 0, 0, CMD_BALANCE},
|
||||
|
||||
{"niter", 1, 0, CMD_NITER},
|
||||
|
||||
{"tpwgts", 1, 0, CMD_TPWGTS},
|
||||
|
||||
{"seed", 1, 0, CMD_SEED},
|
||||
|
||||
{"dbglvl", 1, 0, CMD_DBGLVL},
|
||||
|
||||
{"help", 0, 0, CMD_HELP},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mappings for the various parameter values
|
||||
*-------------------------------------------------------------------*/
|
||||
static gk_StringMap_t mtype_options[] = {
|
||||
{"rm", MTYPE_RM},
|
||||
{"hem", MTYPE_HEM},
|
||||
{"shem", MTYPE_SHEM},
|
||||
{"shebm", MTYPE_SHEBM_ONENORM},
|
||||
{"sbhem", MTYPE_SBHEM_ONENORM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t itype_options[] = {
|
||||
{"greedy", ITYPE_GGPKL},
|
||||
{"random", ITYPE_RANDOM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
static gk_StringMap_t rtype_options[] = {
|
||||
{"fm", RTYPE_FM},
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------
|
||||
* Mini help
|
||||
*-------------------------------------------------------------------*/
|
||||
static char helpstr[][100] =
|
||||
{
|
||||
" ",
|
||||
"Usage: pmetis [options] <filename> <nparts>",
|
||||
" ",
|
||||
" Required parameters",
|
||||
" filename Stores the graph to be partitioned.",
|
||||
" nparts The number of partitions to split the graph.",
|
||||
" ",
|
||||
" Optional parameters",
|
||||
" -mtyep=string",
|
||||
" Specifies the scheme to be used to match the vertices of the graph",
|
||||
" during the coarsening.",
|
||||
" The possible values are:",
|
||||
" rm - Random matching",
|
||||
" hem - Heavy-edge matching",
|
||||
" shem - Sorted heavy-edge matching [default]",
|
||||
" shebm - Combination of shem and balanced matching for",
|
||||
" multi-constraint.",
|
||||
" sbhem - Similar as shebm but priority is given to balance",
|
||||
" ",
|
||||
" -itype=string",
|
||||
" Specifies the scheme to be used to compute the initial partitioning",
|
||||
" of the graph.",
|
||||
" The possible values are:",
|
||||
" greedy - Grow a bisection using a greedy strategy [default]",
|
||||
" random - Compute a bisection at random",
|
||||
" ",
|
||||
" -rtype=string",
|
||||
" Specifies the scheme to be used for refinement",
|
||||
" The possible values are:",
|
||||
" fm - FM refinement",
|
||||
" ",
|
||||
" -balance",
|
||||
" Specifies that the final partitioning should contain nparts-1 equal",
|
||||
" size partitions with the last partition having upto nparts-1 fewer",
|
||||
" vertices.",
|
||||
" ",
|
||||
" -seed=int ",
|
||||
" Selects the seed of the random number generator. ",
|
||||
" ",
|
||||
" -dbglvl=int ",
|
||||
" Selects the dbglvl. ",
|
||||
" ",
|
||||
" -help",
|
||||
" Prints this message.",
|
||||
""
|
||||
};
|
||||
|
||||
static char shorthelpstr[][100] = {
|
||||
" ",
|
||||
" Usage: pmetis [options] <filename> <nparts>",
|
||||
" use 'pmetis -help' for a summary of the options.",
|
||||
""
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This is the entry point of the command-line argument parser
|
||||
**************************************************************************/
|
||||
void parse_cmdline(ParamType *params, int argc, char *argv[])
|
||||
{
|
||||
int i, j, k;
|
||||
int c, option_index;
|
||||
|
||||
/* initialize the params data structure */
|
||||
params->mtype = PMETIS_CTYPE;
|
||||
params->itype = PMETIS_ITYPE;
|
||||
params->rtype = PMETIS_RTYPE;
|
||||
params->dbglvl = PMETIS_DBGLVL;
|
||||
|
||||
params->balance = 0;
|
||||
params->seed = -1;
|
||||
params->dbglvl = 0;
|
||||
params->filename = NULL;
|
||||
params->nparts = 1;
|
||||
|
||||
|
||||
/* Parse the command line arguments */
|
||||
while ((c = gk_getopt_long_only(argc, argv, "", long_options, &option_index)) != -1) {
|
||||
switch (c) {
|
||||
case CMD_MTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->mtype = gk_GetStringID(mtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_ITYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->itype = gk_GetStringID(itype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
case CMD_RTYPE:
|
||||
if (gk_optarg)
|
||||
if ((params->rtype = gk_GetStringID(rtype_options, gk_optarg)) == -1)
|
||||
errexit("Invalid option -%s=%s\n", long_options[option_index].name, gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_BALANCE:
|
||||
params->balance = 1;
|
||||
break;
|
||||
|
||||
|
||||
case CMD_SEED:
|
||||
if (gk_optarg) params->seed = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_DBGLVL:
|
||||
if (gk_optarg) params->dbglvl = atoi(gk_optarg);
|
||||
break;
|
||||
|
||||
case CMD_HELP:
|
||||
for (i=0; strlen(helpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", helpstr[i]);
|
||||
exit(0);
|
||||
break;
|
||||
case '?':
|
||||
default:
|
||||
mprintf("Illegal command-line option(s)\nUse %s -help for a summary of the options.\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
if (argc-gk_optind != 2) {
|
||||
mprintf("Missing parameters.");
|
||||
for (i=0; strlen(shorthelpstr[i]) > 0; i++)
|
||||
mprintf("%s\n", shorthelpstr[i]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
params->filename = strdup(argv[gk_optind++]);
|
||||
params->nparts = atoi(argv[gk_optind++]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,97 @@
|
||||
/*
|
||||
* Copyright 2003, Regents of the University of Minnesota
|
||||
*
|
||||
* cmetis.c
|
||||
*
|
||||
* This file contains the driving routine for partitioning for
|
||||
* sub-domain direct factorization.
|
||||
*
|
||||
* Started 3/25/03
|
||||
* George
|
||||
*
|
||||
* $Id: cmetis.c,v 1.5 2003/04/08 12:52:59 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, options[10], nnodes, nclean, naclean, ndirty, maxdepth;
|
||||
idxtype *part, *sflag;
|
||||
float lbvec[MAXNCON];
|
||||
GraphType graph;
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
ParamType params;
|
||||
void *cinfo;
|
||||
double TOTALTmr, METISTmr, IOTmr;
|
||||
|
||||
parse_cmdline(¶ms, argc, argv);
|
||||
|
||||
if (params.nparts < 2) {
|
||||
mprintf("The number of partitions should be greater than 1!\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, params.filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
ReadCoordinates(&graph, params.xyzfilename);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D, #Parts: %D\n", params.filename, graph.nvtxs, graph.nedges/2, params.nparts);
|
||||
if (graph.ncon > 1)
|
||||
mprintf(" Balancing Constraints: %D\n", graph.ncon);
|
||||
mprintf("\nRecursive Partitioning... -------------------------------------------\n");
|
||||
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
sflag = idxsmalloc(graph.nvtxs, 1, "main: sflag");
|
||||
options[0] = 0;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
cinfo = METIS_PartGraphForContact(&graph.nvtxs, graph.xadj, graph.adjncy, graph.coords, sflag,
|
||||
&numflag, &(params.nparts), options, &edgecut, part);
|
||||
|
||||
METIS_UpdateContactInfo(cinfo, &graph.nvtxs, graph.coords, sflag);
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
ComputePartitionBalance(&graph, params.nparts, part, lbvec);
|
||||
|
||||
graph.vwgt = idxsmalloc(graph.nvtxs, 1, "main: graph->vwgt");
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D, Volume: %7D, Balance: ", params.nparts, edgecut,
|
||||
ComputeVolume(&graph, part));
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%5.2f ", lbvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WritePartition(params.filename, part, graph.nvtxs, params.nparts);
|
||||
gk_stopcputimer(IOTmr);
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f (CMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Total: \t\t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, &graph.coords, &part, &sflag, LTERM);
|
||||
}
|
||||
|
||||
@ -0,0 +1,45 @@
|
||||
/*
|
||||
* defs.h
|
||||
*
|
||||
* This file contains various constant definitions
|
||||
*
|
||||
* Started 8/9/02
|
||||
* George
|
||||
*
|
||||
*/
|
||||
|
||||
#define CMD_MTYPE 1
|
||||
#define CMD_ITYPE 2
|
||||
#define CMD_RTYPE 3
|
||||
|
||||
#define CMD_BALANCE 10
|
||||
#define CMD_NITER 20
|
||||
#define CMD_NTRIALS 21
|
||||
|
||||
#define CMD_TPWGTS 30
|
||||
|
||||
#define CMD_SEED 50
|
||||
|
||||
#define CMD_OUTPUT 100
|
||||
#define CMD_NOOUTPUT 101
|
||||
|
||||
#define CMD_DBGLVL 1000
|
||||
#define CMD_HELP 1001
|
||||
|
||||
|
||||
|
||||
|
||||
/* The text labels for MTypes */
|
||||
static char mtypenames[][10] = {"", "None", "MAXTF", "SQRT", "LOG", "IDF"};
|
||||
|
||||
|
||||
/* The text labels for ITypes */
|
||||
static char itypenames[][10] = {"", "None", "IDF"};
|
||||
|
||||
|
||||
/* The text labels for RTypes */
|
||||
static char rtypenames[][20] = {"", "I1", "I2", "E1", "G1", "G1'", "H1", "H2", "SLINK",
|
||||
"SLINK_W", "CLINK", "CLINK_W", "UPGMA", "UPGMA_W",
|
||||
"UPGMA_W2", "Cut", "RCut", "NCut", "MMCut"};
|
||||
|
||||
|
||||
@ -0,0 +1,58 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* graphchk.c
|
||||
*
|
||||
* This file checks the validity of a graph
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: graphchk.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype wgtflag;
|
||||
|
||||
if (argc != 2) {
|
||||
mprintf("Usage: %s <GraphFile>\n", argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
if (graph.nvtxs == 0) {
|
||||
mprintf("Empty graph!\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D\n\n", filename, graph.nvtxs, graph.nedges/2);
|
||||
mprintf("Checking Graph... ---------------------------------------------------\n");
|
||||
|
||||
if (CheckGraph(&graph))
|
||||
mprintf(" The format of the graph is correct!\n");
|
||||
else
|
||||
mprintf(" The format of the graph is incorrect!\n");
|
||||
|
||||
mprintf("\n**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,690 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* io.c
|
||||
*
|
||||
* This file contains routines related to I/O
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: io.c,v 1.7 2003/04/13 04:45:14 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the spd matrix
|
||||
**************************************************************************/
|
||||
void ReadGraph(GraphType *graph, char *filename, idxtype *wgtflag)
|
||||
{
|
||||
idxtype i, j, k, l, fmt, readew, readvw, ncon, edge, ewgt;
|
||||
idxtype *xadj, *adjncy, *vwgt, *adjwgt;
|
||||
char *line, *oldstr, *newstr;
|
||||
FILE *fpin;
|
||||
|
||||
InitGraph(graph);
|
||||
|
||||
line = gk_cmalloc(MAXLINE+1, "ReadGraph: line");
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
do {
|
||||
fgets(line, MAXLINE, fpin);
|
||||
} while (line[0] == '%' && !feof(fpin));
|
||||
|
||||
if (feof(fpin)) {
|
||||
graph->nvtxs = 0;
|
||||
gk_free((void **)&line, LTERM);
|
||||
return;
|
||||
}
|
||||
|
||||
fmt = ncon = 0;
|
||||
msscanf(line, "%D %D %D %D", &(graph->nvtxs), &(graph->nedges), &fmt, &ncon);
|
||||
|
||||
|
||||
readew = (fmt%10 > 0);
|
||||
readvw = ((fmt/10)%10 > 0);
|
||||
if (fmt >= 100) {
|
||||
mprintf("Cannot read this type of file format!");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
|
||||
*wgtflag = 0;
|
||||
if (readew)
|
||||
*wgtflag += 1;
|
||||
if (readvw)
|
||||
*wgtflag += 2;
|
||||
|
||||
if (ncon > 0 && !readvw) {
|
||||
mprintf("------------------------------------------------------------------------------\n");
|
||||
mprintf("*** I detected an error in your input file ***\n\n");
|
||||
mprintf("You specified ncon=%D, but the fmt parameter does not specify vertex weights\n", ncon);
|
||||
mprintf("Make sure that the fmt parameter is set to either 10 or 11.\n");
|
||||
mprintf("------------------------------------------------------------------------------\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
graph->nedges *=2;
|
||||
ncon = graph->ncon = (ncon == 0 ? 1 : ncon);
|
||||
|
||||
/*mprintf("%D %D %D %D %D [%D %D]\n", fmt, fmt%10, (fmt/10)%10, ncon, graph->ncon, readew, readvw);*/
|
||||
|
||||
if (graph->nvtxs > MAXIDX)
|
||||
errexit("\nThe matrix is too big: %d [%d %d]\n", graph->nvtxs, MAXIDX, sizeof(idxtype));
|
||||
|
||||
xadj = graph->xadj = idxsmalloc(graph->nvtxs+1, 0, "ReadGraph: xadj");
|
||||
adjncy = graph->adjncy = idxmalloc(graph->nedges, "ReadGraph: adjncy");
|
||||
|
||||
vwgt = graph->vwgt = (readvw ? idxmalloc(ncon*graph->nvtxs, "ReadGraph: vwgt") : NULL);
|
||||
adjwgt = graph->adjwgt = (readew ? idxmalloc(graph->nedges, "ReadGraph: adjwgt") : NULL);
|
||||
|
||||
/* Start reading the graph file */
|
||||
for (xadj[0]=0, k=0, i=0; i<graph->nvtxs; i++) {
|
||||
do {
|
||||
fgets(line, MAXLINE, fpin);
|
||||
} while (line[0] == '%' && !feof(fpin));
|
||||
oldstr = line;
|
||||
newstr = NULL;
|
||||
|
||||
if (strlen(line) == MAXLINE)
|
||||
errexit("\nBuffer for fgets not big enough!\n");
|
||||
|
||||
if (readvw) {
|
||||
for (l=0; l<ncon; l++) {
|
||||
vwgt[i*ncon+l] = strtoidx(oldstr, &newstr, 10);
|
||||
oldstr = newstr;
|
||||
}
|
||||
}
|
||||
|
||||
for (;;) {
|
||||
edge = strtoidx(oldstr, &newstr, 10) -1;
|
||||
oldstr = newstr;
|
||||
|
||||
if (readew) {
|
||||
ewgt = strtoidx(oldstr, &newstr, 10);
|
||||
oldstr = newstr;
|
||||
}
|
||||
|
||||
if (edge < 0)
|
||||
break;
|
||||
|
||||
adjncy[k] = edge;
|
||||
if (readew)
|
||||
adjwgt[k] = ewgt;
|
||||
k++;
|
||||
}
|
||||
xadj[i+1] = k;
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
if (k != graph->nedges) {
|
||||
mprintf("------------------------------------------------------------------------------\n");
|
||||
mprintf("*** I detected an error in your input file ***\n\n");
|
||||
mprintf("In the first line of the file, you specified that the graph contained\n%D edges. However, I only found %D edges in the file.\n", graph->nedges/2, k/2);
|
||||
if (2*k == graph->nedges) {
|
||||
mprintf("\n *> I detected that you specified twice the number of edges that you have in\n");
|
||||
mprintf(" the file. Remember that the number of edges specified in the first line\n");
|
||||
mprintf(" counts each edge between vertices v and u only once.\n\n");
|
||||
}
|
||||
mprintf("Please specify the correct number of edges in the first line of the file.\n");
|
||||
mprintf("------------------------------------------------------------------------------\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_free((void **)&line, LTERM);
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the spd matrix
|
||||
**************************************************************************/
|
||||
void ReadCoordinates(GraphType *graph, char *filename)
|
||||
{
|
||||
idxtype i, j, k, l, nvtxs, fmt, readew, readvw, ncon, edge, ewgt;
|
||||
FILE *fpin;
|
||||
char *line;
|
||||
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
nvtxs = graph->nvtxs;
|
||||
|
||||
graph->coords = gk_dsmalloc(3*nvtxs, 0.0, "ReadCoordinates: coords");
|
||||
|
||||
line = gk_cmalloc(MAXLINE+1, "ReadCoordinates: line");
|
||||
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
fgets(line, MAXLINE, fpin);
|
||||
msscanf(line, "%lf %lf %lf", graph->coords+3*i+0, graph->coords+3*i+1, graph->coords+3*i+2);
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
gk_free((void **)&line, LTERM);
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes out the partition vector
|
||||
**************************************************************************/
|
||||
void WritePartition(char *fname, idxtype *part, idxtype n, idxtype nparts)
|
||||
{
|
||||
FILE *fpout;
|
||||
idxtype i;
|
||||
char filename[256];
|
||||
|
||||
msprintf(filename,"%s.part.%D",fname, nparts);
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
for (i=0; i<n; i++)
|
||||
fprintf(fpout,"%" PRIIDX "\n", part[i]);
|
||||
|
||||
gk_fclose(fpout);
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes out the partition vectors for a mesh
|
||||
**************************************************************************/
|
||||
void WriteMeshPartition(char *fname, idxtype nparts, idxtype ne, idxtype *epart,
|
||||
idxtype nn, idxtype *npart)
|
||||
{
|
||||
FILE *fpout;
|
||||
idxtype i;
|
||||
char filename[256];
|
||||
|
||||
msprintf(filename,"%s.epart.%D",fname, nparts);
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
for (i=0; i<ne; i++)
|
||||
fprintf(fpout,"%" PRIIDX "\n", epart[i]);
|
||||
|
||||
gk_fclose(fpout);
|
||||
|
||||
|
||||
msprintf(filename,"%s.npart.%D",fname, nparts);
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
for (i=0; i<nn; i++)
|
||||
fprintf(fpout, "%" PRIIDX "\n", npart[i]);
|
||||
|
||||
gk_fclose(fpout);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes out the partition vector
|
||||
**************************************************************************/
|
||||
void WritePermutation(char *fname, idxtype *iperm, idxtype n)
|
||||
{
|
||||
FILE *fpout;
|
||||
idxtype i;
|
||||
char filename[256];
|
||||
|
||||
msprintf(filename,"%s.iperm",fname);
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
for (i=0; i<n; i++)
|
||||
fprintf(fpout, "%" PRIIDX "\n", iperm[i]);
|
||||
|
||||
gk_fclose(fpout);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function checks if a graph is valid
|
||||
**************************************************************************/
|
||||
int CheckGraph(GraphType *graph)
|
||||
{
|
||||
idxtype i, j, k, l, nvtxs, err=0;
|
||||
idxtype *xadj, *adjncy, *adjwgt;
|
||||
|
||||
nvtxs = graph->nvtxs;
|
||||
xadj = graph->xadj;
|
||||
adjncy = graph->adjncy;
|
||||
adjwgt = graph->adjwgt;
|
||||
|
||||
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
for (j=xadj[i]; j<xadj[i+1]; j++) {
|
||||
k = adjncy[j];
|
||||
|
||||
if (i == k) {
|
||||
mprintf("Vertex %D contains a self-loop (i.e., diagonal entry in the matrix)!\n", i);
|
||||
err++;
|
||||
}
|
||||
else {
|
||||
for (l=xadj[k]; l<xadj[k+1]; l++) {
|
||||
if (adjncy[l] == i) {
|
||||
if (adjwgt != NULL && adjwgt[l] != adjwgt[j]) {
|
||||
mprintf("Edges (%D %D) and (%D %D) do not have the same weight! %D %D\n", i,k,k,i, adjwgt[l], adjwgt[adjncy[j]]);
|
||||
err++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (l == xadj[k+1]) {
|
||||
mprintf("Missing edge: (%D %D)!\n", k, i);
|
||||
err++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (err > 0)
|
||||
mprintf("A total of %D errors exist in the input file. Correct them, and run again!\n", err);
|
||||
|
||||
return (err == 0 ? 1 : 0);
|
||||
}
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* This function detect the input mesh type
|
||||
***************************************************************************/
|
||||
int MeshType(char *filename)
|
||||
{
|
||||
int i, j, k, l, len, cnt=0;
|
||||
FILE *fpin;
|
||||
char temp[40], inpt[80];
|
||||
int firstline[3];
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin,"%[^\n]s", inpt);
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
len = strlen(inpt);
|
||||
|
||||
i=0;k=0;
|
||||
while (inpt[i]==' ') i++;
|
||||
while (i<=len) {
|
||||
if (inpt[i]==' ' || i==len) {
|
||||
l=0;
|
||||
for (j=k; j<i;j++ )
|
||||
temp[l++]=inpt[j];
|
||||
|
||||
temp[l]='\0';
|
||||
firstline[cnt++] = atoi(temp);
|
||||
while (inpt[i]==' ') i++;
|
||||
k=i;
|
||||
if (i==len) break;
|
||||
}
|
||||
else
|
||||
i++;
|
||||
}
|
||||
|
||||
|
||||
if (cnt==1)
|
||||
return 0; /*Mixed element without weight */
|
||||
else if (cnt==2 && firstline[1]>0)
|
||||
return 1; /*Fixed element without weight*/
|
||||
else if (cnt==2 && firstline[1]==-1)
|
||||
return 2; /*Mixed element with weight*/
|
||||
else if (cnt==3 && firstline[2]==-1)
|
||||
return 3; /*Fixed element with weight*/
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the element node array of a mesh
|
||||
**************************************************************************/
|
||||
idxtype *ReadMesh(char *filename, idxtype *ne, idxtype *nn, idxtype *etype)
|
||||
{
|
||||
idxtype i, j, k, esize;
|
||||
idxtype *elmnts;
|
||||
FILE *fpin;
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D %D", ne, etype);
|
||||
|
||||
switch (*etype) {
|
||||
case 1:
|
||||
esize = 3;
|
||||
break;
|
||||
case 2:
|
||||
esize = 4;
|
||||
break;
|
||||
case 3:
|
||||
esize = 8;
|
||||
break;
|
||||
case 4:
|
||||
esize = 4;
|
||||
break;
|
||||
case 5:
|
||||
esize = 2;
|
||||
break;
|
||||
default:
|
||||
errexit("Unknown mesh-element type: %d\n", *etype);
|
||||
}
|
||||
|
||||
elmnts = idxmalloc(esize*(*ne), "ReadMesh: elmnts");
|
||||
|
||||
for (j=esize*(*ne), i=0; i<j; i++) {
|
||||
mfscanf(fpin, "%D", elmnts+i);
|
||||
elmnts[i]--;
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
*nn = elmnts[idxargmax(j, elmnts)]+1;
|
||||
|
||||
return elmnts;
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the element node array of a mesh with weight
|
||||
**************************************************************************/
|
||||
idxtype *ReadMeshWgt(char *filename, idxtype *ne, idxtype *nn, idxtype *etype,
|
||||
idxtype *vwgt)
|
||||
{
|
||||
idxtype i, j, k, esize;
|
||||
idxtype *elmnts;
|
||||
FILE *fpin;
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D %D", ne, etype);
|
||||
mfscanf(fpin, "%D", &i);
|
||||
|
||||
switch (*etype) {
|
||||
case 1:
|
||||
esize = 3;
|
||||
break;
|
||||
case 2:
|
||||
esize = 4;
|
||||
break;
|
||||
case 3:
|
||||
esize = 8;
|
||||
break;
|
||||
case 4:
|
||||
esize = 4;
|
||||
break;
|
||||
case 5:
|
||||
esize = 2;
|
||||
break;
|
||||
default:
|
||||
errexit("Unknown mesh-element type: %d\n", *etype);
|
||||
}
|
||||
|
||||
elmnts = idxmalloc(esize*(*ne), "ReadMeshWgt: elmnts");
|
||||
|
||||
for (j=0, i=0; i<*ne; i++) {
|
||||
mfscanf(fpin, "%D", vwgt+i);
|
||||
for (k=0; k<esize; k++) {
|
||||
mfscanf(fpin, "%D", elmnts+j);
|
||||
elmnts[j++]--;
|
||||
}
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
*nn = elmnts[idxargmax(j, elmnts)]+1;
|
||||
|
||||
return elmnts;
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the weights of each elements
|
||||
**************************************************************************/
|
||||
idxtype *ReadWgt(char *filename, idxtype *ne, idxtype *nn, idxtype *etype)
|
||||
{
|
||||
idxtype i, j, k, l, esize;
|
||||
idxtype *vwgt;
|
||||
FILE *fpin;
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D %D", ne, etype);
|
||||
mfscanf(fpin, "%D", &i);
|
||||
|
||||
switch (*etype) {
|
||||
case 1:
|
||||
esize = 3;
|
||||
break;
|
||||
case 2:
|
||||
esize = 4;
|
||||
break;
|
||||
case 3:
|
||||
esize = 8;
|
||||
break;
|
||||
case 4:
|
||||
esize = 4;
|
||||
break;
|
||||
case 5:
|
||||
esize = 2;
|
||||
break;
|
||||
default:
|
||||
errexit("Unknown mesh-element type: %d\n", *etype);
|
||||
}
|
||||
|
||||
vwgt = idxmalloc(*ne, "ReadWgt: vwgt");
|
||||
|
||||
for (j=0, i=0; i<*ne; i++) {
|
||||
mfscanf(fpin, "%D", vwgt+i);
|
||||
for (k=0; k<esize; k++) {
|
||||
mfscanf(fpin, "%D", &l);
|
||||
j++;
|
||||
}
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
return vwgt;
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads # of element of a mixed mesh
|
||||
**************************************************************************/
|
||||
idxtype MixedElements(char *filename)
|
||||
{
|
||||
idxtype ne;
|
||||
FILE *fpin;
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D", &ne);
|
||||
gk_fclose(fpin);
|
||||
|
||||
return ne;
|
||||
}
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the element node array of a i Mixed mesh
|
||||
**************************************************************************/
|
||||
idxtype *ReadMixedMesh(char *filename, idxtype *ne, idxtype *nn, idxtype *etype)
|
||||
{
|
||||
idxtype i, j, k, esize;
|
||||
idxtype *elmnts;
|
||||
FILE *fpin;
|
||||
idxtype sizes[]={-1,3,4,8,4,2};
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D", ne);
|
||||
|
||||
elmnts = idxmalloc(8*(*ne), "ReadMixedMesh: elmnts");
|
||||
|
||||
for (j=0, i=0; i<*ne; i++) {
|
||||
mfscanf(fpin, "%D", etype+i);
|
||||
for (k=0;k<sizes[etype[i]];k++) {
|
||||
mfscanf(fpin, "%D", elmnts+j);
|
||||
elmnts[j++]--;
|
||||
}
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
*nn = elmnts[idxargmax(j, elmnts)]+1;
|
||||
|
||||
return elmnts;
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function reads the element node array of a Mixed mesh with weight
|
||||
**************************************************************************/
|
||||
idxtype *ReadMixedMeshWgt(char *filename, idxtype *ne, idxtype *nn,
|
||||
idxtype *etype, idxtype *vwgt)
|
||||
{
|
||||
idxtype i, j, k, esize;
|
||||
idxtype *elmnts;
|
||||
FILE *fpin;
|
||||
idxtype sizes[]={-1,3,4,8,4,2};
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mfscanf(fpin, "%D", ne);
|
||||
|
||||
mfscanf(fpin, "%D", nn);
|
||||
|
||||
elmnts = idxmalloc(8*(*ne), "ReadMixedMeshWgt: elmnts");
|
||||
|
||||
for (j=0, i=0; i<*ne; i++) {
|
||||
mfscanf(fpin, "%D",etype+i);
|
||||
mfscanf(fpin, "%D",vwgt+i);
|
||||
|
||||
for (k=0;k<sizes[etype[i]];k++) {
|
||||
mfscanf(fpin, "%D", elmnts+j);
|
||||
elmnts[j++]--;
|
||||
}
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
*nn = elmnts[idxargmax(j, elmnts)]+1;
|
||||
|
||||
return elmnts;
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
* This function reads the element node array of a i Mixed mesh
|
||||
**************************************************************************/
|
||||
idxtype *ReadMgcnums(char *filename)
|
||||
{
|
||||
idxtype i;
|
||||
idxtype *mgc;
|
||||
FILE *fpin;
|
||||
|
||||
fpin = gk_fopen(filename, "r", __func__);
|
||||
|
||||
mgc = idxmalloc(36, "Readmgcnums: mgcnums");
|
||||
|
||||
for (i=0; i<36; i++) {
|
||||
if (i<6 || i%6==0)
|
||||
mgc[i]=-1;
|
||||
else
|
||||
mfscanf(fpin, "%D", mgc+i);
|
||||
}
|
||||
|
||||
gk_fclose(fpin);
|
||||
|
||||
return mgc;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes a graphs into a file
|
||||
**************************************************************************/
|
||||
void WriteGraph(char *filename, idxtype nvtxs, idxtype *xadj, idxtype *adjncy)
|
||||
{
|
||||
idxtype i, j;
|
||||
FILE *fpout;
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
mfprintf(fpout, "%D %D", nvtxs, xadj[nvtxs]/2);
|
||||
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
mfprintf(fpout, "\n");
|
||||
for (j=xadj[i]; j<xadj[i+1]; j++)
|
||||
fprintf(fpout, " %" PRIIDX, adjncy[j]+1);
|
||||
}
|
||||
|
||||
gk_fclose(fpout);
|
||||
}
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes weighted graph into a file
|
||||
**************************************************************************/
|
||||
void WriteWgtGraph(char *filename, idxtype nvtxs, idxtype *xadj, idxtype *adjncy, idxtype *vwgt)
|
||||
{
|
||||
idxtype i, j;
|
||||
FILE *fpout;
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
mfprintf(fpout, "%D %D", nvtxs, xadj[nvtxs]/2);
|
||||
mfprintf(fpout, " %D", 10);
|
||||
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
fprintf(fpout, "\n");
|
||||
fprintf(fpout, "%" PRIIDX, vwgt[i]);
|
||||
|
||||
for (j=xadj[i]; j<xadj[i+1]; j++)
|
||||
fprintf(fpout, " %" PRIIDX, adjncy[j]+1);
|
||||
}
|
||||
|
||||
gk_fclose(fpout);
|
||||
}
|
||||
|
||||
/*************************************************************************
|
||||
* This function writes a graphs into a file
|
||||
**************************************************************************/
|
||||
void WriteMocGraph(GraphType *graph)
|
||||
{
|
||||
idxtype i, j, nvtxs, ncon;
|
||||
idxtype *xadj, *adjncy;
|
||||
float *nvwgt;
|
||||
char filename[256];
|
||||
FILE *fpout;
|
||||
|
||||
nvtxs = graph->nvtxs;
|
||||
ncon = graph->ncon;
|
||||
xadj = graph->xadj;
|
||||
adjncy = graph->adjncy;
|
||||
nvwgt = graph->nvwgt;
|
||||
|
||||
msprintf(filename, "moc.graph.%D.%D", nvtxs, ncon);
|
||||
|
||||
fpout = gk_fopen(filename, "w", __func__);
|
||||
|
||||
mfprintf(fpout, "%D %D 10 1 %D", nvtxs, xadj[nvtxs]/2, ncon);
|
||||
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
mfprintf(fpout, "\n");
|
||||
for (j=0; j<ncon; j++)
|
||||
fprintf(fpout, "%" PRIIDX " ", (int)((float)10e6*nvwgt[i*ncon+j]));
|
||||
|
||||
for (j=xadj[i]; j<xadj[i+1]; j++)
|
||||
fprintf(fpout, " %" PRIIDX, adjncy[j]+1);
|
||||
}
|
||||
|
||||
gk_fclose(fpout);
|
||||
}
|
||||
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* kfmetis.c
|
||||
*
|
||||
* This file contains the driving routine for partitioning for
|
||||
* sub-domain direct factorization.
|
||||
*
|
||||
* Started 8/11/02
|
||||
* George
|
||||
*
|
||||
* $Id: kfmetis.c,v 1.2 2002/08/13 16:40:14 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, options[10];
|
||||
idxtype *part;
|
||||
float lbvec[MAXNCON];
|
||||
GraphType graph;
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
ParamType params;
|
||||
double TOTALTmr, METISTmr, IOTmr;
|
||||
|
||||
|
||||
parse_cmdline(¶ms, argc, argv);
|
||||
|
||||
|
||||
if (params.nparts < 2) {
|
||||
mprintf("The number of partitions should be greater than 1!\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, params.filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D, #Parts: %D\n", params.filename, graph.nvtxs, graph.nedges/2, params.nparts);
|
||||
if (graph.ncon > 1)
|
||||
mprintf(" Balancing Constraints: %D\n", graph.ncon);
|
||||
mprintf("\nRecursive Partitioning... -------------------------------------------\n");
|
||||
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
options[0] = 0;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
METIS_PartFillGraph(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &(params.nparts), options, &edgecut, part);
|
||||
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
ComputePartitionBalance(&graph, params.nparts, part, lbvec);
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D, Balance: ", params.nparts, edgecut);
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%5.2f ", lbvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
// WritePartition(params.filename, part, graph.nvtxs, params.nparts);
|
||||
gk_stopcputimer(IOTmr);
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f (PMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Total: \t\t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, &part, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,111 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* kmetis.c
|
||||
*
|
||||
* This file contains the driving routine for kmetis
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: kmetis.c,v 1.6 2003/07/31 16:15:50 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, nparts, options[10];
|
||||
idxtype *part;
|
||||
float rubvec[MAXNCON], lbvec[MAXNCON];
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
double TOTALTmr, METISTmr, IOTmr;
|
||||
|
||||
if (argc != 3) {
|
||||
mprintf("Usage: %s <GraphFile> <Nparts>\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
nparts = atoi(argv[2]);
|
||||
|
||||
if (nparts < 2) {
|
||||
mprintf("The number of partitions should be greater than 1!\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
|
||||
/* The following is for debuging empty graphs...
|
||||
graph.nedges = 0;
|
||||
idxset(graph.nvtxs+1, 0, graph.xadj);
|
||||
*/
|
||||
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D, #Parts: %D\n", filename, graph.nvtxs, graph.nedges/2, nparts);
|
||||
if (graph.ncon > 1)
|
||||
mprintf(" Balancing Constraints: %D\n", graph.ncon);
|
||||
mprintf("\nK-way Partitioning... -----------------------------------------------\n");
|
||||
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
options[0] = 0;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
if (graph.ncon == 1) {
|
||||
METIS_PartGraphKway(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
}
|
||||
else {
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
rubvec[i] = HORIZONTAL_IMBALANCE;
|
||||
|
||||
METIS_mCPartGraphKway(&graph.nvtxs, &graph.ncon, graph.xadj, graph.adjncy, graph.vwgt,
|
||||
graph.adjwgt, &wgtflag, &numflag, &nparts, rubvec, options, &edgecut, part);
|
||||
}
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
ComputePartitionBalance(&graph, nparts, part, lbvec);
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D, Balance: ", nparts, edgecut);
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%5.2f ", lbvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WritePartition(filename, part, graph.nvtxs, nparts);
|
||||
gk_stopcputimer(IOTmr);
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f (KMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Total: \t\t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, &part, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,158 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* mesh2dual.c
|
||||
*
|
||||
* This file reads in the element node connectivity array of a mesh and writes
|
||||
* out its dual in the format suitable for Metis.
|
||||
*
|
||||
* Started 9/29/97
|
||||
* George
|
||||
*
|
||||
* $Id: mesh2dual.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, ne, nn, etype, mtype, cnt, numflag=0;
|
||||
idxtype *elmnts, *xadj, *adjncy, *metype;
|
||||
idxtype *conmat, *elms, *weights;
|
||||
double IOTmr, DUALTmr;
|
||||
char fileout[256], etypestr[5][5] = {"TRI", "TET", "HEX", "QUAD", "LINE"};
|
||||
|
||||
if (argc <2) {
|
||||
mprintf("Usage: %s <meshfile> [confile]\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
|
||||
mtype=MeshType(argv[1]);
|
||||
ne=MixedElements(argv[1]);
|
||||
metype = idxmalloc(ne, "main: metype");
|
||||
weights = idxmalloc(ne, "main: weights");
|
||||
|
||||
if (mtype==1 || mtype==3){
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
if (mtype==1)
|
||||
elmnts = ReadMesh(argv[1], &ne, &nn, &etype);
|
||||
else
|
||||
elmnts = ReadMeshWgt(argv[1], &ne, &nn, &etype, weights);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, etypestr[etype-1]);
|
||||
mprintf("Forming Dual Graph... -----------------------------------------------\n");
|
||||
|
||||
xadj = idxmalloc(ne+1, "main: xadj");
|
||||
elms = idxsmalloc(ne+1, 0, "main: elms");
|
||||
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
cnt=METIS_MeshToDualCount(&ne, &nn, elmnts, elms, &etype, &numflag);
|
||||
adjncy = idxmalloc(cnt+1, "main: adjncy");
|
||||
METIS_MeshToDual(&ne, &nn, elmnts, elms, &etype, &numflag, xadj, adjncy);
|
||||
gk_stopcputimer(DUALTmr);
|
||||
|
||||
mprintf(" Dual Information: #Vertices: %D, #Edges: %D\n", ne, xadj[ne]/2);
|
||||
|
||||
msprintf(fileout, "%s.dgraph", argv[1]);
|
||||
gk_startcputimer(IOTmr);
|
||||
if (mtype==1)
|
||||
WriteGraph(fileout, ne, xadj, adjncy);
|
||||
else
|
||||
WriteWgtGraph(fileout, ne, xadj, adjncy, weights);
|
||||
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Dual Creation:\t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
}
|
||||
|
||||
else {
|
||||
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
|
||||
|
||||
if(mtype==0)
|
||||
elmnts = ReadMixedMesh(argv[1], &ne, &nn, metype);
|
||||
else
|
||||
elmnts = ReadMixedMeshWgt(argv[1], &ne, &nn, metype, weights);
|
||||
|
||||
if (argc==3)
|
||||
conmat = ReadMgcnums(argv[2]);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, "Mixed");
|
||||
mprintf("Forming Dual Graph... ----------------------------------------------\n");
|
||||
|
||||
xadj = idxmalloc(ne+1, "main: xadj");
|
||||
elms = idxsmalloc(ne+1, 0, "main: elms");
|
||||
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
|
||||
if (argc==3){
|
||||
cnt=METIS_MixedMeshToDualCount(&ne, &nn, elmnts, elms, metype, &numflag,
|
||||
conmat, 1);
|
||||
adjncy = idxmalloc(cnt+1, "main: adjncy");
|
||||
METIS_MixedMeshToDual(&ne, &nn, elmnts, elms, metype, &numflag, xadj, adjncy,
|
||||
conmat, 1);
|
||||
}
|
||||
else{
|
||||
cnt=METIS_MixedMeshToDualCount(&ne, &nn, elmnts, elms, metype, &numflag,
|
||||
conmat, 0);
|
||||
adjncy = idxmalloc(cnt+1, "main: adjncy");
|
||||
METIS_MixedMeshToDual(&ne, &nn, elmnts, elms, metype, &numflag, xadj, adjncy, conmat, 0);
|
||||
}
|
||||
gk_stopcputimer(DUALTmr);
|
||||
|
||||
mprintf(" Dual Information: #Vertices: %D, #Edges: %D\n", ne, xadj[ne]/2);
|
||||
|
||||
msprintf(fileout, "%s.dgraph", argv[1]);
|
||||
gk_startcputimer(IOTmr);
|
||||
|
||||
if (mtype==0)
|
||||
WriteGraph(fileout, ne, xadj, adjncy);
|
||||
else
|
||||
WriteWgtGraph(fileout, ne, xadj, adjncy, weights);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Dual Creation:\t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
}
|
||||
|
||||
gk_free((void **)&elmnts, &xadj, &adjncy, &metype, &weights, &elms, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,129 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* mesh2nodal.c
|
||||
*
|
||||
* This file reads in the element node connectivity array of a mesh and writes
|
||||
* out its dual in the format suitable for Metis.
|
||||
*
|
||||
* Started 9/29/97
|
||||
* George
|
||||
*
|
||||
* $Id: mesh2nodal.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, ne, nn, etype, mtype, numflag=0;
|
||||
idxtype *elmnts, *xadj, *adjncy, *metype, *weights;
|
||||
double IOTmr, DUALTmr;
|
||||
char fileout[256], etypestr[5][5] = {"TRI", "TET", "HEX", "QUAD", "LINE"};
|
||||
|
||||
if (argc != 2) {
|
||||
mprintf("Usage: %s <meshfile>\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
mtype=MeshType(argv[1]);
|
||||
ne=MixedElements(argv[1]);
|
||||
metype = idxmalloc(ne, "main: metype");
|
||||
weights = idxmalloc(ne, "main: weights");
|
||||
|
||||
|
||||
if (mtype==1 || mtype==3){
|
||||
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
if (mtype==1)
|
||||
elmnts = ReadMesh(argv[1], &ne, &nn, &etype);
|
||||
else
|
||||
elmnts = ReadMeshWgt(argv[1], &ne, &nn, &etype, weights);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, etypestr[etype-1]);
|
||||
mprintf("Forming Nodal Graph... ----------------------------------------------\n");
|
||||
|
||||
xadj = idxmalloc(nn+1, "main: xadj");
|
||||
adjncy = idxmalloc(20*nn, "main: adjncy");
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
METIS_MeshToNodal(&ne, &nn, elmnts, &etype, &numflag, xadj, adjncy);
|
||||
gk_stopcputimer(DUALTmr);
|
||||
|
||||
mprintf(" Nodal Information: #Vertices: %D, #Edges: %D\n", nn, xadj[nn]/2);
|
||||
|
||||
msprintf(fileout, "%s.ngraph", argv[1]);
|
||||
gk_startcputimer(IOTmr);
|
||||
WriteGraph(fileout, nn, xadj, adjncy);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Nodal Creation:\t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
}
|
||||
|
||||
else{
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
if(mtype==0)
|
||||
elmnts = ReadMixedMesh(argv[1], &ne, &nn, metype);
|
||||
else
|
||||
elmnts = ReadMixedMeshWgt(argv[1], &ne, &nn, metype, weights);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, "Mixed");
|
||||
mprintf("Forming Nodal Graph... ----------------------------------------------\n");
|
||||
|
||||
xadj = idxmalloc(nn+1, "main: xadj");
|
||||
adjncy = idxmalloc(20*nn, "main: adjncy");
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
METIS_MixedMeshToNodal(&ne, &nn, elmnts, metype, &numflag, xadj, adjncy);
|
||||
gk_stopcputimer(DUALTmr);
|
||||
|
||||
mprintf(" Nodal Information: #Vertices: %D, #Edges: %D\n", nn, xadj[nn]/2);
|
||||
|
||||
msprintf(fileout, "%s.ngraph", argv[1]);
|
||||
gk_startcputimer(IOTmr);
|
||||
WriteGraph(fileout, nn, xadj, adjncy);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Nodal Creation:\t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
}
|
||||
|
||||
gk_free((void **)&elmnts, &xadj, &adjncy, &metype, &weights, LTERM);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,196 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* metis.c
|
||||
*
|
||||
* This file contains the driving routine for multilevel method
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: metis.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, nparts, OpType, options[10], nbytes;
|
||||
idxtype *part, *perm, *iperm, *sizes;
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
|
||||
|
||||
if (argc != 11) {
|
||||
mprintf("Usage: %s <GraphFile> <Nparts> <Mtype> <Rtype> <IPtype> <Oflags> <Pfactor> <Nseps> <OPtype> <Options> \n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
nparts = atoi(argv[2]);
|
||||
options[OPTION_CTYPE] = atoi(argv[3]);
|
||||
options[OPTION_RTYPE] = atoi(argv[4]);
|
||||
options[OPTION_ITYPE] = atoi(argv[5]);
|
||||
options[OPTION_OFLAGS] = atoi(argv[6]);
|
||||
options[OPTION_PFACTOR] = atoi(argv[7]);
|
||||
options[OPTION_NSEPS] = atoi(argv[8]);
|
||||
OpType = atoi(argv[9]);
|
||||
options[OPTION_DBGLVL] = atoi(argv[10]);
|
||||
|
||||
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
mprintf("Partitioning a graph with %D vertices and %D edges\n", graph.nvtxs, graph.nedges/2);
|
||||
|
||||
METIS_EstimateMemory(&graph.nvtxs, graph.xadj, graph.adjncy, &numflag, &OpType, &nbytes);
|
||||
mprintf("Metis will need %D Mbytes\n", nbytes/(1024*1024));
|
||||
|
||||
part = perm = iperm = NULL;
|
||||
|
||||
options[0] = 1;
|
||||
switch (OpType) {
|
||||
case OP_PMETIS:
|
||||
mprintf("Recursive Partitioning... ------------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
METIS_PartGraphRecursive(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D\n", nparts, edgecut);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case OP_KMETIS:
|
||||
mprintf("K-way Partitioning... -----------------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
METIS_PartGraphKway(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D\n", nparts, edgecut);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case OP_OEMETIS:
|
||||
gk_free((void **)&graph.vwgt, &graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("Edge-based Nested Dissection Ordering... ----------------------------\n");
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
|
||||
METIS_EdgeND(&graph.nvtxs, graph.xadj, graph.adjncy, &numflag, options, perm, iperm);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, iperm, graph.nvtxs, 0));
|
||||
|
||||
ComputeFillIn(&graph, iperm);
|
||||
|
||||
gk_free((void **)&perm, &iperm, LTERM);
|
||||
break;
|
||||
case OP_ONMETIS:
|
||||
gk_free((void **)&graph.vwgt, &graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("Node-based Nested Dissection Ordering... ----------------------------\n");
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
|
||||
METIS_NodeND(&graph.nvtxs, graph.xadj, graph.adjncy, &numflag, options, perm, iperm);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, iperm, graph.nvtxs, 0));
|
||||
|
||||
ComputeFillIn(&graph, iperm);
|
||||
|
||||
gk_free((void **)&perm, &iperm, LTERM);
|
||||
break;
|
||||
case OP_ONWMETIS:
|
||||
gk_free((void **)&graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("WNode-based Nested Dissection Ordering... ---------------------------\n");
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
|
||||
METIS_NodeWND(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, &numflag, options, perm, iperm);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, iperm, graph.nvtxs, 0));
|
||||
|
||||
ComputeFillIn(&graph, iperm);
|
||||
|
||||
gk_free((void **)&perm, &iperm, LTERM);
|
||||
break;
|
||||
case 6:
|
||||
gk_free((void **)&graph.vwgt, &graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("Node-based Nested Dissection Ordering... ----------------------------\n");
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
sizes = idxmalloc(2*nparts, "main: sizes");
|
||||
|
||||
METIS_NodeNDP(graph.nvtxs, graph.xadj, graph.adjncy, nparts, options, perm, iperm, sizes);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, iperm, graph.nvtxs, 0));
|
||||
|
||||
ComputeFillIn(&graph, iperm);
|
||||
|
||||
for (i=0; i<2*nparts-1; i++)
|
||||
mprintf("%D ", sizes[i]);
|
||||
mprintf("\n");
|
||||
|
||||
gk_free((void **)&perm, &iperm, &sizes, LTERM);
|
||||
break;
|
||||
case 7:
|
||||
mprintf("K-way Vol Partitioning... -------------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
METIS_PartGraphVKway(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, NULL,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Volume: %7D\n", nparts, edgecut);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case 9:
|
||||
mprintf("K-way Partitioning (with vwgts)... ----------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
graph.vwgt = idxmalloc(graph.nvtxs, "main: graph.vwgt");
|
||||
for (i=0; i<graph.nvtxs; i++)
|
||||
graph.vwgt[i] = graph.xadj[i+1]-graph.xadj[i]+1;
|
||||
wgtflag = 2;
|
||||
|
||||
METIS_PartGraphKway(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D\n", nparts, edgecut);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case 10:
|
||||
break;
|
||||
default:
|
||||
errexit("Unknown");
|
||||
}
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* metisbin.h
|
||||
*
|
||||
* This file contains the various header inclusions
|
||||
*
|
||||
* Started 8/9/02
|
||||
* George
|
||||
*/
|
||||
|
||||
#include <GKlib.h>
|
||||
#include <stddef.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
#include <stdio.h>
|
||||
#include <ctype.h>
|
||||
#include <math.h>
|
||||
#include <time.h>
|
||||
#include <string.h>
|
||||
#include <limits.h>
|
||||
#include <signal.h>
|
||||
#include <setjmp.h>
|
||||
#include <assert.h>
|
||||
|
||||
|
||||
#if defined(ENABLE_OPENMP)
|
||||
#include <omp.h>
|
||||
#endif
|
||||
|
||||
|
||||
#include <metis.h>
|
||||
#include "../libmetis/defs.h"
|
||||
#include "../libmetis/struct.h"
|
||||
#include "../libmetis/rename.h"
|
||||
#include "../libmetis/macros.h"
|
||||
#include "../libmetis/proto.h"
|
||||
#include "defs.h"
|
||||
#include "struct.h"
|
||||
#include "proto.h"
|
||||
|
||||
|
||||
#if defined(COMPILER_MSC)
|
||||
#define rint(x) ((idxtype)((x)+0.5)) /* MSC does not have rint() function */
|
||||
#endif
|
||||
|
||||
|
||||
#if defined(COMPILER_GCC)
|
||||
extern char* strdup (const char *);
|
||||
#endif
|
||||
|
||||
@ -0,0 +1,146 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* metis.c
|
||||
*
|
||||
* This file contains the driving routine for multilevel method
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: mmetis.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, nparts, OpType, options[10], nbytes;
|
||||
idxtype *part, *perm, *iperm, *sizes;
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
idxtype *mvwgt, *vwgt, *vsize;
|
||||
float rubvec[MAXNCON];
|
||||
|
||||
|
||||
if (argc < 8) {
|
||||
mprintf("Usage: %s <GraphFile> <Nparts> <Mtype> <Rtype> <IPtype> <OpType> <Options> \n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
nparts = atoi(argv[2]);
|
||||
options[OPTION_CTYPE] = atoi(argv[3]);
|
||||
options[OPTION_RTYPE] = atoi(argv[4]);
|
||||
options[OPTION_ITYPE] = atoi(argv[5]);
|
||||
OpType = atoi(argv[6]);
|
||||
options[OPTION_DBGLVL] = atoi(argv[7]);
|
||||
|
||||
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
mprintf("Partitioning a graph with %D vertices and %D edges. Constraints: %D\n", graph.nvtxs, graph.nedges/2, graph.ncon);
|
||||
|
||||
part = perm = iperm = NULL;
|
||||
vsize = NULL;
|
||||
|
||||
options[0] = 1;
|
||||
switch (OpType) {
|
||||
case OP_PMETIS:
|
||||
mprintf("Recursive Partitioning... ------------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
METIS_mCPartGraphRecursive(&graph.nvtxs, &graph.ncon, graph.xadj, graph.adjncy,
|
||||
graph.vwgt, graph.adjwgt, &wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D\n", nparts, edgecut);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case OP_KMETIS:
|
||||
mprintf("K-way Partitioning... ----------------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
if (argc != 8+graph.ncon)
|
||||
errexit("You must supply %d ub constraints!\n", graph.ncon);
|
||||
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
rubvec[i] = atof(argv[8+i]);
|
||||
|
||||
METIS_mCPartGraphKway(&graph.nvtxs, &graph.ncon, graph.xadj, graph.adjncy, graph.vwgt,
|
||||
graph.adjwgt, &wgtflag, &numflag, &nparts, rubvec, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D \tUBVec: ", nparts, edgecut);
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%.3f ", rubvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
if (options[OPTION_DBGLVL]&1024) {
|
||||
/* Partition each objective separately and see the results */
|
||||
vwgt = idxmalloc(graph.nvtxs, "vwgt");
|
||||
|
||||
for (j=0; j<graph.ncon; j++) {
|
||||
for (i=0; i<graph.nvtxs; i++)
|
||||
vwgt[i] = graph.vwgt[i*graph.ncon+j];
|
||||
|
||||
options[0] = 0;
|
||||
METIS_PartGraphKway(&graph.nvtxs, graph.xadj, graph.adjncy, vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &nparts, options, &edgecut, part);
|
||||
|
||||
mprintf("Partitioning using constrain %D ------------------------------------\n", j);
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
}
|
||||
gk_free((void **)&vwgt, LTERM);
|
||||
}
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
case 3:
|
||||
mprintf("Recursive Partitioning... -----------------------------------------\n");
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
|
||||
if (argc != 8+graph.ncon)
|
||||
errexit("You must supply %d ub constraints!\n", graph.ncon);
|
||||
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
rubvec[i] = atof(argv[8+i]);
|
||||
|
||||
METIS_mCHPartGraphRecursive(&graph.nvtxs, &graph.ncon, graph.xadj, graph.adjncy,
|
||||
graph.vwgt, graph.adjwgt, &wgtflag, &numflag, &nparts, rubvec, options, &edgecut, part);
|
||||
|
||||
IFSET(options[OPTION_DBGLVL], DBG_OUTPUT, WritePartition(filename, part, graph.nvtxs, nparts));
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D \tUBVec: ", nparts, edgecut);
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%.3f ", rubvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
ComputePartitionInfo(&graph, nparts, part);
|
||||
|
||||
gk_free((void **)&part, LTERM);
|
||||
break;
|
||||
default:
|
||||
errexit("Unknown");
|
||||
}
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* oemetis.c
|
||||
*
|
||||
* This file contains the driving routine for multilevel method
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: oemetis.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, options[10];
|
||||
idxtype *perm, *iperm;
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype numflag = 0, wgtflag;
|
||||
double TOTALTmr, METISTmr, IOTmr, SMBTmr;
|
||||
|
||||
|
||||
if (argc != 2) {
|
||||
mprintf("Usage: %s <GraphFile>\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(SMBTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
if (graph.ncon != 1) {
|
||||
mprintf("Ordering can only be applied to graphs with one constraint.\n");
|
||||
exit(0);
|
||||
}
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
/* Ordering does not use weights! */
|
||||
gk_free((void **)&graph.vwgt, &graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D\n\n", filename, graph.nvtxs, graph.nedges/2);
|
||||
mprintf("Edge-Based Ordering... ----------------------------------------------\n");
|
||||
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
options[0] = 0;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
METIS_EdgeND(&graph.nvtxs, graph.xadj, graph.adjncy, &numflag, options, perm, iperm);
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WritePermutation(filename, iperm, graph.nvtxs);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(SMBTmr);
|
||||
ComputeFillIn(&graph, iperm);
|
||||
gk_stopcputimer(SMBTmr);
|
||||
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Ordering: \t %7.3f (OEMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Symbolic Factorization: \t %7.3f\n", gk_getcputimer(SMBTmr));
|
||||
mprintf(" Total: \t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &perm, &iperm, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* onmetis.c
|
||||
*
|
||||
* This file contains the driving routine for multilevel method
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: onmetis.c,v 1.2 2002/08/10 06:02:53 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, options[10];
|
||||
idxtype *perm, *iperm;
|
||||
GraphType graph;
|
||||
char filename[256];
|
||||
idxtype numflag = 0, wgtflag;
|
||||
double TOTALTmr, METISTmr, IOTmr, SMBTmr;
|
||||
|
||||
|
||||
if (argc != 2) {
|
||||
mprintf("Usage: %s <GraphFile>\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
strcpy(filename, argv[1]);
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(SMBTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
if (graph.ncon != 1) {
|
||||
mprintf("Ordering can only be applied to graphs with one constraint.\n");
|
||||
exit(0);
|
||||
}
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
/* Ordering does not use weights! */
|
||||
gk_free((void **)&graph.vwgt, &graph.adjwgt, LTERM);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D\n\n", filename, graph.nvtxs, graph.nedges/2);
|
||||
mprintf("Node-Based Ordering... ----------------------------------------------\n");
|
||||
|
||||
perm = idxmalloc(graph.nvtxs, "main: perm");
|
||||
iperm = idxmalloc(graph.nvtxs, "main: iperm");
|
||||
options[0] = 0;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
METIS_NodeND(&graph.nvtxs, graph.xadj, graph.adjncy, &numflag, options, perm, iperm);
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WritePermutation(filename, iperm, graph.nvtxs);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(SMBTmr);
|
||||
ComputeFillIn(&graph, iperm);
|
||||
gk_stopcputimer(SMBTmr);
|
||||
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Ordering: \t %7.3f (ONMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Symbolic Factorization: \t %7.3f\n", gk_getcputimer(SMBTmr));
|
||||
mprintf(" Total: \t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &perm, &iperm, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,122 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* partdmesh.c
|
||||
*
|
||||
* This file reads in the element node connectivity array of a mesh and
|
||||
* partitions both the elements and the nodes using KMETIS on the dual graph.
|
||||
*
|
||||
* Started 9/29/97
|
||||
* George
|
||||
*
|
||||
* $Id: partdmesh.c,v 1.2 2002/08/10 06:02:54 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, ne, nn, etype, mtype, numflag=0, nparts, edgecut, custom=0;
|
||||
idxtype *elmnts, *epart, *npart, *metype, *conmat, *weights;
|
||||
double IOTmr, DUALTmr;
|
||||
char etypestr[5][5] = {"TRI", "TET", "HEX", "QUAD", "LINE"};
|
||||
GraphType graph;
|
||||
|
||||
if (argc < 3) {
|
||||
mprintf("Usage: %s <meshfile> <nparts> [confile]\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
nparts = atoi(argv[2]);
|
||||
if (nparts < 2) {
|
||||
mprintf("nparts must be greater than one.\n");
|
||||
exit(0);
|
||||
}
|
||||
mtype=MeshType(argv[1]);
|
||||
ne=MixedElements(argv[1]);
|
||||
metype = idxmalloc(ne, "main: metype");
|
||||
weights = idxmalloc(ne, "main: weights");
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
|
||||
if(mtype==1)
|
||||
elmnts = ReadMesh(argv[1], &ne, &nn, &etype);
|
||||
else if(mtype==3)
|
||||
elmnts = ReadMeshWgt(argv[1], &ne, &nn, &etype, weights);
|
||||
else if(mtype==0)
|
||||
elmnts = ReadMixedMesh(argv[1], &ne, &nn, metype);
|
||||
else
|
||||
elmnts = ReadMixedMeshWgt(argv[1], &ne, &nn, metype, weights);
|
||||
|
||||
|
||||
if (argc==4){
|
||||
conmat = ReadMgcnums(argv[2]);
|
||||
custom=1;
|
||||
}
|
||||
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
epart = idxmalloc(ne, "main: epart");
|
||||
npart = idxmalloc(nn, "main: npart");
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
if (mtype==1)
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, etypestr[etype-1]);
|
||||
else
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, "Mixed");
|
||||
mprintf("Partitioning Dual Graph... ------------------------------------------\n");
|
||||
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
if (mtype==1)
|
||||
METIS_PartMeshDual(&ne, &nn, elmnts, &etype, &numflag, &nparts, &edgecut, epart, npart, 0, NULL);
|
||||
else if (mtype==3)
|
||||
METIS_PartMeshDual(&ne, &nn, elmnts, &etype, &numflag, &nparts, &edgecut, epart, npart, 2, weights);
|
||||
else if (mtype==0)
|
||||
METIS_PartMixedMeshDual(&ne, &nn, elmnts, metype, &numflag, &nparts, &edgecut, epart, npart, conmat, custom, 0, NULL);
|
||||
else
|
||||
METIS_PartMixedMeshDual(&ne, &nn, elmnts, metype, &numflag, &nparts, &edgecut, epart, npart, conmat, custom, 2, weights);
|
||||
|
||||
gk_stopcputimer(DUALTmr);
|
||||
mprintf(" %D-way Edge-Cut: %7D, Balance: %5.2f\n", nparts, edgecut, ComputeElementBalance(ne, nparts, epart));
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WriteMeshPartition(argv[1], nparts, ne, epart, nn, npart);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
/*
|
||||
graph.nvtxs = nn;
|
||||
graph.xadj = idxmalloc(nn+1, "xadj");
|
||||
graph.vwgt = idxsmalloc(nn, 1, "vwgt");
|
||||
graph.adjncy = idxmalloc(20*nn, "adjncy");
|
||||
graph.adjwgt = idxsmalloc(20*nn, 1, "adjncy");
|
||||
|
||||
METIS_MeshToNodal(&ne, &nn, elmnts, &etype, &numflag, graph.xadj, graph.adjncy);
|
||||
|
||||
ComputePartitionInfo(&graph, nparts, npart);
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, LTERM);
|
||||
*/
|
||||
|
||||
gk_free((void **)&elmnts, &epart, &npart, &metype, &weights, LTERM);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,117 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* partnmesh.c
|
||||
*
|
||||
* This file reads in the element node connectivity array of a mesh and
|
||||
* partitions both the elements and the nodes using KMETIS on the dual graph.
|
||||
*
|
||||
* Started 9/29/97
|
||||
* George
|
||||
*
|
||||
* $Id: partnmesh.c,v 1.2 2002/08/10 06:02:54 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, j, ne, nn, etype, mtype, numflag=0, nparts, edgecut;
|
||||
idxtype *elmnts, *epart, *npart, *metype, *weights;
|
||||
double IOTmr, DUALTmr;
|
||||
char etypestr[5][5] = {"TRI", "TET", "HEX", "QUAD", "LINE"};
|
||||
GraphType graph;
|
||||
|
||||
if (argc != 3) {
|
||||
mprintf("Usage: %s <meshfile> <nparts>\n",argv[0]);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
nparts = atoi(argv[2]);
|
||||
if (nparts < 2) {
|
||||
mprintf("nparts must be greater than one.\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_clearcputimer(IOTmr);
|
||||
gk_clearcputimer(DUALTmr);
|
||||
|
||||
mtype=MeshType(argv[1]);
|
||||
ne=MixedElements(argv[1]);
|
||||
metype = idxmalloc(ne, "main: metype");
|
||||
weights = idxmalloc(ne, "main: weights");
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
|
||||
if(mtype==1)
|
||||
elmnts = ReadMesh(argv[1], &ne, &nn, &etype);
|
||||
else if(mtype==3)
|
||||
elmnts = ReadMeshWgt(argv[1], &ne, &nn, &etype, weights);
|
||||
else if(mtype==0)
|
||||
elmnts = ReadMixedMesh(argv[1], &ne, &nn, metype);
|
||||
else
|
||||
elmnts = ReadMixedMeshWgt(argv[1], &ne, &nn, metype, weights);
|
||||
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
epart = idxmalloc(ne, "main: epart");
|
||||
npart = idxmalloc(nn, "main: npart");
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Mesh Information ----------------------------------------------------\n");
|
||||
if (mtype==1)
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, etypestr[etype-1]);
|
||||
else
|
||||
mprintf(" Name: %s, #Elements: %D, #Nodes: %D, Etype: %s\n\n", argv[1], ne, nn, "Mixed");
|
||||
mprintf("Partitioning Nodal Graph... -----------------------------------------\n");
|
||||
|
||||
|
||||
gk_startcputimer(DUALTmr);
|
||||
|
||||
if (mtype==1 || mtype==3)
|
||||
METIS_PartMeshNodal(&ne, &nn, elmnts, &etype, &numflag, &nparts, &edgecut, epart, npart);
|
||||
else
|
||||
METIS_PartMixedMeshNodal(&ne, &nn, elmnts, metype, &numflag, &nparts, &edgecut, epart, npart);
|
||||
|
||||
gk_stopcputimer(DUALTmr);
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D, Balance: %5.2f\n", nparts, edgecut, ComputeElementBalance(ne, nparts, epart));
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WriteMeshPartition(argv[1], nparts, ne, epart, nn, npart);
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f\n", gk_getcputimer(DUALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
/*
|
||||
graph.nvtxs = ne;
|
||||
graph.xadj = idxmalloc(ne+1, "xadj");
|
||||
graph.vwgt = idxsmalloc(ne, 1, "vwgt");
|
||||
graph.adjncy = idxmalloc(10*ne, "adjncy");
|
||||
graph.adjwgt = idxsmalloc(10*ne, 1, "adjncy");
|
||||
|
||||
METIS_MeshToDual(&ne, &nn, elmnts, &etype, &numflag, graph.xadj, graph.adjncy);
|
||||
|
||||
ComputePartitionInfo(&graph, nparts, epart);
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, LTERM);
|
||||
*/
|
||||
|
||||
gk_free((void **)&elmnts, &epart, &npart, &metype, &weights, LTERM);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,105 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* pmetis.c
|
||||
*
|
||||
* This file contains the driving routine for multilevel method
|
||||
*
|
||||
* Started 8/28/94
|
||||
* George
|
||||
*
|
||||
* $Id: pmetis.c,v 1.3 2002/08/10 06:57:51 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* Let the game begin
|
||||
**************************************************************************/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
idxtype i, options[10];
|
||||
idxtype *part;
|
||||
float lbvec[MAXNCON];
|
||||
GraphType graph;
|
||||
idxtype numflag = 0, wgtflag = 0, edgecut;
|
||||
ParamType params;
|
||||
double TOTALTmr, METISTmr, IOTmr;
|
||||
|
||||
|
||||
parse_cmdline(¶ms, argc, argv);
|
||||
|
||||
|
||||
if (params.nparts < 2) {
|
||||
mprintf("The number of partitions should be greater than 1!\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
gk_clearcputimer(TOTALTmr);
|
||||
gk_clearcputimer(METISTmr);
|
||||
gk_clearcputimer(IOTmr);
|
||||
|
||||
gk_startcputimer(TOTALTmr);
|
||||
gk_startcputimer(IOTmr);
|
||||
ReadGraph(&graph, params.filename, &wgtflag);
|
||||
if (graph.nvtxs <= 0) {
|
||||
mprintf("Empty graph. Nothing to do.\n");
|
||||
exit(0);
|
||||
}
|
||||
gk_stopcputimer(IOTmr);
|
||||
|
||||
mprintf("**********************************************************************\n");
|
||||
mprintf("%s", METISTITLE);
|
||||
mprintf("Graph Information ---------------------------------------------------\n");
|
||||
mprintf(" Name: %s, #Vertices: %D, #Edges: %D, #Parts: %D\n", params.filename, graph.nvtxs, graph.nedges/2, params.nparts);
|
||||
if (graph.ncon > 1)
|
||||
mprintf(" Balancing Constraints: %D\n", graph.ncon);
|
||||
mprintf("\nRecursive Partitioning... -------------------------------------------\n");
|
||||
|
||||
part = idxmalloc(graph.nvtxs, "main: part");
|
||||
options[0] = 0;
|
||||
options[0] = 1;
|
||||
options[OPTION_CTYPE] = params.mtype;
|
||||
options[OPTION_ITYPE] = params.itype;
|
||||
options[OPTION_RTYPE] = params.rtype;
|
||||
options[OPTION_DBGLVL] = params.dbglvl;
|
||||
|
||||
gk_startcputimer(METISTmr);
|
||||
if (graph.ncon == 1) {
|
||||
METIS_PartGraphRecursive(&graph.nvtxs, graph.xadj, graph.adjncy, graph.vwgt, graph.adjwgt,
|
||||
&wgtflag, &numflag, &(params.nparts), options, &edgecut, part);
|
||||
}
|
||||
else {
|
||||
METIS_mCPartGraphRecursive(&graph.nvtxs, &graph.ncon, graph.xadj, graph.adjncy, graph.vwgt,
|
||||
graph.adjwgt, &wgtflag, &numflag, &(params.nparts), options, &edgecut, part);
|
||||
}
|
||||
|
||||
gk_stopcputimer(METISTmr);
|
||||
|
||||
ComputePartitionBalance(&graph, params.nparts, part, lbvec);
|
||||
|
||||
mprintf(" %D-way Edge-Cut: %7D, Balance: ", params.nparts, edgecut);
|
||||
for (i=0; i<graph.ncon; i++)
|
||||
mprintf("%5.2f ", lbvec[i]);
|
||||
mprintf("\n");
|
||||
|
||||
|
||||
gk_startcputimer(IOTmr);
|
||||
WritePartition(params.filename, part, graph.nvtxs, params.nparts);
|
||||
gk_stopcputimer(IOTmr);
|
||||
gk_stopcputimer(TOTALTmr);
|
||||
|
||||
mprintf("\nTiming Information --------------------------------------------------\n");
|
||||
mprintf(" I/O: \t\t %7.3f\n", gk_getcputimer(IOTmr));
|
||||
mprintf(" Partitioning: \t\t %7.3f (PMETIS time)\n", gk_getcputimer(METISTmr));
|
||||
mprintf(" Total: \t\t %7.3f\n", gk_getcputimer(TOTALTmr));
|
||||
mprintf("**********************************************************************\n");
|
||||
|
||||
|
||||
gk_free((void **)&graph.xadj, &graph.adjncy, &graph.vwgt, &graph.adjwgt, &part, LTERM);
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,47 @@
|
||||
/*
|
||||
* proto.h
|
||||
*
|
||||
* This file contains function prototypes
|
||||
*
|
||||
* Started 11/1/99
|
||||
* George
|
||||
*
|
||||
* $Id: proto.h,v 1.15 2003/04/04 23:22:49 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef _PROTOBIN_H_
|
||||
#define _PROTOBIN_H_
|
||||
|
||||
|
||||
/* io.c */
|
||||
void ReadGraph(GraphType *, char *, idxtype *);
|
||||
void ReadCoordinates(GraphType *, char *);
|
||||
void WritePartition(char *, idxtype *, idxtype, idxtype);
|
||||
void WriteMeshPartition(char *, idxtype, idxtype, idxtype *, idxtype, idxtype *);
|
||||
void WritePermutation(char *, idxtype *, idxtype);
|
||||
int CheckGraph(GraphType *);
|
||||
int MeshType(char *);
|
||||
idxtype *ReadWgt(char *, idxtype *, idxtype *, idxtype *);
|
||||
idxtype *ReadMesh(char *, idxtype *, idxtype *, idxtype *);
|
||||
idxtype *ReadMeshWgt(char *, idxtype *, idxtype *, idxtype *, idxtype *);
|
||||
idxtype *ReadMixedMesh(char *, idxtype *, idxtype *, idxtype *);
|
||||
idxtype *ReadMixedMeshWgt(char *, idxtype *, idxtype *, idxtype *, idxtype *);
|
||||
void WriteGraph(char *, idxtype, idxtype *, idxtype *);
|
||||
idxtype MixedElements(char *);
|
||||
idxtype *ReadMgcnums(char *);
|
||||
void WriteWgtGraph(char *, idxtype , idxtype *, idxtype *, idxtype *);
|
||||
|
||||
|
||||
/* smbfactor.c */
|
||||
void ComputeFillIn(GraphType *, idxtype *);
|
||||
idxtype ComputeFillIn2(GraphType *, idxtype *);
|
||||
idxtype smbfct(idxtype, idxtype *, idxtype *, idxtype *, idxtype *, idxtype *, idxtype *, idxtype *, idxtype *, idxtype *);
|
||||
|
||||
/* cmdline.c */
|
||||
void parse_cmdline(ParamType *params, int argc, char *argv[]);
|
||||
|
||||
|
||||
/* cpmetis.c */
|
||||
|
||||
#endif
|
||||
@ -0,0 +1,385 @@
|
||||
/*
|
||||
* Copyright 1997, Regents of the University of Minnesota
|
||||
*
|
||||
* smbfactor.c
|
||||
*
|
||||
* This file performs the symbolic factorization of a matrix
|
||||
*
|
||||
* Started 8/1/97
|
||||
* George
|
||||
*
|
||||
* $Id: smbfactor.c,v 1.2 2002/08/10 06:02:55 karypis Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
#include <metisbin.h>
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function sets up data structures for fill-in computations
|
||||
**************************************************************************/
|
||||
void ComputeFillIn(GraphType *graph, idxtype *iperm)
|
||||
{
|
||||
idxtype i, j, k, nvtxs, maxlnz, maxsub;
|
||||
idxtype *xadj, *adjncy;
|
||||
idxtype *perm, *xlnz, *xnzsub, *nzsub;
|
||||
double opc;
|
||||
|
||||
/*
|
||||
mprintf("\nSymbolic factorization... --------------------------------------------\n");
|
||||
*/
|
||||
|
||||
nvtxs = graph->nvtxs;
|
||||
xadj = graph->xadj;
|
||||
adjncy = graph->adjncy;
|
||||
|
||||
maxsub = 4*xadj[nvtxs];
|
||||
|
||||
/* Relabel the vertices so that it starts from 1 */
|
||||
k = xadj[nvtxs];
|
||||
for (i=0; i<k; i++)
|
||||
adjncy[i]++;
|
||||
for (i=0; i<nvtxs+1; i++)
|
||||
xadj[i]++;
|
||||
|
||||
/* Allocate the required memory */
|
||||
perm = idxmalloc(nvtxs+1, "ComputeFillIn: perm");
|
||||
xlnz = idxmalloc(nvtxs+1, "ComputeFillIn: xlnz");
|
||||
xnzsub = idxmalloc(nvtxs+1, "ComputeFillIn: xnzsub");
|
||||
nzsub = idxmalloc(maxsub, "ComputeFillIn: nzsub");
|
||||
|
||||
/* Construct perm from iperm and change the numbering of iperm */
|
||||
for (i=0; i<nvtxs; i++)
|
||||
perm[iperm[i]] = i;
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
iperm[i]++;
|
||||
perm[i]++;
|
||||
}
|
||||
|
||||
/*
|
||||
* Call sparspak routine.
|
||||
*/
|
||||
if (smbfct(nvtxs, xadj, adjncy, perm, iperm, xlnz, &maxlnz, xnzsub, nzsub, &maxsub)) {
|
||||
gk_free((void **)&nzsub, LTERM);
|
||||
|
||||
maxsub = 4*maxsub;
|
||||
nzsub = idxmalloc(maxsub, "ComputeFillIn: nzsub");
|
||||
if (smbfct(nvtxs, xadj, adjncy, perm, iperm, xlnz, &maxlnz, xnzsub, nzsub, &maxsub))
|
||||
errexit("MAXSUB is too small!");
|
||||
}
|
||||
|
||||
opc = 0;
|
||||
for (i=0; i<nvtxs; i++)
|
||||
xlnz[i]--;
|
||||
for (i=0; i<nvtxs; i++)
|
||||
opc += (xlnz[i+1]-xlnz[i])*(xlnz[i+1]-xlnz[i]) - (xlnz[i+1]-xlnz[i]);
|
||||
|
||||
mprintf(" Nonzeros: %D, \tOperation Count: %6.4le\n", maxlnz, opc);
|
||||
|
||||
|
||||
gk_free((void **)&perm, &xlnz, &xnzsub, &nzsub, LTERM);
|
||||
|
||||
|
||||
/* Relabel the vertices so that it starts from 0 */
|
||||
for (i=0; i<nvtxs; i++)
|
||||
iperm[i]--;
|
||||
for (i=0; i<nvtxs+1; i++)
|
||||
xadj[i]--;
|
||||
k = xadj[nvtxs];
|
||||
for (i=0; i<k; i++)
|
||||
adjncy[i]--;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This function sets up data structures for fill-in computations
|
||||
**************************************************************************/
|
||||
idxtype ComputeFillIn2(GraphType *graph, idxtype *iperm)
|
||||
{
|
||||
idxtype i, j, k, nvtxs, maxlnz, maxsub;
|
||||
idxtype *xadj, *adjncy;
|
||||
idxtype *perm, *xlnz, *xnzsub, *nzsub;
|
||||
double opc;
|
||||
|
||||
nvtxs = graph->nvtxs;
|
||||
xadj = graph->xadj;
|
||||
adjncy = graph->adjncy;
|
||||
|
||||
maxsub = 4*xadj[nvtxs];
|
||||
|
||||
/* Relabel the vertices so that it starts from 1 */
|
||||
k = xadj[nvtxs];
|
||||
for (i=0; i<k; i++)
|
||||
adjncy[i]++;
|
||||
for (i=0; i<nvtxs+1; i++)
|
||||
xadj[i]++;
|
||||
|
||||
/* Allocate the required memory */
|
||||
perm = idxmalloc(nvtxs+1, "ComputeFillIn: perm");
|
||||
xlnz = idxmalloc(nvtxs+1, "ComputeFillIn: xlnz");
|
||||
xnzsub = idxmalloc(nvtxs+1, "ComputeFillIn: xnzsub");
|
||||
nzsub = idxmalloc(maxsub, "ComputeFillIn: nzsub");
|
||||
|
||||
/* Construct perm from iperm and change the numbering of iperm */
|
||||
for (i=0; i<nvtxs; i++)
|
||||
perm[iperm[i]] = i;
|
||||
for (i=0; i<nvtxs; i++) {
|
||||
iperm[i]++;
|
||||
perm[i]++;
|
||||
}
|
||||
|
||||
/*
|
||||
* Call sparspak routine.
|
||||
*/
|
||||
if (smbfct(nvtxs, xadj, adjncy, perm, iperm, xlnz, &maxlnz, xnzsub, nzsub, &maxsub)) {
|
||||
gk_free((void **)&nzsub, LTERM);
|
||||
|
||||
maxsub = 4*maxsub;
|
||||
nzsub = idxmalloc(maxsub, "ComputeFillIn: nzsub");
|
||||
if (smbfct(nvtxs, xadj, adjncy, perm, iperm, xlnz, &maxlnz, xnzsub, nzsub, &maxsub))
|
||||
errexit("MAXSUB is too small!");
|
||||
}
|
||||
|
||||
opc = 0;
|
||||
for (i=0; i<nvtxs; i++)
|
||||
xlnz[i]--;
|
||||
for (i=0; i<nvtxs; i++)
|
||||
opc += (xlnz[i+1]-xlnz[i])*(xlnz[i+1]-xlnz[i]) - (xlnz[i+1]-xlnz[i]);
|
||||
|
||||
|
||||
gk_free((void **)&perm, &xlnz, &xnzsub, &nzsub, LTERM);
|
||||
|
||||
|
||||
/* Relabel the vertices so that it starts from 0 */
|
||||
for (i=0; i<nvtxs; i++)
|
||||
iperm[i]--;
|
||||
for (i=0; i<nvtxs+1; i++)
|
||||
xadj[i]--;
|
||||
k = xadj[nvtxs];
|
||||
for (i=0; i<k; i++)
|
||||
adjncy[i]--;
|
||||
|
||||
return maxlnz;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/*****************************************************************
|
||||
********** SMBFCT ..... SYMBOLIC FACTORIZATION *********
|
||||
******************************************************************
|
||||
* PURPOSE - THIS ROUTINE PERFORMS SYMBOLIC FACTORIZATION
|
||||
* ON A PERMUTED LINEAR SYSTEM AND IT ALSO SETS UP THE
|
||||
* COMPRESSED DATA STRUCTURE FOR THE SYSTEM.
|
||||
*
|
||||
* INPUT PARAMETERS -
|
||||
* NEQNS - NUMBER OF EQUATIONS.
|
||||
* (XADJ, ADJNCY) - THE ADJACENCY STRUCTURE.
|
||||
* (PERM, INVP) - THE PERMUTATION VECTOR AND ITS INVERSE.
|
||||
*
|
||||
* UPDATED PARAMETERS -
|
||||
* MAXSUB - SIZE OF THE SUBSCRIPT ARRAY NZSUB. ON RETURN,
|
||||
* IT CONTAINS THE NUMBER OF SUBSCRIPTS USED
|
||||
*
|
||||
* OUTPUT PARAMETERS -
|
||||
* XLNZ - INDEX INTO THE NONZERO STORAGE VECTOR LNZ.
|
||||
* (XNZSUB, NZSUB) - THE COMPRESSED SUBSCRIPT VECTORS.
|
||||
* MAXLNZ - THE NUMBER OF NONZEROS FOUND.
|
||||
*
|
||||
*******************************************************************/
|
||||
idxtype smbfct(idxtype neqns, idxtype *xadj, idxtype *adjncy, idxtype *perm, idxtype *invp,
|
||||
idxtype *xlnz, idxtype *maxlnz, idxtype *xnzsub, idxtype *nzsub, idxtype *maxsub)
|
||||
{
|
||||
/* Local variables */
|
||||
idxtype node, rchm, mrgk, lmax, i, j, k, m, nabor, nzbeg, nzend;
|
||||
idxtype kxsub, jstop, jstrt, mrkflg, inz, knz, flag;
|
||||
idxtype *mrglnk, *marker, *rchlnk;
|
||||
|
||||
rchlnk = idxmalloc(neqns+1, "smbfct: rchlnk");
|
||||
marker = idxsmalloc(neqns+1, 0, "smbfct: marker");
|
||||
mrglnk = idxsmalloc(neqns+1, 0, "smbfct: mgrlnk");
|
||||
|
||||
/* Parameter adjustments */
|
||||
--marker;
|
||||
--mrglnk;
|
||||
--rchlnk;
|
||||
--nzsub;
|
||||
--xnzsub;
|
||||
--xlnz;
|
||||
--invp;
|
||||
--perm;
|
||||
--adjncy;
|
||||
--xadj;
|
||||
|
||||
/* Function Body */
|
||||
flag = 0;
|
||||
nzbeg = 1;
|
||||
nzend = 0;
|
||||
xlnz[1] = 1;
|
||||
|
||||
/* FOR EACH COLUMN KNZ COUNTS THE NUMBER OF NONZEROS IN COLUMN K ACCUMULATED IN RCHLNK. */
|
||||
for (k = 1; k <= neqns; ++k) {
|
||||
knz = 0;
|
||||
mrgk = mrglnk[k];
|
||||
mrkflg = 0;
|
||||
marker[k] = k;
|
||||
if (mrgk != 0)
|
||||
marker[k] = marker[mrgk];
|
||||
xnzsub[k] = nzend;
|
||||
node = perm[k];
|
||||
|
||||
if (xadj[node] >= xadj[node+1]) {
|
||||
xlnz[k+1] = xlnz[k];
|
||||
continue;
|
||||
}
|
||||
|
||||
/* USE RCHLNK TO LINK THROUGH THE STRUCTURE OF A(*,K) BELOW DIAGONAL */
|
||||
rchlnk[k] = neqns+1;
|
||||
for (j=xadj[node]; j<xadj[node+1]; j++) {
|
||||
nabor = invp[adjncy[j]];
|
||||
if (nabor <= k)
|
||||
continue;
|
||||
rchm = k;
|
||||
|
||||
do {
|
||||
m = rchm;
|
||||
rchm = rchlnk[m];
|
||||
} while (rchm <= nabor);
|
||||
|
||||
knz++;
|
||||
rchlnk[m] = nabor;
|
||||
rchlnk[nabor] = rchm;
|
||||
if (marker[nabor] != marker[k])
|
||||
mrkflg = 1;
|
||||
}
|
||||
|
||||
/* TEST FOR MASS SYMBOLIC ELIMINATION */
|
||||
lmax = 0;
|
||||
if (mrkflg != 0 || mrgk == 0 || mrglnk[mrgk] != 0)
|
||||
goto L350;
|
||||
xnzsub[k] = xnzsub[mrgk] + 1;
|
||||
knz = xlnz[mrgk + 1] - (xlnz[mrgk] + 1);
|
||||
goto L1400;
|
||||
|
||||
|
||||
/* LINK THROUGH EACH COLUMN I THAT AFFECTS L(*,K) */
|
||||
L350:
|
||||
i = k;
|
||||
while ((i = mrglnk[i]) != 0) {
|
||||
inz = xlnz[i+1] - (xlnz[i]+1);
|
||||
jstrt = xnzsub[i] + 1;
|
||||
jstop = xnzsub[i] + inz;
|
||||
|
||||
if (inz > lmax) {
|
||||
lmax = inz;
|
||||
xnzsub[k] = jstrt;
|
||||
}
|
||||
|
||||
/* MERGE STRUCTURE OF L(*,I) IN NZSUB INTO RCHLNK. */
|
||||
rchm = k;
|
||||
for (j = jstrt; j <= jstop; ++j) {
|
||||
nabor = nzsub[j];
|
||||
do {
|
||||
m = rchm;
|
||||
rchm = rchlnk[m];
|
||||
} while (rchm < nabor);
|
||||
|
||||
if (rchm != nabor) {
|
||||
knz++;
|
||||
rchlnk[m] = nabor;
|
||||
rchlnk[nabor] = rchm;
|
||||
rchm = nabor;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* CHECK IF SUBSCRIPTS DUPLICATE THOSE OF ANOTHER COLUMN */
|
||||
if (knz == lmax)
|
||||
goto L1400;
|
||||
|
||||
/* OR IF TAIL OF K-1ST COLUMN MATCHES HEAD OF KTH */
|
||||
if (nzbeg > nzend)
|
||||
goto L1200;
|
||||
|
||||
i = rchlnk[k];
|
||||
for (jstrt = nzbeg; jstrt <= nzend; ++jstrt) {
|
||||
if (nzsub[jstrt] < i)
|
||||
continue;
|
||||
|
||||
if (nzsub[jstrt] == i)
|
||||
goto L1000;
|
||||
else
|
||||
goto L1200;
|
||||
}
|
||||
goto L1200;
|
||||
|
||||
L1000:
|
||||
xnzsub[k] = jstrt;
|
||||
for (j = jstrt; j <= nzend; ++j) {
|
||||
if (nzsub[j] != i)
|
||||
goto L1200;
|
||||
|
||||
i = rchlnk[i];
|
||||
if (i > neqns)
|
||||
goto L1400;
|
||||
}
|
||||
nzend = jstrt - 1;
|
||||
|
||||
/* COPY THE STRUCTURE OF L(*,K) FROM RCHLNK TO THE DATA STRUCTURE (XNZSUB, NZSUB) */
|
||||
L1200:
|
||||
nzbeg = nzend + 1;
|
||||
nzend += knz;
|
||||
|
||||
if (nzend > *maxsub) {
|
||||
flag = 1; /* Out of memory */
|
||||
break;
|
||||
}
|
||||
|
||||
i = k;
|
||||
for (j=nzbeg; j<=nzend; ++j) {
|
||||
i = rchlnk[i];
|
||||
nzsub[j] = i;
|
||||
marker[i] = k;
|
||||
}
|
||||
xnzsub[k] = nzbeg;
|
||||
marker[k] = k;
|
||||
|
||||
/*
|
||||
* UPDATE THE VECTOR MRGLNK. NOTE COLUMN L(*,K) JUST FOUND
|
||||
* IS REQUIRED TO DETERMINE COLUMN L(*,J), WHERE
|
||||
* L(J,K) IS THE FIRST NONZERO IN L(*,K) BELOW DIAGONAL.
|
||||
*/
|
||||
L1400:
|
||||
if (knz > 1) {
|
||||
kxsub = xnzsub[k];
|
||||
i = nzsub[kxsub];
|
||||
mrglnk[k] = mrglnk[i];
|
||||
mrglnk[i] = k;
|
||||
}
|
||||
|
||||
xlnz[k + 1] = xlnz[k] + knz;
|
||||
}
|
||||
|
||||
if (flag == 0) {
|
||||
*maxlnz = xlnz[neqns] - 1;
|
||||
*maxsub = xnzsub[neqns];
|
||||
xnzsub[neqns + 1] = xnzsub[neqns];
|
||||
}
|
||||
|
||||
marker++;
|
||||
mrglnk++;
|
||||
rchlnk++;
|
||||
nzsub++;
|
||||
xnzsub++;
|
||||
xlnz++;
|
||||
invp++;
|
||||
perm++;
|
||||
adjncy++;
|
||||
xadj++;
|
||||
gk_free((void **)&rchlnk, &mrglnk, &marker, LTERM);
|
||||
|
||||
return flag;
|
||||
|
||||
}
|
||||
|
||||
@ -0,0 +1,54 @@
|
||||
/*
|
||||
* struct.h
|
||||
*
|
||||
* This file contains data structures for the various programs of METIS.
|
||||
*
|
||||
* Started 8/9/02
|
||||
* George
|
||||
*
|
||||
* $Id: struct.h,v 1.8 2003/04/04 23:22:50 karypis Exp $
|
||||
*/
|
||||
|
||||
#ifndef _STRUCTBIN_H_
|
||||
#define _STRUCTBIN_H_
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* The following data structure implements a string-2-idxtype mapping
|
||||
* table used for parsing command-line options
|
||||
**************************************************************************/
|
||||
typedef struct {
|
||||
char *name;
|
||||
idxtype id;
|
||||
} StringMapType;
|
||||
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
* This data structure stores the various command line arguments
|
||||
**************************************************************************/
|
||||
typedef struct {
|
||||
idxtype mtype;
|
||||
idxtype itype;
|
||||
idxtype rtype;
|
||||
|
||||
idxtype balance;
|
||||
idxtype ntrials;
|
||||
idxtype niter;
|
||||
|
||||
idxtype seed;
|
||||
idxtype dbglvl;
|
||||
|
||||
idxtype nparts;
|
||||
|
||||
char *filename;
|
||||
char *xyzfilename;
|
||||
char *tpwgts;
|
||||
|
||||
float iotimer;
|
||||
float clustertimer;
|
||||
float reporttimer;
|
||||
} ParamType;
|
||||
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user