linux/kernel/sysctl.c
<<
>>
Prefs
   1/*
   2 * sysctl.c: General linux system control interface
   3 *
   4 * Begun 24 March 1995, Stephen Tweedie
   5 * Added /proc support, Dec 1995
   6 * Added bdflush entry and intvec min/max checking, 2/23/96, Tom Dyas.
   7 * Added hooks for /proc/sys/net (minor, minor patch), 96/4/1, Mike Shaver.
   8 * Added kernel/java-{interpreter,appletviewer}, 96/5/10, Mike Shaver.
   9 * Dynamic registration fixes, Stephen Tweedie.
  10 * Added kswapd-interval, ctrl-alt-del, printk stuff, 1/8/97, Chris Horn.
  11 * Made sysctl support optional via CONFIG_SYSCTL, 1/10/97, Chris
  12 *  Horn.
  13 * Added proc_doulongvec_ms_jiffies_minmax, 09/08/99, Carlos H. Bauer.
  14 * Added proc_doulongvec_minmax, 09/08/99, Carlos H. Bauer.
  15 * Changed linked lists to use list.h instead of lists.h, 02/24/00, Bill
  16 *  Wendling.
  17 * The list_for_each() macro wasn't appropriate for the sysctl loop.
  18 *  Removed it and replaced it with older style, 03/23/00, Bill Wendling
  19 */
  20
  21#include <linux/module.h>
  22#include <linux/mm.h>
  23#include <linux/swap.h>
  24#include <linux/slab.h>
  25#include <linux/sysctl.h>
  26#include <linux/bitmap.h>
  27#include <linux/signal.h>
  28#include <linux/printk.h>
  29#include <linux/proc_fs.h>
  30#include <linux/security.h>
  31#include <linux/ctype.h>
  32#include <linux/kmemcheck.h>
  33#include <linux/kmemleak.h>
  34#include <linux/fs.h>
  35#include <linux/init.h>
  36#include <linux/kernel.h>
  37#include <linux/kobject.h>
  38#include <linux/net.h>
  39#include <linux/sysrq.h>
  40#include <linux/highuid.h>
  41#include <linux/writeback.h>
  42#include <linux/ratelimit.h>
  43#include <linux/compaction.h>
  44#include <linux/hugetlb.h>
  45#include <linux/initrd.h>
  46#include <linux/key.h>
  47#include <linux/times.h>
  48#include <linux/limits.h>
  49#include <linux/dcache.h>
  50#include <linux/dnotify.h>
  51#include <linux/syscalls.h>
  52#include <linux/vmstat.h>
  53#include <linux/nfs_fs.h>
  54#include <linux/acpi.h>
  55#include <linux/reboot.h>
  56#include <linux/ftrace.h>
  57#include <linux/perf_event.h>
  58#include <linux/kprobes.h>
  59#include <linux/pipe_fs_i.h>
  60#include <linux/oom.h>
  61#include <linux/kmod.h>
  62#include <linux/capability.h>
  63#include <linux/binfmts.h>
  64#include <linux/sched/sysctl.h>
  65#include <linux/kexec.h>
  66#include <linux/mount.h>
  67
  68#include <asm/uaccess.h>
  69#include <asm/processor.h>
  70
  71#ifdef CONFIG_X86
  72#include <asm/nmi.h>
  73#include <asm/stacktrace.h>
  74#include <asm/io.h>
  75#endif
  76#ifdef CONFIG_SPARC
  77#include <asm/setup.h>
  78#endif
  79#ifdef CONFIG_BSD_PROCESS_ACCT
  80#include <linux/acct.h>
  81#endif
  82#ifdef CONFIG_RT_MUTEXES
  83#include <linux/rtmutex.h>
  84#endif
  85#if defined(CONFIG_PROVE_LOCKING) || defined(CONFIG_LOCK_STAT)
  86#include <linux/lockdep.h>
  87#endif
  88#ifdef CONFIG_CHR_DEV_SG
  89#include <scsi/sg.h>
  90#endif
  91
  92#ifdef CONFIG_LOCKUP_DETECTOR
  93#include <linux/nmi.h>
  94#endif
  95
  96
  97#if defined(CONFIG_SYSCTL)
  98
  99/* External variables not in a header file. */
 100extern int may_detach_mounts;
 101extern int max_threads;
 102extern int suid_dumpable;
 103#ifdef CONFIG_COREDUMP
 104extern int core_uses_pid;
 105extern char core_pattern[];
 106extern unsigned int core_pipe_limit;
 107#endif
 108extern int pid_max;
 109extern int pid_max_min, pid_max_max;
 110extern int percpu_pagelist_fraction;
 111extern int compat_log;
 112extern int latencytop_enabled;
 113extern int sysctl_nr_open_min, sysctl_nr_open_max;
 114#ifndef CONFIG_MMU
 115extern int sysctl_nr_trim_pages;
 116#endif
 117
 118/* Constants used for minimum and  maximum */
 119#ifdef CONFIG_LOCKUP_DETECTOR
 120static int sixty = 60;
 121#endif
 122
 123static int __maybe_unused neg_one = -1;
 124static int zero;
 125static int __maybe_unused one = 1;
 126static int __maybe_unused two = 2;
 127static int __maybe_unused four = 4;
 128static unsigned long one_ul = 1;
 129static int one_hundred = 100;
 130#ifdef CONFIG_PRINTK
 131static int ten_thousand = 10000;
 132#endif
 133
 134/* this is needed for the proc_doulongvec_minmax of vm_dirty_bytes */
 135static unsigned long dirty_bytes_min = 2 * PAGE_SIZE;
 136
 137/* this is needed for the proc_dointvec_minmax for [fs_]overflow UID and GID */
 138static int maxolduid = 65535;
 139static int minolduid;
 140
 141static int ngroups_max = NGROUPS_MAX;
 142static const int cap_last_cap = CAP_LAST_CAP;
 143
 144/*this is needed for proc_doulongvec_minmax of sysctl_hung_task_timeout_secs */
 145#ifdef CONFIG_DETECT_HUNG_TASK
 146static unsigned long hung_task_timeout_max = (LONG_MAX/HZ);
 147#endif
 148
 149#ifdef CONFIG_INOTIFY_USER
 150#include <linux/inotify.h>
 151#endif
 152#ifdef CONFIG_SPARC
 153#endif
 154
 155#ifdef CONFIG_SPARC64
 156extern int sysctl_tsb_ratio;
 157#endif
 158
 159#ifdef __hppa__
 160extern int pwrsw_enabled;
 161#endif
 162
 163#ifdef CONFIG_SYSCTL_ARCH_UNALIGN_ALLOW
 164extern int unaligned_enabled;
 165#endif
 166
 167#ifdef CONFIG_IA64
 168extern int unaligned_dump_stack;
 169#endif
 170
 171#ifdef CONFIG_SYSCTL_ARCH_UNALIGN_NO_WARN
 172extern int no_unaligned_warning;
 173#endif
 174
 175#ifdef CONFIG_PROC_SYSCTL
 176
 177/**
 178 * enum sysctl_writes_mode - supported sysctl write modes
 179 *
 180 * @SYSCTL_WRITES_LEGACY: each write syscall must fully contain the sysctl value
 181 *      to be written, and multiple writes on the same sysctl file descriptor
 182 *      will rewrite the sysctl value, regardless of file position. No warning
 183 *      is issued when the initial position is not 0.
 184 * @SYSCTL_WRITES_WARN: same as above but warn when the initial file position is
 185 *      not 0.
 186 * @SYSCTL_WRITES_STRICT: writes to numeric sysctl entries must always be at
 187 *      file position 0 and the value must be fully contained in the buffer
 188 *      sent to the write syscall. If dealing with strings respect the file
 189 *      position, but restrict this to the max length of the buffer, anything
 190 *      passed the max lenght will be ignored. Multiple writes will append
 191 *      to the buffer.
 192 *
 193 * These write modes control how current file position affects the behavior of
 194 * updating sysctl values through the proc interface on each write.
 195 */
 196enum sysctl_writes_mode {
 197        SYSCTL_WRITES_LEGACY            = -1,
 198        SYSCTL_WRITES_WARN              = 0,
 199        SYSCTL_WRITES_STRICT            = 1,
 200};
 201
 202static enum sysctl_writes_mode sysctl_writes_strict = SYSCTL_WRITES_STRICT;
 203
 204static int proc_do_cad_pid(struct ctl_table *table, int write,
 205                  void __user *buffer, size_t *lenp, loff_t *ppos);
 206static int proc_taint(struct ctl_table *table, int write,
 207                               void __user *buffer, size_t *lenp, loff_t *ppos);
 208#endif
 209
 210#ifdef CONFIG_PRINTK
 211static int proc_dointvec_minmax_sysadmin(struct ctl_table *table, int write,
 212                                void __user *buffer, size_t *lenp, loff_t *ppos);
 213#endif
 214
 215static int proc_dointvec_minmax_coredump(struct ctl_table *table, int write,
 216                void __user *buffer, size_t *lenp, loff_t *ppos);
 217#ifdef CONFIG_COREDUMP
 218static int proc_dostring_coredump(struct ctl_table *table, int write,
 219                void __user *buffer, size_t *lenp, loff_t *ppos);
 220#endif
 221
 222#ifdef CONFIG_MAGIC_SYSRQ
 223/* Note: sysrq code uses it's own private copy */
 224static int __sysrq_enabled = SYSRQ_DEFAULT_ENABLE;
 225
 226static int sysrq_sysctl_handler(ctl_table *table, int write,
 227                                void __user *buffer, size_t *lenp,
 228                                loff_t *ppos)
 229{
 230        int error;
 231
 232        error = proc_dointvec(table, write, buffer, lenp, ppos);
 233        if (error)
 234                return error;
 235
 236        if (write)
 237                sysrq_toggle_support(__sysrq_enabled);
 238
 239        return 0;
 240}
 241
 242#endif
 243
 244static struct ctl_table kern_table[];
 245static struct ctl_table vm_table[];
 246static struct ctl_table fs_table[];
 247static struct ctl_table debug_table[];
 248static struct ctl_table dev_table[];
 249extern struct ctl_table random_table[];
 250#ifdef CONFIG_EPOLL
 251extern struct ctl_table epoll_table[];
 252#endif
 253
 254#ifdef HAVE_ARCH_PICK_MMAP_LAYOUT
 255int sysctl_legacy_va_layout;
 256#endif
 257
 258/* The default sysctl tables: */
 259
 260static struct ctl_table sysctl_base_table[] = {
 261        {
 262                .procname       = "kernel",
 263                .mode           = 0555,
 264                .child          = kern_table,
 265        },
 266        {
 267                .procname       = "vm",
 268                .mode           = 0555,
 269                .child          = vm_table,
 270        },
 271        {
 272                .procname       = "fs",
 273                .mode           = 0555,
 274                .child          = fs_table,
 275        },
 276        {
 277                .procname       = "debug",
 278                .mode           = 0555,
 279                .child          = debug_table,
 280        },
 281        {
 282                .procname       = "dev",
 283                .mode           = 0555,
 284                .child          = dev_table,
 285        },
 286        { }
 287};
 288
 289#ifdef CONFIG_SCHED_DEBUG
 290static int min_sched_granularity_ns = 100000;           /* 100 usecs */
 291static int max_sched_granularity_ns = NSEC_PER_SEC;     /* 1 second */
 292static int min_wakeup_granularity_ns;                   /* 0 usecs */
 293static int max_wakeup_granularity_ns = NSEC_PER_SEC;    /* 1 second */
 294#ifdef CONFIG_SMP
 295static int min_sched_tunable_scaling = SCHED_TUNABLESCALING_NONE;
 296static int max_sched_tunable_scaling = SCHED_TUNABLESCALING_END-1;
 297#endif /* CONFIG_SMP */
 298#endif /* CONFIG_SCHED_DEBUG */
 299
 300#ifdef CONFIG_COMPACTION
 301static int min_extfrag_threshold;
 302static int max_extfrag_threshold = 1000;
 303#endif
 304
 305static struct ctl_table kern_table[] = {
 306        {
 307                .procname       = "sched_child_runs_first",
 308                .data           = &sysctl_sched_child_runs_first,
 309                .maxlen         = sizeof(unsigned int),
 310                .mode           = 0644,
 311                .proc_handler   = proc_dointvec,
 312        },
 313#ifdef CONFIG_SCHED_DEBUG
 314        {
 315                .procname       = "sched_min_granularity_ns",
 316                .data           = &sysctl_sched_min_granularity,
 317                .maxlen         = sizeof(unsigned int),
 318                .mode           = 0644,
 319                .proc_handler   = sched_proc_update_handler,
 320                .extra1         = &min_sched_granularity_ns,
 321                .extra2         = &max_sched_granularity_ns,
 322        },
 323        {
 324                .procname       = "sched_latency_ns",
 325                .data           = &sysctl_sched_latency,
 326                .maxlen         = sizeof(unsigned int),
 327                .mode           = 0644,
 328                .proc_handler   = sched_proc_update_handler,
 329                .extra1         = &min_sched_granularity_ns,
 330                .extra2         = &max_sched_granularity_ns,
 331        },
 332        {
 333                .procname       = "sched_wakeup_granularity_ns",
 334                .data           = &sysctl_sched_wakeup_granularity,
 335                .maxlen         = sizeof(unsigned int),
 336                .mode           = 0644,
 337                .proc_handler   = sched_proc_update_handler,
 338                .extra1         = &min_wakeup_granularity_ns,
 339                .extra2         = &max_wakeup_granularity_ns,
 340        },
 341#ifdef CONFIG_SMP
 342        {
 343                .procname       = "sched_tunable_scaling",
 344                .data           = &sysctl_sched_tunable_scaling,
 345                .maxlen         = sizeof(enum sched_tunable_scaling),
 346                .mode           = 0644,
 347                .proc_handler   = sched_proc_update_handler,
 348                .extra1         = &min_sched_tunable_scaling,
 349                .extra2         = &max_sched_tunable_scaling,
 350        },
 351        {
 352                .procname       = "sched_migration_cost_ns",
 353                .data           = &sysctl_sched_migration_cost,
 354                .maxlen         = sizeof(unsigned int),
 355                .mode           = 0644,
 356                .proc_handler   = proc_dointvec,
 357        },
 358        {
 359                .procname       = "sched_nr_migrate",
 360                .data           = &sysctl_sched_nr_migrate,
 361                .maxlen         = sizeof(unsigned int),
 362                .mode           = 0644,
 363                .proc_handler   = proc_dointvec,
 364        },
 365        {
 366                .procname       = "sched_time_avg_ms",
 367                .data           = &sysctl_sched_time_avg,
 368                .maxlen         = sizeof(unsigned int),
 369                .mode           = 0644,
 370                .proc_handler   = proc_dointvec,
 371        },
 372        {
 373                .procname       = "sched_shares_window_ns",
 374                .data           = &sysctl_sched_shares_window,
 375                .maxlen         = sizeof(unsigned int),
 376                .mode           = 0644,
 377                .proc_handler   = proc_dointvec,
 378        },
 379        {
 380                .procname       = "timer_migration",
 381                .data           = &sysctl_timer_migration,
 382                .maxlen         = sizeof(unsigned int),
 383                .mode           = 0644,
 384                .proc_handler   = proc_dointvec_minmax,
 385                .extra1         = &zero,
 386                .extra2         = &one,
 387        },
 388#ifdef CONFIG_SCHEDSTATS
 389        {
 390                .procname       = "sched_schedstats",
 391                .data           = NULL,
 392                .maxlen         = sizeof(unsigned int),
 393                .mode           = 0644,
 394                .proc_handler   = sysctl_schedstats,
 395                .extra1         = &zero,
 396                .extra2         = &one,
 397        },
 398#endif /* CONFIG_SCHEDSTATS */
 399#endif /* CONFIG_SMP */
 400#ifdef CONFIG_NUMA_BALANCING
 401        {
 402                .procname       = "numa_balancing_scan_delay_ms",
 403                .data           = &sysctl_numa_balancing_scan_delay,
 404                .maxlen         = sizeof(unsigned int),
 405                .mode           = 0644,
 406                .proc_handler   = proc_dointvec,
 407        },
 408        {
 409                .procname       = "numa_balancing_scan_period_min_ms",
 410                .data           = &sysctl_numa_balancing_scan_period_min,
 411                .maxlen         = sizeof(unsigned int),
 412                .mode           = 0644,
 413                .proc_handler   = proc_dointvec,
 414        },
 415        {
 416                .procname       = "numa_balancing_scan_period_max_ms",
 417                .data           = &sysctl_numa_balancing_scan_period_max,
 418                .maxlen         = sizeof(unsigned int),
 419                .mode           = 0644,
 420                .proc_handler   = proc_dointvec,
 421        },
 422        {
 423                .procname       = "numa_balancing_scan_size_mb",
 424                .data           = &sysctl_numa_balancing_scan_size,
 425                .maxlen         = sizeof(unsigned int),
 426                .mode           = 0644,
 427                .proc_handler   = proc_dointvec_minmax,
 428                .extra1         = &one,
 429        },
 430        {
 431                .procname       = "numa_balancing_settle_count",
 432                .data           = &sysctl_numa_balancing_settle_count,
 433                .maxlen         = sizeof(unsigned int),
 434                .mode           = 0644,
 435                .proc_handler   = proc_dointvec,
 436        },
 437        {
 438                .procname       = "numa_balancing",
 439                .data           = NULL, /* filled in by handler */
 440                .maxlen         = sizeof(unsigned int),
 441                .mode           = 0644,
 442                .proc_handler   = sysctl_numa_balancing,
 443                .extra1         = &zero,
 444                .extra2         = &one,
 445        },
 446#endif /* CONFIG_NUMA_BALANCING */
 447#endif /* CONFIG_SCHED_DEBUG */
 448        {
 449                .procname       = "sched_rt_period_us",
 450                .data           = &sysctl_sched_rt_period,
 451                .maxlen         = sizeof(unsigned int),
 452                .mode           = 0644,
 453                .proc_handler   = sched_rt_handler,
 454        },
 455        {
 456                .procname       = "sched_rt_runtime_us",
 457                .data           = &sysctl_sched_rt_runtime,
 458                .maxlen         = sizeof(int),
 459                .mode           = 0644,
 460                .proc_handler   = sched_rt_handler,
 461        },
 462        {
 463                .procname       = "sched_rr_timeslice_ms",
 464                .data           = &sched_rr_timeslice,
 465                .maxlen         = sizeof(int),
 466                .mode           = 0644,
 467                .proc_handler   = sched_rr_handler,
 468        },
 469#ifdef CONFIG_SCHED_AUTOGROUP
 470        {
 471                .procname       = "sched_autogroup_enabled",
 472                .data           = &sysctl_sched_autogroup_enabled,
 473                .maxlen         = sizeof(unsigned int),
 474                .mode           = 0644,
 475                .proc_handler   = proc_dointvec_minmax,
 476                .extra1         = &zero,
 477                .extra2         = &one,
 478        },
 479#endif
 480#ifdef CONFIG_CFS_BANDWIDTH
 481        {
 482                .procname       = "sched_cfs_bandwidth_slice_us",
 483                .data           = &sysctl_sched_cfs_bandwidth_slice,
 484                .maxlen         = sizeof(unsigned int),
 485                .mode           = 0644,
 486                .proc_handler   = proc_dointvec_minmax,
 487                .extra1         = &one,
 488        },
 489#endif
 490#ifdef CONFIG_PROVE_LOCKING
 491        {
 492                .procname       = "prove_locking",
 493                .data           = &prove_locking,
 494                .maxlen         = sizeof(int),
 495                .mode           = 0644,
 496                .proc_handler   = proc_dointvec,
 497        },
 498#endif
 499#ifdef CONFIG_LOCK_STAT
 500        {
 501                .procname       = "lock_stat",
 502                .data           = &lock_stat,
 503                .maxlen         = sizeof(int),
 504                .mode           = 0644,
 505                .proc_handler   = proc_dointvec,
 506        },
 507#endif
 508        {
 509                .procname       = "panic",
 510                .data           = &panic_timeout,
 511                .maxlen         = sizeof(int),
 512                .mode           = 0644,
 513                .proc_handler   = proc_dointvec,
 514        },
 515#ifdef CONFIG_COREDUMP
 516        {
 517                .procname       = "core_uses_pid",
 518                .data           = &core_uses_pid,
 519                .maxlen         = sizeof(int),
 520                .mode           = 0644,
 521                .proc_handler   = proc_dointvec,
 522        },
 523        {
 524                .procname       = "core_pattern",
 525                .data           = core_pattern,
 526                .maxlen         = CORENAME_MAX_SIZE,
 527                .mode           = 0644,
 528                .proc_handler   = proc_dostring_coredump,
 529        },
 530        {
 531                .procname       = "core_pipe_limit",
 532                .data           = &core_pipe_limit,
 533                .maxlen         = sizeof(unsigned int),
 534                .mode           = 0644,
 535                .proc_handler   = proc_dointvec,
 536        },
 537#endif
 538#ifdef CONFIG_PROC_SYSCTL
 539        {
 540                .procname       = "tainted",
 541                .maxlen         = sizeof(long),
 542                .mode           = 0644,
 543                .proc_handler   = proc_taint,
 544        },
 545        {
 546                .procname       = "sysctl_writes_strict",
 547                .data           = &sysctl_writes_strict,
 548                .maxlen         = sizeof(int),
 549                .mode           = 0644,
 550                .proc_handler   = proc_dointvec_minmax,
 551                .extra1         = &neg_one,
 552                .extra2         = &one,
 553        },
 554#endif
 555#ifdef CONFIG_LATENCYTOP
 556        {
 557                .procname       = "latencytop",
 558                .data           = &latencytop_enabled,
 559                .maxlen         = sizeof(int),
 560                .mode           = 0644,
 561                .proc_handler   = sysctl_latencytop,
 562        },
 563#endif
 564#ifdef CONFIG_BLK_DEV_INITRD
 565        {
 566                .procname       = "real-root-dev",
 567                .data           = &real_root_dev,
 568                .maxlen         = sizeof(int),
 569                .mode           = 0644,
 570                .proc_handler   = proc_dointvec,
 571        },
 572#endif
 573        {
 574                .procname       = "print-fatal-signals",
 575                .data           = &print_fatal_signals,
 576                .maxlen         = sizeof(int),
 577                .mode           = 0644,
 578                .proc_handler   = proc_dointvec,
 579        },
 580#ifdef CONFIG_SPARC
 581        {
 582                .procname       = "reboot-cmd",
 583                .data           = reboot_command,
 584                .maxlen         = 256,
 585                .mode           = 0644,
 586                .proc_handler   = proc_dostring,
 587        },
 588        {
 589                .procname       = "stop-a",
 590                .data           = &stop_a_enabled,
 591                .maxlen         = sizeof (int),
 592                .mode           = 0644,
 593                .proc_handler   = proc_dointvec,
 594        },
 595        {
 596                .procname       = "scons-poweroff",
 597                .data           = &scons_pwroff,
 598                .maxlen         = sizeof (int),
 599                .mode           = 0644,
 600                .proc_handler   = proc_dointvec,
 601        },
 602#endif
 603#ifdef CONFIG_SPARC64
 604        {
 605                .procname       = "tsb-ratio",
 606                .data           = &sysctl_tsb_ratio,
 607                .maxlen         = sizeof (int),
 608                .mode           = 0644,
 609                .proc_handler   = proc_dointvec,
 610        },
 611#endif
 612#ifdef __hppa__
 613        {
 614                .procname       = "soft-power",
 615                .data           = &pwrsw_enabled,
 616                .maxlen         = sizeof (int),
 617                .mode           = 0644,
 618                .proc_handler   = proc_dointvec,
 619        },
 620#endif
 621#ifdef CONFIG_SYSCTL_ARCH_UNALIGN_ALLOW
 622        {
 623                .procname       = "unaligned-trap",
 624                .data           = &unaligned_enabled,
 625                .maxlen         = sizeof (int),
 626                .mode           = 0644,
 627                .proc_handler   = proc_dointvec,
 628        },
 629#endif
 630        {
 631                .procname       = "ctrl-alt-del",
 632                .data           = &C_A_D,
 633                .maxlen         = sizeof(int),
 634                .mode           = 0644,
 635                .proc_handler   = proc_dointvec,
 636        },
 637#ifdef CONFIG_FUNCTION_TRACER
 638        {
 639                .procname       = "ftrace_enabled",
 640                .data           = &ftrace_enabled,
 641                .maxlen         = sizeof(int),
 642                .mode           = 0644,
 643                .proc_handler   = ftrace_enable_sysctl,
 644        },
 645#endif
 646#ifdef CONFIG_STACK_TRACER
 647        {
 648                .procname       = "stack_tracer_enabled",
 649                .data           = &stack_tracer_enabled,
 650                .maxlen         = sizeof(int),
 651                .mode           = 0644,
 652                .proc_handler   = stack_trace_sysctl,
 653        },
 654#endif
 655#ifdef CONFIG_TRACING
 656        {
 657                .procname       = "ftrace_dump_on_oops",
 658                .data           = &ftrace_dump_on_oops,
 659                .maxlen         = sizeof(int),
 660                .mode           = 0644,
 661                .proc_handler   = proc_dointvec,
 662        },
 663        {
 664                .procname       = "traceoff_on_warning",
 665                .data           = &__disable_trace_on_warning,
 666                .maxlen         = sizeof(__disable_trace_on_warning),
 667                .mode           = 0644,
 668                .proc_handler   = proc_dointvec,
 669        },
 670#endif
 671#ifdef CONFIG_KEXEC_CORE
 672        {
 673                .procname       = "kexec_load_disabled",
 674                .data           = &kexec_load_disabled,
 675                .maxlen         = sizeof(int),
 676                .mode           = 0644,
 677                /* only handle a transition from default "0" to "1" */
 678                .proc_handler   = proc_dointvec_minmax,
 679                .extra1         = &one,
 680                .extra2         = &one,
 681        },
 682#endif
 683#ifdef CONFIG_MODULES
 684        {
 685                .procname       = "modprobe",
 686                .data           = &modprobe_path,
 687                .maxlen         = KMOD_PATH_LEN,
 688                .mode           = 0644,
 689                .proc_handler   = proc_dostring,
 690        },
 691        {
 692                .procname       = "modules_disabled",
 693                .data           = &modules_disabled,
 694                .maxlen         = sizeof(int),
 695                .mode           = 0644,
 696                /* only handle a transition from default "0" to "1" */
 697                .proc_handler   = proc_dointvec_minmax,
 698                .extra1         = &one,
 699                .extra2         = &one,
 700        },
 701#endif
 702
 703        {
 704                .procname       = "hotplug",
 705                .data           = &uevent_helper,
 706                .maxlen         = UEVENT_HELPER_PATH_LEN,
 707                .mode           = 0644,
 708                .proc_handler   = proc_dostring,
 709        },
 710
 711#ifdef CONFIG_CHR_DEV_SG
 712        {
 713                .procname       = "sg-big-buff",
 714                .data           = &sg_big_buff,
 715                .maxlen         = sizeof (int),
 716                .mode           = 0444,
 717                .proc_handler   = proc_dointvec,
 718        },
 719#endif
 720#ifdef CONFIG_BSD_PROCESS_ACCT
 721        {
 722                .procname       = "acct",
 723                .data           = &acct_parm,
 724                .maxlen         = 3*sizeof(int),
 725                .mode           = 0644,
 726                .proc_handler   = proc_dointvec,
 727        },
 728#endif
 729#ifdef CONFIG_MAGIC_SYSRQ
 730        {
 731                .procname       = "sysrq",
 732                .data           = &__sysrq_enabled,
 733                .maxlen         = sizeof (int),
 734                .mode           = 0644,
 735                .proc_handler   = sysrq_sysctl_handler,
 736        },
 737#endif
 738#ifdef CONFIG_PROC_SYSCTL
 739        {
 740                .procname       = "cad_pid",
 741                .data           = NULL,
 742                .maxlen         = sizeof (int),
 743                .mode           = 0600,
 744                .proc_handler   = proc_do_cad_pid,
 745        },
 746#endif
 747        {
 748                .procname       = "threads-max",
 749                .data           = &max_threads,
 750                .maxlen         = sizeof(int),
 751                .mode           = 0644,
 752                .proc_handler   = proc_dointvec,
 753        },
 754        {
 755                .procname       = "random",
 756                .mode           = 0555,
 757                .child          = random_table,
 758        },
 759        {
 760                .procname       = "usermodehelper",
 761                .mode           = 0555,
 762                .child          = usermodehelper_table,
 763        },
 764        {
 765                .procname       = "overflowuid",
 766                .data           = &overflowuid,
 767                .maxlen         = sizeof(int),
 768                .mode           = 0644,
 769                .proc_handler   = proc_dointvec_minmax,
 770                .extra1         = &minolduid,
 771                .extra2         = &maxolduid,
 772        },
 773        {
 774                .procname       = "overflowgid",
 775                .data           = &overflowgid,
 776                .maxlen         = sizeof(int),
 777                .mode           = 0644,
 778                .proc_handler   = proc_dointvec_minmax,
 779                .extra1         = &minolduid,
 780                .extra2         = &maxolduid,
 781        },
 782#ifdef CONFIG_S390
 783#ifdef CONFIG_MATHEMU
 784        {
 785                .procname       = "ieee_emulation_warnings",
 786                .data           = &sysctl_ieee_emulation_warnings,
 787                .maxlen         = sizeof(int),
 788                .mode           = 0644,
 789                .proc_handler   = proc_dointvec,
 790        },
 791#endif
 792        {
 793                .procname       = "userprocess_debug",
 794                .data           = &show_unhandled_signals,
 795                .maxlen         = sizeof(int),
 796                .mode           = 0644,
 797                .proc_handler   = proc_dointvec,
 798        },
 799#endif
 800        {
 801                .procname       = "pid_max",
 802                .data           = &pid_max,
 803                .maxlen         = sizeof (int),
 804                .mode           = 0644,
 805                .proc_handler   = proc_dointvec_minmax,
 806                .extra1         = &pid_max_min,
 807                .extra2         = &pid_max_max,
 808        },
 809        {
 810                .procname       = "panic_on_oops",
 811                .data           = &panic_on_oops,
 812                .maxlen         = sizeof(int),
 813                .mode           = 0644,
 814                .proc_handler   = proc_dointvec,
 815        },
 816#if defined CONFIG_PRINTK
 817        {
 818                .procname       = "printk",
 819                .data           = &console_loglevel,
 820                .maxlen         = 4*sizeof(int),
 821                .mode           = 0644,
 822                .proc_handler   = proc_dointvec,
 823        },
 824        {
 825                .procname       = "printk_ratelimit",
 826                .data           = &printk_ratelimit_state.interval,
 827                .maxlen         = sizeof(int),
 828                .mode           = 0644,
 829                .proc_handler   = proc_dointvec_jiffies,
 830        },
 831        {
 832                .procname       = "printk_ratelimit_burst",
 833                .data           = &printk_ratelimit_state.burst,
 834                .maxlen         = sizeof(int),
 835                .mode           = 0644,
 836                .proc_handler   = proc_dointvec,
 837        },
 838        {
 839                .procname       = "printk_delay",
 840                .data           = &printk_delay_msec,
 841                .maxlen         = sizeof(int),
 842                .mode           = 0644,
 843                .proc_handler   = proc_dointvec_minmax,
 844                .extra1         = &zero,
 845                .extra2         = &ten_thousand,
 846        },
 847        {
 848                .procname       = "dmesg_restrict",
 849                .data           = &dmesg_restrict,
 850                .maxlen         = sizeof(int),
 851                .mode           = 0644,
 852                .proc_handler   = proc_dointvec_minmax_sysadmin,
 853                .extra1         = &zero,
 854                .extra2         = &one,
 855        },
 856        {
 857                .procname       = "kptr_restrict",
 858                .data           = &kptr_restrict,
 859                .maxlen         = sizeof(int),
 860                .mode           = 0644,
 861                .proc_handler   = proc_dointvec_minmax_sysadmin,
 862                .extra1         = &zero,
 863                .extra2         = &two,
 864        },
 865#endif
 866        {
 867                .procname       = "ngroups_max",
 868                .data           = &ngroups_max,
 869                .maxlen         = sizeof (int),
 870                .mode           = 0444,
 871                .proc_handler   = proc_dointvec,
 872        },
 873        {
 874                .procname       = "cap_last_cap",
 875                .data           = (void *)&cap_last_cap,
 876                .maxlen         = sizeof(int),
 877                .mode           = 0444,
 878                .proc_handler   = proc_dointvec,
 879        },
 880#if defined(CONFIG_LOCKUP_DETECTOR)
 881        {
 882                .procname       = "watchdog",
 883                .data           = &watchdog_user_enabled,
 884                .maxlen         = sizeof (int),
 885                .mode           = 0644,
 886                .proc_handler   = proc_watchdog,
 887                .extra1         = &zero,
 888                .extra2         = &one,
 889        },
 890        {
 891                .procname       = "watchdog_thresh",
 892                .data           = &watchdog_thresh,
 893                .maxlen         = sizeof(int),
 894                .mode           = 0644,
 895                .proc_handler   = proc_watchdog_thresh,
 896                .extra1         = &zero,
 897                .extra2         = &sixty,
 898        },
 899        {
 900                .procname       = "nmi_watchdog",
 901                .data           = &nmi_watchdog_enabled,
 902                .maxlen         = sizeof (int),
 903                .mode           = 0644,
 904                .proc_handler   = proc_nmi_watchdog,
 905                .extra1         = &zero,
 906#if defined(CONFIG_HAVE_NMI_WATCHDOG) || defined(CONFIG_HARDLOCKUP_DETECTOR)
 907                .extra2         = &one,
 908#else
 909                .extra2         = &zero,
 910#endif
 911        },
 912#if 0
 913        {
 914                .procname       = "soft_watchdog",
 915                .data           = &soft_watchdog_enabled,
 916                .maxlen         = sizeof (int),
 917                .mode           = 0644,
 918                .proc_handler   = proc_soft_watchdog,
 919                .extra1         = &zero,
 920                .extra2         = &one,
 921        },
 922#endif
 923        {
 924                .procname       = "watchdog_cpumask",
 925                .data           = cpumask_bits(&watchdog_cpumask),
 926                .maxlen         = NR_CPUS,
 927                .mode           = 0644,
 928                .proc_handler   = proc_watchdog_cpumask,
 929        },
 930        {
 931                .procname       = "softlockup_panic",
 932                .data           = &softlockup_panic,
 933                .maxlen         = sizeof(int),
 934                .mode           = 0644,
 935                .proc_handler   = proc_dointvec_minmax,
 936                .extra1         = &zero,
 937                .extra2         = &one,
 938        },
 939#ifdef CONFIG_HARDLOCKUP_DETECTOR
 940        {
 941                .procname       = "hardlockup_panic",
 942                .data           = &hardlockup_panic,
 943                .maxlen         = sizeof(int),
 944                .mode           = 0644,
 945                .proc_handler   = proc_dointvec_minmax,
 946                .extra1         = &zero,
 947                .extra2         = &one,
 948        },
 949#endif
 950#ifdef CONFIG_SMP
 951        {
 952                .procname       = "softlockup_all_cpu_backtrace",
 953                .data           = &sysctl_softlockup_all_cpu_backtrace,
 954                .maxlen         = sizeof(int),
 955                .mode           = 0644,
 956                .proc_handler   = proc_dointvec_minmax,
 957                .extra1         = &zero,
 958                .extra2         = &one,
 959        },
 960        {
 961                .procname       = "hardlockup_all_cpu_backtrace",
 962                .data           = &sysctl_hardlockup_all_cpu_backtrace,
 963                .maxlen         = sizeof(int),
 964                .mode           = 0644,
 965                .proc_handler   = proc_dointvec_minmax,
 966                .extra1         = &zero,
 967                .extra2         = &one,
 968        },
 969#endif /* CONFIG_SMP */
 970#endif
 971#if defined(CONFIG_X86_LOCAL_APIC) && defined(CONFIG_X86)
 972        {
 973                .procname       = "unknown_nmi_panic",
 974                .data           = &unknown_nmi_panic,
 975                .maxlen         = sizeof (int),
 976                .mode           = 0644,
 977                .proc_handler   = proc_dointvec,
 978        },
 979#endif
 980#if defined(CONFIG_X86)
 981        {
 982                .procname       = "panic_on_unrecovered_nmi",
 983                .data           = &panic_on_unrecovered_nmi,
 984                .maxlen         = sizeof(int),
 985                .mode           = 0644,
 986                .proc_handler   = proc_dointvec,
 987        },
 988        {
 989                .procname       = "panic_on_io_nmi",
 990                .data           = &panic_on_io_nmi,
 991                .maxlen         = sizeof(int),
 992                .mode           = 0644,
 993                .proc_handler   = proc_dointvec,
 994        },
 995#ifdef CONFIG_DEBUG_STACKOVERFLOW
 996        {
 997                .procname       = "panic_on_stackoverflow",
 998                .data           = &sysctl_panic_on_stackoverflow,
 999                .maxlen         = sizeof(int),
1000                .mode           = 0644,
1001                .proc_handler   = proc_dointvec,
1002        },
1003#endif
1004        {
1005                .procname       = "bootloader_type",
1006                .data           = &bootloader_type,
1007                .maxlen         = sizeof (int),
1008                .mode           = 0444,
1009                .proc_handler   = proc_dointvec,
1010        },
1011        {
1012                .procname       = "bootloader_version",
1013                .data           = &bootloader_version,
1014                .maxlen         = sizeof (int),
1015                .mode           = 0444,
1016                .proc_handler   = proc_dointvec,
1017        },
1018        {
1019                .procname       = "io_delay_type",
1020                .data           = &io_delay_type,
1021                .maxlen         = sizeof(int),
1022                .mode           = 0644,
1023                .proc_handler   = proc_dointvec,
1024        },
1025#endif
1026#if defined(CONFIG_MMU)
1027        {
1028                .procname       = "randomize_va_space",
1029                .data           = &randomize_va_space,
1030                .maxlen         = sizeof(int),
1031                .mode           = 0644,
1032                .proc_handler   = proc_dointvec,
1033        },
1034#endif
1035#if defined(CONFIG_S390) && defined(CONFIG_SMP)
1036        {
1037                .procname       = "spin_retry",
1038                .data           = &spin_retry,
1039                .maxlen         = sizeof (int),
1040                .mode           = 0644,
1041                .proc_handler   = proc_dointvec,
1042        },
1043#endif
1044#if     defined(CONFIG_ACPI_SLEEP) && defined(CONFIG_X86)
1045        {
1046                .procname       = "acpi_video_flags",
1047                .data           = &acpi_realmode_flags,
1048                .maxlen         = sizeof (unsigned long),
1049                .mode           = 0644,
1050                .proc_handler   = proc_doulongvec_minmax,
1051        },
1052#endif
1053#ifdef CONFIG_SYSCTL_ARCH_UNALIGN_NO_WARN
1054        {
1055                .procname       = "ignore-unaligned-usertrap",
1056                .data           = &no_unaligned_warning,
1057                .maxlen         = sizeof (int),
1058                .mode           = 0644,
1059                .proc_handler   = proc_dointvec,
1060        },
1061#endif
1062#ifdef CONFIG_IA64
1063        {
1064                .procname       = "unaligned-dump-stack",
1065                .data           = &unaligned_dump_stack,
1066                .maxlen         = sizeof (int),
1067                .mode           = 0644,
1068                .proc_handler   = proc_dointvec,
1069        },
1070#endif
1071#ifdef CONFIG_DETECT_HUNG_TASK
1072        {
1073                .procname       = "hung_task_panic",
1074                .data           = &sysctl_hung_task_panic,
1075                .maxlen         = sizeof(int),
1076                .mode           = 0644,
1077                .proc_handler   = proc_dointvec_minmax,
1078                .extra1         = &zero,
1079                .extra2         = &one,
1080        },
1081        {
1082                .procname       = "hung_task_check_count",
1083                .data           = &sysctl_hung_task_check_count,
1084                .maxlen         = sizeof(unsigned long),
1085                .mode           = 0644,
1086                .proc_handler   = proc_doulongvec_minmax,
1087        },
1088        {
1089                .procname       = "hung_task_timeout_secs",
1090                .data           = &sysctl_hung_task_timeout_secs,
1091                .maxlen         = sizeof(unsigned long),
1092                .mode           = 0644,
1093                .proc_handler   = proc_dohung_task_timeout_secs,
1094                .extra2         = &hung_task_timeout_max,
1095        },
1096        {
1097                .procname       = "hung_task_warnings",
1098                .data           = &sysctl_hung_task_warnings,
1099                .maxlen         = sizeof(int),
1100                .mode           = 0644,
1101                .proc_handler   = proc_dointvec_minmax,
1102                .extra1         = &neg_one,
1103        },
1104#endif
1105#ifdef CONFIG_COMPAT
1106        {
1107                .procname       = "compat-log",
1108                .data           = &compat_log,
1109                .maxlen         = sizeof (int),
1110                .mode           = 0644,
1111                .proc_handler   = proc_dointvec,
1112        },
1113#endif
1114#ifdef CONFIG_RT_MUTEXES
1115        {
1116                .procname       = "max_lock_depth",
1117                .data           = &max_lock_depth,
1118                .maxlen         = sizeof(int),
1119                .mode           = 0644,
1120                .proc_handler   = proc_dointvec,
1121        },
1122#endif
1123        {
1124                .procname       = "poweroff_cmd",
1125                .data           = &poweroff_cmd,
1126                .maxlen         = POWEROFF_CMD_PATH_LEN,
1127                .mode           = 0644,
1128                .proc_handler   = proc_dostring,
1129        },
1130#ifdef CONFIG_KEYS
1131        {
1132                .procname       = "keys",
1133                .mode           = 0555,
1134                .child          = key_sysctls,
1135        },
1136#endif
1137#ifdef CONFIG_RCU_TORTURE_TEST
1138        {
1139                .procname       = "rcutorture_runnable",
1140                .data           = &rcutorture_runnable,
1141                .maxlen         = sizeof(int),
1142                .mode           = 0644,
1143                .proc_handler   = proc_dointvec,
1144        },
1145#endif
1146#ifdef CONFIG_PERF_EVENTS
1147        /*
1148         * User-space scripts rely on the existence of this file
1149         * as a feature check for perf_events being enabled.
1150         *
1151         * So it's an ABI, do not remove!
1152         */
1153        {
1154                .procname       = "perf_event_paranoid",
1155                .data           = &sysctl_perf_event_paranoid,
1156                .maxlen         = sizeof(sysctl_perf_event_paranoid),
1157                .mode           = 0644,
1158                .proc_handler   = proc_dointvec,
1159        },
1160        {
1161                .procname       = "perf_event_mlock_kb",
1162                .data           = &sysctl_perf_event_mlock,
1163                .maxlen         = sizeof(sysctl_perf_event_mlock),
1164                .mode           = 0644,
1165                .proc_handler   = proc_dointvec,
1166        },
1167        {
1168                .procname       = "perf_event_max_sample_rate",
1169                .data           = &sysctl_perf_event_sample_rate,
1170                .maxlen         = sizeof(sysctl_perf_event_sample_rate),
1171                .mode           = 0644,
1172                .proc_handler   = perf_proc_update_handler,
1173                .extra1         = &one,
1174        },
1175        {
1176                .procname       = "perf_cpu_time_max_percent",
1177                .data           = &sysctl_perf_cpu_time_max_percent,
1178                .maxlen         = sizeof(sysctl_perf_cpu_time_max_percent),
1179                .mode           = 0644,
1180                .proc_handler   = perf_cpu_time_max_percent_handler,
1181                .extra1         = &zero,
1182                .extra2         = &one_hundred,
1183        },
1184#endif
1185#ifdef CONFIG_KMEMCHECK
1186        {
1187                .procname       = "kmemcheck",
1188                .data           = &kmemcheck_enabled,
1189                .maxlen         = sizeof(int),
1190                .mode           = 0644,
1191                .proc_handler   = proc_dointvec,
1192        },
1193#endif
1194        {
1195                .procname       = "panic_on_warn",
1196                .data           = &panic_on_warn,
1197                .maxlen         = sizeof(int),
1198                .mode           = 0644,
1199                .proc_handler   = proc_dointvec_minmax,
1200                .extra1         = &zero,
1201                .extra2         = &one,
1202        },
1203        { }
1204};
1205
1206static struct ctl_table vm_table[] = {
1207        {
1208                .procname       = "overcommit_memory",
1209                .data           = &sysctl_overcommit_memory,
1210                .maxlen         = sizeof(sysctl_overcommit_memory),
1211                .mode           = 0644,
1212                .proc_handler   = proc_dointvec_minmax,
1213                .extra1         = &zero,
1214                .extra2         = &two,
1215        },
1216        {
1217                .procname       = "panic_on_oom",
1218                .data           = &sysctl_panic_on_oom,
1219                .maxlen         = sizeof(sysctl_panic_on_oom),
1220                .mode           = 0644,
1221                .proc_handler   = proc_dointvec_minmax,
1222                .extra1         = &zero,
1223                .extra2         = &two,
1224        },
1225        {
1226                .procname       = "oom_kill_allocating_task",
1227                .data           = &sysctl_oom_kill_allocating_task,
1228                .maxlen         = sizeof(sysctl_oom_kill_allocating_task),
1229                .mode           = 0644,
1230                .proc_handler   = proc_dointvec,
1231        },
1232        {
1233                .procname       = "oom_dump_tasks",
1234                .data           = &sysctl_oom_dump_tasks,
1235                .maxlen         = sizeof(sysctl_oom_dump_tasks),
1236                .mode           = 0644,
1237                .proc_handler   = proc_dointvec,
1238        },
1239        {
1240                .procname       = "overcommit_ratio",
1241                .data           = &sysctl_overcommit_ratio,
1242                .maxlen         = sizeof(sysctl_overcommit_ratio),
1243                .mode           = 0644,
1244                .proc_handler   = overcommit_ratio_handler,
1245        },
1246        {
1247                .procname       = "overcommit_kbytes",
1248                .data           = &sysctl_overcommit_kbytes,
1249                .maxlen         = sizeof(sysctl_overcommit_kbytes),
1250                .mode           = 0644,
1251                .proc_handler   = overcommit_kbytes_handler,
1252        },
1253        {
1254                .procname       = "page-cluster", 
1255                .data           = &page_cluster,
1256                .maxlen         = sizeof(int),
1257                .mode           = 0644,
1258                .proc_handler   = proc_dointvec_minmax,
1259                .extra1         = &zero,
1260        },
1261        {
1262                .procname       = "dirty_background_ratio",
1263                .data           = &dirty_background_ratio,
1264                .maxlen         = sizeof(dirty_background_ratio),
1265                .mode           = 0644,
1266                .proc_handler   = dirty_background_ratio_handler,
1267                .extra1         = &zero,
1268                .extra2         = &one_hundred,
1269        },
1270        {
1271                .procname       = "dirty_background_bytes",
1272                .data           = &dirty_background_bytes,
1273                .maxlen         = sizeof(dirty_background_bytes),
1274                .mode           = 0644,
1275                .proc_handler   = dirty_background_bytes_handler,
1276                .extra1         = &one_ul,
1277        },
1278        {
1279                .procname       = "dirty_ratio",
1280                .data           = &vm_dirty_ratio,
1281                .maxlen         = sizeof(vm_dirty_ratio),
1282                .mode           = 0644,
1283                .proc_handler   = dirty_ratio_handler,
1284                .extra1         = &zero,
1285                .extra2         = &one_hundred,
1286        },
1287        {
1288                .procname       = "dirty_bytes",
1289                .data           = &vm_dirty_bytes,
1290                .maxlen         = sizeof(vm_dirty_bytes),
1291                .mode           = 0644,
1292                .proc_handler   = dirty_bytes_handler,
1293                .extra1         = &dirty_bytes_min,
1294        },
1295        {
1296                .procname       = "dirty_writeback_centisecs",
1297                .data           = &dirty_writeback_interval,
1298                .maxlen         = sizeof(dirty_writeback_interval),
1299                .mode           = 0644,
1300                .proc_handler   = dirty_writeback_centisecs_handler,
1301        },
1302        {
1303                .procname       = "dirty_expire_centisecs",
1304                .data           = &dirty_expire_interval,
1305                .maxlen         = sizeof(dirty_expire_interval),
1306                .mode           = 0644,
1307                .proc_handler   = proc_dointvec_minmax,
1308                .extra1         = &zero,
1309        },
1310        {
1311                .procname       = "nr_pdflush_threads",
1312                .mode           = 0444 /* read-only */,
1313                .proc_handler   = pdflush_proc_obsolete,
1314        },
1315        {
1316                .procname       = "swappiness",
1317                .data           = &vm_swappiness,
1318                .maxlen         = sizeof(vm_swappiness),
1319                .mode           = 0644,
1320                .proc_handler   = proc_dointvec_minmax,
1321                .extra1         = &zero,
1322                .extra2         = &one_hundred,
1323        },
1324#ifdef CONFIG_HUGETLB_PAGE
1325        {
1326                .procname       = "nr_hugepages",
1327                .data           = NULL,
1328                .maxlen         = sizeof(unsigned long),
1329                .mode           = 0644,
1330                .proc_handler   = hugetlb_sysctl_handler,
1331                .extra1         = (void *)&hugetlb_zero,
1332                .extra2         = (void *)&hugetlb_infinity,
1333        },
1334#ifdef CONFIG_NUMA
1335        {
1336                .procname       = "nr_hugepages_mempolicy",
1337                .data           = NULL,
1338                .maxlen         = sizeof(unsigned long),
1339                .mode           = 0644,
1340                .proc_handler   = &hugetlb_mempolicy_sysctl_handler,
1341                .extra1         = (void *)&hugetlb_zero,
1342                .extra2         = (void *)&hugetlb_infinity,
1343        },
1344#endif
1345         {
1346                .procname       = "hugetlb_shm_group",
1347                .data           = &sysctl_hugetlb_shm_group,
1348                .maxlen         = sizeof(gid_t),
1349                .mode           = 0644,
1350                .proc_handler   = proc_dointvec,
1351         },
1352         {
1353                .procname       = "hugepages_treat_as_movable",
1354                .data           = &hugepages_treat_as_movable,
1355                .maxlen         = sizeof(int),
1356                .mode           = 0644,
1357                .proc_handler   = proc_dointvec,
1358        },
1359        {
1360                .procname       = "nr_overcommit_hugepages",
1361                .data           = NULL,
1362                .maxlen         = sizeof(unsigned long),
1363                .mode           = 0644,
1364                .proc_handler   = hugetlb_overcommit_handler,
1365                .extra1         = (void *)&hugetlb_zero,
1366                .extra2         = (void *)&hugetlb_infinity,
1367        },
1368#endif
1369        {
1370                .procname       = "lowmem_reserve_ratio",
1371                .data           = &sysctl_lowmem_reserve_ratio,
1372                .maxlen         = sizeof(sysctl_lowmem_reserve_ratio),
1373                .mode           = 0644,
1374                .proc_handler   = lowmem_reserve_ratio_sysctl_handler,
1375        },
1376        {
1377                .procname       = "drop_caches",
1378                .data           = &sysctl_drop_caches,
1379                .maxlen         = sizeof(int),
1380                .mode           = 0644,
1381                .proc_handler   = drop_caches_sysctl_handler,
1382                .extra1         = &one,
1383                .extra2         = &four,
1384        },
1385#ifdef CONFIG_COMPACTION
1386        {
1387                .procname       = "compact_memory",
1388                .data           = &sysctl_compact_memory,
1389                .maxlen         = sizeof(int),
1390                .mode           = 0200,
1391                .proc_handler   = sysctl_compaction_handler,
1392        },
1393        {
1394                .procname       = "extfrag_threshold",
1395                .data           = &sysctl_extfrag_threshold,
1396                .maxlen         = sizeof(int),
1397                .mode           = 0644,
1398                .proc_handler   = sysctl_extfrag_handler,
1399                .extra1         = &min_extfrag_threshold,
1400                .extra2         = &max_extfrag_threshold,
1401        },
1402
1403#endif /* CONFIG_COMPACTION */
1404        {
1405                .procname       = "min_free_kbytes",
1406                .data           = &min_free_kbytes,
1407                .maxlen         = sizeof(min_free_kbytes),
1408                .mode           = 0644,
1409                .proc_handler   = min_free_kbytes_sysctl_handler,
1410                .extra1         = &zero,
1411        },
1412        {
1413                .procname       = "percpu_pagelist_fraction",
1414                .data           = &percpu_pagelist_fraction,
1415                .maxlen         = sizeof(percpu_pagelist_fraction),
1416                .mode           = 0644,
1417                .proc_handler   = percpu_pagelist_fraction_sysctl_handler,
1418                .extra1         = &zero,
1419        },
1420#ifdef CONFIG_MMU
1421        {
1422                .procname       = "max_map_count",
1423                .data           = &sysctl_max_map_count,
1424                .maxlen         = sizeof(sysctl_max_map_count),
1425                .mode           = 0644,
1426                .proc_handler   = proc_dointvec_minmax,
1427                .extra1         = &zero,
1428        },
1429#else
1430        {
1431                .procname       = "nr_trim_pages",
1432                .data           = &sysctl_nr_trim_pages,
1433                .maxlen         = sizeof(sysctl_nr_trim_pages),
1434                .mode           = 0644,
1435                .proc_handler   = proc_dointvec_minmax,
1436                .extra1         = &zero,
1437        },
1438#endif
1439        {
1440                .procname       = "laptop_mode",
1441                .data           = &laptop_mode,
1442                .maxlen         = sizeof(laptop_mode),
1443                .mode           = 0644,
1444                .proc_handler   = proc_dointvec_jiffies,
1445        },
1446        {
1447                .procname       = "block_dump",
1448                .data           = &block_dump,
1449                .maxlen         = sizeof(block_dump),
1450                .mode           = 0644,
1451                .proc_handler   = proc_dointvec,
1452                .extra1         = &zero,
1453        },
1454        {
1455                .procname       = "vfs_cache_pressure",
1456                .data           = &sysctl_vfs_cache_pressure,
1457                .maxlen         = sizeof(sysctl_vfs_cache_pressure),
1458                .mode           = 0644,
1459                .proc_handler   = proc_dointvec,
1460                .extra1         = &zero,
1461        },
1462#ifdef HAVE_ARCH_PICK_MMAP_LAYOUT
1463        {
1464                .procname       = "legacy_va_layout",
1465                .data           = &sysctl_legacy_va_layout,
1466                .maxlen         = sizeof(sysctl_legacy_va_layout),
1467                .mode           = 0644,
1468                .proc_handler   = proc_dointvec,
1469                .extra1         = &zero,
1470        },
1471#endif
1472#ifdef CONFIG_NUMA
1473        {
1474                .procname       = "zone_reclaim_mode",
1475                .data           = &zone_reclaim_mode,
1476                .maxlen         = sizeof(zone_reclaim_mode),
1477                .mode           = 0644,
1478                .proc_handler   = proc_dointvec,
1479                .extra1         = &zero,
1480        },
1481        {
1482                .procname       = "min_unmapped_ratio",
1483                .data           = &sysctl_min_unmapped_ratio,
1484                .maxlen         = sizeof(sysctl_min_unmapped_ratio),
1485                .mode           = 0644,
1486                .proc_handler   = sysctl_min_unmapped_ratio_sysctl_handler,
1487                .extra1         = &zero,
1488                .extra2         = &one_hundred,
1489        },
1490        {
1491                .procname       = "min_slab_ratio",
1492                .data           = &sysctl_min_slab_ratio,
1493                .maxlen         = sizeof(sysctl_min_slab_ratio),
1494                .mode           = 0644,
1495                .proc_handler   = sysctl_min_slab_ratio_sysctl_handler,
1496                .extra1         = &zero,
1497                .extra2         = &one_hundred,
1498        },
1499#endif
1500#ifdef CONFIG_SMP
1501        {
1502                .procname       = "stat_interval",
1503                .data           = &sysctl_stat_interval,
1504                .maxlen         = sizeof(sysctl_stat_interval),
1505                .mode           = 0644,
1506                .proc_handler   = proc_dointvec_jiffies,
1507        },
1508#endif
1509#ifdef CONFIG_MMU
1510        {
1511                .procname       = "mmap_min_addr",
1512                .data           = &dac_mmap_min_addr,
1513                .maxlen         = sizeof(unsigned long),
1514                .mode           = 0644,
1515                .proc_handler   = mmap_min_addr_handler,
1516        },
1517#endif
1518#ifdef CONFIG_NUMA
1519        {
1520                .procname       = "numa_zonelist_order",
1521                .data           = &numa_zonelist_order,
1522                .maxlen         = NUMA_ZONELIST_ORDER_LEN,
1523                .mode           = 0644,
1524                .proc_handler   = numa_zonelist_order_handler,
1525        },
1526#endif
1527#if (defined(CONFIG_X86_32) && !defined(CONFIG_UML))|| \
1528   (defined(CONFIG_SUPERH) && defined(CONFIG_VSYSCALL))
1529        {
1530                .procname       = "vdso_enabled",
1531                .data           = &vdso_enabled,
1532                .maxlen         = sizeof(vdso_enabled),
1533                .mode           = 0644,
1534                .proc_handler   = proc_dointvec,
1535                .extra1         = &zero,
1536        },
1537#endif
1538#ifdef CONFIG_HIGHMEM
1539        {
1540                .procname       = "highmem_is_dirtyable",
1541                .data           = &vm_highmem_is_dirtyable,
1542                .maxlen         = sizeof(vm_highmem_is_dirtyable),
1543                .mode           = 0644,
1544                .proc_handler   = proc_dointvec_minmax,
1545                .extra1         = &zero,
1546                .extra2         = &one,
1547        },
1548#endif
1549#ifdef CONFIG_MEMORY_FAILURE
1550        {
1551                .procname       = "memory_failure_early_kill",
1552                .data           = &sysctl_memory_failure_early_kill,
1553                .maxlen         = sizeof(sysctl_memory_failure_early_kill),
1554                .mode           = 0644,
1555                .proc_handler   = proc_dointvec_minmax,
1556                .extra1         = &zero,
1557                .extra2         = &one,
1558        },
1559        {
1560                .procname       = "memory_failure_recovery",
1561                .data           = &sysctl_memory_failure_recovery,
1562                .maxlen         = sizeof(sysctl_memory_failure_recovery),
1563                .mode           = 0644,
1564                .proc_handler   = proc_dointvec_minmax,
1565                .extra1         = &zero,
1566                .extra2         = &one,
1567        },
1568#endif
1569        {
1570                .procname       = "user_reserve_kbytes",
1571                .data           = &sysctl_user_reserve_kbytes,
1572                .maxlen         = sizeof(sysctl_user_reserve_kbytes),
1573                .mode           = 0644,
1574                .proc_handler   = proc_doulongvec_minmax,
1575        },
1576        {
1577                .procname       = "admin_reserve_kbytes",
1578                .data           = &sysctl_admin_reserve_kbytes,
1579                .maxlen         = sizeof(sysctl_admin_reserve_kbytes),
1580                .mode           = 0644,
1581                .proc_handler   = proc_doulongvec_minmax,
1582        },
1583#ifdef CONFIG_HAVE_ARCH_MMAP_RND_BITS
1584        {
1585                .procname       = "mmap_rnd_bits",
1586                .data           = &mmap_rnd_bits,
1587                .maxlen         = sizeof(mmap_rnd_bits),
1588                .mode           = 0600,
1589                .proc_handler   = proc_dointvec_minmax,
1590                .extra1         = (void *)&mmap_rnd_bits_min,
1591                .extra2         = (void *)&mmap_rnd_bits_max,
1592        },
1593#endif
1594#ifdef CONFIG_HAVE_ARCH_MMAP_RND_COMPAT_BITS
1595        {
1596                .procname       = "mmap_rnd_compat_bits",
1597                .data           = &mmap_rnd_compat_bits,
1598                .maxlen         = sizeof(mmap_rnd_compat_bits),
1599                .mode           = 0600,
1600                .proc_handler   = proc_dointvec_minmax,
1601                .extra1         = (void *)&mmap_rnd_compat_bits_min,
1602                .extra2         = (void *)&mmap_rnd_compat_bits_max,
1603        },
1604#endif
1605        { }
1606};
1607
1608static struct ctl_table fs_table[] = {
1609        {
1610                .procname       = "inode-nr",
1611                .data           = &inodes_stat,
1612                .maxlen         = 2*sizeof(int),
1613                .mode           = 0444,
1614                .proc_handler   = proc_nr_inodes,
1615        },
1616        {
1617                .procname       = "inode-state",
1618                .data           = &inodes_stat,
1619                .maxlen         = 7*sizeof(int),
1620                .mode           = 0444,
1621                .proc_handler   = proc_nr_inodes,
1622        },
1623        {
1624                .procname       = "file-nr",
1625                .data           = &files_stat,
1626                .maxlen         = sizeof(files_stat),
1627                .mode           = 0444,
1628                .proc_handler   = proc_nr_files,
1629        },
1630        {
1631                .procname       = "file-max",
1632                .data           = &files_stat.max_files,
1633                .maxlen         = sizeof(files_stat.max_files),
1634                .mode           = 0644,
1635                .proc_handler   = proc_doulongvec_minmax,
1636        },
1637        {
1638                .procname       = "nr_open",
1639                .data           = &sysctl_nr_open,
1640                .maxlen         = sizeof(int),
1641                .mode           = 0644,
1642                .proc_handler   = proc_dointvec_minmax,
1643                .extra1         = &sysctl_nr_open_min,
1644                .extra2         = &sysctl_nr_open_max,
1645        },
1646        {
1647                .procname       = "dentry-state",
1648                .data           = &dentry_stat,
1649                .maxlen         = 6*sizeof(int),
1650                .mode           = 0444,
1651                .proc_handler   = proc_nr_dentry,
1652        },
1653        {
1654                .procname       = "overflowuid",
1655                .data           = &fs_overflowuid,
1656                .maxlen         = sizeof(int),
1657                .mode           = 0644,
1658                .proc_handler   = proc_dointvec_minmax,
1659                .extra1         = &minolduid,
1660                .extra2         = &maxolduid,
1661        },
1662        {
1663                .procname       = "overflowgid",
1664                .data           = &fs_overflowgid,
1665                .maxlen         = sizeof(int),
1666                .mode           = 0644,
1667                .proc_handler   = proc_dointvec_minmax,
1668                .extra1         = &minolduid,
1669                .extra2         = &maxolduid,
1670        },
1671#ifdef CONFIG_FILE_LOCKING
1672        {
1673                .procname       = "leases-enable",
1674                .data           = &leases_enable,
1675                .maxlen         = sizeof(int),
1676                .mode           = 0644,
1677                .proc_handler   = proc_dointvec,
1678        },
1679#endif
1680#ifdef CONFIG_DNOTIFY
1681        {
1682                .procname       = "dir-notify-enable",
1683                .data           = &dir_notify_enable,
1684                .maxlen         = sizeof(int),
1685                .mode           = 0644,
1686                .proc_handler   = proc_dointvec,
1687        },
1688#endif
1689#ifdef CONFIG_MMU
1690#ifdef CONFIG_FILE_LOCKING
1691        {
1692                .procname       = "lease-break-time",
1693                .data           = &lease_break_time,
1694                .maxlen         = sizeof(int),
1695                .mode           = 0644,
1696                .proc_handler   = proc_dointvec,
1697        },
1698#endif
1699#ifdef CONFIG_AIO
1700        {
1701                .procname       = "aio-nr",
1702                .data           = &aio_nr,
1703                .maxlen         = sizeof(aio_nr),
1704                .mode           = 0444,
1705                .proc_handler   = proc_doulongvec_minmax,
1706        },
1707        {
1708                .procname       = "aio-max-nr",
1709                .data           = &aio_max_nr,
1710                .maxlen         = sizeof(aio_max_nr),
1711                .mode           = 0644,
1712                .proc_handler   = proc_doulongvec_minmax,
1713        },
1714#endif /* CONFIG_AIO */
1715#ifdef CONFIG_INOTIFY_USER
1716        {
1717                .procname       = "inotify",
1718                .mode           = 0555,
1719                .child          = inotify_table,
1720        },
1721#endif  
1722#ifdef CONFIG_EPOLL
1723        {
1724                .procname       = "epoll",
1725                .mode           = 0555,
1726                .child          = epoll_table,
1727        },
1728#endif
1729#endif
1730        {
1731                .procname       = "protected_symlinks",
1732                .data           = &sysctl_protected_symlinks,
1733                .maxlen         = sizeof(int),
1734                .mode           = 0600,
1735                .proc_handler   = proc_dointvec_minmax,
1736                .extra1         = &zero,
1737                .extra2         = &one,
1738        },
1739        {
1740                .procname       = "protected_hardlinks",
1741                .data           = &sysctl_protected_hardlinks,
1742                .maxlen         = sizeof(int),
1743                .mode           = 0600,
1744                .proc_handler   = proc_dointvec_minmax,
1745                .extra1         = &zero,
1746                .extra2         = &one,
1747        },
1748        {
1749                .procname       = "suid_dumpable",
1750                .data           = &suid_dumpable,
1751                .maxlen         = sizeof(int),
1752                .mode           = 0644,
1753                .proc_handler   = proc_dointvec_minmax_coredump,
1754                .extra1         = &zero,
1755                .extra2         = &two,
1756        },
1757#if defined(CONFIG_BINFMT_MISC) || defined(CONFIG_BINFMT_MISC_MODULE)
1758        {
1759                .procname       = "binfmt_misc",
1760                .mode           = 0555,
1761                .child          = sysctl_mount_point,
1762        },
1763#endif
1764        {
1765                .procname       = "pipe-max-size",
1766                .data           = &pipe_max_size,
1767                .maxlen         = sizeof(pipe_max_size),
1768                .mode           = 0644,
1769                .proc_handler   = &pipe_proc_fn,
1770                .extra1         = &pipe_min_size,
1771        },
1772        {
1773                .procname       = "pipe-user-pages-hard",
1774                .data           = &pipe_user_pages_hard,
1775                .maxlen         = sizeof(pipe_user_pages_hard),
1776                .mode           = 0644,
1777                .proc_handler   = proc_doulongvec_minmax,
1778        },
1779        {
1780                .procname       = "pipe-user-pages-soft",
1781                .data           = &pipe_user_pages_soft,
1782                .maxlen         = sizeof(pipe_user_pages_soft),
1783                .mode           = 0644,
1784                .proc_handler   = proc_doulongvec_minmax,
1785        },
1786        {
1787                .procname       = "mount-max",
1788                .data           = &sysctl_mount_max,
1789                .maxlen         = sizeof(unsigned int),
1790                .mode           = 0644,
1791                .proc_handler   = proc_dointvec_minmax,
1792                .extra1         = &one,
1793        },
1794        { }
1795};
1796
1797static struct ctl_table debug_table[] = {
1798#ifdef CONFIG_SYSCTL_EXCEPTION_TRACE
1799        {
1800                .procname       = "exception-trace",
1801                .data           = &show_unhandled_signals,
1802                .maxlen         = sizeof(int),
1803                .mode           = 0644,
1804                .proc_handler   = proc_dointvec
1805        },
1806#endif
1807#if defined(CONFIG_OPTPROBES)
1808        {
1809                .procname       = "kprobes-optimization",
1810                .data           = &sysctl_kprobes_optimization,
1811                .maxlen         = sizeof(int),
1812                .mode           = 0644,
1813                .proc_handler   = proc_kprobes_optimization_handler,
1814                .extra1         = &zero,
1815                .extra2         = &one,
1816        },
1817#endif
1818#if defined(CONFIG_TREE_RCU) || defined(CONFIG_PREEMPT_RCU)
1819        {
1820                .procname       = "panic_on_rcu_stall",
1821                .data           = &sysctl_panic_on_rcu_stall,
1822                .maxlen         = sizeof(sysctl_panic_on_rcu_stall),
1823                .mode           = 0644,
1824                .proc_handler   = proc_dointvec_minmax,
1825                .extra1         = &zero,
1826                .extra2         = &one,
1827        },
1828#endif
1829        { }
1830};
1831
1832static struct ctl_table dev_table[] = {
1833        { }
1834};
1835
1836int __init sysctl_init(void)
1837{
1838        struct ctl_table_header *hdr;
1839
1840        hdr = register_sysctl_table(sysctl_base_table);
1841        kmemleak_not_leak(hdr);
1842        return 0;
1843}
1844
1845#endif /* CONFIG_SYSCTL */
1846
1847/*
1848 * /proc/sys support
1849 */
1850
1851#ifdef CONFIG_PROC_SYSCTL
1852
1853static int _proc_do_string(char *data, int maxlen, int write,
1854                           char __user *buffer,
1855                           size_t *lenp, loff_t *ppos)
1856{
1857        size_t len;
1858        char __user *p;
1859        char c;
1860
1861        if (!data || !maxlen || !*lenp) {
1862                *lenp = 0;
1863                return 0;
1864        }
1865
1866        if (write) {
1867                if (sysctl_writes_strict == SYSCTL_WRITES_STRICT) {
1868                        /* Only continue writes not past the end of buffer. */
1869                        len = strlen(data);
1870                        if (len > maxlen - 1)
1871                                len = maxlen - 1;
1872
1873                        if (*ppos > len)
1874                                return 0;
1875                        len = *ppos;
1876                } else {
1877                        /* Start writing from beginning of buffer. */
1878                        len = 0;
1879                }
1880
1881                *ppos += *lenp;
1882                p = buffer;
1883                while ((p - buffer) < *lenp && len < maxlen - 1) {
1884                        if (get_user(c, p++))
1885                                return -EFAULT;
1886                        if (c == 0 || c == '\n')
1887                                break;
1888                        data[len++] = c;
1889                }
1890                data[len] = 0;
1891        } else {
1892                len = strlen(data);
1893                if (len > maxlen)
1894                        len = maxlen;
1895
1896                if (*ppos > len) {
1897                        *lenp = 0;
1898                        return 0;
1899                }
1900
1901                data += *ppos;
1902                len  -= *ppos;
1903
1904                if (len > *lenp)
1905                        len = *lenp;
1906                if (len)
1907                        if (copy_to_user(buffer, data, len))
1908                                return -EFAULT;
1909                if (len < *lenp) {
1910                        if (put_user('\n', buffer + len))
1911                                return -EFAULT;
1912                        len++;
1913                }
1914                *lenp = len;
1915                *ppos += len;
1916        }
1917        return 0;
1918}
1919
1920static void warn_sysctl_write(struct ctl_table *table)
1921{
1922        pr_warn_once("%s wrote to %s when file position was not 0!\n"
1923                "This will not be supported in the future. To silence this\n"
1924                "warning, set kernel.sysctl_writes_strict = -1\n",
1925                current->comm, table->procname);
1926}
1927
1928/**
1929 * proc_first_pos_non_zero_ignore - check if firs position is allowed
1930 * @ppos: file position
1931 * @table: the sysctl table
1932 *
1933 * Returns true if the first position is non-zero and the sysctl_writes_strict
1934 * mode indicates this is not allowed for numeric input types. String proc
1935 * hadlers can ignore the return value.
1936 */
1937static bool proc_first_pos_non_zero_ignore(loff_t *ppos,
1938                                           struct ctl_table *table)
1939{
1940        if (!*ppos)
1941                return false;
1942
1943        switch (sysctl_writes_strict) {
1944        case SYSCTL_WRITES_STRICT:
1945                return true;
1946        case SYSCTL_WRITES_WARN:
1947                warn_sysctl_write(table);
1948                return false;
1949        default:
1950                return false;
1951        }
1952}
1953
1954/**
1955 * proc_dostring - read a string sysctl
1956 * @table: the sysctl table
1957 * @write: %TRUE if this is a write to the sysctl file
1958 * @buffer: the user buffer
1959 * @lenp: the size of the user buffer
1960 * @ppos: file position
1961 *
1962 * Reads/writes a string from/to the user buffer. If the kernel
1963 * buffer provided is not large enough to hold the string, the
1964 * string is truncated. The copied string is %NULL-terminated.
1965 * If the string is being read by the user process, it is copied
1966 * and a newline '\n' is added. It is truncated if the buffer is
1967 * not large enough.
1968 *
1969 * Returns 0 on success.
1970 */
1971int proc_dostring(struct ctl_table *table, int write,
1972                  void __user *buffer, size_t *lenp, loff_t *ppos)
1973{
1974        if (write)
1975                proc_first_pos_non_zero_ignore(ppos, table);
1976
1977        return _proc_do_string((char *)(table->data), table->maxlen, write,
1978                               (char __user *)buffer, lenp, ppos);
1979}
1980
1981static size_t proc_skip_spaces(char **buf)
1982{
1983        size_t ret;
1984        char *tmp = skip_spaces(*buf);
1985        ret = tmp - *buf;
1986        *buf = tmp;
1987        return ret;
1988}
1989
1990static void proc_skip_char(char **buf, size_t *size, const char v)
1991{
1992        while (*size) {
1993                if (**buf != v)
1994                        break;
1995                (*size)--;
1996                (*buf)++;
1997        }
1998}
1999
2000#define TMPBUFLEN 22
2001/**
2002 * proc_get_long - reads an ASCII formatted integer from a user buffer
2003 *
2004 * @buf: a kernel buffer
2005 * @size: size of the kernel buffer
2006 * @val: this is where the number will be stored
2007 * @neg: set to %TRUE if number is negative
2008 * @perm_tr: a vector which contains the allowed trailers
2009 * @perm_tr_len: size of the perm_tr vector
2010 * @tr: pointer to store the trailer character
2011 *
2012 * In case of success %0 is returned and @buf and @size are updated with
2013 * the amount of bytes read. If @tr is non-NULL and a trailing
2014 * character exists (size is non-zero after returning from this
2015 * function), @tr is updated with the trailing character.
2016 */
2017static int proc_get_long(char **buf, size_t *size,
2018                          unsigned long *val, bool *neg,
2019                          const char *perm_tr, unsigned perm_tr_len, char *tr)
2020{
2021        int len;
2022        char *p, tmp[TMPBUFLEN];
2023
2024        if (!*size)
2025                return -EINVAL;
2026
2027        len = *size;
2028        if (len > TMPBUFLEN - 1)
2029                len = TMPBUFLEN - 1;
2030
2031        memcpy(tmp, *buf, len);
2032
2033        tmp[len] = 0;
2034        p = tmp;
2035        if (*p == '-' && *size > 1) {
2036                *neg = true;
2037                p++;
2038        } else
2039                *neg = false;
2040        if (!isdigit(*p))
2041                return -EINVAL;
2042
2043        *val = simple_strtoul(p, &p, 0);
2044
2045        len = p - tmp;
2046
2047        /* We don't know if the next char is whitespace thus we may accept
2048         * invalid integers (e.g. 1234...a) or two integers instead of one
2049         * (e.g. 123...1). So lets not allow such large numbers. */
2050        if (len == TMPBUFLEN - 1)
2051                return -EINVAL;
2052
2053        if (len < *size && perm_tr_len && !memchr(perm_tr, *p, perm_tr_len))
2054                return -EINVAL;
2055
2056        if (tr && (len < *size))
2057                *tr = *p;
2058
2059        *buf += len;
2060        *size -= len;
2061
2062        return 0;
2063}
2064
2065/**
2066 * proc_put_long - converts an integer to a decimal ASCII formatted string
2067 *
2068 * @buf: the user buffer
2069 * @size: the size of the user buffer
2070 * @val: the integer to be converted
2071 * @neg: sign of the number, %TRUE for negative
2072 *
2073 * In case of success %0 is returned and @buf and @size are updated with
2074 * the amount of bytes written.
2075 */
2076static int proc_put_long(void __user **buf, size_t *size, unsigned long val,
2077                          bool neg)
2078{
2079        int len;
2080        char tmp[TMPBUFLEN], *p = tmp;
2081
2082        sprintf(p, "%s%lu", neg ? "-" : "", val);
2083        len = strlen(tmp);
2084        if (len > *size)
2085                len = *size;
2086        if (copy_to_user(*buf, tmp, len))
2087                return -EFAULT;
2088        *size -= len;
2089        *buf += len;
2090        return 0;
2091}
2092#undef TMPBUFLEN
2093
2094static int proc_put_char(void __user **buf, size_t *size, char c)
2095{
2096        if (*size) {
2097                char __user **buffer = (char __user **)buf;
2098                if (put_user(c, *buffer))
2099                        return -EFAULT;
2100                (*size)--, (*buffer)++;
2101                *buf = *buffer;
2102        }
2103        return 0;
2104}
2105
2106static int do_proc_dointvec_conv(bool *negp, unsigned long *lvalp,
2107                                 int *valp,
2108                                 int write, void *data)
2109{
2110        if (write) {
2111                if (*negp) {
2112                        if (*lvalp > (unsigned long) INT_MAX + 1)
2113                                return -EINVAL;
2114                        *valp = -*lvalp;
2115                } else {
2116                        if (*lvalp > (unsigned long) INT_MAX)
2117                                return -EINVAL;
2118                        *valp = *lvalp;
2119                }
2120        } else {
2121                int val = *valp;
2122                if (val < 0) {
2123                        *negp = true;
2124                        *lvalp = (unsigned long)-val;
2125                } else {
2126                        *negp = false;
2127                        *lvalp = (unsigned long)val;
2128                }
2129        }
2130        return 0;
2131}
2132
2133static int do_proc_douintvec_conv(unsigned long *lvalp,
2134                                  unsigned int *valp,
2135                                  int write, void *data)
2136{
2137        if (write) {
2138                if (*lvalp > UINT_MAX)
2139                        return -EINVAL;
2140                *valp = *lvalp;
2141        } else {
2142                unsigned int val = *valp;
2143                *lvalp = (unsigned long)val;
2144        }
2145        return 0;
2146}
2147
2148static const char proc_wspace_sep[] = { ' ', '\t', '\n' };
2149
2150static int __do_proc_dointvec(void *tbl_data, struct ctl_table *table,
2151                  int write, void __user *buffer,
2152                  size_t *lenp, loff_t *ppos,
2153                  int (*conv)(bool *negp, unsigned long *lvalp, int *valp,
2154                              int write, void *data),
2155                  void *data)
2156{
2157        int *i, vleft, first = 1, err = 0;
2158        unsigned long page = 0;
2159        size_t left;
2160        char *kbuf;
2161        
2162        if (!tbl_data || !table->maxlen || !*lenp || (*ppos && !write)) {
2163                *lenp = 0;
2164                return 0;
2165        }
2166        
2167        i = (int *) tbl_data;
2168        vleft = table->maxlen / sizeof(*i);
2169        left = *lenp;
2170
2171        if (!conv)
2172                conv = do_proc_dointvec_conv;
2173
2174        if (write) {
2175                if (proc_first_pos_non_zero_ignore(ppos, table))
2176                        goto out;
2177
2178                if (left > PAGE_SIZE - 1)
2179                        left = PAGE_SIZE - 1;
2180                page = __get_free_page(GFP_TEMPORARY);
2181                kbuf = (char *) page;
2182                if (!kbuf)
2183                        return -ENOMEM;
2184                if (copy_from_user(kbuf, buffer, left)) {
2185                        err = -EFAULT;
2186                        goto free;
2187                }
2188                kbuf[left] = 0;
2189        }
2190
2191        for (; left && vleft--; i++, first=0) {
2192                unsigned long lval;
2193                bool neg;
2194
2195                if (write) {
2196                        left -= proc_skip_spaces(&kbuf);
2197
2198                        if (!left)
2199                                break;
2200                        err = proc_get_long(&kbuf, &left, &lval, &neg,
2201                                             proc_wspace_sep,
2202                                             sizeof(proc_wspace_sep), NULL);
2203                        if (err)
2204                                break;
2205                        if (conv(&neg, &lval, i, 1, data)) {
2206                                err = -EINVAL;
2207                                break;
2208                        }
2209                } else {
2210                        if (conv(&neg, &lval, i, 0, data)) {
2211                                err = -EINVAL;
2212                                break;
2213                        }
2214                        if (!first)
2215                                err = proc_put_char(&buffer, &left, '\t');
2216                        if (err)
2217                                break;
2218                        err = proc_put_long(&buffer, &left, lval, neg);
2219                        if (err)
2220                                break;
2221                }
2222        }
2223
2224        if (!write && !first && left && !err)
2225                err = proc_put_char(&buffer, &left, '\n');
2226        if (write && !err && left)
2227                left -= proc_skip_spaces(&kbuf);
2228free:
2229        if (write) {
2230                free_page(page);
2231                if (first)
2232                        return err ? : -EINVAL;
2233        }
2234        *lenp -= left;
2235out:
2236        *ppos += *lenp;
2237        return err;
2238}
2239
2240static int do_proc_dointvec(struct ctl_table *table, int write,
2241                  void __user *buffer, size_t *lenp, loff_t *ppos,
2242                  int (*conv)(bool *negp, unsigned long *lvalp, int *valp,
2243                              int write, void *data),
2244                  void *data)
2245{
2246        return __do_proc_dointvec(table->data, table, write,
2247                        buffer, lenp, ppos, conv, data);
2248}
2249
2250static int do_proc_douintvec_w(unsigned int *tbl_data,
2251                               struct ctl_table *table,
2252                               void __user *buffer,
2253                               size_t *lenp, loff_t *ppos,
2254                               int (*conv)(unsigned long *lvalp,
2255                                           unsigned int *valp,
2256                                           int write, void *data),
2257                               void *data)
2258{
2259        unsigned long lval;
2260        int err = 0;
2261        size_t left;
2262        bool neg;
2263        char *kbuf = NULL, *p;
2264
2265        left = *lenp;
2266
2267        if (proc_first_pos_non_zero_ignore(ppos, table))
2268                goto bail_early;
2269
2270        if (left > PAGE_SIZE - 1)
2271                left = PAGE_SIZE - 1;
2272
2273        p = kbuf = memdup_user_nul(buffer, left);
2274        if (IS_ERR(kbuf))
2275                return -EINVAL;
2276
2277        left -= proc_skip_spaces(&p);
2278        if (!left) {
2279                err = -EINVAL;
2280                goto out_free;
2281        }
2282
2283        err = proc_get_long(&p, &left, &lval, &neg,
2284                             proc_wspace_sep,
2285                             sizeof(proc_wspace_sep), NULL);
2286        if (err || neg) {
2287                err = -EINVAL;
2288                goto out_free;
2289        }
2290
2291        if (conv(&lval, tbl_data, 1, data)) {
2292                err = -EINVAL;
2293                goto out_free;
2294        }
2295
2296        if (!err && left)
2297                left -= proc_skip_spaces(&p);
2298
2299out_free:
2300        kfree(kbuf);
2301        if (err)
2302                return -EINVAL;
2303
2304        return 0;
2305
2306        /* This is in keeping with old __do_proc_dointvec() */
2307bail_early:
2308        *ppos += *lenp;
2309        return err;
2310}
2311
2312static int do_proc_douintvec_r(unsigned int *tbl_data, void __user *buffer,
2313                               size_t *lenp, loff_t *ppos,
2314                               int (*conv)(unsigned long *lvalp,
2315                                           unsigned int *valp,
2316                                           int write, void *data),
2317                               void *data)
2318{
2319        unsigned long lval;
2320        int err = 0;
2321        size_t left;
2322
2323        left = *lenp;
2324
2325        if (conv(&lval, tbl_data, 0, data)) {
2326                err = -EINVAL;
2327                goto out;
2328        }
2329
2330        err = proc_put_long(&buffer, &left, lval, false);
2331        if (err || !left)
2332                goto out;
2333
2334        err = proc_put_char(&buffer, &left, '\n');
2335
2336out:
2337        *lenp -= left;
2338        *ppos += *lenp;
2339
2340        return err;
2341}
2342
2343static int __do_proc_douintvec(void *tbl_data, struct ctl_table *table,
2344                               int write, void __user *buffer,
2345                               size_t *lenp, loff_t *ppos,
2346                               int (*conv)(unsigned long *lvalp,
2347                                           unsigned int *valp,
2348                                           int write, void *data),
2349                               void *data)
2350{
2351        unsigned int *i, vleft;
2352
2353        if (!tbl_data || !table->maxlen || !*lenp || (*ppos && !write)) {
2354                *lenp = 0;
2355                return 0;
2356        }
2357
2358        i = (unsigned int *) tbl_data;
2359        vleft = table->maxlen / sizeof(*i);
2360
2361        /*
2362         * Arrays are not supported, keep this simple. *Do not* add
2363         * support for them.
2364         */
2365        if (vleft != 1) {
2366                *lenp = 0;
2367                return -EINVAL;
2368        }
2369
2370        if (!conv)
2371                conv = do_proc_douintvec_conv;
2372
2373        if (write)
2374                return do_proc_douintvec_w(i, table, buffer, lenp, ppos,
2375                                           conv, data);
2376        return do_proc_douintvec_r(i, buffer, lenp, ppos, conv, data);
2377}
2378
2379static int do_proc_douintvec(struct ctl_table *table, int write,
2380                             void __user *buffer, size_t *lenp, loff_t *ppos,
2381                             int (*conv)(unsigned long *lvalp,
2382                                         unsigned int *valp,
2383                                         int write, void *data),
2384                             void *data)
2385{
2386        return __do_proc_douintvec(table->data, table, write,
2387                                   buffer, lenp, ppos, conv, data);
2388}
2389
2390/**
2391 * proc_dointvec - read a vector of integers
2392 * @table: the sysctl table
2393 * @write: %TRUE if this is a write to the sysctl file
2394 * @buffer: the user buffer
2395 * @lenp: the size of the user buffer
2396 * @ppos: file position
2397 *
2398 * Reads/writes up to table->maxlen/sizeof(unsigned int) integer
2399 * values from/to the user buffer, treated as an ASCII string. 
2400 *
2401 * Returns 0 on success.
2402 */
2403int proc_dointvec(struct ctl_table *table, int write,
2404                     void __user *buffer, size_t *lenp, loff_t *ppos)
2405{
2406        return do_proc_dointvec(table, write, buffer, lenp, ppos, NULL, NULL);
2407}
2408
2409/**
2410 * proc_douintvec - read a vector of unsigned integers
2411 * @table: the sysctl table
2412 * @write: %TRUE if this is a write to the sysctl file
2413 * @buffer: the user buffer
2414 * @lenp: the size of the user buffer
2415 * @ppos: file position
2416 *
2417 * Reads/writes up to table->maxlen/sizeof(unsigned int) unsigned integer
2418 * values from/to the user buffer, treated as an ASCII string.
2419 *
2420 * Returns 0 on success.
2421 */
2422int proc_douintvec(struct ctl_table *table, int write,
2423                     void __user *buffer, size_t *lenp, loff_t *ppos)
2424{
2425        return do_proc_douintvec(table, write, buffer, lenp, ppos,
2426                                 do_proc_douintvec_conv, NULL);
2427}
2428
2429/*
2430 * Taint values can only be increased
2431 * This means we can safely use a temporary.
2432 */
2433static int proc_taint(struct ctl_table *table, int write,
2434                               void __user *buffer, size_t *lenp, loff_t *ppos)
2435{
2436        struct ctl_table t;
2437        unsigned long tmptaint = get_taint();
2438        int err;
2439
2440        if (write && !capable(CAP_SYS_ADMIN))
2441                return -EPERM;
2442
2443        t = *table;
2444        t.data = &tmptaint;
2445        err = proc_doulongvec_minmax(&t, write, buffer, lenp, ppos);
2446        if (err < 0)
2447                return err;
2448
2449        if (write) {
2450                /*
2451                 * Poor man's atomic or. Not worth adding a primitive
2452                 * to everyone's atomic.h for this
2453                 */
2454                int i;
2455                for (i = 0; i < BITS_PER_LONG && tmptaint >> i; i++) {
2456                        if ((tmptaint >> i) & 1)
2457                                add_taint(i, LOCKDEP_STILL_OK);
2458                }
2459        }
2460
2461        return err;
2462}
2463
2464#ifdef CONFIG_PRINTK
2465static int proc_dointvec_minmax_sysadmin(struct ctl_table *table, int write,
2466                                void __user *buffer, size_t *lenp, loff_t *ppos)
2467{
2468        if (write && !capable(CAP_SYS_ADMIN))
2469                return -EPERM;
2470
2471        return proc_dointvec_minmax(table, write, buffer, lenp, ppos);
2472}
2473#endif
2474
2475struct do_proc_dointvec_minmax_conv_param {
2476        int *min;
2477        int *max;
2478};
2479
2480static int do_proc_dointvec_minmax_conv(bool *negp, unsigned long *lvalp,
2481                                        int *valp,
2482                                        int write, void *data)
2483{
2484        struct do_proc_dointvec_minmax_conv_param *param = data;
2485        if (write) {
2486                int val = *negp ? -*lvalp : *lvalp;
2487                if ((param->min && *param->min > val) ||
2488                    (param->max && *param->max < val))
2489                        return -EINVAL;
2490                *valp = val;
2491        } else {
2492                int val = *valp;
2493                if (val < 0) {
2494                        *negp = true;
2495                        *lvalp = (unsigned long)-val;
2496                } else {
2497                        *negp = false;
2498                        *lvalp = (unsigned long)val;
2499                }
2500        }
2501        return 0;
2502}
2503
2504/**
2505 * proc_dointvec_minmax - read a vector of integers with min/max values
2506 * @table: the sysctl table
2507 * @write: %TRUE if this is a write to the sysctl file
2508 * @buffer: the user buffer
2509 * @lenp: the size of the user buffer
2510 * @ppos: file position
2511 *
2512 * Reads/writes up to table->maxlen/sizeof(unsigned int) integer
2513 * values from/to the user buffer, treated as an ASCII string.
2514 *
2515 * This routine will ensure the values are within the range specified by
2516 * table->extra1 (min) and table->extra2 (max).
2517 *
2518 * Returns 0 on success.
2519 */
2520int proc_dointvec_minmax(struct ctl_table *table, int write,
2521                  void __user *buffer, size_t *lenp, loff_t *ppos)
2522{
2523        struct do_proc_dointvec_minmax_conv_param param = {
2524                .min = (int *) table->extra1,
2525                .max = (int *) table->extra2,
2526        };
2527        return do_proc_dointvec(table, write, buffer, lenp, ppos,
2528                                do_proc_dointvec_minmax_conv, &param);
2529}
2530
2531struct do_proc_douintvec_minmax_conv_param {
2532        unsigned int *min;
2533        unsigned int *max;
2534};
2535
2536static int do_proc_douintvec_minmax_conv(unsigned long *lvalp,
2537                                         unsigned int *valp,
2538                                         int write, void *data)
2539{
2540        struct do_proc_douintvec_minmax_conv_param *param = data;
2541
2542        if (write) {
2543                unsigned int val = *lvalp;
2544
2545                if (*lvalp > UINT_MAX)
2546                        return -EINVAL;
2547
2548                if ((param->min && *param->min > val) ||
2549                    (param->max && *param->max < val))
2550                        return -ERANGE;
2551
2552                *valp = val;
2553        } else {
2554                unsigned int val = *valp;
2555                *lvalp = (unsigned long) val;
2556        }
2557
2558        return 0;
2559}
2560
2561/**
2562 * proc_douintvec_minmax - read a vector of unsigned ints with min/max values
2563 * @table: the sysctl table
2564 * @write: %TRUE if this is a write to the sysctl file
2565 * @buffer: the user buffer
2566 * @lenp: the size of the user buffer
2567 * @ppos: file position
2568 *
2569 * Reads/writes up to table->maxlen/sizeof(unsigned int) unsigned integer
2570 * values from/to the user buffer, treated as an ASCII string. Negative
2571 * strings are not allowed.
2572 *
2573 * This routine will ensure the values are within the range specified by
2574 * table->extra1 (min) and table->extra2 (max). There is a final sanity
2575 * check for UINT_MAX to avoid having to support wrap around uses from
2576 * userspace.
2577 *
2578 * Returns 0 on success.
2579 */
2580int proc_douintvec_minmax(struct ctl_table *table, int write,
2581                          void __user *buffer, size_t *lenp, loff_t *ppos)
2582{
2583        struct do_proc_douintvec_minmax_conv_param param = {
2584                .min = (unsigned int *) table->extra1,
2585                .max = (unsigned int *) table->extra2,
2586        };
2587        return do_proc_douintvec(table, write, buffer, lenp, ppos,
2588                                 do_proc_douintvec_minmax_conv, &param);
2589}
2590
2591struct do_proc_dopipe_max_size_conv_param {
2592        unsigned int *min;
2593};
2594
2595static int do_proc_dopipe_max_size_conv(unsigned long *lvalp,
2596                                        unsigned int *valp,
2597                                        int write, void *data)
2598{
2599        struct do_proc_dopipe_max_size_conv_param *param = data;
2600
2601        if (write) {
2602                unsigned int val;
2603
2604                if (*lvalp > UINT_MAX)
2605                        return -EINVAL;
2606
2607                val = round_pipe_size(*lvalp);
2608                if (val == 0)
2609                        return -EINVAL;
2610
2611                if (param->min && *param->min > val)
2612                        return -ERANGE;
2613
2614                *valp = val;
2615        } else {
2616                unsigned int val = *valp;
2617                *lvalp = (unsigned long) val;
2618        }
2619
2620        return 0;
2621}
2622
2623int proc_dopipe_max_size(struct ctl_table *table, int write,
2624                         void __user *buffer, size_t *lenp, loff_t *ppos)
2625{
2626        struct do_proc_dopipe_max_size_conv_param param = {
2627                .min = (unsigned int *) table->extra1,
2628        };
2629        return do_proc_douintvec(table, write, buffer, lenp, ppos,
2630                                 do_proc_dopipe_max_size_conv, &param);
2631}
2632
2633static void validate_coredump_safety(void)
2634{
2635#ifdef CONFIG_COREDUMP
2636        if (suid_dumpable == SUID_DUMP_ROOT &&
2637            core_pattern[0] != '/' && core_pattern[0] != '|') {
2638                printk(KERN_WARNING "Unsafe core_pattern used with "\
2639                        "suid_dumpable=2. Pipe handler or fully qualified "\
2640                        "core dump path required.\n");
2641        }
2642#endif
2643}
2644
2645static int proc_dointvec_minmax_coredump(struct ctl_table *table, int write,
2646                void __user *buffer, size_t *lenp, loff_t *ppos)
2647{
2648        int error = proc_dointvec_minmax(table, write, buffer, lenp, ppos);
2649        if (!error)
2650                validate_coredump_safety();
2651        return error;
2652}
2653
2654#ifdef CONFIG_COREDUMP
2655static int proc_dostring_coredump(struct ctl_table *table, int write,
2656                  void __user *buffer, size_t *lenp, loff_t *ppos)
2657{
2658        int error = proc_dostring(table, write, buffer, lenp, ppos);
2659        if (!error)
2660                validate_coredump_safety();
2661        return error;
2662}
2663#endif
2664
2665static int __do_proc_doulongvec_minmax(void *data, struct ctl_table *table, int write,
2666                                     void __user *buffer,
2667                                     size_t *lenp, loff_t *ppos,
2668                                     unsigned long convmul,
2669                                     unsigned long convdiv)
2670{
2671        unsigned long *i, *min, *max;
2672        int vleft, first = 1, err = 0;
2673        unsigned long page = 0;
2674        size_t left;
2675        char *kbuf;
2676
2677        if (!data || !table->maxlen || !*lenp || (*ppos && !write)) {
2678                *lenp = 0;
2679                return 0;
2680        }
2681
2682        i = (unsigned long *) data;
2683        min = (unsigned long *) table->extra1;
2684        max = (unsigned long *) table->extra2;
2685        vleft = table->maxlen / sizeof(unsigned long);
2686        left = *lenp;
2687
2688        if (write) {
2689                if (proc_first_pos_non_zero_ignore(ppos, table))
2690                        goto out;
2691
2692                if (left > PAGE_SIZE - 1)
2693                        left = PAGE_SIZE - 1;
2694                page = __get_free_page(GFP_TEMPORARY);
2695                kbuf = (char *) page;
2696                if (!kbuf)
2697                        return -ENOMEM;
2698                if (copy_from_user(kbuf, buffer, left)) {
2699                        err = -EFAULT;
2700                        goto free;
2701                }
2702                kbuf[left] = 0;
2703        }
2704
2705        for (; left && vleft--; i++, first = 0) {
2706                unsigned long val;
2707
2708                if (write) {
2709                        bool neg;
2710
2711                        left -= proc_skip_spaces(&kbuf);
2712
2713                        err = proc_get_long(&kbuf, &left, &val, &neg,
2714                                             proc_wspace_sep,
2715                                             sizeof(proc_wspace_sep), NULL);
2716                        if (err)
2717                                break;
2718                        if (neg)
2719                                continue;
2720                        if ((min && val < *min) || (max && val > *max))
2721                                continue;
2722                        *i = val;
2723                } else {
2724                        val = convdiv * (*i) / convmul;
2725                        if (!first)
2726                                err = proc_put_char(&buffer, &left, '\t');
2727                        err = proc_put_long(&buffer, &left, val, false);
2728                        if (err)
2729                                break;
2730                }
2731        }
2732
2733        if (!write && !first && left && !err)
2734                err = proc_put_char(&buffer, &left, '\n');
2735        if (write && !err)
2736                left -= proc_skip_spaces(&kbuf);
2737free:
2738        if (write) {
2739                free_page(page);
2740                if (first)
2741                        return err ? : -EINVAL;
2742        }
2743        *lenp -= left;
2744out:
2745        *ppos += *lenp;
2746        return err;
2747}
2748
2749static int do_proc_doulongvec_minmax(struct ctl_table *table, int write,
2750                                     void __user *buffer,
2751                                     size_t *lenp, loff_t *ppos,
2752                                     unsigned long convmul,
2753                                     unsigned long convdiv)
2754{
2755        return __do_proc_doulongvec_minmax(table->data, table, write,
2756                        buffer, lenp, ppos, convmul, convdiv);
2757}
2758
2759/**
2760 * proc_doulongvec_minmax - read a vector of long integers with min/max values
2761 * @table: the sysctl table
2762 * @write: %TRUE if this is a write to the sysctl file
2763 * @buffer: the user buffer
2764 * @lenp: the size of the user buffer
2765 * @ppos: file position
2766 *
2767 * Reads/writes up to table->maxlen/sizeof(unsigned long) unsigned long
2768 * values from/to the user buffer, treated as an ASCII string.
2769 *
2770 * This routine will ensure the values are within the range specified by
2771 * table->extra1 (min) and table->extra2 (max).
2772 *
2773 * Returns 0 on success.
2774 */
2775int proc_doulongvec_minmax(struct ctl_table *table, int write,
2776                           void __user *buffer, size_t *lenp, loff_t *ppos)
2777{
2778    return do_proc_doulongvec_minmax(table, write, buffer, lenp, ppos, 1l, 1l);
2779}
2780
2781/**
2782 * proc_doulongvec_ms_jiffies_minmax - read a vector of millisecond values with min/max values
2783 * @table: the sysctl table
2784 * @write: %TRUE if this is a write to the sysctl file
2785 * @buffer: the user buffer
2786 * @lenp: the size of the user buffer
2787 * @ppos: file position
2788 *
2789 * Reads/writes up to table->maxlen/sizeof(unsigned long) unsigned long
2790 * values from/to the user buffer, treated as an ASCII string. The values
2791 * are treated as milliseconds, and converted to jiffies when they are stored.
2792 *
2793 * This routine will ensure the values are within the range specified by
2794 * table->extra1 (min) and table->extra2 (max).
2795 *
2796 * Returns 0 on success.
2797 */
2798int proc_doulongvec_ms_jiffies_minmax(struct ctl_table *table, int write,
2799                                      void __user *buffer,
2800                                      size_t *lenp, loff_t *ppos)
2801{
2802    return do_proc_doulongvec_minmax(table, write, buffer,
2803                                     lenp, ppos, HZ, 1000l);
2804}
2805
2806
2807static int do_proc_dointvec_jiffies_conv(bool *negp, unsigned long *lvalp,
2808                                         int *valp,
2809                                         int write, void *data)
2810{
2811        if (write) {
2812                if (*lvalp > LONG_MAX / HZ)
2813                        return 1;
2814                *valp = *negp ? -(*lvalp*HZ) : (*lvalp*HZ);
2815        } else {
2816                int val = *valp;
2817                unsigned long lval;
2818                if (val < 0) {
2819                        *negp = true;
2820                        lval = (unsigned long)-val;
2821                } else {
2822                        *negp = false;
2823                        lval = (unsigned long)val;
2824                }
2825                *lvalp = lval / HZ;
2826        }
2827        return 0;
2828}
2829
2830static int do_proc_dointvec_userhz_jiffies_conv(bool *negp, unsigned long *lvalp,
2831                                                int *valp,
2832                                                int write, void *data)
2833{
2834        if (write) {
2835                if (USER_HZ < HZ && *lvalp > (LONG_MAX / HZ) * USER_HZ)
2836                        return 1;
2837                *valp = clock_t_to_jiffies(*negp ? -*lvalp : *lvalp);
2838        } else {
2839                int val = *valp;
2840                unsigned long lval;
2841                if (val < 0) {
2842                        *negp = true;
2843                        lval = (unsigned long)-val;
2844                } else {
2845                        *negp = false;
2846                        lval = (unsigned long)val;
2847                }
2848                *lvalp = jiffies_to_clock_t(lval);
2849        }
2850        return 0;
2851}
2852
2853static int do_proc_dointvec_ms_jiffies_conv(bool *negp, unsigned long *lvalp,
2854                                            int *valp,
2855                                            int write, void *data)
2856{
2857        if (write) {
2858                unsigned long jif = msecs_to_jiffies(*negp ? -*lvalp : *lvalp);
2859
2860                if (jif > INT_MAX)
2861                        return 1;
2862                *valp = (int)jif;
2863        } else {
2864                int val = *valp;
2865                unsigned long lval;
2866                if (val < 0) {
2867                        *negp = true;
2868                        lval = (unsigned long)-val;
2869                } else {
2870                        *negp = false;
2871                        lval = (unsigned long)val;
2872                }
2873                *lvalp = jiffies_to_msecs(lval);
2874        }
2875        return 0;
2876}
2877
2878/**
2879 * proc_dointvec_jiffies - read a vector of integers as seconds
2880 * @table: the sysctl table
2881 * @write: %TRUE if this is a write to the sysctl file
2882 * @buffer: the user buffer
2883 * @lenp: the size of the user buffer
2884 * @ppos: file position
2885 *
2886 * Reads/writes up to table->maxlen/sizeof(unsigned int) integer
2887 * values from/to the user buffer, treated as an ASCII string. 
2888 * The values read are assumed to be in seconds, and are converted into
2889 * jiffies.
2890 *
2891 * Returns 0 on success.
2892 */
2893int proc_dointvec_jiffies(struct ctl_table *table, int write,
2894                          void __user *buffer, size_t *lenp, loff_t *ppos)
2895{
2896    return do_proc_dointvec(table,write,buffer,lenp,ppos,
2897                            do_proc_dointvec_jiffies_conv,NULL);
2898}
2899
2900/**
2901 * proc_dointvec_userhz_jiffies - read a vector of integers as 1/USER_HZ seconds
2902 * @table: the sysctl table
2903 * @write: %TRUE if this is a write to the sysctl file
2904 * @buffer: the user buffer
2905 * @lenp: the size of the user buffer
2906 * @ppos: pointer to the file position
2907 *
2908 * Reads/writes up to table->maxlen/sizeof(unsigned int) integer
2909 * values from/to the user buffer, treated as an ASCII string. 
2910 * The values read are assumed to be in 1/USER_HZ seconds, and 
2911 * are converted into jiffies.
2912 *
2913 * Returns 0 on success.
2914 */
2915int proc_dointvec_userhz_jiffies(struct ctl_table *table, int write,
2916                                 void __user *buffer, size_t *lenp, loff_t *ppos)
2917{
2918    return do_proc_dointvec(table,write,buffer,lenp,ppos,
2919                            do_proc_dointvec_userhz_jiffies_conv,NULL);
2920}
2921
2922/**
2923 * proc_dointvec_ms_jiffies - read a vector of integers as 1 milliseconds
2924 * @table: the sysctl table
2925 * @write: %TRUE if this is a write to the sysctl file
2926 * @buffer: the user buffer
2927 * @lenp: the size of the user buffer
2928 * @ppos: file position
2929 * @ppos: the current position in the file
2930 *
2931 * Reads/writes up to table->maxlen/sizeof(unsigned int) integer
2932 * values from/to the user buffer, treated as an ASCII string. 
2933 * The values read are assumed to be in 1/1000 seconds, and 
2934 * are converted into jiffies.
2935 *
2936 * Returns 0 on success.
2937 */
2938int proc_dointvec_ms_jiffies(struct ctl_table *table, int write,
2939                             void __user *buffer, size_t *lenp, loff_t *ppos)
2940{
2941        return do_proc_dointvec(table, write, buffer, lenp, ppos,
2942                                do_proc_dointvec_ms_jiffies_conv, NULL);
2943}
2944
2945static int proc_do_cad_pid(struct ctl_table *table, int write,
2946                           void __user *buffer, size_t *lenp, loff_t *ppos)
2947{
2948        struct pid *new_pid;
2949        pid_t tmp;
2950        int r;
2951
2952        tmp = pid_vnr(cad_pid);
2953
2954        r = __do_proc_dointvec(&tmp, table, write, buffer,
2955                               lenp, ppos, NULL, NULL);
2956        if (r || !write)
2957                return r;
2958
2959        new_pid = find_get_pid(tmp);
2960        if (!new_pid)
2961                return -ESRCH;
2962
2963        put_pid(xchg(&cad_pid, new_pid));
2964        return 0;
2965}
2966
2967/**
2968 * proc_do_large_bitmap - read/write from/to a large bitmap
2969 * @table: the sysctl table
2970 * @write: %TRUE if this is a write to the sysctl file
2971 * @buffer: the user buffer
2972 * @lenp: the size of the user buffer
2973 * @ppos: file position
2974 *
2975 * The bitmap is stored at table->data and the bitmap length (in bits)
2976 * in table->maxlen.
2977 *
2978 * We use a range comma separated format (e.g. 1,3-4,10-10) so that
2979 * large bitmaps may be represented in a compact manner. Writing into
2980 * the file will clear the bitmap then update it with the given input.
2981 *
2982 * Returns 0 on success.
2983 */
2984int proc_do_large_bitmap(struct ctl_table *table, int write,
2985                         void __user *buffer, size_t *lenp, loff_t *ppos)
2986{
2987        int err = 0;
2988        bool first = 1;
2989        size_t left = *lenp;
2990        unsigned long bitmap_len = table->maxlen;
2991        unsigned long *bitmap = (unsigned long *) table->data;
2992        unsigned long *tmp_bitmap = NULL;
2993        char tr_a[] = { '-', ',', '\n' }, tr_b[] = { ',', '\n', 0 }, c;
2994
2995        if (!bitmap_len || !left || (*ppos && !write)) {
2996                *lenp = 0;
2997                return 0;
2998        }
2999
3000        if (write) {
3001                unsigned long page = 0;
3002                char *kbuf;
3003
3004                if (left > PAGE_SIZE - 1)
3005                        left = PAGE_SIZE - 1;
3006
3007                page = __get_free_page(GFP_TEMPORARY);
3008                kbuf = (char *) page;
3009                if (!kbuf)
3010                        return -ENOMEM;
3011                if (copy_from_user(kbuf, buffer, left)) {
3012                        free_page(page);
3013                        return -EFAULT;
3014                }
3015                kbuf[left] = 0;
3016
3017                tmp_bitmap = kzalloc(BITS_TO_LONGS(bitmap_len) * sizeof(unsigned long),
3018                                     GFP_KERNEL);
3019                if (!tmp_bitmap) {
3020                        free_page(page);
3021                        return -ENOMEM;
3022                }
3023                proc_skip_char(&kbuf, &left, '\n');
3024                while (!err && left) {
3025                        unsigned long val_a, val_b;
3026                        bool neg;
3027
3028                        err = proc_get_long(&kbuf, &left, &val_a, &neg, tr_a,
3029                                             sizeof(tr_a), &c);
3030                        if (err)
3031                                break;
3032                        if (val_a >= bitmap_len || neg) {
3033                                err = -EINVAL;
3034                                break;
3035                        }
3036
3037                        val_b = val_a;
3038                        if (left) {
3039                                kbuf++;
3040                                left--;
3041                        }
3042
3043                        if (c == '-') {
3044                                err = proc_get_long(&kbuf, &left, &val_b,
3045                                                     &neg, tr_b, sizeof(tr_b),
3046                                                     &c);
3047                                if (err)
3048                                        break;
3049                                if (val_b >= bitmap_len || neg ||
3050                                    val_a > val_b) {
3051                                        err = -EINVAL;
3052                                        break;
3053                                }
3054                                if (left) {
3055                                        kbuf++;
3056                                        left--;
3057                                }
3058                        }
3059
3060                        bitmap_set(tmp_bitmap, val_a, val_b - val_a + 1);
3061                        first = 0;
3062                        proc_skip_char(&kbuf, &left, '\n');
3063                }
3064                free_page(page);
3065        } else {
3066                unsigned long bit_a, bit_b = 0;
3067
3068                while (left) {
3069                        bit_a = find_next_bit(bitmap, bitmap_len, bit_b);
3070                        if (bit_a >= bitmap_len)
3071                                break;
3072                        bit_b = find_next_zero_bit(bitmap, bitmap_len,
3073                                                   bit_a + 1) - 1;
3074
3075                        if (!first) {
3076                                err = proc_put_char(&buffer, &left, ',');
3077                                if (err)
3078                                        break;
3079                        }
3080                        err = proc_put_long(&buffer, &left, bit_a, false);
3081                        if (err)
3082                                break;
3083                        if (bit_a != bit_b) {
3084                                err = proc_put_char(&buffer, &left, '-');
3085                                if (err)
3086                                        break;
3087                                err = proc_put_long(&buffer, &left, bit_b, false);
3088                                if (err)
3089                                        break;
3090                        }
3091
3092                        first = 0; bit_b++;
3093                }
3094                if (!err)
3095                        err = proc_put_char(&buffer, &left, '\n');
3096        }
3097
3098        if (!err) {
3099                if (write) {
3100                        if (*ppos)
3101                                bitmap_or(bitmap, bitmap, tmp_bitmap, bitmap_len);
3102                        else
3103                                bitmap_copy(bitmap, tmp_bitmap, bitmap_len);
3104                }
3105                kfree(tmp_bitmap);
3106                *lenp -= left;
3107                *ppos += *lenp;
3108                return 0;
3109        } else {
3110                kfree(tmp_bitmap);
3111                return err;
3112        }
3113}
3114
3115#else /* CONFIG_PROC_SYSCTL */
3116
3117int proc_dostring(struct ctl_table *table, int write,
3118                  void __user *buffer, size_t *lenp, loff_t *ppos)
3119{
3120        return -ENOSYS;
3121}
3122
3123int proc_dointvec(struct ctl_table *table, int write,
3124                  void __user *buffer, size_t *lenp, loff_t *ppos)
3125{
3126        return -ENOSYS;
3127}
3128
3129int proc_douintvec(struct ctl_table *table, int write,
3130                  void __user *buffer, size_t *lenp, loff_t *ppos)
3131{
3132        return -ENOSYS;
3133}
3134
3135int proc_dointvec_minmax(struct ctl_table *table, int write,
3136                    void __user *buffer, size_t *lenp, loff_t *ppos)
3137{
3138        return -ENOSYS;
3139}
3140
3141int proc_douintvec_minmax(struct ctl_table *table, int write,
3142                          void __user *buffer, size_t *lenp, loff_t *ppos)
3143{
3144        return -ENOSYS;
3145}
3146
3147int proc_dopipe_max_size(struct ctl_table *table, int write,
3148                         void __user *buffer, size_t *lenp, loff_t *ppos)
3149{
3150        return -ENOSYS;
3151}
3152
3153int proc_dointvec_jiffies(struct ctl_table *table, int write,
3154                    void __user *buffer, size_t *lenp, loff_t *ppos)
3155{
3156        return -ENOSYS;
3157}
3158
3159int proc_dointvec_userhz_jiffies(struct ctl_table *table, int write,
3160                    void __user *buffer, size_t *lenp, loff_t *ppos)
3161{
3162        return -ENOSYS;
3163}
3164
3165int proc_dointvec_ms_jiffies(struct ctl_table *table, int write,
3166                             void __user *buffer, size_t *lenp, loff_t *ppos)
3167{
3168        return -ENOSYS;
3169}
3170
3171int proc_doulongvec_minmax(struct ctl_table *table, int write,
3172                    void __user *buffer, size_t *lenp, loff_t *ppos)
3173{
3174        return -ENOSYS;
3175}
3176
3177int proc_doulongvec_ms_jiffies_minmax(struct ctl_table *table, int write,
3178                                      void __user *buffer,
3179                                      size_t *lenp, loff_t *ppos)
3180{
3181    return -ENOSYS;
3182}
3183
3184
3185#endif /* CONFIG_PROC_SYSCTL */
3186
3187/*
3188 * No sense putting this after each symbol definition, twice,
3189 * exception granted :-)
3190 */
3191EXPORT_SYMBOL(proc_dointvec);
3192EXPORT_SYMBOL(proc_douintvec);
3193EXPORT_SYMBOL(proc_dointvec_jiffies);
3194EXPORT_SYMBOL(proc_dointvec_minmax);
3195EXPORT_SYMBOL_GPL(proc_douintvec_minmax);
3196EXPORT_SYMBOL_GPL(proc_dopipe_max_size);
3197EXPORT_SYMBOL(proc_dointvec_userhz_jiffies);
3198EXPORT_SYMBOL(proc_dointvec_ms_jiffies);
3199EXPORT_SYMBOL(proc_dostring);
3200EXPORT_SYMBOL(proc_doulongvec_minmax);
3201EXPORT_SYMBOL(proc_doulongvec_ms_jiffies_minmax);
3202