Skip to content

Commit 7a898c6

Browse files
committed
Promote warning to type error in count()
1 parent 5b8e12a commit 7a898c6

15 files changed

+449
-617
lines changed

Zend/tests/generators/errors/count_error.phpt

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,10 @@ try {
1111
count($gen);
1212
} catch (Exception $e) {
1313
echo $e;
14-
}
14+
} catch (\TypeError $e) {
15+
echo $e->getMessage() . "\n";
16+
}
1517

1618
?>
17-
--EXPECTF--
18-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
19+
--EXPECT--
20+
Parameter must be an array or an object that implements Countable

Zend/zend_vm_def.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8616,7 +8616,7 @@ ZEND_VM_COLD_CONST_HANDLER(190, ZEND_COUNT, CONST|TMPVAR|CV, UNUSED)
86168616
} else {
86178617
count = 1;
86188618
}
8619-
zend_error(E_WARNING, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
8619+
zend_type_error("Parameter must be an array or an object that implements Countable");
86208620
break;
86218621
}
86228622

Zend/zend_vm_execute.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9558,7 +9558,7 @@ static ZEND_VM_COLD ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_COUNT_SPEC_CONST_
95589558
} else {
95599559
count = 1;
95609560
}
9561-
zend_error(E_WARNING, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
9561+
zend_type_error("Parameter must be an array or an object that implements Countable");
95629562
break;
95639563
}
95649564

@@ -16687,7 +16687,7 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_COUNT_SPEC_TMPVAR_UNUSED_HANDL
1668716687
} else {
1668816688
count = 1;
1668916689
}
16690-
zend_error(E_WARNING, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
16690+
zend_type_error("Parameter must be an array or an object that implements Countable");
1669116691
break;
1669216692
}
1669316693

@@ -47323,7 +47323,7 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_COUNT_SPEC_CV_UNUSED_HANDLER(Z
4732347323
} else {
4732447324
count = 1;
4732547325
}
47326-
zend_error(E_WARNING, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
47326+
zend_type_error("Parameter must be an array or an object that implements Countable");
4732747327
break;
4732847328
}
4732947329

ext/ffi/tests/008.phpt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ foreach ($a as $key => $val) {
1616

1717
$a = FFI::new("struct {int x,y;}");
1818
try {
19-
var_dump(@count($a));
19+
var_dump(count($a));
2020
} catch (Throwable $e) {
2121
echo get_class($e) . ": " . $e->getMessage()."\n";
2222
}
@@ -34,5 +34,5 @@ int(3)
3434
0 => 0
3535
1 => 10
3636
2 => 20
37-
FFI\Exception: Attempt to count() on non C array
37+
TypeError: Parameter must be an array or an object that implements Countable
3838
FFI\Exception: Attempt to iterate on non C array

ext/standard/array.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -773,7 +773,7 @@ PHP_FUNCTION(count)
773773

774774
switch (Z_TYPE_P(array)) {
775775
case IS_NULL:
776-
php_error_docref(NULL, E_WARNING, "Parameter must be an array or an object that implements Countable");
776+
zend_type_error("Parameter must be an array or an object that implements Countable");
777777
RETURN_LONG(0);
778778
break;
779779
case IS_ARRAY:
@@ -804,12 +804,12 @@ PHP_FUNCTION(count)
804804
}
805805

806806
/* If There's no handler and it doesn't implement Countable then add a warning */
807-
php_error_docref(NULL, E_WARNING, "Parameter must be an array or an object that implements Countable");
807+
zend_type_error("Parameter must be an array or an object that implements Countable");
808808
RETURN_LONG(1);
809809
break;
810810
}
811811
default:
812-
php_error_docref(NULL, E_WARNING, "Parameter must be an array or an object that implements Countable");
812+
zend_type_error("Parameter must be an array or an object that implements Countable");
813813
RETURN_LONG(1);
814814
break;
815815
}
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
--TEST--
2+
Test count() function error conditions
3+
--FILE--
4+
<?php
5+
/* Prototype: int count ( mixed $var [, int $mode] );
6+
Description: Count elements in an array, or properties in an object
7+
*/
8+
9+
try {
10+
count(NULL, COUNT_NORMAL);
11+
} catch (\TypeError $e) {
12+
echo $e->getMessage() . "\n";
13+
}
14+
try {
15+
count(NULL, COUNT_RECURSIVE);
16+
} catch (\TypeError $e) {
17+
echo $e->getMessage() . "\n";
18+
}
19+
try {
20+
count(NULL);
21+
} catch (\TypeError $e) {
22+
echo $e->getMessage() . "\n";
23+
}
24+
25+
try {
26+
count("string", COUNT_NORMAL);
27+
} catch (\TypeError $e) {
28+
echo $e->getMessage() . "\n";
29+
}
30+
try {
31+
count("string", COUNT_RECURSIVE);
32+
} catch (\TypeError $e) {
33+
echo $e->getMessage() . "\n";
34+
}
35+
try {
36+
count("string");
37+
} catch (\TypeError $e) {
38+
echo $e->getMessage() . "\n";
39+
}
40+
try {
41+
count("");
42+
} catch (\TypeError $e) {
43+
echo $e->getMessage() . "\n";
44+
}
45+
46+
try {
47+
count(100);
48+
} catch (\TypeError $e) {
49+
echo $e->getMessage() . "\n";
50+
}
51+
try {
52+
count(-23.45);
53+
} catch (\TypeError $e) {
54+
echo $e->getMessage() . "\n";
55+
}
56+
57+
try {
58+
@count($a);
59+
} catch (\TypeError $e) {
60+
echo $e->getMessage() . "\n";
61+
}
62+
63+
?>
64+
--EXPECT--
65+
Parameter must be an array or an object that implements Countable
66+
Parameter must be an array or an object that implements Countable
67+
Parameter must be an array or an object that implements Countable
68+
Parameter must be an array or an object that implements Countable
69+
Parameter must be an array or an object that implements Countable
70+
Parameter must be an array or an object that implements Countable
71+
Parameter must be an array or an object that implements Countable
72+
Parameter must be an array or an object that implements Countable
73+
Parameter must be an array or an object that implements Countable
74+
Parameter must be an array or an object that implements Countable

ext/standard/tests/array/count_invalid.phpt

Lines changed: 46 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -3,40 +3,51 @@ Only arrays and countable objects can be counted
33
--FILE--
44
<?php
55

6-
$result = count(null);
7-
var_dump($result);
8-
9-
$result = count("string");
10-
var_dump($result);
11-
12-
$result = count(123);
13-
var_dump($result);
14-
15-
$result = count(true);
16-
var_dump($result);
17-
18-
$result = count(false);
19-
var_dump($result);
20-
21-
$result = count((object) []);
22-
var_dump($result);
6+
try {
7+
$result = count(null);
8+
var_dump($result);
9+
} catch (\TypeError $e) {
10+
echo $e->getMessage() . "\n";
11+
}
12+
13+
try {
14+
$result = count("string");
15+
var_dump($result);
16+
} catch (\TypeError $e) {
17+
echo $e->getMessage() . "\n";
18+
}
19+
20+
try {
21+
$result = count(123);
22+
var_dump($result);
23+
} catch (\TypeError $e) {
24+
echo $e->getMessage() . "\n";
25+
}
26+
27+
try {
28+
$result = count(true);
29+
var_dump($result);
30+
} catch (\TypeError $e) {
31+
echo $e->getMessage() . "\n";
32+
}
33+
try {
34+
$result = count(false);
35+
var_dump($result);
36+
} catch (\TypeError $e) {
37+
echo $e->getMessage() . "\n";
38+
}
39+
try {
40+
$result = count((object) []);
41+
var_dump($result);
42+
} catch (\TypeError $e) {
43+
echo $e->getMessage() . "\n";
44+
}
2345

2446
?>
25-
--EXPECTF--
26-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
27-
int(0)
28-
29-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
30-
int(1)
31-
32-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
33-
int(1)
34-
35-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
36-
int(1)
37-
38-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
39-
int(1)
40-
41-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
42-
int(1)
47+
--EXPECT--
48+
Parameter must be an array or an object that implements Countable
49+
Parameter must be an array or an object that implements Countable
50+
Parameter must be an array or an object that implements Countable
51+
Parameter must be an array or an object that implements Countable
52+
Parameter must be an array or an object that implements Countable
53+
Parameter must be an array or an object that implements Countable

ext/standard/tests/array/count_recursive.phpt

Lines changed: 16 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,10 @@ Test count() function
33
--FILE--
44
<?php
55
/* Prototype: int count ( mixed $var [, int $mode] );
6-
Discription: Count elements in an array, or properties in an object
6+
Description: Count elements in an array, or properties in an object
77
*/
88

99
echo "*** Testing basic functionality of count() function ***\n";
10-
print "-- Testing NULL --\n";
11-
$arr = NULL;
12-
print "COUNT_NORMAL: should be 0, is ".count($arr, COUNT_NORMAL)."\n";
13-
print "COUNT_RECURSIVE: should be 0, is ".count($arr, COUNT_RECURSIVE)."\n";
14-
1510
print "-- Testing arrays --\n";
1611
$arr = array(1, array(3, 4, array(6, array(8))));
1712
print "COUNT_NORMAL: should be 2, is ".count($arr, COUNT_NORMAL)."\n";
@@ -22,12 +17,7 @@ $arr = array("a" => 1, "b" => 2, array("c" => 3, array("d" => 5)));
2217
print "COUNT_NORMAL: should be 3, is ".count($arr, COUNT_NORMAL)."\n";
2318
print "COUNT_RECURSIVE: should be 6, is ".count($arr, COUNT_RECURSIVE)."\n";
2419

25-
print "-- Testing strings --\n";
26-
print "COUNT_NORMAL: should be 1, is ".count("string", COUNT_NORMAL)."\n";
27-
print "COUNT_RECURSIVE: should be 1, is ".count("string", COUNT_RECURSIVE)."\n";
28-
29-
print "-- Testing various types with no second argument --\n";
30-
print "COUNT_NORMAL: should be 1, is ".count("string")."\n";
20+
print "-- Testing array with no second argument --\n";
3121
print "COUNT_NORMAL: should be 2, is ".count(array("a", array("b")))."\n";
3222

3323
$arr = array('a'=>array(NULL, NULL, NULL), 1=>array(NULL=>1, 1=>NULL),
@@ -38,40 +28,24 @@ print "COUNT_RECURSIVE: should be 13, is ".count($arr, COUNT_RECURSIVE)."\n";
3828

3929
echo "\n*** Testing possible variations of count() function on arrays ***";
4030
$count_array = array(
41-
array(),
42-
array( 1 => "string"),
43-
array( "" => "string", 0 => "a", NULL => "b", -1.00 => "c",
44-
array(array(array(NULL)))),
45-
array( -2.44444 => 12, array(array(1, 2, array(array("0"))))),
46-
array( "a" => 1, "b" => -2.344, "b" => "string", "c" => NULL, "d" => -2.344),
47-
array( 4 => 1, 3 => -2.344, "3" => "string", "2" => NULL,
48-
1 => -2.344, array()),
49-
array( TRUE => TRUE, FALSE => FALSE, "" => "", " " => " ",
50-
NULL => NULL, "\x000" => "\x000", "\000" => "\000"),
51-
array( NULL, 1.23 => "Hi", "string" => "hello",
52-
array("" => "World", "-2.34" => "a", "0" => "b"))
31+
array(),
32+
array( 1 => "string"),
33+
array( "" => "string", 0 => "a", NULL => "b", -1.00 => "c", array(array(array(NULL)))),
34+
array( -2.44444 => 12, array(array(1, 2, array(array("0"))))),
35+
array( "a" => 1, "b" => -2.344, "b" => "string", "c" => NULL, "d" => -2.344),
36+
array( 4 => 1, 3 => -2.344, "3" => "string", "2" => NULL, 1 => -2.344, array()),
37+
array( TRUE => TRUE, FALSE => FALSE, "" => "", " " => " ", NULL => NULL, "\x000" => "\x000", "\000" => "\000"),
38+
array( NULL, 1.23 => "Hi", "string" => "hello", array("" => "World", "-2.34" => "a", "0" => "b") )
5339
);
5440

5541
$i = 0;
5642
foreach ($count_array as $count_value) {
57-
echo "\n-- Iteration $i --\n";
58-
print "COUNT_NORMAL is ".count($count_value, COUNT_NORMAL)."\n";
59-
print "COUNT_RECURSIVE is ".count($count_value, COUNT_RECURSIVE)."\n";
60-
$i++;
43+
echo "\n-- Iteration $i --\n";
44+
print "COUNT_NORMAL is ".count($count_value, COUNT_NORMAL)."\n";
45+
print "COUNT_RECURSIVE is ".count($count_value, COUNT_RECURSIVE)."\n";
46+
$i++;
6147
}
6248

63-
64-
/* Testing count() by passing constant with no second argument */
65-
print "\n-- Testing count() on constants with no second argument --\n";
66-
print "COUNT_NORMAL: should be 1, is ".count(100)."\n";
67-
print "COUNT_NORMAL: should be 1, is ".count(-23.45)."\n";
68-
69-
print "\n-- Testing count() on NULL and Unset variables --\n";
70-
print "COUNT_NORMAL: should be 0, is ".count(NULL)."\n";
71-
print "COUNT_NORMAL: should be 1, is ".count("")."\n";
72-
print "COUNT_NORMAL: should be 0, is ".@count($a)."\n";
73-
74-
7549
print "\n-- Testing count() on an empty sub-array --\n";
7650
$arr = array(1, array(3, 4, array()));
7751
print "COUNT_NORMAL: should be 2, is ".count($arr, COUNT_NORMAL)."\n";
@@ -117,32 +91,15 @@ echo "\nDone";
11791
fclose( $resource1 );
11892
closedir( $resource2 );
11993
?>
120-
--EXPECTF--
94+
--EXPECT--
12195
*** Testing basic functionality of count() function ***
122-
-- Testing NULL --
123-
124-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
125-
COUNT_NORMAL: should be 0, is 0
126-
127-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
128-
COUNT_RECURSIVE: should be 0, is 0
12996
-- Testing arrays --
13097
COUNT_NORMAL: should be 2, is 2
13198
COUNT_RECURSIVE: should be 8, is 8
13299
-- Testing hashes --
133100
COUNT_NORMAL: should be 3, is 3
134101
COUNT_RECURSIVE: should be 6, is 6
135-
-- Testing strings --
136-
137-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
138-
COUNT_NORMAL: should be 1, is 1
139-
140-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
141-
COUNT_RECURSIVE: should be 1, is 1
142-
-- Testing various types with no second argument --
143-
144-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
145-
COUNT_NORMAL: should be 1, is 1
102+
-- Testing array with no second argument --
146103
COUNT_NORMAL: should be 2, is 2
147104
-- Testing really cool arrays --
148105
COUNT_NORMAL: should be 3, is 3
@@ -181,23 +138,6 @@ COUNT_RECURSIVE is 6
181138
COUNT_NORMAL is 4
182139
COUNT_RECURSIVE is 7
183140

184-
-- Testing count() on constants with no second argument --
185-
186-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
187-
COUNT_NORMAL: should be 1, is 1
188-
189-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
190-
COUNT_NORMAL: should be 1, is 1
191-
192-
-- Testing count() on NULL and Unset variables --
193-
194-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
195-
COUNT_NORMAL: should be 0, is 0
196-
197-
Warning: count(): Parameter must be an array or an object that implements Countable in %s on line %d
198-
COUNT_NORMAL: should be 1, is 1
199-
COUNT_NORMAL: should be 0, is 0
200-
201141
-- Testing count() on an empty sub-array --
202142
COUNT_NORMAL: should be 2, is 2
203143
COUNT_RECURSIVE: should be 5, is 5

0 commit comments

Comments
 (0)