// File: /workspace/github_c_makefile_star2_O2/canboat[P]canboat/analyzer/analyzer-explain.c
// Function: explainPGN
static void explainPGN(Pgn pgn)
{
  int  i;
  int  len;
  bool isVariable;

  printf("PGN: %d / %08o / %05X - %s\n\n", pgn.pgn, pgn.pgn, pgn.pgn, pgn.description);

  if (pgn.explanation != NULL)
  {
    printf("     %s\n", pgn.explanation);
  }
  if (pgn.url != NULL)
  {
    printf("     URL: %s\n", pgn.url);
  }
  len = getMinimalPgnLength(&pgn, &isVariable);
  if (isVariable)
  {
    printf("     The length is variable but at least %d bytes\n", len);
  }
  else
  {
    printf("     The length is %d bytes\n", len);
  }

  if (pgn.repeatingCount1 > 0)
  {
    if (pgn.repeatingField1 < 255)
    {
      printf("     Fields %u thru %u repeat n times, where n is the value contained in field %u.\n\n",
             pgn.repeatingStart1,
             pgn.repeatingStart1 + pgn.repeatingCount1,
             pgn.repeatingField1);
    }
    else
    {
      printf("     Fields %u thru %u repeat until the data in the PGN is exhausted.\n\n",
             pgn.repeatingStart1,
             pgn.repeatingStart1 + pgn.repeatingCount1);
    }
  }

  if (pgn.repeatingCount2 > 0)
  {
    if (pgn.repeatingField2 < 255)
    {
      printf("     Fields %u thru %u repeat n times, where n is the value contained in field %u.\n\n",
             pgn.repeatingStart2,
             pgn.repeatingStart2 + pgn.repeatingCount2,
             pgn.repeatingField2);
    }
    else
    {
      printf("     Fields %u thru %u repeat until the data in the PGN is exhausted.\n\n",
             pgn.repeatingStart2,
             pgn.repeatingStart2 + pgn.repeatingCount2);
    }
  }

  if (pgn.interval != 0 && pgn.interval < UINT16_MAX)
  {
    printf("     The PGN is normally transmitted every %u ms\n", pgn.interval);
  }
  if (pgn.interval == UINT16_MAX)
  {
    printf("     The PGN is transmitted on-demand or when data is available\n");
  }
  if (pgn.priority != 0)
  {
    printf("     The default priority is %u\n", pgn.priority);
  }

  for (i = 0; i < ARRAY_SIZE(pgn.fieldList) && pgn.fieldList[i].name; i++)
  {
    Field f = pgn.fieldList[i];
    printf("  Field #%d: %s%s%s\n",
           i + 1,
           f.name,
           f.name[0] && (f.description && f.description[0] && f.description[0] != ',') ? " - " : "",
           (!f.description || f.description[0] == ',') ? "" : f.description);
    if (f.size == LEN_VARIABLE)
    {
      printf("                  Bits: variable\n");
    }
    else
    {
      printf("                  Bits: %u\n", f.size);
    }

    if (f.unit && f.unit[0] == '=')
    {
      printf("                  Match: %s\n", &f.unit[1]);
    }
    else if (f.unit && f.unit[0] != ',')
    {
      printf("                  Unit: %s\n", f.unit);
    }

    if (f.resolution != 0.0)
    {
      printf("                  Resolution: %g\n", f.resolution);
    }
    printf("                  Signed: %s\n", (f.hasSign) ? "true" : "false");
    if (f.offset != 0)
    {
      if (f.resolution == 1.0 || f.resolution == 0.0)
      {
        printf("                  Offset: %d\n", f.offset);
      }
      else
      {
        printf("                  Offset: %" PRId64 "\n", (int64_t) (f.offset * f.resolution));
      }
    }
    if (f.partOfPrimaryKey)
    {
      printf("                  Part Of Primary Key: true\n");
    }

    if (f.lookup.function.pairEnumerator != NULL)
    {
      switch (f.lookup.type)
      {
        case LOOKUP_TYPE_PAIR: {
          printf("                  Enumeration: %s\n", f.lookup.name);
          if (!(f.unit && f.unit[0] == '='))
          {
            uint64_t maxValue = (UINT64_C(1) << f.size) - 1;
            printf("                  Range: 0..%" PRIu64 "\n", maxValue);
            (f.lookup.function.pairEnumerator)(explainPairText);
          }
          break;
        }

        case LOOKUP_TYPE_TRIPLET: {
          uint64_t maxValue = (UINT64_C(1) << f.size) - 1;
          printf("                  IndirectEnumeration: %s\n", f.lookup.name);
          printf("                  Range: 0..%" PRIu64 "\n", maxValue);
          (f.lookup.function.tripletEnumerator)(explainTripletText);
          break;
        }

        case LOOKUP_TYPE_BIT: {
          uint64_t maxValue = f.size;

          printf("                  BitEnumeration: %s\n", f.lookup.name);
          printf("                  BitRange: 0..%" PRIu64 "\n", maxValue);
          (f.lookup.function.bitEnumerator)(explainBitText);
          break;
        }

        case LOOKUP_TYPE_FIELDTYPE: {
          printf("                  Enumeration: %s\n", f.lookup.name);
          if (!(f.unit && f.unit[0] == '='))
          {
            uint64_t maxValue = (UINT64_C(1) << f.size) - 1;
            printf("                  Range: 0..%" PRIu64 "\n", maxValue);
            (f.lookup.function.fieldtypeEnumerator)(explainFieldtypeText);
          }
          break;
        }

        default:
          break;
      }
    }
  }

  printf("\n\n");
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x38, %rsp
leaq 0x70(%rsp), %rbx
movl 0x8(%rbx), %ecx
movq (%rbx), %r8
leaq 0x13496(%rip), %rdi     # 0x2227e
movl %ecx, %esi
movl %ecx, %edx
xorl %eax, %eax
callq 0xd110
movq %rbx, %rax
movq 0x15d8(%rbx), %rsi
testq %rsi, %rsi
je 0xee15
leaq 0x13492(%rip), %rdi     # 0x2229b
xorl %eax, %eax
callq 0xd110
leaq 0x70(%rsp), %rax
movq 0x15e0(%rax), %rsi
testq %rsi, %rsi
je 0xee2f
leaq 0x1347c(%rip), %rdi     # 0x222a4
xorl %eax, %eax
callq 0xd110
leaq 0xf(%rsp), %r14
leaq 0x70(%rsp), %rdi
movq %r14, %rsi
callq 0xf289
leaq 0x1346a(%rip), %rcx     # 0x222b2
leaq 0x13496(%rip), %rdi     # 0x222e5
cmpb $0x0, (%r14)
cmovneq %rcx, %rdi
movl %eax, %esi
xorl %eax, %eax
callq 0xd110
leaq 0x70(%rsp), %rdi
movzbl 0x15eb(%rdi), %edx
testl %edx, %edx
je 0xeeb4
movzbl 0x15ef(%rdi), %ecx
cmpl $0xff, %ecx
je 0xee98
movzbl 0x15ed(%rdi), %esi
addl %esi, %edx
leaq 0x13473(%rip), %rdi     # 0x22302
xorl %eax, %eax
callq 0xd110
jmp 0xeeaf
movzbl 0x15ed(%rdi), %esi
addl %esi, %edx
leaq 0x134af(%rip), %rdi     # 0x22357
xorl %eax, %eax
callq 0xd110
leaq 0x70(%rsp), %rdi
movzbl 0x15ec(%rdi), %edx
testl %edx, %edx
je 0xef03
movzbl 0x15f0(%rdi), %ecx
cmpl $0xff, %ecx
je 0xeee7
movzbl 0x15ee(%rdi), %esi
addl %esi, %edx
leaq 0x13424(%rip), %rdi     # 0x22302
xorl %eax, %eax
callq 0xd110
jmp 0xeefe
movzbl 0x15ee(%rdi), %esi
addl %esi, %edx
leaq 0x13460(%rip), %rdi     # 0x22357
xorl %eax, %eax
callq 0xd110
leaq 0x70(%rsp), %rdi
movzwl 0x15e8(%rdi), %esi
leal -0x1(%rsi), %eax
cmpw $-0x3, %ax
ja 0xef23
leaq 0x13485(%rip), %rdi     # 0x2239f
xorl %eax, %eax
callq 0xd110
jmp 0xef37
cmpl $0xffff, %esi           # imm = 0xFFFF
jne 0xef3c
leaq 0x153ac(%rip), %rdi     # 0x242de
callq 0xd0c0
leaq 0x70(%rsp), %rdi
movzbl 0x15ea(%rdi), %esi
testl %esi, %esi
je 0xef5a
leaq 0x13483(%rip), %rdi     # 0x223d1
xorl %eax, %eax
callq 0xd110
leaq 0x70(%rsp), %rdi
movl $0x88, %r14d
pushq $0x1
popq %rsi
leaq 0x13434(%rip), %r10     # 0x2239e
cmpq $0x1630, %r14           # imm = 0x1630
je 0xf26f
movq -0x70(%rdi,%r14), %rdx
testq %rdx, %rdx
je 0xf26f
movq -0x50(%rdi,%r14), %rax
cmpb $0x0, (%rdx)
setne %cl
testq %rax, %rax
setne %r8b
andb %cl, %r8b
cmpb $0x1, %r8b
jne 0xefbf
movb (%rax), %r9b
movq %r10, %rcx
movq %rax, %r8
testb %r9b, %r9b
je 0xefdb
cmpb $0x2c, %r9b
leaq 0x1344e(%rip), %rcx     # 0x22407
cmoveq %r10, %rcx
jmp 0xefd0
movq %r10, %rcx
movq %r10, %r8
testq %rax, %rax
je 0xefdb
movb (%rax), %r9b
movq %r10, %rcx
cmpb $0x2c, %r9b
cmoveq %r10, %rax
movq %rax, %r8
movl -0x60(%rdi,%r14), %ebx
movq -0x58(%rdi,%r14), %r15
movl -0x48(%rdi,%r14), %r13d
movsd -0x40(%rdi,%r14), %xmm0
movsd %xmm0, 0x20(%rsp)
movb -0x27(%rdi,%r14), %r12b
movb -0x26(%rdi,%r14), %al
movb %al, 0xe(%rsp)
movq -0x10(%rdi,%r14), %rax
movq %rax, 0x18(%rsp)
movl -0x8(%rdi,%r14), %ebp
movq (%rdi,%r14), %rax
movq %rax, 0x30(%rsp)
leaq 0x133ce(%rip), %rdi     # 0x223f2
movl %esi, 0x2c(%rsp)
xorl %eax, %eax
callq 0xd110
testq %rbx, %rbx
movq %rbx, 0x10(%rsp)
je 0xf04b
leaq 0x133cb(%rip), %rdi     # 0x2240b
movl %ebx, %esi
xorl %eax, %eax
callq 0xd110
jmp 0xf057
leaq 0x152cc(%rip), %rdi     # 0x2431e
callq 0xd0c0
testq %r15, %r15
movsd 0x20(%rsp), %xmm0
je 0xf094
movzbl (%r15), %eax
cmpl $0x2c, %eax
je 0xf094
cmpl $0x3d, %eax
jne 0xf07d
leaq 0x1(%r15), %rsi
leaq 0x133ac(%rip), %rdi     # 0x22427
jmp 0xf087
leaq 0x133c0(%rip), %rdi     # 0x22444
movq %r15, %rsi
xorl %eax, %eax
callq 0xd110
movsd 0x20(%rsp), %xmm0
ucomisd 0x10304(%rip), %xmm0    # 0x1f3a0
jne 0xf0a0
jnp 0xf0ae
leaq 0x133b9(%rip), %rdi     # 0x22460
movb $0x1, %al
callq 0xd110
testb $0x1, %r12b
leaq 0x133e7(%rip), %rsi     # 0x224a0
leaq 0x152a6(%rip), %rax     # 0x24366
cmovneq %rax, %rsi
leaq 0x133b7(%rip), %rdi     # 0x22482
xorl %eax, %eax
callq 0xd110
testl %r13d, %r13d
je 0xf124
movsd 0x20(%rsp), %xmm1
ucomisd 0x102b3(%rip), %xmm1    # 0x1f398
jne 0xf0e9
jnp 0xf113
ucomisd 0x102af(%rip), %xmm1    # 0x1f3a0
jne 0xf0f5
jnp 0xf113
cvtsi2sd %r13d, %xmm0
mulsd %xmm0, %xmm1
cvttsd2si %xmm1, %rsi
leaq 0x133ba(%rip), %rdi     # 0x224c4
xorl %eax, %eax
callq 0xd110
jmp 0xf124
leaq 0x1338c(%rip), %rdi     # 0x224a6
movl %r13d, %esi
xorl %eax, %eax
callq 0xd110
testb $0x1, 0xe(%rsp)
je 0xf137
leaq 0x1520d(%rip), %rdi     # 0x2433f
callq 0xd0c0
movq 0x30(%rsp), %rbx
testq %rbx, %rbx
je 0xf258
decl %ebp
cmpl $0x3, %ebp
ja 0xf258
leaq 0x10251(%rip), %rcx     # 0x1f3a8
movslq (%rcx,%rbp,4), %rax
addq %rcx, %rax
jmpq *%rax
leaq 0x1337c(%rip), %rdi     # 0x224e3
movq 0x18(%rsp), %rsi
xorl %eax, %eax
callq 0xd110
testq %r15, %r15
je 0xf182
cmpb $0x3d, (%r15)
je 0xf258
pushq $-0x1
popq %rsi
movq 0x10(%rsp), %rcx
shlq %cl, %rsi
notq %rsi
leaq 0x1336f(%rip), %rdi     # 0x22506
xorl %eax, %eax
callq 0xd110
leaq 0x1cb(%rip), %rdi       # 0xf370
jmp 0xf256
leaq 0x133a1(%rip), %rdi     # 0x22552
movq 0x18(%rsp), %rsi
xorl %eax, %eax
callq 0xd110
leaq 0x133b4(%rip), %rdi     # 0x22578
movq 0x10(%rsp), %rsi
xorl %eax, %eax
callq 0xd110
leaq 0x1c4(%rip), %rdi       # 0xf39b
jmp 0xf256
leaq 0x13303(%rip), %rdi     # 0x224e3
movq 0x18(%rsp), %rsi
xorl %eax, %eax
callq 0xd110
testq %r15, %r15
je 0xf1f7
cmpb $0x3d, (%r15)
je 0xf258
pushq $-0x1
popq %rsi
movq 0x10(%rsp), %rcx
shlq %cl, %rsi
notq %rsi
leaq 0x132fa(%rip), %rdi     # 0x22506
xorl %eax, %eax
callq 0xd110
leaq 0x195(%rip), %rdi       # 0xf3af
jmp 0xf256
pushq $-0x1
popq %r15
movq 0x10(%rsp), %rcx
shlq %cl, %r15
notq %r15
leaq 0x132f5(%rip), %rdi     # 0x22527
movq 0x18(%rsp), %rsi
xorl %eax, %eax
callq 0xd110
leaq 0x132c1(%rip), %rdi     # 0x22506
movq %r15, %rsi
xorl %eax, %eax
callq 0xd110
leaq 0x12e(%rip), %rdi       # 0xf384
callq *%rbx
addq $0xa8, %r14
movl 0x2c(%rsp), %esi
incl %esi
leaq 0x70(%rsp), %rdi
jmp 0xef63
leaq 0x13127(%rip), %rdi     # 0x2239d
addq $0x38, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
jmp 0xd0c0