mirror of
https://github.com/php/php-src.git
synced 2025-08-15 21:48:51 +02:00
mb_detect_encoding will not return non-encodings
Among the text encodings supported by mbstring are several which are not really 'text encodings'. These include Base64, QPrint, UUencode, HTML entities, '7 bit', and '8 bit'. Rather than providing an explicit list of text encodings which they are interested in, users may pass the output of mb_list_encodings to mb_detect_encoding. Since Base64, QPrint, and so on are included in the output of mb_list_encodings, mb_detect_encoding can return one of these as its 'detected encoding' (and in fact, this often happens). Before mb_detect_encoding was enhanced so it could detect any of the supported text encodings, this did not happen, and it is never desired.
This commit is contained in:
parent
28b346bc06
commit
a2bc57e0e5
4 changed files with 29 additions and 2 deletions
|
@ -2664,6 +2664,23 @@ PHP_FUNCTION(mb_strtolower)
|
|||
}
|
||||
/* }}} */
|
||||
|
||||
static void remove_non_encodings_from_elist(const mbfl_encoding **elist, size_t *size)
|
||||
{
|
||||
/* mbstring supports some 'text encodings' which aren't really text encodings
|
||||
* at all, but really 'byte encodings', like Base64, QPrint, and so on.
|
||||
* These should never be returned by `mb_detect_encoding`. */
|
||||
int shift = 0;
|
||||
for (int i = 0; i < *size; i++) {
|
||||
const mbfl_encoding *encoding = elist[i];
|
||||
if (encoding->no_encoding <= mbfl_no_encoding_charset_min) {
|
||||
shift++; /* Remove this encoding from the list */
|
||||
} else if (shift) {
|
||||
elist[i - shift] = encoding;
|
||||
}
|
||||
}
|
||||
*size -= shift;
|
||||
}
|
||||
|
||||
/* {{{ Encodings of the given string is returned (as a string) */
|
||||
PHP_FUNCTION(mb_detect_encoding)
|
||||
{
|
||||
|
@ -2709,6 +2726,14 @@ PHP_FUNCTION(mb_detect_encoding)
|
|||
RETURN_THROWS();
|
||||
}
|
||||
|
||||
if (free_elist) {
|
||||
remove_non_encodings_from_elist(elist, &size);
|
||||
if (size == 0) {
|
||||
efree(ZEND_VOIDP(elist));
|
||||
RETURN_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
if (ZEND_NUM_ARGS() < 3) {
|
||||
strict = MBSTRG(strict_detection);
|
||||
}
|
||||
|
|
|
@ -16,5 +16,5 @@ var_dump(mb_detect_encoding("foobar.", "ascii,html"));
|
|||
bool(false)
|
||||
string(5) "ASCII"
|
||||
string(5) "ASCII"
|
||||
string(13) "HTML-ENTITIES"
|
||||
bool(false)
|
||||
string(5) "ASCII"
|
||||
|
|
|
@ -61,6 +61,7 @@ echo mb_detect_encoding($test, ['UTF-8', 'UTF-16']), "\n";
|
|||
|
||||
// We once had a problem where all kind of strings would be detected as 'UUENCODE'
|
||||
echo mb_detect_encoding('abc', ['UUENCODE', 'UTF-8']), "\n";
|
||||
echo mb_detect_encoding('abc', ['UUENCODE', 'QPrint', 'HTML-ENTITIES', 'Base64', '7bit', '8bit', 'SJIS']), "\n";
|
||||
|
||||
echo "== DETECT ORDER ==\n";
|
||||
|
||||
|
@ -242,6 +243,7 @@ ISO-8859-1
|
|||
UTF-8
|
||||
UTF-8
|
||||
UTF-8
|
||||
SJIS
|
||||
== DETECT ORDER ==
|
||||
JIS: JIS
|
||||
EUC-JP: EUC-JP
|
||||
|
|
|
@ -17,7 +17,7 @@ var_dump(mb_convert_encoding("ABC", "8bit", "7bit"));
|
|||
echo "7bit done\n";
|
||||
|
||||
// "8bit"
|
||||
var_dump(mb_convert_encoding("\x01\x00", "8bit", "UTF-16BE")); // codepoints over 0xFF are illegal for '8-bit'
|
||||
var_dump(mb_convert_encoding("\x01\x00", "8bit", "UTF-16BE")); // codepoints over 0xFF are illegal or '8-bit'
|
||||
echo "8bit done\n";
|
||||
|
||||
// UCS-2
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue