Piotr Caban : msvcrt: Added _splitpath_s implementation.

Alexandre Julliard julliard at winehq.org
Mon Aug 30 13:00:38 CDT 2010


Module: wine
Branch: master
Commit: 899d9a042b18a511aecd92dba72084e6d63cc28d
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=899d9a042b18a511aecd92dba72084e6d63cc28d

Author: Piotr Caban <piotr at codeweavers.com>
Date:   Sun Aug 29 16:59:35 2010 +0200

msvcrt: Added _splitpath_s implementation.

---

 dlls/msvcr100/msvcr100.spec |    2 +-
 dlls/msvcr80/msvcr80.spec   |    2 +-
 dlls/msvcr90/msvcr90.spec   |    2 +-
 dlls/msvcrt/dir.c           |  105 ++++++++++++++++++++++++++++++++----------
 dlls/msvcrt/msvcrt.h        |    5 ++
 dlls/msvcrt/msvcrt.spec     |    4 +-
 6 files changed, 90 insertions(+), 30 deletions(-)

diff --git a/dlls/msvcr100/msvcr100.spec b/dlls/msvcr100/msvcr100.spec
index 66c0f7b..100e78a 100644
--- a/dlls/msvcr100/msvcr100.spec
+++ b/dlls/msvcr100/msvcr100.spec
@@ -1116,7 +1116,7 @@
 @ cdecl _spawnvp(long str ptr) msvcrt._spawnvp
 @ cdecl _spawnvpe(long str ptr ptr) msvcrt._spawnvpe
 @ cdecl _splitpath(str ptr ptr ptr ptr) msvcrt._splitpath
-@ stub _splitpath_s
+@ cdecl _splitpath_s(str ptr long ptr long ptr long ptr long) msvcrt._splitpath_s
 @ stub _sprintf_l
 @ stub _sprintf_p
 @ stub _sprintf_p_l
diff --git a/dlls/msvcr80/msvcr80.spec b/dlls/msvcr80/msvcr80.spec
index efc450d..206769a 100644
--- a/dlls/msvcr80/msvcr80.spec
+++ b/dlls/msvcr80/msvcr80.spec
@@ -970,7 +970,7 @@
 @ cdecl _spawnvp(long str ptr) msvcrt._spawnvp
 @ cdecl _spawnvpe(long str ptr ptr) msvcrt._spawnvpe
 @ cdecl _splitpath(str ptr ptr ptr ptr) msvcrt._splitpath
-@ stub _splitpath_s
+@ cdecl _splitpath_s(str ptr long ptr long ptr long ptr long) msvcrt._splitpath_s
 @ stub _sprintf_l
 @ stub _sprintf_p
 @ stub _sprintf_p_l
diff --git a/dlls/msvcr90/msvcr90.spec b/dlls/msvcr90/msvcr90.spec
index e0d0068..b0e3df8 100644
--- a/dlls/msvcr90/msvcr90.spec
+++ b/dlls/msvcr90/msvcr90.spec
@@ -956,7 +956,7 @@
 @ cdecl _spawnvp(long str ptr) msvcrt._spawnvp
 @ cdecl _spawnvpe(long str ptr ptr) msvcrt._spawnvpe
 @ cdecl _splitpath(str ptr ptr ptr ptr) msvcrt._splitpath
-@ stub _splitpath_s
+@ cdecl _splitpath_s(str ptr long ptr long ptr long ptr long) msvcrt._splitpath_s
 @ stub _sprintf_l
 @ stub _sprintf_p
 @ stub _sprintf_p_l
diff --git a/dlls/msvcrt/dir.c b/dlls/msvcrt/dir.c
index c5b6638..5beb91b 100644
--- a/dlls/msvcrt/dir.c
+++ b/dlls/msvcrt/dir.c
@@ -745,27 +745,42 @@ int CDECL _wrmdir(const MSVCRT_wchar_t * dir)
   return -1;
 }
 
-/*********************************************************************
- *		_wsplitpath (MSVCRT.@)
- *
- * Unicode version of _splitpath.
+/******************************************************************
+ *		_splitpath_s (MSVCRT.@)
  */
-void CDECL _wsplitpath(const MSVCRT_wchar_t *inpath, MSVCRT_wchar_t *drv, MSVCRT_wchar_t *dir,
-                       MSVCRT_wchar_t *fname, MSVCRT_wchar_t *ext )
+int _splitpath_s(const char* inpath,
+        char* drive, MSVCRT_size_t sz_drive,
+        char* dir, MSVCRT_size_t sz_dir,
+        char* fname, MSVCRT_size_t sz_fname,
+        char* ext, MSVCRT_size_t sz_ext)
 {
-    const MSVCRT_wchar_t *p, *end;
+    const char *p, *end;
+
+    if (!inpath || (!drive && sz_drive) ||
+            (drive && !sz_drive) ||
+            (!dir && sz_dir) ||
+            (dir && !sz_dir) ||
+            (!fname && sz_fname) ||
+            (fname && !sz_fname) ||
+            (!ext && sz_ext) ||
+            (ext && !sz_ext))
+    {
+        *MSVCRT__errno() = MSVCRT_EINVAL;
+        return MSVCRT_EINVAL;
+    }
 
     if (inpath[0] && inpath[1] == ':')
     {
-        if (drv)
+        if (drive)
         {
-            drv[0] = inpath[0];
-            drv[1] = inpath[1];
-            drv[2] = 0;
+            if (sz_drive <= 2) goto do_error;
+            drive[0] = inpath[0];
+            drive[1] = inpath[1];
+            drive[2] = 0;
         }
         inpath += 2;
     }
-    else if (drv) drv[0] = 0;
+    else if (drive) drive[0] = '\0';
 
     /* look for end of directory part */
     end = NULL;
@@ -775,7 +790,8 @@ void CDECL _wsplitpath(const MSVCRT_wchar_t *inpath, MSVCRT_wchar_t *drv, MSVCRT
     {
         if (dir)
         {
-            memcpy( dir, inpath, (end - inpath) * sizeof(MSVCRT_wchar_t) );
+            if (sz_dir <= end - inpath) goto do_error;
+            memcpy( dir, inpath, (end - inpath) );
             dir[end - inpath] = 0;
         }
         inpath = end;
@@ -790,10 +806,33 @@ void CDECL _wsplitpath(const MSVCRT_wchar_t *inpath, MSVCRT_wchar_t *drv, MSVCRT
 
     if (fname)
     {
-        memcpy( fname, inpath, (end - inpath) * sizeof(MSVCRT_wchar_t) );
+        if (sz_fname <= end - inpath) goto do_error;
+        memcpy( fname, inpath, (end - inpath) );
         fname[end - inpath] = 0;
     }
-    if (ext) strcpyW( ext, end );
+    if (ext)
+    {
+        if (sz_ext <= strlen(end)) goto do_error;
+        strcpy( ext, end );
+    }
+    return 0;
+do_error:
+    if (drive)  drive[0] = '\0';
+    if (dir)    dir[0] = '\0';
+    if (fname)  fname[0]= '\0';
+    if (ext)    ext[0]= '\0';
+    *MSVCRT__errno() = MSVCRT_ERANGE;
+    return MSVCRT_ERANGE;
+}
+
+/*********************************************************************
+ *              _splitpath (MSVCRT.@)
+ */
+void CDECL _splitpath(const char *inpath, char *drv, char *dir,
+        char *fname, char *ext)
+{
+    _splitpath_s(inpath, drv, MSVCRT__MAX_DRIVE, dir, MSVCRT__MAX_DIR,
+            fname, MSVCRT__MAX_FNAME, ext, MSVCRT__MAX_EXT);
 }
 
 /******************************************************************
@@ -809,15 +848,18 @@ int _wsplitpath_s(const MSVCRT_wchar_t* inpath,
 {
     const MSVCRT_wchar_t *p, *end;
 
-    if (!inpath) return MSVCRT_EINVAL;
-    if (!drive && sz_drive) return MSVCRT_EINVAL;
-    if (drive && !sz_drive) return MSVCRT_EINVAL;
-    if (!dir && sz_dir) return MSVCRT_EINVAL;
-    if (dir && !sz_dir) return MSVCRT_EINVAL;
-    if (!fname && sz_fname) return MSVCRT_EINVAL;
-    if (fname && !sz_fname) return MSVCRT_EINVAL;
-    if (!ext && sz_ext) return MSVCRT_EINVAL;
-    if (ext && !sz_ext) return MSVCRT_EINVAL;
+    if (!inpath || (!drive && sz_drive) ||
+            (drive && !sz_drive) ||
+            (!dir && sz_dir) ||
+            (dir && !sz_dir) ||
+            (!fname && sz_fname) ||
+            (fname && !sz_fname) ||
+            (!ext && sz_ext) ||
+            (ext && !sz_ext))
+    {
+        *MSVCRT__errno() = MSVCRT_EINVAL;
+        return MSVCRT_EINVAL;
+    }
 
     if (inpath[0] && inpath[1] == ':')
     {
@@ -871,10 +913,23 @@ do_error:
     if (dir)    dir[0] = '\0';
     if (fname)  fname[0]= '\0';
     if (ext)    ext[0]= '\0';
+    *MSVCRT__errno() = MSVCRT_ERANGE;
     return MSVCRT_ERANGE;
 }
 
 /*********************************************************************
+ *		_wsplitpath (MSVCRT.@)
+ *
+ * Unicode version of _splitpath.
+ */
+void CDECL _wsplitpath(const MSVCRT_wchar_t *inpath, MSVCRT_wchar_t *drv, MSVCRT_wchar_t *dir,
+        MSVCRT_wchar_t *fname, MSVCRT_wchar_t *ext)
+{
+    _wsplitpath_s(inpath, drv, MSVCRT__MAX_DRIVE, dir, MSVCRT__MAX_DIR,
+            fname, MSVCRT__MAX_FNAME, ext, MSVCRT__MAX_EXT);
+}
+
+/*********************************************************************
  *		_wfullpath (MSVCRT.@)
  *
  * Unicode version of _fullpath.
diff --git a/dlls/msvcrt/msvcrt.h b/dlls/msvcrt/msvcrt.h
index 86df133..8e0bd43 100644
--- a/dlls/msvcrt/msvcrt.h
+++ b/dlls/msvcrt/msvcrt.h
@@ -47,6 +47,11 @@
 #define MSVCRT_I64_MIN    (-MSVCRT_I64_MAX-1)
 #define MSVCRT_UI64_MAX   (((unsigned __int64)0xffffffff << 32) | 0xffffffff)
 
+#define MSVCRT__MAX_DRIVE  3
+#define MSVCRT__MAX_DIR    256
+#define MSVCRT__MAX_FNAME  256
+#define MSVCRT__MAX_EXT    256
+
 typedef unsigned short MSVCRT_wchar_t;
 typedef unsigned short MSVCRT_wint_t;
 typedef unsigned short MSVCRT_wctype_t;
diff --git a/dlls/msvcrt/msvcrt.spec b/dlls/msvcrt/msvcrt.spec
index 022b0bd..9c9ff7a 100644
--- a/dlls/msvcrt/msvcrt.spec
+++ b/dlls/msvcrt/msvcrt.spec
@@ -892,8 +892,8 @@
 @ cdecl _spawnve(long str ptr ptr) MSVCRT__spawnve
 @ cdecl _spawnvp(long str ptr)
 @ cdecl _spawnvpe(long str ptr ptr) MSVCRT__spawnvpe
-@ cdecl _splitpath(str ptr ptr ptr ptr) ntdll._splitpath
-# stub _splitpath_s
+@ cdecl _splitpath(str ptr ptr ptr ptr)
+@ cdecl _splitpath_s(str ptr long ptr long ptr long ptr long)
 # stub _sprintf_l
 # stub _sprintf_p_l
 # stub _sprintf_s_l




More information about the wine-cvs mailing list