Skip to content

Commit 935e77d

Browse files
committed
Further patch rangetypes_selfuncs.c's statistics slot management.
Values in a STATISTIC_KIND_RANGE_LENGTH_HISTOGRAM slot are float8, not of the type of the column the statistics are for. This bug is at least partly the fault of sloppy specification comments for get_attstatsslot()/free_attstatsslot(): the type OID they want is that of the stavalues entries, not of the underlying column. (I double-checked other callers and they seem to get this right.) Adjust the comments to be more correct. Per buildfarm. Security: CVE-2017-7484
1 parent 2d5e7b4 commit 935e77d

File tree

3 files changed

+15
-12
lines changed

3 files changed

+15
-12
lines changed

src/backend/utils/adt/rangetypes_selfuncs.c

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
#include "access/htup_details.h"
2121
#include "catalog/pg_operator.h"
2222
#include "catalog/pg_statistic.h"
23+
#include "catalog/pg_type.h"
2324
#include "utils/builtins.h"
2425
#include "utils/lsyscache.h"
2526
#include "utils/rangetypes.h"
@@ -246,16 +247,17 @@ calc_rangesel(TypeCacheEntry *typcache, VariableStatData *vardata,
246247

247248
/* Try to get fraction of empty ranges */
248249
if (get_attstatsslot(vardata->statsTuple,
249-
vardata->atttype, vardata->atttypmod,
250-
STATISTIC_KIND_RANGE_LENGTH_HISTOGRAM, InvalidOid,
250+
FLOAT8OID, -1,
251+
STATISTIC_KIND_RANGE_LENGTH_HISTOGRAM,
252+
InvalidOid,
251253
NULL,
252254
NULL, NULL,
253255
&numbers, &nnumbers))
254256
{
255257
if (nnumbers != 1)
256258
elog(ERROR, "invalid empty fraction statistic"); /* shouldn't happen */
257259
empty_frac = numbers[0];
258-
free_attstatsslot(vardata->atttype, NULL, 0, numbers, nnumbers);
260+
free_attstatsslot(FLOAT8OID, NULL, 0, numbers, nnumbers);
259261
}
260262
else
261263
{
@@ -424,7 +426,7 @@ calc_hist_selectivity(TypeCacheEntry *typcache, VariableStatData *vardata,
424426
{
425427
if (!(HeapTupleIsValid(vardata->statsTuple) &&
426428
get_attstatsslot(vardata->statsTuple,
427-
vardata->atttype, vardata->atttypmod,
429+
FLOAT8OID, -1,
428430
STATISTIC_KIND_RANGE_LENGTH_HISTOGRAM,
429431
InvalidOid,
430432
NULL,
@@ -438,7 +440,7 @@ calc_hist_selectivity(TypeCacheEntry *typcache, VariableStatData *vardata,
438440
/* check that it's a histogram, not just a dummy entry */
439441
if (length_nhist < 2)
440442
{
441-
free_attstatsslot(vardata->atttype,
443+
free_attstatsslot(FLOAT8OID,
442444
length_hist_values, length_nhist, NULL, 0);
443445
free_attstatsslot(vardata->atttype, hist_values, nhist, NULL, 0);
444446
return -1.0;
@@ -578,7 +580,7 @@ calc_hist_selectivity(TypeCacheEntry *typcache, VariableStatData *vardata,
578580
break;
579581
}
580582

581-
free_attstatsslot(vardata->atttype,
583+
free_attstatsslot(FLOAT8OID,
582584
length_hist_values, length_nhist, NULL, 0);
583585
free_attstatsslot(vardata->atttype, hist_values, nhist, NULL, 0);
584586

src/backend/utils/cache/lsyscache.c

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2832,17 +2832,17 @@ get_attavgwidth(Oid relid, AttrNumber attnum)
28322832
* that have been provided by a stats hook and didn't really come from
28332833
* pg_statistic.
28342834
*
2835-
* statstuple: pg_statistics tuple to be examined.
2836-
* atttype: type OID of attribute (can be InvalidOid if values == NULL).
2837-
* atttypmod: typmod of attribute (can be 0 if values == NULL).
2835+
* statstuple: pg_statistic tuple to be examined.
2836+
* atttype: type OID of slot's stavalues (can be InvalidOid if values == NULL).
2837+
* atttypmod: typmod of slot's stavalues (can be 0 if values == NULL).
28382838
* reqkind: STAKIND code for desired statistics slot kind.
28392839
* reqop: STAOP value wanted, or InvalidOid if don't care.
28402840
* actualop: if not NULL, *actualop receives the actual STAOP value.
28412841
* values, nvalues: if not NULL, the slot's stavalues are extracted.
28422842
* numbers, nnumbers: if not NULL, the slot's stanumbers are extracted.
28432843
*
28442844
* If assigned, values and numbers are set to point to palloc'd arrays.
2845-
* If the attribute type is pass-by-reference, the values referenced by
2845+
* If the stavalues datatype is pass-by-reference, the values referenced by
28462846
* the values array are themselves palloc'd. The palloc'd stuff can be
28472847
* freed by calling free_attstatsslot.
28482848
*
@@ -2972,7 +2972,8 @@ get_attstatsslot(HeapTuple statstuple,
29722972
* free_attstatsslot
29732973
* Free data allocated by get_attstatsslot
29742974
*
2975-
* atttype need be valid only if values != NULL.
2975+
* atttype is the type of the individual values in values[].
2976+
* It need be valid only if values != NULL.
29762977
*/
29772978
void
29782979
free_attstatsslot(Oid atttype,

src/include/catalog/pg_statistic.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -275,7 +275,7 @@ typedef FormData_pg_statistic *Form_pg_statistic;
275275
* fraction of empty ranges. stavalues is a histogram of non-empty lengths, in
276276
* a format similar to STATISTIC_KIND_HISTOGRAM: it contains M (>=2) range
277277
* values that divide the column data values into M-1 bins of approximately
278-
* equal population. The lengths are stores as float8s, as measured by the
278+
* equal population. The lengths are stored as float8s, as measured by the
279279
* range type's subdiff function. Only non-null rows are considered.
280280
*/
281281
#define STATISTIC_KIND_RANGE_LENGTH_HISTOGRAM 6

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy