int21 move a5

György 'Nog' Jeney nog at sdf.lonestar.org
Sat Nov 9 07:51:40 CST 2002


ChangeLog:
 * dlls/winedos/int21.c
 * msdos/int21.c
   Move find{first|next} to winedos

nog.

-------------- next part --------------
--- dlls/winedos/int21.c.a4	2002-11-09 08:34:24.000000000 +0200
+++ dlls/winedos/int21.c	2002-11-09 09:41:20.000000000 +0200
@@ -33,6 +33,7 @@
 #include "miscemu.h"
 #include "msdos.h"
 #include "file.h"
+#include "task.h"
 #include "wine/unicode.h"
 #include "wine/debug.h"
 
@@ -40,6 +41,107 @@
 
 WORD CodePage = 437;
 
+static int GetDosDrive(int drive)
+{
+  if(drive)
+    return drive - 1;
+  else {
+    char root[MAX_PATH];
+    GetCurrentDirectoryA(MAX_PATH, root);
+    return toupper(*root) - 'A';
+  }
+}
+
+static BYTE *GetCurrentDTA(CONTEXT86 *context)
+{
+    TDB *pTask = GlobalLock16(GetCurrentTask());
+
+    return (BYTE *)CTX_SEG_OFF_TO_LIN(context, SELECTOROF(pTask->dta),
+                                                (DWORD)OFFSETOF(pTask->dta));
+}
+
+static int INT21_FindFirst( CONTEXT86 *context )
+{
+    const char *path;
+    FINDFILE_DTA *dta = (FINDFILE_DTA *)GetCurrentDTA(context);
+    int count = 0;
+    WIN32_FIND_DATAA entry;
+
+    path = (const char *)CTX_SEG_OFF_TO_LIN(context, context->SegDs,
+                                            context->Edx);
+
+    /* Fill in the DTA */
+    strcpy(dta->mask, path);
+    dta->search_attr = CX_reg(context);
+    dta->count = 0;
+    dta->cluster = 0; /* What are we meant to do here ?? */
+    dta->drive = GetDosDrive(0);
+
+    if((dta->handle = FindFirstFileA(path, &entry)) == INVALID_HANDLE_VALUE)
+       return 0;
+
+findagain:
+
+    /* Check to see if the attributes match */
+    if(dta->search_attr == (entry.dwFileAttributes & 0x1f)) {
+      /* The search attributes match, return file valid */
+      strcpy(dta->mask, path);
+      dta->search_attr = CX_reg(context);
+      dta->count = count;
+
+      dta->fileattr = dta->search_attr;
+      FileTimeToDosDateTime(&entry.ftLastWriteTime, &dta->filedate, &dta->filetime);
+      dta->filesize = entry.nFileSizeLow;
+      strcpy(dta->filename, entry.cAlternateFileName);
+      TRACE("Search attributes match, returning %s, drive %x\n", dta->filename,
+                                                                 dta->drive);
+    } else {
+      /* Continue searching */
+      if(FindNextFileA(dta->handle, &entry)) {
+        count++;
+        goto findagain;
+      } else {
+        FindClose(dta->handle);
+        return 0;
+      }
+    }
+
+    if (!memchr(dta->mask,'?',11)) {
+        /* wildcardless search, release resources in case no findnext will
+         * be issued, and as a workaround in case file creation messes up
+         * findnext, as sometimes happens with pkunzip */
+        FindClose(dta->handle);
+    }
+
+    return 1;
+}
+
+static int INT21_FindNext(CONTEXT86 *context)
+{
+    FINDFILE_DTA *dta = (FINDFILE_DTA *)GetCurrentDTA(context);
+    WIN32_FIND_DATAA entry;
+    int count = dta->count;
+
+    for(;; ++count) {
+      if(FindNextFileA(dta->handle, &entry)) {
+        if(dta->search_attr == (entry.dwFileAttributes & 0x1f)) {
+          dta->count = count;
+          dta->fileattr = dta->search_attr;
+          FileTimeToDosDateTime(&entry.ftLastWriteTime, &dta->filedate,
+                                &dta->filetime);
+          dta->filesize = entry.nFileSizeLow;
+          strcpy(dta->filename, entry.cAlternateFileName);
+          return 1;
+        }
+      } else {
+        FindClose(dta->handle);
+        return 0;
+      }
+    }
+
+    return 1;
+}
+
 /***********************************************************************
  *           INT21_GetExtendedError
  */
@@ -516,6 +618,27 @@
         DOSVM_retval = 0;
         break;
 
+    case 0x4e: /* "FINDFIRST" - FIND FIRST MATCHING FILE */
+        TRACE("FINDFIRST mask 0x%04x spec %s\n", CX_reg(context),
+              (LPCSTR)CTX_SEG_OFF_TO_LIN(context, context->SegDs, context->Edx));
+        if(!INT21_FindFirst(context)) {
+            SetLastError( ERROR_NO_MORE_FILES );
+            SET_AX( context, ERROR_NO_MORE_FILES );
+            SET_CFLAG(context);
+        }
+        break;
+
+    case 0x4f: /* "FINDNEXT" - FIND NEXT MATCHING FILE */
+        TRACE("FINDNEXT\n");
+        if (!INT21_FindNext(context))
+        {
+            SetLastError( ERROR_NO_MORE_FILES );
+            SET_AX( context, ERROR_NO_MORE_FILES );
+            SET_CFLAG(context);
+        }
+        else SET_AX( context, 0 );  /* OK */
+        break;
+
     case 0x50: /* SET CURRENT PROCESS ID (SET PSP ADDRESS) */
         TRACE("SET CURRENT PROCESS ID (SET PSP ADDRESS)\n");
         DOSVM_psp = BX_reg(context);
--- msdos/int21.c.a4	2002-11-09 08:15:42.000000000 +0200
+++ msdos/int21.c	2002-11-09 09:41:17.000000000 +0200
@@ -614,92 +614,6 @@
     return DRIVE_Chdir( drive, dirnameW );
 }
 
-
-static int INT21_FindFirst( CONTEXT86 *context )
-{
-    char *p;
-    const char *path;
-    DOS_FULL_NAME full_name;
-    FINDFILE_DTA *dta = (FINDFILE_DTA *)GetCurrentDTA(context);
-    WCHAR pathW[MAX_PATH];
-    WCHAR maskW[12];
-
-    path = (const char *)CTX_SEG_OFF_TO_LIN(context, context->SegDs, context->Edx);
-    MultiByteToWideChar(CP_OEMCP, 0, path, -1, pathW, MAX_PATH);
-
-    dta->unixPath = NULL;
-    if (!DOSFS_GetFullName( pathW, FALSE, &full_name ))
-    {
-        SET_AX( context, GetLastError() );
-        SET_CFLAG(context);
-        return 0;
-    }
-    dta->unixPath = HeapAlloc( GetProcessHeap(), 0, strlen(full_name.long_name)+1 );
-    strcpy( dta->unixPath, full_name.long_name );
-    p = strrchr( dta->unixPath, '/' );
-    *p = '\0';
-
-    MultiByteToWideChar(CP_OEMCP, 0, p + 1, -1, pathW, MAX_PATH);
-
-    /* Note: terminating NULL in dta->mask overwrites dta->search_attr
-     *       (doesn't matter as it is set below anyway)
-     */
-    if (!DOSFS_ToDosFCBFormat( pathW, maskW ))
-    {
-        HeapFree( GetProcessHeap(), 0, dta->unixPath );
-        dta->unixPath = NULL;
-        SetLastError( ERROR_FILE_NOT_FOUND );
-        SET_AX( context, ERROR_FILE_NOT_FOUND );
-        SET_CFLAG(context);
-        return 0;
-    }
-    WideCharToMultiByte(CP_OEMCP, 0, maskW, 12, dta->mask, sizeof(dta->mask), NULL, NULL);
-    dta->drive = (path[0] && (path[1] == ':')) ? toupper(path[0]) - 'A'
-                                               : DRIVE_GetCurrentDrive();
-    dta->count = 0;
-    dta->search_attr = CL_reg(context);
-    return 1;
-}
-
-
-static int INT21_FindNext( CONTEXT86 *context )
-{
-    FINDFILE_DTA *dta = (FINDFILE_DTA *)GetCurrentDTA(context);
-    WIN32_FIND_DATAA entry;
-    int count;
-
-    if (!dta->unixPath) return 0;
-    if (!(count = DOSFS_FindNext( dta->unixPath, dta->mask, NULL, dta->drive,
-                                  dta->search_attr, dta->count, &entry )))
-    {
-        HeapFree( GetProcessHeap(), 0, dta->unixPath );
-        dta->unixPath = NULL;
-        return 0;
-    }
-    if ((int)dta->count + count > 0xffff)
-    {
-        WARN("Too many directory entries in %s\n", dta->unixPath );
-        HeapFree( GetProcessHeap(), 0, dta->unixPath );
-        dta->unixPath = NULL;
-        return 0;
-    }
-    dta->count += count;
-    dta->fileattr = entry.dwFileAttributes;
-    dta->filesize = entry.nFileSizeLow;
-    FileTimeToDosDateTime( &entry.ftLastWriteTime,
-                           &dta->filedate, &dta->filetime );
-    strcpy( dta->filename, entry.cAlternateFileName );
-    if (!memchr(dta->mask,'?',11)) {
-	/* wildcardless search, release resources in case no findnext will
-	 * be issued, and as a workaround in case file creation messes up
-	 * findnext, as sometimes happens with pkunzip */
-        HeapFree( GetProcessHeap(), 0, dta->unixPath );
-        dta->unixPath = NULL;
-    }
-    return 1;
-}
-
-
 static BOOL INT21_CreateTempFile( CONTEXT86 *context )
 {
     static int counter = 0;
@@ -1527,22 +1441,6 @@
         ExitThread( AL_reg(context) );
         break;
 
-    case 0x4e: /* "FINDFIRST" - FIND FIRST MATCHING FILE */
-        TRACE("FINDFIRST mask 0x%04x spec %s\n",CX_reg(context),
-	      (LPCSTR)CTX_SEG_OFF_TO_LIN(context,  context->SegDs, context->Edx));
-        if (!INT21_FindFirst(context)) break;
-        /* fall through */
-
-    case 0x4f: /* "FINDNEXT" - FIND NEXT MATCHING FILE */
-        TRACE("FINDNEXT\n");
-        if (!INT21_FindNext(context))
-        {
-            SetLastError( ERROR_NO_MORE_FILES );
-            SET_AX( context, ERROR_NO_MORE_FILES );
-            SET_CFLAG(context);
-        }
-        else SET_AX( context, 0 );  /* OK */
-        break;
     case 0x51: /* GET PSP ADDRESS */
         TRACE("GET CURRENT PROCESS ID (GET PSP ADDRESS)\n");
         /* FIXME: should we return the original DOS PSP upon */



More information about the wine-patches mailing list