NetCDF  4.9.2
dvar.c
Go to the documentation of this file.
1 /* Copyright 2010-2018 University Corporation for Atmospheric
2  Research/Unidata. See COPYRIGHT file for more info. */
9 #include "config.h"
10 #include "netcdf.h"
11 #include "netcdf_filter.h"
12 #include "ncdispatch.h"
13 #include "nc4internal.h"
14 #include "netcdf_f.h"
15 #include "nc4internal.h"
16 
213 int
214 nc_def_var(int ncid, const char *name, nc_type xtype,
215  int ndims, const int *dimidsp, int *varidp)
216 {
217  NC* ncp;
218  int stat = NC_NOERR;
219 
220  if ((stat = NC_check_id(ncid, &ncp)))
221  return stat;
222  TRACE(nc_def_var);
223  return ncp->dispatch->def_var(ncid, name, xtype, ndims,
224  dimidsp, varidp);
225 }
226 
308 int
309 nc_def_var_fill(int ncid, int varid, int no_fill, const void *fill_value)
310 {
311  NC* ncp;
312  int stat = NC_check_id(ncid,&ncp);
313  if(stat != NC_NOERR) return stat;
314 
315  /* Using NC_GLOBAL is illegal, as this API has no provision for
316  * specifying the type of the fillvalue, it must of necessity be
317  * using the type of the variable to interpret the bytes of the
318  * fill_value argument. */
319  if (varid == NC_GLOBAL) return NC_EGLOBAL;
320 
321  return ncp->dispatch->def_var_fill(ncid,varid,no_fill,fill_value);
322 }
323 
460 int
461 nc_def_var_deflate(int ncid, int varid, int shuffle, int deflate, int deflate_level)
462 {
463  NC* ncp;
464  int stat = NC_check_id(ncid,&ncp);
465  if(stat != NC_NOERR) return stat;
466  return ncp->dispatch->def_var_deflate(ncid,varid,shuffle,deflate,deflate_level);
467 }
468 
559 int
560 nc_def_var_quantize(int ncid, int varid, int quantize_mode, int nsd)
561 {
562  NC* ncp;
563  int stat = NC_check_id(ncid,&ncp);
564  if(stat != NC_NOERR) return stat;
565 
566  /* Using NC_GLOBAL is illegal. */
567  if (varid == NC_GLOBAL) return NC_EGLOBAL;
568  return ncp->dispatch->def_var_quantize(ncid,varid,quantize_mode,nsd);
569 }
570 
608 int
609 nc_def_var_fletcher32(int ncid, int varid, int fletcher32)
610 {
611  NC* ncp;
612  int stat = NC_check_id(ncid,&ncp);
613  if(stat != NC_NOERR) return stat;
614  return ncp->dispatch->def_var_fletcher32(ncid,varid,fletcher32);
615 }
616 
728 int
729 nc_def_var_chunking(int ncid, int varid, int storage, const size_t *chunksizesp)
730 {
731  NC* ncp;
732  int stat = NC_check_id(ncid, &ncp);
733  if(stat != NC_NOERR) return stat;
734  return ncp->dispatch->def_var_chunking(ncid, varid, storage,
735  chunksizesp);
736 }
737 
806 int
807 nc_def_var_endian(int ncid, int varid, int endian)
808 {
809  NC* ncp;
810  int stat = NC_check_id(ncid,&ncp);
811  if(stat != NC_NOERR) return stat;
812  return ncp->dispatch->def_var_endian(ncid,varid,endian);
813 }
814 
863 int
864 nc_def_var_szip(int ncid, int varid, int options_mask, int pixels_per_block)
865 {
866  int ret;
867 
868  /* This will cause H5Pset_szip to be called when the var is
869  * created. */
870  unsigned int params[2];
871  params[0] = options_mask;
872  params[1] = pixels_per_block;
873  if ((ret = nc_def_var_filter(ncid, varid, HDF5_FILTER_SZIP, 2, params)))
874  return ret;
875 
876  return NC_NOERR;
877 }
878 
945 int
946 nc_rename_var(int ncid, int varid, const char *name)
947 {
948  NC* ncp;
949  int stat = NC_check_id(ncid, &ncp);
950  if(stat != NC_NOERR) return stat;
951  TRACE(nc_rename_var);
952  return ncp->dispatch->rename_var(ncid, varid, name);
953 }
965 int
966 NC_is_recvar(int ncid, int varid, size_t* nrecs)
967 {
968  int status = NC_NOERR;
969  int unlimid;
970  int ndims;
971  int dimset[NC_MAX_VAR_DIMS];
972 
973  status = nc_inq_unlimdim(ncid,&unlimid);
974  if(status != NC_NOERR) return 0; /* no unlimited defined */
975  status = nc_inq_varndims(ncid,varid,&ndims);
976  if(status != NC_NOERR) return 0; /* no unlimited defined */
977  if(ndims == 0) return 0; /* scalar */
978  status = nc_inq_vardimid(ncid,varid,dimset);
979  if(status != NC_NOERR) return 0; /* no unlimited defined */
980  status = nc_inq_dim(ncid,dimset[0],NULL,nrecs);
981  if(status != NC_NOERR) return 0;
982  return (dimset[0] == unlimid ? 1: 0);
983 }
984 
1010 int
1011 NC_inq_recvar(int ncid, int varid, int* nrecdimsp, int *is_recdim)
1012 {
1013  int status = NC_NOERR;
1014  int unlimid;
1015  int nvardims;
1016  int dimset[NC_MAX_VAR_DIMS];
1017  int dim;
1018  int nrecdims = 0;
1019 
1020  status = nc_inq_varndims(ncid,varid,&nvardims);
1021  if(status != NC_NOERR) return status;
1022  if(nvardims == 0) return NC_NOERR; /* scalars have no dims */
1023  for(dim = 0; dim < nvardims; dim++)
1024  is_recdim[dim] = 0;
1025  status = nc_inq_unlimdim(ncid, &unlimid);
1026  if(status != NC_NOERR) return status;
1027  if(unlimid == -1) return status; /* no unlimited dims for any variables */
1028 #ifdef USE_NETCDF4
1029  {
1030  int nunlimdims;
1031  int *unlimids;
1032  int recdim;
1033  status = nc_inq_unlimdims(ncid, &nunlimdims, NULL); /* for group or file, not variable */
1034  if(status != NC_NOERR) return status;
1035  if(nunlimdims == 0) return status;
1036 
1037  if (!(unlimids = malloc(nunlimdims * sizeof(int))))
1038  return NC_ENOMEM;
1039  status = nc_inq_unlimdims(ncid, &nunlimdims, unlimids); /* for group or file, not variable */
1040  if(status != NC_NOERR) {
1041  free(unlimids);
1042  return status;
1043  }
1044  status = nc_inq_vardimid(ncid, varid, dimset);
1045  if(status != NC_NOERR) {
1046  free(unlimids);
1047  return status;
1048  }
1049  for (dim = 0; dim < nvardims; dim++) { /* netCDF-4 rec dims need not be first dim for a rec var */
1050  for(recdim = 0; recdim < nunlimdims; recdim++) {
1051  if(dimset[dim] == unlimids[recdim]) {
1052  is_recdim[dim] = 1;
1053  nrecdims++;
1054  }
1055  }
1056  }
1057  free(unlimids);
1058  }
1059 #else
1060  status = nc_inq_vardimid(ncid, varid, dimset);
1061  if(status != NC_NOERR) return status;
1062  if(dimset[0] == unlimid) {
1063  is_recdim[0] = 1;
1064  nrecdims++;
1065  }
1066 #endif /* USE_NETCDF4 */
1067  if(nrecdimsp) *nrecdimsp = nrecdims;
1068  return status;
1069 }
1070 
1071 /* Ok to use NC pointers because
1072  all IOSP's will use that structure,
1073  but not ok to use e.g. NC_Var pointers
1074  because they may be different structure
1075  entirely.
1076 */
1077 
1088 int
1089 nctypelen(nc_type type)
1090 {
1091  switch(type){
1092  case NC_CHAR :
1093  return ((int)sizeof(char));
1094  case NC_BYTE :
1095  return ((int)sizeof(signed char));
1096  case NC_SHORT :
1097  return ((int)sizeof(short));
1098  case NC_INT :
1099  return ((int)sizeof(int));
1100  case NC_FLOAT :
1101  return ((int)sizeof(float));
1102  case NC_DOUBLE :
1103  return ((int)sizeof(double));
1104 
1105  /* These can occur in netcdf-3 code */
1106  case NC_UBYTE :
1107  return ((int)sizeof(unsigned char));
1108  case NC_USHORT :
1109  return ((int)(sizeof(unsigned short)));
1110  case NC_UINT :
1111  return ((int)sizeof(unsigned int));
1112  case NC_INT64 :
1113  return ((int)sizeof(signed long long));
1114  case NC_UINT64 :
1115  return ((int)sizeof(unsigned long long));
1116 #ifdef USE_NETCDF4
1117  case NC_STRING :
1118  return ((int)sizeof(char*));
1119 #endif /*USE_NETCDF4*/
1120 
1121  default:
1122  return -1;
1123  }
1124 }
1125 
1134 size_t
1135 NC_atomictypelen(nc_type xtype)
1136 {
1137  size_t sz = 0;
1138  switch(xtype) {
1139  case NC_NAT: sz = 0; break;
1140  case NC_BYTE: sz = sizeof(signed char); break;
1141  case NC_CHAR: sz = sizeof(char); break;
1142  case NC_SHORT: sz = sizeof(short); break;
1143  case NC_INT: sz = sizeof(int); break;
1144  case NC_FLOAT: sz = sizeof(float); break;
1145  case NC_DOUBLE: sz = sizeof(double); break;
1146  case NC_INT64: sz = sizeof(signed long long); break;
1147  case NC_UBYTE: sz = sizeof(unsigned char); break;
1148  case NC_USHORT: sz = sizeof(unsigned short); break;
1149  case NC_UINT: sz = sizeof(unsigned int); break;
1150  case NC_UINT64: sz = sizeof(unsigned long long); break;
1151 #ifdef USE_NETCDF4
1152  case NC_STRING: sz = sizeof(char*); break;
1153 #endif
1154  default: break;
1155  }
1156  return sz;
1157 }
1158 
1167 char *
1168 NC_atomictypename(nc_type xtype)
1169 {
1170  char* nm = NULL;
1171  switch(xtype) {
1172  case NC_NAT: nm = "undefined"; break;
1173  case NC_BYTE: nm = "byte"; break;
1174  case NC_CHAR: nm = "char"; break;
1175  case NC_SHORT: nm = "short"; break;
1176  case NC_INT: nm = "int"; break;
1177  case NC_FLOAT: nm = "float"; break;
1178  case NC_DOUBLE: nm = "double"; break;
1179  case NC_INT64: nm = "int64"; break;
1180  case NC_UBYTE: nm = "ubyte"; break;
1181  case NC_USHORT: nm = "ushort"; break;
1182  case NC_UINT: nm = "uint"; break;
1183  case NC_UINT64: nm = "uint64"; break;
1184 #ifdef USE_NETCDF4
1185  case NC_STRING: nm = "string"; break;
1186 #endif
1187  default: break;
1188  }
1189  return nm;
1190 }
1191 
1209 int
1210 NC_getshape(int ncid, int varid, int ndims, size_t* shape)
1211 {
1212  int dimids[NC_MAX_VAR_DIMS];
1213  int i;
1214  int status = NC_NOERR;
1215 
1216  if ((status = nc_inq_vardimid(ncid, varid, dimids)))
1217  return status;
1218  for(i = 0; i < ndims; i++)
1219  if ((status = nc_inq_dimlen(ncid, dimids[i], &shape[i])))
1220  break;
1221 
1222  return status;
1223 }
1224 
1249 int
1250 NC_check_nulls(int ncid, int varid, const size_t *start, size_t **count,
1251  ptrdiff_t **stride)
1252 {
1253  int varndims;
1254  int stat;
1255 
1256  if ((stat = nc_inq_varndims(ncid, varid, &varndims)))
1257  return stat;
1258 
1259  /* For non-scalar vars, start is required. */
1260  if (!start && varndims)
1261  return NC_EINVALCOORDS;
1262 
1263  /* If count is NULL, assume full extent of var. */
1264  if (!*count)
1265  {
1266  if (!(*count = malloc(varndims * sizeof(size_t))))
1267  return NC_ENOMEM;
1268  if ((stat = NC_getshape(ncid, varid, varndims, *count)))
1269  {
1270  free(*count);
1271  *count = NULL;
1272  return stat;
1273  }
1274  }
1275 
1276  /* If stride is NULL, do nothing, if *stride is NULL use all
1277  * 1s. */
1278  if (stride && !*stride)
1279  {
1280  int i;
1281 
1282  if (!(*stride = malloc(varndims * sizeof(ptrdiff_t))))
1283  return NC_ENOMEM;
1284  for (i = 0; i < varndims; i++)
1285  (*stride)[i] = 1;
1286  }
1287 
1288  return NC_NOERR;
1289 }
1290 
1315 int
1316 nc_free_string(size_t len, char **data)
1317 {
1318  int i;
1319  for (i = 0; i < len; i++)
1320  free(data[i]);
1321  return NC_NOERR;
1322 }
1393 int
1394 nc_set_var_chunk_cache(int ncid, int varid, size_t size, size_t nelems,
1395  float preemption)
1396 {
1397  NC* ncp;
1398  int stat = NC_check_id(ncid, &ncp);
1399  if(stat != NC_NOERR) return stat;
1400  return ncp->dispatch->set_var_chunk_cache(ncid, varid, size,
1401  nelems, preemption);
1402 }
1403 
1434 int
1435 nc_get_var_chunk_cache(int ncid, int varid, size_t *sizep, size_t *nelemsp,
1436  float *preemptionp)
1437 {
1438  NC* ncp;
1439  int stat = NC_check_id(ncid, &ncp);
1440  if(stat != NC_NOERR) return stat;
1441  return ncp->dispatch->get_var_chunk_cache(ncid, varid, sizep,
1442  nelemsp, preemptionp);
1443 }
1444 
1445 #ifndef USE_NETCDF4
1446 /* Make sure the fortran API is defined, even if it only returns errors */
1447 
1448 int
1449 nc_set_chunk_cache_ints(int size, int nelems, int preemption)
1450 {
1451  return NC_ENOTBUILT;
1452 }
1453 
1454 int
1455 nc_get_chunk_cache_ints(int *sizep, int *nelemsp, int *preemptionp)
1456 {
1457  return NC_ENOTBUILT;
1458 }
1459 
1460 int
1461 nc_set_var_chunk_cache_ints(int ncid, int varid, int size, int nelems,
1462  int preemption)
1463 {
1464  return NC_ENOTBUILT;
1465 }
1466 
1467 int
1468 nc_get_var_chunk_cache_ints(int ncid, int varid, int *sizep,
1469  int *nelemsp, int *preemptionp)
1470 {
1471  return NC_ENOTBUILT;
1472 }
1473 
1474 #endif /*USE_NETCDF4*/
1475 
EXTERNL int nc_inq_dimlen(int ncid, int dimid, size_t *lenp)
Find the length of a dimension.
Definition: ddim.c:467
EXTERNL int nc_inq_dim(int ncid, int dimid, char *name, size_t *lenp)
Find the name and length of a dimension.
Definition: ddim.c:216
EXTERNL int nc_inq_unlimdim(int ncid, int *unlimdimidp)
Find the ID of the unlimited dimension.
Definition: ddim.c:350
EXTERNL int nc_inq_varndims(int ncid, int varid, int *ndimsp)
Learn how many dimensions are associated with a variable.
Definition: dvarinq.c:202
int nc_def_var_endian(int ncid, int varid, int endian)
Define endianness of a variable.
Definition: dvar.c:807
int nc_free_string(size_t len, char **data)
Free string space allocated by the library.
Definition: dvar.c:1316
int nc_def_var_szip(int ncid, int varid, int options_mask, int pixels_per_block)
Set szip compression settings on a variable.
Definition: dvar.c:864
int nc_set_var_chunk_cache(int ncid, int varid, size_t size, size_t nelems, float preemption)
Change the cache settings for a chunked variable.
Definition: dvar.c:1394
int nc_def_var_deflate(int ncid, int varid, int shuffle, int deflate, int deflate_level)
Set the zlib compression and shuffle settings for a variable in an netCDF/HDF5 file.
Definition: dvar.c:461
int nc_def_var_fletcher32(int ncid, int varid, int fletcher32)
Set checksum for a var.
Definition: dvar.c:609
int nc_def_var_quantize(int ncid, int varid, int quantize_mode, int nsd)
Turn on quantization for a variable.
Definition: dvar.c:560
EXTERNL int nc_inq_vardimid(int ncid, int varid, int *dimidsp)
Learn the dimension IDs associated with a variable.
Definition: dvarinq.c:225
int nc_def_var_fill(int ncid, int varid, int no_fill, const void *fill_value)
Set the fill value for a variable.
Definition: dvar.c:309
int nc_def_var(int ncid, const char *name, nc_type xtype, int ndims, const int *dimidsp, int *varidp)
Define a new variable.
Definition: dvar.c:214
int nc_rename_var(int ncid, int varid, const char *name)
Rename a variable.
Definition: dvar.c:946
int nc_def_var_chunking(int ncid, int varid, int storage, const size_t *chunksizesp)
Define storage and, if chunked storage is used, chunking parameters for a variable.
Definition: dvar.c:729
int nc_get_var_chunk_cache(int ncid, int varid, size_t *sizep, size_t *nelemsp, float *preemptionp)
Get the per-variable chunk cache settings from the HDF5 layer.
Definition: dvar.c:1435
Main header file for the C API.
#define NC_UINT
unsigned 4-byte int
Definition: netcdf.h:44
#define NC_INT
signed 4 byte integer
Definition: netcdf.h:38
#define NC_MAX_VAR_DIMS
max per variable dimensions
Definition: netcdf.h:282
#define NC_BYTE
signed 1 byte integer
Definition: netcdf.h:35
EXTERNL int nc_inq_unlimdims(int ncid, int *nunlimdimsp, int *unlimdimidsp)
Return number and list of unlimited dimensions.
Definition: dvarinq.c:672
#define NC_NAT
Not A Type.
Definition: netcdf.h:34
#define NC_DOUBLE
double precision floating point number
Definition: netcdf.h:41
#define NC_UBYTE
unsigned 1 byte int
Definition: netcdf.h:42
#define NC_FLOAT
single precision floating point number
Definition: netcdf.h:40
#define NC_ENOMEM
Memory allocation (malloc) failure.
Definition: netcdf.h:448
#define NC_SHORT
signed 2 byte integer
Definition: netcdf.h:37
#define NC_EINVALCOORDS
Index exceeds dimension bound.
Definition: netcdf.h:400
#define NC_INT64
signed 8-byte int
Definition: netcdf.h:45
#define NC_GLOBAL
Attribute id to put/get a global attribute.
Definition: netcdf.h:254
#define NC_UINT64
unsigned 8-byte int
Definition: netcdf.h:46
#define NC_NOERR
No Error.
Definition: netcdf.h:368
EXTERNL int nc_def_var_filter(int ncid, int varid, unsigned int id, size_t nparams, const unsigned int *parms)
Define a new variable filter Assumes HDF5 format using unsigned ints.
Definition: dfilter.c:124
#define NC_USHORT
unsigned 2-byte int
Definition: netcdf.h:43
#define NC_STRING
string
Definition: netcdf.h:47
#define NC_ENOTBUILT
Attempt to use feature that was not turned on when netCDF was built.
Definition: netcdf.h:508
#define NC_EGLOBAL
Action prohibited on NC_GLOBAL varid.
Definition: netcdf.h:423
#define NC_CHAR
ISO/ASCII character.
Definition: netcdf.h:36
int nc_type
The nc_type type is just an int.
Definition: netcdf.h:25