Reimplemented FindFirstFileEx and removed some overhead.
Modified: trunk/reactos/lib/kernel32/file/find.c

Modified: trunk/reactos/lib/kernel32/file/find.c
--- trunk/reactos/lib/kernel32/file/find.c	2005-08-11 18:49:40 UTC (rev 17290)
+++ trunk/reactos/lib/kernel32/file/find.c	2005-08-11 19:02:31 UTC (rev 17291)
@@ -28,20 +28,98 @@
 typedef struct _KERNEL32_FIND_FILE_DATA
 {
    HANDLE DirectoryHandle;
+   BOOLEAN DirectoryOnly;
    PFILE_BOTH_DIR_INFORMATION pFileInfo;
 } KERNEL32_FIND_FILE_DATA, *PKERNEL32_FIND_FILE_DATA;
 
 
 /* FUNCTIONS ****************************************************************/
 
+VOID
+InternalCopyFindDataW(LPWIN32_FIND_DATAW            lpFindFileData,
+                      PFILE_BOTH_DIR_INFORMATION    lpFileInfo)
+{
+    lpFindFileData->dwFileAttributes = lpFileInfo->FileAttributes;
 
+    lpFindFileData->ftCreationTime.dwHighDateTime = lpFileInfo->CreationTime.u.HighPart;
+    lpFindFileData->ftCreationTime.dwLowDateTime = lpFileInfo->CreationTime.u.LowPart;
+
+    lpFindFileData->ftLastAccessTime.dwHighDateTime = lpFileInfo->LastAccessTime.u.HighPart;
+    lpFindFileData->ftLastAccessTime.dwLowDateTime = lpFileInfo->LastAccessTime.u.LowPart;
+
+    lpFindFileData->ftLastWriteTime.dwHighDateTime = lpFileInfo->LastWriteTime.u.HighPart;
+    lpFindFileData->ftLastWriteTime.dwLowDateTime = lpFileInfo->LastWriteTime.u.LowPart;
+
+    lpFindFileData->nFileSizeHigh = lpFileInfo->EndOfFile.u.HighPart;
+    lpFindFileData->nFileSizeLow = lpFileInfo->EndOfFile.u.LowPart;
+
+    memcpy (lpFindFileData->cFileName, lpFileInfo->FileName, lpFileInfo->FileNameLength);
+    lpFindFileData->cFileName[lpFileInfo->FileNameLength / sizeof(WCHAR)] = 0;
+
+    memcpy (lpFindFileData->cAlternateFileName, lpFileInfo->ShortName, lpFileInfo->ShortNameLength);
+    lpFindFileData->cAlternateFileName[lpFileInfo->ShortNameLength / sizeof(WCHAR)] = 0;
+}
+
+VOID
+InternalCopyFindDataA(LPWIN32_FIND_DATAA            lpFindFileData,
+                      PFILE_BOTH_DIR_INFORMATION    lpFileInfo)
+{
+    UNICODE_STRING FileNameU;
+    ANSI_STRING FileNameA;
+
+    lpFindFileData->dwFileAttributes = lpFileInfo->FileAttributes;
+
+    lpFindFileData->ftCreationTime.dwHighDateTime = lpFileInfo->CreationTime.u.HighPart;
+    lpFindFileData->ftCreationTime.dwLowDateTime = lpFileInfo->CreationTime.u.LowPart;
+
+    lpFindFileData->ftLastAccessTime.dwHighDateTime = lpFileInfo->LastAccessTime.u.HighPart;
+    lpFindFileData->ftLastAccessTime.dwLowDateTime = lpFileInfo->LastAccessTime.u.LowPart;
+
+    lpFindFileData->ftLastWriteTime.dwHighDateTime = lpFileInfo->LastWriteTime.u.HighPart;
+    lpFindFileData->ftLastWriteTime.dwLowDateTime = lpFileInfo->LastWriteTime.u.LowPart;
+
+    lpFindFileData->nFileSizeHigh = lpFileInfo->EndOfFile.u.HighPart;
+    lpFindFileData->nFileSizeLow = lpFileInfo->EndOfFile.u.LowPart;
+
+    FileNameU.Length = FileNameU.MaximumLength = lpFileInfo->FileNameLength;
+    FileNameU.Buffer = lpFileInfo->FileName;
+
+    FileNameA.MaximumLength = sizeof(lpFindFileData->cFileName) - sizeof(CHAR);
+    FileNameA.Buffer = lpFindFileData->cFileName;
+
+    /* convert unicode string to ansi (or oem) */
+    if (bIsFileApiAnsi)
+    	RtlUnicodeStringToAnsiString (&FileNameA, &FileNameU, FALSE);
+    else
+        RtlUnicodeStringToOemString (&FileNameA, &FileNameU, FALSE);
+
+    FileNameA.Buffer[FileNameA.Length] = 0;
+
+    DPRINT("lpFileInfo->ShortNameLength %d\n", lpFileInfo->ShortNameLength);
+
+    FileNameU.Length = FileNameU.MaximumLength = lpFileInfo->ShortNameLength;
+    FileNameU.Buffer = lpFileInfo->ShortName;
+
+    FileNameA.MaximumLength = sizeof(lpFindFileData->cAlternateFileName) - sizeof(CHAR);
+    FileNameA.Buffer = lpFindFileData->cAlternateFileName;
+
+    /* convert unicode string to ansi (or oem) */
+    if (bIsFileApiAnsi)
+	RtlUnicodeStringToAnsiString (&FileNameA, &FileNameU, FALSE);
+    else
+    	RtlUnicodeStringToOemString (&FileNameA, &FileNameU, FALSE);
+
+    FileNameA.Buffer[FileNameA.Length] = 0;
+}
+
 /*
  * @implemented
  */
 BOOL
 STDCALL
 InternalFindNextFile (
-	HANDLE	hFindFile
+	HANDLE	hFindFile,
+        PUNICODE_STRING SearchPattern
 	)
 {
 	PKERNEL32_FIND_FILE_DATA IData;
@@ -52,32 +130,40 @@
 
 	IData = (PKERNEL32_FIND_FILE_DATA)hFindFile;
 
-	if (IData->pFileInfo->NextEntryOffset != 0)
-	{
-	   IData->pFileInfo = (PVOID)((ULONG_PTR)IData->pFileInfo + IData->pFileInfo->NextEntryOffset);
-	   DPRINT("Found %.*S\n",IData->pFileInfo->FileNameLength/sizeof(WCHAR), IData->pFileInfo->FileName);
-	   return TRUE;
-	}
-	IData->pFileInfo = (PVOID)((ULONG_PTR)IData + sizeof(KERNEL32_FIND_FILE_DATA));
-	IData->pFileInfo->FileIndex = 0;
-	Status = NtQueryDirectoryFile (IData->DirectoryHandle,
-	                               NULL,
-	                               NULL,
-	                               NULL,
-	                               &IoStatusBlock,
-	                               (PVOID)IData->pFileInfo,
-	                               FIND_DATA_SIZE,
-	                               FileBothDirectoryInformation,
-	                               FALSE,
-	                               NULL,
-	                               FALSE);
-	if (!NT_SUCCESS(Status))
-	{
-		SetLastErrorByStatus (Status);
-		return FALSE;
-	}
-	DPRINT("Found %.*S\n",IData->pFileInfo->FileNameLength/sizeof(WCHAR), IData->pFileInfo->FileName);
-	return TRUE;
+        while (1)
+        {
+            if (IData->pFileInfo->NextEntryOffset != 0)
+	    {
+	        IData->pFileInfo = (PVOID)((ULONG_PTR)IData->pFileInfo + IData->pFileInfo->NextEntryOffset);
+            }
+            else
+            {
+                IData->pFileInfo = (PVOID)((ULONG_PTR)IData + sizeof(KERNEL32_FIND_FILE_DATA));
+	        IData->pFileInfo->FileIndex = 0;
+	        Status = NtQueryDirectoryFile (IData->DirectoryHandle,
+	                                       NULL,
+                                               NULL,
+                                               NULL,
+                                               &IoStatusBlock,
+                                               (PVOID)IData->pFileInfo,
+                                               FIND_DATA_SIZE,
+                                               FileBothDirectoryInformation,
+                                               SearchPattern ? TRUE : FALSE,
+                                               SearchPattern,
+                                               SearchPattern ? TRUE : FALSE);
+                SearchPattern = NULL;
+                if (!NT_SUCCESS(Status))
+                {
+                    SetLastErrorByStatus (Status);
+                    return FALSE;
+	        }
+            }
+            if (!IData->DirectoryOnly || IData->pFileInfo->FileAttributes & FILE_ATTRIBUTE_DIRECTORY)
+            {
+	        DPRINT("Found %.*S\n",IData->pFileInfo->FileNameLength/sizeof(WCHAR), IData->pFileInfo->FileName);
+	        return TRUE;
+            }
+        }
 }
 
 
@@ -87,7 +173,8 @@
 HANDLE
 STDCALL
 InternalFindFirstFile (
-	LPCWSTR	lpFileName
+	LPCWSTR	lpFileName,
+        BOOLEAN DirectoryOnly
 	)
 {
 	OBJECT_ATTRIBUTES ObjectAttributes;
@@ -273,34 +360,22 @@
 	}
 	IData->pFileInfo = (PVOID)((ULONG_PTR)IData + sizeof(KERNEL32_FIND_FILE_DATA));
 	IData->pFileInfo->FileIndex = 0;
+        IData->DirectoryOnly = DirectoryOnly;
 
-	Status = NtQueryDirectoryFile (IData->DirectoryHandle,
-	                               NULL,
-	                               NULL,
-	                               NULL,
-	                               &IoStatusBlock,
-	                               (PVOID)IData->pFileInfo,
-	                               FIND_DATA_SIZE,
-	                               FileBothDirectoryInformation,
-	                               TRUE,
-	                               &PatternStr,
-	                               TRUE);
+        bResult = InternalFindNextFile((HANDLE)IData, &PatternStr);
 	if (NULL != SlashlessFileName)
 	{
 	   RtlFreeHeap(hProcessHeap,
 	               0,
 	               SlashlessFileName);
 	}
-	if (!NT_SUCCESS(Status))
-	{
-	   DPRINT("Status %lx\n", Status);
-	   CloseHandle (IData->DirectoryHandle);
-	   RtlFreeHeap (hProcessHeap, 0, IData);
-	   SetLastErrorByStatus (Status);
-	   return NULL;
-	}
-	DPRINT("Found %.*S\n",IData->pFileInfo->FileNameLength/sizeof(WCHAR), IData->pFileInfo->FileName);
 
+        if (!bResult)
+        {
+            FindClose((HANDLE)IData);
+            return NULL;
+        }
+
 	return IData;
 }
 
@@ -332,7 +407,7 @@
 		                             &FileName,
 		                             TRUE);
 
-	IData = InternalFindFirstFile (FileNameU.Buffer);
+	IData = InternalFindFirstFile (FileNameU.Buffer, FALSE);
 
 	RtlFreeUnicodeString (&FileNameU);
 
@@ -346,59 +421,9 @@
 	       IData->pFileInfo->FileNameLength);
 
 	/* copy data into WIN32_FIND_DATA structure */
-	lpFindFileData->dwFileAttributes = IData->pFileInfo->FileAttributes;
+        InternalCopyFindDataA(lpFindFileData, IData->pFileInfo);
 
-	lpFindFileData->ftCreationTime.dwHighDateTime = IData->pFileInfo->CreationTime.u.HighPart;
-	lpFindFileData->ftCreationTime.dwLowDateTime = IData->pFileInfo->CreationTime.u.LowPart;
 
-	lpFindFileData->ftLastAccessTime.dwHighDateTime = IData->pFileInfo->LastAccessTime.u.HighPart;
-	lpFindFileData->ftLastAccessTime.dwLowDateTime = IData->pFileInfo->LastAccessTime.u.LowPart;
-
-	lpFindFileData->ftLastWriteTime.dwHighDateTime = IData->pFileInfo->LastWriteTime.u.HighPart;
-	lpFindFileData->ftLastWriteTime.dwLowDateTime = IData->pFileInfo->LastWriteTime.u.LowPart;
-
-	lpFindFileData->nFileSizeHigh = IData->pFileInfo->EndOfFile.u.HighPart;
-	lpFindFileData->nFileSizeLow = IData->pFileInfo->EndOfFile.u.LowPart;
-
-	FileNameU.Length = IData->pFileInfo->FileNameLength;
-	FileNameU.MaximumLength = FileNameU.Length + sizeof(WCHAR);
-	FileNameU.Buffer = IData->pFileInfo->FileName;
-
-	FileName.Length = 0;
-	FileName.MaximumLength = MAX_PATH;
-	FileName.Buffer = lpFindFileData->cFileName;
-
-	/* convert unicode string to ansi (or oem) */
-	if (bIsFileApiAnsi)
-		RtlUnicodeStringToAnsiString (&FileName,
-		                              &FileNameU,
-		                              FALSE);
-	else
-		RtlUnicodeStringToOemString (&FileName,
-		                             &FileNameU,
-		                             FALSE);
-
-	DPRINT("IData->pFileInfo->ShortNameLength %d\n",
-	       IData->pFileInfo->ShortNameLength);
-
-	FileNameU.Length = IData->pFileInfo->ShortNameLength;
-	FileNameU.MaximumLength = FileNameU.Length + sizeof(WCHAR);
-	FileNameU.Buffer = IData->pFileInfo->ShortName;
-
-	FileName.Length = 0;
-	FileName.MaximumLength = 14;
-	FileName.Buffer = lpFindFileData->cAlternateFileName;
-
-	/* convert unicode string to ansi (or oem) */
-	if (bIsFileApiAnsi)
-		RtlUnicodeStringToAnsiString (&FileName,
-		                              &FileNameU,
-		                              FALSE);
-	else
-		RtlUnicodeStringToOemString (&FileName,
-		                             &FileNameU,
-		                             FALSE);
-
 	return (HANDLE)IData;
 }
 
@@ -413,8 +438,6 @@
 	LPWIN32_FIND_DATAA lpFindFileData)
 {
 	PKERNEL32_FIND_FILE_DATA IData;
-	UNICODE_STRING FileNameU;
-	ANSI_STRING FileName;
 
 	if (hFindFile == INVALID_HANDLE_VALUE)
 	{
@@ -424,7 +447,7 @@
 	}
 
 	IData = (PKERNEL32_FIND_FILE_DATA)hFindFile;
-	if (!InternalFindNextFile (hFindFile))
+	if (!InternalFindNextFile (hFindFile, NULL))
 	{
 		DPRINT("InternalFindNextFile() failed\n");
 		return FALSE;
@@ -434,59 +457,8 @@
 	       IData->pFileInfo->FileNameLength);
 
 	/* copy data into WIN32_FIND_DATA structure */
-	lpFindFileData->dwFileAttributes = IData->pFileInfo->FileAttributes;
+        InternalCopyFindDataA(lpFindFileData, IData->pFileInfo);
 
-	lpFindFileData->ftCreationTime.dwHighDateTime = IData->pFileInfo->CreationTime.u.HighPart;
-	lpFindFileData->ftCreationTime.dwLowDateTime = IData->pFileInfo->CreationTime.u.LowPart;
-
-	lpFindFileData->ftLastAccessTime.dwHighDateTime = IData->pFileInfo->LastAccessTime.u.HighPart;
-	lpFindFileData->ftLastAccessTime.dwLowDateTime = IData->pFileInfo->LastAccessTime.u.LowPart;
-
-	lpFindFileData->ftLastWriteTime.dwHighDateTime = IData->pFileInfo->LastWriteTime.u.HighPart;
-	lpFindFileData->ftLastWriteTime.dwLowDateTime = IData->pFileInfo->LastWriteTime.u.LowPart;
-
-	lpFindFileData->nFileSizeHigh = IData->pFileInfo->EndOfFile.u.HighPart;
-	lpFindFileData->nFileSizeLow = IData->pFileInfo->EndOfFile.u.LowPart;
-
-	FileNameU.Length = IData->pFileInfo->FileNameLength;
-	FileNameU.MaximumLength = FileNameU.Length + sizeof(WCHAR);
-	FileNameU.Buffer = IData->pFileInfo->FileName;
-
-	FileName.Length = 0;
-	FileName.MaximumLength = MAX_PATH;
-	FileName.Buffer = lpFindFileData->cFileName;
-
-	/* convert unicode string to ansi (or oem) */
-	if (bIsFileApiAnsi)
-		RtlUnicodeStringToAnsiString (&FileName,
-		                              &FileNameU,
-		                              FALSE);
-	else
-		RtlUnicodeStringToOemString (&FileName,
-		                             &FileNameU,
-		                             FALSE);
-
-	DPRINT("IData->pFileInfo->ShortNameLength %d\n",
-	       IData->pFileInfo->ShortNameLength);
-
-	FileNameU.Length = IData->pFileInfo->ShortNameLength;
-	FileNameU.MaximumLength = FileNameU.Length + sizeof(WCHAR);
-	FileNameU.Buffer = IData->pFileInfo->ShortName;
-
-	FileName.Length = 0;
-	FileName.MaximumLength = 14;
-	FileName.Buffer = lpFindFileData->cAlternateFileName;
-
-	/* convert unicode string to ansi (or oem) */
-	if (bIsFileApiAnsi)
-		RtlUnicodeStringToAnsiString (&FileName,
-		                              &FileNameU,
-		                              FALSE);
-	else
-		RtlUnicodeStringToOemString (&FileName,
-		                             &FileNameU,
-		                             FALSE);
-
 	return TRUE;
 }
 
@@ -529,42 +501,15 @@
 	LPWIN32_FIND_DATAW	lpFindFileData
 	)
 {
-	PKERNEL32_FIND_FILE_DATA IData;
 
-	IData = InternalFindFirstFile (lpFileName);
-	if (IData == NULL)
-	{
-		DPRINT("Failing request\n");
-		return INVALID_HANDLE_VALUE;
-	}
-
-	/* copy data into WIN32_FIND_DATA structure */
-	lpFindFileData->dwFileAttributes = IData->pFileInfo->FileAttributes;
-
-	lpFindFileData->ftCreationTime.dwHighDateTime = IData->pFileInfo->CreationTime.u.HighPart;
-	lpFindFileData->ftCreationTime.dwLowDateTime = IData->pFileInfo->CreationTime.u.LowPart;
-
-	lpFindFileData->ftLastAccessTime.dwHighDateTime = IData->pFileInfo->LastAccessTime.u.HighPart;
-	lpFindFileData->ftLastAccessTime.dwLowDateTime = IData->pFileInfo->LastAccessTime.u.LowPart;
-
-	lpFindFileData->ftLastWriteTime.dwHighDateTime = IData->pFileInfo->LastWriteTime.u.HighPart;
-	lpFindFileData->ftLastWriteTime.dwLowDateTime = IData->pFileInfo->LastWriteTime.u.LowPart;
-
-	lpFindFileData->nFileSizeHigh = IData->pFileInfo->EndOfFile.u.HighPart;
-	lpFindFileData->nFileSizeLow = IData->pFileInfo->EndOfFile.u.LowPart;
-
-	memcpy (lpFindFileData->cFileName,
-	        IData->pFileInfo->FileName,
-	        IData->pFileInfo->FileNameLength);
-	lpFindFileData->cFileName[IData->pFileInfo->FileNameLength / sizeof(WCHAR)] = 0;
-	memcpy (lpFindFileData->cAlternateFileName,
-	        IData->pFileInfo->ShortName,
-	        IData->pFileInfo->ShortNameLength);
-	lpFindFileData->cAlternateFileName[IData->pFileInfo->ShortNameLength / sizeof(WCHAR)] = 0;
-	return IData;
+        return FindFirstFileExW (lpFileName,
+                                 FindExInfoStandard,
+                                 (LPVOID)lpFindFileData,
+                                 FindExSearchNameMatch,
+                                 NULL,
+                                 0);
 }
 
-
 /*
  * @implemented
  */
@@ -585,38 +530,15 @@
 	}
 
 	IData = (PKERNEL32_FIND_FILE_DATA)hFindFile;
-	if (!InternalFindNextFile(hFindFile))
+	if (!InternalFindNextFile(hFindFile, NULL))
 	{
 		DPRINT("Failing request\n");
 		return FALSE;
 	}
 
 	/* copy data into WIN32_FIND_DATA structure */
-	lpFindFileData->dwFileAttributes = IData->pFileInfo->FileAttributes;
+        InternalCopyFindDataW(lpFindFileData, IData->pFileInfo);
 
-	lpFindFileData->ftCreationTime.dwHighDateTime = IData->pFileInfo->CreationTime.u.HighPart;
-	lpFindFileData->ftCreationTime.dwLowDateTime = IData->pFileInfo->CreationTime.u.LowPart;
-
-	lpFindFileData->ftLastAccessTime.dwHighDateTime = IData->pFileInfo->LastAccessTime.u.HighPart;
-	lpFindFileData->ftLastAccessTime.dwLowDateTime = IData->pFileInfo->LastAccessTime.u.LowPart;
-
-	lpFindFileData->ftLastWriteTime.dwHighDateTime = IData->pFileInfo->LastWriteTime.u.HighPart;
-	lpFindFileData->ftLastWriteTime.dwLowDateTime = IData->pFileInfo->LastWriteTime.u.LowPart;
-
-	lpFindFileData->nFileSizeHigh = IData->pFileInfo->EndOfFile.u.HighPart;
-	lpFindFileData->nFileSizeLow = IData->pFileInfo->EndOfFile.u.LowPart;
-
-	lpFindFileData->nFileSizeHigh = IData->pFileInfo->EndOfFile.u.HighPart;
-	lpFindFileData->nFileSizeLow = IData->pFileInfo->EndOfFile.u.LowPart;
-
-        memcpy (lpFindFileData->cFileName,
-	        IData->pFileInfo->FileName,
-	        IData->pFileInfo->FileNameLength);
-	lpFindFileData->cFileName[IData->pFileInfo->FileNameLength / sizeof(WCHAR)] = 0;
-	memcpy (lpFindFileData->cAlternateFileName,
-	        IData->pFileInfo->ShortName,
-	        IData->pFileInfo->ShortNameLength);
-	lpFindFileData->cAlternateFileName[IData->pFileInfo->ShortNameLength / sizeof(WCHAR)] = 0;
 	return TRUE;
 }
 
@@ -626,20 +548,44 @@
  */
 HANDLE
 STDCALL
-FindFirstFileExW (
-	LPCWSTR			lpFileName,
-	FINDEX_INFO_LEVELS	fInfoLevelId,
-	LPVOID			lpFindFileData,
-	FINDEX_SEARCH_OPS	fSearchOp,
-	LPVOID			lpSearchFilter,
-	DWORD			dwAdditionalFlags
-	)
+FindFirstFileExW (LPCWSTR               lpFileName,
+                  FINDEX_INFO_LEVELS    fInfoLevelId,
+                  LPVOID                lpFindFileData,
+                  FINDEX_SEARCH_OPS     fSearchOp,
+                  LPVOID                lpSearchFilter,
+                  DWORD                 dwAdditionalFlags)
 {
-	/* FIXME */
-	return (HANDLE) 0;
-}
+    PKERNEL32_FIND_FILE_DATA IData;
 
+    if (fInfoLevelId != FindExInfoStandard)
+    {
+        SetLastError(ERROR_INVALID_PARAMETER);
+        return INVALID_HANDLE_VALUE;
+    }
+    if (fSearchOp == FindExSearchNameMatch || fSearchOp == FindExSearchLimitToDirectories)
+    {
+        if (lpSearchFilter)
+        {
+            SetLastError(ERROR_INVALID_PARAMETER);
+            return INVALID_HANDLE_VALUE;
+        }
 
+        IData = InternalFindFirstFile (lpFileName, fSearchOp == FindExSearchLimitToDirectories ? TRUE : FALSE);
+	if (IData == NULL)
+	{
+		DPRINT("Failing request\n");
+		return INVALID_HANDLE_VALUE;
+	}
+
+	/* copy data into WIN32_FIND_DATA structure */
+        InternalCopyFindDataW((LPWIN32_FIND_DATAW)lpFindFileData, IData->pFileInfo);
+
+	return (HANDLE)IData;
+    }
+    SetLastError(ERROR_INVALID_PARAMETER);
+    return INVALID_HANDLE_VALUE;
+}
+
 /*
  * @unimplemented
  */
@@ -654,8 +600,46 @@
 	DWORD			dwAdditionalFlags
 	)
 {
-	/* FIXME */
-	return (HANDLE) 0;
+    PKERNEL32_FIND_FILE_DATA IData;
+    UNICODE_STRING FileNameU;
+    ANSI_STRING FileNameA;
+
+    if (fInfoLevelId != FindExInfoStandard)
+    {
+        SetLastError(ERROR_INVALID_PARAMETER);
+        return INVALID_HANDLE_VALUE;
+    }
+    if (fSearchOp == FindExSearchNameMatch || fSearchOp == FindExSearchLimitToDirectories)
+    {
+        if (lpSearchFilter)
+        {
+            SetLastError(ERROR_INVALID_PARAMETER);
+            return INVALID_HANDLE_VALUE;
+        }
+	
+        RtlInitAnsiString (&FileNameA, (LPSTR)lpFileName);
+
+	/* convert ansi (or oem) string to unicode */
+	if (bIsFileApiAnsi)
+            RtlAnsiStringToUnicodeString (&FileNameU, &FileNameA, TRUE);
+	else
+            RtlOemStringToUnicodeString (&FileNameU, &FileNameA, TRUE);
+
+	IData = InternalFindFirstFile (FileNameU.Buffer, FALSE);
+
+	RtlFreeUnicodeString (&FileNameU);
+
+	if (IData == NULL)
+	{
+		DPRINT("Failing request\n");
+		return INVALID_HANDLE_VALUE;
+	}
+
+	/* copy data into WIN32_FIND_DATA structure */
+        InternalCopyFindDataA(lpFindFileData, IData->pFileInfo);
+    }
+    SetLastError(ERROR_INVALID_PARAMETER);
+    return INVALID_HANDLE_VALUE;
 }