PostGIS  3.4.0dev-r@@SVN_REVISION@@

◆ rtpg_nmapalgebraexpr_callback()

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

Definition at line 1065 of file rtpg_mapalgebra.c.

1068  {
1070  SPIPlanPtr plan = NULL;
1071  int i = 0;
1072  uint8_t id = 0;
1073 
1074  if (arg == NULL)
1075  return 0;
1076 
1077  *value = 0;
1078  *nodata = 0;
1079 
1080  /* 2 raster */
1081  if (arg->rasters > 1) {
1082  /* nodata1 = 1 AND nodata2 = 1, nodatanodataval */
1083  if (arg->nodata[0][0][0] && arg->nodata[1][0][0]) {
1084  if (callback->nodatanodata.hasval)
1085  *value = callback->nodatanodata.val;
1086  else
1087  *nodata = 1;
1088  }
1089  /* nodata1 = 1 AND nodata2 != 1, nodata1expr */
1090  else if (arg->nodata[0][0][0] && !arg->nodata[1][0][0]) {
1091  id = 1;
1092  if (callback->expr[id].hasval)
1093  *value = callback->expr[id].val;
1094  else if (callback->expr[id].spi_plan)
1095  plan = callback->expr[id].spi_plan;
1096  else
1097  *nodata = 1;
1098  }
1099  /* nodata1 != 1 AND nodata2 = 1, nodata2expr */
1100  else if (!arg->nodata[0][0][0] && arg->nodata[1][0][0]) {
1101  id = 2;
1102  if (callback->expr[id].hasval)
1103  *value = callback->expr[id].val;
1104  else if (callback->expr[id].spi_plan)
1105  plan = callback->expr[id].spi_plan;
1106  else
1107  *nodata = 1;
1108  }
1109  /* expression */
1110  else {
1111  id = 0;
1112  if (callback->expr[id].hasval)
1113  *value = callback->expr[id].val;
1114  else if (callback->expr[id].spi_plan)
1115  plan = callback->expr[id].spi_plan;
1116  else {
1117  if (callback->nodatanodata.hasval)
1118  *value = callback->nodatanodata.val;
1119  else
1120  *nodata = 1;
1121  }
1122  }
1123  }
1124  /* 1 raster */
1125  else {
1126  /* nodata = 1, nodata1expr */
1127  if (arg->nodata[0][0][0]) {
1128  id = 1;
1129  if (callback->expr[id].hasval)
1130  *value = callback->expr[id].val;
1131  else if (callback->expr[id].spi_plan)
1132  plan = callback->expr[id].spi_plan;
1133  else
1134  *nodata = 1;
1135  }
1136  /* expression */
1137  else {
1138  id = 0;
1139  if (callback->expr[id].hasval)
1140  *value = callback->expr[id].val;
1141  else if (callback->expr[id].spi_plan)
1142  plan = callback->expr[id].spi_plan;
1143  else {
1144  /* see if nodata1expr is available */
1145  id = 1;
1146  if (callback->expr[id].hasval)
1147  *value = callback->expr[id].val;
1148  else if (callback->expr[id].spi_plan)
1149  plan = callback->expr[id].spi_plan;
1150  else
1151  *nodata = 1;
1152  }
1153  }
1154  }
1155 
1156  /* run prepared plan */
1157  if (plan != NULL) {
1158  Datum values[12];
1159  char nulls[12];
1160  int err = 0;
1161 
1162  TupleDesc tupdesc;
1163  SPITupleTable *tuptable = NULL;
1164  HeapTuple tuple;
1165  Datum datum;
1166  bool isnull = FALSE;
1167 
1168  POSTGIS_RT_DEBUGF(4, "Running plan %d", id);
1169 
1170  /* init values and nulls */
1171  memset(values, (Datum) NULL, sizeof(Datum) * callback->kw.count);
1172  memset(nulls, FALSE, sizeof(char) * callback->kw.count);
1173 
1174  if (callback->expr[id].spi_argcount) {
1175  int idx = 0;
1176 
1177  for (i = 0; i < callback->kw.count; i++) {
1178  idx = callback->expr[id].spi_argpos[i];
1179  if (idx < 1) continue;
1180  idx--; /* 1-based now 0-based */
1181 
1182  switch (i) {
1183  /* [rast.x] */
1184  case 0:
1185  values[idx] = Int32GetDatum(arg->src_pixel[0][0] + 1);
1186  break;
1187  /* [rast.y] */
1188  case 1:
1189  values[idx] = Int32GetDatum(arg->src_pixel[0][1] + 1);
1190  break;
1191  /* [rast.val] */
1192  case 2:
1193  /* [rast] */
1194  case 3:
1195  if (!arg->nodata[0][0][0])
1196  values[idx] = Float8GetDatum(arg->values[0][0][0]);
1197  else
1198  nulls[idx] = TRUE;
1199  break;
1200 
1201  /* [rast1.x] */
1202  case 4:
1203  values[idx] = Int32GetDatum(arg->src_pixel[0][0] + 1);
1204  break;
1205  /* [rast1.y] */
1206  case 5:
1207  values[idx] = Int32GetDatum(arg->src_pixel[0][1] + 1);
1208  break;
1209  /* [rast1.val] */
1210  case 6:
1211  /* [rast1] */
1212  case 7:
1213  if (!arg->nodata[0][0][0])
1214  values[idx] = Float8GetDatum(arg->values[0][0][0]);
1215  else
1216  nulls[idx] = TRUE;
1217  break;
1218 
1219  /* [rast2.x] */
1220  case 8:
1221  values[idx] = Int32GetDatum(arg->src_pixel[1][0] + 1);
1222  break;
1223  /* [rast2.y] */
1224  case 9:
1225  values[idx] = Int32GetDatum(arg->src_pixel[1][1] + 1);
1226  break;
1227  /* [rast2.val] */
1228  case 10:
1229  /* [rast2] */
1230  case 11:
1231  if (!arg->nodata[1][0][0])
1232  values[idx] = Float8GetDatum(arg->values[1][0][0]);
1233  else
1234  nulls[idx] = TRUE;
1235  break;
1236  }
1237 
1238  }
1239  }
1240 
1241  /* run prepared plan */
1242  err = SPI_execute_plan(plan, values, nulls, TRUE, 1);
1243  if (err != SPI_OK_SELECT || SPI_tuptable == NULL || SPI_processed != 1) {
1244  elog(ERROR, "rtpg_nmapalgebraexpr_callback: Unexpected error when running prepared statement %d", id);
1245  return 0;
1246  }
1247 
1248  /* get output of prepared plan */
1249  tupdesc = SPI_tuptable->tupdesc;
1250  tuptable = SPI_tuptable;
1251  tuple = tuptable->vals[0];
1252 
1253  datum = SPI_getbinval(tuple, tupdesc, 1, &isnull);
1254  if (SPI_result == SPI_ERROR_NOATTRIBUTE) {
1255  if (SPI_tuptable) SPI_freetuptable(tuptable);
1256  elog(ERROR, "rtpg_nmapalgebraexpr_callback: Could not get result of prepared statement %d", id);
1257  return 0;
1258  }
1259 
1260  if (!isnull) {
1261  *value = DatumGetFloat8(datum);
1262  POSTGIS_RT_DEBUG(4, "Getting value from Datum");
1263  }
1264  else {
1265  /* 2 raster, check nodatanodataval */
1266  if (arg->rasters > 1) {
1267  if (callback->nodatanodata.hasval)
1268  *value = callback->nodatanodata.val;
1269  else
1270  *nodata = 1;
1271  }
1272  /* 1 raster, check nodataval */
1273  else {
1274  if (callback->expr[1].hasval)
1275  *value = callback->expr[1].val;
1276  else
1277  *nodata = 1;
1278  }
1279  }
1280 
1281  if (SPI_tuptable) SPI_freetuptable(tuptable);
1282  }
1283 
1284  POSTGIS_RT_DEBUGF(4, "(value, nodata) = (%f, %d)", *value, *nodata);
1285  return 1;
1286 }
#define TRUE
Definition: dbfopen.c:73
#define FALSE
Definition: dbfopen.c:72
int value
Definition: genraster.py:62
#define POSTGIS_RT_DEBUG(level, msg)
Definition: rtpostgis.h:65
#define POSTGIS_RT_DEBUGF(level, msg,...)
Definition: rtpostgis.h:69
double *** values
Definition: librtcore.h:2612
uint16_t rasters
Definition: librtcore.h:2604
struct rtpg_nmapalgebraexpr_callback_arg::@26 kw
struct rtpg_nmapalgebraexpr_callback_arg::@24 expr[3]
struct rtpg_nmapalgebraexpr_callback_arg::@25 nodatanodata

References rtpg_nmapalgebraexpr_callback_arg::count, rtpg_nmapalgebraexpr_callback_arg::expr, FALSE, rtpg_nmapalgebraexpr_callback_arg::hasval, rtpg_nmapalgebraexpr_callback_arg::kw, rt_iterator_arg_t::nodata, rtpg_nmapalgebraexpr_callback_arg::nodatanodata, POSTGIS_RT_DEBUG, POSTGIS_RT_DEBUGF, rt_iterator_arg_t::rasters, rtpg_nmapalgebraexpr_callback_arg::spi_argcount, rtpg_nmapalgebraexpr_callback_arg::spi_argpos, rtpg_nmapalgebraexpr_callback_arg::spi_plan, rt_iterator_arg_t::src_pixel, TRUE, rtpg_nmapalgebraexpr_callback_arg::val, genraster::value, and rt_iterator_arg_t::values.

Referenced by RASTER_nMapAlgebraExpr().

Here is the caller graph for this function: