1 
/* * Mode: C++; tabwidth: 4; indenttabsmode: nil; cbasicoffset: 4 * */ 
2 
/* ***** BEGIN LICENSE BLOCK ***** 
3 
* Version: MPL 1.1/GPL 2.0/LGPL 2.1 
4 
* 
5 
* The contents of this file are subject to the Mozilla Public License Version 
6 
* 1.1 (the "License"); you may not use this file except in compliance with 
7 
* the License. You may obtain a copy of the License at 
8 
* http://www.mozilla.org/MPL/ 
9 
* 
10 
* Software distributed under the License is distributed on an "AS IS" basis, 
11 
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License 
12 
* for the specific language governing rights and limitations under the 
13 
* License. 
14 
* 
15 
* The Original Code is Mozilla Communicator client code, released 
16 
* March 31, 1998. 
17 
* 
18 
* The Initial Developer of the Original Code is 
19 
* Netscape Communications Corporation. 
20 
* Portions created by the Initial Developer are Copyright (C) 1998 
21 
* the Initial Developer. All Rights Reserved. 
22 
* 
23 
* Contributor(s): 
24 
* 
25 
* Alternatively, the contents of this file may be used under the terms of 
26 
* either of the GNU General Public License Version 2 or later (the "GPL"), 
27 
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), 
28 
* in which case the provisions of the GPL or the LGPL are applicable instead 
29 
* of those above. If you wish to allow use of your version of this file only 
30 
* under the terms of either the GPL or the LGPL, and not to allow others to 
31 
* use your version of this file under the terms of the MPL, indicate your 
32 
* decision by deleting the provisions above and replace them with the notice 
33 
* and other provisions required by the GPL or the LGPL. If you do not delete 
34 
* the provisions above, a recipient may use your version of this file under 
35 
* the terms of any one of the MPL, the GPL or the LGPL. 
36 
* 
37 
* ***** END LICENSE BLOCK ***** */ 
38 

39 
#include "jsstdint.h" 
40 
#include "jsbit.h" 
41 
#include "jsutil.h" 
42 

43 
/* 
44 
* Check that we can use js_bitscan_clz32 to implement JS_FLOOR_LOG2 and 
45 
* JS_FLOOR_LOG2W and js_bitscan_clz64 to implement JS_FLOOR_LOG2W on 64bit 
46 
* systems. 
47 
*/ 
48 
#ifdef JS_HAS_BUILTIN_BITSCAN32 
49 
JS_STATIC_ASSERT(sizeof(unsigned int) == sizeof(JSUint32)); 
50 
JS_STATIC_ASSERT_IF(JS_BYTES_PER_WORD == 4, 
51 
sizeof(unsigned int) == sizeof(JSUword)); 
52 
#endif 
53 
#ifdef JS_HAS_BUILTIN_BITSCAN64 
54 
JS_STATIC_ASSERT_IF(JS_BYTES_PER_WORD == 8, 
55 
sizeof(unsigned long long) == sizeof(JSUword)); 
56 
#endif 
57 

58 
/* 
59 
* Compute the log of the least power of 2 greater than or equal to n 
60 
*/ 
61 
JS_PUBLIC_API(JSIntn) 
62 
JS_CeilingLog2(JSUint32 n) 
63 
{ 
64 
JSIntn log2; 
65 

66 
JS_CEILING_LOG2(log2, n); 
67 
return log2; 
68 
} 
69 

70 
/* 
71 
* Compute the log of the greatest power of 2 less than or equal to n. 
72 
* This really just finds the highest set bit in the word. 
73 
*/ 
74 
JS_PUBLIC_API(JSIntn) 
75 
JS_FloorLog2(JSUint32 n) 
76 
{ 
77 
JSIntn log2; 
78 

79 
JS_FLOOR_LOG2(log2, n); 
80 
return log2; 
81 
} 
82 

83 
/* 
84 
* js_FloorLog2wImpl has to be defined only for 64bit nonGCC case. 
85 
*/ 
86 
#if !defined(JS_HAS_BUILTIN_BITSCAN64) && JS_BYTES_PER_WORD == 8 
87 

88 
JSUword 
89 
js_FloorLog2wImpl(JSUword n) 
90 
{ 
91 
JSUword log2, m; 
92 

93 
JS_ASSERT(n != 0); 
94 

95 
log2 = 0; 
96 
m = n >> 32; 
97 
if (m != 0) { n = m; log2 = 32; } 
98 
m = n >> 16; 
99 
if (m != 0) { n = m; log2 = 16; } 
100 
m = n >> 8; 
101 
if (m != 0) { n = m; log2 = 8; } 
102 
m = n >> 4; 
103 
if (m != 0) { n = m; log2 = 4; } 
104 
m = n >> 2; 
105 
if (m != 0) { n = m; log2 = 2; } 
106 
log2 = (n >> 1); 
107 

108 
return log2; 
109 
} 
110 

111 
#endif 