Bug 14895 - corruption in popen pclose
Summary: corruption in popen pclose
Status: RESOLVED INVALID
Alias: None
Product: glibc
Classification: Unclassified
Component: stdio (show other bugs)
Version: 2.14
: P2 normal
Target Milestone: ---
Assignee: Not yet assigned to anyone
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2012-11-30 09:59 UTC by Ajeet Yadav
Modified: 2019-04-10 12:18 UTC (History)
5 users (show)

See Also:
Host:
Target:
Build:
Last reconfirmed:
fweimer: security-


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Ajeet Yadav 2012-11-30 09:59:42 UTC
Linux version 3.0.33 (Cortex A15)
Below program crashes with 2.14.1 glibc but runs fine with 2.11.1 glibc.

#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <string.h>
#include <errno.h>

#define MAX_LINE_SIZE 80

#define MAX_THREAD 20
#define MAX_POPEN 10
#define MALLOC_SIZE 16

void* pipe_thread(void *arg)
{
	int i;
	char *p = NULL;
	FILE *fp[MAX_POPEN];
	char shellCommand[MAX_LINE_SIZE];

	memset(shellCommand, 0x00, MAX_LINE_SIZE);
	sprintf(shellCommand, "mount");
	signal(SIGPIPE, SIG_IGN);

	while (1) {
		for (i = 0; i < MAX_POPEN; ++i) {
			fp[i] = popen(shellCommand, "r");
		}

		if (p) {
			free(p);
		}

		for (i = 0; i < MAX_POPEN; ++i) {
			if (fp[i])
				pclose(fp[i]);
		}

		p = malloc(MALLOC_SIZE);
		if (p)
			memset(p, 0, MALLOC_SIZE);
	}
	return NULL;
} 

int main(int argc, char *argv[])
{
	int i;
	pthread_t tid;

	for (i = 0; i < MAX_THREAD; ++i) {
		pthread_create(&tid, NULL, &pipe_thread, (void*)NULL);
	}
	sleep(60);
}

gdb logs:
(gdb) bt
#0  0x4014f998 in _IO_new_fclose (fp=0x1) at iofclose.c:74
#1  0x4015b59c in fwide (fp=0xb8, mode=<optimized out>) at fwide.c:47
#2  0x00008a6c in ?? ()
Cannot access memory at address 0x8
#3  0x00008a6c in ?? ()
Cannot access memory at address 0x8
Backtrace stopped: previous frame identical to this frame (corrupt stack?)
Comment 1 Ajeet Yadav 2012-12-01 10:37:00 UTC
Yesturday I have been able to fix this issue with below patch, now this problem no longer occurs.
But still my interest is 1> Why this patch fixes the problem ? 2> What change between 2.11.1 and 2.14.1 might have caused this problem
------------------------------------------------------------------------------
 diff --git a/libio/iopopen.c b/libio/iopopen.c
 --- a/libio/iopopen.c
 +++ b/libio/iopopen.c
 @@ -299,6 +299,7 @@ _IO_new_popen (command, mode)
    new_f = (struct locked_FILE *) malloc (sizeof (struct locked_FILE));
    if (new_f == NULL)
      return NULL;
 +  memset(new_f, 0, sizeof (struct locked_FILE));
  #ifdef _IO_MTSAFE_IO
    new_f->fpx.file.file._lock = &new_f->lock;
  #endif
------------------------------------------------------------------------------
Comment 2 OndrejBilka 2013-05-22 09:13:38 UTC
Cannot reproduce on x64. Looks like platform specific issue.
Marcus could you reproduce this?
Comment 3 Florian Weimer 2014-06-16 09:07:49 UTC
Ajeet, can you reproduce this with more recent glibc versions?

(This bug report reminds me of some other bug I saw, but I can't find it.)
Comment 4 Adhemerval Zanella 2018-10-18 21:32:41 UTC
I tried the testcase provided in comment #1 on armhf and x86_64 against 2.27 and master along with valgrind and address sanitizer. None indicated any issue in any platform.

The patch proposed on comment #2 possible just commit the malloced pages for the process and it leads to think this might be a kernel (maybe related to COW).

I will close this bug as INVALID by the end of the week, please reopen if you see any issue with a different system.
Comment 5 Adhemerval Zanella 2018-10-19 12:12:26 UTC
Close as previous comment.