forked from Unidata/netcdf-c
-
Notifications
You must be signed in to change notification settings - Fork 0
/
constraints4.c
180 lines (163 loc) · 5.72 KB
/
constraints4.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
/*********************************************************************
* Copyright 1993, UCAR/Unidata
* See netcdf/COPYRIGHT file for copying and redistribution conditions.
* $Header: /upc/share/CVS/netcdf-3/libncdap4/constraints4.c,v 1.9 2010/04/13 03:36:31 dmh Exp $
*********************************************************************/
#include "ncdap4.h"
#ifdef DEBUG
#include "dapdump.h"
#endif
/* In order to construct the projection,
we need to make sure to match the relevant dimensions
against the relevant nodes in which the ultimate target
is contained. For netcdf4, we only need to do this
for one level.
*/
NCerror
buildvaraprojection4(Getvara* getvar,
const size_t* startp, const size_t* countp, const ptrdiff_t* stridep,
DCEprojection** projectionp)
{
int i;
NCerror ncstat = NC_NOERR;
NClist* dimset;
CDFnode* var = getvar->target;
DCEprojection* projection = NULL;
NClist* segments = NULL;
DCEsegment* segment;
segment = (DCEsegment*)dcecreate(CES_SEGMENT);
segment->cdfnode = var;
ASSERT((segment->cdfnode != NULL));
segment->name = nulldup(segment->cdfnode->ocname);
segment->slicesdefined = 0; /* temporary */
segment->slicesdeclized = 0; /* temporary */
segments = nclistnew();
nclistpush(segments,(ncelem)segment);
projection = (DCEprojection*)dcecreate(CES_PROJECT);
projection->discrim = CES_VAR;
projection->var = (DCEvar*)dcecreate(CES_VAR);
projection->var->segments = segments;
/* All slices are assigned to the first (and only segment) */
dimset = var->array.dimset0;
segment->rank = nclistlength(var->array.dimset0);
for(i=0;i<segment->rank;i++) {
DCEslice* slice = &segment->slices[i];
CDFnode* dim = (CDFnode*)nclistget(dimset,i);
slice->first = startp[i];
slice->stride = stridep[i];
slice->count = countp[i];
slice->length = slice->count * slice->stride;
slice->stop = (slice->first + slice->length);
ASSERT(dim->dim.declsize > 0);
slice->declsize = dim->dim.declsize;
}
segment->slicesdefined = 1;
segment->slicesdeclized = 1;
if(projectionp) *projectionp = projection;
if(ncstat) dcefree((DCEnode*)projection);
return ncstat;
}
#ifdef IGNORE
/* Compute the set of prefetched data;
note that even if caching is off, we will
still prefetch the small variables.
*/
NCerror
prefetchdata4(NCDAPCOMMON* nccomm)
{
int i,j;
NCerror ncstat = NC_NOERR;
NClist* allvars = nccomm->cdf.varnodes;
DCEconstraint* constraint = nccomm->oc.dapconstraint;
NClist* vars = nclistnew();
NCcachenode* cache = NULL;
DCEconstraint* newconstraint = NULL;
/* Check if we can do constraints */
if(FLAGSET(nccomm->controls,NCF_UNCONSTRAINABLE)) { /*cannot constrain*/
/* If we cannot constrain, then pull in everything */
for(i=0;i<nclistlength(allvars);i++) {
nclistpush(vars,nclistget(allvars,i));
}
} else { /* can do constraints */
/* pull in those variables of sufficiently small size */
for(i=0;i<nclistlength(allvars);i++) {
CDFnode* var = (CDFnode*)nclistget(allvars,i);
size_t nelems = 1;
/* Compute the # of elements in the variable */
for(j=0;j<nclistlength(var->array.dimensions);j++) {
CDFnode* dim = (CDFnode*)nclistget(var->array.dimensions,j);
nelems *= dim->dim.declsize;
}
if(nelems <= nccomm->cdf.smallsizelimit)
nclistpush(vars,(ncelem)var);
}
}
/* If there are no vars, then do nothing */
if(nclistlength(vars) == 0) {
nccomm->cdf.cache->prefetch = NULL;
goto done;
}
/* Construct the projections for this set of vars */
newconstraint = (DCEconstraint*)dcecreate(CES_CONSTRAINT);
/* Initially, the constraints are same as the merged constraints */
newconstraint = dceclone((DCEnode*)constraint);
canonicalprojection34(vars,newconstraint->projections);
/* similar for selections */
newconstraint->selections = dceclonelist(constraint->selections);
ncstat = buildcachenode34(nccomm,newconstraint,vars,&cache,0);
if(ncstat) goto done;
/* Make cache node be the prefetch node */
nccomm->cdf.cache->prefetch = cache;
if(FLAGSET(nccomm->controls,NCF_SHOWFETCH)) {
/* Log the set of prefetch variables */
NCbytes* buf = ncbytesnew();
ncbytescat(buf,"prefetch.vars: ");
for(i=0;i<nclistlength(vars);i++) {
CDFnode* var = (CDFnode*)nclistget(vars,i);
ncbytescat(buf," ");
ncbytescat(buf,makesimplepathstring3(var));
}
ncbytescat(buf,"\n");
nclog(NCLOGNOTE,ncbytescontents(buf));
ncbytesfree(buf);
}
done:
if(ncstat) {
freenccachenode(nccomm,cache);
}
return THROW(ncstat);
}
/* Based on the tactic, determine the set of variables to add */
static void
computevarset4(NCDAP4* drno, Getvara* getvar, NClist* varlist)
{
int i;
nclistclear(varlist);
for(i=0;i<nclistlength(drno->dap.cdf.varnodes);i++) {
CDFnode* var = (CDFnode*)nclistget(drno->dap.cdf.varnodes,i);
#ifdef IGNORE
int ok = 1;
for(j=0;j<nclistlength(var->array.ncdimensions);j++) {
CDFnode* dim = (CDFnode*)nclistget(var->array.ncdimensions,j);
if(dim->dim.declsize == NC_UNLIMITED) {ok = 0; break;}
}
if(!ok) continue;
#endif
switch (getvar->tactic->tactic) {
case tactic_all: /* add all visible variables */
nclistpush(varlist,(ncelem)var);
break;
case tactic_partial: /* add only small variables + target */
if(var->estimatedsize < drno->dap.cdf.smallsizelimit
|| getvar->target == var) {
nclistpush(varlist,(ncelem)var);
}
break;
case tactic_var: /* add only target var */
if(getvar->target == var) nclistpush(varlist,(ncelem)var);
break;
default: break;
}
}
}
#endif