Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 165683
b: refs/heads/master
c: a293980
h: refs/heads/master
i:
  165681: 8b599a0
  165679: a7d320c
v: v3
  • Loading branch information
Neil Horman authored and Linus Torvalds committed Sep 24, 2009
1 parent 797ddce commit b97ae8e
Show file tree
Hide file tree
Showing 4 changed files with 50 additions and 6 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 725eae32df7754044809973034429a47e6035158
refs/heads/master: a293980c2e261bd5b0d2a77340dd04f684caff58
22 changes: 22 additions & 0 deletions trunk/Documentation/sysctl/kernel.txt
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ show up in /proc/sys/kernel:
- callhome [ S390 only ]
- auto_msgmni
- core_pattern
- core_pipe_limit
- core_uses_pid
- ctrl-alt-del
- dentry-state
Expand Down Expand Up @@ -135,6 +136,27 @@ core_pattern is used to specify a core dumpfile pattern name.

==============================================================

core_pipe_limit:

This sysctl is only applicable when core_pattern is configured to pipe core
files to user space helper a (when the first character of core_pattern is a '|',
see above). When collecting cores via a pipe to an application, it is
occasionally usefull for the collecting application to gather data about the
crashing process from its /proc/pid directory. In order to do this safely, the
kernel must wait for the collecting process to exit, so as not to remove the
crashing processes proc files prematurely. This in turn creates the possibility
that a misbehaving userspace collecting process can block the reaping of a
crashed process simply by never exiting. This sysctl defends against that. It
defines how many concurrent crashing processes may be piped to user space
applications in parallel. If this value is exceeded, then those crashing
processes above that value are noted via the kernel log and their cores are
skipped. 0 is a special value, indicating that unlimited processes may be
captured in parallel, but that no waiting will take place (i.e. the collecting
process is not guaranteed access to /proc/<crahing pid>/). This value defaults
to 0.

==============================================================

core_uses_pid:

The default coredump filename is "core". By setting
Expand Down
23 changes: 18 additions & 5 deletions trunk/fs/exec.c
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@

int core_uses_pid;
char core_pattern[CORENAME_MAX_SIZE] = "core";
unsigned int core_pipe_limit;
int suid_dumpable = 0;

/* The maximal length of core_pattern is also specified in sysctl.c */
Expand Down Expand Up @@ -1744,7 +1745,8 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
unsigned long core_limit = current->signal->rlim[RLIMIT_CORE].rlim_cur;
char **helper_argv = NULL;
int helper_argc = 0;
char *delimit;
int dump_count = 0;
static atomic_t core_dump_count = ATOMIC_INIT(0);

audit_core_dumps(signr);

Expand Down Expand Up @@ -1826,28 +1828,36 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
goto fail_unlock;
}

dump_count = atomic_inc_return(&core_dump_count);
if (core_pipe_limit && (core_pipe_limit < dump_count)) {
printk(KERN_WARNING "Pid %d(%s) over core_pipe_limit\n",
task_tgid_vnr(current), current->comm);
printk(KERN_WARNING "Skipping core dump\n");
goto fail_dropcount;
}

helper_argv = argv_split(GFP_KERNEL, corename+1, &helper_argc);
if (!helper_argv) {
printk(KERN_WARNING "%s failed to allocate memory\n",
__func__);
goto fail_unlock;
goto fail_dropcount;
}

core_limit = RLIM_INFINITY;

/* SIGPIPE can happen, but it's just never processed */
if (call_usermodehelper_pipe(corename+1, helper_argv, NULL,
if (call_usermodehelper_pipe(helper_argv[0], helper_argv, NULL,
&file)) {
printk(KERN_INFO "Core dump to %s pipe failed\n",
corename);
goto fail_unlock;
goto fail_dropcount;
}
} else
file = filp_open(corename,
O_CREAT | 2 | O_NOFOLLOW | O_LARGEFILE | flag,
0600);
if (IS_ERR(file))
goto fail_unlock;
goto fail_dropcount;
inode = file->f_path.dentry->d_inode;
if (inode->i_nlink > 1)
goto close_fail; /* multiple links - don't dump */
Expand Down Expand Up @@ -1877,6 +1887,9 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
current->signal->group_exit_code |= 0x80;
close_fail:
filp_close(file, NULL);
fail_dropcount:
if (dump_count)
atomic_dec(&core_dump_count);
fail_unlock:
if (helper_argv)
argv_free(helper_argv);
Expand Down
9 changes: 9 additions & 0 deletions trunk/kernel/sysctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ extern int max_threads;
extern int core_uses_pid;
extern int suid_dumpable;
extern char core_pattern[];
extern unsigned int core_pipe_limit;
extern int pid_max;
extern int min_free_kbytes;
extern int pid_max_min, pid_max_max;
Expand Down Expand Up @@ -423,6 +424,14 @@ static struct ctl_table kern_table[] = {
.proc_handler = &proc_dostring,
.strategy = &sysctl_string,
},
{
.ctl_name = CTL_UNNUMBERED,
.procname = "core_pipe_limit",
.data = &core_pipe_limit,
.maxlen = sizeof(unsigned int),
.mode = 0644,
.proc_handler = &proc_dointvec,
},
#ifdef CONFIG_PROC_SYSCTL
{
.procname = "tainted",
Expand Down

0 comments on commit b97ae8e

Please sign in to comment.