]> git.saurik.com Git - wxWidgets.git/commitdiff
added wxSafeConvertMB2WX/WX2MB() and use them when interfacing with C functions which...
authorVadim Zeitlin <vadim@wxwidgets.org>
Sun, 11 Mar 2007 23:38:42 +0000 (23:38 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Sun, 11 Mar 2007 23:38:42 +0000 (23:38 +0000)
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@44771 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

docs/changes.txt
include/wx/strconv.h
src/common/strconv.cpp
src/palmos/utils.cpp
src/unix/utilsunx.cpp

index f9fea6f4236cbaef869509f115ed0d6314081bcd..e6b69a5b93945aca49ea683f6970153181bc996e 100644 (file)
@@ -70,6 +70,10 @@ All:
 - Fixed Base64 computation in wxHTTP (p_michalczyk)
 - Fix handling of wxSOCKET_REUSEADDR in wxDatagramSocket (troelsk)
 
+Unix Ports:
+
+- Fixed crash in wxGetUserName() in Unicode build
+
 wxMSW
 
 - Fix lack of spin control update event when control lost focus.
index ba28c8a81ab8792f24578b14d76420418b49155f..4e4afff9dca2bfef9a106ecf407d635a0c52d03e 100644 (file)
@@ -521,10 +521,25 @@ extern WXDLLIMPEXP_DATA_BASE(wxMBConv *) wxConvCurrent;
 #if wxUSE_UNICODE
     #define wxConvertWX2MB(s)   wxConvCurrent->cWX2MB(s)
     #define wxConvertMB2WX(s)   wxConvCurrent->cMB2WX(s)
+
+    // these functions should be used when the conversions really, really have
+    // to succeed (usually because we pass their results to a standard C
+    // function which would crash if we passed NULL to it), so these functions
+    // always return a valid pointer if their argument is non-NULL
+
+    // this function safety is achieved by trying wxConvLibc first, wxConvUTF8
+    // next if it fails and, finally, wxConvISO8859_1 which always succeeds
+    extern WXDLLIMPEXP_BASE wxWCharBuffer wxSafeConvertMB2WX(const char *s);
+
+    // this function uses wxConvLibc and wxConvUTF8(MAP_INVALID_UTF8_TO_OCTAL)
+    // if it fails
+    extern WXDLLIMPEXP_BASE wxCharBuffer wxSafeConvertWX2MB(const wchar_t *ws);
 #else // ANSI
     // no conversions to do
     #define wxConvertWX2MB(s)   (s)
     #define wxConvertMB2WX(s)   (s)
+    #define wxSafeConvertMB2WX(s) (s)
+    #define wxSafeConvertWX2MB(s) (s)
 #endif // Unicode/ANSI
 
 #endif // _WX_STRCONV_H_
index bd0a0926c3eaae36e22d52a78be4537886a48ea5..e5150240356d7ca440498f931aec47934430399e 100644 (file)
@@ -3650,9 +3650,39 @@ WXDLLIMPEXP_DATA_BASE(wxMBConv *) wxConvFileName = &
 #else
                                     wxConvUTF8Obj;
 #endif
-#else
+#else // !__WXOSX__
                                     wxConvLibcObj;
-#endif
+#endif // __WXOSX__/!__WXOSX__
+
+#if wxUSE_UNICODE
+
+wxWCharBuffer wxSafeConvertMB2WX(const char *s)
+{
+    if ( !s )
+        return wxWCharBuffer();
+
+    wxWCharBuffer wbuf(wxConvLibc.cMB2WX(s));
+    if ( !wbuf )
+        wbuf = wxConvUTF8.cMB2WX(s);
+    if ( !wbuf )
+        wbuf = wxConvISO8859_1.cMB2WX(s);
+
+    return wbuf;
+}
+
+wxCharBuffer wxSafeConvertWX2MB(const wchar_t *ws)
+{
+    if ( !ws )
+        return wxCharBuffer();
+
+    wxCharBuffer buf(wxConvLibc.cWX2MB(ws));
+    if ( !buf )
+        buf = wxMBConvUTF8(wxMBConvUTF8::MAP_INVALID_UTF8_TO_OCTAL).cWX2MB(ws);
+
+    return buf;
+}
+
+#endif // wxUSE_UNICODE
 
 #else // !wxUSE_WCHAR_T
 
index 81db337f9b7e1b9500c6efb82e23d3c370523b76..f9f5806ec856ab36d5dbebe33ff21e514bfad3d7 100644 (file)
@@ -90,7 +90,7 @@ bool wxGetUserName(wxChar *buf, int maxSize)
         return false;
     }
 
-    wxStrncpy (buf, wxConvertMB2WX(id), maxSize - 1);
+    wxStrncpy (buf, wxSafeConvertMB2WX(id), maxSize - 1);
 
     // free the buffer
     MemPtrUnlock(id);
index 3688288505735f3cd0404c916d4c644176509fa2..73148ac61310490dd218fa9dbe9c745642ef1cf3 100644 (file)
@@ -473,7 +473,7 @@ long wxExecute(wxChar **argv, int flags, wxProcess *process)
 
     while (argv[mb_argc])
     {
-        wxWX2MBbuf mb_arg = wxConvertWX2MB(argv[mb_argc]);
+        wxWX2MBbuf mb_arg = wxSafeConvertWX2MB(argv[mb_argc]);
         mb_argv[mb_argc] = strdup(mb_arg);
         mb_argc++;
     }
@@ -722,7 +722,7 @@ char *wxGetUserHome( const wxString &user )
         }
         if ((ptr = wxGetenv(wxT("USER"))) != NULL || (ptr = wxGetenv(wxT("LOGNAME"))) != NULL)
         {
-            who = getpwnam(wxConvertWX2MB(ptr));
+            who = getpwnam(wxSafeConvertWX2MB(ptr));
         }
 
         // We now make sure the the user exists!
@@ -736,7 +736,7 @@ char *wxGetUserHome( const wxString &user )
       who = getpwnam (user.mb_str());
     }
 
-    return wxConvertMB2WX(who ? who->pw_dir : 0);
+    return wxSafeConvertMB2WX(who ? who->pw_dir : 0);
 }
 
 // ----------------------------------------------------------------------------
@@ -787,7 +787,7 @@ static bool wxGetHostNameInternal(wxChar *buf, int sz)
     bool ok = uname(&uts) != -1;
     if ( ok )
     {
-        wxStrncpy(buf, wxConvertMB2WX(uts.nodename), sz - 1);
+        wxStrncpy(buf, wxSafeConvertMB2WX(uts.nodename), sz - 1);
         buf[sz] = wxT('\0');
     }
 #elif defined(HAVE_GETHOSTNAME)
@@ -795,7 +795,7 @@ static bool wxGetHostNameInternal(wxChar *buf, int sz)
     bool ok = gethostname(cbuf, sz) != -1;
     if ( ok )
     {
-        wxStrncpy(buf, wxConvertMB2WX(cbuf), sz - 1);
+        wxStrncpy(buf, wxSafeConvertMB2WX(cbuf), sz - 1);
         buf[sz] = wxT('\0');
     }
 #else // no uname, no gethostname
@@ -839,7 +839,7 @@ bool wxGetFullHostName(wxChar *buf, int sz)
     {
         if ( !wxStrchr(buf, wxT('.')) )
         {
-            struct hostent *host = gethostbyname(wxConvertWX2MB(buf));
+            struct hostent *host = gethostbyname(wxSafeConvertWX2MB(buf));
             if ( !host )
             {
                 wxLogSysError(_("Cannot get the official hostname"));
@@ -849,7 +849,7 @@ bool wxGetFullHostName(wxChar *buf, int sz)
             else
             {
                 // the canonical name
-                wxStrncpy(buf, wxConvertMB2WX(host->h_name), sz);
+                wxStrncpy(buf, wxSafeConvertMB2WX(host->h_name), sz);
             }
         }
         //else: it's already a FQDN (BSD behaves this way)
@@ -865,7 +865,7 @@ bool wxGetUserId(wxChar *buf, int sz)
     *buf = wxT('\0');
     if ((who = getpwuid(getuid ())) != NULL)
     {
-        wxStrncpy (buf, wxConvertMB2WX(who->pw_name), sz - 1);
+        wxStrncpy (buf, wxSafeConvertMB2WX(who->pw_name), sz - 1);
         return true;
     }
 
@@ -874,24 +874,23 @@ bool wxGetUserId(wxChar *buf, int sz)
 
 bool wxGetUserName(wxChar *buf, int sz)
 {
+#ifdef HAVE_PW_GECOS
     struct passwd *who;
 
     *buf = wxT('\0');
     if ((who = getpwuid (getuid ())) != NULL)
     {
-        // pw_gecos field in struct passwd is not standard
-#ifdef HAVE_PW_GECOS
        char *comma = strchr(who->pw_gecos, ',');
        if (comma)
            *comma = '\0'; // cut off non-name comment fields
-       wxStrncpy (buf, wxConvertMB2WX(who->pw_gecos), sz - 1);
-#else // !HAVE_PW_GECOS
-       wxStrncpy (buf, wxConvertMB2WX(who->pw_name), sz - 1);
-#endif // HAVE_PW_GECOS/!HAVE_PW_GECOS
+       wxStrncpy (buf, wxSafeConvertMB2WX(who->pw_gecos), sz - 1);
        return true;
     }
 
     return false;
+#else // !HAVE_PW_GECOS
+    return wxGetUserId(buf, sz);
+#endif // HAVE_PW_GECOS/!HAVE_PW_GECOS
 }
 
 bool wxIsPlatform64Bit()