mirror of
https://git.freebsd.org/src.git
synced 2026-01-16 23:02:24 +00:00
Add --libxo support for geom status and list sub commands.
Submitted-by: Johan Söllvander MFC-after: 1 week Differential Revision: https://reviews.freebsd.org/D37615
This commit is contained in:
parent
2241cd10d6
commit
0d4642a67e
2 changed files with 157 additions and 77 deletions
|
|
@ -9,7 +9,7 @@ MAN= geom.8
|
|||
CFLAGS+= -I${.CURDIR} -I${.CURDIR}/core
|
||||
CFLAGS+= -DGEOM_CLASS_DIR=\"${GEOM_CLASS_DIR}\"
|
||||
|
||||
LIBADD= geom util
|
||||
LIBADD= geom util xo
|
||||
|
||||
.if defined(RESCUE)
|
||||
.PATH: ${SRCTOP}/lib/geom/part \
|
||||
|
|
|
|||
|
|
@ -49,9 +49,12 @@
|
|||
#include <assert.h>
|
||||
#include <libgeom.h>
|
||||
#include <geom.h>
|
||||
#include <libxo/xo.h>
|
||||
|
||||
#include "misc/subr.h"
|
||||
|
||||
#define GEOM_XO_VERSION "1"
|
||||
|
||||
#ifdef STATIC_GEOM_CLASSES
|
||||
extern uint32_t gpart_version;
|
||||
extern struct g_command gpart_class_commands[];
|
||||
|
|
@ -513,6 +516,7 @@ run_command(int argc, char *argv[])
|
|||
gctl_free(req);
|
||||
if (verbose)
|
||||
printf("Done.\n");
|
||||
xo_finish();
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
|
|
@ -810,6 +814,10 @@ main(int argc, char *argv[])
|
|||
provider_name = NULL;
|
||||
tflag = false;
|
||||
|
||||
argc = xo_parse_args(argc, argv);
|
||||
if (argc < 0)
|
||||
return (argc);
|
||||
|
||||
if (strcmp(getprogname(), "geom") == 0) {
|
||||
while ((ch = getopt(argc, argv, "hp:t")) != -1) {
|
||||
switch (ch) {
|
||||
|
|
@ -831,6 +839,7 @@ main(int argc, char *argv[])
|
|||
* Don't adjust argc and argv, it would break get_class().
|
||||
*/
|
||||
}
|
||||
xo_set_version(GEOM_XO_VERSION);
|
||||
|
||||
if (tflag && provider_name != NULL) {
|
||||
errx(EXIT_FAILURE,
|
||||
|
|
@ -839,6 +848,7 @@ main(int argc, char *argv[])
|
|||
|
||||
if (provider_name != NULL) {
|
||||
list_one_geom_by_provider(provider_name);
|
||||
xo_finish();
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
|
@ -882,29 +892,33 @@ find_geom(struct gclass *classp, const char *name)
|
|||
}
|
||||
|
||||
static void
|
||||
list_one_provider(struct gprovider *pp, const char *prefix)
|
||||
list_one_provider(struct gprovider *pp, const char *padding)
|
||||
{
|
||||
struct gconfig *conf;
|
||||
char buf[5];
|
||||
|
||||
printf("Name: %s\n", pp->lg_name);
|
||||
xo_emit("{Lcw:Name}{:Name}\n", pp->lg_name);
|
||||
humanize_number(buf, sizeof(buf), (int64_t)pp->lg_mediasize, "",
|
||||
HN_AUTOSCALE, HN_B | HN_NOSPACE | HN_DECIMAL);
|
||||
printf("%sMediasize: %jd (%s)\n", prefix, (intmax_t)pp->lg_mediasize,
|
||||
buf);
|
||||
printf("%sSectorsize: %u\n", prefix, pp->lg_sectorsize);
|
||||
xo_emit("{P:/%s}{Lcw:Mediasize}{:Mediasize/%jd} ({N:/%s})\n",
|
||||
padding, (intmax_t)pp->lg_mediasize, buf);
|
||||
xo_emit("{P:/%s}{Lcw:Sectorsize}{:Sectorsize/%u} \n",
|
||||
padding, pp->lg_sectorsize);
|
||||
if (pp->lg_stripesize > 0 || pp->lg_stripeoffset > 0) {
|
||||
printf("%sStripesize: %ju\n", prefix, pp->lg_stripesize);
|
||||
printf("%sStripeoffset: %ju\n", prefix, pp->lg_stripeoffset);
|
||||
xo_emit("{P:/%s}{Lcw:Stripesize}{Stripesize/%ju}\n",
|
||||
padding, pp->lg_stripesize);
|
||||
xo_emit("{P:/%s}{Lcw:Stripeoffset}{Stripeoffset/%ju}\n",
|
||||
padding, pp->lg_stripeoffset);
|
||||
}
|
||||
printf("%sMode: %s\n", prefix, pp->lg_mode);
|
||||
xo_emit("{P:/%s}{Lcw:Mode}{Mode}\n", padding, pp->lg_mode);
|
||||
LIST_FOREACH(conf, &pp->lg_config, lg_config) {
|
||||
printf("%s%s: %s\n", prefix, conf->lg_name, conf->lg_val);
|
||||
xo_emit("{P:/%s}{Lcwa:}{a:}\n", padding, conf->lg_name,
|
||||
conf->lg_name, conf->lg_val);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
list_one_consumer(struct gconsumer *cp, const char *prefix)
|
||||
list_one_consumer(struct gconsumer *cp, const char *padding)
|
||||
{
|
||||
struct gprovider *pp;
|
||||
struct gconfig *conf;
|
||||
|
|
@ -915,20 +929,24 @@ list_one_consumer(struct gconsumer *cp, const char *prefix)
|
|||
else {
|
||||
char buf[5];
|
||||
|
||||
printf("Name: %s\n", pp->lg_name);
|
||||
xo_emit("{Lcw:Name}{:Name}\n", pp->lg_name);
|
||||
humanize_number(buf, sizeof(buf), (int64_t)pp->lg_mediasize, "",
|
||||
HN_AUTOSCALE, HN_B | HN_NOSPACE | HN_DECIMAL);
|
||||
printf("%sMediasize: %jd (%s)\n", prefix,
|
||||
(intmax_t)pp->lg_mediasize, buf);
|
||||
printf("%sSectorsize: %u\n", prefix, pp->lg_sectorsize);
|
||||
xo_emit("{P:/%s}{Lcw:Mediasize}{:Mediasize/%jd} ({N:/%s})\n",
|
||||
padding, (intmax_t)pp->lg_mediasize, buf);
|
||||
xo_emit("{P:/%s}{Lcw:Sectorsize}{:Sectorsize/%u}\n",
|
||||
padding, pp->lg_sectorsize);
|
||||
if (pp->lg_stripesize > 0 || pp->lg_stripeoffset > 0) {
|
||||
printf("%sStripesize: %ju\n", prefix, pp->lg_stripesize);
|
||||
printf("%sStripeoffset: %ju\n", prefix, pp->lg_stripeoffset);
|
||||
xo_emit("{P:/%s}{Lcw:Stripesize}{:Stripesize/%ju}\n",
|
||||
padding, pp->lg_stripesize);
|
||||
xo_emit("{P:/%s}{Lcw:Stripeoffset}{:Stripesize/%ju}\n",
|
||||
padding, pp->lg_stripeoffset);
|
||||
}
|
||||
printf("%sMode: %s\n", prefix, cp->lg_mode);
|
||||
xo_emit("{P:/%s}{Lcw:Mode}{:Mode}\n", padding, pp->lg_mode);
|
||||
}
|
||||
LIST_FOREACH(conf, &cp->lg_config, lg_config) {
|
||||
printf("%s%s: %s\n", prefix, conf->lg_name, conf->lg_val);
|
||||
xo_emit("{P:/%s}{Lcwa:}{a:}\n", padding, conf->lg_name,
|
||||
conf->lg_name, conf->lg_val);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -940,27 +958,36 @@ list_one_geom(struct ggeom *gp)
|
|||
struct gconfig *conf;
|
||||
unsigned n;
|
||||
|
||||
printf("Geom name: %s\n", gp->lg_name);
|
||||
xo_emit("{Lcw:Geom name}{:Name}\n", gp->lg_name);
|
||||
LIST_FOREACH(conf, &gp->lg_config, lg_config) {
|
||||
printf("%s: %s\n", conf->lg_name, conf->lg_val);
|
||||
xo_emit("{Lcwa:}{a:}\n", conf->lg_name, conf->lg_name,
|
||||
conf->lg_val);
|
||||
}
|
||||
if (!LIST_EMPTY(&gp->lg_provider)) {
|
||||
printf("Providers:\n");
|
||||
xo_open_list("Providers");
|
||||
xo_emit("{Tc:Providers}\n");
|
||||
n = 1;
|
||||
LIST_FOREACH(pp, &gp->lg_provider, lg_provider) {
|
||||
printf("%u. ", n++);
|
||||
xo_emit("{T:/%u} ", n++);
|
||||
xo_open_instance("provider");
|
||||
list_one_provider(pp, " ");
|
||||
xo_close_instance("provider");
|
||||
}
|
||||
xo_close_list("Providers");
|
||||
}
|
||||
if (!LIST_EMPTY(&gp->lg_consumer)) {
|
||||
printf("Consumers:\n");
|
||||
xo_open_list("Consumers");
|
||||
xo_emit("{Tc:Consumers}\n");
|
||||
n = 1;
|
||||
LIST_FOREACH(cp, &gp->lg_consumer, lg_consumer) {
|
||||
printf("%u. ", n++);
|
||||
xo_emit("{T:/%u} ", n++);
|
||||
xo_open_instance("consumer");
|
||||
list_one_consumer(cp, " ");
|
||||
xo_close_instance("consumer");
|
||||
}
|
||||
xo_close_list("Consumers");
|
||||
}
|
||||
printf("\n");
|
||||
xo_emit("\n");
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -978,8 +1005,10 @@ list_one_geom_by_provider(const char *provider_name)
|
|||
if (gp == NULL)
|
||||
errx(EXIT_FAILURE, "Cannot find provider '%s'.", provider_name);
|
||||
|
||||
printf("Geom class: %s\n", gp->lg_class->lg_name);
|
||||
xo_open_container("Geom");
|
||||
xo_emit("{Lwc:Geom class}{:Class}\n", gp->lg_class->lg_name);
|
||||
list_one_geom(gp);
|
||||
xo_close_container("Geom");
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -1038,14 +1067,20 @@ std_list(struct gctl_req *req, unsigned flags __unused)
|
|||
"an instance named '%s'.",
|
||||
gclass_name, name);
|
||||
}
|
||||
xo_open_container("Geom");
|
||||
list_one_geom(gp);
|
||||
xo_close_container("Geom");
|
||||
}
|
||||
} else {
|
||||
xo_open_list("Geoms");
|
||||
LIST_FOREACH(gp, &classp->lg_geom, lg_geom) {
|
||||
if (LIST_EMPTY(&gp->lg_provider) && !all)
|
||||
continue;
|
||||
xo_open_instance("geom");
|
||||
list_one_geom(gp);
|
||||
xo_close_instance("geom");
|
||||
}
|
||||
xo_close_list("Geoms");
|
||||
}
|
||||
geom_deletetree(&mesh);
|
||||
}
|
||||
|
|
@ -1115,34 +1150,24 @@ status_update_len_prs(struct ggeom *gp, int *name_len, int *status_len)
|
|||
}
|
||||
|
||||
static char *
|
||||
status_one_consumer(struct gconsumer *cp)
|
||||
status_one_consumer(struct gconsumer *cp, const char *value)
|
||||
{
|
||||
static char buf[256];
|
||||
struct gprovider *pp;
|
||||
struct gconfig *conf;
|
||||
const char *state, *syncr;
|
||||
char *ret;
|
||||
|
||||
pp = cp->lg_provider;
|
||||
if (pp == NULL)
|
||||
return (NULL);
|
||||
state = NULL;
|
||||
syncr = NULL;
|
||||
ret = NULL;
|
||||
LIST_FOREACH(conf, &cp->lg_config, lg_config) {
|
||||
if (strcasecmp(conf->lg_name, "state") == 0)
|
||||
state = conf->lg_val;
|
||||
if (strcasecmp(conf->lg_name, "synchronized") == 0)
|
||||
syncr = conf->lg_val;
|
||||
if (strcasecmp(conf->lg_name, value) == 0)
|
||||
ret = conf->lg_val;
|
||||
}
|
||||
if (state == NULL && syncr == NULL)
|
||||
snprintf(buf, sizeof(buf), "%s", pp->lg_name);
|
||||
else if (state != NULL && syncr != NULL) {
|
||||
snprintf(buf, sizeof(buf), "%s (%s, %s)", pp->lg_name,
|
||||
state, syncr);
|
||||
} else {
|
||||
snprintf(buf, sizeof(buf), "%s (%s)", pp->lg_name,
|
||||
state ? state : syncr);
|
||||
}
|
||||
return (buf);
|
||||
|
||||
if (ret == NULL)
|
||||
return (NULL);
|
||||
return (ret);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -1150,8 +1175,8 @@ status_one_geom(struct ggeom *gp, int script, int name_len, int status_len)
|
|||
{
|
||||
struct gconsumer *cp;
|
||||
struct gconfig *conf;
|
||||
const char *name, *status, *component;
|
||||
int gotone;
|
||||
const char *name, *status, *cstate, *csyncr;
|
||||
int gotone, len;
|
||||
|
||||
name = gp->lg_name;
|
||||
status = "N/A";
|
||||
|
|
@ -1161,21 +1186,49 @@ status_one_geom(struct ggeom *gp, int script, int name_len, int status_len)
|
|||
break;
|
||||
}
|
||||
}
|
||||
gotone = 0;
|
||||
gotone = len = 0;
|
||||
xo_open_instance("status");
|
||||
LIST_FOREACH(cp, &gp->lg_consumer, lg_consumer) {
|
||||
component = status_one_consumer(cp);
|
||||
if (component == NULL)
|
||||
cstate = status_one_consumer(cp, "state");
|
||||
csyncr = status_one_consumer(cp, "synchronized");
|
||||
if (cstate == NULL && csyncr == NULL)
|
||||
continue;
|
||||
if (!gotone || script) {
|
||||
if (!gotone) {
|
||||
xo_emit("{:name/%*s} {:status/%*s} ",
|
||||
name_len, name, status_len, status);
|
||||
} else {
|
||||
xo_emit("{d:name/%*s} {d:status/%*s} ",
|
||||
name_len, name, status_len, status);
|
||||
}
|
||||
xo_open_list("components");
|
||||
}
|
||||
|
||||
xo_open_instance("components");
|
||||
if (cstate != NULL && csyncr != NULL) {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:state}, {:synchronized})\n",
|
||||
len, "", cp->lg_provider->lg_name, cstate, csyncr);
|
||||
} else if (cstate != NULL) {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:state})\n",
|
||||
len, "", cp->lg_provider->lg_name, cstate);
|
||||
} else {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:synchronized})\n",
|
||||
len, "", cp->lg_provider->lg_name, csyncr);
|
||||
}
|
||||
xo_close_instance("components");
|
||||
gotone = 1;
|
||||
printf("%*s %*s %s\n", name_len, name, status_len, status,
|
||||
component);
|
||||
if (!script)
|
||||
name = status = "";
|
||||
if (!len && !script)
|
||||
len = name_len + status_len + 4;
|
||||
}
|
||||
if (!gotone) {
|
||||
printf("%*s %*s %s\n", name_len, name, status_len, status,
|
||||
"N/A");
|
||||
xo_emit("{:name/%*s} {:status/%*s} ", name_len, name, status_len, status);
|
||||
xo_open_list("components");
|
||||
xo_open_instance("components");
|
||||
xo_emit("{P:/%*s}{d:compontent}\n", len, "", "N/A");
|
||||
xo_close_instance("components");
|
||||
}
|
||||
xo_close_list("components");
|
||||
xo_close_instance("status");
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -1184,9 +1237,10 @@ status_one_geom_prs(struct ggeom *gp, int script, int name_len, int status_len)
|
|||
struct gprovider *pp;
|
||||
struct gconsumer *cp;
|
||||
struct gconfig *conf;
|
||||
const char *name, *status, *component;
|
||||
int gotone;
|
||||
const char *name, *status, *cstate, *csyncr;
|
||||
int gotone, len;
|
||||
|
||||
xo_open_instance("status");
|
||||
LIST_FOREACH(pp, &gp->lg_provider, lg_provider) {
|
||||
name = pp->lg_name;
|
||||
status = "N/A";
|
||||
|
|
@ -1202,22 +1256,50 @@ status_one_geom_prs(struct ggeom *gp, int script, int name_len, int status_len)
|
|||
break;
|
||||
}
|
||||
}
|
||||
gotone = 0;
|
||||
gotone = len = 0;
|
||||
LIST_FOREACH(cp, &gp->lg_consumer, lg_consumer) {
|
||||
component = status_one_consumer(cp);
|
||||
if (component == NULL)
|
||||
cstate = status_one_consumer(cp, "state");
|
||||
csyncr = status_one_consumer(cp, "synchronized");
|
||||
if (cstate == NULL && csyncr == NULL)
|
||||
continue;
|
||||
|
||||
if (!gotone || script) {
|
||||
if (!gotone) {
|
||||
xo_emit("{:name/%*s} {:status/%*s} ",
|
||||
name_len, name, status_len, status);
|
||||
} else {
|
||||
xo_emit("{d:name/%*s} {d:status/%*s} ",
|
||||
name_len, name, status_len, status);
|
||||
}
|
||||
xo_open_list("components");
|
||||
}
|
||||
|
||||
xo_open_instance("component");
|
||||
if (cstate != NULL && csyncr != NULL) {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:state}, {:synchronized})\n",
|
||||
len, "", cp->lg_provider->lg_name, cstate, csyncr);
|
||||
} else if (cstate != NULL) {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:state})\n",
|
||||
len, "", cp->lg_provider->lg_name, cstate);
|
||||
} else {
|
||||
xo_emit("{P:/%*s}{:compontent} ({:synchronized})\n",
|
||||
len, "", cp->lg_provider->lg_name, csyncr);
|
||||
}
|
||||
xo_close_instance("component");
|
||||
gotone = 1;
|
||||
printf("%*s %*s %s\n", name_len, name,
|
||||
status_len, status, component);
|
||||
if (!script)
|
||||
name = status = "";
|
||||
if (!len && !script)
|
||||
len = name_len + status_len + 4;
|
||||
}
|
||||
if (!gotone) {
|
||||
printf("%*s %*s %s\n", name_len, name,
|
||||
status_len, status, "N/A");
|
||||
xo_emit("{:name/%*s} {:status/%*s} ", name_len, name, status_len, status);
|
||||
xo_open_list("components");
|
||||
xo_open_instance("components");
|
||||
xo_emit("{P:/%*s}{d:compontent}\n", len, "", "N/A");
|
||||
xo_close_instance("components");
|
||||
}
|
||||
xo_close_list("components");
|
||||
}
|
||||
xo_close_instance("status");
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -1240,13 +1322,9 @@ std_status(struct gctl_req *req, unsigned flags __unused)
|
|||
all = gctl_get_int(req, "all");
|
||||
geoms = gctl_get_int(req, "geoms");
|
||||
script = gctl_get_int(req, "script");
|
||||
if (script) {
|
||||
name_len = 0;
|
||||
status_len = 0;
|
||||
} else {
|
||||
name_len = strlen("Name");
|
||||
status_len = strlen("Status");
|
||||
}
|
||||
name_len = strlen("Name");
|
||||
status_len = strlen("Status");
|
||||
|
||||
if (nargs > 0) {
|
||||
for (i = 0, n = 0; i < nargs; i++) {
|
||||
name = gctl_get_ascii(req, "arg%d", i);
|
||||
|
|
@ -1282,9 +1360,10 @@ std_status(struct gctl_req *req, unsigned flags __unused)
|
|||
goto end;
|
||||
}
|
||||
if (!script) {
|
||||
printf("%*s %*s %s\n", name_len, "Name", status_len, "Status",
|
||||
"Components");
|
||||
xo_emit("{T:/%*s} {T:/%*s} {T:Components}\n",
|
||||
name_len, "Name", status_len, "Status");
|
||||
}
|
||||
xo_open_list("status");
|
||||
if (nargs > 0) {
|
||||
for (i = 0; i < nargs; i++) {
|
||||
name = gctl_get_ascii(req, "arg%d", i);
|
||||
|
|
@ -1312,6 +1391,7 @@ std_status(struct gctl_req *req, unsigned flags __unused)
|
|||
}
|
||||
}
|
||||
}
|
||||
xo_close_list("status");
|
||||
end:
|
||||
geom_deletetree(&mesh);
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue