diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java index 9b6fa7ed45bd..8db3f6d03261 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java @@ -42,6 +42,7 @@ import java.util.Locale; * @author Dmitry Avdeev */ public abstract class LocalFileSystemBase extends LocalFileSystem { + protected static final Logger LOG = Logger.getInstance("#com.intellij.openapi.vfs.impl.local.LocalFileSystemImpl"); private final List myHandlers = new ArrayList(); diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32Kernel.java b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32Kernel.java index bd452b825773..6787968237fd 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32Kernel.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32Kernel.java @@ -20,10 +20,8 @@ import com.sun.jna.win32.StdCallLibrary; import com.sun.jna.win32.W32APIFunctionMapper; import com.sun.jna.win32.W32APITypeMapper; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; +import java.io.FileNotFoundException; +import java.util.*; /** * @author Dmitry Avdeev @@ -46,6 +44,7 @@ public class Win32Kernel { }}; public static class HANDLE extends PointerType { + public Object fromNative(Object nativeValue, FromNativeContext context) { Object o = super.fromNative(nativeValue, context); if (INVALID_HANDLE_VALUE.equals(o)) return INVALID_HANDLE_VALUE; @@ -53,59 +52,72 @@ public class Win32Kernel { } } - private static int DATA_SIZE = new WIN32_FIND_DATA().size(); - - private Map myCache = new HashMap(); - private List myDatas = new ArrayList(); - - private WIN32_FIND_DATA getData() { - if (myDatas.isEmpty()) { - myDatas.add(new WIN32_FIND_DATA()); + private static class FileInfo { + private FileInfo(WIN32_FIND_DATA data) { + this.dwFileAttributes = data.dwFileAttributes; + this.ftLastWriteTime = data.ftLastWriteTime.toLong(); } - return myDatas.remove(0); + + int dwFileAttributes; + long ftLastWriteTime; } + private final static WIN32_FIND_DATA DATA = new WIN32_FIND_DATA(); + + private Map myCache = new HashMap(); + public String[] list(String absolutePath) { - myDatas.addAll(myCache.values()); myCache.clear(); ArrayList list = new ArrayList(); - WIN32_FIND_DATA data = getData(); - HANDLE hFind = myKernel.FindFirstFile(absolutePath.replace('/', '\\') + "\\*", data); + HANDLE hFind = myKernel.FindFirstFile(absolutePath.replace('/', '\\') + "\\*", DATA); if (hFind == INVALID_HANDLE_VALUE) return new String[0]; do { - String name = toString(data.cFileName); + String name = toString(DATA.cFileName); if (name.equals(".") || name.equals("..")) { continue; } - myCache.put(absolutePath + "/" + name, data); + myCache.put(absolutePath + "/" + name, new FileInfo(DATA)); list.add(name); - data = getData(); } - while (myKernel.FindNextFile(hFind, data)); + while (myKernel.FindNextFile(hFind, DATA)); myKernel.FindClose(hFind); return list.toArray(new String[list.size()]); } - public boolean isDirectory(String path) throws NotAvailableException { - WIN32_FIND_DATA data = getData(path); + public boolean exists(String path) { + try { + getData(path); + return true; + } + catch (FileNotFoundException e) { + return false; + } + } + + public boolean isDirectory(String path) throws FileNotFoundException { + FileInfo data = getData(path); return (data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0; } - public boolean isWritable(String path) throws NotAvailableException { + public boolean isWritable(String path) throws FileNotFoundException { return (getData(path).dwFileAttributes & FILE_ATTRIBUTE_READONLY) == 0; } - - public long getTimeStamp(String path) throws NotAvailableException { - return getData(path).ftLastWriteTime.toLong(); + public long getTimeStamp(String path) throws FileNotFoundException { + return getData(path).ftLastWriteTime; } - private WIN32_FIND_DATA getData(String path) throws NotAvailableException { - WIN32_FIND_DATA data = myCache.get(path); + private FileInfo getData(String path) throws FileNotFoundException { + FileInfo data = myCache.get(path); if (data == null) { - throw new NotAvailableException(path); + myCache.clear(); + HANDLE hFind = myKernel.FindFirstFile(path.replace('/', '\\'), DATA); + if (hFind == INVALID_HANDLE_VALUE) throw new FileNotFoundException(path); + data = new FileInfo(DATA); + myKernel.FindClose(hFind); + myCache.put(path, data); } return data; } @@ -124,8 +136,6 @@ public class Win32Kernel { boolean FindNextFile(HANDLE hFindFile, WIN32_FIND_DATA lpFindFileData); boolean FindClose(HANDLE hFindFile); - - int GetLastError(); } public static class FILETIME extends Structure implements Structure.ByValue { @@ -142,15 +152,11 @@ public class Win32Kernel { } public long toLong() { - long result = dwHighDateTime; - result = result << 32; - result = result + l(dwLowDateTime); - result = result / 10000; - result = result - 11644473600000l; - return result; + return (((long)dwHighDateTime << 32) + l(dwLowDateTime)) / 10000 - 11644473600000l; } } + @SuppressWarnings({"UnusedDeclaration"}) public static class WIN32_FIND_DATA extends Structure { public int dwFileAttributes; @@ -172,12 +178,5 @@ public class Win32Kernel { public char[] cFileName = new char[MAX_PATH]; public char[] cAlternateFileName = new char[14]; - - } - - public static class NotAvailableException extends Exception { - public NotAvailableException(String message) { - super(message); - } } } diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32LocalFileSystem.java b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32LocalFileSystem.java index cde59de70fa6..18ee4893b600 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32LocalFileSystem.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/win32/Win32LocalFileSystem.java @@ -19,6 +19,7 @@ import com.intellij.openapi.vfs.VirtualFile; import com.intellij.openapi.vfs.impl.local.LocalFileSystemBase; import org.jetbrains.annotations.NotNull; +import java.io.FileNotFoundException; import java.util.Collection; import java.util.Set; @@ -44,7 +45,7 @@ public class Win32LocalFileSystem extends LocalFileSystemBase { try { return myKernel.isDirectory(file.getPath()); } - catch (Win32Kernel.NotAvailableException e) { + catch (FileNotFoundException e) { return super.isDirectory(file); } } @@ -54,7 +55,7 @@ public class Win32LocalFileSystem extends LocalFileSystemBase { try { return myKernel.isWritable(file.getPath()); } - catch (Win32Kernel.NotAvailableException e) { + catch (FileNotFoundException e) { return super.isWritable(file); } } @@ -64,11 +65,16 @@ public class Win32LocalFileSystem extends LocalFileSystemBase { try { return myKernel.getTimeStamp(file.getPath()); } - catch (Win32Kernel.NotAvailableException e) { + catch (FileNotFoundException e) { return super.getTimeStamp(file); } } + @Override + public boolean exists(VirtualFile fileOrDirectory) { + return myKernel.exists(fileOrDirectory.getPath()); + } + @Override public WatchRequest addRootToWatch(@NotNull String rootPath, boolean toWatchRecursively) { throw new UnsupportedOperationException(); diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/newvfs/persistent/RefreshWorker.java b/platform/platform-impl/src/com/intellij/openapi/vfs/newvfs/persistent/RefreshWorker.java index d8be748b20af..31c1ca5c5ad1 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/newvfs/persistent/RefreshWorker.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/newvfs/persistent/RefreshWorker.java @@ -63,6 +63,7 @@ public class RefreshWorker { (applicationEx.isUnitTestMode() || applicationEx.isInternal())) { delegate = new Win32LocalFileSystem(); } + final PersistentFS persistence = (PersistentFS)ManagingFS.getInstance(); while (!myRefreshQueue.isEmpty()) {