#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*/ buf;

/* Variables and functions */
int B115200;
int /*<<< orphan*/ O_RDONLY;
int /*<<< orphan*/ TIOCMBIC;
int /*<<< orphan*/ TIOCMBIS;
int TIOCM_DTR;
int /*<<< orphan*/ close(int);
scalar_t__ eraseFlash(int);
int /*<<< orphan*/ fprintf(int /*<<< orphan*/, char *, ...);
int /*<<< orphan*/ ioctl(int, int /*<<< orphan*/, int *);
int /*<<< orphan*/ jumpToAddress(int, unsigned int);
int open(char *, int /*<<< orphan*/);
int openserial(char const *, int);
int read(int, unsigned char *, int);
int /*<<< orphan*/ stderr;
int /*<<< orphan*/ strcmp(char *, char *);
int usage();
int /*<<< orphan*/ usleep(int);
scalar_t__ write(int, unsigned char *, int);
scalar_t__ writeMemory(int, unsigned int, unsigned char *, int);
int main(int argc, char *argv[]) {
  int speed = B115200;
  const char *device = "/dev/ttyUSB0";
  unsigned char x;
  int fd, n;
  unsigned char buf[32768];
  unsigned do_erase = 0;
  unsigned do_write = 0;
  unsigned do_exec = 0;
  unsigned addr = 0;
  if (argc < 2)
    return usage();
  if (!strcmp(argv[1], "erase")) {
    do_erase = 1;
  } else if (!strcmp(argv[1], "flash")) {
    do_erase = 1;
    do_write = 1;
    addr = 0x08000000;
  } else if (!strcmp(argv[1], "exec")) {
    do_write = 1;
    do_exec = 1;
    addr = 0x20001000;
  } else {
    return usage();
  }
  if (do_write && argc != 3)
    return usage();
  fd = openserial(device, speed);
  if (fd < 0) {
    fprintf(stderr, "stderr open '%s'\n", device);
    return -1;
  }
  n = TIOCM_DTR;
  ioctl(fd, TIOCMBIS, &n);
  usleep(2500);
  ioctl(fd, TIOCMBIC, &n);
  usleep(2500);
  for (n = 0; n < 5; n++) {
    unsigned char SYNC = 0x7F;
    if (write(fd, &SYNC, 1)) {
    }
    if (read(fd, &x, 1) != 1)
      continue;
    if ((x == 0x79) || (x == 0x1f))
      break;
  }
  if (n == 5) {
    fprintf(stderr, "sync failure\n");
    return -1;
  }
  if (do_write) {
    int fd2 = open(argv[2], O_RDONLY);
    n = read(fd2, buf, sizeof(buf));
    close(fd2);
    if ((fd2 < 0) || (n <= 0)) {
      fprintf(stderr, "cannot read '%s'\n", argv[2]);
      return -1;
    }
    n += (n % 4);
    if (do_erase) {
      fprintf(stderr, "erasing flash...\n");
      if (eraseFlash(fd)) {
        fprintf(stderr, "erase failed\n");
        return -1;
      }
    }
    fprintf(stderr, "sending %d bytes...\n", n);
    if (writeMemory(fd, addr, buf, n)) {
      fprintf(stderr, "write failed\n");
      return -1;
    }
    fprintf(stderr, "done\n");
    if (do_exec) {
      jumpToAddress(fd, addr);
    } else {
      return 0;
    }
  } else if (do_erase) {
    if (eraseFlash(fd)) {
      fprintf(stderr, "erase failed\n");
      return -1;
    }
    fprintf(stderr, "flash erased\n");
    return 0;
  }
  for (;;) {
    if (read(fd, &x, 1) == 1) {
      if (x == 27)
        break;
      if ((x < 0x20) || (x > 0x7f))
        if ((x != 10) && (x != 13))
          x = '.';
      fprintf(stderr, "%c", x);
    }
  }
  return 0;
}


x86 assembly (clang, -O0):
<main>:
push   %rbp
mov    %rsp,%rbp
sub    $0x8050,%rsp
movl   $0x0,-0x4(%rbp)
mov    %edi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    0x2dc8(%rip),%rax
mov    (%rax),%eax
mov    %eax,-0x14(%rbp)
lea    0xe04(%rip),%rax
mov    %rax,-0x20(%rbp)
movl   $0x0,-0x8034(%rbp)
movl   $0x0,-0x8038(%rbp)
movl   $0x0,-0x803c(%rbp)
movl   $0x0,-0x8040(%rbp)
cmpl   $0x2,-0x8(%rbp)
jge    1241 <main+0x71>
mov    $0x0,%al
call   10d0 <usage@plt>
mov    %eax,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    -0x10(%rbp),%rax
mov    0x8(%rax),%rdi
lea    0xdbd(%rip),%rsi
call   1080 <strcmp@plt>
cmp    $0x0,%eax
jne    126d <main+0x9d>
movl   $0x1,-0x8034(%rbp)
jmp    1306 <main+0x136>
mov    -0x10(%rbp),%rax
mov    0x8(%rax),%rdi
lea    0xd97(%rip),%rsi
call   1080 <strcmp@plt>
cmp    $0x0,%eax
jne    12ad <main+0xdd>
movl   $0x1,-0x8034(%rbp)
movl   $0x1,-0x8038(%rbp)
movl   $0x8000000,-0x8040(%rbp)
jmp    1301 <main+0x131>
mov    -0x10(%rbp),%rax
mov    0x8(%rax),%rdi
lea    0xd5d(%rip),%rsi
call   1080 <strcmp@plt>
cmp    $0x0,%eax
jne    12ed <main+0x11d>
movl   $0x1,-0x8038(%rbp)
movl   $0x1,-0x803c(%rbp)
movl   $0x20001000,-0x8040(%rbp)
jmp    12fc <main+0x12c>
mov    $0x0,%al
call   10d0 <usage@plt>
mov    %eax,-0x4(%rbp)
jmp    1714 <main+0x544>
jmp    1301 <main+0x131>
jmp    1306 <main+0x136>
cmpl   $0x0,-0x8038(%rbp)
je     132c <main+0x15c>
cmpl   $0x3,-0x8(%rbp)
je     132c <main+0x15c>
mov    $0x0,%al
call   10d0 <usage@plt>
mov    %eax,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    -0x20(%rbp),%rdi
mov    -0x14(%rbp),%esi
call   10a0 <openserial@plt>
mov    %eax,-0x28(%rbp)
cmpl   $0x0,-0x28(%rbp)
jge    136c <main+0x19c>
mov    0x2c74(%rip),%rax
mov    (%rax),%edi
mov    -0x20(%rbp),%rdx
lea    0xcc5(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    0x2c6d(%rip),%rax
mov    (%rax),%eax
mov    %eax,-0x2c(%rbp)
mov    -0x28(%rbp),%edi
mov    0x2c4e(%rip),%rax
mov    (%rax),%esi
lea    -0x2c(%rbp),%rdx
call   1040 <ioctl@plt>
mov    $0x9c4,%edi
call   10f0 <usleep@plt>
mov    -0x28(%rbp),%edi
mov    0x2c27(%rip),%rax
mov    (%rax),%esi
lea    -0x2c(%rbp),%rdx
call   1040 <ioctl@plt>
mov    $0x9c4,%edi
call   10f0 <usleep@plt>
movl   $0x0,-0x2c(%rbp)
cmpl   $0x5,-0x2c(%rbp)
jge    1442 <main+0x272>
movb   $0x7f,-0x8041(%rbp)
mov    -0x28(%rbp),%edi
lea    -0x8041(%rbp),%rsi
mov    $0x1,%edx
call   1030 <write@plt>
cmp    $0x0,%rax
je     13f1 <main+0x221>
jmp    13f1 <main+0x221>
mov    -0x28(%rbp),%edi
lea    -0x21(%rbp),%rsi
mov    $0x1,%edx
call   1060 <read@plt>
cmp    $0x1,%eax
je     1410 <main+0x240>
jmp    1434 <main+0x264>
movzbl -0x21(%rbp),%eax
cmp    $0x79,%eax
je     142a <main+0x25a>
movzbl -0x21(%rbp),%eax
cmp    $0x1f,%eax
jne    142f <main+0x25f>
jmp    1442 <main+0x272>
jmp    1434 <main+0x264>
mov    -0x2c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x2c(%rbp)
jmp    13bd <main+0x1ed>
cmpl   $0x5,-0x2c(%rbp)
jne    146f <main+0x29f>
mov    0x2b6d(%rip),%rax
mov    (%rax),%edi
lea    0xbd4(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
cmpl   $0x0,-0x8038(%rbp)
je     1615 <main+0x445>
mov    -0x10(%rbp),%rax
mov    0x10(%rax),%rdi
mov    0x2b5d(%rip),%rax
mov    (%rax),%esi
call   10e0 <open@plt>
mov    %eax,-0x8048(%rbp)
mov    -0x8048(%rbp),%edi
lea    -0x8030(%rbp),%rsi
mov    $0x8000,%edx
call   1060 <read@plt>
mov    %eax,-0x2c(%rbp)
mov    -0x8048(%rbp),%edi
call   1050 <close@plt>
cmpl   $0x0,-0x8048(%rbp)
jl     14d4 <main+0x304>
cmpl   $0x0,-0x2c(%rbp)
jg     14ff <main+0x32f>
mov    0x2ae5(%rip),%rax
mov    (%rax),%edi
mov    -0x10(%rbp),%rax
mov    0x10(%rax),%rdx
lea    0xb52(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    -0x2c(%rbp),%eax
mov    $0x4,%ecx
cltd
idiv   %ecx
add    -0x2c(%rbp),%edx
mov    %edx,-0x2c(%rbp)
cmpl   $0x0,-0x8034(%rbp)
je     156e <main+0x39e>
mov    0x2a9c(%rip),%rax
mov    (%rax),%edi
lea    0xb23(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
mov    -0x28(%rbp),%edi
call   10b0 <eraseFlash@plt>
cmp    $0x0,%rax
je     1569 <main+0x399>
mov    0x2a73(%rip),%rax
mov    (%rax),%edi
lea    0xb0c(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
jmp    156e <main+0x39e>
mov    0x2a4b(%rip),%rax
mov    (%rax),%edi
mov    -0x2c(%rbp),%edx
lea    0xaef(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
mov    -0x28(%rbp),%edi
mov    -0x8040(%rbp),%esi
lea    -0x8030(%rbp),%rdx
mov    -0x2c(%rbp),%ecx
call   1070 <writeMemory@plt>
cmp    $0x0,%rax
je     15cd <main+0x3fd>
mov    0x2a0f(%rip),%rax
mov    (%rax),%edi
lea    0xacb(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    0x29ec(%rip),%rax
mov    (%rax),%edi
lea    0xab6(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
cmpl   $0x0,-0x803c(%rbp)
je     1604 <main+0x434>
mov    -0x28(%rbp),%edi
mov    -0x8040(%rbp),%esi
call   10c0 <jumpToAddress@plt>
jmp    1610 <main+0x440>
movl   $0x0,-0x4(%rbp)
jmp    1714 <main+0x544>
jmp    167f <main+0x4af>
cmpl   $0x0,-0x8034(%rbp)
je     167a <main+0x4aa>
mov    -0x28(%rbp),%edi
call   10b0 <eraseFlash@plt>
cmp    $0x0,%rax
je     1657 <main+0x487>
mov    0x2985(%rip),%rax
mov    (%rax),%edi
lea    0xa1e(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0xffffffff,-0x4(%rbp)
jmp    1714 <main+0x544>
mov    0x2962(%rip),%rax
mov    (%rax),%edi
lea    0xa32(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
movl   $0x0,-0x4(%rbp)
jmp    1714 <main+0x544>
jmp    167f <main+0x4af>
jmp    1684 <main+0x4b4>
mov    -0x28(%rbp),%edi
lea    -0x21(%rbp),%rsi
mov    $0x1,%edx
call   1060 <read@plt>
cmp    $0x1,%eax
jne    1708 <main+0x538>
movzbl -0x21(%rbp),%eax
cmp    $0x1b,%eax
jne    16b0 <main+0x4e0>
jmp    170d <main+0x53d>
movzbl -0x21(%rbp),%eax
cmp    $0x20,%eax
jl     16ca <main+0x4fa>
movzbl -0x21(%rbp),%eax
cmp    $0x7f,%eax
jle    16ed <main+0x51d>
movzbl -0x21(%rbp),%eax
cmp    $0xa,%eax
je     16e8 <main+0x518>
movzbl -0x21(%rbp),%eax
cmp    $0xd,%eax
je     16e8 <main+0x518>
movb   $0x2e,-0x21(%rbp)
jmp    16ed <main+0x51d>
mov    0x28cc(%rip),%rax
mov    (%rax),%edi
movzbl -0x21(%rbp),%edx
lea    0x9a6(%rip),%rsi
mov    $0x0,%al
call   1090 <fprintf@plt>
jmp    1684 <main+0x4b4>
movl   $0x0,-0x4(%rbp)
mov    -0x4(%rbp),%eax
add    $0x8050,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<main>:
push   %rbp
push   %r15
push   %r14
push   %r13
push   %r12
push   %rbx
sub    $0x8018,%rsp
cmp    $0x1,%edi
jg     11fe <main+0x2e>
xor    %eax,%eax
add    $0x8018,%rsp
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
jmp    10d0 <usage@plt>
mov    %rsi,%r12
mov    %edi,%ebp
mov    0x2dae(%rip),%rax
mov    (%rax),%r13d
mov    0x8(%rsi),%rbx
lea    0xdf5(%rip),%rsi
mov    %rbx,%rdi
call   1080 <strcmp@plt>
mov    %eax,%r15d
test   %eax,%eax
je     125c <main+0x8c>
lea    0xde5(%rip),%rsi
mov    %rbx,%rdi
call   1080 <strcmp@plt>
mov    %eax,%r14d
test   %eax,%eax
sete   0x7(%rsp)
je     1268 <main+0x98>
lea    0xdd0(%rip),%rsi
mov    %rbx,%rdi
call   1080 <strcmp@plt>
test   %eax,%eax
jne    11e6 <main+0x16>
mov    $0x20001000,%eax
jmp    126d <main+0x9d>
movb   $0x1,0x7(%rsp)
xor    %eax,%eax
xor    %r14d,%r14d
jmp    127d <main+0xad>
mov    $0x8000000,%eax
test   %r14d,%r14d
setne  %r14b
cmp    $0x3,%ebp
jne    11e6 <main+0x16>
mov    %eax,0xc(%rsp)
lea    0xd78(%rip),%rdi
mov    %r13d,%esi
call   10a0 <openserial@plt>
test   %eax,%eax
js     136a <main+0x19a>
mov    %eax,%ebx
mov    0x2d3f(%rip),%rax
mov    (%rax),%eax
mov    %eax,0x8(%rsp)
mov    0x2d22(%rip),%rax
mov    (%rax),%esi
lea    0x8(%rsp),%rbp
mov    %ebx,%edi
mov    %rbp,%rdx
call   1040 <ioctl@plt>
mov    $0x9c4,%edi
call   10f0 <usleep@plt>
mov    0x2cf8(%rip),%rax
mov    (%rax),%esi
mov    %ebx,%edi
mov    %rbp,%rdx
call   1040 <ioctl@plt>
mov    $0x9c4,%edi
call   10f0 <usleep@plt>
movl   $0x0,0x8(%rsp)
lea    0x10(%rsp),%r13
lea    0x6(%rsp),%rbp
jmp    1310 <main+0x140>
nopw   0x0(%rax,%rax,1)
mov    0x8(%rsp),%ecx
lea    0x1(%rcx),%eax
mov    %eax,0x8(%rsp)
cmp    $0x4,%ecx
jge    1349 <main+0x179>
movb   $0x7f,0x10(%rsp)
mov    %ebx,%edi
mov    %r13,%rsi
mov    $0x1,%edx
call   1030 <write@plt>
mov    %ebx,%edi
mov    %rbp,%rsi
mov    $0x1,%edx
call   1060 <read@plt>
cmp    $0x1,%eax
jne    1300 <main+0x130>
movzbl 0x6(%rsp),%eax
cmp    $0x1f,%al
je     1345 <main+0x175>
cmp    $0x79,%al
jne    1300 <main+0x130>
mov    0x8(%rsp),%eax
cmp    $0x5,%eax
jne    1386 <main+0x1b6>
mov    0x2c6b(%rip),%rax
mov    (%rax),%edi
lea    0xcd2(%rip),%rsi
xor    %eax,%eax
call   1090 <fprintf@plt>
jmp    145d <main+0x28d>
mov    0x2c4f(%rip),%rax
mov    (%rax),%edi
lea    0xca4(%rip),%rsi
lea    0xc7f(%rip),%rdx
jmp    1456 <main+0x286>
test   %r15d,%r15d
je     1417 <main+0x247>
mov    0x10(%r12),%rdi
mov    0x2c4d(%rip),%rax
mov    (%rax),%esi
call   10e0 <open@plt>
mov    %eax,%ebp
lea    0x10(%rsp),%rsi
mov    %eax,%edi
mov    $0x8000,%edx
call   1060 <read@plt>
mov    %eax,0x8(%rsp)
mov    %ebp,%edi
call   1050 <close@plt>
test   %ebp,%ebp
js     1441 <main+0x271>
mov    0x8(%rsp),%eax
test   %eax,%eax
jle    1441 <main+0x271>
mov    %eax,%edx
and    $0x3,%edx
add    %eax,%edx
mov    %edx,0x8(%rsp)
test   %r14b,%r14b
jne    148c <main+0x2bc>
mov    0x2bd9(%rip),%rbp
mov    0x0(%rbp),%edi
lea    0xc5f(%rip),%rsi
xor    %eax,%eax
call   1090 <fprintf@plt>
mov    %ebx,%edi
call   10b0 <eraseFlash@plt>
test   %rax,%rax
je     1488 <main+0x2b8>
mov    0x0(%rbp),%edi
lea    0xc50(%rip),%rsi
jmp    135e <main+0x18e>
test   %r14b,%r14b
jne    151a <main+0x34a>
mov    %ebx,%edi
call   10b0 <eraseFlash@plt>
mov    0x2b92(%rip),%rcx
mov    (%rcx),%edi
test   %rax,%rax
je     1476 <main+0x2a6>
lea    0xc26(%rip),%rsi
jmp    135e <main+0x18e>
mov    0x2b78(%rip),%rax
mov    (%rax),%edi
mov    0x10(%r12),%rdx
lea    0xbe8(%rip),%rsi
xor    %eax,%eax
call   1090 <fprintf@plt>
mov    $0xffffffff,%ebp
mov    %ebp,%eax
add    $0x8018,%rsp
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
ret
lea    0xc1c(%rip),%rsi
xor    %ebp,%ebp
xor    %eax,%eax
call   1090 <fprintf@plt>
jmp    1462 <main+0x292>
mov    0x8(%rsp),%edx
mov    0x2b2d(%rip),%r14
mov    (%r14),%edi
lea    0xbd3(%rip),%rsi
xor    %ebp,%ebp
xor    %eax,%eax
call   1090 <fprintf@plt>
mov    0x8(%rsp),%ecx
lea    0x10(%rsp),%rdx
mov    %ebx,%edi
mov    0xc(%rsp),%esi
call   1070 <writeMemory@plt>
mov    (%r14),%edi
test   %rax,%rax
je     14ce <main+0x2fe>
lea    0xbbc(%rip),%rsi
jmp    135e <main+0x18e>
lea    0xbbe(%rip),%rsi
xor    %eax,%eax
call   1090 <fprintf@plt>
cmpb   $0x0,0x7(%rsp)
jne    1462 <main+0x292>
mov    %ebx,%edi
mov    0xc(%rsp),%esi
call   10c0 <jumpToAddress@plt>
jmp    151a <main+0x34a>
cs nopw 0x0(%rax,%rax,1)
xchg   %ax,%ax
mov    0x2ab9(%rip),%rcx
mov    (%rcx),%edi
movzbl %al,%edx
lea    0xb94(%rip),%rsi
xor    %eax,%eax
call   1090 <fprintf@plt>
lea    0x6(%rsp),%rsi
mov    %ebx,%edi
mov    $0x1,%edx
call   1060 <read@plt>
cmp    $0x1,%eax
jne    151a <main+0x34a>
movzbl 0x6(%rsp),%eax
cmp    $0x1b,%al
je     1557 <main+0x387>
cmp    $0x1f,%al
jg     1500 <main+0x330>
cmp    $0xd,%al
movzbl %al,%ecx
mov    $0x2e,%edx
cmove  %ecx,%edx
cmp    $0xa,%al
cmove  %ecx,%edx
mov    %dl,0x6(%rsp)
mov    %edx,%eax
jmp    1500 <main+0x330>
xor    %ebp,%ebp
jmp    1462 <main+0x292>

LLVM IR (-O0):
@B115200 = global i32 0
@.str = [13 x i8] c"/dev/ttyUSB0\00"
@.str.1 = [6 x i8] c"erase\00"
@.str.2 = [6 x i8] c"flash\00"
@.str.3 = [5 x i8] c"exec\00"
@stderr = global i32 0
@.str.4 = [18 x i8] c"stderr open '%s'\0A\00"
@TIOCM_DTR = global i32 0
@TIOCMBIS = global i32 0
@TIOCMBIC = global i32 0
@.str.5 = [14 x i8] c"sync failure\0A\00"
@O_RDONLY = global i32 0
@.str.6 = [18 x i8] c"cannot read '%s'\0A\00"
@.str.7 = [18 x i8] c"erasing flash...\0A\00"
@.str.8 = [14 x i8] c"erase failed\0A\00"
@.str.9 = [21 x i8] c"sending %d bytes...\0A\00"
@.str.10 = [14 x i8] c"write failed\0A\00"
@.str.11 = [6 x i8] c"done\0A\00"
@.str.12 = [14 x i8] c"flash erased\0A\00"
@.str.13 = [3 x i8] c"%c\00"
define i32 @main(i32 %0, i8** %1) {
%3 = alloca i32
%4 = alloca i32
%5 = alloca i8**
%6 = alloca i32
%7 = alloca i8*
%8 = alloca i8
%9 = alloca i32
%10 = alloca i32
%11 = alloca [32768 x i8]
%12 = alloca i32
%13 = alloca i32
%14 = alloca i32
%15 = alloca i32
%16 = alloca i8
%17 = alloca i32
store i32 0, i32* %3
store i32 %0, i32* %4
store i8** %1, i8*** %5
%18 = load i32, i32* @B115200
store i32 %18, i32* %6
store i8* getelementptr inbounds ([13 x i8], [13 x i8]* @.str, i64 0, i64 0), i8** %7
store i32 0, i32* %12
store i32 0, i32* %13
store i32 0, i32* %14
store i32 0, i32* %15
%19 = load i32, i32* %4
%20 = icmp slt i32 %19, 2
br i1 %20, label %21, label %23
21: ; preds = %2
%22 = call i32 (...) @usage()
store i32 %22, i32* %3
br label %223
23: ; preds = %2
%24 = load i8**, i8*** %5
%25 = getelementptr inbounds i8*, i8** %24, i64 1
%26 = load i8*, i8** %25
%27 = call i32 @strcmp(i8* %26, i8* getelementptr inbounds ([6 x i8], [6 x i8]* @.str.1, i64 0, i64 0))
%28 = icmp ne i32 %27, 0
br i1 %28, label %30, label %29
29: ; preds = %23
store i32 1, i32* %12
br label %48
30: ; preds = %23
%31 = load i8**, i8*** %5
%32 = getelementptr inbounds i8*, i8** %31, i64 1
%33 = load i8*, i8** %32
%34 = call i32 @strcmp(i8* %33, i8* getelementptr inbounds ([6 x i8], [6 x i8]* @.str.2, i64 0, i64 0))
%35 = icmp ne i32 %34, 0
br i1 %35, label %37, label %36
36: ; preds = %30
store i32 1, i32* %12
store i32 1, i32* %13
store i32 134217728, i32* %15
br label %47
37: ; preds = %30
%38 = load i8**, i8*** %5
%39 = getelementptr inbounds i8*, i8** %38, i64 1
%40 = load i8*, i8** %39
%41 = call i32 @strcmp(i8* %40, i8* getelementptr inbounds ([5 x i8], [5 x i8]* @.str.3, i64 0, i64 0))
%42 = icmp ne i32 %41, 0
br i1 %42, label %44, label %43
43: ; preds = %37
store i32 1, i32* %13
store i32 1, i32* %14
store i32 536875008, i32* %15
br label %46
44: ; preds = %37
%45 = call i32 (...) @usage()
store i32 %45, i32* %3
br label %223
46: ; preds = %43
br label %47
47: ; preds = %46, %36
br label %48
48: ; preds = %47, %29
%49 = load i32, i32* %13
%50 = icmp ne i32 %49, 0
br i1 %50, label %51, label %56
51: ; preds = %48
%52 = load i32, i32* %4
%53 = icmp ne i32 %52, 3
br i1 %53, label %54, label %56
54: ; preds = %51
%55 = call i32 (...) @usage()
store i32 %55, i32* %3
br label %223
56: ; preds = %51, %48
%57 = load i8*, i8** %7
%58 = load i32, i32* %6
%59 = call i32 @openserial(i8* %57, i32 %58)
store i32 %59, i32* %9
%60 = load i32, i32* %9
%61 = icmp slt i32 %60, 0
br i1 %61, label %62, label %66
62: ; preds = %56
%63 = load i32, i32* @stderr
%64 = load i8*, i8** %7
%65 = call i32 (i32, i8*, ...) @fprintf(i32 %63, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.4, i64 0, i64 0), i8* %64)
store i32 -1, i32* %3
br label %223
66: ; preds = %56
%67 = load i32, i32* @TIOCM_DTR
store i32 %67, i32* %10
%68 = load i32, i32* %9
%69 = load i32, i32* @TIOCMBIS
%70 = call i32 @ioctl(i32 %68, i32 %69, i32* %10)
%71 = call i32 @usleep(i32 2500)
%72 = load i32, i32* %9
%73 = load i32, i32* @TIOCMBIC
%74 = call i32 @ioctl(i32 %72, i32 %73, i32* %10)
%75 = call i32 @usleep(i32 2500)
store i32 0, i32* %10
br label %76
76: ; preds = %99, %66
%77 = load i32, i32* %10
%78 = icmp slt i32 %77, 5
br i1 %78, label %79, label %102
79: ; preds = %76
store i8 127, i8* %16
%80 = load i32, i32* %9
%81 = call i64 @write(i32 %80, i8* %16, i32 1)
%82 = icmp ne i64 %81, 0
br i1 %82, label %83, label %84
83: ; preds = %79
br label %84
84: ; preds = %83, %79
%85 = load i32, i32* %9
%86 = call i32 @read(i32 %85, i8* %8, i32 1)
%87 = icmp ne i32 %86, 1
br i1 %87, label %88, label %89
88: ; preds = %84
br label %99
89: ; preds = %84
%90 = load i8, i8* %8
%91 = zext i8 %90 to i32
%92 = icmp eq i32 %91, 121
br i1 %92, label %97, label %93
93: ; preds = %89
%94 = load i8, i8* %8
%95 = zext i8 %94 to i32
%96 = icmp eq i32 %95, 31
br i1 %96, label %97, label %98
97: ; preds = %93, %89
br label %102
98: ; preds = %93
br label %99
99: ; preds = %98, %88
%100 = load i32, i32* %10
%101 = add nsw i32 %100, 1
store i32 %101, i32* %10
br label %76
102: ; preds = %97, %76
%103 = load i32, i32* %10
%104 = icmp eq i32 %103, 5
br i1 %104, label %105, label %108
105: ; preds = %102
%106 = load i32, i32* @stderr
%107 = call i32 (i32, i8*, ...) @fprintf(i32 %106, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.5, i64 0, i64 0))
store i32 -1, i32* %3
br label %223
108: ; preds = %102
%109 = load i32, i32* %13
%110 = icmp ne i32 %109, 0
br i1 %110, label %111, label %174
111: ; preds = %108
%112 = load i8**, i8*** %5
%113 = getelementptr inbounds i8*, i8** %112, i64 2
%114 = load i8*, i8** %113
%115 = load i32, i32* @O_RDONLY
%116 = call i32 @open(i8* %114, i32 %115)
store i32 %116, i32* %17
%117 = load i32, i32* %17
%118 = getelementptr inbounds [32768 x i8], [32768 x i8]* %11, i64 0, i64 0
%119 = call i32 @read(i32 %117, i8* %118, i32 32768)
store i32 %119, i32* %10
%120 = load i32, i32* %17
%121 = call i32 @close(i32 %120)
%122 = load i32, i32* %17
%123 = icmp slt i32 %122, 0
br i1 %123, label %127, label %124
124: ; preds = %111
%125 = load i32, i32* %10
%126 = icmp sle i32 %125, 0
br i1 %126, label %127, label %133
127: ; preds = %124, %111
%128 = load i32, i32* @stderr
%129 = load i8**, i8*** %5
%130 = getelementptr inbounds i8*, i8** %129, i64 2
%131 = load i8*, i8** %130
%132 = call i32 (i32, i8*, ...) @fprintf(i32 %128, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.6, i64 0, i64 0), i8* %131)
store i32 -1, i32* %3
br label %223
133: ; preds = %124
%134 = load i32, i32* %10
%135 = srem i32 %134, 4
%136 = load i32, i32* %10
%137 = add nsw i32 %136, %135
store i32 %137, i32* %10
%138 = load i32, i32* %12
%139 = icmp ne i32 %138, 0
br i1 %139, label %140, label %150
140: ; preds = %133
%141 = load i32, i32* @stderr
%142 = call i32 (i32, i8*, ...) @fprintf(i32 %141, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.7, i64 0, i64 0))
%143 = load i32, i32* %9
%144 = call i64 @eraseFlash(i32 %143)
%145 = icmp ne i64 %144, 0
br i1 %145, label %146, label %149
146: ; preds = %140
%147 = load i32, i32* @stderr
%148 = call i32 (i32, i8*, ...) @fprintf(i32 %147, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.8, i64 0, i64 0))
store i32 -1, i32* %3
br label %223
149: ; preds = %140
br label %150
150: ; preds = %149, %133
%151 = load i32, i32* @stderr
%152 = load i32, i32* %10
%153 = call i32 (i32, i8*, ...) @fprintf(i32 %151, i8* getelementptr inbounds ([21 x i8], [21 x i8]* @.str.9, i64 0, i64 0), i32 %152)
%154 = load i32, i32* %9
%155 = load i32, i32* %15
%156 = getelementptr inbounds [32768 x i8], [32768 x i8]* %11, i64 0, i64 0
%157 = load i32, i32* %10
%158 = call i64 @writeMemory(i32 %154, i32 %155, i8* %156, i32 %157)
%159 = icmp ne i64 %158, 0
br i1 %159, label %160, label %163
160: ; preds = %150
%161 = load i32, i32* @stderr
%162 = call i32 (i32, i8*, ...) @fprintf(i32 %161, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.10, i64 0, i64 0))
store i32 -1, i32* %3
br label %223
163: ; preds = %150
%164 = load i32, i32* @stderr
%165 = call i32 (i32, i8*, ...) @fprintf(i32 %164, i8* getelementptr inbounds ([6 x i8], [6 x i8]* @.str.11, i64 0, i64 0))
%166 = load i32, i32* %14
%167 = icmp ne i32 %166, 0
br i1 %167, label %168, label %172
168: ; preds = %163
%169 = load i32, i32* %9
%170 = load i32, i32* %15
%171 = call i32 @jumpToAddress(i32 %169, i32 %170)
br label %173
172: ; preds = %163
store i32 0, i32* %3
br label %223
173: ; preds = %168
br label %188
174: ; preds = %108
%175 = load i32, i32* %12
%176 = icmp ne i32 %175, 0
br i1 %176, label %177, label %187
177: ; preds = %174
%178 = load i32, i32* %9
%179 = call i64 @eraseFlash(i32 %178)
%180 = icmp ne i64 %179, 0
br i1 %180, label %181, label %184
181: ; preds = %177
%182 = load i32, i32* @stderr
%183 = call i32 (i32, i8*, ...) @fprintf(i32 %182, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.8, i64 0, i64 0))
store i32 -1, i32* %3
br label %223
184: ; preds = %177
%185 = load i32, i32* @stderr
%186 = call i32 (i32, i8*, ...) @fprintf(i32 %185, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.12, i64 0, i64 0))
store i32 0, i32* %3
br label %223
187: ; preds = %174
br label %188
188: ; preds = %187, %173
br label %189
189: ; preds = %221, %188
%190 = load i32, i32* %9
%191 = call i32 @read(i32 %190, i8* %8, i32 1)
%192 = icmp eq i32 %191, 1
br i1 %192, label %193, label %221
193: ; preds = %189
%194 = load i8, i8* %8
%195 = zext i8 %194 to i32
%196 = icmp eq i32 %195, 27
br i1 %196, label %197, label %198
197: ; preds = %193
br label %222
198: ; preds = %193
%199 = load i8, i8* %8
%200 = zext i8 %199 to i32
%201 = icmp slt i32 %200, 32
br i1 %201, label %206, label %202
202: ; preds = %198
%203 = load i8, i8* %8
%204 = zext i8 %203 to i32
%205 = icmp sgt i32 %204, 127
br i1 %205, label %206, label %216
206: ; preds = %202, %198
%207 = load i8, i8* %8
%208 = zext i8 %207 to i32
%209 = icmp ne i32 %208, 10
br i1 %209, label %210, label %215
210: ; preds = %206
%211 = load i8, i8* %8
%212 = zext i8 %211 to i32
%213 = icmp ne i32 %212, 13
br i1 %213, label %214, label %215
214: ; preds = %210
store i8 46, i8* %8
br label %215
215: ; preds = %214, %210, %206
br label %216
216: ; preds = %215, %202
%217 = load i32, i32* @stderr
%218 = load i8, i8* %8
%219 = zext i8 %218 to i32
%220 = call i32 (i32, i8*, ...) @fprintf(i32 %217, i8* getelementptr inbounds ([3 x i8], [3 x i8]* @.str.13, i64 0, i64 0), i32 %219)
br label %221
221: ; preds = %216, %189
br label %189
222: ; preds = %197
store i32 0, i32* %3
br label %223
223: ; preds = %222, %184, %181, %172, %160, %146, %127, %105, %62, %54, %44, %21
%224 = load i32, i32* %3
ret i32 %224
}

LLVM IR (-O2):
@B115200 = global i32 0
@.str = [13 x i8] c"/dev/ttyUSB0\00"
@.str.1 = [6 x i8] c"erase\00"
@.str.2 = [6 x i8] c"flash\00"
@.str.3 = [5 x i8] c"exec\00"
@stderr = global i32 0
@.str.4 = [18 x i8] c"stderr open '%s'\0A\00"
@TIOCM_DTR = global i32 0
@TIOCMBIS = global i32 0
@TIOCMBIC = global i32 0
@.str.5 = [14 x i8] c"sync failure\0A\00"
@O_RDONLY = global i32 0
@.str.6 = [18 x i8] c"cannot read '%s'\0A\00"
@.str.7 = [18 x i8] c"erasing flash...\0A\00"
@.str.8 = [14 x i8] c"erase failed\0A\00"
@.str.9 = [21 x i8] c"sending %d bytes...\0A\00"
@.str.10 = [14 x i8] c"write failed\0A\00"
@.str.11 = [6 x i8] c"done\0A\00"
@.str.12 = [14 x i8] c"flash erased\0A\00"
@.str.13 = [3 x i8] c"%c\00"
define i32 @main(i32 %0, i8** nocapture %1) {
%3 = alloca i8
%4 = alloca i32
%5 = alloca [32768 x i8]
%6 = alloca i8
%7 = load i32, i32* @B115200
%8 = bitcast i32* %4 to i8*
%9 = getelementptr inbounds [32768 x i8], [32768 x i8]* %5, i64 0, i64 0
%10 = icmp slt i32 %0, 2
br i1 %10, label %11, label %13
11: ; preds = %2
%12 = tail call i32 (...) @usage()
br label %140
13: ; preds = %2
%14 = getelementptr inbounds i8*, i8** %1, i64 1
%15 = load i8*, i8** %14
%16 = tail call i32 @strcmp(i8* dereferenceable(1) %15, i8* dereferenceable(6) getelementptr inbounds ([6 x i8], [6 x i8]* @.str.1, i64 0, i64 0))
%17 = icmp eq i32 %16, 0
br i1 %17, label %32, label %18
18: ; preds = %13
%19 = tail call i32 @strcmp(i8* dereferenceable(1) %15, i8* dereferenceable(6) getelementptr inbounds ([6 x i8], [6 x i8]* @.str.2, i64 0, i64 0))
%20 = icmp eq i32 %19, 0
br i1 %20, label %26, label %21
21: ; preds = %18
%22 = tail call i32 @strcmp(i8* dereferenceable(1) %15, i8* dereferenceable(5) getelementptr inbounds ([5 x i8], [5 x i8]* @.str.3, i64 0, i64 0))
%23 = icmp eq i32 %22, 0
br i1 %23, label %26, label %24
24: ; preds = %21
%25 = tail call i32 (...) @usage()
br label %140
26: ; preds = %21, %18
%27 = phi i32 [ 134217728, %18 ], [ 536875008, %21 ]
%28 = xor i1 %20, true
%29 = icmp eq i32 %0, 3
br i1 %29, label %32, label %30
30: ; preds = %26
%31 = tail call i32 (...) @usage()
br label %140
32: ; preds = %13, %26
%33 = phi i32 [ %27, %26 ], [ 0, %13 ]
%34 = phi i1 [ %20, %26 ], [ true, %13 ]
%35 = phi i1 [ %28, %26 ], [ false, %13 ]
%36 = tail call i32 @openserial(i8* getelementptr inbounds ([13 x i8], [13 x i8]* @.str, i64 0, i64 0), i32 %7)
%37 = icmp slt i32 %36, 0
br i1 %37, label %38, label %41
38: ; preds = %32
%39 = load i32, i32* @stderr
%40 = tail call i32 (i32, i8*, ...) @fprintf(i32 %39, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.4, i64 0, i64 0), i8* getelementptr inbounds ([13 x i8], [13 x i8]* @.str, i64 0, i64 0))
br label %140
41: ; preds = %32
%42 = load i32, i32* @TIOCM_DTR
store i32 %42, i32* %4
%43 = load i32, i32* @TIOCMBIS
%44 = call i32 @ioctl(i32 %36, i32 %43, i32* %4)
%45 = call i32 @usleep(i32 2500)
%46 = load i32, i32* @TIOCMBIC
%47 = call i32 @ioctl(i32 %36, i32 %46, i32* %4)
%48 = call i32 @usleep(i32 2500)
store i32 0, i32* %4
br label %49
49: ; preds = %41, %56
store i8 127, i8* %6
%50 = call i64 @write(i32 %36, i8* %6, i32 1)
%51 = call i32 @read(i32 %36, i8* %3, i32 1)
%52 = icmp eq i32 %51, 1
br i1 %52, label %54, label %53
53: ; preds = %49
br label %56
54: ; preds = %49
%55 = load i8, i8* %3
switch i8 %55, label %56 [
i8 121, label %60
i8 31, label %60
]
56: ; preds = %54, %53
%57 = load i32, i32* %4
%58 = add nsw i32 %57, 1
store i32 %58, i32* %4
%59 = icmp slt i32 %57, 4
br i1 %59, label %49, label %62
60: ; preds = %54, %54
%61 = load i32, i32* %4
br label %62
62: ; preds = %56, %60
%63 = phi i32 [ %61, %60 ], [ %58, %56 ]
%64 = icmp eq i32 %63, 5
br i1 %64, label %65, label %68
65: ; preds = %62
%66 = load i32, i32* @stderr
%67 = call i32 (i32, i8*, ...) @fprintf(i32 %66, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.5, i64 0, i64 0))
br label %140
68: ; preds = %62
br i1 %17, label %111, label %69
69: ; preds = %68
%70 = getelementptr inbounds i8*, i8** %1, i64 2
%71 = load i8*, i8** %70
%72 = load i32, i32* @O_RDONLY
%73 = call i32 @open(i8* %71, i32 %72)
%74 = call i32 @read(i32 %73, i8* %9, i32 32768)
store i32 %74, i32* %4
%75 = call i32 @close(i32 %73)
%76 = icmp slt i32 %73, 0
%77 = load i32, i32* %4
%78 = icmp slt i32 %77, 1
%79 = select i1 %76, i1 true, i1 %78
br i1 %79, label %80, label %84
80: ; preds = %69
%81 = load i32, i32* @stderr
%82 = load i8*, i8** %70
%83 = call i32 (i32, i8*, ...) @fprintf(i32 %81, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.6, i64 0, i64 0), i8* %82)
br label %140
84: ; preds = %69
%85 = and i32 %77, 3
%86 = add nuw nsw i32 %85, %77
store i32 %86, i32* %4
br i1 %35, label %97, label %87
87: ; preds = %84
%88 = load i32, i32* @stderr
%89 = call i32 (i32, i8*, ...) @fprintf(i32 %88, i8* getelementptr inbounds ([18 x i8], [18 x i8]* @.str.7, i64 0, i64 0))
%90 = call i64 @eraseFlash(i32 %36)
%91 = icmp eq i64 %90, 0
br i1 %91, label %92, label %94
92: ; preds = %87
%93 = load i32, i32* %4
br label %97
94: ; preds = %87
%95 = load i32, i32* @stderr
%96 = call i32 (i32, i8*, ...) @fprintf(i32 %95, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.8, i64 0, i64 0))
br label %140
97: ; preds = %92, %84
%98 = phi i32 [ %93, %92 ], [ %86, %84 ]
%99 = load i32, i32* @stderr
%100 = call i32 (i32, i8*, ...) @fprintf(i32 %99, i8* getelementptr inbounds ([21 x i8], [21 x i8]* @.str.9, i64 0, i64 0), i32 %98)
%101 = load i32, i32* %4
%102 = call i64 @writeMemory(i32 %36, i32 %33, i8* %9, i32 %101)
%103 = icmp eq i64 %102, 0
%104 = load i32, i32* @stderr
br i1 %103, label %107, label %105
105: ; preds = %97
%106 = call i32 (i32, i8*, ...) @fprintf(i32 %104, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.10, i64 0, i64 0))
br label %140
107: ; preds = %97
%108 = call i32 (i32, i8*, ...) @fprintf(i32 %104, i8* getelementptr inbounds ([6 x i8], [6 x i8]* @.str.11, i64 0, i64 0))
br i1 %34, label %140, label %109
109: ; preds = %107
%110 = call i32 @jumpToAddress(i32 %36, i32 %33)
br label %112
111: ; preds = %68
br i1 %35, label %112, label %113
112: ; preds = %109, %111
br label %121
113: ; preds = %111
%114 = call i64 @eraseFlash(i32 %36)
%115 = icmp eq i64 %114, 0
%116 = load i32, i32* @stderr
br i1 %115, label %119, label %117
117: ; preds = %113
%118 = call i32 (i32, i8*, ...) @fprintf(i32 %116, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.8, i64 0, i64 0))
br label %140
119: ; preds = %113
%120 = call i32 (i32, i8*, ...) @fprintf(i32 %116, i8* getelementptr inbounds ([14 x i8], [14 x i8]* @.str.12, i64 0, i64 0))
br label %140
121: ; preds = %139, %112
%122 = call i32 @read(i32 %36, i8* %3, i32 1)
%123 = icmp eq i32 %122, 1
br i1 %123, label %124, label %139
124: ; preds = %121
%125 = load i8, i8* %3
%126 = icmp eq i8 %125, 27
br i1 %126, label %140, label %127
127: ; preds = %124
%128 = icmp slt i8 %125, 32
br i1 %128, label %129, label %134
129: ; preds = %127
%130 = icmp ne i8 %125, 10
%131 = icmp ne i8 %125, 13
%132 = and i1 %130, %131
%133 = select i1 %132, i8 46, i8 %125
store i8 %133, i8* %3
br label %134
134: ; preds = %129, %127
%135 = phi i8 [ %133, %129 ], [ %125, %127 ]
%136 = load i32, i32* @stderr
%137 = zext i8 %135 to i32
%138 = call i32 (i32, i8*, ...) @fprintf(i32 %136, i8* getelementptr inbounds ([3 x i8], [3 x i8]* @.str.13, i64 0, i64 0), i32 %137)
br label %139
139: ; preds = %134, %121
br label %121
140: ; preds = %124, %107, %80, %94, %105, %119, %117, %65, %38, %30, %24, %11
%141 = phi i32 [ %12, %11 ], [ %25, %24 ], [ %31, %30 ], [ -1, %38 ], [ -1, %65 ], [ -1, %117 ], [ 0, %119 ], [ 0, %107 ], [ -1, %80 ], [ -1, %94 ], [ -1, %105 ], [ 0, %124 ]
ret i32 %141
}