diff -Naur /usr/local/src/util-linux-2.9r/MCONFIG /usr/local/src/util-linux-2.9r_ehd/MCONFIG --- /usr/local/src/util-linux-2.9r/MCONFIG Fri Mar 12 18:40:49 1999 +++ /usr/local/src/util-linux-2.9r_ehd/MCONFIG Fri Jun 25 16:23:38 1999 @@ -16,7 +16,7 @@ # If HAVE_PAM is set to "yes", then login, chfn, chsh, and newgrp # will use PAM for authentication. Additionally, passwd will not be # installed as it is not PAM aware. -HAVE_PAM=no +HAVE_PAM=yes # If HAVE_SHADOW is set to "yes", then login, chfn, chsh, newgrp, passwd, # and vipw will not be built or installed from the login-utils diff -Naur /usr/local/src/util-linux-2.9r/defines.h /usr/local/src/util-linux-2.9r_ehd/defines.h --- /usr/local/src/util-linux-2.9r/defines.h Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/defines.h Fri Jun 25 11:33:00 1999 @@ -0,0 +1,5 @@ +#define HAVE_inet_aton +#define HAVE_scsi_h +#define HAVE_locale_h +#define HAVE_libintl_h +#define ENABLE_NLS diff -Naur /usr/local/src/util-linux-2.9r/login-utils/Changelog.ehd /usr/local/src/util-linux-2.9r_ehd/login-utils/Changelog.ehd --- /usr/local/src/util-linux-2.9r/login-utils/Changelog.ehd Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/Changelog.ehd Sun Jul 11 22:54:03 1999 @@ -0,0 +1,86 @@ + +Version 0.6, Jul 11, 1999, Id Est + + - fixed a bug wherein if the home-directory file creation process + was aborted somehow before the user correctly supplied a password, + the loop device wouldn't be freed. closed a couple of open file + descriptors that were left open past the point they should've + been closed. + + - modified "login.c" to allow the user to choose the size of his/her + login directory (4/8/16/32/64/128/256/512/1024 MB). + + - minor error message modification. + +Version 0.5, Jun 25, 1999, Id Est + + - modified "login-utils/Makefile" to link in "rmd160.o" to "login" + whether or not "HAVE_PAM=yes" and/or "USE_TTY_GROUP=yes" are + defined in the file "MCONFIG". + + - modified "README.ehd" to explain what must be done to compile + "login" on a system that doesn't use PAM. + +Version 0.4, Jun 24, 1999, Id Est + + - added "util-linux-2.9r.tar.gz" and "util-linux-2.9r_ehd.tar.gz" + to the website. + + - modified README.ehd to reflect a fix for the problem of a user + not being about to log in because of stale lock files left over + after a sudden loss of system power. here is the gist of the + problem and the solution: + + here's what i found concerning abrupt power-off with an active + encrypted-home-directory: + + user "test" was logged in with home="/crypt/test" when i powered-down + the system. when "test" attempted to login after the system came back + up, i saw the following: + + login: test + Password: + Last login: Thu Jun 24 07:34:47 on tty2 + Need a passphrase to enter your home directory. + Passphrase: + No directory /crypt/test! + Logging in with home="/". + bash: /crypt/test/.bash_profile: Permission denied + $ + + logging "test" out and re-logging in didn't change anything. + + the problem was that a lock file was left in "/var/lock/login" when the + system lost power, and was not removed when the system came back up. + + i logged "test" out, removed the stale lock file, and "test" was able + to successfully log in. all the files in "test"'s home directory + appeared to be fine. + + so the solution is to put the following line in "/etc/rc.d/rc.sysinit" + (or the equivalent on a non-RedHat system) to remove stale lock files + before the system comes up: + + ... + /bin/rm -f /var/lock/login/* + ... + +Version 0.3, Jun 22, 1999, Id Est + + - added code to allow user to choose his/her encryption method + from BLOWFISH, CAST128, DFC, IDEA, MARS, RC6, or SERPENT + (default: BLOWFISH). + +Version 0.2, Jun 19, 1999, Id Est + + - fixed bug wherein if you entered a too-short password three times + in a row, you were allowed to continue creating the encrypted + directory anyway. + + - added messages detailing exactly which system error that occurred + during the encrypted-directory creation process to allow for easier + debugging. + +Version 0.1, Jun 17, 1999, Id Est + + - first public release. diff -Naur /usr/local/src/util-linux-2.9r/login-utils/Makefile /usr/local/src/util-linux-2.9r_ehd/login-utils/Makefile --- /usr/local/src/util-linux-2.9r/login-utils/Makefile Wed Feb 24 12:24:54 1999 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/Makefile Fri Jun 25 16:16:02 1999 @@ -1,4 +1,5 @@ # Makefile -- Makefile for util-linux Linux utilities + # Created: Sat Dec 26 20:09:40 1992 # Revised: Sun Nov 10 20:28:43 1996 by faith@cs.unc.edu # Copyright 1992, 1993, 1994, 1995 Rickard E. Faith (faith@cs.unc.edu) @@ -94,10 +95,10 @@ last: last.o ifeq "$(HAVE_PAM)" "yes" -login: login.o $(LIB)/setproctitle.o +login: login.o $(LIB)/setproctitle.o rmd160.o $(CC) $(LDFLAGS) -o $@ $^ $(CRYPT) $(PAM) else -login: login.o $(LIB)/setproctitle.o checktty.o +login: login.o $(LIB)/setproctitle.o checktty.o rmd160.o $(CC) $(LDFLAGS) -o $@ $^ $(CRYPT) endif @@ -123,12 +124,12 @@ ifeq "$(USE_TTY_GROUP)" "yes" login.o: login.c $(LIB)/pathnames.h $(LIB)/setproctitle.c $(LIB)/setproctitle.h - $(CC) -c $(CFLAGS) $(PAMFL) -DUSE_TTY_GROUP login.c + $(CC) -c $(CFLAGS) $(PAMFL) -DUSE_TTY_GROUP -DEHD login.c mesg.o: mesg.c $(LIB)/err.h $(CC) -c $(CFLAGS) -DUSE_TTY_GROUP mesg.c else login.o: $(LIB)/pathnames.h - $(CC) -c $(CFLAGS) $(PAMFL) login.c + $(CC) -c $(CFLAGS) $(PAMFL) -DEHD login.c mesg.o: $(LIB)/err.h endif diff -Naur /usr/local/src/util-linux-2.9r/login-utils/README.ehd /usr/local/src/util-linux-2.9r_ehd/login-utils/README.ehd --- /usr/local/src/util-linux-2.9r/login-utils/README.ehd Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/README.ehd Sun Jul 11 22:53:46 1999 @@ -0,0 +1,268 @@ + +WHAT IS THIS? + +I have patched util-linux-2.9r so that "login" will generate and use +encrypted home directories. This patch will only work with 2.2.X kernels +that have been patched with the strong encryption patches available on +www.kerneli.org. + + +WHY? + +I couldn't get CFS to work on my laptop, and TCFS hasn't been ported to +2.2.X yet. ppdd is still pretty new. If there was a linux version of +"Scramdisk", I probably wouldn't have bothered to write this. + + +NO, I MEANT WHY SHOULD I USE IT? + +You could use it to keep your home directory encrypted when you're not +logged in. When you log in, your directory is automagically decrypted. +When you logout, your home directory, and the files in it, are encrypted +again. + +Hmm, my friend D. says this isn't correct. He says whatever you read/write +is decrypted/encrypted on-the-fly. + +Anyway, if you're running linux on a laptop, and the laptop gets stolen, +your files can't be read. + + +WHAT'S THE CATCH? + +This is *alpha* software. It no doubt contains bugs, more bugs, and yet +more bugs. Use it at your own risk. The author accepts no responsibility +for loss of your precious data. If you're not comfortable patching critical +system programs, this probably isn't for you. You should be comfortable with +loop devices before making use of this patch. + + +HOW DOES IT WORK? + +If your home directory begins with "/crypt/", the following happens when +you log in: + + - a free loop device is found. + + - you're asked for the size of your home directory (4/8/16/32/64/128/ + 256/512/1024 MB). + + - once you've selected a size, a nMB-sized file named "/crypt/(your-id)" + is created (ie. /crypt/101). + + - you are asked for a passphrase and given your choice of encryption + algorithm. + + - if this is the first time you've logged in, the password you gave + is one-way hashed and put into the file "/crypt/(your uid).x", or + compared against the contents of that file otherwise. if the given + passphrase(s) don't match, you get bounced out at this point. + + - the loop device is set up using the previously created file and + the passphrase you supplied. + + - if this is the first time through, a ext2 filesystem is created + on the loop device, otherwise the filesystem is checked for + errors. if no errors are found, the filesystem is mounted on + the loop device and you can proceed normally. + + - if you're logged in and you log in again from another VT, you're + asked for the passphrase, which is compared against the stored + passphrase, and if they match, you can proceed. this is to stop + somebody who knows your login password, but not your EHD passphrase + from piggybacking into your directory. + + - when you log out the last time, the filesystem is unmounted and + the loop device is freed. + + +HOW DO I USE IT? + + - you must be running 2.2.X with strong encryption. go to + www.kerneli.org to download the kernel patches to enable + strong encryption in your 2.2.X kernel. + + - you must have loop devices enabled in the kernel, as well as + strong encryption. + + - you must find a copy of "util-linux-2.9r.tar.gz", then gunzip and + untar it somewhere to produce the directory "util-linux-2.9r". + + as an alternative, you can download the already-patched file + "util-linux-2.9r_ehd.tar.gz" directly from this website and + skip the next step. + + - download the file "ehd-X.Ypatch". put this file into the same + place you put "util-linux-2.9r". type the command + + patch -p0 < ehd-X.Y.patch + + you should now have the directory "util-linux-2.9r_ehd". + + - change directory to util-linux-2.9r_ehd. + + - if your system doesn't use PAM (PAM = Pluggable Authentication Modules, + used by default in RedHat, apparently not used in Slackware, i'm not + sure about Debian or any other variants), you'll have to modify the + file "MCONFIG" and comment out the line "HAVE_PAM=yes". + + - type "./config". + + - cd util-linux-2.9r_ehd/mount, and type "make" to create a version + of "losetup" that contains BLOWFISH encryption. + + - before installing "losetup", test it by doing the following: + + dd if=/dev/zero of=/tmp/testfile bs=1k count=1024 + ./losetup -e blowfish /dev/loop0 /tmp/testfile + mkfs -t ext2 /dev/loop0 1024 + mount -t ext2 /dev/loop0 /mnt + umount /dev/loop0 + ./losetup -d /dev/loop0 + + if that worked, strongly-encrypted loop devices should be working + correctly. + + - after building "losetup", cd ../login-utils, and type "make login". + + - test "login" by doing the following: + + - make sure that you're logged in AT LEAST once as root on + another VT! + + - make sure you have at least 4MB free under "/" ! + + - cp /bin/login /bin/login.old && chattr +i /bin/login.old + - cp -f login /bin/login + - mkdir /crypt + + - create a user called "test", with a home directory of "/crypt/test". + + - try logging in as "test". you should see + + You don't seem to have an encrypted home directory. + Setting one up for you. + + Choose a size for your home directory: + + 4: 4MB + 8: 8MB + 16: 16MB + 32: 32MB (default) + 64: 64MB + 128: 128MB + 256: 256MB + 512: 512MB + 1024: 1024MB + + Size [32MB] ? 4 + + Creating a 4MB home directory. Patience please ... done. + + Choose an encryption method: + + 0: BLOWFISH (default) + 1: CAST128 + 2: DFC + 3: IDEA + 4: MARS + 5: RC6 + 6: SERPENT + + Encryption method [0] ? + + Using the BLOWFISH encryption method. + + You'll need a passphrase to decrypt your home directory. + It can be up to 256 characters long. + + *DO NOT* use your login password! + + Passphrase: + + - type in a passphrase. you should see + + Again, please: + + - retype your passphrase. if you retyped it correctly you should see + + Saving encrypted passphrase ... (a few seconds pass) done. + Creating filesystem ... (a few seconds pass) done. + Mounting filesystem as your home ... (a few seconds pass) done. + + - logout, and then try logging in the same way again as "test". + you should see + + Last login: Mon Jun 7 20:09:23 on tty3 + Your home directory appears to be encrypted. + Passphrase: + + - type in your passphrase. you should see + + Checking filesystem ... looks OK. + Mounting filesystem as your home ... done. + + +I REBOOTED AND NOW I CAN'T LOG IN ANYMORE! + + Stale lock files can be left around in "/var/lock/login" if the system + loses power / is rebooted when an encrypted-home-directory is active, + which will make it impossible for the user to log back in. The solution + to this problem is to put the following line into the file + + "/etc/rc.d/rc.sysinit" (or the equivalent on non-RedHat systems) + + to remove any stale lock files when the system comes up: + + ... + + /bin/rm -f /var/lock/login/* + + ... + + +CAVEATS + + Root can read your files once you've logged in. You can't change your + password once you've set it, and if you forget it, you're screwed. + "su" and "ssh" aren't supported yet. If you remove or muck with + "/crypt/XXX" and/or "/crypt/XXX.x" and/or "/var/lock/login/*" while + you're logged in, things will break badly. If anybody but you is in + your directory when you logout, the filesystem won't umount and the + loop device won't be deallocated. If "e2fsck", "mkfs", and "mount" + are in funny places, it won't work. + + If things go very wrong, you may be able to recover using something + like the following: + + # losetup -d /dev/loop0 (or loop1 or loop2 or whatever) + # /bin/rm -fr /var/lock/login + + If that doesn't work, reboot, and everything should get cleaned up + correctly. + + I wouldn't change root's home directory to "/crypt/root" myself, + but if anybody wants to try, I'd be interested in hearing what + happened. Probably things will blow up in a spectacular fashion + and hose your system. Don't say I didn't warn you. + + +DOCUMENTATION + + For now, aside from this file, there is none. Read the source. + + +BUGS + + No doubt there are bugs. If you find them, please send email. + Try to be descriptive. "It doesn't work!" isn't much help. + And before you ask, I can't help you if you forget your + passphrase. Pick up any phone and ask for the NSA, they'll + be glad to help you :) + + Constructive comments, money, and beer are welcome. + Flames and spam -> /dev/null. + + Id Est + July 11, 1999. + diff -Naur /usr/local/src/util-linux-2.9r/login-utils/login.c /usr/local/src/util-linux-2.9r_ehd/login-utils/login.c --- /usr/local/src/util-linux-2.9r/login-utils/login.c Sat May 1 20:16:35 1999 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/login.c Sun Jul 11 22:45:01 1999 @@ -56,6 +56,32 @@ - added Native Language Support Sun Mar 21 1999 - Arnaldo Carvalho de Melo - fixed strerr(errno) in gettext calls + + 1999-6-16, Id Est + - added support for BLOWFISH-encrypted home directories. + + 1999-6-19, Id Est + - fixed bug wherein if you entered a too-short password three times + in a row, you were allowed to continue creating the encrypted + directory anyway. + - added messages detailing exactly which system error that occurred + during the encrypted-directory creation process to allow for easier + debugging. + + 1999-6-22, Id Est + - added code to allow user to choose his/her encryption method + from BLOWFISH, CAST128, DFC, IDEA, MARS, RC6, or SERPENT + (default: BLOWFISH). + + 1999-7-11, Id Est + - fixed a bug wherein if the home-directory file creation process + was aborted somehow before the user correctly supplied a password, + the loop device wouldn't be freed. closed a couple of open file + descriptors that were left open past the point they should've + been closed. + - modified to allow the user to choose the size of his/her login + directory (4/8/16/32/64/128/256/512/1024 MB). + - minor error message modification. */ /* @@ -119,6 +145,23 @@ #include "my_crypt.h" #include "nls.h" +#ifdef EHD +#include +#include "loop.h" +#include "rmd160.h" +#define LOGINLOCK "/var/lock/login/.lock" +#define MAX_LOOP 8 +#define PIDDIR "/var/lock/login" +#define USE_BLOWFISH 0 +#define USE_CAST128 1 +#define USE_DFC 2 +#define USE_IDEA 3 +#define USE_MARS 4 +#define USE_RC6 5 +#define USE_SERPENT 6 +#define MAXSIZES 9 +#endif /*EHD*/ + #ifdef __linux__ # include # include @@ -273,6 +316,51 @@ } +#ifdef EHD +static int +run(char *cmd) +{ + /* safer than using system() */ + + char *argv[4]; + extern char **environ; + int pid, status; + + if (!cmd) + return(1); + + switch (pid = fork()) { + + case -1: + return(-1); + + case 0: /* child */ + + argv[0] = "sh"; + argv[1] = "-c"; + argv[2] = cmd; + argv[3] = 0; + (void) execve("/bin/sh", argv, environ); + exit(127); + /*NOTREACHED*/ + + default: /* parent */ + + do { + if (waitpid(pid, &status, 0) == -1) { + + if (errno != EINTR) + return(-1); + } else + return(status); + + } while(1); + } + +} /* run */ +#endif /* EHD */ + + int main(int argc, char **argv) { @@ -304,7 +392,18 @@ #ifndef __linux__ int ioctlval; #endif - +#ifdef EHD + char buf[40], buf2[40], cmd[256], f[64], line[256], p1[256], p2[256], + *pass = NULL, tmp[256], zilch[1024]; + int fd, i, j, k, ld, loginlock, loopdev = -1, make_fs = 0, + mb = 0, ok = 0, pf, usercount = 0; + static const char bin2hex[] = { + '0', '1', '2', '3', '4', '5', '6', '7', + '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' + }; + static const int sizes[] = { 4, 8, 16, 32, 64, 128, 256, 512, 1024 }; +struct loop_info loopinfo; +#endif /* EHD */ signal(SIGALRM, timedout); alarm((unsigned int)timeout); signal(SIGQUIT, SIG_IGN); @@ -1041,14 +1140,672 @@ } } - signal(SIGALRM, SIG_DFL); - signal(SIGQUIT, SIG_DFL); - signal(SIGTSTP, SIG_IGN); - signal(SIGHUP, SIG_DFL); +#ifdef EHD + if (strncmp(pwd->pw_dir, "/crypt/", 7) == 0) { + + (void) mkdir(PIDDIR, 0700); + + if ((loginlock = open(LOGINLOCK, O_CREAT|O_WRONLY, 0600)) < 0) { + (void) fprintf(stderr, "Cannot create loginlock!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + exit(1); + /*NOTREACHED*/ + } + + (void) flock(loginlock, LOCK_EX); /* block */ + + (void) sprintf(tmp, "%s/%d", PIDDIR, pwd->pw_uid); + if ((fd = open(tmp, O_RDONLY)) < 0) { + + /* user isn't logged in at all, so find a free loop device. */ + + for (i = 0; i < MAX_LOOP; i++) { + + (void) sprintf(tmp, "/dev/loop%d", i); + if ((ld = open(tmp, O_RDWR)) < 0) + continue; + + if (ioctl(ld, LOOP_GET_STATUS, &loopinfo) < 0) { + (void) close(ld); + loopdev = i; + break; + } + + (void) close(ld); + } + + if (loopdev < 0) { + (void) fprintf(stderr, "Cannot get a loop device!\n"); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) sprintf(f, "/crypt/%d", (int) pwd->pw_uid); + if ((fd = open(f, O_RDONLY)) < 0) { + + (void) fprintf(stderr, + "\nYou don't seem to have an encrypted home directory.\n"); + (void) fprintf(stderr, "Setting one up for you.\n"); + + for (i = 0, ok = 0; i < 3; i++) { + + (void) fprintf(stderr, "\n%s:\n\n", + i == 2 ? "Last chance. Choose a size" : + "Choose a size for your home directory"); + + for (j = 0; j < MAXSIZES; j++) + (void) fprintf(stderr, " %4d: %4dMB%s", + sizes[j], sizes[j], + sizes[j] == 32 ? " (default)\n" : "\n"); + + (void) fprintf(stderr, "\nSize [32MB] ? "); + + (void) memset(line, 0, 256); + (void) fgets(line, 255, stdin); + + if (!line[0] || line[0] == '\n') { + mb = 32; + ok = 1; + break; + } + + mb = atoi(line); + + if (mb < 0) { + (void) fprintf(stderr, "\nInvalid size.\n"); + continue; + } + + for (j = 0; j < MAXSIZES; j++) + if (mb == sizes[j]) { + ok = 1; + break; + } + + if (ok) + break; + else + (void) fprintf(stderr, "\nInvalid size.\n"); + } + + if (!ok) { + (void) fprintf(stderr, "\nTry again later.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) fprintf(stderr, + "\nCreating a home directory of %dMB. Patience please ...", + mb); + + if ((fd = open(f, O_CREAT|O_WRONLY, 0600)) < 0) { + (void) fprintf(stderr, + "Cannot create your encrypted home directory!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) memset(zilch, 0, 1024); + for (i = 0; i < mb * 1024; i++) + (void) write(fd, zilch, 1024); + (void) close(fd); + (void) chown(f, 0, 0); + (void) chmod(f, 0600); + + make_fs = 1; + + (void) fprintf(stderr, " done.\n"); + } + + /* + * set up the loop device. + */ + + (void) sprintf(tmp, "/dev/loop%d", loopdev); + if ((ld = open(tmp, O_RDONLY)) < 0) { + (void) fprintf(stderr, "Cannot open loop device %d!\n", + loopdev); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) unlink(f); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) sprintf(tmp, "/crypt/%d", (int) pwd->pw_uid); + if ((fd = open(tmp, O_RDWR)) < 0) { + (void) fprintf(stderr, "Cannot open loop device %d!\n", + loopdev); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) unlink(f); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) memset(&loopinfo, 0, sizeof(loopinfo)); + (void) strncpy(loopinfo.lo_name, tmp, LO_NAME_SIZE); + loopinfo.lo_name[LO_NAME_SIZE-1] = 0; + loopinfo.lo_offset = 0; + + if (make_fs) { + + /* + * allow the user to choose the encryption method. + */ + + for (i = 0, ok = 0; i < 3; i++) { + + (void) fprintf(stderr, "\n%s:\n\n", + i == 2 ? "Last chance. Choose a method" : + "Choose an encryption method"); + + (void) fprintf(stderr, "\t0: BLOWFISH (default)\n"); + (void) fprintf(stderr, "\t1: CAST128\n"); + (void) fprintf(stderr, "\t2: DFC\n"); + (void) fprintf(stderr, "\t3: IDEA\n"); + (void) fprintf(stderr, "\t4: MARS\n"); + (void) fprintf(stderr, "\t5: RC6\n"); + (void) fprintf(stderr, "\t6: SERPENT\n"); + (void) fprintf(stderr, "\nEncryption method [0] ? "); + (void) fflush(stderr); + + (void) memset(line, 0, 256); + (void) fgets(line, 255, stdin); + + if (!line[0] || line[0] == '\n') { + loopinfo.lo_encrypt_type = LO_CRYPT_BLOW; + loopinfo.lo_encrypt_key_size = 20; /* 160 bit key */ + ok = 1; + break; + } + + switch (line[0] - '0') { + + case USE_BLOWFISH: + loopinfo.lo_encrypt_type = LO_CRYPT_BLOW; + loopinfo.lo_encrypt_key_size = 20; /* 160 bit key */ + ok = 1; + break; + + case USE_CAST128: + loopinfo.lo_encrypt_type = LO_CRYPT_CAST128; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + case USE_DFC: + loopinfo.lo_encrypt_type = LO_CRYPT_DFC; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + case USE_IDEA: + loopinfo.lo_encrypt_type = LO_CRYPT_IDEA; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + case USE_MARS: + loopinfo.lo_encrypt_type = LO_CRYPT_MARS; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + case USE_RC6: + loopinfo.lo_encrypt_type = LO_CRYPT_RC6; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + case USE_SERPENT: + loopinfo.lo_encrypt_type = LO_CRYPT_SERPENT; + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + ok = 1; + break; + + default: + (void) fprintf(stderr, + "\nUnknown encryption method %d.\n", line[0] - '0'); + } + + if (ok) + break; + } + + if (!ok) { + (void) fprintf(stderr, "\nTry again later.\n"); + (void) sleep(5); + (void) unlink(f); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) fprintf(stderr, "\nUsing the %s encryption method.\n", + loopinfo.lo_encrypt_type == LO_CRYPT_BLOW ? "BLOWFISH" : + loopinfo.lo_encrypt_type == LO_CRYPT_CAST128 ? "CAST128" : + loopinfo.lo_encrypt_type == LO_CRYPT_DFC ? "DFC" : + loopinfo.lo_encrypt_type == LO_CRYPT_IDEA ? "IDEA" : + loopinfo.lo_encrypt_type == LO_CRYPT_MARS ? "MARS" : + loopinfo.lo_encrypt_type == LO_CRYPT_RC6 ? "RC6" : + "SERPENT"); + + /* + * ask the user for a password to decrypt the home directory. + * hash it, then write it to a file near the home directory. + * would like to compare the given password to the login + * password, but i don't think PAM will let us do that. + */ + + (void) fprintf(stderr, + "\nYou'll need a passphrase to decrypt this directory.\n"); + (void) fprintf(stderr, + "It can be up to 256 characters long.\n"); + (void) fprintf(stderr, + "\n*DO NOT* use your login password!\n\n"); + + for (i = 0, ok = 0; i < 3; i++) { + + pass = NULL; + (void) memset(p1, 0, 256); + (void) memset(p2, 0, 256); + + pass = getpass("Passphrase: "); + if (!pass) + continue; + + if (strlen(pass) < 8) { + (void) fprintf(stderr, + "Passphrase is WAAAAY too short!\n"); + continue; + } + + (void) strncpy(p1, pass, strlen(pass)); + p1[strlen(pass)] = '\0'; + + pass = getpass("Again, please: "); + if (!pass) { + (void) fprintf(stderr, "They don't match!\n"); + continue; + } + + (void) strncpy(p2, pass, strlen(pass)); + p2[strlen(pass)] = '\0'; + + if (strncmp(p1, p2, strlen(p1)) != 0) { + (void) fprintf(stderr, "They don't match!\n"); + continue; + } + + ok = 1; + (void) memset(p1, 0, 256); + (void) memset(p2, 0, 256); + break; + } + + if (!ok) { + (void) fprintf(stderr, "\nTry again later.\n"); + (void) sleep(5); + (void) unlink(f); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + MDcalc((byte *)loopinfo.lo_encrypt_key, pass, strlen(pass)); + + /* + * write the hashed password and the encryption method + * out to a file so that if the user tries to login a + * second time, s/he'll be asked for the password before + * s/he can access his/her home directory. + */ + + (void) fprintf(stderr, + "\nSaving encrypted passphrase and encryption method..."); + + for (i = 0, j = 0; i < 20; i++, j+=2) { + buf[j] = bin2hex[loopinfo.lo_encrypt_key[i] >> 4]; + buf[j+1] = bin2hex[loopinfo.lo_encrypt_key[i] & 0xf]; + } + + (void) sprintf(tmp, "/crypt/%d.x", (int) pwd->pw_uid); + if ((pf = open(tmp, O_CREAT|O_WRONLY|O_TRUNC|O_SYNC, 0400)) + < 0) { + (void) fprintf(stderr, "Cannot create passphrase file!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) unlink(f); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) write(pf, buf, 40); + (void) write(pf, &loopinfo.lo_encrypt_type, + sizeof(loopinfo.lo_encrypt_type)); + (void) close(pf); + + (void) fprintf(stderr, " done.\n"); + + } else { + + (void) fprintf(stderr, + "Your home directory appears to be encrypted.\n"); + + for (i = 0, ok = 0; i < 3; i++) { + + pass = getpass("Passphrase: "); + if (!pass) + continue; + + MDcalc((byte *)loopinfo.lo_encrypt_key, pass, + strlen(pass)); + + for (j = 0, k = 0; j < 20; j++, k+=2) { + buf[k] = bin2hex[loopinfo.lo_encrypt_key[j] >> 4]; + buf[k+1] = bin2hex[loopinfo.lo_encrypt_key[j] & 0xf]; + } + + (void) sprintf(tmp, "/crypt/%d.x", (int) pwd->pw_uid); + if ((pf = open(tmp, O_RDONLY)) < 0) { + (void) fprintf(stderr, + "Can't open passphrase file!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, + "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) read(pf, buf2, 40); + (void) read(pf, &loopinfo.lo_encrypt_type, + sizeof(loopinfo.lo_encrypt_type)); + (void) close(pf); + + if (memcmp(buf, buf2, 40)) { + (void) fprintf(stderr, "Invalid passphrase!\n"); + continue; + } + + ok = 1; + break; + } + + if (!ok) { + (void) fprintf(stderr, "\nTry again later.\n"); + (void) sleep(5); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + switch(loopinfo.lo_encrypt_type) { + + case LO_CRYPT_BLOW: + loopinfo.lo_encrypt_key_size = 20; /* 160 bit key */ + break; + + case LO_CRYPT_CAST128: + case LO_CRYPT_DFC: + case LO_CRYPT_IDEA: + case LO_CRYPT_MARS: + case LO_CRYPT_RC6: + case LO_CRYPT_SERPENT: + loopinfo.lo_encrypt_key_size = 16; /* 128 bit key */ + break; + + default: + (void) fprintf(stderr, + "\nUnknown encryption method %d!\n", + loopinfo.lo_encrypt_type); + (void) fprintf(stderr, + "Contact system administrator.\n"); + (void) sleep(10); + (void) ioctl(fd, LOOP_CLR_FD, 0); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + } + + /* + * set up the loop device, then make a filesystem on it, + * and mount it. if the filesystem has already been made, + * just check it for errors. + */ + + if (ioctl(ld, LOOP_SET_FD, fd) < 0 || + ioctl(ld, LOOP_SET_STATUS, &loopinfo) < 0) { + (void) fprintf(stderr, "Cannot setup loop device %d!\n", + loopdev); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, + "Contact system administrator.\n"); + (void) sleep(10); + (void) ioctl(fd, LOOP_CLR_FD, 0); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + if (make_fs) { + + (void) fprintf(stderr, "Creating %dMB filesystem ...", mb); + (void) sprintf(cmd, + "/sbin/mkfs -t ext2 -q /dev/loop%d %d > /dev/null 2>&1", + loopdev, mb * 1024); + if (run(cmd) < 0) { + (void) fprintf(stderr, + "Cannot create filesystem on /dev/loop%d!\n", + loopdev); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, + "Contact system administrator.\n"); + (void) sleep(10); + (void) unlink(f); + (void) ioctl(fd, LOOP_CLR_FD, 0); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) fprintf(stderr, " done.\n"); + + } else { + + (void) fprintf(stderr, "Checking filesystem ..."); + (void) sprintf(cmd, + "/sbin/e2fsck -f -p /dev/loop%d > /dev/null 2>&1", + loopdev); + if (run(cmd) < 0) { + (void) fprintf(stderr, "Invalid home directory!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, + "Contact system administrator.\n"); + (void) sleep(10); + (void) unlink(f); + (void) ioctl(fd, LOOP_CLR_FD, 0); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) fprintf(stderr, " looks OK.\n"); + } + + (void) mkdir(pwd->pw_dir, 0700); + + (void) fprintf(stderr, "Mounting filesystem as your home ..."); + (void) sprintf(tmp, "/dev/loop%d", loopdev); + if (mount(tmp, pwd->pw_dir, "ext2", 0xC0ED0000 | 16, NULL) < 0) { + (void) fprintf(stderr, "Cannot mount directory!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) ioctl(ld, LOOP_CLR_FD, 0); + (void) rmdir(pwd->pw_dir); + (void) unlink(f); + (void) close(fd); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + (void) sleep(10); + exit(1); + /*NOTREACHED*/ + } + + (void) chown(pwd->pw_dir, pwd->pw_uid, pwd->pw_gid); + (void) chmod (pwd->pw_dir, 0700); + + (void) close(ld); + (void) close(fd); + + (void) fprintf(stderr, " done.\n"); + + } else { + + /* + * user is already logged in at least once, + * no need to do all that stuff, but must + * ask the user for a password to enter + * the home directory. + */ + + (void) close(fd); + + (void) fprintf(stderr, + "Need a passphrase to enter your home directory.\n"); + + for (i = 0, ok = 0; i < 3; i++) { + + pass = getpass("Passphrase: "); + if (!pass) + continue; + + MDcalc((byte *)loopinfo.lo_encrypt_key, pass, strlen(pass)); + for (j = 0, k = 0; j < 20; j++, k+=2) { + buf[k] = bin2hex[loopinfo.lo_encrypt_key[j] >> 4]; + buf[k+1] = bin2hex[loopinfo.lo_encrypt_key[j] & 0xf]; + } + + (void) sprintf(tmp, "/crypt/%d.x", (int) pwd->pw_uid); + if ((pf = open(tmp, O_RDONLY)) < 0) { + (void) fprintf(stderr, "Can't open passphrase file!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, + "Contact system adminstrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) read(pf, buf2, 40); + (void) close(pf); + + if (memcmp(buf, buf2, 40)) { + (void) fprintf(stderr, "Invalid passphrase!\n"); + continue; + } + + ok = 1; + break; + } + + if (!ok) { + (void) fprintf(stderr, "\nTry again later.\n"); + (void) sleep(5); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + } + + (void) sprintf(tmp, "%s/%d", PIDDIR, pwd->pw_uid); + if ((fd = open(tmp, O_CREAT|O_RDWR|O_SYNC, 0600)) < 0) { + (void) fprintf(stderr, "Can't open session file for update!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + exit(1); + /*NOTREACHED*/ + } + + (void) read(fd, &loopdev, sizeof(int)); + (void) read(fd, &usercount, sizeof(int)); + + (void) lseek(fd, 0, 0); + + (void) write(fd, &loopdev, sizeof(int)); + usercount++; + (void) write(fd, &usercount, sizeof(int)); + (void) close(fd); + + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + } +#endif /* EHD */ + + signal(SIGALRM, SIG_DFL); + signal(SIGQUIT, SIG_DFL); + signal(SIGTSTP, SIG_IGN); + signal(SIGHUP, SIG_DFL); #ifdef USE_PAM - /* We must fork before setuid() because we need to call - * pam_close_session() as root. + /* We must fork before setuid() because we need to call + * pam_close_session() as root. */ signal(SIGINT, SIG_IGN); childPid = fork(); @@ -1061,11 +1818,97 @@ } else if (childPid) { /* parent - wait for child to finish, then cleanup session */ wait(NULL); - PAM_END; - exit(0); - } - /* child */ +#ifdef EHD + if (strncmp(pwd->pw_dir, "/crypt/", 7) == 0) { + + /* + * child has exited. decrement the session count, or if + * this is the last session, detach the loop device, + * and remove the mount point and session file. + */ + + loopdev = usercount = -1; + + if ((loginlock = open(LOGINLOCK, O_CREAT|O_WRONLY, 0600)) < 0) { + (void) fprintf(stderr, "Cannot lock session directory!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + goto outa_here; + } + + (void) flock(loginlock, LOCK_EX); + + (void) sprintf(tmp, "%s/%d", PIDDIR, pwd->pw_uid); + if ((fd = open(tmp, O_RDWR|O_SYNC)) < 0) { + (void) fprintf(stderr, "Cannot open session record!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + goto outa_here; + } + + (void) read(fd, &loopdev, sizeof(int)); + (void) read(fd, &usercount, sizeof(int)); + + if (usercount < 2) { + + (void) chdir("/"); + + (void) sprintf(tmp, "/dev/loop%d", loopdev); + (void) umount(tmp); + + if ((ld = open(tmp, O_RDONLY)) < 0) { + (void) fprintf(stderr, "Cannot open loop device!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + goto outa_here; + } + + if (ioctl(ld, LOOP_CLR_FD, 0) < 0) { + (void) fprintf(stderr, "Cannot reset loop device!\n"); + (void) fprintf(stderr, "System error %d.\n", errno); + (void) fprintf(stderr, "Contact system administrator.\n"); + (void) sleep(10); + (void) close(ld); + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + goto outa_here; + } + + (void) close(ld); + (void) close(fd); + + (void) sprintf(tmp, "%s/%d", PIDDIR, pwd->pw_uid); + (void) unlink(tmp); + + (void) rmdir(pwd->pw_dir); + + } else { + + (void) lseek(fd, 0, 0); + (void) write(fd, &loopdev, sizeof(int)); + usercount--; + (void) write(fd, &usercount, sizeof(int)); + (void) close(fd); + } + + (void) flock(loginlock, LOCK_UN); + (void) close(loginlock); + } +outa_here: +#endif /* EHD */ + PAM_END; + exit(0); + } + /* child */ #endif + signal(SIGINT, SIG_DFL); /* discard permissions last so can't get killed and drop core */ diff -Naur /usr/local/src/util-linux-2.9r/login-utils/loop.h /usr/local/src/util-linux-2.9r_ehd/login-utils/loop.h --- /usr/local/src/util-linux-2.9r/login-utils/loop.h Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/loop.h Mon Jun 7 20:12:41 1999 @@ -0,0 +1,4 @@ +#include +#define dev_t __kernel_dev_t +#include +#undef dev_t diff -Naur /usr/local/src/util-linux-2.9r/login-utils/rmd160.c /usr/local/src/util-linux-2.9r_ehd/login-utils/rmd160.c --- /usr/local/src/util-linux-2.9r/login-utils/rmd160.c Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/rmd160.c Mon Jun 7 15:01:17 1999 @@ -0,0 +1,373 @@ +/********************************************************************\ + * + * FILE: rmd160.c + * + * CONTENTS: A sample C-implementation of the RIPEMD-160 + * hash-function. + * TARGET: any computer with an ANSI C compiler + * + * AUTHOR: Antoon Bosselaers, ESAT-COSIC + * DATE: 1 March 1996 + * VERSION: 1.0 + * + * Copyright (c) Katholieke Universiteit Leuven + * 1996, All Rights Reserved + * +\********************************************************************/ + +/* header files */ +#include +#include +#include +#include "rmd160.h" + +/********************************************************************/ + +/* macro definitions */ + +/* collect four bytes into one word: */ +#define BYTES_TO_DWORD(strptr) \ + (((dword) *((strptr)+3) << 24) | \ + ((dword) *((strptr)+2) << 16) | \ + ((dword) *((strptr)+1) << 8) | \ + ((dword) *(strptr))) + +/* ROL(x, n) cyclically rotates x over n bits to the left */ +/* x must be of an unsigned 32 bits type and 0 <= n < 32. */ +#define ROL(x, n) (((x) << (n)) | ((x) >> (32-(n)))) + +/* the five basic functions F(), G() and H() */ +#define F(x, y, z) ((x) ^ (y) ^ (z)) +#define G(x, y, z) (((x) & (y)) | (~(x) & (z))) +#define H(x, y, z) (((x) | ~(y)) ^ (z)) +#define I(x, y, z) (((x) & (z)) | ((y) & ~(z))) +#define J(x, y, z) ((x) ^ ((y) | ~(z))) + +/* the ten basic operations FF() through III() */ +#define FF(a, b, c, d, e, x, s) {\ + (a) += F((b), (c), (d)) + (x);\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define GG(a, b, c, d, e, x, s) {\ + (a) += G((b), (c), (d)) + (x) + 0x5a827999UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define HH(a, b, c, d, e, x, s) {\ + (a) += H((b), (c), (d)) + (x) + 0x6ed9eba1UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define II(a, b, c, d, e, x, s) {\ + (a) += I((b), (c), (d)) + (x) + 0x8f1bbcdcUL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define JJ(a, b, c, d, e, x, s) {\ + (a) += J((b), (c), (d)) + (x) + 0xa953fd4eUL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define FFF(a, b, c, d, e, x, s) {\ + (a) += F((b), (c), (d)) + (x);\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define GGG(a, b, c, d, e, x, s) {\ + (a) += G((b), (c), (d)) + (x) + 0x7a6d76e9UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define HHH(a, b, c, d, e, x, s) {\ + (a) += H((b), (c), (d)) + (x) + 0x6d703ef3UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define III(a, b, c, d, e, x, s) {\ + (a) += I((b), (c), (d)) + (x) + 0x5c4dd124UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define JJJ(a, b, c, d, e, x, s) {\ + (a) += J((b), (c), (d)) + (x) + 0x50a28be6UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } + + +/********************************************************************/ + +void MDinit(dword *MDbuf) +{ + MDbuf[0] = 0x67452301UL; + MDbuf[1] = 0xefcdab89UL; + MDbuf[2] = 0x98badcfeUL; + MDbuf[3] = 0x10325476UL; + MDbuf[4] = 0xc3d2e1f0UL; + + return; +} + +/********************************************************************/ + +void compress(dword *MDbuf, dword *X) +{ + dword aa = MDbuf[0], bb = MDbuf[1], cc = MDbuf[2], + dd = MDbuf[3], ee = MDbuf[4]; + dword aaa = MDbuf[0], bbb = MDbuf[1], ccc = MDbuf[2], + ddd = MDbuf[3], eee = MDbuf[4]; + + /* round 1 */ + FF(aa, bb, cc, dd, ee, X[ 0], 11); + FF(ee, aa, bb, cc, dd, X[ 1], 14); + FF(dd, ee, aa, bb, cc, X[ 2], 15); + FF(cc, dd, ee, aa, bb, X[ 3], 12); + FF(bb, cc, dd, ee, aa, X[ 4], 5); + FF(aa, bb, cc, dd, ee, X[ 5], 8); + FF(ee, aa, bb, cc, dd, X[ 6], 7); + FF(dd, ee, aa, bb, cc, X[ 7], 9); + FF(cc, dd, ee, aa, bb, X[ 8], 11); + FF(bb, cc, dd, ee, aa, X[ 9], 13); + FF(aa, bb, cc, dd, ee, X[10], 14); + FF(ee, aa, bb, cc, dd, X[11], 15); + FF(dd, ee, aa, bb, cc, X[12], 6); + FF(cc, dd, ee, aa, bb, X[13], 7); + FF(bb, cc, dd, ee, aa, X[14], 9); + FF(aa, bb, cc, dd, ee, X[15], 8); + + /* round 2 */ + GG(ee, aa, bb, cc, dd, X[ 7], 7); + GG(dd, ee, aa, bb, cc, X[ 4], 6); + GG(cc, dd, ee, aa, bb, X[13], 8); + GG(bb, cc, dd, ee, aa, X[ 1], 13); + GG(aa, bb, cc, dd, ee, X[10], 11); + GG(ee, aa, bb, cc, dd, X[ 6], 9); + GG(dd, ee, aa, bb, cc, X[15], 7); + GG(cc, dd, ee, aa, bb, X[ 3], 15); + GG(bb, cc, dd, ee, aa, X[12], 7); + GG(aa, bb, cc, dd, ee, X[ 0], 12); + GG(ee, aa, bb, cc, dd, X[ 9], 15); + GG(dd, ee, aa, bb, cc, X[ 5], 9); + GG(cc, dd, ee, aa, bb, X[ 2], 11); + GG(bb, cc, dd, ee, aa, X[14], 7); + GG(aa, bb, cc, dd, ee, X[11], 13); + GG(ee, aa, bb, cc, dd, X[ 8], 12); + + /* round 3 */ + HH(dd, ee, aa, bb, cc, X[ 3], 11); + HH(cc, dd, ee, aa, bb, X[10], 13); + HH(bb, cc, dd, ee, aa, X[14], 6); + HH(aa, bb, cc, dd, ee, X[ 4], 7); + HH(ee, aa, bb, cc, dd, X[ 9], 14); + HH(dd, ee, aa, bb, cc, X[15], 9); + HH(cc, dd, ee, aa, bb, X[ 8], 13); + HH(bb, cc, dd, ee, aa, X[ 1], 15); + HH(aa, bb, cc, dd, ee, X[ 2], 14); + HH(ee, aa, bb, cc, dd, X[ 7], 8); + HH(dd, ee, aa, bb, cc, X[ 0], 13); + HH(cc, dd, ee, aa, bb, X[ 6], 6); + HH(bb, cc, dd, ee, aa, X[13], 5); + HH(aa, bb, cc, dd, ee, X[11], 12); + HH(ee, aa, bb, cc, dd, X[ 5], 7); + HH(dd, ee, aa, bb, cc, X[12], 5); + + /* round 4 */ + II(cc, dd, ee, aa, bb, X[ 1], 11); + II(bb, cc, dd, ee, aa, X[ 9], 12); + II(aa, bb, cc, dd, ee, X[11], 14); + II(ee, aa, bb, cc, dd, X[10], 15); + II(dd, ee, aa, bb, cc, X[ 0], 14); + II(cc, dd, ee, aa, bb, X[ 8], 15); + II(bb, cc, dd, ee, aa, X[12], 9); + II(aa, bb, cc, dd, ee, X[ 4], 8); + II(ee, aa, bb, cc, dd, X[13], 9); + II(dd, ee, aa, bb, cc, X[ 3], 14); + II(cc, dd, ee, aa, bb, X[ 7], 5); + II(bb, cc, dd, ee, aa, X[15], 6); + II(aa, bb, cc, dd, ee, X[14], 8); + II(ee, aa, bb, cc, dd, X[ 5], 6); + II(dd, ee, aa, bb, cc, X[ 6], 5); + II(cc, dd, ee, aa, bb, X[ 2], 12); + + /* round 5 */ + JJ(bb, cc, dd, ee, aa, X[ 4], 9); + JJ(aa, bb, cc, dd, ee, X[ 0], 15); + JJ(ee, aa, bb, cc, dd, X[ 5], 5); + JJ(dd, ee, aa, bb, cc, X[ 9], 11); + JJ(cc, dd, ee, aa, bb, X[ 7], 6); + JJ(bb, cc, dd, ee, aa, X[12], 8); + JJ(aa, bb, cc, dd, ee, X[ 2], 13); + JJ(ee, aa, bb, cc, dd, X[10], 12); + JJ(dd, ee, aa, bb, cc, X[14], 5); + JJ(cc, dd, ee, aa, bb, X[ 1], 12); + JJ(bb, cc, dd, ee, aa, X[ 3], 13); + JJ(aa, bb, cc, dd, ee, X[ 8], 14); + JJ(ee, aa, bb, cc, dd, X[11], 11); + JJ(dd, ee, aa, bb, cc, X[ 6], 8); + JJ(cc, dd, ee, aa, bb, X[15], 5); + JJ(bb, cc, dd, ee, aa, X[13], 6); + + /* parallel round 1 */ + JJJ(aaa, bbb, ccc, ddd, eee, X[ 5], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[14], 9); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 7], 9); + JJJ(ccc, ddd, eee, aaa, bbb, X[ 0], 11); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 9], 13); + JJJ(aaa, bbb, ccc, ddd, eee, X[ 2], 15); + JJJ(eee, aaa, bbb, ccc, ddd, X[11], 15); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 4], 5); + JJJ(ccc, ddd, eee, aaa, bbb, X[13], 7); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 6], 7); + JJJ(aaa, bbb, ccc, ddd, eee, X[15], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[ 8], 11); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 1], 14); + JJJ(ccc, ddd, eee, aaa, bbb, X[10], 14); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 3], 12); + JJJ(aaa, bbb, ccc, ddd, eee, X[12], 6); + + /* parallel round 2 */ + III(eee, aaa, bbb, ccc, ddd, X[ 6], 9); + III(ddd, eee, aaa, bbb, ccc, X[11], 13); + III(ccc, ddd, eee, aaa, bbb, X[ 3], 15); + III(bbb, ccc, ddd, eee, aaa, X[ 7], 7); + III(aaa, bbb, ccc, ddd, eee, X[ 0], 12); + III(eee, aaa, bbb, ccc, ddd, X[13], 8); + III(ddd, eee, aaa, bbb, ccc, X[ 5], 9); + III(ccc, ddd, eee, aaa, bbb, X[10], 11); + III(bbb, ccc, ddd, eee, aaa, X[14], 7); + III(aaa, bbb, ccc, ddd, eee, X[15], 7); + III(eee, aaa, bbb, ccc, ddd, X[ 8], 12); + III(ddd, eee, aaa, bbb, ccc, X[12], 7); + III(ccc, ddd, eee, aaa, bbb, X[ 4], 6); + III(bbb, ccc, ddd, eee, aaa, X[ 9], 15); + III(aaa, bbb, ccc, ddd, eee, X[ 1], 13); + III(eee, aaa, bbb, ccc, ddd, X[ 2], 11); + + /* parallel round 3 */ + HHH(ddd, eee, aaa, bbb, ccc, X[15], 9); + HHH(ccc, ddd, eee, aaa, bbb, X[ 5], 7); + HHH(bbb, ccc, ddd, eee, aaa, X[ 1], 15); + HHH(aaa, bbb, ccc, ddd, eee, X[ 3], 11); + HHH(eee, aaa, bbb, ccc, ddd, X[ 7], 8); + HHH(ddd, eee, aaa, bbb, ccc, X[14], 6); + HHH(ccc, ddd, eee, aaa, bbb, X[ 6], 6); + HHH(bbb, ccc, ddd, eee, aaa, X[ 9], 14); + HHH(aaa, bbb, ccc, ddd, eee, X[11], 12); + HHH(eee, aaa, bbb, ccc, ddd, X[ 8], 13); + HHH(ddd, eee, aaa, bbb, ccc, X[12], 5); + HHH(ccc, ddd, eee, aaa, bbb, X[ 2], 14); + HHH(bbb, ccc, ddd, eee, aaa, X[10], 13); + HHH(aaa, bbb, ccc, ddd, eee, X[ 0], 13); + HHH(eee, aaa, bbb, ccc, ddd, X[ 4], 7); + HHH(ddd, eee, aaa, bbb, ccc, X[13], 5); + + /* parallel round 4 */ + GGG(ccc, ddd, eee, aaa, bbb, X[ 8], 15); + GGG(bbb, ccc, ddd, eee, aaa, X[ 6], 5); + GGG(aaa, bbb, ccc, ddd, eee, X[ 4], 8); + GGG(eee, aaa, bbb, ccc, ddd, X[ 1], 11); + GGG(ddd, eee, aaa, bbb, ccc, X[ 3], 14); + GGG(ccc, ddd, eee, aaa, bbb, X[11], 14); + GGG(bbb, ccc, ddd, eee, aaa, X[15], 6); + GGG(aaa, bbb, ccc, ddd, eee, X[ 0], 14); + GGG(eee, aaa, bbb, ccc, ddd, X[ 5], 6); + GGG(ddd, eee, aaa, bbb, ccc, X[12], 9); + GGG(ccc, ddd, eee, aaa, bbb, X[ 2], 12); + GGG(bbb, ccc, ddd, eee, aaa, X[13], 9); + GGG(aaa, bbb, ccc, ddd, eee, X[ 9], 12); + GGG(eee, aaa, bbb, ccc, ddd, X[ 7], 5); + GGG(ddd, eee, aaa, bbb, ccc, X[10], 15); + GGG(ccc, ddd, eee, aaa, bbb, X[14], 8); + + /* parallel round 5 */ + FFF(bbb, ccc, ddd, eee, aaa, X[12] , 8); + FFF(aaa, bbb, ccc, ddd, eee, X[15] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[10] , 12); + FFF(ddd, eee, aaa, bbb, ccc, X[ 4] , 9); + FFF(ccc, ddd, eee, aaa, bbb, X[ 1] , 12); + FFF(bbb, ccc, ddd, eee, aaa, X[ 5] , 5); + FFF(aaa, bbb, ccc, ddd, eee, X[ 8] , 14); + FFF(eee, aaa, bbb, ccc, ddd, X[ 7] , 6); + FFF(ddd, eee, aaa, bbb, ccc, X[ 6] , 8); + FFF(ccc, ddd, eee, aaa, bbb, X[ 2] , 13); + FFF(bbb, ccc, ddd, eee, aaa, X[13] , 6); + FFF(aaa, bbb, ccc, ddd, eee, X[14] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[ 0] , 15); + FFF(ddd, eee, aaa, bbb, ccc, X[ 3] , 13); + FFF(ccc, ddd, eee, aaa, bbb, X[ 9] , 11); + FFF(bbb, ccc, ddd, eee, aaa, X[11] , 11); + + /* combine results */ + ddd += cc + MDbuf[1]; /* final result for MDbuf[0] */ + MDbuf[1] = MDbuf[2] + dd + eee; + MDbuf[2] = MDbuf[3] + ee + aaa; + MDbuf[3] = MDbuf[4] + aa + bbb; + MDbuf[4] = MDbuf[0] + bb + ccc; + MDbuf[0] = ddd; + + return; +} + +/********************************************************************/ + +void MDfinish(dword *MDbuf, byte *strptr, dword lswlen, dword mswlen) +{ + unsigned int i; /* counter */ + dword X[16]; /* message words */ + + memset(X, 0, 16*sizeof(dword)); + + /* put bytes from strptr into X */ + for (i=0; i<(lswlen&63); i++) { + /* byte i goes into word X[i div 4] at pos. 8*(i mod 4) */ + X[i>>2] ^= (dword) *strptr++ << (8 * (i&3)); + } + + /* append "1" bit to the message. Be careful : + message = "" -> "10000000" = 128 */ + X[(lswlen>>2)&15] ^= (dword)1 << (8*(lswlen&3)+7); + + if ((lswlen & 63) > 55) { + /* length goes to next block */ + compress(MDbuf, X); + memset(X, 0, 16*sizeof(dword)); + } + + /* append length in bits*/ + X[14] = lswlen << 3; + X[15] = (lswlen >> 29) | (mswlen << 3); + compress(MDbuf, X); + + return; +} + +void MDcalc(byte *MD,byte *sp,dword sl) +{ + dword X[16]; + dword MDbuf[5]; + int i,j; + + MDinit(MDbuf); + + while (sl >= 64) + { + memset(X,0,16*sizeof(dword)); + + for (i=0; i<64; i++) + X[i>>2] |= ((dword)(*sp++)) << (8 * (i&3)); + + sl-=64; + compress(MDbuf,X); + + }; + + MDfinish(MDbuf,sp,sl,0); + + for (i=0;i<5;i++) + for (j=0;j<4;j++) + *MD++=(byte)((MDbuf[i]>>(j*8))&0xFF); +} + +/************************ end of file rmd160.c **********************/ + diff -Naur /usr/local/src/util-linux-2.9r/login-utils/rmd160.h /usr/local/src/util-linux-2.9r_ehd/login-utils/rmd160.h --- /usr/local/src/util-linux-2.9r/login-utils/rmd160.h Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/login-utils/rmd160.h Sun Jun 6 20:03:47 1999 @@ -0,0 +1,58 @@ +/********************************************************************\ + * + * FILE: rmd160.h + * + * CONTENTS: Header file for a sample C-implementation of the + * RIPEMD-160 hash-function. + * TARGET: any computer with an ANSI C compiler + * + * AUTHOR: Antoon Bosselaers, ESAT-COSIC + * DATE: 1 March 1996 + * VERSION: 1.0 + * + * Copyright (c) Katholieke Universiteit Leuven + * 1996, All Rights Reserved + * +\********************************************************************/ + +#ifndef RMD160H /* make sure this file is read only once */ +#define RMD160H + +/********************************************************************/ + +/* typedef 8 and 32 bit types, resp. */ +/* adapt these, if necessary, + for your operating system and compiler */ + +typedef unsigned char byte; +typedef unsigned long dword; + +/********************************************************************/ + +/* function prototypes */ + +void MDinit(dword *MDbuf); +/* + * initializes MDbuffer to "magic constants" + */ + +void compress(dword *MDbuf, dword *X); +/* + * the compression function. + * transforms MDbuf using message bytes X[0] through X[15] + */ + +void MDfinish(dword *MDbuf, byte *strptr, dword lswlen, dword mswlen); +/* + * puts bytes from strptr into X and pad out; appends length + * and finally, compresses the last block(s) + * note: length in bits == 8 * (lswlen + 2^32 mswlen). + * note: there are (lswlen mod 64) bytes left in strptr. + */ + +void MDcalc(byte *MDbuf,byte *sp,dword sl); + +#endif /* RMD160H */ + +/*********************** end of file rmd160.h ***********************/ + diff -Naur /usr/local/src/util-linux-2.9r/make_include /usr/local/src/util-linux-2.9r_ehd/make_include --- /usr/local/src/util-linux-2.9r/make_include Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/make_include Fri Jun 25 11:33:00 1999 @@ -0,0 +1,6 @@ +HAVE_NCURSES=yes +CURSESFLAGS=-I/usr/include/ncurses -DNCH=0 +LIBCURSES=-lncurses +NEED_LIBCRYPT=yes +FOREIGN = --foreign-user +HAVE_XGETTEXT=yes diff -Naur /usr/local/src/util-linux-2.9r/mount/Makefile /usr/local/src/util-linux-2.9r_ehd/mount/Makefile --- /usr/local/src/util-linux-2.9r/mount/Makefile Wed Feb 24 11:48:48 1999 +++ /usr/local/src/util-linux-2.9r_ehd/mount/Makefile Wed Jun 2 16:35:14 1999 @@ -36,7 +36,7 @@ GEN_FILES = nfsmount.x nfsmount.h nfsmount_xdr.c nfsmount_clnt.c # comment these out if you are not compiling in loop support -LO_OBJS=lomount.o +LO_OBJS=lomount.o rmd160.o all: $(PROGS) @@ -64,7 +64,7 @@ swapon: swapon.o version.o $(LINK) $^ -o $@ -losetup: losetup.o +losetup: losetup.o rmd160.o $(LINK) $^ -o $@ mount.o umount.o nfsmount.o losetup.o fstab.o sundries.o: sundries.h diff -Naur /usr/local/src/util-linux-2.9r/mount/README.mount /usr/local/src/util-linux-2.9r_ehd/mount/README.mount --- /usr/local/src/util-linux-2.9r/mount/README.mount Mon Jun 23 07:40:33 1997 +++ /usr/local/src/util-linux-2.9r_ehd/mount/README.mount Mon Jun 7 20:35:25 1999 @@ -7,4 +7,3 @@ Presently maintained by Andries Brouwer . Ftp site: ftp.win.tue.nl:/pub/linux/util . - diff -Naur /usr/local/src/util-linux-2.9r/mount/lomount.c /usr/local/src/util-linux-2.9r_ehd/mount/lomount.c --- /usr/local/src/util-linux-2.9r/mount/lomount.c Sun Mar 21 14:06:19 1999 +++ /usr/local/src/util-linux-2.9r_ehd/mount/lomount.c Wed Jun 2 16:36:10 1999 @@ -26,6 +26,7 @@ #include "loop.h" #include "lomount.h" +#include "rmd160.h" #include "nls.h" char *xstrdup (const char *s); /* not: #include "sundries.h" */ @@ -40,6 +41,14 @@ { LO_CRYPT_NONE, "none" }, { LO_CRYPT_XOR, "xor" }, { LO_CRYPT_DES, "DES" }, + { LO_CRYPT_FISH2, "twofish" }, + { LO_CRYPT_BLOW, "blowfish"}, + { LO_CRYPT_CAST128, "cast128"}, + { LO_CRYPT_SERPENT, "serpent"}, + { LO_CRYPT_MARS, "mars" }, + { LO_CRYPT_RC6, "rc6" }, + { LO_CRYPT_DFC, "dfc" }, + { LO_CRYPT_IDEA, "idea"}, { -1, NULL } }; @@ -218,6 +227,24 @@ return 1; } break; + case LO_CRYPT_FISH2: + case LO_CRYPT_BLOW: + pass = getpass("Password :"); + MDcalc((byte *)loopinfo.lo_encrypt_key,pass,strlen(pass)); + loopinfo.lo_encrypt_key_size=20; /* 160 Bit key */ + break; + + case LO_CRYPT_IDEA: + case LO_CRYPT_CAST128: + case LO_CRYPT_SERPENT: + case LO_CRYPT_MARS: + case LO_CRYPT_RC6: + case LO_CRYPT_DFC: + pass = getpass("Password :"); + MDcalc((byte *)loopinfo.lo_encrypt_key,pass,strlen(pass)); + loopinfo.lo_encrypt_key_size=16; /* 128 Bit key */ + break; + default: fprintf (stderr, _("Don't know how to get key for encryption system %d\n"), diff -Naur /usr/local/src/util-linux-2.9r/mount/losetup.c /usr/local/src/util-linux-2.9r_ehd/mount/losetup.c --- /usr/local/src/util-linux-2.9r/mount/losetup.c Wed Feb 24 11:45:51 1999 +++ /usr/local/src/util-linux-2.9r_ehd/mount/losetup.c Sun Jun 6 19:52:18 1999 @@ -17,6 +17,7 @@ #include "loop.h" #include "lomount.h" +#include "rmd160.h" #include "nls.h" #ifdef LOOP_SET_FD @@ -31,6 +32,14 @@ { LO_CRYPT_NONE,"none" }, { LO_CRYPT_XOR, "xor" }, { LO_CRYPT_DES, "DES" }, + { LO_CRYPT_FISH2, "twofish" }, + { LO_CRYPT_BLOW, "blowfish" }, + { LO_CRYPT_CAST128, "cast128" }, + { LO_CRYPT_SERPENT, "serpent" }, + { LO_CRYPT_MARS, "mars" }, + { LO_CRYPT_RC6, "rc6" }, + { LO_CRYPT_DFC, "dfc" }, + { LO_CRYPT_IDEA, "idea" }, { -1, NULL } }; @@ -85,7 +94,7 @@ struct loop_info loopinfo; int fd, ffd, mode, i; char *pass; - + mode = *loopro ? O_RDONLY : O_RDWR; if ((ffd = open (file, mode)) < 0 && !*loopro && (errno != EROFS || (ffd = open (file, mode = O_RDONLY)) < 0)) { @@ -133,6 +142,22 @@ exit(1); } break; + case LO_CRYPT_FISH2: + case LO_CRYPT_BLOW: + pass = getpass("Password: "); + MDcalc((byte *)loopinfo.lo_encrypt_key,pass,strlen(pass)); + loopinfo.lo_encrypt_key_size=20; /* 160 Bit key */ + break; + case LO_CRYPT_CAST128: + case LO_CRYPT_SERPENT: + case LO_CRYPT_MARS: + case LO_CRYPT_RC6: + case LO_CRYPT_DFC: + case LO_CRYPT_IDEA: + pass = getpass("Password: "); + MDcalc((byte *)loopinfo.lo_encrypt_key,pass,strlen(pass)); + loopinfo.lo_encrypt_key_size=16; /* 128 Bit key */ + break; default: fprintf(stderr, _("Don't know how to get key for encryption system %d\n"), @@ -219,6 +244,11 @@ } else { if (offset && sscanf(offset,"%d",&off) != 1) usage(); + + (void) fprintf(stderr, + "\nDEBUG! args to set_loop are: %s %s %d %s\n\n", + argv[optind], argv[optind+1], off, encryption); + set_loop(argv[optind],argv[optind+1],off,encryption,&ro); } return 0; diff -Naur /usr/local/src/util-linux-2.9r/mount/mount.c /usr/local/src/util-linux-2.9r_ehd/mount/mount.c --- /usr/local/src/util-linux-2.9r/mount/mount.c Tue Apr 6 19:06:25 1999 +++ /usr/local/src/util-linux-2.9r_ehd/mount/mount.c Sun Jun 6 20:16:05 1999 @@ -376,7 +376,14 @@ static int mount5 (struct mountargs *args) { - int ret = mount (args->spec, args->node, args->type, + + int ret; + +(void) fprintf(stderr, +"\nDEBUG! mount5(): spec = %s, node = %s, type = %s, flags = %d, opts = %s\n\n", + args->spec, args->node, args->type, args->flags, args->data); + + ret = mount (args->spec, args->node, args->type, MS_MGC_VAL | (args->flags), args->data); if (ret == 0) mountcount++; @@ -554,7 +561,6 @@ mountargs[i++] = oo; } mountargs[i] = NULL; - execv(mountprog, mountargs); exit(1); /* exec failed */ } else if (fork() != -1) { int status; diff -Naur /usr/local/src/util-linux-2.9r/mount/rmd160.c /usr/local/src/util-linux-2.9r_ehd/mount/rmd160.c --- /usr/local/src/util-linux-2.9r/mount/rmd160.c Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/mount/rmd160.c Wed Jun 2 16:58:09 1999 @@ -0,0 +1,371 @@ +/********************************************************************\ + * + * FILE: rmd160.c + * + * CONTENTS: A sample C-implementation of the RIPEMD-160 + * hash-function. + * TARGET: any computer with an ANSI C compiler + * + * AUTHOR: Antoon Bosselaers, ESAT-COSIC + * DATE: 1 March 1996 + * VERSION: 1.0 + * + * Copyright (c) Katholieke Universiteit Leuven + * 1996, All Rights Reserved + * +\********************************************************************/ + +/* header files */ +#include +#include +#include +#include "rmd160.h" + +/********************************************************************/ + +/* macro definitions */ + +/* collect four bytes into one word: */ +#define BYTES_TO_DWORD(strptr) \ + (((dword) *((strptr)+3) << 24) | \ + ((dword) *((strptr)+2) << 16) | \ + ((dword) *((strptr)+1) << 8) | \ + ((dword) *(strptr))) + +/* ROL(x, n) cyclically rotates x over n bits to the left */ +/* x must be of an unsigned 32 bits type and 0 <= n < 32. */ +#define ROL(x, n) (((x) << (n)) | ((x) >> (32-(n)))) + +/* the five basic functions F(), G() and H() */ +#define F(x, y, z) ((x) ^ (y) ^ (z)) +#define G(x, y, z) (((x) & (y)) | (~(x) & (z))) +#define H(x, y, z) (((x) | ~(y)) ^ (z)) +#define I(x, y, z) (((x) & (z)) | ((y) & ~(z))) +#define J(x, y, z) ((x) ^ ((y) | ~(z))) + +/* the ten basic operations FF() through III() */ +#define FF(a, b, c, d, e, x, s) {\ + (a) += F((b), (c), (d)) + (x);\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define GG(a, b, c, d, e, x, s) {\ + (a) += G((b), (c), (d)) + (x) + 0x5a827999UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define HH(a, b, c, d, e, x, s) {\ + (a) += H((b), (c), (d)) + (x) + 0x6ed9eba1UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define II(a, b, c, d, e, x, s) {\ + (a) += I((b), (c), (d)) + (x) + 0x8f1bbcdcUL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define JJ(a, b, c, d, e, x, s) {\ + (a) += J((b), (c), (d)) + (x) + 0xa953fd4eUL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define FFF(a, b, c, d, e, x, s) {\ + (a) += F((b), (c), (d)) + (x);\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define GGG(a, b, c, d, e, x, s) {\ + (a) += G((b), (c), (d)) + (x) + 0x7a6d76e9UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define HHH(a, b, c, d, e, x, s) {\ + (a) += H((b), (c), (d)) + (x) + 0x6d703ef3UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define III(a, b, c, d, e, x, s) {\ + (a) += I((b), (c), (d)) + (x) + 0x5c4dd124UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } +#define JJJ(a, b, c, d, e, x, s) {\ + (a) += J((b), (c), (d)) + (x) + 0x50a28be6UL;\ + (a) = ROL((a), (s)) + (e);\ + (c) = ROL((c), 10);\ + } + + +/********************************************************************/ + +void MDinit(dword *MDbuf) +{ + MDbuf[0] = 0x67452301UL; + MDbuf[1] = 0xefcdab89UL; + MDbuf[2] = 0x98badcfeUL; + MDbuf[3] = 0x10325476UL; + MDbuf[4] = 0xc3d2e1f0UL; + + return; +} + +/********************************************************************/ + +void compress(dword *MDbuf, dword *X) +{ + dword aa = MDbuf[0], bb = MDbuf[1], cc = MDbuf[2], + dd = MDbuf[3], ee = MDbuf[4]; + dword aaa = MDbuf[0], bbb = MDbuf[1], ccc = MDbuf[2], + ddd = MDbuf[3], eee = MDbuf[4]; + + /* round 1 */ + FF(aa, bb, cc, dd, ee, X[ 0], 11); + FF(ee, aa, bb, cc, dd, X[ 1], 14); + FF(dd, ee, aa, bb, cc, X[ 2], 15); + FF(cc, dd, ee, aa, bb, X[ 3], 12); + FF(bb, cc, dd, ee, aa, X[ 4], 5); + FF(aa, bb, cc, dd, ee, X[ 5], 8); + FF(ee, aa, bb, cc, dd, X[ 6], 7); + FF(dd, ee, aa, bb, cc, X[ 7], 9); + FF(cc, dd, ee, aa, bb, X[ 8], 11); + FF(bb, cc, dd, ee, aa, X[ 9], 13); + FF(aa, bb, cc, dd, ee, X[10], 14); + FF(ee, aa, bb, cc, dd, X[11], 15); + FF(dd, ee, aa, bb, cc, X[12], 6); + FF(cc, dd, ee, aa, bb, X[13], 7); + FF(bb, cc, dd, ee, aa, X[14], 9); + FF(aa, bb, cc, dd, ee, X[15], 8); + + /* round 2 */ + GG(ee, aa, bb, cc, dd, X[ 7], 7); + GG(dd, ee, aa, bb, cc, X[ 4], 6); + GG(cc, dd, ee, aa, bb, X[13], 8); + GG(bb, cc, dd, ee, aa, X[ 1], 13); + GG(aa, bb, cc, dd, ee, X[10], 11); + GG(ee, aa, bb, cc, dd, X[ 6], 9); + GG(dd, ee, aa, bb, cc, X[15], 7); + GG(cc, dd, ee, aa, bb, X[ 3], 15); + GG(bb, cc, dd, ee, aa, X[12], 7); + GG(aa, bb, cc, dd, ee, X[ 0], 12); + GG(ee, aa, bb, cc, dd, X[ 9], 15); + GG(dd, ee, aa, bb, cc, X[ 5], 9); + GG(cc, dd, ee, aa, bb, X[ 2], 11); + GG(bb, cc, dd, ee, aa, X[14], 7); + GG(aa, bb, cc, dd, ee, X[11], 13); + GG(ee, aa, bb, cc, dd, X[ 8], 12); + + /* round 3 */ + HH(dd, ee, aa, bb, cc, X[ 3], 11); + HH(cc, dd, ee, aa, bb, X[10], 13); + HH(bb, cc, dd, ee, aa, X[14], 6); + HH(aa, bb, cc, dd, ee, X[ 4], 7); + HH(ee, aa, bb, cc, dd, X[ 9], 14); + HH(dd, ee, aa, bb, cc, X[15], 9); + HH(cc, dd, ee, aa, bb, X[ 8], 13); + HH(bb, cc, dd, ee, aa, X[ 1], 15); + HH(aa, bb, cc, dd, ee, X[ 2], 14); + HH(ee, aa, bb, cc, dd, X[ 7], 8); + HH(dd, ee, aa, bb, cc, X[ 0], 13); + HH(cc, dd, ee, aa, bb, X[ 6], 6); + HH(bb, cc, dd, ee, aa, X[13], 5); + HH(aa, bb, cc, dd, ee, X[11], 12); + HH(ee, aa, bb, cc, dd, X[ 5], 7); + HH(dd, ee, aa, bb, cc, X[12], 5); + + /* round 4 */ + II(cc, dd, ee, aa, bb, X[ 1], 11); + II(bb, cc, dd, ee, aa, X[ 9], 12); + II(aa, bb, cc, dd, ee, X[11], 14); + II(ee, aa, bb, cc, dd, X[10], 15); + II(dd, ee, aa, bb, cc, X[ 0], 14); + II(cc, dd, ee, aa, bb, X[ 8], 15); + II(bb, cc, dd, ee, aa, X[12], 9); + II(aa, bb, cc, dd, ee, X[ 4], 8); + II(ee, aa, bb, cc, dd, X[13], 9); + II(dd, ee, aa, bb, cc, X[ 3], 14); + II(cc, dd, ee, aa, bb, X[ 7], 5); + II(bb, cc, dd, ee, aa, X[15], 6); + II(aa, bb, cc, dd, ee, X[14], 8); + II(ee, aa, bb, cc, dd, X[ 5], 6); + II(dd, ee, aa, bb, cc, X[ 6], 5); + II(cc, dd, ee, aa, bb, X[ 2], 12); + + /* round 5 */ + JJ(bb, cc, dd, ee, aa, X[ 4], 9); + JJ(aa, bb, cc, dd, ee, X[ 0], 15); + JJ(ee, aa, bb, cc, dd, X[ 5], 5); + JJ(dd, ee, aa, bb, cc, X[ 9], 11); + JJ(cc, dd, ee, aa, bb, X[ 7], 6); + JJ(bb, cc, dd, ee, aa, X[12], 8); + JJ(aa, bb, cc, dd, ee, X[ 2], 13); + JJ(ee, aa, bb, cc, dd, X[10], 12); + JJ(dd, ee, aa, bb, cc, X[14], 5); + JJ(cc, dd, ee, aa, bb, X[ 1], 12); + JJ(bb, cc, dd, ee, aa, X[ 3], 13); + JJ(aa, bb, cc, dd, ee, X[ 8], 14); + JJ(ee, aa, bb, cc, dd, X[11], 11); + JJ(dd, ee, aa, bb, cc, X[ 6], 8); + JJ(cc, dd, ee, aa, bb, X[15], 5); + JJ(bb, cc, dd, ee, aa, X[13], 6); + + /* parallel round 1 */ + JJJ(aaa, bbb, ccc, ddd, eee, X[ 5], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[14], 9); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 7], 9); + JJJ(ccc, ddd, eee, aaa, bbb, X[ 0], 11); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 9], 13); + JJJ(aaa, bbb, ccc, ddd, eee, X[ 2], 15); + JJJ(eee, aaa, bbb, ccc, ddd, X[11], 15); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 4], 5); + JJJ(ccc, ddd, eee, aaa, bbb, X[13], 7); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 6], 7); + JJJ(aaa, bbb, ccc, ddd, eee, X[15], 8); + JJJ(eee, aaa, bbb, ccc, ddd, X[ 8], 11); + JJJ(ddd, eee, aaa, bbb, ccc, X[ 1], 14); + JJJ(ccc, ddd, eee, aaa, bbb, X[10], 14); + JJJ(bbb, ccc, ddd, eee, aaa, X[ 3], 12); + JJJ(aaa, bbb, ccc, ddd, eee, X[12], 6); + + /* parallel round 2 */ + III(eee, aaa, bbb, ccc, ddd, X[ 6], 9); + III(ddd, eee, aaa, bbb, ccc, X[11], 13); + III(ccc, ddd, eee, aaa, bbb, X[ 3], 15); + III(bbb, ccc, ddd, eee, aaa, X[ 7], 7); + III(aaa, bbb, ccc, ddd, eee, X[ 0], 12); + III(eee, aaa, bbb, ccc, ddd, X[13], 8); + III(ddd, eee, aaa, bbb, ccc, X[ 5], 9); + III(ccc, ddd, eee, aaa, bbb, X[10], 11); + III(bbb, ccc, ddd, eee, aaa, X[14], 7); + III(aaa, bbb, ccc, ddd, eee, X[15], 7); + III(eee, aaa, bbb, ccc, ddd, X[ 8], 12); + III(ddd, eee, aaa, bbb, ccc, X[12], 7); + III(ccc, ddd, eee, aaa, bbb, X[ 4], 6); + III(bbb, ccc, ddd, eee, aaa, X[ 9], 15); + III(aaa, bbb, ccc, ddd, eee, X[ 1], 13); + III(eee, aaa, bbb, ccc, ddd, X[ 2], 11); + + /* parallel round 3 */ + HHH(ddd, eee, aaa, bbb, ccc, X[15], 9); + HHH(ccc, ddd, eee, aaa, bbb, X[ 5], 7); + HHH(bbb, ccc, ddd, eee, aaa, X[ 1], 15); + HHH(aaa, bbb, ccc, ddd, eee, X[ 3], 11); + HHH(eee, aaa, bbb, ccc, ddd, X[ 7], 8); + HHH(ddd, eee, aaa, bbb, ccc, X[14], 6); + HHH(ccc, ddd, eee, aaa, bbb, X[ 6], 6); + HHH(bbb, ccc, ddd, eee, aaa, X[ 9], 14); + HHH(aaa, bbb, ccc, ddd, eee, X[11], 12); + HHH(eee, aaa, bbb, ccc, ddd, X[ 8], 13); + HHH(ddd, eee, aaa, bbb, ccc, X[12], 5); + HHH(ccc, ddd, eee, aaa, bbb, X[ 2], 14); + HHH(bbb, ccc, ddd, eee, aaa, X[10], 13); + HHH(aaa, bbb, ccc, ddd, eee, X[ 0], 13); + HHH(eee, aaa, bbb, ccc, ddd, X[ 4], 7); + HHH(ddd, eee, aaa, bbb, ccc, X[13], 5); + + /* parallel round 4 */ + GGG(ccc, ddd, eee, aaa, bbb, X[ 8], 15); + GGG(bbb, ccc, ddd, eee, aaa, X[ 6], 5); + GGG(aaa, bbb, ccc, ddd, eee, X[ 4], 8); + GGG(eee, aaa, bbb, ccc, ddd, X[ 1], 11); + GGG(ddd, eee, aaa, bbb, ccc, X[ 3], 14); + GGG(ccc, ddd, eee, aaa, bbb, X[11], 14); + GGG(bbb, ccc, ddd, eee, aaa, X[15], 6); + GGG(aaa, bbb, ccc, ddd, eee, X[ 0], 14); + GGG(eee, aaa, bbb, ccc, ddd, X[ 5], 6); + GGG(ddd, eee, aaa, bbb, ccc, X[12], 9); + GGG(ccc, ddd, eee, aaa, bbb, X[ 2], 12); + GGG(bbb, ccc, ddd, eee, aaa, X[13], 9); + GGG(aaa, bbb, ccc, ddd, eee, X[ 9], 12); + GGG(eee, aaa, bbb, ccc, ddd, X[ 7], 5); + GGG(ddd, eee, aaa, bbb, ccc, X[10], 15); + GGG(ccc, ddd, eee, aaa, bbb, X[14], 8); + + /* parallel round 5 */ + FFF(bbb, ccc, ddd, eee, aaa, X[12] , 8); + FFF(aaa, bbb, ccc, ddd, eee, X[15] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[10] , 12); + FFF(ddd, eee, aaa, bbb, ccc, X[ 4] , 9); + FFF(ccc, ddd, eee, aaa, bbb, X[ 1] , 12); + FFF(bbb, ccc, ddd, eee, aaa, X[ 5] , 5); + FFF(aaa, bbb, ccc, ddd, eee, X[ 8] , 14); + FFF(eee, aaa, bbb, ccc, ddd, X[ 7] , 6); + FFF(ddd, eee, aaa, bbb, ccc, X[ 6] , 8); + FFF(ccc, ddd, eee, aaa, bbb, X[ 2] , 13); + FFF(bbb, ccc, ddd, eee, aaa, X[13] , 6); + FFF(aaa, bbb, ccc, ddd, eee, X[14] , 5); + FFF(eee, aaa, bbb, ccc, ddd, X[ 0] , 15); + FFF(ddd, eee, aaa, bbb, ccc, X[ 3] , 13); + FFF(ccc, ddd, eee, aaa, bbb, X[ 9] , 11); + FFF(bbb, ccc, ddd, eee, aaa, X[11] , 11); + + /* combine results */ + ddd += cc + MDbuf[1]; /* final result for MDbuf[0] */ + MDbuf[1] = MDbuf[2] + dd + eee; + MDbuf[2] = MDbuf[3] + ee + aaa; + MDbuf[3] = MDbuf[4] + aa + bbb; + MDbuf[4] = MDbuf[0] + bb + ccc; + MDbuf[0] = ddd; + + return; +} + +/********************************************************************/ + +void MDfinish(dword *MDbuf, byte *strptr, dword lswlen, dword mswlen) +{ + unsigned int i; /* counter */ + dword X[16]; /* message words */ + + memset(X, 0, 16*sizeof(dword)); + + /* put bytes from strptr into X */ + for (i=0; i<(lswlen&63); i++) { + /* byte i goes into word X[i div 4] at pos. 8*(i mod 4) */ + X[i>>2] ^= (dword) *strptr++ << (8 * (i&3)); + } + + /* append "1" bit to the message. Be careful : + message = "" -> "10000000" = 128 */ + X[(lswlen>>2)&15] ^= (dword)1 << (8*(lswlen&3)+7); + + if ((lswlen & 63) > 55) { + /* length goes to next block */ + compress(MDbuf, X); + memset(X, 0, 16*sizeof(dword)); + } + + /* append length in bits*/ + X[14] = lswlen << 3; + X[15] = (lswlen >> 29) | (mswlen << 3); + compress(MDbuf, X); + + return; +} + +void MDcalc(byte *MD,byte *sp,dword sl) +{ dword X[16]; + dword MDbuf[5]; + int i,j; + + MDinit(MDbuf); + + while (sl >= 64) + { + memset(X,0,16*sizeof(dword)); + + for (i=0; i<64; i++) + X[i>>2] |= ((dword)(*sp++)) << (8 * (i&3)); + + sl-=64; + compress(MDbuf,X); + + }; + MDfinish(MDbuf,sp,sl,0); + + for (i=0;i<5;i++) + for (j=0;j<4;j++) + *MD++=(byte)((MDbuf[i]>>(j*8))&0xFF); +} + +/************************ end of file rmd160.c **********************/ + diff -Naur /usr/local/src/util-linux-2.9r/mount/rmd160.h /usr/local/src/util-linux-2.9r_ehd/mount/rmd160.h --- /usr/local/src/util-linux-2.9r/mount/rmd160.h Wed Dec 31 17:00:00 1969 +++ /usr/local/src/util-linux-2.9r_ehd/mount/rmd160.h Wed Jun 2 16:35:25 1999 @@ -0,0 +1,58 @@ +/********************************************************************\ + * + * FILE: rmd160.h + * + * CONTENTS: Header file for a sample C-implementation of the + * RIPEMD-160 hash-function. + * TARGET: any computer with an ANSI C compiler + * + * AUTHOR: Antoon Bosselaers, ESAT-COSIC + * DATE: 1 March 1996 + * VERSION: 1.0 + * + * Copyright (c) Katholieke Universiteit Leuven + * 1996, All Rights Reserved + * +\********************************************************************/ + +#ifndef RMD160H /* make sure this file is read only once */ +#define RMD160H + +/********************************************************************/ + +/* typedef 8 and 32 bit types, resp. */ +/* adapt these, if necessary, + for your operating system and compiler */ + +typedef unsigned char byte; +typedef unsigned long dword; + +/********************************************************************/ + +/* function prototypes */ + +void MDinit(dword *MDbuf); +/* + * initializes MDbuffer to "magic constants" + */ + +void compress(dword *MDbuf, dword *X); +/* + * the compression function. + * transforms MDbuf using message bytes X[0] through X[15] + */ + +void MDfinish(dword *MDbuf, byte *strptr, dword lswlen, dword mswlen); +/* + * puts bytes from strptr into X and pad out; appends length + * and finally, compresses the last block(s) + * note: length in bits == 8 * (lswlen + 2^32 mswlen). + * note: there are (lswlen mod 64) bytes left in strptr. + */ + +void MDcalc(byte *MDbuf,byte *sp,dword sl); + +#endif /* RMD160H */ + +/*********************** end of file rmd160.h ***********************/ +