Module Name:    src
Committed By:   riastradh
Date:           Mon Aug 27 14:52:16 UTC 2018

Modified Files:
        src/sys/external/bsd/drm2/include/linux: bitmap.h

Log Message:
Split bitmap_set/clear into begin/middle/end sections.

For clarity and speed.  Largely from uwe@ with tweaks from me.


To generate a diff of this commit:
cvs rdiff -u -r1.7 -r1.8 src/sys/external/bsd/drm2/include/linux/bitmap.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/external/bsd/drm2/include/linux/bitmap.h
diff -u src/sys/external/bsd/drm2/include/linux/bitmap.h:1.7 src/sys/external/bsd/drm2/include/linux/bitmap.h:1.8
--- src/sys/external/bsd/drm2/include/linux/bitmap.h:1.7	Mon Aug 27 14:51:05 2018
+++ src/sys/external/bsd/drm2/include/linux/bitmap.h	Mon Aug 27 14:52:16 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: bitmap.h,v 1.7 2018/08/27 14:51:05 riastradh Exp $	*/
+/*	$NetBSD: bitmap.h,v 1.8 2018/08/27 14:52:16 riastradh Exp $	*/
 
 /*-
  * Copyright (c) 2018 The NetBSD Foundation, Inc.
@@ -105,16 +105,28 @@ bitmap_set(unsigned long *bitmap, size_t
 {
 	const size_t bpl = NBBY * sizeof(*bitmap);
 	unsigned long *p = bitmap + startbit/bpl;
-	unsigned long mask;
-	unsigned sz;
+	unsigned initial = startbit%bpl;
 
-	for (sz = bpl - (startbit%bpl), mask = ~0UL << (startbit%bpl);
-	     nbits >= sz;
-	     nbits -= sz, sz = bpl, mask = ~0UL)
-		*p++ |= mask;
+	/* Handle an initial odd word if any.  */
+	if (initial) {
+		/* Does the whole thing fit in a single word?  */
+		if (nbits <= bpl - initial) {
+			/* Yes: just set nbits starting at initial.  */
+			*p |= ~(~0ULL << nbits) << initial;
+			return;
+		}
+		/* Nope: set all bits above initial, and advance.  */
+		*p++ |= ~0ULL << initial;
+		nbits -= bpl - initial;
+	}
+
+	/* Set the middle part to all bits 1.  */
+	for (; nbits >= bpl; nbits -= bpl)
+		*p++ = ~0UL;
 
+	/* Handle a final odd word if any by setting its low nbits.  */
 	if (nbits)
-		*p |= mask & ~(~0UL << (nbits + bpl - sz));
+		*p |= ~(~0ULL << nbits);
 }
 
 /*
@@ -128,16 +140,28 @@ bitmap_clear(unsigned long *bitmap, size
 {
 	const size_t bpl = NBBY * sizeof(*bitmap);
 	unsigned long *p = bitmap + startbit/bpl;
-	unsigned long mask;
-	unsigned sz;
+	unsigned initial = startbit%bpl;
 
-	for (sz = bpl - (startbit%bpl), mask = ~(~0UL << (startbit%bpl));
-	     nbits >= sz;
-	     nbits -= sz, sz = bpl, mask = 0UL)
-		*p++ &= mask;
+	/* Handle an initial odd word if any.  */
+	if (initial) {
+		/* Does the whole thing fit in a single word?  */
+		if (nbits <= bpl - initial) {
+			/* Yes: just clear nbits starting at initial.  */
+			*p &= ~(~(~0ULL << nbits) << initial);
+			return;
+		}
+		/* Nope: clear all bits above initial, and advance.  */
+		*p++ &= ~(~0ULL << initial);
+		nbits -= bpl - initial;
+	}
+
+	/* Zero the middle part.  */
+	for (; nbits >= bpl; nbits -= bpl)
+		*p++ = 0UL;
 
+	/* Handle a final odd word if any by clearing its low nbits.  */
 	if (nbits)
-		*p &= mask | (~0UL << (nbits + bpl - sz));
+		*p &= ~0ULL << nbits;
 }
 
 /*

Reply via email to