From owner-svn-src-all@FreeBSD.ORG Sun Jan 20 22:25:59 2013 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by hub.freebsd.org (Postfix) with ESMTP id E4DA7A88; Sun, 20 Jan 2013 22:25:59 +0000 (UTC) (envelope-from nwhitehorn@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:1900:2254:2068::e6a:0]) by mx1.freebsd.org (Postfix) with ESMTP id C93DB88D; Sun, 20 Jan 2013 22:25:59 +0000 (UTC) Received: from svn.freebsd.org ([127.0.1.70]) by svn.freebsd.org (8.14.5/8.14.5) with ESMTP id r0KMPxVq041943; Sun, 20 Jan 2013 22:25:59 GMT (envelope-from nwhitehorn@svn.freebsd.org) Received: (from nwhitehorn@localhost) by svn.freebsd.org (8.14.5/8.14.5/Submit) id r0KMPxYi041939; Sun, 20 Jan 2013 22:25:59 GMT (envelope-from nwhitehorn@svn.freebsd.org) Message-Id: <201301202225.r0KMPxYi041939@svn.freebsd.org> From: Nathan Whitehorn Date: Sun, 20 Jan 2013 22:25:59 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r245700 - head/usr.sbin/bsdinstall/partedit X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 20 Jan 2013 22:26:00 -0000 Author: nwhitehorn Date: Sun Jan 20 22:25:58 2013 New Revision: 245700 URL: http://svnweb.freebsd.org/changeset/base/245700 Log: Add a simple scripted partitioner. Documentation and more scripting support will come soon. This lets the install process have a line like: bsdinstall scriptedpart 'ada0 GPT {1.5G freebsd-ufs /, 10G freebsd-swap, auto freebsd-ufs /usr}' to set up a system with a 1.5GB /, some swap space, and a /usr using the rest of ada0. MFC after: 1 month Added: head/usr.sbin/bsdinstall/partedit/scripted.c (contents, props changed) Modified: head/usr.sbin/bsdinstall/partedit/Makefile head/usr.sbin/bsdinstall/partedit/partedit.c head/usr.sbin/bsdinstall/partedit/partedit.h Modified: head/usr.sbin/bsdinstall/partedit/Makefile ============================================================================== --- head/usr.sbin/bsdinstall/partedit/Makefile Sun Jan 20 22:25:25 2013 (r245699) +++ head/usr.sbin/bsdinstall/partedit/Makefile Sun Jan 20 22:25:58 2013 (r245700) @@ -2,7 +2,8 @@ BINDIR= /usr/libexec/bsdinstall PROG= partedit -LINKS= ${BINDIR}/partedit ${BINDIR}/autopart +LINKS= ${BINDIR}/partedit ${BINDIR}/autopart \ + ${BINDIR}/partedit ${BINDIR}/scriptedpart SYMLINKS= ${BINDIR}/partedit /usr/sbin/sade LDADD= -lgeom -lncursesw -lutil -ldialog -lm @@ -15,7 +16,7 @@ PARTEDIT_ARCH= generic .endif SRCS= diskeditor.c partedit.c gpart_ops.c partedit_${PARTEDIT_ARCH}.c \ - part_wizard.c + part_wizard.c scripted.c WARNS?= 3 MAN= sade.8 Modified: head/usr.sbin/bsdinstall/partedit/partedit.c ============================================================================== --- head/usr.sbin/bsdinstall/partedit/partedit.c Sun Jan 20 22:25:25 2013 (r245699) +++ head/usr.sbin/bsdinstall/partedit/partedit.c Sun Jan 20 22:25:58 2013 (r245700) @@ -96,13 +96,16 @@ main(int argc, const char **argv) prompt = "Please review the disk setup. When complete, press " "the Finish button."; part_wizard(); + } else if (strcmp(basename(argv[0]), "scriptedpart") == 0) { + scripted_editor(argc, argv); + prompt = NULL; } else { prompt = "Create partitions for FreeBSD. No changes will be " "made until you select Finish."; } /* Show the part editor either immediately, or to confirm wizard */ - while (1) { + while (prompt != NULL) { dlg_clear(); dlg_put_backtitle(); @@ -189,6 +192,15 @@ main(int argc, const char **argv) free(items); } + if (prompt == NULL) { + error = geom_gettree(&mesh); + if (validate_setup()) { + error = apply_changes(&mesh); + } else { + gpart_revert_all(&mesh); + error = -1; + } + } geom_deletetree(&mesh); free(items); Modified: head/usr.sbin/bsdinstall/partedit/partedit.h ============================================================================== --- head/usr.sbin/bsdinstall/partedit/partedit.h Sun Jan 20 22:25:25 2013 (r245699) +++ head/usr.sbin/bsdinstall/partedit/partedit.h Sun Jan 20 22:25:58 2013 (r245700) @@ -55,6 +55,7 @@ struct partition_metadata *get_part_meta void delete_part_metadata(const char *name); int part_wizard(void); +int scripted_editor(int argc, const char **argv); /* gpart operations */ void gpart_delete(struct gprovider *pp); Added: head/usr.sbin/bsdinstall/partedit/scripted.c ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ head/usr.sbin/bsdinstall/partedit/scripted.c Sun Jan 20 22:25:58 2013 (r245700) @@ -0,0 +1,205 @@ +/*- + * Copyright (c) 2013 Nathan Whitehorn + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#include +#include +#include +#include + +#include +#include +#include + +#include "partedit.h" + +static struct gprovider * +provider_for_name(struct gmesh *mesh, const char *name) +{ + struct gclass *classp; + struct gprovider *pp = NULL; + struct ggeom *gp; + + LIST_FOREACH(classp, &mesh->lg_class, lg_class) { + if (strcmp(classp->lg_name, "DISK") != 0 && + strcmp(classp->lg_name, "PART") != 0 && + strcmp(classp->lg_name, "RAID") != 0 && + strcmp(classp->lg_name, "MD") != 0) + continue; + + LIST_FOREACH(gp, &classp->lg_geom, lg_geom) { + if (LIST_EMPTY(&gp->lg_provider)) + continue; + + LIST_FOREACH(pp, &gp->lg_provider, lg_provider) + if (strcmp(pp->lg_name, name) == 0) + break; + + if (pp != NULL) break; + } + + if (pp != NULL) break; + } + + return (pp); +} + +static int +part_config(char *disk, const char *scheme, char *config) +{ + char *partition, *ap, *size = NULL, *type = NULL, *mount = NULL; + struct gclass *classp; + struct gmesh mesh; + struct ggeom *gpart = NULL; + int error; + + if (scheme == NULL) + scheme = default_scheme(); + + error = geom_gettree(&mesh); + + /* Remove any existing partitioning and create new scheme */ + LIST_FOREACH(classp, &mesh.lg_class, lg_class) + if (strcmp(classp->lg_name, "PART") == 0) + break; + if (classp != NULL) { + LIST_FOREACH(gpart, &classp->lg_geom, lg_geom) + if (strcmp(gpart->lg_name, disk) == 0) + break; + } + if (gpart != NULL) + gpart_destroy(gpart); + gpart_partition(disk, scheme); + + if (strcmp(scheme, "PC98") == 0 || strcmp(scheme, "MBR") == 0) { + struct gmesh submesh; + geom_gettree(&submesh); + gpart_create(provider_for_name(&submesh, disk), + "freebsd", NULL, NULL, &disk, 0); + geom_deletetree(&submesh); + } else { + disk= strdup(disk); + } + + geom_deletetree(&mesh); + error = geom_gettree(&mesh); + + /* Create partitions */ + while ((partition = strsep(&config, ",")) != NULL) { + while ((ap = strsep(&partition, " \t\n")) != NULL) { + if (*ap == '\0') + continue; + if (size == NULL) + size = ap; + else if (type == NULL) + type = ap; + else if (mount == NULL) + mount = ap; + } + if (size == NULL) + continue; + if (strcmp(size, "auto") == 0) + size = NULL; + gpart_create(provider_for_name(&mesh, disk), type, size, mount, + NULL, 0); + geom_deletetree(&mesh); + error = geom_gettree(&mesh); + size = type = mount = NULL; + } + + geom_deletetree(&mesh); + free(disk); + + return (0); +} + +static +int parse_disk_config(char *input) +{ + char *ap; + char *disk = NULL, *scheme = NULL, *partconfig = NULL; + + while (input != NULL && *input != 0) { + if (isspace(*input)) { + input++; + continue; + } + + switch(*input) { + case '{': + input++; + partconfig = strchr(input, '}'); + if (partconfig == NULL) { + fprintf(stderr, "Malformed partition setup " + "string: %s\n", input); + return (1); + } + *partconfig = '\0'; + ap = partconfig+1; + partconfig = input; + input = ap; + break; + default: + if (disk == NULL) + disk = strsep(&input, " \t\n"); + else if (scheme == NULL) + scheme = strsep(&input, " \t\n"); + else { + fprintf(stderr, "Unknown directive: %s\n", + strsep(&input, " \t\n")); + return (1); + } + } + } while (input != NULL && *input != 0); + + if (disk != NULL) + part_config(disk, scheme, partconfig); + + return (0); +} + +int +scripted_editor(int argc, const char **argv) +{ + char *token; + int i, len = 0; + + for (i = 1; i < argc; i++) + len += strlen(argv[i]) + 1; + char inputbuf[len], *input = inputbuf; + strcpy(input, argv[1]); + for (i = 2; i < argc; i++) { + strcat(input, " "); + strcat(input, argv[i]); + } + + while ((token = strsep(&input, ";")) != NULL) + parse_disk_config(token); + + return (0); +} +