static int read_fixed_atoms(fio_fd fd, int N, int num_free, const int *indexes, int reverseEndian, const float *fixedcoords, float *freeatoms, float *pos, int charmm) { int i, input_integer[2], rec_scale; if(charmm & DCD_HAS_64BIT_REC) { rec_scale=RECSCALE64BIT; } else { rec_scale=RECSCALE32BIT; } /* Read leading integer */ input_integer[1]=0; if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; if (reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != 4*num_free) return DCD_BADFORMAT; /* Read free atom coordinates */ if (fio_fread(freeatoms, 4*num_free, 1, fd) != 1) return DCD_BADREAD; if (reverseEndian) swap4_aligned(freeatoms, num_free); /* Copy fixed and free atom coordinates into position buffer */ memcpy(pos, fixedcoords, 4*N); for (i=0; i<num_free; i++) pos[indexes[i]-1] = freeatoms[i]; /* Read trailing integer */ input_integer[1]=0; if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; if (reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != 4*num_free) return DCD_BADFORMAT; return DCD_SUCCESS; }
void IMDSimBlocking::send_forces(int num, int *ind, float *forces) { // Total data sent will be one int and three floats for each atom if (!isConnected()) return; if (need2flip) { swap4_aligned(ind, num); swap4_aligned(forces, 3*num); } if (imd_send_mdcomm(sock, num, ind, forces)) { msgErr << "Error sending MDComm indices+forces" << sendmsg; disconnect(); } }
static int read_charmm_extrablock(fio_fd fd, int charmm, int reverseEndian, float *unitcell) { int i, input_integer[2], rec_scale; if (charmm & DCD_HAS_64BIT_REC) { rec_scale = RECSCALE64BIT; } else { rec_scale = RECSCALE32BIT; } if ((charmm & DCD_IS_CHARMM) && (charmm & DCD_HAS_EXTRA_BLOCK)) { /* Leading integer must be 48 */ input_integer[1] = 0; if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; if (reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) == 48) { double tmp[6]; if (fio_fread(tmp, 48, 1, fd) != 1) return DCD_BADREAD; if (reverseEndian) swap8_aligned(tmp, 6); for (i=0; i<6; i++) unitcell[i] = (float)tmp[i]; } else { /* unrecognized block, just skip it */ if (fio_fseek(fd, (input_integer[0]+input_integer[1]), FIO_SEEK_CUR)) return DCD_BADREAD; } if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; } return DCD_SUCCESS; }
void IMDSimBlocking::process_energies(int32 /* length */) { if (imd_recv_energies(sock, &imdEnergies)) { msgErr << "Error reading energies!" << sendmsg; disconnect(); } else { if (need2flip) swap4_aligned(&imdEnergies, sizeof(imdEnergies) / 4); } }
static int read_pbeq_data(void *v, int set, float *datablock, float *colorblock) { pbeq_t *pbeq = (pbeq_t *)v; int ndata = pbeq->ndata; int nclx = pbeq->nclx; int ncly = pbeq->ncly; int nclz = pbeq->nclz; FILE *fd = pbeq->fd; int trash; // skip first Fortran length record for // WRITE(UNIT)(PHI(I),I=1,NCLX*NCLY*NCLZ) if (fread(&trash, 4, 1, fd) != 1) return MOLFILE_ERROR; /* Read the densities. Order for file is z fast, y medium, x slow */ int x, y, z; int count=0; for (x=0; x<nclx; x++) { for (y=0; y<ncly; y++) { for (z=0; z<nclz; z++) { int addr = z*nclx*ncly + y*nclx + x; if (fread(datablock + addr, 4, 1, fd) != 1) { printf("pbeqplugin) Error reading potential map cell: %d,%d,%d\n", x, y, z); printf("pbeqplugin) offset: %d\n", ftell(fd)); return MOLFILE_ERROR; } count++; } } } #if 0 // skip last Fortran length record for // WRITE(UNIT)(PHI(I),I=1,NCLX*NCLY*NCLZ) if (fread(&trash, 4, 1, fd) != 1) return NULL; // print debugging info for early versions printf("pbeqplugin) read %d phi values from block\n", count); for (x=0; x<1000000; x++) { int trash; if (fread(&trash, 4, 1, fd) != 1) { printf("pbeqplugin) read %d extra phi values past the end of the block\n", x); break; } } #endif if (pbeq->swap) { swap4_aligned(datablock, ndata); } return MOLFILE_SUCCESS; }
static int read_ccp4_data(void *v, int set, float *datablock, float *colorblock) { ccp4_t *ccp4 = (ccp4_t *)v; float *rowdata; int x, y, z, xSize, ySize, zSize, xySize, extent[3], coord[3]; FILE *fd = ccp4->fd; xSize = ccp4->vol[0].xsize; ySize = ccp4->vol[0].ysize; zSize = ccp4->vol[0].zsize; xySize = xSize * ySize; // coord = <col, row, sec> // extent = <colSize, rowSize, secSize> extent[ccp4->xyz2crs[0]] = xSize; extent[ccp4->xyz2crs[1]] = ySize; extent[ccp4->xyz2crs[2]] = zSize; rowdata = new float[extent[0]]; fseek(fd, ccp4->dataOffset, SEEK_SET); for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { // Read an entire row of data from the file, then write it into the // datablock with the correct slice ordering. if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); return MOLFILE_ERROR; } if ( fread(rowdata, sizeof(float), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); return MOLFILE_ERROR; } for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + y*xSize + z*xySize] = rowdata[coord[0]]; } } } if (ccp4->swap == 1) swap4_aligned(datablock, xySize * zSize); delete [] rowdata; return MOLFILE_SUCCESS; }
static int read_js_timestep(void *v, int natoms, molfile_timestep_t *ts) { jshandle *js = (jshandle *)v; int framelen = (natoms * 3 * sizeof(float)) + (6 * sizeof(double));; /* if we have a valid ts pointer, read the timestep, otherwise skip it */ if (ts != NULL) { int readlen; fio_iovec iov[2]; double unitcell[6]; unitcell[0] = unitcell[2] = unitcell[5] = 1.0f; unitcell[1] = unitcell[3] = unitcell[4] = 90.0f; /* setup the I/O vector */ iov[0].iov_base = (fio_caddr_t) ts->coords; /* read coordinates */ iov[0].iov_len = natoms * 3 * sizeof(float); iov[1].iov_base = (fio_caddr_t) &unitcell[0]; /* read PBC unit cell */ iov[1].iov_len = 6 * sizeof(double); /* Do all of the reads with a single syscall, for peak efficiency. */ /* On smart kernels, readv() causes only one context switch, and */ /* can effeciently scatter the reads to the various buffers. */ readlen = fio_readv(js->fd, &iov[0], 2); /* check the number of read bytes versus what we expected */ if (readlen != framelen) return MOLFILE_EOF; /* perform byte swapping if necessary */ if (js->reverseendian) { swap4_aligned(ts->coords, natoms * 3); swap8_aligned(unitcell, 6); } /* copy unit cell values into VMD */ ts->A = unitcell[0]; ts->B = unitcell[1]; ts->C = unitcell[2]; ts->alpha = 90.0 - asin(unitcell[3]) * 90.0 / M_PI_2; ts->beta = 90.0 - asin(unitcell[4]) * 90.0 / M_PI_2; ts->gamma = 90.0 - asin(unitcell[5]) * 90.0 / M_PI_2; } else { /* skip this frame, seek to the next frame */ if (fio_fseek(js->fd, framelen, FIO_SEEK_CUR)) return MOLFILE_EOF; } return MOLFILE_SUCCESS; }
static int read_plt_data(void *v, int set, float *datablock, float *colorblock) { plt_t *plt = (plt_t *)v; int swap, ndata; FILE *fd = plt->fd; swap = plt->swap; ndata = plt->vol[0].xsize * plt->vol[0].ysize * plt->vol[0].zsize; // Read the densities. Order for file is x fast, y medium, z slow if ( fread(datablock, sizeof(float), ndata, fd) != ndata ) { fprintf(stderr, "pltplugin) Error reading data, not enough values read.\n"); return MOLFILE_ERROR; } if (swap) swap4_aligned(datablock, ndata); return MOLFILE_SUCCESS; }
static int read_charmm_4dim(fio_fd fd, int charmm, int reverseEndian) { int input_integer[2],rec_scale; if (charmm & DCD_HAS_64BIT_REC) { rec_scale=RECSCALE64BIT; } else { rec_scale=RECSCALE32BIT; } /* If this is a CHARMm file and contains a 4th dimension block, */ /* we must skip past it to avoid problems */ if ((charmm & DCD_IS_CHARMM) && (charmm & DCD_HAS_4DIMS)) { input_integer[1]=0; if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; if (reverseEndian) swap4_aligned(input_integer, rec_scale); if (fio_fseek(fd, (input_integer[0]+input_integer[1]), FIO_SEEK_CUR)) return DCD_BADREAD; if (fio_fread(input_integer, sizeof(int), rec_scale, fd) != rec_scale) return DCD_BADREAD; } return DCD_SUCCESS; }
static int read_spider_data(void *v, int set, float *datablock, float *colorblock) { spider_t *vol = (spider_t *)v; FILE *fd = vol->fd; int xsize, ysize, zsize, xysize, total; xsize = vol->vol[0].xsize; ysize = vol->vol[0].ysize; zsize = vol->vol[0].zsize; xysize = xsize * ysize; total = xysize * zsize; // Read the values from the file fread(datablock, total * sizeof(float), 1, fd); // perform byte swapping if necessary if (vol->byteswap) swap4_aligned(datablock, total); return MOLFILE_SUCCESS; }
static void *open_plt_read(const char *filepath, const char *filetype, int *natoms) { FILE *fd; plt_t *plt; int swap=0; // File header data: int intHeader[5]; float floatHeader[6]; fd = fopen(filepath, "rb"); if (!fd) { fprintf(stderr, "pltplugin) Error opening file.\n"); return NULL; } // Integer header info: rank (always 3), surface type, z length, y length, // x length. fread(intHeader, sizeof(int), 5, fd); if (intHeader[0] != 3) { // check if the bytes need to be swapped swap4_aligned(intHeader, 5); if (intHeader[0] == 3) swap = 1; else { fprintf(stderr, "pltplugin) Incorrect header.\n"); return NULL; } } // Float header info: z min, z max, y min, y max, xmin, x max. fread(floatHeader, sizeof(float), 6, fd); if (swap) swap4_aligned(floatHeader, 6); // Allocate and initialize the plt structure plt = new plt_t; plt->fd = fd; plt->vol = NULL; *natoms = MOLFILE_NUMATOMS_NONE; plt->nsets = 1; // this file contains only one data set plt->swap = swap; plt->vol = new molfile_volumetric_t[1]; strcpy(plt->vol[0].dataname, "PLT Electron Density Map"); // Best guesses for unit cell information, as none is included in the plt // file format. plt->vol[0].origin[0] = floatHeader[4]; plt->vol[0].origin[1] = floatHeader[2]; plt->vol[0].origin[2] = floatHeader[0]; plt->vol[0].xaxis[0] = floatHeader[5] - floatHeader[4]; plt->vol[0].xaxis[1] = 0; plt->vol[0].xaxis[2] = 0; plt->vol[0].yaxis[0] = 0; plt->vol[0].yaxis[1] = floatHeader[3] - floatHeader[2]; plt->vol[0].yaxis[2] = 0; plt->vol[0].zaxis[0] = 0; plt->vol[0].zaxis[1] = 0; plt->vol[0].zaxis[2] = floatHeader[1] - floatHeader[0]; plt->vol[0].xsize = intHeader[4]; plt->vol[0].ysize = intHeader[3]; plt->vol[0].zsize = intHeader[2]; plt->vol[0].has_color = 0; return plt; }
/* * Read the header information from a dcd file. * Input: fd - a file struct opened for binary reading. * Output: 0 on success, negative error code on failure. * Side effects: *natoms set to number of atoms per frame * *nsets set to number of frames in dcd file * *istart set to starting timestep of dcd file * *nsavc set to timesteps between dcd saves * *delta set to value of trajectory timestep * *nfixed set to number of fixed atoms * *freeind may be set to heap-allocated space * *reverse set to one if reverse-endian, zero if not. * *charmm set to internal code for handling charmm data. */ static int read_dcdheader(fio_fd fd, int *N, int *NSET, int *ISTART, int *NSAVC, double *DELTA, int *NAMNF, int **FREEINDEXES, float **fixedcoords, int *reverseEndian, int *charmm) { unsigned int input_integer[2]; /* buffer space */ int i, ret_val, rec_scale; union hdrufb_union { char charvalue[84]; /* char buffer used to store header */ int intvalue; } hdrbuf; int NTITLE; int dcdcordmagic; char *corp = (char *) &dcdcordmagic; /* coordinate dcd file magic string 'CORD' */ corp[0] = 'C'; corp[1] = 'O'; corp[2] = 'R'; corp[3] = 'D'; /* First thing in the file should be an 84. * some 64-bit compiles have a 64-bit record length indicator, * so we have to read two ints and check in a more complicated * way. :-( */ ret_val = READ(fd, input_integer, 2*sizeof(unsigned int)); CHECK_FREAD(ret_val, "reading first int from dcd file"); CHECK_FEOF(ret_val, "reading first int from dcd file"); /* Check magic number in file header and determine byte order*/ if ((input_integer[0]+input_integer[1]) == 84) { *reverseEndian=0; rec_scale=RECSCALE64BIT; printf("dcdplugin) detected CHARMM -i8 64-bit DCD file of native endianness\n"); } else if (input_integer[0] == 84 && input_integer[1] == dcdcordmagic) { *reverseEndian=0; rec_scale=RECSCALE32BIT; printf("dcdplugin) detected standard 32-bit DCD file of native endianness\n"); } else { /* now try reverse endian */ swap4_aligned(input_integer, 2); /* will have to unswap magic if 32-bit */ if ((input_integer[0]+input_integer[1]) == 84) { *reverseEndian=1; rec_scale=RECSCALE64BIT; printf("dcdplugin) detected CHARMM -i8 64-bit DCD file of opposite endianness\n"); } else { swap4_aligned(&input_integer[1], 1); /* unswap magic (see above) */ if (input_integer[0] == 84 && input_integer[1] == dcdcordmagic) { *reverseEndian=1; rec_scale=RECSCALE32BIT; printf("dcdplugin) detected standard 32-bit DCD file of opposite endianness\n"); } else { /* not simply reversed endianism or -i8, something rather more evil */ printf("dcdplugin) unrecognized DCD header:\n"); printf("dcdplugin) [0]: %10d [1]: %10d\n", input_integer[0], input_integer[1]); printf("dcdplugin) [0]: 0x%08x [1]: 0x%08x\n", input_integer[0], input_integer[1]); return DCD_BADFORMAT; } } } /* check for magic string, in case of long record markers */ if (rec_scale == RECSCALE64BIT) { ret_val = READ(fd, input_integer, sizeof(unsigned int)); if (input_integer[0] != dcdcordmagic) { printf("dcdplugin) failed to find CORD magic in CHARMM -i8 64-bit DCD file\n"); return DCD_BADFORMAT; } } /* Buffer the entire header for random access */ ret_val = READ(fd, hdrbuf.charvalue, 80); CHECK_FREAD(ret_val, "buffering header"); CHECK_FEOF(ret_val, "buffering header"); /* CHARMm-genereate DCD files set the last integer in the */ /* header, which is unused by X-PLOR, to its version number. */ /* Checking if this is nonzero tells us this is a CHARMm file */ /* and to look for other CHARMm flags. */ if (*((int *) (hdrbuf.charvalue + 76)) != 0) { (*charmm) = DCD_IS_CHARMM; if (*((int *) (hdrbuf.charvalue + 40)) != 0) (*charmm) |= DCD_HAS_EXTRA_BLOCK; if (*((int *) (hdrbuf.charvalue + 44)) == 1) (*charmm) |= DCD_HAS_4DIMS; if (rec_scale == RECSCALE64BIT) (*charmm) |= DCD_HAS_64BIT_REC; } else { (*charmm) = DCD_IS_XPLOR; /* must be an X-PLOR format DCD file */ } if (*charmm & DCD_IS_CHARMM) { /* CHARMM and NAMD versions 2.1b1 and later */ printf("dcdplugin) CHARMM format DCD file (also NAMD 2.1 and later)\n"); } else { /* CHARMM and NAMD versions prior to 2.1b1 */ printf("dcdplugin) X-PLOR format DCD file (also NAMD 2.0 and earlier)\n"); } /* Store the number of sets of coordinates (NSET) */ (*NSET) = *((int *)(hdrbuf.charvalue)); if (*reverseEndian) swap4_unaligned(NSET, 1); /* Store ISTART, the starting timestep */ (*ISTART) = *((int *) (hdrbuf.charvalue + 4)); if (*reverseEndian) swap4_unaligned(ISTART, 1); /* Store NSAVC, the number of timesteps between dcd saves */ (*NSAVC) = *((int *) (hdrbuf.charvalue + 8)); if (*reverseEndian) swap4_unaligned(NSAVC, 1); /* Store NAMNF, the number of fixed atoms */ (*NAMNF) = *((int *) (hdrbuf.charvalue + 32)); if (*reverseEndian) swap4_unaligned(NAMNF, 1); /* Read in the timestep, DELTA */ /* Note: DELTA is stored as a double with X-PLOR but as a float with CHARMm */ if ((*charmm) & DCD_IS_CHARMM) { float ftmp; ftmp = *((float *)(hdrbuf.charvalue+36)); /* is this safe on Alpha? */ if (*reverseEndian) swap4_aligned(&ftmp, 1); *DELTA = (double)ftmp; } else { (*DELTA) = *((double *)(hdrbuf.charvalue + 36)); if (*reverseEndian) swap8_unaligned(DELTA, 1); } /* Get the end size of the first block */ ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading second 84 from dcd file"); CHECK_FEOF(ret_val, "reading second 84 from dcd file"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if (rec_scale == RECSCALE64BIT) { if ((input_integer[0]+input_integer[1]) != 84) { return DCD_BADFORMAT; } } else { if (input_integer[0] != 84) { return DCD_BADFORMAT; } } /* Read in the size of the next block */ input_integer[1] = 0; ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading size of title block"); CHECK_FEOF(ret_val, "reading size of title block"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if ((((input_integer[0]+input_integer[1])-4) % 80) == 0) { /* Read NTITLE, the number of 80 character title strings there are */ ret_val = READ(fd, &NTITLE, sizeof(int)); CHECK_FREAD(ret_val, "reading NTITLE"); CHECK_FEOF(ret_val, "reading NTITLE"); if (*reverseEndian) swap4_aligned(&NTITLE, 1); for (i=0; i<NTITLE; i++) { fio_fseek(fd, 80, FIO_SEEK_CUR); CHECK_FEOF(ret_val, "reading TITLE"); } /* Get the ending size for this block */ ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading size of title block"); CHECK_FEOF(ret_val, "reading size of title block"); } else { return DCD_BADFORMAT; } /* Read in an integer '4' */ input_integer[1] = 0; ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading a '4'"); CHECK_FEOF(ret_val, "reading a '4'"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != 4) { return DCD_BADFORMAT; } /* Read in the number of atoms */ ret_val = READ(fd, N, sizeof(int)); CHECK_FREAD(ret_val, "reading number of atoms"); CHECK_FEOF(ret_val, "reading number of atoms"); if (*reverseEndian) swap4_aligned(N, 1); /* Read in an integer '4' */ input_integer[1] = 0; ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading a '4'"); CHECK_FEOF(ret_val, "reading a '4'"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != 4) { return DCD_BADFORMAT; } *FREEINDEXES = NULL; *fixedcoords = NULL; if (*NAMNF != 0) { (*FREEINDEXES) = (int *) calloc(((*N)-(*NAMNF)), sizeof(int)); if (*FREEINDEXES == NULL) return DCD_BADMALLOC; *fixedcoords = (float *) calloc((*N)*4 - (*NAMNF), sizeof(float)); if (*fixedcoords == NULL) return DCD_BADMALLOC; /* Read in index array size */ input_integer[1]=0; ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading size of index array"); CHECK_FEOF(ret_val, "reading size of index array"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != ((*N)-(*NAMNF))*4) { return DCD_BADFORMAT; } ret_val = READ(fd, (*FREEINDEXES), ((*N)-(*NAMNF))*sizeof(int)); CHECK_FREAD(ret_val, "reading size of index array"); CHECK_FEOF(ret_val, "reading size of index array"); if (*reverseEndian) swap4_aligned((*FREEINDEXES), ((*N)-(*NAMNF))); input_integer[1]=0; ret_val = READ(fd, input_integer, rec_scale*sizeof(int)); CHECK_FREAD(ret_val, "reading size of index array"); CHECK_FEOF(ret_val, "reading size of index array"); if (*reverseEndian) swap4_aligned(input_integer, rec_scale); if ((input_integer[0]+input_integer[1]) != ((*N)-(*NAMNF))*4) { return DCD_BADFORMAT; } } return DCD_SUCCESS; }
void cMRC<T>::readHeader(const std::string& fileName, cMapHeader& header) { const std::string funcName("void cMRC::readHeader(" "const std::string& fileName, " "cMapHeader& header)"); checkExtension(fileName); std::ifstream fileHandle; fileHandle.open(fileName.c_str(), std::ifstream::binary); assure(fileHandle, fileName.c_str()); int map_dim[3], data_mode, origin[3], cell_grid[3], axes_order[3]; float cell_dim[3], cell_angle[3]; float density_min, density_max, density_mean; int spacegroup, sym_byte; char mapStamp[] = " "; fileHandle.read((char*) map_dim, 3*sizeof(int)); // NX, NY, NZ fileHandle.read((char*) &data_mode, sizeof(int)); // MODE fileHandle.read((char*) origin, 3*sizeof(int)); // NXSTART, NYSTART, NZSTART fileHandle.read((char*) cell_grid, 3*sizeof(int)); // MX, MY, MZ fileHandle.read((char*) cell_dim, 3*sizeof(float)); // CELLA fileHandle.read((char*) cell_angle, 3*sizeof(float)); // CELLB fileHandle.read((char*) axes_order, 3*sizeof(int)); // MAPC, MAPR, MAPS fileHandle.read((char*) &density_min, sizeof(float)); // DMIN fileHandle.read((char*) &density_max, sizeof(float)); // DMAX fileHandle.read((char*) &density_mean, sizeof(float)); // DMEAN fileHandle.read((char*) &spacegroup, sizeof(int)); // ISPG fileHandle.read((char*) &sym_byte, sizeof(int)); // NSYMBT fileHandle.seekg(208, std::ios::beg); fileHandle.read((char*) mapStamp, 4*sizeof(char)); // MAP // check for the need of byte swapping header.edian_swap = false; if (map_dim[0] < 0 || map_dim[0] > 100000 || map_dim[1] < 0 || map_dim[1] > 100000 || map_dim[2] < 0 || map_dim[2] > 100000) { header.edian_swap = true; } if (header.edian_swap) { swap4_aligned(map_dim, 3); swap4_aligned(&data_mode, 1); swap4_aligned(origin, 3); swap4_aligned(cell_grid, 3); swap4_aligned(cell_dim, 3); swap4_aligned(cell_angle, 3); swap4_aligned(axes_order, 3); swap4_aligned(&density_min, 1); swap4_aligned(&density_max, 1); swap4_aligned(&density_mean, 1); swap4_aligned(&spacegroup, 1); swap4_aligned(&sym_byte, 1); swap4_aligned(mapStamp, 1); } // check data mode and 'MAP' stamp require(data_mode >=0 || data_mode <= 2, funcName + ": non-supported data type (data_mode != 0,1,2) in" + fileName); if (map_dim[2] != 1) { require(strcmp(mapStamp, "MAP ") == 0, funcName + ": cannot detect the 'MAP' string in " + fileName); } // check symmetry validity size_t fileSize, dataOffset, nelement = (size_t) map_dim[0] * (size_t) map_dim[1] * (size_t) map_dim[2]; fileHandle.seekg(0, std::ios::end); fileSize = fileHandle.tellg(); switch (data_mode) { case 0: // int8 dataOffset = fileSize - 1 * nelement; break; case 1: // int16 dataOffset = fileSize - 2 * nelement; break; case 2: // float32 dataOffset = fileSize - 4 * nelement; break; case 6: // uint16 dataOffset = fileSize - 2 * nelement; break; default: ERROR(funcName, "unsupported data mode in reading " + fileName); } if ((int) dataOffset != (CCP4_HEADER_SIZE + sym_byte)) { if (dataOffset < CCP4_HEADER_SIZE) { ERROR(funcName, "file " + fileName + " has size smaller than expected"); } else if (dataOffset == CCP4_HEADER_SIZE) { ERROR(funcName, "the symmetry record in " + fileName + " is bogus"); } else { ERROR(funcName, "file " + fileName + " has size larger than expected"); } } // save header information header.file_name = fileName; header.data_mode = data_mode; header.spacegroup = spacegroup; header.sym_byte = sym_byte; header.cell_dim[0] = cell_dim[0]; header.cell_dim[1] = cell_dim[1]; header.cell_dim[2] = cell_dim[2]; header.cell_angle[0] = cell_angle[0]; header.cell_angle[1] = cell_angle[1]; header.cell_angle[2] = cell_angle[2]; header.map_dim[0] = map_dim[0]; header.map_dim[1] = map_dim[1]; header.map_dim[2] = map_dim[2]; header.origin[0] = origin[0]; header.origin[1] = origin[1]; header.origin[2] = origin[2]; header.cell_grid[0] = cell_grid[0]; header.cell_grid[1] = cell_grid[1]; header.cell_grid[2] = cell_grid[2]; header.axes_order[0] = axes_order[0]; header.axes_order[1] = axes_order[1]; header.axes_order[2] = axes_order[2]; header.min = density_min; header.max = density_max; header.mean = density_mean; fileHandle.close(); }
void cMRC<T>::readData(const std::string& fileName, cData3<T>& object, cMapHeader& header) { const std::string funcName("void cMRC::readData(const std::string& fileName, " "cData3<T>& object, cMapHeader& header)"); checkExtension(fileName); std::ifstream fileHandle; fileHandle.open(fileName.c_str(), std::ifstream::binary); assure(fileHandle, fileName.c_str()); // allocate new memory object.memReAlloc(cVector3<size_t>((size_t) header.map_dim[0], (size_t) header.map_dim[1], (size_t) header.map_dim[2])); // seek to data starting point fileHandle.seekg(CCP4_HEADER_SIZE + header.sym_byte, std::ios::beg); unsigned char* bufferData = NULL; size_t bufferLength = (size_t) std::pow(2,header.data_mode) * header.getNelement(); array_new(bufferData, bufferLength); fileHandle.read((char*) bufferData, bufferLength); switch (header.data_mode) { case 0: // int8 array_index_col2row((int8_t*) bufferData, object.getAddrData(), object.getNrow(), object.getNcol(), object.getNsec()); break; case 1: // int16 if (header.edian_swap) { swap2_aligned(bufferData, header.getNelement()); } array_index_col2row((int16_t*) bufferData, object.getAddrData(), object.getNrow(), object.getNcol(), object.getNsec()); break; case 2: // float32 if (header.edian_swap) { swap4_aligned(bufferData, header.getNelement()); } array_index_col2row((float*) bufferData, object.getAddrData(), object.getNrow(), object.getNcol(), object.getNsec()); break; case 6: // uint16 if (header.edian_swap) { swap2_aligned(bufferData, header.getNelement()); } array_index_col2row((uint16_t*) bufferData, object.getAddrData(), object.getNrow(), object.getNcol(), object.getNsec()); break; default: ERROR(funcName, "unsupported data mode in reading " + fileName); } array_delete(bufferData); fileHandle.close(); }
static void *open_pbeq_read(const char *filepath, const char *filetype, int *natoms) { FILE *fd; pbeq_t *pbeq; int nclx, ncly, nclz; int trash, length; double dcel; double xbcen, ybcen, zbcen; double epsw, epsp, conc, tmemb, zmemb, epsm; int swap=0; fd = fopen(filepath, "rb"); if (!fd) { printf("pbeqplugin) Error opening file %s.\n", filepath); return NULL; } // skip first Fortran length record for // WRITE(UNIT) NCLX,NCLY,NCLZ,DCEL,XBCEN,YBCEN,ZBCEN if (fread(&length, 4, 1, fd) != 1) return NULL; if (fread(&nclx, 4, 1, fd) != 1) return NULL; if (fread(&ncly, 4, 1, fd) != 1) return NULL; if (fread(&nclz, 4, 1, fd) != 1) return NULL; // test endianness first if (length != 44) { swap = 1; swap4_aligned(&length, 1); if (length != 44) { printf("pbeqplugin) length record != 44, unrecognized format (length: %d)\n", length); return NULL; } } if (swap) { swap4_aligned(&nclx, 1); swap4_aligned(&ncly, 1); swap4_aligned(&nclz, 1); } // this is a risky strategy for detecting endianness, // but it works so far, and the charmm potential maps don't // have version numbers, magic numbers, or anything else that we // might otherwise use for this purpose. if ((nclx > 4000 && ncly > 4000 && nclz > 4000) || (nclx * ncly * nclz < 0)) { printf("pbeqplugin) inconclusive byte ordering, bailing out\n"); return NULL; } // read the rest of the header if (fread(&dcel, 8, 1, fd) != 1) return NULL; if (fread(&xbcen, 8, 1, fd) != 1) return NULL; if (fread(&ybcen, 8, 1, fd) != 1) return NULL; if (fread(&zbcen, 8, 1, fd) != 1) return NULL; // skip second Fortran length record for // WRITE(UNIT) NCLX,NCLY,NCLZ,DCEL,XBCEN,YBCEN,ZBCEN if (fread(&trash, 4, 1, fd) != 1) return NULL; // skip first Fortran length record for // WRITE(UNIT) EPSW,EPSP,CONC,TMEMB,ZMEMB,EPSM if (fread(&trash, 4, 1, fd) != 1) return NULL; if (fread(&epsw, 8, 1, fd) != 1) return NULL; if (fread(&epsp, 8, 1, fd) != 1) return NULL; if (fread(&conc, 8, 1, fd) != 1) return NULL; if (fread(&tmemb, 8, 1, fd) != 1) return NULL; if (fread(&zmemb, 8, 1, fd) != 1) return NULL; if (fread(&epsm, 8, 1, fd) != 1) return NULL; // skip second Fortran length record for // WRITE(UNIT) EPSW,EPSP,CONC,TMEMB,ZMEMB,EPSM if (fread(&trash, 4, 1, fd) != 1) return NULL; // byte swap the header data if necessary if (swap) { swap8_aligned(&dcel, 1); swap8_aligned(&xbcen, 1); swap8_aligned(&ybcen, 1); swap8_aligned(&zbcen, 1); swap8_aligned(&epsw, 1); swap8_aligned(&epsp, 1); swap8_aligned(&conc, 1); swap8_aligned(&tmemb, 1); swap8_aligned(&zmemb, 1); swap8_aligned(&epsm, 1); } #if 0 // print header info for debugging of early versions printf("pbeqplugin) nclx:%d nxly:%d nclz:%d\n", nclx, ncly, nclz); printf("pbeqplugin) dcel: %f\n", dcel); printf("pbeqplugin) x/y/zbcen: %g %g %g\n", xbcen, ybcen, zbcen); printf("pbeqplugin) epsw/p: %g %g conc: %g tmemb: %g zmemb: %g epsm: %g\n", epsw, epsp, conc, tmemb, zmemb, epsm); #endif /* Allocate and initialize the pbeq structure */ pbeq = new pbeq_t; pbeq->fd = fd; pbeq->vol = NULL; *natoms = MOLFILE_NUMATOMS_NONE; pbeq->nsets = 1; /* this file contains only one data set */ pbeq->ndata = nclx*ncly*nclz; pbeq->nclx = nclx; pbeq->ncly = ncly; pbeq->nclz = nclz; pbeq->swap = swap; pbeq->vol = new molfile_volumetric_t[1]; strcpy(pbeq->vol[0].dataname, "CHARMM PBEQ Potential Map"); pbeq->vol[0].origin[0] = -0.5*((nclx-1) * dcel) + xbcen; pbeq->vol[0].origin[1] = -0.5*((ncly-1) * dcel) + ybcen; pbeq->vol[0].origin[2] = -0.5*((nclz-1) * dcel) + zbcen; // print origin info, for debuggin of early versions printf("pbeqplugin) box LL origin: %g %g %g\n", pbeq->vol[0].origin[0], pbeq->vol[0].origin[1], pbeq->vol[0].origin[2]); pbeq->vol[0].xaxis[0] = (nclx-1) * dcel; pbeq->vol[0].xaxis[1] = 0; pbeq->vol[0].xaxis[2] = 0; pbeq->vol[0].yaxis[0] = 0; pbeq->vol[0].yaxis[1] = (ncly-1) * dcel; pbeq->vol[0].yaxis[2] = 0; pbeq->vol[0].zaxis[0] = 0; pbeq->vol[0].zaxis[1] = 0; pbeq->vol[0].zaxis[2] = (nclz-1) * dcel; pbeq->vol[0].xsize = nclx; pbeq->vol[0].ysize = ncly; pbeq->vol[0].zsize = nclz; pbeq->vol[0].has_color = 0; return pbeq; }
static void *open_spider_read(const char *filepath, const char *filetype, int *natoms) { FILE *fd; spider_t *vol; int total; /* file header buffer union */ union buffer { float fbuf[256]; char cbuf[1024]; } h; fd = fopen(filepath, "rb"); if (!fd) { fprintf(stderr, "spiderplugin) Error opening file.\n"); return NULL; } /* allocate and initialize the spider structure */ vol = new spider_t; vol->fd = fd; vol->vol = NULL; vol->byteswap = 0; *natoms = MOLFILE_NUMATOMS_NONE; vol->nsets = 1; /* this file contains only one data set */ vol->vol = new molfile_volumetric_t[1]; strcpy(vol->vol[0].dataname, "SPIDER map"); // read SPIDER file header if (fread(&h.cbuf, 1024, 1, fd) < 1) { printf("spiderplugin) failed to read file header\n"); return NULL; } // perform sanity checks on header values to see if we // need to do byte swapping, or abort. vol->nslice = (h.fbuf[0] < 0) ? -h.fbuf[0] : h.fbuf[0]; vol->nrow = h.fbuf[1]; vol->nsam = h.fbuf[11]; total = vol->nslice * vol->nrow * vol->nsam; if (total <= 0 || vol->nsam <= 0 || vol->nsam > 100000 || vol->nrow <= 0 || vol->nrow > 100000 || vol->nslice <= 0 || vol->nslice > 100000) { printf("spiderplugin) Non-native endianness or unusual file detected\n"); // byte swap the entire header in hopes of making sense of this gibberish vol->byteswap = 1; swap4_aligned(&h.fbuf, 256); vol->nslice = (h.fbuf[0] < 0) ? -h.fbuf[0] : h.fbuf[0]; vol->nrow = h.fbuf[1]; vol->nsam = h.fbuf[11]; total = vol->nslice * vol->nrow * vol->nsam; // check to see if we still have gibberish or not, bail out if we do. if (total <= 0 || vol->nsam <= 0 || vol->nsam > 100000 || vol->nrow <= 0 || vol->nrow > 100000 || vol->nslice <= 0 || vol->nslice > 100000) { printf("spiderplugin) bad header values in file fail sanity checks\n"); delete [] vol->vol; delete vol; return NULL; } } if (vol->byteswap) { printf("spiderplugin) Enabling byte swapping\n"); } vol->nlabel = h.fbuf[3]; vol->iform = h.fbuf[4]; vol->imami = h.fbuf[5]; vol->fmax = h.fbuf[6]; vol->fmin = h.fbuf[7]; vol->av = h.fbuf[8]; vol->sig = h.fbuf[9]; vol->headrec = h.fbuf[12]; vol->iangle = h.fbuf[13]; vol->phi = h.fbuf[14]; vol->theta = h.fbuf[15]; vol->gamma = h.fbuf[16]; vol->xoffset = h.fbuf[17]; vol->yoffset = h.fbuf[18]; vol->zoffset = h.fbuf[19]; vol->scale = h.fbuf[20]; vol->headbyt = h.fbuf[21]; vol->reclen = h.fbuf[22]; vol->nstack = h.fbuf[23]; vol->inuse = h.fbuf[24]; vol->maxim = h.fbuf[25]; printf("spider nslice: %d\n", vol->nslice); printf("spider nrow: %d\n", vol->nrow); printf("spider nsam: %d\n", vol->nsam); printf("spider iform: %d\n", vol->iform); printf("spider scale: %f\n", vol->scale); printf("spider xoffset: %f\n", vol->xoffset); printf("spider yoffset: %f\n", vol->yoffset); printf("spider zoffset: %f\n", vol->zoffset); printf("spider phi: %f\n", vol->phi); printf("spider theta: %f\n", vol->theta); printf("spider gamma: %f\n", vol->gamma); /* correct bad headbyt and reclen SPIDER files */ if (vol->iform < 4 && (vol->reclen < (vol->nsam * 4))) vol->reclen = vol->nsam * 4; int headrec = 1024 / vol->reclen; if (vol->reclen < 1024 && (1024 % (vol->reclen)) != 0) headrec++; int headbyt = headrec * vol->reclen; if (vol->iform < 4 && (vol->headbyt < headbyt)) vol->headbyt = headbyt; printf("spider headbyt: %d\n", vol->headbyt); /* seek to data offset */ fseek(fd, vol->headbyt, SEEK_SET); /* SPIDER files contain no color information */ vol->vol[0].has_color = 0; vol->vol[0].xsize = vol->nsam; vol->vol[0].ysize = vol->nrow; vol->vol[0].zsize = vol->nslice; /* Set the unit cell origin and basis vectors */ float vz[3] = {0.0, 0.0, 0.0}; memcpy(vol->vol[0].xaxis, &vz, sizeof(vz)); memcpy(vol->vol[0].yaxis, &vz, sizeof(vz)); memcpy(vol->vol[0].zaxis, &vz, sizeof(vz)); /* the scale value may be zero, if so, just reset to 1.0 */ float vscale = vol->scale; if (vscale == 0.0) vscale = 1.0; /* the data is stored in y/x/-z order and coordinate handedness */ /* we should probably rewrite the loader loop to shuffle x/y */ /* so that future conversions to other formats don't leave it in */ /* an unusual packing order. For now this works however */ float xlen = vscale * (vol->vol[0].ysize-1); float ylen = vscale * (vol->vol[0].xsize-1); float zlen = vscale * (vol->vol[0].zsize-1); vol->vol[0].xaxis[1] = xlen; vol->vol[0].yaxis[0] = ylen; vol->vol[0].zaxis[2] = -zlen; vol->vol[0].origin[0] = vol->yoffset - (0.5 * ylen); vol->vol[0].origin[1] = vol->xoffset - (0.5 * xlen); vol->vol[0].origin[2] = vol->zoffset + (0.5 * zlen); printf("spider final offset: (%f, %f, %f)\n", vol->vol[0].origin[0], vol->vol[0].origin[1], vol->vol[0].origin[2]); printf("spider final axes:\n"); printf(" X (%f, %f, %f)\n", vol->vol[0].xaxis[0], vol->vol[0].xaxis[1], vol->vol[0].xaxis[2]); printf(" Y (%f, %f, %f)\n", vol->vol[0].yaxis[0], vol->vol[0].yaxis[1], vol->vol[0].yaxis[2]); printf(" Z (%f, %f, %f)\n", vol->vol[0].zaxis[0], vol->vol[0].zaxis[1], vol->vol[0].zaxis[2]); return vol; }
static int read_rawgraphics(void *v, int *nelem, const molfile_graphics_t **data) { grasp_t *grasp = (grasp_t *)v; FILE *infile = grasp->fd; // Reverse engineering is your friend, and combined with FORTRAN code, voila! // od -c shows the header starts off: // \0 \0 \0 P f o r m a t = 2 // and according to ungrasp, this is a 1 for grasp versions 1.0 // and 1.1, and 2 for grasp version 1.2 // Also, the header lines are of length 80 characters + 4 header chars // + 4 trailer chars // The 4 bytes at the beginning/end are standard Fortran array trash /// Pointers grassp type GRASSP datax; char trash[4]; #define TRASH fread(trash, 4, 1, infile) char line[81]; // FIRST LINE OF HEADER; contains format type TRASH; fread(line, 1, 80, infile); // make sure it says 'format=' if (strncmp(line, "format=", 7) != 0) { printf("graspplugin) First characters of file don't look like a GRASP file\n"); return MOLFILE_ERROR; } TRASH; // next char should be a 0 or 1 char gfiletype = line[7]; if (gfiletype == '1') { gfiletype = 1; } else if (gfiletype == '2') { gfiletype = 2; } else { printf("graspplugin) GRASP file is in format %c, but only '1' or '2' is supported\n", gfiletype); return MOLFILE_ERROR; } // SECOND LINE: contains "vertices,accessibles,normals,triangles" TRASH; fread(line, 1, 80, infile); TRASH; // THIRD LINE: contains (0 or more of)? // "potentials,curvature,distances,gproperty,g2property,vertexcolor TRASH; line3(infile, &datax);/// Reads line 3 TRASH; // FOURTH LINE stores vertices, triangles, gridsize, lattice spacing int nvert, ntriangles, gridsize; float lattice; TRASH; fread(line, 1, 80, infile); TRASH; sscanf(line, "%d%d%d%f", &nvert, &ntriangles, &gridsize, &lattice); /// Stores color float *colores = new float [3*nvert]; // FIFTH LINE stores the center (x,y,z) position float center[3]; TRASH; fread(line, 1, 80, infile); TRASH; sscanf(line, "%f%f%f", center, center+1, center+2); float *vertex = new float[3 * nvert]; float *access = new float[3 * nvert]; float *normal = new float[3 * nvert]; int *triangle = new int[3 * ntriangles]; float *properties = new float[3* nvert]; if (!vertex || !access || !normal || !triangle || !properties) { delete [] vertex; delete [] access; delete [] normal; delete [] triangle; delete [] properties; printf("graspplugin) Failed vertex/access/normal/triangle allocations.\n"); return MOLFILE_ERROR; } // ungrasp says: // if (filetype.eq.1) then integer*2 // if (filetype.eq.2) then integer*4 // And read them in. Who needs error checking? TRASH; fread(vertex, 3 * sizeof(float), nvert, infile); TRASH; TRASH; fread(access, 3 * sizeof(float), nvert, infile); TRASH; TRASH; fread(normal, 3 * sizeof(float), nvert, infile); TRASH; if (is_little_endian()) { swap4_aligned(vertex, 3*nvert); swap4_aligned(access, 3*nvert); swap4_aligned(normal, 3*nvert); } if (gfiletype == 2) { TRASH; fread(triangle, 3 * sizeof(int), ntriangles, infile); TRASH; TRASH; fread(properties, 3 * sizeof(float), nvert, infile); if (is_little_endian()) { swap4_aligned(triangle, 3*ntriangles); swap4_aligned(properties, 3*nvert); } } else { #if 1 int i; short *striangle = new short[3 * ntriangles]; if (!striangle) { delete [] vertex; delete [] access; delete [] normal; delete [] triangle; delete [] properties; printf("graspplugin) Failed short triangle allocation.\n"); return MOLFILE_ERROR; } TRASH; fread(striangle, sizeof(short), 3 * ntriangles, infile); TRASH; TRASH; fread(properties, sizeof(float), 3 * nvert, infile); if (is_little_endian()) { swap2_aligned(striangle, 3 * ntriangles); swap4_aligned(properties, 3*nvert);} for (i=0; i<3*ntriangles; i++) { triangle[i] = striangle[i]; } delete [] striangle; #else // do it the slow way (converting from short to int) int i; short tmp[3]; TRASH; for (i=0; i<ntriangles; i++) { fread(tmp, sizeof(short), 3, infile); if (is_little_endian()) swap2_aligned(tmp, 3); triangle[3*i+0] = tmp[0]; triangle[3*i+1] = tmp[1]; triangle[3*i+2] = tmp[2]; } TRASH; TRASH; fread(properties, sizeof(float), 3 * nvert, infile); if (is_little_endian()) swap4_aligned(properties, 3*nvert); #endif } /// Gets properties: potentials, curvature, distances, gproperty, g2property or vertexcolor Get_Property_Values(&datax, properties, colores, nvert); // And draw things grasp->graphics = new molfile_graphics_t[3*ntriangles]; int vert1, vert2, vert3; for (int tri_count = 0; tri_count < ntriangles; tri_count++) { vert1 = triangle[3*tri_count+0] - 1; // from 1-based FORTRAN vert2 = triangle[3*tri_count+1] - 1; // to 0-based C++ vert3 = triangle[3*tri_count+2] - 1; if (vert1 < 0 || vert2 < 0 || vert3 < 0 || vert1 >= nvert || vert2 >= nvert || vert3 >= nvert) { printf("graspplugin) Error, out-of-range vertex index, aborting.\n"); delete [] vertex; delete [] access; delete [] normal; delete [] triangle; delete [] properties; return MOLFILE_ERROR; } grasp->graphics[2*tri_count ].type = MOLFILE_TRINORM; grasp->graphics[2*tri_count+1].type = MOLFILE_NORMS; grasp->graphics[2*tri_count+2].type = MOLFILE_COLOR; float *tridata = grasp->graphics[2*tri_count ].data; float *normdata = grasp->graphics[2*tri_count+1].data; float *colordata = grasp->graphics[2*tri_count+2].data; memcpy(tridata , vertex+3*vert1, 3*sizeof(float)); memcpy(tridata+3, vertex+3*vert2, 3*sizeof(float)); memcpy(tridata+6, vertex+3*vert3, 3*sizeof(float)); memcpy(normdata , normal+3*vert1, 3*sizeof(float)); memcpy(normdata+3, normal+3*vert2, 3*sizeof(float)); memcpy(normdata+6, normal+3*vert3, 3*sizeof(float)); memcpy(colordata , properties+3*vert1, 3*sizeof(float)); memcpy(colordata+3, properties+3*vert2, 3*sizeof(float)); memcpy(colordata+6, properties+3*vert3, 3*sizeof(float)); } *nelem = 2*ntriangles; *data = grasp->graphics; delete [] triangle; delete [] normal; delete [] access; delete [] vertex; delete [] properties; return MOLFILE_SUCCESS; }
static int read_js_structure(void *mydata, int *optflags, molfile_atom_t *atoms) { jshandle *js = (jshandle *) mydata; int i; *optflags = MOLFILE_NOOPTIONS; /* set to no options until we read them */ /* write flags data to the file */ fio_read_int32(js->fd, &js->optflags); if (js->reverseendian) swap4_aligned(&js->optflags, 1); printf("jsplugin) read option flags: %0x08x\n", js->optflags); /* determine whether or not this file contains structure info or not */ if (js->optflags & JSOPT_STRUCTURE) { int numatomnames, numatomtypes, numresnames, numsegids, numchains; char **atomnames = NULL; char **atomtypes = NULL; char **resnames = NULL; char **segids = NULL; char **chains = NULL; short *shortbuf = NULL; /* temp buf for decoding atom records */ int *intbuf = NULL; /* temp buf for decoding atom records */ float *fltbuf = NULL; /* temp buf for decoding atom records */ /* read in block of name string table sizes */ fio_read_int32(js->fd, &numatomnames); fio_read_int32(js->fd, &numatomtypes); fio_read_int32(js->fd, &numresnames); fio_read_int32(js->fd, &numsegids); fio_read_int32(js->fd, &numchains); if (js->reverseendian) { swap4_aligned(&numatomnames, js->natoms); swap4_aligned(&numatomtypes, js->natoms); swap4_aligned(&numresnames, js->natoms); swap4_aligned(&numsegids, js->natoms); swap4_aligned(&numchains, js->natoms); } printf("jsplugin) reading string tables...\n"); printf("jsplugin) %d %d %d %d %d\n", numatomnames, numatomtypes, numresnames, numsegids, numchains); /* allocate string tables */ atomnames = (char **) malloc(numatomnames * sizeof(char *)); atomtypes = (char **) malloc(numatomtypes * sizeof(char *)); resnames = (char **) malloc(numresnames * sizeof(char *)); segids = (char **) malloc(numsegids * sizeof(char *)); chains = (char **) malloc(numchains * sizeof(char *)); printf("jsplugin) atom names...\n"); /* read in the string tables */ for (i=0; i<numatomnames; i++) { atomnames[i] = (char *) malloc(16 * sizeof(char)); fio_fread(atomnames[i], 16 * sizeof(char), 1, js->fd); } printf("jsplugin) atom types...\n"); for (i=0; i<numatomtypes; i++) { atomtypes[i] = (char *) malloc(16 * sizeof(char)); fio_fread(atomtypes[i], 16 * sizeof(char), 1, js->fd); } printf("jsplugin) residue names...\n"); for (i=0; i<numresnames; i++) { resnames[i] = (char *) malloc(8 * sizeof(char)); fio_fread(resnames[i], 8 * sizeof(char), 1, js->fd); } printf("jsplugin) segment names...\n"); for (i=0; i<numsegids; i++) { segids[i] = (char *) malloc(8 * sizeof(char)); fio_fread(segids[i], 8 * sizeof(char), 1, js->fd); } printf("jsplugin) chain names...\n"); for (i=0; i<numchains; i++) { chains[i] = (char *) malloc(2 * sizeof(char)); fio_fread(chains[i], 2 * sizeof(char), 1, js->fd); } printf("jsplugin) reading numeric field tables...\n"); /* read in all of the atom fields */ shortbuf = (void *) malloc(js->natoms * sizeof(short)); printf("jsplugin) atom name indices...\n"); /* read in atom names */ fio_fread(shortbuf, js->natoms * sizeof(short), 1, js->fd); if (js->reverseendian) swap2_aligned(shortbuf, js->natoms); for (i=0; i<js->natoms; i++) { strcpy(atoms[i].name, atomnames[shortbuf[i]]); } printf("jsplugin) atom type indices...\n"); /* read in atom types */ fio_fread(shortbuf, js->natoms * sizeof(short), 1, js->fd); if (js->reverseendian) swap2_aligned(shortbuf, js->natoms); for (i=0; i<js->natoms; i++) { strcpy(atoms[i].type, atomtypes[shortbuf[i]]); } printf("jsplugin) residue name indices...\n"); /* read in resnames */ fio_fread(shortbuf, js->natoms * sizeof(short), 1, js->fd); if (js->reverseendian) swap2_aligned(shortbuf, js->natoms); for (i=0; i<js->natoms; i++) { strcpy(atoms[i].resname, resnames[shortbuf[i]]); } printf("jsplugin) segment name indices...\n"); /* read in segids */ fio_fread(shortbuf, js->natoms * sizeof(short), 1, js->fd); if (js->reverseendian) swap2_aligned(shortbuf, js->natoms); for (i=0; i<js->natoms; i++) { strcpy(atoms[i].segid, segids[shortbuf[i]]); } printf("jsplugin) chain name indices...\n"); /* read in chains */ fio_fread(shortbuf, js->natoms * sizeof(short), 1, js->fd); if (js->reverseendian) swap2_aligned(shortbuf, js->natoms); for (i=0; i<js->natoms; i++) { strcpy(atoms[i].chain, chains[shortbuf[i]]); } if (shortbuf != NULL) { free(shortbuf); shortbuf=NULL; } /* * read in integer data blocks */ intbuf = (int *) malloc(js->natoms * sizeof(int)); printf("jsplugin) residue indices...\n"); /* read in resid */ fio_fread(intbuf, js->natoms * sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(intbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].resid = intbuf[i]; } if (intbuf != NULL) { free(intbuf); intbuf = NULL; } printf("jsplugin) reading optional per-atom tables...\n"); /* * read in optional single-precision float data blocks */ if (js->optflags & (JSOPT_OCCUPANCY | JSOPT_BFACTOR | JSOPT_MASS | JSOPT_RADIUS | JSOPT_CHARGE)) fltbuf = (void *) malloc(js->natoms * sizeof(float)); /* read in optional data if it exists */ if (js->optflags & JSOPT_OCCUPANCY) { printf("jsplugin) occupancy...\n"); *optflags |= MOLFILE_OCCUPANCY; fio_fread(fltbuf, js->natoms * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(fltbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].occupancy = fltbuf[i]; } } if (js->optflags & JSOPT_BFACTOR) { printf("jsplugin) bfactor...\n"); *optflags |= MOLFILE_BFACTOR; fio_fread(fltbuf, js->natoms * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(fltbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].bfactor = fltbuf[i]; } } if (js->optflags & JSOPT_MASS) { printf("jsplugin) mass...\n"); *optflags |= MOLFILE_MASS; fio_fread(fltbuf, js->natoms * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(fltbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].mass = fltbuf[i]; } } if (js->optflags & JSOPT_CHARGE) { printf("jsplugin) charge...\n"); *optflags |= MOLFILE_CHARGE; fio_fread(fltbuf, js->natoms * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(fltbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].charge = fltbuf[i]; } } if (js->optflags & JSOPT_RADIUS) { printf("jsplugin) radius...\n"); *optflags |= MOLFILE_RADIUS; fio_fread(fltbuf, js->natoms * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(fltbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].radius = fltbuf[i]; } } if (fltbuf != NULL) { free(fltbuf); fltbuf=NULL; } /* * read in optional integer data blocks */ if (js->optflags & JSOPT_ATOMICNUMBER) intbuf = (void *) malloc(js->natoms * sizeof(int)); if (js->optflags & JSOPT_ATOMICNUMBER) { printf("jsplugin) atomic number...\n"); *optflags |= MOLFILE_ATOMICNUMBER; fio_fread(intbuf, js->natoms * sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(intbuf, js->natoms); for (i=0; i<js->natoms; i++) { atoms[i].atomicnumber = intbuf[i]; } } if (intbuf != NULL) { free(intbuf); intbuf = NULL; } /* * read in bonds and fractional bond orders */ if (js->optflags & JSOPT_BONDS) { fio_fread(&js->nbonds, sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(&js->nbonds, 1); printf("jsplugin) %d bonds...\n", js->nbonds); js->bondfrom = (int *) malloc(js->nbonds * sizeof(int)); js->bondto = (int *) malloc(js->nbonds * sizeof(int)); fio_fread(js->bondfrom, js->nbonds * sizeof(int), 1, js->fd); fio_fread(js->bondto, js->nbonds * sizeof(int), 1, js->fd); if (js->reverseendian) { swap4_aligned(js->bondfrom, js->nbonds); swap4_aligned(js->bondto, js->nbonds); } if (js->optflags & JSOPT_BONDORDERS) { printf("jsplugin) bond orders...\n"); js->bondorders = (void *) malloc(js->nbonds * sizeof(float)); fio_fread(js->bondorders, js->nbonds * sizeof(float), 1, js->fd); if (js->reverseendian) swap4_aligned(js->bondorders, js->nbonds); } } if (js->optflags & JSOPT_ANGLES) { fio_fread(&js->numangles, sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(&js->numangles, 1); printf("jsplugin) %d angles...\n", js->numangles); js->angles = (int *) malloc(3 * js->numangles * sizeof(int)); fio_fread(js->angles, sizeof(int)*3*js->numangles, 1, js->fd); if (js->reverseendian) swap4_aligned(&js->angles, 3*js->numangles); fio_fread(&js->numdihedrals, sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(&js->numdihedrals, 1); printf("jsplugin) %d dihedrals...\n", js->numdihedrals); js->dihedrals = (int *) malloc(4 * js->numdihedrals * sizeof(int)); fio_fread(js->dihedrals, sizeof(int)*4*js->numdihedrals, 1, js->fd); if (js->reverseendian) swap4_aligned(&js->dihedrals, 4*js->numdihedrals); fio_fread(&js->numimpropers, sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(&js->numimpropers, 1); js->impropers = (int *) malloc(4 * js->numimpropers * sizeof(int)); printf("jsplugin) %d impropers...\n", js->numimpropers); fio_fread(js->impropers, sizeof(int)*4*js->numimpropers, 1, js->fd); if (js->reverseendian) swap4_aligned(&js->impropers, 4*js->numimpropers); } if (js->optflags & JSOPT_CTERMS) { fio_fread(&js->numcterms, sizeof(int), 1, js->fd); if (js->reverseendian) swap4_aligned(&js->numcterms, 1); js->cterms = (int *) malloc(8 * js->numcterms * sizeof(int)); printf("jsplugin) %d cterms...\n", js->numcterms); fio_fread(js->cterms, sizeof(int)*8*js->numcterms, 1, js->fd); if (js->reverseendian) swap4_aligned(&js->cterms, 8*js->numcterms); } printf("jsplugin) final optflags: %08x\n", *optflags); printf("jsplugin) structure information complete\n"); return MOLFILE_SUCCESS; } printf("jsplugin) no structure information available\n"); /* else, we have no structure information */ return MOLFILE_NOSTRUCTUREDATA; }
static void *open_js_read(const char *path, const char *filetype, int *natoms) { jshandle *js; int jsmagicnumber, jsendianism, jsmajorversion, jsminorversion; struct stat stbuf; char strbuf[1024]; int rc = 0; if (!path) return NULL; /* See if the file exists, and get its size */ memset(&stbuf, 0, sizeof(struct stat)); if (stat(path, &stbuf)) { printf("jsplugin) Could not access file '%s'.\n", path); return NULL; } js = (jshandle *)malloc(sizeof(jshandle)); memset(js, 0, sizeof(jshandle)); if (fio_open(path, FIO_READ, &js->fd) < 0) { printf("jsplugin) Could not open file '%s' for reading.\n", path); free(js); return NULL; } /* emit header information */ fio_fread(strbuf, strlen(JSHEADERSTRING), 1, js->fd); strbuf[strlen(JSHEADERSTRING)] = '\0'; if (strcmp(strbuf, JSHEADERSTRING)) { printf("jsplugin) Bad trajectory header!\n"); printf("jsplugin) Read string: %s\n", strbuf); return NULL; } fio_read_int32(js->fd, &jsmagicnumber); fio_read_int32(js->fd, &jsendianism); fio_read_int32(js->fd, &jsmajorversion); fio_read_int32(js->fd, &jsminorversion); fio_read_int32(js->fd, &js->natoms); fio_read_int32(js->fd, &js->nframes); if ((jsmagicnumber != JSMAGICNUMBER) || (jsendianism != JSENDIANISM)) { printf("jsplugin) opposite endianism file, enabling byte swapping\n"); js->reverseendian = 1; swap4_aligned(&jsmagicnumber, 1); swap4_aligned(&jsendianism, 1); swap4_aligned(&jsmajorversion, 1); swap4_aligned(&jsminorversion, 1); swap4_aligned(&js->natoms, 1); swap4_aligned(&js->nframes, 1); } else { printf("jsplugin) native endianism file\n"); } if ((jsmagicnumber != JSMAGICNUMBER) || (jsendianism != JSENDIANISM)) { printf("jsplugin) read_jsreader returned %d\n", rc); fio_fclose(js->fd); free(js); return NULL; } if (jsmajorversion != JSMAJORVERSION) { printf("jsplugin) major version mismatch\n"); printf("jsplugin) file version: %d\n", jsmajorversion); printf("jsplugin) plugin version: %d\n", JSMAJORVERSION); fio_fclose(js->fd); free(js); return NULL; } *natoms = js->natoms; return js; }
static void *open_ccp4_read(const char *filepath, const char *filetype, int *natoms) { FILE *fd; ccp4_t *ccp4; char mapString[4], symData[81]; int nxyzstart[3], extent[3], grid[3], crs2xyz[3], voxtype, symBytes; float origin2k[3]; int swap, i, xIndex, yIndex, zIndex; long dataOffset, filesize; float cellDimensions[3], cellAngles[3], xaxis[3], yaxis[3], zaxis[3]; float alpha, beta, gamma, xScale, yScale, zScale, z1, z2, z3; float amin, amax, amean; int dataflags=0,imodstamp=0,imodflags=0; fd = fopen(filepath, "rb"); if (!fd) { printf("ccp4plugin) Error opening file %s\n", filepath); return NULL; } if ((fread(extent, sizeof(int), 3, fd) != 3) || (fread(&voxtype, sizeof(int), 1, fd) != 1) || (fread(nxyzstart, sizeof(int), 3, fd) != 3) || (fread(grid, sizeof(int), 3, fd) != 3) || (fread(cellDimensions, sizeof(float), 3, fd) != 3) || (fread(cellAngles, sizeof(float), 3, fd) != 3) || (fread(crs2xyz, sizeof(int), 3, fd) != 3) || (fread(&amin, sizeof(float), 1, fd) != 1) || (fread(&amax, sizeof(float), 1, fd) != 1) || (fread(&amean, sizeof(float), 1, fd) != 1)) { printf("ccp4plugin) Error: Improperly formatted line.\n"); return NULL; } // Check the number of bytes used for storing symmetry operators // (word 23, byte 92) fseek(fd, 23 * 4, SEEK_SET); if ((fread(&symBytes, sizeof(int), 1, fd) != 1) ) { printf("ccp4plugin) Error: Failed reading symmetry bytes record.\n"); return NULL; } // read MRC2000 Origin record at word 49, byte 196, and use it if necessary // http://www2.mrc-lmb.cam.ac.uk/image2000.html fseek(fd, 49 * 4, SEEK_SET); if (fread(origin2k, sizeof(float), 3, fd) != 3) { printf("ccp4plugin) Error: unable to read ORIGIN records at offset 196.\n"); } // Check for IMOD stamp at offset 152, indicating an IMOD file fseek(fd, 152, SEEK_SET); if (fread(&imodstamp, sizeof(int), 1, fd) != 1) { printf("ccp4plugin) Error: failed to read IMOD stamp from MRC file.\n"); return NULL; } if (fread(&imodflags, sizeof(int), 1, fd) != 1) { printf("ccp4plugin) Error: failed to read IMOD flags from MRC file.\n"); return NULL; } // Check file endianism using some heuristics swap = 0; int tmp[3]; memcpy(tmp, extent, 3*sizeof(int)); if (tmp[0] > 65536 || tmp[1] > 65536 || tmp[2] > 65536) { swap4_aligned(tmp, 3); if (tmp[0] > 65536 || tmp[1] > 65536 || tmp[2] > 65536) { swap = 0; printf("ccp4plugin) Guessing file endianism: native\n"); } else { swap = 1; printf("ccp4plugin) Guessing file endianism: swapped\n"); } } if (voxtype > 16 && swap == 0) { tmp[0] = voxtype; swap4_aligned(tmp, 1); if (tmp[0] <= 16) { swap = 1; printf("ccp4plugin) Guessing file endianism: swapped\n"); } } // Byte-swap header information if needed if (swap == 1) { swap4_aligned(extent, 3); swap4_aligned(&voxtype, 1); swap4_aligned(nxyzstart, 3); swap4_aligned(origin2k, 3); swap4_aligned(grid, 3); swap4_aligned(cellDimensions, 3); swap4_aligned(cellAngles, 3); swap4_aligned(crs2xyz, 3); swap4_aligned(&amin, 1); swap4_aligned(&amax, 1); swap4_aligned(&amean, 1); swap4_aligned(&symBytes, 1); swap4_aligned(&imodstamp, 1); swap4_aligned(&imodflags, 1); } // Check for the string "MAP" at word 52 byte 208, indicating a CCP4 file. fseek(fd, 52 * 4, SEEK_SET); if (fgets(mapString, 4, fd) == NULL) { printf("ccp4plugin) Error: unable to read 'MAP' string, not a valid CCP4/IMOD MRC file.\n"); return NULL; } if ((strcmp(mapString, "MAP") != 0) && (imodstamp != IMOD_MAGIC_STAMP)) { // Older versions of IMOD (2.6.19 or below) do not have the "MAP " string. // If the IMOD stamp is there its probably a valid MRC file printf("ccp4plugin) Warning: 'MAP' string missing!\n"); printf("ccp4plugin) This usually indicates an invalid IMOD file,\n"); printf("ccp4plugin) but some old IMOD versions did not specify 'MAP'.\n"); printf("ccp4plugin) File loading will proceed but may ultimately fail.\n"); } // Check if we found an IMOD file or not if (imodstamp == IMOD_MAGIC_STAMP) { printf("ccp4plugin) MRC file generated by IMOD-compatible program.\n"); dataflags |= DATA_FLAG_IMOD_FORMAT; // mark that this file came from IMOD if (imodflags & IMOD_FLAG_SIGNED) { dataflags |= DATA_FLAG_SIGNED; printf("ccp4plugin) IMOD flag: data uses signed-bytes\n"); } else { printf("ccp4plugin) IMOD flag: data uses unsigned-bytes\n"); } if (imodflags & IMOD_FLAG_HEADER_SPACING) printf("ccp4plugin) IMOD flag: pixel spacing set in extended header\n"); if (imodflags & IMOD_FLAG_ORIGIN_INVERTED_SIGN) printf("ccp4plugin) IMOD flag: origin sign is inverted.\n"); } else { imodflags = 0; printf("ccp4plugin) No IMOD stamp found.\n"); if (amin < 0) { printf("ccp4plugin) Note: amin < 0, signed voxels are implied\n"); dataflags |= DATA_FLAG_SIGNED; } else { printf("ccp4plugin) Note: amin >= 0, unsigned voxels are implied\n"); } } // Check the data type of the file. switch (voxtype) { case MRC_TYPE_BYTE: printf("ccp4plugin) voxel type: byte\n"); break; case MRC_TYPE_SHORT: printf("ccp4plugin) voxel type: short (16-bit signed int)\n"); break; case MRC_TYPE_FLOAT: printf("ccp4plugin) voxel type: float (32-bit real)\n"); break; case MRC_TYPE_SHORT2: printf("ccp4plugin) voxel type: short2 (2x 16-bit signed int)\n"); printf("ccp4plugin) Error: unimplemented voxel format\n"); return NULL; case MRC_TYPE_FLOAT2: printf("ccp4plugin) voxel type: float2 (2x 32-bit real)\n"); printf("ccp4plugin) Error: unimplemented voxel format\n"); return NULL; case MRC_TYPE_USHORT: printf("ccp4plugin) voxel type: ushort (16-bit unsigned int)\n"); break; case MRC_TYPE_UCHAR3: printf("ccp4plugin) voxel type: uchar3 (3x unsigned char)\n"); break; default: printf("ccp4plugin) Error: Only byte, short (16-bit integer) or float (32-bit real) data types are supported.\n"); return NULL; } #if 1 printf("ccp4plugin) extent: %d x %d x %d\n", extent[0], extent[1], extent[2]); printf("ccp4plugin) nxyzstart: %d, %d, %d\n", nxyzstart[0], nxyzstart[1], nxyzstart[2]); printf("ccp4plugin) origin2k: %f, %f, %f\n", origin2k[0], origin2k[1], origin2k[2]); printf("ccp4plugin) grid: %d x %d x %d\n", grid[0], grid[1], grid[2]); printf("ccp4plugin) celldim: %f x %f x %f\n", cellDimensions[0], cellDimensions[1], cellDimensions[2]); printf("cpp4plugin)cellangles: %f, %f, %f\n", cellAngles[0], cellAngles[1], cellAngles[2]); printf("ccp4plugin) crs2xyz: %d %d %d\n", crs2xyz[0], crs2xyz[1], crs2xyz[2]); printf("ccp4plugin) amin: %g amax: %g amean: %g\n", amin, amax, amean); printf("ccp4plugin) symBytes: %d\n", symBytes); #endif // Check the dataOffset: this fixes the problem caused by files claiming // to have symmetry records when they do not. fseek(fd, 0, SEEK_END); filesize = ftell(fd); // compute data offset using file size and voxel type info long voxcount = long(extent[0]) * long(extent[1]) * long(extent[2]); if (voxtype == MRC_TYPE_BYTE) { dataOffset = filesize - sizeof(char)*voxcount; } else if (voxtype == MRC_TYPE_FLOAT) { dataOffset = filesize - sizeof(float)*voxcount; } else if (voxtype == MRC_TYPE_SHORT || voxtype == MRC_TYPE_USHORT) { dataOffset = filesize - sizeof(short)*voxcount; } else if (voxtype == MRC_TYPE_UCHAR3) { dataOffset = filesize - sizeof(uchar3)*voxcount; } else { printf("ccp4plugin) unimplemented voxel type!\n"); } if (dataOffset != (CCP4HDSIZE + symBytes)) { if (dataOffset == CCP4HDSIZE) { // Bogus symmetry record information printf("ccp4plugin) Warning: file contains bogus symmetry record.\n"); symBytes = 0; } else if (dataOffset < CCP4HDSIZE) { printf("ccp4plugin) Error: File appears truncated and doesn't match header.\n"); return NULL; } else if ((dataOffset > CCP4HDSIZE) && (dataOffset < (1024*1024))) { // Fix for loading SPIDER files which are larger than usual // In this specific case, we must absolutely trust the symBytes record dataOffset = CCP4HDSIZE + symBytes; printf("ccp4plugin) Warning: File is larger than expected and doesn't match header.\n"); printf("ccp4plugin) Warning: Continuing file load, good luck!\n"); } else { printf("ccp4plugin) Error: File is MUCH larger than expected and doesn't match header.\n"); return NULL; } } // Read symmetry records -- organized as 80-byte lines of text. if (symBytes != 0) { printf("ccp4plugin) Symmetry records found:\n"); fseek(fd, CCP4HDSIZE, SEEK_SET); for (i = 0; i < symBytes/80; i++) { fgets(symData, 81, fd); printf("ccp4plugin) %s\n", symData); } } // check extent and grid interval counts if (grid[0] == 0 && extent[0] > 0) { grid[0] = extent[0] - 1; printf("ccp4plugin) Warning: Fixed X interval count\n"); } if (grid[1] == 0 && extent[1] > 0) { grid[1] = extent[1] - 1; printf("ccp4plugin) Warning: Fixed Y interval count\n"); } if (grid[2] == 0 && extent[2] > 0) { grid[2] = extent[2] - 1; printf("ccp4plugin) Warning: Fixed Z interval count\n"); } // Allocate and initialize the ccp4 structure ccp4 = new ccp4_t; memset(ccp4, 0, sizeof(ccp4_t)); ccp4->fd = fd; ccp4->vol = NULL; *natoms = MOLFILE_NUMATOMS_NONE; ccp4->nsets = 1; // this EDM file contains only one data set ccp4->voxtype = voxtype; ccp4->voxcount = voxcount; ccp4->dataflags = dataflags; ccp4->imodstamp = imodstamp; ccp4->imodflags = imodflags; ccp4->swap = swap; ccp4->dataOffset = dataOffset; ccp4->amin = amin; ccp4->amax = amax; ccp4->amean = amean; ccp4->vol = new molfile_volumetric_t[1]; memset(ccp4->vol, 0, sizeof(molfile_volumetric_t)); strcpy(ccp4->vol[0].dataname, "CCP4 Electron Density Map"); // Mapping between CCP4 column, row, section and VMD x, y, z. if (crs2xyz[0] == 0 && crs2xyz[1] == 0 && crs2xyz[2] == 0) { printf("ccp4plugin) Warning: All crs2xyz records are zero.\n"); printf("ccp4plugin) Warning: Setting crs2xyz to 1, 2, 3\n"); crs2xyz[0] = 1; crs2xyz[0] = 2; crs2xyz[0] = 3; } ccp4->xyz2crs[crs2xyz[0]-1] = 0; ccp4->xyz2crs[crs2xyz[1]-1] = 1; ccp4->xyz2crs[crs2xyz[2]-1] = 2; xIndex = ccp4->xyz2crs[0]; yIndex = ccp4->xyz2crs[1]; zIndex = ccp4->xyz2crs[2]; // calculate non-orthogonal unit cell coordinates alpha = (M_PI / 180.0) * cellAngles[0]; beta = (M_PI / 180.0) * cellAngles[1]; gamma = (M_PI / 180.0) * cellAngles[2]; if (cellDimensions[0] == 0.0 && cellDimensions[1] == 0.0 && cellDimensions[2] == 0.0) { printf("ccp4plugin) Warning: Cell dimensions are all zero.\n"); printf("ccp4plugin) Warning: Setting to 1.0, 1.0, 1.0 for viewing.\n"); printf("ccp4plugin) Warning: Map file will not align with other structures.\n"); cellDimensions[0] = 1.0; cellDimensions[1] = 1.0; cellDimensions[2] = 1.0; } xScale = cellDimensions[0] / grid[0]; yScale = cellDimensions[1] / grid[1]; zScale = cellDimensions[2] / grid[2]; if ((alpha == 0) || (beta == 0) || (gamma == 0)) { printf("ccp4plugin) orthorhombic unit cell axes\n"); xaxis[0] = xScale; xaxis[1] = 0; xaxis[2] = 0; yaxis[0] = 0; yaxis[1] = yScale; yaxis[2] = 0; zaxis[0] = 0; zaxis[1] = 0; zaxis[2] = zScale; } else { // calculate non-orthogonal unit cell coordinates printf("ccp4plugin) computing non-orthorhombic unit cell axes\n"); xaxis[0] = xScale; xaxis[1] = 0; xaxis[2] = 0; yaxis[0] = cos(gamma) * yScale; yaxis[1] = sin(gamma) * yScale; yaxis[2] = 0; z1 = cos(beta); z2 = (cos(alpha) - cos(beta)*cos(gamma)) / sin(gamma); z3 = sqrt(1.0 - z1*z1 - z2*z2); zaxis[0] = z1 * zScale; zaxis[1] = z2 * zScale; zaxis[2] = z3 * zScale; } #if 0 printf("ccp4plugin) scale: %g %g %g\n", xScale, yScale, zScale); printf("ccp4plugin) xax: %g %g %g\n", xaxis[0], xaxis[1], xaxis[2]); printf("ccp4plugin) yax: %g %g %g\n", yaxis[0], yaxis[1], yaxis[2]); printf("ccp4plugin) zax: %g %g %g\n", zaxis[0], zaxis[1], zaxis[2]); #endif #if 1 // Handle both MRC-2000 and older format maps if (origin2k[0] == 0.0f && origin2k[1] == 0.0f && origin2k[2] == 0.0f) { printf("ccp4plugin) using CCP4 n[xyz]start origin\n"); ccp4->vol[0].origin[0] = xaxis[0] * nxyzstart[xIndex] + yaxis[0] * nxyzstart[yIndex] + zaxis[0] * nxyzstart[zIndex]; ccp4->vol[0].origin[1] = yaxis[1] * nxyzstart[yIndex] + zaxis[1] * nxyzstart[zIndex]; ccp4->vol[0].origin[2] = zaxis[2] * nxyzstart[zIndex]; } else { // Use ORIGIN records rather than old n[xyz]start records // http://www2.mrc-lmb.cam.ac.uk/image2000.html // XXX the ORIGIN field is only used by the EM community, and // has undefined meaning for non-orthogonal maps and/or // non-cubic voxels, etc. printf("ccp4plugin) using MRC2000 origin\n"); ccp4->vol[0].origin[0] = origin2k[xIndex]; ccp4->vol[0].origin[1] = origin2k[yIndex]; ccp4->vol[0].origin[2] = origin2k[zIndex]; } #else // old code that only pays attention to old MRC nxstart/nystart/nzstart ccp4->vol[0].origin[0] = xaxis[0] * nxyzstart[xIndex] + yaxis[0] * nxyzstart[yIndex] + zaxis[0] * nxyzstart[zIndex]; ccp4->vol[0].origin[1] = yaxis[1] * nxyzstart[yIndex] + zaxis[1] * nxyzstart[zIndex]; ccp4->vol[0].origin[2] = zaxis[2] * nxyzstart[zIndex]; #endif ccp4->vol[0].xaxis[0] = xaxis[0] * (extent[xIndex]-1); ccp4->vol[0].xaxis[1] = 0; ccp4->vol[0].xaxis[2] = 0; ccp4->vol[0].yaxis[0] = yaxis[0] * (extent[yIndex]-1); ccp4->vol[0].yaxis[1] = yaxis[1] * (extent[yIndex]-1); ccp4->vol[0].yaxis[2] = 0; ccp4->vol[0].zaxis[0] = zaxis[0] * (extent[zIndex]-1); ccp4->vol[0].zaxis[1] = zaxis[1] * (extent[zIndex]-1); ccp4->vol[0].zaxis[2] = zaxis[2] * (extent[zIndex]-1); ccp4->vol[0].xsize = extent[xIndex]; ccp4->vol[0].ysize = extent[yIndex]; ccp4->vol[0].zsize = extent[zIndex]; ccp4->vol[0].has_color = 0; #if 0 printf("ccp4plugin) origin: %.3f %.3f %.3f\n", ccp4->vol[0].origin[0], ccp4->vol[0].origin[1], ccp4->vol[0].origin[2]); printf("ccp4plugin) xax': %g %g %g\n", ccp4->vol[0].xaxis[0], ccp4->vol[0].xaxis[1], ccp4->vol[0].xaxis[2]); printf("ccp4plugin) yax': %g %g %g\n", ccp4->vol[0].yaxis[0], ccp4->vol[0].yaxis[1], ccp4->vol[0].yaxis[2]); printf("ccp4plugin) zax': %g %g %g\n", ccp4->vol[0].zaxis[0], ccp4->vol[0].zaxis[1], ccp4->vol[0].zaxis[2]); printf("ccp4plugin) sz: %d %d %d\n", ccp4->vol[0].xsize, ccp4->vol[0].ysize, ccp4->vol[0].zsize); #endif return ccp4; }
static void *open_fs4_read(const char *filepath, const char *filetype, int *natoms) { fs4_t *fs4; FILE *fd; float header[32], scale, fmsCellSize[3], alpha, beta, gamma, z1, z2, z3; int dataBegin, blocksize, geom[16], fmsGridSize[3], norn, swap=0; fd = fopen(filepath, "rb"); if (!fd) { fprintf(stderr, "fs4plugin) Error opening file.\n"); return NULL; } // Use the first four-byte integer in the file to determine the file's // byte-order fread(&dataBegin, sizeof(int), 1, fd); if (dataBegin > 255) { // check if the bytes need to be swapped swap4_aligned(&dataBegin, 1); if (dataBegin <= 255) { swap = 1; } else { fprintf(stderr, "fs4plugin) Cannot read file: header block is too large.\n"); return NULL; } } // Read the header rewind(fd); blocksize = fortread_4(header, 32, swap, fd); // Handle files produced by old versions of (cns|ccp)2fsfour if (blocksize == 28) { printf("fs4plugin) Recognized %s cns2fsfour map.\n", swap ? "opposite-endian" : "same-endian"); // Read the geometry block blocksize = fortread_4(geom, 16, swap, fd); if (blocksize != 7) { fprintf(stderr, "fs4plugin) Incorrect size for geometry block.\n"); return NULL; } fmsGridSize[0] = geom[0]; fmsGridSize[1] = geom[1]; fmsGridSize[2] = geom[2]; norn = geom[4]; // Warn about assumptions printf("fs4plugin) Warning: file does not contain unit cell lengths or angles.\n"); scale = 50.0; fmsCellSize[0] = 1.0; fmsCellSize[1] = 1.0; fmsCellSize[2] = 1.0; alpha = 90.0; beta = 90.0; gamma = 90.0; } // Handle standard fsfour files else if (blocksize == 31) { printf("fs4plugin) Recognize standard fsfour map.\n"); fmsCellSize[0] = header[21]; fmsCellSize[1] = header[22]; fmsCellSize[2] = header[23]; alpha = header[24]; beta = header[25]; gamma = header[26]; // Skip the symmetry block if one present blocksize = fortread_4(geom, 16, swap, fd); if (blocksize == 9) { printf("fs4plugin) Skipping symmetry block.\n"); blocksize = fortread_4(geom, 16, swap, fd); } // Read the geometry block if (blocksize != 13) { fprintf(stderr, "fs4plugin) Incorrect size for geometry block.\n"); return NULL; } fmsGridSize[0] = geom[0]; fmsGridSize[1] = geom[1]; fmsGridSize[2] = geom[2]; scale = *((float *) geom + 3); if (scale == 0) { scale = 50; } norn = geom[4]; if ((norn < 0) || (norn > 2)) { fprintf(stderr, "fs4plugin) norn out of range.\n"); return NULL; } } // Unrecognized format else { fprintf(stderr, "fs4plugin) Unrecognized map format.\n"); return NULL; } // Convert degrees to radians alpha *= M_PI / 180.0; beta *= M_PI / 180.0; gamma *= M_PI / 180.0; // Warn about assumptions printf("fs4plugin) Warning: file does not contain molecule center.\nCentering at <0, 0, 0>\n"); // Allocate and initialize the fs4 structure fs4 = new fs4_t; fs4->fd = fd; fs4->vol = NULL; *natoms = MOLFILE_NUMATOMS_NONE; fs4->nsets = 1; // this file contains only one data set fs4->swap = swap; fs4->scale = scale; if (norn == 0) { // x fast, z medium, y slow fs4->x = 0; fs4->y = 2; fs4->z = 1; fs4->f = 0; fs4->m = 2; fs4->s = 1; } else if (norn == 1) { // y fast, z medium, x slow fs4->x = 2; fs4->y = 0; fs4->z = 1; fs4->f = 1; fs4->m = 2; fs4->s = 0; } else { // norn ==2 // x fast, y medium, z slow fs4->x = 0; fs4->y = 1; fs4->z = 2; fs4->f = 0; fs4->m = 1; fs4->s = 2; } fs4->vol = new molfile_volumetric_t[1]; strcpy(fs4->vol[0].dataname, "Fsfour Electron Density Map"); // Place the origin at {0 0 0} fs4->vol[0].origin[0] = 0.0; fs4->vol[0].origin[1] = 0.0; fs4->vol[0].origin[2] = 0.0; fs4->vol[0].xaxis[0] = fmsCellSize[0]; fs4->vol[0].xaxis[1] = 0.0; fs4->vol[0].xaxis[2] = 0.0; fs4->vol[0].yaxis[0] = cos(gamma) * fmsCellSize[1]; fs4->vol[0].yaxis[1] = sin(gamma) * fmsCellSize[1]; fs4->vol[0].yaxis[2] = 0.0; z1 = cos(beta); z2 = (cos(alpha) - cos(beta)*cos(gamma)) / sin(gamma); z3 = sqrt(1.0 - z1*z1 - z2*z2); fs4->vol[0].zaxis[0] = z1 * fmsCellSize[2]; fs4->vol[0].zaxis[1] = z2 * fmsCellSize[2]; fs4->vol[0].zaxis[2] = z3 * fmsCellSize[2]; fs4->vol[0].xsize = fmsGridSize[fs4->x]; fs4->vol[0].ysize = fmsGridSize[fs4->y]; fs4->vol[0].zsize = fmsGridSize[fs4->z]; fs4->vol[0].has_color = 0; return fs4; }
static int read_uhbd_data(void *v, int set, float *datablock, float *colorblock) { uhbd_t *uhbd = (uhbd_t *)v; FILE *fd = uhbd->fd; char inbuf[LINESIZE]; float grid[6]; int z, xsize, ysize, zsize, xysize, count, count2, total, i; xsize = uhbd->vol[0].xsize; ysize = uhbd->vol[0].ysize; zsize = uhbd->vol[0].zsize; xysize = xsize * ysize; total = xysize * zsize; if (uhbd->scale) { int headerblock[6]; // The binary data is written one z-slice at a time. First, a // block of three ints indicating which slice is next, of the form // kk, im, jm, where kk is the on-based slice index, and im and jm // are the x and y dimensions. We just read past them and also read the // start of the next block, which is the actual data. for (z=0; z<zsize; z++) { if (fread(headerblock, sizeof(int), 6, fd) != 6) { fprintf(stderr, "uhbdplugin) Error reading header block in binary uhbd file\n"); return MOLFILE_ERROR; } // TODO: some sanity checks on the header block. if (fread(datablock + z*xysize, sizeof(float), xysize, fd) != xysize) { fprintf(stderr, "uhbdplugin) Error reading data block in binary uhbd file\n"); return MOLFILE_ERROR; } // read the trailing block delimiter fseek(fd, 4, SEEK_CUR); } if (uhbd->doswap) { swap4_aligned(datablock, total); } return MOLFILE_SUCCESS; } /* Read the values from the file */ for (z = 0; z < zsize; z++) { // read header if (uhbdgets(inbuf, LINESIZE, fd, "uhbdplugin) error while getting density plane indices\n") == NULL) return MOLFILE_ERROR; // read data for (count = 0; count < xysize/6; count++) { if (uhbdgets(inbuf, LINESIZE, fd, "uhbdplugin) error while getting density values\n") == NULL) return MOLFILE_ERROR; if (sscanf(inbuf, "%e %e %e %e %e %e", &grid[0], &grid[1], &grid[2], &grid[3], &grid[4], &grid[5]) != 6) { printf("uhbdplugin) Error reading grid data.\n"); return MOLFILE_ERROR; } for (i = 0; i < 6; i++) { datablock[i + count*6 + z*xysize] = grid[i]; } } if ((xysize%6) != 0) { if (uhbdgets(inbuf, LINESIZE, fd, "uhbdplugin) error reading data elements modulo 6\n") == NULL) return MOLFILE_ERROR; count2 = sscanf(inbuf, "%e %e %e %e %e %e", &grid[0], &grid[1], &grid[2], &grid[3], &grid[4], &grid[5]); if (count2 != (xysize%6)) { printf("uhbdplugin) Error: incorrect number of data points.\n"); return MOLFILE_ERROR; } for (i = 0; i < count2; i++) { datablock[i + (count+1)*6 + z*xysize] = grid[i]; } } } return MOLFILE_SUCCESS; }
static void *open_ccp4_read(const char *filepath, const char *filetype, int *natoms) { FILE *fd; ccp4_t *ccp4; char mapString[4], symData[81]; int nxyzstart[3], extent[3], grid[3], crs2xyz[3], mode, symBytes; float origin2k[3]; int swap, i, xIndex, yIndex, zIndex; long dataOffset, filesize; float cellDimensions[3], cellAngles[3], xaxis[3], yaxis[3], zaxis[3]; float alpha, beta, gamma, xScale, yScale, zScale, z1, z2, z3; fd = fopen(filepath, "rb"); if (!fd) { printf("ccp4plugin) Error opening file %s\n", filepath); return NULL; } if ( (fread(extent, sizeof(int), 3, fd) != 3) || (fread(&mode, sizeof(int), 1, fd) != 1) || (fread(nxyzstart, sizeof(int), 3, fd) != 3) || (fread(grid, sizeof(int), 3, fd) != 3) || (fread(cellDimensions, sizeof(float), 3, fd) != 3) || (fread(cellAngles, sizeof(float), 3, fd) != 3) || (fread(crs2xyz, sizeof(int), 3, fd) != 3) ) { printf("ccp4plugin) Error: Improperly formatted line.\n"); return NULL; } // Check the number of bytes used for storing symmetry operators // (word 23, byte 92) fseek(fd, 23 * 4, SEEK_SET); if ((fread(&symBytes, sizeof(int), 1, fd) != 1) ) { printf("ccp4plugin) Error: Failed reading symmetry bytes record.\n"); return NULL; } // read MRC2000 Origin record at word 49, byte 196, and use it if necessary // http://www2.mrc-lmb.cam.ac.uk/image2000.html fseek(fd, 49 * 4, SEEK_SET); if (fread(origin2k, sizeof(float), 3, fd) != 3) { printf("ccp4plugin) Error: unable to read ORIGIN records at offset 196.\n"); } // Check for the string "MAP" at word 52 byte 208, indicating a CCP4 file. fseek(fd, 52 * 4, SEEK_SET); if ( (fgets(mapString, 4, fd) == NULL) || (strcmp(mapString, "MAP") != 0) ) { printf("ccp4plugin) Error: 'MAP' string missing, not a valid CCP4 file.\n"); return NULL; } swap = 0; // Check the data type of the file. if (mode != 2) { // Check if the byte-order is flipped swap4_aligned(&mode, 1); if (mode != 2) { printf("ccp4plugin) Error: Non-real (32-bit float) data types are unsupported.\n"); return NULL; } else { swap = 1; // enable byte swapping } } // Swap all the information obtained from the header if (swap == 1) { swap4_aligned(extent, 3); swap4_aligned(nxyzstart, 3); swap4_aligned(origin2k, 3); swap4_aligned(grid, 3); swap4_aligned(cellDimensions, 3); swap4_aligned(cellAngles, 3); swap4_aligned(crs2xyz, 3); swap4_aligned(&symBytes, 1); } #if 1 printf("ccp4plugin) extent: %d x %d x %d\n", extent[0], extent[1], extent[2]); printf("ccp4plugin) nxyzstart: %d x %d x %d\n", nxyzstart[0], nxyzstart[1], nxyzstart[2]); printf("ccp4plugin) origin2k: %f x %f x %f\n", origin2k[0], origin2k[1], origin2k[2]); printf("ccp4plugin) grid: %d x %d x %d\n", grid[0], grid[1], grid[2]); printf("ccp4plugin) celldim: %f x %f x %f\n", cellDimensions[0], cellDimensions[1], cellDimensions[2]); printf("cpp4plugin)cellangles: %f, %f, %f\n", cellAngles[0], cellAngles[1], cellAngles[2]); printf("ccp4plugin) crs2xyz: %d %d %d\n", crs2xyz[0], crs2xyz[1], crs2xyz[2]); printf("ccp4plugin) symBytes: %d\n", symBytes); #endif // Check the dataOffset: this fixes the problem caused by files claiming // to have symmetry records when they do not. fseek(fd, 0, SEEK_END); filesize = ftell(fd); dataOffset = filesize - 4*(extent[0]*extent[1]*extent[2]); if (dataOffset != (CCP4HDSIZE + symBytes)) { if (dataOffset == CCP4HDSIZE) { // Bogus symmetry record information printf("ccp4plugin) Warning: file contains bogus symmetry record.\n"); symBytes = 0; } else if (dataOffset < CCP4HDSIZE) { printf("ccp4plugin) Error: File appears truncated and doesn't match header.\n"); return NULL; } else if ((dataOffset > CCP4HDSIZE) && (dataOffset < (1024*1024))) { // Fix for loading SPIDER files which are larger than usual // In this specific case, we must absolutely trust the symBytes record dataOffset = CCP4HDSIZE + symBytes; printf("ccp4plugin) Warning: File is larger than expected and doesn't match header.\n"); printf("ccp4plugin) Warning: Continuing file load, good luck!\n"); } else { printf("ccp4plugin) Error: File is MUCH larger than expected and doesn't match header.\n"); return NULL; } } // Read symmetry records -- organized as 80-byte lines of text. if (symBytes != 0) { printf("ccp4plugin) Symmetry records found:\n"); fseek(fd, CCP4HDSIZE, SEEK_SET); for (i = 0; i < symBytes/80; i++) { fgets(symData, 81, fd); printf("ccp4plugin) %s\n", symData); } } // check extent and grid interval counts if (grid[0] == 0 && extent[0] > 0) { grid[0] = extent[0] - 1; printf("ccp4plugin) Warning: Fixed X interval count\n"); } if (grid[1] == 0 && extent[1] > 0) { grid[1] = extent[1] - 1; printf("ccp4plugin) Warning: Fixed Y interval count\n"); } if (grid[2] == 0 && extent[2] > 0) { grid[2] = extent[2] - 1; printf("ccp4plugin) Warning: Fixed Z interval count\n"); } // Allocate and initialize the ccp4 structure ccp4 = new ccp4_t; ccp4->fd = fd; ccp4->vol = NULL; *natoms = MOLFILE_NUMATOMS_NONE; ccp4->nsets = 1; // this EDM file contains only one data set ccp4->swap = swap; ccp4->dataOffset = dataOffset; ccp4->vol = new molfile_volumetric_t[1]; strcpy(ccp4->vol[0].dataname, "CCP4 Electron Density Map"); // Mapping between CCP4 column, row, section and VMD x, y, z. if (crs2xyz[0] == 0 && crs2xyz[1] == 0 && crs2xyz[2] == 0) { printf("ccp4plugin) Warning: All crs2xyz records are zero.\n"); printf("ccp4plugin) Warning: Setting crs2xyz to 1, 2, 3\n"); crs2xyz[0] = 1; crs2xyz[0] = 2; crs2xyz[0] = 3; } ccp4->xyz2crs[crs2xyz[0]-1] = 0; ccp4->xyz2crs[crs2xyz[1]-1] = 1; ccp4->xyz2crs[crs2xyz[2]-1] = 2; xIndex = ccp4->xyz2crs[0]; yIndex = ccp4->xyz2crs[1]; zIndex = ccp4->xyz2crs[2]; // calculate non-orthogonal unit cell coordinates alpha = (M_PI / 180.0) * cellAngles[0]; beta = (M_PI / 180.0) * cellAngles[1]; gamma = (M_PI / 180.0) * cellAngles[2]; if (cellDimensions[0] == 0.0 && cellDimensions[1] == 0.0 && cellDimensions[2] == 0.0) { printf("ccp4plugin) Warning: Cell dimensions are all zero.\n"); printf("ccp4plugin) Warning: Setting to 1.0, 1.0, 1.0 for viewing.\n"); printf("ccp4plugin) Warning: Map file will not align with other structures.\n"); cellDimensions[0] = 1.0; cellDimensions[1] = 1.0; cellDimensions[2] = 1.0; } xScale = cellDimensions[0] / grid[0]; yScale = cellDimensions[1] / grid[1]; zScale = cellDimensions[2] / grid[2]; // calculate non-orthogonal unit cell coordinates xaxis[0] = xScale; xaxis[1] = 0; xaxis[2] = 0; yaxis[0] = cos(gamma) * yScale; yaxis[1] = sin(gamma) * yScale; yaxis[2] = 0; z1 = cos(beta); z2 = (cos(alpha) - cos(beta)*cos(gamma)) / sin(gamma); z3 = sqrt(1.0 - z1*z1 - z2*z2); zaxis[0] = z1 * zScale; zaxis[1] = z2 * zScale; zaxis[2] = z3 * zScale; #if 1 // Handle both MRC-2000 and older format maps if (origin2k[0] == 0.0f && origin2k[1] == 0.0f && origin2k[2] == 0.0f) { printf("ccp4plugin) using CCP4 n[xyz]start origin\n"); ccp4->vol[0].origin[0] = xaxis[0] * nxyzstart[xIndex] + yaxis[0] * nxyzstart[yIndex] + zaxis[0] * nxyzstart[zIndex]; ccp4->vol[0].origin[1] = yaxis[1] * nxyzstart[yIndex] + zaxis[1] * nxyzstart[zIndex]; ccp4->vol[0].origin[2] = zaxis[2] * nxyzstart[zIndex]; } else { // Use ORIGIN records rather than old n[xyz]start records // http://www2.mrc-lmb.cam.ac.uk/image2000.html // XXX the ORIGIN field is only used by the EM community, and // has undefined meaning for non-orthogonal maps and/or // non-cubic voxels, etc. printf("ccp4plugin) using MRC2000 origin\n"); ccp4->vol[0].origin[0] = origin2k[xIndex]; ccp4->vol[0].origin[1] = origin2k[yIndex]; ccp4->vol[0].origin[2] = origin2k[zIndex]; } #else // old code that only pays attention to old MRC nxstart/nystart/nzstart ccp4->vol[0].origin[0] = xaxis[0] * nxyzstart[xIndex] + yaxis[0] * nxyzstart[yIndex] + zaxis[0] * nxyzstart[zIndex]; ccp4->vol[0].origin[1] = yaxis[1] * nxyzstart[yIndex] + zaxis[1] * nxyzstart[zIndex]; ccp4->vol[0].origin[2] = zaxis[2] * nxyzstart[zIndex]; #endif #if 0 printf("ccp4plugin) origin: %.3f %.3f %.3f\n", ccp4->vol[0].origin[0], ccp4->vol[0].origin[1], ccp4->vol[0].origin[2]); #endif ccp4->vol[0].xaxis[0] = xaxis[0] * (extent[xIndex]-1); ccp4->vol[0].xaxis[1] = 0; ccp4->vol[0].xaxis[2] = 0; ccp4->vol[0].yaxis[0] = yaxis[0] * (extent[yIndex]-1); ccp4->vol[0].yaxis[1] = yaxis[1] * (extent[yIndex]-1); ccp4->vol[0].yaxis[2] = 0; ccp4->vol[0].zaxis[0] = zaxis[0] * (extent[zIndex]-1); ccp4->vol[0].zaxis[1] = zaxis[1] * (extent[zIndex]-1); ccp4->vol[0].zaxis[2] = zaxis[2] * (extent[zIndex]-1); ccp4->vol[0].xsize = extent[xIndex]; ccp4->vol[0].ysize = extent[yIndex]; ccp4->vol[0].zsize = extent[zIndex]; ccp4->vol[0].has_color = 0; return ccp4; }
void IMDSimBlocking::get_next_ts(float *pos, IMDEnergies *buf) { new_coords_ready = 0; memcpy(pos, curpos, 3*numcoords*sizeof(float)); memcpy(buf, &imdEnergies, sizeof(IMDEnergies)); if (need2flip) swap4_aligned(pos, 3*numcoords); }
/* * Read a dcd timestep from a dcd file * Input: fd - a file struct opened for binary reading, from which the * header information has already been read. * natoms, nfixed, first, *freeind, reverse, charmm - the corresponding * items as set by read_dcdheader * first - true if this is the first frame we are reading. * x, y, z: space for natoms each of floats. * unitcell - space for six floats to hold the unit cell data. * Not set if no unit cell data is present. * Output: 0 on success, negative error code on failure. * Side effects: x, y, z contain the coordinates for the timestep read. * unitcell holds unit cell data if present. */ static int read_dcdstep(fio_fd fd, int N, float *X, float *Y, float *Z, float *unitcell, int num_fixed, int first, int *indexes, float *fixedcoords, int reverseEndian, int charmm) { int ret_val, rec_scale; /* Return value from read */ if (charmm & DCD_HAS_64BIT_REC) { rec_scale=RECSCALE64BIT; } else { rec_scale=RECSCALE32BIT; } if ((num_fixed==0) || first) { /* temp storage for reading formatting info */ /* note: has to be max size we'll ever use */ int tmpbuf[6*RECSCALEMAX]; fio_iovec iov[7]; /* I/O vector for fio_readv() call */ fio_size_t readlen; /* number of bytes actually read */ int i; /* if there are no fixed atoms or this is the first timestep read */ /* then we read all coordinates normally. */ /* read the charmm periodic cell information */ /* XXX this too should be read together with the other items in a */ /* single fio_readv() call in order to prevent lots of extra */ /* kernel/user context switches. */ ret_val = read_charmm_extrablock(fd, charmm, reverseEndian, unitcell); if (ret_val) return ret_val; /* setup the I/O vector for the call to fio_readv() */ iov[0].iov_base = (fio_caddr_t) &tmpbuf[0]; /* read format integer */ iov[0].iov_len = rec_scale*sizeof(int); iov[1].iov_base = (fio_caddr_t) X; /* read X coordinates */ iov[1].iov_len = sizeof(float)*N; iov[2].iov_base = (fio_caddr_t) &tmpbuf[1*rec_scale]; /* read 2 format integers */ iov[2].iov_len = rec_scale*sizeof(int) * 2; iov[3].iov_base = (fio_caddr_t) Y; /* read Y coordinates */ iov[3].iov_len = sizeof(float)*N; iov[4].iov_base = (fio_caddr_t) &tmpbuf[3*rec_scale]; /* read 2 format integers */ iov[4].iov_len = rec_scale*sizeof(int) * 2; iov[5].iov_base = (fio_caddr_t) Z; /* read Y coordinates */ iov[5].iov_len = sizeof(float)*N; iov[6].iov_base = (fio_caddr_t) &tmpbuf[5*rec_scale]; /* read format integer */ iov[6].iov_len = rec_scale*sizeof(int); readlen = fio_readv(fd, &iov[0], 7); if (readlen != (rec_scale*6*sizeof(int) + 3*N*sizeof(float))) return DCD_BADREAD; /* convert endianism if necessary */ if (reverseEndian) { swap4_aligned(&tmpbuf[0], rec_scale*6); swap4_aligned(X, N); swap4_aligned(Y, N); swap4_aligned(Z, N); } /* double-check the fortran format size values for safety */ if(rec_scale == 1) { for (i=0; i<6; i++) { if (tmpbuf[i] != sizeof(float)*N) return DCD_BADFORMAT; } } else { for (i=0; i<6; i++) { if ((tmpbuf[2*i]+tmpbuf[2*i+1]) != sizeof(float)*N) return DCD_BADFORMAT; } } /* copy fixed atom coordinates into fixedcoords array if this was the */ /* first timestep, to be used from now on. We just copy all atoms. */ if (num_fixed && first) { memcpy(fixedcoords, X, N*sizeof(float)); memcpy(fixedcoords+N, Y, N*sizeof(float)); memcpy(fixedcoords+2*N, Z, N*sizeof(float)); } /* read in the optional charmm 4th array */ /* XXX this too should be read together with the other items in a */ /* single fio_readv() call in order to prevent lots of extra */ /* kernel/user context switches. */ ret_val = read_charmm_4dim(fd, charmm, reverseEndian); if (ret_val) return ret_val; } else { /* if there are fixed atoms, and this isn't the first frame, then we */ /* only read in the non-fixed atoms for all subsequent timesteps. */ ret_val = read_charmm_extrablock(fd, charmm, reverseEndian, unitcell); if (ret_val) return ret_val; ret_val = read_fixed_atoms(fd, N, N-num_fixed, indexes, reverseEndian, fixedcoords, fixedcoords+3*N, X, charmm); if (ret_val) return ret_val; ret_val = read_fixed_atoms(fd, N, N-num_fixed, indexes, reverseEndian, fixedcoords+N, fixedcoords+3*N, Y, charmm); if (ret_val) return ret_val; ret_val = read_fixed_atoms(fd, N, N-num_fixed, indexes, reverseEndian, fixedcoords+2*N, fixedcoords+3*N, Z, charmm); if (ret_val) return ret_val; ret_val = read_charmm_4dim(fd, charmm, reverseEndian); if (ret_val) return ret_val; } return DCD_SUCCESS; }
static int read_ccp4_data(void *v, int set, float *datablock, float *colorblock) { ccp4_t *ccp4 = (ccp4_t *)v; int x, y, z, xSize, ySize, zSize, extent[3], coord[3]; long xySize; FILE *fd = ccp4->fd; xSize = ccp4->vol[0].xsize; ySize = ccp4->vol[0].ysize; zSize = ccp4->vol[0].zsize; xySize = xSize * ySize; // coord = <col, row, sec> // extent = <colSize, rowSize, secSize> extent[ccp4->xyz2crs[0]] = xSize; extent[ccp4->xyz2crs[1]] = ySize; extent[ccp4->xyz2crs[2]] = zSize; fseek(fd, ccp4->dataOffset, SEEK_SET); // Read entire rows of data from the file, then write into the // datablock with the correct slice ordering. if ((ccp4->voxtype == MRC_TYPE_BYTE) && (ccp4->dataflags & DATA_FLAG_SIGNED)) { printf("ccp4plugin) reading signed-byte voxel data\n"); signed char *rowdata = new signed char[extent[0]]; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if ( fread(rowdata, sizeof(char), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + long(y*xSize) + long(z*xySize)] = rowdata[coord[0]]; } } } delete [] rowdata; } else if ((ccp4->voxtype == MRC_TYPE_BYTE) && !(ccp4->dataflags & DATA_FLAG_SIGNED)) { printf("ccp4plugin) reading unsigned-byte voxel data\n"); unsigned char *rowdata = new unsigned char[extent[0]]; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if ( fread(rowdata, sizeof(unsigned char), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + long(y*xSize) + long(z*xySize)] = rowdata[coord[0]]; } } } delete [] rowdata; } else if (ccp4->voxtype == MRC_TYPE_FLOAT) { printf("ccp4plugin) reading float (32-bit real) voxel data\n"); float *rowdata = new float[extent[0]]; int x, y, z; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (fread(rowdata, sizeof(float), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + long(y*xSize) + long(z*xySize)] = rowdata[coord[0]]; } } } delete [] rowdata; if (ccp4->swap == 1) swap4_aligned(datablock, xySize * zSize); } else if (ccp4->voxtype == MRC_TYPE_SHORT) { printf("ccp4plugin) reading short (16-bit int) voxel data\n"); short *rowdata = new short[extent[0]]; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (fread(rowdata, sizeof(short), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ccp4->swap == 1) swap2_aligned(rowdata, extent[0]); for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + long(y*xSize) + long(z*xySize)] = rowdata[coord[0]]; } } } delete [] rowdata; } else if (ccp4->voxtype == MRC_TYPE_SHORT2) { /* IMOD developers said that this is not used anymore and not worth our time to implement */ printf("TYPE_SHORT2 not implemented yet...\n"); return MOLFILE_ERROR; } else if (ccp4->voxtype == MRC_TYPE_USHORT) { printf("ccp4plugin) reading unsigned short (16-bit int) voxel data\n"); unsigned short *rowdata = new unsigned short[extent[0]]; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (fread(rowdata, sizeof(unsigned short), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ccp4->swap == 1) swap2_aligned(rowdata, extent[0]); for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; datablock[x + long(y*xSize) + long(z*xySize)] = rowdata[coord[0]]; } } } delete [] rowdata; } else if (ccp4->voxtype == MRC_TYPE_UCHAR3) { printf("ccp4plugin) reading unsigned char * 3 (8-bit uchar * 3) voxel data\n"); uchar3 *rowdata = new uchar3[extent[0]]; float grayscale; for (coord[2] = 0; coord[2] < extent[2]; coord[2]++) { for (coord[1] = 0; coord[1] < extent[1]; coord[1]++) { if (feof(fd)) { printf("ccp4plugin) Unexpected end-of-file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if (ferror(fd)) { printf("ccp4plugin) Problem reading the file.\n"); delete [] rowdata; return MOLFILE_ERROR; } if ( fread(rowdata, sizeof(uchar3), extent[0], fd) != extent[0] ) { printf("ccp4plugin) Error reading data row.\n"); delete [] rowdata; return MOLFILE_ERROR; } for (coord[0] = 0; coord[0] < extent[0]; coord[0]++) { x = coord[ccp4->xyz2crs[0]]; y = coord[ccp4->xyz2crs[1]]; z = coord[ccp4->xyz2crs[2]]; grayscale = rowdata[coord[0]].red + rowdata[coord[0]].blue + rowdata[coord[0]].green; datablock[x + long(y*xSize) + long(z*xySize)] = grayscale/3.0; } } } delete [] rowdata; } return MOLFILE_SUCCESS; }