From: brian Date: Wed, 9 Jul 2008 21:07:20 +0000 (+0000) Subject: b=15625 X-Git-Tag: v1_7_0_51~2^9~2 X-Git-Url: https://git.whamcloud.com/?a=commitdiff_plain;h=ce298f8777da753c3c91fa83378ce4a827224871;p=fs%2Flustre-release.git b=15625 i=adilger i=nathan Service Tags. If the service tags package is installed on a Lustre node when a Lustre target is mounted, a service tag will be generated which can then optionally be collected by a Registration Client for addition to the Sun asset inventory system being offered at inventory.sun.com. --- diff --git a/lustre/utils/mount_utils.c b/lustre/utils/mount_utils.c new file mode 100644 index 0000000..17d00d7 --- /dev/null +++ b/lustre/utils/mount_utils.c @@ -0,0 +1,230 @@ +#include +#include +#include +#include +#include +#include +#include +#include + +extern char *progname; +extern int verbose; + +#define vprint if (verbose > 0) printf +#define verrprint if (verbose >= 0) printf + +void fatal(void) +{ + verbose = 0; + fprintf(stderr, "\n%s FATAL: ", progname); +} + +int run_command(char *cmd, int cmdsz) +{ + char log[] = "/tmp/run_command_logXXXXXX"; + int fd = -1, rc; + + if ((cmdsz - strlen(cmd)) < 6) { + fatal(); + fprintf(stderr, "Command buffer overflow: %.*s...\n", + cmdsz, cmd); + return ENOMEM; + } + + if (verbose > 1) { + printf("cmd: %s\n", cmd); + } else { + if ((fd = mkstemp(log)) >= 0) { + close(fd); + strcat(cmd, " >"); + strcat(cmd, log); + } + } + strcat(cmd, " 2>&1"); + + /* Can't use popen because we need the rv of the command */ + rc = system(cmd); + if (rc && (fd >= 0)) { + char buf[128]; + FILE *fp; + fp = fopen(log, "r"); + if (fp) { + while (fgets(buf, sizeof(buf), fp) != NULL) { + printf(" %s", buf); + } + fclose(fp); + } + } + if (fd >= 0) + remove(log); + return rc; +} + +int get_mountdata(char *dev, struct lustre_disk_data *mo_ldd) +{ + + char tmpdir[] = "/tmp/lustre_tmp.XXXXXX"; + char cmd[256]; + char filepnm[128]; + FILE *filep; + int ret = 0; + int ret2 = 0; + int cmdsz = sizeof(cmd); + + /* Make a temporary directory to hold Lustre data files. */ + if (!mkdtemp(tmpdir)) { + verrprint(stderr, "%s: Can't create temporary " + "directory %s: %s\n", + progname, tmpdir, strerror(errno)); + return errno; + } + + snprintf(cmd, cmdsz, "/sbin/debugfs -c -R 'dump /%s %s/mountdata' %s", + MOUNT_DATA_FILE, tmpdir, dev); + + ret = run_command(cmd, cmdsz); + if (ret) { + verrprint("%s: Unable to dump %s dir (%d)\n", + progname, MOUNT_CONFIGS_DIR, ret); + goto out_rmdir; + } + + sprintf(filepnm, "%s/mountdata", tmpdir); + filep = fopen(filepnm, "r"); + if (filep) { + vprint("Reading %s\n", MOUNT_DATA_FILE); + fread(mo_ldd, sizeof(*mo_ldd), 1, filep); + } else { + verrprint("%s: Unable to read %d.%d config %s.\n", + progname, LUSTRE_MAJOR, LUSTRE_MINOR, filepnm); + goto out_close; + } + +out_close: + fclose(filep); + +out_rmdir: + snprintf(cmd, cmdsz, "rm -rf %s", tmpdir); + ret2 = run_command(cmd, cmdsz); + if (ret2) { + verrprint("Failed to remove temp dir %s (%d)\n", tmpdir, ret2); + /* failure return from run_command() is more important + * than the failure to remove a dir */ + if (!ret) + ret = ret2; + } + + return ret; +} + +#define PARENT_URN "urn:uuid:2bb5bdbf-6c4b-11dc-9b8e-080020a9ed93" +#define PARENT_PRODUCT "Lustre" + +static int stclient(char *type, char *arch) +{ + + char product[64]; + char *urn = NULL; + char cmd[1024]; + FILE *fp; + int i; + + if (strcmp(type, "Client") == 0) + urn = CLIENT_URN; + else if (strcmp(type, "MDS") == 0) + urn = MDS_URN; + else if (strcmp(type, "MGS") == 0) + urn = MGS_URN; + else if (strcmp(type, "OSS") == 0) + urn = OSS_URN; + + snprintf(product, 64, "Lustre %s %d.%d.%d", type, LUSTRE_MAJOR, + LUSTRE_MINOR, LUSTRE_PATCH); + + /* need to see if the entry exists first */ + snprintf(cmd, 1024, + "/opt/sun/servicetag/bin/stclient -f -t '%s' ", urn); + fp = popen(cmd, "r"); + if (!fp) { + if (verbose) + fprintf(stderr, "%s: trying to run stclient -f: %s\n", + progname, strerror(errno)); + return 0; + } + + i = fread(cmd, 1, sizeof(cmd), fp); + if (i) { + cmd[i] = 0; + if (strcmp(cmd, "Record not found\n") != 0) { + /* exists, just return */ + pclose(fp); + return 0; + } + } + pclose(fp); + + snprintf(cmd, 1024, "/opt/sun/servicetag/bin/stclient -a -p '%s' " + "-e %d.%d.%d -t '%s' -S mount -F '%s' -P '%s' -m SUN " + "-A %s -z global", product, LUSTRE_MAJOR, LUSTRE_MINOR, + LUSTRE_PATCH, urn, PARENT_URN, PARENT_PRODUCT, arch); + + return(run_command(cmd, sizeof(cmd))); +} + +void register_service_tags(char *usource, char *source, char *target) +{ + struct lustre_disk_data mo_ldd; + struct utsname utsname_buf; + struct stat stat_buf; + char stclient_loc[] = "/opt/sun/servicetag/bin/stclient"; + int rc; + + rc = stat(stclient_loc, &stat_buf); + + if (rc == 0) { + /* call the service tags stclient to show that we use Lustre on + this system */ + + rc = uname(&utsname_buf); + if (rc) { + if (verbose) + fprintf(stderr, + "%s: trying to get uname failed: %s, " + "inventory tags will not be created\n", + progname, strerror(errno)); + } else { + + /* client or server? */ + if (strchr(usource, ':')) { + stclient("Client", utsname_buf.machine); + } else { + /* first figure what type of device it is */ + rc = get_mountdata(source, &mo_ldd); + if (rc) { + if (verbose) + fprintf(stderr, + "%s: trying to read mountdata from %s " + "failed: %s, inventory tags will not " + "be created\n", + progname, target, strerror(errno)); + } else { + + if (IS_MDT(&mo_ldd)) + stclient("MDS", utsname_buf.machine); + + if (IS_MGS(&mo_ldd)) + stclient("MGS", utsname_buf.machine); + + if (IS_OST(&mo_ldd)) + stclient("OSS", utsname_buf.machine); + } + } + } + } else { + if (errno != ENOENT && verbose) { + fprintf(stderr, + "%s: trying to stat stclient failed: %s\n", + progname, strerror(errno)); + } + } +}