* Makeconfig (all-subdirs): Add 'crypt' subdirectory. * sysdeps/unix/sysv/linux/configure.in (inhibit_glue): Don't complain if there is no crypt add-on. * crypt/configure: Removed.

* crypt/crypt.texi: Update documentation of US export restrictions
to match the 14 Jan 2000 regulations.
2000-02-28  Geoff Keating  <geoffk@cygnus.com>

	* Makeconfig (all-subdirs): Add 'crypt' subdirectory.
	* sysdeps/unix/sysv/linux/configure.in (inhibit_glue): Don't
	complain if there is no crypt add-on.
	* crypt/configure: Removed.
	
	* crypt/crypt.texi: Update documentation of US export restrictions
	to match the 14 Jan 2000 regulations.

2000-02-28  Geoff Keating  <geoffk@cygnus.com>

	* crypt: New subdirectory, merged in from the crypt add-on.
This commit is contained in:
Geoff Keating 2000-02-29 05:21:42 +00:00
parent 178f833f30
commit 63f791d303
31 changed files with 3815 additions and 36 deletions

View File

@ -1,3 +1,17 @@
2000-02-28 Geoff Keating <geoffk@cygnus.com>
* Makeconfig (all-subdirs): Add 'crypt' subdirectory.
* sysdeps/unix/sysv/linux/configure.in (inhibit_glue): Don't
complain if there is no crypt add-on.
* crypt/configure: Removed.
* crypt/crypt.texi: Update documentation of US export restrictions
to match the 14 Jan 2000 regulations.
2000-02-28 Geoff Keating <geoffk@cygnus.com>
* crypt: New subdirectory, merged in from the crypt add-on.
2000-02-28 Ulrich Drepper <drepper@redhat.com>
* include/unistd.h: Add __rmdir and __mkdir prototypes.

View File

@ -782,8 +782,8 @@ all-subdirs = csu assert ctype locale intl catgets math setjmp signal \
stdlib stdio-common $(stdio) malloc string wcsmbs time dirent \
grp pwd posix io termios resource misc socket sysvipc gmon \
gnulib iconv iconvdata wctype manual shadow md5-crypt po argp \
$(add-ons) nss localedata timezone rt debug $(sysdep-subdirs) \
$(dlfcn) $(binfmt-subdir)
crypt $(add-ons) nss localedata timezone rt debug \
$(sysdep-subdirs) $(dlfcn) $(binfmt-subdir)
all-subdirs := $(filter-out $(sysdep-inhibit-subdirs),$(all-subdirs))
# The mach and hurd subdirectories have many generated header files which

1
crypt/Banner Normal file
View File

@ -0,0 +1 @@
crypt add-on version 2.1 by Michael Glad and others

482
crypt/COPYING.LIB Normal file
View File

@ -0,0 +1,482 @@
GNU LIBRARY GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1991 Free Software Foundation, Inc.
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
[This is the first released version of the library GPL. It is
numbered 2 because it goes with version 2 of the ordinary GPL.]
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
Licenses are intended to guarantee your freedom to share and change
free software--to make sure the software is free for all its users.
This license, the Library General Public License, applies to some
specially designated Free Software Foundation software, and to any
other libraries whose authors decide to use it. You can use it for
your libraries, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if
you distribute copies of the library, or if you modify it.
For example, if you distribute copies of the library, whether gratis
or for a fee, you must give the recipients all the rights that we gave
you. You must make sure that they, too, receive or can get the source
code. If you link a program with the library, you must provide
complete object files to the recipients so that they can relink them
with the library, after making changes to the library and recompiling
it. And you must show them these terms so they know their rights.
Our method of protecting your rights has two steps: (1) copyright
the library, and (2) offer you this license which gives you legal
permission to copy, distribute and/or modify the library.
Also, for each distributor's protection, we want to make certain
that everyone understands that there is no warranty for this free
library. If the library is modified by someone else and passed on, we
want its recipients to know that what they have is not the original
version, so that any problems introduced by others will not reflect on
the original authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that companies distributing free
software will individually obtain patent licenses, thus in effect
transforming the program into proprietary software. To prevent this,
we have made it clear that any patent must be licensed for everyone's
free use or not licensed at all.
Most GNU software, including some libraries, is covered by the ordinary
GNU General Public License, which was designed for utility programs. This
license, the GNU Library General Public License, applies to certain
designated libraries. This license is quite different from the ordinary
one; be sure to read it in full, and don't assume that anything in it is
the same as in the ordinary license.
The reason we have a separate public license for some libraries is that
they blur the distinction we usually make between modifying or adding to a
program and simply using it. Linking a program with a library, without
changing the library, is in some sense simply using the library, and is
analogous to running a utility program or application program. However, in
a textual and legal sense, the linked executable is a combined work, a
derivative of the original library, and the ordinary General Public License
treats it as such.
Because of this blurred distinction, using the ordinary General
Public License for libraries did not effectively promote software
sharing, because most developers did not use the libraries. We
concluded that weaker conditions might promote sharing better.
However, unrestricted linking of non-free programs would deprive the
users of those programs of all benefit from the free status of the
libraries themselves. This Library General Public License is intended to
permit developers of non-free programs to use free libraries, while
preserving your freedom as a user of such programs to change the free
libraries that are incorporated in them. (We have not seen how to achieve
this as regards changes in header files, but we have achieved it as regards
changes in the actual functions of the Library.) The hope is that this
will lead to faster development of free libraries.
The precise terms and conditions for copying, distribution and
modification follow. Pay close attention to the difference between a
"work based on the library" and a "work that uses the library". The
former contains code derived from the library, while the latter only
works together with the library.
Note that it is possible for a library to be covered by the ordinary
General Public License rather than by this special one.
GNU LIBRARY GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License Agreement applies to any software library which
contains a notice placed by the copyright holder or other authorized
party saying it may be distributed under the terms of this Library
General Public License (also called "this License"). Each licensee is
addressed as "you".
A "library" means a collection of software functions and/or data
prepared so as to be conveniently linked with application programs
(which use some of those functions and data) to form executables.
The "Library", below, refers to any such software library or work
which has been distributed under these terms. A "work based on the
Library" means either the Library or any derivative work under
copyright law: that is to say, a work containing the Library or a
portion of it, either verbatim or with modifications and/or translated
straightforwardly into another language. (Hereinafter, translation is
included without limitation in the term "modification".)
"Source code" for a work means the preferred form of the work for
making modifications to it. For a library, complete source code means
all the source code for all modules it contains, plus any associated
interface definition files, plus the scripts used to control compilation
and installation of the library.
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running a program using the Library is not restricted, and output from
such a program is covered only if its contents constitute a work based
on the Library (independent of the use of the Library in a tool for
writing it). Whether that is true depends on what the Library does
and what the program that uses the Library does.
1. You may copy and distribute verbatim copies of the Library's
complete source code as you receive it, in any medium, provided that
you conspicuously and appropriately publish on each copy an
appropriate copyright notice and disclaimer of warranty; keep intact
all the notices that refer to this License and to the absence of any
warranty; and distribute a copy of this License along with the
Library.
You may charge a fee for the physical act of transferring a copy,
and you may at your option offer warranty protection in exchange for a
fee.
2. You may modify your copy or copies of the Library or any portion
of it, thus forming a work based on the Library, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) The modified work must itself be a software library.
b) You must cause the files modified to carry prominent notices
stating that you changed the files and the date of any change.
c) You must cause the whole of the work to be licensed at no
charge to all third parties under the terms of this License.
d) If a facility in the modified Library refers to a function or a
table of data to be supplied by an application program that uses
the facility, other than as an argument passed when the facility
is invoked, then you must make a good faith effort to ensure that,
in the event an application does not supply such function or
table, the facility still operates, and performs whatever part of
its purpose remains meaningful.
(For example, a function in a library to compute square roots has
a purpose that is entirely well-defined independent of the
application. Therefore, Subsection 2d requires that any
application-supplied function or table used by this function must
be optional: if the application does not supply it, the square
root function must still compute square roots.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Library,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Library, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote
it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Library.
In addition, mere aggregation of another work not based on the Library
with the Library (or with a work based on the Library) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may opt to apply the terms of the ordinary GNU General Public
License instead of this License to a given copy of the Library. To do
this, you must alter all the notices that refer to this License, so
that they refer to the ordinary GNU General Public License, version 2,
instead of to this License. (If a newer version than version 2 of the
ordinary GNU General Public License has appeared, then you can specify
that version instead if you wish.) Do not make any other change in
these notices.
Once this change is made in a given copy, it is irreversible for
that copy, so the ordinary GNU General Public License applies to all
subsequent copies and derivative works made from that copy.
This option is useful when you wish to copy part of the code of
the Library into a program that is not a library.
4. You may copy and distribute the Library (or a portion or
derivative of it, under Section 2) in object code or executable form
under the terms of Sections 1 and 2 above provided that you accompany
it with the complete corresponding machine-readable source code, which
must be distributed under the terms of Sections 1 and 2 above on a
medium customarily used for software interchange.
If distribution of object code is made by offering access to copy
from a designated place, then offering equivalent access to copy the
source code from the same place satisfies the requirement to
distribute the source code, even though third parties are not
compelled to copy the source along with the object code.
5. A program that contains no derivative of any portion of the
Library, but is designed to work with the Library by being compiled or
linked with it, is called a "work that uses the Library". Such a
work, in isolation, is not a derivative work of the Library, and
therefore falls outside the scope of this License.
However, linking a "work that uses the Library" with the Library
creates an executable that is a derivative of the Library (because it
contains portions of the Library), rather than a "work that uses the
library". The executable is therefore covered by this License.
Section 6 states terms for distribution of such executables.
When a "work that uses the Library" uses material from a header file
that is part of the Library, the object code for the work may be a
derivative work of the Library even though the source code is not.
Whether this is true is especially significant if the work can be
linked without the Library, or if the work is itself a library. The
threshold for this to be true is not precisely defined by law.
If such an object file uses only numerical parameters, data
structure layouts and accessors, and small macros and small inline
functions (ten lines or less in length), then the use of the object
file is unrestricted, regardless of whether it is legally a derivative
work. (Executables containing this object code plus portions of the
Library will still fall under Section 6.)
Otherwise, if the work is a derivative of the Library, you may
distribute the object code for the work under the terms of Section 6.
Any executables containing that work also fall under Section 6,
whether or not they are linked directly with the Library itself.
6. As an exception to the Sections above, you may also compile or
link a "work that uses the Library" with the Library to produce a
work containing portions of the Library, and distribute that work
under terms of your choice, provided that the terms permit
modification of the work for the customer's own use and reverse
engineering for debugging such modifications.
You must give prominent notice with each copy of the work that the
Library is used in it and that the Library and its use are covered by
this License. You must supply a copy of this License. If the work
during execution displays copyright notices, you must include the
copyright notice for the Library among them, as well as a reference
directing the user to the copy of this License. Also, you must do one
of these things:
a) Accompany the work with the complete corresponding
machine-readable source code for the Library including whatever
changes were used in the work (which must be distributed under
Sections 1 and 2 above); and, if the work is an executable linked
with the Library, with the complete machine-readable "work that
uses the Library", as object code and/or source code, so that the
user can modify the Library and then relink to produce a modified
executable containing the modified Library. (It is understood
that the user who changes the contents of definitions files in the
Library will not necessarily be able to recompile the application
to use the modified definitions.)
b) Accompany the work with a written offer, valid for at
least three years, to give the same user the materials
specified in Subsection 6a, above, for a charge no more
than the cost of performing this distribution.
c) If distribution of the work is made by offering access to copy
from a designated place, offer equivalent access to copy the above
specified materials from the same place.
d) Verify that the user has already received a copy of these
materials or that you have already sent this user a copy.
For an executable, the required form of the "work that uses the
Library" must include any data and utility programs needed for
reproducing the executable from it. However, as a special exception,
the source code distributed need not include anything that is normally
distributed (in either source or binary form) with the major
components (compiler, kernel, and so on) of the operating system on
which the executable runs, unless that component itself accompanies
the executable.
It may happen that this requirement contradicts the license
restrictions of other proprietary libraries that do not normally
accompany the operating system. Such a contradiction means you cannot
use both them and the Library together in an executable that you
distribute.
7. You may place library facilities that are a work based on the
Library side-by-side in a single library together with other library
facilities not covered by this License, and distribute such a combined
library, provided that the separate distribution of the work based on
the Library and of the other library facilities is otherwise
permitted, and provided that you do these two things:
a) Accompany the combined library with a copy of the same work
based on the Library, uncombined with any other library
facilities. This must be distributed under the terms of the
Sections above.
b) Give prominent notice with the combined library of the fact
that part of it is a work based on the Library, and explaining
where to find the accompanying uncombined form of the same work.
8. You may not copy, modify, sublicense, link with, or distribute
the Library except as expressly provided under this License. Any
attempt otherwise to copy, modify, sublicense, link with, or
distribute the Library is void, and will automatically terminate your
rights under this License. However, parties who have received copies,
or rights, from you under this License will not have their licenses
terminated so long as such parties remain in full compliance.
9. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Library or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Library (or any work based on the
Library), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Library or works based on it.
10. Each time you redistribute the Library (or any work based on the
Library), the recipient automatically receives a license from the
original licensor to copy, distribute, link with or modify the Library
subject to these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
11. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Library at all. For example, if a patent
license would not permit royalty-free redistribution of the Library by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Library.
If any portion of this section is held invalid or unenforceable under any
particular circumstance, the balance of the section is intended to apply,
and the section as a whole is intended to apply in other circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
12. If the distribution and/or use of the Library is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Library under this License may add
an explicit geographical distribution limitation excluding those countries,
so that distribution is permitted only in or among countries not thus
excluded. In such case, this License incorporates the limitation as if
written in the body of this License.
13. The Free Software Foundation may publish revised and/or new
versions of the Library General Public License from time to time.
Such new versions will be similar in spirit to the present version,
but may differ in detail to address new problems or concerns.
Each version is given a distinguishing version number. If the Library
specifies a version number of this License which applies to it and
"any later version", you have the option of following the terms and
conditions either of that version or of any later version published by
the Free Software Foundation. If the Library does not specify a
license version number, you may choose any version ever published by
the Free Software Foundation.
14. If you wish to incorporate parts of the Library into other free
programs whose distribution conditions are incompatible with these,
write to the author to ask for permission. For software which is
copyrighted by the Free Software Foundation, write to the Free
Software Foundation; we sometimes make exceptions for this. Our
decision will be guided by the two goals of preserving the free status
of all derivatives of our free software and of promoting the sharing
and reuse of software generally.
NO WARRANTY
15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
DAMAGES.
END OF TERMS AND CONDITIONS
Appendix: How to Apply These Terms to Your New Libraries
If you develop a new library, and you want it to be of the greatest
possible use to the public, we recommend making it free software that
everyone can redistribute and change. You can do so by permitting
redistribution under these terms (or, alternatively, under the terms of the
ordinary General Public License).
To apply these terms, attach the following notices to the library. It is
safest to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least the
"copyright" line and a pointer to where the full notice is found.
<one line to give the library's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
Also add information on how to contact you by electronic and paper mail.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the library, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the
library `Frob' (a library for tweaking knobs) written by James Random Hacker.
<signature of Ty Coon>, 1 April 1990
Ty Coon, President of Vice
That's all there is to it!

24
crypt/ChangeLog.old Normal file
View File

@ -0,0 +1,24 @@
1998-12-25 Geoff Keating <geoffk@ozemail.com.au>
* sysdeps/unix/ufc-crypt.h: Use <stdint.h>.
* configure: Delete the code dealing with building the add-on
outside glibc, as this doesn't work.
1998-12-10 Geoff Keating <geoffk@ozemail.com.au>
* sysdeps/unix/crypt-entry.c: Don't include "patchlevel.h".
* sysdeps/unix/crypt.h: Move __crypt_r, __setkey_r, __encrypt_r to...
* sysdeps/unix/crypt-private.h: ...here.
* sysdeps/unix/crypt.h: Add __restrict to the structure parameters.
* sysdeps/unix/crypt-private.h: Likewise. Also add const to
first parameter of _ufc_mk_keytab_r.
* sysdeps/unix/crypt.c: Update prototypes.
* sysdeps/unix/crypt-entry.c: Likewise.
* sysdeps/unix/crypt_util.c: Likewise.
* sysdeps/unix/crypt-entry.c (crypt): Use __crypt_r not crypt_r.
ChangeLog starts here, with version 2.0.96.

36
crypt/Makefile Normal file
View File

@ -0,0 +1,36 @@
# Copyright (C) 1996 Free Software Foundation, Inc.
# This file is part of the GNU C Library.
# The GNU C Library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Library General Public License as
# published by the Free Software Foundation; either version 2 of the
# License, or (at your option) any later version.
# The GNU C Library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Library General Public License for more details.
# You should have received a copy of the GNU Library General Public
# License along with the GNU C Library; see the file COPYING.LIB. If not,
# write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
#
# Sub-makefile for DES crypt portion of the library.
#
subdir := crypt
tests = cert
include ../Makeconfig
rpath-dirs += md5-crypt
include ../Rules
ifeq ($(build-shared),yes)
$(objpfx)cert: $(common-objpfx)md5-crypt/libcrypt.so$(libcrypt.so-version)
else
$(objpfx)cert: $(common-objpfx)md5-crypt/libcrypt.a
endif

49
crypt/README Normal file
View File

@ -0,0 +1,49 @@
This is the distribution tar file for the cryptography add-on to the
GNU C library. For the version number, see the file "Banner".
The add-on is not included in the main distribution of the GNU C
library because some governments, most notably those of France,
Russia, and the US, have very restrictive rules governing the
distribution and use of encryption software. Please read the node
"Legal Problems" in the manual for more details.
In particular, the US does not allow export of this software without a
licence, including via the Internet. So please do not download it
from the main FSF FTP site at ftp.gnu.org if you are outside
the US. This software was completely developed outside the US.
To install the add-on, unpack the tar file in the top level of the GNU
C library distribution. Then build GNU C library like this:
configure --enable-add-ons
make
make install
It is not presently possible to add the add-on to the GNU C library
without recompiling the GNU C library.
The additional functionality provided by the add-on consists of:
* DES-based crypt(). This is only for backwards compatibility;
for new installations the MD5-based crypt(), provided with the main
GNU C library distribution, should be used instead.
* The AUTH_DES RPC authentication method. In a given situation, this
may be more or less secure than the AUTH_UNIX authentication method
which is provided with the main GNU C library distribution.
* User-visible DES encryption routines. Note that DES by itself is
not now considered a very secure encryption method.
The add-on also includes a manual, the file "crypt.texi". The manual
will be integrated with the GNU C library manual when the GNU C
library is installed.
Report bugs in this library (or its manual) in the same way as for the
GNU C library; that is, using the `glibcbug' shell script to send
e-mail to <bugs@gnu.org>. Simply run this shell script and fill in
the information. Nevertheless you can still send bug reports to
<bug-glibc@gnu.org> as normal electronic mails.
The add-on is free software. See the file COPYING.LIB for copying
conditions.

135
crypt/README.ufc-crypt Normal file
View File

@ -0,0 +1,135 @@
The following is the README for UFC-crypt, with those portions deleted
that are known to be incorrect for the implementation used with the
GNU C library.
UFC-crypt: ultra fast 'crypt' implementation
============================================
@(#)README 2.27 11 Sep 1996
Design goals/non goals:
----------------------
- Crypt implementation plugin compatible with crypt(3)/fcrypt.
- High performance when used for password cracking.
- Portable to most 32/64 bit machines.
- Startup time/mixed salt performance not critical.
Features of the implementation:
------------------------------
- On most machines, UFC-crypt runs 30-60 times faster than crypt(3) when
invoked repeated times with the same salt and varying passwords.
- With mostly constant salts, performance is about two to three times
that of the default fcrypt implementation shipped with Alec
Muffets 'Crack' password cracker. For instructions on how to
plug UFC-crypt into 'Crack', see below.
- With alternating salts, performance is only about twice
that of crypt(3).
- Requires 165 kb for tables.
Author & licensing etc
----------------------
UFC-crypt is created by Michael Glad, email: glad@daimi.aau.dk, and has
been donated to the Free Software Foundation, Inc. It is covered by the
GNU library license version 2, see the file 'COPYING.LIB'.
NOTES FOR USERS OUTSIDE THE US:
------------------------------
The US government limits the export of DES based software/hardware.
This software is written in Aarhus, Denmark. It can therefore be retrieved
from ftp sites outside the US without breaking US law. Please do not
ftp it from american sites.
Benchmark table:
---------------
The table shows how many operations per second UFC-crypt can
do on various machines.
|--------------|-------------------------------------------|
|Machine | SUN* SUN* HP* DecStation HP |
| | 3/50 ELC 9000/425e 3100 9000/720 |
|--------------|-------------------------------------------|
| Crypt(3)/sec | 4.6 30 15 25 57 |
| Ufc/sec | 220 990 780 1015 3500 |
|--------------|-------------------------------------------|
| Speedup | 48 30 52 40 60 |
|--------------|-------------------------------------------|
*) Compiled using special assembly language support module.
It seems as if performance is limited by CPU bus and data cache capacity.
This also makes the benchmarks debatable compared to a real test with
UFC-crypt wired into Crack. However, the table gives an outline of
what can be expected.
Optimizations:
-------------
Here are the optimizations used relative to an ordinary implementation
such as the one said to be used in crypt(3).
Major optimizations
*******************
- Keep data packed as bits in integer variables -- allows for
fast permutations & parallel xor's in CPU hardware.
- Let adjacent final & initial permutations collapse.
- Keep working data in 'E expanded' format all the time.
- Implement DES 'f' function mostly by table lookup
- Calculate the above function on 12 bit basis rather than 6
as would be the most natural.
- Implement setup routines so that performance is limited by the DES
inner loops only.
- Instead of doing salting in the DES inner loops, modify the above tables
each time a new salt is seen. According to the BSD crypt code this is
ugly :-)
Minor (dirty) optimizations
***************************
- combine iterations of DES inner loop so that DES only loops
8 times. This saves a lot of variable swapping.
- Implement key access by a walking pointer rather than coding
as array indexing.
- As described, the table based f function uses a 3 dimensional array:
sb ['number of 12 bit segment']['12 bit index']['48 bit half index']
Code the routine with 4 (one dimensional) vectors.
- Design the internal data format & uglify the DES loops so that
the compiler does not need to do bit shifts when indexing vectors.
Revision history
****************
UFC patchlevel 0: base version; released to alt.sources on Sep 24 1991
UFC patchlevel 1: patch released to alt.sources on Sep 27 1991.
No longer rebuilds sb tables when seeing a new salt.
UFC-crypt pl0: Essentially UFC pl 1. Released to comp.sources.misc
on Oct 22 1991.
UFC-crypt pl1: Released to comp.sources.misc in march 1992
* setkey/encrypt routines added
* added validation/benchmarking programs
* reworked keyschedule setup code
* memory demands reduced
* 64 bit support added

112
crypt/cert.c Normal file
View File

@ -0,0 +1,112 @@
/*
* This crypt(3) validation program shipped with UFC-crypt
* is derived from one distributed with Phil Karns PD DES package.
*
* @(#)cert.c 1.8 11 Aug 1996
*/
#include <stdio.h>
#include "crypt.h"
int totfails = 0;
#if __STDC__ - 0
int main (int argc, char *argv[]);
void get8 (char *cp);
void put8 (char *cp);
void good_bye (void) __attribute__ ((noreturn));
#else
void get8(), put8();
#endif
void good_bye ()
{
if(totfails == 0) {
printf("Passed DES validation suite\n");
exit(0);
} else {
printf("%d failures during DES validation suite!!!\n", totfails);
exit(1);
}
}
int
main(argc, argv)
int argc;
char *argv[];
{
char key[64],plain[64],cipher[64],answer[64];
int i;
int test;
int fail;
for(test=0;!feof(stdin);test++){
get8(key);
printf(" K: "); put8(key);
setkey(key);
get8(plain);
printf(" P: "); put8(plain);
get8(answer);
printf(" C: "); put8(answer);
for(i=0;i<64;i++)
cipher[i] = plain[i];
encrypt(cipher, 0);
for(i=0;i<64;i++)
if(cipher[i] != answer[i])
break;
fail = 0;
if(i != 64){
printf(" Encrypt FAIL");
fail++; totfails++;
}
encrypt(cipher, 1);
for(i=0;i<64;i++)
if(cipher[i] != plain[i])
break;
if(i != 64){
printf(" Decrypt FAIL");
fail++; totfails++;
}
if(fail == 0)
printf(" OK");
printf("\n");
}
good_bye();
}
void
get8(cp)
char *cp;
{
int i,j,t;
for(i=0;i<8;i++){
scanf("%2x",&t);
if(feof(stdin))
good_bye();
for(j=0; j<8 ; j++) {
*cp++ = (t & (0x01 << (7-j))) != 0;
}
}
}
void
put8(cp)
char *cp;
{
int i,j,t;
for(i=0;i<8;i++){
t = 0;
for(j = 0; j<8; j++)
t = (t<<1) | *cp++;
printf("%02x", t);
}
}

171
crypt/cert.input Normal file
View File

@ -0,0 +1,171 @@
0101010101010101 95f8a5e5dd31d900 8000000000000000
0101010101010101 dd7f121ca5015619 4000000000000000
0101010101010101 2e8653104f3834ea 2000000000000000
0101010101010101 4bd388ff6cd81d4f 1000000000000000
0101010101010101 20b9e767b2fb1456 0800000000000000
0101010101010101 55579380d77138ef 0400000000000000
0101010101010101 6cc5defaaf04512f 0200000000000000
0101010101010101 0d9f279ba5d87260 0100000000000000
0101010101010101 d9031b0271bd5a0a 0080000000000000
0101010101010101 424250b37c3dd951 0040000000000000
0101010101010101 b8061b7ecd9a21e5 0020000000000000
0101010101010101 f15d0f286b65bd28 0010000000000000
0101010101010101 add0cc8d6e5deba1 0008000000000000
0101010101010101 e6d5f82752ad63d1 0004000000000000
0101010101010101 ecbfe3bd3f591a5e 0002000000000000
0101010101010101 f356834379d165cd 0001000000000000
0101010101010101 2b9f982f20037fa9 0000800000000000
0101010101010101 889de068a16f0be6 0000400000000000
0101010101010101 e19e275d846a1298 0000200000000000
0101010101010101 329a8ed523d71aec 0000100000000000
0101010101010101 e7fce22557d23c97 0000080000000000
0101010101010101 12a9f5817ff2d65d 0000040000000000
0101010101010101 a484c3ad38dc9c19 0000020000000000
0101010101010101 fbe00a8a1ef8ad72 0000010000000000
0101010101010101 750d079407521363 0000008000000000
0101010101010101 64feed9c724c2faf 0000004000000000
0101010101010101 f02b263b328e2b60 0000002000000000
0101010101010101 9d64555a9a10b852 0000001000000000
0101010101010101 d106ff0bed5255d7 0000000800000000
0101010101010101 e1652c6b138c64a5 0000000400000000
0101010101010101 e428581186ec8f46 0000000200000000
0101010101010101 aeb5f5ede22d1a36 0000000100000000
0101010101010101 e943d7568aec0c5c 0000000080000000
0101010101010101 df98c8276f54b04b 0000000040000000
0101010101010101 b160e4680f6c696f 0000000020000000
0101010101010101 fa0752b07d9c4ab8 0000000010000000
0101010101010101 ca3a2b036dbc8502 0000000008000000
0101010101010101 5e0905517bb59bcf 0000000004000000
0101010101010101 814eeb3b91d90726 0000000002000000
0101010101010101 4d49db1532919c9f 0000000001000000
0101010101010101 25eb5fc3f8cf0621 0000000000800000
0101010101010101 ab6a20c0620d1c6f 0000000000400000
0101010101010101 79e90dbc98f92cca 0000000000200000
0101010101010101 866ecedd8072bb0e 0000000000100000
0101010101010101 8b54536f2f3e64a8 0000000000080000
0101010101010101 ea51d3975595b86b 0000000000040000
0101010101010101 caffc6ac4542de31 0000000000020000
0101010101010101 8dd45a2ddf90796c 0000000000010000
0101010101010101 1029d55e880ec2d0 0000000000008000
0101010101010101 5d86cb23639dbea9 0000000000004000
0101010101010101 1d1ca853ae7c0c5f 0000000000002000
0101010101010101 ce332329248f3228 0000000000001000
0101010101010101 8405d1abe24fb942 0000000000000800
0101010101010101 e643d78090ca4207 0000000000000400
0101010101010101 48221b9937748a23 0000000000000200
0101010101010101 dd7c0bbd61fafd54 0000000000000100
0101010101010101 2fbc291a570db5c4 0000000000000080
0101010101010101 e07c30d7e4e26e12 0000000000000040
0101010101010101 0953e2258e8e90a1 0000000000000020
0101010101010101 5b711bc4ceebf2ee 0000000000000010
0101010101010101 cc083f1e6d9e85f6 0000000000000008
0101010101010101 d2fd8867d50d2dfe 0000000000000004
0101010101010101 06e7ea22ce92708f 0000000000000002
0101010101010101 166b40b44aba4bd6 0000000000000001
8001010101010101 0000000000000000 95a8d72813daa94d
4001010101010101 0000000000000000 0eec1487dd8c26d5
2001010101010101 0000000000000000 7ad16ffb79c45926
1001010101010101 0000000000000000 d3746294ca6a6cf3
0801010101010101 0000000000000000 809f5f873c1fd761
0401010101010101 0000000000000000 c02faffec989d1fc
0201010101010101 0000000000000000 4615aa1d33e72f10
0180010101010101 0000000000000000 2055123350c00858
0140010101010101 0000000000000000 df3b99d6577397c8
0120010101010101 0000000000000000 31fe17369b5288c9
0110010101010101 0000000000000000 dfdd3cc64dae1642
0108010101010101 0000000000000000 178c83ce2b399d94
0104010101010101 0000000000000000 50f636324a9b7f80
0102010101010101 0000000000000000 a8468ee3bc18f06d
0101800101010101 0000000000000000 a2dc9e92fd3cde92
0101400101010101 0000000000000000 cac09f797d031287
0101200101010101 0000000000000000 90ba680b22aeb525
0101100101010101 0000000000000000 ce7a24f350e280b6
0101080101010101 0000000000000000 882bff0aa01a0b87
0101040101010101 0000000000000000 25610288924511c2
0101020101010101 0000000000000000 c71516c29c75d170
0101018001010101 0000000000000000 5199c29a52c9f059
0101014001010101 0000000000000000 c22f0a294a71f29f
0101012001010101 0000000000000000 ee371483714c02ea
0101011001010101 0000000000000000 a81fbd448f9e522f
0101010801010101 0000000000000000 4f644c92e192dfed
0101010401010101 0000000000000000 1afa9a66a6df92ae
0101010201010101 0000000000000000 b3c1cc715cb879d8
0101010180010101 0000000000000000 19d032e64ab0bd8b
0101010140010101 0000000000000000 3cfaa7a7dc8720dc
0101010120010101 0000000000000000 b7265f7f447ac6f3
0101010110010101 0000000000000000 9db73b3c0d163f54
0101010108010101 0000000000000000 8181b65babf4a975
0101010104010101 0000000000000000 93c9b64042eaa240
0101010102010101 0000000000000000 5570530829705592
0101010101800101 0000000000000000 8638809e878787a0
0101010101400101 0000000000000000 41b9a79af79ac208
0101010101200101 0000000000000000 7a9be42f2009a892
0101010101100101 0000000000000000 29038d56ba6d2745
0101010101080101 0000000000000000 5495c6abf1e5df51
0101010101040101 0000000000000000 ae13dbd561488933
0101010101020101 0000000000000000 024d1ffa8904e389
0101010101018001 0000000000000000 d1399712f99bf02e
0101010101014001 0000000000000000 14c1d7c1cffec79e
0101010101012001 0000000000000000 1de5279dae3bed6f
0101010101011001 0000000000000000 e941a33f85501303
0101010101010801 0000000000000000 da99dbbc9a03f379
0101010101010401 0000000000000000 b7fc92f91d8e92e9
0101010101010201 0000000000000000 ae8e5caa3ca04e85
0101010101010180 0000000000000000 9cc62df43b6eed74
0101010101010140 0000000000000000 d863dbb5c59a91a0
0101010101010120 0000000000000000 a1ab2190545b91d7
0101010101010110 0000000000000000 0875041e64c570f7
0101010101010108 0000000000000000 5a594528bebef1cc
0101010101010104 0000000000000000 fcdb3291de21f0c0
0101010101010102 0000000000000000 869efd7f9f265a09
1046913489980131 0000000000000000 88d55e54f54c97b4
1007103489988020 0000000000000000 0c0cc00c83ea48fd
10071034c8980120 0000000000000000 83bc8ef3a6570183
1046103489988020 0000000000000000 df725dcad94ea2e9
1086911519190101 0000000000000000 e652b53b550be8b0
1086911519580101 0000000000000000 af527120c485cbb0
5107b01519580101 0000000000000000 0f04ce393db926d5
1007b01519190101 0000000000000000 c9f00ffc74079067
3107915498080101 0000000000000000 7cfd82a593252b4e
3107919498080101 0000000000000000 cb49a2f9e91363e3
10079115b9080140 0000000000000000 00b588be70d23f56
3107911598080140 0000000000000000 406a9a6ab43399ae
1007d01589980101 0000000000000000 6cb773611dca9ada
9107911589980101 0000000000000000 67fd21c17dbb5d70
9107d01589190101 0000000000000000 9592cb4110430787
1007d01598980120 0000000000000000 a6b7ff68a318ddd3
1007940498190101 0000000000000000 4d102196c914ca16
0107910491190401 0000000000000000 2dfa9f4573594965
0107910491190101 0000000000000000 b46604816c0e0774
0107940491190401 0000000000000000 6e7e6221a4f34e87
19079210981a0101 0000000000000000 aa85e74643233199
1007911998190801 0000000000000000 2e5a19db4d1962d6
10079119981a0801 0000000000000000 23a866a809d30894
1007921098190101 0000000000000000 d812d961f017d320
100791159819010b 0000000000000000 055605816e58608f
1004801598190101 0000000000000000 abd88e8b1b7716f1
1004801598190102 0000000000000000 537ac95be69da1e1
1004801598190108 0000000000000000 aed0f6ae3c25cdd8
1002911598100104 0000000000000000 b3e35a5ee53e7b8d
1002911598190104 0000000000000000 61c79c71921a2ef8
1002911598100201 0000000000000000 e2f5728f0995013c
1002911698100101 0000000000000000 1aeac39a61f0a464
7ca110454a1a6e57 01a1d6d039776742 690f5b0d9a26939b
0131d9619dc1376e 5cd54ca83def57da 7a389d10354bd271
07a1133e4a0b2686 0248d43806f67172 868ebb51cab4599a
3849674c2602319e 51454b582ddf440a 7178876e01f19b2a
04b915ba43feb5b6 42fd443059577fa2 af37fb421f8c4095
0113b970fd34f2ce 059b5e0851cf143a 86a560f10ec6d85b
0170f175468fb5e6 0756d8e0774761d2 0cd3da020021dc09
43297fad38e373fe 762514b829bf486a ea676b2cb7db2b7a
07a7137045da2a16 3bdd119049372802 dfd64a815caf1a0f
04689104c2fd3b2f 26955f6835af609a 5c513c9c4886c088
37d06bb516cb7546 164d5e404f275232 0a2aeeae3ff4ab77
1f08260d1ac2465e 6b056e18759f5cca ef1bf03e5dfa575a
584023641aba6176 004bd6ef09176062 88bf0db6d70dee56
025816164629b007 480d39006ee762f2 a1f9915541020b56
49793ebc79b3258f 437540c8698f3cfa 6fbf1cafcffd0556
4fb05e1515ab73a7 072d43a077075292 2f22e49bab7ca1ac
49e95d6d4ca229bf 02fe55778117f12a 5a6b612cc26cce4a
018310dc409b26d6 1d9d5c5018f728c2 5f4c038ed12b2e41
1c587f1c13924fef 305532286d6f295a 63fac0d034d9f793

412
crypt/crypt.texi Normal file
View File

@ -0,0 +1,412 @@
@node Cryptographic Functions
@c @node Cryptographic Functions, , Top, Top
@chapter DES Encryption and Password Handling
@c %MENU% DES encryption and password handling
On many systems, it is unnecessary to have any kind of user
authentication; for instance, a workstation which is not connected to a
network probably does not need any user authentication, because to use
the machine an intruder must have physical access.
Sometimes, however, it is necessary to be sure that a user is authorised
to use some service a machine provides---for instance, to log in as a
particular user id (@pxref{Users and Groups}). One traditional way of
doing this is for each user to choose a secret @dfn{password}; then, the
system can ask someone claiming to be a user what the user's password
is, and if the person gives the correct password then the system can
grant the appropriate privileges.
If all the passwords are just stored in a file somewhere, then this file
has to be very carefully protected. To avoid this, passwords are run
through a @dfn{one-way function}, a function which makes it difficult to
work out what its input was by looking at its output, before storing in
the file.
The GNU C library already provides a one-way function based on MD5. The
@code{crypt} add-on provides additional compatibility with the standard
UNIX one-way function based on the Data Encryption Standard.
It also provides support for Secure RPC, and some library functions that
can be used to perform normal DES encryption.
The add-on is not included in the main distribution of the GNU C library
because some governments, most notably those of France, Russia,
and the US, have very restrictive rules governing the distribution and
use of encryption software. The first section below tries to describe some
of those rules.
@menu
* Legal Problems:: This software can get you locked up, or worse.
* getpass:: Prompting the user for a password.
* crypt:: A one-way function for UNIX passwords.
* DES Encryption:: Routines for DES encryption.
@end menu
@node Legal Problems
@section Legal Problems
Because of the continuously changing state of the law, it's not possible
to provide a definitive survey of the laws affecting cryptography.
Instead, this section warns you of some of the known trouble spots; this
may help you when you try to find out what the laws of your country are.
Some countries require that you have a licence to use, posess, or import
cryptography. These countries are believed to include Byelorussia,
Burma, France, India, Indonesia, Israel, Kazakhstan, Pakistan, Russia,
and Saudi Arabia.
Some countries restrict the transmission of encrypted messages by radio;
some telecommunications carriers restrict the transmission of encrypted
messages over their network.
Many countries have some form of export control for encryption software.
The Wassenaar Arrangement is a multilateral agreement between 33
countries (Argentina, Australia, Austria, Belgium, Bulgaria, Canada, the
Czech Republic, Denmark, Finland, France, Germany, Greece, Hungary,
Ireland, Italy, Japan, Luxembourg, the Netherlands, New Zealand, Norway,
Poland, Portugal, the Republic of Korea, Romania, the Russian
Federation, the Slovak Republic, Spain, Sweden, Switzerland, Turkey,
Ukraine, the United Kingdom and the United States) which restricts some
kinds of encryption exports. Different countries apply the arrangement
in different ways; some do not allow the exception for certain kinds of
``public domain'' software (which would include this library), some
only restrict the export of software in tangible form, and others impose
significant additional restrictions.
The United States has additional rules. This software would generally
be exportable under 15 CFR 740.13(e), which permits exports of
``encryption source code'' which is ``publicly available'' and which is
``not subject to an express agreement for the payment of a licensing fee or
royalty for commercial production or sale of any product developed with
the source code'' to most countries.
The rules in this area are continuously changing. If you know of any
information in this manual that is out-of-date, please report it using
the @code{glibcbug} script. @xref{Reporting Bugs}.
@node getpass
@section Reading Passwords
When reading in a password, it is desirable to avoid displaying it on
the screen, to help keep it secret. The following function handles this
in a convenient way.
@comment unistd.h
@comment BSD
@deftypefun {char *} getpass (const char * @var{prompt})
@code{getpass} outputs @var{prompt}, then reads a string in from the
terminal without echoing it. It tries to connect to the real terminal,
@file{/dev/tty}, if possible, to encourage users not to put plaintext
passwords in files; otherwise, it uses @code{stdin} and @code{stderr}.
@code{getpass} also disables the INTR, QUIT, and SUSP characters on the
terminal using the @code{ISIG} terminal attribute (@pxref{Local Modes}).
The terminal is flushed before and after @code{getpass}, so that
characters of a mistyped password are not accidentally visible.
In other C libraries, @code{getpass} may only return the first
@code{PASS_MAX} bytes of a password. The GNU C library has no limit, so
@code{PASS_MAX} is undefined.
The prototype for this function is in @file{unistd.h}. @code{PASS_MAX}
would be defined in @file{limits.h}.
@end deftypefun
This precise set of operations may not suit all possible situations. In
this case, it is recommended that users write their own @code{getpass}
substitute. For instance, a very simple substitute is as follows:
@smallexample
@include ../crypt/mygetpass.c.texi
@end smallexample
The substitute takes the same parameters as @code{getline}
(@pxref{Line Input}); the user must print any prompt desired.
@node crypt
@section Encrypting Passwords
@comment crypt.h
@comment BSD, SVID
@deftypefun {char *} crypt (const char * @var{key}, const char * @var{salt})
The @code{crypt} function takes a password, @var{key}, as a string, and
a @var{salt} character array which is described below, and returns a
printable ASCII string which starts with another salt. It is believed
that, given the output of the function, the best way to find a @var{key}
that will produce that output is to guess values of @var{key} until the
original value of @var{key} is found.
The @var{salt} parameter does two things. Firstly, it selects which
algorithm is used, the MD5-based one or the DES-based one. Secondly, it
makes life harder for someone trying to guess passwords against a file
containing many passwords; without a @var{salt}, an intruder can make a
guess, run @code{crypt} on it once, and compare the result with all the
passwords. With a @var{salt}, the intruder must run @code{crypt} once
for each different salt.
For the MD5-based algorithm, the @var{salt} should consist of the string
@code{$1$}, followed by up to 8 characters, terminated by either
another @code{$} or the end of the string. The result of @code{crypt}
will be the @var{salt}, followed by a @code{$} if the salt didn't end
with one, followed by 22 characters from the alphabet
@code{./0-9A-Za-z}, up to 34 characters total. Every character in the
@var{key} is significant.
For the DES-based algorithm, the @var{salt} should consist of two
characters from the alphabet @code{./0-9A-Za-z}, and the result of
@code{crypt} will be those two characters followed by 11 more from the
same alphabet, 13 in total. Only the first 8 characters in the
@var{key} are significant. If the @code{crypt} add-on is not installed,
trying to use the DES-based algorithm will return an empty string and
set @code{errno} to @code{EOPNOTSUPP}.
The MD5-based algorithm is available in the GNU C library even if the
@code{crypt} add-on is not installed. It also has no limit on the
useful length of the password used, and is slightly more secure. It is
therefore preferred over the DES-based algorithm.
When the user enters their password for the first time, the @var{salt}
should be set to a new string which is reasonably random. To verify a
password against the result of a previous call to @code{crypt}, pass
the result of the previous call as the @var{salt}.
@end deftypefun
The following short program is an example of how to use @code{crypt} the
first time a password is entered. Note that the @var{salt} generation
is just barely acceptable; in particular, it is not unique between
machines, and in many applications it would not be acceptable to let an
attacker know what time the user's password was last set.
@smallexample
@include ../crypt/genpass.c.texi
@end smallexample
The next program shows how to verify a password. It prompts the user
for a password and prints ``Access granted.'' if the user types
@code{GNU libc manual}.
@smallexample
@include ../crypt/testpass.c.texi
@end smallexample
@comment crypt.h
@comment GNU
@deftypefun {char *} crypt_r (const char * @var{key}, const char * @var{salt}, {struct crypt_data *} @var{data})
The @code{crypt_r} function does the same thing as @code{crypt}, but
takes an extra parameter which includes space for its result (among
other things), so it can be reentrant. @code{data@w{->}initialized} must be
cleared to zero before the first time @code{crypt_r} is called.
The @code{crypt_r} function is a GNU extension.
@end deftypefun
The @code{crypt} and @code{crypt_r} functions are prototyped in the
header @file{crypt.h}.
@node DES Encryption
@section DES Encryption
The Data Encryption Standard is described in the US Government Federal
Information Processing Standards (FIPS) 46-3 published by the National
Institute of Standards and Technology. The DES has been very thoroughly
analysed since it was developed in the late 1970s, and no new
significant flaws have been found.
However, the DES uses only a 56-bit key (plus 8 parity bits), and a
machine has been built in 1998 which can search through all possible
keys in about 6 days, which cost about US$200000; faster searches would
be possible with more money. This makes simple DES unsecure for most
purposes, and NIST no longer permits new US government systems
to use simple DES.
For serious encryption functionality, it is recommended that one of the
many free encryption libraries be used instead of these routines.
The DES is a reversible operation which takes a 64-bit block and a
64-bit key, and produces another 64-bit block. Usually the bits are
numbered so that the most-significant bit, the first bit, of each block
is numbered 1.
Under that numbering, every 8th bit of the key (the 8th, 16th, and so
on) is not used by the encryption algorithm itself. But the key must
have odd parity; that is, out of bits 1 through 8, and 9 through 16, and
so on, there must be an odd number of `1' bits, and this completely
specifies the unused bits.
@comment crypt.h
@comment BSD, SVID
@deftypefun void setkey (const char * @var{key})
The @code{setkey} function sets an internal data structure to be an
expanded form of @var{key}. @var{key} is specified as an array of 64
bits each stored in a @code{char}, the first bit is @code{key[0]} and
the 64th bit is @code{key[63]}. The @var{key} should have the correct
parity.
@end deftypefun
@comment crypt.h
@comment BSD, SVID
@deftypefun void encrypt (char * @var{block}, int @var{edflag})
The @code{encrypt} function encrypts @var{block} if
@var{edflag} is 0, otherwise it decrypts @var{block}, using a key
previously set by @code{setkey}. The result is
placed in @var{block}.
Like @code{setkey}, @var{block} is specified as an array of 64 bits each
stored in a @code{char}, but there are no parity bits in @var{block}.
@end deftypefun
@comment crypt.h
@comment GNU
@deftypefun void setkey_r (const char * @var{key}, {struct crypt_data *} @var{data})
@comment crypt.h
@comment GNU
@deftypefunx void encrypt_r (char * @var{block}, int @var{edflag}, {struct crypt_data *} @var{data})
These are reentrant versions of @code{setkey} and @code{encrypt}. The
only difference is the extra parameter, which stores the expanded
version of @var{key}. Before calling @code{setkey_r} the first time,
@code{data->initialised} must be cleared to zero.
@end deftypefun
The @code{setkey_r} and @code{encrypt_r} functions are GNU extensions.
@code{setkey}, @code{encrypt}, @code{setkey_r}, and @code{encrypt_r} are
defined in @file{crypt.h}.
If the @code{crypt} add-on is not used to build the library, programs
that use these four functions will crash when the functions are called.
If this is a problem, the @code{ecb_crypt} function described below is
recommended instead.
@comment rpc/des_crypt.h
@comment SUNRPC
@deftypefun int ecb_crypt (char * @var{key}, char * @var{blocks}, unsigned @var{len}, unsigned @var{mode})
The function @code{ecb_crypt} encrypts or decrypts one or more blocks
using DES. Each block is encrypted independently.
The @var{blocks} and the @var{key} are stored packed in 8-bit bytes, so
that the first bit of the key is the most-significant bit of
@code{key[0]} and the 63rd bit of the key is stored as the
least-significant bit of @code{key[7]}. The @var{key} should have the
correct parity.
@var{len} is the number of bytes in @var{blocks}. It should be a
multiple of 8 (so that there is a whole number of blocks to encrypt).
@var{len} is limited to a maximum of @code{DES_MAXDATA} bytes.
The result of the encryption replaces the input in @var{blocks}.
The @var{mode} parameter is the bitwise OR of two of the following:
@table @code
@comment rpc/des_crypt.h
@comment SUNRPC
@item DES_ENCRYPT
@findex DES_ENCRYPT
This constant, used in the @var{mode} parameter, specifies that
@var{blocks} is to be encrypted.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DES_DECRYPT
@findex DES_DECRYPT
This constant, used in the @var{mode} parameter, specifies that
@var{blocks} is to be decrypted.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DES_HW
@findex DES_HW
This constant, used in the @var{mode} parameter, asks to use a hardware
device. If no hardware device is available, encryption happens anyway,
but in software.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DES_SW
@findex DES_SW
This constant, used in the @var{mode} parameter, specifies that no
hardware device is to be used.
@end table
The result of the function will be one of these values:
@table @code
@comment rpc/des_crypt.h
@comment SUNRPC
@item DESERR_NONE
@findex DESERR_NONE
The encryption succeeded.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DESERR_NOHWDEVICE
@findex DESERR_NOHWDEVICE
The encryption succeeded, but there was no hardware device available.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DESERR_HWERROR
@findex DESERR_HWERROR
The encryption failed because of a hardware problem. In the GNU
library, this error code is also returned if the @code{crypt} add-on was
not used to build the library.
@comment rpc/des_crypt.h
@comment SUNRPC
@item DESERR_BADPARAM
@findex DESERR_BADPARAM
The encryption failed because of a bad parameter, for instance @var{len}
is not a multiple of 8 or @var{len} is larger than @code{DES_MAXDATA}.
@end table
@end deftypefun
@comment rpc/des_crypt.h
@comment SUNRPC
@deftypefun int DES_FAILED (int @var{err})
This macro returns 1 if @var{err} is a `success' result code from
@code{ecb_crypt} or @code{cbc_crypt}, and 0 otherwise.
@end deftypefun
@comment rpc/des_crypt.h
@comment SUNRPC
@deftypefun int cbc_crypt (char * @var{key}, char * @var{blocks}, unsigned @var{len}, unsigned @var{mode}, char * @var{ivec})
The function @code{cbc_crypt} encrypts or decrypts one or more blocks
using DES in Cipher Block Chaining mode.
For encryption in CBC mode, each block is exclusive-ored with @var{ivec}
before being encrypted, then @var{ivec} is replaced with the result of
the encryption, then the next block is processed. Decryption is the
reverse of this process.
This has the advantage that blocks which are the same before being
encrypted are very unlikely to be the same after being encrypted, making
it much harder to detect patterns in the data.
Usually, @var{ivec} is set to 8 random bytes before encryption starts.
Then the 8 random bytes are transmitted along with the encrypted data
(without themselves being encrypted), and passed back in as @var{ivec}
for decryption. Another possibility is to set @var{ivec} to 8 zeroes
initially, and have the first the block encrypted consist of 8 random
bytes.
Otherwise, all the parameters are similar to those for @code{ecb_crypt}.
@end deftypefun
@comment rpc/des_crypt.h
@comment SUNRPC
@deftypefun void des_setparity (char * @var{key})
The function @code{des_setparity} changes the 64-bit @var{key}, stored
packed in 8-bit bytes, to have odd parity by altering the low bits of
each byte.
@end deftypefun
The @code{ecb_crypt}, @code{cbc_crypt}, and @code{des_setparity}
functions and their accompanying macros are all defined in the header
@file{rpc/des_crypt.h}.

32
crypt/examples/genpass.c Normal file
View File

@ -0,0 +1,32 @@
#include <stdio.h>
#include <time.h>
#include <unistd.h>
#include <crypt.h>
int
main(void)
{
unsigned long seed[2];
char salt[] = "$1$........";
const char *const seedchars =
"./0123456789ABCDEFGHIJKLMNOPQRST"
"UVWXYZabcdefghijklmnopqrstuvwxyz";
char *password;
int i;
/* Generate a (not very) random seed.
You should do it better than this... */
seed[0] = time(NULL);
seed[1] = getpid() ^ (seed[0] >> 14 & 0x30000);
/* Turn it into printable characters from `seedchars'. */
for (i = 0; i < 8; i++)
salt[3+i] = seedchars[(seed[i/5] >> (i%5)*6) & 0x3f];
/* Read in the user's password and encrypt it. */
password = crypt(getpass("Password:"), salt);
/* Print the results. */
puts(password);
return 0;
}

View File

@ -0,0 +1,25 @@
#include <termios.h>
#include <stdio.h>
ssize_t
my_getpass (char **lineptr, size_t *n, FILE *stream)
{
struct termios old, new;
int nread;
/* Turn echoing off and fail if we can't. */
if (tcgetattr (fileno (stream), &old) != 0)
return -1;
new = old;
new.c_lflag &= ~ECHO;
if (tcsetattr (fileno (stream), TCSAFLUSH, &new) != 0)
return -1;
/* Read the password. */
nread = getline (lineptr, n, stream);
/* Restore terminal. */
(void) tcsetattr (fileno (stream), TCSAFLUSH, &old);
return nread;
}

26
crypt/examples/testpass.c Normal file
View File

@ -0,0 +1,26 @@
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <crypt.h>
int
main(void)
{
/* Hashed form of "GNU libc manual". */
const char *const pass = "$1$/iSaq7rB$EoUw5jJPPvAPECNaaWzMK/";
char *result;
int ok;
/*@group*/
/* Read in the user's password and encrypt it,
passing the expected password in as the salt. */
result = crypt(getpass("Password:"), pass);
/*@end group*/
/* Test the result. */
ok = strcmp (result, pass) == 0;
puts(ok ? "Access granted." : "Access denied.");
return ok ? 0 : 1;
}

32
crypt/genpass.c.texi Normal file
View File

@ -0,0 +1,32 @@
#include <stdio.h>
#include <time.h>
#include <unistd.h>
#include <crypt.h>
int
main(void)
@{
unsigned long seed[2];
char salt[] = "$1$........";
const char *const seedchars =
"./0123456789ABCDEFGHIJKLMNOPQRST"
"UVWXYZabcdefghijklmnopqrstuvwxyz";
char *password;
int i;
/* @r{Generate a (not very) random seed.
You should do it better than this...} */
seed[0] = time(NULL);
seed[1] = getpid() ^ (seed[0] >> 14 & 0x30000);
/* @r{Turn it into printable characters from `seedchars'.} */
for (i = 0; i < 8; i++)
salt[3+i] = seedchars[(seed[i/5] >> (i%5)*6) & 0x3f];
/* @r{Read in the user's password and encrypt it.} */
password = crypt(getpass("Password:"), salt);
/* @r{Print the results.} */
puts(password);
return 0;
@}

25
crypt/mygetpass.c.texi Normal file
View File

@ -0,0 +1,25 @@
#include <termios.h>
#include <stdio.h>
ssize_t
my_getpass (char **lineptr, size_t *n, FILE *stream)
@{
struct termios old, new;
int nread;
/* @r{Turn echoing off and fail if we can't.} */
if (tcgetattr (fileno (stream), &old) != 0)
return -1;
new = old;
new.c_lflag &= ~ECHO;
if (tcsetattr (fileno (stream), TCSAFLUSH, &new) != 0)
return -1;
/* @r{Read the password.} */
nread = getline (lineptr, n, stream);
/* @r{Restore terminal.} */
(void) tcsetattr (fileno (stream), TCSAFLUSH, &old);
return nread;
@}

153
crypt/speeds.c Normal file
View File

@ -0,0 +1,153 @@
/*
* This fcrypt/crypt speed testing program
* is derived from one floating around in
* the net. It's distributed along with
* UFC-crypt but is not covered by any
* licence.
*
* @(#)speeds.c 1.11 20 Aug 1996
*/
#include <signal.h>
#include <stdio.h>
#ifndef SIGVTALRM
/*
* patch from chip@chinacat.unicom.com (Chip Rosenthal):
* you may enable it if your system does not include
* a setitimer() function. You'll have to ensure the
* existence a environment variable: HZ giving how many
* ticks goes per second.
* If not existing in your default environment 50, 60
* or even 100 may be the right value. Perhaps you should
* then use 'time ./ufc 10000' instead of guessing.
*/
#define NO_ITIMER
#endif
#ifdef NO_ITIMER
#include <sys/types.h>
#include <sys/times.h>
#else
#include <sys/time.h>
#endif
static int cnt;
#ifdef NO_ITIMER
char *hz;
struct tms tstart, tfinish;
#endif
#define ITIME 10 /* Number of seconds to run test. */
char *crypt(), *fcrypt();
void
Stop ()
{
double elapsed;
#ifdef NO_ITIMER
(void) times(&tfinish);
elapsed = ((tfinish.tms_utime + tfinish.tms_stime) -
(tstart.tms_utime + tstart.tms_stime)) / atoi(hz);
printf("elapsed time = %d sec, CPU time = %f sec\n", ITIME, elapsed);
#else
elapsed = ITIME;
#endif
printf ("Did %f %s()s per second.\n", ((float) cnt) / elapsed,
#if defined(FCRYPT)
"fcrypt"
#else
"crypt"
#endif
);
exit (0);
}
/*
* Silly rewrite of 'bzero'. I do so
* because some machines don't have
* bzero and some don't have memset.
*/
static void clearmem(start, cnt)
char *start;
int cnt;
{ while(cnt--)
*start++ = '\0';
}
main ()
{
char *s;
#ifdef NO_ITIMER
extern char *getenv();
#else
struct itimerval itv;
#endif
#ifdef NO_ITIMER
if ((hz = getenv("HZ")) == NULL) {
fprintf(stderr, "HZ environment parameter undefined\n");
exit(1);
}
#endif
#ifdef FCRYPT
printf("\n");
printf("Warning: this version of the speed program may run slower when\n");
printf("benchmarking UFC-crypt than previous versions. This is because it\n");
printf("stresses the CPU hardware cache in order to get benchmark figures\n");
printf("that corresponds closer to the performance that can be expected in\n");
printf("a password cracker.\n\n");
#endif
printf ("Running %s for %d seconds of virtual time ...\n",
#ifdef FCRYPT
"UFC-crypt",
#else
"crypt(libc)",
#endif
ITIME);
#ifdef FCRYPT
init_des ();
#endif
#ifdef NO_ITIMER
signal(SIGALRM, Stop);
switch (fork()) {
case -1:
perror("fork failed");
exit(1);
case 0:
sleep(10);
kill(getppid(), SIGALRM);
exit(0);
default:
(void) times(&tstart);
}
#else
clearmem ((char*)&itv, (int)sizeof (itv));
signal (SIGVTALRM, Stop);
itv.it_value.tv_sec = ITIME;
itv.it_value.tv_usec = 0;
setitimer (ITIMER_VIRTUAL, &itv, NULL);
#endif
s = "fredred";
for (cnt = 0;; cnt++)
{
#ifdef FCRYPT
s = fcrypt (s, "eek");
#else
s = crypt (s, "eek");
#endif
}
}

View File

@ -0,0 +1,2 @@
# The Hurd uses Unix like DES crypto function.
unix

View File

@ -0,0 +1,4 @@
ifeq ($(subdir),md5-crypt)
libcrypt-routines += crypt crypt_util
dont_distribute += crypt.c crypt_util.c
endif

View File

@ -0,0 +1,149 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 1992, 1993, 1996, 1997 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* crypt entry points
*
* @(#)crypt-entry.c 1.2 12/20/96
*
*/
#ifdef DEBUG
#include <stdio.h>
#endif
#include <string.h>
#ifndef STATIC
#define STATIC static
#endif
#ifndef DOS
#include "ufc-crypt.h"
#else
/*
* Thanks to greg%wind@plains.NoDak.edu (Greg W. Wettstein)
* for DOS patches
*/
#include "ufc.h"
#endif
#include "crypt.h"
#include "crypt-private.h"
/* Prototypes for local functions. */
#if __STDC__ - 0
#ifndef __GNU_LIBRARY__
void _ufc_clearmem (char *start, int cnt);
#else
#define _ufc_clearmem(start, cnt) memset(start, 0, cnt)
#endif
extern char *__md5_crypt_r (const char *key, const char *salt, char *buffer,
int buflen);
extern char *__md5_crypt (const char *key, const char *salt);
#endif
/* Define our magic string to mark salt for MD5 encryption
replacement. This is meant to be the same as for other MD5 based
encryption implementations. */
static const char md5_salt_prefix[] = "$1$";
/* For use by the old, non-reentrant routines (crypt/encrypt/setkey) */
extern struct crypt_data _ufc_foobar;
/*
* UNIX crypt function
*/
char *
__crypt_r (key, salt, data)
const char *key;
const char *salt;
struct crypt_data * __restrict data;
{
ufc_long res[4];
char ktab[9];
ufc_long xx = 25; /* to cope with GCC long long compiler bugs */
#ifdef _LIBC
/* Try to find out whether we have to use MD5 encryption replacement. */
if (strncmp (md5_salt_prefix, salt, sizeof (md5_salt_prefix) - 1) == 0)
return __md5_crypt_r (key, salt, (char *) data,
sizeof (struct crypt_data));
#endif
/*
* Hack DES tables according to salt
*/
_ufc_setup_salt_r (salt, data);
/*
* Setup key schedule
*/
_ufc_clearmem (ktab, (int) sizeof (ktab));
(void) strncpy (ktab, key, 8);
_ufc_mk_keytab_r (ktab, data);
/*
* Go for the 25 DES encryptions
*/
_ufc_clearmem ((char*) res, (int) sizeof (res));
_ufc_doit_r (xx, data, &res[0]);
/*
* Do final permutations
*/
_ufc_dofinalperm_r (res, data);
/*
* And convert back to 6 bit ASCII
*/
_ufc_output_conversion_r (res[0], res[1], salt, data);
return data->crypt_3_buf;
}
weak_alias (__crypt_r, crypt_r)
char *
crypt (key, salt)
const char *key;
const char *salt;
{
#ifdef _LIBC
/* Try to find out whether we have to use MD5 encryption replacement. */
if (strncmp (md5_salt_prefix, salt, sizeof (md5_salt_prefix) - 1) == 0)
return __md5_crypt (key, salt);
#endif
return __crypt_r (key, salt, &_ufc_foobar);
}
/*
* To make fcrypt users happy.
* They don't need to call init_des.
*/
#ifdef _LIBC
weak_alias (crypt, fcrypt)
#else
char *
__fcrypt (key, salt)
const char *key;
const char *salt;
{
return crypt (key, salt);
}
#endif

View File

@ -0,0 +1,60 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 92, 93, 96, 97, 98 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* @(#)crypt-private.h 1.4 12/20/96
*/
/* Prototypes for local functions in libcrypt.a. */
#ifndef CRYPT_PRIVATE_H
#define CRYPT_PRIVATE_H 1
#include <features.h>
/* crypt.c */
extern void _ufc_doit_r (ufc_long itr, struct crypt_data * __restrict __data,
ufc_long *res);
/* crypt_util.c */
extern void __init_des_r (struct crypt_data * __restrict __data);
extern void __init_des (void);
extern void _ufc_setup_salt_r (__const char *s,
struct crypt_data * __restrict __data);
extern void _ufc_mk_keytab_r (__const char *key,
struct crypt_data * __restrict __data);
extern void _ufc_dofinalperm_r (ufc_long *res,
struct crypt_data * __restrict __data);
extern void _ufc_output_conversion_r (ufc_long v1, ufc_long v2,
__const char *salt,
struct crypt_data * __restrict __data);
extern void __setkey_r (__const char *__key,
struct crypt_data * __restrict __data);
extern void __encrypt_r (char * __restrict __block, int __edflag,
struct crypt_data * __restrict __data);
/* crypt-entry.c */
extern char *__crypt_r (__const char *__key, __const char *__salt,
struct crypt_data * __restrict __data);
extern char *fcrypt (__const char *key, __const char *salt);
#endif /* crypt-private.h */

120
crypt/sysdeps/unix/crypt.c Normal file
View File

@ -0,0 +1,120 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 1992, 1993, 1996 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* @(#)crypt.c 2.25 12/20/96
*
* Semiportable C version
*
*/
#include "ufc-crypt.h"
#include "crypt.h"
#include "crypt-private.h"
#ifdef _UFC_32_
/*
* 32 bit version
*/
#define SBA(sb, v) (*(long32*)((char*)(sb)+(v)))
void
_ufc_doit_r(itr, __data, res)
ufc_long itr, *res;
struct crypt_data * __restrict __data;
{
int i;
long32 s, *k;
long32 *sb01 = (long32*)__data->sb0;
long32 *sb23 = (long32*)__data->sb2;
long32 l1, l2, r1, r2;
l1 = (long32)res[0]; l2 = (long32)res[1];
r1 = (long32)res[2]; r2 = (long32)res[3];
while(itr--) {
k = (long32*)__data->keysched;
for(i=8; i--; ) {
s = *k++ ^ r1;
l1 ^= SBA(sb01, s & 0xffff); l2 ^= SBA(sb01, (s & 0xffff)+4);
l1 ^= SBA(sb01, s >>= 16 ); l2 ^= SBA(sb01, (s )+4);
s = *k++ ^ r2;
l1 ^= SBA(sb23, s & 0xffff); l2 ^= SBA(sb23, (s & 0xffff)+4);
l1 ^= SBA(sb23, s >>= 16 ); l2 ^= SBA(sb23, (s )+4);
s = *k++ ^ l1;
r1 ^= SBA(sb01, s & 0xffff); r2 ^= SBA(sb01, (s & 0xffff)+4);
r1 ^= SBA(sb01, s >>= 16 ); r2 ^= SBA(sb01, (s )+4);
s = *k++ ^ l2;
r1 ^= SBA(sb23, s & 0xffff); r2 ^= SBA(sb23, (s & 0xffff)+4);
r1 ^= SBA(sb23, s >>= 16 ); r2 ^= SBA(sb23, (s )+4);
}
s=l1; l1=r1; r1=s; s=l2; l2=r2; r2=s;
}
res[0] = l1; res[1] = l2; res[2] = r1; res[3] = r2;
}
#endif
#ifdef _UFC_64_
/*
* 64 bit version
*/
#define SBA(sb, v) (*(long64*)((char*)(sb)+(v)))
void
_ufc_doit_r(itr, __data, res)
ufc_long itr, *res;
struct crypt_data * __restrict __data;
{
int i;
long64 l, r, s, *k;
register long64 *sb01 = (long64*)__data->sb0;
register long64 *sb23 = (long64*)__data->sb2;
l = (((long64)res[0]) << 32) | ((long64)res[1]);
r = (((long64)res[2]) << 32) | ((long64)res[3]);
while(itr--) {
k = (long64*)__data->keysched;
for(i=8; i--; ) {
s = *k++ ^ r;
l ^= SBA(sb23, (s ) & 0xffff);
l ^= SBA(sb23, (s >>= 16) & 0xffff);
l ^= SBA(sb01, (s >>= 16) & 0xffff);
l ^= SBA(sb01, (s >>= 16) );
s = *k++ ^ l;
r ^= SBA(sb23, (s ) & 0xffff);
r ^= SBA(sb23, (s >>= 16) & 0xffff);
r ^= SBA(sb01, (s >>= 16) & 0xffff);
r ^= SBA(sb01, (s >>= 16) );
}
s=l; l=r; r=s;
}
res[0] = l >> 32; res[1] = l & 0xffffffff;
res[2] = r >> 32; res[3] = r & 0xffffffff;
}
#endif

View File

@ -0,0 +1,71 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 92, 93, 96, 97, 98 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with the GNU C Library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* @(#)crypt.h 1.5 12/20/96
*
*/
#ifndef _CRYPT_H
#define _CRYPT_H 1
#include <features.h>
__BEGIN_DECLS
/* Encrypt at most 8 characters from KEY using salt to perturb DES. */
extern char *crypt __P ((__const char *__key, __const char *__salt));
/* Setup DES tables according KEY. */
extern void setkey __P ((__const char *__key));
/* Encrypt data in BLOCK in place if EDFLAG is zero; otherwise decrypt
block in place. */
extern void encrypt __P ((char *__block, int __edflag));
#ifdef __USE_GNU
/* Reentrant versions of the functions above. The additional argument
points to a structure where the results are placed in. */
struct crypt_data
{
char keysched[16 * 8];
char sb0[32768];
char sb1[32768];
char sb2[32768];
char sb3[32768];
/* end-of-aligment-critical-data */
char crypt_3_buf[14];
char current_salt[2];
long int current_saltbits;
int direction, initialized;
};
extern char *crypt_r __P ((__const char *__key, __const char *__salt,
struct crypt_data * __restrict __data));
extern void setkey_r __P ((__const char *__key,
struct crypt_data * __restrict __data));
extern void encrypt_r __P ((char *__block, int __edflag,
struct crypt_data * __restrict __data));
#endif
__END_DECLS
#endif /* crypt.h */

View File

@ -0,0 +1,914 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 92, 93, 96, 97, 98 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* @(#)crypt_util.c 2.56 12/20/96
*
* Support routines
*
*/
#ifdef DEBUG
#include <stdio.h>
#endif
#include <string.h>
#ifndef STATIC
#define STATIC static
#endif
#ifndef DOS
#include "patchlevel.h"
#include "ufc-crypt.h"
#else
/*
* Thanks to greg%wind@plains.NoDak.edu (Greg W. Wettstein)
* for DOS patches
*/
#include "pl.h"
#include "ufc.h"
#endif
#include "crypt.h"
#include "crypt-private.h"
/* Prototypes for local functions. */
#if __STDC__ - 0
#ifndef __GNU_LIBRARY__
void _ufc_clearmem (char *start, int cnt);
void _ufc_copymem (char *from, char *to, int cnt);
#endif
#ifdef _UFC_32_
STATIC void shuffle_sb (long32 *k, ufc_long saltbits);
#else
STATIC void shuffle_sb (long64 *k, ufc_long saltbits);
#endif
#endif
static const char patchlevel_str[] = PATCHLEVEL;
/*
* Permutation done once on the 56 bit
* key derived from the original 8 byte ASCII key.
*/
static const int pc1[56] = {
57, 49, 41, 33, 25, 17, 9, 1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27, 19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15, 7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29, 21, 13, 5, 28, 20, 12, 4
};
/*
* How much to rotate each 28 bit half of the pc1 permutated
* 56 bit key before using pc2 to give the i' key
*/
static const int rots[16] = {
1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1
};
/*
* Permutation giving the key
* of the i' DES round
*/
static const int pc2[48] = {
14, 17, 11, 24, 1, 5, 3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8, 16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55, 30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53, 46, 42, 50, 36, 29, 32
};
/*
* The E expansion table which selects
* bits from the 32 bit intermediate result.
*/
static const int esel[48] = {
32, 1, 2, 3, 4, 5, 4, 5, 6, 7, 8, 9,
8, 9, 10, 11, 12, 13, 12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21, 20, 21, 22, 23, 24, 25,
24, 25, 26, 27, 28, 29, 28, 29, 30, 31, 32, 1
};
/*
* Permutation done on the
* result of sbox lookups
*/
static const int perm32[32] = {
16, 7, 20, 21, 29, 12, 28, 17, 1, 15, 23, 26, 5, 18, 31, 10,
2, 8, 24, 14, 32, 27, 3, 9, 19, 13, 30, 6, 22, 11, 4, 25
};
/*
* The sboxes
*/
static const int sbox[8][4][16]= {
{ { 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7 },
{ 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8 },
{ 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0 },
{ 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13 }
},
{ { 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10 },
{ 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5 },
{ 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15 },
{ 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9 }
},
{ { 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8 },
{ 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1 },
{ 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7 },
{ 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12 }
},
{ { 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15 },
{ 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9 },
{ 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4 },
{ 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14 }
},
{ { 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9 },
{ 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6 },
{ 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14 },
{ 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3 }
},
{ { 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11 },
{ 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8 },
{ 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6 },
{ 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13 }
},
{ { 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1 },
{ 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6 },
{ 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2 },
{ 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12 }
},
{ { 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7 },
{ 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2 },
{ 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8 },
{ 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11 }
}
};
/*
* This is the initial
* permutation matrix
*/
static const int initial_perm[64] = {
58, 50, 42, 34, 26, 18, 10, 2, 60, 52, 44, 36, 28, 20, 12, 4,
62, 54, 46, 38, 30, 22, 14, 6, 64, 56, 48, 40, 32, 24, 16, 8,
57, 49, 41, 33, 25, 17, 9, 1, 59, 51, 43, 35, 27, 19, 11, 3,
61, 53, 45, 37, 29, 21, 13, 5, 63, 55, 47, 39, 31, 23, 15, 7
};
/*
* This is the final
* permutation matrix
*/
static const int final_perm[64] = {
40, 8, 48, 16, 56, 24, 64, 32, 39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30, 37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28, 35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26, 33, 1, 41, 9, 49, 17, 57, 25
};
#define ascii_to_bin(c) ((c)>='a'?(c-59):(c)>='A'?((c)-53):(c)-'.')
#define bin_to_ascii(c) ((c)>=38?((c)-38+'a'):(c)>=12?((c)-12+'A'):(c)+'.')
static const ufc_long BITMASK[24] = {
0x40000000, 0x20000000, 0x10000000, 0x08000000, 0x04000000, 0x02000000,
0x01000000, 0x00800000, 0x00400000, 0x00200000, 0x00100000, 0x00080000,
0x00004000, 0x00002000, 0x00001000, 0x00000800, 0x00000400, 0x00000200,
0x00000100, 0x00000080, 0x00000040, 0x00000020, 0x00000010, 0x00000008
};
static const unsigned char bytemask[8] = {
0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01
};
static const ufc_long longmask[32] = {
0x80000000, 0x40000000, 0x20000000, 0x10000000,
0x08000000, 0x04000000, 0x02000000, 0x01000000,
0x00800000, 0x00400000, 0x00200000, 0x00100000,
0x00080000, 0x00040000, 0x00020000, 0x00010000,
0x00008000, 0x00004000, 0x00002000, 0x00001000,
0x00000800, 0x00000400, 0x00000200, 0x00000100,
0x00000080, 0x00000040, 0x00000020, 0x00000010,
0x00000008, 0x00000004, 0x00000002, 0x00000001
};
/*
* do_pc1: permform pc1 permutation in the key schedule generation.
*
* The first index is the byte number in the 8 byte ASCII key
* - second - - the two 28 bits halfs of the result
* - third - selects the 7 bits actually used of each byte
*
* The result is kept with 28 bit per 32 bit with the 4 most significant
* bits zero.
*/
static ufc_long do_pc1[8][2][128];
/*
* do_pc2: permform pc2 permutation in the key schedule generation.
*
* The first index is the septet number in the two 28 bit intermediate values
* - second - - - septet values
*
* Knowledge of the structure of the pc2 permutation is used.
*
* The result is kept with 28 bit per 32 bit with the 4 most significant
* bits zero.
*/
static ufc_long do_pc2[8][128];
/*
* eperm32tab: do 32 bit permutation and E selection
*
* The first index is the byte number in the 32 bit value to be permuted
* - second - is the value of this byte
* - third - selects the two 32 bit values
*
* The table is used and generated internally in init_des to speed it up
*/
static ufc_long eperm32tab[4][256][2];
/*
* efp: undo an extra e selection and do final
* permutation giving the DES result.
*
* Invoked 6 bit a time on two 48 bit values
* giving two 32 bit longs.
*/
static ufc_long efp[16][64][2];
/*
* For use by the old, non-reentrant routines
* (crypt/encrypt/setkey)
*/
struct crypt_data _ufc_foobar;
#ifdef __GNU_LIBRARY__
#include <bits/libc-lock.h>
__libc_lock_define_initialized (static, _ufc_tables_lock)
#endif
#ifdef DEBUG
void
_ufc_prbits(a, n)
ufc_long *a;
int n;
{
ufc_long i, j, t, tmp;
n /= 8;
for(i = 0; i < n; i++) {
tmp=0;
for(j = 0; j < 8; j++) {
t=8*i+j;
tmp|=(a[t/24] & BITMASK[t % 24])?bytemask[j]:0;
}
(void)printf("%02x ",tmp);
}
printf(" ");
}
static void
_ufc_set_bits(v, b)
ufc_long v;
ufc_long *b;
{
ufc_long i;
*b = 0;
for(i = 0; i < 24; i++) {
if(v & longmask[8 + i])
*b |= BITMASK[i];
}
}
#endif
#ifndef __GNU_LIBRARY__
/*
* Silly rewrites of 'bzero'/'memset'. I do so
* because some machines don't have
* bzero and some don't have memset.
*/
void
_ufc_clearmem(start, cnt)
char *start;
int cnt;
{
while(cnt--)
*start++ = '\0';
}
void
_ufc_copymem(from, to, cnt)
char *from, *to;
int cnt;
{
while(cnt--)
*to++ = *from++;
}
#else
#define _ufc_clearmem(start, cnt) memset(start, 0, cnt)
#define _ufc_copymem(from, to, cnt) memcpy(to, from, cnt)
#endif
/* lookup a 6 bit value in sbox */
#define s_lookup(i,s) sbox[(i)][(((s)>>4) & 0x2)|((s) & 0x1)][((s)>>1) & 0xf];
/*
* Initialize unit - may be invoked directly
* by fcrypt users.
*/
void
__init_des_r(__data)
struct crypt_data * __restrict __data;
{
int comes_from_bit;
int bit, sg;
ufc_long j;
ufc_long mask1, mask2;
int e_inverse[64];
static volatile int small_tables_initialized = 0;
#ifdef _UFC_32_
long32 *sb[4];
sb[0] = (long32*)__data->sb0; sb[1] = (long32*)__data->sb1;
sb[2] = (long32*)__data->sb2; sb[3] = (long32*)__data->sb3;
#endif
#ifdef _UFC_64_
long64 *sb[4];
sb[0] = (long64*)__data->sb0; sb[1] = (long64*)__data->sb1;
sb[2] = (long64*)__data->sb2; sb[3] = (long64*)__data->sb3;
#endif
if(small_tables_initialized == 0) {
#ifdef __GNU_LIBRARY__
__libc_lock_lock (_ufc_tables_lock);
if(small_tables_initialized)
goto small_tables_done;
#endif
/*
* Create the do_pc1 table used
* to affect pc1 permutation
* when generating keys
*/
_ufc_clearmem((char*)do_pc1, (int)sizeof(do_pc1));
for(bit = 0; bit < 56; bit++) {
comes_from_bit = pc1[bit] - 1;
mask1 = bytemask[comes_from_bit % 8 + 1];
mask2 = longmask[bit % 28 + 4];
for(j = 0; j < 128; j++) {
if(j & mask1)
do_pc1[comes_from_bit / 8][bit / 28][j] |= mask2;
}
}
/*
* Create the do_pc2 table used
* to affect pc2 permutation when
* generating keys
*/
_ufc_clearmem((char*)do_pc2, (int)sizeof(do_pc2));
for(bit = 0; bit < 48; bit++) {
comes_from_bit = pc2[bit] - 1;
mask1 = bytemask[comes_from_bit % 7 + 1];
mask2 = BITMASK[bit % 24];
for(j = 0; j < 128; j++) {
if(j & mask1)
do_pc2[comes_from_bit / 7][j] |= mask2;
}
}
/*
* Now generate the table used to do combined
* 32 bit permutation and e expansion
*
* We use it because we have to permute 16384 32 bit
* longs into 48 bit in order to initialize sb.
*
* Looping 48 rounds per permutation becomes
* just too slow...
*
*/
_ufc_clearmem((char*)eperm32tab, (int)sizeof(eperm32tab));
for(bit = 0; bit < 48; bit++) {
ufc_long mask1,comes_from;
comes_from = perm32[esel[bit]-1]-1;
mask1 = bytemask[comes_from % 8];
for(j = 256; j--;) {
if(j & mask1)
eperm32tab[comes_from / 8][j][bit / 24] |= BITMASK[bit % 24];
}
}
/*
* Create an inverse matrix for esel telling
* where to plug out bits if undoing it
*/
for(bit=48; bit--;) {
e_inverse[esel[bit] - 1 ] = bit;
e_inverse[esel[bit] - 1 + 32] = bit + 48;
}
/*
* create efp: the matrix used to
* undo the E expansion and effect final permutation
*/
_ufc_clearmem((char*)efp, (int)sizeof efp);
for(bit = 0; bit < 64; bit++) {
int o_bit, o_long;
ufc_long word_value, mask1, mask2;
int comes_from_f_bit, comes_from_e_bit;
int comes_from_word, bit_within_word;
/* See where bit i belongs in the two 32 bit long's */
o_long = bit / 32; /* 0..1 */
o_bit = bit % 32; /* 0..31 */
/*
* And find a bit in the e permutated value setting this bit.
*
* Note: the e selection may have selected the same bit several
* times. By the initialization of e_inverse, we only look
* for one specific instance.
*/
comes_from_f_bit = final_perm[bit] - 1; /* 0..63 */
comes_from_e_bit = e_inverse[comes_from_f_bit]; /* 0..95 */
comes_from_word = comes_from_e_bit / 6; /* 0..15 */
bit_within_word = comes_from_e_bit % 6; /* 0..5 */
mask1 = longmask[bit_within_word + 26];
mask2 = longmask[o_bit];
for(word_value = 64; word_value--;) {
if(word_value & mask1)
efp[comes_from_word][word_value][o_long] |= mask2;
}
}
small_tables_initialized = 1;
#ifdef __GNU_LIBRARY__
small_tables_done:
__libc_lock_unlock(_ufc_tables_lock);
#endif
}
/*
* Create the sb tables:
*
* For each 12 bit segment of an 48 bit intermediate
* result, the sb table precomputes the two 4 bit
* values of the sbox lookups done with the two 6
* bit halves, shifts them to their proper place,
* sends them through perm32 and finally E expands
* them so that they are ready for the next
* DES round.
*
*/
_ufc_clearmem((char*)__data->sb0, (int)sizeof(__data->sb0));
_ufc_clearmem((char*)__data->sb1, (int)sizeof(__data->sb1));
_ufc_clearmem((char*)__data->sb2, (int)sizeof(__data->sb2));
_ufc_clearmem((char*)__data->sb3, (int)sizeof(__data->sb3));
for(sg = 0; sg < 4; sg++) {
int j1, j2;
int s1, s2;
for(j1 = 0; j1 < 64; j1++) {
s1 = s_lookup(2 * sg, j1);
for(j2 = 0; j2 < 64; j2++) {
ufc_long to_permute, inx;
s2 = s_lookup(2 * sg + 1, j2);
to_permute = (((ufc_long)s1 << 4) |
(ufc_long)s2) << (24 - 8 * (ufc_long)sg);
#ifdef _UFC_32_
inx = ((j1 << 6) | j2) << 1;
sb[sg][inx ] = eperm32tab[0][(to_permute >> 24) & 0xff][0];
sb[sg][inx+1] = eperm32tab[0][(to_permute >> 24) & 0xff][1];
sb[sg][inx ] |= eperm32tab[1][(to_permute >> 16) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[1][(to_permute >> 16) & 0xff][1];
sb[sg][inx ] |= eperm32tab[2][(to_permute >> 8) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[2][(to_permute >> 8) & 0xff][1];
sb[sg][inx ] |= eperm32tab[3][(to_permute) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[3][(to_permute) & 0xff][1];
#endif
#ifdef _UFC_64_
inx = ((j1 << 6) | j2);
sb[sg][inx] =
((long64)eperm32tab[0][(to_permute >> 24) & 0xff][0] << 32) |
(long64)eperm32tab[0][(to_permute >> 24) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[1][(to_permute >> 16) & 0xff][0] << 32) |
(long64)eperm32tab[1][(to_permute >> 16) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[2][(to_permute >> 8) & 0xff][0] << 32) |
(long64)eperm32tab[2][(to_permute >> 8) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[3][(to_permute) & 0xff][0] << 32) |
(long64)eperm32tab[3][(to_permute) & 0xff][1];
#endif
}
}
}
__data->initialized++;
}
void
__init_des()
{
__init_des_r(&_ufc_foobar);
}
/*
* Process the elements of the sb table permuting the
* bits swapped in the expansion by the current salt.
*/
#ifdef _UFC_32_
STATIC void
shuffle_sb(k, saltbits)
long32 *k;
ufc_long saltbits;
{
ufc_long j;
long32 x;
for(j=4096; j--;) {
x = (k[0] ^ k[1]) & (long32)saltbits;
*k++ ^= x;
*k++ ^= x;
}
}
#endif
#ifdef _UFC_64_
STATIC void
shuffle_sb(k, saltbits)
long64 *k;
ufc_long saltbits;
{
ufc_long j;
long64 x;
for(j=4096; j--;) {
x = ((*k >> 32) ^ *k) & (long64)saltbits;
*k++ ^= (x << 32) | x;
}
}
#endif
/*
* Setup the unit for a new salt
* Hopefully we'll not see a new salt in each crypt call.
*/
void
_ufc_setup_salt_r(s, __data)
__const char *s;
struct crypt_data * __restrict __data;
{
ufc_long i, j, saltbits;
if(__data->initialized == 0)
__init_des_r(__data);
if(s[0] == __data->current_salt[0] && s[1] == __data->current_salt[1])
return;
__data->current_salt[0] = s[0]; __data->current_salt[1] = s[1];
/*
* This is the only crypt change to DES:
* entries are swapped in the expansion table
* according to the bits set in the salt.
*/
saltbits = 0;
for(i = 0; i < 2; i++) {
long c=ascii_to_bin(s[i]);
for(j = 0; j < 6; j++) {
if((c >> j) & 0x1)
saltbits |= BITMASK[6 * i + j];
}
}
/*
* Permute the sb table values
* to reflect the changed e
* selection table
*/
#ifdef _UFC_32_
#define LONGG long32*
#endif
#ifdef _UFC_64_
#define LONGG long64*
#endif
shuffle_sb((LONGG)__data->sb0, __data->current_saltbits ^ saltbits);
shuffle_sb((LONGG)__data->sb1, __data->current_saltbits ^ saltbits);
shuffle_sb((LONGG)__data->sb2, __data->current_saltbits ^ saltbits);
shuffle_sb((LONGG)__data->sb3, __data->current_saltbits ^ saltbits);
__data->current_saltbits = saltbits;
}
void
_ufc_mk_keytab_r(key, __data)
const char *key;
struct crypt_data * __restrict __data;
{
ufc_long v1, v2, *k1;
int i;
#ifdef _UFC_32_
long32 v, *k2;
k2 = (long32*)__data->keysched;
#endif
#ifdef _UFC_64_
long64 v, *k2;
k2 = (long64*)__data->keysched;
#endif
v1 = v2 = 0; k1 = &do_pc1[0][0][0];
for(i = 8; i--;) {
v1 |= k1[*key & 0x7f]; k1 += 128;
v2 |= k1[*key++ & 0x7f]; k1 += 128;
}
for(i = 0; i < 16; i++) {
k1 = &do_pc2[0][0];
v1 = (v1 << rots[i]) | (v1 >> (28 - rots[i]));
v = k1[(v1 >> 21) & 0x7f]; k1 += 128;
v |= k1[(v1 >> 14) & 0x7f]; k1 += 128;
v |= k1[(v1 >> 7) & 0x7f]; k1 += 128;
v |= k1[(v1 ) & 0x7f]; k1 += 128;
#ifdef _UFC_32_
*k2++ = (v | 0x00008000);
v = 0;
#endif
#ifdef _UFC_64_
v = (v << 32);
#endif
v2 = (v2 << rots[i]) | (v2 >> (28 - rots[i]));
v |= k1[(v2 >> 21) & 0x7f]; k1 += 128;
v |= k1[(v2 >> 14) & 0x7f]; k1 += 128;
v |= k1[(v2 >> 7) & 0x7f]; k1 += 128;
v |= k1[(v2 ) & 0x7f];
#ifdef _UFC_32_
*k2++ = (v | 0x00008000);
#endif
#ifdef _UFC_64_
*k2++ = v | 0x0000800000008000l;
#endif
}
__data->direction = 0;
}
/*
* Undo an extra E selection and do final permutations
*/
void
_ufc_dofinalperm_r(res, __data)
ufc_long *res;
struct crypt_data * __restrict __data;
{
ufc_long v1, v2, x;
ufc_long l1,l2,r1,r2;
l1 = res[0]; l2 = res[1];
r1 = res[2]; r2 = res[3];
x = (l1 ^ l2) & __data->current_saltbits; l1 ^= x; l2 ^= x;
x = (r1 ^ r2) & __data->current_saltbits; r1 ^= x; r2 ^= x;
v1=v2=0; l1 >>= 3; l2 >>= 3; r1 >>= 3; r2 >>= 3;
v1 |= efp[15][ r2 & 0x3f][0]; v2 |= efp[15][ r2 & 0x3f][1];
v1 |= efp[14][(r2 >>= 6) & 0x3f][0]; v2 |= efp[14][ r2 & 0x3f][1];
v1 |= efp[13][(r2 >>= 10) & 0x3f][0]; v2 |= efp[13][ r2 & 0x3f][1];
v1 |= efp[12][(r2 >>= 6) & 0x3f][0]; v2 |= efp[12][ r2 & 0x3f][1];
v1 |= efp[11][ r1 & 0x3f][0]; v2 |= efp[11][ r1 & 0x3f][1];
v1 |= efp[10][(r1 >>= 6) & 0x3f][0]; v2 |= efp[10][ r1 & 0x3f][1];
v1 |= efp[ 9][(r1 >>= 10) & 0x3f][0]; v2 |= efp[ 9][ r1 & 0x3f][1];
v1 |= efp[ 8][(r1 >>= 6) & 0x3f][0]; v2 |= efp[ 8][ r1 & 0x3f][1];
v1 |= efp[ 7][ l2 & 0x3f][0]; v2 |= efp[ 7][ l2 & 0x3f][1];
v1 |= efp[ 6][(l2 >>= 6) & 0x3f][0]; v2 |= efp[ 6][ l2 & 0x3f][1];
v1 |= efp[ 5][(l2 >>= 10) & 0x3f][0]; v2 |= efp[ 5][ l2 & 0x3f][1];
v1 |= efp[ 4][(l2 >>= 6) & 0x3f][0]; v2 |= efp[ 4][ l2 & 0x3f][1];
v1 |= efp[ 3][ l1 & 0x3f][0]; v2 |= efp[ 3][ l1 & 0x3f][1];
v1 |= efp[ 2][(l1 >>= 6) & 0x3f][0]; v2 |= efp[ 2][ l1 & 0x3f][1];
v1 |= efp[ 1][(l1 >>= 10) & 0x3f][0]; v2 |= efp[ 1][ l1 & 0x3f][1];
v1 |= efp[ 0][(l1 >>= 6) & 0x3f][0]; v2 |= efp[ 0][ l1 & 0x3f][1];
res[0] = v1; res[1] = v2;
}
/*
* crypt only: convert from 64 bit to 11 bit ASCII
* prefixing with the salt
*/
void
_ufc_output_conversion_r(v1, v2, salt, __data)
ufc_long v1, v2;
__const char *salt;
struct crypt_data * __restrict __data;
{
int i, s, shf;
__data->crypt_3_buf[0] = salt[0];
__data->crypt_3_buf[1] = salt[1] ? salt[1] : salt[0];
for(i = 0; i < 5; i++) {
shf = (26 - 6 * i); /* to cope with MSC compiler bug */
__data->crypt_3_buf[i + 2] = bin_to_ascii((v1 >> shf) & 0x3f);
}
s = (v2 & 0xf) << 2;
v2 = (v2 >> 2) | ((v1 & 0x3) << 30);
for(i = 5; i < 10; i++) {
shf = (56 - 6 * i);
__data->crypt_3_buf[i + 2] = bin_to_ascii((v2 >> shf) & 0x3f);
}
__data->crypt_3_buf[12] = bin_to_ascii(s);
__data->crypt_3_buf[13] = 0;
}
/*
* UNIX encrypt function. Takes a bitvector
* represented by one byte per bit and
* encrypt/decrypt according to edflag
*/
void
__encrypt_r(__block, __edflag, __data)
char *__block;
int __edflag;
struct crypt_data * __restrict __data;
{
ufc_long l1, l2, r1, r2, res[4];
int i;
#ifdef _UFC_32_
long32 *kt;
kt = (long32*)__data->keysched;
#endif
#ifdef _UFC_64_
long64 *kt;
kt = (long64*)__data->keysched;
#endif
/*
* Undo any salt changes to E expansion
*/
_ufc_setup_salt_r("..", __data);
/*
* Reverse key table if
* changing operation (encrypt/decrypt)
*/
if((__edflag == 0) != (__data->direction == 0)) {
for(i = 0; i < 8; i++) {
#ifdef _UFC_32_
long32 x;
x = kt[2 * (15-i)];
kt[2 * (15-i)] = kt[2 * i];
kt[2 * i] = x;
x = kt[2 * (15-i) + 1];
kt[2 * (15-i) + 1] = kt[2 * i + 1];
kt[2 * i + 1] = x;
#endif
#ifdef _UFC_64_
long64 x;
x = kt[15-i];
kt[15-i] = kt[i];
kt[i] = x;
#endif
}
__data->direction = __edflag;
}
/*
* Do initial permutation + E expansion
*/
i = 0;
for(l1 = 0; i < 24; i++) {
if(__block[initial_perm[esel[i]-1]-1])
l1 |= BITMASK[i];
}
for(l2 = 0; i < 48; i++) {
if(__block[initial_perm[esel[i]-1]-1])
l2 |= BITMASK[i-24];
}
i = 0;
for(r1 = 0; i < 24; i++) {
if(__block[initial_perm[esel[i]-1+32]-1])
r1 |= BITMASK[i];
}
for(r2 = 0; i < 48; i++) {
if(__block[initial_perm[esel[i]-1+32]-1])
r2 |= BITMASK[i-24];
}
/*
* Do DES inner loops + final conversion
*/
res[0] = l1; res[1] = l2;
res[2] = r1; res[3] = r2;
_ufc_doit_r((ufc_long)1, __data, &res[0]);
/*
* Do final permutations
*/
_ufc_dofinalperm_r(res, __data);
/*
* And convert to bit array
*/
l1 = res[0]; r1 = res[1];
for(i = 0; i < 32; i++) {
*__block++ = (l1 & longmask[i]) != 0;
}
for(i = 0; i < 32; i++) {
*__block++ = (r1 & longmask[i]) != 0;
}
}
weak_alias (__encrypt_r, encrypt_r)
void
encrypt(__block, __edflag)
char *__block;
int __edflag;
{
__encrypt_r(__block, __edflag, &_ufc_foobar);
}
/*
* UNIX setkey function. Take a 64 bit DES
* key and setup the machinery.
*/
void
__setkey_r(__key, __data)
__const char *__key;
struct crypt_data * __restrict __data;
{
int i,j;
unsigned char c;
unsigned char ktab[8];
_ufc_setup_salt_r("..", __data); /* be sure we're initialized */
for(i = 0; i < 8; i++) {
for(j = 0, c = 0; j < 8; j++)
c = c << 1 | *__key++;
ktab[i] = c >> 1;
}
_ufc_mk_keytab_r(ktab, __data);
}
weak_alias (__setkey_r, setkey_r)
void
setkey(__key)
__const char *__key;
{
__setkey_r(__key, &_ufc_foobar);
}

View File

@ -0,0 +1,615 @@
/* Copyright (C) 1992 Eric Young - see COPYING for more details */
/* Collected from libdes and modified for SECURE RPC by Martin Kuck 1994 */
#include <string.h>
#include "des.h"
static const unsigned long des_SPtrans[8][64] =
{
{ /* nibble 0 */
0x00820200, 0x00020000, 0x80800000, 0x80820200,
0x00800000, 0x80020200, 0x80020000, 0x80800000,
0x80020200, 0x00820200, 0x00820000, 0x80000200,
0x80800200, 0x00800000, 0x00000000, 0x80020000,
0x00020000, 0x80000000, 0x00800200, 0x00020200,
0x80820200, 0x00820000, 0x80000200, 0x00800200,
0x80000000, 0x00000200, 0x00020200, 0x80820000,
0x00000200, 0x80800200, 0x80820000, 0x00000000,
0x00000000, 0x80820200, 0x00800200, 0x80020000,
0x00820200, 0x00020000, 0x80000200, 0x00800200,
0x80820000, 0x00000200, 0x00020200, 0x80800000,
0x80020200, 0x80000000, 0x80800000, 0x00820000,
0x80820200, 0x00020200, 0x00820000, 0x80800200,
0x00800000, 0x80000200, 0x80020000, 0x00000000,
0x00020000, 0x00800000, 0x80800200, 0x00820200,
0x80000000, 0x80820000, 0x00000200, 0x80020200},
{ /* nibble 1 */
0x10042004, 0x00000000, 0x00042000, 0x10040000,
0x10000004, 0x00002004, 0x10002000, 0x00042000,
0x00002000, 0x10040004, 0x00000004, 0x10002000,
0x00040004, 0x10042000, 0x10040000, 0x00000004,
0x00040000, 0x10002004, 0x10040004, 0x00002000,
0x00042004, 0x10000000, 0x00000000, 0x00040004,
0x10002004, 0x00042004, 0x10042000, 0x10000004,
0x10000000, 0x00040000, 0x00002004, 0x10042004,
0x00040004, 0x10042000, 0x10002000, 0x00042004,
0x10042004, 0x00040004, 0x10000004, 0x00000000,
0x10000000, 0x00002004, 0x00040000, 0x10040004,
0x00002000, 0x10000000, 0x00042004, 0x10002004,
0x10042000, 0x00002000, 0x00000000, 0x10000004,
0x00000004, 0x10042004, 0x00042000, 0x10040000,
0x10040004, 0x00040000, 0x00002004, 0x10002000,
0x10002004, 0x00000004, 0x10040000, 0x00042000},
{ /* nibble 2 */
0x41000000, 0x01010040, 0x00000040, 0x41000040,
0x40010000, 0x01000000, 0x41000040, 0x00010040,
0x01000040, 0x00010000, 0x01010000, 0x40000000,
0x41010040, 0x40000040, 0x40000000, 0x41010000,
0x00000000, 0x40010000, 0x01010040, 0x00000040,
0x40000040, 0x41010040, 0x00010000, 0x41000000,
0x41010000, 0x01000040, 0x40010040, 0x01010000,
0x00010040, 0x00000000, 0x01000000, 0x40010040,
0x01010040, 0x00000040, 0x40000000, 0x00010000,
0x40000040, 0x40010000, 0x01010000, 0x41000040,
0x00000000, 0x01010040, 0x00010040, 0x41010000,
0x40010000, 0x01000000, 0x41010040, 0x40000000,
0x40010040, 0x41000000, 0x01000000, 0x41010040,
0x00010000, 0x01000040, 0x41000040, 0x00010040,
0x01000040, 0x00000000, 0x41010000, 0x40000040,
0x41000000, 0x40010040, 0x00000040, 0x01010000},
{ /* nibble 3 */
0x00100402, 0x04000400, 0x00000002, 0x04100402,
0x00000000, 0x04100000, 0x04000402, 0x00100002,
0x04100400, 0x04000002, 0x04000000, 0x00000402,
0x04000002, 0x00100402, 0x00100000, 0x04000000,
0x04100002, 0x00100400, 0x00000400, 0x00000002,
0x00100400, 0x04000402, 0x04100000, 0x00000400,
0x00000402, 0x00000000, 0x00100002, 0x04100400,
0x04000400, 0x04100002, 0x04100402, 0x00100000,
0x04100002, 0x00000402, 0x00100000, 0x04000002,
0x00100400, 0x04000400, 0x00000002, 0x04100000,
0x04000402, 0x00000000, 0x00000400, 0x00100002,
0x00000000, 0x04100002, 0x04100400, 0x00000400,
0x04000000, 0x04100402, 0x00100402, 0x00100000,
0x04100402, 0x00000002, 0x04000400, 0x00100402,
0x00100002, 0x00100400, 0x04100000, 0x04000402,
0x00000402, 0x04000000, 0x04000002, 0x04100400},
{ /* nibble 4 */
0x02000000, 0x00004000, 0x00000100, 0x02004108,
0x02004008, 0x02000100, 0x00004108, 0x02004000,
0x00004000, 0x00000008, 0x02000008, 0x00004100,
0x02000108, 0x02004008, 0x02004100, 0x00000000,
0x00004100, 0x02000000, 0x00004008, 0x00000108,
0x02000100, 0x00004108, 0x00000000, 0x02000008,
0x00000008, 0x02000108, 0x02004108, 0x00004008,
0x02004000, 0x00000100, 0x00000108, 0x02004100,
0x02004100, 0x02000108, 0x00004008, 0x02004000,
0x00004000, 0x00000008, 0x02000008, 0x02000100,
0x02000000, 0x00004100, 0x02004108, 0x00000000,
0x00004108, 0x02000000, 0x00000100, 0x00004008,
0x02000108, 0x00000100, 0x00000000, 0x02004108,
0x02004008, 0x02004100, 0x00000108, 0x00004000,
0x00004100, 0x02004008, 0x02000100, 0x00000108,
0x00000008, 0x00004108, 0x02004000, 0x02000008},
{ /* nibble 5 */
0x20000010, 0x00080010, 0x00000000, 0x20080800,
0x00080010, 0x00000800, 0x20000810, 0x00080000,
0x00000810, 0x20080810, 0x00080800, 0x20000000,
0x20000800, 0x20000010, 0x20080000, 0x00080810,
0x00080000, 0x20000810, 0x20080010, 0x00000000,
0x00000800, 0x00000010, 0x20080800, 0x20080010,
0x20080810, 0x20080000, 0x20000000, 0x00000810,
0x00000010, 0x00080800, 0x00080810, 0x20000800,
0x00000810, 0x20000000, 0x20000800, 0x00080810,
0x20080800, 0x00080010, 0x00000000, 0x20000800,
0x20000000, 0x00000800, 0x20080010, 0x00080000,
0x00080010, 0x20080810, 0x00080800, 0x00000010,
0x20080810, 0x00080800, 0x00080000, 0x20000810,
0x20000010, 0x20080000, 0x00080810, 0x00000000,
0x00000800, 0x20000010, 0x20000810, 0x20080800,
0x20080000, 0x00000810, 0x00000010, 0x20080010},
{ /* nibble 6 */
0x00001000, 0x00000080, 0x00400080, 0x00400001,
0x00401081, 0x00001001, 0x00001080, 0x00000000,
0x00400000, 0x00400081, 0x00000081, 0x00401000,
0x00000001, 0x00401080, 0x00401000, 0x00000081,
0x00400081, 0x00001000, 0x00001001, 0x00401081,
0x00000000, 0x00400080, 0x00400001, 0x00001080,
0x00401001, 0x00001081, 0x00401080, 0x00000001,
0x00001081, 0x00401001, 0x00000080, 0x00400000,
0x00001081, 0x00401000, 0x00401001, 0x00000081,
0x00001000, 0x00000080, 0x00400000, 0x00401001,
0x00400081, 0x00001081, 0x00001080, 0x00000000,
0x00000080, 0x00400001, 0x00000001, 0x00400080,
0x00000000, 0x00400081, 0x00400080, 0x00001080,
0x00000081, 0x00001000, 0x00401081, 0x00400000,
0x00401080, 0x00000001, 0x00001001, 0x00401081,
0x00400001, 0x00401080, 0x00401000, 0x00001001},
{ /* nibble 7 */
0x08200020, 0x08208000, 0x00008020, 0x00000000,
0x08008000, 0x00200020, 0x08200000, 0x08208020,
0x00000020, 0x08000000, 0x00208000, 0x00008020,
0x00208020, 0x08008020, 0x08000020, 0x08200000,
0x00008000, 0x00208020, 0x00200020, 0x08008000,
0x08208020, 0x08000020, 0x00000000, 0x00208000,
0x08000000, 0x00200000, 0x08008020, 0x08200020,
0x00200000, 0x00008000, 0x08208000, 0x00000020,
0x00200000, 0x00008000, 0x08000020, 0x08208020,
0x00008020, 0x08000000, 0x00000000, 0x00208000,
0x08200020, 0x08008020, 0x08008000, 0x00200020,
0x08208000, 0x00000020, 0x00200020, 0x08008000,
0x08208020, 0x00200000, 0x08200000, 0x08000020,
0x00208000, 0x00008020, 0x08008020, 0x08200000,
0x00000020, 0x08208000, 0x00208020, 0x00000000,
0x08000000, 0x08200020, 0x00008000, 0x00208020}};
static const unsigned long des_skb[8][64] =
{
{ /* for C bits (numbered as per FIPS 46) 1 2 3 4 5 6 */
0x00000000, 0x00000010, 0x20000000, 0x20000010,
0x00010000, 0x00010010, 0x20010000, 0x20010010,
0x00000800, 0x00000810, 0x20000800, 0x20000810,
0x00010800, 0x00010810, 0x20010800, 0x20010810,
0x00000020, 0x00000030, 0x20000020, 0x20000030,
0x00010020, 0x00010030, 0x20010020, 0x20010030,
0x00000820, 0x00000830, 0x20000820, 0x20000830,
0x00010820, 0x00010830, 0x20010820, 0x20010830,
0x00080000, 0x00080010, 0x20080000, 0x20080010,
0x00090000, 0x00090010, 0x20090000, 0x20090010,
0x00080800, 0x00080810, 0x20080800, 0x20080810,
0x00090800, 0x00090810, 0x20090800, 0x20090810,
0x00080020, 0x00080030, 0x20080020, 0x20080030,
0x00090020, 0x00090030, 0x20090020, 0x20090030,
0x00080820, 0x00080830, 0x20080820, 0x20080830,
0x00090820, 0x00090830, 0x20090820, 0x20090830},
{ /* for C bits (numbered as per FIPS 46) 7 8 10 11 12 13 */
0x00000000, 0x02000000, 0x00002000, 0x02002000,
0x00200000, 0x02200000, 0x00202000, 0x02202000,
0x00000004, 0x02000004, 0x00002004, 0x02002004,
0x00200004, 0x02200004, 0x00202004, 0x02202004,
0x00000400, 0x02000400, 0x00002400, 0x02002400,
0x00200400, 0x02200400, 0x00202400, 0x02202400,
0x00000404, 0x02000404, 0x00002404, 0x02002404,
0x00200404, 0x02200404, 0x00202404, 0x02202404,
0x10000000, 0x12000000, 0x10002000, 0x12002000,
0x10200000, 0x12200000, 0x10202000, 0x12202000,
0x10000004, 0x12000004, 0x10002004, 0x12002004,
0x10200004, 0x12200004, 0x10202004, 0x12202004,
0x10000400, 0x12000400, 0x10002400, 0x12002400,
0x10200400, 0x12200400, 0x10202400, 0x12202400,
0x10000404, 0x12000404, 0x10002404, 0x12002404,
0x10200404, 0x12200404, 0x10202404, 0x12202404},
{ /* for C bits (numbered as per FIPS 46) 14 15 16 17 19 20 */
0x00000000, 0x00000001, 0x00040000, 0x00040001,
0x01000000, 0x01000001, 0x01040000, 0x01040001,
0x00000002, 0x00000003, 0x00040002, 0x00040003,
0x01000002, 0x01000003, 0x01040002, 0x01040003,
0x00000200, 0x00000201, 0x00040200, 0x00040201,
0x01000200, 0x01000201, 0x01040200, 0x01040201,
0x00000202, 0x00000203, 0x00040202, 0x00040203,
0x01000202, 0x01000203, 0x01040202, 0x01040203,
0x08000000, 0x08000001, 0x08040000, 0x08040001,
0x09000000, 0x09000001, 0x09040000, 0x09040001,
0x08000002, 0x08000003, 0x08040002, 0x08040003,
0x09000002, 0x09000003, 0x09040002, 0x09040003,
0x08000200, 0x08000201, 0x08040200, 0x08040201,
0x09000200, 0x09000201, 0x09040200, 0x09040201,
0x08000202, 0x08000203, 0x08040202, 0x08040203,
0x09000202, 0x09000203, 0x09040202, 0x09040203},
{ /* for C bits (numbered as per FIPS 46) 21 23 24 26 27 28 */
0x00000000, 0x00100000, 0x00000100, 0x00100100,
0x00000008, 0x00100008, 0x00000108, 0x00100108,
0x00001000, 0x00101000, 0x00001100, 0x00101100,
0x00001008, 0x00101008, 0x00001108, 0x00101108,
0x04000000, 0x04100000, 0x04000100, 0x04100100,
0x04000008, 0x04100008, 0x04000108, 0x04100108,
0x04001000, 0x04101000, 0x04001100, 0x04101100,
0x04001008, 0x04101008, 0x04001108, 0x04101108,
0x00020000, 0x00120000, 0x00020100, 0x00120100,
0x00020008, 0x00120008, 0x00020108, 0x00120108,
0x00021000, 0x00121000, 0x00021100, 0x00121100,
0x00021008, 0x00121008, 0x00021108, 0x00121108,
0x04020000, 0x04120000, 0x04020100, 0x04120100,
0x04020008, 0x04120008, 0x04020108, 0x04120108,
0x04021000, 0x04121000, 0x04021100, 0x04121100,
0x04021008, 0x04121008, 0x04021108, 0x04121108},
{ /* for D bits (numbered as per FIPS 46) 1 2 3 4 5 6 */
0x00000000, 0x10000000, 0x00010000, 0x10010000,
0x00000004, 0x10000004, 0x00010004, 0x10010004,
0x20000000, 0x30000000, 0x20010000, 0x30010000,
0x20000004, 0x30000004, 0x20010004, 0x30010004,
0x00100000, 0x10100000, 0x00110000, 0x10110000,
0x00100004, 0x10100004, 0x00110004, 0x10110004,
0x20100000, 0x30100000, 0x20110000, 0x30110000,
0x20100004, 0x30100004, 0x20110004, 0x30110004,
0x00001000, 0x10001000, 0x00011000, 0x10011000,
0x00001004, 0x10001004, 0x00011004, 0x10011004,
0x20001000, 0x30001000, 0x20011000, 0x30011000,
0x20001004, 0x30001004, 0x20011004, 0x30011004,
0x00101000, 0x10101000, 0x00111000, 0x10111000,
0x00101004, 0x10101004, 0x00111004, 0x10111004,
0x20101000, 0x30101000, 0x20111000, 0x30111000,
0x20101004, 0x30101004, 0x20111004, 0x30111004},
{ /* for D bits (numbered as per FIPS 46) 8 9 11 12 13 14 */
0x00000000, 0x08000000, 0x00000008, 0x08000008,
0x00000400, 0x08000400, 0x00000408, 0x08000408,
0x00020000, 0x08020000, 0x00020008, 0x08020008,
0x00020400, 0x08020400, 0x00020408, 0x08020408,
0x00000001, 0x08000001, 0x00000009, 0x08000009,
0x00000401, 0x08000401, 0x00000409, 0x08000409,
0x00020001, 0x08020001, 0x00020009, 0x08020009,
0x00020401, 0x08020401, 0x00020409, 0x08020409,
0x02000000, 0x0A000000, 0x02000008, 0x0A000008,
0x02000400, 0x0A000400, 0x02000408, 0x0A000408,
0x02020000, 0x0A020000, 0x02020008, 0x0A020008,
0x02020400, 0x0A020400, 0x02020408, 0x0A020408,
0x02000001, 0x0A000001, 0x02000009, 0x0A000009,
0x02000401, 0x0A000401, 0x02000409, 0x0A000409,
0x02020001, 0x0A020001, 0x02020009, 0x0A020009,
0x02020401, 0x0A020401, 0x02020409, 0x0A020409},
{ /* for D bits (numbered as per FIPS 46) 16 17 18 19 20 21 */
0x00000000, 0x00000100, 0x00080000, 0x00080100,
0x01000000, 0x01000100, 0x01080000, 0x01080100,
0x00000010, 0x00000110, 0x00080010, 0x00080110,
0x01000010, 0x01000110, 0x01080010, 0x01080110,
0x00200000, 0x00200100, 0x00280000, 0x00280100,
0x01200000, 0x01200100, 0x01280000, 0x01280100,
0x00200010, 0x00200110, 0x00280010, 0x00280110,
0x01200010, 0x01200110, 0x01280010, 0x01280110,
0x00000200, 0x00000300, 0x00080200, 0x00080300,
0x01000200, 0x01000300, 0x01080200, 0x01080300,
0x00000210, 0x00000310, 0x00080210, 0x00080310,
0x01000210, 0x01000310, 0x01080210, 0x01080310,
0x00200200, 0x00200300, 0x00280200, 0x00280300,
0x01200200, 0x01200300, 0x01280200, 0x01280300,
0x00200210, 0x00200310, 0x00280210, 0x00280310,
0x01200210, 0x01200310, 0x01280210, 0x01280310},
{ /* for D bits (numbered as per FIPS 46) 22 23 24 25 27 28 */
0x00000000, 0x04000000, 0x00040000, 0x04040000,
0x00000002, 0x04000002, 0x00040002, 0x04040002,
0x00002000, 0x04002000, 0x00042000, 0x04042000,
0x00002002, 0x04002002, 0x00042002, 0x04042002,
0x00000020, 0x04000020, 0x00040020, 0x04040020,
0x00000022, 0x04000022, 0x00040022, 0x04040022,
0x00002020, 0x04002020, 0x00042020, 0x04042020,
0x00002022, 0x04002022, 0x00042022, 0x04042022,
0x00000800, 0x04000800, 0x00040800, 0x04040800,
0x00000802, 0x04000802, 0x00040802, 0x04040802,
0x00002800, 0x04002800, 0x00042800, 0x04042800,
0x00002802, 0x04002802, 0x00042802, 0x04042802,
0x00000820, 0x04000820, 0x00040820, 0x04040820,
0x00000822, 0x04000822, 0x00040822, 0x04040822,
0x00002820, 0x04002820, 0x00042820, 0x04042820,
0x00002822, 0x04002822, 0x00042822, 0x04042822},
};
#define c2l(c,l) (l =((unsigned long)(*((c)++))) , \
l|=((unsigned long)(*((c)++)))<< 8, \
l|=((unsigned long)(*((c)++)))<<16, \
l|=((unsigned long)(*((c)++)))<<24)
#define l2c(l,c) (*((c)++)=(unsigned char)(((l) )&0xff), \
*((c)++)=(unsigned char)(((l)>> 8)&0xff), \
*((c)++)=(unsigned char)(((l)>>16)&0xff), \
*((c)++)=(unsigned char)(((l)>>24)&0xff))
/*
* IP and FP
* The problem is more of a geometric problem that random bit fiddling.
* 0 1 2 3 4 5 6 7 62 54 46 38 30 22 14 6
* 8 9 10 11 12 13 14 15 60 52 44 36 28 20 12 4
* 16 17 18 19 20 21 22 23 58 50 42 34 26 18 10 2
* 24 25 26 27 28 29 30 31 to 56 48 40 32 24 16 8 0
*
* 32 33 34 35 36 37 38 39 63 55 47 39 31 23 15 7
* 40 41 42 43 44 45 46 47 61 53 45 37 29 21 13 5
* 48 49 50 51 52 53 54 55 59 51 43 35 27 19 11 3
* 56 57 58 59 60 61 62 63 57 49 41 33 25 17 9 1
*
* The output has been subject to swaps of the form
* 0 1 -> 3 1 but the odd and even bits have been put into
* 2 3 2 0
* different words. The main trick is to remember that
* t=((l>>size)^r)&(mask);
* r^=t;
* l^=(t<<size);
* can be used to swap and move bits between words.
*
* So l = 0 1 2 3 r = 16 17 18 19
* 4 5 6 7 20 21 22 23
* 8 9 10 11 24 25 26 27
* 12 13 14 15 28 29 30 31
* becomes (for size == 2 and mask == 0x3333)
* t = 2^16 3^17 -- -- l = 0 1 16 17 r = 2 3 18 19
* 6^20 7^21 -- -- 4 5 20 21 6 7 22 23
* 10^24 11^25 -- -- 8 9 24 25 10 11 24 25
* 14^28 15^29 -- -- 12 13 28 29 14 15 28 29
*
* Thanks for hints from Richard Outerbridge - he told me IP&FP
* could be done in 15 xor, 10 shifts and 5 ands.
* When I finally started to think of the problem in 2D
* I first got ~42 operations without xors. When I remembered
* how to use xors :-) I got it to its final state.
*/
#define PERM_OP(a,b,t,n,m) ((t)=((((a)>>(n))^(b))&(m)),\
(b)^=(t),\
(a)^=((t)<<(n)))
#define HPERM_OP(a,t,n,m) ((t)=((((a)<<(16-(n)))^(a))&(m)),\
(a)=(a)^(t)^(t>>(16-(n))))
/* The changes to this macro may help or hinder, depending on the
* compiler and the achitecture. gcc2 always seems to do well :-).
* Inspired by Dana How <how@isl.stanford.edu>
* DO NOT use the alternative version on machines with 8 byte longs.
*/
#ifdef ALT_ECB
#define D_ENCRYPT(L,R,S) \
u=((R^s[S ])<<2); \
t= R^s[S+1]; \
t=((t>>2)+(t<<30)); \
L^= \
*(const unsigned long *)(des_SP+0x0100+((t )&0xfc))+ \
*(const unsigned long *)(des_SP+0x0300+((t>> 8)&0xfc))+ \
*(const unsigned long *)(des_SP+0x0500+((t>>16)&0xfc))+ \
*(const unsigned long *)(des_SP+0x0700+((t>>24)&0xfc))+ \
*(const unsigned long *)(des_SP+ ((u )&0xfc))+ \
*(const unsigned long *)(des_SP+0x0200+((u>> 8)&0xfc))+ \
*(const unsigned long *)(des_SP+0x0400+((u>>16)&0xfc))+ \
*(const unsigned long *)(des_SP+0x0600+((u>>24)&0xfc));
#else /* original version */
#define D_ENCRYPT(L,R,S) \
u=(R^s[S ]); \
t=R^s[S+1]; \
t=((t>>4)+(t<<28)); \
L^= des_SPtrans[1][(t )&0x3f]| \
des_SPtrans[3][(t>> 8)&0x3f]| \
des_SPtrans[5][(t>>16)&0x3f]| \
des_SPtrans[7][(t>>24)&0x3f]| \
des_SPtrans[0][(u )&0x3f]| \
des_SPtrans[2][(u>> 8)&0x3f]| \
des_SPtrans[4][(u>>16)&0x3f]| \
des_SPtrans[6][(u>>24)&0x3f];
#endif
#define ITERATIONS 16
static const char shifts2[16] =
{0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0};
static void des_set_key (char *, unsigned long *) internal_function;
static void des_encrypt (unsigned long *, unsigned long *, int)
internal_function;
int _des_crypt (char *, unsigned, struct desparams *);
static void
internal_function
des_set_key (char *key, unsigned long *schedule)
{
register unsigned long c, d, t, s;
register unsigned char *in;
register unsigned long *k;
register int i;
k = (unsigned long *) schedule;
in = (unsigned char *) key;
c2l (in, c);
c2l (in, d);
/* I now do it in 47 simple operations :-)
* Thanks to John Fletcher (john_fletcher@lccmail.ocf.llnl.gov)
* for the inspiration. :-) */
PERM_OP (d, c, t, 4, 0x0f0f0f0f);
HPERM_OP (c, t, -2, 0xcccc0000);
HPERM_OP (d, t, -2, 0xcccc0000);
PERM_OP (d, c, t, 1, 0x55555555);
PERM_OP (c, d, t, 8, 0x00ff00ff);
PERM_OP (d, c, t, 1, 0x55555555);
d = (((d & 0x000000ff) << 16) | (d & 0x0000ff00) |
((d & 0x00ff0000) >> 16) | ((c & 0xf0000000) >> 4));
c &= 0x0fffffff;
for (i = 0; i < ITERATIONS; i++)
{
if (shifts2[i])
{
c = ((c >> 2) | (c << 26));
d = ((d >> 2) | (d << 26));
}
else
{
c = ((c >> 1) | (c << 27));
d = ((d >> 1) | (d << 27));
}
c &= 0x0fffffff;
d &= 0x0fffffff;
/* could be a few less shifts but I am to lazy at this
* point in time to investigate */
s = des_skb[0][(c) & 0x3f] |
des_skb[1][((c >> 6) & 0x03) | ((c >> 7) & 0x3c)] |
des_skb[2][((c >> 13) & 0x0f) | ((c >> 14) & 0x30)] |
des_skb[3][((c >> 20) & 0x01) | ((c >> 21) & 0x06) | ((c >> 22) & 0x38)];
t = des_skb[4][(d) & 0x3f] |
des_skb[5][((d >> 7) & 0x03) | ((d >> 8) & 0x3c)] |
des_skb[6][(d >> 15) & 0x3f] |
des_skb[7][((d >> 21) & 0x0f) | ((d >> 22) & 0x30)];
/* table contained 0213 4657 */
*(k++) = ((t << 16) | (s & 0x0000ffff)) & 0xffffffff;
s = ((s >> 16) | (t & 0xffff0000));
s = (s << 4) | (s >> 28);
*(k++) = s & 0xffffffff;
}
}
static void
internal_function
des_encrypt (unsigned long *buf, unsigned long *schedule, int encrypt)
{
register unsigned long l, r, t, u;
#ifdef ALT_ECB
register const unsigned char *des_SP = (const unsigned char *) des_SPtrans;
#endif
register int i;
register unsigned long *s;
l = buf[0];
r = buf[1];
/* do IP */
PERM_OP (r, l, t, 4, 0x0f0f0f0f);
PERM_OP (l, r, t, 16, 0x0000ffff);
PERM_OP (r, l, t, 2, 0x33333333);
PERM_OP (l, r, t, 8, 0x00ff00ff);
PERM_OP (r, l, t, 1, 0x55555555);
/* r and l are reversed - remember that :-) - fix
* it in the next step */
/* Things have been modified so that the initial rotate is
* done outside the loop. This required the
* des_SPtrans values in sp.h to be rotated 1 bit to the right.
* One perl script later and things have a 5% speed up on a sparc2.
* Thanks to Richard Outerbridge <71755.204@CompuServe.COM>
* for pointing this out. */
t = (r << 1) | (r >> 31);
r = (l << 1) | (l >> 31);
l = t;
/* clear the top bits on machines with 8byte longs */
l &= 0xffffffff;
r &= 0xffffffff;
s = (unsigned long *) schedule;
/* I don't know if it is worth the effort of loop unrolling the
* inner loop */
if (encrypt)
{
for (i = 0; i < 32; i += 4)
{
D_ENCRYPT (l, r, i + 0); /* 1 */
D_ENCRYPT (r, l, i + 2); /* 2 */
}
}
else
{
for (i = 30; i > 0; i -= 4)
{
D_ENCRYPT (l, r, i - 0); /* 16 */
D_ENCRYPT (r, l, i - 2); /* 15 */
}
}
l = (l >> 1) | (l << 31);
r = (r >> 1) | (r << 31);
/* clear the top bits on machines with 8byte longs */
l &= 0xffffffff;
r &= 0xffffffff;
/* swap l and r
* we will not do the swap so just remember they are
* reversed for the rest of the subroutine
* luckily FP fixes this problem :-) */
PERM_OP (r, l, t, 1, 0x55555555);
PERM_OP (l, r, t, 8, 0x00ff00ff);
PERM_OP (r, l, t, 2, 0x33333333);
PERM_OP (l, r, t, 16, 0x0000ffff);
PERM_OP (r, l, t, 4, 0x0f0f0f0f);
buf[0] = l;
buf[1] = r;
l = r = t = u = 0;
}
int
_des_crypt (char *buf, unsigned len, struct desparams *desp)
{
unsigned long schedule[32];
register unsigned long tin0, tin1;
register unsigned long tout0, tout1, xor0, xor1;
register unsigned char *in, *out;
unsigned long tbuf[2];
unsigned char *iv, *oiv;
int cbc_mode;
cbc_mode = (desp->des_mode == CBC) ? 1 : 0;
in = (unsigned char *) buf;
out = (unsigned char *) buf;
oiv = iv = (unsigned char *) desp->des_ivec;
des_set_key (desp->des_key, schedule);
tin0 = tin1 = 0; /* For GCC */
if (desp->des_dir == ENCRYPT)
{
c2l (iv, tout0);
c2l (iv, tout1);
for (; len > 0; len -= 8)
{
c2l (in, tin0);
c2l (in, tin1);
if (cbc_mode)
{
tin0 ^= tout0;
tin1 ^= tout1;
}
tbuf[0] = tin0;
tbuf[1] = tin1;
des_encrypt (tbuf, schedule, 1);
tout0 = tbuf[0];
tout1 = tbuf[1];
l2c (tout0, out);
l2c (tout1, out);
}
l2c (tout0, oiv);
l2c (tout1, oiv);
}
else
{
c2l (iv, xor0);
c2l (iv, xor1);
for (; len > 0; len -= 8)
{
c2l (in, tin0);
c2l (in, tin1);
tbuf[0] = tin0;
tbuf[1] = tin1;
des_encrypt (tbuf, schedule, 0);
if (cbc_mode)
{
tout0 = tbuf[0] ^ xor0;
tout1 = tbuf[1] ^ xor1;
xor0 = tin0;
xor1 = tin1;
}
else
{
tout0 = tbuf[0];
tout1 = tbuf[1];
}
l2c (tout0, out);
l2c (tout1, out);
}
l2c (tin0, oiv);
l2c (tin1, oiv);
}
tin0 = tin1 = tout0 = tout1 = xor0 = xor1 = 0;
tbuf[0] = tbuf[1] = 0;
__bzero (schedule, sizeof (schedule));
return (1);
}

View File

@ -0,0 +1,25 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 1992, 1993, 1996 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; see the file COPYING.LIB. If not,
* write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*
* @(#)patchlevel.h 1.13 9/10/96
*
*/
#define PATCHLEVEL "UFC-crypt, patchlevel 1e, @(#)patchlevel.h 1.13 9/10/96"

View File

@ -0,0 +1,29 @@
/* Types for UFC-crypt.
Copyright (C) 1998 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If not,
write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
#include <stdint.h>
typedef uint_fast32_t ufc_long;
typedef uint64_t long64;
typedef uint32_t long32;
#if UINT_FAST32_MAX == UINT_FAST64_MAX
# define _UFC_64_
#else
# define _UFC_32_
#endif

26
crypt/testpass.c.texi Normal file
View File

@ -0,0 +1,26 @@
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <crypt.h>
int
main(void)
@{
/* @r{Hashed form of "GNU libc manual".} */
const char *const pass = "$1$/iSaq7rB$EoUw5jJPPvAPECNaaWzMK/";
char *result;
int ok;
@group
/* @r{Read in the user's password and encrypt it,
passing the expected password in as the salt.} */
result = crypt(getpass("Password:"), pass);
@end group
/* @r{Test the result.} */
ok = strcmp (result, pass) == 0;
puts(ok ? "Access granted." : "Access denied.");
return ok ? 0 : 1;
@}

55
crypt/ufc.c Normal file
View File

@ -0,0 +1,55 @@
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991, 1992, 1993, 1996 Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the Free
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* @(#)ufc.c 2.7 9/10/96
*
* Stub main program for debugging
* and benchmarking.
*
*/
#include <stdio.h>
char *crypt();
main(argc, argv)
int argc;
char **argv;
{ char *s;
unsigned long i,iterations;
if(argc != 2) {
fprintf(stderr, "usage: ufc iterations\n");
exit(1);
}
argv++;
iterations = atoi(*argv);
printf("ufc: running %d iterations\n", iterations);
for(i=0; i<iterations; i++)
s=crypt("foob","ar");
if(strcmp(s, "arlEKn0OzVJn.") == 0)
printf("OK\n");
else {
printf("wrong result: %s!!\n", s);
exit(1);
}
exit(0);
}

View File

@ -13,7 +13,7 @@ if test -n "$sysheaders"; then
fi
echo $ac_n "checking installed Linux kernel header files""... $ac_c" 1>&6
echo "configure:16: checking installed Linux kernel header files" >&5
if eval "test \"\${libc_cv_linux2010+set}\" = set"; then
if eval "test \"`echo '$''{'libc_cv_linux2010'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
@ -107,21 +107,11 @@ if test "$prefix" = "/usr" -o "$prefix" = "/usr/"; then
libc_cv_rootsbindir="/sbin"
fi
# Under Linux the LinuxThreads and crypt add-on should be available.
# Under Linux the LinuxThreads add-on should be available.
case $add_ons in
# Both are available. Good.
*linuxthreads*crypt* | *crypt*linuxthreads*)
message=
;;
*linuxthreads*)
message="\
*** WARNING:
*** Are you sure you do not want to use the \`crypt' add-on?"
;;
*crypt*)
message="\
*** WARNING:
*** Are you sure you do not want to use the \`linuxthread' add-on?"
message=
;;
*)
message="\
@ -133,11 +123,11 @@ esac
if test "$message"; then
if test $enable_sanity = yes; then
echo "\
*** You should not compile the GNU libc without the \`linuxthreads' and
*** \`crypt' add-on. Not using them risks to be incompatible with the
*** libraries of other systems. Consider getting the add-ons and restart
*** You should not compile the GNU libc without the \`linuxthreads'
*** add-on. Not using them risks being incompatible with the
*** libraries of other systems. Consider getting the add-on and restarting
*** the configuration.
*** If you really mean to avoid those add-ons run configure again, now
*** If you really mean to not use this add-on, run configure again
*** using the extra parameter \`--disable-sanity-checks'."
exit 1
else
@ -172,7 +162,7 @@ if test $host = $build; then
ac_prefix=$ac_default_prefix
fi
echo $ac_n "checking for symlinks in ${ac_prefix}/include""... $ac_c" 1>&6
echo "configure:176: checking for symlinks in ${ac_prefix}/include" >&5
echo "configure:166: checking for symlinks in ${ac_prefix}/include" >&5
ac_message=
if test -L ${ac_prefix}/include/net; then
ac_message="$ac_message

View File

@ -78,21 +78,11 @@ if test "$prefix" = "/usr" -o "$prefix" = "/usr/"; then
libc_cv_rootsbindir="/sbin"
fi
# Under Linux the LinuxThreads and crypt add-on should be available.
# Under Linux the LinuxThreads add-on should be available.
case $add_ons in
# Both are available. Good.
*linuxthreads*crypt* | *crypt*linuxthreads*)
message=
;;
*linuxthreads*)
message="\
*** WARNING:
*** Are you sure you do not want to use the \`crypt' add-on?"
;;
*crypt*)
message="\
*** WARNING:
*** Are you sure you do not want to use the \`linuxthread' add-on?"
message=
;;
*)
message="\
@ -104,11 +94,11 @@ esac
if test "$message"; then
if test $enable_sanity = yes; then
echo "\
*** You should not compile the GNU libc without the \`linuxthreads' and
*** \`crypt' add-on. Not using them risks to be incompatible with the
*** libraries of other systems. Consider getting the add-ons and restart
*** You should not compile the GNU libc without the \`linuxthreads'
*** add-on. Not using them risks being incompatible with the
*** libraries of other systems. Consider getting the add-on and restarting
*** the configuration.
*** If you really mean to avoid those add-ons run configure again, now
*** If you really mean to not use this add-on, run configure again
*** using the extra parameter \`--disable-sanity-checks'."
exit 1
else