Skip to content

Commit 21227dc

Browse files
committed
Use php_mb_get_encoding instead of mbfl_name2encoding to get encoding
This reduces the number of places where the error message template is used. Also promote the mb_check_encoding() warning to ValueError and add a test to cover the behaviour.
1 parent 11f0e1d commit 21227dc

File tree

2 files changed

+67
-37
lines changed

2 files changed

+67
-37
lines changed

ext/mbstring/mbstring.c

Lines changed: 25 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -3045,16 +3045,14 @@ PHP_FUNCTION(mb_list_encodings)
30453045
PHP_FUNCTION(mb_encoding_aliases)
30463046
{
30473047
const mbfl_encoding *encoding;
3048-
char *name = NULL;
3049-
size_t name_len;
3048+
zend_string *encoding_name = NULL;
30503049

3051-
if (zend_parse_parameters(ZEND_NUM_ARGS(), "s", &name, &name_len) == FAILURE) {
3050+
if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &encoding_name) == FAILURE) {
30523051
RETURN_THROWS();
30533052
}
30543053

3055-
encoding = mbfl_name2encoding(name);
3054+
encoding = php_mb_get_encoding(encoding_name, 1);
30563055
if (!encoding) {
3057-
zend_argument_value_error(1, "must be a valid encoding, \"%s\" given", name);
30583056
RETURN_THROWS();
30593057
}
30603058

@@ -3074,8 +3072,7 @@ PHP_FUNCTION(mb_encode_mimeheader)
30743072
{
30753073
const mbfl_encoding *charset, *transenc;
30763074
mbfl_string string, result, *ret;
3077-
char *charset_name = NULL;
3078-
size_t charset_name_len;
3075+
zend_string *charset_name = NULL;
30793076
char *trans_enc_name = NULL;
30803077
size_t trans_enc_name_len;
30813078
char *linefeed = "\r\n";
@@ -3085,17 +3082,16 @@ PHP_FUNCTION(mb_encode_mimeheader)
30853082
string.no_language = MBSTRG(language);
30863083
string.encoding = MBSTRG(current_internal_encoding);
30873084

3088-
if (zend_parse_parameters(ZEND_NUM_ARGS(), "s|sssl", (char **)&string.val, &string.len, &charset_name, &charset_name_len, &trans_enc_name, &trans_enc_name_len, &linefeed, &linefeed_len, &indent) == FAILURE) {
3085+
if (zend_parse_parameters(ZEND_NUM_ARGS(), "s|Sssl", (char **)&string.val, &string.len, &charset_name, &trans_enc_name, &trans_enc_name_len, &linefeed, &linefeed_len, &indent) == FAILURE) {
30893086
RETURN_THROWS();
30903087
}
30913088

30923089
charset = &mbfl_encoding_pass;
30933090
transenc = &mbfl_encoding_base64;
30943091

30953092
if (charset_name != NULL) {
3096-
charset = mbfl_name2encoding(charset_name);
3093+
charset = php_mb_get_encoding(charset_name, 2);
30973094
if (!charset) {
3098-
zend_argument_value_error(2, "must be a valid encoding, \"%s\" given", charset_name);
30993095
RETURN_THROWS();
31003096
}
31013097
} else {
@@ -3347,29 +3343,27 @@ static int mb_recursive_convert_variable(mbfl_buffer_converter *convd, zval *var
33473343
PHP_FUNCTION(mb_convert_variables)
33483344
{
33493345
zval *args;
3346+
zend_string *to_enc_str;
33503347
zend_string *from_enc_str;
33513348
HashTable *from_enc_ht;
33523349
mbfl_string string, result;
33533350
const mbfl_encoding *from_encoding, *to_encoding;
33543351
mbfl_encoding_detector *identd;
33553352
mbfl_buffer_converter *convd;
33563353
int n, argc;
3357-
size_t to_enc_len;
33583354
size_t elistsz;
33593355
const mbfl_encoding **elist;
3360-
char *to_enc;
33613356
int recursion_error = 0;
33623357

33633358
ZEND_PARSE_PARAMETERS_START(3, -1)
3364-
Z_PARAM_STRING(to_enc, to_enc_len)
3359+
Z_PARAM_STR(to_enc_str)
33653360
Z_PARAM_STR_OR_ARRAY_HT(from_enc_str, from_enc_ht)
33663361
Z_PARAM_VARIADIC('+', args, argc)
33673362
ZEND_PARSE_PARAMETERS_END();
33683363

33693364
/* new encoding */
3370-
to_encoding = mbfl_name2encoding(to_enc);
3365+
to_encoding = php_mb_get_encoding(to_enc_str, 1);
33713366
if (!to_encoding) {
3372-
zend_argument_value_error(1, "must be a valid encoding, \"%s\" given", to_enc);
33733367
RETURN_THROWS();
33743368
}
33753369

@@ -3476,36 +3470,31 @@ PHP_FUNCTION(mb_convert_variables)
34763470
static void
34773471
php_mb_numericentity_exec(INTERNAL_FUNCTION_PARAMETERS, int type)
34783472
{
3479-
char *str, *encoding = NULL;
3480-
size_t str_len, encoding_len;
3473+
char *str = NULL;
3474+
size_t str_len;
3475+
zend_string *encoding = NULL;
34813476
zval *hash_entry;
34823477
HashTable *target_hash;
34833478
int i, *convmap, *mapelm, mapsize=0;
34843479
zend_bool is_hex = 0;
34853480
mbfl_string string, result, *ret;
34863481

34873482
if (type == 0) {
3488-
if (zend_parse_parameters(ZEND_NUM_ARGS(), "sh|sb", &str, &str_len, &target_hash, &encoding, &encoding_len, &is_hex) == FAILURE) {
3483+
if (zend_parse_parameters(ZEND_NUM_ARGS(), "sh|Sb", &str, &str_len, &target_hash, &encoding, &is_hex) == FAILURE) {
34893484
RETURN_THROWS();
34903485
}
34913486
} else {
3492-
if (zend_parse_parameters(ZEND_NUM_ARGS(), "sh|s", &str, &str_len, &target_hash, &encoding, &encoding_len) == FAILURE) {
3487+
if (zend_parse_parameters(ZEND_NUM_ARGS(), "sh|S", &str, &str_len, &target_hash, &encoding) == FAILURE) {
34933488
RETURN_THROWS();
34943489
}
34953490
}
34963491

34973492
string.no_language = MBSTRG(language);
3498-
string.encoding = MBSTRG(current_internal_encoding);
34993493
string.val = (unsigned char *)str;
35003494
string.len = str_len;
3501-
3502-
/* encoding */
3503-
if (encoding && encoding_len > 0) {
3504-
string.encoding = mbfl_name2encoding(encoding);
3505-
if (!string.encoding) {
3506-
zend_argument_value_error(3, "must be a valid encoding, \"%s\" given", encoding);
3507-
RETURN_THROWS();
3508-
}
3495+
string.encoding = php_mb_get_encoding(encoding, 3);
3496+
if (!string.encoding) {
3497+
RETURN_THROWS();
35093498
}
35103499

35113500
if (type == 0 && is_hex) {
@@ -4216,7 +4205,6 @@ static inline int php_mb_check_encoding_impl(mbfl_buffer_converter *convd, const
42164205
return 0;
42174206
}
42184207

4219-
42204208
MBSTRING_API int php_mb_check_encoding(
42214209
const char *input, size_t length, const mbfl_encoding *encoding)
42224210
{
@@ -4236,7 +4224,6 @@ MBSTRING_API int php_mb_check_encoding(
42364224
return 0;
42374225
}
42384226

4239-
42404227
static int php_mb_check_encoding_recursive(HashTable *vars, const mbfl_encoding *encoding)
42414228
{
42424229
mbfl_buffer_converter *convd;
@@ -4304,20 +4291,21 @@ PHP_FUNCTION(mb_check_encoding)
43044291
{
43054292
zend_string *input_str = NULL, *enc = NULL;
43064293
HashTable *input_ht = NULL;
4307-
const mbfl_encoding *encoding = MBSTRG(current_internal_encoding);
4294+
const mbfl_encoding *encoding;
43084295

43094296
ZEND_PARSE_PARAMETERS_START(0, 2)
43104297
Z_PARAM_OPTIONAL
43114298
Z_PARAM_STR_OR_ARRAY_HT(input_str, input_ht)
43124299
Z_PARAM_STR(enc)
43134300
ZEND_PARSE_PARAMETERS_END();
43144301

4315-
if (enc != NULL) {
4316-
encoding = mbfl_name2encoding(ZSTR_VAL(enc));
4317-
if (!encoding || encoding == &mbfl_encoding_pass) {
4318-
php_error_docref(NULL, E_WARNING, "Invalid encoding \"%s\"", ZSTR_VAL(enc));
4319-
RETURN_FALSE;
4320-
}
4302+
encoding = php_mb_get_encoding(enc, 2);
4303+
if (!encoding) {
4304+
RETURN_THROWS();
4305+
}
4306+
if (encoding == &mbfl_encoding_pass) {
4307+
zend_argument_value_error(2, "cannot check \"pass\" encoding");
4308+
RETURN_THROWS();
43214309
}
43224310

43234311
if (input_ht) {
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
--TEST--
2+
mb_check_encoding() with invalid encodings
3+
--SKIPIF--
4+
<?php extension_loaded('mbstring') or die('skip mbstring not available'); ?>
5+
--FILE--
6+
<?php
7+
8+
$str = "Normal string";
9+
$arr = [1234, 12.34, TRUE, FALSE, NULL, $str, 'key'=>$str, $str=>'val'];
10+
11+
echo 'Using "BAD" as encoding' . \PHP_EOL;
12+
try {
13+
var_dump(mb_check_encoding($str, 'BAD'));
14+
} catch (\ValueError $e) {
15+
echo $e->getMessage() . \PHP_EOL;
16+
}
17+
try {
18+
var_dump(mb_check_encoding($arr, 'BAD'));
19+
} catch (\ValueError $e) {
20+
echo $e->getMessage() . \PHP_EOL;
21+
}
22+
23+
echo 'Using "pass" as encoding' . \PHP_EOL;
24+
try {
25+
var_dump(mb_check_encoding($str, 'pass'));
26+
} catch (\ValueError $e) {
27+
echo $e->getMessage() . \PHP_EOL;
28+
}
29+
try {
30+
var_dump(mb_check_encoding($arr, 'pass'));
31+
} catch (\ValueError $e) {
32+
echo $e->getMessage() . \PHP_EOL;
33+
}
34+
35+
?>
36+
--EXPECT--
37+
Using "BAD" as encoding
38+
mb_check_encoding(): Argument #2 ($encoding) must be a valid encoding, "BAD" given
39+
mb_check_encoding(): Argument #2 ($encoding) must be a valid encoding, "BAD" given
40+
Using "pass" as encoding
41+
mb_check_encoding(): Argument #2 ($encoding) cannot check "pass" encoding
42+
mb_check_encoding(): Argument #2 ($encoding) cannot check "pass" encoding

0 commit comments

Comments
 (0)