]> git.ipfire.org Git - people/jschlag/ipfire-2.x.git/blame - src/patches/glibc/glibc-rh1074353.patch
glibc: new RHEL6 patches / fix CVE-2015-7547 and more
[people/jschlag/ipfire-2.x.git] / src / patches / glibc / glibc-rh1074353.patch
CommitLineData
bb330e25
AF
1commit bc8f194c8c29e46e8ee4034f06e46988dfff38f7
2Author: Siddhesh Poyarekar <siddhesh@redhat.com>
3Date: Wed Apr 30 12:00:39 2014 +0530
4
5 Initialize all of datahead structure in nscd (BZ #16791)
6
7 The datahead structure has an unused padding field that remains
8 uninitialized. Valgrind prints out a warning for it on querying a
9 netgroups entry. This is harmless, but is a potential data leak since
10 it would result in writing out an uninitialized byte to the cache
11 file. Besides, this happens only when there is a cache miss, so we're
12 not adding computation to any fast path.
13
14commit 1cdeb2372ddecac0dfe0c132a033e9590ffa07d2
15Author: Siddhesh Poyarekar <siddhesh@redhat.com>
16Date: Wed Apr 30 11:57:09 2014 +0530
17
18 Consolidate code to initialize nscd dataset header
19
20 This patch consolidates the code to initialize the header of a dataset
21 into a single set of functions (one for positive and another for
22 negative datasets) primarily to reduce repetition of code. The
23 secondary reason is to simplify Patch 2/2 which fixes the problem of
24 an uninitialized byte in the header by initializing an unused field in
25 the structure and hence preventing a possible data leak into the cache
26 file.
27
28diff --git a/nscd/aicache.c b/nscd/aicache.c
29index 98d40a1..d7966bd 100644
30--- a/nscd/aicache.c
31+++ b/nscd/aicache.c
32@@ -383,17 +383,12 @@ addhstaiX (struct database_dyn *db, int fd, request_header *req,
33 cp = family;
34 }
35
36- /* Fill in the rest of the dataset. */
37- dataset->head.allocsize = total + req->key_len;
38- dataset->head.recsize = total - offsetof (struct dataset, resp);
39- dataset->head.notfound = false;
40- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
41- dataset->head.usable = true;
42-
43- /* Compute the timeout time. */
44- dataset->head.ttl = ttl == INT32_MAX ? db->postimeout : ttl;
45- timeout = dataset->head.timeout = time (NULL) + dataset->head.ttl;
46+ timeout = datahead_init_pos (&dataset->head, total + req->key_len,
47+ total - offsetof (struct dataset, resp),
48+ he == NULL ? 0 : dh->nreloads + 1,
49+ ttl == INT32_MAX ? db->postimeout : ttl);
50
51+ /* Fill in the rest of the dataset. */
52 dataset->resp.version = NSCD_VERSION;
53 dataset->resp.found = 1;
54 dataset->resp.naddrs = naddrs;
55@@ -528,15 +523,9 @@ next_nip:
56 else if ((dataset = mempool_alloc (db, (sizeof (struct dataset)
57 + req->key_len), 1)) != NULL)
58 {
59- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
60- dataset->head.recsize = total;
61- dataset->head.notfound = true;
62- dataset->head.nreloads = 0;
63- dataset->head.usable = true;
64-
65- /* Compute the timeout time. */
66- timeout = dataset->head.timeout = time (NULL) + db->negtimeout;
67- dataset->head.ttl = db->negtimeout;
68+ timeout = datahead_init_neg (&dataset->head,
69+ sizeof (struct dataset) + req->key_len,
70+ total, db->negtimeout);
71
72 /* This is the reply. */
73 memcpy (&dataset->resp, &notfound, total);
74diff --git a/nscd/grpcache.c b/nscd/grpcache.c
75index b5a33eb..df59fa7 100644
76--- a/nscd/grpcache.c
77+++ b/nscd/grpcache.c
78@@ -128,14 +128,10 @@ cache_addgr (struct database_dyn *db, int fd, request_header *req,
79 }
80 else if ((dataset = mempool_alloc (db, sizeof (struct dataset) + req->key_len, 1)) != NULL)
81 {
82- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
83- dataset->head.recsize = total;
84- dataset->head.notfound = true;
85- dataset->head.nreloads = 0;
86- dataset->head.usable = true;
87-
88- /* Compute the timeout time. */
89- timeout = dataset->head.timeout = t + db->negtimeout;
90+ timeout = datahead_init_neg (&dataset->head,
91+ (sizeof (struct dataset)
92+ + req->key_len), total,
93+ db->negtimeout);
94
95 /* This is the reply. */
96 memcpy (&dataset->resp, &notfound, total);
97@@ -232,14 +228,10 @@ cache_addgr (struct database_dyn *db, int fd, request_header *req,
98 dataset_temporary = true;
99 }
100
101- dataset->head.allocsize = total + n;
102- dataset->head.recsize = total - offsetof (struct dataset, resp);
103- dataset->head.notfound = false;
104- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
105- dataset->head.usable = true;
106-
107- /* Compute the timeout time. */
108- timeout = dataset->head.timeout = t + db->postimeout;
109+ timeout = datahead_init_pos (&dataset->head, total + n,
110+ total - offsetof (struct dataset, resp),
111+ he == NULL ? 0 : dh->nreloads + 1,
112+ db->postimeout);
113
114 dataset->resp.version = NSCD_VERSION;
115 dataset->resp.found = 1;
116diff --git a/nscd/hstcache.c b/nscd/hstcache.c
117index a79b67a..d4f1ad2 100644
118--- a/nscd/hstcache.c
119+++ b/nscd/hstcache.c
120@@ -152,15 +152,11 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req,
121 else if ((dataset = mempool_alloc (db, (sizeof (struct dataset)
122 + req->key_len), 1)) != NULL)
123 {
124- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
125- dataset->head.recsize = total;
126- dataset->head.notfound = true;
127- dataset->head.nreloads = 0;
128- dataset->head.usable = true;
129-
130- /* Compute the timeout time. */
131- dataset->head.ttl = ttl == INT32_MAX ? db->negtimeout : ttl;
132- timeout = dataset->head.timeout = t + dataset->head.ttl;
133+ timeout = datahead_init_neg (&dataset->head,
134+ (sizeof (struct dataset)
135+ + req->key_len), total,
136+ (ttl == INT32_MAX
137+ ? db->negtimeout : ttl));
138
139 /* This is the reply. */
140 memcpy (&dataset->resp, resp, total);
141@@ -257,15 +253,10 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req,
142 alloca_used = true;
143 }
144
145- dataset->head.allocsize = total + req->key_len;
146- dataset->head.recsize = total - offsetof (struct dataset, resp);
147- dataset->head.notfound = false;
148- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
149- dataset->head.usable = true;
150-
151- /* Compute the timeout time. */
152- dataset->head.ttl = ttl == INT32_MAX ? db->postimeout : ttl;
153- timeout = dataset->head.timeout = t + dataset->head.ttl;
154+ timeout = datahead_init_pos (&dataset->head, total + req->key_len,
155+ total - offsetof (struct dataset, resp),
156+ he == NULL ? 0 : dh->nreloads + 1,
157+ ttl == INT32_MAX ? db->postimeout : ttl);
158
159 dataset->resp.version = NSCD_VERSION;
160 dataset->resp.found = 1;
161diff --git a/nscd/initgrcache.c b/nscd/initgrcache.c
162index 1bf9f0d..361319f 100644
163--- a/nscd/initgrcache.c
164+++ b/nscd/initgrcache.c
165@@ -213,14 +213,10 @@ addinitgroupsX (struct database_dyn *db, int fd, request_header *req,
166 else if ((dataset = mempool_alloc (db, (sizeof (struct dataset)
167 + req->key_len), 1)) != NULL)
168 {
169- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
170- dataset->head.recsize = total;
171- dataset->head.notfound = true;
172- dataset->head.nreloads = 0;
173- dataset->head.usable = true;
174-
175- /* Compute the timeout time. */
176- timeout = dataset->head.timeout = time (NULL) + db->negtimeout;
177+ timeout = datahead_init_neg (&dataset->head,
178+ (sizeof (struct dataset)
179+ + req->key_len), total,
180+ db->negtimeout);
181
182 /* This is the reply. */
183 memcpy (&dataset->resp, &notfound, total);
184@@ -276,14 +272,10 @@ addinitgroupsX (struct database_dyn *db, int fd, request_header *req,
185 alloca_used = true;
186 }
187
188- dataset->head.allocsize = total + req->key_len;
189- dataset->head.recsize = total - offsetof (struct dataset, resp);
190- dataset->head.notfound = false;
191- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
192- dataset->head.usable = true;
193-
194- /* Compute the timeout time. */
195- timeout = dataset->head.timeout = time (NULL) + db->postimeout;
196+ timeout = datahead_init_pos (&dataset->head, total + req->key_len,
197+ total - offsetof (struct dataset, resp),
198+ he == NULL ? 0 : dh->nreloads + 1,
199+ db->postimeout);
200
201 dataset->resp.version = NSCD_VERSION;
202 dataset->resp.found = 1;
203diff --git a/nscd/netgroupcache.c b/nscd/netgroupcache.c
204index 820d823..b3d40e9 100644
205--- a/nscd/netgroupcache.c
206+++ b/nscd/netgroupcache.c
207@@ -90,15 +90,9 @@ do_notfound (struct database_dyn *db, int fd, request_header *req,
208 /* If we cannot permanently store the result, so be it. */
209 if (dataset != NULL)
210 {
211- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
212- dataset->head.recsize = total;
213- dataset->head.notfound = true;
214- dataset->head.nreloads = 0;
215- dataset->head.usable = true;
216-
217- /* Compute the timeout time. */
218- timeout = dataset->head.timeout = time (NULL) + db->negtimeout;
219- dataset->head.ttl = db->negtimeout;
220+ timeout = datahead_init_neg (&dataset->head,
221+ sizeof (struct dataset) + req->key_len,
222+ total, db->negtimeout);
223
224 /* This is the reply. */
225 memcpy (&dataset->resp, &notfound, total);
226@@ -359,13 +353,10 @@ addgetnetgrentX (struct database_dyn *db, int fd, request_header *req,
227
228 /* Fill in the dataset. */
229 dataset = (struct dataset *) buffer;
230- dataset->head.allocsize = total + req->key_len;
231- dataset->head.recsize = total - offsetof (struct dataset, resp);
232- dataset->head.notfound = false;
233- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
234- dataset->head.usable = true;
235- dataset->head.ttl = db->postimeout;
236- timeout = dataset->head.timeout = time (NULL) + dataset->head.ttl;
237+ timeout = datahead_init_pos (&dataset->head, total + req->key_len,
238+ total - offsetof (struct dataset, resp),
239+ he == NULL ? 0 : dh->nreloads + 1,
240+ db->postimeout);
241
242 dataset->resp.version = NSCD_VERSION;
243 dataset->resp.found = 1;
244@@ -541,12 +532,12 @@ addinnetgrX (struct database_dyn *db, int fd, request_header *req,
245 dataset = &dataset_mem;
246 }
247
248- dataset->head.allocsize = sizeof (*dataset) + req->key_len;
249- dataset->head.recsize = sizeof (innetgroup_response_header);
250+ datahead_init_pos (&dataset->head, sizeof (*dataset) + req->key_len,
251+ sizeof (innetgroup_response_header),
252+ he == NULL ? 0 : dh->nreloads + 1, result->head.ttl);
253+ /* Set the notfound status and timeout based on the result from
254+ getnetgrent. */
255 dataset->head.notfound = result->head.notfound;
256- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
257- dataset->head.usable = true;
258- dataset->head.ttl = result->head.ttl;
259 dataset->head.timeout = timeout;
260
261 dataset->resp.version = NSCD_VERSION;
262diff --git a/nscd/nscd-client.h b/nscd/nscd-client.h
263index 98f77e7..ee16df6 100644
264--- a/nscd/nscd-client.h
265+++ b/nscd/nscd-client.h
266@@ -236,6 +236,48 @@ struct datahead
267 } data[0];
268 };
269
270+static inline time_t
271+datahead_init_common (struct datahead *head, nscd_ssize_t allocsize,
272+ nscd_ssize_t recsize, uint32_t ttl)
273+{
274+ /* Initialize so that we don't write out junk in uninitialized data to the
275+ cache. */
276+ memset (head, 0, sizeof (*head));
277+
278+ head->allocsize = allocsize;
279+ head->recsize = recsize;
280+ head->usable = true;
281+
282+ head->ttl = ttl;
283+
284+ /* Compute and return the timeout time. */
285+ return head->timeout = time (NULL) + ttl;
286+}
287+
288+static inline time_t
289+datahead_init_pos (struct datahead *head, nscd_ssize_t allocsize,
290+ nscd_ssize_t recsize, uint8_t nreloads, uint32_t ttl)
291+{
292+ time_t ret = datahead_init_common (head, allocsize, recsize, ttl);
293+
294+ head->notfound = false;
295+ head->nreloads = nreloads;
296+
297+ return ret;
298+}
299+
300+static inline time_t
301+datahead_init_neg (struct datahead *head, nscd_ssize_t allocsize,
302+ nscd_ssize_t recsize, uint32_t ttl)
303+{
304+ time_t ret = datahead_init_common (head, allocsize, recsize, ttl);
305+
306+ /* We don't need to touch nreloads here since it is set to our desired value
307+ (0) when we clear the structure. */
308+ head->notfound = true;
309+
310+ return ret;
311+}
312
313 /* Structure for one hash table entry. */
314 struct hashentry
315diff --git a/nscd/pwdcache.c b/nscd/pwdcache.c
316index fa355c3..41c245b 100644
317--- a/nscd/pwdcache.c
318+++ b/nscd/pwdcache.c
319@@ -135,14 +135,10 @@ cache_addpw (struct database_dyn *db, int fd, request_header *req,
320 else if ((dataset = mempool_alloc (db, (sizeof (struct dataset)
321 + req->key_len), 1)) != NULL)
322 {
323- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
324- dataset->head.recsize = total;
325- dataset->head.notfound = true;
326- dataset->head.nreloads = 0;
327- dataset->head.usable = true;
328-
329- /* Compute the timeout time. */
330- timeout = dataset->head.timeout = t + db->negtimeout;
331+ timeout = datahead_init_neg (&dataset->head,
332+ (sizeof (struct dataset)
333+ + req->key_len), total,
334+ db->negtimeout);
335
336 /* This is the reply. */
337 memcpy (&dataset->resp, &notfound, total);
338@@ -215,14 +211,10 @@ cache_addpw (struct database_dyn *db, int fd, request_header *req,
339 alloca_used = true;
340 }
341
342- dataset->head.allocsize = total + n;
343- dataset->head.recsize = total - offsetof (struct dataset, resp);
344- dataset->head.notfound = false;
345- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
346- dataset->head.usable = true;
347-
348- /* Compute the timeout time. */
349- timeout = dataset->head.timeout = t + db->postimeout;
350+ timeout = datahead_init_pos (&dataset->head, total + n,
351+ total - offsetof (struct dataset, resp),
352+ he == NULL ? 0 : dh->nreloads + 1,
353+ db->postimeout);
354
355 dataset->resp.version = NSCD_VERSION;
356 dataset->resp.found = 1;
357diff --git a/nscd/servicescache.c b/nscd/servicescache.c
358index 12ce9b2..95bdcfe 100644
359--- a/nscd/servicescache.c
360+++ b/nscd/servicescache.c
361@@ -120,14 +120,10 @@ cache_addserv (struct database_dyn *db, int fd, request_header *req,
362 else if ((dataset = mempool_alloc (db, (sizeof (struct dataset)
363 + req->key_len), 1)) != NULL)
364 {
365- dataset->head.allocsize = sizeof (struct dataset) + req->key_len;
366- dataset->head.recsize = total;
367- dataset->head.notfound = true;
368- dataset->head.nreloads = 0;
369- dataset->head.usable = true;
370-
371- /* Compute the timeout time. */
372- timeout = dataset->head.timeout = t + db->negtimeout;
373+ timeout = datahead_init_neg (&dataset->head,
374+ (sizeof (struct dataset)
375+ + req->key_len), total,
376+ db->negtimeout);
377
378 /* This is the reply. */
379 memcpy (&dataset->resp, &notfound, total);
380@@ -207,14 +203,10 @@ cache_addserv (struct database_dyn *db, int fd, request_header *req,
381 alloca_used = true;
382 }
383
384- dataset->head.allocsize = total + req->key_len;
385- dataset->head.recsize = total - offsetof (struct dataset, resp);
386- dataset->head.notfound = false;
387- dataset->head.nreloads = he == NULL ? 0 : (dh->nreloads + 1);
388- dataset->head.usable = true;
389-
390- /* Compute the timeout time. */
391- timeout = dataset->head.timeout = t + db->postimeout;
392+ timeout = datahead_init_pos (&dataset->head, total + req->key_len,
393+ total - offsetof (struct dataset, resp),
394+ he == NULL ? 0 : dh->nreloads + 1,
395+ db->postimeout);
396
397 dataset->resp.version = NSCD_VERSION;
398 dataset->resp.found = 1;