Trisurf Monte Carlo simulator
Samo Penic
2013-11-23 50f10f120936a429dc450f58a40951fa5d59458a
Somewhat evolved paralelism.
7 files modified
99 ■■■■■ changed files
src/general.h 1 ●●●● patch | view | raw | blame | history
src/io.c 13 ●●●●● patch | view | raw | blame | history
src/taint_test.c 4 ●●●● patch | view | raw | blame | history
src/tape 2 ●●● patch | view | raw | blame | history
src/timestep.c 74 ●●●● patch | view | raw | blame | history
src/timestep.h 4 ●●● patch | view | raw | blame | history
src/vertexmove.c 1 ●●●● patch | view | raw | blame | history
src/general.h
@@ -239,6 +239,7 @@
    ts_double cm[3];
    ts_double volume;
    ts_spharm *sphHarmonics;
    ts_uint threads;
} ts_vesicle;
src/io.c
@@ -297,7 +297,8 @@
ts_vesicle *parsetape(ts_uint *mcsweeps, ts_uint *inititer, ts_uint *iterations){
    long int nshell=17,ncxmax=60, ncymax=60, nczmax=60;  // THIS IS DUE TO CONFUSE BUG!
    char *buf=malloc(255*sizeof(char));
    long int brezveze0=1;
    buf[0]=0;
    long int smps=1;
    long int brezveze1=1;
    long int brezveze2=1;
    ts_double xk0=25.0, dmax=1.67,stepsize=0.15;
@@ -314,8 +315,8 @@
    CFG_SIMPLE_INT("mcsweeps",&mcsw),
    CFG_SIMPLE_INT("inititer", &init),
        CFG_SIMPLE_BOOL("quiet",&quiet),
        CFG_SIMPLE_STR("multiprocessing",buf),
        CFG_SIMPLE_INT("smp_cores",&brezveze0),
        CFG_SIMPLE_STR("multiprocessing",&buf),
        CFG_SIMPLE_INT("smp_cores",&smps),
        CFG_SIMPLE_INT("cluster_nodes",&brezveze1),
        CFG_SIMPLE_INT("distributed_processes",&brezveze2),
        CFG_END()
@@ -343,7 +344,11 @@
    vesicle->clist->ncmax[1]=ncymax;
    vesicle->clist->ncmax[2]=nczmax;
    vesicle->clist->max_occupancy=8;
    if(strcmp(buf,"smp")==0){
    vesicle->threads=smps;
    } else {
    vesicle->threads=1;
    }
    cfg_free(cfg);
    free(buf);
  //  fprintf(stderr,"NSHELL=%u\n",vesicle->nshell);
src/taint_test.c
@@ -25,7 +25,7 @@
for(i=0;i<vesicle->vlist->n;i++){
    vertex_taint(vesicle->vlist->vtx[i],1);
    vertex_untaint(vesicle->vlist->vtx[i],1);
    printf("%d taint level %d\n",i,vesicle->vlist->vtx[i]->locked);
    printf("%d taint amount %d\n",i,vesicle->vlist->vtx[i]->locked);
    if(vertex_tainted(vesicle->vlist->vtx[i], 0, 1)) printf("Ooops, Main  %d is tainted!\n",i);
    for(j=0;j<vesicle->vlist->vtx[i]->neigh_no;j++){
        if(vertex_tainted(vesicle->vlist->vtx[i]->neigh[j], 0, 1)){
@@ -37,7 +37,7 @@
}
printf("At the end you should see no Ooopses and all taint levels should be 0!\n");
printf("At the end you should see no Ooopses and all taint amounts should be 0!\n");
vesicle_free(vesicle);
return 0;
}
src/tape
@@ -29,7 +29,7 @@
#what type of multiprocessing? (*none, smp, cluster, distributed, cuda, auto)
#currently only none makes sense.
multiprocessing=none
multiprocessing=smp
#how many cores are allowed to process in SMP?
smp_cores=2
#how many nodes in cluster?
src/timestep.c
@@ -13,42 +13,36 @@
#include "io.h"
ts_bool run_simulation(ts_vesicle *vesicle, ts_uint mcsweeps, ts_uint inititer, ts_uint iterations){
    ts_uint i, j;
    ts_uint i, j,k ;
    centermass(vesicle);
    cell_occupation(vesicle);
    ts_fprintf(stdout, "Starting simulation (first %d x %d MC sweeps will not be recorded on disk)\n", inititer, mcsweeps);
    pthread_t tid1,tid2, tid3, tid4;
    thdata data1, data2, data3, data4;
    pthread_mutex_t mutex;
    data1.thread_no=0;
    data2.thread_no=1;
    data1.vesicle=vesicle;
    data2.vesicle=vesicle;
           data3.thread_no=2;
    data4.thread_no=3;
    data3.vesicle=vesicle;
    data4.vesicle=vesicle;
    ts_fprintf(stdout, "Starting %d threads\n",vesicle->threads);
    data1.vtx_tainting_lock=&mutex;
    data2.vtx_tainting_lock=&mutex;
    data3.vtx_tainting_lock=&mutex;
    data4.vtx_tainting_lock=&mutex;
    pthread_t *tid=(pthread_t *)malloc(sizeof(pthread_t)*vesicle->threads);
    thdata *data=(thdata *)malloc(sizeof(thdata)*vesicle->threads);
    pthread_mutex_t mutex_taint, mutex_untaint;
    pthread_mutex_init(&mutex_taint,NULL);
    pthread_mutex_init(&mutex_untaint,NULL);
    pthread_mutex_init(&mutex,NULL);
    for(i=0;i<vesicle->threads;i++){
        data[i].thread_no=i;
        data[i].vesicle=vesicle;
        data[i].threads=vesicle->threads;
        data[i].vtx_tainting_lock=&mutex_taint;
        data[i].vtx_untainting_lock=&mutex_untaint;
    }
     for(i=0;i<inititer+iterations;i++){
        for(j=0;j<mcsweeps;j++){
            pthread_create(&tid1,NULL,single_timestep,(void *)&data1);
                pthread_create(&tid2,NULL,single_timestep,(void *)&data2);
                pthread_create(&tid3,NULL,single_timestep,(void *)&data3);
                pthread_create(&tid4,NULL,single_timestep,(void *)&data4);
                pthread_join(tid1,NULL);
                pthread_join(tid2,NULL);
                pthread_join(tid3,NULL);
                pthread_join(tid4,NULL);
//    single_timestep(vesicle);
            for(k=0;k<vesicle->threads;k++){
                pthread_create(&tid[k], NULL, single_timestep, (void *)&data[k]);
            }
            for(k=0;k<vesicle->threads;k++){
                    pthread_join(tid[k],NULL);
            }
        //    single_timestep(vesicle);
        }
        centermass(vesicle);
        cell_occupation(vesicle);
@@ -57,7 +51,8 @@
        }
    }
    pthread_mutex_destroy(&mutex);
    pthread_mutex_destroy(&mutex_taint);
    pthread_mutex_destroy(&mutex_untaint);
    pthread_exit(NULL);
    return TS_SUCCESS;
}
@@ -67,15 +62,16 @@
    data=(thdata *)thread_data;
    ts_vesicle *vesicle=data->vesicle;
    ts_uint thID=data->thread_no;
    ts_uint partition_size=(ts_uint)(vesicle->vlist->n/4);
    ts_uint partition_size=(ts_uint)(vesicle->vlist->n/data->threads);
    ts_uint end;
    if(thID==3){
    if(thID==data->threads-1){
        end=vesicle->vlist->n;
    } else {
        end=(thID+1)*partition_size;
    }
    ts_double rnvec[3];
    ts_uint i; //b;
    ts_uint i,j; //b;
//    ts_fprintf(stdout,"Thread thID=%d report for duty. My vtxes are in range from %d to %d.\n",thID,thID*partition_size, end-1);
    for(i=thID*partition_size;i<end;i++){
        rnvec[0]=drand48();
        rnvec[1]=drand48();
@@ -84,15 +80,25 @@
    /**** THREAD IS POTENTIALLY LOCKED ******/
    pthread_mutex_lock(data->vtx_tainting_lock); //taint if no other process is tainting or wait until you can taint
    //    ts_fprintf(stdout, "thID=%d:: Tainting vertex %d, level=%d. Waiting....\n",thID, i, vesicle->vlist->vtx[i]->locked);
    while(vertex_tainted(vesicle->vlist->vtx[i],1,1)){
        ts_fprintf(stdout, "thID=%d:: Vertex %d is tainted, so I cannot try vertexmove. Level=%d. WAITING!\n",thID, i, vesicle->vlist->vtx[i]->locked);
        ts_fprintf(stdout, "thID=%d:: Vertex %d is tainted, so I cannot try vertexmove. Level=%d. BU(H)TELJ!\n   neigh. vtxs: ",thID, i, vesicle->vlist->vtx[i]->locked);
        for(j=0; j<vesicle->vlist->vtx[i]->neigh_no; j++){
            ts_fprintf(stdout, "%d ", vesicle->vlist->vtx[i]->neigh[j]->idx);
        }
        ts_fprintf(stdout, ".\n");
    }
    vertex_taint(vesicle->vlist->vtx[i],1);
    pthread_mutex_lock(data->vtx_untainting_lock);
    vertex_taint(vesicle->vlist->vtx[i],2);
    pthread_mutex_unlock(data->vtx_untainting_lock);
    pthread_mutex_unlock(data->vtx_tainting_lock);
    /**** THREAD IS RELEASING MUTEX RESOURCES ******/
        single_verticle_timestep(vesicle,vesicle->vlist->vtx[i],rnvec);
    vertex_untaint(vesicle->vlist->vtx[i],1);
    pthread_mutex_lock(data->vtx_untainting_lock);
    vertex_untaint(vesicle->vlist->vtx[i],2);
    pthread_mutex_unlock(data->vtx_untainting_lock);
//        ts_fprintf(stdout, "Vertex %d should be untainted, level=%d.\n", i, vesicle->vlist->vtx[i]->locked);
    }
src/timestep.h
@@ -4,9 +4,11 @@
typedef struct str_thdata
{
    int thread_no;
    ts_uint thread_no;
    ts_uint threads;
    ts_vesicle *vesicle;
    pthread_mutex_t *vtx_tainting_lock;
    pthread_mutex_t *vtx_untainting_lock;
} thdata;
src/vertexmove.c
@@ -108,6 +108,7 @@
    }
    
    //update the normals of triangles that share bead i.
    //TODO: check if we could backup that too?
   for(i=0;i<vtx->tristar_no;i++) triangle_normal_vector(vtx->tristar[i]);
    return TS_FAIL;