00001
00050 #include "apbscfg.h"
00051
00052 #if defined(HAVE_MC_H)
00053 #include "apbs/vcsm.h"
00054
00055
00056 #if !defined(VINLINE_VCSM)
00057
00058 VPUBLIC Valist* Vcsm_getValist(Vcsm *thee) {
00059
00060 VASSERT(thee != VNULL);
00061 return thee->alist;
00062
00063 }
00064
00065 VPUBLIC int Vcsm_getNumberAtoms(Vcsm *thee, int isimp) {
00066
00067 VASSERT(thee != VNULL);
00068 VASSERT(thee->initFlag);
00069 return thee->nsqm[isimp];
00070
00071 }
00072
00073 VPUBLIC Vatom* Vcsm_getAtom(Vcsm *thee, int iatom, int isimp) {
00074
00075
00076 VASSERT(thee != VNULL);
00077 VASSERT(thee->initFlag);
00078
00079 VASSERT(iatom < (thee->nsqm)[isimp]);
00080 return Valist_getAtom(thee->alist, (thee->sqm)[isimp][iatom]);
00081
00082 }
00083
00084 VPUBLIC int Vcsm_getAtomIndex(Vcsm *thee, int iatom, int isimp) {
00085
00086
00087 VASSERT(thee != VNULL);
00088 VASSERT(thee->initFlag);
00089
00090 VASSERT(iatom < (thee->nsqm)[isimp]);
00091 return (thee->sqm)[isimp][iatom];
00092
00093 }
00094
00095 VPUBLIC int Vcsm_getNumberSimplices(Vcsm *thee, int iatom) {
00096
00097
00098 VASSERT(thee != VNULL);
00099 VASSERT(thee->initFlag);
00100
00101 return (thee->nqsm)[iatom];
00102
00103 }
00104
00105 VPUBLIC SS* Vcsm_getSimplex(Vcsm *thee, int isimp, int iatom) {
00106
00107
00108 VASSERT(thee != VNULL);
00109 VASSERT(thee->initFlag);
00110
00111 return Gem_SS(thee->gm, (thee->qsm)[iatom][isimp]);
00112
00113 }
00114
00115 VPUBLIC int Vcsm_getSimplexIndex(Vcsm *thee, int isimp, int iatom) {
00116
00117
00118 VASSERT(thee != VNULL);
00119 VASSERT(thee->initFlag);
00120
00121 return (thee->qsm)[iatom][isimp];
00122
00123 }
00124
00125 VPUBLIC unsigned long int Vcsm_memChk(Vcsm *thee) {
00126 if (thee == VNULL) return 0;
00127 return Vmem_bytes(thee->vmem);
00128 }
00129
00130 #endif
00131
00132 VPUBLIC Vcsm* Vcsm_ctor(Valist *alist, Gem *gm) {
00133
00134
00135 Vcsm *thee = VNULL;
00136 thee = Vmem_malloc(VNULL, 1, sizeof(Vcsm) );
00137 VASSERT( thee != VNULL);
00138 VASSERT( Vcsm_ctor2(thee, alist, gm));
00139
00140 return thee;
00141 }
00142
00143 VPUBLIC int Vcsm_ctor2(Vcsm *thee, Valist *alist, Gem *gm) {
00144
00145 VASSERT( thee != VNULL );
00146
00147
00148 thee->vmem = Vmem_ctor("APBS:VCSM");
00149
00150
00151 if( alist == VNULL) {
00152 Vnm_print(2,"Vcsm_ctor2: got null pointer to Valist object!\n");
00153 return 0;
00154 }
00155 thee->alist = alist;
00156 if( gm == VNULL) {
00157 Vnm_print(2,"Vcsm_ctor2: got a null pointer to the Gem object!\n");
00158 return 0;
00159 }
00160 thee->gm = gm;
00161
00162 thee->initFlag = 0;
00163 return 1;
00164 }
00165
00166 VPUBLIC void Vcsm_init(Vcsm *thee) {
00167
00168
00169 int iatom, jatom, isimp, jsimp, gotSimp;
00170
00171 Vatom *atom;
00172 double *position;
00173
00174 SS *simplex;
00175
00176
00177 if (thee == VNULL) {
00178 Vnm_print(2, "Vcsm_init: Error! Got NULL thee!\n");
00179 VASSERT(0);
00180 }
00181 if (thee->gm == VNULL) {
00182 VASSERT(thee->gm != VNULL);
00183 Vnm_print(2, "Vcsm_init: Error! Got NULL thee->gm!\n");
00184 VASSERT(0);
00185 }
00186 thee->nsimp = Gem_numSS(thee->gm);
00187 if (thee->nsimp <= 0) {
00188 Vnm_print(2, "Vcsm_init: Error! Got %d simplices!\n", thee->nsimp);
00189 VASSERT(0);
00190 }
00191 thee->natom = Valist_getNumberAtoms(thee->alist);
00192
00193
00194
00195 thee->sqm = Vmem_malloc(thee->vmem, thee->nsimp, sizeof(int *));
00196 VASSERT(thee->sqm != VNULL);
00197 thee->nsqm = Vmem_malloc(thee->vmem, thee->nsimp, sizeof(int));
00198 VASSERT(thee->nsqm != VNULL);
00199 for (isimp=0; isimp<thee->nsimp; isimp++) (thee->nsqm)[isimp] = 0;
00200
00201
00202 for (iatom=0; iatom<thee->natom; iatom++) {
00203 atom = Valist_getAtom(thee->alist, iatom);
00204 position = Vatom_getPosition(atom);
00205 gotSimp = 0;
00206 for (isimp=0; isimp<thee->nsimp; isimp++) {
00207 simplex = Gem_SS(thee->gm, isimp);
00208 if (Gem_pointInSimplex(thee->gm, simplex, position)) {
00209 (thee->nsqm)[isimp]++;
00210 gotSimp = 1;
00211 }
00212 }
00213 }
00214
00215
00216 for (isimp=0; isimp<thee->nsimp; isimp++) {
00217 if ((thee->nsqm)[isimp] > 0) {
00218 thee->sqm[isimp] = Vmem_malloc(thee->vmem, (thee->nsqm)[isimp],
00219 sizeof(int));
00220 VASSERT(thee->sqm[isimp] != VNULL);
00221 }
00222 }
00223
00224
00225 for (isimp=0; isimp<thee->nsimp; isimp++) {
00226 jsimp = 0;
00227 simplex = Gem_SS(thee->gm, isimp);
00228 for (iatom=0; iatom<thee->natom; iatom++) {
00229 atom = Valist_getAtom(thee->alist, iatom);
00230 position = Vatom_getPosition(atom);
00231
00232 if (Gem_pointInSimplex(thee->gm, simplex, position)) {
00233
00234 (thee->sqm)[isimp][jsimp] = iatom;
00235 jsimp++;
00236 }
00237 }
00238 }
00239
00240 thee->msimp = thee->nsimp;
00241
00242
00243 thee->qsm = Vmem_malloc(thee->vmem, thee->natom, sizeof(int *));
00244 VASSERT(thee->qsm != VNULL);
00245 thee->nqsm = Vmem_malloc(thee->vmem, thee->natom, sizeof(int));
00246 VASSERT(thee->nqsm != VNULL);
00247 for (iatom=0; iatom<thee->natom; iatom++) (thee->nqsm)[iatom] = 0;
00248
00249
00250 for (isimp=0; isimp<thee->nsimp; isimp++) {
00251 for (iatom=0; iatom<thee->nsqm[isimp]; iatom++) {
00252 jatom = thee->sqm[isimp][iatom];
00253 thee->nqsm[jatom]++;
00254 }
00255 }
00256
00257
00258 for (iatom=0; iatom<thee->natom; iatom++) {
00259 if (thee->nqsm[iatom] == 0) {
00260 Vnm_print(2, "Vcsm_init: Atom %d not placed in simplex!\n", iatom);
00261 VASSERT(0);
00262 }
00263 }
00264
00265
00266 for (iatom=0; iatom<thee->natom; iatom++) {
00267 thee->qsm[iatom] = Vmem_malloc(thee->vmem, (thee->nqsm)[iatom],
00268 sizeof(int));
00269 VASSERT(thee->qsm[iatom] != VNULL);
00270 thee->nqsm[iatom] = 0;
00271 }
00272
00273 for (isimp=0; isimp<thee->nsimp; isimp++) {
00274 for (iatom=0; iatom<thee->nsqm[isimp]; iatom++) {
00275 jatom = thee->sqm[isimp][iatom];
00276 thee->qsm[jatom][thee->nqsm[jatom]] = isimp;
00277 thee->nqsm[jatom]++;
00278 }
00279 }
00280
00281 thee->initFlag = 1;
00282 }
00283
00284 VPUBLIC void Vcsm_dtor(Vcsm **thee) {
00285 if ((*thee) != VNULL) {
00286 Vcsm_dtor2(*thee);
00287 Vmem_free(VNULL, 1, sizeof(Vcsm), (void **)thee);
00288 (*thee) = VNULL;
00289 }
00290 }
00291
00292 VPUBLIC void Vcsm_dtor2(Vcsm *thee) {
00293 int i;
00294
00295 if ((thee != VNULL) && thee->initFlag) {
00296
00297 for (i=0; i<thee->msimp; i++) {
00298 if (thee->nsqm[i] > 0) Vmem_free(thee->vmem, thee->nsqm[i],
00299 sizeof(int), (void **)&(thee->sqm[i]));
00300 }
00301 for (i=0; i<thee->natom; i++) {
00302 if (thee->nqsm[i] > 0) Vmem_free(thee->vmem, thee->nqsm[i],
00303 sizeof(int), (void **)&(thee->qsm[i]));
00304 }
00305 Vmem_free(thee->vmem, thee->msimp, sizeof(int *),
00306 (void **)&(thee->sqm));
00307 Vmem_free(thee->vmem, thee->msimp, sizeof(int),
00308 (void **)&(thee->nsqm));
00309 Vmem_free(thee->vmem, thee->natom, sizeof(int *),
00310 (void **)&(thee->qsm));
00311 Vmem_free(thee->vmem, thee->natom, sizeof(int),
00312 (void **)&(thee->nqsm));
00313
00314 }
00315 Vmem_dtor(&(thee->vmem));
00316 }
00317
00318 VPUBLIC int Vcsm_update(Vcsm *thee, SS **simps, int num) {
00319
00320
00321 int isimp, jsimp, iatom, jatom, atomID, simpID;
00322 int nsimps, gotMem;
00323
00324 Vatom *atom;
00325 SS *simplex;
00326 double *position;
00327
00328 int *qParent, nqParent;
00329 int **sqmNew, *nsqmNew;
00330 int *affAtoms, nAffAtoms;
00331 int *dnqsm, *nqsmNew, **qsmNew;
00332
00333 VASSERT(thee != VNULL);
00334 VASSERT(thee->initFlag);
00335
00336
00337
00338 isimp = thee->nsimp + num - 1;
00339 gotMem = 0;
00340 while (!gotMem) {
00341 if (isimp > thee->msimp) {
00342 isimp = 2 * isimp;
00343 thee->nsqm = Vmem_realloc(thee->vmem, thee->msimp, sizeof(int),
00344 (void **)&(thee->nsqm), isimp);
00345 VASSERT(thee->nsqm != VNULL);
00346 thee->sqm = Vmem_realloc(thee->vmem, thee->msimp, sizeof(int *),
00347 (void **)&(thee->sqm), isimp);
00348 VASSERT(thee->sqm != VNULL);
00349 thee->msimp = isimp;
00350 } else gotMem = 1;
00351 }
00352
00353 for (isimp = thee->nsimp; isimp<thee->nsimp+num-1 ; isimp++) {
00354 thee->nsqm[isimp] = 0;
00355 }
00356
00357 thee->nsimp = thee->nsimp + num - 1;
00358
00359
00360
00361 isimp = SS_id(simps[0]);
00362 if (thee->nsqm[isimp] == 0) {
00363 for (isimp=1; isimp<num; isimp++) {
00364 thee->nsqm[SS_id(simps[isimp])] = 0;
00365 }
00366 return 1;
00367 }
00368
00369
00370
00371 isimp = SS_id(simps[0]);
00372 nqParent = thee->nsqm[isimp];
00373 qParent = thee->sqm[isimp];
00374
00375 sqmNew = Vmem_malloc(thee->vmem, num, sizeof(int *));
00376 VASSERT(sqmNew != VNULL);
00377 nsqmNew = Vmem_malloc(thee->vmem, num, sizeof(int));
00378 VASSERT(nsqmNew != VNULL);
00379 for (isimp=0; isimp<num; isimp++) nsqmNew[isimp] = 0;
00380
00381
00382
00383 for (iatom=0; iatom<nqParent; iatom++) {
00384
00385 atomID = qParent[iatom];
00386 atom = Valist_getAtom(thee->alist, atomID);
00387 position = Vatom_getPosition(atom);
00388 nsimps = 0;
00389
00390 jsimp = 0;
00391
00392 for (isimp=0; isimp<num; isimp++) {
00393 simplex = simps[isimp];
00394 if (Gem_pointInSimplex(thee->gm, simplex, position)) {
00395 nsqmNew[isimp]++;
00396 jsimp = 1;
00397 }
00398 }
00399
00400 VASSERT(jsimp != 0);
00401 }
00402
00403
00404 iatom = 0;
00405 for (isimp=0; isimp<num; isimp++) iatom += nsqmNew[isimp];
00406 if (iatom < nqParent) {
00407 Vnm_print(2,"Vcsm_update: Lost %d (of %d) atoms!\n",
00408 nqParent - iatom, nqParent);
00409 VASSERT(0);
00410 }
00411
00412
00413 for (isimp=0; isimp<num; isimp++) {
00414 if (nsqmNew[isimp] > 0) {
00415 sqmNew[isimp] = Vmem_malloc(thee->vmem, nsqmNew[isimp],
00416 sizeof(int));
00417 VASSERT(sqmNew[isimp] != VNULL);
00418 }
00419 }
00420
00421
00422 for (isimp=0; isimp<num; isimp++) {
00423
00424 jsimp = 0;
00425 simplex = simps[isimp];
00426
00427
00428 for (iatom=0; iatom<nqParent; iatom++) {
00429
00430 atomID = qParent[iatom];
00431 atom = Valist_getAtom(thee->alist, atomID);
00432 position = Vatom_getPosition(atom);
00433 if (Gem_pointInSimplex(thee->gm, simplex, position)) {
00434 sqmNew[isimp][jsimp] = atomID;
00435 jsimp++;
00436 }
00437 }
00438 }
00439
00440
00441
00442
00443 affAtoms = thee->sqm[SS_id(simps[0])];
00444 nAffAtoms = thee->nsqm[SS_id(simps[0])];
00445
00446
00447
00448
00449
00450 dnqsm = Vmem_malloc(thee->vmem, nAffAtoms, sizeof(int));
00451 VASSERT(dnqsm != VNULL);
00452 nqsmNew = Vmem_malloc(thee->vmem, nAffAtoms, sizeof(int));
00453 VASSERT(nqsmNew != VNULL);
00454 qsmNew = Vmem_malloc(thee->vmem, nAffAtoms, sizeof(int*));
00455 VASSERT(qsmNew != VNULL);
00456 for (iatom=0; iatom<nAffAtoms; iatom++) {
00457 dnqsm[iatom] = -1;
00458 atomID = affAtoms[iatom];
00459 for (isimp=0; isimp<num; isimp++) {
00460 for (jatom=0; jatom<nsqmNew[isimp]; jatom++) {
00461 if (sqmNew[isimp][jatom] == atomID) dnqsm[iatom]++;
00462 }
00463 }
00464 VASSERT(dnqsm[iatom] > -1);
00465 }
00466
00467 for (iatom=0;iatom<nAffAtoms; iatom++) {
00468 atomID = affAtoms[iatom];
00469 qsmNew[iatom] = Vmem_malloc(thee->vmem,
00470 (dnqsm[iatom] + thee->nqsm[atomID]),
00471 sizeof(int));
00472 nqsmNew[iatom] = 0;
00473 VASSERT(qsmNew[iatom] != VNULL);
00474 }
00475
00476
00477 for (isimp=0; isimp<num; isimp++) {
00478 simpID = SS_id(simps[isimp]);
00479 for (iatom=0; iatom<nsqmNew[isimp]; iatom++) {
00480 atomID = sqmNew[isimp][iatom];
00481 for (jatom=0; jatom<nAffAtoms; jatom++) {
00482 if (atomID == affAtoms[jatom]) break;
00483 }
00484 if (jatom < nAffAtoms) {
00485 qsmNew[jatom][nqsmNew[jatom]] = simpID;
00486 nqsmNew[jatom]++;
00487 }
00488 }
00489 }
00490
00491 for (iatom=0; iatom<nAffAtoms; iatom++) {
00492 atomID = affAtoms[iatom];
00493 for (isimp=0; isimp<thee->nqsm[atomID]; isimp++) {
00494 for (jsimp=0; jsimp<num; jsimp++) {
00495 simpID = SS_id(simps[jsimp]);
00496 if (thee->qsm[atomID][isimp] == simpID) break;
00497 }
00498 if (jsimp == num) {
00499 qsmNew[iatom][nqsmNew[iatom]] = thee->qsm[atomID][isimp];
00500 nqsmNew[iatom]++;
00501 }
00502 }
00503 }
00504
00505
00506
00507 for (iatom=0; iatom<nAffAtoms; iatom++) {
00508 atomID = affAtoms[iatom];
00509 Vmem_free(thee->vmem, thee->nqsm[atomID], sizeof(int),
00510 (void **)&(thee->qsm[atomID]));
00511 thee->qsm[atomID] = qsmNew[iatom];
00512 thee->nqsm[atomID] = nqsmNew[iatom];
00513 }
00514 for (isimp=0; isimp<num; isimp++) {
00515 simpID = SS_id(simps[isimp]);
00516 if (thee->nsqm[simpID] > 0) Vmem_free(thee->vmem, thee->nsqm[simpID],
00517 sizeof(int), (void **)&(thee->sqm[simpID]));
00518 thee->sqm[simpID] = sqmNew[isimp];
00519 thee->nsqm[simpID] = nsqmNew[isimp];
00520 }
00521
00522 Vmem_free(thee->vmem, num, sizeof(int *), (void **)&sqmNew);
00523 Vmem_free(thee->vmem, num, sizeof(int), (void **)&nsqmNew);
00524 Vmem_free(thee->vmem, nAffAtoms, sizeof(int *), (void **)&qsmNew);
00525 Vmem_free(thee->vmem, nAffAtoms, sizeof(int), (void **)&nqsmNew);
00526 Vmem_free(thee->vmem, nAffAtoms, sizeof(int), (void **)&dnqsm);
00527
00528
00529 return 1;
00530
00531
00532 }
00533
00534 #endif