int BN_num_bits_word(unsigned long long l) {
  static const char bits[256] = {
      0, 1, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5,
      5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
      6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7, 7, 7,
      7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
      7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
      7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
      8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
      8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
      8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
      8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
      8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
  };
  if (l & 0xffffffff00000000LL) {
    if (l & 0xffff000000000000LL) {
      if (l & 0xff00000000000000LL) {
        return (bits[(int)(l >> 56)] + 56);
      } else
        return (bits[(int)(l >> 48)] + 48);
    } else {
      if (l & 0x0000ff0000000000LL) {
        return (bits[(int)(l >> 40)] + 40);
      } else
        return (bits[(int)(l >> 32)] + 32);
    }
  } else {
    if (l & 0xffff0000L) {
      if (l & 0xff000000L)
        return (bits[(int)(l >> 24L)] + 24);
      else
        return (bits[(int)(l >> 16L)] + 16);
    } else {
      if (l & 0xff00L)
        return (bits[(int)(l >> 8)] + 8);
      else
        return (bits[(int)(l)]);
    }
  }
}


x86 assembly (clang, -O0):
<BN_num_bits_word>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x10(%rbp)
movabs $0xffffffff00000000,%rax
ff ff ff
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     11ec <BN_num_bits_word+0xec>
movabs $0xffff000000000000,%rax
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     1192 <BN_num_bits_word+0x92>
movabs $0xff00000000000000,%rax
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     1171 <BN_num_bits_word+0x71>
mov    -0x10(%rbp),%rax
shr    $0x38,%rax
movslq %eax,%rcx
lea    0xe9e(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x38,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
mov    -0x10(%rbp),%rax
shr    $0x30,%rax
movslq %eax,%rcx
lea    0xe7d(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x30,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
movabs $0xff0000000000,%rax
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     11cb <BN_num_bits_word+0xcb>
mov    -0x10(%rbp),%rax
shr    $0x28,%rax
movslq %eax,%rcx
lea    0xe44(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x28,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
mov    -0x10(%rbp),%rax
shr    $0x20,%rax
movslq %eax,%rcx
lea    0xe23(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x20,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
movabs $0xffff0000,%rax
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     125e <BN_num_bits_word+0x15e>
movabs $0xff000000,%rax
and    -0x10(%rbp),%rax
cmp    $0x0,%rax
je     123d <BN_num_bits_word+0x13d>
mov    -0x10(%rbp),%rax
shr    $0x18,%rax
movslq %eax,%rcx
lea    0xdd2(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x18,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
mov    -0x10(%rbp),%rax
shr    $0x10,%rax
movslq %eax,%rcx
lea    0xdb1(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x10,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
mov    -0x10(%rbp),%rax
and    $0xff00,%rax
cmp    $0x0,%rax
je     1293 <BN_num_bits_word+0x193>
mov    -0x10(%rbp),%rax
shr    $0x8,%rax
movslq %eax,%rcx
lea    0xd7c(%rip),%rax
movsbl (%rax,%rcx,1),%eax
add    $0x8,%eax
mov    %eax,-0x4(%rbp)
jmp    12a8 <BN_num_bits_word+0x1a8>
mov    -0x10(%rbp),%rax
movslq %eax,%rcx
lea    0xd5f(%rip),%rax
movsbl (%rax,%rcx,1),%eax
mov    %eax,-0x4(%rbp)
mov    -0x4(%rbp),%eax
pop    %rbp
ret

x86 assembly (clang, -O2):
<BN_num_bits_word>:
mov    %rdi,%rax
shr    $0x20,%rax
jne    112c <BN_num_bits_word+0x2c>
test   $0xffff0000,%edi
je     116c <BN_num_bits_word+0x6c>
test   $0xff000000,%edi
je     118f <BN_num_bits_word+0x8f>
shr    $0x18,%rdi
lea    0xedc(%rip),%rax
movsbl (%rdi,%rax,1),%eax
add    $0x18,%eax
ret
mov    %rdi,%rcx
shr    $0x30,%rcx
jne    1157 <BN_num_bits_word+0x57>
movabs $0xff0000000000,%rcx
test   %rcx,%rdi
je     11a2 <BN_num_bits_word+0xa2>
shr    $0x28,%rdi
lea    0xeb1(%rip),%rax
movsbl (%rdi,%rax,1),%eax
add    $0x28,%eax
ret
lea    0xea2(%rip),%rax
shr    $0x38,%rdi
jne    1187 <BN_num_bits_word+0x87>
movsbl (%rcx,%rax,1),%eax
add    $0x30,%eax
ret
test   $0xff00,%edi
je     11b1 <BN_num_bits_word+0xb1>
shr    $0x8,%rdi
lea    0xe81(%rip),%rax
movsbl (%rdi,%rax,1),%eax
add    $0x8,%eax
ret
movsbl (%rdi,%rax,1),%eax
add    $0x38,%eax
ret
shr    $0x10,%rdi
lea    0xe66(%rip),%rax
movsbl (%rdi,%rax,1),%eax
add    $0x10,%eax
ret
lea    0xe57(%rip),%rcx
movsbl (%rax,%rcx,1),%eax
add    $0x20,%eax
ret
movslq %edi,%rax
lea    0xe45(%rip),%rcx
movsbl (%rax,%rcx,1),%eax
ret

LLVM IR (-O0):
@BN_num_bits_word.bits = internal constant [256 x i8] c"\00\01\02\02\03\03\03\03\04\04\04\04\04\04\04\04\05\05\05\05\05\05\05\05\05\05\05\05\05\05\05\05\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08"
define i32 @BN_num_bits_word(i64 %0) {
%2 = alloca i32
%3 = alloca i64
store i64 %0, i64* %3
%4 = load i64, i64* %3
%5 = and i64 %4, -4294967296
%6 = icmp ne i64 %5, 0
br i1 %6, label %7, label %55
7: ; preds = %1
%8 = load i64, i64* %3
%9 = and i64 %8, -281474976710656
%10 = icmp ne i64 %9, 0
br i1 %10, label %11, label %33
11: ; preds = %7
%12 = load i64, i64* %3
%13 = and i64 %12, -72057594037927936
%14 = icmp ne i64 %13, 0
br i1 %14, label %15, label %24
15: ; preds = %11
%16 = load i64, i64* %3
%17 = lshr i64 %16, 56
%18 = trunc i64 %17 to i32
%19 = sext i32 %18 to i64
%20 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %19
%21 = load i8, i8* %20
%22 = sext i8 %21 to i32
%23 = add nsw i32 %22, 56
store i32 %23, i32* %2
br label %101
24: ; preds = %11
%25 = load i64, i64* %3
%26 = lshr i64 %25, 48
%27 = trunc i64 %26 to i32
%28 = sext i32 %27 to i64
%29 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %28
%30 = load i8, i8* %29
%31 = sext i8 %30 to i32
%32 = add nsw i32 %31, 48
store i32 %32, i32* %2
br label %101
33: ; preds = %7
%34 = load i64, i64* %3
%35 = and i64 %34, 280375465082880
%36 = icmp ne i64 %35, 0
br i1 %36, label %37, label %46
37: ; preds = %33
%38 = load i64, i64* %3
%39 = lshr i64 %38, 40
%40 = trunc i64 %39 to i32
%41 = sext i32 %40 to i64
%42 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %41
%43 = load i8, i8* %42
%44 = sext i8 %43 to i32
%45 = add nsw i32 %44, 40
store i32 %45, i32* %2
br label %101
46: ; preds = %33
%47 = load i64, i64* %3
%48 = lshr i64 %47, 32
%49 = trunc i64 %48 to i32
%50 = sext i32 %49 to i64
%51 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %50
%52 = load i8, i8* %51
%53 = sext i8 %52 to i32
%54 = add nsw i32 %53, 32
store i32 %54, i32* %2
br label %101
55: ; preds = %1
%56 = load i64, i64* %3
%57 = and i64 %56, 4294901760
%58 = icmp ne i64 %57, 0
br i1 %58, label %59, label %81
59: ; preds = %55
%60 = load i64, i64* %3
%61 = and i64 %60, 4278190080
%62 = icmp ne i64 %61, 0
br i1 %62, label %63, label %72
63: ; preds = %59
%64 = load i64, i64* %3
%65 = lshr i64 %64, 24
%66 = trunc i64 %65 to i32
%67 = sext i32 %66 to i64
%68 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %67
%69 = load i8, i8* %68
%70 = sext i8 %69 to i32
%71 = add nsw i32 %70, 24
store i32 %71, i32* %2
br label %101
72: ; preds = %59
%73 = load i64, i64* %3
%74 = lshr i64 %73, 16
%75 = trunc i64 %74 to i32
%76 = sext i32 %75 to i64
%77 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %76
%78 = load i8, i8* %77
%79 = sext i8 %78 to i32
%80 = add nsw i32 %79, 16
store i32 %80, i32* %2
br label %101
81: ; preds = %55
%82 = load i64, i64* %3
%83 = and i64 %82, 65280
%84 = icmp ne i64 %83, 0
br i1 %84, label %85, label %94
85: ; preds = %81
%86 = load i64, i64* %3
%87 = lshr i64 %86, 8
%88 = trunc i64 %87 to i32
%89 = sext i32 %88 to i64
%90 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %89
%91 = load i8, i8* %90
%92 = sext i8 %91 to i32
%93 = add nsw i32 %92, 8
store i32 %93, i32* %2
br label %101
94: ; preds = %81
%95 = load i64, i64* %3
%96 = trunc i64 %95 to i32
%97 = sext i32 %96 to i64
%98 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %97
%99 = load i8, i8* %98
%100 = sext i8 %99 to i32
store i32 %100, i32* %2
br label %101
101: ; preds = %94, %85, %72, %63, %46, %37, %24, %15
%102 = load i32, i32* %2
ret i32 %102
}

LLVM IR (-O2):
@BN_num_bits_word.bits = internal unnamed_addr constant [256 x i8] c"\00\01\02\02\03\03\03\03\04\04\04\04\04\04\04\04\05\05\05\05\05\05\05\05\05\05\05\05\05\05\05\05\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\06\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\07\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08\08"
define i32 @BN_num_bits_word(i64 %0) {
%2 = icmp ult i64 %0, 4294967296
br i1 %2, label %34, label %3
3: ; preds = %1
%4 = icmp ult i64 %0, 281474976710656
br i1 %4, label %19, label %5
5: ; preds = %3
%6 = icmp ult i64 %0, 72057594037927936
br i1 %6, label %13, label %7
7: ; preds = %5
%8 = lshr i64 %0, 56
%9 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %8
%10 = load i8, i8* %9
%11 = sext i8 %10 to i32
%12 = add nsw i32 %11, 56
br label %67
13: ; preds = %5
%14 = lshr i64 %0, 48
%15 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %14
%16 = load i8, i8* %15
%17 = sext i8 %16 to i32
%18 = add nsw i32 %17, 48
br label %67
19: ; preds = %3
%20 = and i64 %0, 280375465082880
%21 = icmp eq i64 %20, 0
br i1 %21, label %28, label %22
22: ; preds = %19
%23 = lshr i64 %0, 40
%24 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %23
%25 = load i8, i8* %24
%26 = sext i8 %25 to i32
%27 = add nsw i32 %26, 40
br label %67
28: ; preds = %19
%29 = lshr i64 %0, 32
%30 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %29
%31 = load i8, i8* %30
%32 = sext i8 %31 to i32
%33 = add nsw i32 %32, 32
br label %67
34: ; preds = %1
%35 = and i64 %0, 4294901760
%36 = icmp eq i64 %35, 0
br i1 %36, label %52, label %37
37: ; preds = %34
%38 = and i64 %0, 4278190080
%39 = icmp eq i64 %38, 0
br i1 %39, label %46, label %40
40: ; preds = %37
%41 = lshr i64 %0, 24
%42 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %41
%43 = load i8, i8* %42
%44 = sext i8 %43 to i32
%45 = add nsw i32 %44, 24
br label %67
46: ; preds = %37
%47 = lshr i64 %0, 16
%48 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %47
%49 = load i8, i8* %48
%50 = sext i8 %49 to i32
%51 = add nsw i32 %50, 16
br label %67
52: ; preds = %34
%53 = and i64 %0, 65280
%54 = icmp eq i64 %53, 0
br i1 %54, label %61, label %55
55: ; preds = %52
%56 = lshr i64 %0, 8
%57 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %56
%58 = load i8, i8* %57
%59 = sext i8 %58 to i32
%60 = add nsw i32 %59, 8
br label %67
61: ; preds = %52
%62 = shl nuw i64 %0, 32
%63 = ashr exact i64 %62, 32
%64 = getelementptr inbounds [256 x i8], [256 x i8]* @BN_num_bits_word.bits, i64 0, i64 %63
%65 = load i8, i8* %64
%66 = sext i8 %65 to i32
br label %67
67: ; preds = %61, %55, %46, %40, %28, %22, %13, %7
%68 = phi i32 [ %12, %7 ], [ %18, %13 ], [ %27, %22 ], [ %33, %28 ], [ %45, %40 ], [ %51, %46 ], [ %60, %55 ], [ %66, %61 ]
ret i32 %68
}