]> granicus.if.org Git - postgresql/commitdiff
Clean up foreign-key caching code in planner.
authorTom Lane <tgl@sss.pgh.pa.us>
Mon, 11 Apr 2016 03:47:30 +0000 (23:47 -0400)
committerTom Lane <tgl@sss.pgh.pa.us>
Mon, 11 Apr 2016 03:47:30 +0000 (23:47 -0400)
Coverity complained that the code added by 015e88942aa50f0d lacked an
error check for SearchSysCache1 failures, which it should have.  But
the code was pretty duff in other ways too, including failure to think
about whether it could really cope with arrays of different lengths.

src/backend/optimizer/util/plancat.c

index 86cc640cf267c81f947fc9db4c0cc129e0a021c9..9c11b09cbcc57be8100b4beb3876032659aa52c2 100644 (file)
@@ -408,17 +408,20 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
 
        foreach(l, fkoidlist)
        {
-               int                     i;
-               ArrayType  *arr;
+               Oid                     fkoid = lfirst_oid(l);
+               HeapTuple       htup;
+               Form_pg_constraint constraint;
+               ForeignKeyOptInfo *info;
                Datum           adatum;
                bool            isnull;
+               ArrayType  *arr;
                int                     numkeys;
-               Oid                     fkoid = lfirst_oid(l);
-
-               HeapTuple       htup = SearchSysCache1(CONSTROID, ObjectIdGetDatum(fkoid));
-               Form_pg_constraint constraint = (Form_pg_constraint) GETSTRUCT(htup);
+               int                     i;
 
-               ForeignKeyOptInfo *info;
+               htup = SearchSysCache1(CONSTROID, ObjectIdGetDatum(fkoid));
+               if (!HeapTupleIsValid(htup)) /* should not happen */
+                       elog(ERROR, "cache lookup failed for constraint %u", fkoid);
+               constraint = (Form_pg_constraint) GETSTRUCT(htup);
 
                Assert(constraint->contype == CONSTRAINT_FOREIGN);
 
@@ -434,8 +437,7 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
 
                arr = DatumGetArrayTypeP(adatum);
                numkeys = ARR_DIMS(arr)[0];
-               info->conkeys = (int*)palloc0(numkeys * sizeof(int));
-
+               info->conkeys = (int*)palloc(numkeys * sizeof(int));
                for (i = 0; i < numkeys; i++)
                        info->conkeys[i] = ((int16 *) ARR_DATA_PTR(arr))[i];
 
@@ -445,9 +447,8 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
                Assert(!isnull);
 
                arr = DatumGetArrayTypeP(adatum);
-               numkeys = ARR_DIMS(arr)[0];
-               info->confkeys = (int*)palloc0(numkeys * sizeof(int));
-
+               Assert(numkeys == ARR_DIMS(arr)[0]);
+               info->confkeys = (int*)palloc(numkeys * sizeof(int));
                for (i = 0; i < numkeys; i++)
                        info->confkeys[i] = ((int16 *) ARR_DATA_PTR(arr))[i];
 
@@ -457,9 +458,8 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
                Assert(!isnull);
 
                arr = DatumGetArrayTypeP(adatum);
-               numkeys = ARR_DIMS(arr)[0];
-               info->conpfeqop = (Oid*)palloc0(numkeys * sizeof(Oid));
-
+               Assert(numkeys == ARR_DIMS(arr)[0]);
+               info->conpfeqop = (Oid*)palloc(numkeys * sizeof(Oid));
                for (i = 0; i < numkeys; i++)
                        info->conpfeqop[i] = ((Oid *) ARR_DATA_PTR(arr))[i];
 
@@ -467,7 +467,7 @@ get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent,
 
                ReleaseSysCache(htup);
 
-               fkinfos = lcons(info, fkinfos);
+               fkinfos = lappend(fkinfos, info);
        }
 
        list_free(fkoidlist);