コード例 #1
0
ファイル: file_seek.c プロジェクト: KurtWoloch/fbc
FBCALL int fb_FileSeekLarge( int fnum, long long newpos )
{
    return fb_FileSeekEx( FB_FILE_TO_HANDLE(fnum), newpos );
}
コード例 #2
0
ファイル: file_get.c プロジェクト: jasonkfirth/fbc
/*:::::*/
int fb_FileGetDataEx( FB_FILE *handle, fb_off_t pos, void *dst, size_t length,
					  size_t *bytesread, int adjust_rec_pos, int is_unicode )
{
    int res;
    size_t chars, read_chars;
    char *pachData = (char *)dst;

	if( bytesread )
		*bytesread = 0;

    if( !FB_HANDLE_USED(handle) )
		return fb_ErrorSetNum( FB_RTERROR_ILLEGALFUNCTIONCALL );

	if( pos < 0 )
		return fb_ErrorSetNum( FB_RTERROR_ILLEGALFUNCTIONCALL );		

    FB_LOCK();

    res = fb_ErrorSetNum( FB_RTERROR_OK );

    chars = length;

    /* seek to newpos */
    if( pos > 0 )
        res = fb_FileSeekEx( handle, pos );

    /* any data in the put-back buffer? */
    if( handle->putback_size != 0 )
    {
        size_t bytes, len;
    	FB_WCHAR *wcp;
    	char *cp;

        bytes = chars;
        if( handle->encod != FB_FILE_ENCOD_ASCII )
        	bytes *= sizeof( FB_WCHAR );

        bytes = (handle->putback_size >= bytes? bytes : handle->putback_size);

        if( !is_unicode )
        {
        	if( handle->encod == FB_FILE_ENCOD_ASCII )
        		memcpy( pachData, handle->putback_buffer, bytes );
        	else
        	{
        		cp = pachData;
        		wcp = (FB_WCHAR *)handle->putback_buffer;
        		len = bytes;
        		while( len > 0 )
        		{
        			*cp++ = *wcp++;
        			len -= sizeof( FB_WCHAR );
        		}
        	}
        }
        else
        {
        	if( handle->encod != FB_FILE_ENCOD_ASCII )
        		memcpy( pachData, handle->putback_buffer, bytes );
        	else
        	{
        		cp = pachData;
        		wcp = (FB_WCHAR *)handle->putback_buffer;
        		len = bytes;
        		while( len-- > 0 )
        			*wcp++ = *cp++;
        	}
        }

        handle->putback_size -= bytes;
        if( handle->putback_size != 0 )
        {
            memmove( handle->putback_buffer,
                     handle->putback_buffer + bytes,
                     handle->putback_size );
		}

        pachData += bytes;

        if( handle->encod != FB_FILE_ENCOD_ASCII )
        	bytes /= sizeof( FB_WCHAR );

        read_chars = bytes;
        chars -= bytes;
    }
    else
    	read_chars = 0;

    if ( (res == FB_RTERROR_OK) && (chars != 0) )
    {
        /* do read */
        if( !is_unicode )
        {
        	if( handle->hooks->pfnRead == NULL )
            	res = fb_ErrorSetNum( FB_RTERROR_ILLEGALFUNCTIONCALL );
        	else
        	{
        		res = handle->hooks->pfnRead( handle, pachData, &chars );
        		read_chars += chars;
        	}
        }
        else
        {
        	if( handle->hooks->pfnReadWstr == NULL )
            	res = fb_ErrorSetNum( FB_RTERROR_ILLEGALFUNCTIONCALL );
        	else
        	{
        		res = handle->hooks->pfnReadWstr( handle, (FB_WCHAR *)pachData, &chars );
        		read_chars += chars;
        	}
        }
    }

    if( handle->mode == FB_FILE_MODE_RANDOM &&
        res == FB_RTERROR_OK &&
        adjust_rec_pos &&
        handle->len != 0 &&
        handle->hooks->pfnSeek != NULL )
    {
        /* if in random mode, reads must be of reclen.
         * The device must also support the SEEK method and the length
         * must be non-null */

		if( length != handle->len )
			res = fb_ErrorSetNum( FB_RTERROR_FILEIO );


        size_t skip_size = (handle->len -
        				   ((!is_unicode? read_chars: read_chars*sizeof( FB_WCHAR )) % handle->len)) % handle->len;

        if( skip_size != 0 )
        {
            /* don't forget the put back buffer */
            if( skip_size > handle->putback_size )
            {
                skip_size -= handle->putback_size;
                handle->putback_size = 0;
            }
            else
            {
                handle->putback_size -= skip_size;
                skip_size = 0;
            }
        }

        if (skip_size!=0)
        {
            /* devices that don't support seek should simulate it
             with read or never allow to be opened for random access */
            handle->hooks->pfnSeek( handle, skip_size, SEEK_CUR );
        }
    }

	if( bytesread )
		*bytesread = read_chars;

	FB_UNLOCK();

	/* set the error code again - handle->hooks->pfnSeek() may have reset it */
	return fb_ErrorSetNum( res );
}
コード例 #3
0
ファイル: file_seek.c プロジェクト: KurtWoloch/fbc
FBCALL int fb_FileSeek( int fnum, int newpos )
{
    return fb_FileSeekEx( FB_FILE_TO_HANDLE(fnum), newpos );
}