Exemplo n.º 1
0
int zfork(){
    ZRT_LOG(L_INFO, P_TEXT, "call zvm_fork");
    /*zvm fork syscall here
      ...*/
    int res = zvm_fork();
    ZRT_LOG(L_INFO, "zvm_fork res=%d", res);

    /*update state for removable mounts, all removable mounts needs to be refreshed*/
    get_fstab_observer()->reset_removable(HANDLE_ONLY_FSTAB_SECTION);

    /*re-read nvram file because after fork his content can be changed. */
    /*Folowing nvram handlers using only stack and nor heap*/
    struct NvramLoaderPublicInterface* nvram = INSTANCE_L(NVRAM_LOADER)();
    /*if nvram config file not empty then do parsing*/
    if ( nvram->read(nvram, DEV_NVRAM) > 0 ){
	nvram->parse(nvram);

	/*handle debug section - verbosity*/
	if ( NULL != nvram->section_by_name( nvram, DEBUG_SECTION_NAME ) ){
	    ZRT_LOG(L_INFO, "%s", "nvram handle debug");
	    nvram->handle(nvram, HANDLE_ONLY_DEBUG_SECTION, NULL, NULL, NULL );
	}
	/*handle time section*/
	if ( NULL != nvram->section_by_name( nvram, TIME_SECTION_NAME ) ){
	    nvram->handle(nvram, HANDLE_ONLY_TIME_SECTION, static_timeval(), NULL, NULL);
	}
    }
    ZRT_LOG(L_SHORT, "zfork() res=%d ", res);
    return res;
}
Exemplo n.º 2
0
struct MNvramObserver* get_fstab_observer(){
    if ( s_inited_observer ) 
	return s_inited_observer;
    struct MNvramObserver* self = &s_fstab_observer;
    ZRT_LOG(L_INFO, "Create observer for section: %s", FSTAB_SECTION_NAME);
    /*setup section name*/
    strncpy(self->observed_section_name, FSTAB_SECTION_NAME, NVRAM_MAX_SECTION_NAME_LEN);
    /*setup section keys*/
    keys_construct(&self->keys);
    /*add keys and check returned key indexes that are the same as expected*/
    int key_index;
    /*check parameters*/
    key_index = self->keys.add_key(&self->keys, FSTAB_PARAM_CHANNEL_KEY);
    assert(FSTAB_PARAM_CHANNEL_KEY_INDEX==key_index);
    key_index = self->keys.add_key(&self->keys, FSTAB_PARAM_MOUNTPOINT_KEY);
    assert(FSTAB_PARAM_MOUNTPOINT_KEY_INDEX==key_index);
    key_index = self->keys.add_key(&self->keys, FSTAB_PARAM_ACCESS_KEY);
    assert(FSTAB_PARAM_ACCESS_KEY_INDEX==key_index);
    key_index = self->keys.add_key(&self->keys, FSTAB_PARAM_REMOVABLE);
    assert(FSTAB_PARAM_REMOVABLE_KEY_INDEX==key_index);

    /*setup functions*/
    s_fstab_observer.handle_nvram_record = handle_fstab_record;
    ZRT_LOG(L_SHORT, "OK observer for section: %s", FSTAB_SECTION_NAME);
    s_inited_observer = &s_fstab_observer;
    return s_inited_observer;
}
Exemplo n.º 3
0
/*fuse must use this function in own implementation, it's should
  always exist at least as stub, to get fuse library compiled*/
int fuse_main_common_implem(struct fuse_operations *op, const char *mountpoint, void *user_data){
    #ifdef FUSEGLUE_EXT
    ZRT_LOG(L_SHORT, "Perform fuse mount and wait in thread, path=%s", mountpoint );
    assert(s_fuse_mount_data!=NULL);
    struct async_lock_data *lock_data = match_mount_data_by_mountpoint(mountpoint);
    if (lock_data==NULL){
        ZRT_LOG(L_ERROR, "Can't find fuse fs lock_data for mountpoint=%s", mountpoint );
        assert(0);
    }

    /*perform filesystem mount here*/
    int res = mount_fuse_fs(op, mountpoint, lock_data->args.expect_absolute_path,
                            lock_data->args.proxy_mode);
    if (res != 0){
        ZRT_LOG(L_ERROR, "Fuse fs mount error %d", res );
        update_cond_value(lock_data, EConditionInitializationError);
    }
    else{
        /*fuse init function*/
        if ( op->init ){
            lock_data->conn = calloc(1, sizeof(struct fuse_conn_info));
            op->init(lock_data->conn);
        }
        /*when it finishes, update cond to continue zrt running*/
        update_cond_value(lock_data, EConditionInitialized);

        /*wait here until exit*/
        wait_cond_value_less_than_expected(lock_data, EConditionWaitingFinalization);
    }
    ZRT_LOG(L_SHORT, "Finalize fuse mount, err=%d, path=%s", res, mountpoint );
    return res;
#else
    return -1;
#endif /*FUSEGLUE_EXT*/
}
Exemplo n.º 4
0
struct MountInfo* mm_mountinfo_bypath( struct MountsManager *mounts_manager,
                                       const char* path, int *mount_index ){
    struct MountInfo *mount_info=NULL;
    int i;
    for( i=0; i < mounts_manager->mount_items.num_entries; i++ ){
        /*if matched path and mount path*/
        struct MountInfo *current_mount_info 
            = (struct MountInfo *)DynArrayGet(&mounts_manager->mount_items, i);
        if ( current_mount_info == NULL ) continue;
        const char* mount_path = current_mount_info->mount_path;
        /*if path is matched, then check mountpoint*/
        if ( !strncmp( mount_path, path, strlen(mount_path) ) ){
            if ( mount_info == NULL ||
                 strlen(mount_path) > strlen(mount_info->mount_path) ){
                mount_info = current_mount_info;
                *mount_index=i;
            }
        }
    }

    if ( mount_info != NULL ){
	ZRT_LOG(L_EXTRA, "located mount by path=%s: mountpoint=%s, mount_index=%d", 
                path, mount_info->mount_path, *mount_index);
        return mount_info;
    }
    else{
	ZRT_LOG(L_EXTRA, "didn't locate mount by path=%s", path);
        return NULL;
    }
}
Exemplo n.º 5
0
void handle_mount_import(struct FstabObserver* observer, struct FstabRecordContainer* record){
    assert(s_channels_mount != NULL);
    assert(s_transparent_mount != NULL);
    if ( record != NULL ){
        /*get all params*/
        char* channel_alias = NULL;
        char* mount_path = NULL;
        char* access = NULL;
        char* removable = NULL;
        char* fsname = NULL;
        GET_FSTAB_PARAMS(&record->mount, &channel_alias, &mount_path, &access, &removable, &fsname);
        int removable_record = !strcasecmp( removable, FSTAB_VAL_REMOVABLE_YES);

        /* In case if we need to inject files into FS.*/
        if ( !strcmp(access, FSTAB_VAL_ACCESS_READ) && 
             EFstabMountWaiting == record->mount_status &&
             ( removable_record || (!s_updated_fstab_records && !removable_record) ) ){
            /*
             * inject tar contents related to record into mount_path folder of filesystem;
             * Content of filesystem is reading from supported archive type linked to channel, 
             * currently TAR can be mounted, into MemMount filesystem
             */
            ZRT_LOG(L_SHORT, "mount now: channel=%s, mount_path=%s, access=%s, removable=%s, fsname=%s",
                    channel_alias, mount_path, access, removable, fsname);
            record->mount_status = EFstabMountProcessing;
            /*create mounts reader linked to tar archive that contains filesystem image,
              it call "read" from MountsPublicInterface and don't call "read" function from posix layer*/
            struct MountsReader* mounts_reader =
                alloc_mounts_reader( s_channels_mount, channel_alias );

            if ( mounts_reader ){
                /*create image loader, passed 1st param: image alias, 2nd param: Root filesystem;
                 * Root filesystem passed instead MemMount to reject adding of files into /dev folder;
                 * For example if archive contains non empty /dev folder that contents will be ignored*/
                struct ImageInterface* image_loader =
                    alloc_image_loader( s_transparent_mount );
		/*create archive unpacker*/
		struct UnpackInterface* tar_unpacker =
		    alloc_unpacker_tar( mounts_reader, image_loader->observer_implementation );

		/*read archive from linked channel and add all contents into Filesystem*/
		int inject_res = image_loader->deploy_image( mount_path, tar_unpacker );
		record->mount_status = EFstabMountComplete;
		if ( inject_res >=0  ){
		    ZRT_LOG( L_SHORT, 
			     "From %s archive readed and injected %d files "
			     "into %s folder of ZRT filesystem",
			     channel_alias, inject_res, mount_path );
		}
		else{
		    ZRT_LOG( L_ERROR, "Error %d occured while injecting files from %s archive", 
			     inject_res, channel_alias );
		}
		free_unpacker_tar( tar_unpacker );
		free_image_loader( image_loader );
		free_mounts_reader( mounts_reader );
	    }
	}
    }
}
Exemplo n.º 6
0
int exec_fuse_main(const char *mountpoint, int expect_absolute_path, char proxy_mode,
                   int (*fs_main)(int, char**), int fs_argc, char **fs_argv){
    int res=0;
    /*create mounts data array*/
    if ( s_fuse_mount_data == NULL ){
        s_fuse_mount_data = calloc(1, sizeof(struct DynArray));
        DynArrayCtor( s_fuse_mount_data, 2 /*granularity*/ );
    }

    /*prepare parameters for thread function*/
    struct async_lock_data *lock_data = calloc(1, sizeof(struct async_lock_data));
    strncpy(lock_data->args.mountpoint, mountpoint, sizeof(lock_data->args.mountpoint) );
    strncpy(lock_data->name, mountpoint, sizeof(lock_data->name) );
    lock_data->args.expect_absolute_path = expect_absolute_path;
    lock_data->args.proxy_mode = proxy_mode;
    lock_data->args.mount_argc = fs_argc;
    lock_data->args.mount_argv = fs_argv;
    lock_data->args.mount_main = fs_main;
    lock_data->mutex = PTHREAD_MUTEX_INITIALIZER;
    lock_data->cond = PTHREAD_COND_INITIALIZER;
    lock_data->cond_value = EConditionWaitingInitialization;

    /*add to array*/
    if (! DynArraySet( s_fuse_mount_data, s_fuse_mount_data->num_entries, lock_data )){
        /*error adding to array*/
        ZRT_LOG(L_ERROR, "Error adding fuse mount data with mountpoint %s", 
                mountpoint ); 
        free(lock_data);
        return -1;
    }
    /*save array index of just added lock_data*/
    lock_data->index = s_fuse_mount_data->num_entries-1;

    pthread_t thread_create_fuse;
    if (pthread_create(&thread_create_fuse, NULL, exec_fuse_main_async, lock_data) != 0){
        return -1;
    }
 
    /*Wait here for condition while fuse fs will not be created
      successfully or will raise an error*/

    wait_cond_value_less_than_expected( lock_data, EConditionInitializationError);
    if ( match_cond_value(lock_data, EConditionInitializationError) ){
        /*File system init error*/
        res=-1;
    }
    else{
        /*Wait while filesystem initialization is done, it is signalled by
          lock_data.cond. It is expected fuse_main to be called
          inside mount_main, and then it releases condition below*/
        wait_cond_value_less_than_expected( lock_data, EConditionInitialized);
        ZRT_LOG(L_INFO, "%s", "fuse fs initializer finished" ); 
        res=0;
    }

    /*keep all data allocated until EConditionWaitingFinalization*/
    return res;
}
Exemplo n.º 7
0
/*low level function, copy dirent args into buf*/
static ssize_t put_dirent_into_buf( char *buf, 
				   int buf_size, 
				   unsigned long d_ino, 
				   unsigned long d_off,
				   unsigned long mode,
				   const char *d_name ){
    DIRENT *dirent = (DIRENT *) buf;
    ZRT_LOG(L_EXTRA, "dirent offset: ino_off=%u, off_off=%u, reclen_off=%u, name_off=%u",
            offsetof( DIRENT, d_ino ),
            offsetof( DIRENT, d_off ),
            offsetof( DIRENT, d_reclen ),
            offsetof( DIRENT, d_name ) );

    int namelength = strlen(d_name);
    size_t adjusted_size = adjusted_dirent_size(namelength);

    /*if size of the current dirent data is less than available buffer size
     then fill it by data*/
    if ( adjusted_size <= buf_size ){
        dirent->d_reclen = adjusted_size;
        dirent->d_ino = d_ino;
#ifdef ZRTDIRENT
	dirent->d_type = d_type_from_mode(mode);
#endif //ZRTDIRENT
        if ( d_off == 0x7fffffff )
            dirent->d_off = 0x7fffffff;
        else
            dirent->d_off = d_off+dirent->d_reclen;

        memcpy( dirent->d_name, d_name, namelength );
        ((char*)dirent->d_name)[namelength] = '\0';

        ZRT_LOG(L_SHORT, "dirent: name=%s, ino=%u, d_off=%u, d_reclen=%d "
#ifdef ZRTDIRENT
		", d_type=%d"
#endif
                ,d_name, 
		(unsigned int)d_ino, 
		(unsigned int)d_off, 
		dirent->d_reclen
#ifdef ZRTDIRENT
		,dirent->d_type 
#endif
		);
        return dirent->d_reclen;
    }
    /*buffer is not enough to save current dirent structure*/
    else{
        ZRT_LOG(L_EXTRA, "no enough buffer, "
		"data_size=%d, buf_size=%d", 
		adjusted_size, buf_size);
        return -1; /*no enough buffer size*/
    }
}
Exemplo n.º 8
0
void update_cond_value(struct async_lock_data * lock_data, int new_cond_value)
{
    pthread_mutex_lock( &lock_data->mutex );
    ZRT_LOG(L_INFO, "update condition='%s' current value=%d, new value=%d", 
	    lock_data->name, lock_data->cond_value, new_cond_value ); 
    lock_data->cond_value = new_cond_value;
    pthread_cond_signal( &lock_data->cond );      
    ZRT_LOG(L_INFO, "update condition='%s' current value=%d, new value=%d", 
	    lock_data->name, lock_data->cond_value, new_cond_value ); 
    pthread_mutex_unlock( &lock_data->mutex );
}
Exemplo n.º 9
0
/*wait while cond value is LESS THAN expected*/
void wait_cond_value_less_than_expected(struct async_lock_data * lock_data, int expected_cond_value)
{
    pthread_mutex_lock( &lock_data->mutex );
    ZRT_LOG(L_INFO, "condition='%s' current value=%d, wait value=%d", 
	    lock_data->name, lock_data->cond_value, expected_cond_value ); 
    while( lock_data->cond_value < expected_cond_value )
	pthread_cond_wait( &lock_data->cond, &lock_data->mutex );
    pthread_cond_signal( &lock_data->cond );      
    ZRT_LOG(L_INFO, "condition='%s' new value=%d", 
	    lock_data->name, lock_data->cond_value ); 
    pthread_mutex_unlock( &lock_data->mutex );
}
Exemplo n.º 10
0
/*unpack observer 1st parameter : main unpack interface that gives access to observer, stream and mounted fs*/
static int extract_entry( struct UnpackInterface* unpacker, 
			  TypeFlag type, const char* name, int entry_size ){
    /*parse path and create directories recursively*/
    ZRT_LOG( L_INFO, "type=%s, name=%s, entry_size=%d", 
	     STR_ARCH_ENTRY_TYPE(type), name, entry_size );

    /*setup path parser observer
     *observers callback will be called for every paursed subdir extracted from full path*/
    struct ParsePathObserver path_observer;
    path_observer.callback_parse = callback_parse;
    path_observer.anyobj = unpacker->observer->mounts;

    /*run path parser*/
    int parsed_dir_count = parse_path( &path_observer, name );
    ZRT_LOG(L_INFO, "parsed_dir_count=%d", parsed_dir_count );

    if ( type == ETypeDir ){
	create_dir_and_cache_name(name, strlen(name));
    }
    else{
	int out_fd = unpacker->observer->mounts->open(name, O_WRONLY | O_CREAT, S_IRWXU);
	if (out_fd < 0) {
	    ZRT_LOG( L_ERROR, "create new file error, name=%s", name );
	    return -1;
	}

	int should_write = entry_size;
	int write_err = 0;
        /*read file by blocks*/
        while (entry_size > 0) {
            int len = (*unpacker->stream_reader->read)( unpacker->stream_reader,
                    block, sizeof(block) );
            if (len != sizeof(block)) {
		ZRT_LOG(L_ERROR, "read error. current file can't be saved name=%s", name);
                return -1;
            }
	    int wrote;
            if (entry_size > sizeof(block)) {
		WRITE_FILE( &wrote, &write_err, out_fd, block, sizeof(block) );
            } else {
		WRITE_FILE( &wrote, &write_err, out_fd, block, entry_size );
            }
	    if ( write_err ){
		return -1;
	    }
            entry_size -= sizeof(block);
        }
	ZRT_LOG(L_SHORT, "%7d B saved : %s", should_write, name);
	unpacker->observer->mounts->close(out_fd);
    }
    return 0;
}
Exemplo n.º 11
0
int  zrt_zcall_enhanced_open(const char *name, int flags, mode_t mode, int *newfd){
    LOG_SYSCALL_START("name=%s flags=%d mode=%o(octal)", name, flags, mode );

    char* absolute_path;
    char temp_path[PATH_MAX];
    int ret=-1;
    errno=0;
    VALIDATE_SYSCALL_PTR(name);
    
    /*reset mode bits, that is not actual for permissions*/
    mode&=(S_IRWXU|S_IRWXG|S_IRWXO);
    APPLY_UMASK(&mode);

    if ( (absolute_path = zrealpath(name, temp_path)) != NULL ){
	ZRT_LOG(L_SHORT, "absolute_path=%s", absolute_path);
	if ( (ret = s_transparent_mount->open(s_transparent_mount, absolute_path, flags, mode )) >= 0 ){
	    /*get fd by pointer*/
	    *newfd  = ret;
	    ret =0;
	}
    }

    LOG_SHORT_SYSCALL_FINISH( ret, 
			      "*newfd=%d, name=%s, flags=%s, mode=%s", 
			      *newfd, name, 
			      STR_ALLOCA_COPY(STR_FILE_OPEN_FLAGS(flags)),
			      STR_ALLOCA_COPY(STR_STAT_ST_MODE(mode)));
    return ret;
}
Exemplo n.º 12
0
static 
struct ParsedRecord* 
get_parsed_record(struct ParsedRecord* record,
		  const struct KeyList* keys,
		  struct internal_parse_data* params_array, 
		  int params_count){
    assert(keys);
    int i;
    for(i=0; i < params_count; i++ ){
	/*if key matched it return key index, in specified list of expecting keys so it's
	 *guarantied that key always has determinded index even for unspecified their order*/
	int key_index =  keys->find(keys, params_array[i].key, params_array[i].keylen);
	/*if current key is wrong*/
	if ( key_index < 0 ){
#ifdef PARSER_DEBUG_LOG
	    ZRT_LOG(L_ERROR, "invalid key '%s'", 
		    GET_STRING(params_array[i].key, params_array[i].keylen ) );
#endif
	    return NULL; /*error*/
	}
	else{
	    /*save current param*/
	    record->parsed_params_array[key_index].key_index = key_index; /*param index*/
	    record->parsed_params_array[key_index].val = params_array[i].val;
	    record->parsed_params_array[key_index].vallen = params_array[i].vallen;
	}
    }
    return record;
}
Exemplo n.º 13
0
/*get pointer to file structure
 *substitude glibc implementation */
FILE *fdopen(int fd, const char *mode){
    LOG_SYSCALL_START("fd=%d mode=%s", fd, mode);
    FILE* f = NULL;

    struct MountsManager* mm = mounts_manager();        /*get access to main mounts object*/
    struct MountsInterface* mif = mm->mount_byhandle(fd); /*get valid mount or NULL*/
    if ( mif ){
	struct mount_specific_implem* implem = mif->implem();
    	assert(implem);                                /*mount specific implem can't be NULL*/
	
	/*check if handle has appropriate path*/
	const char* path = implem->handle_path(fd);
	
	/*run fopen with path parameter instead fd handle*/
	if ( path ){
	    ZRT_LOG(L_SHORT, "fopen(path:%s, mode:%s)", path, mode);
	    f = fopen(path, mode);
	}
    }

    if ( f == NULL ){
	SET_ERRNO(EBADF);
    }

    LOG_SYSCALL_FINISH( (f==NULL), "fd=%d mode=%s", fd, mode );
    return f;
}
Exemplo n.º 14
0
/* check path directory is cached or not.
 * it's extract part related to full directory name from path and compare it
 * to previously cached dir name that's already created on filesystem.
 * @param path to check
 * @return 0 if cached, -1 if not;
 *  */
int create_dir_and_cache_name( const char* dirpath, int len ){
    int res = strncmp( dirpath, s_cached_full_path, len) == 0? 0: 1;
    if ( res != 0 ){
        /*reset old cache and save path in cache*/
	memset(s_cached_full_path, '\0', sizeof(s_cached_full_path));
        strncpy( s_cached_full_path, dirpath, len );
	/* create dir*/
	int ret = mkdir( s_cached_full_path, S_IRWXU );
	if ( ret != 0 && errno != EEXIST ){
	    /*error while creating dir, new path handled, cache not saved, 
	     *it is needed to create sub dir previously*/
	    memset(s_cached_full_path, '\0', sizeof(s_cached_full_path));
	    res = -1; /*new path handled, cache not saved*/
	}
	else{
	    /*directory exist*/
	    res = 0;
	}
	ZRT_LOG(L_EXTRA, "mkdir errno=%d, ret=%d: %s", errno, ret, s_cached_full_path);
    }
    else{
	/*path already handled*/
    }
    return res;
}
Exemplo n.º 15
0
static int get_inode(int handle, ino_t* inode ){
    CHECK_HANDLE(handle);
    ZRT_LOG( L_EXTRA, "handle=%d, inode=%d, inode pointer=%p",
	     handle, (int)s_handle_slots[handle].inode, &(s_handle_slots[handle]).inode );
    *inode = s_handle_slots[handle].inode;
    return 0;
}
Exemplo n.º 16
0
void buf_flush_write( BufferedIOWrite* self, int handle ){
    if ( self->data.cursor ){
	int b = self->write_override(handle, self->data.buf, self->data.cursor);
	ZRT_LOG(L_EXTRA, "buffered_io: flush %d/%d bytes \n", b, self->data.cursor );
	self->data.cursor = 0;
    }
}
Exemplo n.º 17
0
static int fuse_operations_mount_ftruncate_size(struct MountsPublicInterface* this_, int fd, off_t length) {
    int ret;
    struct FuseOperationsMount* fs = (struct FuseOperationsMount*)this_;
    const struct OpenFileDescription* ofd = fs->handle_allocator->ofd(fd);
    if (ofd==NULL) {
        SET_ERRNO(ENOENT);
        return -1;
    }
    struct FuseFileOptionalData *fdata = (struct FuseFileOptionalData *)ofd->optional_data;
    struct stat st;

    CHECK_FUNC_ENSURE_EXIST(fs, ftruncate);
    GET_STAT_ENSURE_EXIST(fs, fdata->path, &st);

    if ( S_ISDIR(st.st_mode) ) {
        SET_ERRNO(EISDIR);
        return -1;
    }

    int flags = ofd->flags & O_ACCMODE;
    /*check if file was not opened for writing*/
    if ( flags!=O_WRONLY && flags!=O_RDWR ) {
        ZRT_LOG(L_ERROR, "file open flags=%s not allow truncate",
                STR_FILE_OPEN_FLAGS(flags));
        SET_ERRNO( EINVAL );
        return -1;
    }

    if ( (ret=fs->fuse_operations->ftruncate(fdata->path, length, fdata->finfo )) < 0 ) {
        SET_ERRNO(-ret);
        return -1;
    }

    return ret;
}
Exemplo n.º 18
0
/*
 * exit. without it the user program cannot terminate correctly.
 */
void zrt_zcall_enhanced_exit(int status){
    ZRT_LOG(L_SHORT, "status %d exiting...", status);
    get_fstab_observer()->mount_export(HANDLE_ONLY_FSTAB_SECTION);
    zvm_exit(status); /*get controls into zerovm*/
    /* unreachable code*/
    return; 
}
Exemplo n.º 19
0
int zrt_zcall_ftruncate(int fd, off_t length){
    CHECK_EXIT_IF_ZRT_NOT_READY;

    LOG_SYSCALL_START("fd=%d,length=%lld", fd, length);
    
    struct MountsPublicInterface* transpar_mount = transparent_mount();
    assert(transpar_mount);

    errno=0;
    int ret;
    off_t saved_pos;
    struct stat st;
    /*save file position*/
    saved_pos = lseek( fd, 0, SEEK_CUR);
    CHECK_NON_NEGATIVE_VALUE_RETURN_ERROR(saved_pos);

    /*get end pos of file*/
    ret = fstat(fd, &st);
    assert(ret==0);
    CHECK_NON_NEGATIVE_VALUE_RETURN_ERROR(st.st_size);

    /*if filesize should be increased then just write null bytes '\0' into*/
    if ( length > st.st_size ){
	/*set cursor to the end of file, and check assertion*/
	off_t endpos = lseek( fd, st.st_size, SEEK_SET);
	CHECK_NON_NEGATIVE_VALUE_RETURN_ERROR(st.st_size);
	assert(endpos==st.st_size);

	/*just write amount of bytes starting from end of file*/
	int res = write_file_padding(fd, length-st.st_size);
	CHECK_NON_NEGATIVE_VALUE_RETURN_ERROR(res);
    }
    else{ 
	/*truncate data if user wants to reduce filesize
	 *set new file size*/
	int res = transpar_mount->ftruncate_size(transpar_mount, fd, length);	
	CHECK_NON_NEGATIVE_VALUE_RETURN_ERROR(res);
    }

    /*restore file position, it's should stay unchanged*/
    if ( saved_pos < length ){
	LSEEK_SET_ASSERT_IF_FAIL(fd, saved_pos);
    }
    else if (saved_pos > length){
	/*it is impossible to restore oldpos because it's not valid anymore
	 *it's pointing beyond of the file*/
    }

    /*final check of real file size and expected size*/
    ret = fstat(fd, &st);
    assert(ret==0);
    ZRT_LOG(L_INFO, "real truncated file size is %lld", st.st_size );
    assert(st.st_size==length);

    LOG_SHORT_SYSCALL_FINISH( 0, "fd=%d, old_length=%lld,new_length=%lld", 
			      fd, st.st_size, length);
    return 0;
}
Exemplo n.º 20
0
/*interface function
 while handling data it's saving it to buffer provided in obj1 and updating 
 used buffer space (index) in obj3 param*/
void handle_env_record(struct MNvramObserver* observer,
		       struct ParsedRecord* record,
		       void* obj1, void* obj2, void* obj3){
    assert(record);
    /*get param*/
    char* envname = NULL;
    ALLOCA_PARAM_VALUE(record->parsed_params_array[ENV_PARAM_NAME_KEY_INDEX], 
		      &envname);
    /*get param*/
    char* envval = NULL;
    ALLOCA_PARAM_VALUE(record->parsed_params_array[ENV_PARAM_VALUE_KEY_INDEX], 
		      &envval);
    ZRT_LOG(L_INFO, "env record: %s=%s", envname, envval);
    /*unescape value*/
    char* unescaped_value_result = alloca( strlen(envval)+1 );
    int unescaped_value_len =
	unescape_string_copy_to_dest(envval, 
				     record->parsed_params_array[ENV_PARAM_VALUE_KEY_INDEX].vallen, 
				     unescaped_value_result);
    ZRT_LOG(L_SHORT, "env record: %s=%s (escaped) %d", envname, unescaped_value_result, unescaped_value_len);

    /*If handling envs at session start preparing main() arguments,
     it's expected code running at prolog stage*/
    if ( obj1 && obj2 && obj3 ){
	char* buffer = (char*)obj1; /*obj1 - char* */
	int bufsize = *(int*)obj2;  /*obj2 - int*  */
	int* index = (int*)obj3;    /*obj3 - int*  */
	assert(buffer); /*into buffer will be saved results*/

	add_pair_to_temp_buffer(buffer, bufsize, index,
				envname, 
				record->parsed_params_array[ENV_PARAM_NAME_KEY_INDEX].vallen, 
				unescaped_value_result, 
				unescaped_value_len);
    }
    /*Handling envs at forked session, no another input parameters needed */
    else{
	if ( setenv(envname, unescaped_value_result, 1) == 0 ){
	    ZRT_LOG(L_INFO, P_TEXT, "env overwrite success");
	}
	else{
	    ZRT_LOG(L_INFO, P_TEXT, "env overwrite failed");
	}
    }
}
Exemplo n.º 21
0
static int add_key_to_list(struct KeyList* list, const char* key){
    assert(list);
    /*copy key up to maximum length*/
    strncpy( list->keys[list->count], key, NVRAM_MAX_KEY_LENGTH );
    ZRT_LOG(L_INFO, "%s", key);
    /*if folowing assert is raised then just increase NVRAM_MAX_KEYS_COUNT_IN_RECORD value*/
    assert(list->count<NVRAM_MAX_KEYS_COUNT_IN_RECORD);
    return list->count++; /*get index of added key*/
}
Exemplo n.º 22
0
struct MNvramObserver* get_precache_observer(){
    struct MNvramObserver* self = &s_precache_observer;
    ZRT_LOG(L_INFO, "Create observer for section: %s", PRECACHE_SECTION_NAME);
    /*setup section name*/
    strncpy(self->observed_section_name, PRECACHE_SECTION_NAME, NVRAM_MAX_SECTION_NAME_LEN);
    /*setup section keys*/
    keys_construct(&self->keys);
    /*add keys and check returned key indexes that are the same as expected*/
    int key_index;
    /*check parameters*/
    key_index = self->keys.add_key(&self->keys, PRECACHE_PARAM_PRECACHE_KEY);
    assert(PRECACHE_PARAM_PRECACHE_KEY_INDEX==key_index);

    /*setup functions*/
    s_precache_observer.handle_nvram_record = handle_precache_record;
    ZRT_LOG(L_SHORT, "OK observer for section: %s", PRECACHE_SECTION_NAME);
    return &s_precache_observer;
}
Exemplo n.º 23
0
char *getcwd(char *buf, size_t size)
{
    if ( !buf ) return NULL;

    ZRT_LOG(L_SHORT, "buf=%s, size=%d", buf, size);
    
    /*buf size is not enough */
    if ( size < sizeof DEFAULT_WORKING_DIRPATH ){
	SET_ERRNO(ERANGE);
    }
    /*buf size is enough to set path "/"  */
    else{
	/*copy into buffer exactly dir of the specified size*/
	strcpy(buf, DEFAULT_WORKING_DIRPATH);
    }

    ZRT_LOG(L_SHORT, "return buf=%s, len=%d", buf, strlen(DEFAULT_WORKING_DIRPATH) );
    return buf;
}
Exemplo n.º 24
0
int AddAllChannelsRelatedToNodeTypeFromDir( struct ChannelsConfigInterface *chan_if,
        const char *dirpath, int channel_mode, int nodetype, const char* nodename_text ){
    int res=0;
    int extracted_len;
    int extracted_nodeid=0;
    const char *readdir_get_name = NULL;
    int fd=-1;
    /***********************************************************************
     open in channel, readed from /dev/in dir */
    ZRT_LOG(L_SHORT, "Add directory=%s content items matched by pattern=%s", 
	    dirpath, nodename_text);
    DIR *dp = opendir( dirpath );
    while ( (readdir_get_name=listdir(dp)) && !res ){
        /*fetch node type name and node identifier*/
        extracted_nodeid = ExtractNodeNameId( readdir_get_name, &extracted_len );
        /*if iterated directory item matched with nodename pattern
	 *then extract handle of that directory item by opening of it's file
	 *and add it to channels config*/
	ZRT_LOG(L_EXTRA, "directory item=%s, len=%d", readdir_get_name, extracted_len );
        if ( extracted_len == strlen(nodename_text) 
	     && 
	     !strncmp(nodename_text, readdir_get_name, extracted_len ) )
        {
            snprintf( s_temp_path, MAX_PATH_LENGTH, "%s/%s", dirpath, readdir_get_name );
            if ( channel_mode == EChannelModeWrite )
                fd = open( s_temp_path, O_WRONLY); /*open channel fetched from manifest configuration*/
            else
                fd = open( s_temp_path, O_RDONLY); /*open channel fetched from manifest configuration*/
	    ZRT_LOG(L_SHORT, "matched item=%s by pattern=%s", readdir_get_name, nodename_text);
            assert(fd>=0);
            if ( extracted_nodeid == -1 ) extracted_nodeid = 1; /*for single node without id*/
            if( chan_if->AddChannel( chan_if, nodetype, extracted_nodeid, fd, channel_mode ) 
		== NULL ){
                res=-1;
                break;
            }
        }
    }

    closedir(dp);
    ZRT_LOG(L_SHORT, "channels added to config, res=%d by pattern=%s", res, nodename_text);
    return res;
}
Exemplo n.º 25
0
struct passwd* getpwuid(uid_t uid)
{
    ZRT_LOG(L_SHORT, "uid=%u", uid);
    if ( uid == 1 )
	return &s_passwd_data_1;
    else{
	SET_ERRNO(ENOENT);    /*uid mismatch*/
    }
    return NULL;
}
Exemplo n.º 26
0
static int add_key_to_list(struct KeyList* list, const char* key, const char* optional_default_value){
    assert(list);
    /*copy key up to maximum length*/
    list->keys[list->count] = key;
    list->optional_default_values[list->count] = optional_default_value;

    ZRT_LOG(L_INFO, "%s, optional=%s", key, optional_default_value);
    /*if folowing assert is raised then just increase NVRAM_MAX_KEYS_COUNT_IN_RECORD value*/
    assert(list->count<NVRAM_MAX_KEYS_COUNT_IN_RECORD);
    return list->count++; /*get index of added key*/
}
Exemplo n.º 27
0
void zrt_internal_session_info( const struct UserManifest const* manifest ){
    int i;
    char **envp = environ;
    time_t t = time(NULL);
    int pages_count = (int)(manifest->heap_size / sysconf(_SC_PAGE_SIZE));

    LOG_DEBUG(ELogTitle, "ZVM SESSION INFO", "=======")
    LOG_DEBUG(ELogAddress, (intptr_t)manifest->heap_ptr, "ZVM Manifest heap pointer" )
    LOG_DEBUG(ELogSize, manifest->heap_size, "ZVM Manifest heap size" )

    /*get from system, print environment variables*/
    LOG_DEBUG(ELogTime, ctime(&t), "System time" )
    LOG_DEBUG(ELogSize, sysconf(_SC_PAGE_SIZE), "Page size _SC_PAGE_SIZE" )
    LOG_DEBUG(ELogCount, pages_count, "Memory pages count"  )
    LOG_DEBUG(ELogAddress, manifest->heap_ptr + manifest->heap_size, "Heap highest page" )
    LOG_DEBUG(ELogAddress, sbrk(0), "sbrk(0)" )

    LOG_DEBUG(ELogTitle, "Environment variables", "======")
    i=0;
    while( envp[i] ){
        ZRT_LOG(L_BASE, "envp[%d] = '%s'", i, envp[i]);
	++i;
    }

    LOG_DEBUG(ELogCount, manifest->channels_count, "channels list")
    /*print channels list*/
    for(i = 0; i < manifest->channels_count; ++i)
	{
	    ZRT_LOG(L_BASE, "channel[%2d].name = '%s'", i, manifest->channels[i].name);
	    ZRT_LOG(L_BASE, "channel[%2d].type=%d, size=%lld", i, 
		    manifest->channels[i].type, manifest->channels[i].size);
	    ZRT_LOG(L_BASE, "channel[%2d].limits[GetsLimit=%7lld, GetSizeLimit=%7lld]", i, 
		    manifest->channels[i].limits[GetsLimit], 
		    manifest->channels[i].limits[GetSizeLimit]);
	    ZRT_LOG(L_BASE, "channel[%2d].limits[PutsLimit=%7lld, PutSizeLimit=%7lld]", i, 
		    manifest->channels[i].limits[PutsLimit],
		    manifest->channels[i].limits[PutSizeLimit]);
	}
}
Exemplo n.º 28
0
int seek_unused_slot( int starting_from ){
    int i;
    starting_from = starting_from<0 ?0 :starting_from;
    for ( i=starting_from; i < MAX_HANDLES_COUNT; i++ ){
        if ( s_handle_slots[i].used == EHandleAvailable ){
	    /*found closest unusable slot*/
            ZRT_LOG( L_INFO, "slot index=%d, EHandleAvailable", i );
            s_first_unused_slot = i;
            return s_first_unused_slot;
        }
    }
    return -1;
}
Exemplo n.º 29
0
static int transparent_fcntl(int fd, int cmd, ...){
    int ret=0;
    struct MountsInterface* mount = s_mounts_manager->mount_byhandle(fd);
    if ( mount ){
	va_list args;
	if ( cmd == F_SETLK || cmd == F_SETLKW || cmd == F_GETLK ){
	    va_start(args, cmd);
	    struct flock* input_lock = va_arg(args, struct flock*);
	    ZRT_LOG(L_SHORT, "flock=%p", input_lock );
	    if ( 0 == (ret=mount->fcntl(fd, cmd, input_lock)) ){
		ret = fcntl_implem(mount->implem(), fd, cmd, input_lock);
	    }
	    va_end(args);
	}
	else if( cmd == F_GETFL	){
Exemplo n.º 30
0
void __zrt_log_pop_name( const char* expected_name ) {
#ifdef LOG_FUNCTION_STACK_NAMES
    if ( !s_log_enabled ) return ; /*logging switched off*/
    char *s = strrchr(s_nested_syscalls_str, ' ');
    if ( s ){
	const char* actual_name = s+1;
	if (strcmp(expected_name, actual_name)){
	    ZRT_LOG(L_ERROR, "expected_name=%s, actual_name=%s", expected_name, actual_name);
	    /*check if popped name is equal to expectations*/
	    assert( !strcmp(expected_name, actual_name) ); 
	}
        s[0] = '\0';
    }
#endif
}