Changeset 524
- Timestamp:
- 12/01/14 18:58:38 (10 years ago)
- Location:
- XIOS/branchs/xios-1.0/src/output
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
XIOS/branchs/xios-1.0/src/output/netCdfInterface.cpp
r508 r524 8 8 */ 9 9 10 #include "netCdfInterface.hpp" 11 #include "netCdfException.hpp" 12 13 namespace xios 14 { 15 /*! 16 This function creates a new netcdf file and return its id 17 \param [in] fileName Name of the file 18 \param [in] cMode create mode 19 \param [in/out] ncId id of the created file 20 \return Status code 21 */ 22 int CNetCdfInterface::create(const StdString& fileName, int cMode, int& ncId) 23 { 24 int status = nc_create((fileName.c_str()), cMode, &ncId); 25 if (NC_NOERR != status) 26 { 27 StdString errormsg(nc_strerror(status)); 28 StdStringStream sstr; 29 sstr << "Error in calling function : nc_create((fileName.c_str()), cMode, &ncId) " << std::endl 30 << errormsg << std::endl 31 << "Unable to create file, given its name : " << fileName 32 << "and its creation mode " << creationMode2String(cMode) << std::endl; 33 StdString e = sstr.str(); 34 throw CNetCdfException(e); 35 } 36 37 return status; 38 } 39 40 /*! 41 This function creates a new netcdf file on parallel file system 42 \param [in] fileName Name of the file 43 \param [in] cMode create mode 44 \param [in] comm MPI communicator 45 \param [in] info MPI information 46 \param [in/out] ncId id of the created file 47 \return Status code 48 */ 49 int CNetCdfInterface::createPar(const StdString& fileName, int cMode, MPI_Comm comm, MPI_Info info, int& ncId) 50 { 51 int status = xios::nc_create_par((fileName.c_str()), cMode, comm, info, &ncId); 52 if (NC_NOERR != status) 53 { 54 StdString errormsg(nc_strerror(status)); 55 StdStringStream sstr; 56 sstr << "Error in calling function : nc_create_par((fileName.c_str()), cMode, comm, info, &ncId) " << std::endl 57 << errormsg << std::endl 58 << "Unable to create file on parallel filesys, given its name : " << std::endl 59 << "and its creation mode " << creationMode2String(cMode) << std::endl; 60 StdString e = sstr.str(); 61 throw CNetCdfException(e); 62 } 63 64 return status; 65 } 66 67 /*! 68 This function opens a netcdf file, given its name and open mode, return its id 69 \param [in] fileName Name of the file 70 \param [in] oMode open mode 71 \param [in/out] ncId id of the opening file 72 \return Status code 73 */ 74 int CNetCdfInterface::open(const StdString& fileName, int oMode, int& ncId) 75 { 76 int status = nc_open((fileName.c_str()), oMode, &ncId); 77 if (NC_NOERR != status) 78 { 79 StdString errormsg(nc_strerror(status)); 80 StdStringStream sstr; 81 sstr << "Error in calling function : nc_open((fileName.c_str()), oMode, &ncId) "<< std::endl 82 << errormsg << std::endl 83 << "Unable to open file, given its name : " << fileName 84 << "and its open mode " << openMode2String(oMode) << std::endl; 85 StdString e = sstr.str(); 86 throw CNetCdfException(e); 87 } 88 89 return status; 90 } 91 92 93 /*! 94 This function opens a new netcdf file on parallel file system 95 \param [in] fileName Name of the file 96 \param [in] oMode open mode 97 \param [in] comm MPI communicator 98 \param [in] info MPI information 99 \param [in/out] ncId id of the opened file 100 \return Status code 101 */ 102 int CNetCdfInterface::openPar(const StdString& fileName, int oMode, MPI_Comm comm, MPI_Info info, int& ncId) 103 { 104 int status = xios::nc_open_par((fileName.c_str()), oMode, comm, info, &ncId); 105 if (NC_NOERR != status) 106 { 107 StdString errormsg(nc_strerror(status)); 108 StdStringStream sstr; 109 sstr << "Error in calling function " << "nc_open_par((fileName.c_str()), oMode, comm, info, &ncId) " << std::endl 110 << errormsg << std::endl 111 << "Unable to open file on parallel filesys, given its name : " << fileName 112 << "and its open mode " << openMode2String(oMode) << std::endl; 113 StdString e = sstr.str(); 114 throw CNetCdfException(e); 115 } 116 117 return status; 118 } 119 120 /*! 121 This function closes a netcdf file, given its id 122 \param [in] ncId id of the opening netcdf file 123 \return Status code 124 */ 125 int CNetCdfInterface::close(int ncId) 126 { 127 int status = nc_close(ncId); 128 if (NC_NOERR != status) 129 { 130 StdString errormsg(nc_strerror(status)); 131 StdStringStream sstr; 132 sstr << "Error in calling function " << "nc_close(ncId)" << std::endl 133 << errormsg << std::endl 134 << "Unable to close file, given its id : " << ncId << std::endl; 135 StdString e = sstr.str(); 136 throw CNetCdfException(e); 137 } 138 139 return status; 140 } 141 142 /*! 143 This function put a netcdf file into define mode, given its id 144 \param [in] ncId id of the opening netcdf file to be put into define mode 145 \return Status code 146 */ 147 int CNetCdfInterface::reDef(int ncId) 148 { 149 int status = nc_redef(ncId); 150 if (NC_NOERR != status) 151 { 152 StdString errormsg(nc_strerror(status)); 153 StdStringStream sstr; 154 sstr << "Error in calling function " << "nc_redef(ncId)" << std::endl 155 << errormsg << std::endl 156 << "Unable to put this file into define mode given its id : " << ncId << std::endl; 157 StdString e = sstr.str(); 158 throw CNetCdfException(e); 159 } 160 161 return status; 162 } 163 164 /*! 165 This function ends a netcdf file define mode, given its id 166 \param [in] ncId id of the opening netcdf file to be put into define mode 167 \return Status code 168 */ 169 int CNetCdfInterface::endDef(int ncId) 170 { 171 int status = nc_enddef(ncId); 172 if (NC_NOERR != status) 173 { 174 StdString errormsg(nc_strerror(status)); 175 StdStringStream sstr; 176 177 sstr << "Error in calling function " << "nc_enddef(ncId)" << std::endl 178 << errormsg << std::endl 179 << "Unable to end define mode of this file, given its id : " << ncId << std::endl; 180 StdString e = sstr.str(); 181 throw CNetCdfException(e); 182 } 183 184 return status; 185 } 186 187 /*! 188 This function makes a request to netcdf with ncid and group name then return ncid of the named group 189 \param [in] ncid Groupd id (or File Id) 190 \param [in] grpName Name of the desired group (or file) 191 \param [in/out] grpId Group id if the group is found 192 \return Status code 193 */ 194 int CNetCdfInterface::inqNcId(int ncid, const StdString& grpName, int& grpId) 195 { 196 int status = nc_inq_ncid(ncid, (grpName.c_str()), &grpId); 197 if (NC_NOERR != status) 198 { 199 StdString errormsg(nc_strerror(status)); 200 StdStringStream sstr; 201 202 sstr << "Error in calling function " << "nc_inq_ncid(ncid, (grpName.c_str()), &grpId)" << std::endl 203 << errormsg << std::endl 204 << "Unable to get id of a group (File), given its name : " << grpName << std::endl; 205 StdString e = sstr.str(); 206 throw CNetCdfException(e); 207 } 208 209 return status; 210 } 211 212 213 /*! 214 This function makes a request to netcdf with ncid and variable name then return ncid of the named variable 215 \param [in] ncid Groupd id (or File Id) 216 \param [in] varName Name of the desired variable 217 \param [in/out] varId Variable id if this variable is found 218 \return Status code 219 */ 220 int CNetCdfInterface::inqVarId(int ncid,const StdString& varName, int& varId) 221 { 222 int status = nc_inq_varid(ncid, (varName.c_str()), &varId); 223 if (NC_NOERR != status) 224 { 225 StdString errormsg(nc_strerror(status)); 226 StdStringStream sstr; 227 228 sstr << "Error in calling function : nc_inq_varid(ncid, (varName.c_str()), &varId)" << std::endl 229 << (errormsg) << std::endl 230 << "Unable to get id of variable with name : " << varName << std::endl; 231 StdString e = sstr.str(); 232 throw CNetCdfException(e); 233 } 234 235 return status; 236 } 237 238 /*! 239 This function makes a request to netcdf with a netCdf dimension name then return ncid of the named dimension 240 \param [in] ncid Groupd id (or File Id) 241 \param [in] dimName Name of the desired dimension 242 \param [in/out] dimId Dimension id if this dimension is found 243 \return Status code 244 */ 245 int CNetCdfInterface::inqDimId(int ncid,const StdString& dimName, int& dimId) 246 { 247 int status = nc_inq_dimid(ncid, (dimName.c_str()), &dimId); 248 if (NC_NOERR != status) 249 { 250 StdString errormsg(nc_strerror(status)); 251 StdStringStream sstr; 252 253 sstr << "Error in calling function " << "nc_inq_dimid(ncid, (dimName.c_str()), &dimId)" << std::endl 254 << errormsg << std::endl 255 << "Unable to get id of dimension, given its name : " << dimName << std::endl; 256 StdString e = sstr.str(); 257 throw CNetCdfException(e); 258 } 259 260 return status; 261 } 262 263 /*! 264 This function makes a request to netcdf with a netCdf dimension name then return ncid of the named dimension 265 \param [in] ncid Groupd id (or File Id) 266 \param [in/out] dimId Dimension id if this dimension is found 267 \return Status code 268 */ 269 int CNetCdfInterface::inqUnLimDim(int ncid, int& dimId) 270 { 271 int status = nc_inq_unlimdim(ncid, &dimId); 272 if (NC_NOERR != status) 273 { 274 StdString errormsg(nc_strerror(status)); 275 StdStringStream sstr; 276 277 sstr << "Error in calling function " << "nc_inq_dimid" << std::endl 278 << errormsg << std::endl 279 << "Unable to get id of unlimited dimension " << std::endl; 280 StdString e = sstr.str(); 281 throw CNetCdfException(e); 282 } 283 284 return status; 285 } 286 287 /*! 288 This function makes a request to netcdf, returns name of a dimension, given its id 289 \param [in] ncid Groupd id (or File Id) 290 \param [in] dimId Id of desired dimension 291 \param [in/out] dimName Name of desired dimension 292 \return Status code 293 */ 294 int CNetCdfInterface::inqDimName(int ncid, int dimId, StdString& dimName) 295 { 296 char fullNameIn[NC_MAX_NAME +1]; 297 int status = nc_inq_dimname(ncid, dimId, fullNameIn); 298 if (NC_NOERR != status) 299 { 300 StdString errormsg(nc_strerror(status)); 301 StdStringStream sstr; 302 303 sstr << "Error in calling function " << "nc_inq_dimname(ncid, dimId, fullNameIn)" << std::endl 304 << errormsg << std::endl 305 << "Unable to get dimension name from its id : " << dimId << std::endl; 306 StdString e = sstr.str(); 307 throw CNetCdfException(e); 308 } 309 dimName = StdString(fullNameIn); 310 return status; 311 } 312 313 /*! 314 This function makes a request to netcdf, returns length of a dimension, given its id 315 \param [in] ncid Groupd id (or File Id) 316 \param [in] dimId Id of desired dimension 317 \param [in/out] dimLen Length of desired dimension 318 \return Status code 319 */ 320 int CNetCdfInterface::inqDimLen(int ncid, int dimId, StdSize& dimLen) 321 { 322 int status = nc_inq_dimlen(ncid, dimId, &dimLen); 323 if (NC_NOERR != status) 324 { 325 StdString errormsg(nc_strerror(status)); 326 StdStringStream sstr; 327 328 sstr << "Error in calling function " << "nc_inq_dimlen(ncid, dimId, &dimLen)" << std::endl 329 << errormsg << std::endl 330 << "Unable to get dimension length from its id: " << dimId << std::endl; 331 StdString e = sstr.str(); 332 throw CNetCdfException(e); 333 } 334 335 return status; 336 } 337 338 /*! 339 This function makes a request to netcdf, returns number of dimensions of a variable, given its id 340 \param [in] ncid Groupd id (or File Id) 341 \param [in] varId Id of variable 342 \param [in/out] ndims number of dimension of the variable 343 \return Status code 344 */ 345 int CNetCdfInterface::inqVarNDims(int ncid, int varId, int& nDims) 346 { 347 int status = nc_inq_varndims(ncid, varId, &nDims); 348 if (NC_NOERR != status) 349 { 350 StdString errormsg(nc_strerror(status)); 351 StdStringStream sstr; 352 353 sstr << "Error in calling function " << "nc_inq_varndims(ncid, varId, &nDims)" << std::endl 354 << errormsg << std::endl 355 << "Unable to get the number of dimension of variable with Id : " << varId << std::endl; 356 StdString e = sstr.str(); 357 throw CNetCdfException(e); 358 } 359 360 return status; 361 } 362 363 /*! 364 This function makes a request to netcdf, returns a list of dimension ID describing the shape of the variable, given its id 365 \param [in] ncid Groupd id (or File Id) 366 \param [in] varId Id of variable 367 \param [in/out] dimIds list of dimension of the variable 368 \return Status code 369 */ 370 int CNetCdfInterface::inqVarDimId(int ncid, int varId, int* dimIds) 371 { 372 int status = nc_inq_vardimid(ncid, varId, dimIds); 373 if (NC_NOERR != status) 374 { 375 StdString errormsg(nc_strerror(status)); 376 StdStringStream sstr; 377 378 sstr << "Error in calling function " << "nc_inq_vardimid(ncid, varId, dimIds)" << std::endl 379 << errormsg << std::endl 380 << "Unable to get list of dimension id of the variable with id " << varId << std::endl; 381 StdString e = sstr.str(); 382 throw CNetCdfException(e); 383 } 384 385 return status; 386 } 387 388 /*! 389 This function makes a request to netcdf, to find all dimension in a group 390 \param [in] ncid Groupd id (or File Id) 391 \param [in/out] nDims number of list of dimension 392 \param [in/out] dimIds list of dimension in a group or any of its parent 393 \param [in] includeParents number of parents 394 \return Status code 395 */ 396 int CNetCdfInterface::inqDimIds(int ncid, int& nDims, int* dimIds, int includeParents) 397 { 398 int status = nc_inq_dimids(ncid, &nDims, dimIds, includeParents); 399 if (NC_NOERR != status) 400 { 401 StdString errormsg(nc_strerror(status)); 402 StdStringStream sstr; 403 404 sstr << "Error in calling function " << "nc_inq_dimids(ncid, &nDims, dimIds, includeParents)" << std::endl; 405 sstr << errormsg << std::endl; 406 sstr << "Unable to retrieve number of dimension in the group with id : " << ncid << std::endl; 407 sstr << "With number of Parents " << includeParents << std::endl; 408 StdString e = sstr.str(); 409 throw CNetCdfException(e); 410 } 411 412 return status; 413 } 414 415 /*! 416 This function makes a request to netcdf with a id of a prent groupd and then return id of the created group, given its name 417 \param [in] parentNcid Id of parent groupd(or File Id) 418 \param [in] grpName Name of the desired group 419 \param [in/out] grpId Group id if this group is created sucessfully 420 \return Status code 421 */ 422 int CNetCdfInterface::defGrp(int parentNcid, const StdString& grpName, int& grpId) 423 { 424 int status = nc_def_grp(parentNcid, (grpName.c_str()), &grpId); 425 if (NC_NOERR != status) 426 { 427 StdString errormsg(nc_strerror(status)); 428 StdStringStream sstr; 429 430 sstr << "Error in calling function " << "nc_def_grp(parentNcid, (grpName.c_str()), &grpId)" << std::endl; 431 sstr << errormsg << std::endl; 432 sstr << "Unable to create group Id, given its name : " << grpName << std::endl; 433 StdString e = sstr.str(); 434 throw CNetCdfException(e); 435 } 436 437 return status; 438 } 439 440 /*! 441 This function makes a request to netcdf, add a new dimension to an open netcdf in define mode 442 \param [in] ncid Id of groupd(or File Id) 443 \param [in] dimName Name of the desired dimension 444 \param [in/out] grpId Group id if this group is created sucessfully 445 \return Status code 446 */ 447 int CNetCdfInterface::defDim(int ncid, const StdString& dimName, StdSize dimLen, int& dimId) 448 { 449 int status = nc_def_dim(ncid, (dimName.c_str()), dimLen, &dimId); 450 if (NC_NOERR != status) 451 { 452 StdString errormsg(nc_strerror(status)); 453 StdStringStream sstr; 454 455 sstr << "Error in calling function " << "nc_def_dim(ncid, (dimName.c_str()), dimLen, &dimId)" << std::endl; 456 sstr << errormsg << std::endl; 457 sstr << "Unable to create dimension with name : " << dimName 458 << " and with length " << dimLen << std::endl; 459 StdString e = sstr.str(); 460 throw CNetCdfException(e); 461 } 462 463 return status; 464 } 465 466 /*! 467 This function makes a request to netcdf with its id, to add a new variable to an open netCdf in define mode, 468 return a variable id, given its name, type, the number of dimensions and list of dimension id 469 \param [in] ncid Id of groupd(or File Id) 470 \param [in] varName Name of the desired dimension 471 \param [in] xtypes One of the set of predefined netCDF data types 472 \param [in] nDims Number of dimension for the variable 473 \param [in] dimIds List of ndims dimension ids corresponding to the variable dimensions 474 \param [in/out] varId Variable id if it is added sucessfully 475 \return Status code 476 */ 477 int CNetCdfInterface::defVar(int ncid,const StdString& varName, nc_type xtype, 478 int nDims, const int dimIds[], int& varId) 479 { 480 int status = nc_def_var(ncid, (varName.c_str()), xtype, nDims, dimIds, &varId); 481 if (NC_NOERR != status) 482 { 483 StdString errormsg(nc_strerror(status)); 484 StdStringStream sstr; 485 486 sstr << "Error in calling function " << " nc_def_var(ncid, (varName.c_str()), xtype, nDims, dimIds, &varId)" << std::endl; 487 sstr << errormsg << std::endl; 488 sstr << "Unable to add a new variable with name : " << varName 489 << " with type " << xtype 490 << " and number of dimension " << nDims << std::endl; 491 StdString e = sstr.str(); 492 throw CNetCdfException(e); 493 } 494 495 return status; 496 } 497 498 /*! 499 This function makes a request to netcdf with a ncid, to set the chunking size of a variable, 500 given variable id and type of storage 501 \param [in] ncid Id groupd(or File Id) 502 \param [in] varId Id of the variable 503 \param [in] storage Type of storage (It can be : NC_CONTIGUOUS, NC_CHUNKED) 504 \param [in/out] chunkSize array list of chunk sizes 505 \return Status code 506 */ 507 int CNetCdfInterface::defVarChunking(int ncid, int varId, int storage, StdSize chunkSize[]) 508 { 509 int status = nc_def_var_chunking(ncid, varId, storage, chunkSize); 510 if (NC_NOERR != status) 511 { 512 StdString errormsg(nc_strerror(status)); 513 StdStringStream sstr; 514 515 sstr << "Error in calling function " << "nc_def_var_chunking(ncid, varId, storage, chunkSize)" << std::endl; 516 sstr << errormsg << std::endl; 517 sstr << "Unable to set chunk size of the variable with id : " << varId 518 << " and storage type " << storage << std::endl; 519 StdString e = sstr.str(); 520 throw CNetCdfException(e); 521 } 522 523 return status; 524 } 525 526 /*! 527 This function makes a request to netcdf with a ncid, to set the fill parameters for a variable, 528 given variable id and type of fill 529 \param [in] ncid Id groupd(or File Id) 530 \param [in] varId Id of the variable 531 \param [in] noFill turn on/off nofill mode on a variable 532 \param [in/out] fillValue 533 \return Status code 534 */ 535 int CNetCdfInterface::defVarFill(int ncid, int varId, int noFill, void* fillValue) 536 { 537 int status = nc_def_var_fill(ncid, varId, noFill, fillValue); 538 if (NC_NOERR != status) 539 { 540 StdString errormsg(nc_strerror(status)); 541 StdStringStream sstr; 542 543 sstr << "Error in calling function " << "nc_def_var_fill(ncid, varId, noFill, fillValue)" << std::endl; 544 sstr << errormsg << std::endl; 545 sstr << "Unable to set fill parameters of the variable with id : " << varId 546 << " and fill option " << noFill << std::endl; 547 StdString e = sstr.str(); 548 throw CNetCdfException(e); 549 } 550 551 return status; 552 } 553 554 /*! 555 This function makes a request to netcdf with a ncid, to change the way read/write operations are performed 556 collectively or independently on the variable. 557 \param [in] ncid Id groupd(or File Id) 558 \param [in] varId Id of the variable 559 \param [in] noFill turn on/off nofill mode on a variable 560 \param [in/out] fillValue 561 \return Status code 562 */ 563 int CNetCdfInterface::varParAccess(int ncid, int varId, int access) 564 { 565 int status = nc_var_par_access(ncid, varId, access); 566 if (NC_NOERR != status) 567 { 568 StdString errormsg(nc_strerror(status)); 569 StdStringStream sstr; 570 571 sstr << "Error in calling function " << "nc_var_par_access(ncid, varId, access)" << std::endl; 572 sstr << errormsg << std::endl; 573 sstr << "Unable to change read/write option of the variable with id : " << varId << std::endl; 574 StdString e = sstr.str(); 575 throw CNetCdfException(e); 576 } 577 578 return status; 579 } 580 581 /*! 582 This function makes a synchronisation of the disk copy of a netCDF dataset. 583 \param [in] ncid Id groupd(or File Id) 584 \return Status code 585 */ 586 int CNetCdfInterface::sync(int ncid) 587 { 588 int status = nc_sync(ncid); 589 if (NC_NOERR != status) 590 { 591 StdString errormsg(nc_strerror(status)); 592 StdStringStream sstr; 593 594 sstr << "Error in calling function " << "nc_sync(ncid)" << std::endl; 595 sstr << errormsg << std::endl; 596 sstr << "Unable to make a synchronization of a netCDF file with id : " << ncid << std::endl; 597 StdString e = sstr.str(); 598 throw CNetCdfException(e); 599 } 600 601 return status; 602 } 603 604 /*! 605 This function makes a request to netcdf with its id, to add or change a variable attribute or gloabl attribute, 606 given its name, type, number of values provided for attribute 607 \param [in] ncid Id of groupd(or File Id) 608 \param [in] varId Id of the variable 609 \param [in] attrName Name of the attribute 610 \param [in] xtypes One of the set of predefined netCDF data types 611 \param [in] numVal Number of values 612 \param [in] op Array of values provided for attribute 613 \return Status code 614 */ 615 int CNetCdfInterface::putAtt(int ncid, int varId, const StdString& attrName, nc_type xtype, 616 StdSize numVal, const void* op) 617 { 618 int status = nc_put_att(ncid, varId, (attrName.c_str()), xtype, numVal, op); 619 if (NC_NOERR != status) 620 { 621 StdString errormsg(nc_strerror(status)); 622 StdStringStream sstr; 623 624 sstr << "Error in calling function " << "nc_put_att(ncid, varId, (attrName.c_str()), xtype, numVal, op)" << std::endl; 625 sstr << errormsg << std::endl; 626 sstr << "Unable to set attribute " << attrName << " for a variable with id : " << varId 627 << " with number of attribute " << numVal 628 << " with type " << xtype << std::endl; 629 StdString e = sstr.str(); 630 throw CNetCdfException(e); 631 } 632 633 return status; 634 } 635 636 // Some specilization of putAttributeType 637 template<> 638 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 639 StdSize numVal, const double* op) 640 { 641 return (nc_put_att_double(ncid, varid, attrName, NC_DOUBLE, numVal, op)); 642 } 643 644 template<> 645 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 646 StdSize numVal, const float* op) 647 { 648 return (nc_put_att_float(ncid, varid, attrName, NC_FLOAT, numVal, op)); 649 } 650 651 template<> 652 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 653 StdSize numVal, const int* op) 654 { 655 return (nc_put_att_int(ncid, varid, attrName, NC_INT, numVal, op)); 656 } 657 658 template<> 659 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 660 StdSize numVal, const long* op) 661 { 662 return (nc_put_att_long(ncid, varid, attrName, NC_LONG, numVal, op)); 663 } 664 665 template<> 666 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 667 StdSize numVal, const short* op) 668 { 669 return (nc_put_att_short(ncid, varid, attrName, NC_SHORT, numVal, op)); 670 } 671 672 673 // Some specilization of putVariableType 674 template<> 675 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const double* op) 676 { 677 return (nc_put_vara_double(ncid, varid, start, count, op)); 678 } 679 680 template<> 681 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const float* op) 682 { 683 return (nc_put_vara_float(ncid, varid, start, count, op)); 684 } 685 686 template<> 687 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const int* op) 688 { 689 return (nc_put_vara_int(ncid, varid, start, count, op)); 690 } 691 692 /*! 693 This function verifies an existence of a variable by using its name. 694 Be careful, althoug false means variable doens't exist, it could show that netCDF file doesn't either 695 \param [in] ncid Id of groupd(or File Id) 696 \param [in] attrName Name of the variable 697 \return Existence of variable 698 */ 699 bool CNetCdfInterface::isVarExisted(int ncId, const StdString& varName) 700 { 701 int varId = 0; 702 return (NC_NOERR == (nc_inq_varid(ncId, varName.c_str(), &varId))); 703 } 704 705 StdString CNetCdfInterface::openMode2String(int oMode) 706 { 707 StdString modeMes; 708 switch (oMode) 709 { 710 case NC_NOWRITE: 711 modeMes = StdString("NC_NOWRITE : Opening netCDF file with read-only access with buffering and caching access"); 712 break; 713 case NC_SHARE: 714 modeMes = StdString("NC_SHARE : Several processes can read the file concurrently"); 715 break; 716 case NC_WRITE: 717 modeMes = StdString("NC_WRITE : NetCDF file is readable and writable"); 718 break; 719 default: 720 modeMes = StdString("In the composed opening mode"); 721 break; 722 return modeMes; 723 } 724 } 725 726 StdString CNetCdfInterface::creationMode2String(int cMode) 727 { 728 StdString modeMes; 729 switch (cMode) 730 { 731 case NC_NOCLOBBER: 732 modeMes = StdString("NC_NOCLOBBER : Not overwrite an exisiting netCDF file "); 733 break; 734 case NC_SHARE: 735 modeMes = StdString("NC_SHARE : Several processes can read from and write into the file concurrently"); 736 break; 737 case NC_64BIT_OFFSET: 738 modeMes = StdString("NC_64BIT_OFFSET : NetCDF file is 64-bit offset"); 739 break; 740 case NC_NETCDF4: 741 modeMes = StdString("NC_NETCDF4 : NetCDF file is HDF5/NetCDF-4"); 742 break; 743 case NC_CLASSIC_MODEL: 744 modeMes = StdString("NC_CLASSIC_MODEL : NetCDF file is classical model"); 745 break; 746 default: 747 modeMes = StdString("In the composed creation mode"); 748 break; 749 return modeMes; 750 } 751 } 752 10 #include "netCdfInterface.hpp" 11 #include "netCdfException.hpp" 12 13 namespace xios 14 { 15 /*! 16 This function creates a new netcdf file and return its id 17 \param [in] fileName Name of the file 18 \param [in] cMode create mode 19 \param [in/out] ncId id of the created file 20 \return Status code 21 */ 22 int CNetCdfInterface::create(const StdString& fileName, int cMode, int& ncId) 23 { 24 int status = nc_create((fileName.c_str()), cMode, &ncId); 25 if (NC_NOERR != status) 26 { 27 StdString errormsg(nc_strerror(status)); 28 StdStringStream sstr; 29 sstr << "Error in calling function : nc_create((fileName.c_str()), cMode, &ncId) " << std::endl 30 << errormsg << std::endl 31 << "Unable to create file, given its name : " << fileName 32 << "and its creation mode " << creationMode2String(cMode) << std::endl; 33 StdString e = sstr.str(); 34 throw CNetCdfException(e); 35 } 36 37 return status; 38 } 39 40 /*! 41 This function creates a new netcdf file on parallel file system 42 \param [in] fileName Name of the file 43 \param [in] cMode create mode 44 \param [in] comm MPI communicator 45 \param [in] info MPI information 46 \param [in/out] ncId id of the created file 47 \return Status code 48 */ 49 int CNetCdfInterface::createPar(const StdString& fileName, int cMode, MPI_Comm comm, MPI_Info info, int& ncId) 50 { 51 int status = xios::nc_create_par((fileName.c_str()), cMode, comm, info, &ncId); 52 if (NC_NOERR != status) 53 { 54 StdString errormsg(nc_strerror(status)); 55 StdStringStream sstr; 56 sstr << "Error in calling function : nc_create_par((fileName.c_str()), cMode, comm, info, &ncId) " << std::endl 57 << errormsg << std::endl 58 << "Unable to create file on parallel filesys, given its name : " << std::endl 59 << "and its creation mode " << creationMode2String(cMode) << std::endl; 60 StdString e = sstr.str(); 61 throw CNetCdfException(e); 62 } 63 64 return status; 65 } 66 67 /*! 68 This function opens a netcdf file, given its name and open mode, return its id 69 \param [in] fileName Name of the file 70 \param [in] oMode open mode 71 \param [in/out] ncId id of the opening file 72 \return Status code 73 */ 74 int CNetCdfInterface::open(const StdString& fileName, int oMode, int& ncId) 75 { 76 int status = nc_open((fileName.c_str()), oMode, &ncId); 77 if (NC_NOERR != status) 78 { 79 StdString errormsg(nc_strerror(status)); 80 StdStringStream sstr; 81 sstr << "Error in calling function : nc_open((fileName.c_str()), oMode, &ncId) "<< std::endl 82 << errormsg << std::endl 83 << "Unable to open file, given its name : " << fileName 84 << "and its open mode " << openMode2String(oMode) << std::endl; 85 StdString e = sstr.str(); 86 throw CNetCdfException(e); 87 } 88 89 return status; 90 } 91 92 93 /*! 94 This function opens a new netcdf file on parallel file system 95 \param [in] fileName Name of the file 96 \param [in] oMode open mode 97 \param [in] comm MPI communicator 98 \param [in] info MPI information 99 \param [in/out] ncId id of the opened file 100 \return Status code 101 */ 102 int CNetCdfInterface::openPar(const StdString& fileName, int oMode, MPI_Comm comm, MPI_Info info, int& ncId) 103 { 104 int status = xios::nc_open_par((fileName.c_str()), oMode, comm, info, &ncId); 105 if (NC_NOERR != status) 106 { 107 StdString errormsg(nc_strerror(status)); 108 StdStringStream sstr; 109 sstr << "Error in calling function " << "nc_open_par((fileName.c_str()), oMode, comm, info, &ncId) " << std::endl 110 << errormsg << std::endl 111 << "Unable to open file on parallel filesys, given its name : " << fileName 112 << "and its open mode " << openMode2String(oMode) << std::endl; 113 StdString e = sstr.str(); 114 throw CNetCdfException(e); 115 } 116 117 return status; 118 } 119 120 /*! 121 This function closes a netcdf file, given its id 122 \param [in] ncId id of the opening netcdf file 123 \return Status code 124 */ 125 int CNetCdfInterface::close(int ncId) 126 { 127 int status = nc_close(ncId); 128 if (NC_NOERR != status) 129 { 130 StdString errormsg(nc_strerror(status)); 131 StdStringStream sstr; 132 sstr << "Error in calling function " << "nc_close(ncId)" << std::endl 133 << errormsg << std::endl 134 << "Unable to close file, given its id : " << ncId << std::endl; 135 StdString e = sstr.str(); 136 throw CNetCdfException(e); 137 } 138 139 return status; 140 } 141 142 /*! 143 This function put a netcdf file into define mode, given its id 144 \param [in] ncId id of the opening netcdf file to be put into define mode 145 \return Status code 146 */ 147 int CNetCdfInterface::reDef(int ncId) 148 { 149 int status = nc_redef(ncId); 150 if (NC_NOERR != status) 151 { 152 StdString errormsg(nc_strerror(status)); 153 StdStringStream sstr; 154 sstr << "Error in calling function " << "nc_redef(ncId)" << std::endl 155 << errormsg << std::endl 156 << "Unable to put this file into define mode given its id : " << ncId << std::endl; 157 StdString e = sstr.str(); 158 throw CNetCdfException(e); 159 } 160 161 return status; 162 } 163 164 /*! 165 This function ends a netcdf file define mode, given its id 166 \param [in] ncId id of the opening netcdf file to be put into define mode 167 \return Status code 168 */ 169 int CNetCdfInterface::endDef(int ncId) 170 { 171 int status = nc_enddef(ncId); 172 if (NC_NOERR != status) 173 { 174 StdString errormsg(nc_strerror(status)); 175 StdStringStream sstr; 176 177 sstr << "Error in calling function " << "nc_enddef(ncId)" << std::endl 178 << errormsg << std::endl 179 << "Unable to end define mode of this file, given its id : " << ncId << std::endl; 180 StdString e = sstr.str(); 181 throw CNetCdfException(e); 182 } 183 184 return status; 185 } 186 187 /*! 188 This function makes a request to netcdf with ncid and group name then return ncid of the named group 189 \param [in] ncid Groupd id (or File Id) 190 \param [in] grpName Name of the desired group (or file) 191 \param [in/out] grpId Group id if the group is found 192 \return Status code 193 */ 194 int CNetCdfInterface::inqNcId(int ncid, const StdString& grpName, int& grpId) 195 { 196 int status = nc_inq_ncid(ncid, (grpName.c_str()), &grpId); 197 if (NC_NOERR != status) 198 { 199 StdString errormsg(nc_strerror(status)); 200 StdStringStream sstr; 201 202 sstr << "Error in calling function " << "nc_inq_ncid(ncid, (grpName.c_str()), &grpId)" << std::endl 203 << errormsg << std::endl 204 << "Unable to get id of a group (File), given its name : " << grpName << std::endl; 205 StdString e = sstr.str(); 206 throw CNetCdfException(e); 207 } 208 209 return status; 210 } 211 212 213 /*! 214 This function makes a request to netcdf with ncid and variable name then return ncid of the named variable 215 \param [in] ncid Groupd id (or File Id) 216 \param [in] varName Name of the desired variable 217 \param [in/out] varId Variable id if this variable is found 218 \return Status code 219 */ 220 int CNetCdfInterface::inqVarId(int ncid,const StdString& varName, int& varId) 221 { 222 int status = nc_inq_varid(ncid, (varName.c_str()), &varId); 223 if (NC_NOERR != status) 224 { 225 StdString errormsg(nc_strerror(status)); 226 StdStringStream sstr; 227 228 sstr << "Error in calling function : nc_inq_varid(ncid, (varName.c_str()), &varId)" << std::endl 229 << (errormsg) << std::endl 230 << "Unable to get id of variable with name : " << varName << std::endl; 231 StdString e = sstr.str(); 232 throw CNetCdfException(e); 233 } 234 235 return status; 236 } 237 238 /*! 239 This function makes a request to netcdf with a netCdf dimension name then return ncid of the named dimension 240 \param [in] ncid Groupd id (or File Id) 241 \param [in] dimName Name of the desired dimension 242 \param [in/out] dimId Dimension id if this dimension is found 243 \return Status code 244 */ 245 int CNetCdfInterface::inqDimId(int ncid,const StdString& dimName, int& dimId) 246 { 247 int status = nc_inq_dimid(ncid, (dimName.c_str()), &dimId); 248 if (NC_NOERR != status) 249 { 250 StdString errormsg(nc_strerror(status)); 251 StdStringStream sstr; 252 253 sstr << "Error in calling function " << "nc_inq_dimid(ncid, (dimName.c_str()), &dimId)" << std::endl 254 << errormsg << std::endl 255 << "Unable to get id of dimension, given its name : " << dimName << std::endl; 256 StdString e = sstr.str(); 257 throw CNetCdfException(e); 258 } 259 260 return status; 261 } 262 263 /*! 264 This function makes a request to netcdf with a netCdf dimension name then return ncid of the named dimension 265 \param [in] ncid Groupd id (or File Id) 266 \param [in/out] dimId Dimension id if this dimension is found 267 \return Status code 268 */ 269 int CNetCdfInterface::inqUnLimDim(int ncid, int& dimId) 270 { 271 int status = nc_inq_unlimdim(ncid, &dimId); 272 if (NC_NOERR != status) 273 { 274 StdString errormsg(nc_strerror(status)); 275 StdStringStream sstr; 276 277 sstr << "Error in calling function " << "nc_inq_dimid" << std::endl 278 << errormsg << std::endl 279 << "Unable to get id of unlimited dimension " << std::endl; 280 StdString e = sstr.str(); 281 throw CNetCdfException(e); 753 282 } 283 284 return status; 285 } 286 287 /*! 288 This function makes a request to netcdf, returns name of a dimension, given its id 289 \param [in] ncid Groupd id (or File Id) 290 \param [in] dimId Id of desired dimension 291 \param [in/out] dimName Name of desired dimension 292 \return Status code 293 */ 294 int CNetCdfInterface::inqDimName(int ncid, int dimId, StdString& dimName) 295 { 296 char fullNameIn[NC_MAX_NAME +1]; 297 int status = nc_inq_dimname(ncid, dimId, fullNameIn); 298 if (NC_NOERR != status) 299 { 300 StdString errormsg(nc_strerror(status)); 301 StdStringStream sstr; 302 303 sstr << "Error in calling function " << "nc_inq_dimname(ncid, dimId, fullNameIn)" << std::endl 304 << errormsg << std::endl 305 << "Unable to get dimension name from its id : " << dimId << std::endl; 306 StdString e = sstr.str(); 307 throw CNetCdfException(e); 308 } 309 dimName = StdString(fullNameIn); 310 return status; 311 } 312 313 /*! 314 This function makes a request to netcdf, returns length of a dimension, given its id 315 \param [in] ncid Groupd id (or File Id) 316 \param [in] dimId Id of desired dimension 317 \param [in/out] dimLen Length of desired dimension 318 \return Status code 319 */ 320 int CNetCdfInterface::inqDimLen(int ncid, int dimId, StdSize& dimLen) 321 { 322 int status = nc_inq_dimlen(ncid, dimId, &dimLen); 323 if (NC_NOERR != status) 324 { 325 StdString errormsg(nc_strerror(status)); 326 StdStringStream sstr; 327 328 sstr << "Error in calling function " << "nc_inq_dimlen(ncid, dimId, &dimLen)" << std::endl 329 << errormsg << std::endl 330 << "Unable to get dimension length from its id: " << dimId << std::endl; 331 StdString e = sstr.str(); 332 throw CNetCdfException(e); 333 } 334 335 return status; 336 } 337 338 /*! 339 This function makes a request to netcdf, returns number of dimensions of a variable, given its id 340 \param [in] ncid Groupd id (or File Id) 341 \param [in] varId Id of variable 342 \param [in/out] ndims number of dimension of the variable 343 \return Status code 344 */ 345 int CNetCdfInterface::inqVarNDims(int ncid, int varId, int& nDims) 346 { 347 int status = nc_inq_varndims(ncid, varId, &nDims); 348 if (NC_NOERR != status) 349 { 350 StdString errormsg(nc_strerror(status)); 351 StdStringStream sstr; 352 353 sstr << "Error in calling function " << "nc_inq_varndims(ncid, varId, &nDims)" << std::endl 354 << errormsg << std::endl 355 << "Unable to get the number of dimension of variable with Id : " << varId << std::endl; 356 StdString e = sstr.str(); 357 throw CNetCdfException(e); 358 } 359 360 return status; 361 } 362 363 /*! 364 This function makes a request to netcdf, returns a list of dimension ID describing the shape of the variable, given its id 365 \param [in] ncid Groupd id (or File Id) 366 \param [in] varId Id of variable 367 \param [in/out] dimIds list of dimension of the variable 368 \return Status code 369 */ 370 int CNetCdfInterface::inqVarDimId(int ncid, int varId, int* dimIds) 371 { 372 int status = nc_inq_vardimid(ncid, varId, dimIds); 373 if (NC_NOERR != status) 374 { 375 StdString errormsg(nc_strerror(status)); 376 StdStringStream sstr; 377 378 sstr << "Error in calling function " << "nc_inq_vardimid(ncid, varId, dimIds)" << std::endl 379 << errormsg << std::endl 380 << "Unable to get list of dimension id of the variable with id " << varId << std::endl; 381 StdString e = sstr.str(); 382 throw CNetCdfException(e); 383 } 384 385 return status; 386 } 387 388 /*! 389 This function makes a request to netcdf, to find all dimension in a group 390 \param [in] ncid Groupd id (or File Id) 391 \param [in/out] nDims number of list of dimension 392 \param [in/out] dimIds list of dimension in a group or any of its parent 393 \param [in] includeParents number of parents 394 \return Status code 395 */ 396 int CNetCdfInterface::inqDimIds(int ncid, int& nDims, int* dimIds, int includeParents) 397 { 398 int status = nc_inq_dimids(ncid, &nDims, dimIds, includeParents); 399 if (NC_NOERR != status) 400 { 401 StdString errormsg(nc_strerror(status)); 402 StdStringStream sstr; 403 404 sstr << "Error in calling function " << "nc_inq_dimids(ncid, &nDims, dimIds, includeParents)" << std::endl; 405 sstr << errormsg << std::endl; 406 sstr << "Unable to retrieve number of dimension in the group with id : " << ncid << std::endl; 407 sstr << "With number of Parents " << includeParents << std::endl; 408 StdString e = sstr.str(); 409 throw CNetCdfException(e); 410 } 411 412 return status; 413 } 414 415 /*! 416 This function makes a request to netcdf with a id of a prent groupd and then return id of the created group, given its name 417 \param [in] parentNcid Id of parent groupd(or File Id) 418 \param [in] grpName Name of the desired group 419 \param [in/out] grpId Group id if this group is created sucessfully 420 \return Status code 421 */ 422 int CNetCdfInterface::defGrp(int parentNcid, const StdString& grpName, int& grpId) 423 { 424 int status = nc_def_grp(parentNcid, (grpName.c_str()), &grpId); 425 if (NC_NOERR != status) 426 { 427 StdString errormsg(nc_strerror(status)); 428 StdStringStream sstr; 429 430 sstr << "Error in calling function " << "nc_def_grp(parentNcid, (grpName.c_str()), &grpId)" << std::endl; 431 sstr << errormsg << std::endl; 432 sstr << "Unable to create group Id, given its name : " << grpName << std::endl; 433 StdString e = sstr.str(); 434 throw CNetCdfException(e); 435 } 436 437 return status; 438 } 439 440 /*! 441 This function makes a request to netcdf, add a new dimension to an open netcdf in define mode 442 \param [in] ncid Id of groupd(or File Id) 443 \param [in] dimName Name of the desired dimension 444 \param [in/out] grpId Group id if this group is created sucessfully 445 \return Status code 446 */ 447 int CNetCdfInterface::defDim(int ncid, const StdString& dimName, StdSize dimLen, int& dimId) 448 { 449 int status = nc_def_dim(ncid, (dimName.c_str()), dimLen, &dimId); 450 if (NC_NOERR != status) 451 { 452 StdString errormsg(nc_strerror(status)); 453 StdStringStream sstr; 454 455 sstr << "Error in calling function " << "nc_def_dim(ncid, (dimName.c_str()), dimLen, &dimId)" << std::endl; 456 sstr << errormsg << std::endl; 457 sstr << "Unable to create dimension with name : " << dimName 458 << " and with length " << dimLen << std::endl; 459 StdString e = sstr.str(); 460 throw CNetCdfException(e); 461 } 462 463 return status; 464 } 465 466 /*! 467 This function makes a request to netcdf with its id, to add a new variable to an open netCdf in define mode, 468 return a variable id, given its name, type, the number of dimensions and list of dimension id 469 \param [in] ncid Id of groupd(or File Id) 470 \param [in] varName Name of the desired dimension 471 \param [in] xtypes One of the set of predefined netCDF data types 472 \param [in] nDims Number of dimension for the variable 473 \param [in] dimIds List of ndims dimension ids corresponding to the variable dimensions 474 \param [in/out] varId Variable id if it is added sucessfully 475 \return Status code 476 */ 477 int CNetCdfInterface::defVar(int ncid,const StdString& varName, nc_type xtype, 478 int nDims, const int dimIds[], int& varId) 479 { 480 int status = nc_def_var(ncid, (varName.c_str()), xtype, nDims, dimIds, &varId); 481 if (NC_NOERR != status) 482 { 483 StdString errormsg(nc_strerror(status)); 484 StdStringStream sstr; 485 486 sstr << "Error in calling function " << " nc_def_var(ncid, (varName.c_str()), xtype, nDims, dimIds, &varId)" << std::endl; 487 sstr << errormsg << std::endl; 488 sstr << "Unable to add a new variable with name : " << varName 489 << " with type " << xtype 490 << " and number of dimension " << nDims << std::endl; 491 StdString e = sstr.str(); 492 throw CNetCdfException(e); 493 } 494 495 return status; 496 } 497 498 /*! 499 This function makes a request to netcdf with a ncid, to set the chunking size of a variable, 500 given variable id and type of storage 501 \param [in] ncid Id groupd(or File Id) 502 \param [in] varId Id of the variable 503 \param [in] storage Type of storage (It can be : NC_CONTIGUOUS, NC_CHUNKED) 504 \param [in/out] chunkSize array list of chunk sizes 505 \return Status code 506 */ 507 int CNetCdfInterface::defVarChunking(int ncid, int varId, int storage, StdSize chunkSize[]) 508 { 509 int status = nc_def_var_chunking(ncid, varId, storage, chunkSize); 510 if (NC_NOERR != status) 511 { 512 StdString errormsg(nc_strerror(status)); 513 StdStringStream sstr; 514 515 sstr << "Error in calling function " << "nc_def_var_chunking(ncid, varId, storage, chunkSize)" << std::endl; 516 sstr << errormsg << std::endl; 517 sstr << "Unable to set chunk size of the variable with id : " << varId 518 << " and storage type " << storage << std::endl; 519 StdString e = sstr.str(); 520 throw CNetCdfException(e); 521 } 522 523 return status; 524 } 525 526 /*! 527 This function makes a request to netcdf with a ncid, to set the fill parameters for a variable, 528 given variable id and type of fill 529 \param [in] ncid Id groupd(or File Id) 530 \param [in] varId Id of the variable 531 \param [in] noFill turn on/off nofill mode on a variable 532 \param [in/out] fillValue 533 \return Status code 534 */ 535 int CNetCdfInterface::defVarFill(int ncid, int varId, int noFill, void* fillValue) 536 { 537 int status = nc_def_var_fill(ncid, varId, noFill, fillValue); 538 if (NC_NOERR != status) 539 { 540 StdString errormsg(nc_strerror(status)); 541 StdStringStream sstr; 542 543 sstr << "Error in calling function " << "nc_def_var_fill(ncid, varId, noFill, fillValue)" << std::endl; 544 sstr << errormsg << std::endl; 545 sstr << "Unable to set fill parameters of the variable with id : " << varId 546 << " and fill option " << noFill << std::endl; 547 StdString e = sstr.str(); 548 throw CNetCdfException(e); 549 } 550 551 return status; 552 } 553 554 /*! 555 This function makes a request to netcdf with a ncid, to change the way read/write operations are performed 556 collectively or independently on the variable. 557 \param [in] ncid Id groupd(or File Id) 558 \param [in] varId Id of the variable 559 \param [in] noFill turn on/off nofill mode on a variable 560 \param [in/out] fillValue 561 \return Status code 562 */ 563 int CNetCdfInterface::varParAccess(int ncid, int varId, int access) 564 { 565 int status = nc_var_par_access(ncid, varId, access); 566 if (NC_NOERR != status) 567 { 568 StdString errormsg(nc_strerror(status)); 569 StdStringStream sstr; 570 571 sstr << "Error in calling function " << "nc_var_par_access(ncid, varId, access)" << std::endl; 572 sstr << errormsg << std::endl; 573 sstr << "Unable to change read/write option of the variable with id : " << varId << std::endl; 574 StdString e = sstr.str(); 575 throw CNetCdfException(e); 576 } 577 578 return status; 579 } 580 581 /*! 582 This function makes a synchronisation of the disk copy of a netCDF dataset. 583 \param [in] ncid Id groupd(or File Id) 584 \return Status code 585 */ 586 int CNetCdfInterface::sync(int ncid) 587 { 588 int status = nc_sync(ncid); 589 if (NC_NOERR != status) 590 { 591 StdString errormsg(nc_strerror(status)); 592 StdStringStream sstr; 593 594 sstr << "Error in calling function " << "nc_sync(ncid)" << std::endl; 595 sstr << errormsg << std::endl; 596 sstr << "Unable to make a synchronization of a netCDF file with id : " << ncid << std::endl; 597 StdString e = sstr.str(); 598 throw CNetCdfException(e); 599 } 600 601 return status; 602 } 603 604 /*! 605 This function makes a request to netcdf with its id, to add or change a variable attribute or gloabl attribute, 606 given its name, type, number of values provided for attribute 607 \param [in] ncid Id of groupd(or File Id) 608 \param [in] varId Id of the variable 609 \param [in] attrName Name of the attribute 610 \param [in] xtypes One of the set of predefined netCDF data types 611 \param [in] numVal Number of values 612 \param [in] op Array of values provided for attribute 613 \return Status code 614 */ 615 int CNetCdfInterface::putAtt(int ncid, int varId, const StdString& attrName, nc_type xtype, 616 StdSize numVal, const void* op) 617 { 618 int status = nc_put_att(ncid, varId, (attrName.c_str()), xtype, numVal, op); 619 if (NC_NOERR != status) 620 { 621 StdString errormsg(nc_strerror(status)); 622 StdStringStream sstr; 623 624 sstr << "Error in calling function " << "nc_put_att(ncid, varId, (attrName.c_str()), xtype, numVal, op)" << std::endl; 625 sstr << errormsg << std::endl; 626 sstr << "Unable to set attribute " << attrName << " for a variable with id : " << varId 627 << " with number of attribute " << numVal 628 << " with type " << xtype << std::endl; 629 StdString e = sstr.str(); 630 throw CNetCdfException(e); 631 } 632 633 return status; 634 } 635 636 // Some specilization of putAttributeType 637 template<> 638 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 639 StdSize numVal, const double* op) 640 { 641 return (nc_put_att_double(ncid, varid, attrName, NC_DOUBLE, numVal, op)); 642 } 643 644 template<> 645 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 646 StdSize numVal, const float* op) 647 { 648 return (nc_put_att_float(ncid, varid, attrName, NC_FLOAT, numVal, op)); 649 } 650 651 template<> 652 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 653 StdSize numVal, const int* op) 654 { 655 return (nc_put_att_int(ncid, varid, attrName, NC_INT, numVal, op)); 656 } 657 658 template<> 659 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 660 StdSize numVal, const long* op) 661 { 662 return (nc_put_att_long(ncid, varid, attrName, NC_LONG, numVal, op)); 663 } 664 665 template<> 666 int CNetCdfInterface::ncPutAttType(int ncid, int varid, const char* attrName, 667 StdSize numVal, const short* op) 668 { 669 return (nc_put_att_short(ncid, varid, attrName, NC_SHORT, numVal, op)); 670 } 671 672 673 // Some specilization of putVariableType 674 template<> 675 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const double* op) 676 { 677 return (nc_put_vara_double(ncid, varid, start, count, op)); 678 } 679 680 template<> 681 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const float* op) 682 { 683 return (nc_put_vara_float(ncid, varid, start, count, op)); 684 } 685 686 template<> 687 int CNetCdfInterface::ncPutVaraType(int ncid, int varid, const StdSize* start, const StdSize* count, const int* op) 688 { 689 return (nc_put_vara_int(ncid, varid, start, count, op)); 690 } 691 692 /*! 693 This function verifies an existence of a variable by using its name. 694 Be careful, althoug false means variable doens't exist, it could show that netCDF file doesn't either 695 \param [in] ncid Id of groupd(or File Id) 696 \param [in] attrName Name of the variable 697 \return Existence of variable 698 */ 699 bool CNetCdfInterface::isVarExisted(int ncId, const StdString& varName) 700 { 701 int varId = 0; 702 return (NC_NOERR == (nc_inq_varid(ncId, varName.c_str(), &varId))); 703 } 704 705 StdString CNetCdfInterface::openMode2String(int oMode) 706 { 707 StdString modeMes; 708 switch (oMode) 709 { 710 case NC_NOWRITE: 711 modeMes = StdString("NC_NOWRITE : Opening netCDF file with read-only access with buffering and caching access"); 712 break; 713 case NC_SHARE: 714 modeMes = StdString("NC_SHARE : Several processes can read the file concurrently"); 715 break; 716 case NC_WRITE: 717 modeMes = StdString("NC_WRITE : NetCDF file is readable and writable"); 718 break; 719 default: 720 modeMes = StdString("In the composed opening mode"); 721 break; 722 return modeMes; 723 } 724 } 725 726 StdString CNetCdfInterface::creationMode2String(int cMode) 727 { 728 StdString modeMes; 729 switch (cMode) 730 { 731 case NC_NOCLOBBER: 732 modeMes = StdString("NC_NOCLOBBER : Not overwrite an exisiting netCDF file "); 733 break; 734 case NC_SHARE: 735 modeMes = StdString("NC_SHARE : Several processes can read from and write into the file concurrently"); 736 break; 737 case NC_64BIT_OFFSET: 738 modeMes = StdString("NC_64BIT_OFFSET : NetCDF file is 64-bit offset"); 739 break; 740 case NC_NETCDF4: 741 modeMes = StdString("NC_NETCDF4 : NetCDF file is HDF5/NetCDF-4"); 742 break; 743 case NC_CLASSIC_MODEL: 744 modeMes = StdString("NC_CLASSIC_MODEL : NetCDF file is classical model"); 745 break; 746 default: 747 modeMes = StdString("In the composed creation mode"); 748 break; 749 return modeMes; 750 } 751 } 752 753 } -
XIOS/branchs/xios-1.0/src/output/netCdfInterface.hpp
r514 r524 11 11 12 12 #include "xmlioserver_spl.hpp" 13 14 #if !defined(USING_NETCDF_PAR) 15 #include "exception.hpp" 16 #endif 17 13 18 #include "mpi.hpp" 14 19 #include "netcdf.hpp" -
XIOS/branchs/xios-1.0/src/output/netcdf.hpp
r501 r524 24 24 25 25 #if !defined(USING_NETCDF_PAR) 26 27 26 #define NC_INDEPENDENT 0 27 #define NC_COLLECTIVE 1 28 28 #endif 29 29 … … 40 40 #endif 41 41 } 42 42 43 43 inline int nc_open_par(const char *path, int mode, MPI_Comm comm, MPI_Info info,int *ncidp) 44 { 44 { 45 45 #if defined(USING_NETCDF_PAR) 46 46 return ::nc_open_par(path, mode, comm, info, ncidp) ; … … 51 51 #endif 52 52 } 53 53 54 54 inline int nc_var_par_access(int ncid, int varid, int par_access) 55 55 {
Note: See TracChangeset
for help on using the changeset viewer.