static
RBOOL
    findDoc
    (
        rSequence doc,
        DocSearchContext* ctx
    )
{
    RBOOL isMatch = FALSE;
    RPCHAR filePathA = NULL;
    RPWCHAR filePathW = NULL;
    CryptoLib_Hash* pHash = NULL;
    RU32 hashSize = 0;

    if( rpal_memory_isValid( doc ) &&
        NULL != ctx )
    {
        rSequence_getSTRINGA( doc, RP_TAGS_FILE_PATH, &filePathA );
        rSequence_getSTRINGW( doc, RP_TAGS_FILE_PATH, &filePathW );
        rSequence_getBUFFER( doc, RP_TAGS_HASH, (RPU8*)&pHash, &hashSize );

        if( ( NULL == filePathA || NULL == ctx->exprA || rpal_string_match( ctx->exprA, filePathA, FALSE ) ) &&
            ( NULL == filePathW || NULL == ctx->exprW || rpal_string_matchw( ctx->exprW, filePathW, FALSE ) ) &&
            ( NULL == pHash || NULL == ctx->pHash || 0 == rpal_memory_memcmp( pHash, ctx->pHash, hashSize ) ) )
        {
            isMatch = TRUE;
        }
    }

    return isMatch;
}
// Receives a task to start denying a tree at a given root.
// Can be a single atom or a list of atoms.
RPRIVATE
RVOID
    denyNewTree
    (
        rpcm_tag notifType,
        rSequence event
    )
{
    RPU8 atomId = NULL;
    RU32 size = 0;
    rList atomList = NULL;

    UNREFERENCED_PARAMETER( notifType );

    // We accept a single atom, or a list of atoms
    if( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atomId, &size ) &&
        HBS_ATOM_ID_SIZE == size )
    {
        denyExistingTree( atomId );
    }
    else if( rSequence_getLIST( event, RP_TAGS_HBS_THIS_ATOM, &atomList ) )
    {
        while( rList_getBUFFER( atomList, RP_TAGS_HBS_THIS_ATOM, &atomId, &size ) &&
               HBS_ATOM_ID_SIZE == size )
        {
            denyExistingTree( atomId );
        }
    }
}
RPRIVATE
RVOID
    mem_read
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid;
    RU64 baseAddr;
    RU32 memSize;
    RPVOID mem;

    RPU8 atom = NULL;
    RU32 atomSize = 0;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( ( rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid ) ||
              ( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atom, &atomSize ) &&
                HBS_ATOM_ID_SIZE == atomSize &&
                0 != ( pid = atoms_getPid( atom ) ) ) ) &&
            rSequence_getRU64( event, RP_TAGS_BASE_ADDRESS, &baseAddr ) &&
            rSequence_getRU32( event, RP_TAGS_MEMORY_SIZE, &memSize ) )
        {
            if( processLib_getProcessMemory( pid, (RPVOID)rpal_ULongToPtr( baseAddr ), memSize, &mem, TRUE ) )
            {
                rSequence_addBUFFER( event, RP_TAGS_MEMORY_DUMP, (RPU8)mem, memSize );
                rpal_memory_free( mem );
            }
            else
            {
                rSequence_addRU32( event, RP_TAGS_ERROR, rpal_error_getLast() );
                rpal_debug_error( "failed to get memory (base address = 0x%llx, size = 0x%x ) for pid 0x%x.", 
                                  baseAddr, 
                                  memSize, 
                                  pid );
            }
        }

        hbs_timestampEvent( event, 0 );
        hbs_publish( RP_TAGS_NOTIFICATION_MEM_READ_REP, event );
    }
}
RPRIVATE
RVOID
    mem_handles
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid;
    rList handleList;

    RPU8 atom = NULL;
    RU32 atomSize = 0;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid ) ||
            ( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atom, &atomSize ) &&
              HBS_ATOM_ID_SIZE == atomSize &&
              0 != ( pid = atoms_getPid( atom ) ) ) )
        {
            if( NULL != ( handleList = processLib_getHandles( pid, TRUE, NULL ) ) )
            {
                if( !rSequence_addLIST( event, RP_TAGS_HANDLES, handleList ) )
                {
                    rList_free( handleList );
                }
            }
            else
            {
                rSequence_addRU32( event, RP_TAGS_ERROR, rpal_error_getLast() );
            }
        }

        hbs_timestampEvent( event, 0 );
        hbs_publish( RP_TAGS_NOTIFICATION_MEM_HANDLES_REP, event );
    }
}
static
RVOID
    updateSignatures
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RPU8 buffer = NULL;
    RU32 bufferSize = 0;
    YR_RULES* rules = NULL;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( rSequence_getBUFFER( event, RP_TAGS_RULES, &buffer, &bufferSize ) )
        {
            if( NULL != ( rules = loadYaraRules( buffer, bufferSize ) ) )
            {
                if( rMutex_lock( g_global_rules_mutex ) )
                {
                    g_global_rules = rules;

                    rMutex_unlock( g_global_rules_mutex );
                }
                else
                {
                    yr_rules_destroy( rules );
                }
            }
        }
    }

    yr_finalize_thread();
}
static
RVOID
    getDocument
    (
        rpcm_tag notifId,
        rSequence notif
    )
{
    rSequence tmp = NULL;
    DocSearchContext ctx = { 0 };
    RU32 hashSize = 0;
    rList foundDocs = NULL;
    RBOOL isAAlloced = FALSE;
    RBOOL isWAlloced = FALSE;
    UNREFERENCED_PARAMETER( notifId );

    if( NULL != notif )
    {
        if( !rSequence_getSTRINGA( notif, RP_TAGS_STRING_PATTERN, &ctx.exprA ) )
        {
            ctx.exprA = NULL;
        }
        if( !rSequence_getSTRINGW( notif, RP_TAGS_STRING_PATTERN, &ctx.exprW ) )
        {
            ctx.exprW = NULL;
        }
        if( NULL != ctx.exprA && NULL == ctx.exprW )
        {
            ctx.exprW = rpal_string_atow( ctx.exprA );
            isWAlloced = TRUE;
        }
        if( NULL != ctx.exprW && NULL == ctx.exprA )
        {
            ctx.exprA = rpal_string_wtoa( ctx.exprW );
            isAAlloced = TRUE;
        }
        if( !rSequence_getBUFFER( notif, RP_TAGS_HASH, (RPU8*)&ctx.pHash, &hashSize ) ||
            sizeof( *ctx.pHash ) != hashSize )
        {
            // Unexpected hash size, let's not gamble 
            ctx.pHash = NULL;
        }
    }

    if( rMutex_lock( cacheMutex ) )
    {
        if( NULL != ( foundDocs = rList_new( RP_TAGS_FILE_INFO, RPCM_SEQUENCE ) ) )
        {
            while( HbsRingBuffer_find( documentCache, (HbsRingBufferCompareFunc)findDoc, &ctx, &tmp ) )
            {
                // TODO: optimize this since if we're dealing with large files
                // we will be temporarily using large amounts of duplicate memory.
                // We just need to do some shallow free of the datastructures
                // somehow.
                if( NULL != ( tmp = rSequence_duplicate( tmp ) ) )
                {
                    if( !rList_addSEQUENCE( foundDocs, tmp ) )
                    {
                        rSequence_free( tmp );
                    }
                }
            }

            if( !rSequence_addLIST( notif, RP_TAGS_FILES, foundDocs ) )
            {
                rList_free( foundDocs );
            }
        }

        rMutex_unlock( cacheMutex );

        notifications_publish( RP_TAGS_NOTIFICATION_GET_DOCUMENT_REP, notif );
    }

    if( isAAlloced )
    {
        rpal_memory_free( ctx.exprA );
    }
    if( isWAlloced )
    {
        rpal_memory_free( ctx.exprW );
    }
}
Exemple #7
0
//=============================================================================
//  Entry Point
//=============================================================================
RU32
RPAL_THREAD_FUNC
    RpHcpI_mainThread
    (
        rEvent isTimeToStop
    )
{
    RU32 ret = 0;

    RU64 nextBeaconTime = 0;

    rList cloudMessages = NULL;
    rSequence msg = NULL;
    rList newConfigurations = NULL;
    rList newNotifications = NULL;
    RPU8 newConfigurationHash = NULL;
    RU32 newHashSize = 0;
    rSequence staticConfig = NULL;
    RU8* tmpBuffer = NULL;
    RU32 tmpSize = 0;

    FORCE_LINK_THAT( HCP_IFACE );

    CryptoLib_init();

    getPrivileges();

    // This is the event for the collectors, it is different than the
    // hbs proper event so that we can restart the collectors without
    // signaling hbs as a whole.
    if( NULL == ( g_hbs_state.isTimeToStop = rEvent_create( TRUE ) ) )
    {
        return (RU32)-1;
    }

    // By default, no collectors are running
    rEvent_set( g_hbs_state.isTimeToStop );

    // We attempt to load some initial config from the serialized
    // rSequence that can be patched in this binary.
    if( NULL != ( staticConfig = getStaticConfig() ) )
    {
        if( rSequence_getBUFFER( staticConfig, RP_TAGS_HBS_ROOT_PUBLIC_KEY, &tmpBuffer, &tmpSize ) )
        {
            hbs_cloud_pub_key = rpal_memory_duplicate( tmpBuffer, tmpSize );
            if( NULL == hbs_cloud_pub_key )
            {
                hbs_cloud_pub_key = hbs_cloud_default_pub_key;
            }
            rpal_debug_info( "loading hbs root public key from static config" );
        }

        if( rSequence_getRU32( staticConfig, RP_TAGS_MAX_QUEUE_SIZE, &g_hbs_state.maxQueueNum ) )
        {
            rpal_debug_info( "loading max queue size from static config" );
        }
        else
        {
            g_hbs_state.maxQueueNum = HBS_EXFIL_QUEUE_MAX_NUM;
        }

        if( rSequence_getRU32( staticConfig, RP_TAGS_MAX_SIZE, &g_hbs_state.maxQueueSize ) )
        {
            rpal_debug_info( "loading max queue num from static config" );
        }
        else
        {
            g_hbs_state.maxQueueSize = HBS_EXFIL_QUEUE_MAX_SIZE;
        }

        rSequence_free( staticConfig );
    }
    else
    {
        hbs_cloud_pub_key = hbs_cloud_default_pub_key;
        g_hbs_state.maxQueueNum = HBS_EXFIL_QUEUE_MAX_NUM;
        g_hbs_state.maxQueueSize = HBS_EXFIL_QUEUE_MAX_SIZE;
    }

    if( !rQueue_create( &g_hbs_state.outQueue, freeExfilEvent, g_hbs_state.maxQueueNum ) )
    {
        rEvent_free( g_hbs_state.isTimeToStop );
        return (RU32)-1;
    }

    // We simply enqueue a message to let the cloud know we're starting
    sendStartupEvent();

    while( !rEvent_wait( isTimeToStop, (RU32)nextBeaconTime ) )
    {
        nextBeaconTime = MSEC_FROM_SEC( HBS_DEFAULT_BEACON_TIMEOUT + 
                         ( rpal_rand() % HBS_DEFAULT_BEACON_TIMEOUT_FUZZ ) );

        if( NULL != ( cloudMessages = beaconHome() ) )
        {
            while( rList_getSEQUENCE( cloudMessages, RP_TAGS_MESSAGE, &msg ) )
            {
                // Cloud message indicating next requested beacon time, as a Seconds delta
                if( rSequence_getTIMEDELTA( msg, RP_TAGS_TIMEDELTA, &nextBeaconTime ) )
                {
                    nextBeaconTime = MSEC_FROM_SEC( nextBeaconTime );
                    rpal_debug_info( "received set_next_beacon" );
                }

                if( NULL == newConfigurations &&
                    rSequence_getLIST( msg, RP_TAGS_HBS_CONFIGURATIONS, &newConfigurations ) )
                {
                    rpal_debug_info( "received a new profile" );

                    if( rSequence_getBUFFER( msg, RP_TAGS_HASH, &newConfigurationHash, &newHashSize ) &&
                        newHashSize == CRYPTOLIB_HASH_SIZE )
                    {
                        newConfigurations = rList_duplicate( newConfigurations );
                        rpal_memory_memcpy( &( g_hbs_state.currentConfigHash ), 
                                            newConfigurationHash, 
                                            CRYPTOLIB_HASH_SIZE );
                        g_hbs_state.isProfilePresent = TRUE;
                    }
                    else
                    {
                        newConfigurations = NULL;
                        rpal_debug_error( "profile hash received is invalid" );
                    }
                }

                if( NULL == newNotifications &&
                    rSequence_getLIST( msg, RP_TAGS_HBS_CLOUD_NOTIFICATIONS, &newNotifications ) )
                {
                    rpal_debug_info( "received cloud events" );
                    newNotifications = rList_duplicate( newNotifications );
                }
            }

            rList_free( cloudMessages );
        }

        // If this is the initial boot and we have no profile yet, we'll load a dummy
        // blank profile and use our defaults.
        if( NULL == newConfigurations &&
            !g_hbs_state.isProfilePresent &&
            !rEvent_wait( isTimeToStop, 0 ) )
        {
            newConfigurations = rList_new( RP_TAGS_HCP_MODULES, RPCM_SEQUENCE );
            rpal_debug_info( "setting empty profile" );
        }

        if( NULL != newConfigurations )
        {
            // We try to be as responsive as possible when asked to quit
            // so if we happen to have received the signal during a beacon
            // we will action the quit instead of the config change.
            if( !rEvent_wait( isTimeToStop, 0 ) )
            {
                rpal_debug_info( "begining sensor update on new profile" );
                shutdownCollectors();

                updateCollectorConfigs( newConfigurations );
                rList_free( newConfigurations );
                newConfigurations = NULL;

                startCollectors();
            }
            else
            {
                rList_free( newConfigurations );
            }

            newConfigurations = NULL;
        }

        if( NULL != newNotifications )
        {
            if( !rEvent_wait( isTimeToStop, 0 ) )
            {
                publishCloudNotifications( newNotifications );
            }

            rList_free( newNotifications );

            newNotifications = NULL;
        }
    }

    // We issue one last beacon indicating we are stopping
    sendShutdownEvent();

    // Shutdown everything
    shutdownCollectors();

    // Cleanup the last few resources
    rEvent_free( g_hbs_state.isTimeToStop );
    rQueue_free( g_hbs_state.outQueue );

    CryptoLib_deinit();

    if( hbs_cloud_default_pub_key != hbs_cloud_pub_key &&
        NULL != hbs_cloud_pub_key )
    {
        rpal_memory_free( hbs_cloud_pub_key );
        hbs_cloud_pub_key = NULL;
    }

    return ret;
}
Exemple #8
0
static RVOID
    publishCloudNotifications
    (
        rList notifications
    )
{
    rSequence notif = NULL;
    RPU8 buff = NULL;
    RU32 buffSize = 0;
    RPU8 sig = NULL;
    RU32 sigSize = 0;
    rpHCPId curId = { 0 };
    rSequence cloudEvent = NULL;
    rSequence targetId = { 0 };
    RU32 eventId = 0;
    rSequence localEvent = NULL;
    RU64 expiry = 0;
    rpHCPId tmpId = { 0 };
    rSequence receipt = NULL;

    while( rList_getSEQUENCE( notifications, RP_TAGS_HBS_CLOUD_NOTIFICATION, &notif ) )
    {
        cloudEvent = NULL;

        if( rSequence_getBUFFER( notif, RP_TAGS_BINARY, &buff, &buffSize ) &&
            rSequence_getBUFFER( notif, RP_TAGS_SIGNATURE, &sig, &sigSize ) )
        {
            if( CryptoLib_verify( buff, buffSize, hbs_cloud_pub_key, sig ) )
            {
                if( !rpHcpI_getId( &curId ) )
                {
                    rpal_debug_error( "error getting current id for cloud notifications." );
                }
                else
                {
                    if( !rSequence_deserialise( &cloudEvent, buff, buffSize, NULL ) )
                    {
                        cloudEvent = NULL;
                        rpal_debug_warning( "error deserializing cloud event." );
                    }
                }
            }
            else
            {
                rpal_debug_warning( "cloud event signature invalid." );
            }
        }

        if( rpal_memory_isValid( cloudEvent ) )
        {
            if( rSequence_getSEQUENCE( cloudEvent, RP_TAGS_HCP_ID, &targetId ) &&
                rSequence_getRU32( cloudEvent, RP_TAGS_HBS_NOTIFICATION_ID, &eventId ) &&
                rSequence_getSEQUENCE( cloudEvent, RP_TAGS_HBS_NOTIFICATION, &localEvent ) )
            {
                rSequence_getTIMESTAMP( cloudEvent, RP_TAGS_EXPIRY, &expiry );

                tmpId = rpHcpI_seqToHcpId( targetId );

                curId.id.configId = 0;
                tmpId.id.configId = 0;
                
                if( NULL != ( receipt = rSequence_new() ) )
                {
                    if( rSequence_addSEQUENCE( receipt, 
                                               RP_TAGS_HBS_CLOUD_NOTIFICATION, 
                                               rSequence_duplicate( cloudEvent ) ) )
                    {
                        if( !rQueue_add( g_hbs_state.outQueue, receipt, 0 ) )
                        {
                            rSequence_free( receipt );
                            receipt = NULL;
                        }
                    }
                    else
                    {
                        rSequence_free( receipt );
                        receipt = NULL;
                    }
                }

                if( curId.raw == tmpId.raw &&
                    rpal_time_getGlobal() <= expiry )
                {
                    if( !notifications_publish( eventId, localEvent ) )
                    {
                        rpal_debug_error( "error publishing event from cloud." );
                    }
                }
                else
                {
                    rpal_debug_warning( "event expired or for wrong id." );
                }
            }

            if( rpal_memory_isValid( cloudEvent ) )
            {
                rSequence_free( cloudEvent );
                cloudEvent = NULL;
            }
        }
    }
}
RBOOL
    processMessage
    (
        rSequence seq
    )
{
    RBOOL isSuccess = FALSE;
    RU8 command = 0;
    rSequence idSeq = NULL;
    rpHCPId tmpId = { 0 };
    rpHCPId emptyId = { 0 };
    RU64 tmpTime = 0;
    rThread hQuitThread = 0;

    rpHCPIdentStore identStore = {0};
    RPU8 token = NULL;
    RU32 tokenSize = 0;

    OBFUSCATIONLIB_DECLARE( store, RP_HCP_CONFIG_IDENT_STORE );

    if( NULL != seq )
    {
        if( rSequence_getRU8( seq, RP_TAGS_OPERATION, &command ) )
        {
            rpal_debug_info( "Received command 0x%0X.", command );
            switch( command )
            {
            case RP_HCP_COMMAND_LOAD_MODULE:
                isSuccess = loadModule( &g_hcpContext, seq );
                break;
            case RP_HCP_COMMAND_UNLOAD_MODULE:
                isSuccess = unloadModule( &g_hcpContext, seq );
                break;
            case RP_HCP_COMMAND_SET_HCP_ID:
                if( rSequence_getSEQUENCE( seq, RP_TAGS_HCP_IDENT, &idSeq ) )
                {
                    tmpId = seqToHcpId( idSeq );

                    if( 0 != rpal_memory_memcmp( &emptyId, &tmpId, sizeof( emptyId ) ) )
                    {
                        g_hcpContext.currentId = tmpId;
                        
                        OBFUSCATIONLIB_TOGGLE( store );
                        
                        if( rSequence_getBUFFER( seq, RP_TAGS_HCP_ENROLLMENT_TOKEN, &token, &tokenSize ) )
                        {
                            identStore.agentId = tmpId;

                            if( saveHcpId( (RPNCHAR)store, &identStore, token, tokenSize ) )
                            {
                                isSuccess = TRUE;
                            }

                            if( NULL != g_hcpContext.enrollmentToken )
                            {
                                rpal_memory_free( g_hcpContext.enrollmentToken );
                                g_hcpContext.enrollmentToken = NULL;
                            }

                            if( NULL != ( g_hcpContext.enrollmentToken = rpal_memory_alloc( tokenSize ) ) )
                            {
                                rpal_memory_memcpy( g_hcpContext.enrollmentToken, token, tokenSize );
                                g_hcpContext.enrollmentTokenSize = tokenSize;

                                isSuccess = TRUE;
                            }
                        }
                        else
                        {
                            rpal_debug_warning( "hcp id is missing token" );
                        }

                        OBFUSCATIONLIB_TOGGLE( store );
                    }
                }
                break;
            case RP_HCP_COMMAND_SET_GLOBAL_TIME:
                if( rSequence_getTIMESTAMP( seq, RP_TAGS_TIMESTAMP, &tmpTime ) )
                {
                    rpal_time_setGlobalOffset( tmpTime - rpal_time_getLocal() );
                    isSuccess = TRUE;
                }
                break;
            case RP_HCP_COMMAND_QUIT:
                if( 0 != ( hQuitThread = rpal_thread_new( thread_quitAndCleanup, NULL ) ) )
                {
                    rpal_thread_free( hQuitThread );
                    isSuccess = TRUE;
                }
                break;
            case RP_HCP_COMMAND_UPGRADE:
                isSuccess = upgradeHcp( seq );
                break;
            default:
                break;
            }

            if( isSuccess )
            {
                rpal_debug_info( "Command was successful." );
            }
            else
            {
                rpal_debug_warning( "Command was not successful." );
            }
        }
    }

    return isSuccess;
}
Exemple #10
0
RPRIVATE_TESTABLE
RBOOL
    upgradeHcp
    (
        rSequence seq
    )
{
    RBOOL isSuccess = FALSE;

    RPU8 tmpBuff = NULL;
    RU32 tmpSize = 0;
    RPU8 tmpSig = NULL;
    RU32 tmpSigSize = 0;
    RPNCHAR currentModulePath = NULL;
    RPNCHAR backupPath = NULL;

    if( NULL != seq )
    {
        if( rSequence_getBUFFER( seq,
                                 RP_TAGS_BINARY,
                                 &tmpBuff,
                                 &tmpSize ) &&
            rSequence_getBUFFER( seq,
                                 RP_TAGS_SIGNATURE,
                                 &tmpSig,
                                 &tmpSigSize ) &&
            CRYPTOLIB_SIGNATURE_SIZE == tmpSigSize )
        {
            // We got the data, now verify the buffer signature
            if( CryptoLib_verify( tmpBuff, tmpSize, getRootPublicKey(), tmpSig ) )
            {
                if( NULL != ( currentModulePath = processLib_getCurrentModulePath() ) )
                {
                    if( NULL != ( backupPath = rpal_string_strdup( currentModulePath ) ) &&
                        NULL != ( backupPath = rpal_string_strcatEx( backupPath, _NC( ".old" ) ) ) )
                    {
                        rpal_file_delete( backupPath, FALSE );

                        if( rpal_file_move( currentModulePath, backupPath ) )
                        {
                            if( rpal_file_write( currentModulePath, tmpBuff, tmpSize, TRUE ) )
                            {
                                rpal_debug_info( "hcp was successfully updated" );
                                isSuccess = TRUE;
                            }
                            else
                            {
                                rpal_debug_warning( "failed to write new hcp to disk" );

                                if( !rpal_file_move( backupPath, currentModulePath ) )
                                {
                                    rpal_debug_warning( "old hcp was reverted" );
                                }
                                else
                                {
                                    rpal_debug_error( "could not revert old hcp" );
                                }
                            }
                        }
                        else
                        {
                            rpal_debug_warning( "failed to move hcp to backup location" );
                        }

                        rpal_memory_free( backupPath );
                    }

                    rpal_memory_free( currentModulePath );
                }
                else
                {
                    rpal_debug_error( "failed to get current module path" );
                }
            }
            else
            {
                rpal_debug_warning( "New HCP binary signature is invalid." );
            }
        }
        else
        {
            rpal_debug_warning( "Upgrade command missing or invalid component." );
        }
    }

    return isSuccess;
}
RPRIVATE
RVOID
    mem_map
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid;
    rList memMapList = NULL;
    rList modulesList = NULL;
    rSequence modEntry = NULL;
    rSequence memEntry = NULL;

    RPNCHAR tmpModName = NULL;
    RPNCHAR tmpModPath = NULL;
    RU64 memStart = 0;
    RU64 memSize = 0;
    RU64 modStart = 0;
    RU64 modSize = 0;

    RPU8 atom = NULL;
    RU32 atomSize = 0;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid ) ||
            ( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atom, &atomSize ) &&
              HBS_ATOM_ID_SIZE == atomSize &&
              0 != ( pid = atoms_getPid( atom ) ) ) )
        {
            if( NULL != ( memMapList = processLib_getProcessMemoryMap( pid ) ) )
            {
                // Try to enhance the raw map
                if( NULL != ( modulesList = processLib_getProcessModules( pid ) ) )
                {
                    // Looking for memory pages within the known module
                    rList_resetIterator( memMapList );
                    while( rList_getSEQUENCE( memMapList, RP_TAGS_MEMORY_REGION, &memEntry ) )
                    {
                        if( rSequence_getPOINTER64( memEntry, RP_TAGS_BASE_ADDRESS, &memStart ) &&
                            rSequence_getRU64( memEntry, RP_TAGS_MEMORY_SIZE, &memSize ) )
                        {
                            tmpModName = NULL;
                            tmpModPath = NULL;

                            rList_resetIterator( modulesList );
                            while( rList_getSEQUENCE( modulesList, RP_TAGS_DLL, &modEntry ) )
                            {
                                if( rSequence_getPOINTER64( modEntry, RP_TAGS_BASE_ADDRESS, &modStart ) &&
                                    rSequence_getRU64( modEntry, RP_TAGS_MEMORY_SIZE, &modSize ) )
                                {
                                    if( memStart >= modStart && memStart <= ( modStart + modSize ) )
                                    {
                                        // Match, we get just the basic info
                                        rSequence_getSTRINGN( modEntry, RP_TAGS_MODULE_NAME, &tmpModName );
                                        rSequence_getSTRINGN( modEntry, RP_TAGS_FILE_PATH, &tmpModPath );
                                        break;
                                    }
                                }
                                else
                                {
                                    break;
                                }
                            }

                            // I can assert that the strings read from the memEntry WILL NOT be used
                            // hereon since doing so would be dangerous as I am about to modify
                            // the memEntry sequence after the read and therefore those pointers
                            // may not be good anymore after this point.
                            rSequence_unTaintRead( memEntry );

                            if( NULL != tmpModName )
                            {
                                rSequence_addSTRINGN( memEntry, RP_TAGS_MODULE_NAME, tmpModName );
                            }
                            if( NULL != tmpModPath )
                            {
                                rSequence_addSTRINGN( memEntry, RP_TAGS_FILE_PATH, tmpModPath );
                            }
                        }
                    }

                    rList_resetIterator( memMapList );

                    rList_free( modulesList );
                }

                if( !rSequence_addLIST( event, RP_TAGS_MEMORY_MAP, memMapList ) )
                {
                    rList_free( memMapList );
                }
            }
            else
            {
                rSequence_addRU32( event, RP_TAGS_ERROR, rpal_error_getLast() );
            }
        }
    }

    hbs_timestampEvent( event, 0 );
    hbs_publish( RP_TAGS_NOTIFICATION_MEM_MAP_REP, event );
}
Exemple #12
0
RBOOL
    rpHostCommonPlatformLib_launch
    (
        RU8 configHint,
        RPNCHAR primaryHomeUrl,
        RPNCHAR secondaryHomeUrl
    )
{
    RBOOL isInitSuccessful = FALSE;
    rSequence staticConfig = NULL;
    RPCHAR tmpStr = NULL;
    rSequence tmpSeq = NULL;
    RPU8 tmpBuffer = NULL;
    RU32 tmpSize = 0;
    RU16 tmpPort = 0;

    rpal_debug_info( "launching hcp" );

#ifdef RPAL_PLATFORM_WINDOWS
    if( setGlobalCrashHandler() &&
        SetConsoleCtrlHandler( (PHANDLER_ROUTINE)ctrlHandler, TRUE ) )
    {
        rpal_debug_info( "global crash handler set" );
    }
    else
    {
        rpal_debug_warning( "error setting global crash handler" );
    }
#endif

    if( 1 == rInterlocked_increment32( &g_hcpContext.isRunning ) )
    {
        if( rpal_initialize( NULL, RPAL_COMPONENT_HCP ) )
        {
            CryptoLib_init();

            if( NULL == ( g_hcpContext.cloudConnectionMutex = rMutex_create() ) ||
                NULL == ( g_hcpContext.isCloudOnline = rEvent_create( TRUE ) ) )
            {
                rMutex_free( g_hcpContext.cloudConnectionMutex );
                rpal_debug_error( "could not create cloud connection mutex or event" );
                return FALSE;
            }

            g_hcpContext.currentId.raw = g_idTemplate.raw;

            // We attempt to load some initial config from the serialized
            // rSequence that can be patched in this binary.
            if( NULL != ( staticConfig = getStaticConfig() ) )
            {
                if( rSequence_getSTRINGA( staticConfig, RP_TAGS_HCP_PRIMARY_URL, &tmpStr ) &&
                    rSequence_getRU16( staticConfig, RP_TAGS_HCP_PRIMARY_PORT, &tmpPort ) )
                {
                    g_hcpContext.primaryUrl = rpal_string_strdupA( tmpStr );
                    g_hcpContext.primaryPort = tmpPort;
                    rpal_debug_info( "loading primary url from static config" );
                }

                if( rSequence_getSTRINGA( staticConfig, RP_TAGS_HCP_SECONDARY_URL, &tmpStr ) &&
                    rSequence_getRU16( staticConfig, RP_TAGS_HCP_SECONDARY_PORT, &tmpPort ) )
                {
                    g_hcpContext.secondaryUrl = rpal_string_strdupA( tmpStr );
                    g_hcpContext.secondaryPort = tmpPort;
                    rpal_debug_info( "loading secondary url from static config" );
                }
                if( rSequence_getSEQUENCE( staticConfig, RP_TAGS_HCP_ID, &tmpSeq ) )
                {
                    g_hcpContext.currentId = seqToHcpId( tmpSeq );
                    rpal_debug_info( "loading default id from static config" );
                }

                if( rSequence_getBUFFER( staticConfig, RP_TAGS_HCP_C2_PUBLIC_KEY, &tmpBuffer, &tmpSize ) )
                {
                    setC2PublicKey( rpal_memory_duplicate( tmpBuffer, tmpSize ) );
                    rpal_debug_info( "loading c2 public key from static config" );
                }

                if( rSequence_getBUFFER( staticConfig, RP_TAGS_HCP_ROOT_PUBLIC_KEY, &tmpBuffer, &tmpSize ) )
                {
                    setRootPublicKey( rpal_memory_duplicate( tmpBuffer, tmpSize ) );
                    rpal_debug_info( "loading root public key from static config" );
                }

                if( rSequence_getSTRINGA( staticConfig, RP_TAGS_HCP_DEPLOYMENT_KEY, &tmpStr ) )
                {
                    g_hcpContext.deploymentKey = rpal_string_strdupA( tmpStr );
                    rpal_debug_info( "loading deployment key from static config" );
                }

                rSequence_free( staticConfig );
            }

            // Now we will override the defaults (if present) with command
            // line parameters.
            if( NULL != primaryHomeUrl &&
                0 != rpal_string_strlen( primaryHomeUrl ) )
            {
                if( NULL != g_hcpContext.primaryUrl )
                {
                    rpal_memory_free( g_hcpContext.primaryUrl );
                    g_hcpContext.primaryUrl = NULL;
                }
                g_hcpContext.primaryUrl = rpal_string_ntoa( primaryHomeUrl );
            }

            if( NULL != secondaryHomeUrl &&
                0 != rpal_string_strlen( secondaryHomeUrl  ) )
            {
                if( NULL != g_hcpContext.secondaryUrl )
                {
                    rpal_memory_free( g_hcpContext.secondaryUrl );
                    g_hcpContext.secondaryUrl = NULL;
                }
                g_hcpContext.secondaryUrl = rpal_string_ntoa( secondaryHomeUrl );
            }

            g_hcpContext.enrollmentToken = NULL;
            g_hcpContext.enrollmentTokenSize = 0;

            getStoreConf();  /* Sets the agent ID platform. */
            
            // Set the current configId
            g_hcpContext.currentId.id.configId = configHint;

            if( startBeacons() )
            {
                isInitSuccessful = TRUE;
            }
            else
            {
                rpal_debug_warning( "error starting beacons" );
            }

            CryptoLib_deinit();
        }
        else
        {
            rpal_debug_warning( "hcp platform could not init rpal" );
        }
    }
    else
    {
        rInterlocked_decrement32( &g_hcpContext.isRunning );
        rpal_debug_info( "hcp already launched" );
    }

    return isInitSuccessful;
}
RPRIVATE
RVOID
    mem_find_string
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid = 0;
    RU32 currentPid = 0;
    rList searchStrings = NULL;
    rList processes = NULL;
    rSequence process = NULL;
    processLibProcEntry* pids = NULL;
    RU32 nCurrent = 0;
    RU32 minLength = 5;
    RU32 maxLength = 128;

    RPU8 atom = NULL;
    RU32 atomSize = 0;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( ( rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid ) ||
              ( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atom, &atomSize ) &&
                HBS_ATOM_ID_SIZE == atomSize &&
                0 != ( pid = atoms_getPid( atom ) ) ) ) &&
            rSequence_getLIST( event, RP_TAGS_STRINGSW, &searchStrings ) )
        {
            currentPid = processLib_getCurrentPid();

            if( NULL != ( processes = rList_new( RP_TAGS_PROCESS, RPCM_SEQUENCE ) ) )
            {
                if( 0 != pid )
                {
                    if( NULL != ( process = _findStringsInProcess( pid, 
                                                                   searchStrings, 
                                                                   minLength, 
                                                                   maxLength ) ) )
                    {
                        if( !rList_addSEQUENCE( processes, process ) )
                        {
                            rSequence_free( process );
                        }
                    }
                }
                else
                {
                    if( NULL != ( pids = processLib_getProcessEntries( TRUE ) ) )
                    {
                        while( 0 != pids[ nCurrent ].pid )
                        {
                            if( currentPid != pids[ nCurrent ].pid )
                            {
                                if( NULL != ( process = _findStringsInProcess( pids[ nCurrent ].pid, 
                                                                               searchStrings, 
                                                                               minLength, 
                                                                               maxLength ) ) )
                                {
                                    if( !rList_addSEQUENCE( processes, process ) )
                                    {
                                        rSequence_free( process );
                                    }
                                }
                            }

                            nCurrent++;
                        }

                        rpal_memory_free( pids );
                    }
                }

                if( !rSequence_addLIST( event, RP_TAGS_PROCESSES, processes ) )
                {
                    rList_free( processes );
                }
            }
        }

        hbs_timestampEvent( event, 0 );
        hbs_publish( RP_TAGS_NOTIFICATION_MEM_FIND_STRING_REP, event );
    }
}
RPRIVATE
RVOID
    mem_strings
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid = 0;
    rList memMapList = NULL;
    rSequence region = NULL;
    RU64 memBase = 0;
    RU64 memSize = 0;
    RPU8 pRegion = NULL;
    rList stringsAList = NULL;
    rList stringsWList = NULL;
    RU32 minLength = 5;
    RU32 maxLength = 128;

    RPU8 atom = NULL;
    RU32 atomSize = 0;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        if( rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid ) ||
            ( rSequence_getBUFFER( event, RP_TAGS_HBS_THIS_ATOM, &atom, &atomSize ) &&
              HBS_ATOM_ID_SIZE == atomSize &&
              0 != ( pid = atoms_getPid( atom ) ) ) )
        {
            if( NULL != ( memMapList = processLib_getProcessMemoryMap( pid ) ) &&
                ( NULL != ( stringsAList = rList_new( RP_TAGS_STRINGSA, RPCM_STRINGA ) ) ) &&
                ( NULL != ( stringsWList = rList_new( RP_TAGS_STRINGSW, RPCM_STRINGW ) ) ) )
            {
                while( rList_getSEQUENCE( memMapList, RP_TAGS_MEMORY_REGION, &region ) )
                {
                    if( rSequence_getPOINTER64( region, RP_TAGS_BASE_ADDRESS, &memBase ) &&
                        rSequence_getRU64( region, RP_TAGS_MEMORY_SIZE, &memSize ) )
                    {
                        if( processLib_getProcessMemory( pid, 
                                                         (RPVOID)rpal_ULongToPtr( memBase ), 
                                                         memSize, 
                                                         (RPVOID*)&pRegion,
                                                         TRUE ) )
                        {
                            // now search for strings inside this region
                            _getStringsList( stringsAList, stringsWList, pRegion, memSize, minLength, maxLength );

                            rpal_memory_free( pRegion );
                        }
                    }
                }

                if( !rSequence_addLIST( event, RP_TAGS_STRINGSA, stringsAList ) )
                {
                    rList_free( stringsAList );
                }
                if( !rSequence_addLIST( event, RP_TAGS_STRINGSW, stringsWList ) )
                {
                    rList_free( stringsWList );
                }
            }
            else
            {
                rSequence_addRU32( event, RP_TAGS_ERROR, rpal_error_getLast() );
            }

            if( NULL != memMapList )
            {
                rList_free( memMapList );
            }
        }

        hbs_timestampEvent( event, 0 );
        hbs_publish( RP_TAGS_NOTIFICATION_MEM_STRINGS_REP, event );
    }
}
Exemple #15
0
RPRIVATE_TESTABLE
RBOOL 
    loadModule
    (
        rpHCPContext* hcpContext,
        rSequence seq
    )
{
    RBOOL isSuccess = FALSE;

    RU32 moduleIndex = (RU32)(-1);

    RPU8 tmpBuff = NULL;
    RU32 tmpSize = 0;

    RPU8 tmpSig = NULL;
    RU32 tmpSigSize = 0;

    rpal_thread_func pEntry = NULL;

    rpHCPModuleContext* modContext = NULL;

    OBFUSCATIONLIB_DECLARE( entryName, RP_HCP_CONFIG_MODULE_ENTRY );
    OBFUSCATIONLIB_DECLARE( recvMessage, RP_HCP_CONFIG_MODULE_RECV_MESSAGE );

    if( NULL != seq &&
        NULL != hcpContext )
    {
        for( moduleIndex = 0; moduleIndex < RP_HCP_CONTEXT_MAX_MODULES; moduleIndex++ )
        {
            if( 0 == hcpContext->modules[ moduleIndex ].hThread )
            {
                // Found an empty spot
                break;
            }
        }
    }

    if( RP_HCP_CONTEXT_MAX_MODULES != moduleIndex &&
        (RU32)(-1) != moduleIndex )
    {
        // We got an empty spot for our module
        if( rSequence_getRU8( seq, 
                              RP_TAGS_HCP_MODULE_ID, 
                              &(hcpContext->modules[ moduleIndex ].id ) ) &&
            rSequence_getBUFFER( seq,
                                 RP_TAGS_BINARY, 
                                 &tmpBuff, 
                                 &tmpSize ) &&
            rSequence_getBUFFER( seq,
                                 RP_TAGS_SIGNATURE,
                                 &tmpSig,
                                 &tmpSigSize ) &&
            CRYPTOLIB_SIGNATURE_SIZE == tmpSigSize )
        {
            // We got the data, now verify the buffer signature
            if( CryptoLib_verify( tmpBuff, tmpSize, getRootPublicKey(), tmpSig ) )
            {
                // Ready to load the module
                rpal_debug_info( "loading module in memory" );
                hcpContext->modules[ moduleIndex ].hModule = MemoryLoadLibrary( tmpBuff, tmpSize );

                if( NULL != hcpContext->modules[ moduleIndex ].hModule )
                {
                    OBFUSCATIONLIB_TOGGLE( entryName );

                    pEntry = (rpal_thread_func)MemoryGetProcAddress( hcpContext->modules[ moduleIndex ].hModule,
                                                            (RPCHAR)entryName );

                    OBFUSCATIONLIB_TOGGLE( entryName );

                    if( NULL != pEntry )
                    {
                        modContext = &(hcpContext->modules[ moduleIndex ].context);

                        modContext->pCurrentId = &( hcpContext->currentId );
                        modContext->func_sendHome = doSend;
                        modContext->isTimeToStop = rEvent_create( TRUE );
                        modContext->rpalContext = rpal_Context_get();
                        modContext->isOnlineEvent = hcpContext->isCloudOnline;

                        if( NULL != modContext->isTimeToStop )
                        {
                            hcpContext->modules[ moduleIndex ].isTimeToStop = modContext->isTimeToStop;

                            OBFUSCATIONLIB_TOGGLE( recvMessage );
                            hcpContext->modules[ moduleIndex ].func_recvMessage =
                                    (rpHCPModuleMsgEntry)MemoryGetProcAddress( hcpContext->modules[ moduleIndex ].hModule,
                                                                               (RPCHAR)recvMessage );
                            OBFUSCATIONLIB_TOGGLE( recvMessage );

                            hcpContext->modules[ moduleIndex ].hThread = rpal_thread_new( pEntry, modContext );

                            if( 0 != hcpContext->modules[ moduleIndex ].hThread )
                            {
                                CryptoLib_hash( tmpBuff, tmpSize, &(hcpContext->modules[ moduleIndex ].hash ) );
                                hcpContext->modules[ moduleIndex ].isOsLoaded = FALSE;
                                isSuccess = TRUE;
                            }
                            else
                            {
                                rpal_debug_warning( "Error creating handler thread for new module." );
                            }
                        }
                    }
                    else
                    {
                        rpal_debug_warning( "Could not find new module's entry point." );
                    }
                }
                else
                {
                    rpal_debug_warning( "Error loading module in memory." );
                }
            }
            else
            {
                rpal_debug_warning( "New module signature invalid." );
            }
        }
        else
        {
            rpal_debug_warning( "Could not find core module components to load." );
        }

        // Main cleanup
        if( !isSuccess )
        {
            if( NULL != modContext )
            {
                IF_VALID_DO( modContext->isTimeToStop, rEvent_free );
            }

            if( NULL != hcpContext->modules[ moduleIndex ].hModule )
            {
                MemoryFreeLibrary( hcpContext->modules[ moduleIndex ].hModule );
            }

            rpal_memory_zero( &(hcpContext->modules[ moduleIndex ] ),
                              sizeof( hcpContext->modules[ moduleIndex ] ) );
        }
    }
    else
    {
        rpal_debug_error( "Could not find a spot for new module, or invalid module id!" );
    }

    return isSuccess;
}
static
RVOID
    doScan
    (
        rpcm_tag eventType,
        rSequence event
    )
{
    RU32 pid = 0;
    RPWCHAR fileW = NULL;
    RPCHAR fileA = NULL;
    RPWCHAR procW = NULL;
    RPCHAR procA = NULL;
    RPU8 rulesBuffer = NULL;
    RU32 rulesBufferSize = 0;
    YR_RULES* rules = NULL;
    YaraMatchContext matchContext = { 0 };
    processLibProcEntry* processes = NULL;
    processLibProcEntry* curProc = NULL;
    RU32 scanError = 0;
    rSequence processInfo = NULL;
    RPWCHAR tmpW = NULL;
    RPCHAR tmpA = NULL;

    UNREFERENCED_PARAMETER( eventType );

    if( rpal_memory_isValid( event ) )
    {
        rSequence_getRU32( event, RP_TAGS_PROCESS_ID, &pid );
        rSequence_getSTRINGW( event, RP_TAGS_FILE_PATH, &fileW );
        rSequence_getSTRINGA( event, RP_TAGS_FILE_PATH, &fileA );
        rSequence_getSTRINGW( event, RP_TAGS_PROCESS, &procW );
        rSequence_getSTRINGA( event, RP_TAGS_PROCESS, &procA );

        if( rSequence_getBUFFER( event, RP_TAGS_RULES, &rulesBuffer, &rulesBufferSize ) )
        {
            rules = loadYaraRules( rulesBuffer, rulesBufferSize );
        }

        if( NULL != rules )
        {
            if( NULL != fileW )
            {
                fileA = rpal_string_wtoa( fileW );
            }

            if( NULL != procW )
            {
                procA = rpal_string_wtoa( procW );
            }

            if( NULL != fileA )
            {
                rpal_debug_info( "scanning file with yara" );
                matchContext.fileInfo = event;

                // Scan this file
                if( ERROR_SUCCESS != ( scanError = yr_rules_scan_file( rules,
                                                                       fileA,
                                                                       SCAN_FLAGS_FAST_MODE,
                                                                       _yaraFileMatchCallback,
                                                                       &matchContext,
                                                                       60 ) ) )
                {
                    rpal_debug_warning( "Yara file scan error: %d", scanError );
                }
            }
            else if( NULL != procA )
            {
                // Scan processes matching
                if( NULL != ( processes = processLib_getProcessEntries( TRUE ) ) )
                {
                    curProc = processes;
                    while( 0 != curProc->pid )
                    {
                        if( NULL != ( processInfo = processLib_getProcessInfo( curProc->pid, NULL ) ) )
                        {
                            if( rSequence_getSTRINGW( processInfo, RP_TAGS_FILE_PATH, &tmpW ) ||
                                rSequence_getSTRINGA( processInfo, RP_TAGS_FILE_PATH, &tmpA ) )
                            {
                                if( NULL != tmpW )
                                {
                                    tmpA = rpal_string_wtoa( tmpW );
                                }

                                if( NULL != tmpA )
                                {
                                    if( rpal_string_match( procA, tmpA, RPAL_PLATFORM_FS_CASE_SENSITIVITY ) )
                                    {
                                        matchContext.pid = curProc->pid;
                                        matchContext.processInfo = processInfo;

                                        scanError = _scanProcessWith( curProc->pid,
                                                                      &matchContext,
                                                                      rules,
                                                                      NULL );
                                    }
                                }

                                if( NULL != tmpW && NULL != tmpA )
                                {
                                    // If both are allocated it means we got a strW and converted to A
                                    // so we must free the strA version.
                                    rpal_memory_free( tmpA );
                                }
                            }

                            rSequence_free( processInfo );
                        }

                        curProc++;
                    }

                    rpal_memory_free( processes );
                }
            }
            else if( 0 != pid )
            {
                // Scan this process
                matchContext.pid = pid;
                scanError = _scanProcessWith( pid, &matchContext, rules, NULL );
                rSequence_free( matchContext.processInfo );
            }
            else
            {
                // Scan all processes
                if( NULL != ( processes = processLib_getProcessEntries( TRUE ) ) )
                {
                    curProc = processes;
                    while( 0 != curProc->pid )
                    {
                        matchContext.pid = curProc->pid;

                        scanError = _scanProcessWith( curProc->pid, &matchContext, rules, NULL );
                        rSequence_free( matchContext.processInfo );

                        curProc++;
                    }
                        
                    rpal_memory_free( processes );
                }
            }


            if( NULL != fileW && NULL != fileA )
            {
                // If both are allocated it means we got a strW and converted to A
                // so we must free the strA version.
                rpal_memory_free( fileA );
            }

            if( NULL != procW && NULL != procA )
            {
                // If both are allocated it means we got a strW and converted to A
                // so we must free the strA version.
                rpal_memory_free( procA );
            }

            yr_rules_destroy( rules );
        }
        else
        {
            rpal_debug_warning( "no rules in yara scan request" );
            reportError( event, RPAL_ERROR_NOT_SUPPORTED, "yara rules do not parse" );
        }
    }

    rpal_debug_info( "finished on demand yara scan" );
    reportError( event, scanError, "done" );

    yr_finalize_thread();
}
static
RVOID
    processHashedEvent
    (
        rpcm_tag notifType,
        rSequence event
    )
{
    RPWCHAR nameW = NULL;
    RPCHAR nameA = NULL;
    CryptoLib_Hash* pHash = NULL;
    CryptoLib_Hash localHash = { 0 };
    
    UNREFERENCED_PARAMETER( notifType );

    if( rpal_memory_isValid( event ) )
    {
        if( rSequence_getSTRINGA( event, RP_TAGS_FILE_PATH, &nameA ) ||
            rSequence_getSTRINGW( event, RP_TAGS_FILE_PATH, &nameW ) ||
            rSequence_getSTRINGA( event, RP_TAGS_DLL, &nameA ) ||
            rSequence_getSTRINGW( event, RP_TAGS_DLL, &nameW ) ||
            rSequence_getSTRINGA( event, RP_TAGS_EXECUTABLE, &nameA ) ||
            rSequence_getSTRINGW( event, RP_TAGS_EXECUTABLE, &nameW ) )
        {
            rSequence_getBUFFER( event, RP_TAGS_HASH, (RPU8*)&pHash, NULL );
            
            if( NULL != nameA )
            {
                if( NULL == pHash )
                {
                    if( _MAX_FILE_HASH_SIZE < rpal_file_getSize( nameA, TRUE ) )
                    {
                        rSequence_unTaintRead( event );
                        rSequence_addRU32( event, RP_TAGS_ERROR, RPAL_ERROR_FILE_TOO_LARGE );

                        if( rSequence_getSTRINGA( event, RP_TAGS_FILE_PATH, &nameA ) ||
                            rSequence_getSTRINGA( event, RP_TAGS_DLL, &nameA ) ||
                            rSequence_getSTRINGA( event, RP_TAGS_EXECUTABLE, &nameA ) )
                        {
                            // Find the name again with shortcircuit
                        }
                    }
                    else if( CryptoLib_hashFileA( nameA, &localHash, TRUE ) )
                    {
                        pHash = &localHash;
                    }
                }

                processCodeIdentA( nameA, pHash, 0, event );
            }
            else if( NULL != nameW )
            {
                if( NULL == pHash )
                {
                    if( _MAX_FILE_HASH_SIZE < rpal_file_getSizew( nameW, TRUE ) )
                    {
                        rSequence_unTaintRead( event );
                        rSequence_addRU32( event, RP_TAGS_ERROR, RPAL_ERROR_FILE_TOO_LARGE );

                        if( rSequence_getSTRINGW( event, RP_TAGS_FILE_PATH, &nameW ) ||
                            rSequence_getSTRINGW( event, RP_TAGS_DLL, &nameW ) ||
                            rSequence_getSTRINGW( event, RP_TAGS_EXECUTABLE, &nameW ) )
                        {
                            // Find the name again with shortcircuit
                        }
                    }
                    else if( CryptoLib_hashFileW( nameW, &localHash, TRUE ) )
                    {
                        pHash = &localHash;
                    }
                }

                processCodeIdentW( nameW, pHash, 0, event );
            }
        }
    }
}