#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 */
typedef int /*<<< orphan*/ md_buf;
typedef int /*<<< orphan*/ EVP_MD_CTX;
typedef int /*<<< orphan*/ EVP_MD;
typedef int /*<<< orphan*/ EVP_CIPHER;

/* Variables and functions */
int EVP_CIPHER_iv_length(int /*<<< orphan*/ const *);
int EVP_CIPHER_key_length(int /*<<< orphan*/ const *);
int /*<<< orphan*/ EVP_DigestFinal_ex(int /*<<< orphan*/ *, unsigned char *,
                                      unsigned int *);
int /*<<< orphan*/ EVP_DigestInit_ex(int /*<<< orphan*/ *,
                                     int /*<<< orphan*/ const *,
                                     int /*<<< orphan*/ *);
int /*<<< orphan*/ EVP_DigestUpdate(int /*<<< orphan*/ *, unsigned char const *,
                                    unsigned int);
int EVP_MAX_IV_LENGTH;
int EVP_MAX_KEY_LENGTH;
int EVP_MAX_MD_SIZE;
int /*<<< orphan*/ EVP_MD_CTX_free(int /*<<< orphan*/ *);
int /*<<< orphan*/ *EVP_MD_CTX_new();
int /*<<< orphan*/ OPENSSL_assert(int);
int /*<<< orphan*/ OPENSSL_cleanse(unsigned char *, int);
unsigned int PKCS5_SALT_LEN;
int EVP_BytesToKey(const EVP_CIPHER *type, const EVP_MD *md,
                   const unsigned char *salt, const unsigned char *data,
                   int datal, int count, unsigned char *key,
                   unsigned char *iv) {
  EVP_MD_CTX *c;
  unsigned char md_buf[EVP_MAX_MD_SIZE];
  int niv, nkey, addmd = 0;
  unsigned int mds = 0, i;
  int rv = 0;
  nkey = EVP_CIPHER_key_length(type);
  niv = EVP_CIPHER_iv_length(type);
  OPENSSL_assert(nkey <= EVP_MAX_KEY_LENGTH);
  OPENSSL_assert(niv <= EVP_MAX_IV_LENGTH);
  if (data == NULL)
    return (nkey);
  c = EVP_MD_CTX_new();
  if (c == NULL)
    goto err;
  for (;;) {
    if (!EVP_DigestInit_ex(c, md, NULL))
      goto err;
    if (addmd++)
      if (!EVP_DigestUpdate(c, &(md_buf[0]), mds))
        goto err;
    if (!EVP_DigestUpdate(c, data, datal))
      goto err;
    if (salt != NULL)
      if (!EVP_DigestUpdate(c, salt, PKCS5_SALT_LEN))
        goto err;
    if (!EVP_DigestFinal_ex(c, &(md_buf[0]), &mds))
      goto err;
    for (i = 1; i < (unsigned int)count; i++) {
      if (!EVP_DigestInit_ex(c, md, NULL))
        goto err;
      if (!EVP_DigestUpdate(c, &(md_buf[0]), mds))
        goto err;
      if (!EVP_DigestFinal_ex(c, &(md_buf[0]), &mds))
        goto err;
    }
    i = 0;
    if (nkey) {
      for (;;) {
        if (nkey == 0)
          break;
        if (i == mds)
          break;
        if (key != NULL)
          *(key++) = md_buf[i];
        nkey--;
        i++;
      }
    }
    if (niv && (i != mds)) {
      for (;;) {
        if (niv == 0)
          break;
        if (i == mds)
          break;
        if (iv != NULL)
          *(iv++) = md_buf[i];
        niv--;
        i++;
      }
    }
    if ((nkey == 0) && (niv == 0))
      break;
  }
  rv = EVP_CIPHER_key_length(type);
err:
  EVP_MD_CTX_free(c);
  OPENSSL_cleanse(md_buf, sizeof(md_buf));
  return rv;
}


x86 assembly (clang, -O0):
<EVP_BytesToKey>:
push   %rbp
mov    %rsp,%rbp
sub    $0x80,%rsp
mov    0x18(%rbp),%rax
mov    0x10(%rbp),%rax
mov    %rdi,-0x10(%rbp)
mov    %rsi,-0x18(%rbp)
mov    %rdx,-0x20(%rbp)
mov    %rcx,-0x28(%rbp)
mov    %r8d,-0x2c(%rbp)
mov    %r9d,-0x30(%rbp)
mov    0x2e16(%rip),%rax
mov    (%rax),%eax
mov    %rax,-0x78(%rbp)
mov    %rsp,%rcx
mov    %rcx,-0x40(%rbp)
mov    %rax,%rdx
add    $0xf,%rdx
and    $0xfffffffffffffff0,%rdx
mov    %rsp,%rcx
sub    %rdx,%rcx
mov    %rcx,-0x70(%rbp)
mov    %rcx,%rsp
mov    %rax,-0x48(%rbp)
movl   $0x0,-0x54(%rbp)
movl   $0x0,-0x58(%rbp)
movl   $0x0,-0x60(%rbp)
mov    -0x10(%rbp),%rdi
call   10b0 <EVP_CIPHER_key_length@plt>
mov    %eax,-0x50(%rbp)
mov    -0x10(%rbp),%rdi
call   1080 <EVP_CIPHER_iv_length@plt>
mov    %eax,-0x4c(%rbp)
mov    -0x50(%rbp),%eax
mov    0x2dbe(%rip),%rcx
cmp    (%rcx),%eax
setle  %al
and    $0x1,%al
movzbl %al,%edi
call   1040 <OPENSSL_assert@plt>
mov    -0x4c(%rbp),%eax
mov    0x2dad(%rip),%rcx
cmp    (%rcx),%eax
setle  %al
and    $0x1,%al
movzbl %al,%edi
call   1040 <OPENSSL_assert@plt>
cmpq   $0x0,-0x28(%rbp)
jne    1267 <EVP_BytesToKey+0xd7>
mov    -0x50(%rbp),%eax
mov    %eax,-0x4(%rbp)
movl   $0x1,-0x64(%rbp)
jmp    1514 <EVP_BytesToKey+0x384>
mov    $0x0,%al
call   10a0 <EVP_MD_CTX_new@plt>
mov    %rax,-0x38(%rbp)
cmpq   $0x0,-0x38(%rbp)
jne    1282 <EVP_BytesToKey+0xf2>
jmp    14ef <EVP_BytesToKey+0x35f>
jmp    1287 <EVP_BytesToKey+0xf7>
mov    -0x38(%rbp),%rdi
mov    -0x18(%rbp),%rsi
xor    %eax,%eax
mov    %eax,%edx
call   1070 <EVP_DigestInit_ex@plt>
cmp    $0x0,%eax
jne    12a6 <EVP_BytesToKey+0x116>
jmp    14ef <EVP_BytesToKey+0x35f>
mov    -0x54(%rbp),%eax
mov    %eax,%ecx
add    $0x1,%ecx
mov    %ecx,-0x54(%rbp)
cmp    $0x0,%eax
je     12dd <EVP_BytesToKey+0x14d>
mov    -0x70(%rbp),%rsi
mov    -0x38(%rbp),%rdi
mov    -0x58(%rbp),%edx
call   1090 <EVP_DigestUpdate@plt>
cmp    $0x0,%eax
jne    12d8 <EVP_BytesToKey+0x148>
jmp    14ef <EVP_BytesToKey+0x35f>
jmp    12dd <EVP_BytesToKey+0x14d>
mov    -0x38(%rbp),%rdi
mov    -0x28(%rbp),%rsi
mov    -0x2c(%rbp),%edx
call   1090 <EVP_DigestUpdate@plt>
cmp    $0x0,%eax
jne    12fb <EVP_BytesToKey+0x16b>
jmp    14ef <EVP_BytesToKey+0x35f>
cmpq   $0x0,-0x20(%rbp)
je     132f <EVP_BytesToKey+0x19f>
mov    -0x38(%rbp),%rdi
mov    -0x20(%rbp),%rsi
mov    0x2cbb(%rip),%rax
mov    (%rax),%edx
call   1090 <EVP_DigestUpdate@plt>
cmp    $0x0,%eax
jne    132a <EVP_BytesToKey+0x19a>
jmp    14ef <EVP_BytesToKey+0x35f>
jmp    132f <EVP_BytesToKey+0x19f>
mov    -0x70(%rbp),%rsi
mov    -0x38(%rbp),%rdi
lea    -0x58(%rbp),%rdx
call   1050 <EVP_DigestFinal_ex@plt>
cmp    $0x0,%eax
jne    134e <EVP_BytesToKey+0x1be>
jmp    14ef <EVP_BytesToKey+0x35f>
movl   $0x1,-0x5c(%rbp)
mov    -0x5c(%rbp),%eax
cmp    -0x30(%rbp),%eax
jae    13d0 <EVP_BytesToKey+0x240>
mov    -0x38(%rbp),%rdi
mov    -0x18(%rbp),%rsi
xor    %eax,%eax
mov    %eax,%edx
call   1070 <EVP_DigestInit_ex@plt>
cmp    $0x0,%eax
jne    1380 <EVP_BytesToKey+0x1f0>
jmp    14ef <EVP_BytesToKey+0x35f>
mov    -0x70(%rbp),%rsi
mov    -0x38(%rbp),%rdi
mov    -0x58(%rbp),%edx
call   1090 <EVP_DigestUpdate@plt>
cmp    $0x0,%eax
jne    139e <EVP_BytesToKey+0x20e>
jmp    14ef <EVP_BytesToKey+0x35f>
mov    -0x70(%rbp),%rsi
mov    -0x38(%rbp),%rdi
lea    -0x58(%rbp),%rdx
call   1050 <EVP_DigestFinal_ex@plt>
cmp    $0x0,%eax
jne    13bd <EVP_BytesToKey+0x22d>
jmp    14ef <EVP_BytesToKey+0x35f>
jmp    13c2 <EVP_BytesToKey+0x232>
mov    -0x5c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x5c(%rbp)
jmp    1355 <EVP_BytesToKey+0x1c5>
movl   $0x0,-0x5c(%rbp)
cmpl   $0x0,-0x50(%rbp)
je     1448 <EVP_BytesToKey+0x2b8>
jmp    13e6 <EVP_BytesToKey+0x256>
cmpl   $0x0,-0x50(%rbp)
jne    13f5 <EVP_BytesToKey+0x265>
jmp    1443 <EVP_BytesToKey+0x2b3>
mov    -0x5c(%rbp),%eax
cmp    -0x58(%rbp),%eax
jne    1406 <EVP_BytesToKey+0x276>
jmp    1443 <EVP_BytesToKey+0x2b3>
cmpq   $0x0,0x10(%rbp)
je     142c <EVP_BytesToKey+0x29c>
mov    -0x70(%rbp),%rax
mov    -0x5c(%rbp),%ecx
mov    (%rax,%rcx,1),%cl
mov    0x10(%rbp),%rax
mov    %rax,%rdx
add    $0x1,%rdx
mov    %rdx,0x10(%rbp)
mov    %cl,(%rax)
mov    -0x50(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x50(%rbp)
mov    -0x5c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x5c(%rbp)
jmp    13e6 <EVP_BytesToKey+0x256>
jmp    1448 <EVP_BytesToKey+0x2b8>
cmpl   $0x0,-0x4c(%rbp)
je     14c5 <EVP_BytesToKey+0x335>
mov    -0x5c(%rbp),%eax
cmp    -0x58(%rbp),%eax
je     14c5 <EVP_BytesToKey+0x335>
jmp    1463 <EVP_BytesToKey+0x2d3>
cmpl   $0x0,-0x4c(%rbp)
jne    1472 <EVP_BytesToKey+0x2e2>
jmp    14c0 <EVP_BytesToKey+0x330>
mov    -0x5c(%rbp),%eax
cmp    -0x58(%rbp),%eax
jne    1483 <EVP_BytesToKey+0x2f3>
jmp    14c0 <EVP_BytesToKey+0x330>
cmpq   $0x0,0x18(%rbp)
je     14a9 <EVP_BytesToKey+0x319>
mov    -0x70(%rbp),%rax
mov    -0x5c(%rbp),%ecx
mov    (%rax,%rcx,1),%cl
mov    0x18(%rbp),%rax
mov    %rax,%rdx
add    $0x1,%rdx
mov    %rdx,0x18(%rbp)
mov    %cl,(%rax)
mov    -0x4c(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x4c(%rbp)
mov    -0x5c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x5c(%rbp)
jmp    1463 <EVP_BytesToKey+0x2d3>
jmp    14c5 <EVP_BytesToKey+0x335>
cmpl   $0x0,-0x50(%rbp)
jne    14de <EVP_BytesToKey+0x34e>
cmpl   $0x0,-0x4c(%rbp)
jne    14de <EVP_BytesToKey+0x34e>
jmp    14e3 <EVP_BytesToKey+0x353>
jmp    1287 <EVP_BytesToKey+0xf7>
mov    -0x10(%rbp),%rdi
call   10b0 <EVP_CIPHER_key_length@plt>
mov    %eax,-0x60(%rbp)
mov    -0x38(%rbp),%rdi
call   1030 <EVP_MD_CTX_free@plt>
mov    -0x70(%rbp),%rdi
mov    -0x78(%rbp),%rax
mov    %eax,%esi
call   1060 <OPENSSL_cleanse@plt>
mov    -0x60(%rbp),%eax
mov    %eax,-0x4(%rbp)
movl   $0x1,-0x64(%rbp)
mov    -0x40(%rbp),%rax
mov    %rax,%rsp
mov    -0x4(%rbp),%eax
mov    %rbp,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<EVP_BytesToKey>:
push   %rbp
mov    %rsp,%rbp
push   %r15
push   %r14
push   %r13
push   %r12
push   %rbx
sub    $0x68,%rsp
mov    %r9,-0x70(%rbp)
mov    %r8d,-0x58(%rbp)
mov    %rcx,%r15
mov    %rdx,-0x48(%rbp)
mov    %rsi,-0x78(%rbp)
mov    %rdi,%rbx
mov    0x2e1a(%rip),%rax
mov    (%rax),%eax
mov    %rsp,%r13
mov    %rax,-0x88(%rbp)
add    $0xf,%rax
and    $0xfffffffffffffff0,%rax
sub    %rax,%r13
mov    %r13,%rsp
movl   $0x0,-0x2c(%rbp)
call   10b0 <EVP_CIPHER_key_length@plt>
mov    %eax,%r14d
mov    %rbx,-0x80(%rbp)
mov    %rbx,%rdi
call   1080 <EVP_CIPHER_iv_length@plt>
mov    %eax,%r12d
mov    0x2de3(%rip),%rax
xor    %edi,%edi
mov    %r14,-0x50(%rbp)
cmp    (%rax),%r14d
setle  %dil
call   1040 <OPENSSL_assert@plt>
mov    0x2dd2(%rip),%rax
xor    %edi,%edi
cmp    (%rax),%r12d
setle  %dil
call   1040 <OPENSSL_assert@plt>
mov    %r15,-0x90(%rbp)
test   %r15,%r15
je     142e <EVP_BytesToKey+0x29e>
mov    %r13,-0x38(%rbp)
xor    %r14d,%r14d
xor    %eax,%eax
call   10a0 <EVP_MD_CTX_new@plt>
mov    %rax,%r15
test   %rax,%rax
je     1437 <EVP_BytesToKey+0x2a7>
mov    0x18(%rbp),%rsi
mov    0x10(%rbp),%rdi
mov    -0x70(%rbp),%rax
add    $0xffffffff,%eax
mov    %eax,-0x54(%rbp)
movl   $0x0,-0x3c(%rbp)
mov    -0x38(%rbp),%rbx
mov    -0x48(%rbp),%r14
mov    -0x38(%rbp),%r13
mov    %rdi,-0x60(%rbp)
mov    %rsi,-0x68(%rbp)
mov    %r15,%rdi
mov    -0x78(%rbp),%rsi
xor    %edx,%edx
call   1070 <EVP_DigestInit_ex@plt>
test   %eax,%eax
je     1434 <EVP_BytesToKey+0x2a4>
cmpl   $0x0,-0x3c(%rbp)
je     12ad <EVP_BytesToKey+0x11d>
mov    -0x2c(%rbp),%edx
mov    %r15,%rdi
mov    %rbx,%rsi
call   1090 <EVP_DigestUpdate@plt>
test   %eax,%eax
je     1434 <EVP_BytesToKey+0x2a4>
mov    %r15,%rdi
mov    -0x90(%rbp),%rsi
mov    -0x58(%rbp),%edx
call   1090 <EVP_DigestUpdate@plt>
test   %eax,%eax
je     1434 <EVP_BytesToKey+0x2a4>
test   %r14,%r14
je     12e8 <EVP_BytesToKey+0x158>
mov    0x2cfd(%rip),%rax
mov    (%rax),%edx
mov    %r15,%rdi
mov    %r14,%rsi
call   1090 <EVP_DigestUpdate@plt>
test   %eax,%eax
je     1434 <EVP_BytesToKey+0x2a4>
mov    %r15,%rdi
mov    %rbx,%rsi
lea    -0x2c(%rbp),%rdx
call   1050 <EVP_DigestFinal_ex@plt>
test   %eax,%eax
je     1434 <EVP_BytesToKey+0x2a4>
mov    -0x54(%rbp),%ebx
cmpl   $0x2,-0x70(%rbp)
jb     1360 <EVP_BytesToKey+0x1d0>
nopl   0x0(%rax,%rax,1)
xor    %r14d,%r14d
mov    %r15,%rdi
mov    -0x78(%rbp),%rsi
xor    %edx,%edx
call   1070 <EVP_DigestInit_ex@plt>
test   %eax,%eax
je     1437 <EVP_BytesToKey+0x2a7>
mov    -0x2c(%rbp),%edx
mov    %r15,%rdi
mov    %r13,%rsi
call   1090 <EVP_DigestUpdate@plt>
test   %eax,%eax
je     1437 <EVP_BytesToKey+0x2a7>
mov    %r15,%rdi
mov    %r13,%rsi
lea    -0x2c(%rbp),%rdx
call   1050 <EVP_DigestFinal_ex@plt>
test   %eax,%eax
je     1437 <EVP_BytesToKey+0x2a7>
add    $0xffffffff,%ebx
jne    1310 <EVP_BytesToKey+0x180>
nopl   0x0(%rax,%rax,1)
mov    -0x50(%rbp),%rdx
mov    %edx,%edx
test   %rdx,%rdx
je     13a7 <EVP_BytesToKey+0x217>
xor    %eax,%eax
mov    -0x38(%rbp),%rbx
mov    -0x68(%rbp),%rsi
mov    -0x60(%rbp),%rdi
jmp    1396 <EVP_BytesToKey+0x206>
nopl   0x0(%rax,%rax,1)
movzbl (%rbx,%rax,1),%ecx
mov    %cl,(%rdi)
add    $0x1,%rdi
add    $0x1,%rax
cmp    %eax,%edx
je     1423 <EVP_BytesToKey+0x293>
mov    -0x2c(%rbp),%ecx
cmp    %rcx,%rax
je     1400 <EVP_BytesToKey+0x270>
test   %rdi,%rdi
jne    1380 <EVP_BytesToKey+0x1f0>
xor    %edi,%edi
jmp    138a <EVP_BytesToKey+0x1fa>
xor    %edx,%edx
xor    %eax,%eax
mov    -0x38(%rbp),%rbx
mov    -0x68(%rbp),%rsi
mov    -0x60(%rbp),%rdi
test   %r12d,%r12d
je     1407 <EVP_BytesToKey+0x277>
cmp    -0x2c(%rbp),%eax
je     140a <EVP_BytesToKey+0x27a>
mov    -0x48(%rbp),%r14
jmp    13e4 <EVP_BytesToKey+0x254>
nopw   0x0(%rax,%rax,1)
xor    %esi,%esi
cmp    $0x1,%r12d
je     13fb <EVP_BytesToKey+0x26b>
add    $0x1,%eax
add    $0xffffffff,%r12d
cmp    -0x2c(%rbp),%eax
je     140e <EVP_BytesToKey+0x27e>
test   %rsi,%rsi
je     13d0 <EVP_BytesToKey+0x240>
mov    %eax,%ecx
movzbl (%rbx,%rcx,1),%ecx
mov    %cl,(%rsi)
add    $0x1,%rsi
cmp    $0x1,%r12d
jne    13d8 <EVP_BytesToKey+0x248>
xor    %r12d,%r12d
jmp    140e <EVP_BytesToKey+0x27e>
sub    %eax,%edx
test   %r12d,%r12d
jne    13bc <EVP_BytesToKey+0x22c>
xor    %r12d,%r12d
mov    -0x48(%rbp),%r14
addl   $0x1,-0x3c(%rbp)
mov    %rdx,-0x50(%rbp)
mov    %edx,%eax
or     %r12d,%eax
jne    1273 <EVP_BytesToKey+0xe3>
jmp    1461 <EVP_BytesToKey+0x2d1>
mov    %edx,%eax
xor    %edx,%edx
test   %r12d,%r12d
jne    13bc <EVP_BytesToKey+0x22c>
jmp    1407 <EVP_BytesToKey+0x277>
mov    -0x50(%rbp),%rax
jmp    1452 <EVP_BytesToKey+0x2c2>
xor    %r14d,%r14d
mov    %r15,%rdi
call   1030 <EVP_MD_CTX_free@plt>
mov    -0x38(%rbp),%rdi
mov    -0x88(%rbp),%rsi
call   1060 <OPENSSL_cleanse@plt>
mov    %r14d,%eax
lea    -0x28(%rbp),%rsp
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
ret
mov    -0x80(%rbp),%rdi
call   10b0 <EVP_CIPHER_key_length@plt>
mov    %eax,%r14d
jmp    1437 <EVP_BytesToKey+0x2a7>

LLVM IR (-O0):
@EVP_MAX_MD_SIZE = global i32 0
@EVP_MAX_KEY_LENGTH = global i32 0
@EVP_MAX_IV_LENGTH = global i32 0
@PKCS5_SALT_LEN = global i32 0
define i32 @EVP_BytesToKey(i32* %0, i32* %1, i8* %2, i8* %3, i32 %4, i32 %5, i8* %6, i8* %7) {
%9 = alloca i32
%10 = alloca i32*
%11 = alloca i32*
%12 = alloca i8*
%13 = alloca i8*
%14 = alloca i32
%15 = alloca i32
%16 = alloca i8*
%17 = alloca i8*
%18 = alloca i32*
%19 = alloca i8*
%20 = alloca i64
%21 = alloca i32
%22 = alloca i32
%23 = alloca i32
%24 = alloca i32
%25 = alloca i32
%26 = alloca i32
%27 = alloca i32
store i32* %0, i32** %10
store i32* %1, i32** %11
store i8* %2, i8** %12
store i8* %3, i8** %13
store i32 %4, i32* %14
store i32 %5, i32* %15
store i8* %6, i8** %16
store i8* %7, i8** %17
%28 = load i32, i32* @EVP_MAX_MD_SIZE
%29 = zext i32 %28 to i64
%30 = call i8* @llvm.stacksave()
store i8* %30, i8** %19
%31 = alloca i8, i64 %29
store i64 %29, i64* %20
store i32 0, i32* %23
store i32 0, i32* %24
store i32 0, i32* %26
%32 = load i32*, i32** %10
%33 = call i32 @EVP_CIPHER_key_length(i32* %32)
store i32 %33, i32* %22
%34 = load i32*, i32** %10
%35 = call i32 @EVP_CIPHER_iv_length(i32* %34)
store i32 %35, i32* %21
%36 = load i32, i32* %22
%37 = load i32, i32* @EVP_MAX_KEY_LENGTH
%38 = icmp sle i32 %36, %37
%39 = zext i1 %38 to i32
%40 = call i32 @OPENSSL_assert(i32 %39)
%41 = load i32, i32* %21
%42 = load i32, i32* @EVP_MAX_IV_LENGTH
%43 = icmp sle i32 %41, %42
%44 = zext i1 %43 to i32
%45 = call i32 @OPENSSL_assert(i32 %44)
%46 = load i8*, i8** %13
%47 = icmp eq i8* %46, null
br i1 %47, label %48, label %50
48: ; preds = %8
%49 = load i32, i32* %22
store i32 %49, i32* %9
store i32 1, i32* %27
br label %205
50: ; preds = %8
%51 = call i32* (...) @EVP_MD_CTX_new()
store i32* %51, i32** %18
%52 = load i32*, i32** %18
%53 = icmp eq i32* %52, null
br i1 %53, label %54, label %55
54: ; preds = %50
br label %199
55: ; preds = %50
br label %56
56: ; preds = %195, %55
%57 = load i32*, i32** %18
%58 = load i32*, i32** %11
%59 = call i32 @EVP_DigestInit_ex(i32* %57, i32* %58, i32* null)
%60 = icmp ne i32 %59, 0
br i1 %60, label %62, label %61
61: ; preds = %56
br label %199
62: ; preds = %56
%63 = load i32, i32* %23
%64 = add nsw i32 %63, 1
store i32 %64, i32* %23
%65 = icmp ne i32 %63, 0
br i1 %65, label %66, label %74
66: ; preds = %62
%67 = load i32*, i32** %18
%68 = getelementptr inbounds i8, i8* %31, i64 0
%69 = load i32, i32* %24
%70 = call i32 @EVP_DigestUpdate(i32* %67, i8* %68, i32 %69)
%71 = icmp ne i32 %70, 0
br i1 %71, label %73, label %72
72: ; preds = %66
br label %199
73: ; preds = %66
br label %74
74: ; preds = %73, %62
%75 = load i32*, i32** %18
%76 = load i8*, i8** %13
%77 = load i32, i32* %14
%78 = call i32 @EVP_DigestUpdate(i32* %75, i8* %76, i32 %77)
%79 = icmp ne i32 %78, 0
br i1 %79, label %81, label %80
80: ; preds = %74
br label %199
81: ; preds = %74
%82 = load i8*, i8** %12
%83 = icmp ne i8* %82, null
br i1 %83, label %84, label %92
84: ; preds = %81
%85 = load i32*, i32** %18
%86 = load i8*, i8** %12
%87 = load i32, i32* @PKCS5_SALT_LEN
%88 = call i32 @EVP_DigestUpdate(i32* %85, i8* %86, i32 %87)
%89 = icmp ne i32 %88, 0
br i1 %89, label %91, label %90
90: ; preds = %84
br label %199
91: ; preds = %84
br label %92
92: ; preds = %91, %81
%93 = load i32*, i32** %18
%94 = getelementptr inbounds i8, i8* %31, i64 0
%95 = call i32 @EVP_DigestFinal_ex(i32* %93, i8* %94, i32* %24)
%96 = icmp ne i32 %95, 0
br i1 %96, label %98, label %97
97: ; preds = %92
br label %199
98: ; preds = %92
store i32 1, i32* %25
br label %99
99: ; preds = %123, %98
%100 = load i32, i32* %25
%101 = load i32, i32* %15
%102 = icmp ult i32 %100, %101
br i1 %102, label %103, label %126
103: ; preds = %99
%104 = load i32*, i32** %18
%105 = load i32*, i32** %11
%106 = call i32 @EVP_DigestInit_ex(i32* %104, i32* %105, i32* null)
%107 = icmp ne i32 %106, 0
br i1 %107, label %109, label %108
108: ; preds = %103
br label %199
109: ; preds = %103
%110 = load i32*, i32** %18
%111 = getelementptr inbounds i8, i8* %31, i64 0
%112 = load i32, i32* %24
%113 = call i32 @EVP_DigestUpdate(i32* %110, i8* %111, i32 %112)
%114 = icmp ne i32 %113, 0
br i1 %114, label %116, label %115
115: ; preds = %109
br label %199
116: ; preds = %109
%117 = load i32*, i32** %18
%118 = getelementptr inbounds i8, i8* %31, i64 0
%119 = call i32 @EVP_DigestFinal_ex(i32* %117, i8* %118, i32* %24)
%120 = icmp ne i32 %119, 0
br i1 %120, label %122, label %121
121: ; preds = %116
br label %199
122: ; preds = %116
br label %123
123: ; preds = %122
%124 = load i32, i32* %25
%125 = add i32 %124, 1
store i32 %125, i32* %25
br label %99
126: ; preds = %99
store i32 0, i32* %25
%127 = load i32, i32* %22
%128 = icmp ne i32 %127, 0
br i1 %128, label %129, label %155
129: ; preds = %126
br label %130
130: ; preds = %149, %129
%131 = load i32, i32* %22
%132 = icmp eq i32 %131, 0
br i1 %132, label %133, label %134
133: ; preds = %130
br label %154
134: ; preds = %130
%135 = load i32, i32* %25
%136 = load i32, i32* %24
%137 = icmp eq i32 %135, %136
br i1 %137, label %138, label %139
138: ; preds = %134
br label %154
139: ; preds = %134
%140 = load i8*, i8** %16
%141 = icmp ne i8* %140, null
br i1 %141, label %142, label %149
142: ; preds = %139
%143 = load i32, i32* %25
%144 = zext i32 %143 to i64
%145 = getelementptr inbounds i8, i8* %31, i64 %144
%146 = load i8, i8* %145
%147 = load i8*, i8** %16
%148 = getelementptr inbounds i8, i8* %147, i32 1
store i8* %148, i8** %16
store i8 %146, i8* %147
br label %149
149: ; preds = %142, %139
%150 = load i32, i32* %22
%151 = add nsw i32 %150, -1
store i32 %151, i32* %22
%152 = load i32, i32* %25
%153 = add i32 %152, 1
store i32 %153, i32* %25
br label %130
154: ; preds = %138, %133
br label %155
155: ; preds = %154, %126
%156 = load i32, i32* %21
%157 = icmp ne i32 %156, 0
br i1 %157, label %158, label %188
158: ; preds = %155
%159 = load i32, i32* %25
%160 = load i32, i32* %24
%161 = icmp ne i32 %159, %160
br i1 %161, label %162, label %188
162: ; preds = %158
br label %163
163: ; preds = %182, %162
%164 = load i32, i32* %21
%165 = icmp eq i32 %164, 0
br i1 %165, label %166, label %167
166: ; preds = %163
br label %187
167: ; preds = %163
%168 = load i32, i32* %25
%169 = load i32, i32* %24
%170 = icmp eq i32 %168, %169
br i1 %170, label %171, label %172
171: ; preds = %167
br label %187
172: ; preds = %167
%173 = load i8*, i8** %17
%174 = icmp ne i8* %173, null
br i1 %174, label %175, label %182
175: ; preds = %172
%176 = load i32, i32* %25
%177 = zext i32 %176 to i64
%178 = getelementptr inbounds i8, i8* %31, i64 %177
%179 = load i8, i8* %178
%180 = load i8*, i8** %17
%181 = getelementptr inbounds i8, i8* %180, i32 1
store i8* %181, i8** %17
store i8 %179, i8* %180
br label %182
182: ; preds = %175, %172
%183 = load i32, i32* %21
%184 = add nsw i32 %183, -1
store i32 %184, i32* %21
%185 = load i32, i32* %25
%186 = add i32 %185, 1
store i32 %186, i32* %25
br label %163
187: ; preds = %171, %166
br label %188
188: ; preds = %187, %158, %155
%189 = load i32, i32* %22
%190 = icmp eq i32 %189, 0
br i1 %190, label %191, label %195
191: ; preds = %188
%192 = load i32, i32* %21
%193 = icmp eq i32 %192, 0
br i1 %193, label %194, label %195
194: ; preds = %191
br label %196
195: ; preds = %191, %188
br label %56
196: ; preds = %194
%197 = load i32*, i32** %10
%198 = call i32 @EVP_CIPHER_key_length(i32* %197)
store i32 %198, i32* %26
br label %199
199: ; preds = %196, %121, %115, %108, %97, %90, %80, %72, %61, %54
%200 = load i32*, i32** %18
%201 = call i32 @EVP_MD_CTX_free(i32* %200)
%202 = trunc i64 %29 to i32
%203 = call i32 @OPENSSL_cleanse(i8* %31, i32 %202)
%204 = load i32, i32* %26
store i32 %204, i32* %9
store i32 1, i32* %27
br label %205
205: ; preds = %199, %48
%206 = load i8*, i8** %19
%207 = load i32, i32* %9
ret i32 %207
}

LLVM IR (-O2):
@EVP_MAX_MD_SIZE = global i32 0
@EVP_MAX_KEY_LENGTH = global i32 0
@EVP_MAX_IV_LENGTH = global i32 0
@PKCS5_SALT_LEN = global i32 0
define i32 @EVP_BytesToKey(i32* %0, i32* %1, i8* %2, i8* %3, i32 %4, i32 %5, i8* writeonly %6, i8* writeonly %7) {
%9 = alloca i32
%10 = load i32, i32* @EVP_MAX_MD_SIZE
%11 = zext i32 %10 to i64
%12 = alloca i8, i64 %11
%13 = bitcast i32* %9 to i8*
store i32 0, i32* %9
%14 = tail call i32 @EVP_CIPHER_key_length(i32* %0)
%15 = tail call i32 @EVP_CIPHER_iv_length(i32* %0)
%16 = load i32, i32* @EVP_MAX_KEY_LENGTH
%17 = icmp sle i32 %14, %16
%18 = zext i1 %17 to i32
%19 = tail call i32 @OPENSSL_assert(i32 %18)
%20 = load i32, i32* @EVP_MAX_IV_LENGTH
%21 = icmp sle i32 %15, %20
%22 = zext i1 %21 to i32
%23 = tail call i32 @OPENSSL_assert(i32 %22)
%24 = icmp eq i8* %3, null
br i1 %24, label %132, label %25
25: ; preds = %8
%26 = tail call i32* (...) @EVP_MD_CTX_new()
%27 = icmp eq i32* %26, null
br i1 %27, label %128, label %28
28: ; preds = %25
%29 = icmp eq i8* %2, null
%30 = icmp ugt i32 %5, 1
br label %31
31: ; preds = %28, %120
%32 = phi i8* [ %121, %120 ], [ %7, %28 ]
%33 = phi i8* [ %95, %120 ], [ %6, %28 ]
%34 = phi i32 [ %122, %120 ], [ %15, %28 ]
%35 = phi i32 [ %96, %120 ], [ %14, %28 ]
%36 = phi i32 [ %40, %120 ], [ 0, %28 ]
%37 = call i32 @EVP_DigestInit_ex(i32* %26, i32* %1, i32* null)
%38 = icmp eq i32 %37, 0
br i1 %38, label %128, label %39
39: ; preds = %31
%40 = add nuw nsw i32 %36, 1
%41 = icmp eq i32 %36, 0
br i1 %41, label %46, label %42
42: ; preds = %39
%43 = load i32, i32* %9
%44 = call i32 @EVP_DigestUpdate(i32* %26, i8* %12, i32 %43)
%45 = icmp eq i32 %44, 0
br i1 %45, label %128, label %46
46: ; preds = %42, %39
%47 = call i32 @EVP_DigestUpdate(i32* %26, i8* %3, i32 %4)
%48 = icmp eq i32 %47, 0
br i1 %48, label %128, label %49
49: ; preds = %46
br i1 %29, label %54, label %50
50: ; preds = %49
%51 = load i32, i32* @PKCS5_SALT_LEN
%52 = call i32 @EVP_DigestUpdate(i32* %26, i8* %2, i32 %51)
%53 = icmp eq i32 %52, 0
br i1 %53, label %128, label %54
54: ; preds = %50, %49
%55 = call i32 @EVP_DigestFinal_ex(i32* %26, i8* %12, i32* %9)
%56 = icmp eq i32 %55, 0
br i1 %56, label %128, label %57
57: ; preds = %54
br i1 %30, label %60, label %72
58: ; preds = %68
%59 = icmp eq i32 %71, %5
br i1 %59, label %72, label %60
60: ; preds = %57, %58
%61 = phi i32 [ %71, %58 ], [ 1, %57 ]
%62 = call i32 @EVP_DigestInit_ex(i32* %26, i32* %1, i32* null)
%63 = icmp eq i32 %62, 0
br i1 %63, label %128, label %64
64: ; preds = %60
%65 = load i32, i32* %9
%66 = call i32 @EVP_DigestUpdate(i32* %26, i8* %12, i32 %65)
%67 = icmp eq i32 %66, 0
br i1 %67, label %128, label %68
68: ; preds = %64
%69 = call i32 @EVP_DigestFinal_ex(i32* %26, i8* %12, i32* %9)
%70 = icmp eq i32 %69, 0
%71 = add nuw i32 %61, 1
br i1 %70, label %128, label %58
72: ; preds = %58, %57
%73 = icmp eq i32 %35, 0
br i1 %73, label %94, label %74
74: ; preds = %72, %87
%75 = phi i64 [ %90, %87 ], [ 0, %72 ]
%76 = phi i8* [ %88, %87 ], [ %33, %72 ]
%77 = phi i32 [ %89, %87 ], [ %35, %72 ]
%78 = load i32, i32* %9
%79 = zext i32 %78 to i64
%80 = icmp eq i64 %75, %79
br i1 %80, label %92, label %81
81: ; preds = %74
%82 = icmp eq i8* %76, null
br i1 %82, label %87, label %83
83: ; preds = %81
%84 = getelementptr inbounds i8, i8* %12, i64 %75
%85 = load i8, i8* %84
%86 = getelementptr inbounds i8, i8* %76, i64 1
store i8 %85, i8* %76
br label %87
87: ; preds = %83, %81
%88 = phi i8* [ %86, %83 ], [ null, %81 ]
%89 = add nsw i32 %77, -1
%90 = add nuw nsw i64 %75, 1
%91 = icmp eq i32 %89, 0
br i1 %91, label %94, label %74
92: ; preds = %74
%93 = trunc i64 %75 to i32
br label %94
94: ; preds = %87, %92, %72
%95 = phi i8* [ %33, %72 ], [ %76, %92 ], [ %88, %87 ]
%96 = phi i32 [ 0, %72 ], [ %77, %92 ], [ 0, %87 ]
%97 = phi i32 [ 0, %72 ], [ %93, %92 ], [ %35, %87 ]
%98 = icmp eq i32 %34, 0
br i1 %98, label %120, label %99
99: ; preds = %94
%100 = load i32, i32* %9
%101 = icmp eq i32 %97, %100
br i1 %101, label %120, label %102
102: ; preds = %99, %116
%103 = phi i32 [ %117, %116 ], [ %97, %99 ]
%104 = phi i32 [ %114, %116 ], [ %34, %99 ]
%105 = phi i8* [ %113, %116 ], [ %32, %99 ]
%106 = icmp eq i8* %105, null
br i1 %106, label %112, label %107
107: ; preds = %102
%108 = zext i32 %103 to i64
%109 = getelementptr inbounds i8, i8* %12, i64 %108
%110 = load i8, i8* %109
%111 = getelementptr inbounds i8, i8* %105, i64 1
store i8 %110, i8* %105
br label %112
112: ; preds = %107, %102
%113 = phi i8* [ %111, %107 ], [ null, %102 ]
%114 = add nsw i32 %104, -1
%115 = icmp eq i32 %114, 0
br i1 %115, label %120, label %116
116: ; preds = %112
%117 = add i32 %103, 1
%118 = load i32, i32* %9
%119 = icmp eq i32 %117, %118
br i1 %119, label %120, label %102
120: ; preds = %116, %112, %99, %94
%121 = phi i8* [ %32, %99 ], [ %32, %94 ], [ %113, %112 ], [ %113, %116 ]
%122 = phi i32 [ %34, %99 ], [ 0, %94 ], [ %114, %116 ], [ 0, %112 ]
%123 = icmp eq i32 %96, 0
%124 = icmp eq i32 %122, 0
%125 = select i1 %123, i1 %124, i1 false
br i1 %125, label %126, label %31
126: ; preds = %120
%127 = call i32 @EVP_CIPHER_key_length(i32* %0)
br label %128
128: ; preds = %54, %50, %46, %42, %31, %68, %64, %60, %25, %126
%129 = phi i32 [ 0, %25 ], [ %127, %126 ], [ 0, %60 ], [ 0, %64 ], [ 0, %68 ], [ 0, %31 ], [ 0, %42 ], [ 0, %46 ], [ 0, %50 ], [ 0, %54 ]
%130 = call i32 @EVP_MD_CTX_free(i32* %26)
%131 = call i32 @OPENSSL_cleanse(i8* %12, i32 %10)
br label %132
132: ; preds = %8, %128
%133 = phi i32 [ %129, %128 ], [ %14, %8 ]
ret i32 %133
}