1--TEST--
2Persistent connections and mysqli.max_links
3--SKIPIF--
4<?php
5	require_once('skipif.inc');
6	require_once('skipifemb.inc');
7	require_once('skipifconnectfailure.inc');
8	require_once('table.inc');
9
10	mysqli_query($link, 'DROP USER pcontest');
11	mysqli_query($link, 'DROP USER pcontest@localhost');
12
13	if (!mysqli_query($link, 'CREATE USER pcontest@"%" IDENTIFIED BY "pcontest"') ||
14		!mysqli_query($link, 'CREATE USER pcontest@localhost IDENTIFIED BY "pcontest"')) {
15		printf("skip Cannot create second DB user [%d] %s", mysqli_errno($link), mysqli_error($link));
16		mysqli_close($link);
17		die("skip CREATE USER failed");
18	}
19
20	// we might be able to specify the host using CURRENT_USER(), but...
21	if (!mysqli_query($link, sprintf("GRANT SELECT ON TABLE %s.test TO pcontest@'%%'", $db)) ||
22		!mysqli_query($link, sprintf("GRANT SELECT ON TABLE %s.test TO pcontest@'localhost'", $db))) {
23		printf("skip Cannot GRANT SELECT to second DB user [%d] %s", mysqli_errno($link), mysqli_error($link));
24		mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest');
25		mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest@localhost');
26		mysqli_query($link, 'DROP USER pcontest@localhost');
27		mysqli_query($link, 'DROP USER pcontest');
28		mysqli_close($link);
29		die("skip GRANT failed");
30	}
31
32	if (!($link_pcontest = @my_mysqli_connect($host, 'pcontest', 'pcontest', $db, $port, $socket))) {
33		mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest');
34		mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest@localhost');
35		mysqli_query($link, 'DROP USER pcontest@localhost');
36		mysqli_query($link, 'DROP USER pcontest');
37		mysqli_close($link);
38		die("skip CONNECT using new user failed");
39    }
40	mysqli_close($link);
41?>
42--INI--
43mysqli.allow_persistent=1
44mysqli.max_persistent=2
45--FILE--
46<?php
47	require_once("connect.inc");
48	require_once('table.inc');
49
50
51	if (!mysqli_query($link, 'DROP USER pcontest') ||
52		!mysqli_query($link, 'DROP USER pcontest@localhost') ||
53		!mysqli_query($link, 'CREATE USER pcontest@"%" IDENTIFIED BY "pcontest"') ||
54		!mysqli_query($link, 'CREATE USER pcontest@localhost IDENTIFIED BY "pcontest"') ||
55		!mysqli_query($link, sprintf("GRANT SELECT ON TABLE %s.test TO pcontest@'%%'", $db)) ||
56		!mysqli_query($link, sprintf("GRANT SELECT ON TABLE %s.test TO pcontest@'localhost'", $db))) {
57		printf("[000] Init failed, [%d] %s\n",
58			mysqli_errno($plink), mysqli_error($plink));
59	}
60
61	if (!$plink = my_mysqli_connect('p:' . $host, 'pcontest', 'pcontest', $db, $port, $socket))
62		printf("[001] Cannot connect using the second DB user created during SKIPIF, [%d] %s\n",
63			mysqli_connect_errno(), mysqli_connect_error());
64
65	ob_start();
66	phpinfo();
67	$phpinfo = strip_tags(ob_get_contents());
68	ob_end_clean();
69
70	$phpinfo = substr($phpinfo, strpos($phpinfo, 'MysqlI Support => enabled'), 500);
71	if (!preg_match('@Active Persistent Links\s+=>\s+(\d+)@ismU', $phpinfo, $matches))
72		printf("[002] Cannot get # active persistent links from phpinfo()\n");
73	$num_plinks = $matches[1];
74
75	if (!$res = mysqli_query($plink, 'SELECT id, label FROM test WHERE id = 1'))
76		printf("[003] Cannot run query on persistent connection of second DB user, [%d] %s\n",
77			mysqli_errno($plink), mysqli_error($plink));
78
79	if (!$row = mysqli_fetch_assoc($res))
80		printf("[004] Cannot run fetch result, [%d] %s\n",
81			mysqli_errno($plink), mysqli_error($plink));
82	mysqli_free_result($res);
83	var_dump($row);
84
85	// change the password for the second DB user and kill the persistent connection
86	if (!mysqli_query($link, 'SET PASSWORD FOR pcontest = PASSWORD("newpass")') ||
87			!mysqli_query($link, 'FLUSH PRIVILEGES'))
88		printf("[005] Cannot change PW of second DB user, [%d] %s\n", mysqli_errno($link), mysqli_error($link));
89
90        // change the password for the second DB user and kill the persistent connection
91	if (!mysqli_query($link, 'SET PASSWORD FOR pcontest@localhost = PASSWORD("newpass")') ||
92			!mysqli_query($link, 'FLUSH PRIVILEGES'))
93		printf("[006] Cannot change PW of second DB user, [%d] %s\n", mysqli_errno($link), mysqli_error($link));
94
95	// persistent connections cannot be closed but only be killed
96	$pthread_id = mysqli_thread_id($plink);
97	if (!mysqli_query($link, sprintf('KILL %d', $pthread_id)))
98		printf("[007] Cannot KILL persistent connection of second DB user, [%d] %s\n", mysqli_errno($link), mysqli_error($link));
99	// give the server a second to really kill the thread
100	sleep(1);
101
102	if (!$res = mysqli_query($link, "SHOW FULL PROCESSLIST"))
103		printf("[008] [%d] %s\n", mysqli_errno($link), mysqli_error($link));
104
105	$running_threads = array();
106	while ($row = mysqli_fetch_assoc($res))
107		$running_threads[$row['Id']] = $row;
108	mysqli_free_result($res);
109
110	if (isset($running_threads[$pthread_id]))
111		printf("[009] Persistent connection has not been killed\n");
112
113	// this fails and we have 0 (<= $num_plinks) connections
114	if ($plink = @my_mysqli_connect('p:' . $host, 'pcontest', 'pcontest', $db, $port, $socket))
115		printf("[010] Can connect using the old password, [%d] %s\n",
116			mysqli_connect_errno($link), mysqli_connect_error($link));
117
118	ob_start();
119	phpinfo();
120	$phpinfo = strip_tags(ob_get_contents());
121	ob_end_clean();
122	$phpinfo = substr($phpinfo, stripos($phpinfo, 'MysqlI Support => enabled'), 500);
123	if (!preg_match('@Active Persistent Links\s+=>\s+(\d+)@ismU', $phpinfo, $matches))
124		printf("[010] Cannot get # of active persistent links from phpinfo()\n");
125
126	$num_plinks_kill = $matches[1];
127	if ($num_plinks_kill > $num_plinks)
128		printf("[011] Expecting Active Persistent Links < %d, got %d\n", $num_plinks, $num_plinks_kill);
129
130	if (!$plink = my_mysqli_connect('p:' . $host, 'pcontest', 'newpass', $db, $port, $socket))
131		printf("[012] Cannot connect using the new password, [%d] %s\n",
132			mysqli_connect_errno(), mysqli_connect_error());
133
134	if (!$res = mysqli_query($plink, 'SELECT id, label FROM test WHERE id = 1'))
135		printf("[013] Cannot run query on persistent connection of second DB user, [%d] %s\n",
136			mysqli_errno($plink), mysqli_error($plink));
137
138	if (!$row = mysqli_fetch_assoc($res))
139		printf("[014] Cannot run fetch result, [%d] %s\n",
140			mysqli_errno($plink), mysqli_error($plink));
141	mysqli_free_result($res);
142	var_dump($row);
143
144	if ($plink2 = my_mysqli_connect('p:' . $host, 'pcontest', 'newpass', $db, $port, $socket))
145		printf("[015] Can open more persistent connections than allowed, [%d] %s\n",
146			mysqli_connect_errno(), mysqli_connect_error());
147
148	ob_start();
149	phpinfo();
150	$phpinfo = strip_tags(ob_get_contents());
151	ob_end_clean();
152	$phpinfo = substr($phpinfo, stripos($phpinfo, 'MysqlI Support => enabled'), 500);
153	if (!preg_match('@Active Persistent Links\s+=>\s+(\d+)@ismU', $phpinfo, $matches))
154		printf("[016] Cannot get # of active persistent links from phpinfo()\n");
155
156	$num_plinks = $matches[1];
157	if ($num_plinks > (int)ini_get('mysqli.max_persistent'))
158		printf("[017] mysqli.max_persistent=%d allows %d open connections!\n", ini_get('mysqli.max_persistent'),$num_plinks);
159
160	mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest');
161	mysqli_query($link, 'DROP USER pcontest');
162	mysqli_close($link);
163	print "done!";
164?>
165--CLEAN--
166<?php
167require_once("connect.inc");
168if (!$link = my_mysqli_connect($host, $user, $passwd, $db, $port, $socket))
169   printf("[c001] [%d] %s\n", mysqli_connect_errno(), mysqli_connect_error());
170
171if (!mysqli_query($link, "DROP TABLE IF EXISTS test"))
172	printf("[c002] Cannot drop table, [%d] %s\n", mysqli_errno($link), mysqli_error($link));
173
174mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest');
175mysqli_query($link, 'REVOKE ALL PRIVILEGES, GRANT OPTION FROM pcontest@localhost');
176mysqli_query($link, 'DROP USER pcontest@localhost');
177mysqli_query($link, 'DROP USER pcontest');
178
179mysqli_close($link);
180?>
181--EXPECTF--
182array(2) {
183  [%u|b%"id"]=>
184  %unicode|string%(1) "1"
185  [%u|b%"label"]=>
186  %unicode|string%(1) "a"
187}
188array(2) {
189  [%u|b%"id"]=>
190  %unicode|string%(1) "1"
191  [%u|b%"label"]=>
192  %unicode|string%(1) "a"
193}
194
195Warning: %s: Too many open persistent links (%d) in %s on line %d
196done!