Parsing .job Files
John McCash recently posted an interesting article to the SANS Forensic blog on decoding the binary Scheduled Task .job file format (John's article referred to tasks created using at.exe).
Based on John's article, I wrote a Perl script that parses the binary structure of the .job file header, and also gets some of the variable data that follows the header. For right now, I've got a number of the header fields translated and extracted, and I've been testing against a couple of .job files I've created on my own system; the output appears as follows:
C:\Perl\forensics>jobparse.pl d:\cases\apple.job
Command : :C:\Program Files\Apple Software Update\SoftwareUpdate.exe -task
Status : Task is disabled
Last Run Date: Thu Jul 16 16:21:00 2009 Exit Code : 0x0
So, this is a good start. I've had engagements where analysis of the Scheduled Tasks log file proved to be critical, so I can see how being able to get details from the .job file might also be important. Also, as John pointed out, information about the binary structure of .job files may assist you if you find indications of deleted .job files in unallocated space. If you get a hit and are able to backtrack a bit, you may find enough information in unallocated space to be able to decipher the header fields.
As a side note, I did find some minor issues with how the MS documentation identifies some of the fields in the structures; for example, the documentation shows a total of 9 2-byte fields for the UUID, but UUIDs are defined as being 128-bits long (ie, 8 bytes); this threw my initial parsing code off by 2 bytes. Interestingly enough, this applies to Windows XP systems, and the last run time for the job is maintained in the header as a 128-bit wide field; here I was thinking that the new date format was only part of Vista and Windows 7! Eesh!
Addendum: Interesting thought...the timestamps (and other data) embedded in .job files are updated when the task is run; therefore, this information can be used to provide indications of activity that modifies file MAC times, such as AV scanning, searches, or AF tactics...
Based on John's article, I wrote a Perl script that parses the binary structure of the .job file header, and also gets some of the variable data that follows the header. For right now, I've got a number of the header fields translated and extracted, and I've been testing against a couple of .job files I've created on my own system; the output appears as follows:
C:\Perl\forensics>jobparse.pl d:\cases\apple.job
Command : :C:\Program Files\Apple Software Update\SoftwareUpdate.exe -task
Status : Task is disabled
Last Run Date: Thu Jul 16 16:21:00 2009 Exit Code : 0x0
So, this is a good start. I've had engagements where analysis of the Scheduled Tasks log file proved to be critical, so I can see how being able to get details from the .job file might also be important. Also, as John pointed out, information about the binary structure of .job files may assist you if you find indications of deleted .job files in unallocated space. If you get a hit and are able to backtrack a bit, you may find enough information in unallocated space to be able to decipher the header fields.
As a side note, I did find some minor issues with how the MS documentation identifies some of the fields in the structures; for example, the documentation shows a total of 9 2-byte fields for the UUID, but UUIDs are defined as being 128-bits long (ie, 8 bytes); this threw my initial parsing code off by 2 bytes. Interestingly enough, this applies to Windows XP systems, and the last run time for the job is maintained in the header as a 128-bit wide field; here I was thinking that the new date format was only part of Vista and Windows 7! Eesh!
Addendum: Interesting thought...the timestamps (and other data) embedded in .job files are updated when the task is run; therefore, this information can be used to provide indications of activity that modifies file MAC times, such as AV scanning, searches, or AF tactics...