/* !C****************************************************************************** Output_t *OpenOutput(char *file_name, Img_coord_int_t *size) !C****************************************************************************** !Description: 'OutputFile' sets up the 'output' data structure, opens the output file for write access, and creates the output Science Data Set (SDS). !Input Parameters:thi file_name output file name nband number of bands (SDSs) to be created sds_name names of SDSs to be created size SDS size !Output Parameters: (returns) 'output' data structure or NULL when an error occurs !Team Unique Header: ! Design Notes: 1. When 'OutputFile' returns sucessfully, the file is open for HDF access and the SDS is open for access. 2. An error status is returned when: a. the output image dimensions are zero or negative b. an invalid output data type is passed c. memory allocation is not successful d. duplicating strings is not successful e. errors occur when opening the output HDF file f. errors occur when creating and initializing the SDS. 3. Error messages are handled with the 'RETURN_ERROR' macro. 4. 'FreeOutput' should be called to deallocate memory used by the 'output' data structures. 5. 'CloseFile' should be called after all of the data is written and before the 'output' data structure memory is released. !END**************************************************************************** */ Output_t *OpenOutput(char *file_name, Img_coord_int_t *size) { Output_t *this; char *error_string = (char *)NULL; Myhdf_dim_t *dim[MYHDF_MAX_RANK]; Myhdf_sds_t *sds; int ir, ib; int nband_csm_setup; char *sds_name_csm[NBAND_CSM] = {"cloud_snow_mask"}; /* Check parameters */ if (size->l < 1) RETURN_ERROR("invalid number of output lines", "OpenOutput", (Output_t *)NULL); if (size->s < 1) RETURN_ERROR("invalid number of samples per output line", "OpenOutput", (Output_t *)NULL); /* Create the Output data structure */ this = (Output_t *)malloc(sizeof(Output_t)); if (this == (Output_t *)NULL) RETURN_ERROR("allocating Output data structure", "OpenOutput", (Output_t *)NULL); /* Populate the data structure */ this->file_name = DupString(file_name); if (this->file_name == (char *)NULL) { free(this); RETURN_ERROR("duplicating file name", "OpenOutput", (Output_t *)NULL); } this->open = false; this->size.l = size->l; this->size.s = size->s; for (ib = 0; ib < NBAND_CSM; ib++) { this->sds_csm[ib].name = (char *)NULL; this->sds_csm[ib].dim[0].name = (char *)NULL; this->sds_csm[ib].dim[1].name = (char *)NULL; } /* Open file for SD access */ this->sds_file_id = SDstart((char *)file_name, DFACC_RDWR); if (this->sds_file_id == HDF_ERROR) { free(this->file_name); free(this); RETURN_ERROR("opening output file for SD access", "OpenOutput", (Output_t *)NULL); } this->open = true; /* Set up the KT SDSs */ /*****************************************************************/ /**** new new new ****/ /*****************************************************************/ nband_csm_setup = 0; for (ib = 0; ib < NBAND_CSM; ib++) { sds = &this->sds_csm[ib]; sds->type = DFNT_UINT8; sds->rank = 2; sds->name = DupString(sds_name_csm[ib]); if (sds->name == (char *)NULL) { error_string = "duplicating sds name"; break; } dim[0] = &sds->dim[0]; dim[1] = &sds->dim[1]; dim[0]->nval = this->size.l; dim[1]->nval = this->size.s; dim[0]->type = dim[1]->type = sds->type; dim[0]->name = DupString(DIM_CSM_LINE); if (dim[0]->name == (char *)NULL) { error_string = "duplicating dim name (l)"; break; } dim[1]->name = DupString(DIM_CSM_SAMP); if (dim[1]->name == (char *)NULL) { error_string = "duplicating dim name (s)"; break; } if (!PutSDSInfo(this->sds_file_id, sds)) { error_string = "setting up the SDS"; break; } for (ir = 0; ir < sds->rank; ir++) { if (!PutSDSDimInfo(sds->id, dim[ir], ir)) { error_string = "setting up the dimension"; break; } } if (error_string != (char *)NULL) break; nband_csm_setup++; } if (error_string == (char *)NULL) { if (sizeof(uint8) != sizeof(unsigned char)) { for (ib = 0; ib < NBAND_CSM; ib++) { this->buf_csm[ib] = (uint8 *)calloc(this->size.s, sizeof(uint8)); if (this->buf_csm[ib] == (uint8 *)NULL) { error_string = "allocating input buffer"; break; } } } } if (error_string != (char *)NULL) { for (ib = 0; ib < NBAND_CSM; ib++) { sds = &this->sds_csm[ib]; if (sds->name != (char *)NULL) free(sds->name); if (ib < nband_csm_setup) SDendaccess(sds->id); if ( sizeof(uint8) != sizeof(unsigned char) && this->buf_csm[ib] != (uint8 *)NULL ) free(this->buf_csm[ib]); if (sds->dim[0].name != (char *)NULL) free(sds->dim[0].name); if (sds->dim[1].name != (char *)NULL) free(sds->dim[1].name); } SDend(this->sds_file_id); free(this->file_name); free(this); RETURN_ERROR(error_string, "OpenOutput", (Output_t *)NULL); } return this; }
Output_t *OutputFile(char *file_name, char *sds_name, int output_data_type, Space_def_t *space_def) /* !C****************************************************************************** !Description: 'OutputFile' sets up the 'output' data structure, opens the output file for write access, and creates the output Science Data Set (SDS). !Input Parameters: file_name output file name sds_name name of sds to be created output_data_type output HDF data type; data types currently supported are CHAR8, UINT8, INT8, INT16, UINT16, INT32, and UINT32. space_def output space definition; the following fields are input: img_size !Output Parameters: (returns) 'output' data structure or NULL when an error occurs !Team Unique Header: ! Design Notes: 1. When 'OutputFile' returns sucessfully, the file is open for HDF access and the SDS is open for access. 2. An error status is returned when: a. the output image dimensions are zero or negative b. an invalid output data type is passed c. memory allocation is not successful d. duplicating strings is not successful e. errors occur when opening the output HDF file f. errors occur when creating and initializing the SDS. 3. Error messages are handled with the 'LOG_RETURN_ERROR' macro. 4. 'FreeOutput' should be called to deallocate memory used by the 'output' data structures. 5. 'CloseFile' should be called after all of the data is written and before the 'output' data structure memory is released. !END**************************************************************************** */ { Output_t *this; int ir; char *error_string = (char *)NULL; char tmpstr[1024]; /* Check parameters */ if (space_def->img_size.l < 1) LOG_RETURN_ERROR("invalid number of output lines", "OutputFile", (Output_t *)NULL); if (space_def->img_size.s < 1) LOG_RETURN_ERROR("invalid number of samples per output line", "OutputFile", (Output_t *)NULL); if (output_data_type != DFNT_CHAR8 && output_data_type != DFNT_UINT8 && output_data_type != DFNT_INT8 && output_data_type != DFNT_INT16 && output_data_type != DFNT_UINT16 && output_data_type != DFNT_INT32 && output_data_type != DFNT_UINT32) LOG_RETURN_ERROR("output data type not supported", "OpenOutput", (Output_t *)NULL); /* Create the Output data structure */ this = (Output_t *)malloc(sizeof(Output_t)); if (this == (Output_t *)NULL) LOG_RETURN_ERROR("allocating Output data structure", "OpenOutput", (Output_t *)NULL); /* Populate the data structure */ this->file_name = DupString(file_name); if (this->file_name == (char *)NULL) { free(this); LOG_RETURN_ERROR("duplicating file name", "OutputFile", (Output_t *)NULL); } this->sds.name = DupString(sds_name); if (this->sds.name == (char *)NULL) { free(this->file_name); free(this); LOG_RETURN_ERROR("duplicating sds name", "OutputFile", (Output_t *)NULL); } this->size.l = space_def->img_size.l; this->size.s = space_def->img_size.s; /* Open file for SD access */ this->sds_file_id = SDstart((char *)file_name, DFACC_RDWR); if (this->sds_file_id == HDF_ERROR) { free(this->sds.name); free(this->file_name); free(this); LOG_RETURN_ERROR("opening output file for SD access", "OutputFile", (Output_t *)NULL); } this->open = true; /* Set up SDS */ this->sds.type = output_data_type; this->sds.rank = 2; this->sds.dim[0].nval = this->size.l; this->sds.dim[1].nval = this->size.s; if (!PutSDSInfo(this->sds_file_id, &this->sds)) error_string = "setting up the SDS"; if (error_string == (char *)NULL) { this->sds.dim[0].type = output_data_type; this->sds.dim[1].type = output_data_type; if (space_def->proj_num == PROJ_GEO) sprintf (tmpstr, "lines %.8f", space_def->pixel_size*DEG); else sprintf (tmpstr, "lines %.2f", space_def->pixel_size); this->sds.dim[0].name = DupString(tmpstr); if (this->sds.dim[0].name == (char *)NULL) { SDendaccess(this->sds.id); error_string = "duplicating dim name (l)"; } } if (error_string == (char *)NULL) { if (space_def->proj_num == PROJ_GEO) sprintf (tmpstr, "samps %.8f", space_def->pixel_size*DEG); else sprintf (tmpstr, "samps %.2f", space_def->pixel_size); this->sds.dim[1].name = DupString(tmpstr); if (this->sds.dim[1].name == (char *)NULL) { free(this->sds.dim[0].name); SDendaccess(this->sds.id); error_string = "duplicating dim name (s)"; } } if (error_string == (char *)NULL) { for (ir = 0; ir < this->sds.rank; ir++) { if (!PutSDSDimInfo(this->sds.id, &this->sds.dim[ir], ir)) { free(this->sds.dim[1].name); free(this->sds.dim[0].name); SDendaccess(this->sds.id); error_string = "setting up the SDS"; break; } } } if (error_string != (char *)NULL) { SDend(this->sds_file_id); free(this->sds.name); free(this->file_name); free(this); LOG_RETURN_ERROR(error_string, "OutputFile", (Output_t *)NULL); } return this; }
/****************************************************************************** !Description: 'OutputFile' sets up the 'output' data structure, opens the output file for write access, and creates the output Science Data Set (SDS). !Input Parameters:ds_output file_name output file name nband number of image bands (SDSs) to be created nband_qa number of QA bands (SDSs) to be created sds_names array of SDS names for each image band qa_sds_names array of SDS names for each QA band size SDS size !Output Parameters: (returns) 'output' data structure or NULL when an error occurs !Team Unique Header: !Design Notes: *****************************************************************************/ Output_t *OpenOutput(char *file_name, int nband, int nband_qa, char sds_names[NBAND_REFL_MAX_OUT][MAX_STR_LEN], char qa_sds_names[NUM_QA_BAND][MAX_STR_LEN], Img_coord_int_t *size) { Output_t *ds_output = NULL; char *error_string = NULL; Myhdf_dim_t *dim[MYHDF_MAX_RANK]; Myhdf_sds_t *sds = NULL; int ir, ib; //float *buf = NULL; int16 *buf = NULL; uint8 *qa_buf = NULL; /* Check parameters */ if (size->l < 1) RETURN_ERROR("invalid number of output lines", "OpenOutput", NULL); if (size->s < 1) RETURN_ERROR("invalid number of samples per output line", "OpenOutput", NULL); if (nband < 1 || nband > NBAND_REFL_MAX_OUT) RETURN_ERROR("invalid number of bands", "OpenOutput", NULL); /* Create the Output data structure */ ds_output = (Output_t *)malloc(sizeof(Output_t)); if (ds_output == NULL) RETURN_ERROR("allocating Output data structure", "OpenOutput", NULL); /* Populate the data structure */ ds_output->file_name = DupString(file_name); if (ds_output->file_name == (char *)NULL) { free(ds_output); RETURN_ERROR("duplicating file name", "OpenOutput", NULL); } ds_output->open = false; ds_output->nband = nband; ds_output->nqa_band = nband_qa; ds_output->size.l = size->l; ds_output->size.s = size->s; for (ib = 0; ib < ds_output->nband; ib++) { ds_output->sds[ib].name = NULL; ds_output->sds[ib].dim[0].name = NULL; ds_output->sds[ib].dim[1].name = NULL; ds_output->buf[ib] = NULL; } for (ib = 0; ib < ds_output->nqa_band; ib++) { ds_output->qa_sds[ib].name = NULL; ds_output->qa_sds[ib].dim[0].name = NULL; ds_output->qa_sds[ib].dim[1].name = NULL; ds_output->qa_buf[ib] = NULL; } /* Open file for SD access */ ds_output->sds_file_id = SDstart((char *)file_name, DFACC_RDWR); if (ds_output->sds_file_id == HDF_ERROR) { free(ds_output->file_name); free(ds_output); RETURN_ERROR("opening output file for SD access", "OpenOutput", NULL); } ds_output->open = true; /* Set up the image SDSs */ for (ib = 0; ib < ds_output->nband; ib++) { sds = &ds_output->sds[ib]; sds->rank = 2; sds->type = DFNT_INT16; sds->name = DupString(sds_names[ib]); if (sds->name == NULL) { error_string = "duplicating sds name"; RETURN_ERROR(error_string, "CreateOutput", false); } dim[0] = &sds->dim[0]; dim[1] = &sds->dim[1]; dim[0]->nval = ds_output->size.l; dim[1]->nval = ds_output->size.s; dim[0]->type = dim[1]->type = sds->type; dim[0]->name = DupString("YDim_Grid"); if (dim[0]->name == NULL) { error_string = "duplicating dim name (l)"; RETURN_ERROR(error_string, "CreateOutput", false); } dim[1]->name = DupString("XDim_Grid"); if (dim[1]->name == NULL) { error_string = "duplicating dim name (s)"; RETURN_ERROR(error_string, "CreateOutput", false); } if (!PutSDSInfo(ds_output->sds_file_id, sds)) { error_string = "setting up the SDS"; RETURN_ERROR(error_string, "CreateOutput", false); } for (ir = 0; ir < sds->rank; ir++) { if (!PutSDSDimInfo(sds->id, dim[ir], ir)) { error_string = "setting up the dimension"; RETURN_ERROR(error_string, "CreateOutput", false); } } } /* end for image bands */ /* Set up the QA SDSs */ for (ib = 0; ib < ds_output->nqa_band; ib++) { sds = &ds_output->qa_sds[ib]; sds->rank = 2; sds->type = DFNT_UINT8; sds->name = DupString(qa_sds_names[ib]); if (sds->name == NULL) { error_string = "duplicating sds name"; RETURN_ERROR(error_string, "CreateOutput", false); } dim[0] = &sds->dim[0]; dim[1] = &sds->dim[1]; dim[0]->nval = ds_output->size.l; dim[1]->nval = ds_output->size.s; dim[0]->type = dim[1]->type = sds->type; dim[0]->name = DupString("YDim_Grid"); if (dim[0]->name == NULL) { error_string = "duplicating dim name (l)"; RETURN_ERROR(error_string, "CreateOutput", false); } dim[1]->name = DupString("XDim_Grid"); if (dim[1]->name == NULL) { error_string = "duplicating dim name (s)"; RETURN_ERROR(error_string, "CreateOutput", false); } if (!PutSDSInfo(ds_output->sds_file_id, sds)) { error_string = "setting up the SDS"; RETURN_ERROR(error_string, "CreateOutput", false); } for (ir = 0; ir < sds->rank; ir++) { if (!PutSDSDimInfo(sds->id, dim[ir], ir)) { error_string = "setting up the dimension"; RETURN_ERROR(error_string, "CreateOutput", false); } } } /* end for QA bands */ /* Allocate output buffers */ // buf = (float *)calloc((size_t)(ds_output->size.s * ds_output->nband), sizeof(float)); buf = (int16 *)calloc((size_t)(ds_output->size.s * ds_output->nband), sizeof(int16)); if (buf == NULL) error_string = "allocating output buffer"; else { ds_output->buf[0] = buf; for (ib = 1; ib < ds_output->nband; ib++) ds_output->buf[ib] = ds_output->buf[ib - 1] + ds_output->size.s; } qa_buf = (uint8 *)calloc((size_t)(ds_output->size.s * ds_output->nqa_band), sizeof(uint8)); if (qa_buf == NULL) error_string = "allocating output QA buffer"; else { ds_output->qa_buf[0] = qa_buf; for (ib = 1; ib < ds_output->nqa_band; ib++) ds_output->qa_buf[ib] = ds_output->qa_buf[ib - 1] + ds_output->size.s; } if (error_string != NULL) { FreeOutput (ds_output); CloseOutput (ds_output); RETURN_ERROR(error_string, "OpenOutput", (Output_t *)NULL); } return ds_output; }