diff --git a/datastore_server/source/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProvider.java b/datastore_server/source/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProvider.java
index 31a549ef986560ad78262a92c6d98cccd30cfed2..90ce73e550bfb7114bc57c2ccc6703957c9d7ccb 100644
--- a/datastore_server/source/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProvider.java
+++ b/datastore_server/source/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProvider.java
@@ -91,14 +91,16 @@ public class DatabaseBasedDataSetPathInfoProvider implements IDataSetPathInfoPro
                 String relativePathLikeExpression);
 
         @Select(SELECT_DATA_SET_FILES
-                + "WHERE dase_id = ?{1} AND relative_path = '?{2}' AND file_name ~ ?{3}")
-        public List<DataSetFileRecord> listDataSetFilesByFilenameRegex(long dataSetId,
-                String startingPath, String filenameRegex);
+                + "WHERE dase_id = ?{1} AND relative_path = ?{2} || file_name AND file_name ~ ?{3}")
+        public List<DataSetFileRecord> listDataSetFilesByFilenameRegex(
+                long dataSetId, String startingPath, String filenameRegex);
 
         @Select(SELECT_DATA_SET_FILES
-                + "WHERE dase_id = ?{1} AND relative_path = '?{2}' AND file_name LIKE ?{3}")
-        public List<DataSetFileRecord> listDataSetFilesByFilenameLikeExpression(long dataSetId,
-                String startingPath, String filenameLikeExpression);
+                + "WHERE dase_id = ?{1} AND relative_path = ?{2} || file_name AND file_name LIKE ?{3}")
+        public List<DataSetFileRecord> listDataSetFilesByFilenameLikeExpression(
+                long dataSetId, String startingPath,
+                String filenameLikeExpression);
+
     }
 
     private static interface ILoader
@@ -162,7 +164,8 @@ public class DatabaseBasedDataSetPathInfoProvider implements IDataSetPathInfoPro
         Map<String, Integer> files = new HashMap<String, Integer>();
         IPathInfoDAO queries = getDao();
         Long id = queries.tryToGetDataSetId(dataSetCode);
-        if (id == null) {
+        if (id == null)
+        {
             return files;
         }
         List<DataSetFileRecord> records = getDao().listDataSetFiles(id);
@@ -255,18 +258,31 @@ public class DatabaseBasedDataSetPathInfoProvider implements IDataSetPathInfoPro
         public List<DataSetPathInfo> listMatchingPathInfos(String startingPath,
                 String fileNamePattern)
         {
+            String aStartingPath = null;
+
+            if (startingPath == null || startingPath.trim().length() == 0)
+            {
+                aStartingPath = "";
+            } else if (startingPath.endsWith("/"))
+            {
+                aStartingPath = startingPath;
+            } else
+            {
+                aStartingPath = startingPath + "/";
+            }
+
             String likeExpressionOrNull =
                     DBUtils.tryToTranslateRegExpToLikePattern(prepareDBStyleRegex(fileNamePattern));
             List<DataSetFileRecord> records;
             if (likeExpressionOrNull == null)
             {
                 records =
-                        dao.listDataSetFilesByFilenameRegex(dataSetId, startingPath,
+                        dao.listDataSetFilesByFilenameRegex(dataSetId, aStartingPath,
                                 prepareDBStyleRegex(fileNamePattern));
             } else
             {
                 records =
-                        dao.listDataSetFilesByFilenameLikeExpression(dataSetId, startingPath,
+                        dao.listDataSetFilesByFilenameLikeExpression(dataSetId, aStartingPath,
                                 likeExpressionOrNull);
             }
             return asPathInfos(records);
diff --git a/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/datastoreserver/systemtests/PathInfoDatabaseTest.java b/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/datastoreserver/systemtests/PathInfoDatabaseTest.java
index f02dd0138849f1590966b2a3cdff96167a30842a..c1c5b5171297a7cf1821a6fce2958194d913b0c7 100644
--- a/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/datastoreserver/systemtests/PathInfoDatabaseTest.java
+++ b/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/datastoreserver/systemtests/PathInfoDatabaseTest.java
@@ -31,9 +31,12 @@ import javax.sql.DataSource;
 import net.lemnik.eodsql.QueryTool;
 
 import org.apache.commons.lang.time.StopWatch;
+import org.testng.Assert;
+import org.testng.annotations.BeforeTest;
 import org.testng.annotations.Test;
 
 import ch.systemsx.cisd.etlserver.path.IPathsInfoDAO;
+import ch.systemsx.cisd.openbis.dss.generic.shared.ISingleDataSetPathInfoProvider;
 import ch.systemsx.cisd.openbis.dss.generic.shared.ServiceProvider;
 import ch.systemsx.cisd.openbis.dss.generic.shared.dto.DataSetPathInfo;
 import ch.systemsx.cisd.openbis.dss.generic.shared.utils.PathInfoDataSourceProvider;
@@ -44,19 +47,34 @@ import ch.systemsx.cisd.openbis.dss.generic.shared.utils.PathInfoDataSourceProvi
 @Test(groups = "slow")
 public class PathInfoDatabaseTest extends SystemTestCase
 {
-    @Test
-    public void testPathInfoDatabase() throws Exception
+
+    @BeforeTest
+    private void initDatabase() throws Exception
     {
         DataSource dataSource = PathInfoDataSourceProvider.getDataSource();
-        cleanUpDatabase(dataSource);
 
         StopWatch stopWatch = new StopWatch();
         stopWatch.start();
+
+        cleanUpDatabase(dataSource);
+
+        System.out.println(stopWatch.getTime() + " msec for cleaning up old entries");
+
+        stopWatch.reset();
+        stopWatch.start();
+
         int n = feedDataBase(dataSource);
+
         System.out.println(stopWatch.getTime() + " msec for creating " + n + " entries");
+    }
 
-        stopWatch.reset();
+    @Test
+    public void testPathInfoDatabase() throws Exception
+    {
+        DataSource dataSource = PathInfoDataSourceProvider.getDataSource();
+        StopWatch stopWatch = new StopWatch();
         List<String> paths = new ArrayList<String>();
+
         Connection connection = null;
         String regex = ".*file-[2-3].*81.*(25|49).*36.*";
         try
@@ -123,15 +141,209 @@ public class PathInfoDatabaseTest extends SystemTestCase
                 + "file-3-9/file-9-81/file-7-49/file-6-36-xyz.xml]", paths.toString());
     }
 
+    @Test
+    public void testListMatchingPathInfosWithRelativePathPatternWithExactMatch()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider
+                .listMatchingPathInfos("file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml");
+
+        assertRelativePaths(actualFiles, "file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithRelativePathPatternWithoutAnyMatch()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider
+                .listMatchingPathInfos("file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml.notexisting");
+
+        assertRelativePaths(actualFiles, new String[] {});
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithRelativePathPatternWithSpecialCharactersConvertableToLike()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider
+                .listMatchingPathInfos("special_characters_%\\?\\.file-9-81/.*file.*1.*xml");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-9-81/special_characters_%?.file-1-1-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-4-16-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithRelativePathPatternWithSpecialCharactersNotConvertableToLike()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider
+                .listMatchingPathInfos("special_characters_%\\?\\.file-9-81/.*(file-0-0|file-2-4).*");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-9-81/special_characters_%?.file-0-0-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-2-4-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathAndFileNamePatternWithExactMatch()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "file-9-81/file-9-81/file-9-81", "file-9-81-xyz.xml");
+
+        assertRelativePaths(actualFiles, "file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithEmptyStartingPath()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos("", "special_characters_%\\?\\.file-8-64");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-8-64");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithNullStartingPath()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(null, "special_characters_%\\?\\.file-8-64");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-8-64");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathWithoutSlash()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "file-9-81/file-9-81/file-9-81", "file-9-81-xyz.xml");
+
+        assertRelativePaths(actualFiles, "file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathWithSlash()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "file-9-81/file-9-81/file-9-81/", "file-9-81-xyz.xml");
+
+        assertRelativePaths(actualFiles, "file-9-81/file-9-81/file-9-81/file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathAndFileNamePatternWithoutAnyMatch()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "file-9-81/file-9-81/file-9-81", "file-9-81-xyz.xml.notexisting");
+
+        assertRelativePaths(actualFiles, new String[] {});
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathThatMatchesRelativePathAndEmptyFileNamePattern()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-1");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "file-9-81/file-9-81/file-9-81-xyz.xml", "");
+
+        assertRelativePaths(actualFiles, new String[] {});
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathWithSpecialCharactersAndFileNamePatternConvertableToLike()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "special_characters_%?.file-9-81", ".*file.*1.*xml");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-9-81/special_characters_%?.file-1-1-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-4-16-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-9-81-xyz.xml");
+    }
+
+    @Test
+    public void testListMatchingPathInfosWithStartingPathWithSpecialCharactersAndFileNamePatternNotConvertableToLike()
+    {
+        ISingleDataSetPathInfoProvider provider = ServiceProvider
+                .getDataSetPathInfoProvider()
+                .tryGetSingleDataSetPathInfoProvider("ds-2");
+
+        List<DataSetPathInfo> actualFiles = provider.listMatchingPathInfos(
+                "special_characters_%?.file-9-81", ".*(file-0-0|file-2-4).*");
+
+        assertRelativePaths(actualFiles, "special_characters_%?.file-9-81/special_characters_%?.file-0-0-xyz.xml",
+                "special_characters_%?.file-9-81/special_characters_%?.file-2-4-xyz.xml");
+    }
+
+    private void assertRelativePaths(List<DataSetPathInfo> actualFiles, String... expectedRelativePaths)
+    {
+        Assert.assertEquals(actualFiles.size(), expectedRelativePaths.length);
+
+        for (int i = 0; i < expectedRelativePaths.length; i++)
+        {
+            String expectedRelativePath = expectedRelativePaths[i];
+            DataSetPathInfo actualFile = actualFiles.get(i);
+
+            Assert.assertEquals(actualFile.getRelativePath(), expectedRelativePath);
+        }
+    }
+
     private int feedDataBase(DataSource dataSource)
     {
         int numberOfEntries = 0;
         IPathsInfoDAO dao = QueryTool.getQuery(dataSource, IPathsInfoDAO.class);
         try
         {
-            long id = dao.createDataSet("ds-1", "a/b/c/");
-            long parentId = dao.createDataSetFile(id, null, "", "ds-1", 0, true, new Date(4711));
-            numberOfEntries += feedDataBase(dao, id, parentId, 3, "");
+            long id;
+            long parentId;
+
+            id = dao.createDataSet("ds-1", "a/b/c/");
+            parentId = dao.createDataSetFile(id, null, "", "ds-1", 0, true, new Date(4711));
+            numberOfEntries += feedDataBase(dao, id, parentId, 3, "", "");
+
+            id = dao.createDataSet("ds-2", "a2/b2/c2/");
+            parentId = dao.createDataSetFile(id, null, "", "ds-2", 0, true, new Date(4722));
+            numberOfEntries += feedDataBase(dao, id, parentId, 1, "", "special_characters_%?.");
+
             dao.commit();
         } catch (Exception ex)
         {
@@ -143,13 +355,13 @@ public class PathInfoDatabaseTest extends SystemTestCase
     }
 
     private int feedDataBase(IPathsInfoDAO dao, long dataSetId, Long parentId, int level,
-            String prefix)
+            String prefix, String fileNamePrefix)
     {
         int numberOfEntries = 0;
         for (int i = 0; i < 10; i++)
         {
             boolean directory = level > 0;
-            String fileName = "file-" + i + "-" + (i * i) + (directory ? "" : "-xyz.xml");
+            String fileName = fileNamePrefix + "file-" + i + "-" + (i * i) + (directory ? "" : "-xyz.xml");
             long id =
                     dao.createDataSetFile(dataSetId, parentId, prefix + fileName, fileName, level
                             * 100 + i, directory, new Date(4711));
@@ -157,7 +369,7 @@ public class PathInfoDatabaseTest extends SystemTestCase
             if (directory)
             {
                 numberOfEntries +=
-                        feedDataBase(dao, dataSetId, id, level - 1, prefix + fileName + "/");
+                        feedDataBase(dao, dataSetId, id, level - 1, prefix + fileName + "/", fileNamePrefix);
             }
         }
         return numberOfEntries;
@@ -183,7 +395,7 @@ public class PathInfoDatabaseTest extends SystemTestCase
         try
         {
             connection = dataSource.getConnection();
-            connection.createStatement().execute("delete from data_sets where code like 'ds-1'");
+            connection.createStatement().execute("delete from data_sets where code like 'ds-1' or code like 'ds-2'");
         } finally
         {
             close(connection);
diff --git a/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProviderTest.java b/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProviderTest.java
index 2b2acca96c79f3021dba2e60f8b6ea57482163be..73b740ab0d20a24c9829ffe466992554f636c966 100644
--- a/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProviderTest.java
+++ b/datastore_server/sourceTest/java/ch/systemsx/cisd/openbis/dss/generic/server/DatabaseBasedDataSetPathInfoProviderTest.java
@@ -39,9 +39,9 @@ import ch.systemsx.cisd.openbis.dss.generic.shared.dto.DataSetPathInfo;
 /**
  * @author Franz-Josef Elmer
  */
-@Friend(toClasses = {DatabaseBasedDataSetPathInfoProvider.class, 
-        DatabaseBasedDataSetPathInfoProvider.IPathInfoDAO.class, 
-        DatabaseBasedDataSetPathInfoProvider.DataSetFileRecord.class})
+@Friend(toClasses = { DatabaseBasedDataSetPathInfoProvider.class,
+        DatabaseBasedDataSetPathInfoProvider.IPathInfoDAO.class,
+        DatabaseBasedDataSetPathInfoProvider.DataSetFileRecord.class })
 public class DatabaseBasedDataSetPathInfoProviderTest extends AssertJUnit
 {
     private static final Long DATA_SET_ID = 41L;
@@ -351,7 +351,7 @@ public class DatabaseBasedDataSetPathInfoProviderTest extends AssertJUnit
         context.checking(new Expectations()
             {
                 {
-                    one(dao).listDataSetFilesByFilenameRegex(DATA_SET_ID, startingPath,
+                    one(dao).listDataSetFilesByFilenameRegex(DATA_SET_ID, startingPath + "/",
                             "^" + regex + "$");
                     will(returnValue(Arrays.asList(rc1, rc2)));
                 }
@@ -378,7 +378,7 @@ public class DatabaseBasedDataSetPathInfoProviderTest extends AssertJUnit
         context.checking(new Expectations()
             {
                 {
-                    one(dao).listDataSetFilesByFilenameLikeExpression(DATA_SET_ID, startingPath,
+                    one(dao).listDataSetFilesByFilenameLikeExpression(DATA_SET_ID, startingPath + "/",
                             "child%");
                     will(returnValue(Arrays.asList(rc1, rc2)));
                 }