unsigned int wps_pin_checksum(unsigned int pin) {
  unsigned int acc = 0;
  while (pin) {
    acc += 3 * (pin % 10);
    pin /= 10;
    acc += pin % 10;
    pin /= 10;
  }
  return (10 - acc % 10) % 10;
}


x86 assembly (clang, -O0):
<wps_pin_checksum>:
push   %rbp
mov    %rsp,%rbp
mov    %edi,-0x4(%rbp)
movl   $0x0,-0x8(%rbp)
cmpl   $0x0,-0x4(%rbp)
je     1162 <wps_pin_checksum+0x62>
mov    -0x4(%rbp),%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
imul   $0x3,%edx,%eax
add    -0x8(%rbp),%eax
mov    %eax,-0x8(%rbp)
mov    -0x4(%rbp),%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
mov    %eax,-0x4(%rbp)
mov    -0x4(%rbp),%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
add    -0x8(%rbp),%edx
mov    %edx,-0x8(%rbp)
mov    -0x4(%rbp),%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
mov    %eax,-0x4(%rbp)
jmp    110e <wps_pin_checksum+0xe>
mov    -0x8(%rbp),%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
mov    $0xa,%eax
sub    %edx,%eax
mov    $0xa,%ecx
xor    %edx,%edx
div    %ecx
mov    %edx,%eax
pop    %rbp
ret

x86 assembly (clang, -O2):
<wps_pin_checksum>:
xor    %eax,%eax
test   %edi,%edi
je     1184 <wps_pin_checksum+0x84>
mov    $0xcccccccd,%r8d
nopl   0x0(%rax)
mov    %edi,%edx
imul   $0x51eb851f,%rdx,%rsi
imul   %r8,%rdx
shr    $0x23,%rdx
lea    (%rdx,%rdx,1),%ecx
lea    (%rcx,%rcx,4),%r9d
mov    %edi,%ecx
sub    %r9d,%ecx
lea    (%rcx,%rcx,2),%ecx
add    %eax,%ecx
mov    %rdx,%rax
imul   %r8,%rax
shr    $0x23,%rax
add    %eax,%eax
lea    (%rax,%rax,4),%eax
sub    %eax,%edx
mov    %edx,%eax
add    %ecx,%eax
shr    $0x25,%rsi
cmp    $0x63,%edi
mov    %esi,%edi
ja     1110 <wps_pin_checksum+0x10>
mov    %eax,%ecx
mov    $0xcccccccd,%edx
imul   %rcx,%rdx
shr    $0x23,%rdx
add    %edx,%edx
lea    (%rdx,%rdx,4),%ecx
sub    %ecx,%eax
mov    $0xa,%cl
sub    %al,%cl
movzbl %cl,%eax
imul   $0xcd,%eax,%ecx
shr    $0xa,%ecx
and    $0xfffffffe,%ecx
lea    (%rcx,%rcx,4),%ecx
sub    %cl,%al
movzbl %al,%eax
ret

LLVM IR (-O0):
define i32 @wps_pin_checksum(i32 %0) {
%2 = alloca i32
%3 = alloca i32
store i32 %0, i32* %2
store i32 0, i32* %3
br label %4
4: ; preds = %7, %1
%5 = load i32, i32* %2
%6 = icmp ne i32 %5, 0
br i1 %6, label %7, label %21
7: ; preds = %4
%8 = load i32, i32* %2
%9 = urem i32 %8, 10
%10 = mul i32 3, %9
%11 = load i32, i32* %3
%12 = add i32 %11, %10
store i32 %12, i32* %3
%13 = load i32, i32* %2
%14 = udiv i32 %13, 10
store i32 %14, i32* %2
%15 = load i32, i32* %2
%16 = urem i32 %15, 10
%17 = load i32, i32* %3
%18 = add i32 %17, %16
store i32 %18, i32* %3
%19 = load i32, i32* %2
%20 = udiv i32 %19, 10
store i32 %20, i32* %2
br label %4
21: ; preds = %4
%22 = load i32, i32* %3
%23 = urem i32 %22, 10
%24 = sub i32 10, %23
%25 = urem i32 %24, 10
ret i32 %25
}

LLVM IR (-O2):
define i32 @wps_pin_checksum(i32 %0) {
%2 = icmp eq i32 %0, 0
br i1 %2, label %20, label %3
3: ; preds = %1, %3
%4 = phi i32 [ %11, %3 ], [ 0, %1 ]
%5 = phi i32 [ %12, %3 ], [ %0, %1 ]
%6 = urem i32 %5, 10
%7 = mul nuw nsw i32 %6, 3
%8 = add i32 %7, %4
%9 = udiv i32 %5, 10
%10 = urem i32 %9, 10
%11 = add i32 %8, %10
%12 = udiv i32 %5, 100
%13 = icmp ult i32 %5, 100
br i1 %13, label %14, label %3
14: ; preds = %3
%15 = urem i32 %11, 10
%16 = trunc i32 %15 to i8
%17 = sub nuw nsw i8 10, %16
%18 = urem i8 %17, 10
%19 = zext i8 %18 to i32
br label %20
20: ; preds = %14, %1
%21 = phi i32 [ 0, %1 ], [ %19, %14 ]
ret i32 %21
}