PostGIS 3.0.6dev-r@@SVN_REVISION@@
Loading...
Searching...
No Matches

◆ rtpg_nmapalgebra_callback()

static int rtpg_nmapalgebra_callback ( rt_iterator_arg  arg,
void *  userarg,
double *  value,
int *  nodata 
)
static

Definition at line 374 of file rtpg_mapalgebra.c.

377 {
379
380 int16 typlen;
381 bool typbyval;
382 char typalign;
383
384 ArrayType *mdValues = NULL;
385 Datum *_values = NULL;
386 bool *_nodata = NULL;
387
388 ArrayType *mdPos = NULL;
389 Datum *_pos = NULL;
390 bool *_null = NULL;
391
392 int i = 0;
393 uint32_t x = 0;
394 uint32_t y = 0;
395 int z = 0;
396 int dim[3] = {0};
397 int lbound[3] = {1, 1, 1};
398 Datum datum = (Datum) NULL;
399
400 if (arg == NULL)
401 return 0;
402
403 *value = 0;
404 *nodata = 0;
405
406 dim[0] = arg->rasters;
407 dim[1] = arg->rows;
408 dim[2] = arg->columns;
409
410 _values = palloc(sizeof(Datum) * arg->rasters * arg->rows * arg->columns);
411 _nodata = palloc(sizeof(bool) * arg->rasters * arg->rows * arg->columns);
412 if (_values == NULL || _nodata == NULL) {
413 elog(ERROR, "rtpg_nmapalgebra_callback: Could not allocate memory for values array");
414 return 0;
415 }
416
417 /* build mdValues */
418 i = 0;
419 /* raster */
420 for (z = 0; z < arg->rasters; z++) {
421 /* Y axis */
422 for (y = 0; y < arg->rows; y++) {
423 /* X axis */
424 for (x = 0; x < arg->columns; x++) {
425 POSTGIS_RT_DEBUGF(4, "(z, y ,x) = (%d, %d, %d)", z, y, x);
426 POSTGIS_RT_DEBUGF(4, "(value, nodata) = (%f, %d)", arg->values[z][y][x], arg->nodata[z][y][x]);
427
428 _nodata[i] = (bool) arg->nodata[z][y][x];
429 if (!_nodata[i])
430 _values[i] = Float8GetDatum(arg->values[z][y][x]);
431 else
432 _values[i] = (Datum) NULL;
433
434 i++;
435 }
436 }
437 }
438
439 /* info about the type of item in the multi-dimensional array (float8). */
440 get_typlenbyvalalign(FLOAT8OID, &typlen, &typbyval, &typalign);
441
442 /* construct mdValues */
443 mdValues = construct_md_array(
444 _values, _nodata,
445 3, dim, lbound,
446 FLOAT8OID,
447 typlen, typbyval, typalign
448 );
449 pfree(_nodata);
450 pfree(_values);
451
452 _pos = palloc(sizeof(Datum) * (arg->rasters + 1) * 2);
453 _null = palloc(sizeof(bool) * (arg->rasters + 1) * 2);
454 if (_pos == NULL || _null == NULL) {
455 pfree(mdValues);
456 elog(ERROR, "rtpg_nmapalgebra_callback: Could not allocate memory for position array");
457 return 0;
458 }
459 memset(_null, 0, sizeof(bool) * (arg->rasters + 1) * 2);
460
461 /* build mdPos */
462 i = 0;
463 _pos[i] = arg->dst_pixel[0] + 1;
464 i++;
465 _pos[i] = arg->dst_pixel[1] + 1;
466 i++;
467
468 for (z = 0; z < arg->rasters; z++) {
469 _pos[i] = (Datum)arg->src_pixel[z][0] + 1;
470 i++;
471
472 _pos[i] = (Datum)arg->src_pixel[z][1] + 1;
473 i++;
474 }
475
476 /* info about the type of item in the multi-dimensional array (int4). */
477 get_typlenbyvalalign(INT4OID, &typlen, &typbyval, &typalign);
478
479 /* reuse dim and lbound, just tweak to what we need */
480 dim[0] = arg->rasters + 1;
481 dim[1] = 2;
482 lbound[0] = 0;
483
484 /* construct mdPos */
485 mdPos = construct_md_array(
486 _pos, _null,
487 2, dim, lbound,
488 INT4OID,
489 typlen, typbyval, typalign
490 );
491 pfree(_pos);
492 pfree(_null);
493
494#if POSTGIS_PGSQL_VERSION < 120
495 callback->ufc_info.arg[0] = PointerGetDatum(mdValues);
496 callback->ufc_info.arg[1] = PointerGetDatum(mdPos);
497#else
498 callback->ufc_info->args[0].value = PointerGetDatum(mdValues);
499 callback->ufc_info->args[1].value = PointerGetDatum(mdPos);
500#endif
501
502 /* call user callback function */
503#if POSTGIS_PGSQL_VERSION < 120
504 datum = FunctionCallInvoke(&(callback->ufc_info));
505#else
506 datum = FunctionCallInvoke(callback->ufc_info);
507#endif
508 pfree(mdValues);
509 pfree(mdPos);
510
511 /* result is not null*/
512#if POSTGIS_PGSQL_VERSION < 120
513 if (!callback->ufc_info.isnull) {
514#else
515 if (!callback->ufc_info->isnull)
516 {
517#endif
518 switch (callback->ufc_rettype) {
519 case FLOAT8OID:
520 *value = DatumGetFloat8(datum);
521 break;
522 case FLOAT4OID:
523 *value = (double) DatumGetFloat4(datum);
524 break;
525 case INT4OID:
526 *value = (double) DatumGetInt32(datum);
527 break;
528 case INT2OID:
529 *value = (double) DatumGetInt16(datum);
530 break;
531 }
532 }
533 else
534 *nodata = 1;
535
536 return 1;
537}
int value
Definition genraster.py:62
#define POSTGIS_RT_DEBUGF(level, msg,...)
Definition rtpostgis.h:65
double *** values
Definition librtcore.h:2460
FunctionCallInfoData ufc_info

References rt_iterator_arg_t::columns, rt_iterator_arg_t::dst_pixel, rt_iterator_arg_t::nodata, POSTGIS_RT_DEBUGF, rt_iterator_arg_t::rasters, rt_iterator_arg_t::rows, rt_iterator_arg_t::src_pixel, rtpg_nmapalgebra_callback_arg::ufc_info, rtpg_nmapalgebra_callback_arg::ufc_rettype, and rt_iterator_arg_t::values.

Referenced by RASTER_nMapAlgebra().

Here is the caller graph for this function: