#define NULL ((void *)0)
typedef unsigned long size_t; // Customize by platform.
typedef long intptr_t;
typedef unsigned long uintptr_t;
typedef long scalar_t__; // Either arithmetic or pointer type.
/* By default, we understand bool (as a convenience). */
typedef int bool;
#define false 0
#define true 1

/* Forward declarations */

/* Type definitions */

/* Variables and functions */
unsigned long pci_read_config32(int, int);
int /*<<< orphan*/ pci_write_config32(int, int, unsigned long);
void notify_bsp_ap_is_stopped(void) {
  unsigned long reg;
  unsigned long apic_id;
  apic_id = *((volatile unsigned long *)(0xfee00000 + 0x020));
  apic_id >>= 24;
  if (apic_id != 0) {
    reg = pci_read_config32(((((0) & 0xFF) << 16) |
                             (((24 + apic_id) & 0x1f) << 11) |
                             (((0) & 0x7) << 8)),
                            0x6C);
    reg |= 1 << 4;
    pci_write_config32(((((0) & 0xFF) << 16) | (((24 + apic_id) & 0x1f) << 11) |
                        (((0) & 0x7) << 8)),
                       0x6C, reg);
  }
}


x86 assembly (clang, -O0):
<notify_bsp_ap_is_stopped>:
push   %rbp
mov    %rsp,%rbp
sub    $0x10,%rsp
mov    $0xfee00020,%eax
mov    (%rax),%rax
mov    %rax,-0x10(%rbp)
mov    -0x10(%rbp),%rax
shr    $0x18,%rax
mov    %rax,-0x10(%rbp)
cmpq   $0x0,-0x10(%rbp)
je     11a7 <notify_bsp_ap_is_stopped+0x87>
mov    -0x10(%rbp),%rax
add    $0x18,%rax
and    $0x1f,%rax
shl    $0xb,%rax
or     $0x0,%rax
or     $0x0,%rax
mov    %eax,%edi
mov    $0x6c,%esi
call   1030 <pci_read_config32@plt>
mov    %rax,-0x8(%rbp)
mov    -0x8(%rbp),%rax
or     $0x10,%rax
mov    %rax,-0x8(%rbp)
mov    -0x10(%rbp),%rax
add    $0x18,%rax
and    $0x1f,%rax
shl    $0xb,%rax
or     $0x0,%rax
or     $0x0,%rax
mov    %eax,%edi
mov    -0x8(%rbp),%rdx
mov    $0x6c,%esi
call   1040 <pci_write_config32@plt>
add    $0x10,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<notify_bsp_ap_is_stopped>:
push   %rbx
mov    $0xfee00020,%eax
mov    (%rax),%rax
cmp    $0x1000000,%rax
jae    1133 <notify_bsp_ap_is_stopped+0x13>
pop    %rbx
ret
shr    $0xd,%eax
and    $0xf800,%eax
add    $0xc000,%eax
movzwl %ax,%ebx
mov    %ebx,%edi
mov    $0x6c,%esi
call   1030 <pci_read_config32@plt>
or     $0x10,%rax
mov    %ebx,%edi
mov    $0x6c,%esi
mov    %rax,%rdx
pop    %rbx
jmp    1040 <pci_write_config32@plt>

LLVM IR (-O0):
define void @notify_bsp_ap_is_stopped() {
%1 = alloca i64
%2 = alloca i64
%3 = load volatile i64, i64* inttoptr (i64 4276092960 to i64*)
store i64 %3, i64* %2
%4 = load i64, i64* %2
%5 = lshr i64 %4, 24
store i64 %5, i64* %2
%6 = load i64, i64* %2
%7 = icmp ne i64 %6, 0
br i1 %7, label %8, label %28
8: ; preds = %0
%9 = load i64, i64* %2
%10 = add i64 24, %9
%11 = and i64 %10, 31
%12 = shl i64 %11, 11
%13 = or i64 0, %12
%14 = or i64 %13, 0
%15 = trunc i64 %14 to i32
%16 = call i64 @pci_read_config32(i32 %15, i32 108)
store i64 %16, i64* %1
%17 = load i64, i64* %1
%18 = or i64 %17, 16
store i64 %18, i64* %1
%19 = load i64, i64* %2
%20 = add i64 24, %19
%21 = and i64 %20, 31
%22 = shl i64 %21, 11
%23 = or i64 0, %22
%24 = or i64 %23, 0
%25 = trunc i64 %24 to i32
%26 = load i64, i64* %1
%27 = call i32 @pci_write_config32(i32 %25, i32 108, i64 %26)
br label %28
28: ; preds = %8, %0
ret void
}

LLVM IR (-O2):
define void @notify_bsp_ap_is_stopped() {
%1 = load volatile i64, i64* inttoptr (i64 4276092960 to i64*)
%2 = icmp ult i64 %1, 16777216
br i1 %2, label %12, label %3
3: ; preds = %0
%4 = trunc i64 %1 to i32
%5 = lshr i32 %4, 13
%6 = and i32 %5, 63488
%7 = add nuw nsw i32 %6, 49152
%8 = and i32 %7, 63488
%9 = tail call i64 @pci_read_config32(i32 %8, i32 108)
%10 = or i64 %9, 16
%11 = tail call i32 @pci_write_config32(i32 %8, i32 108, i64 %10)
br label %12
12: ; preds = %3, %0
ret void
}