rDNS security of MySQL remote connections - mysql

Consider a MySQL server that accepts remote connections.
What happens if you have a publicly facing MySQL server, and grant access to e.g.:
'sqluser'#'localhost'
If an attacker now sets his rDNS to "localhost", will he able to access this database?
Is there an extra check that also tries to resolve the rDNS back to the IP?
Regardless, database servers shouldn't be internet facing, but this a what-if-question.

It appears that MySQL uses forward-confirmed reverse DNS (FCrDNS) to counter these kind of attacks.
Most of the logic for the hostname checks can be found in sql/hostname.cc. Moreover, several checks are also performed to make sure that the rDNS doesn't contain an IP or is otherwise poisoned.

Related

MySQL ODBC Driver - Is there a way to block an access of MySQL Connector ODBC Driver?

Good afternoon, i have 2 PC's, where one is my WAMP server, with MySQL Database and so on. And the other i made a connection to my DB throw MySQL Connector ODBC Driver.
My doubt is if is there a way to block access of this second PC to my Server PC ?
I'm learning about MySQL control management, and i came across with this case, and i couldn't found an answer searching about this by myself.
No, there's no builtin mechanism in MySQL Server that detects that a connection attempt is from a MySQL Connector ODBC Driver, and blocks the connection.
It is possible to block connections to the MySQL Server, by setting up the appropriate user definitions in MySQL Server (entries in the mysql.user table).
In MySQL, a user is identified by a user name together with a host (either a DNS hostname or IP address, depending on whether we've specified skip-name-resolve option.)
If we setup MySQL users with wildcard hostname '%', then we are allowing TCP/IP connections from any host or any IP address.
If we remove user entries with a wildcard hostname, and instead create users with a more specific hostname (or IP address), then connections will be allowed only from the specified host/IP address. With a net effect of blocking connections from other hosts.
This topic is more fully addressed in the MySQL Reference Manual
https://dev.mysql.com/doc/refman/5.7/en/connection-access.html
Also, for TCP/IP connection attempts, a network firewall (for example, Iptables on Linux) can be configured to knock down connections before they are even seen by MySQL Server.

Hosted MySql, Views, client Ipaddress change and Access Denied

I have a hosted MySql server with many databases each with many views. I access the server remotely from my office using HeidiSql.
Once in a while the IP address of my office changes. When this happens, I have to add the new office IP address to the server using cPanel and the "Remote MySql" tool so that I can remotely connect again.
However, all of the views have definer: USER#OLD_IP_ADDRESS. If I need to change a view, I get Access Denied. Up to now, I have been deleting the view (yes, i can delete the view) and recreating it, which makes the view's definer USER#NEW_IP_ADDRESS, and then I can edit the view -- until the Ip address changes again.
So, my question is: What is the best practice is an environment like this. Is there a way to define the views once and, without causing a security risk, be able to edit the views after an IP Address change.
Thanks for any guidance.
You could loosen the host in the MySQL user account a bit, according to the IP range of your internet provider. That way, you don't need to change it every time you get a slightly different IP:
user#123.456.789.%
user#123.456.%
This of course loosens the security in this account, but if your password is be a good one, it should not be too risky.
A better way is to make the MySQL server only accessible via SSH. In that case, your MySQL server can be set up using the --skip-networking option, as you always connecting from localhost. Your user account can be user#localhost or user#127.0.0.1, which then would solve your above mentioned problem for all times.
HeidiSQL also supports SSH tunneled MySQL connections, see here for some tutorial.

ATTACK ON AWS RDS MySQL .static.midphase.com resembles IPv4-address itself

I'm running EC2 with MySQL RDS to serve dynamic websites' content.
The server was down due to 'too many connection' error on RDS database.
As it was urgent, I restart database server straight away and the problem gone.
However, I'm unable to see what queries produce those connection (as I didn't run SHOW PROCESS LISTS before reboot RDS).
CloudWatch show 250+ connections during period of issue which is obviously huge distinction from normal operating on other days.
I try to address the issue by see log in RDS, but there is quite a minimal message there.
The error message
2014-05-03 06:10:08 3628 [Warning] IP address '173.244.206.19' has been resolved to the host name '173.244.206.19.static.midphase.com', which resembles IPv4-address itself.
From above, 173.244.206.19 is not in our IP list both public and private. (but connection open to 0.0.0.0 secured with password which I'm going to limit IP remote in security group soon)
Questions
Is 173.244.206.19.static.midphase.com is something to do with RDS by default. I think this is obviously an attack sign but just would like to confirm.
What does 'resembles IPv4-address itself' mean? As this is RDS database server only, why server does need to resolve DNS?
Are there any way to digging into this for further detail (e.g. to see specific query).
I'm going to prevent this by only limit the IP access along with CloudWatch alarm setting for 10+ connections. Anything else I should do.
Thank you for reading through this guys. I'm the only developer in company start-up which take care for all front-end/backend/application/network. Therefore, apology if there are dummy questions out here.
However, your help would be really appreciated and will save a bit of my life writing the report.
You are maybe the target of a DDOS attack or a brute-force password discovery attempt.
I would report this to AWS support - as they can help to mitigate the effect of the attack.
As a best practice, we do not recommend to use 0.0.0.0/0 as source IP address for incoming connection rule in Security Group.
Try to restrict which IP addresses are authorised to connect to your database.
If you are accessing from on prem network, specify only your on-prem address range.
If you're accessing your database from an app server installed on EC2, use the ID of the App Server Security Group (sg-xxxx) as source authorised to connect to your database.

Restricting MySQL connections from localhost to improve security

I heard that anyone that knows my MySQL Username and Password can access it, Even if it's listening only to localhost.
Supposing my info is as following:
USER: root
PASS: 123456
Host: LOCALHOST (only)
How is it possible that anyone out there (local) can access it?
If you restrict access from remote hosts to your usernames and passwords then someone won't be able to access the database externally.
You could also configure your firewall to only allow traffic to 3306 (MySQL Default Port) from the localhost machine.
Update
To setup your user so they can only access through LOCALHOST use:
GRANT ALL PRIVILEGES ON *.* TO db_user #'localhost' IDENTIFIED BY 'db_passwd';
GRANT ALL PRIVILEGES ON *.* TO db_user #'127.0.0.1' IDENTIFIED BY 'db_passwd';
Also, bind your MySQL server to the local address. You can do this by editing the [mysqld] section of my.cnf:
[mysqld]
bind-address = 127.0.0.1
you can block direct access to MySQL at the firewall or within MySQL itself, but the most likely way you'd be hacked is through an insecure web application - in that situation the attacker would most likely be able to read your database login and connect from the server.
So keep your applications secure - keep everything updated, don't allow file uploads, use suPHP if you have multiple accounts etc.
If you restrict your mysql application follow this steps:
1.You could just block port 3306. If the site is on the same server then it will still be able to access the database using localhost as the hostname.
2.Just add "bind-address = 127.0.0.1" to the "[mysqld]" section of their my.cnf file to restrict access to localhost only.
Most of people use this type of restriction.
This is an older question that I stumbled across, but if Darkeden had phpMyAdmin or similar running, anyone can log in to that using valid MySQL credentials.
If it was compromised, then in addition to restricting connections, change all passwords.
I didn't see an answer that answered his (adjusted) question - he has locked it to localhost and the attacker is still getting in.
If you have truly restricted it to local host (check using netstat -an | egrep 3306 to check it is listening to 127.0.0.1 not 0.0.0.0),
then the only way of accessing it is to originate a connection from that local host.
Initial steps to take:
probably rebuild a replacement system from scratch and hardening it before you make it publicly accessible (having a repeatable recipe eg using ansible will help as you may have to go through a few iterations to learn how he gets in)
Check with reputable security scanners what you obvious holes are,
Get help from a security professional (depends if you want to spend $ or time and frustration to fix)
Apply security patches,
Remove services you don't need,
restrict the database access to only those programs that need it,
redo all your passwords,
check for installed root kits, and other viruses,
secure your server if at your own office and train staff in handling social engineering,
use a service that will monitor and filter the requests coming through and deny direct access (eg use cloudflare as a cheep starting point)
check for keyboard loggers (physical and software and other viruses) on all machines used to access the server),
check for physical means of logging your keystrokes in accessing your server (eg web cam style used in atm), the more exotic include sound (https://en.wikipedia.org/wiki/Acoustic_cryptanalysis), typing with a nearby wifi access point (eg https://www.schneier.com/blog/archives/2016/08/keystroke_recog.html)
Add an audit trail and monitor database activity to work out how he is getting through, but at least you need to do all the obvious securing first because otherwise he will just hop from one security hole to another
He could be also getting through using:
accessing via some program you are running (eg a web server) that is externally accessible and has a security hole that allows him to run arbitrary sql commands through its existing database connection - see https://www.w3schools.com/sql/sql_injection.asp
tricking some program he has access to from outside to proxy a connection for him to localhost:3306 (eg through a miss-configured network firewall on the machine)
tricking some program to run a local program (bash. mysql etc), and from there gaining access to the database - buffer overflows and other specially crafted data is a common issue to running arbitrary code
man in the middle attack on a connection that has legitimate access
bugs in a program that is automatically or manually processing data from outside, eg email, processing of postscript/pdf/any document with scripting processing - even viewing a text file can be dangerous - see https://www.proteansec.com/linux/blast-past-executing-code-terminal-emulators-via-escape-sequences/
social engineering a way through getting people to give you access
managing to get a hardware device attached to a computer that has access (how many people will pick up a "memory stick" lying in the work car park and check it out instead its a "programmable keyboard", and ALL computers trust keyboards!)
and then many more all the other sorts of methods I don't know, but those that are involved share ...
Just remember that you need to have practical security, I think xkcd says it just right: https://xkcd.com/538/

MySQL user host networking

How is the host for a MySQL user evaluated by the database? My server tries to connect to the database from myhostname but fails even though I've set the hostname for that server in /etc/hostname It does work when I use an IP though.
The user was created like so:
GRANT ALL ON db.* TO 'dude'#'myhostname';
The MySQL error will tell you the hostname the server machine thinks your user is connecting from. Depending on DNS settings, this may or may not be the hostname your client thinks is assigned to itself. The name as seen from the server is the one you need to set in your GRANT statement.
(Which is logical. Suppose I know that the server gives privileges to host Alice. I have host Bob. Since it's my host, I can change its name to Alice. If just doing this granted me Alice's privileges, the whole GRANT scheme would be completely insecure! What happens is that my host thinks it's Alice, but the server sees my IP, asks the DNS "Who is this?" and receives "He's Bob". I still can steal Alice's privileges, but I need to compromise the DNS records somehow)
In a pinch, add the client IP and hostname to the server /etc/hosts file. This is a hack, however, and proper DNS setting is the way to go: a forgotten hosts hack might cost you a long time of head scratching a few months down the road.
As explained in DNS Lookup Optimization and the Host Cache from the MySQL manual:
The server performs host name resolution using the thread-safe gethostbyaddr_r() and gethostbyname_r() calls if the operating system supports them. Otherwise, the thread performing the lookup locks a mutex and calls gethostbyaddr() and gethostbyname() instead.
Therefore the resolution of the connecting IP to myhostname is a matter for the operating-system, rather than MySQL. You should first determine that your OS is correctly resolving the client IP and, if not, debug your OS or nameservice configuration (questions on this subject might be better directed to Super User or Sever Fault, rather than StackOverflow).