static void read_crystal(Stream *st, struct image *image, StreamReadFlags srf) { char line[1024]; char *rval = NULL; struct rvec as, bs, cs; int have_as = 0; int have_bs = 0; int have_cs = 0; int have_latt = 0; int have_cen = 0; int have_ua = 0; char centering = 'P'; char unique_axis = '*'; LatticeType lattice_type = L_TRICLINIC; Crystal *cr; int n; Crystal **crystals_new; cr = crystal_new(); if ( cr == NULL ) { ERROR("Failed to allocate crystal!\n"); return; } do { float u, v, w, lim, rad; char c; rval = fgets(line, 1023, st->fh); /* Trouble? */ if ( rval == NULL ) break; chomp(line); if ( (srf & STREAM_READ_UNITCELL) && (sscanf(line, "astar = %f %f %f", &u, &v, &w) == 3) ) { as.u = u*1e9; as.v = v*1e9; as.w = w*1e9; have_as = 1; } if ( (srf & STREAM_READ_UNITCELL) && (sscanf(line, "bstar = %f %f %f", &u, &v, &w) == 3) ) { bs.u = u*1e9; bs.v = v*1e9; bs.w = w*1e9; have_bs = 1; } if ( (srf & STREAM_READ_UNITCELL) && (sscanf(line, "cstar = %f %f %f", &u, &v, &w) == 3) ) { cs.u = u*1e9; cs.v = v*1e9; cs.w = w*1e9; have_cs = 1; } if ( (srf & STREAM_READ_UNITCELL) && (sscanf(line, "centering = %c", &c) == 1) ) { if ( !have_cen ) { centering = c; have_cen = 1; } else { ERROR("Duplicate centering ignored.\n"); } } if ( (srf & STREAM_READ_UNITCELL) && (sscanf(line, "unique_axis = %c", &c) == 1) ) { if ( !have_ua ) { unique_axis = c; have_ua = 1; } else { ERROR("Duplicate unique axis ignored.\n"); } } if ( (srf & STREAM_READ_UNITCELL) && (strncmp(line, "lattice_type = ", 15) == 0) ) { if ( !have_latt ) { lattice_type = lattice_from_str(line+15); have_latt = 1; } else { ERROR("Duplicate lattice type ignored.\n"); } } if ( strncmp(line, "num_saturated_reflections = ", 28) == 0 ) { int n = atoi(line+28); crystal_set_num_saturated_reflections(cr, n); } if ( sscanf(line, "diffraction_resolution_limit = %f nm^-1", &lim) == 1 ) { crystal_set_resolution_limit(cr, lim*1e9); } if ( sscanf(line, "profile_radius = %f nm^-1", &rad) == 1 ) { crystal_set_profile_radius(cr, rad*1e9); } if ( (strcmp(line, REFLECTION_START_MARKER) == 0) && (srf & STREAM_READ_REFLECTIONS) ) { RefList *reflist; /* The reflection list format in the stream diverges * after 2.2 */ if ( AT_LEAST_VERSION(st, 2, 2) ) { reflist = read_stream_reflections(st->fh); } else { reflist = read_stream_reflections_2_1(st->fh); } if ( reflist == NULL ) { ERROR("Failed while reading reflections\n"); break; } crystal_set_reflections(cr, reflist); } if ( strcmp(line, CRYSTAL_END_MARKER) == 0 ) break; } while ( 1 ); if ( have_as && have_bs && have_cs ) { UnitCell *cell; cell = crystal_get_cell(cr); if ( cell != NULL ) { ERROR("Duplicate cell found in stream!\n"); ERROR("I'll use the most recent one.\n"); cell_free(cell); } cell = cell_new_from_reciprocal_axes(as, bs, cs); if ( have_cen && have_ua && have_latt ) { cell_set_centering(cell, centering); cell_set_unique_axis(cell, unique_axis); cell_set_lattice_type(cell, lattice_type); } /* else keep default triclinic P */ crystal_set_cell(cr, cell); have_as = 0; have_bs = 0; have_cs = 0; have_latt = 0; have_ua = 0; have_cen = 0; } /* Unused at the moment */ crystal_set_mosaicity(cr, 0.0); /* Add crystal to the list for this image */ n = image->n_crystals+1; crystals_new = realloc(image->crystals, n*sizeof(Crystal *)); if ( crystals_new == NULL ) { ERROR("Failed to expand crystal list!\n"); } else { image->crystals = crystals_new; image->crystals[image->n_crystals++] = cr; } }
int write_chunk(Stream *st, struct image *i, struct hdfile *hdfile, int include_peaks, int include_reflections, struct event* ev) { int j; char *indexer; int ret = 0; fprintf(st->fh, CHUNK_START_MARKER"\n"); fprintf(st->fh, "Image filename: %s\n", i->filename); if ( i->event != NULL ) { fprintf(st->fh, "Event: %s\n", get_event_string(i->event)); } fprintf(st->fh, "Image serial number: %i\n", i->serial); indexer = indexer_str(i->indexed_by); fprintf(st->fh, "indexed_by = %s\n", indexer); free(indexer); fprintf(st->fh, "photon_energy_eV = %f\n", J_to_eV(ph_lambda_to_en(i->lambda))); fprintf(st->fh, "beam_divergence = %.2e rad\n", i->div); fprintf(st->fh, "beam_bandwidth = %.2e (fraction)\n", i->bw); copy_hdf5_fields(hdfile, i->copyme, st->fh, ev); if ( i->det != NULL ) { int j; double tclen = 0.0; for ( j=0; j<i->det->n_panels; j++ ) { tclen += i->det->panels[j].clen; } fprintf(st->fh, "average_camera_length = %f m\n", tclen / i->det->n_panels); for ( j=0; j<i->det->n_rigid_groups; j++ ) { struct rigid_group *rg = i->det->rigid_groups[j]; if ( !rg->have_deltas ) continue; fprintf(st->fh, "rg_delta_%s_fsx = %f\n", rg->name, rg->d_fsx); fprintf(st->fh, "rg_delta_%s_ssx = %f\n", rg->name, rg->d_ssx); fprintf(st->fh, "rg_delta_%s_cnx = %f\n", rg->name, rg->d_cnx); fprintf(st->fh, "rg_delta_%s_fsy = %f\n", rg->name, rg->d_fsy); fprintf(st->fh, "rg_delta_%s_ssy = %f\n", rg->name, rg->d_ssy); fprintf(st->fh, "rg_delta_%s_cny = %f\n", rg->name, rg->d_cny); } } fprintf(st->fh, "num_peaks = %lli\n", i->num_peaks); fprintf(st->fh, "num_saturated_peaks = %lli\n", i->num_saturated_peaks); if ( include_peaks ) { if ( AT_LEAST_VERSION(st, 2, 3) ) { ret = write_peaks_2_3(i, st->fh); } else { ret = write_peaks(i, st->fh); } } for ( j=0; j<i->n_crystals; j++ ) { if ( crystal_get_user_flag(i->crystals[j]) == 0 ) { ret = write_crystal(st, i->crystals[j], include_reflections); } } fprintf(st->fh, CHUNK_END_MARKER"\n"); fflush(st->fh); return ret; }
static void write_crystal(Stream *st, Crystal *cr, int include_reflections) { UnitCell *cell; RefList *reflist; double asx, asy, asz; double bsx, bsy, bsz; double csx, csy, csz; double a, b, c, al, be, ga; double rad; fprintf(st->fh, CRYSTAL_START_MARKER"\n"); cell = crystal_get_cell(cr); assert(cell != NULL); cell_get_parameters(cell, &a, &b, &c, &al, &be, &ga); fprintf(st->fh, "Cell parameters %7.5f %7.5f %7.5f nm," " %7.5f %7.5f %7.5f deg\n", a*1.0e9, b*1.0e9, c*1.0e9, rad2deg(al), rad2deg(be), rad2deg(ga)); cell_get_reciprocal(cell, &asx, &asy, &asz, &bsx, &bsy, &bsz, &csx, &csy, &csz); fprintf(st->fh, "astar = %+9.7f %+9.7f %+9.7f nm^-1\n", asx/1e9, asy/1e9, asz/1e9); fprintf(st->fh, "bstar = %+9.7f %+9.7f %+9.7f nm^-1\n", bsx/1e9, bsy/1e9, bsz/1e9); fprintf(st->fh, "cstar = %+9.7f %+9.7f %+9.7f nm^-1\n", csx/1e9, csy/1e9, csz/1e9); fprintf(st->fh, "lattice_type = %s\n", str_lattice(cell_get_lattice_type(cell))); fprintf(st->fh, "centering = %c\n", cell_get_centering(cell)); fprintf(st->fh, "unique_axis = %c\n", cell_get_unique_axis(cell)); rad = crystal_get_profile_radius(cr); fprintf(st->fh, "profile_radius = %.5f nm^-1\n", rad/1e9); reflist = crystal_get_reflections(cr); if ( reflist != NULL ) { fprintf(st->fh, "diffraction_resolution_limit" " = %.2f nm^-1 or %.2f A\n", crystal_get_resolution_limit(cr)/1e9, 1e10 / crystal_get_resolution_limit(cr)); fprintf(st->fh, "num_reflections = %i\n", num_reflections(reflist)); fprintf(st->fh, "num_saturated_reflections = %lli\n", crystal_get_num_saturated_reflections(cr)); } if ( include_reflections ) { if ( reflist != NULL ) { fprintf(st->fh, REFLECTION_START_MARKER"\n"); if ( AT_LEAST_VERSION(st, 2, 2) ) { write_stream_reflections(st->fh, reflist); } else { /* This function writes like a normal reflection * list was written in stream 2.1 */ write_stream_reflections_2_1(st->fh, reflist); } fprintf(st->fh, REFLECTION_END_MARKER"\n"); } else { fprintf(st->fh, "No integrated reflections.\n"); } } fprintf(st->fh, CRYSTAL_END_MARKER"\n"); }
/* Read the next chunk from a stream and fill in 'image' */ int read_chunk_2(Stream *st, struct image *image, StreamReadFlags srf) { char line[1024]; char *rval = NULL; int have_filename = 0; int have_ev = 0; if ( find_start_of_chunk(st->fh) ) return 1; image->lambda = -1.0; image->features = NULL; image->crystals = NULL; image->n_crystals = 0; image->event = NULL; image->stuff_from_stream = NULL; if ( (srf & STREAM_READ_REFLECTIONS) || (srf & STREAM_READ_UNITCELL) ) { srf |= STREAM_READ_CRYSTALS; } do { long long num_peaks; int ser; float div, bw; rval = fgets(line, 1023, st->fh); /* Trouble? */ if ( rval == NULL ) break; chomp(line); if ( strncmp(line, "Image filename: ", 16) == 0 ) { image->filename = strdup(line+16); have_filename = 1; } if ( strncmp(line, "Event: ", 7) == 0 ) { image->event = get_event_from_event_string(line+7); } if ( strncmp(line, "indexed_by = ", 13) == 0 ) { IndexingMethod *list; list = build_indexer_list(line+13); image->indexed_by = list[0]; free(list); have_filename = 1; } if ( strncmp(line, "photon_energy_eV = ", 19) == 0 ) { image->lambda = ph_en_to_lambda(eV_to_J(atof(line+19))); have_ev = 1; } if ( sscanf(line, "beam_divergence = %e rad", &div) == 1 ) { image->div = div; } if ( sscanf(line, "beam_bandwidth = %f %%", &bw) == 1 ) { image->bw = bw/100.0; } if ( sscanf(line, "num_peaks = %lld %%", &num_peaks) == 1 ) { image->num_peaks = num_peaks; } if ( sscanf(line, "Image serial number: %i", &ser) == 1 ) { image->serial = ser; } if ( strncmp(line, "camera_length_", 14) == 0 ) { if ( image->det != NULL ) { int k; char name[1024]; struct panel *p; for ( k=0; k<strlen(line)-14; k++ ) { char ch = line[k+14]; name[k] = ch; if ( (ch == ' ') || (ch == '=') ) { name[k] = '\0'; break; } } p = find_panel_by_name(image->det, name); if ( p == NULL ) { ERROR("No panel '%s'\n", name); } else { p->clen = atof(line+14+k+3); } } } if ( strncmp(line, "hdf5", 3) == 0 ) { int fail; fail = read_and_store_hdf5_field(image, line); if ( fail ) { ERROR("Failed to read hd5 fields from stream.\n"); return 1; } } if ( (srf & STREAM_READ_PEAKS) && strcmp(line, PEAK_LIST_START_MARKER) == 0 ) { int fail; if ( AT_LEAST_VERSION(st, 2, 3) ) { fail = read_peaks_2_3(st->fh, image); } else { fail = read_peaks(st->fh, image); } if ( fail ) { ERROR("Failed while reading peaks\n"); return 1; } } if ( (srf & STREAM_READ_CRYSTALS) && (strcmp(line, CRYSTAL_START_MARKER) == 0) ) { read_crystal(st, image, srf); } /* A chunk must have at least a filename and a wavelength, * otherwise it's incomplete */ if ( strcmp(line, CHUNK_END_MARKER) == 0 ) { if ( have_filename && have_ev ) return 0; ERROR("Incomplete chunk found in input file.\n"); return 1; } } while ( 1 ); if ( !feof(st->fh) ) { ERROR("Error reading stream.\n"); } return 1; /* Either error or EOF, don't care because we will complain * on the terminal if it was an error. */ }