Skip to content

Commit 84be22f

Browse files
committed
Validate phonemes parameter of metaphone()
And thus avoid the false return value.
1 parent d0fb2f4 commit 84be22f

File tree

4 files changed

+24
-36
lines changed

4 files changed

+24
-36
lines changed

ext/standard/basic_functions.stub.php

+1-1
Original file line numberDiff line numberDiff line change
@@ -494,7 +494,7 @@ function inet_pton(string $ip_address): string|false {}
494494

495495
/* metaphone.c */
496496

497-
function metaphone(string $text, int $phones = 0): string|false {}
497+
function metaphone(string $text, int $phonemes = 0): string {}
498498

499499
/* {{{ head.c */
500500
function header(string $string, bool $replace = true, int $http_response_code = 0): void {}

ext/standard/basic_functions_arginfo.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/* This is a generated file, edit the .stub.php file instead.
2-
* Stub hash: 5e8cd8c22edadede2814b26b6fb984f1c3626850 */
2+
* Stub hash: 5d9126adf07f6f480b5879f551de466140b98462 */
33

44
ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_set_time_limit, 0, 1, _IS_BOOL, 0)
55
ZEND_ARG_TYPE_INFO(0, seconds, IS_LONG, 0)
@@ -725,9 +725,9 @@ ZEND_BEGIN_ARG_WITH_RETURN_TYPE_MASK_EX(arginfo_inet_pton, 0, 1, MAY_BE_STRING|M
725725
ZEND_END_ARG_INFO()
726726
#endif
727727

728-
ZEND_BEGIN_ARG_WITH_RETURN_TYPE_MASK_EX(arginfo_metaphone, 0, 1, MAY_BE_STRING|MAY_BE_FALSE)
728+
ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_metaphone, 0, 1, IS_STRING, 0)
729729
ZEND_ARG_TYPE_INFO(0, text, IS_STRING, 0)
730-
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, phones, IS_LONG, 0, "0")
730+
ZEND_ARG_TYPE_INFO_WITH_DEFAULT_VALUE(0, phonemes, IS_LONG, 0, "0")
731731
ZEND_END_ARG_INFO()
732732

733733
ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_header, 0, 1, IS_VOID, 0)

ext/standard/metaphone.c

+14-28
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020

2121
#include "php.h"
2222

23-
static int metaphone(unsigned char *word, size_t word_len, zend_long max_phonemes, zend_string **phoned_word, int traditional);
23+
static void metaphone(unsigned char *word, size_t word_len, zend_long max_phonemes, zend_string **phoned_word, int traditional);
2424

2525
/* {{{ Break english phrases down into their phonemes */
2626
PHP_FUNCTION(metaphone)
@@ -35,14 +35,13 @@ PHP_FUNCTION(metaphone)
3535
Z_PARAM_LONG(phones)
3636
ZEND_PARSE_PARAMETERS_END();
3737

38-
if (metaphone((unsigned char *)ZSTR_VAL(str), ZSTR_LEN(str), phones, &result, 1) == 0) {
39-
RETVAL_STR(result);
40-
} else {
41-
if (result) {
42-
zend_string_free(result);
43-
}
44-
RETURN_FALSE;
38+
if (phones < 0) {
39+
zend_argument_value_error(2, "must be greater than or equal to 0");
40+
RETURN_THROWS();
4541
}
42+
43+
metaphone((unsigned char *)ZSTR_VAL(str), ZSTR_LEN(str), phones, &result, 1);
44+
RETVAL_STR(result);
4645
}
4746
/* }}} */
4847

@@ -145,7 +144,7 @@ static char Lookahead(char *word, int how_far)
145144
ZSTR_LEN(*phoned_word) = p_idx; \
146145
}
147146
/* Slap a null character on the end of the phoned word */
148-
#define End_Phoned_Word { \
147+
#define End_Phoned_Word() { \
149148
if (p_idx == max_buffer_len) { \
150149
*phoned_word = zend_string_extend(*phoned_word, 1 * sizeof(char) + max_buffer_len, 0); \
151150
max_buffer_len += 1; \
@@ -160,24 +159,13 @@ static char Lookahead(char *word, int how_far)
160159
#define Isbreak(c) (!isalpha(c))
161160

162161
/* {{{ metaphone */
163-
static int metaphone(unsigned char *word, size_t word_len, zend_long max_phonemes, zend_string **phoned_word, int traditional)
162+
static void metaphone(unsigned char *word, size_t word_len, zend_long max_phonemes, zend_string **phoned_word, int traditional)
164163
{
165164
int w_idx = 0; /* point in the phonization we're at. */
166165
size_t p_idx = 0; /* end of the phoned phrase */
167166
size_t max_buffer_len = 0; /* maximum length of the destination buffer */
168-
169-
/*-- Parameter checks --*/
170-
/* Negative phoneme length is meaningless */
171-
172-
if (max_phonemes < 0)
173-
return -1;
174-
175-
/* Empty/null string is meaningless */
176-
/* Overly paranoid */
177-
/* assert(word != NULL && word[0] != '\0'); */
178-
179-
if (word == NULL)
180-
return -1;
167+
ZEND_ASSERT(word != NULL);
168+
ZEND_ASSERT(max_phonemes >= 0);
181169

182170
/*-- Allocate memory for our phoned_phrase --*/
183171
if (max_phonemes == 0) { /* Assume largest possible */
@@ -194,8 +182,8 @@ static int metaphone(unsigned char *word, size_t word_len, zend_long max_phoneme
194182
for (; !isalpha(Curr_Letter); w_idx++) {
195183
/* On the off chance we were given nothing but crap... */
196184
if (Curr_Letter == '\0') {
197-
End_Phoned_Word
198-
return SUCCESS; /* For testing */
185+
End_Phoned_Word();
186+
return;
199187
}
200188
}
201189

@@ -460,8 +448,6 @@ static int metaphone(unsigned char *word, size_t word_len, zend_long max_phoneme
460448
w_idx += skip_letter;
461449
} /* END FOR */
462450

463-
End_Phoned_Word;
464-
465-
return 0;
451+
End_Phoned_Word();
466452
} /* END metaphone */
467453
/* }}} */

ext/standard/tests/strings/metaphone.phpt

+6-4
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,12 @@ metaphone() tests
55

66
var_dump(metaphone(""));
77
var_dump(metaphone(-1));
8-
var_dump(metaphone(-1, -1));
98

10-
var_dump(metaphone("valid phrase", -1));
9+
try {
10+
var_dump(metaphone("valid phrase", -1));
11+
} catch (ValueError $e) {
12+
echo $e->getMessage(), "\n";
13+
}
1114
var_dump(metaphone("valid phrase", 0));
1215
var_dump(metaphone("valid phrase", 10000));
1316

@@ -27,8 +30,7 @@ echo "Done\n";
2730
--EXPECT--
2831
string(0) ""
2932
string(0) ""
30-
bool(false)
31-
bool(false)
33+
metaphone(): Argument #2 ($phonemes) must be greater than or equal to 0
3234
string(6) "FLTFRS"
3335
string(6) "FLTFRS"
3436
string(26) "0FLFRWRTKRFLNKHTLSLN0KLTR0"

0 commit comments

Comments
 (0)