Exemple #1
0
/*
 * Update shared with a new cache.
 * This function checks
 *     if new cache has a newer timestamp than the shared cache and updates,
 * 		   then the updateTS of the shared cache before it starts to update the cached data.
 * 		   else return.
 * 	   except when the processType is RULE_ENGINE_INIT_CACHE, which means that the share caches has not been initialized.
 * 		   or when the processType is RULE_ENGINE_REFRESH_CACHE, which means that we want to refresh the cache with the new cache.
 * It prepares the data in the new cache for copying into the shared cache.
 * It checks the timestamp again and does the actually copying.
 */
int updateCache( const char* _inst_name, size_t size, Cache *cache ) {
        unsigned char *buf = ( unsigned char * ) malloc( size );
        if ( buf != NULL ) {
            int ret;
            unsigned char *cacheBuf = buf;
            Cache *cacheCopy = copyCache( &cacheBuf, size, cache );
            if ( cacheCopy != NULL ) {
#ifdef DEBUG
                printf( "Buffer usage: %fM\n", ( ( double )( cacheCopy->dataSize ) ) / ( 1024 * 1024 ) );
#endif
                size_t pointersSize = ( cacheCopy->address + cacheCopy->cacheSize ) - cacheCopy->pointers;
                mutex_type *mutex;
                lockWriteMutex(_inst_name, &mutex);
                unsigned char *shared = prepareServerSharedMemory( _inst_name );
                if (shared == NULL) {
                    ret = -1;
                } else {
                    long diff = shared - cacheCopy->address;
                    unsigned char *pointers = cacheCopy->pointers;

                    applyDiff( pointers, pointersSize, diff, 0 );
                    applyDiffToPointers( pointers, pointersSize, diff );

                    memset( shared, 0, SHMMAX );
                    /* copy data */
                    memcpy( shared, buf, cacheCopy->dataSize );
                    /* copy pointers */
                    memcpy( cacheCopy->pointers, pointers, pointersSize );
                    ret = 0;
                    detachSharedMemory( _inst_name );
                }
                unlockWriteMutex(_inst_name, &mutex);
            }
            else {
                rodsLog( LOG_ERROR, "Error updating cache." );
                ret = -1;
            }
            free( buf );
            return ret;
        }
        else {
            rodsLog( LOG_ERROR, "Cannot update cache because of out of memory error, let some other process update it later when memory is available." );
            return -1;
        }

}
Exemple #2
0
int loadRuleFromCacheOrFile( int processType, char *irbSet, ruleStruct_t *inRuleStruct ) {
    char r1[NAME_LEN], r2[RULE_SET_DEF_LENGTH], r3[RULE_SET_DEF_LENGTH];
    snprintf( r2, sizeof( r2 ), "%s", irbSet );
    int res = 0;

#ifdef DEBUG
    /*Cache *cache;*/
#endif

    /* get max timestamp */
    char fn[MAX_NAME_LEN];
    time_type timestamp = time_type_initializer, mtim;
    while ( strlen( r2 ) > 0 ) {
        rSplitStr( r2, r1, NAME_LEN, r3, RULE_SET_DEF_LENGTH, ',' );
        getRuleBasePath( r1, fn );
        if ( ( res = getModifiedTime( fn, &mtim ) ) != 0 ) {
            return res;
        }
        if ( time_type_gt( mtim, timestamp ) ) {
            time_type_set( timestamp, mtim );
        }
        snprintf( r2, sizeof( r2 ), "%s", r3 );
    }
    snprintf( r2, sizeof( r2 ), "%s", irbSet );

#ifdef CACHE_ENABLE

    int update = 0;
    unsigned char *buf = NULL;
    /* try to find shared memory cache */
    if ( processType == RULE_ENGINE_TRY_CACHE && inRuleStruct == &coreRuleStrct ) {
        buf = prepareNonServerSharedMemory();
        if ( buf != NULL ) {
            Cache * cache = restoreCache( buf );
            detachSharedMemory();

            if ( cache == NULL ) {
                rodsLog( LOG_ERROR, "Failed to restore cache." );
            }
            else {
                int diffIrbSet = strcmp( cache->ruleBase, irbSet ) != 0;
                if ( diffIrbSet ) {
                    rodsLog( LOG_DEBUG, "Rule base set changed, old value is %s", cache->ruleBase );
                }

                if ( diffIrbSet || time_type_gt( timestamp, cache->timestamp ) ) {
                    update = 1;
                    free( cache->address );
                    rodsLog( LOG_DEBUG, "Rule base set or rule files modified, force refresh." );
                }
                else {

                    cache->cacheStatus = INITIALIZED;
                    ruleEngineConfig = *cache;
                    /* generate extRuleSet */
                    generateRegions();
                    generateRuleSets();
                    generateFunctionDescriptionTables();
                    if ( inRuleStruct == &coreRuleStrct && ruleEngineConfig.ruleEngineStatus == UNINITIALIZED ) {
                        getSystemFunctions( ruleEngineConfig.sysFuncDescIndex->current, ruleEngineConfig.sysRegion );
                    }
                    /* ruleEngineConfig.extRuleSetStatus = LOCAL;
                    ruleEngineConfig.extFuncDescIndexStatus = LOCAL; */
                    /* createRuleIndex(inRuleStruct); */
                    ruleEngineConfig.ruleEngineStatus = INITIALIZED;
                    //free( cache );
                    return res;
                }
            }
            //free( cache );
        }
        else {
            rodsLog( LOG_DEBUG, "Cannot open shared memory." );
        }
    }
#endif

    if ( ruleEngineConfig.ruleEngineStatus == INITIALIZED ) {
        /* Reloading rule set, clear previously generated rule set */
        unlinkFuncDescIndex();
        clearRuleIndex( inRuleStruct );
    }

    generateRegions();
    generateRuleSets();
    generateFunctionDescriptionTables();
    if ( inRuleStruct == &coreRuleStrct && ruleEngineConfig.ruleEngineStatus == UNINITIALIZED ) {
        getSystemFunctions( ruleEngineConfig.sysFuncDescIndex->current, ruleEngineConfig.sysRegion );
    }
    /*ruleEngineConfig.extRuleSetStatus = LOCAL;
    ruleEngineConfig.extFuncDescIndexStatus = LOCAL;*/
    while ( strlen( r2 ) > 0 ) {
        int i = rSplitStr( r2, r1, NAME_LEN, r3, RULE_SET_DEF_LENGTH, ',' );
        if ( i == 0 ) {
            i = readRuleStructAndRuleSetFromFile( r1, inRuleStruct );
        }
#ifdef DEBUG
        printf( "%d rules in core rule set\n", ruleEngineConfig.coreRuleSet->len );
#endif
        if ( i != 0 ) {
            res = i;
            ruleEngineConfig.ruleEngineStatus = INITIALIZED;
            return res;
        }
        snprintf( r2, sizeof( r2 ), "%s", r3 );
    }

    createRuleIndex( inRuleStruct );
    /* set max timestamp */
    time_type_set( ruleEngineConfig.timestamp, timestamp );
    snprintf( ruleEngineConfig.ruleBase, sizeof( ruleEngineConfig.ruleBase ), "%s", irbSet );

#ifdef CACHE_ENABLE
    if ( ( processType == RULE_ENGINE_INIT_CACHE || update ) && inRuleStruct == &coreRuleStrct ) {
        unsigned char *shared = prepareServerSharedMemory();

        if ( shared != NULL ) {
            int ret = updateCache( shared, SHMMAX, &ruleEngineConfig, processType );
            detachSharedMemory();
            if ( ret != 0 ) {
                removeSharedMemory();
            }
        }
        else {
            rodsLog( LOG_ERROR, "Cannot open shared memory." );
        }
    }
#endif

    ruleEngineConfig.ruleEngineStatus = INITIALIZED;

    return res;
}