#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 */
int rand5();
int rand7(void) {
  int n = 5 * (rand5() - 1) + (rand5() - 1);
  while (n > 20)
    n = 5 * (rand5() - 1) + (rand5() - 1);
  return (n % 7) + 1;
}


x86 assembly (clang, -O0):
<rand7>:
push   %rbp
mov    %rsp,%rbp
sub    $0x10,%rsp
mov    $0x0,%al
call   1030 <rand5@plt>
sub    $0x1,%eax
imul   $0x5,%eax,%eax
mov    %eax,-0x8(%rbp)
mov    $0x0,%al
call   1030 <rand5@plt>
mov    %eax,%ecx
mov    -0x8(%rbp),%eax
sub    $0x1,%ecx
add    %ecx,%eax
mov    %eax,-0x4(%rbp)
cmpl   $0x14,-0x4(%rbp)
jle    116f <rand7+0x5f>
mov    $0x0,%al
call   1030 <rand5@plt>
sub    $0x1,%eax
imul   $0x5,%eax,%eax
mov    %eax,-0xc(%rbp)
mov    $0x0,%al
call   1030 <rand5@plt>
mov    %eax,%ecx
mov    -0xc(%rbp),%eax
sub    $0x1,%ecx
add    %ecx,%eax
mov    %eax,-0x4(%rbp)
jmp    113c <rand7+0x2c>
mov    -0x4(%rbp),%eax
mov    $0x7,%ecx
cltd
idiv   %ecx
mov    %edx,%eax
add    $0x1,%eax
add    $0x10,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<rand7>:
push   %rbx
xor    %eax,%eax
call   1030 <rand5@plt>
lea    (%rax,%rax,4),%ebx
xor    %eax,%eax
call   1030 <rand5@plt>
add    %ebx,%eax
add    $0xfffffffa,%eax
cmp    $0x15,%eax
jl     114b <rand7+0x3b>
nopl   0x0(%rax)
xor    %eax,%eax
call   1030 <rand5@plt>
lea    (%rax,%rax,4),%ebx
xor    %eax,%eax
call   1030 <rand5@plt>
add    %ebx,%eax
add    $0xfffffffa,%eax
cmp    $0x14,%eax
jg     1130 <rand7+0x20>
cltq
imul   $0xffffffff92492493,%rax,%rcx
shr    $0x20,%rcx
add    %eax,%ecx
mov    %ecx,%edx
shr    $0x1f,%edx
sar    $0x2,%ecx
add    %edx,%ecx
lea    0x0(,%rcx,8),%edx
sub    %edx,%ecx
add    %ecx,%eax
add    $0x1,%eax
pop    %rbx
ret

LLVM IR (-O0):
define i32 @rand7() {
%1 = alloca i32
%2 = call i32 (...) @rand5()
%3 = sub nsw i32 %2, 1
%4 = mul nsw i32 5, %3
%5 = call i32 (...) @rand5()
%6 = sub nsw i32 %5, 1
%7 = add nsw i32 %4, %6
store i32 %7, i32* %1
br label %8
8: ; preds = %11, %0
%9 = load i32, i32* %1
%10 = icmp sgt i32 %9, 20
br i1 %10, label %11, label %18
11: ; preds = %8
%12 = call i32 (...) @rand5()
%13 = sub nsw i32 %12, 1
%14 = mul nsw i32 5, %13
%15 = call i32 (...) @rand5()
%16 = sub nsw i32 %15, 1
%17 = add nsw i32 %14, %16
store i32 %17, i32* %1
br label %8
18: ; preds = %8
%19 = load i32, i32* %1
%20 = srem i32 %19, 7
%21 = add nsw i32 %20, 1
ret i32 %21
}

LLVM IR (-O2):
define i32 @rand7() {
%1 = tail call i32 (...) @rand5()
%2 = mul i32 %1, 5
%3 = tail call i32 (...) @rand5()
%4 = add i32 %2, %3
%5 = add i32 %4, -6
%6 = icmp sgt i32 %5, 20
br i1 %6, label %7, label %14
7: ; preds = %0, %7
%8 = tail call i32 (...) @rand5()
%9 = mul i32 %8, 5
%10 = tail call i32 (...) @rand5()
%11 = add i32 %9, %10
%12 = add i32 %11, -6
%13 = icmp sgt i32 %12, 20
br i1 %13, label %7, label %14
14: ; preds = %7, %0
%15 = phi i32 [ %5, %0 ], [ %12, %7 ]
%16 = srem i32 %15, 7
%17 = add nsw i32 %16, 1
ret i32 %17
}