88818e8ea36bf0ebc53f44b7bfbb60c4fd0ba358
[physik/nlsop.git] / nlsop.c
1 /*
2  * nlsop.c 
3  *
4  * author: frank zirkelbach (frank.zirkelbach@physik.uni-augsburg.de)
5  *
6  * this program tries helping to understand the amorphous depuration
7  * and recrystallization of SiCx while ion implantation at temperatures
8  * below 400 degree celsius.
9  * hopefully the program will simulate the stabilization of the
10  * selforganizing lamella structure in the observed behaviour.
11  *
12  * refs: 
13  *  - J. K. N. Lindner. Habil.Schrift, Universitaet Augsburg.
14  *  - Maik Haeberlen. Diplomarbeit, Universitaet Augsburg.
15  *
16  * Copyright (C) 2004 Frank Zirkelbach
17  *
18  * This program is free software; you can redistribute it and/or modify
19  * it under the terms of the GNU General Public License as published by
20  * the Free Software Foundation; either version 2 of the License, or
21  * (at your option) any later version.
22  *
23  * This program is distributed in the hope that it will be useful,
24  * but WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
26  * GNU General Public License for more details.
27  *
28  * You should have received a copy of the GNU General Public License
29  * along with this program; if not, write to the Free Software
30  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
31  *
32  */
33
34 #define _GNU_SOURCE
35 #include <stdio.h>
36 #include <stdlib.h>
37 #include <string.h>
38 #include <sys/types.h>
39 #include <sys/stat.h>
40 #include <fcntl.h>
41 #include <unistd.h>
42
43 #include "nlsop.h"
44
45 #include "dfbapi.h"
46 #include "random.h"
47
48 #define MAKE_AMORPH(N) *(N)|=AMORPH
49 #define MAKE_CRYST(N) *(N)&=~AMORPH
50
51 int usage(void)
52 {
53  puts("usage:");
54  puts("-h \t\t help");
55  puts("-n \t\t no user interaction");
56  puts("-Z \t\t cryst -> amorph c diffusion in z direction");
57  puts("-i \t\t no cryst to cryst diffusion");
58  printf("-x <value> \t # x cells (default %d)\n",_X);
59  printf("-y <value> \t # y cells (default %d)\n",_Y);
60  printf("-z <value> \t # z cells (default %d)\n",_Z);
61  printf("-s <value> \t steps (default %d)\n",STEPS);
62  printf("-d <value> \t refresh display (default %d)\n",REFRESH);
63  printf("-r <value> \t amorphous influence range (default %d)\n",RANGE);
64  printf("-f <value> \t stress induced amorphization influence (default %f)\n",S_D);
65  printf("-p <value> \t ballistic amorphization influence (default %f)\n",B_D);
66  printf("-F <value> \t carbon induced amorphization influence (default %f)\n",C_D);
67  printf("-D <value> \t diffusion rate from cryst to amorph cells (default %f)\n",DR_AC);
68  printf("-e <value> \t do diffusion every <value> steps (default %d)\n",DIFF_RATE);
69  puts("-g <file> <step> continue simulation from file and step (step > 0)!");
70  printf("-W <value> \t write every <value> steps to save file (default %d)\n",RESAVE);
71  puts("-C <file> \t convert file to gnuplot format");
72  puts("-L <file> \t load from file");
73  puts("-S <file> \t save to file");
74  puts("-R <file> \t read from random file");
75  puts("-P <file> \t specify implantation profile file");
76  puts("-N <file> \t specify nuclear energy loss profile file");
77  printf("-H <value> \t collisions per ion in simulation window (default %d)\n",CPI);
78  printf("-m <value> \t number of ion hits sputtering 3nm (default %d)\n",S_RATE);
79  
80  return 1;
81 }
82
83 int sputter(d3_lattice *d3_l)
84 {
85  int i,size;
86  int offh,offl;
87
88  size=d3_l->max_x*d3_l->max_y;
89  offl=0;
90  offh=size;
91
92  for(i=0;i<d3_l->max_z-1;i++)
93  {
94   memcpy(d3_l->status+offl,d3_l->status+offh,size);
95   memcpy(d3_l->extra+offl,d3_l->extra+offh,size*sizeof(int));
96   offl=offh;
97   offh+=size;
98  }
99  memset(d3_l->status+offl,0,size);
100  memset(d3_l->extra+offl,0,size);
101
102  return 1;
103 }
104
105 int process_cell(d3_lattice *d3_l,u32 x,u32 y,u32 z,info *my_info,u32 nel_z)
106 {
107  unsigned char *thiz;
108  int *conc;
109  int i,j;
110  int off;
111  double p,q;
112
113  thiz=d3_l->status+x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
114  conc=d3_l->extra+x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
115  p=my_info->b*nel_z;
116  for(i=-(my_info->range);i<=my_info->range;i++)
117  {
118   for(j=-(my_info->range);j<=my_info->range;j++)
119   {
120    if(!(i==0 && j==0))
121    {
122     off=((x+d3_l->max_x+i)%d3_l->max_x)+((y+d3_l->max_y+j)%d3_l->max_x)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
123     if(*(d3_l->status+off)&AMORPH) p+=my_info->s*(*(d3_l->extra+off))*URAND_MAX/(i*i+j*j);
124    } 
125   }
126  }
127  p+=*conc*my_info->c*URAND_MAX;
128  if(!(*thiz&AMORPH))
129  {
130   if(get_rand(URAND_MAX)<=p) MAKE_AMORPH(thiz);
131  } else
132  {
133   /* assume 1-p probability */
134   /* also look for neighbours ! */
135   q=(URAND_MAX-p)>0?URAND_MAX-p:0;
136   j=0;
137   j+=(*(d3_l->status+((x+d3_l->max_x+1)%d3_l->max_x)+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
138   j+=(*(d3_l->status+((x+d3_l->max_x-1)%d3_l->max_x)+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
139   j+=(*(d3_l->status+x+((y+1+d3_l->max_y)%d3_l->max_y)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
140   j+=(*(d3_l->status+x+((y-1+d3_l->max_y)%d3_l->max_y)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
141   j+=(*(d3_l->status+x+y*d3_l->max_x+((z+1+d3_l->max_z)%d3_l->max_z)*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
142   j+=(*(d3_l->status+x+y*d3_l->max_x+((z-1+d3_l->max_z)%d3_l->max_z)*d3_l->max_x*d3_l->max_y)&AMORPH)?1:0;
143
144   p+=((q/6)*j);
145   if(get_rand(URAND_MAX)>p) MAKE_CRYST(thiz);
146  }
147  
148  return 1;
149 }
150
151 int distrib_c(d3_lattice *d3_l,info *my_info,int step,u32 rj_m,u32 *rj_g)
152 {
153  u32 x,y,z;
154  int i,j,k,c;
155  int offset,off;
156  int carry;
157
158  /* put one c ion somewhere in the lattice */
159  x=get_rand(d3_l->max_x);
160  y=get_rand(d3_l->max_y);
161  z=get_rand_reject(d3_l->max_z,rj_m,rj_g);
162  *(d3_l->extra+x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)+=1;
163  (my_info->cc)++;
164
165  if(step%my_info->diff_rate==0)
166  {
167
168  for(i=0;i<d3_l->max_x;i++)
169  {
170   for(j=0;j<d3_l->max_y;j++)
171   {
172    for(k=0;k<d3_l->max_z;k++)
173    {
174     offset=i+j*d3_l->max_x+k*d3_l->max_x*d3_l->max_y;
175     /* case amorph: amorph <- cryst diffusion */
176     if(*(d3_l->status+offset)&AMORPH)
177     {
178      for(c=-1;c<=1;c++)
179      {
180       if(c!=0)
181       {
182        off=((i+d3_l->max_x+c)%d3_l->max_x)+j*d3_l->max_x+k*d3_l->max_x*d3_l->max_y;
183        carry=0;
184        if(!(*(d3_l->status+off)&AMORPH)) carry=(int)(my_info->dr_ac*(*(d3_l->extra+off)));
185        if(carry!=0)
186        {
187         *(d3_l->extra+offset)+=carry;
188         *(d3_l->extra+off)-=carry;
189        }
190       }
191      }
192      for(c=-1;c<=1;c++)
193      {
194       if(c!=0)
195       {
196        off=i+((j+c+d3_l->max_y)%d3_l->max_y)*d3_l->max_x+k*d3_l->max_x*d3_l->max_y;
197        carry=0;
198        if(!(*(d3_l->status+off)&AMORPH)) carry=(int)(my_info->dr_ac*(*(d3_l->extra+off)));
199        if(carry!=0)
200        {
201         *(d3_l->extra+offset)+=carry; 
202         *(d3_l->extra+off)-=carry; 
203        }
204       }
205      }
206      /* z diff */
207      if(k!=0)
208      {
209       off=i+j*d3_l->max_x+(k-1)*d3_l->max_x*d3_l->max_y;
210       carry=0;
211       if(!*(d3_l->status+off)&AMORPH) carry=(int)(my_info->dr_ac*(*(d3_l->extra+off)));
212       if(carry!=0)
213       {
214        *(d3_l->extra+off)-=carry;
215        *(d3_l->extra+offset)+=carry;
216       }
217      }
218      if(k!=d3_l->max_z-1)
219      {
220       off=i+j*d3_l->max_x+(k+1)*d3_l->max_x*d3_l->max_y;
221       carry=0;
222       if(!*(d3_l->status+off)&AMORPH) carry=(int)(my_info->dr_ac*(*(d3_l->extra+off)));
223      if(carry!=0)
224       {
225        *(d3_l->extra+off)-=carry;
226        *(d3_l->extra+offset)+=carry;
227       }
228      }
229     }
230    } /* for z */
231   } /* for y */
232  } /* for x */
233
234  } /* if step modulo diff_rate == 0 */
235
236  return 1;
237 }
238
239 int calc_pressure(d3_lattice *d3_l,int range)
240 {
241  int i,j,off;
242  double count,max=0;
243  int x,y,z;
244
245  for(x=0;x<d3_l->max_x;x++)
246  {
247   for(y=0;y<d3_l->max_y;y++)
248   {
249    for(z=0;z<d3_l->max_z;z++)
250    {
251     count=0;
252     for(i=-range;i<=range;i++)
253     {
254      for(j=-range;j<=range;j++)
255      {
256       if(i!=0 && j!=0)
257       {
258        off=((x+d3_l->max_x+i)%d3_l->max_x)+((y+d3_l->max_y+j)%d3_l->max_x)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
259        if(*(d3_l->status+off)&AMORPH) count+=((double)*(d3_l->extra+off))/(i*i+j*j);
260       }
261      }
262     }
263     if(count>max) max=count;
264    }
265   }
266  }
267
268  for(x=0;x<d3_l->max_x;x++)
269  {
270   for(y=0;y<d3_l->max_y;y++)
271   {
272    for(z=0;z<d3_l->max_z;z++)
273    {
274     count=0;
275     for(i=-range;i<=range;i++)
276     {
277      for(j=-range;j<=range;j++)
278      {
279       if(i!=0 && j!=0)
280       {
281        off=((x+d3_l->max_x+i)%d3_l->max_x)+((y+d3_l->max_y+j)%d3_l->max_x)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
282        if(*(d3_l->status+off)&AMORPH) count+=((double)*(d3_l->extra+off))/(i*i+j*j);
283       }
284      }
285     }
286     *((unsigned int *)(d3_l->v_ptr)+x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)=(count*500/max);
287    }
288   }
289  }
290
291  return 1;
292 }
293
294 int calc_max_extra(d3_lattice *d3_l)
295 {
296  int x,y,z;
297  int off,max=0;
298
299  for(x=0;x<d3_l->max_x;x++)
300  {
301   for(y=0;y<d3_l->max_y;y++)
302   {
303    for(z=0;z<d3_l->max_z;z++)
304    {
305     off=x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
306     if(*(d3_l->extra+off)>max) max=*(d3_l->extra+off);
307    }
308   }
309  }
310
311  return max;
312 }
313
314 int write_ac_distr(d3_lattice *d3_l,int ac_distr)
315 {
316  int fd,x,y,z;
317  int count,offset;
318  char file[32];
319  int si_count;
320  
321  if(ac_distr==1) strcpy(file,"carbon_in_av.plot");
322  if(ac_distr==2) strcpy(file,"carbon_in_cv.plot");
323  if(ac_distr==3) strcpy(file,"carbon.plot");
324  if(ac_distr==4) strcpy(file,"amorphous_volumes.plot");
325
326  if((fd=open(file,O_WRONLY|O_CREAT))<0)
327  {
328   puts("cannot open plot file");
329   return -1;
330  }
331
332  for(z=0;z<d3_l->max_z;z++)
333  {
334   count=0;
335   si_count=0;
336   for(x=0;x<d3_l->max_x;x++)
337   {
338    for(y=0;y<d3_l->max_y;y++)
339    {
340     offset=x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y;
341     if(ac_distr==1)
342      if(*(d3_l->status+offset)&AMORPH)
343      {
344       count+=*(d3_l->extra+offset);
345       si_count+=1;
346      }
347     if(ac_distr==2)
348      if(!(*(d3_l->status+offset)&AMORPH))
349      {
350       count+=*(d3_l->extra+offset);
351       si_count+=1;
352      }
353     if(ac_distr==3)
354     {
355      count+=*(d3_l->extra+offset);
356      si_count+=1;
357     }
358     if(ac_distr==4)
359      if(*(d3_l->status+offset)&AMORPH) count+=1;
360    }
361   }
362   si_count*=SI_PER_VOLUME;
363   if(ac_distr==4) dprintf(fd,"%d %d\n",z*CELL_LENGTH,count);
364 #ifdef ATPROZ
365   else
366   {
367    if(si_count)
368     dprintf(fd,"%d %f\n",z*CELL_LENGTH,100.0*count/(si_count+count));
369    else
370     dprintf(fd,"%d 0\n",z*CELL_LENGTH);
371   }
372 #else
373   else dprintf(fd,"%d %d\n",z*CELL_LENGTH,count/(d3_l->max_x*d3_l->max_y));
374 #endif
375  }
376  close(fd);
377  
378  return 1;
379 }
380
381 int write_bmp(d3_lattice *d3_l,int window,u32 x,u32 y,u32 z,int max)
382 {
383  int fd,i,j,size=0,foo=0,k,sum;
384  int width=0,height=0;
385  char bmpfile[MAX_CHARS];
386  char buf[128];
387
388  if(window==1)
389  {
390   sprintf(bmpfile,"x-z_%d.bmp",y);
391   foo=3*d3_l->max_x;
392   size=(foo+(4-foo%4))*d3_l->max_z;
393   height=d3_l->max_z;
394   width=d3_l->max_x;
395  }
396  if(window==2)
397  {
398   sprintf(bmpfile,"y-z_%d.bmp",x);
399   foo=3*d3_l->max_y;
400   size=(foo+(4-foo%4))*d3_l->max_z;
401   height=d3_l->max_z;
402   width=d3_l->max_y;
403  }
404  if(window==3)
405  {
406   sprintf(bmpfile,"x-y_%d.bmp",z);
407   foo=3*d3_l->max_x;
408   size=(foo+(4-foo%4))*d3_l->max_y;
409   width=d3_l->max_x;
410   height=d3_l->max_y;
411  }
412  if(window==4)
413  {
414   sprintf(bmpfile,"x-z_cdistr_%d.bmp",y);
415   foo=3*d3_l->max_x;
416   size=(foo+(4-foo%4))*d3_l->max_z;
417   height=d3_l->max_z;
418   width=d3_l->max_x;
419  }
420  if(window==5)
421  {
422   sprintf(bmpfile,"y-z_cdistr_%d.bmp",x);
423   foo=3*d3_l->max_y;
424   size=(foo+(4-foo%4))*d3_l->max_z;
425   height=d3_l->max_z;
426   width=d3_l->max_y;
427  }
428  if(window==6)
429  {
430   sprintf(bmpfile,"x-y_cdistr_%d.bmp",z);
431   foo=3*d3_l->max_x;
432   size=(foo+(4-foo%4))*d3_l->max_y;
433   width=d3_l->max_x;
434   height=d3_l->max_y;
435  }
436  if(window==7)
437  {
438   sprintf(bmpfile,"x-z_pressure_%d.bmp",y);
439   foo=3*d3_l->max_x;
440   size=(foo+(4-foo%4))*d3_l->max_z;
441   height=d3_l->max_z;
442   width=d3_l->max_x;
443  }
444  if(window==8)
445  {
446   sprintf(bmpfile,"y-z_pressure_%d.bmp",x);
447   foo=3*d3_l->max_y;
448   size=(foo+(4-foo%4))*d3_l->max_z;
449   height=d3_l->max_z;
450   width=d3_l->max_y;
451  }
452  if(window==9)
453  {
454   sprintf(bmpfile,"x-y_pressure_%d.bmp",z);
455   foo=3*d3_l->max_x;
456   size=(foo+(4-foo%4))*d3_l->max_y;
457   height=d3_l->max_y;
458   width=d3_l->max_x;
459  }
460  if(window==10)
461  {
462   sprintf(bmpfile,"x-z_c_cdistr_%d.bmp",y);
463   foo=3*d3_l->max_x;
464   size=(foo+(4-foo%4))*d3_l->max_z;
465   height=d3_l->max_z;
466   width=d3_l->max_x;
467  }
468  if(window==11)
469  {
470   sprintf(bmpfile,"y-z_c_cdistr_%d.bmp",x);
471   foo=3*d3_l->max_y;
472   size=(foo+(4-foo%4))*d3_l->max_z;
473   height=d3_l->max_z;
474   width=d3_l->max_y;
475  }
476  if(window==12)
477  {
478   sprintf(bmpfile,"x-y_c_cdistr_%d.bmp",z);
479   foo=3*d3_l->max_x;
480   size=(foo+(4-foo%4))*d3_l->max_y;
481   height=d3_l->max_y;
482   width=d3_l->max_x;
483  }
484  if((fd=open(bmpfile,O_WRONLY|O_CREAT))<0)
485  {
486   puts("cannot open bmp file");
487   return -1;
488  }
489
490  /* bmpheader */
491  buf[0]='B'; /* std header start */
492  buf[1]='M';
493  buf[2]=(size+0x36)&0xff; /* file size */
494  buf[3]=(size+0x36)>>8;
495  memset(buf+4,0,6);
496  buf[10]=0x36; /* offset to data */
497  memset(buf+11,0,3);
498  buf[14]=0x28; /* length of bmp info header */
499  memset(buf+15,0,3);
500  buf[18]=width&0xff; /* width and height */
501  buf[19]=width>>8;
502  memset(buf+20,0,2);
503  buf[22]=height&0xff;
504  buf[23]=height>>8;
505  memset(buf+24,0,2);
506  buf[26]=1; /* # planes -> 1 */
507  buf[27]=0;
508  buf[28]=24; /* bits per pixel -> 2^24 (true color) */
509  buf[29]=0;
510  memset(buf+30,0,4); /* compression -> none */
511  buf[34]=size&0xff; /* data size */
512  buf[35]=size>>8;
513  memset(buf+36,0,2);
514  buf[38]=0x12; /* res: pixel/meter */
515  buf[39]=0x0b;
516  memset(buf+40,0,2);
517  buf[42]=0x12;
518  buf[43]=0x0b;
519  memset(buf+44,0,2); 
520  memset(buf+46,0,8); /* no colors, no important colors */
521
522  if(write(fd,buf,54)<54)
523  {
524   puts("failed writing bmp header");
525   return -1;
526  }
527  if(window==1)
528  {
529   for(j=0;j<d3_l->max_z;j++)
530   {
531    for(i=0;i<d3_l->max_x;i++)
532    {
533     sum=0;
534     for(k=-2;k<=2;k++)
535      if(*(d3_l->status+i+(((y+k+d3_l->max_y)%d3_l->max_y)*d3_l->max_x)+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y)&RED) sum+=0xff;
536     sum/=5;
537     memset(buf,(unsigned char)sum,3);
538     if(write(fd,buf,3)<3)
539     {
540      puts("failed writing rgb values to bmp file");
541      return-1;
542     }
543    }
544    if(foo%4)
545    {
546     memset(buf,0,4-foo%4);
547     if(write(fd,buf,4-foo%4)<4-foo%4)
548     {
549      puts("failed writing 4 byte ending");
550      return -1;
551     }
552    } 
553   }
554  }
555  if(window==2)
556  {
557   for(j=0;j<d3_l->max_z;j++)
558   {
559    for(i=0;i<d3_l->max_y;i++)
560    {
561     sum=0;
562     for(k=-2;k<=2;k++)
563      if(*(d3_l->status+((x+k+d3_l->max_x)%d3_l->max_x)+i*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y)&RED) sum+=0xff;
564     sum/=5;
565     memset(buf,(unsigned char)sum,3);
566     if(write(fd,buf,3)<3)
567     {
568      puts("failed writing rgb values to bmp file");
569      return-1;
570     }
571    }
572    if(foo%4)
573    {
574     memset(buf,0,4-foo%4);
575     if(write(fd,buf,4-foo%4)<4-foo%4)
576     {
577      puts("failed writing 4 byte ending");
578      return -1;
579     }
580    }
581   }
582  }
583  if(window==3)
584  {
585   for(j=0;j<d3_l->max_y;j++)
586   {
587    for(i=0;i<d3_l->max_x;i++)
588    {
589     if(*(d3_l->status+i+(d3_l->max_y-j-1)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&RED) memset(buf,0xff,3);
590     else memset(buf,0,3);
591     if(write(fd,buf,3)<3)
592     {
593      puts("failed writing rgb values to bmp file");
594      return -1;
595     }
596    }
597    if(foo%4)
598    {
599     memset(buf,0,4-foo%4);
600     if(write(fd,buf,4-foo%4)<4-foo%4)
601     {
602      puts("failed writing 4 byte ending");
603      return -1;
604     }
605    }
606   }
607  }
608  if(window==4)
609  {
610   for(j=0;j<d3_l->max_z;j++)
611   {
612    for(i=0;i<d3_l->max_x;i++)
613    {
614     sum=*(d3_l->extra+i+y*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
615     sum=sum*255/max;
616     memset(buf+1,(unsigned char)sum,2);
617     buf[0]=0xff;
618     if(write(fd,buf,3)<3)
619     {
620      puts("failed writing rgb values to bmp file");
621      return-1;
622     }
623    }
624    if(foo%4)
625    {
626     memset(buf,0,4-foo%4);
627     if(write(fd,buf,4-foo%4)<4-foo%4)
628     {
629      puts("failed writing 4 byte ending");
630      return -1;
631     }
632    }
633   }
634  }
635  if(window==5)
636  { 
637   for(j=0;j<d3_l->max_z;j++) 
638   {                     
639    for(i=0;i<d3_l->max_x;i++)
640    {
641     sum=*(d3_l->extra+x+i*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
642     sum=sum*255/max;
643     memset(buf+1,(unsigned char)sum,2);
644     buf[0]=0xff;
645     if(write(fd,buf,3)<3)
646     {
647      puts("failed writing rgb values to bmp file");
648      return-1;  
649     }
650    }
651    if(foo%4)
652    {
653     memset(buf,0,4-foo%4);
654     if(write(fd,buf,4-foo%4)<4-foo%4)
655     {
656      puts("failed writing 4 byte ending");
657      return -1;
658     }
659    }
660   }
661  }
662  if(window==6)
663  {   
664   for(j=0;j<d3_l->max_y;j++)
665   {  
666    for(i=0;i<d3_l->max_x;i++)
667    { 
668     sum=*(d3_l->extra+i+(d3_l->max_y-j-1)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y);
669     sum=sum*255/max;
670     memset(buf+1,(unsigned char)sum,2);
671     buf[0]=0xff;
672     if(write(fd,buf,3)<3)
673     {
674      puts("failed writing rgb values to bmp file");
675      return-1;
676     }
677    } 
678    if(foo%4)
679    { 
680     memset(buf,0,4-foo%4);
681     if(write(fd,buf,4-foo%4)<4-foo%4)
682     {
683      puts("failed writing 4 byte ending");
684      return -1;
685     }
686    } 
687   }
688  }
689  if(window==7)
690  {
691   for(j=0;j<d3_l->max_z;j++)
692   {
693    for(i=0;i<d3_l->max_x;i++)
694    {
695     sum=*((unsigned int *)(d3_l->v_ptr)+i+y*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
696       buf[0]=0;
697     if(sum<=255) {
698       buf[1]=0;
699       buf[2]=sum;
700     } else {
701       buf[1]=(sum-255);
702       buf[2]=0xff;
703     }
704     if(write(fd,buf,3)<3)
705     {
706      puts("failed writing rgb values to bmp file");
707      return-1;
708     }
709    }
710    if(foo%4)
711    {
712     memset(buf,0,4-foo%4);
713     if(write(fd,buf,4-foo%4)<4-foo%4)
714     {
715      puts("failed writing 4 byte ending");
716      return -1;
717     }
718    }
719   }
720  }
721  if(window==8)
722  { 
723   for(j=0;j<d3_l->max_z;j++) 
724   {                     
725    for(i=0;i<d3_l->max_x;i++)
726    {
727     sum=*((unsigned int *)(d3_l->v_ptr)+x+i*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
728       buf[0]=0;
729     if(sum<=255) {
730       buf[1]=0;
731       buf[2]=sum;
732     } else {
733       buf[1]=(sum-255);
734       buf[2]=0xff;
735     }
736     if(write(fd,buf,3)<3)
737     {
738      puts("failed writing rgb values to bmp file");
739      return-1;  
740     }
741    }
742    if(foo%4)
743    {
744     memset(buf,0,4-foo%4);
745     if(write(fd,buf,4-foo%4)<4-foo%4)
746     {
747      puts("failed writing 4 byte ending");
748      return -1;
749     }
750    }
751   }
752  }
753  if(window==9)
754  {   
755   for(j=0;j<d3_l->max_y;j++)
756   {  
757    for(i=0;i<d3_l->max_x;i++)
758    {
759     sum=*((unsigned int *)(d3_l->v_ptr)+i+(d3_l->max_y-j-1)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y);
760       buf[0]=0;
761     if(sum<=255) {
762       buf[1]=0;
763       buf[2]=sum;
764     } else {
765       buf[1]=(sum-255);
766       buf[2]=0xff;
767     }
768     printf("sum = %d => r: %02x g: %02x b: %02x\n",sum,buf[2],buf[1],buf[0]);
769     if(write(fd,buf,3)<3)
770     {
771      puts("failed writing rgb values to bmp file");
772      return-1;
773     }
774    } 
775    if(foo%4)
776    { 
777     memset(buf,0,4-foo%4);
778     if(write(fd,buf,4-foo%4)<4-foo%4)
779     {
780      puts("failed writing 4 byte ending");
781      return -1;
782     }
783    } 
784   }
785  }
786  if(window==10)
787  {
788   for(j=0;j<d3_l->max_z;j++)
789   {
790    for(i=0;i<d3_l->max_x;i++)
791    {
792     if(!(*(d3_l->status+i+y*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y)&RED)) sum=*(d3_l->extra+i+y*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
793     else sum=0;
794     sum=sum*255/max;
795     memset(buf,(unsigned char)sum,3);
796     if(write(fd,buf,3)<3)
797     {
798      puts("failed writing rgb values to bmp file");
799      return-1;
800     }
801    }
802    if(foo%4)
803    {
804     memset(buf,0,4-foo%4);
805     if(write(fd,buf,4-foo%4)<4-foo%4)
806     {
807      puts("failed writing 4 byte ending");
808      return -1;
809     }
810    }
811   }
812  }
813  if(window==11)
814  { 
815   for(j=0;j<d3_l->max_z;j++) 
816   {                     
817    for(i=0;i<d3_l->max_x;i++)
818    {
819     if(!(*(d3_l->status+x+i*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y)&RED)) sum=*(d3_l->extra+x+i*d3_l->max_x+(d3_l->max_z-j-1)*d3_l->max_x*d3_l->max_y);
820     else sum=0;
821     sum=sum*255/max;
822     memset(buf,(unsigned char)sum,3);
823     if(write(fd,buf,3)<3)
824     {
825      puts("failed writing rgb values to bmp file");
826      return-1;  
827     }
828    }
829    if(foo%4)
830    {
831     memset(buf,0,4-foo%4);
832     if(write(fd,buf,4-foo%4)<4-foo%4)
833     {
834      puts("failed writing 4 byte ending");
835      return -1;
836     }
837    }
838   }
839  }
840  if(window==12)
841  {   
842   for(j=0;j<d3_l->max_y;j++)
843   {  
844    for(i=0;i<d3_l->max_x;i++)
845    {
846     if(!(*(d3_l->status+i+(d3_l->max_y-j-1)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&RED)) sum=*(d3_l->extra+i+(d3_l->max_y-j-1)*d3_l->max_x+z*d3_l->max_x*d3_l->max_y);
847     else sum=0;
848     sum=sum*255/max;
849     memset(buf,(unsigned char)sum,3);
850     if(write(fd,buf,3)<3)
851     {
852      puts("failed writing rgb values to bmp file");
853      return-1;
854     }
855    } 
856    if(foo%4)
857    { 
858     memset(buf,0,4-foo%4);
859     if(write(fd,buf,4-foo%4)<4-foo%4)
860     {
861      puts("failed writing 4 byte ending");
862      return -1;
863     }
864    }
865   }
866  }
867  close(fd);
868
869  return 1;
870 }
871
872 int save_to_file(char *sf,d3_lattice *d3_l,info *my_inf)
873 {
874  int sf_fd,c;
875
876  if((sf_fd=open(sf,O_WRONLY|O_CREAT))<0)
877  {
878   puts("cannot open save file");
879   return -1;
880  }
881  if(write(sf_fd,d3_l,sizeof(d3_lattice))<sizeof(d3_lattice))
882  {
883   puts("failed saving d3 lattice struct");
884   return -1;
885  }
886  if(write(sf_fd,my_inf,sizeof(info))<sizeof(info))
887  {
888   puts("failed saving info struct");
889   return-1;
890  }
891  c=d3_l->max_x*d3_l->max_y*d3_l->max_z;
892  if(write(sf_fd,d3_l->status,c*sizeof(unsigned char))<c*sizeof(unsigned char))
893  {
894   puts("failed saving status of d3 lattice sites");
895   return -1;
896  }
897  if(write(sf_fd,d3_l->extra,c*sizeof(int))<c*sizeof(int))
898  {
899   puts("failed saving sites concentration");
900   return -1;
901  }
902  close(sf_fd);
903
904  return 1;
905 }
906
907 int load_from_file(char *lf,d3_lattice *d3_l,info *my_inf)
908 {
909
910  int lf_fd,c,pos,end,data,data_len,strip;
911
912  if((lf_fd=open(lf,O_RDONLY))<0)
913  {
914   puts("cannot open load file");
915   return -1;
916  }
917  if(read(lf_fd,d3_l,sizeof(d3_lattice))<sizeof(d3_lattice))
918  {
919   puts("failed reading d3 lattice struct");
920   return -1;
921  }
922  pos=lseek(lf_fd,0,SEEK_CUR);
923  printf("psition: %d (%d)\n",pos,sizeof(d3_lattice));
924  data=d3_l->max_x*d3_l->max_y*d3_l->max_z;
925  data_len=data*(sizeof(int)+sizeof(unsigned char));
926  printf("there are %d volumes so we need %d of bytes\n",data,data_len);
927  end=lseek(lf_fd,0,SEEK_END);
928  c=end-pos-data_len;
929  printf("end: %d => length: %d => guessed info size: %d bytes\n",end,end-pos,c);
930  strip=sizeof(info)-c;
931  printf("as real programs info size is %d, we strip %d bytes\n",sizeof(info),strip);
932  lseek(lf_fd,pos,SEEK_SET);
933  c=sizeof(info);
934  if(strip>0) c-=strip;
935  if(c<0)
936  {
937   puts("info smaller then strip size");
938   return -1;
939  }
940  if(read(lf_fd,my_inf,c)<c)
941  {
942   puts("failed reading info struct");
943   return-1;
944  }
945  if(strip>0) memset(my_inf+c,0,strip);
946  if(strip<0) lseek(lf_fd,(-1*strip),SEEK_CUR);
947  c=d3_l->max_x*d3_l->max_y*d3_l->max_z;
948  if((d3_l->status=(unsigned char*)malloc(c*sizeof(unsigned char)))==NULL)
949  {
950   puts("cannot allocate status buffer");
951   return -1;
952  }
953  if((d3_l->extra=(int *)malloc(c*sizeof(int)))==NULL)
954  {
955   puts("cannot allocate concentration buffer");
956   return -1;
957  }
958  if(read(lf_fd,d3_l->status,c*sizeof(unsigned char))<c*sizeof(unsigned char))
959  {
960   puts("failed reading status of d3 lattice sites");
961   return -1;
962  }
963  if(read(lf_fd,d3_l->extra,c*sizeof(int))<c*sizeof(int))
964  {
965   puts("failed reading sites concentration");
966   return -1;
967  }
968  close(lf_fd);
969
970  return 1;
971 }
972
973 int convert_file(char *cf,d3_lattice *d3_l)
974 {
975  int x,y,z;
976  int c_fd;
977
978  if((c_fd=open(cf,O_WRONLY|O_CREAT))<0)
979  {
980   puts("cannot open convert file");
981   return -1;
982  }
983  dprintf(c_fd,"# created by nlsop (gnuplot format)\n");
984  for(x=0;x<d3_l->max_x;x++)
985  {
986   for(y=0;y<d3_l->max_y;y++)
987   {
988    for(z=0;z<d3_l->max_z;z++)
989    {
990     if(*(d3_l->status+x+y*d3_l->max_x+z*d3_l->max_x*d3_l->max_y)&AMORPH) dprintf(c_fd,"%d %d %d\n",x,y,z);
991    }
992   }
993  }
994  close(c_fd);
995
996  return 1;
997 }
998
999 int get_c_ratio(double *c_ratio,char *pfile,info *my_info,d3_lattice *d3_l)
1000 {
1001  double all,a,b,d;
1002  int i,k;
1003  int p_fd;
1004  unsigned char buf[32];
1005  char *p;
1006  unsigned char c;
1007
1008  if((p_fd=open(pfile,O_RDONLY))<0)
1009  {
1010   puts("cannot open profile file");
1011   return -1;
1012  }
1013  k=1;
1014  d=0;
1015  all=0;
1016  while(k)
1017  {
1018   for(i=0;i<32;i++)
1019   {
1020    k=read(p_fd,&c,1);
1021    buf[i]=c;
1022    if(c=='\n') break;
1023   }
1024   if(k)
1025   {
1026    p=strtok(buf," ");
1027    a=atof(p)/10; /* nm */
1028    p=strtok(NULL," ");
1029    b=atof(p);
1030    if(a<=d3_l->max_z*CELL_LENGTH) d+=b;
1031    all+=b;
1032   }
1033  }
1034  *c_ratio=d/all;
1035  close(p_fd);
1036
1037  return 1;
1038 }
1039
1040 u32 get_reject_graph(info *my_info,d3_lattice *d3_l,char *file,u32 *graph) {
1041  double a,b;
1042  int i,j,k;
1043  int fd;
1044  char buf[32],*p;
1045  unsigned char *flag;
1046  u32 max;
1047
1048  max=0;
1049  if((fd=open(file,O_RDONLY))<0)
1050  {
1051   puts("cannot open file to calculate rejection graph");
1052   return -1;
1053  }
1054  if((flag=(unsigned char *)malloc(d3_l->max_z))==NULL)
1055  {
1056   puts("cannot malloc flag memory for rejection graph");
1057   return -1;
1058  }
1059  memset(flag,0,d3_l->max_z);
1060  memset(graph,0,d3_l->max_z*sizeof(u32));
1061  /* get fixpoints */
1062  k=1;
1063  while(k)
1064  {
1065   for(i=0;i<32;i++)
1066   {
1067    k=read(fd,&buf[i],1);
1068    if((buf[i]=='\n')||(k==0)) break;
1069   }
1070   if(k)
1071   {
1072    p=strtok(buf," ");
1073    a=atof(p)/10; /* nm */
1074    p=strtok(NULL," ");
1075    b=atof(p);
1076    if(a>d3_l->max_z*CELL_LENGTH) k=0;
1077    else 
1078    {
1079     graph[(int)(a/CELL_LENGTH)]=(int)(URAND_MAX/100*b);
1080     flag[(int)(a/CELL_LENGTH)]=1;
1081    }
1082   }
1083  }
1084  /* do (linear) interpolation here! */
1085  i=0;
1086  a=0;
1087  while(i<d3_l->max_z)
1088  {
1089   /* graph[0] is 0! */
1090   j=i;
1091   i++;
1092   while(flag[i]==0&&i<d3_l->max_z) i++;
1093   for(k=j+1;k<i;k++) graph[k]=(int)((k-j)*((int)graph[i]-(int)graph[j])/(i-j))+graph[j];
1094   if(graph[i]>max) max=graph[i];
1095  }
1096
1097  free(flag);
1098
1099 #ifdef DEBUG_INTERPOL_PROFILE
1100  printf("debug: %s (interpolated profile)\n",file);
1101  for(i=0;i<d3_l->max_z;i++) printf("%d %d\n",i,graph[i]);
1102 #endif
1103
1104  return max;
1105 }
1106
1107 int get_amorphous_layer_info(d3_lattice *d3_l,int *sai,int *sacl,int *eacl) {
1108   int i,j,a,oend,nend,count;
1109   unsigned char sacl_is_set=0;
1110   unsigned char eacl_is_set=0;
1111   unsigned char sai_is_set=0;
1112
1113   a=d3_l->max_x*d3_l->max_y;
1114   nend=a;
1115   oend=0;
1116
1117   for(i=0;i<d3_l->max_z;i++) {
1118     count=0;
1119     for(j=oend;j<nend;j++) if(*(d3_l->status+j)&AMORPH) count++;
1120     oend=nend;
1121     nend+=a;
1122     if((count>=A_START*a)&&(!sai_is_set)) {
1123       *sai=i;
1124       sai_is_set=1;
1125     }
1126     if((count>=AC_START*a)&&(!sacl_is_set)) {
1127       *sacl=i;
1128       sacl_is_set=1;
1129     }
1130     if((count<=A_END*a)&&(sacl_is_set)&&(!eacl_is_set)) {
1131       *eacl=i;
1132       eacl_is_set=1;
1133     }
1134     if((eacl_is_set)&&(count>=A_END*a)) eacl_is_set=0;
1135   }
1136   return 1;
1137 }
1138
1139 int main(int argc,char **argv)
1140 {
1141  u32 x,y,z,x_c,y_c,z_c;
1142  int i,j,quit,escape,switchmode,nowait,bmp,ac_distr;
1143  int refresh,resave;
1144  int c_step;
1145  int sai,sacl,eacl;
1146  char s_file[MAX_CHARS];
1147  char s_file_tmp[MAX_CHARS];
1148  char l_file[MAX_CHARS];
1149  char c_file[MAX_CHARS];
1150  char p_file[MAX_CHARS];
1151  char n_e_file[MAX_CHARS];
1152  char convert;
1153  char r_file[MAX_CHARS];
1154 #ifdef USE_DFB_API
1155  char xyz_txt[MAX_TXT];
1156  char status_txt[MAX_TXT];
1157  char conc_txt[MAX_TXT];
1158  char steps_txt[MAX_TXT];
1159  char cc_txt[MAX_TXT];
1160  char a_txt[MAX_TXT];
1161  char s_txt[MAX_TXT];
1162  char ballistic_txt[MAX_TXT];
1163  char carbon_txt[MAX_TXT];
1164  char stress_txt[MAX_TXT];
1165  char r_txt[MAX_TXT];
1166  char zdiff_txt[MAX_TXT];
1167  char diff_txt[MAX_TXT];
1168  char dr_ac_txt[MAX_TXT];
1169  char dose_txt[MAX_TXT];
1170  char mode_txt[MAX_TXT];
1171  char hpi_txt[MAX_TXT];
1172  char srate_txt[MAX_TXT];
1173  char start_ai_txt[MAX_TXT];
1174  char start_acl_txt[MAX_TXT];
1175  char end_acl_txt[MAX_TXT];
1176  char *arg_v[MAX_ARGV];
1177 #endif
1178  d3_lattice d3_l;
1179  info my_info;
1180  unsigned char mode;
1181  double c_ratio;
1182 #ifdef USE_DFB_API
1183  int max_extra;
1184 #endif
1185  u32 *c_profile;
1186  u32 *n_e_loss;
1187  u32 ne_max,ip_max;
1188  u32 nel_z;
1189  unsigned char do_sputter;
1190
1191  d3_l.max_x=_X;
1192  d3_l.max_y=_Y;
1193  d3_l.max_z=_Z;
1194  my_info.steps=STEPS;
1195  my_info.range=RANGE;
1196  refresh=REFRESH;
1197  resave=RESAVE;
1198  my_info.s=S_D;
1199  my_info.b=B_D;
1200  my_info.c=C_D;
1201  my_info.cc=CC;
1202  my_info.dr_ac=DR_AC;
1203  my_info.diff_rate=DIFF_RATE;
1204  my_info.cpi=CPI;
1205  my_info.s_rate=S_RATE;
1206  nowait=0;
1207  quit=0;
1208  escape=0;
1209  switchmode=0;
1210  c_step=0;
1211  strcpy(s_file,"");
1212  strcpy(l_file,"");
1213  strcpy(c_file,"");
1214  strcpy(p_file,IMP_PROFILE);
1215  strcpy(n_e_file,NEL_PROFILE);
1216  convert=0;
1217  strcpy(r_file,"");
1218  mode=0;
1219  ne_max=0;
1220  ip_max=0;
1221  sai=0;
1222  sacl=0;
1223  eacl=0;
1224  do_sputter=1;
1225
1226 #ifdef MORE_PRINTF
1227  printf("reading argv ...");
1228 #endif
1229
1230  for(i=1;i<argc;i++)
1231  {
1232   if(argv[i][0]=='-')
1233   {
1234    switch(argv[i][1])
1235    {
1236     case 'h':
1237      usage();
1238      return -1;
1239     case 'n':
1240      nowait=1;
1241      break;
1242     case 'x':
1243      d3_l.max_x=atoi(argv[++i]);
1244      break;
1245     case 'y':
1246      d3_l.max_y=atoi(argv[++i]);
1247      break;
1248     case 'z':
1249      d3_l.max_z=atoi(argv[++i]);
1250      break;
1251     case 's':
1252      my_info.steps=atoi(argv[++i]);
1253      break;
1254     case 'd':
1255      refresh=atoi(argv[++i]);
1256      break;
1257     case 'r':
1258      my_info.range=atoi(argv[++i]);
1259      break;
1260     case 'f':
1261      my_info.s=atof(argv[++i]);
1262      break;
1263     case 'p':
1264      my_info.b=atof(argv[++i]);
1265      break;
1266     case 'F':
1267      my_info.c=atof(argv[++i]);
1268      break;
1269     case 'W':
1270      resave=atoi(argv[++i]);
1271      break;
1272     case 'C':
1273      strcpy(l_file,argv[++i]);
1274      if(i<argc-1) if(argv[i+1][0]!='-') strcpy(c_file,argv[++i]);
1275      convert=1;
1276      break;
1277     case 'D':
1278      my_info.dr_ac=atof(argv[++i]);
1279      break;
1280     case 'e':
1281      my_info.diff_rate=atoi(argv[++i]);
1282      break;
1283     case 'L':
1284      strcpy(l_file,argv[++i]);
1285      break;
1286     case 'S':
1287      strcpy(s_file,argv[++i]);
1288      break;
1289     case 'R':
1290      strcpy(r_file,argv[++i]);
1291      break;
1292     case 'P':
1293      strcpy(p_file,argv[++i]);
1294      break;
1295     case 'N':
1296      strcpy(n_e_file,argv[++i]);
1297      break;
1298     case 'g':
1299      strcpy(l_file,argv[++i]);
1300      if(i<argc-1) if(argv[i+1][0]!='-') c_step=atoi(argv[++i]);
1301      break;
1302     case 'H':
1303      my_info.cpi=atoi(argv[++i]);
1304      break;
1305     case 'm':
1306      my_info.s_rate=atoi(argv[++i]);
1307      break;
1308     default:
1309      usage();
1310      return -1;
1311    }
1312   } else usage();
1313  }
1314
1315 #ifdef MORE_PRINTF
1316  printf(" done\n");
1317 #endif
1318
1319  x=d3_l.max_x/2-1;
1320  y=d3_l.max_y/2-1;
1321  z=d3_l.max_z/2-1;
1322
1323 #ifdef NODFB
1324  if(!strcmp(s_file,""))
1325  {
1326   puts("NODFB defined, run with -S option");
1327   return -1;
1328  }
1329 #endif
1330
1331  printf("random api init ...");
1332  if(!strcmp(r_file,"")) rand_init(NULL);
1333  else rand_init(r_file);
1334  printf(" done\n");
1335
1336  if(!strcmp(l_file,""))
1337  {
1338   i=d3_l.max_x*d3_l.max_y*d3_l.max_z;
1339 #ifdef USE_DFB_API
1340   printf("d3 lattice init ...");
1341   d3_lattice_init(&argc,argv,&d3_l);
1342   printf(" done\n");
1343 #endif
1344   if((d3_l.status=(unsigned char *)malloc(i*sizeof(unsigned char)))==NULL)
1345   {
1346    puts("failed allocating status buffer");
1347    return -1;
1348   }
1349   memset(d3_l.status,0,i*sizeof(unsigned char));
1350   if((d3_l.extra=(int *)malloc(i*sizeof(int)))==NULL)
1351   {
1352    puts("failed allocating concentration buffer");
1353    return -1;
1354   }
1355   memset(d3_l.extra,0,i*sizeof(int));
1356  } else
1357  {
1358   printf("loading file ...");
1359   load_from_file(l_file,&d3_l,&my_info);
1360   printf(" done\n");
1361   if(convert) 
1362   {   
1363    if(!strcmp(c_file,"")) sprintf(c_file,"%s_gnuplot",l_file);
1364    printf("converting file %s to %s\n",l_file,c_file);
1365    convert_file(c_file,&d3_l);
1366    puts("done");
1367    return 1;
1368   }
1369 #ifdef USE_DFB_API
1370   printf("d3 lattice init ...");
1371   d3_lattice_init(&argc,argv,&d3_l);
1372   printf(" done\n");
1373 #endif
1374  }
1375
1376 #ifdef USE_DFB_API
1377  printf("event init ...");
1378  d3_event_init(&d3_l);
1379  printf(" done\n");
1380 #endif
1381
1382 #ifdef USE_DFB_API
1383  strcpy(a_txt,"args:");
1384  sprintf(s_txt,"steps: %d",my_info.steps);
1385  sprintf(dose_txt,"dose: %.2fe+17 C/cm²",my_info.steps*1.0/(d3_l.max_x*d3_l.max_y*CELL_LENGTH*CELL_LENGTH*1000));
1386  sprintf(r_txt,"stress influence range: %d",my_info.range);
1387  sprintf(stress_txt,"stress term: %f",my_info.s);
1388  sprintf(ballistic_txt,"ballistic term: %f",my_info.b);
1389  sprintf(carbon_txt,"carbon term: %f",my_info.c);
1390  sprintf(dr_ac_txt,"a/c diffusion rate: %f",my_info.dr_ac);
1391  sprintf(zdiff_txt,"diffusion in z direction: yes");
1392  sprintf(diff_txt,"diffusion every %d steps",my_info.diff_rate);
1393  strcpy(mode_txt,"view: a/c mode");
1394  sprintf(hpi_txt,"hits per ion: %d",my_info.cpi);
1395  sprintf(srate_txt,"sputter rate (3nm/#c): %d",my_info.s_rate);
1396  get_amorphous_layer_info(&d3_l,&sai,&sacl,&eacl);
1397  sprintf(start_ai_txt,"start of a-inclusions: %d nm (%d)",3*sai,sai);
1398  sprintf(start_acl_txt,"start of a-layer: %d nm (%d)",3*sacl,sacl);
1399  sprintf(end_acl_txt,"end of a-layer: %d nm (%d)",3*eacl,eacl);
1400  arg_v[1]=mode_txt;
1401  arg_v[2]=xyz_txt;
1402  arg_v[3]=status_txt;
1403  arg_v[4]=conc_txt;
1404  arg_v[5]=NULL;
1405  arg_v[6]=steps_txt;
1406  arg_v[7]=cc_txt;
1407  arg_v[8]=NULL;
1408  arg_v[9]=a_txt;
1409  arg_v[10]=s_txt;
1410  arg_v[11]=dose_txt;
1411  arg_v[12]=diff_txt;
1412  arg_v[13]=zdiff_txt;
1413  arg_v[14]=dr_ac_txt;
1414  arg_v[15]=ballistic_txt;
1415  arg_v[16]=carbon_txt;
1416  arg_v[17]=stress_txt;
1417  arg_v[18]=r_txt;
1418  arg_v[19]=hpi_txt;
1419  arg_v[20]=srate_txt;
1420  arg_v[21]=NULL;
1421  arg_v[22]=start_ai_txt;
1422  arg_v[23]=start_acl_txt;
1423  arg_v[24]=end_acl_txt;
1424  arg_v[25]=NULL;
1425 #endif
1426
1427  /* compute graphs for random number rejection method */
1428  printf("random rejection graphs ...");
1429  if((c_profile=(u32 *)malloc(d3_l.max_z*sizeof(unsigned int)))==NULL)
1430  {
1431   puts("failed allocating memory for carbon profile graph");
1432   return -1;
1433  }
1434  if((n_e_loss=(u32 *)malloc(d3_l.max_z*sizeof(unsigned int)))==NULL)
1435  {
1436   puts("failed allocating memory for nuclear energy loss graph");
1437   return -1;
1438  }
1439  ip_max=get_reject_graph(&my_info,&d3_l,p_file,c_profile);
1440  ne_max=get_reject_graph(&my_info,&d3_l,n_e_file,n_e_loss);
1441  printf(" done\n");
1442
1443  if((!strcmp(l_file,""))||(c_step))
1444  {
1445
1446   /* this should be obsolete - z is high enough - we check now! */
1447   if(c_profile[d3_l.max_z-1]!=0)
1448   {
1449    printf("max_z (%d) too small - sputtering not possible\n",d3_l.max_z);
1450    do_sputter=0;
1451   }
1452   /* calculate ratio of c_simwindow / c_total */
1453   if(!do_sputter)
1454   {
1455    get_c_ratio(&c_ratio,p_file,&my_info,&d3_l);
1456    printf("calculated c ratio: %f\n",c_ratio);
1457   }
1458
1459   /* sputtering realy possible ?*/
1460   if(n_e_loss[d3_l.max_z-1]!=0)
1461    printf("warning: max_z (%d) too small - there may be amorphous volumes\n",d3_l.max_z);
1462
1463 #ifdef DEBUG_RAND
1464  i=0;
1465  while(1)
1466  {
1467 #ifdef DEBUG_CP
1468   printf("%d\n",get_rand_reject(d3_l.max_z,ip_max,c_profile));
1469 #endif
1470 #ifdef DEBUG_NEL
1471   printf("%d\n",get_rand_reject(d3_l.max_z,ne_max,n_e_loss));
1472 #endif
1473 #ifdef DEBUG_NORM
1474   printf("%d\n",get_rand(d3_l.max_z));
1475 #endif
1476 #ifdef DEBUG_LINEAR
1477   printf("%d\n",get_rand_lgp(d3_l.max_z,1,0));
1478 #endif
1479  if(i==10000000) return 1;
1480  i++;
1481  }
1482 #endif
1483
1484 #ifdef MORE_PRINTF
1485   printf("starting simulation ... now! :)\n");
1486 #endif
1487
1488   i=(c_step?c_step:0);
1489   while((i<my_info.steps) && (quit==0) && (escape==0))
1490   {
1491 #ifdef MORE_PRINTF
1492    if(i%refresh==0) printf("step: %d\n",i);
1493 #endif
1494    for(j=0;j<my_info.cpi;j++)
1495    {
1496     x_c=get_rand(d3_l.max_x);
1497     y_c=get_rand(d3_l.max_y);
1498     // z_c=get_rand_reject(d3_l.max_z,ne_max,n_e_loss);
1499     z_c=get_rand(d3_l.max_z);
1500     nel_z=URAND_MAX*(1.0*n_e_loss[z_c]/ne_max);
1501     process_cell(&d3_l,x_c,y_c,z_c,&my_info,nel_z);
1502    }
1503    distrib_c(&d3_l,&my_info,i,ip_max,c_profile);
1504 #ifdef USE_DFB_API
1505    if(i%refresh==0)
1506    {
1507     sprintf(xyz_txt,"x: %d  y: %d  z: %d (%d nm)",x+1,y+1,z+1,z*3);
1508     sprintf(status_txt,"status: %c",(*(d3_l.status+x+y*d3_l.max_x+z*d3_l.max_x*d3_l.max_y)&AMORPH)?'a':'c');
1509     sprintf(conc_txt,"carbon: %d",*(d3_l.extra+x+y*d3_l.max_x+z*d3_l.max_x*d3_l.max_y));
1510     sprintf(steps_txt,"step: %d",i);
1511     sprintf(cc_txt,"total c: %d",my_info.cc);
1512     get_amorphous_layer_info(&d3_l,&sai,&sacl,&eacl);
1513     sprintf(start_ai_txt,"start of a-inclusions: %d nm (%d)",3*sai,sai);
1514     sprintf(start_acl_txt,"start of a-layer: %d nm (%d)",3*sacl,sacl);
1515     sprintf(end_acl_txt,"end of a-layer: %d nm (%d)",3*eacl,eacl);
1516     d3_lattice_draw(&d3_l,x,y,z,25,arg_v,mode,0,NULL,0,NULL,0);
1517    }
1518 #endif
1519    if(i%resave==0 && strcmp(s_file,"") && resave!=0 && i!=0)
1520    {
1521     sprintf(s_file_tmp,"%s_%d_of_%d",s_file,i,my_info.steps);
1522     save_to_file(s_file_tmp,&d3_l,&my_info);
1523 #ifdef NODFB
1524     printf("saved %s\n",s_file_tmp);
1525 #endif
1526    }
1527    i++;
1528    if((do_sputter)&(i%my_info.s_rate==0)) sputter(&d3_l);
1529   }
1530  }
1531
1532  if(strcmp(s_file,""))
1533  {
1534    printf("saved %s\n",s_file);
1535    save_to_file(s_file,&d3_l,&my_info);
1536  }
1537
1538 #ifdef USE_DFB_API
1539  /* allocating buffer for pressure values */
1540  printf("allocating buffer for preassure values ...");
1541  if((d3_l.v_ptr=malloc(d3_l.max_x*d3_l.max_y*d3_l.max_z*sizeof(unsigned int)))==NULL)
1542  {
1543   puts("cannot allocate buffer for pressure values");
1544   return -1;
1545  }
1546  printf(" done\n");
1547  /* calc values */
1548  printf("calculating preassure values ...");
1549  calc_pressure(&d3_l,my_info.range);
1550  printf(" done\n");
1551  printf("finding maximum carbon concentration ...");
1552  max_extra=calc_max_extra(&d3_l);
1553  printf(" done\n");
1554
1555  while((quit==0) && (escape==0) && (nowait==0))
1556  {
1557   /* bahh! */
1558   if(switchmode==0) mode=0;
1559   if(switchmode==1) mode=1;
1560   if(switchmode==2) mode=2;
1561   if(switchmode==3) mode=3;
1562   /* end of bahh! */
1563   sprintf(xyz_txt,"x: %d  y: %d  z: %d (%d nm)",x+1,y+1,z+1,z*3);
1564   sprintf(status_txt,"status: %c",(*(d3_l.status+x+y*d3_l.max_x+z*d3_l.max_x*d3_l.max_y)&AMORPH)?'a':'c');
1565   sprintf(conc_txt,"carbon: %d",*(d3_l.extra+x+y*d3_l.max_x+z*d3_l.max_x*d3_l.max_y));
1566   sprintf(steps_txt,"step: end");
1567   sprintf(cc_txt,"total c: %d",my_info.cc);
1568   if(switchmode==0) strcpy(mode_txt,"view: a/c mode");
1569   if(switchmode==1) strcpy(mode_txt,"view: c conc mode");
1570   if(switchmode==2) strcpy(mode_txt,"view: a pressure mode");
1571   if(switchmode==3) strcpy(mode_txt,"view: a/c + profiles mode");
1572   d3_lattice_draw(&d3_l,x,y,z,25,arg_v,mode,max_extra,c_profile,ip_max,n_e_loss,ne_max);
1573   bmp=0;
1574   ac_distr=0;
1575   scan_event(&d3_l,&x,&y,&z,&quit,&escape,&switchmode,&bmp,&ac_distr);
1576   if(bmp) write_bmp(&d3_l,bmp,x,y,z,max_extra);
1577   if(ac_distr) write_ac_distr(&d3_l,ac_distr);
1578  }
1579
1580  d3_lattice_release(&d3_l);
1581 #endif
1582
1583  return 1;
1584 }