-
Notifications
You must be signed in to change notification settings - Fork 66
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Concerns from Reddit #131
Comments
Doesn't the way the values are escaped make any SQL queries executed by this library subjected to a SQL injection attack? |
Not sure yet, need to dive into this deeper, and also deeper in the MySQL protocol to see how we can improve this. Always thought PDO would send a statement + arguments to MySQL and let MySQL put them together. If that's possible that sounds like the route we should take here as well. Wdyt @clue ? |
Firstly regarding the present state, I THINK that these issues will only be exploitable on systems that use the NO_BACKSLASH_ESCAPES mode, or systems that use one of a few specific multibyte character encodings, gbk being a notable example. This ticket addresses three different issues:
My strongly preferred solution to this would be to use genuine prepared statements, as this would solve all three issues in a totally robust way. The library would not need to track how the server is configured at all. The only downsides I can see are:
I think there may be a very simple partial fix that can be done very easily though: change the escape character from a backslash to the ANSI standard of doubling up the single quote. This form is valid for both SQL modes and so addresses [2], and I also believe that it just so happens that there are no character encodings where that particular byte injected into a multibyte character could be used maliciously, thus also solving [3]. This is not a good solution IMO, but may be worth considering as a quick stopgap. I'm not a MySQL user so I apologise if there are any mistakes or misunderstandings in the above! PS. Regarding PDO - be aware that by default the mysql driver uses PDO::ATTR_EMULATE_PREPARES meaning they are also doing client-side escaping (albeit with more attention to server configuration). This is imo a bad approach, and you should disable PDO::ATTR_EMULATE_PREPARES when comparing. |
@WyriHaximus Thanks for bringing this up (can you link to the original discussion?) and thanks to @therealgaxbo for the excellent evaluation 👍
I agree that this is suboptimal and should be improved in a future version. I also agree that while this may be annoying at times, this usually doesn't cause any major issues because it's easy to work around by not mixing literal values with question marks and placeholder values at once. PRs to address this welcome!
This is an interesting one! I haven't personally encountered this in the real world, but I agree that this may indeed be an issue for such installations. PRs to address this welcome!
This is correct. This library doesn't currently provide any explicit support to change the charset (#133) and kind of assumes an ASCII-compatible charset (Latin1/ISO-8859-1, UTF-8 and friends). In case of an ASCII-compatible charset encoding (which includes a multi-byte charset encodings such as UTF-8), I don't currently see how this could cause any issues (except for the NO_BACKSLASH_ESCAPES option mentioned above). In case of other multi-byte charset encodings (GBK comes to mind), this may indeed be used to cause havoc. I agree this is clearly something that should be addressed and I'm not sure how widespread this problem is in the real world. As a very reasonable work around, it's a good idea to stick to UTF-8 which shouldn't show this issue. I could even see us limiting this to UTF-8 via #133 for security reasons until we have better support for this in the future. PRs to address this welcome!
I agree that support for prepared statements would be nice. As you've pointed out, there are some pros and cons to each approach, so I could also see us adding an option similar to PDO's. PRs to address this welcome! |
It was from here: https://www.reddit.com/r/PHP/comments/ms4bns/mysqlis_features_you_probably_would_like_to_know/guygere/?context=3 |
The first problem is that the parser for locating placeholders is literally strpos($sql, '?');. If you have a query with a literal ? in it then it will fail - e.g. "select col1, 'wat?' some_literal from table where id=?" then you will get an exception. This might not be a very common occurrence and indeed you may never run into it, but it show a great lack of attention to fundamental functionality.
Worse is the way that the values are then escaped. It's basically a direct reimplementation of mysql_escape_string(). Note I didn't say mysqli_escape_string, nor mysql_real_escape_string(). So this library is subject to all of the usual multibyte encoding pitfalls.
The text was updated successfully, but these errors were encountered: