Changeset View
Changeset View
Standalone View
Standalone View
sys/kern/vfs_mountroot.c
Show First 20 Lines • Show All 101 Lines • ▼ Show 20 Lines | |||||
/* | /* | ||||
* Mount of the system's /dev. | * Mount of the system's /dev. | ||||
*/ | */ | ||||
struct mount *rootdevmp; | struct mount *rootdevmp; | ||||
char *rootdevnames[2] = {NULL, NULL}; | char *rootdevnames[2] = {NULL, NULL}; | ||||
/* | |||||
* Hooks into md(4) for mount.conf(8)'s .md support. Stored here as | |||||
* this is the only place they are used. Great care should be taken | |||||
* when expanding use as crashes may occur if md(4) is unloaded during | |||||
* calls. | |||||
*/ | |||||
int (*kern_mdattach_p)(struct thread *td, struct md_req *mdr); | |||||
int (*kern_mddetach_p)(struct thread *td, struct md_req *mdr); | |||||
struct mtx root_holds_mtx; | struct mtx root_holds_mtx; | ||||
MTX_SYSINIT(root_holds, &root_holds_mtx, "root_holds", MTX_DEF); | MTX_SYSINIT(root_holds, &root_holds_mtx, "root_holds", MTX_DEF); | ||||
struct root_hold_token { | struct root_hold_token { | ||||
const char *who; | const char *who; | ||||
LIST_ENTRY(root_hold_token) list; | LIST_ENTRY(root_hold_token) list; | ||||
}; | }; | ||||
▲ Show 20 Lines • Show All 423 Lines • ▼ Show 20 Lines | parse_dir_ask(char **conf) | ||||
return (error); | return (error); | ||||
} | } | ||||
static int | static int | ||||
parse_dir_md(char **conf) | parse_dir_md(char **conf) | ||||
{ | { | ||||
struct stat sb; | struct stat sb; | ||||
struct thread *td; | struct thread *td; | ||||
struct md_ioctl *mdio; | struct md_req mdr; | ||||
char *path, *tok; | char *path; | ||||
int error, fd, len; | int error; | ||||
if (kern_mdattach_p == NULL || kern_mddetach_p == NULL) | |||||
return (ENOENT); | |||||
td = curthread; | td = curthread; | ||||
error = parse_token(conf, &tok); | error = parse_token(conf, &path); | ||||
if (error) | if (error) | ||||
return (error); | return (error); | ||||
len = strlen(tok); | |||||
mdio = malloc(sizeof(*mdio) + len + 1, M_TEMP, M_WAITOK | M_ZERO); | |||||
path = (void *)(mdio + 1); | |||||
bcopy(tok, path, len); | |||||
free(tok, M_TEMP); | |||||
/* Get file status. */ | /* Get file status. */ | ||||
error = kern_statat(td, 0, AT_FDCWD, path, UIO_SYSSPACE, &sb, NULL); | error = kern_statat(td, 0, AT_FDCWD, path, UIO_SYSSPACE, &sb, NULL); | ||||
if (error) | if (error) | ||||
goto out; | goto out; | ||||
/* Open /dev/mdctl so that we can attach/detach. */ | bzero(&mdr, sizeof(mdr)); | ||||
error = kern_openat(td, AT_FDCWD, "/dev/" MDCTL_NAME, UIO_SYSSPACE, | mdr.md_type = MD_VNODE; | ||||
O_RDWR, 0); | |||||
if (error) | |||||
goto out; | |||||
fd = td->td_retval[0]; | |||||
mdio->md_version = MDIOVERSION; | |||||
mdio->md_type = MD_VNODE; | |||||
if (root_mount_mddev != -1) { | if (root_mount_mddev != -1) { | ||||
mdio->md_unit = root_mount_mddev; | mdr.md_unit = root_mount_mddev; | ||||
error = kern_ioctl(td, fd, MDIOCDETACH, (void *)mdio); | error = kern_mddetach_p(td, &mdr); | ||||
/* Ignore errors. We don't care. */ | /* Ignore errors. We don't care. */ | ||||
root_mount_mddev = -1; | root_mount_mddev = -1; | ||||
} | } | ||||
mdio->md_file = (void *)(mdio + 1); | mdr.md_file = path; | ||||
mdio->md_options = MD_AUTOUNIT | MD_READONLY; | mdr.md_file_seg = UIO_SYSSPACE; | ||||
mdio->md_mediasize = sb.st_size; | mdr.md_options = MD_AUTOUNIT | MD_READONLY; | ||||
mdio->md_unit = 0; | mdr.md_mediasize = sb.st_size; | ||||
error = kern_ioctl(td, fd, MDIOCATTACH, (void *)mdio); | mdr.md_unit = 0; | ||||
error = kern_mdattach_p(td, &mdr); | |||||
kib: FYI: This conflicts with D14712 | |||||
if (error) | if (error) | ||||
goto out; | goto out; | ||||
if (mdio->md_unit > 9) { | if (mdr.md_unit > 9) { | ||||
printf("rootmount: too many md units\n"); | printf("rootmount: too many md units\n"); | ||||
mdio->md_file = NULL; | mdr.md_file = NULL; | ||||
mdio->md_options = 0; | mdr.md_options = 0; | ||||
mdio->md_mediasize = 0; | mdr.md_mediasize = 0; | ||||
error = kern_ioctl(td, fd, MDIOCDETACH, (void *)mdio); | error = kern_mddetach_p(td, &mdr); | ||||
/* Ignore errors. We don't care. */ | /* Ignore errors. We don't care. */ | ||||
error = ERANGE; | error = ERANGE; | ||||
goto out; | goto out; | ||||
} | } | ||||
root_mount_mddev = mdio->md_unit; | root_mount_mddev = mdr.md_unit; | ||||
printf(MD_NAME "%u attached to %s\n", root_mount_mddev, mdio->md_file); | printf(MD_NAME "%u attached to %s\n", root_mount_mddev, path); | ||||
error = kern_close(td, fd); | |||||
out: | out: | ||||
free(mdio, M_TEMP); | free(path, M_TEMP); | ||||
return (error); | return (error); | ||||
} | } | ||||
static int | static int | ||||
parse_dir_onfail(char **conf) | parse_dir_onfail(char **conf) | ||||
{ | { | ||||
char *action; | char *action; | ||||
int error; | int error; | ||||
▲ Show 20 Lines • Show All 511 Lines • Show Last 20 Lines |
FYI: This conflicts with D14712