Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Underscores in MD5 salts rejected #105

Closed
mzealey opened this issue Jun 26, 2020 · 16 comments · Fixed by #106
Closed

Underscores in MD5 salts rejected #105

mzealey opened this issue Jun 26, 2020 · 16 comments · Fixed by #106
Assignees
Labels
bug Confirmed to be a bug in libxcrypt. documentation Primarily an issue with the documentation.

Comments

@mzealey
Copy link

mzealey commented Jun 26, 2020

So, on a glibc-2.17 based Centos 7 system the following happens:

$ perl -E 'say crypt($ARGV[0], $ARGV[1])' 'foo' '$1$OiaynUa_$AEUnQiyEzpgFp42qhmUlX1'  
$1$OiaynUa_$UKu.5CDrnTktg39GKrZpP0

But on ubuntu (libxcrypt 4.4.10-10ubuntu4):

$ perl -E 'say crypt($ARGV[0], $ARGV[1])' 'foo' '$1$OiaynUa_$AEUnQiyEzpgFp42qhmUlX1'  
*0

and on centos 8 (libxcrypt-devel-4.1.1-4.el8), it produces an empty string and I think an 'invalid argument' message.

If this library is meant to be backwards-compatible it should presumably emulate the behaviour of the centos 7 algo? I don't know much about the salt, but I can't see that substituting the underscroe with something else is going to replicate it correctly?

@besser82
Copy link
Owner

besser82 commented Jun 26, 2020

Hello,

and thanks for your question.

Having an underscore character _ in the salt portion violates the Modular Crypt Format (MFC) string.

Let me explain a bit:

An MFC string is formatted as ${algo_id}[[$]{rounds_or_settings}]${salt}[${hash}]. Although there is no official technical specification, it is agreed upon all characters used in such a string must be valid BASE64 encoded: [a-zA-Z0-9./].

At the time the hash implementations of glibc's libcrypt have been written, considerations have been users of the crypt() function would only pass trusted and/or validated input strings into it. Considerations and concerns about untrusted and/or invalid inputs came up a decade or so later.

Sadly the libcrypt in glibc is not that actively developed, I mean it is maintained, but does not that frequent development as other parts of glibc do. For this (and some other reasons) some people (including me) came up to revive and vastly improve libxcrypt as a (drop in) replacement.

From what I can see here: The behaviour you describe is a bug in glibc's libcrypt which has been fixed for its implementation of descrypt hash several years ago, which made that hash function accept any character.

I conclude libxcrypt has the correct behaviour of refusing any MFC string input that is not valid BASE64 encoded, while the behaviour of glibc libcrypt is faulty.

@zackw Do you agree with me?

@besser82 besser82 self-assigned this Jun 26, 2020
@solardiz
Copy link
Collaborator

@besser82 You didn't ask me, but FWIW I would have treated this rejection of historically accepted unusual (not even invalid) md5crypt salts as a libxcrypt bug.

Like you say, "there is no official technical specification" on what characters the salt string may contain, except with hashes like bcrypt and descrypt where the salt is decoded before being used.

(I also wouldn't have changed glibc's descrypt to reject invalid salts like was done in that commit you reference. Instead, we could have enhanced libxcrypt's FreeSec to handle invalid salts in the same way that old glibc's UFC crypt handled them prior to that commit. I have a revision of FreeSec implementing that. However, now that glibc already went the other way, I am not sure it's a good idea to reintroduce that for descrypt.)

@mzealey
Copy link
Author

mzealey commented Jun 26, 2020

I agree that the behaviour here is in terms of rejecting non-base64 characters is correct according to the spec (whether written down or generally understood), however the aim of this project is to be a drop-in replacement for glibc's libcrypt then this is not happening here. Centos 6 & 7 glibc have this behaviour so it would seem to be a fairly mainstream 'bug' - perhaps 'feature' or 'implementation edge case' would be a better description of it?

@mzealey
Copy link
Author

mzealey commented Jun 26, 2020

Note also that these password salts were generated by older cpanel versions (they now use sha512 or so by default), however many of these hashes are still around. cpanel does not currently support centos 8 so most hosters are using centos 7. However I can imagine this bug being fairly widely seen once the cpanel centos 8 upgrade is available.

@besser82
Copy link
Owner

Let me setup a RHEL 7 VM and do some tests how sha256crypt and sha512crypt act upon unexpected characters in the salt… I will adjust libxcrypt then to behave the same way for the hash functions in question.

@solardiz Sorry for not asking you about this, too. I know you are a quiet busy person, and didn't want to bother you in the first place. Good to know I can explicitly put you in the loop for other reports like this also.
BTW, the change to descrypt in glibc's libcrypt had been make around mid. 2012 or so; long before libxcrypt was meant to be a real drop-in replacement.

@besser82 besser82 added bug Confirmed to be a bug in libxcrypt. documentation Primarily an issue with the documentation. and removed false positive labels Jun 26, 2020
@besser82
Copy link
Owner

Okay, it seems libcrypt on RHEL / CentOS 7 takes any chars (non-printable as well as printable) as a valid salt for {md5,sha256,sha512}crypt. I'm going to release a patch for libxcrypt within the next few days.

@solardiz
Copy link
Collaborator

No problem about not asking me - I didn't mean to complain.

Maybe it makes sense to deliberately reject $ and : and \n inside salt strings for these hashes. For $, it can simply be not supporting it rather than needing to reject it explicitly, depending on how the preceding parsing works.

besser82 added a commit that referenced this issue Jun 27, 2020
It turned out, that some implementations of the md5crypt,
sha256crypt, and sha512crypt hashing methods allow any UTF-8
character to be present in the salt string.  This applies to
the implementations of these hasing methods present in the
libcrypt library supplied by glibc.

Some server applications, which are certified to run on major
enterprise Linux distributions, cPanel for instance, make use
of this 'feature' when computing salts for their internal
user passwords.

For this particular reasons we decided to add a build-time
configurable option to libxcrypt to make the md5crypt,
sha256crypt, and sha512crypt hash methods accept salt strings,
that have been crafted in such a way.  The only not allowed
exceptions for our permisseve implementation are the dollar
sign ($) character, which seperates the sections of a Modular
Crypt Format string, the colon (:) character, which seperates
the sections of the Unix user table, the new-line (\n) character,
and the CR (\r) character.

Also adapt the badsalt test to know about this behaviour, when
building libxcrypt with this configure option.
@besser82
Copy link
Owner

@mzealey I hope my solution in #106 works for you.

@mzealey
Copy link
Author

mzealey commented Jun 27, 2020

Looks great, thanks for your hard work!

@besser82
Copy link
Owner

np, you're welcome!

@rfc1036
Copy link

rfc1036 commented Jun 27, 2020

Did you check if all the other characters actually need to be accepted because something is really using them as salt or if _ is enough? Since ~everybody will enable this then maybe it's a good idea to be conservative and start from just allowing the characters which we know that are being used.

besser82 added a commit that referenced this issue Jun 28, 2020
It turned out, all other existing implementations of the md5crypt,
sha256crypt, and sha512crypt hashing methods allow any printable
ASCII character to be present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the following character, which
serve special purposes in the Unix shadow file:

  * '!' --> User account is locked.
  * '*' --> No initial password set for this user.
  * ':' --> Seperates the different columns.
besser82 added a commit that referenced this issue Jun 28, 2020
It turned out, all other existing implementations of the md5crypt,
sha256crypt, and sha512crypt hashing methods allow any printable
ASCII character to be present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the following characters,
which serve special purposes in the Unix shadow file:

  * '!' --> User account is locked.
  * '*' --> No initial password set for this user.
  * ':' --> Seperates the different columns.
besser82 added a commit that referenced this issue Jun 28, 2020
It turned out, all other existing implementations of the md5crypt,
sha256crypt, and sha512crypt hashing methods allow any printable
ASCII character to be present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.
besser82 added a commit that referenced this issue Jun 28, 2020
It turned out, all other existing implementations of the md5crypt,
sha256crypt, and sha512crypt hashing methods allow any printable
ASCII character to be present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.
besser82 added a commit that referenced this issue Aug 13, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.

Fixes #105
besser82 added a commit that referenced this issue Aug 13, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.

Fixes #105
besser82 added a commit that referenced this issue Aug 13, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.

Fixes #105
besser82 added a commit that referenced this issue Aug 18, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.

Fixes #105
besser82 added a commit that referenced this issue Aug 18, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt to expect this difference in behaviour from
the other hashing methods available in libxcrypt.

Fixes #105
besser82 added a commit that referenced this issue Aug 18, 2020
All other existing implementations of the md5crypt, sha256crypt,
and sha512crypt hashing methods allow any ASCII character to be
present in the salt string.

We changed our implementation of these hash methods to be compliant
with the general behaviour, except for the colon ':' character,
which serves a special purpose in the Unix shadow file.

Also adapt test/badsalt.c to expect the colon characters is an invalid
salt character for all hashing methods.

Fixes #105
@btwe
Copy link

btwe commented Jan 21, 2021

Pfew, this one lead to an erratic error during user authentication of our ldap users. The hashes were generated some time ago with another lib for >6.5k users (rehashing is no option). And some few of them have unsupported chars in their salt (+).
This issue occured after upgrading to centos8. Centos 8.3 still has the unpatched version in their repos. Could you please push them urgently to update libxcrypt in their next minor-release?

zackw added a commit that referenced this issue Jul 3, 2021
Test patterns are now mostly generated rather than manually coded into
a big table.  Not reading past the end of the “setting” part of the
string is tested more thoroughly (this would have caught the sunmd5 $$
bug if it had been available at the time).  Test logs are tidier.

This change exposed a lacuna in handling of text beyond the end of
the setting: we were not rejecting e.g. ‘$3$__not_used_:c809a450df09a3’
because nthash ignores everything after ‘$3$’ and nothing else detects
the colon.  Now setting strings containing ‘:’ or a newline are
rejected in generic code.  (I would like to expand this to match the
rule laid out in crypt(5),

    Hashed passphrases are always entirely printable ASCII, and do not
    contain any whitespace or the characters ‘:’, ‘;’, ‘*’, ‘!’, or
    ‘\’.  (These characters are used as delimiters and special markers
    in the passwd(5) and shadow(5) files.)

but I am worried that that will trip up people with stored passphrases
with weird salt, like in <#105>,
so I’m not doing it yet.
@OleHolmNielsen
Copy link

We have been bitten by the issue of user logins being rejected on CentOS 8.4 (and all other EL8 variants) as well as FC34, which was caused by the user's SHA512 password hash having one or more "+" characters in the salt. Such SHA512 hashes are generated by the university's central IT service on Windows systems, and such hashes ought to be valid according to libxcrypt's crypt(5) man-page:

Hashed passphrases are always entirely printable ASCII, and do not contain any whitespace or the characters ‘:’, ‘;’, ‘*’, ‘!’, or ‘\’.

One is lead to believe that almost any ASCII character is OK in the salt for SHA512 and other hashes, but that is unfortunately not true with the libxcrypt implementation in EL8. Quoting the comment above (June 26, 2020):

Although there is no official technical specification, it is agreed upon all characters used in such a string must be valid BASE64 encoded: [a-zA-Z0-9./].

Question: Could you please change the crypt(5) man-page so it becomes obvious that only the characters [a-zA-Z0-9./] are permitted in salts?

I note that there is in fact an official technical specification of this: The POSIX.1-2017 standard declares in
https://pubs.opengroup.org/onlinepubs/9699919799.2018edition/functions/crypt.html that only the following characters may be used in the salt:

The salt argument shall be a string of at least two bytes in length not including the null character chosen from the set:
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
0 1 2 3 4 5 6 7 8 9 . / 

So it seems that we are on a solid standards-based ground. We only need the documentation to be consistent with the libxcrypt implementation.

@OleHolmNielsen
Copy link

I have a trivial test code for the crypt() function on a CentOS 8.4 system:

/* compile: /usr/bin/gcc -lcrypt -o passwd-sha512 passwd-sha512.c */
/* usage: passwd-sha512 <password> <salt (16 chars max)> */

#define _XOPEN_SOURCE
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <crypt.h>

int main(int argc, char *argv[]) {
  if ( argc < 3 || (int) strlen(argv[2]) > 16 ) {
    printf("usage: %s password salt\n", argv[0]);
    printf("--salt must not larger than 16 characters\n");
    return 0;
  }

  char salt[21];
  sprintf(salt, "$6$%s$", argv[2]);

  printf("%s\n", crypt((char*) argv[1], (char*) salt));
  return 0;
}

When executing this code we get a core dump when non-standard characters are used in the salt:

$ ./passwd-sha512  abcd abcd
$6$abcd$bT9Tu4itxmzGnycF0Rp8CgywJpZsvlNyak/XXgqhZQlP.4o6xJdBos7vwBaUb4UL.wgj1FAWTzBSeVagy/hMA0
$ ./passwd-sha512  abcd abcd+
Segmentation fault (core dumped)

CentOS 8.4 has a libxcrypt-4.1.1-4.el8.x86_64 RPM.

Interestingly, the code does not core dump on CentOS 8 Stream:

$ ./passwd-sha512  abcd abcd+
$6$abcd+$Ey10fMRkH3D.6uK9MjTdRKxxm6TFE1EjG13.GeZ5ua0o8XByuiYia7IffPGR9g9LYado.P5fcn9gejkan2Uv./

with a slightly newer libxcrypt-4.1.1-6.el8.x86_64 RPM.

@zackw
Copy link
Collaborator

zackw commented Jul 7, 2021

@OleHolmNielsen First off, I'm pretty sure your test program segfaults because crypt() is returning NULL. Can you confirm?

We have been allowing + in salts since b2b813a; I believe the oldest upstream version with this change is 4.4.17. Looking at the change log on https://centos.pkgs.org/8-stream/centos-baseos-x86_64/libxcrypt-4.1.1-6.el8.x86_64.rpm.html, I think CentOS backported that change in their 4.1.1-5. I don't know anything about how or when Stream packages propagate into numbered releases of CentOS, you'll need to take that up with them.

Let's move further discussion of what punctuation should be accepted in salts to #135.

@OleHolmNielsen
Copy link

I confirm that crypt() returns NULL on CentOS 8.4. I added code to display the error:

$ ./passwd-sha512 aaaa aaaa+
crypt returned NULL with errno 22 Invalid argument

The same binary works on CentOS 8 Stream:

$  ./passwd-sha512 aaaa aaaa+
$6$aaaa+$jBuvbAFjg5D3jgr1qnPHjC5N1LjcpfbE/fGaQqHGpQxF.Wwl3zT2GGkZrsro2Xlsv1QG0d7GSWq5C1n81fT2n1

So CentOS and RHEL 8.4 don't like "+" in the salt strings, whereas CentOS 8 Stream accepts "+" happily.

besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 5, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
besser82 added a commit that referenced this issue Aug 8, 2021
However, our generic code currently only enforced the absence of
‘:’ and newline.  Prior to 2112d2b, there was no generic check at
all.  Prior to b2b813a, some but not all hashing methods implemented
much more restrictive rules (allowing only their own base64 alphabet
in the salt part of a setting);  these were found to conflict with
existing salts (see #105).

The setting-parsing code in each hashing method is ad hoc and
difficult to audit for what syntax it actually accepts; there
might be other quirks hiding.

The change in this commit enforces salt strings to not contain
characters that are present in the ‘badsalt_chars’ array.

The ‘crypt_checksalt’ function now also validates the passed salt
string for the absense of such invalid characters.

For now we consider the following characters to be valid for any
salt string in the generic check:

0 1 2 3 4 5 6 7 8 9
a b c d e f g h i j k l m n o p q r s t u v w x y z
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
. / + - _ = , $ " # % & ' ( ) < > ? @ [ ] ^ ` { | } ~

Fixes #135.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Confirmed to be a bug in libxcrypt. documentation Primarily an issue with the documentation.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

7 participants