Statement on glibc/iconv Vulnerability

mysql_connect

(PHP 4, PHP 5)

mysql_connect打开一个到 MySQL 服务器的连接

警告

本扩展自 PHP 5.5.0 起已废弃,并在自 PHP 7.0.0 开始被移除。应使用 MySQLiPDO_MySQL 扩展来替换之。参见 MySQL:选择 API 指南来获取更多信息。用以替代本函数的有:

说明

mysql_connect(
    string $server = ini_get("mysql.default_host"),
    string $username = ini_get("mysql.default_user"),
    string $password = ini_get("mysql.default_password"),
    bool $new_link = false,
    int $client_flags = 0
): resource|false

打开或重复使用一个到 MySQL 服务器的连接。

参数

server

MySQL 服务器。可以包括端口号,例如 "hostname:port",或者到本地套接字的路径,例如对于 localhost 的 ":/path/to/socket"。

如果 PHP 指令 mysql.default_host 未定义(默认情况),则默认值是 'localhost:3306'。 在 SQL 安全模式 时,参数被忽略,总是使用 'localhost:3306'。

username

用户名。默认值由 mysql.default_user 定义。 在 SQL 安全模式 时,参数被忽略,总是使用服务器进程所有者的用户名。

password

密码。默认值由mysql.default_password定义。在 SQL 安全模式 时,参数被忽略,总是使用空密码。

new_link

如果用同样的参数第二次调用 mysql_connect(),将不会建立新连接,而将返回已经打开的连接标识。参数 new_link 改变此行为并使 mysql_connect() 总是打开新的连接,甚至当 mysql_connect() 曾在前面被用同样的参数调用过。

client_flags

client_flags 参数可以是以下常量的组合:MYSQL_CLIENT_SSLMYSQL_CLIENT_COMPRESSMYSQL_CLIENT_IGNORE_SPACEMYSQL_CLIENT_INTERACTIVE。进一步信息见 MySQL 客户端常量

返回值

如果成功则返回一个 MySQL 连接标识, 或者在失败时返回 false

示例

示例 #1 mysql_connect() 示例

<?php
$link
= mysql_connect('localhost', 'mysql_user', 'mysql_password');
if (!
$link) {
die(
'Could not connect: ' . mysql_error());
}
echo
'Connected successfully';
mysql_close($link);
?>

示例 #2 mysql_connect() 示例:使用 hostname:port 语法

<?php
// we connect to example.com and port 3307
$link = mysql_connect('example.com:3307', 'mysql_user', 'mysql_password');
if (!
$link) {
die(
'Could not connect: ' . mysql_error());
}
echo
'Connected successfully';
mysql_close($link);

// we connect to localhost at port 3307
$link = mysql_connect('127.0.0.1:3307', 'mysql_user', 'mysql_password');
if (!
$link) {
die(
'Could not connect: ' . mysql_error());
}
echo
'Connected successfully';
mysql_close($link);
?>

示例 #3 mysql_connect() 示例:使用 ":/path/to/socket" 语法

<?php
// we connect to localhost and socket e.g. /tmp/mysql.sock

// variant 1: omit localhost
$link = mysql_connect(':/tmp/mysql', 'mysql_user', 'mysql_password');
if (!
$link) {
die(
'Could not connect: ' . mysql_error());
}
echo
'Connected successfully';
mysql_close($link);


// variant 2: with localhost
$link = mysql_connect('localhost:/tmp/mysql.sock', 'mysql_user', 'mysql_password');
if (!
$link) {
die(
'Could not connect: ' . mysql_error());
}
echo
'Connected successfully';
mysql_close($link);
?>

注释

注意:

只要将 server 指定为 "localhost" 或 "localhost:port",MySQL 客户端库会越过此值并尝试连接到本地套接字(Windows 中的名字管道)。如果想用 TCP/IP,应该用 "127.0.0.1" 代替 "localhost"。如果 MySQL 客户端库试图连接到一个错误的本地套接字,则应该在 php.ini 中设置 mysql.default_host 的正确路径并把 server 留空。

注意:

脚本一结束,到服务器的连接就被关闭,除非之前已经明确调用 mysql_close() 关闭了。

注意:

Error "Can't create TCP/IP socket (10106)" usually means that the variables_order configure directive doesn't contain character E. On Windows, if the environment is not copied the SYSTEMROOT environment variable won't be available and PHP will have problems loading Winsock.

参见

add a note

User Contributed Notes 25 notes

up
1
nicodenboer at yahoo dot com
11 years ago
Be carefull here if you use utf8.

The file db.opt of your database should contain the following lines:
default-character-set=utf8
default-collation=utf8_general_ci

It means that your database is created to use the utf8 characterset.
One way to accomplish this is:
CREATE DATABASE my_database DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci;

Then, after connecting to it from PHP you should use:
mysql_set_charset("UTF8", $connection);

If you don't do this, you will get ugly problems in case other software is reading and writing to the same database!!!!!!
up
-1
VTool
7 years ago
fcgid_module modules/mod_fcgid.so
FcgidMaxRequestLen 209715200
FcgidConnectTimeout 240
FcgidIOTimeout 240
FcgidBusyScanInterval 240
FcgidBusyTimeout 240
# Esta línea instruye al servidor web para que reconozca un tipo nuevo (php)
AddHandler fcgid-script .php
# Esta línea indica al servidor web donde está instalado PHP.
FcgidInitialEnv PHPRC "c:/php"
# Esta línea indica al servidor web que debe ejecutar la aplicación
# php-cgi.exe cuando un cliente (navegador) solicite una página con
# extensión .php
FcgidWrapper "c:/php/php-cgi.exe" .php
# Con esta línea damos los permisos necesarios para que los clientes puedan
# acceder/ejecutar a los archivos .php
<Directory "c:/Apache/htdocs">
Options Indexes FollowSymLinks Includes ExecCGI
AllowOverride None
Allow from all
</Directory>
up
-4
cory dot mawhorter gmail.com
14 years ago
Hopefully this saves someone some grief.

My dev computer is windows and runs wampserver. I have frequent problems with PHP being unable to connect to MySQL after periods of extreme DB activity.

Long story short, it was because I was not running mysql via named-pipes and Windows was running out of available ports to serve PHP. Apparently, on windows, you have 5000 ports to work with and once they are opened, they remain so for 120 seconds before being released. This causes problems with mysql/networking because a new port is requested for each connection.

You can read more about the problem at:
(Link too long and had to be broken up)
http://dev.mysql.com/doc/refman/5.0/en
/can-not-connect-to-server.html#can-not-connect-to-server-on-windows
?>

Since mysql is on localhost, I can just enable named-pipes (which is how you should have mysql setup if you don't need networking) to get around the problem instead of the workaround listed on that page.

For details, see:
http://dev.mysql.com/tech-resources
/articles/securing_mysql_windows.html
up
-7
Harouk
13 years ago
If you encounter speed problems using this command to a distant server, you can add the line "skip-name-resolve" in your my.cnf to fix it.
up
-8
martinnitram at excite dot com
20 years ago
to use load data local infile function from mysql (at mysql 4.0.16, php 4.3.3), set fifth parameter of mysql_connect() to CLIENT_LOCAL_FILES(128), which based on MYSQL C API ( also mysql server support load file, check by "show variables like 'local_infile' ")

Thank 'phpweb at eden2 dot com' to point this out
up
-9
pepik at gmail dot cz
10 years ago
<?php
$server
= 'y.com';
$login='x';
$pass='x';
$db='x';

$spojeni=mysql_connect($server,$login,$pass) or die ('nelze se pripojit');
mysql_select_db($db,$spojeni);
mysql_query("Set names 'utf8'");
?>
up
-7
chaoscontrol_hq at yahoo dot com
19 years ago
In MySQL4.1 and later, the default password hashing format has changed making it incompatible with 3.x clients.
I found out mysql_connect() works on server versions >= 4.1 when your MySQL user password is blank because password authentication isn't done in that case, otherwise you need to use another connection method (e.g. mysqli).
Also if you are using old MySQL tables on a new server (i.e. the passwords are stored in the old format), then the server will use the old auth method automatically and this function should work in all cases.
Hopefully this will help someone, it had me confused for a while because some of the users on my 4.1 server could connect and some couldn't.
up
-9
amn -at- frognet.net
21 years ago
Just in case you didn't know. You can use mysql_connect in a function to connect to a database and the connection is a super-global... meaning you can use mysql_query in other functions or in no function at all and PHP will use the connection that you opened. This is a handy bit of knowledge that helps if you have a large site with lots of scripts. If you create one function to connect to a db, and call that function in all your scripts, it makes for easier code maintenance since you only have to update one line of code to change your mysql connection instead of updating all your scripts individually.
up
-10
avinc@live,hk
13 years ago
My situation: "I could connect to MySQL from the PHP via Apache and MySQL via the MySQL console, and could not connect via the PHP"

But, PHP only can connect to MySQL using mysql_connect("localhost", "root", "password");

"Its selinux not allowing apache to make remote connections"

Solution:
setsebool -P httpd_can_network_connect=1
up
-10
Anonymous
18 years ago
connect to mysql via named pipe under windows :

in my.ini, add this:

[mysqld]
enable-named-pipe

then connect to the server, then connect to mysql using

mysql_connect('.')
up
-10
rui dot batista at netcabo dot pt
17 years ago
Ever wonder what "default username" is?
<?php
$link
= mysql_connect() or die(mysql_error());
$result = mysql_query("SELECT SESSION_USER(), CURRENT_USER();");
$row = mysql_fetch_row($result);
echo
"SESSION USER: ", $row[0], "<br>\n";
echo
"CURRENT USER: ", $row[1], "<br>\n";
?>
Both are ODBC@localhost in my win2k install, so my advice for windows is:
- create a MySQL user named ODBC with no password
- add localhost to ODBC user [right-click ODBC]
- set schema previleges to ODBC@localhost
- use mysql_connect() with no parms, or do not use ;)
This turns to work also with odbc_connect:
odbc_connect("myDSN", "", "")
up
-10
tpl99 at yandex dot ru
13 years ago
Whenever you open two connections to a single database,
you are likely not to get any error when selecting not existing db.

<?php
$db1
= mysql_connect( ... );
mysql_select_db('existing_db',$db1);

$db2 = mysql_connect( ... );
mysql_select_db('not_existing_db', $db2);

mysql_query(... , $db2);
//will return no errors and the query wouldn't be executed.
?>

Pay attention and you may save few hours of debugging.
up
-11
yangqingrong at wudimei dot com
10 years ago
hello,every one.
do use "127.0.0.1" instead of "localhost" for php5.4-win7 if you feel the speed is slow.because win7 use ipv6 default.
"localhost" is for ipv4.

<?php
$conn
=mysql_connect( "127.0.0.1",
"root",
"pass");
?>
up
-12
abelcheung at gmail dot com
14 years ago
Note that named pipe on Windows is unusable since PHP 5.3, and TCP connection shall be used even in localhost.
up
-10
pascalxusNOSPAM at yahoo dot com
15 years ago
I just wanted to share a common wrapper that I use for executing one line SQL statements. Its an easy wrapper to use that takes care of the connection open/close. Optionally, the mysql_connect can be replaced with mysql_pconnect for persistent connections.

function executeQuery( $query, $db, $nocon )
{
if( $nocon != "nocon" )
if( $db != "" ) connect( $db );
else connect( "pascal_crm" );

$result= mysql_query( $query );
$err = mysql_error();
if( $err != "" ) echo "error=$err ";

if( $nocon != "nocon" )
mysql_close();
return $result;
}

Here's a related mysql_pconnect trivia question:
http://www.codesplunk.com/nr/questions/php17.html
up
-12
arithmetric at gmail dot com
16 years ago
If you are trying to open multiple, separate MySQL connections with the same MySQL user, password, and hostname, you must set $new_link = TRUE to prevent mysql_connect from using an existing connection.

For example, you are opening two separate connections to two different databases (but on the same host, and with the same user and password):

$db1 = mysql_connect($dbhost, $dbuser, $dbpass);
$rv = mysql_select_db($dbname1, $db1);
$db2 = mysql_connect($dbhost, $dbuser, $dbpass);
$rv = mysql_select_db($dbname2, $db2);

At this point, both $db1 and $db2 will have selected the database named by $dbname2.

The workaround is to require that the second MySQL connection is new:

$db1 = mysql_connect($dbhost, $dbuser, $dbpass);
$rv = mysql_select_db($dbname1, $db1);
$db2 = mysql_connect($dbhost, $dbuser, $dbpass, TRUE);
$rv = mysql_select_db($dbname2, $db2);

Now, $db1 should have selected $dbname1, and $db2 should have selected $dbname2.

This has been documented on the mysql_select_db page as well.

Note: This occurs only when the server, username, and password parameters are identical for each mysql_connect statement.
up
-12
Graham_Rule at ed dot ac dot uk
20 years ago
Another solution to the security problems of putting usernames and passwords into scripts. I haven't found this documented anywhere else so thought I'd suggest it for the online documentation. ........

Don't put passwords for mysql into scripts which may be read by any user on the machine. Instead put them into an Apache configuration file and make sure that it is not world-readable. (Apache reads its main config files as root.)

For example, add this to your httpd.conf (and chmod it to 600 or 660) then tell your apache to reload itself (apachectl graceful).

<Directory /var/www/html/mydatabase>
php_value mysql.default_user fred
php_value mysql.default_password secret
php_value mysql.default_host server.example.com
</Directory>

Then all you need in your PHP code is

$handle = mysql_connect() or die(mysql_error());

The passwords etc will only be picked up by scripts running in the named directory (or a sub-directory). The same may be done for virtualhosts etc.

If you don't want to keep reloading your Apache server then you ay test things putting the php_value directives into a (world readable) .htaccess file. (Clearly not for production use.)

If you need to debug the values that are being supplied (or not) then use this snippet:

@syslog(LOG_DEBUG, "Using user=".ini_get("mysql.default_user").
" pass=".ini_get("mysql.default_password").
" host=".ini_get("mysql.default_host"));

(This assumes that you are not running in 'safe_mode' and that you are on a unix of some sort.)
up
-12
bimal at sanjaal dot com
12 years ago
Portable connections: If you migrate your source code from one to different servers and you would like to avoid re-configuration on a new serve, user the $_SERVER['SERVER_NAME'] flag as:

<?php
switch($_SERVER['SERVER_NAME'])
{
case
'server1.example.com':
mysqlconnect('host1', 'user1', 'password1');
mysql_select_db('db1');
break;
case
'server2.example.com':
mysqlconnect('host2', 'user2', 'password2');
mysql_select_db('db2');
break;
}
?>

This makes a conditional connection to mysql database. It automatically chooses the correct server according to the server name from where your script runs.

Hopefully, you like this portable configuration.
up
-12
sholland at napervillegi dot com
14 years ago
If you are getting an error "Can't assign requested address" you may have a problem with the mysql port. I had just moved my server to Mac OS X 10.6 and mysql_connect was giving this error. Going into the /etc/php.ini file and setting the default port number to 3306 fixed the problem.

mysql.default_port = 3306

The php.ini file suggests that PHP will select the port by using the $MYSQL_TCP_PORT or the mysql-tcp entry in /etc/services, but in this case it is not so. /etc/services on my machine has 3306 listed, but it didn't get picked up.

This is sort of a bug report, in that the documented feature isn't working. Please don't delete this until the community decides how to address the problem. This is one of those hair pulling exercises to get fixed.
up
-12
php at lanar dot com dot au
12 years ago
After upgrading mysql sever to 5.5.21 from 5.0.9 on centos, my WinXP stopped being able to connect with host with the error message
'Bad Handshake'.

Eventual solution to problem was to remove MYSQL_CLIENT_SSL from the call to mysql_connect().

I will also report this as a bug.
up
-13
Contact at LinuxIntro dot com
15 years ago
When you connect and expect to use a stored procedure,you must pass a special flag to MySQL via the connect command, otherwise you will not get the results returned, and it will result in this error:
PROCEDURE AlexGrim.GetStats_ForumCategories can't return a result set in the given context

To fix this, change you connection string, adding ",false,65536" as the last 2 fields:
$this->con = mysql_connect($this->h,$this->u,$this->p,false,65536);
up
-14
trev at dedicate dot co dot uk
11 years ago
A little note if your scripts sleep a lot, you want to run exactly the same SQL statement 2+ times and you have the "MySQL has gone away" error a lot.

Try setting the 4th parameter to TRUE as it seems sometimes PHP doesn't spot that resource ID x which it used for the last identical lookup is now dud and so tries to use it, thus bypassing tests such as is_resource() and causing a failure.

This is for when mysql_ping() doesn't work for your situation of course.
up
-13
david dot schueler at wapkamera dot de
14 years ago
If you are getting MySQL Errors like #2006: MySQL server has gone away, and you are using mysql_connect() and pcntl_fork() then make shure that you are reconnecting to the mysql server with each created child which you fork()ed.

I pulled my hair out for many days because i was using the same mysql connection for each child and was getting that "MySQL server has gone away" errors.

Here is a simple example:
<?php
$link
= mysql_connect($db_server, $db_user, $db_pass);
mysql_select_db($db_database,$link));

$pid = pcntl_fork();
if (
$pid == -1)
// Error forking child
elseif ($pid) {
// Parent will be here
} else {
// The child has to esablish a *new* mysql connection.
// if you use mysql_connect without the 4th parameter
// then it will use the connection from the parent. But
// if the child dies, the connection will be unaviable in
// the parent too.
// So, note the "true" as 4th parameter.
$newlink = mysql_connect($db_server, $db_user, $db_pass,true);
mysql_select_db($db_database,$newlink));
// ...
}
?>
up
-21
bmagilavy at avalon-internet dot com
15 years ago
If you trying to connect to a remote server, here are a few things that can go wrong. Perhaps this list will save someone some time:

1. You may need to get in touch with the remote server's tech support:

a. to ensure that you can get through its firewall. It is not necessarily enough to have your server number listed in the recipient site's cpanel remote access host list. It depends on how the server company has things set up;

b. to find out what port number they are using for database connections, which may not be the default used by mysql_connect;

c. If you are using ODBC, the host to which you are trying to connect may or may not have any ODBC drivers installed; and

d. If you are working from a dynamic IP, they may be set up to accommodate it, or you may have to use a proxy. See http://forge.mysql.com/wiki/MySQL_Proxy .

2. If you are working from a shared server yourself, the server number you were sent in the sign-up letter is probably NOT the server number you should be using to connect to a remote database. You need the server number of the machine on which your site is sitting, not your virtual account server number on that machine. You can get this from your own tech support.

I am grateful to Jonathan Jones at Bluehost for this analysis.
up
-25
i dot linker at gmail dot com
13 years ago
MySQL connection string regexp:
~mysql://([^:@/]*):?([^@/]*)@?([^/]*)/?([^/]*)~
To Top