Contents
-
Introducing Tachyon
-
Quick Start
-
Implementing Tachyon
-
Using Settings
-
Using Explorer
-
Using Guaranteed State
-
Using Inventory
-
Using Experience
-
Using Patch Success
-
Troubleshooting
-
Extending Tachyon
-
Training
-
Tachyon Operator v5.0 Lab Guide
-
Tachyon Advanced v5.0 Lab Guide
-
Ex 1 - TCN Adv 5.0 - TIMS Explained
-
Ex 2 - TCN Adv 5.0 - TIMS Functions
-
Ex 3 - TCN Adv 5.0 - SCALE The Relational Model
-
Ex 4 - TCN Adv 5.0 - Creating an Instruction: Critical Services
-
Ex 5 - TCN Adv 5.0 - Creating an Instruction that executes a Script
-
Ex 6 - TCN Adv 5.0 - Visualization and Aggregation
-
Ex 7 - TCN Adv 5.0 - Extending Guaranteed State
-
Ex 8 - TCN Adv 5.0 - Real World Examples for Guaranteed State
-
Ex 9 - TCN Adv 5.0 - Tachyon Activity Record
-
Ex 1 - TCN Adv 5.0 - TIMS Explained
-
Tachyon - Nomad as Content Provider Lab Guide
-
Tachyon Operator v5.0 Lab Guide
-
Reference
Tachyon Activity Record
Tachyon Activity Record, also referred to as Tachyon Agent Historic Data Capture is a mechanism through which the Tachyon Agent continuously captures details of certain events as they happen, in a similar way to Windows Task Manager or Perfmon. During startup, the Agent is also able to detect some events that occurred when it was not running. Data is regularly written into a local, compressed and encrypted persistent store, called an inventory. The inventory is accessible to the Agent language as SQL tables. The Agent periodically aggregates data in order to minimise the amount of storage required, so that each capture source has a live, hourly, daily and monthly table. The whole process is designed to minimise impact on device performance, storage and security.
The Agent has two key mechanisms of knowing when an event occurs that is of interest - event-based and polling-based.
Event-based relies on a source external to the Agent (normally the operating system) providing a notification to indicate that something has happened
Polling-based is where the Agent will periodically check a source of data and work out what has changed by looking at differences in the data returned. Polling intervals means some brief events that occur between polls can be missed.
In this Lab, we will use the historical data to identify what processes have run in the past 7 days that haven't run in the past 30 days. This instruction will allow us to identify possible exploits that may have entered an enterprise recently.
Reviewing the Historical Data
Review Historical Data
In this exercise, we will review some of the historical data captured by the Tachyon agent. This will allow us to get an understanding of how we can use said data to evaluate different things on our Tachyon clients.
- Logged in as 1ETRN\Tachyon_AdminG, close TIMS and relaunch it as administrator from the desktop
- Type the following in. Do not copy/paste
- IntelliSense should kick in and display a wide range values once you type in SELECT * from $. These are all the historical data values available for us to use. Note the data returned. These are the processes that have run in the past day.
- Input the following below the existing line into TIMS and click Run
- Note the data returned, including the LookupCount. This information relates to the anything that DNS resolves on the machine
- Query for different historical data values by using the above SELECT statement
- Typing the SELECT statement up to the $ will present you with all the different values available. Review the different data to get a strong understanding of what is available
- Switch to the LOG view at the bottom on the TIMS window and switch the Logging Level to Trace
- Wait for a few seconds and note a slew of DELETE or Insert statements scroll by. This is the Historical Data functionality operating
- Switch Logging Level back to Info and switch back to the Results pane
SELECT * FROM $Process_Daily;
SELECT * FROM $DNS_Daily;
Establishing processes delta
In this exercise, we are going to determine what processes have run in the past week compared to what processes have run in the past month. We are using these timelines, but you can use any timelines within a month period to write this instruction, or subsequently use parameters to allow the operator to input the timelines.
Processes run in the past 7 days
In this Task, we will find out which processes have run in the past 7 days. In addition, we will capture some information related to the executable for the given processes.
- Clear TIMS. Input the following code and click Run
- In this code, we are first establishing a temp table named @thisweek. Into this table we are selecting ExecutionCount, ExecutionDate, ExecutableHash, and ExecutablePath. The Where statement defines the timeframe we want to evaluate. We are evaluating everything between today, and 7 days ago.
@thisweek = SELECT ExecutionCount, strftime("%Y-%m-%d", datetime(TS, "unixepoch")) as ExecutionDate, ExecutableName, ExecutableHash, ExecutablePath FROM $Process_Daily WHERE ExecutionDate >= datetime(datetrunc(strftime("%s","%environment:now%"),"day"),"unixepoch","-7 day");
Summarize execution over past 7 days
In this task, we will summarize the execution of processes in the past 7 days, as opposed to having an individual row for each execution per day. We are not concerned with what ran on what day, rather just what has run in the past 7 days, and how many times.
- Input the following into TIMS below the existing code from above and click Run
- Here, we are overwriting the @thisweek table with the ExecutableHash, ExecutableName, ExecutablePath, and ExecutionCount for each process we identified in the first query. The ExecutionCount is the sum of execution for each process run in the past 7 days
- Note the output. We no longer have the execution date, as these are all the processes that have run in the past 7 days
@thisweek = SELECT ExecutableHash, ExecutableName, ExecutablePath, SUM(ExecutionCount) as ExecutionCount FROM @thisweek group by ExecutableHash, ExecutableName, ExecutablePath;
Identify Processes that have run in the past month but not in the past 7 days
In this task, we will identify the processes that have run in the past month, minus what has run in the past week. This data set will give us the ability to compare what has run in the past week vs. what has run before that.
- Input the following into TIMS below the existing code from above and click Run
- This code is capturing all Processes run from 8 days out. By design, the daily historical data is held for the past 30 days, so here we get everything that is 8 days or older until 30 days
- Due to this being a lab environment, we may not have any processes showing from more than a week ago. This environment is spun up from a template, and thus the historical data will only go as far back as the start time of the environment at the beginning of this course. Change the -8 to -1 to see the processes that have run in the past day to validate the query.
- Note we are only capturing the ExecutableName here. This is because we simply need something to compare against. When we get the delta in the next task, we'll display all the other values we captured in the initial query.
@thismonth = SELECT ExecutableHash, datetime(datetrunc(TS,"day"),"unixepoch") as ExecutionDate FROM $Process_Daily WHERE ExecutionDate <= datetime(datetrunc(strftime("%s","%environment:now%"),"day"),"unixepoch","-8 day");
Getting the delta between the two data sets
We now have data that shows us what has run in the past 7 days as well as what has run between day 8 and 30. We now need to bring the data together to determine what has run in the past 7 days that hadn't run in before that in the past 30 days.
- Input the following into TIMS below the existing code from above and click Run
- Here, we are getting the ExecutableHash, ExecutableName, ExecutablePath, and ExecutionCount values for every process in @thisweek which is not in @thismonth. This is the delta we are looking for
- Review the dataset here it may be very similar to the @thisweek dataset, since we won't have a large delta due to having limited data in the environment
@delta = SELECT ExecutableHash, ExecutableName, ExecutablePath, ExecutionCount FROM @thisweek WHERE ExecutableHash not in (SELECT ExecutableHash FROM @thismonth);
Getting more process details
Now that we have identified the delta in processes run this week vs. the past month, we will work on the final output of the data. We have 4 fields being returned currently, the ExecutableHash, ExecutableName, ExecutablePath, and ExecutionCount. We will now gather further information on the Executable associated with the process as well as format some of the data for final output.
FOREACH loop for each process in the list
Here, we will use the FOREACH loop function to loop through every process in the list we compiled in the last block. Once the loop has been established, we will execute different things to gather further information regarding each process.
- Input the following into TIMS below the existing code from above
- Note the last block which created a variable named @delta. Here we are taking the data from @delta and looping through each row. What we execute in each loop will be defined below
@fileout = FOREACH @process IN @delta DO
Changing the ExecutablePath to friendly name
The output from the previous queries we have run shows a \device\ExecutablePath. In this task, we will convert this to a c: format. Here we will demonstrate the use of a Replace function.
- Input the following into TIMS below the existing code from above
@file = SELECT "C:" || substr(ExecutablePath,24) as FileName, ExecutableHash, ExecutionCount FROM @process;
Here we are using the substr function to replace text from the ExecutablePath with C:. The current path has the following format: \device\harddiskvolume4\<folder>. Count the number of characters before the <folder>. There are 24 characters. So the substr function we're calling here is piped a value of 24, which will replace the first 24 characters of that value with C:.
FileSystem.GetFileDetails
Here we will gather further file details for the final output. Using the FileSystem.GetFileDetails method, we will gather the CreationDate, ModifiedDate, Owner and Size of the files in the @delta list which we are looping.
- Input the following into TIMS below the existing code from above, highlight the single line and click Run
- Note the output. Both the DateCreated and DateModified fields have a T in the middle and a Z at the end. We want to remove this to show a friendly format in our final output
- Delete the above line from TIMS. Input the following below the existing code
- This code is gathering CreationDate, ModifiedDate, Owner and Size for each file in our loop. For the two dates, we are using a combination of replace and substr to remove the T and the Z from the date format outputted by the method
FileSystem.GetFileDetails(FilePath:"c:\\windows\\notepad.exe");
@newfiledata = foreach @r in @file do @filedata = FileSystem.GetFileDetails(FilePath:@r.FileName); DONE; @filedata = select * from @newfiledata; @filedata = SELECT Attributes, replace(substr(DateCreated,0,20),"T"," ") as CreationDate, replace(substr(DateModified,0,20),"T"," ") as ModifiedDate, FilePath as FileName, Owner, Size as ByteSize FROM @filedata;
FileSystem.GetVersionInfo
Here we will gather further file details for the final output. Using the FileSystem.GetVersionInfo method, we will gather the ProductName, ProductVersion, FileVersion and OriginalFileName of the files in the @delta list which we are looping.
- Input the following into TIMS below the existing code from above
- Note the use of the CASE function here. There are many instances where the file description or the product name are null. For any files we encounter which have these null values, we are inputting 'Not provided' into the respective fields. The output will display it as such
@fileinfo = FileSystem.GetVersionInfo(FileName:@file.FileName); @fileinfo = SELECT FileName, case when length(FileDescription) >1 then FileDescription else "Not provided" end as FileDescription, FileVersion, case when length(ProductName) > 1 then ProductName else "Not provided" end as ProductName, ProductVersion, OriginalFilename FROM @fileinfo;
FileSystem.GetDigitalSignature
Here we will gather further file details for the final output. Using the FileSystem.GetDigitalSignature method, we will gather the CertEffiectiveDate, CertExpiryDate, and CertThumbprint of the files in the @delta list which we are looping.
- Input the following into TIMS below the existing code from above, select just the 1 line and click Run
- Delete the previous line, and input the following into TIMS below the existing code from above
- Here, we are capturing the file name, the certificate effective and expiration dates, as well as the thumbprint of the signing certificate. We are also using the replace/substr combination used previously to remove the T and Z from the dates
FileSystem.GetDigitalSignature(FileName:"c:\\program files\\itunes\\itunes.exe");
@filecert = FileSystem.GetDigitalSignature(FileName:@file.FileName); @filecert = SELECT FileName, replace(substr(EffectiveDate,0,20),"T"," ") as CertEffectiveDate, replace(substr(ExpiryDate,0,20),"T"," ") as CertExpiryDate, Thumbprint as CertThumbprint, substr(Subject,instr(Subject,"CN=")+3) as CertSigner FROM @filecert WHERE CertificateType='Signing' order by ExpiryDate DESC limit 1;
Final Output
We have now gathered a wide variety of data for the processes we captured as our delta of new processes that have run in the past week which didn't run for the rest of the past 30 days. It is time to output the data as part of the instruction. We have captured different data in different variables, we now have to bring it together.
Final Output
- Input the following into TIMS below the existing code from above and click Run
- Note the output. It shows all the different attributes we captured for the file associated with the processes we defined in @delta
- Define the schema and aggregation for the Instruction based on what you learned in the previous lab and run the Instruction via Tachyon. Use different settings to see different outputs. When making changes to the Instruction in TIMS, you simply need to change the version in the Instruction Definition pane. You can then save the Instruction as the same XML file, and Tachyon will allow you to upload it as the new version
SELECT @file.FileName, @file.ExecutableHash, @file.ExecutionCount, @filedata.Attributes, @filedata.ByteSize, @filedata.CreationDate, @filedata.ModifiedDate, case when @filedata.Owner is null then "File no longer present on disk" else @filedata.Owner end as Owner, @filedata.ByteSize, case when @fileinfo.FileDescription is null and ByteSize is null then "File no longer present on disk" else @fileinfo.FileDescription end as FileDescription, @fileinfo.FileVersion, @fileinfo.ProductName, @fileinfo.ProductVersion, @fileinfo.OriginalFilename, @filecert.CertEffectiveDate, @filecert.CertExpiryDate, @filecert.CertThumbprint, case when ByteSize is null then "File no longer present on disk" when @filecert.CertSigner is null then "File not signed" else @filecert.CertSigner end as CertSigner, substr(Replace(@file.FileName,DIRECTORYFROMPATH(@file.FileName), ''),2) as File FROM @file left join @fileinfo on @fileinfo.FileName = @file.FileName left join @filecert on @filecert.FileName = @file.FileName left join @filedata on @file.FileName = @filedata.FileName; DONE;
The complete code block is below:
@thisweek = SELECT ExecutionCount, strftime("%Y-%m-%d", datetime(TS, "unixepoch")) as ExecutionDate, ExecutableName, ExecutableHash, ExecutablePath FROM $Process_Daily WHERE ExecutionDate >= datetime(datetrunc(strftime("%s","%environment:now%"),"day"),"unixepoch","-7 day"); @thisweek = SELECT ExecutableHash, ExecutableName, ExecutablePath, SUM(ExecutionCount) as ExecutionCount FROM @thisweek group by ExecutableHash, ExecutableName, ExecutablePath; @thismonth = SELECT ExecutableHash, datetime(datetrunc(TS,"day"),"unixepoch") as ExecutionDate FROM $Process_Daily WHERE ExecutionDate <= datetime(datetrunc(strftime("%s","%environment:now%"),"day"),"unixepoch","-1 day"); @delta = SELECT ExecutableHash, ExecutableName, ExecutablePath, ExecutionCount FROM @thisweek WHERE ExecutableHash not in (SELECT ExecutableHash FROM @thismonth); @fileout = FOREACH @process IN @delta DO @file = SELECT "C:\\" || substr(ExecutablePath,25) as FileName, ExecutableHash, ExecutionCount FROM @process; @newfiledata = foreach @r in @file do @filedata = FileSystem.GetFileDetails(FilePath:@r.FileName); DONE; @filedata = select * from @newfiledata; @filedata = SELECT Attributes, replace(substr(DateCreated,0,20),"T"," ") as CreationDate, replace(substr(DateModified,0,20),"T"," ") as ModifiedDate, FilePath as FileName, Owner, Size as ByteSize FROM @filedata; @fileinfo = FileSystem.GetVersionInfo(FileName:@file.FileName); @fileinfo = SELECT FileName, case when length(FileDescription) >1 then FileDescription else "Not provided" end as FileDescription, FileVersion, case when length(ProductName) > 1 then ProductName else "Not provided" end as ProductName, ProductVersion, OriginalFilename FROM @fileinfo; @filecert = FileSystem.GetDigitalSignature(FileName:@file.FileName); @filecert = SELECT FileName, replace(substr(EffectiveDate,0,20),"T"," ") as CertEffectiveDate, replace(substr(ExpiryDate,0,20),"T"," ") as CertExpiryDate, Thumbprint as CertThumbprint, substr(Subject,instr(Subject,"CN=")+3) as CertSigner FROM @filecert WHERE CertificateType='Signing' order by ExpiryDate DESC limit 1; SELECT @file.FileName, @file.ExecutableHash, @file.ExecutionCount, @filedata.Attributes, @filedata.ByteSize, @filedata.CreationDate, @filedata.ModifiedDate, case when @filedata.Owner is null then "File no longer present on disk" else @filedata.Owner end as Owner, @filedata.ByteSize, case when @fileinfo.FileDescription is null and ByteSize is null then "File no longer present on disk" else @fileinfo.FileDescription end as FileDescription, @fileinfo.FileVersion, @fileinfo.ProductName, @fileinfo.ProductVersion, @fileinfo.OriginalFilename, @filecert.CertEffectiveDate, @filecert.CertExpiryDate, @filecert.CertThumbprint, case when ByteSize is null then "File no longer present on disk" when @filecert.CertSigner is null then "File not signed" else @filecert.CertSigner end as CertSigner, substr(Replace(@file.FileName,DIRECTORYFROMPATH(@file.FileName), ''),2) as File FROM @file left join @fileinfo on @fileinfo.FileName = @file.FileName left join @filecert on @filecert.FileName = @file.FileName left join @filedata on @file.FileName = @filedata.FileName; DONE;
Lab Summary
In this lab, we worked with the Tachyon Activity Record. TAR is historical data, summarized hourly, daily and monthly. This is very important data, as it allows us to compare what is happening current state with any timeframe over the past month. We used different methods to capture different data and used many of the same functions we learned in earlier Labs.