Esempio n. 1
0
/* Enumerate all disks to name devices.  */
static void
enumerate_disks (void)
{
  struct grub_efidisk_data *devices;

  devices = make_devices ();
  if (! devices)
    return;

  name_devices (devices);
  free_devices (devices);
}
Esempio n. 2
0
/* Some utility functions to map GRUB devices with EFI devices.  */
grub_efi_handle_t
grub_efidisk_get_current_bdev_handle (void)
{
  struct grub_efidisk_data *d;

  d = get_device_from_drive (current_drive);
  if (d == NULL)
    return NULL;

  if (current_drive == GRUB_INVALID_DRIVE)
    return NULL;

  if (current_drive == cdrom_drive)
    return d->handle;

  if (! (current_drive & 0x80))
    return d->handle;
  /* If this is the whole disk, just return its own data.  */
  else if (current_partition == 0xFFFFFF)
    return d->handle;
  /* Otherwise, we must query the corresponding device to the firmware.  */
  else
    {
      struct grub_efidisk_data *devices;
      grub_efi_handle_t handle = 0;
      auto int find_partition (struct grub_efidisk_data *c);

      int find_partition (struct grub_efidisk_data *c)
	{
	  grub_efi_hard_drive_device_path_t hd;

	  grub_memcpy (&hd, c->last_device_path, sizeof (hd));

	  if ((GRUB_EFI_DEVICE_PATH_TYPE (c->last_device_path)
	       == GRUB_EFI_MEDIA_DEVICE_PATH_TYPE)
	      && (GRUB_EFI_DEVICE_PATH_SUBTYPE (c->last_device_path)
		  == GRUB_EFI_HARD_DRIVE_DEVICE_PATH_SUBTYPE)
	      && (part_start == hd.partition_start))
	    {
	      handle = c->handle;
	      return 1;
	    }

	  return 0;
	}

      devices = make_devices ();
      iterate_child_devices (devices, d, find_partition);
      free_devices (devices);

      if (handle != 0)
	return handle;
    }
Esempio n. 3
0
/* command line interface for the 'makedev' command */
void
vinum_makedev(int argc, char *argv[], char *arg0[])
{
    make_devices();
}
Esempio n. 4
0
int
main(int argc, char *argv[], char *envp[])
{
    struct stat histstat;

    if (modfind(VINUMMOD) < 0) {
	/* need to load the vinum module */
	if (kldload(VINUMMOD) < 0 || modfind(VINUMMOD) < 0) {
	    perror(VINUMMOD ": Kernel module not available");
	    return 1;
	}
    }
    dateformat = getenv("VINUM_DATEFORMAT");
    if (dateformat == NULL)
	dateformat = "%e %b %Y %H:%M:%S";
    historyfile = getenv("VINUM_HISTORY");
    if (historyfile == NULL)
	historyfile = DEFAULT_HISTORYFILE;
    if (stat(historyfile, &histstat) == 0) {		    /* history file exists */
	if ((histstat.st_mode & S_IFMT) != S_IFREG) {
	    fprintf(stderr,
		"Vinum history file %s must be a regular file\n",
		historyfile);
	    exit(1);
	}
    } else if ((errno != ENOENT)			    /* not "not there",  */
    &&(errno != EROFS)) {				    /* and not read-only file system */
	fprintf(stderr,
	    "Can't open %s: %s (%d)\n",
	    historyfile,
	    strerror(errno),
	    errno);
	exit(1);
    }
    hist = fopen(historyfile, "a+");
    if (hist != NULL) {
	timestamp();
	fprintf(hist, "*** " VINUMMOD " started ***\n");
	fflush(hist);				    /* before we start the daemon */
    }
    superdev = open(VINUM_SUPERDEV_NAME, O_RDWR);	    /* open vinum superdevice */
    if (superdev < 0) {					    /* no go */
	if (errno == ENODEV) {				    /* not configured, */
	    superdev = open(VINUM_WRONGSUPERDEV_NAME, O_RDWR); /* do we have a debug mismatch? */
	    if (superdev >= 0) {			    /* yup! */
#if VINUMDEBUG
		fprintf(stderr,
		    "This program is compiled with debug support, but the kernel module does\n"
		    "not have debug support.  This program must be matched with the kernel\n"
		    "module.  Please alter /usr/src/sbin/" VINUMMOD "/Makefile and remove\n"
		    "the option -DVINUMDEBUG from the CFLAGS definition, or alternatively\n"
		    "edit /usr/src/sys/modules/" VINUMMOD "/Makefile and add the option\n"
		    "-DVINUMDEBUG to the CFLAGS definition.  Then rebuild the component\n"
		    "of your choice with 'make clean all install'.  If you rebuild the kernel\n"
		    "module, you must stop " VINUMMOD " and restart it\n");
#else
		fprintf(stderr,
		    "This program is compiled without debug support, but the kernel module\n"
		    "includes debug support.  This program must be matched with the kernel\n"
		    "module.  Please alter /usr/src/sbin/" VINUMMOD "/Makefile and add\n"
		    "the option -DVINUMDEBUG to the CFLAGS definition, or alternatively\n"
		    "edit /usr/src/sys/modules/" VINUMMOD "/Makefile and remove the option\n"
		    "-DVINUMDEBUG from the CFLAGS definition.  Then rebuild the component\n"
		    "of your choice with 'make clean all install'.  If you rebuild the kernel\n"
		    "module, you must stop " VINUMMOD " and restart it\n");
#endif
		return 1;
	    }
	} else if (errno == ENOENT)			    /* we don't have our node, */
	    make_devices();				    /* create them first */
	if (superdev < 0) {
	    perror("Can't open " VINUM_SUPERDEV_NAME);
	    return 1;
	}
    }
    /* Check if the dæmon is running.  If not, start it in the
     * background */
    start_daemon();

    if (argc > 1) {					    /* we have a command on the line */
	if (setjmp(command_fail) != 0)			    /* long jumped out */
	    return -1;
	parseline(argc - 1, &argv[1]);			    /* do it */
    } else {
	/*
	 * Catch a possible race condition which could cause us to
	 * longjmp() into nowhere if we receive a SIGINT in the next few
	 * lines.
	 */
	if (setjmp(command_fail))			    /* come back here on catastrophic failure */
	    return 1;
	setsigs();					    /* set signal handler */
	for (;;) {					    /* ugh */
	    char *c;
	    int childstatus;				    /* from wait4 */

	    if (setjmp(command_fail) == 2)		    /* come back here on catastrophic failure */
		fprintf(stderr, "*** interrupted ***\n");   /* interrupted */

	    while (wait4(-1, &childstatus, WNOHANG, NULL) > 0);	/* wait for all dead children */
	    c = readline(VINUMMOD " -> ");		    /* get an input */
	    if (c == NULL) {				    /* EOF or error */
		if (ferror(stdin)) {
		    fprintf(stderr, "Can't read input: %s (%d)\n", strerror(errno), errno);
		    return 1;
		} else {				    /* EOF */
		    printf("\n");
		    return 0;
		}
	    } else if (*c) {				    /* got something there */
		add_history(c);				    /* save it in the history */
		strcpy(buffer, c);			    /* put it where we can munge it */
		free(c);
		line++;					    /* count the lines */
		tokens = tokenize(buffer, token);
		/* got something potentially worth parsing */
		if (tokens)
		    parseline(tokens, token);		    /* and do what he says */
	    }
	    if (hist)
		fflush(hist);
	}
    }
    return 0;						    /* normal completion */
}
Esempio n. 5
0
int main(int argc, char *argv[])
{
	char **cmdv, **args;
	char *cmdlines[3];
	int i;
	const char *errmsg;
	int ret = 0;
	int cmdc;
	int fd;
	struct timeval now;
	char *mount_argv[] = {"mount_part", "rootfs", "/root"};
	pid_t pid;
	int nandboot = 0;

	gettimeofday(&now, NULL);
	srand48(now.tv_usec ^ (now.tv_sec << 24));

	/* Default parameters for anything init-like we execute */
	init_argc = argc;
	init_argv = alloca((argc+1)*sizeof(char *));
	memcpy(init_argv, argv, (argc+1)*sizeof(char *));

	/*
	 * omit /dev/console when generating initramfs,
	 * so we create it dynamically
	 */
	if (access("/dev/console", O_RDWR)) {
		mknod("/dev/console", S_IFCHR|0644, makedev(5, 1));
	}

	if ((fd = open("/dev/console", O_RDWR)) != -1) {
		dup2(fd, STDIN_FILENO);
		dup2(fd, STDOUT_FILENO);
		dup2(fd, STDERR_FILENO);

		if (fd > STDERR_FILENO) {
			close(fd);
		}
	}

	mnt_procfs = mount_sys_fs("/proc/cmdline", "/proc", "proc") >= 0;
	if (!mnt_procfs) {
		ret = 1;
		goto bail;
	}

	mnt_sysfs = mount_sys_fs("/sys/bus", "/sys", "sysfs") >= 0;
	if (!mnt_sysfs) {
		ret = 1;
		goto bail;
	}

	/* Construct the effective kernel command line.  The
	   effective kernel command line consists of /arch.cmd, if
	   it exists, /proc/cmdline, plus any arguments after an --
	   argument on the proper command line, in that order. */

	ret = readfile("/arch.cmd", &cmdlines[0]);
	if (ret < 0)
		cmdlines[0] = "";

	ret = readfile("/proc/cmdline", &cmdlines[1]);
	if (ret < 0) {
		fprintf(stderr, "%s: cannot read /proc/cmdline\n", progname);
		ret = 1;
		goto bail;
	}

	cmdlines[2] = NULL;

	/* Find an -- argument, and if so append to the command line */
	for (i = 1; i < argc; i++) {
		if (!strcmp(argv[i], "--")) {
			i++;
			break;
		}
	}
	args = &argv[i];	/* Points either to first argument past -- or
				   to the final NULL */

	/* Count the number of arguments */
	cmdc = split_cmdline(INT_MAX, NULL, argv[0], cmdlines, args);

	/* Actually generate the cmdline array */
	cmdv = (char **)alloca((cmdc+1)*sizeof(char *));
	if (split_cmdline(cmdc, cmdv, argv[0], cmdlines, args) != cmdc) {
		ret = 1;
		goto bail;
	}

	/* Debugging... */
	dump_args(cmdc, cmdv);

	{
		const char * root_device_name = get_arg(cmdc, cmdv, "root=");
		if (strncmp(root_device_name, "/dev/mtdblock", strlen("/dev/mtdblock")) == 0) {
			nandboot = 1;
			printf("kinit: NAND mode, check online upgrade flag\n");
			do_rootfs_OU();
		} else {
			nandboot = 0;
			printf("kinit: None-NAND mode, ignore online upgrade flag\n");
		}
	}

	/* Resume from suspend-to-disk, if appropriate */
	/* If successful, does not return */
	do_resume(cmdc, cmdv);

	/* Initialize networking, if applicable */
	do_ipconfig(cmdc, cmdv);

	check_path("/root");

	if (nandboot) {
		int index = 0;
		while (1) {
			char name[128];
			snprintf(name, sizeof(name), "/sys/block/mtdblock%d", index);
			if (access(name, F_OK) == 0) {
				snprintf(name, sizeof(name), "/dev/mtdblock%d", index);
				create_dev(name, name_to_dev_t(name));
				index++;
			} else {
				break;
			}
		}
		if((pid=fork())<0)
			fprintf(stderr, "fork error.\n");
		else if(pid == 0)
		{
			if((ret = execve("/bin/mount_part", mount_argv, NULL)) <0)
				perror("excute mount_part error\n");
		}
		if(waitpid(pid, NULL, 0) < 0)
			fprintf(stderr, "wait mount_part error.\n");
	} else {
		do_mounts(cmdc, cmdv);
	}

	if (mnt_procfs) {
		umount2("/proc", 0);
		mnt_procfs = 0;
	}

	if (mnt_sysfs) {
		umount2("/sys", 0);
		mnt_sysfs = 0;
	}

	make_devices();

	init_path = find_init("/root", get_arg(cmdc, cmdv, "init="));
	if (!init_path) {
		fprintf(stderr, "%s: init not found!\n", progname);
		ret = 2;
		goto bail;
	}
	DEBUG(("kinit: init_path = %s, init=%s\n", init_path, get_arg(cmdc, cmdv, "init=")));

	init_argv[0] = strrchr(init_path, '/') + 1;

	errmsg = run_init("/root", "/dev/console", init_path, init_argv);

	/* If run_init returned, something went bad */
	fprintf(stderr, "%s: %s: %s\n", progname, errmsg, strerror(errno));
	ret = 2;
	goto bail;

bail:
	if (mnt_procfs)
		umount2("/proc", 0);

	if (mnt_sysfs)
		umount2("/sys", 0);

	/*
	 * If we get here, something bad probably happened, and the kernel
	 * will most likely panic.  Drain console output so the user can
	 * figure out what happened.
	 */
	tcdrain(2);
	tcdrain(1);

	return ret;
}