void timer_init(unsigned long timer_id, unsigned long prescaler,
                unsigned long divider, unsigned long tcntbn,
                unsigned long tcmpbn) {
  unsigned long temp_data;
  temp_data = (*((volatile unsigned long *)((0x7F006000) + 0x00)));
  temp_data = (temp_data & (~(0xff))) | ((prescaler - 1) << 0);
  (*((volatile unsigned long *)((0x7F006000) + 0x00))) = temp_data;
  temp_data = (*((volatile unsigned long *)((0x7F006000) + 0x04)));
  temp_data =
      (temp_data & (~(0xf << (4 * timer_id)))) | (divider << (4 * timer_id));
  temp_data = (temp_data & (~(0xf << 20)));
  (*((volatile unsigned long *)((0x7F006000) + 0x04))) = temp_data;
  (*((volatile unsigned long *)((0x7F006000) + 0x0C))) = tcntbn;
  (*((volatile unsigned long *)((0x7F006000) + 0x10))) = tcmpbn;
  (*((volatile unsigned long *)((0x7F006000) + 0x08))) |= 1 << 1;
  (*((volatile unsigned long *)((0x7F006000) + 0x08))) &= ~(1 << 1);
  (*((volatile unsigned long *)((0x7F006000) + 0x08))) |= (1 << 0) | (1 << 3);
  temp_data = (*((volatile unsigned long *)((0x7F006000) + 0x44)));
  temp_data |= (1 << (timer_id));
  (*((volatile unsigned long *)((0x7F006000) + 0x44))) = temp_data;
}


x86 assembly (clang, -O0):
<timer_init>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    %rdx,-0x18(%rbp)
mov    %rcx,-0x20(%rbp)
mov    %r8,-0x28(%rbp)
mov    $0x7f006000,%eax
mov    (%rax),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
and    $0xffffffffffffff00,%rax
mov    -0x10(%rbp),%rcx
sub    $0x1,%rcx
shl    $0x0,%rcx
or     %rcx,%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rcx
mov    $0x7f006000,%eax
mov    %rcx,(%rax)
mov    $0x7f006004,%eax
mov    (%rax),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
mov    -0x8(%rbp),%rcx
shl    $0x2,%rcx
mov    $0xf,%edx
shl    %cl,%edx
mov    %edx,%ecx
xor    $0xffffffff,%ecx
movslq %ecx,%rcx
and    %rcx,%rax
mov    -0x18(%rbp),%rdx
mov    -0x8(%rbp),%rcx
shl    $0x2,%rcx
shl    %cl,%rdx
mov    %rdx,%rcx
or     %rcx,%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
and    $0xffffffffff0fffff,%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rcx
mov    $0x7f006004,%eax
mov    %rcx,(%rax)
mov    -0x20(%rbp),%rcx
mov    $0x7f00600c,%eax
mov    %rcx,(%rax)
mov    -0x28(%rbp),%rcx
mov    $0x7f006010,%eax
mov    %rcx,(%rax)
mov    $0x7f006008,%eax
mov    (%rax),%rcx
or     $0x2,%rcx
mov    $0x7f006008,%eax
mov    %rcx,(%rax)
mov    $0x7f006008,%eax
mov    (%rax),%rcx
and    $0xfffffffffffffffd,%rcx
mov    $0x7f006008,%eax
mov    %rcx,(%rax)
mov    $0x7f006008,%eax
mov    (%rax),%rcx
or     $0x9,%rcx
mov    $0x7f006008,%eax
mov    %rcx,(%rax)
mov    $0x7f006044,%eax
mov    (%rax),%rax
mov    %rax,-0x30(%rbp)
mov    -0x8(%rbp),%rax
mov    %eax,%ecx
mov    $0x1,%eax
shl    %cl,%eax
cltq
or     -0x30(%rbp),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rcx
mov    $0x7f006044,%eax
mov    %rcx,(%rax)
pop    %rbp
ret

x86 assembly (clang, -O2):
<timer_init>:
mov    %rcx,%rax
mov    $0xffffffffffffff00,%rcx
and    0x7f006000,%rcx
7f
add    $0xffffffffffffffff,%rsi
or     %rcx,%rsi
mov    %rsi,0x7f006000
7f
lea    0x0(,%rdi,4),%ecx
mov    $0xf,%esi
shl    %cl,%esi
not    %esi
movslq %esi,%rsi
and    0x7f006004,%rsi
7f
shl    %cl,%rdx
or     %rsi,%rdx
and    $0xffffffffff0fffff,%rdx
mov    %rdx,0x7f006004
7f
mov    %rax,0x7f00600c
7f
mov    %r8,0x7f006010
7f
orq    $0x2,0x7f006008
7f 02
andq   $0xfffffffffffffffd,0x7f006008
7f fd
orq    $0x9,0x7f006008
7f 09
mov    $0x1,%eax
mov    %edi,%ecx
shl    %cl,%eax
cltq
or     %rax,0x7f006044
7f
ret

LLVM IR (-O0):
define void @timer_init(i64 %0, i64 %1, i64 %2, i64 %3, i64 %4) {
%6 = alloca i64
%7 = alloca i64
%8 = alloca i64
%9 = alloca i64
%10 = alloca i64
%11 = alloca i64
store i64 %0, i64* %6
store i64 %1, i64* %7
store i64 %2, i64* %8
store i64 %3, i64* %9
store i64 %4, i64* %10
%12 = load volatile i64, i64* inttoptr (i64 2130731008 to i64*)
store i64 %12, i64* %11
%13 = load i64, i64* %11
%14 = and i64 %13, -256
%15 = load i64, i64* %7
%16 = sub i64 %15, 1
%17 = shl i64 %16, 0
%18 = or i64 %14, %17
store i64 %18, i64* %11
%19 = load i64, i64* %11
store volatile i64 %19, i64* inttoptr (i64 2130731008 to i64*)
%20 = load volatile i64, i64* inttoptr (i64 2130731012 to i64*)
store i64 %20, i64* %11
%21 = load i64, i64* %11
%22 = load i64, i64* %6
%23 = mul i64 4, %22
%24 = trunc i64 %23 to i32
%25 = shl i32 15, %24
%26 = xor i32 %25, -1
%27 = sext i32 %26 to i64
%28 = and i64 %21, %27
%29 = load i64, i64* %8
%30 = load i64, i64* %6
%31 = mul i64 4, %30
%32 = shl i64 %29, %31
%33 = or i64 %28, %32
store i64 %33, i64* %11
%34 = load i64, i64* %11
%35 = and i64 %34, -15728641
store i64 %35, i64* %11
%36 = load i64, i64* %11
store volatile i64 %36, i64* inttoptr (i64 2130731012 to i64*)
%37 = load i64, i64* %9
store volatile i64 %37, i64* inttoptr (i64 2130731020 to i64*)
%38 = load i64, i64* %10
store volatile i64 %38, i64* inttoptr (i64 2130731024 to i64*)
%39 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%40 = or i64 %39, 2
store volatile i64 %40, i64* inttoptr (i64 2130731016 to i64*)
%41 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%42 = and i64 %41, -3
store volatile i64 %42, i64* inttoptr (i64 2130731016 to i64*)
%43 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%44 = or i64 %43, 9
store volatile i64 %44, i64* inttoptr (i64 2130731016 to i64*)
%45 = load volatile i64, i64* inttoptr (i64 2130731076 to i64*)
store i64 %45, i64* %11
%46 = load i64, i64* %6
%47 = trunc i64 %46 to i32
%48 = shl i32 1, %47
%49 = sext i32 %48 to i64
%50 = load i64, i64* %11
%51 = or i64 %50, %49
store i64 %51, i64* %11
%52 = load i64, i64* %11
store volatile i64 %52, i64* inttoptr (i64 2130731076 to i64*)
ret void
}

LLVM IR (-O2):
define void @timer_init(i64 %0, i64 %1, i64 %2, i64 %3, i64 %4) {
%6 = load volatile i64, i64* inttoptr (i64 2130731008 to i64*)
%7 = and i64 %6, -256
%8 = add i64 %1, -1
%9 = or i64 %7, %8
store volatile i64 %9, i64* inttoptr (i64 2130731008 to i64*)
%10 = load volatile i64, i64* inttoptr (i64 2130731012 to i64*)
%11 = shl i64 %0, 2
%12 = trunc i64 %11 to i32
%13 = shl i32 15, %12
%14 = xor i32 %13, -1
%15 = sext i32 %14 to i64
%16 = and i64 %10, %15
%17 = shl i64 %2, %11
%18 = or i64 %16, %17
%19 = and i64 %18, -15728641
store volatile i64 %19, i64* inttoptr (i64 2130731012 to i64*)
store volatile i64 %3, i64* inttoptr (i64 2130731020 to i64*)
store volatile i64 %4, i64* inttoptr (i64 2130731024 to i64*)
%20 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%21 = or i64 %20, 2
store volatile i64 %21, i64* inttoptr (i64 2130731016 to i64*)
%22 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%23 = and i64 %22, -3
store volatile i64 %23, i64* inttoptr (i64 2130731016 to i64*)
%24 = load volatile i64, i64* inttoptr (i64 2130731016 to i64*)
%25 = or i64 %24, 9
store volatile i64 %25, i64* inttoptr (i64 2130731016 to i64*)
%26 = load volatile i64, i64* inttoptr (i64 2130731076 to i64*)
%27 = trunc i64 %0 to i32
%28 = shl nuw i32 1, %27
%29 = sext i32 %28 to i64
%30 = or i64 %26, %29
store volatile i64 %30, i64* inttoptr (i64 2130731076 to i64*)
ret void
}