diff options
Diffstat (limited to 'init')
-rw-r--r-- | init/Kconfig | 29 | ||||
-rw-r--r-- | init/do_mounts.c | 47 | ||||
-rw-r--r-- | init/do_mounts_rd.c | 12 | ||||
-rw-r--r-- | init/main.c | 60 |
4 files changed, 116 insertions, 32 deletions
diff --git a/init/Kconfig b/init/Kconfig index 7a7acd9..2d60611 100644 --- a/init/Kconfig +++ b/init/Kconfig @@ -118,7 +118,6 @@ config HAVE_KERNEL_LZ4 choice prompt "Kernel compression mode" default KERNEL_GZIP - depends on HAVE_KERNEL_GZIP || HAVE_KERNEL_BZIP2 || HAVE_KERNEL_LZMA || HAVE_KERNEL_XZ || HAVE_KERNEL_LZO || HAVE_KERNEL_LZ4 help The linux kernel is a kind of self-extracting executable. Several compression algorithms are available, which differ @@ -137,6 +136,13 @@ choice If in doubt, select 'gzip' +config KERNEL_UNCOMPRESSED + bool "No compression" + help + No compression at all. The kernel is huge but the compression and + decompression times are zero. + This is usually not what you want. + config KERNEL_GZIP bool "Gzip" depends on HAVE_KERNEL_GZIP @@ -284,7 +290,7 @@ config AUDIT config AUDITSYSCALL bool "Enable system-call auditing support" - depends on AUDIT && (X86 || PPC || S390 || IA64 || UML || SPARC64 || SUPERH || (ARM && AEABI && !OABI_COMPAT)) + depends on AUDIT && (X86 || PARISC || PPC || S390 || IA64 || UML || SPARC64 || SUPERH || (ARM && AEABI && !OABI_COMPAT)) default y if SECURITY_SELINUX help Enable low-overhead system-call auditing infrastructure that @@ -354,7 +360,8 @@ config VIRT_CPU_ACCOUNTING_NATIVE config VIRT_CPU_ACCOUNTING_GEN bool "Full dynticks CPU time accounting" - depends on HAVE_CONTEXT_TRACKING && 64BIT + depends on HAVE_CONTEXT_TRACKING + depends on HAVE_VIRT_CPU_ACCOUNTING_GEN select VIRT_CPU_ACCOUNTING select CONTEXT_TRACKING help @@ -1123,7 +1130,6 @@ config IPC_NS config USER_NS bool "User namespace" - depends on UIDGID_CONVERTED select UIDGID_STRICT_TYPE_CHECKS default n @@ -1157,20 +1163,8 @@ config NET_NS endif # NAMESPACES -config UIDGID_CONVERTED - # True if all of the selected software conmponents are known - # to have uid_t and gid_t converted to kuid_t and kgid_t - # where appropriate and are otherwise safe to use with - # the user namespace. - bool - default y - - # Filesystems - depends on XFS_FS = n - config UIDGID_STRICT_TYPE_CHECKS bool "Require conversions between uid/gids and their internal representation" - depends on UIDGID_CONVERTED default n help While the nececessary conversions are being added to all subsystems this option allows @@ -1615,7 +1609,7 @@ endchoice config SLUB_CPU_PARTIAL default y - depends on SLUB + depends on SLUB && SMP bool "SLUB per cpu partial cache" help Per cpu partial caches accellerate objects allocation and freeing @@ -1683,6 +1677,7 @@ config BASE_SMALL menuconfig MODULES bool "Enable loadable module support" + option modules help Kernel modules are small pieces of compiled code which can be inserted in the running kernel, rather than being diff --git a/init/do_mounts.c b/init/do_mounts.c index 816014c..8e5addc 100644 --- a/init/do_mounts.c +++ b/init/do_mounts.c @@ -26,6 +26,8 @@ #include <linux/async.h> #include <linux/fs_struct.h> #include <linux/slab.h> +#include <linux/ramfs.h> +#include <linux/shmem_fs.h> #include <linux/nfs_fs.h> #include <linux/nfs_fs_sb.h> @@ -195,6 +197,8 @@ done: * is a zero-filled hex representation of the 1-based partition number. * 7) PARTUUID=<UUID>/PARTNROFF=<int> to select a partition in relation to * a partition with a known unique id. + * 8) <major>:<minor> major and minor number of the device separated by + * a colon. * * If name doesn't have fall into the categories above, we return (0,0). * block_class is used to check if something is a disk name. If the disk @@ -588,3 +592,46 @@ out: sys_mount(".", "/", NULL, MS_MOVE, NULL); sys_chroot("."); } + +static bool is_tmpfs; +static struct dentry *rootfs_mount(struct file_system_type *fs_type, + int flags, const char *dev_name, void *data) +{ + static unsigned long once; + void *fill = ramfs_fill_super; + + if (test_and_set_bit(0, &once)) + return ERR_PTR(-ENODEV); + + if (IS_ENABLED(CONFIG_TMPFS) && is_tmpfs) + fill = shmem_fill_super; + + return mount_nodev(fs_type, flags, data, fill); +} + +static struct file_system_type rootfs_fs_type = { + .name = "rootfs", + .mount = rootfs_mount, + .kill_sb = kill_litter_super, +}; + +int __init init_rootfs(void) +{ + int err = register_filesystem(&rootfs_fs_type); + + if (err) + return err; + + if (IS_ENABLED(CONFIG_TMPFS) && !saved_root_name[0] && + (!root_fs_names || strstr(root_fs_names, "tmpfs"))) { + err = shmem_init(); + is_tmpfs = true; + } else { + err = init_ramfs_fs(); + } + + if (err) + unregister_filesystem(&rootfs_fs_type); + + return err; +} diff --git a/init/do_mounts_rd.c b/init/do_mounts_rd.c index 6be2879..7c098ac 100644 --- a/init/do_mounts_rd.c +++ b/init/do_mounts_rd.c @@ -57,6 +57,11 @@ static int __init crd_load(int in_fd, int out_fd, decompress_fn deco); * cramfs * squashfs * gzip + * bzip2 + * lzma + * xz + * lzo + * lz4 */ static int __init identify_ramdisk_image(int fd, int start_block, decompress_fn *decompressor) @@ -342,6 +347,13 @@ static int __init crd_load(int in_fd, int out_fd, decompress_fn deco) int result; crd_infd = in_fd; crd_outfd = out_fd; + + if (!deco) { + pr_emerg("Invalid ramdisk decompression routine. " + "Select appropriate config option.\n"); + panic("Could not decompress initial ramdisk image."); + } + result = deco(NULL, 0, compr_fill, compr_flush, NULL, NULL, error); if (decompress_error) result = 1; diff --git a/init/main.c b/init/main.c index af310af..01573fd 100644 --- a/init/main.c +++ b/init/main.c @@ -76,6 +76,7 @@ #include <linux/elevator.h> #include <linux/sched_clock.h> #include <linux/context_tracking.h> +#include <linux/random.h> #include <asm/io.h> #include <asm/bugs.h> @@ -123,7 +124,6 @@ EXPORT_SYMBOL(system_state); extern void time_init(void); /* Default late time init is NULL. archs can override this later. */ void (*__initdata late_time_init)(void); -extern void softirq_init(void); /* Untouched command line saved by arch-specific code. */ char __initdata boot_command_line[COMMAND_LINE_SIZE]; @@ -131,11 +131,20 @@ char __initdata boot_command_line[COMMAND_LINE_SIZE]; char *saved_command_line; /* Command line for parameter parsing */ static char *static_command_line; +/* Command line for per-initcall parameter parsing */ +static char *initcall_command_line; static char *execute_command; static char *ramdisk_execute_command; /* + * Used to generate warnings if static_key manipulation functions are used + * before jump_label_init is called. + */ +bool static_key_initialized __read_mostly = false; +EXPORT_SYMBOL_GPL(static_key_initialized); + +/* * If set, this is an indication to the drivers that reset the underlying * device before going ahead with the initialization otherwise driver might * rely on the BIOS and skip the reset operation. @@ -347,6 +356,7 @@ static inline void smp_prepare_cpus(unsigned int maxcpus) { } static void __init setup_command_line(char *command_line) { saved_command_line = alloc_bootmem(strlen (boot_command_line)+1); + initcall_command_line = alloc_bootmem(strlen (boot_command_line)+1); static_command_line = alloc_bootmem(strlen (command_line)+1); strcpy (saved_command_line, boot_command_line); strcpy (static_command_line, command_line); @@ -466,7 +476,7 @@ static void __init mm_init(void) mem_init(); kmem_cache_init(); percpu_init_late(); - pgtable_cache_init(); + pgtable_init(); vmalloc_init(); } @@ -692,7 +702,7 @@ int __init_or_module do_one_initcall(initcall_t fn) if (preempt_count() != count) { sprintf(msgbuf, "preemption imbalance "); - preempt_count() = count; + preempt_count_set(count); } if (irqs_disabled()) { strlcat(msgbuf, "disabled interrupts ", sizeof(msgbuf)); @@ -744,9 +754,9 @@ static void __init do_initcall_level(int level) extern const struct kernel_param __start___param[], __stop___param[]; initcall_t *fn; - strcpy(static_command_line, saved_command_line); + strcpy(initcall_command_line, saved_command_line); parse_args(initcall_level_names[level], - static_command_line, __start___param, + initcall_command_line, __start___param, __stop___param - __start___param, level, level, &repair_env_string); @@ -780,6 +790,7 @@ static void __init do_basic_setup(void) do_ctors(); usermodehelper_enable(); do_initcalls(); + random_int_secret_init(); } static void __init do_pre_smp_initcalls(void) @@ -809,10 +820,26 @@ static int run_init_process(const char *init_filename) (const char __user *const __user *)envp_init); } +static int try_to_run_init_process(const char *init_filename) +{ + int ret; + + ret = run_init_process(init_filename); + + if (ret && ret != -ENOENT) { + pr_err("Starting init: %s exists but couldn't execute it (error %d)\n", + init_filename, ret); + } + + return ret; +} + static noinline void __init kernel_init_freeable(void); static int __ref kernel_init(void *unused) { + int ret; + kernel_init_freeable(); /* need to finish all async __init code before freeing the memory */ async_synchronize_full(); @@ -824,9 +851,11 @@ static int __ref kernel_init(void *unused) flush_delayed_fput(); if (ramdisk_execute_command) { - if (!run_init_process(ramdisk_execute_command)) + ret = run_init_process(ramdisk_execute_command); + if (!ret) return 0; - pr_err("Failed to execute %s\n", ramdisk_execute_command); + pr_err("Failed to execute %s (error %d)\n", + ramdisk_execute_command, ret); } /* @@ -836,18 +865,19 @@ static int __ref kernel_init(void *unused) * trying to recover a really broken machine. */ if (execute_command) { - if (!run_init_process(execute_command)) + ret = run_init_process(execute_command); + if (!ret) return 0; - pr_err("Failed to execute %s. Attempting defaults...\n", - execute_command); + pr_err("Failed to execute %s (error %d). Attempting defaults...\n", + execute_command, ret); } - if (!run_init_process("/sbin/init") || - !run_init_process("/etc/init") || - !run_init_process("/bin/init") || - !run_init_process("/bin/sh")) + if (!try_to_run_init_process("/sbin/init") || + !try_to_run_init_process("/etc/init") || + !try_to_run_init_process("/bin/init") || + !try_to_run_init_process("/bin/sh")) return 0; - panic("No init found. Try passing init= option to kernel. " + panic("No working init found. Try passing init= option to kernel. " "See Linux Documentation/init.txt for guidance."); } |