8000 Prevent access of uninitialized memory in radix tree nodes · postgres/postgres@fd49e8f · GitHub
[go: up one dir, main page]

Skip to content
{"payload":{"commit":{"oid":"fd49e8f32325c675d9bb6e26fcdbe9754249932f","url":"/postgres/postgres/commit/fd49e8f32325c675d9bb6e26fcdbe9754249932f","authoredDate":"2024-06-21T14:59:11.000+07:00","committedDate":"2024-06-21T17:29:39.000+07:00","shortMessage":null,"shortMessageMarkdown":"\u003cdiv\u003ePrevent access of uninitialized memory in radix tree nodes\u003c/div\u003e","shortMessageMarkdownLink":null,"bodyMessageHtml":"RT_NODE_16_SEARCH_EQ() performs comparisions using vector registers\non x64-64 and aarch64. We apply a mask to the resulting bitfield\nto eliminate irrelevant bits that may be set. This ensures correct\nbehavior, but Valgrind complains of the partially-uninitialised\nvalues. So far the warnings have only occurred on aarch64, which\nexplains why this hasn't been seen earlier.\n\nTo fix this warning, initialize the whole fixed-sized part of the nodes\nupon allocation, rather than just do the minimum initialization to\nfunction correctly. The initialization for node48 is a bit different\nin that the 256-byte slot index array must be populated with \"invalid\nindex\" rather than zero. Experimentation has shown that compilers\ntend to emit code that uselessly memsets that array twice. To avoid\npessimizing this path, swap the order of the slot_idxs[] and isset[]\narrays so we can initialize with two non-overlapping memset calls.\n\nReported by Tomas Vondra\nAnalysis and patch by Tom Lane, reviewed by Masahiko Sawada. I\ninvestigated the behavior of memset calls to overlapping regions,\nleading to the above tweaks to node48 as discussed in the thread.\n\nDiscussion: \u003ca href=\"https://postgr.es/m/120c63ad-3d12-415f-a7bf-3da451c31bf6%40enterprisedb.com\" rel=\"nofollow\"\u003ehttps://postgr.es/m/120c63ad-3d12-415f-a7bf-3da451c31bf6%40enterprisedb.com\u003c/a\u003e","authors":[{"login":"j-naylor","displayName":"John Naylor","avatarUrl":"https://avatars.githubusercontent.com/u/100744591?v=4","path":"/j-naylor","isGitHub":false}],"committerAttribution":false,"committer":{"login":"j-naylor","displayName":"John Naylor","avatarUrl":"https://avatars.githubusercontent.com/u/100744591?v=4","path":"/j-naylor","isGitHub":false},"parents":["c5c82123d3050c3a5eef0f51e9783f1cc5004ba0"],"globalRelayId":"C_kwDOAA4m0toAKGZkNDllOGYzMjMyNWM2NzVkOWJiNmUyNmZjZGJlOTc1NDI0OTkzMmY","sha1":"c5c82123d3050c3a5eef0f51e9783f1cc5004ba0","sha2":"fd49e8f32325c675d9bb6e26fcdbe9754249932f"},"currentUser":null,"repo":{"id":927442,"defaultBranch":"master","name":"postgres","ownerLogin":"postgres","currentUserCanPush":false,"isFork":false,"isEmpty":false,"createdAt":"2010-09-21T11:35:45.000Z","ownerAvatar":"https://avatars.githubusercontent.com/u/177543?v=4","public":true,"private":false,"isOrgOwned":true},"diffEntryData":[{"diffLines":[{"stylingDirective":null,"type":"HUNK","blobLineNumber":540,"text":"@@ -541,15 +541,19 @@ typedef struct RT_NODE_48","html":"@@ -541,15 +541,19 @@ typedef struct RT_NODE_48","displayNoNewLineWarning":false,"position":0,"left":540,"right":540},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":541,"text":" {","html":" {","displayNoNewLineWarning":false,"position":1,"left":541,"right":541},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":542,"text":" \tRT_NODE\t\tbase;","html":" \t\u003cspan class=pl-smi\u003eRT_NODE\u003c/span\u003e\t\t\u003cspan class=pl-c1\u003ebase\u003c/span\u003e;","displayNoNewLineWarning":false,"position":2,"left":542,"right":542},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":543,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":3,"left":543,"right":543},{"stylingDirective":null,"type":"DELETION","blobLineNumber":544,"text":"-\t/* The index of slots for each fanout */","html":"-\t\u003cspan class=pl-c\u003e/* The index of slots for each fanout */\u003c/span\u003e","displayNoNewLineWarning":false,"position":4,"left":544,"right":543},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":544,"text":"+\t/* bitmap to track which slots are in use */","html":"+\t\u003cspan class=pl-c\u003e/* bitmap to track which slots are in use */\u003c/span\u003e","displayNoNewLineWarning":false,"position":5,"left":544,"right":544},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":545,"text":"+\tbitmapword\tisset[RT_BM_IDX(RT_FANOUT_48_MAX)];","html":"+\t\u003cspan class=pl-smi\u003ebitmapword\u003c/span\u003e\t\u003cspan class=pl-c1\u003eisset\u003c/span\u003e[\u003cspan class=pl-en\u003eRT_BM_IDX\u003c/span\u003e(\u003cspan class=pl-c1\u003eRT_FANOUT_48_MAX\u003c/span\u003e)];","displayNoNewLineWarning":false,"position":6,"left":544,"right":545},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":546,"text":"+","html":"+","displayNoNewLineWarning":false,"position":7,"left":544,"right":546},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":547,"text":"+\t/*","html":"+\t\u003cspan class=pl-c\u003e/*\u003c/span\u003e","displayNoNewLineWarning":false,"position":8,"left":544,"right":547},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":548,"text":"+\t * Lookup table for indexes into the children[] array. We make this the","html":"+\u003cspan class=pl-c\u003e\t * Lookup table for indexes into the children[] array. We make this the\u003c/span\u003e","displayNoNewLineWarning":false,"position":9,"left":544,"right":548},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":549,"text":"+\t * last fixed-size member so that it's convenient to memset separately","html":"+\u003cspan class=pl-c\u003e\t * last fixed-size member so that it\u0026#39;s convenient to memset separately\u003c/span\u003e","displayNoNewLineWarning":false,"position":10,"left":544,"right":549},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":550,"text":"+\t * from the previous members.","html":"+\u003cspan class=pl-c\u003e\t * from the previous members.\u003c/span\u003e","displayNoNewLineWarning":false,"position":11,"left":544,"right":550},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":551,"text":"+\t */","html":"+\u003cspan class=pl-c\u003e\t */\u003c/span\u003e","displayNoNewLineWarning":false,"position":12,"left":544,"right":551},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":552,"text":" \tuint8\t\tslot_idxs[RT_NODE_MAX_SLOTS];","html":" \t\u003cspan class=pl-smi\u003euint8\u003c/span\u003e\t\t\u003cspan class=pl-c1\u003eslot_idxs\u003c/span\u003e[\u003cspan class=pl-c1\u003eRT_NODE_MAX_SLOTS\u003c/span\u003e];","displayNoNewLineWarning":false,"position":13,"left":545,"right":552},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":553,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":14,"left":546,"right":553},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":554,"text":" /* Invalid index */","html":" \u003cspan class=pl-c\u003e/* Invalid index */\u003c/span\u003e","displayNoNewLineWarning":false,"position":15,"left":547,"right":554},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":555,"text":" #define RT_INVALID_SLOT_IDX\t0xFF","html":" \u003cspan class=pl-k\u003e#define\u003c/span\u003e \u003cspan class=pl-c1\u003eRT_INVALID_SLOT_IDX\u003c/span\u003e\t0xFF","displayNoNewLineWarning":false,"position":16,"left":548,"right":555},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":556,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":17,"left":549,"right":556},{"stylingDirective":null,"type":"DELETION","blobLineNumber":550,"text":"-\t/* bitmap to track which slots are in use */","html":"-\t\u003cspan class=pl-c\u003e/* bitmap to track which slots are in use */\u003c/span\u003e","displayNoNewLineWarning":false,"position":18,"left":550,"right":556},{"stylingDirective":null,"type":"DELETION","blobLineNumber":551,"text":"-\tbitmapword\tisset[RT_BM_IDX(RT_FANOUT_48_MAX)];","html":"-\t\u003cspan class=pl-smi\u003ebitmapword\u003c/span\u003e\t\u003cspan class=pl-c1\u003eisset\u003c/span\u003e[\u003cspan class=pl-en\u003eRT_BM_IDX\u003c/span\u003e(\u003cspan class=pl-c1\u003eRT_FANOUT_48_MAX\u003c/span\u003e)];","displayNoNewLineWarning":false,"position":19,"left":551,"right":556},{"stylingDirective":null,"type":"DELETION","blobLineNumber":552,"text":"-","html":"-","displayNoNewLineWarning":false,"position":20,"left":552,"right":556},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":557,"text":" \t/* number of children depends on size class */","html":" \t\u003cspan class=pl-c\u003e/* number of children depends on size class */\u003c/span\u003e","displayNoNewLineWarning":false,"position":21,"left":553,"right":557},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":558,"text":" \tRT_PTR_ALLOC children[FLEXIBLE_ARRAY_MEMBER];","html":" \t\u003cspan class=pl-smi\u003eRT_PTR_ALLOC\u003c/span\u003e \u003cspan class=pl-c1\u003echildren\u003c/span\u003e[\u003cspan class=pl-c1\u003eFLEXIBLE_ARRAY_MEMBER\u003c/span\u003e];","displayNoNewLineWarning":false,"position":22,"left":554,"right":558},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":559,"text":" }\t\t\tRT_NODE_48;","html":" }\t\t\t\u003cspan class=pl-smi\u003eRT_NODE_48\u003c/span\u003e;","displayNoNewLineWarning":false,"position":23,"left":555,"right":559},{"stylingDirective":null,"type":"HUNK","blobLineNumber":848,"text":"@@ -845,27 +849,25 @@ RT_ALLOC_NODE(RT_RADIX_TREE * tree, const uint8 kind, const RT_SIZE_CLASS size_c","html":"@@ -845,27 +849,25 @@ RT_ALLOC_NODE(RT_RADIX_TREE * tree, const uint8 kind, const RT_SIZE_CLASS size_c","displayNoNewLineWarning":false,"position":24,"left":844,"right":848},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":849,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":25,"left":845,"right":849},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":850,"text":" \t/* initialize contents */","html":" \t\u003cspan class=pl-c\u003e/* initialize contents */\u003c/span\u003e","displayNoNewLineWarning":false,"position":26,"left":846,"right":850},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":851,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":27,"left":847,"right":851},{"stylingDirective":null,"type":"DELETION","blobLineNumber":848,"text":"-\tmemset(node, 0, sizeof(RT_NODE));","html":"-\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003enode\u003c/span\u003e, \u003cspan class=pl-c1\u003e0\u003c/span\u003e, \u003cspan class=pl-k\u003esizeof\u003c/span\u003e(\u003cspan class=pl-c1\u003eRT_NODE\u003c/span\u003e));","displayNoNewLineWarning":false,"position":28,"left":848,"right":851},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":852,"text":" \tswitch (kind)","html":" \t\u003cspan class=pl-k\u003eswitch\u003c/span\u003e (\u003cspan class=pl-s1\u003ekind\u003c/span\u003e)","displayNoNewLineWarning":false,"position":29,"left":849,"right":852},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":853,"text":" \t{","html":" \t{","displayNoNewLineWarning":false,"position":30,"left":850,"right":853},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":854,"text":" \t\tcase RT_NODE_KIND_4:","html":" \t\t\u003cspan class=pl-k\u003ecase\u003c/span\u003e \u003cspan class=pl-c1\u003eRT_NODE_KIND_4\u003c/span\u003e:","displayNoNewLineWarning":false,"position":31,"left":851,"right":854},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":855,"text":"+\t\t\tmemset(node, 0, offsetof(RT_NODE_4, children));","html":"+\t\t\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003enode\u003c/span\u003e, \u003cspan class=pl-c1\u003e0\u003c/span\u003e, offsetof(\u003cspan class=pl-smi\u003eRT_NODE_4\u003c/span\u003e, \u003cspan class=pl-c1\u003echildren\u003c/span\u003e));","displayNoNewLineWarning":false,"position":32,"left":851,"right":855},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":856,"text":"+\t\t\tbreak;","html":"+\t\t\t\u003cspan class=pl-k\u003ebreak\u003c/span\u003e;","displayNoNewLineWarning":false,"position":33,"left":851,"right":856},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":857,"text":" \t\tcase RT_NODE_KIND_16:","html":" \t\t\u003cspan class=pl-k\u003ecase\u003c/span\u003e \u003cspan class=pl-c1\u003eRT_NODE_KIND_16\u003c/span\u003e:","displayNoNewLineWarning":false,"position":34,"left":852,"right":857},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":858,"text":"+\t\t\tmemset(node, 0, offsetof(RT_NODE_16, children));","html":"+\t\t\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003enode\u003c/span\u003e, \u003cspan class=pl-c1\u003e0\u003c/span\u003e, offsetof(\u003cspan class=pl-smi\u003eRT_NODE_16\u003c/span\u003e, \u003cspan class=pl-c1\u003echildren\u003c/span\u003e));","displayNoNewLineWarning":false,"position":35,"left":852,"right":858},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":859,"text":" \t\t\tbreak;","html":" \t\t\t\u003cspan class=pl-k\u003ebreak\u003c/span\u003e;","displayNoNewLineWarning":false,"position":36,"left":853,"right":859},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":860,"text":" \t\tcase RT_NODE_KIND_48:","html":" \t\t\u003cspan class=pl-k\u003ecase\u003c/span\u003e \u003cspan class=pl-c1\u003eRT_NODE_KIND_48\u003c/span\u003e:","displayNoNewLineWarning":false,"position":37,"left":854,"right":860},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":861,"text":" \t\t\t{","html":" \t\t\t{","displayNoNewLineWarning":false,"position":38,"left":855,"right":861},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":862,"text":" \t\t\t\tRT_NODE_48 *n48 = (RT_NODE_48 *) node;","html":" \t\t\t\t\u003cspan class=pl-smi\u003eRT_NODE_48\u003c/span\u003e \u003cspan class=pl-c1\u003e*\u003c/span\u003e\u003cspan class=pl-s1\u003en48\u003c/span\u003e \u003cspan class=pl-c1\u003e=\u003c/span\u003e (\u003cspan class=pl-smi\u003eRT_NODE_48\u003c/span\u003e \u003cspan class=pl-c1\u003e*\u003c/span\u003e) \u003cspan class=pl-s1\u003enode\u003c/span\u003e;","displayNoNewLineWarning":false,"position":39,"left":856,"right":862},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":863,"text":" ","html":"\u003cbr\u003e","displayNoNewLineWarning":false,"position":40,"left":857,"right":863},{"stylingDirective":null,"type":"DELETION","blobLineNumber":858,"text":"-\t\t\t\tmemset(n48-\u003eisset, 0, sizeof(n48-\u003eisset));","html":"-\t\t\t\t\u003cspan class=\"pl-en\"\u003ememset\u003c/span\u003e(\u003cspan class=\"pl-s1\"\u003en48\u003c/span\u003e\u003cspan class=\"pl-c1 x x-first\"\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=\"pl-c1 x x-last\"\u003eisset\u003c/span\u003e, \u003cspan class=\"pl-c1\"\u003e0\u003c/span\u003e, \u003cspan class=\"pl-k x x-first\"\u003esizeof\u003c/span\u003e\u003cspan class=\"x\"\u003e(\u003c/span\u003e\u003cspan class=\"pl-s1 x\"\u003en48\u003c/span\u003e\u003cspan class=\"pl-c1 x\"\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=\"pl-c1 x x-last\"\u003eisset\u003c/span\u003e));","displayNoNewLineWarning":false,"position":41,"left":858,"right":863},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":864,"text":"+\t\t\t\tmemset(n48, 0, offsetof(RT_NODE_48, slot_idxs));","html":"+\t\t\t\t\u003cspan class=\"pl-en\"\u003ememset\u003c/span\u003e(\u003cspan class=\"pl-s1\"\u003en48\u003c/span\u003e, \u003cspan class=\"pl-c1\"\u003e0\u003c/span\u003e, \u003cspan class=\"x x-first\"\u003eoffsetof(\u003c/span\u003e\u003cspan class=\"pl-smi x\"\u003eRT_NODE_48\u003c/span\u003e\u003cspan class=\"x\"\u003e, \u003c/span\u003e\u003cspan class=\"pl-c1 x x-last\"\u003eslot_idxs\u003c/span\u003e));","displayNoNewLineWarning":false,"position":42,"left":858,"right":864},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":865,"text":" \t\t\t\tmemset(n48-\u003eslot_idxs, RT_INVALID_SLOT_IDX, sizeof(n48-\u003eslot_idxs));","html":" \t\t\t\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003en48\u003c/span\u003e\u003cspan class=pl-c1\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=pl-c1\u003eslot_idxs\u003c/span\u003e, \u003cspan class=pl-c1\u003eRT_INVALID_SLOT_IDX\u003c/span\u003e, \u003cspan class=pl-k\u003esizeof\u003c/span\u003e(\u003cspan class=pl-s1\u003en48\u003c/span\u003e\u003cspan class=pl-c1\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=pl-c1\u003eslot_idxs\u003c/span\u003e));","displayNoNewLineWarning":false,"position":43,"left":859,"right":865},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":866,"text":" \t\t\t\tbreak;","html":" \t\t\t\t\u003cspan class=pl-k\u003ebreak\u003c/span\u003e;","displayNoNewLineWarning":false,"position":44,"left":860,"right":866},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":867,"text":" \t\t\t}","html":" \t\t\t}","displayNoNewLineWarning":false,"position":45,"left":861,"right":867},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":868,"text":" \t\tcase RT_NODE_KIND_256:","html":" \t\t\u003cspan class=pl-k\u003ecase\u003c/span\u003e \u003cspan class=pl-c1\u003eRT_NODE_KIND_256\u003c/span\u003e:","displayNoNewLineWarning":false,"position":46,"left":862,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":863,"text":"-\t\t\t{","html":"-\t\t\t{","displayNoNewLineWarning":false,"position":47,"left":863,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":864,"text":"-\t\t\t\tRT_NODE_256 *n256 = (RT_NODE_256 *) node;","html":"-\t\t\t\t\u003cspan class=pl-smi\u003eRT_NODE_256\u003c/span\u003e \u003cspan class=pl-c1\u003e*\u003c/span\u003e\u003cspan class=pl-s1\u003en256\u003c/span\u003e \u003cspan class=pl-c1\u003e=\u003c/span\u003e (\u003cspan class=pl-smi\u003eRT_NODE_256\u003c/span\u003e \u003cspan class=pl-c1\u003e*\u003c/span\u003e) \u003cspan class=pl-s1\u003enode\u003c/span\u003e;","displayNoNewLineWarning":false,"position":48,"left":864,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":865,"text":"-","html":"-","displayNoNewLineWarning":false,"position":49,"left":865,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":866,"text":"-\t\t\t\tmemset(n256-\u003eisset, 0, sizeof(n256-\u003eisset));","html":"-\t\t\t\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003en256\u003c/span\u003e\u003cspan class=pl-c1\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=pl-c1\u003eisset\u003c/span\u003e, \u003cspan class=pl-c1\u003e0\u003c/span\u003e, \u003cspan class=pl-k\u003esizeof\u003c/span\u003e(\u003cspan class=pl-s1\u003en256\u003c/span\u003e\u003cspan class=pl-c1\u003e-\u0026gt;\u003c/span\u003e\u003cspan class=pl-c1\u003eisset\u003c/span\u003e));","displayNoNewLineWarning":false,"position":50,"left":866,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":867,"text":"-\t\t\t\tbreak;","html":"-\t\t\t\t\u003cspan class=pl-k\u003ebreak\u003c/span\u003e;","displayNoNewLineWarning":false,"position":51,"left":867,"right":868},{"stylingDirective":null,"type":"DELETION","blobLineNumber":868,"text":"-\t\t\t}","html":"-\t\t\t}","displayNoNewLineWarning":false,"position":52,"left":868,"right":868},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":869,"text":"+\t\t\tmemset(node, 0, offsetof(RT_NODE_256, children));","html":"+\t\t\t\u003cspan class=pl-en\u003ememset\u003c/span\u003e(\u003cspan class=pl-s1\u003enode\u003c/span\u003e, \u003cspan class=pl-c1\u003e0\u003c/span\u003e, offsetof(\u003cspan class=pl-smi\u003eRT_NODE_256\u003c/span\u003e, \u003cspan class=pl-c1\u003echildren\u003c/span\u003e));","displayNoNewLineWarning":false,"position":53,"left":868,"right":869},{"stylingDirective":null,"type":"ADDITION","blobLineNumber":870,"text":"+\t\t\tbreak;","html":"+\t\t\t\u003cspan class=pl-k\u003ebreak\u003c/span\u003e;","displayNoNewLineWarning":false,"position":54,"left":868,"right":870},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":871,"text":" \t\tdefault:","html":" \t\t\u003cspan class=pl-k\u003edefault\u003c/span\u003e:","displayNoNewLineWarning":false,"position":55,"left":869,"right":871},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":872,"text":" \t\t\tpg_unreachable();","html":" \t\t\t\u003cspan class=pl-en\u003epg_unreachable\u003c/span\u003e();","displayNoNewLineWarning":false,"position":56,"left":870,"right":872},{"stylingDirective":null,"type":"CONTEXT","blobLineNumber":873,"text":" \t}","html":" \t}","displayNoNewLineWarning":false,"position":57,"left":871,"right":873}],"diffNumber":0,"diffSize":"0 Bytes","isBinary":false,"isTooBig":false,"collapsed":false,"isSubmodule":false,"lineCount":3054,"linesChanged":26,"newTreeEntry":{"lineCount":3054,"path":"src/include/lib/radixtree.h","mode":100644,"isGenerated":false},"oldTreeEntry":{"lineCount":0,"path":"src/include/lib/radixtree.h","mode":100644},"linesAdded":14,"linesDeleted":12,"path":"src/include/lib/radixtree.h","pathDigest":"58083fb17dc7d5d3821337a4992f3b9d3173436fd7c5dc30a653966f8ee40500","status":"MODIFIED","truncatedReason":null,"oldOid":"c5c82123d3050c3a5eef0f51e9783f1cc5004ba0","newOid":"fd49e8f32325c675d9bb6e26fcdbe9754249932f","copilotChatReference":null,"deletedSha":"c5c82123d3050c3a5eef0f51e9783f1cc5004ba0","canToggleRichDiff":false,"defaultToRichDiff":false,"proseDifffHtml":null,"renderInfo":null,"dependencyDiffPath":null,"submodule":null}],"splitViewPreference":"unified","ignoreWhitespace":false,"repoOwnerGlobalRelayId":"MDEyOk9yZ2FuaXphdGlvbjE3NzU0Mw==","commentsPreference":"visible","diffLineSpacingPreference":"relaxed","useMonospaceFont":false,"pasteUrlLinkAsPlainText":false,"userNotices":[],"path":"/postgres/postgres/commit/fd49e8f32325c675d9bb6e26fcdbe9754249932f","fileTreeExpanded":true,"headerInfo":{"additions":14,"deletions":12,"filesChanged":1,"filesChangedString":"1"},"moreDiffsToLoad":false,"asyncDiffLoadInfo":{"startIndex":1,"truncated":false,"byteCount":1600,"lineShownCount":58},"commentInfo":{"canComment":false,"locked":false,"canLock":false,"repoArchived":false},"csrf_tokens":{"/users/diffview?diff=split":{"post":"lXJ0c9dkoD0e_mDxw4pkUctO7Lp_I7eKSjqBewg04JOjoxpXgz93NU70xtnGVhbafjd5uN7V-s3847-Y-BxaZg"},"/users/diffview?diff=unified":{"post":"NDVtosRRs7lDptnQgOgNjqcKTMM5kDVtPr-pg06s380C5AOGkApksROsf_iFNH8FEnPZwZhmeCqIZpdgvoRlOA"},"/notifications/thread":{"post":"7vy4og34AK-yQ2zqp0f8VHw1a5GWJIsoTyjl9qsFGaIoW-FsqJiYrNu9iFoQbPhIvzk1VaqNXvcZzUuECP160w"}}},"title":"Prevent access of uninitialized memory in radix tree nodes · postgres/postgres@fd49e8f","appPayload":{"helpUrl":"https://docs.github.com","findInDiffWorkerPath":"/assets-cdn/worker/find-in-diff-worker-2bfe39677d14.js","enabled_features":{"diff_ux_refresh_beta":false,"diff_inline_comments":true,"diff_ux_refresh_ssr_five":false,"diff_ux_refresh_ssr_ten":false,"react_diff_line_type_character_correction":true}}}

Commit fd49e8f

Browse files
committed
Prevent access of uninitialized memory in radix tree nodes
RT_NODE_16_SEARCH_EQ() performs comparisions using vector registers on x64-64 and aarch64. We apply a mask to the resulting bitfield to eliminate irrelevant bits that may be set. This ensures correct behavior, but Valgrind complains of the partially-uninitialised values. So far the warnings have only occurred on aarch64, which explains why this hasn't been seen earlier. To fix this warning, initialize the whole fixed-sized part of the nodes upon allocation, rather than just do the minimum initialization to function correctly. The initialization for node48 is a bit different in that the 256-byte slot index array must be populated with "invalid index" rather than zero. Experimentation has shown that compilers tend to emit code that uselessly memsets that array twice. To avoid pessimizing this path, swap the order of the slot_idxs[] and isset[] arrays so we can initialize with two non-overlapping memset calls. Reported by Tomas Vondra Analysis and patch by Tom Lane, reviewed by Masahiko Sawada. I investigated the behavior of memset calls to overlapping regions, leading to the above tweaks to node48 as discussed in the thread. Discussion: https://postgr.es/m/120c63ad-3d12-415f-a7bf-3da451c31bf6%40enterprisedb.com
1 parent c5c8212 commit fd49e8f

File tree

1 file changed

+14
-12
lines changed

1 file changed

+14
-12
lines changed

src/include/lib/radixtree.h

Lines changed: 14 additions & 12 deletions
862
Original file line numberDiff line numberDiff line change
@@ -541,15 +541,19 @@ typedef struct RT_NODE_48
541541
{
542542
RT_NODE base;
543543

544-
/* The index of slots for each fanout */
544+
/* bitmap to track which slots are in use */
545+
bitmapword isset[RT_BM_IDX(RT_FANOUT_48_MAX)];
546+
547+
/*
548+
* Lookup table for indexes into the children[] array. We make this the
549+
* last fixed-size member so that it's convenient to memset separately
550+
* from the previous members.
551+
*/
545552
uint8 slot_idxs[RT_NODE_MAX_SLOTS];
546553

547554
/* Invalid index */
548555
#define RT_INVALID_SLOT_IDX 0xFF
549556

550-
/* bitmap to track which slots are in use */
551-
bitmapword isset[RT_BM_IDX(RT_FANOUT_48_MAX)];
552-
553557
/* number of children depends on size class */
554558
RT_PTR_ALLOC children[FLEXIBLE_ARRAY_MEMBER];
555559
} RT_NODE_48;
@@ -845,27 +849,25 @@ RT_ALLOC_NODE(RT_RADIX_TREE * tree, const uint8 kind, const RT_SIZE_CLASS size_c
845849

846850
/* initialize contents */
847851

848-
memset(node, 0, sizeof(RT_NODE));
849852
switch (kind)
850853
{
851854
case RT_NODE_KIND_4:
855+
memset(node, 0, offsetof(RT_NODE_4, children));
856+
break;
852857
case RT_NODE_KIND_16:
858+
memset(node, 0, offsetof(RT_NODE_16, children));
853859
break;
854860
case RT_NODE_KIND_48:
855861
{
856862
RT_NODE_48 *n48 = (RT_NODE_48 *) node;
857863

858-
memset(n48->isset, 0, sizeof(n48->isset));
864+
memset(n48, 0, offsetof(RT_NODE_48, slot_idxs));
859865
memset(n48->slot_idxs, RT_INVALID_SLOT_IDX, sizeof(n48->slot_idxs));
860866
break;
861867
}
868
case RT_NODE_KIND_256:
863-
{
864-
RT_NODE_256 *n256 = (RT_NODE_256 *) node;
865-
866-
memset(n256->isset, 0, sizeof(n256->isset));
867-
break;
868-
}
869+
memset(node, 0, offsetof(RT_NODE_256, children));
870+
break;
869871
default:
870872
pg_unreachable();
871873
}

0 commit comments

Comments
 (0)
0