#FEATURE
authorClaus Gittinger <cg@exept.de>
Wed, 18 Nov 2015 12:11:39 +0100
changeset 18909 b77b871e2795
parent 18908 0150d9a27bc0
child 18910 815f8cba1f42
#FEATURE class: String changed: #indexOf:startingAt: extra tuning for 64bit CPUs
String.st
--- a/String.st	Wed Nov 18 11:38:08 2015 +0100
+++ b/String.st	Wed Nov 18 12:11:39 2015 +0100
@@ -927,10 +927,10 @@
 #ifdef __SCHTEAM__
     if (start.isSmallInteger()
      && aCharacter.isSTCharacter()) {
-	int idx1Based = start.intValue();   // st index is 1 based
-	int jIdx = self.asString().indexOf(aCharacter.charValue(), idx1Based-1);
-
-	return context._RETURN( jIdx+1 );    // st index is 1 based
+        int idx1Based = start.intValue();   // st index is 1 based
+        int jIdx = self.asString().indexOf(aCharacter.charValue(), idx1Based-1);
+
+        return context._RETURN( jIdx+1 );    // st index is 1 based
     }
 
 #else
@@ -948,77 +948,92 @@
     OBJ cls;
 
     if (__isSmallInteger(start)) {
-	index = __intVal(start);
-	if (index > 0) {
-	    if (__isCharacter(aCharacter)) {
-		byteValue = __intVal(__characterVal(aCharacter));
-		if (byteValue <= 0xFF) {
-		    last = __stringSize(self);
-		    cp = __stringVal(self);
-		    if ((cls = __qClass(self)) != String) {
-			int numInstBytes = __OBJS2BYTES__(__intVal(__ClassInstPtr(cls)->c_ninstvars));
-
-			cp += numInstBytes;
-			last -= numInstBytes;
-		    }
-		    if (index <= last) {
+        index = __intVal(start);
+        if (index > 0) {
+            if (__isCharacter(aCharacter)) {
+                byteValue = __intVal(__characterVal(aCharacter));
+                if (byteValue <= 0xFF) {
+                    last = __stringSize(self);
+                    cp = __stringVal(self);
+                    if ((cls = __qClass(self)) != String) {
+                        int numInstBytes = __OBJS2BYTES__(__intVal(__ClassInstPtr(cls)->c_ninstvars));
+
+                        cp += numInstBytes;
+                        last -= numInstBytes;
+                    }
+                    if (index <= last) {
 # ifdef FAST_MEMCHR
-			ncp = (unsigned char *) memchr(cp+index-1, byteValue, last+1-index);
-			if (ncp) {
-			    RETURN ( __mkSmallInteger(ncp - cp + 1) );
-			}
+                        ncp = (unsigned char *) memchr(cp+index-1, byteValue, last+1-index);
+                        if (ncp) {
+                            RETURN ( __mkSmallInteger(ncp - cp + 1) );
+                        }
 # else
 #  ifdef __UNROLL_LOOPS__
-			{
-			    int last3 = last-3;
-
-			    for (; index <= last3; index += 4) {
-				if (cp[index-1] == byteValue) { RETURN ( __mkSmallInteger(index) ); }
-				if (cp[index-1+1] == byteValue) { RETURN ( __mkSmallInteger(index+1) ); }
-				if (cp[index-1+2] == byteValue) { RETURN ( __mkSmallInteger(index+2) ); }
-				if (cp[index-1+3] == byteValue) { RETURN ( __mkSmallInteger(index+3) ); }
-			    }
-			}
+                        {
+                            int last3 = last-3;
+
+                            for (; index <= last3; index += 4) {
+                                if (cp[index-1] == byteValue) { RETURN ( __mkSmallInteger(index) ); }
+                                if (cp[index-1+1] == byteValue) { RETURN ( __mkSmallInteger(index+1) ); }
+                                if (cp[index-1+2] == byteValue) { RETURN ( __mkSmallInteger(index+2) ); }
+                                if (cp[index-1+3] == byteValue) { RETURN ( __mkSmallInteger(index+3) ); }
+                            }
+                        }
 #  endif
 #  ifdef V1
-			for (; index <= last; index++) {
-			    if (cp[index-1] == byteValue) {
-				RETURN ( __mkSmallInteger(index) );
-			    }
-			}
+                        for (; index <= last; index++) {
+                            if (cp[index-1] == byteValue) {
+                                RETURN ( __mkSmallInteger(index) );
+                            }
+                        }
 #  endif
 #  ifdef V2
-			{
-			    // see bit twiddling hacks
+                        {
+                            // see bit twiddling hacks
 #                           define hasZeroByte(v) (((v) - 0x01010101UL) & ~(v) & 0x80808080UL)
 #                           define hasByteM(v,m)   hasZeroByte( (v) ^ m)
-
-			    // the following loop checks four bytes at once
-			    if (((index-1) & 0x3) == 0) {
-				int last4 = last-4;
-				int m = (~0UL/255 * (byteValue));
-
-				while (index <= last4) {
-				    unsigned int v = *(unsigned int *)(cp+index-1);
-
-				    if (hasByteM(v,m)) break;
-				    index += 4;
-				}
-			    }
-			    while (index <= last) {
-				if (cp[index-1] == byteValue) {
-				    RETURN ( __mkSmallInteger(index) );
-				}
-				index++;
-			    }
-			}
+#   if __POINTER_SIZE__ == 8
+#                           define hasZeroByte8(v) (((v) - 0x0101010101010101ULL) & ~(v) & 0x8080808080808080ULL)
+#                           define hasByteM8(v,m)   hasZeroByte8( (v) ^ m)
+                            // the following loop checks eight bytes at once
+                            if (((index-1) & 0x7) == 0) {
+                                int last8 = last-8;
+                                INT m = (~0UL/255 * (byteValue));
+
+                                while (index <= last8) {
+                                    unsigned INT v = *(unsigned INT *)(cp+index-1);
+
+                                    if (hasByteM8(v,m)) break;
+                                    index += 8;
+                                }
+                            }
+#   endif
+                            // the following loop checks four bytes at once
+                            if (((index-1) & 0x3) == 0) {
+                                int last4 = last-4;
+                                int m = (~0UL/255 * (byteValue));
+
+                                while (index <= last4) {
+                                    unsigned int v = *(unsigned int *)(cp+index-1);
+
+                                    if (hasByteM(v,m)) break;
+                                    index += 4;
+                                }
+                            }
+                            while (index <= last) {
+                                if (cp[index-1] == byteValue) {
+                                    RETURN ( __mkSmallInteger(index) );
+                                }
+                                index++;
+                            }
+                        }
 #  endif
 # endif
-		    }
-		}
-	    }
-	    RETURN ( __mkSmallInteger(0) );
-	}
+                    }
+                }
+            }
+            RETURN ( __mkSmallInteger(0) );
+        }
     }
 # undef V2
 #endif /* not SCHTEAM */
@@ -1121,14 +1136,14 @@
      s atAllPut:$a.
      s at:512 put:(Character space).
      Time millisecondsToRun:[
-	1000000 timesRepeat:[ s indexOf:(Character space) ]
+        1000000 timesRepeat:[ s indexOf:(Character space) ]
      ]
 
      timing (ms):
-	v1: 1763 normal
-	    2340 +unroll
-	    3308 memsrch !!
-	v2: 1045
+        v1: 1763 normal
+            2340 +unroll
+            3308 memsrch !!
+        v2: 1045
     "
 
     "Modified: / 10-01-2012 / 17:09:34 / cg"