PostGIS  2.4.9dev-r@@SVN_REVISION@@

◆ rtpg_nmapalgebra_rastbandarg_process()

static int rtpg_nmapalgebra_rastbandarg_process ( rtpg_nmapalgebra_arg  arg,
ArrayType *  array,
int *  allnull,
int *  allempty,
int *  noband 
)
static

Definition at line 184 of file rtpg_mapalgebra.c.

References FALSE, rtpg_nmapalgebra_arg_t::hasband, rtpg_nmapalgebra_arg_t::isempty, rtpg_nmapalgebra_arg_t::mask, pixval::nband, rtpg_nmapalgebra_arg_t::nband, rtpg_nmapalgebra_arg_t::numraster, rtpg_nmapalgebra_arg_t::ownsdata, rtpg_nmapalgebra_arg_t::pgraster, POSTGIS_RT_DEBUG, POSTGIS_RT_DEBUGF, rtpg_nmapalgebra_arg_t::raster, rt_raster_deserialize(), rt_raster_has_band(), and rt_raster_is_empty().

Referenced by RASTER_nMapAlgebra(), and RASTER_nMapAlgebraExpr().

184  {
185  Oid etype;
186  Datum *e;
187  bool *nulls;
188  int16 typlen;
189  bool typbyval;
190  char typalign;
191  int n = 0;
192 
193  HeapTupleHeader tup;
194  bool isnull;
195  Datum tupv;
196 
197  int i;
198  int j;
199  int nband;
200 
201  if (arg == NULL || array == NULL) {
202  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: NULL values not permitted for parameters");
203  return 0;
204  }
205 
206  etype = ARR_ELEMTYPE(array);
207  get_typlenbyvalalign(etype, &typlen, &typbyval, &typalign);
208 
209  deconstruct_array(
210  array,
211  etype,
212  typlen, typbyval, typalign,
213  &e, &nulls, &n
214  );
215 
216  if (!n) {
217  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Invalid argument for rastbandarg");
218  return 0;
219  }
220 
221  /* prep arg */
222  arg->numraster = n;
223  arg->pgraster = palloc(sizeof(rt_pgraster *) * arg->numraster);
224  arg->raster = palloc(sizeof(rt_raster) * arg->numraster);
225  arg->isempty = palloc(sizeof(uint8_t) * arg->numraster);
226  arg->ownsdata = palloc(sizeof(uint8_t) * arg->numraster);
227  arg->nband = palloc(sizeof(int) * arg->numraster);
228  arg->hasband = palloc(sizeof(uint8_t) * arg->numraster);
229  arg->mask = palloc(sizeof(struct rt_mask_t));
230  if (
231  arg->pgraster == NULL ||
232  arg->raster == NULL ||
233  arg->isempty == NULL ||
234  arg->ownsdata == NULL ||
235  arg->nband == NULL ||
236  arg->hasband == NULL ||
237  arg->mask == NULL
238  ) {
239  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Could not allocate memory for processing rastbandarg");
240  return 0;
241  }
242 
243  *allnull = 0;
244  *allempty = 0;
245  *noband = 0;
246 
247  /* process each element */
248  for (i = 0; i < n; i++) {
249  if (nulls[i]) {
250  arg->numraster--;
251  continue;
252  }
253 
254  POSTGIS_RT_DEBUGF(4, "Processing rastbandarg at index %d", i);
255 
256  arg->raster[i] = NULL;
257  arg->isempty[i] = 0;
258  arg->ownsdata[i] = 1;
259  arg->nband[i] = 0;
260  arg->hasband[i] = 0;
261 
262  /* each element is a tuple */
263  tup = (HeapTupleHeader) DatumGetPointer(e[i]);
264  if (NULL == tup) {
265  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Invalid argument for rastbandarg at index %d", i);
266  return 0;
267  }
268 
269  /* first element, raster */
270  POSTGIS_RT_DEBUG(4, "Processing first element (raster)");
271  tupv = GetAttributeByName(tup, "rast", &isnull);
272  if (isnull) {
273  elog(NOTICE, "First argument (nband) of rastbandarg at index %d is NULL. Assuming NULL raster", i);
274  arg->isempty[i] = 1;
275  arg->ownsdata[i] = 0;
276 
277  (*allnull)++;
278  (*allempty)++;
279  (*noband)++;
280 
281  continue;
282  }
283 
284  arg->pgraster[i] = (rt_pgraster *) PG_DETOAST_DATUM(tupv);
285 
286  /* see if this is a copy of an existing pgraster */
287  for (j = 0; j < i; j++) {
288  if (!arg->isempty[j] && (arg->pgraster[i] == arg->pgraster[j])) {
289  POSTGIS_RT_DEBUG(4, "raster matching existing same raster found");
290  arg->raster[i] = arg->raster[j];
291  arg->ownsdata[i] = 0;
292  break;
293  }
294  }
295 
296  if (arg->ownsdata[i]) {
297  POSTGIS_RT_DEBUG(4, "deserializing raster");
298  arg->raster[i] = rt_raster_deserialize(arg->pgraster[i], FALSE);
299  if (arg->raster[i] == NULL) {
300  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Could not deserialize raster at index %d", i);
301  return 0;
302  }
303  }
304 
305  /* is raster empty? */
306  arg->isempty[i] = rt_raster_is_empty(arg->raster[i]);
307  if (arg->isempty[i]) {
308  (*allempty)++;
309  (*noband)++;
310 
311  continue;
312  }
313 
314  /* second element, nband */
315  POSTGIS_RT_DEBUG(4, "Processing second element (nband)");
316  tupv = GetAttributeByName(tup, "nband", &isnull);
317  if (isnull) {
318  nband = 1;
319  elog(NOTICE, "First argument (nband) of rastbandarg at index %d is NULL. Assuming nband = %d", i, nband);
320  }
321  else
322  nband = DatumGetInt32(tupv);
323 
324  if (nband < 1) {
325  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Band number provided for rastbandarg at index %d must be greater than zero (1-based)", i);
326  return 0;
327  }
328 
329  arg->nband[i] = nband - 1;
330  arg->hasband[i] = rt_raster_has_band(arg->raster[i], arg->nband[i]);
331  if (!arg->hasband[i]) {
332  (*noband)++;
333  POSTGIS_RT_DEBUGF(4, "Band at index %d not found in raster", nband);
334  }
335  }
336 
337  if (arg->numraster < n) {
338  arg->pgraster = repalloc(arg->pgraster, sizeof(rt_pgraster *) * arg->numraster);
339  arg->raster = repalloc(arg->raster, sizeof(rt_raster) * arg->numraster);
340  arg->isempty = repalloc(arg->isempty, sizeof(uint8_t) * arg->numraster);
341  arg->ownsdata = repalloc(arg->ownsdata, sizeof(uint8_t) * arg->numraster);
342  arg->nband = repalloc(arg->nband, sizeof(int) * arg->numraster);
343  arg->hasband = repalloc(arg->hasband, sizeof(uint8_t) * arg->numraster);
344  if (
345  arg->pgraster == NULL ||
346  arg->raster == NULL ||
347  arg->isempty == NULL ||
348  arg->ownsdata == NULL ||
349  arg->nband == NULL ||
350  arg->hasband == NULL
351  ) {
352  elog(ERROR, "rtpg_nmapalgebra_rastbandarg_process: Could not reallocate memory for processed rastbandarg");
353  return 0;
354  }
355  }
356 
357  POSTGIS_RT_DEBUGF(4, "arg->numraster = %d", arg->numraster);
358 
359  return 1;
360 }
rt_pgraster ** pgraster
int rt_raster_is_empty(rt_raster raster)
Return TRUE if the raster is empty.
Definition: rt_raster.c:1338
#define POSTGIS_RT_DEBUGF(level, msg,...)
Definition: rtpostgis.h:65
nband
Definition: pixval.py:52
int rt_raster_has_band(rt_raster raster, int nband)
Return TRUE if the raster has a band of this number.
Definition: rt_raster.c:1351
#define FALSE
Definition: dbfopen.c:168
Struct definitions.
Definition: librtcore.h:2201
#define POSTGIS_RT_DEBUG(level, msg)
Definition: rtpostgis.h:61
unsigned char uint8_t
Definition: uthash.h:79
rt_raster rt_raster_deserialize(void *serialized, int header_only)
Return a raster from a serialized form.
Definition: rt_serialize.c:717
Here is the call graph for this function:
Here is the caller graph for this function: