Bitdefender Hypervisor Memory Introspection
lixagent.h File Reference
#include "aghcall.h"
#include "agent.h"

Go to the source code of this file.

Data Structures

struct  _LIX_AGENT_HEADER
 Header with information about running code inside the guest. More...
 
struct  _LIX_AGENT_TOKEN
 The tokens used by an agent. More...
 
struct  _LIX_AGENT_DATA
 Describes the data of an agent. More...
 
struct  _LIX_AGENT_THREAD
 Describes an agent-thread running inside the guest. More...
 
struct  _LIX_AGENT
 Describe an agent running inside the guest. More...
 
struct  _LIX_AGENT_FUNCTIONS_LIST
 A list of functions required by agent. More...
 
struct  _LIX_AGENT_FUNCTINS
 The functions required by the agent. More...
 
struct  _LIX_AGENT_HANDLER
 Describes a handlers that contains the data required by the agent. More...
 
struct  _LIX_AGENT_INIT_ARGS
 Arguments of the init agent. More...
 
struct  _LIX_AGENT_UNINIT_ARGS
 Arguments of the uninit agent. More...
 
struct  _LIX_AGENT_CREATE_THREAD_ARGS
 Arguments of the create-thread agent. More...
 
struct  _LIX_AGENT_THREAD_DEPLOY_FILE_ARGS
 Arguments of the deploy-file agent. More...
 
struct  _LIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS
 Arguments of the exec agent. More...
 
struct  _LIX_AGENT_THREAD_RUN_CLI_ARGS
 Arguments of the run command-line agent. More...
 

Macros

#define LIX_AGENT_MAX_FUNCTIONS   256
 
#define LIX_AGENT_MAX_NAME_LENGTH   128
 
#define LIX_AGENT_MAX_ARGS_LENGTH   1024
 

Typedefs

typedef struct _LIX_TASK_OBJECT LIX_TASK_OBJECT
 
typedef INTSTATUS(* PFUNC_AgentCallbackHypercall) (void *Context)
 Hypercall callback prototype. More...
 
typedef INTSTATUS(* PFUNC_AgentCallbackCompletion) (void *Context)
 Completion callback prototype. More...
 
typedef enum _LIX_AGENT_HYPERCALL LIX_AGENT_HYPERCALL
 Agent hypercall type. More...
 
typedef enum _LIX_AGENT_TAG LIX_AGENT_TAG
 Tag used to identify an agent with a handler. More...
 
typedef struct _LIX_AGENT_HEADER LIX_AGENT_HEADER
 Header with information about running code inside the guest. More...
 
typedef struct _LIX_AGENT_HEADERPLIX_AGENT_HEADER
 
typedef struct _LIX_AGENT_TOKEN LIX_AGENT_TOKEN
 The tokens used by an agent. More...
 
typedef struct _LIX_AGENT_DATA LIX_AGENT_DATA
 Describes the data of an agent. More...
 
typedef struct _LIX_AGENT_DATAPLIX_AGENT_DATA
 
typedef struct _LIX_AGENT_THREAD LIX_AGENT_THREAD
 Describes an agent-thread running inside the guest. More...
 
typedef struct _LIX_AGENT_THREADPLIX_AGENT_THREAD
 
typedef struct _LIX_AGENT LIX_AGENT
 Describe an agent running inside the guest. More...
 
typedef struct _LIX_AGENTPLIX_AGENT
 
typedef struct _LIX_AGENT_FUNCTIONS_LIST LIX_AGENT_FUNCTIONS_LIST
 A list of functions required by agent. More...
 
typedef struct _LIX_AGENT_FUNCTIONS_LISTPLIX_AGENT_FUNCTIONS_LIST
 
typedef struct _LIX_AGENT_FUNCTINS LIX_AGENT_FUNCTIONS
 The functions required by the agent. More...
 
typedef struct _LIX_AGENT_FUNCTINSPLIX_AGENT_FUNCTIONS
 
typedef struct _LIX_AGENT_HANDLER LIX_AGENT_HANDLER
 Describes a handlers that contains the data required by the agent. More...
 
typedef struct _LIX_AGENT_HANDLERPLIX_AGENT_HANDLER
 
typedef struct _LIX_AGENT_INIT_ARGS LIX_AGENT_INIT_ARGS
 Arguments of the init agent. More...
 
typedef struct _LIX_AGENT_INIT_ARGSPLIX_AGENT_INIT_ARGS
 
typedef struct _LIX_AGENT_UNINIT_ARGS LIX_AGENT_UNINIT_ARGS
 Arguments of the uninit agent. More...
 
typedef struct _LIX_AGENT_UNINIT_ARGSPLIX_AGENT_UNINIT_ARGS
 
typedef struct _LIX_AGENT_CREATE_THREAD_ARGS LIX_AGENT_CREATE_THREAD_ARGS
 Arguments of the create-thread agent. More...
 
typedef struct _LIX_AGENT_CREATE_THREAD_ARGSPLIX_AGENT_CREATE_THREAD_ARGS
 
typedef struct _LIX_AGENT_THREAD_DEPLOY_FILE_ARGS LIX_AGENT_THREAD_DEPLOY_FILE_ARGS
 Arguments of the deploy-file agent. More...
 
typedef struct _LIX_AGENT_THREAD_DEPLOY_FILE_ARGSPLIX_AGENT_THREAD_DEPLOY_FILE_ARGS
 
typedef struct _LIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS LIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS
 Arguments of the exec agent. More...
 
typedef struct _LIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGSPLIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS
 
typedef struct _LIX_AGENT_THREAD_RUN_CLI_ARGS LIX_AGENT_THREAD_RUN_CLI_ARGS
 Arguments of the run command-line agent. More...
 
typedef struct _LIX_AGENT_THREAD_RUN_CLI_ARGSPLIX_AGENT_THREAD_RUN_CLI_ARGS
 

Enumerations

enum  _LIX_AGENT_HYPERCALL { lixAgentHypercallNone = 0, lixAgentHypercallVmcall, lixAgentHypercallInt3 }
 Agent hypercall type. More...
 
enum  _LIX_AGENT_TAG {
  lixAgTagNone = 0, lixAgTagInit, lixAgTagUninit, lixAgTagCreateThread,
  lixAgThreadTagDeployFile, lixAgThreadTagDeployFileExec, lixAgThreadTagRunCommand
}
 Tag used to identify an agent with a handler. More...
 

Functions

INTSTATUS IntLixAgentInject (LIX_AGENT_TAG Tag, PFUNC_AgentCallbackHypercall HypercallCallback, PFUNC_AgentCallbackCompletion CompletionCallback)
 Schedule an agent injection inside the guest. More...
 
INTSTATUS IntLixAgentThreadInject (LIX_AGENT_TAG Tag, DWORD TagEx, AGENT_TYPE AgentType, PFUNC_AgentCallbackHypercall HypercallCallback, PFUNC_AgentCallbackCompletion CompletionCallback, const char *Name, BYTE *ContentAddress, DWORD ContentSize)
 Schedule an thread-agent injection inside the guest. More...
 
INTSTATUS IntLixAgentActivatePendingAgent (void)
 Activates a pending agent that waits to be injected. More...
 
void IntLixAgentEnableInjection (void)
 Enables agent injections. More...
 
AG_WAITSTATE IntLixAgentGetState (DWORD *Tag)
 Gets the global agents state. More...
 
void IntLixAgentDisablePendingAgents (void)
 Disables all pending agents. More...
 
void IntLixAgentNameRemoveByAgid (DWORD Agid)
 Iterates through all agent names and removes the entry that contains the provided ID. More...
 
DWORD IntLixAgentNameGetTagByAgid (DWORD Agid)
 Iterates through all agent names and returns the tag of the agent that has the provided agent ID. More...
 
LIX_AGENT_TAG IntLixAgentIncProcRef (const char *Name)
 Checks if a process is an agent or not, and increments the ref count of that name. More...
 
LIX_AGENT_TAG IntLixAgentDecProcRef (const char *Name, BOOLEAN *Removed)
 Checks if a process is an agent or not, and decrements the ref count of that name. More...
 
INTSTATUS IntLixAgentHandleInt3 (QWORD Rip)
 Called when a INT3 instruction from the current running agent is executed. More...
 
INTSTATUS IntLixAgentHandleVmcall (QWORD Rip)
 Handle a VMCALL that was executed inside the guest. More...
 
void IntLixAgentInit (void)
 Initialize the agents state. More...
 
INTSTATUS IntLixAgentUninit (void)
 Uninit the agents state. More...
 
LIX_AGENT_HANDLERIntLixAgentGetHandlerByTag (LIX_AGENT_TAG AgentTag)
 Iterates through all agent handlers and search the entry that has the provided tag. More...
 
LIX_AGENT_HANDLERIntLixAgentThreadGetHandlerByTag (LIX_AGENT_TAG AgentTag, LIX_AGENT_TAG ThreadTag)
 Iterates through all thread-agent handlers and search the entry that has the provided tag. More...
 
void IntLixAgentSendEvent (AGENT_EVENT_TYPE Event, DWORD AgentTag, DWORD ErrorCode)
 Send an event to the integrator that contains the AGENT_EVENT_TYPE, tag of the agent and the last error code. More...
 

Macro Definition Documentation

◆ LIX_AGENT_MAX_ARGS_LENGTH

#define LIX_AGENT_MAX_ARGS_LENGTH   1024

Definition at line 14 of file lixagent.h.

Referenced by IntLixDepInjectProcess().

◆ LIX_AGENT_MAX_FUNCTIONS

#define LIX_AGENT_MAX_FUNCTIONS   256

Definition at line 11 of file lixagent.h.

◆ LIX_AGENT_MAX_NAME_LENGTH

#define LIX_AGENT_MAX_NAME_LENGTH   128

Definition at line 13 of file lixagent.h.

Typedef Documentation

◆ LIX_AGENT

typedef struct _LIX_AGENT LIX_AGENT

Describe an agent running inside the guest.

◆ LIX_AGENT_CREATE_THREAD_ARGS

Arguments of the create-thread agent.

◆ LIX_AGENT_DATA

Describes the data of an agent.

◆ LIX_AGENT_FUNCTIONS

The functions required by the agent.

◆ LIX_AGENT_FUNCTIONS_LIST

A list of functions required by agent.

◆ LIX_AGENT_HANDLER

Describes a handlers that contains the data required by the agent.

◆ LIX_AGENT_HEADER

Header with information about running code inside the guest.

◆ LIX_AGENT_HYPERCALL

Agent hypercall type.

◆ LIX_AGENT_INIT_ARGS

Arguments of the init agent.

◆ LIX_AGENT_TAG

Tag used to identify an agent with a handler.

◆ LIX_AGENT_THREAD

Describes an agent-thread running inside the guest.

◆ LIX_AGENT_THREAD_DEPLOY_FILE_ARGS

Arguments of the deploy-file agent.

◆ LIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS

◆ LIX_AGENT_THREAD_RUN_CLI_ARGS

Arguments of the run command-line agent.

◆ LIX_AGENT_TOKEN

The tokens used by an agent.

◆ LIX_AGENT_UNINIT_ARGS

Arguments of the uninit agent.

◆ LIX_TASK_OBJECT

Definition at line 17 of file lixagent.h.

◆ PFUNC_AgentCallbackCompletion

typedef INTSTATUS(* PFUNC_AgentCallbackCompletion) (void *Context)

Completion callback prototype.

Parameters
[in]ContextThe running agent.

Definition at line 38 of file lixagent.h.

◆ PFUNC_AgentCallbackHypercall

typedef INTSTATUS(* PFUNC_AgentCallbackHypercall) (void *Context)

Hypercall callback prototype.

Parameters
[in]ContextThe running agent.

Definition at line 26 of file lixagent.h.

◆ PLIX_AGENT

typedef struct _LIX_AGENT * PLIX_AGENT

◆ PLIX_AGENT_CREATE_THREAD_ARGS

◆ PLIX_AGENT_DATA

typedef struct _LIX_AGENT_DATA * PLIX_AGENT_DATA

◆ PLIX_AGENT_FUNCTIONS

◆ PLIX_AGENT_FUNCTIONS_LIST

◆ PLIX_AGENT_HANDLER

◆ PLIX_AGENT_HEADER

◆ PLIX_AGENT_INIT_ARGS

◆ PLIX_AGENT_THREAD

◆ PLIX_AGENT_THREAD_DEPLOY_FILE_ARGS

◆ PLIX_AGENT_THREAD_DEPLOY_FILE_EXEC_ARGS

◆ PLIX_AGENT_THREAD_RUN_CLI_ARGS

◆ PLIX_AGENT_UNINIT_ARGS

Enumeration Type Documentation

◆ _LIX_AGENT_HYPERCALL

Agent hypercall type.

Enumerator
lixAgentHypercallNone 

Invalid hypercall type.

lixAgentHypercallVmcall 

Hypercall using VMCALL instruction.

lixAgentHypercallInt3 

Hypercall using INT3 instruction.

Definition at line 45 of file lixagent.h.

◆ _LIX_AGENT_TAG

Tag used to identify an agent with a handler.

Enumerator
lixAgTagNone 
lixAgTagInit 

The init agent.

lixAgTagUninit 

The uninit agent.

lixAgTagCreateThread 

The create thread agent.

lixAgThreadTagDeployFile 

Deploy a file.

lixAgThreadTagDeployFileExec 

Execute a file (process).

lixAgThreadTagRunCommand 

Run a custom command.

Definition at line 56 of file lixagent.h.

Function Documentation

◆ IntLixAgentActivatePendingAgent()

INTSTATUS IntLixAgentActivatePendingAgent ( void  )

Activates a pending agent that waits to be injected.

The steps required to activate a pending agent are:

  • allocate slack space (used by init/uninit agents) if the agent is not already deployed.
  • deploy the agent buffer that contains all the required data resolved (function addresses, args, tokens).
  • find a suitable instruction of length 1
  • replace the instruction with a INT3 instruction
Return values
INT_STATUS_SUCCESSOn success.
INT_STATUS_NOT_INITIALIZEDIf is not safe to inject the agent;
INT_STATUS_NOT_NEEDED_HINTIf no agent waits to be injected; if an agent is already running.
INT_STATUS_ALREADY_INITIALIZEDIf an agent with the same name is already running.
INT_STATUS_INSUFFICIENT_RESOURCESIf the memory alloc fails.

Definition at line 1082 of file lixagent.c.

Referenced by IntAgentActivatePendingAgent(), IntLixAgentEnableInjection(), IntLixAgentExit(), IntLixAgentInject(), IntLixAgentThreadExit(), and IntLixAgentThreadInject().

◆ IntLixAgentDecProcRef()

LIX_AGENT_TAG IntLixAgentDecProcRef ( const char *  Name,
BOOLEAN Removed 
)

Checks if a process is an agent or not, and decrements the ref count of that name.

Each time a process terminates, we check if it was an agent, and we decrement the reference count if its name. Once the reference count of an agent name reaches 0, it will be removed.

Parameters
[in]NameThe image name of the process which is checked.
[out]RemovedTrue if the agent was removed.
Return values
Theagent tag, if the process is found to be an agent.

Definition at line 1907 of file lixagent.c.

Referenced by IntLixTaskDestroy(), and IntLixTaskHandleExec().

◆ IntLixAgentDisablePendingAgents()

void IntLixAgentDisablePendingAgents ( void  )

Disables all pending agents.

This function should be called during the uninit phase, as it will disable all the pending agents. These agents will never be injected inside the guest.

Definition at line 1844 of file lixagent.c.

Referenced by IntAgentDisablePendingAgents(), and IntLixGuestNew().

◆ IntLixAgentEnableInjection()

void IntLixAgentEnableInjection ( void  )

Enables agent injections.

Definition at line 1964 of file lixagent.c.

Referenced by IntAgentEnableInjection(), and IntLixGuestNew().

◆ IntLixAgentGetHandlerByTag()

LIX_AGENT_HANDLER* IntLixAgentGetHandlerByTag ( LIX_AGENT_TAG  AgentTag)

Iterates through all agent handlers and search the entry that has the provided tag.

Parameters
[in]AgentTagThe agent tag.
Return values
Onsuccess, returns the found handler, otherwise returns NULL.

Definition at line 408 of file lixaghnd.c.

Referenced by IntLixAgentCreate(), IntLixAgentThreadGetHandlerByTag(), IntLixGuestAllocate(), and IntLixGuestDeployUninitAgent().

◆ IntLixAgentGetState()

AG_WAITSTATE IntLixAgentGetState ( DWORD Tag)

Gets the global agents state.

Parameters
[out]TagOptional agent tag, if an agent is active or pending.
Return values
agActiveIf there's an active agent.
agWaitingIf there's a pending agent.
agNoneIf there are no active or pending agents.

Definition at line 1804 of file lixagent.c.

Referenced by IntAgentGetState().

◆ IntLixAgentHandleInt3()

INTSTATUS IntLixAgentHandleInt3 ( QWORD  Rip)

Called when a INT3 instruction from the current running agent is executed.

This function checks if the INT3 instruction is the previously replaced instruction. If true and the instruction is not restored the IntLixAgentStart is called to start the current agent (the instruction is restored only if another CPU already restored the instruction). Otherwise the function checks if the RIP comes from our agents and handles the breakpoint.

Parameters
[in]RipThe address of the INT3 instruction.
Return values
INT_STATUS_SUCCESSOn success.
INT_STATUS_NOT_FOUNDIf the breakpoint is generated from an unrecognized RIP.

Definition at line 1573 of file lixagent.c.

Referenced by IntAgentHandleInt3().

◆ IntLixAgentHandleVmcall()

INTSTATUS IntLixAgentHandleVmcall ( QWORD  Rip)

Handle a VMCALL that was executed inside the guest.

This function handles VMCALLs that took place inside the guest.

Parameters
[in]RipThe address of the VMCALL instruction.
Return values
INT_STATUS_SUCCESSOn success.

Definition at line 1760 of file lixagent.c.

Referenced by IntAgentHandleVmcall().

◆ IntLixAgentIncProcRef()

LIX_AGENT_TAG IntLixAgentIncProcRef ( const char *  Name)

Checks if a process is an agent or not, and increments the ref count of that name.

Each time a process is created, we check if its name matches the name of a previously injected agent. If it does, we flag that process as an agent, and we increment the reference count of the name.

Parameters
[in]NameThe image name of the process which is checked.
Return values
Theagent tag, if the process is found to be an agent.

Definition at line 1869 of file lixagent.c.

Referenced by IntLixTaskCreate(), and IntLixTaskHandleExec().

◆ IntLixAgentInit()

void IntLixAgentInit ( void  )

Initialize the agents state.

Definition at line 1978 of file lixagent.c.

Referenced by IntLixGuestNew().

◆ IntLixAgentInject()

INTSTATUS IntLixAgentInject ( LIX_AGENT_TAG  Tag,
PFUNC_AgentCallbackHypercall  HypercallCallback,
PFUNC_AgentCallbackCompletion  CompletionCallback 
)

Schedule an agent injection inside the guest.

This function schedule the injection of an agent identified by the LIX_AGENT_TAG inside the guest space. This function is used directly only for internal agents (init/uninit).

Parameters
[in]TagThe internal LIX_AGENT_TAG of the agent.
[in]HypercallCallbackThis callback can be called during the agent execution.
[in]CompletionCallbackThis callback is called when the agent has finished execution.
Return values
INT_STATUS_SUCCESSOn success.
INT_STATUS_NOT_INITIALIZEDIf the agent state is not initialized.
INT_STATUS_NOT_FOUNDIf the LIX_AGENT_HANDLER is not found.
INT_STATUS_INSUFFICIENT_RESOURCESIf the memory alloc fails.

Definition at line 896 of file lixagent.c.

Referenced by IntLixGuestAllocate(), and IntLixGuestDeployUninitAgent().

◆ IntLixAgentNameGetTagByAgid()

DWORD IntLixAgentNameGetTagByAgid ( DWORD  Agid)

Iterates through all agent names and returns the tag of the agent that has the provided agent ID.

Parameters
[in]AgidThe agent ID.
Return values
Thetag of the agent that has the provided agent ID.

Definition at line 312 of file lixagent.c.

Referenced by IntLixAgentHandleUserVmcall().

◆ IntLixAgentNameRemoveByAgid()

void IntLixAgentNameRemoveByAgid ( DWORD  Agid)

Iterates through all agent names and removes the entry that contains the provided ID.

Parameters
[in]AgidThe agent ID.

Definition at line 285 of file lixagent.c.

Referenced by IntLixAgentError(), IntLixAgentHandleUserVmcall(), and IntLixAgentThreadError().

◆ IntLixAgentSendEvent()

void IntLixAgentSendEvent ( AGENT_EVENT_TYPE  Event,
DWORD  AgentTag,
DWORD  ErrorCode 
)

Send an event to the integrator that contains the AGENT_EVENT_TYPE, tag of the agent and the last error code.

Parameters
[in]EventThe type of the event.
[in]AgentTagThe tag of the agent
[in]ErrorCodeThe last error-code of the agent.

Definition at line 2119 of file lixagent.c.

Referenced by IntLixAgentCreateThreadCompletion(), IntLixAgentCreateThreadHypercall(), IntLixAgentError(), IntLixAgentStart(), IntLixAgentThreadError(), and IntLixDepComplete().

◆ IntLixAgentThreadGetHandlerByTag()

LIX_AGENT_HANDLER* IntLixAgentThreadGetHandlerByTag ( LIX_AGENT_TAG  AgentTag,
LIX_AGENT_TAG  ThreadTag 
)

Iterates through all thread-agent handlers and search the entry that has the provided tag.

Parameters
[in]AgentTagThe agent tag.
[in]ThreadTagThe thread-agent tag.
Return values
Onsuccess, returns the found handler, otherwise returns NULL.

Definition at line 432 of file lixaghnd.c.

Referenced by IntLixAgentThreadCreate(), IntLixDepInjectFile(), IntLixDepInjectProcess(), and IntLixDepRunCommand().

◆ IntLixAgentThreadInject()

INTSTATUS IntLixAgentThreadInject ( LIX_AGENT_TAG  Tag,
DWORD  TagEx,
AGENT_TYPE  AgentType,
PFUNC_AgentCallbackHypercall  HypercallCallback,
PFUNC_AgentCallbackCompletion  CompletionCallback,
const char *  Name,
BYTE ContentAddress,
DWORD  ContentSize 
)

Schedule an thread-agent injection inside the guest.

A thread-agent is a bootstrap that creates a kthread and allocate a zone of memory; the provided content is copied to the allocated memory zone and the kthread will execute the deployed content.

This function schedule the injection of an thread-agent identified by the LIX_AGENT_TAG inside the guest space.

Parameters
[in]TagThe internal LIX_AGENT_TAG of the agent.
[in]TagExThe tag provided by the integrator.
[in]AgentTypeThe type of the injected agent (AGENT_TYPE).
[in]HypercallCallbackThis callback can be called during the agent execution.
[in]CompletionCallbackThis callback is called when the agent has finished execution.
[in]NameThe agent name.
[in]ContentAddressPointer to a memory area containing the actual agent.
[in]ContentSizeThe size of the agent, in bytes.
Return values
INT_STATUS_SUCCESSOn success.
INT_STATUS_NOT_INITIALIZEDIf the agent state is not initialized; if is not safe to inject the agent; if the bootstrap agent data/code is not deployed yet.
INT_STATUS_ALREADY_INITIALIZEDIf an agent with the same name is already running.
INT_STATUS_INSUFFICIENT_RESOURCESIf the memory alloc fails.

Definition at line 954 of file lixagent.c.

Referenced by IntLixDepInjectFile(), IntLixDepInjectProcess(), and IntLixDepRunCommand().

◆ IntLixAgentUninit()

INTSTATUS IntLixAgentUninit ( void  )

Uninit the agents state.

Return values
INT_STATUS_SUCCESSOn success.
INT_STATUS_NOT_INITIALIZED_HINTIf the agents state has not been initialized yet.

Definition at line 1997 of file lixagent.c.

Referenced by IntLixGuestUninit().