--- MCONFIG +++ MCONFIG @@ -138,8 +138,8 @@ CPUTAIL=486 endif ifeq "$(CPU)" "x86_64" - CPUHEAD=-mcpu= - CPUTAIL=nocona + CPUHEAD=-mtune= + CPUTAIL=k8 endif CPUOPT= $(CPUHEAD)$(CPUTAIL) OPT= -pipe -O2 $(CPUOPT) -fomit-frame-pointer @@ -151,7 +151,7 @@ endif endif -WARNFLAGS = -Wall -Wmissing-prototypes -Wstrict-prototypes +WARNFLAGS = -Wall -Wmissing-prototypes -Wstrict-prototypes -g LIB=../lib --- configure +++ configure @@ -754,3 +754,23 @@ echo "You don't have blkid" fi rm -f conftest conftest.c + +# +# 16. For mount, do we have libvolume_id? +# +echo ' +#include +#include +int main(){ exit(0); volume_id_close(NULL); } +' > conftest.c +LIBS="-lvolume_id" +eval $compile +LIBS= +if test -s conftest; then + echo "HAVE_VOLID=yes" >> make_include + echo "You have libvolume_id" +else + echo "HAVE_VOLID=no" >> make_include + echo "You don't have libvolume_id" +fi +rm -f conftest conftest.c --- mount/Makefile +++ mount/Makefile @@ -1,7 +1,7 @@ include ../make_include include ../MCONFIG -DEFINES = -DHAVE_NFS $(BLKID_DEFINE) +DEFINES = -DHAVE_NFS $(BLKID_DEFINE) $(VOLID_DEFINE) RPCSVCDIR = rpcsvc RPC_CFLAGS = -Wno-unused @@ -25,6 +25,11 @@ BLKID_LIB = -lblkid -luuid endif +ifeq "$(HAVE_VOLID)" "yes" +VOLID_DEFINE = -DHAVE_VOLID +VOLID_LIB = -lvolume_id +endif + PROGS = $(SUID_PROGS) $(NOSUID_PROGS) MAYBE = pivot_root swapoff @@ -48,23 +53,25 @@ mount: mount.o fstab.o sundries.o xmalloc.o realpath.o mntent.o version.o \ get_label_uuid.o mount_by_label.o mount_blkid.o mount_guess_fstype.o \ + mount_udev.o \ getusername.o $(LIB)/setproctitle.o $(LIB)/env.o $(NFS_OBJS) lomount.o \ loumount.o loop.o sha512.o rmd160.o aes.o $(LIB)/xstrncpy.o - $(LINK) $^ -o $@ $(BLKID_LIB) + $(LINK) $^ -o $@ $(BLKID_LIB) $(VOLID_LIB) umount: umount.o fstab.o sundries.o xmalloc.o realpath.o mntent.o \ getusername.o get_label_uuid.o mount_by_label.o mount_blkid.o \ - version.o $(LIB)/env.o loumount.o - $(LINK) $^ -o $@ $(BLKID_LIB) + mount_udev.o version.o $(LIB)/env.o loumount.o + $(LINK) $^ -o $@ $(BLKID_LIB) $(VOLID_LIB) guessfstype: guessfstype.o mount_guess_fstype.o sundries.o realpath.o \ fstab.o mntent.o get_label_uuid.o mount_blkid.o mount_by_label.o \ - xmalloc.o - $(LINK) $^ -o $@ + mount_udev.o xmalloc.o + $(LINK) $^ -o $@ $(VOLID_LIB) swapon: swapon.o version.o xmalloc.o \ - get_label_uuid.o mount_by_label.o mount_blkid.o loop.o sha512.o $(LIB)/xstrncpy.o - $(LINK) $^ -o $@ $(BLKID_LIB) + get_label_uuid.o mount_by_label.o mount_blkid.o mount_udev.o \ + loop.o sha512.o $(LIB)/xstrncpy.o + $(LINK) $^ -o $@ $(BLKID_LIB) $(VOLID_LIB) main_losetup.o: lomount.c $(COMPILE) -DMAIN lomount.c -o $@ @@ -142,7 +149,7 @@ clean: rm -f a.out core *~ *.o swapargs.h $(PROGS) $(MAYBE) - rm -f nfs_mountversion.h + rm -f nfs_mountversion.h nfsmount_clnt.c nfsmount.h nfsmount_xdr.c clobber distclean realclean: clean rm -f $(GEN_FILES) --- mount/fstab.c +++ mount/fstab.c @@ -305,6 +305,7 @@ /* Find the entry (SPEC,FILE) in fstab */ struct mntentchn * getfsspecfile (const char *spec, const char *file) { + char *nspec; struct mntentchn *mc, *mc0; mc0 = fstab_head(); @@ -316,11 +317,12 @@ return mc; /* second attempt: names found after symlink resolution */ + nspec = canonicalize(spec); for (mc = mc0->nxt; mc && mc != mc0; mc = mc->nxt) if ((streq(mc->m.mnt_dir, file) || streq(canonicalize(mc->m.mnt_dir), file)) && (streq(mc->m.mnt_fsname, spec) || - streq(canonicalize(mc->m.mnt_fsname), spec))) + streq(canonicalize(mc->m.mnt_fsname), nspec))) return mc; /* third attempt: names found after LABEL= or UUID= resolution */ @@ -357,11 +359,21 @@ struct mntentchn * getfsspec (const char *spec) { struct mntentchn *mc, *mc0; + const char *nspec, *fsname; mc0 = fstab_head(); - for (mc = mc0->nxt; mc && mc != mc0; mc = mc->nxt) - if (streq(mc->m.mnt_fsname, spec)) + for (mc = mc0->nxt; mc && mc != mc0; mc = mc->nxt) { + if (!strncmp (mc->m.mnt_fsname, "LABEL=", 6)) { + fsname = mount_get_devname_by_label(mc->m.mnt_fsname + 6); + } else if (!strncmp(mc->m.mnt_fsname, "UUID=", 5)) { + fsname = mount_get_devname_by_uuid(mc->m.mnt_fsname + 5); + } else { + fsname = mc->m.mnt_fsname; + } + nspec = canonicalize(fsname); + if (streq(nspec, spec)) return mc; + } return NULL; } --- mount/mount.c +++ mount/mount.c @@ -1667,7 +1667,7 @@ use only for testing purposes - the guessing is not reliable at all */ { - char *fstype; + const char *fstype; fstype = do_guess_fstype(optarg); printf("%s\n", fstype ? fstype : "unknown"); exit(fstype ? 0 : EX_FAIL); @@ -1738,6 +1738,8 @@ if (mc == NULL) mc = getfsspec (spec); if (mc == NULL) + mc = getfsspec (canonicalize(spec)); + if (mc == NULL) die (EX_USAGE, _("mount: cannot find %s in %s"), spec, _PATH_FSTAB); --- mount/mount_blkid.c +++ mount/mount_blkid.c @@ -1,6 +1,7 @@ #include #include "mount_blkid.h" +#ifndef HAVE_VOLID #ifdef HAVE_BLKID blkid_cache blkid; @@ -119,3 +120,4 @@ #endif +#endif --- mount/mount_blkid.h +++ mount/mount_blkid.h @@ -11,3 +11,5 @@ extern const char *mount_get_volume_label_by_spec(const char *spec); extern const char *mount_get_devname(const char *spec); extern const char *mount_get_devname_for_mounting(const char *spec); + +extern const char *volume_id_get_tag(const char *spec, const char *token); --- mount/mount_by_label.c +++ mount/mount_by_label.c @@ -1,4 +1,4 @@ -#ifndef HAVE_BLKID +#if (!defined HAVE_BLKID) && (!defined HAVE_VOLID) /* * mount_by_label.c - aeb * --- mount/mount_guess_fstype.c +++ mount/mount_guess_fstype.c @@ -54,9 +54,23 @@ #define ETC_FILESYSTEMS "/etc/filesystems" #define PROC_FILESYSTEMS "/proc/filesystems" +#ifdef HAVE_VOLID + +static int +known_fstype(const char *fstype) { + return 0; +} + +const char * +do_guess_fstype(const char *spec) +{ + return volume_id_get_tag(spec, "TYPE"); +} + +#else #ifdef HAVE_BLKID -char * +const char * do_guess_fstype(const char *device) { return blkid_get_tag_value(blkid, "TYPE", device); @@ -208,7 +222,7 @@ return (sum == p[511]); } -char * +const char * do_guess_fstype(const char *device) { int fd; char *type = NULL; @@ -536,7 +550,7 @@ } #endif - +#endif static struct tried { struct tried *next; char *type; @@ -578,9 +592,9 @@ tried = NULL; } -char * +const char * guess_fstype(const char *spec) { - char *type = do_guess_fstype(spec); + const char *type = do_guess_fstype(spec); if (verbose) { printf (_("mount: you didn't specify a filesystem type for %s\n"), spec); --- /dev/null 2006-06-02 17:12:45.000000000 +0200 +++ mount/mount_udev.c 2006-06-12 11:14:42.285154088 +0200 @@ -0,0 +1,237 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "mount_blkid.h" + +#ifdef HAVE_VOLID + +extern int verbose; + +struct volume_id_types_t { + int id; + char *token; + char *env; +}; + +enum { + VOLUME_ID_NONE=0, + VOLUME_ID_TYPE, + VOLUME_ID_LABEL, + VOLUME_ID_UUID +}; + +#define volume_id_offset(member) (unsigned long)offsetof(struct volume_id,member) + +struct volume_id_types_t volume_id_types[] = { + { VOLUME_ID_TYPE, "TYPE", "ID_FS_TYPE" }, + { VOLUME_ID_LABEL, "LABEL", "ID_FS_LABEL" }, + { VOLUME_ID_UUID, "UUID", "ID_FS_UUID" }, + { VOLUME_ID_NONE, NULL, NULL }, +}; + +const char * +volume_id_get_tag(const char *spec, const char *token) +{ + struct volume_id *vid; + uint64_t size; + struct volume_id_types_t *volume_id_ptr = volume_id_types; + char *var, *value; + + value = calloc(1, VOLUME_ID_LABEL_SIZE); + if (!value) + return NULL; + + if (!spec) + return NULL; + + while (volume_id_ptr->token && strcmp(volume_id_ptr->token,token)) + volume_id_ptr++; + + if (!volume_id_ptr->token) { + free(value); + value = NULL; + goto out; + } + + /* Quick exit if ID_FS_* variables are set */ + if ((var = getenv(volume_id_ptr->env))) { + strncpy(value,var,VOLUME_ID_LABEL_SIZE - 1); + goto out; + } + + vid = volume_id_open_node(spec); + if (!vid) { + free(value); + value = NULL; + goto out; + } + + if (ioctl(vid->fd, BLKGETSIZE64, &size) != 0) + size = 0; + + if (volume_id_probe_all(vid, 0, size) == 0) { + switch(volume_id_ptr->id) { + case VOLUME_ID_TYPE: + strcpy(value, vid->type); + break; + case VOLUME_ID_LABEL: + strcpy(value, vid->label); + break; + case VOLUME_ID_UUID: + strcpy(value, vid->uuid); + break; + default: + free(value); + value = NULL; + break; + } + } else + value = NULL; + + volume_id_close(vid); + + out: + return value; +} + +void +mount_blkid_get_cache(void) {} + +void +mount_blkid_put_cache(void) {} + +const char * +mount_get_volume_uuid_by_spec(const char *spec) +{ + return volume_id_get_tag(spec, "UUID"); +} + +const char * +mount_get_volume_label_by_spec(const char *spec) +{ + return volume_id_get_tag(spec, "LABEL"); +} + +const char * +mount_get_devname_by_uuid(const char *uuid) { + char *dev = NULL; + + if (!uuid) + return NULL; + + dev = malloc(19 + strlen(uuid)); + if (dev) { + strcpy(dev,"/dev/disk/by-uuid/"); + strcat(dev,uuid); + } + + return dev; +} + +const char * +mount_get_devname_by_label(const char *label) { + char *dev = NULL; + + if (!label) + return NULL; + + dev = malloc(20 + strlen(label)); + if (dev) { + strcpy(dev,"/dev/disk/by-label/"); + strcat(dev,label); + } + + return dev; +} + +const char * +mount_get_devname(const char *spec) +{ + char *token, *cp, *value; + const char *nspec = NULL; + + if (!spec) + return NULL; + + token = strdup(spec); + if (!token) + return NULL; + + /* We have to return an allocated string */ + if (!(cp = strchr(token, '='))) + return token; + + value = token + (cp - token); + *value++ = '\0'; + + if (*value == '"' || *value == '\'') { + char c = *value++; + if (!(cp = strrchr(value, c))) + goto errout; /* missing closing quote */ + *cp = '\0'; + } + + if (!strcmp(token,"LABEL")) { + nspec = mount_get_devname_by_label(value); + } else if (!strcmp(token,"UUID")) { + nspec = mount_get_devname_by_uuid(value); + } + + free(token); + + errout: + return nspec; +} + +/* Also when no UUID= or LABEL= occur? No verbose? No warnings? */ +const char * +mount_get_devname_for_mounting(const char *spec) +{ + char *token, *cp, *value; + const char *nspec = NULL; + + if (!spec) + return NULL; + + token = strdup(spec); + if (!token) + return NULL; + + /* We have to return an allocated string */ + if (!(cp = strchr(token, '='))) + return token; + + value = token + (cp - token); + *value++ = '\0'; + + if (*value == '"' || *value == '\'') { + char c = *value++; + if (!(cp = strrchr(value, c))) + goto errout; /* missing closing quote */ + *cp = '\0'; + } + + if (!strcmp(token,"LABEL")) { + nspec = mount_get_devname_by_label(value); + if (nspec && verbose > 1) + printf(_("mount: going to mount %s by LABEL\n"), spec); + } else if (!strcmp(token,"UUID")) { + nspec = mount_get_devname_by_uuid(value); + if (nspec && verbose > 1) + printf(_("mount: going to mount %s by UUID\n"), spec); + } + + free(token); + + errout: + return nspec; +} + +#endif --- mount/mount_guess_fstype.h +++ mount/mount_guess_fstype.h @@ -8,8 +8,8 @@ struct mountargs { extern int verbose; -char *guess_fstype(const char *device); -char *do_guess_fstype(const char *device); +const char *guess_fstype(const char *device); +const char *do_guess_fstype(const char *device); int procfsloop(int (*mount_fn)(struct mountargs *), struct mountargs *args, const char **type); int is_in_procfs(const char *fstype);