Revision: 14358
          http://edk2.svn.sourceforge.net/edk2/?rev=14358&view=rev
Author:   darylm503
Date:     2013-05-15 01:59:11 +0000 (Wed, 15 May 2013)
Log Message:
-----------
StdLib/LibC/Locale/multibyte_Utf8.c: Fix obscure corner cases in wide to 
multibyte and multibyte to wide character conversions.  The majority of 
problems center around the interpretation of the Length or Limit parameter when 
the Destination parameter is NULL.

DecodeOneStateful: Properly handle combinations of Src, Dest, or Len being NULL 
or 0.

EncodeUtf8: Do not zero-terminate the result string in this worker function.

mbsrtowcs: Remove test for **src == '\0', as per ISO/IEC 9899:199409.  Allows 
"".

wcsrtombs:  The C Language standard, ISO/IEC 9899:199409, states that the 
wcsrtombs() function will stop before encountering the terminating NUL 
character only if Dest is NOT NULL.  This implies that if Dest is NULL, the 
Limit parameter will be ignored.  In order to avoid system hangs, if Dest is 
NULL a Limit value of ASCII_STRING_MAX is automatically used.  Also fixed a 
typo in the function header comment.

With these changes, StdLib now passes all of the C Language Standards 
Compliance Tests for ISO/IEC 9899:199409 (C95).

Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by:  [email protected]
Reviewed-by:    [email protected]

Modified Paths:
--------------
    trunk/edk2/StdLib/LibC/Locale/multibyte_Utf8.c

Modified: trunk/edk2/StdLib/LibC/Locale/multibyte_Utf8.c
===================================================================
--- trunk/edk2/StdLib/LibC/Locale/multibyte_Utf8.c      2013-05-14 23:50:33 UTC 
(rev 14357)
+++ trunk/edk2/StdLib/LibC/Locale/multibyte_Utf8.c      2013-05-15 01:59:11 UTC 
(rev 14358)
@@ -197,19 +197,24 @@
   int           NumConv;
   unsigned char ch;
 
-  if((Src == NULL) || (*Src == '\0')) {
-    return 0;
-  }
   if(pS == NULL) {
     pS = &LocalConvState;
   }
-  SrcEnd  = Src + Len;
   NumConv = 0;
-  while(Src < SrcEnd) {
-    ch = (unsigned char)*Src++;
-    NumConv = ProcessOneByte(ch, pS);
-    if(NumConv != -2)
-      break;
+  if(Src != NULL) {
+    if(*Src != 0) {
+      SrcEnd  = Src + Len;
+      while(Src < SrcEnd) {
+        ch = (unsigned char)*Src++;
+        NumConv = ProcessOneByte(ch, pS);
+        if(NumConv != -2) {
+          break;
+        }
+      }
+    }
+    else if(Dest != NULL) {
+      *Dest = 0;
+    }
   }
   if((NumConv > 0) && (Dest != NULL)) {
     Dest[0] = pS->D[0];
@@ -416,14 +421,6 @@
   */
   if(Dest != NULL) {        // Save character if Dest is not NULL
     memcpy(Dest, Buff, NumInBuff);
-
-    if(ch != 0) {
-      // Terminate the destination string.
-      Dest[NumInBuff] = '\0';
-    }
-    else {
-      NumInBuff = 0;
-    }
   }
   return NumInBuff;             // Tell the caller
 }
@@ -646,7 +643,7 @@
   size_t        RetVal = 0;
   const char   *MySrc;
 
-  if((src == NULL) || (*src == NULL) || (**src == '\0')) {
+  if((src == NULL) || (*src == NULL)) {
     return 0;
   }
 
@@ -855,7 +852,7 @@
 }
 
 /** The wcsrtombs function converts a sequence of wide characters from the 
array
-    indirectly pointed to by Dest into a sequence of corresponding multibyte
+    indirectly pointed to by Src into a sequence of corresponding multibyte
     characters that begins in the conversion state described by the object
     pointed to by ps.
 
@@ -914,15 +911,16 @@
     return (0);
 
   if (Dest == NULL) {
-    if(MaxBytes <= 0) {
-      MaxBytes = ASCII_STRING_MAX;
-    }
-    NumStored = EstimateWtoM(*Src, MaxBytes, NULL);
+    NumStored = EstimateWtoM(*Src, ASCII_STRING_MAX, NULL);
   }
   else {
-    while (OneWcToMcLen(InCh = *(*Src)++) <= MaxBytes) {
+    if((MaxBytes < 0) || (MaxBytes > ASCII_STRING_MAX)) {
+      MaxBytes = ASCII_STRING_MAX;
+    }
+    while ((MaxBytes > 0) && (OneWcToMcLen(InCh = *(*Src)++) <= MaxBytes)) {
       if(InCh == 0) {
         *Src = NULL;
+        *Dest = 0;      // NUL terminate Dest string, but don't count the NUL
         break;
       }
       count = (int)wcrtomb(Dest, InCh, NULL);

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.


------------------------------------------------------------------------------
AlienVault Unified Security Management (USM) platform delivers complete
security visibility with the essential security capabilities. Easily and
efficiently configure, manage, and operate all of your security controls
from a single console and one unified framework. Download a free trial.
http://p.sf.net/sfu/alienvault_d2d
_______________________________________________
edk2-commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/edk2-commits

Reply via email to