PostGIS  3.1.6dev-r@@SVN_REVISION@@

◆ RASTER_clip()

Datum RASTER_clip ( PG_FUNCTION_ARGS  )

Definition at line 3025 of file rtpg_mapalgebra.c.

3026 {
3027  rt_pgraster *pgraster = NULL;
3028  LWGEOM *rastgeom = NULL;
3029  double gt[6] = {0};
3030  int32_t srid = SRID_UNKNOWN;
3031 
3032  rt_pgraster *pgrtn = NULL;
3033  rt_raster rtn = NULL;
3034 
3035  GSERIALIZED *gser = NULL;
3036  LWGEOM *geom = NULL;
3037  lwvarlena_t *wkb = NULL;
3038 
3039  ArrayType *array;
3040  Oid etype;
3041  Datum *e;
3042  bool *nulls;
3043 
3044  int16 typlen;
3045  bool typbyval;
3046  char typalign;
3047 
3048  int i = 0;
3049  int j = 0;
3050  int k = 0;
3051  rtpg_clip_arg arg = NULL;
3052  LWGEOM *tmpgeom = NULL;
3053  rt_iterator itrset;
3054 
3055  rt_raster _raster = NULL;
3056  rt_band band = NULL;
3057  rt_pixtype pixtype;
3058  int hasnodata;
3059  double nodataval;
3060  int noerr = 0;
3061 
3062  POSTGIS_RT_DEBUG(3, "Starting...");
3063 
3064  /* raster or geometry is NULL, return NULL */
3065  if (PG_ARGISNULL(0) || PG_ARGISNULL(2))
3066  PG_RETURN_NULL();
3067 
3068  /* init arg */
3069  arg = rtpg_clip_arg_init();
3070  if (arg == NULL) {
3071  elog(ERROR, "RASTER_clip: Could not initialize argument structure");
3072  PG_RETURN_NULL();
3073  }
3074 
3075  /* raster (0) */
3076  pgraster = (rt_pgraster *) PG_DETOAST_DATUM(PG_GETARG_DATUM(0));
3077 
3078  /* Get raster object */
3079  arg->raster = rt_raster_deserialize(pgraster, FALSE);
3080  if (arg->raster == NULL) {
3081  rtpg_clip_arg_destroy(arg);
3082  PG_FREE_IF_COPY(pgraster, 0);
3083  elog(ERROR, "RASTER_clip: Could not deserialize raster");
3084  PG_RETURN_NULL();
3085  }
3086 
3087  /* raster is empty, return empty raster */
3088  if (rt_raster_is_empty(arg->raster) || rt_raster_get_num_bands(arg->raster) == 0) {
3089  elog(NOTICE, "Input raster is empty or has no bands. Returning empty raster");
3090 
3091  rtpg_clip_arg_destroy(arg);
3092  PG_FREE_IF_COPY(pgraster, 0);
3093 
3094  rtn = rt_raster_new(0, 0);
3095  if (rtn == NULL) {
3096  elog(ERROR, "RASTER_clip: Could not create empty raster");
3097  PG_RETURN_NULL();
3098  }
3099 
3100  pgrtn = rt_raster_serialize(rtn);
3101  rt_raster_destroy(rtn);
3102  if (NULL == pgrtn)
3103  PG_RETURN_NULL();
3104 
3105  SET_VARSIZE(pgrtn, pgrtn->size);
3106  PG_RETURN_POINTER(pgrtn);
3107  }
3108 
3109  /* metadata */
3111  srid = clamp_srid(rt_raster_get_srid(arg->raster));
3112 
3113  /* geometry (2) */
3114  gser = PG_GETARG_GSERIALIZED_P(2);
3115  geom = lwgeom_from_gserialized(gser);
3116 
3117  /* Get a 2D version of the geometry if necessary */
3118  if (lwgeom_ndims(geom) > 2) {
3119  LWGEOM *geom2d = lwgeom_force_2d(geom);
3120  lwgeom_free(geom);
3121  geom = geom2d;
3122  }
3123 
3124  /* check that SRIDs match */
3125  if (srid != clamp_srid(gserialized_get_srid(gser))) {
3126  elog(NOTICE, "Geometry provided does not have the same SRID as the raster. Returning NULL");
3127 
3128  rtpg_clip_arg_destroy(arg);
3129  PG_FREE_IF_COPY(pgraster, 0);
3130  lwgeom_free(geom);
3131  PG_FREE_IF_COPY(gser, 2);
3132 
3133  PG_RETURN_NULL();
3134  }
3135 
3136  /* crop (4) */
3137  if (!PG_ARGISNULL(4) && !PG_GETARG_BOOL(4))
3138  arg->extenttype = ET_FIRST;
3139 
3140  /* get intersection geometry of input raster and input geometry */
3141  if (rt_raster_get_convex_hull(arg->raster, &rastgeom) != ES_NONE) {
3142 
3143  rtpg_clip_arg_destroy(arg);
3144  PG_FREE_IF_COPY(pgraster, 0);
3145  lwgeom_free(geom);
3146  PG_FREE_IF_COPY(gser, 2);
3147 
3148  elog(ERROR, "RASTER_clip: Could not get convex hull of raster");
3149  PG_RETURN_NULL();
3150  }
3151 
3152  tmpgeom = lwgeom_intersection(rastgeom, geom);
3153  lwgeom_free(rastgeom);
3154  lwgeom_free(geom);
3155  PG_FREE_IF_COPY(gser, 2);
3156  geom = tmpgeom;
3157 
3158  /* intersection is empty AND extent type is INTERSECTION, return empty */
3159  if (lwgeom_is_empty(geom) && arg->extenttype == ET_INTERSECTION) {
3160  elog(NOTICE, "The input raster and input geometry do not intersect. Returning empty raster");
3161 
3162  rtpg_clip_arg_destroy(arg);
3163  PG_FREE_IF_COPY(pgraster, 0);
3164  lwgeom_free(geom);
3165 
3166  rtn = rt_raster_new(0, 0);
3167  if (rtn == NULL) {
3168  elog(ERROR, "RASTER_clip: Could not create empty raster");
3169  PG_RETURN_NULL();
3170  }
3171 
3172  pgrtn = rt_raster_serialize(rtn);
3173  rt_raster_destroy(rtn);
3174  if (NULL == pgrtn)
3175  PG_RETURN_NULL();
3176 
3177  SET_VARSIZE(pgrtn, pgrtn->size);
3178  PG_RETURN_POINTER(pgrtn);
3179  }
3180 
3181  /* nband (1) */
3182  if (!PG_ARGISNULL(1)) {
3183  array = PG_GETARG_ARRAYTYPE_P(1);
3184  etype = ARR_ELEMTYPE(array);
3185  get_typlenbyvalalign(etype, &typlen, &typbyval, &typalign);
3186 
3187  switch (etype) {
3188  case INT2OID:
3189  case INT4OID:
3190  break;
3191  default:
3192  rtpg_clip_arg_destroy(arg);
3193  PG_FREE_IF_COPY(pgraster, 0);
3194  lwgeom_free(geom);
3195  elog(ERROR, "RASTER_clip: Invalid data type for band indexes");
3196  PG_RETURN_NULL();
3197  break;
3198  }
3199 
3200  deconstruct_array(
3201  array, etype,
3202  typlen, typbyval, typalign,
3203  &e, &nulls, &(arg->numbands)
3204  );
3205 
3206  arg->band = palloc(sizeof(struct rtpg_clip_band_t) * arg->numbands);
3207  if (arg->band == NULL) {
3208  rtpg_clip_arg_destroy(arg);
3209  PG_FREE_IF_COPY(pgraster, 0);
3210  lwgeom_free(geom);
3211  elog(ERROR, "RASTER_clip: Could not allocate memory for band arguments");
3212  PG_RETURN_NULL();
3213  }
3214 
3215  for (i = 0, j = 0; i < arg->numbands; i++) {
3216  if (nulls[i]) continue;
3217 
3218  switch (etype) {
3219  case INT2OID:
3220  arg->band[j].nband = DatumGetInt16(e[i]) - 1;
3221  break;
3222  case INT4OID:
3223  arg->band[j].nband = DatumGetInt32(e[i]) - 1;
3224  break;
3225  }
3226 
3227  j++;
3228  }
3229 
3230  if (j < arg->numbands) {
3231  arg->band = repalloc(arg->band, sizeof(struct rtpg_clip_band_t) * j);
3232  if (arg->band == NULL) {
3233  rtpg_clip_arg_destroy(arg);
3234  PG_FREE_IF_COPY(pgraster, 0);
3235  lwgeom_free(geom);
3236  elog(ERROR, "RASTER_clip: Could not reallocate memory for band arguments");
3237  PG_RETURN_NULL();
3238  }
3239 
3240  arg->numbands = j;
3241  }
3242 
3243  /* validate band */
3244  for (i = 0; i < arg->numbands; i++) {
3245  if (!rt_raster_has_band(arg->raster, arg->band[i].nband)) {
3246  elog(NOTICE, "Band at index %d not found in raster", arg->band[i].nband + 1);
3247  rtpg_clip_arg_destroy(arg);
3248  PG_FREE_IF_COPY(pgraster, 0);
3249  lwgeom_free(geom);
3250  PG_RETURN_NULL();
3251  }
3252 
3253  arg->band[i].hasnodata = 0;
3254  arg->band[i].nodataval = 0;
3255  }
3256  }
3257  else {
3259 
3260  /* raster may have no bands */
3261  if (arg->numbands) {
3262  arg->band = palloc(sizeof(struct rtpg_clip_band_t) * arg->numbands);
3263  if (arg->band == NULL) {
3264 
3265  rtpg_clip_arg_destroy(arg);
3266  PG_FREE_IF_COPY(pgraster, 0);
3267  lwgeom_free(geom);
3268 
3269  elog(ERROR, "RASTER_clip: Could not allocate memory for band arguments");
3270  PG_RETURN_NULL();
3271  }
3272 
3273  for (i = 0; i < arg->numbands; i++) {
3274  arg->band[i].nband = i;
3275  arg->band[i].hasnodata = 0;
3276  arg->band[i].nodataval = 0;
3277  }
3278  }
3279  }
3280 
3281  /* nodataval (3) */
3282  if (!PG_ARGISNULL(3)) {
3283  array = PG_GETARG_ARRAYTYPE_P(3);
3284  etype = ARR_ELEMTYPE(array);
3285  get_typlenbyvalalign(etype, &typlen, &typbyval, &typalign);
3286 
3287  switch (etype) {
3288  case FLOAT4OID:
3289  case FLOAT8OID:
3290  break;
3291  default:
3292  rtpg_clip_arg_destroy(arg);
3293  PG_FREE_IF_COPY(pgraster, 0);
3294  lwgeom_free(geom);
3295  elog(ERROR, "RASTER_clip: Invalid data type for NODATA values");
3296  PG_RETURN_NULL();
3297  break;
3298  }
3299 
3300  deconstruct_array(
3301  array, etype,
3302  typlen, typbyval, typalign,
3303  &e, &nulls, &k
3304  );
3305 
3306  /* it doesn't matter if there are more nodataval */
3307  for (i = 0, j = 0; i < arg->numbands; i++, j++) {
3308  /* cap j to the last nodataval element */
3309  if (j >= k)
3310  j = k - 1;
3311 
3312  if (nulls[j])
3313  continue;
3314 
3315  arg->band[i].hasnodata = 1;
3316  switch (etype) {
3317  case FLOAT4OID:
3318  arg->band[i].nodataval = DatumGetFloat4(e[j]);
3319  break;
3320  case FLOAT8OID:
3321  arg->band[i].nodataval = DatumGetFloat8(e[j]);
3322  break;
3323  }
3324  }
3325  }
3326 
3327  /* get wkb of geometry */
3328  POSTGIS_RT_DEBUG(3, "getting wkb of geometry");
3329  wkb = lwgeom_to_wkb_varlena(geom, WKB_SFSQL);
3330  lwgeom_free(geom);
3331 
3332  /* rasterize geometry */
3333  arg->mask = rt_raster_gdal_rasterize((unsigned char *)wkb->data,
3334  LWSIZE_GET(wkb->size) - LWVARHDRSZ,
3335  NULL,
3336  0,
3337  NULL,
3338  NULL,
3339  NULL,
3340  NULL,
3341  NULL,
3342  NULL,
3343  NULL,
3344  &(gt[1]),
3345  &(gt[5]),
3346  NULL,
3347  NULL,
3348  &(gt[0]),
3349  &(gt[3]),
3350  &(gt[2]),
3351  &(gt[4]),
3352  NULL);
3353 
3354  pfree(wkb);
3355  if (arg->mask == NULL) {
3356  rtpg_clip_arg_destroy(arg);
3357  PG_FREE_IF_COPY(pgraster, 0);
3358  elog(ERROR, "RASTER_clip: Could not rasterize intersection geometry");
3359  PG_RETURN_NULL();
3360  }
3361 
3362  /* set SRID */
3363  rt_raster_set_srid(arg->mask, srid);
3364 
3365  /* run iterator */
3366 
3367  /* init itrset */
3368  itrset = palloc(sizeof(struct rt_iterator_t) * 2);
3369  if (itrset == NULL) {
3370  rtpg_clip_arg_destroy(arg);
3371  PG_FREE_IF_COPY(pgraster, 0);
3372  elog(ERROR, "RASTER_clip: Could not allocate memory for iterator arguments");
3373  PG_RETURN_NULL();
3374  }
3375 
3376  /* one band at a time */
3377  for (i = 0; i < arg->numbands; i++) {
3378  POSTGIS_RT_DEBUGF(4, "band arg %d (nband, hasnodata, nodataval) = (%d, %d, %f)",
3379  i, arg->band[i].nband, arg->band[i].hasnodata, arg->band[i].nodataval);
3380 
3381  band = rt_raster_get_band(arg->raster, arg->band[i].nband);
3382 
3383  /* band metadata */
3384  pixtype = rt_band_get_pixtype(band);
3385 
3386  if (arg->band[i].hasnodata) {
3387  hasnodata = 1;
3388  nodataval = arg->band[i].nodataval;
3389  }
3390  else if (rt_band_get_hasnodata_flag(band)) {
3391  hasnodata = 1;
3392  rt_band_get_nodata(band, &nodataval);
3393  }
3394  else {
3395  hasnodata = 0;
3396  nodataval = rt_band_get_min_value(band);
3397  }
3398 
3399  /* band is NODATA, create NODATA band and continue */
3401  /* create raster */
3402  if (rtn == NULL) {
3403  noerr = rt_raster_from_two_rasters(arg->raster, arg->mask, arg->extenttype, &rtn, NULL);
3404  if (noerr != ES_NONE) {
3405  rtpg_clip_arg_destroy(arg);
3406  PG_FREE_IF_COPY(pgraster, 0);
3407  elog(ERROR, "RASTER_clip: Could not create output raster");
3408  PG_RETURN_NULL();
3409  }
3410  }
3411 
3412  /* create NODATA band */
3413  if (rt_raster_generate_new_band(rtn, pixtype, nodataval, hasnodata, nodataval, i) < 0) {
3414  rt_raster_destroy(rtn);
3415  rtpg_clip_arg_destroy(arg);
3416  PG_FREE_IF_COPY(pgraster, 0);
3417  elog(ERROR, "RASTER_clip: Could not add NODATA band to output raster");
3418  PG_RETURN_NULL();
3419  }
3420 
3421  continue;
3422  }
3423 
3424  /* raster */
3425  itrset[0].raster = arg->raster;
3426  itrset[0].nband = arg->band[i].nband;
3427  itrset[0].nbnodata = 1;
3428 
3429  /* mask */
3430  itrset[1].raster = arg->mask;
3431  itrset[1].nband = 0;
3432  itrset[1].nbnodata = 1;
3433 
3434  /* pass to iterator */
3435  noerr = rt_raster_iterator(
3436  itrset, 2,
3437  arg->extenttype, NULL,
3438  pixtype,
3439  hasnodata, nodataval,
3440  0, 0,
3441  NULL,
3442  NULL,
3444  &_raster
3445  );
3446 
3447  if (noerr != ES_NONE) {
3448  pfree(itrset);
3449  rtpg_clip_arg_destroy(arg);
3450  if (rtn != NULL) rt_raster_destroy(rtn);
3451  PG_FREE_IF_COPY(pgraster, 0);
3452  elog(ERROR, "RASTER_clip: Could not run raster iterator function");
3453  PG_RETURN_NULL();
3454  }
3455 
3456  /* new raster */
3457  if (rtn == NULL)
3458  rtn = _raster;
3459  /* copy band */
3460  else {
3461  band = rt_raster_get_band(_raster, 0);
3462  if (band == NULL) {
3463  pfree(itrset);
3464  rtpg_clip_arg_destroy(arg);
3465  rt_raster_destroy(_raster);
3466  rt_raster_destroy(rtn);
3467  PG_FREE_IF_COPY(pgraster, 0);
3468  elog(NOTICE, "RASTER_clip: Could not get band from working raster");
3469  PG_RETURN_NULL();
3470  }
3471 
3472  if (rt_raster_add_band(rtn, band, i) < 0) {
3473  pfree(itrset);
3474  rtpg_clip_arg_destroy(arg);
3475  rt_raster_destroy(_raster);
3476  rt_raster_destroy(rtn);
3477  PG_FREE_IF_COPY(pgraster, 0);
3478  elog(ERROR, "RASTER_clip: Could not add new band to output raster");
3479  PG_RETURN_NULL();
3480  }
3481 
3482  rt_raster_destroy(_raster);
3483  }
3484  }
3485 
3486  pfree(itrset);
3487  rtpg_clip_arg_destroy(arg);
3488  PG_FREE_IF_COPY(pgraster, 0);
3489 
3490  pgrtn = rt_raster_serialize(rtn);
3491  rt_raster_destroy(rtn);
3492 
3493  POSTGIS_RT_DEBUG(3, "Finished");
3494 
3495  if (!pgrtn)
3496  PG_RETURN_NULL();
3497 
3498  SET_VARSIZE(pgrtn, pgrtn->size);
3499  PG_RETURN_POINTER(pgrtn);
3500 }
#define FALSE
Definition: dbfopen.c:72
int32_t gserialized_get_srid(const GSERIALIZED *g)
Extract the SRID from the serialized form (it is packed into three bytes so this is a handy function)...
Definition: gserialized.c:126
LWGEOM * lwgeom_from_gserialized(const GSERIALIZED *g)
Allocate a new LWGEOM from a GSERIALIZED.
Definition: gserialized.c:239
int lwgeom_ndims(const LWGEOM *geom)
Return the number of dimensions (2, 3, 4) in a geometry.
Definition: lwgeom.c:938
#define LWVARHDRSZ
Definition: liblwgeom.h:325
void lwgeom_free(LWGEOM *geom)
Definition: lwgeom.c:1138
LWGEOM * lwgeom_intersection(const LWGEOM *geom1, const LWGEOM *geom2)
#define LWSIZE_GET(varsize)
Macro for reading the size from the GSERIALIZED size attribute.
Definition: liblwgeom.h:338
#define SRID_UNKNOWN
Unknown SRID value.
Definition: liblwgeom.h:229
lwvarlena_t * lwgeom_to_wkb_varlena(const LWGEOM *geom, uint8_t variant)
Definition: lwout_wkb.c:851
#define WKB_SFSQL
Definition: liblwgeom.h:2147
int32_t clamp_srid(int32_t srid)
Return a valid SRID from an arbitrary integer Raises a notice if what comes out is different from wha...
Definition: lwutil.c:333
LWGEOM * lwgeom_force_2d(const LWGEOM *geom)
Strip out the Z/M components of an LWGEOM.
Definition: lwgeom.c:776
int32_t rt_raster_get_srid(rt_raster raster)
Get raster's SRID.
Definition: rt_raster.c:356
int rt_raster_generate_new_band(rt_raster raster, rt_pixtype pixtype, double initialvalue, uint32_t hasnodata, double nodatavalue, int index)
Generate a new inline band and add it to a raster.
Definition: rt_raster.c:485
int rt_raster_add_band(rt_raster raster, rt_band band, int index)
Add band data to a raster.
Definition: rt_raster.c:405
int rt_band_get_hasnodata_flag(rt_band band)
Get hasnodata flag value.
Definition: rt_band.c:674
void rt_raster_destroy(rt_raster raster)
Release memory associated to a raster.
Definition: rt_raster.c:82
rt_pixtype
Definition: librtcore.h:185
int rt_band_get_isnodata_flag(rt_band band)
Get isnodata flag value.
Definition: rt_band.c:714
rt_raster rt_raster_new(uint32_t width, uint32_t height)
Construct a raster with given dimensions.
Definition: rt_raster.c:48
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:1342
void * rt_raster_serialize(rt_raster raster)
Return this raster in serialized form.
Definition: rt_serialize.c:521
double rt_band_get_min_value(rt_band band)
Returns the minimal possible value for the band according to the pixel type.
Definition: rt_band.c:1745
@ ES_NONE
Definition: librtcore.h:180
rt_raster rt_raster_gdal_rasterize(const unsigned char *wkb, uint32_t wkb_len, const char *srs, uint32_t num_bands, rt_pixtype *pixtype, double *init, double *value, double *nodata, uint8_t *hasnodata, int *width, int *height, double *scale_x, double *scale_y, double *ul_xw, double *ul_yw, double *grid_xw, double *grid_yw, double *skew_x, double *skew_y, char **options)
Return a raster of the provided geometry.
Definition: rt_raster.c:2491
uint16_t rt_raster_get_num_bands(rt_raster raster)
Definition: rt_raster.c:372
rt_errorstate rt_raster_get_convex_hull(rt_raster raster, LWGEOM **hull)
Get raster's convex hull.
Definition: rt_geometry.c:803
rt_errorstate rt_raster_iterator(rt_iterator itrset, uint16_t itrcount, rt_extenttype extenttype, rt_raster customextent, rt_pixtype pixtype, uint8_t hasnodata, double nodataval, uint16_t distancex, uint16_t distancey, rt_mask mask, void *userarg, int(*callback)(rt_iterator_arg arg, void *userarg, double *value, int *nodata), rt_raster *rtnraster)
n-raster iterator.
void rt_raster_set_srid(rt_raster raster, int32_t srid)
Set raster's SRID.
Definition: rt_raster.c:363
@ ET_INTERSECTION
Definition: librtcore.h:201
@ ET_FIRST
Definition: librtcore.h:203
rt_errorstate rt_band_get_nodata(rt_band band, double *nodata)
Get NODATA value.
Definition: rt_band.c:1730
rt_pixtype rt_band_get_pixtype(rt_band band)
Return pixeltype of this band.
Definition: rt_band.c:631
rt_errorstate rt_raster_from_two_rasters(rt_raster rast1, rt_raster rast2, rt_extenttype extenttype, rt_raster *rtnraster, double *offset)
Definition: rt_raster.c:3337
void rt_raster_get_geotransform_matrix(rt_raster raster, double *gt)
Get 6-element array of raster geotransform matrix.
Definition: rt_raster.c:706
rt_raster rt_raster_deserialize(void *serialized, int header_only)
Return a raster from a serialized form.
Definition: rt_serialize.c:725
int rt_raster_is_empty(rt_raster raster)
Return TRUE if the raster is empty.
Definition: rt_raster.c:1329
rt_band rt_raster_get_band(rt_raster raster, int bandNum)
Return Nth band, or NULL if unavailable.
Definition: rt_raster.c:381
static int lwgeom_is_empty(const LWGEOM *geom)
Return true or false depending on whether a geometry is an "empty" geometry (no vertices members)
Definition: lwinline.h:203
band
Definition: ovdump.py:58
gt
Definition: window.py:78
static rtpg_clip_arg rtpg_clip_arg_init()
static void rtpg_clip_arg_destroy(rtpg_clip_arg arg)
static int rtpg_clip_callback(rt_iterator_arg arg, void *userarg, double *value, int *nodata)
#define POSTGIS_RT_DEBUG(level, msg)
Definition: rtpostgis.h:61
#define POSTGIS_RT_DEBUGF(level, msg,...)
Definition: rtpostgis.h:65
uint32_t size
Definition: liblwgeom.h:321
char data[]
Definition: liblwgeom.h:322
rt_raster raster
Definition: librtcore.h:2444
uint16_t nband
Definition: librtcore.h:2445
uint8_t nbnodata
Definition: librtcore.h:2446
Struct definitions.
Definition: librtcore.h:2251
rtpg_clip_band band
rt_extenttype extenttype

References rtpg_clip_arg_t::band, ovdump::band, clamp_srid(), lwvarlena_t::data, ES_NONE, ET_FIRST, ET_INTERSECTION, rtpg_clip_arg_t::extenttype, FALSE, gserialized_get_srid(), window::gt, rtpg_clip_band_t::hasnodata, lwgeom_force_2d(), lwgeom_free(), lwgeom_from_gserialized(), lwgeom_intersection(), lwgeom_is_empty(), lwgeom_ndims(), lwgeom_to_wkb_varlena(), LWSIZE_GET, LWVARHDRSZ, rtpg_clip_arg_t::mask, rt_iterator_t::nband, rtpg_clip_band_t::nband, rt_iterator_t::nbnodata, rtpg_clip_band_t::nodataval, rtpg_clip_arg_t::numbands, POSTGIS_RT_DEBUG, POSTGIS_RT_DEBUGF, rt_iterator_t::raster, rtpg_clip_arg_t::raster, rt_band_get_hasnodata_flag(), rt_band_get_isnodata_flag(), rt_band_get_min_value(), rt_band_get_nodata(), rt_band_get_pixtype(), rt_raster_add_band(), rt_raster_deserialize(), rt_raster_destroy(), rt_raster_from_two_rasters(), rt_raster_gdal_rasterize(), rt_raster_generate_new_band(), rt_raster_get_band(), rt_raster_get_convex_hull(), rt_raster_get_geotransform_matrix(), rt_raster_get_num_bands(), rt_raster_get_srid(), rt_raster_has_band(), rt_raster_is_empty(), rt_raster_iterator(), rt_raster_new(), rt_raster_serialize(), rt_raster_set_srid(), rtpg_clip_arg_destroy(), rtpg_clip_arg_init(), rtpg_clip_callback(), lwvarlena_t::size, rt_raster_serialized_t::size, SRID_UNKNOWN, and WKB_SFSQL.

Here is the call graph for this function: