Update Changes.
[p5sagit/p5-mst-13.2.git] / doop.c
diff --git a/doop.c b/doop.c
index 0139911..77c7324 100644 (file)
--- a/doop.c
+++ b/doop.c
 
 #define HALF_UTF8_UPGRADE(start,end) \
     STMT_START {                               \
+      if ((start)<(end)) {                     \
        U8* NeWsTr;                             \
        STRLEN LeN = (end) - (start);           \
        NeWsTr = bytes_to_utf8(start, &LeN);    \
        Safefree(start);                        \
        (start) = NeWsTr;                       \
        (end) = (start) + LeN;                  \
+      }                                                \
     } STMT_END
 
 STATIC I32
@@ -91,8 +93,8 @@ S_do_trans_simple(pTHX_ SV *sv)
     }
     *d = '\0';
     sv_setpvn(sv, (const char*)dstart, d - dstart);
+    Safefree(dstart);
     SvUTF8_on(sv);
-    SvLEN_set(sv, 2*len+1);
     SvSETMAGIC(sv);
     return matches;
 }
@@ -485,7 +487,7 @@ Perl_do_join(pTHX_ register SV *sv, SV *del, register SV **mark, register SV **s
     (void)SvUPGRADE(sv, SVt_PV);
     if (SvLEN(sv) < len + items) {     /* current length is way too short */
        while (items-- > 0) {
-           if (*mark && !SvGMAGICAL(*mark) && SvOK(*mark)) {
+           if (*mark && !SvGAMAGIC(*mark) && SvOK(*mark)) {
                SvPV(*mark, tmplen);
                len += tmplen;
            }
@@ -535,7 +537,7 @@ Perl_do_sprintf(pTHX_ SV *sv, I32 len, SV **sarg)
        SvTAINTED_on(sv);
 }
 
-/* XXX SvUTF8 support missing! */
+/* currently converts input to bytes if possible, but doesn't sweat failure */
 UV
 Perl_do_vecget(pTHX_ SV *sv, I32 offset, I32 size)
 {
@@ -547,6 +549,11 @@ Perl_do_vecget(pTHX_ SV *sv, I32 offset, I32 size)
        return retnum;
     if (size < 1 || (size & (size-1))) /* size < 1 or not a power of two */ 
        Perl_croak(aTHX_ "Illegal number of bits in vec");
+
+    if (SvUTF8(sv)) {
+       (void) Perl_sv_utf8_downgrade(aTHX_ sv, TRUE);
+    }
+
     offset *= size;    /* turn into bit offset */
     len = (offset + size + 7) / 8;     /* required number of bytes */
     if (len > srclen) {
@@ -668,7 +675,10 @@ Perl_do_vecget(pTHX_ SV *sv, I32 offset, I32 size)
     return retnum;
 }
 
-/* XXX SvUTF8 support missing! */
+/* currently converts input to bytes if possible but doesn't sweat failures,
+ * although it does ensure that the string it clobbers is not marked as
+ * utf8-valid any more
+ */
 void
 Perl_do_vecset(pTHX_ SV *sv)
 {
@@ -684,9 +694,19 @@ Perl_do_vecset(pTHX_ SV *sv)
     if (!targ)
        return;
     s = (unsigned char*)SvPV_force(targ, targlen);
+    if (SvUTF8(targ)) {
+       /* This is handled by the SvPOK_only below...
+       if (!Perl_sv_utf8_downgrade(aTHX_ targ, TRUE))
+           SvUTF8_off(targ);
+        */
+       (void) Perl_sv_utf8_downgrade(aTHX_ targ, TRUE);
+    }
+
     (void)SvPOK_only(targ);
     lval = SvUV(sv);
     offset = LvTARGOFF(sv);
+    if (offset < 0)
+       Perl_croak(aTHX_ "Assigning to negative offset in vec");
     size = LvTARGLEN(sv);
     if (size < 1 || (size & (size-1))) /* size < 1 or not a power of two */ 
        Perl_croak(aTHX_ "Illegal number of bits in vec");