|
@@ -29,6 +29,7 @@
|
|
|
#include <linux/stat.h>
|
|
|
#include <linux/fcntl.h>
|
|
|
#include <linux/smp_lock.h>
|
|
|
+#include <linux/string.h>
|
|
|
#include <linux/init.h>
|
|
|
#include <linux/pagemap.h>
|
|
|
#include <linux/highmem.h>
|
|
@@ -1514,6 +1515,14 @@ static int format_corename(char *corename, const char *pattern, long signr)
|
|
|
goto out;
|
|
|
out_ptr += rc;
|
|
|
break;
|
|
|
+ /* core limit size */
|
|
|
+ case 'c':
|
|
|
+ rc = snprintf(out_ptr, out_end - out_ptr,
|
|
|
+ "%lu", current->signal->rlim[RLIMIT_CORE].rlim_cur);
|
|
|
+ if (rc > out_end - out_ptr)
|
|
|
+ goto out;
|
|
|
+ out_ptr += rc;
|
|
|
+ break;
|
|
|
default:
|
|
|
break;
|
|
|
}
|
|
@@ -1698,6 +1707,9 @@ int do_coredump(long signr, int exit_code, struct pt_regs * regs)
|
|
|
int flag = 0;
|
|
|
int ispipe = 0;
|
|
|
unsigned long core_limit = current->signal->rlim[RLIMIT_CORE].rlim_cur;
|
|
|
+ char **helper_argv = NULL;
|
|
|
+ int helper_argc = 0;
|
|
|
+ char *delimit;
|
|
|
|
|
|
audit_core_dumps(signr);
|
|
|
|
|
@@ -1746,14 +1758,18 @@ int do_coredump(long signr, int exit_code, struct pt_regs * regs)
|
|
|
* at which point file size limits and permissions will be imposed
|
|
|
* as it does with any other process
|
|
|
*/
|
|
|
- if ((!ispipe) &&
|
|
|
- (core_limit < binfmt->min_coredump))
|
|
|
+ if ((!ispipe) && (core_limit < binfmt->min_coredump))
|
|
|
goto fail_unlock;
|
|
|
|
|
|
if (ispipe) {
|
|
|
core_limit = RLIM_INFINITY;
|
|
|
+ helper_argv = argv_split(GFP_KERNEL, corename+1, &helper_argc);
|
|
|
+ /* Terminate the string before the first option */
|
|
|
+ delimit = strchr(corename, ' ');
|
|
|
+ if (delimit)
|
|
|
+ *delimit = '\0';
|
|
|
/* SIGPIPE can happen, but it's just never processed */
|
|
|
- if(call_usermodehelper_pipe(corename+1, NULL, NULL, &file)) {
|
|
|
+ if(call_usermodehelper_pipe(corename+1, helper_argv, NULL, &file)) {
|
|
|
printk(KERN_INFO "Core dump to %s pipe failed\n",
|
|
|
corename);
|
|
|
goto fail_unlock;
|
|
@@ -1788,6 +1804,9 @@ int do_coredump(long signr, int exit_code, struct pt_regs * regs)
|
|
|
close_fail:
|
|
|
filp_close(file, NULL);
|
|
|
fail_unlock:
|
|
|
+ if (helper_argv)
|
|
|
+ argv_free(helper_argv);
|
|
|
+
|
|
|
current->fsuid = fsuid;
|
|
|
complete_all(&mm->core_done);
|
|
|
fail:
|