commons-issues mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Dennis Zhu (JIRA)" <j...@apache.org>
Subject [jira] [Commented] (VFS-437) [FTP] Program crashes when StackOverFlow Exception happens from pulling a softlinked directory that link to the directory that has the same name one level above
Date Tue, 02 Oct 2012 18:53:08 GMT

    [ https://issues.apache.org/jira/browse/VFS-437?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=13467966#comment-13467966
] 

Dennis Zhu commented on VFS-437:
--------------------------------

Here it is:

VFS-437

1. Configure the remote FTP server's local_root to be a certain directory by modifying vsftpd.conf,
for example "local_root=/Vol1". This will cause all users who log in to this FTP server to
see "/Vol1" as the root "/" folder.
2. Navigate to this local_root folder, and create a symbolic link with the same name that
links to this folder. For example, we create a symlink also called "Vol1" that links to "/Vol1",
so that "Vol1 -> /Vol1".
3. Use VFS to access this FTP server using a URL such as "ftp://test:password@ftp.example.server/Vol1".
For example, using the following test code:

@Test
    public void test()
        throws FileSystemException {
        FileSystemOptions opts = new FileSystemOptions();
        FtpFileSystemConfigBuilder.getInstance().setUserDirIsRoot( opts, true );
        final FileObject file = VFS.getManager().resolveFile( "ftp://test:password@ftp.example.server/Vol1",
opts );
        System.out.println( file );
        for ( FileObject child : file.getChildren() ) {
            System.out.println( child );
            if ( child.getType() == FileType.FOLDER )
                for ( FileObject child2 : child.getChildren() ) {
                    System.out.println( child2 );
                }
        }
    }
	
This will reproduce the StackOverFlow Exception because our URL tries to resolve the directory
"/Vol1", thinking that our root directory is the "/" directory. However, what actually happens
is that our URL actually will try to resolve "/Vol1/Vol1" on the FTP file system. This is
due to the fact that we have setUserDirIsRoot( opts, true ). Now, since resolving "/Vol1"
will bring us back to the "Vol1" symbolic link itself and not the actual directory, we'll
be infinitely trying to perform doGetType() in FtpFileObject on the symbolic link.

In summary, the StackOverFlow is guaranteed to happen when the user is in relative path mode
(setUserDirIsRoot to true) and using a symbolic link to access a file or directory, with the
same name as the symbolic link, on the file system that he doesn't have access to. This is
an edge case that is only likly to happen when the user sets up these kind of symbolic links
that he's not supposed to use in an FTP server. However, this case WILL crash applications
when it comes up.
                
> [FTP] Program crashes when StackOverFlow Exception happens from pulling a softlinked
directory that link to the directory that has the same name one level above 
> -----------------------------------------------------------------------------------------------------------------------------------------------------------------
>
>                 Key: VFS-437
>                 URL: https://issues.apache.org/jira/browse/VFS-437
>             Project: Commons VFS
>          Issue Type: Bug
>    Affects Versions: 2.0
>         Environment: java version "1.7.0_02"
> Java(TM) SE Runtime Environment (build 1.7.0_02-b13)
> Java HotSpot(TM) 64-Bit Server VM (build 22.0-b10, mixed mode)
> Linux version 2.6.18-238.el5 (mockbuild@builder10.centos.org) (gcc version 4.1.2 20080704
(Red Hat 4.1.2-48)) #1 SMP Thu Jan 13 15:51:15 EST 2011
>            Reporter: Jason
>            Priority: Blocker
>             Fix For: 2.1
>
>
> With the setting below, StackOverFlow exceptions occur and server crashes
> set the builder.setUserDirlsRoot (opt, true)
> Attept to pull with:
> ftp://root:password@ip:/Vol1
> Vol directory has the following info
> lrwxrwxrwx  1 root root        5 Oct  5  2007 Vol1 -> /Vol1
> When it tries to look for the parent of the Vol1, it goes back to the same Vol1, which
causes a infinite loop that eventually creates stackoverflow exception.
> The problem is inside the doGetType() method in FtpFileObject
>     @Override
>     protected FileType doGetType()
>         throws Exception
>     {
>         // VFS-210
>         synchronized (getFileSystem())
>         {
>             if (this.fileInfo == null)
>             {
>                 getInfo(false);
>             }
>             if (this.fileInfo == UNKNOWN)
>             {
>                 return FileType.IMAGINARY;
>             }
>             else if (this.fileInfo.isDirectory())
>             {
>                 return FileType.FOLDER;
>             }
>             else if (this.fileInfo.isFile())
>             {
>                 return FileType.FILE;
>             }
>             else if (this.fileInfo.isSymbolicLink())
>             {
>                 return getLinkDestination().getType();
>             }
>         }
>         throw new FileSystemException("vfs.provider.ftp/get-type.error", getName());
>     }
> It will keep hitting the "else if (this.fileinfo.isSymbolicLink())" condition and the
fileinfo displayed is always the Vol1 under root directory.
> Exception is shown below
> java.lang.StackOverflowError
> 	at org.apache.commons.net.ftp.FTPFile.isDirectory(FTPFile.java:116)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:334)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)
> 	at org.apache.commons.vfs2.provider.AbstractFileObject.getType(AbstractFileObject.java:496)
> 	at org.apache.commons.vfs2.provider.ftp.FtpFileObject.doGetType(FtpFileObject.java:344)

--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira

Mime
View raw message