2 * increases the resolution of a conformation by interpolation
7 /* filled in by characterise_input: */
8 static int shift, oldxbits, oldybits, oldx, oldy, oldsz, inc;
10 /* filled in by read_input: */
11 static struct Vertices all;
13 static void characterise_input(void) {
17 r= fstat(0,&stab); if (r) diee("fstat input to find length");
19 if (!stab.st_size || stab.st_size % (sizeof(double)*D3) ||
20 stab.st_size > INT_MAX)
21 fail("input file is not reasonable whole number of doubles\n");
23 oldsz= stab.st_size / (sizeof(double)*D3);
25 shift < XBITS+1 && shift < YBITS+1;
30 oldy= (1<<oldybits)-1;
31 fprintf(stderr,"sizeof(double)=%d XYBITS=%d,%d, XY=%d*%d=%d"
32 " oldsz=%d shift=%d oldxybits=%d,%d oldxy=%d*%d=%d\n",
33 (int)sizeof(double), XBITS,YBITS, X,Y,N,
34 oldsz,shift,oldxbits,oldybits,oldx,oldy,oldx*oldy);
35 if (oldx*oldy == oldsz) goto found;
37 fail("input file size cannot be interpolated to target file size\n");
41 fprintf(stderr,"inc=%d\n",inc);
44 static void read_input(void) {
47 for (oy=y=0; y<Y; oy++, y+=inc) {
48 fprintf(stderr, "y=%2d>%2d", oy,y);
49 for (ox=x=0; x<X; ox++, x+=inc) {
51 ov= (oy << oldxbits) | ox;
53 fprintf(stderr, " 0%02o->0x%02x", ov, v);
54 if (fread(all.a[v], sizeof(double), D3, stdin) != D3)
61 /* We use GSL's interpolation functions. Each xa array is simple
62 * integers, and we do the interpolation three times for each line
63 * of topologically colinear vertices (once, separately, for each of
64 * the three spatial coordinates in the ya array). The `horizontal'
65 * lines are done with periodic boundary conditions, obviously.
67 * This directly gives the required additional vertices:
69 * ,O. O original vertex
71 * ,* - - *. dashed lines are new edges,
72 * / ` ' \ not directly represented
73 * O----`*'----O or manipulated by this program
77 #define NEXTV (v= EDGE_END2(v,direction))
79 static void interpolate_line(int startvertex,
80 int direction /* edge number */,
82 double xa[norig+1], ya[D3][norig+1], n;
83 const gsl_interp_type *it;
85 gsl_interp_accel *accel;
88 for (i=0, v=startvertex;
90 i++, NEXTV, assert(v>=0), NEXTV) {
95 K ya[k][i]= all.a[v][k];
100 it= v>=0 ? gsl_interp_cspline_periodic : gsl_interp_cspline;
103 interp= gsl_interp_alloc(it,n); if (!interp) diee("gsl_interp_alloc");
104 accel= gsl_interp_accel_alloc(); if(!accel) diee("gsl_interp_accel_alloc");
105 GA( gsl_interp_init(interp,xa,ya[k],n) );
107 for (i=0, v=startvertex;
110 assert(v>=0); NEXTV; assert(v>=0);
111 GA( gsl_interp_eval_e(interp,xa,ya[k], i+0.5, accel, &all.a[v][k]) );
114 gsl_interp_accel_free(accel);
115 gsl_interp_free(interp);
119 static void interpolate(void) {
122 if (shift!=1) fail("only interpolation by factor of 2 supported\n");
124 for (y=0; y<Y; y+=inc) {
125 interpolate_line(y<<YSHIFT, 0, oldx);
127 for (x=0; x<X; x+=inc) {
128 interpolate_line(x, 5, oldy);
129 interpolate_line(x, 4, oldy);
133 static void write_output(void) {
134 if (fwrite(all.a,sizeof(all.a),1,stdout) != 1) diee("fwrite");
137 int main(int argc, const char **argv) {
138 if (argc!=1 || isatty(0) || isatty(1))
139 { fputs("usage: interpolate <INPUT.cfm >OUTPUT.cfm\n",stderr); exit(8); }
141 characterise_input();
145 if (fclose(stdout)) diee("fclose stdout");