// File: /workspace/github_cpp_makefile_star2_O3/tomfunkhouser[P]gaps/pkgs/R3Utils/R3Segmentation.cpp
// Function: gaps::R3SegmentationCluster::R3SegmentationCluster(gaps::R3SegmentationCluster*, gaps::R3SegmentationCluster*)
R3SegmentationCluster::
R3SegmentationCluster(R3SegmentationCluster *child1, R3SegmentationCluster *child2)
  : seed_point(NULL),
    points(),
    parent(NULL),
    children(),
    pairs(),
    primitive(),
    area(0),
    color(0,0,0),
    timestamp(0),
    category_identifier(-1),
    category_confidence(0),
    possible_affinity(0),
    total_affinity(0),
    segmentation(NULL),
    segmentation_index(-1)
{
  // Assign seed point
  seed_point = child1->seed_point;

  // Update primitive
  primitive.Update(child1->primitive, child2->primitive, child1->points.NEntries(), child2->points.NEntries());

  // Update color
  if (child1->points.NEntries() + child2->points.NEntries() > 0) {
    color += child1->points.NEntries() * child1->color;
    color += child2->points.NEntries() * child2->color;
    color /= child1->points.NEntries() + child2->points.NEntries();
  }

  // Update category info
  if (child1->points.NEntries() + child2->points.NEntries() > 0) {
    if (child1->category_identifier == child2->category_identifier) {
      // Categories match -- average confidences
      category_identifier = child1->category_identifier;
      category_confidence += child1->points.NEntries() * child1->category_confidence;
      category_confidence += child2->points.NEntries() * child2->category_confidence;
      category_confidence /= child1->points.NEntries() + child2->points.NEntries();
    }
    else {
      // Categories don't match -- trust larger cluster
      if ((child2->category_identifier < 0) || (child1->points.NEntries() > child2->points.NEntries())) {
        category_identifier = child1->category_identifier;
        category_confidence += child1->points.NEntries() * child1->category_confidence;
        category_confidence /= child1->points.NEntries() + child2->points.NEntries();
      }
      else {
        category_identifier = child2->category_identifier;
        category_confidence += child2->points.NEntries() * child2->category_confidence;
        category_confidence /= child1->points.NEntries() + child2->points.NEntries();
      }
    }
  }

  // Update timestamp
  timestamp = 0.5*(child1->timestamp + child2->timestamp);

  // Update area
  area = child1->area + child2->area;

  // Insert points from child1
  while (!child1->points.IsEmpty()) {
    R3SegmentationPoint *point = child1->points.Tail();
    child1->RemovePoint(point);
    RNScalar affinity = Affinity(point);
    if (affinity < 0) affinity = 0;
    possible_affinity += affinity;
    InsertPoint(point, affinity);
  }

  // Insert points from child2
  while (!child2->points.IsEmpty()) {
    R3SegmentationPoint *point = child2->points.Tail();
    child2->RemovePoint(point);
    RNScalar affinity = Affinity(point);
    if (affinity < 0) affinity = 0;
    possible_affinity += affinity;
    InsertPoint(point, affinity);
  }

  // Update hierarchy
  child1->parent = this;
  child2->parent = this;
  children.Insert(child1);
  children.Insert(child2);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x178, %rsp            # imm = 0x178
movq %rdx, %r13
movq %rsi, %rbp
movq %rdi, %r15
xorl %ebx, %ebx
movq %rbx, (%rdi)
leaq 0x8(%rdi), %r12
movq %r12, %rdi
callq 0xc352c
movq %rbx, 0x18(%r15)
leaq 0x20(%r15), %r14
movq %r14, %rdi
callq 0xc352c
movq %r12, (%rsp)
leaq 0x30(%r15), %rdi
movq %rdi, 0x8(%rsp)
callq 0xc352c
leaq 0x40(%r15), %r12
movq %r12, %rdi
xorl %esi, %esi
callq 0x28edc
movq $0x0, 0xe8(%r15)
leaq 0xf0(%r15), %rbx
xorpd %xmm0, %xmm0
xorpd %xmm1, %xmm1
xorpd %xmm2, %xmm2
movq %rbx, %rdi
callq 0xc33a0
movq $0x0, 0x108(%r15)
movl $0xffffffff, %eax       # imm = 0xFFFFFFFF
movl %eax, 0x110(%r15)
xorpd %xmm0, %xmm0
movupd %xmm0, 0x118(%r15)
movupd %xmm0, 0x128(%r15)
movl %eax, 0x138(%r15)
movq (%rbp), %rax
movq %rax, (%r15)
leaq 0x40(%rbp), %rsi
leaq 0xd0(%rsp), %rdi
callq 0x28f4a
leaq 0x40(%r13), %rsi
leaq 0x28(%rsp), %rdi
callq 0x28f4a
xorps %xmm0, %xmm0
cvtsi2sdl 0x14(%rbp), %xmm0
xorps %xmm1, %xmm1
cvtsi2sdl 0x14(%r13), %xmm1
leaq 0xd0(%rsp), %rsi
leaq 0x28(%rsp), %rdx
movq %r12, %rdi
callq 0x29722
leaq 0x30(%rsp), %rdi
callq 0x88520
leaq 0xd8(%rsp), %rdi
callq 0x88520
movl 0x14(%rbp), %eax
movl 0x14(%r13), %ecx
addl %eax, %ecx
jle 0x2a04a
xorps %xmm2, %xmm2
cvtsi2sd %eax, %xmm2
movsd 0xf0(%rbp), %xmm0
mulsd %xmm2, %xmm0
movsd 0xf8(%rbp), %xmm1
mulsd %xmm2, %xmm1
mulsd 0x100(%rbp), %xmm2
leaq 0x10(%rsp), %rdi
callq 0xc33a0
leaq 0x10(%rsp), %rsi
movq %rbx, %rdi
callq 0xc3452
xorps %xmm2, %xmm2
cvtsi2sdl 0x14(%r13), %xmm2
movsd 0xf0(%r13), %xmm0
mulsd %xmm2, %xmm0
movsd 0xf8(%r13), %xmm1
mulsd %xmm2, %xmm1
mulsd 0x100(%r13), %xmm2
leaq 0x10(%rsp), %rdi
callq 0xc33a0
leaq 0x10(%rsp), %rsi
movq %rbx, %rdi
callq 0xc3452
movl 0x14(%r13), %eax
addl 0x14(%rbp), %eax
xorps %xmm0, %xmm0
cvtsi2sd %eax, %xmm0
movq %rbx, %rdi
callq 0xc34fe
movl 0x14(%rbp), %esi
movl 0x14(%r13), %ecx
movl %ecx, %edx
addl %esi, %edx
jle 0x2a04a
leaq 0x118(%r15), %rax
movl 0x110(%rbp), %edi
movl 0x110(%r13), %r8d
cmpl %r8d, %edi
jne 0x29ff1
movl %edi, 0x110(%r15)
xorps %xmm1, %xmm1
cvtsi2sd %esi, %xmm1
mulsd 0x118(%rbp), %xmm1
addsd 0x118(%r15), %xmm1
movsd %xmm1, 0x118(%r15)
xorps %xmm0, %xmm0
cvtsi2sd %ecx, %xmm0
mulsd 0x118(%r13), %xmm0
addsd %xmm1, %xmm0
xorps %xmm1, %xmm1
cvtsi2sd %edx, %xmm1
jmp 0x2a042
testl %r8d, %r8d
setns %r9b
cmpl %ecx, %esi
setle %r10b
xorps %xmm1, %xmm1
cvtsi2sd %edx, %xmm1
testb %r9b, %r10b
jne 0x2a022
movl %edi, 0x110(%r15)
xorps %xmm0, %xmm0
cvtsi2sd %esi, %xmm0
mulsd 0x118(%rbp), %xmm0
jmp 0x2a039
movl %r8d, 0x110(%r15)
xorps %xmm0, %xmm0
cvtsi2sd %ecx, %xmm0
mulsd 0x118(%r13), %xmm0
addsd 0x118(%r15), %xmm0
divsd %xmm1, %xmm0
movsd %xmm0, (%rax)
movsd 0x108(%rbp), %xmm0
addsd 0x108(%r13), %xmm0
mulsd 0xdefa5(%rip), %xmm0    # 0x109008
movsd %xmm0, 0x108(%r15)
movsd 0xe8(%rbp), %xmm0
addsd 0xe8(%r13), %xmm0
movsd %xmm0, 0xe8(%r15)
movslq 0x14(%rbp), %rax
testq %rax, %rax
je 0x2a12d
movq 0x8(%rbp), %rcx
movq -0x8(%rcx,%rax,8), %rbx
movq %rbp, %rdi
movq %rbx, %rsi
callq 0x2a1f0
movq %r15, %rdi
movq %rbx, %rsi
callq 0x2a378
xorpd %xmm1, %xmm1
maxsd %xmm0, %xmm1
movsd 0x120(%r15), %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x120(%r15)
movq %r15, %rdi
movq %rbx, %rsi
movapd %xmm1, %xmm0
callq 0x2a720
jmp 0x2a086
movq 0x8(%r13), %rcx
movq -0x8(%rcx,%rax,8), %rbx
movq %r13, %rdi
movq %rbx, %rsi
callq 0x2a1f0
movq %r15, %rdi
movq %rbx, %rsi
callq 0x2a378
xorpd %xmm1, %xmm1
maxsd %xmm0, %xmm1
movsd 0x120(%r15), %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x120(%r15)
movq %r15, %rdi
movq %rbx, %rsi
movapd %xmm1, %xmm0
callq 0x2a720
movslq 0x14(%r13), %rax
testq %rax, %rax
jne 0x2a0e1
movq %r15, 0x18(%rbp)
movq %r15, 0x18(%r13)
movl 0x2c(%r15), %edx
movq %r14, %rdi
movq %rbp, %rsi
callq 0xc35c2
movl 0x2c(%r15), %edx
movq %r14, %rdi
movq %r13, %rsi
callq 0xc35c2
addq $0x178, %rsp            # imm = 0x178
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq %rax, %rbx
leaq 0x30(%rsp), %rdi
callq 0x88520
jmp 0x2a180
movq %rax, %rbx
leaq 0xd8(%rsp), %rdi
callq 0x88520
jmp 0x2a1ba
movq %rax, %rbx
movq (%rsp), %r12
movq 0x8(%rsp), %r13
jmp 0x2a1cf
movq %rax, %rbx
movq (%rsp), %r12
jmp 0x2a1d7
movq %rax, %rbx
jmp 0x2a1df
jmp 0x2a1b7
jmp 0x2a1b7
jmp 0x2a1b7
jmp 0x2a1b7
jmp 0x2a1b7
jmp 0x2a1b7
movq %rax, %rbx
movq (%rsp), %r12
movq 0x8(%rsp), %r13
addq $0x48, %r15
movq %r15, %rdi
callq 0x88520
movq %r13, %rdi
callq 0xc3596
movq %r14, %rdi
callq 0xc3596
movq %r12, %rdi
callq 0xc3596
movq %rbx, %rdi
callq 0x15ad0
nop