// File: /workspace/github_c_makefile_star2_O0/CarlosLunaMota[P]BinaryTrees/BinaryTrees.c
// Function: rb_tree_union
rb_tree *rb_tree_union(const rb_tree *tree_1, const rb_tree *tree_2) {

    rb_tree *tree = NULL;
    rb_node *pred_1;
    rb_node *node_1;
    rb_node *pred_2;
    rb_node *node_2;
    void    *data;
    int      comp;

    // Sanity check:
    assert(tree_1 != NULL);
    assert(tree_2 != NULL);

    // Special case: Both trees are the same
    if (tree_1 == tree_2) { return rb_tree_copy(tree_1); }

    // Create a new tree:
    tree = new_rb_tree(tree_1->comp);
    if (tree == NULL) { return NULL; }

    // Go to the smallest element of tree_1 while right-threading your path:
    node_1 = tree_1->root;
    if (node_1 != NULL) {
        while (node_1->left != NULL) {
            pred_1 = node_1->left;
            while (pred_1->right != NULL) { pred_1 = pred_1->right; }
            pred_1->right = node_1;
            node_1        = node_1->left;
        }
    }

    // Go to the smallest element of tree_2 while right-threading your path:
    node_2 = tree_2->root;
    if (node_2 != NULL) {
        while (node_2->left != NULL) {
            pred_2 = node_2->left;
            while (pred_2->right != NULL) { pred_2 = pred_2->right; }
            pred_2->right = node_2;
            node_2        = node_2->left;
        }
    }

    // Until we have exhausted at least one of the trees:
    while (node_1 != NULL && node_2 != NULL) {

        // compare both nodes:
        comp = (tree->comp)(node_1->data, node_2->data);

        if (comp < 0) {

            // insert node_1->data in tree /////////////////////////////////////
            data = node_1->data;
            data = rb_tree_insert_max(tree, data);
            assert(data == NULL);
            ////////////////////////////////////////////////////////////////////

            // advance node_1 //////////////////////////////////////////////////
            node_1 = node_1->right;
            if (node_1 != NULL) {
                while (node_1->left != NULL) {
                    pred_1 = node_1->left;
                    while (pred_1->right != NULL && pred_1->right != node_1) {
                        pred_1 = pred_1->right;
                    }
                    if (pred_1->right == NULL) {
                        pred_1->right = node_1;
                        node_1        = node_1->left;
                    } else {
                        pred_1->right = NULL;
                        break;
                    }
                }
            }
            ////////////////////////////////////////////////////////////////////

        } else if (comp > 0) {

            // insert node_2->data in tree /////////////////////////////////////
            data = node_2->data;
            data = rb_tree_insert_max(tree, data);
            assert(data == NULL);
            ////////////////////////////////////////////////////////////////////

            // advance node_2 //////////////////////////////////////////////////
            node_2 = node_2->right;
            if (node_2 != NULL) {
                while (node_2->left != NULL) {
                    pred_2 = node_2->left;
                    while (pred_2->right != NULL && pred_2->right != node_2) {
                        pred_2 = pred_2->right;
                    }
                    if (pred_2->right == NULL) {
                        pred_2->right = node_2;
                        node_2        = node_2->left;
                    } else {
                        pred_2->right = NULL;
                        break;
                    }
                }
            }
            ////////////////////////////////////////////////////////////////////

        } else {

            // insert node_1->data in tree /////////////////////////////////////
            data = node_1->data;
            data = rb_tree_insert_max(tree, data);
            assert(data == NULL);
            ////////////////////////////////////////////////////////////////////

            // advance node_1 //////////////////////////////////////////////////
            node_1 = node_1->right;
            if (node_1 != NULL) {
                while (node_1->left != NULL) {
                    pred_1 = node_1->left;
                    while (pred_1->right != NULL && pred_1->right != node_1) {
                        pred_1 = pred_1->right;
                    }
                    if (pred_1->right == NULL) {
                        pred_1->right = node_1;
                        node_1        = node_1->left;
                    } else {
                        pred_1->right = NULL;
                        break;
                    }
                }
            }
            ////////////////////////////////////////////////////////////////////

            // advance node_2 //////////////////////////////////////////////////
            node_2 = node_2->right;
            if (node_2 != NULL) {
                while (node_2->left != NULL) {
                    pred_2 = node_2->left;
                    while (pred_2->right != NULL && pred_2->right != node_2) {
                        pred_2 = pred_2->right;
                    }
                    if (pred_2->right == NULL) {
                        pred_2->right = node_2;
                        node_2        = node_2->left;
                    } else {
                        pred_2->right = NULL;
                        break;
                    }
                }
            }
            ////////////////////////////////////////////////////////////////////
        }
    }

    // Insert all remaining data from tree_1:
    while (node_1 != NULL) {

        // insert node_1->data in tree /////////////////////////////////////////
        data = node_1->data;
        data = rb_tree_insert_max(tree, data);
        assert(data == NULL);
        ////////////////////////////////////////////////////////////////////////

        // advance node_1 //////////////////////////////////////////////////////
        node_1 = node_1->right;
        if (node_1 != NULL) {
            while (node_1->left != NULL) {
                pred_1 = node_1->left;
                while (pred_1->right != NULL && pred_1->right != node_1) {
                    pred_1 = pred_1->right;
                }
                if (pred_1->right == NULL) {
                    pred_1->right = node_1;
                    node_1        = node_1->left;
                } else {
                    pred_1->right = NULL;
                    break;
                }
            }
        }
        ////////////////////////////////////////////////////////////////////////
    }

    // Insert all remaining data from tree_2:
    while (node_2 != NULL) {

        // insert node_2->data in tree /////////////////////////////////////////
        data = node_2->data;
        data = rb_tree_insert_max(tree, data);
        assert(data == NULL);
        ////////////////////////////////////////////////////////////////////////

        // advance node_2 //////////////////////////////////////////////////////
        node_2 = node_2->right;
        if (node_2 != NULL) {
            while (node_2->left != NULL) {
                pred_2 = node_2->left;
                while (pred_2->right != NULL && pred_2->right != node_2) {
                    pred_2 = pred_2->right;
                }
                if (pred_2->right == NULL) {
                    pred_2->right = node_2;
                    node_2        = node_2->left;
                } else {
                    pred_2->right = NULL;
                    break;
                }
            }
        }
        ////////////////////////////////////////////////////////////////////////
    }

    // Return the resulting tree:
    return tree;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x60, %rsp
movq %rdi, -0x10(%rbp)
movq %rsi, -0x18(%rbp)
movq $0x0, -0x20(%rbp)
cmpq $0x0, -0x10(%rbp)
je 0x120b1
jmp 0x120d0
leaq 0x444d(%rip), %rdi      # 0x16505
leaq 0x413d(%rip), %rsi      # 0x161fc
movl $0xd58, %edx            # imm = 0xD58
leaq 0x48ed(%rip), %rcx      # 0x169b8
callq 0x1060
cmpq $0x0, -0x18(%rbp)
je 0x120d9
jmp 0x120f8
leaq 0x446d(%rip), %rdi      # 0x1654d
leaq 0x4115(%rip), %rsi      # 0x161fc
movl $0xd59, %edx            # imm = 0xD59
leaq 0x48c5(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x10(%rbp), %rax
cmpq -0x18(%rbp), %rax
jne 0x12114
movq -0x10(%rbp), %rdi
callq 0xfed0
movq %rax, -0x8(%rbp)
jmp 0x127b2
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
callq 0xfe40
movq %rax, -0x20(%rbp)
cmpq $0x0, -0x20(%rbp)
jne 0x12139
movq $0x0, -0x8(%rbp)
jmp 0x127b2
movq -0x10(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x30(%rbp)
cmpq $0x0, -0x30(%rbp)
je 0x12199
jmp 0x1214d
movq -0x30(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x12197
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rax
cmpq $0x0, 0x10(%rax)
je 0x1217d
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x28(%rbp)
jmp 0x12164
movq -0x30(%rbp), %rcx
movq -0x28(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x30(%rbp)
jmp 0x1214d
jmp 0x12199
movq -0x18(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x40(%rbp)
cmpq $0x0, -0x40(%rbp)
je 0x121f9
jmp 0x121ad
movq -0x40(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x121f7
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x38(%rbp)
movq -0x38(%rbp), %rax
cmpq $0x0, 0x10(%rax)
je 0x121dd
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x38(%rbp)
jmp 0x121c4
movq -0x40(%rbp), %rcx
movq -0x38(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x40(%rbp)
jmp 0x121ad
jmp 0x121f9
jmp 0x121fb
xorl %eax, %eax
cmpq $0x0, -0x30(%rbp)
movb %al, -0x4d(%rbp)
je 0x12212
cmpq $0x0, -0x40(%rbp)
setne %al
movb %al, -0x4d(%rbp)
movb -0x4d(%rbp), %al
testb $0x1, %al
jne 0x1221e
jmp 0x125b8
movq -0x20(%rbp), %rax
movq 0x8(%rax), %rax
movq -0x30(%rbp), %rcx
movq (%rcx), %rdi
movq -0x40(%rbp), %rcx
movq (%rcx), %rsi
callq *%rax
movl %eax, -0x4c(%rbp)
cmpl $0x0, -0x4c(%rbp)
jge 0x1232f
movq -0x30(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x48(%rbp)
movq -0x20(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x100a0
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jne 0x12268
jmp 0x12287
leaq 0x44ea(%rip), %rdi      # 0x16759
leaq 0x3f86(%rip), %rsi      # 0x161fc
movl $0xd83, %edx            # imm = 0xD83
leaq 0x4736(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x30(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x30(%rbp)
cmpq $0x0, -0x30(%rbp)
je 0x1232a
jmp 0x122a0
movq -0x30(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x12328
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x4e(%rbp)
je 0x122d9
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x30(%rbp), %rax
setne %al
movb %al, -0x4e(%rbp)
movb -0x4e(%rbp), %al
testb $0x1, %al
jne 0x122e2
jmp 0x122f0
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x28(%rbp)
jmp 0x122b7
movq -0x28(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x12315
movq -0x30(%rbp), %rcx
movq -0x28(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x30(%rbp)
jmp 0x12323
movq -0x28(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x12328
jmp 0x122a0
jmp 0x1232a
jmp 0x125b3
cmpl $0x0, -0x4c(%rbp)
jle 0x12425
movq -0x40(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x48(%rbp)
movq -0x20(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x100a0
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jne 0x1235e
jmp 0x1237d
leaq 0x43f4(%rip), %rdi      # 0x16759
leaq 0x3e90(%rip), %rsi      # 0x161fc
movl $0xd9e, %edx            # imm = 0xD9E
leaq 0x4640(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x40(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x40(%rbp)
cmpq $0x0, -0x40(%rbp)
je 0x12420
jmp 0x12396
movq -0x40(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x1241e
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x38(%rbp)
movq -0x38(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x4f(%rbp)
je 0x123cf
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x40(%rbp), %rax
setne %al
movb %al, -0x4f(%rbp)
movb -0x4f(%rbp), %al
testb $0x1, %al
jne 0x123d8
jmp 0x123e6
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x38(%rbp)
jmp 0x123ad
movq -0x38(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x1240b
movq -0x40(%rbp), %rcx
movq -0x38(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x40(%rbp)
jmp 0x12419
movq -0x38(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x1241e
jmp 0x12396
jmp 0x12420
jmp 0x125b1
movq -0x30(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x48(%rbp)
movq -0x20(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x100a0
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jne 0x1244a
jmp 0x12469
leaq 0x4308(%rip), %rdi      # 0x16759
leaq 0x3da4(%rip), %rsi      # 0x161fc
movl $0xdb9, %edx            # imm = 0xDB9
leaq 0x4554(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x30(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x30(%rbp)
cmpq $0x0, -0x30(%rbp)
je 0x1250c
jmp 0x12482
movq -0x30(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x1250a
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x50(%rbp)
je 0x124bb
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x30(%rbp), %rax
setne %al
movb %al, -0x50(%rbp)
movb -0x50(%rbp), %al
testb $0x1, %al
jne 0x124c4
jmp 0x124d2
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x28(%rbp)
jmp 0x12499
movq -0x28(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x124f7
movq -0x30(%rbp), %rcx
movq -0x28(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x30(%rbp)
jmp 0x12505
movq -0x28(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x1250a
jmp 0x12482
jmp 0x1250c
movq -0x40(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x40(%rbp)
cmpq $0x0, -0x40(%rbp)
je 0x125af
jmp 0x12525
movq -0x40(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x125ad
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x38(%rbp)
movq -0x38(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x51(%rbp)
je 0x1255e
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x40(%rbp), %rax
setne %al
movb %al, -0x51(%rbp)
movb -0x51(%rbp), %al
testb $0x1, %al
jne 0x12567
jmp 0x12575
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x38(%rbp)
jmp 0x1253c
movq -0x38(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x1259a
movq -0x40(%rbp), %rcx
movq -0x38(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x40(%rbp)
jmp 0x125a8
movq -0x38(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x125ad
jmp 0x12525
jmp 0x125af
jmp 0x125b1
jmp 0x125b3
jmp 0x121fb
jmp 0x125ba
cmpq $0x0, -0x30(%rbp)
je 0x126b1
movq -0x30(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x48(%rbp)
movq -0x20(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x100a0
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jne 0x125ea
jmp 0x12609
leaq 0x4168(%rip), %rdi      # 0x16759
leaq 0x3c04(%rip), %rsi      # 0x161fc
movl $0xdea, %edx            # imm = 0xDEA
leaq 0x43b4(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x30(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x30(%rbp)
cmpq $0x0, -0x30(%rbp)
je 0x126ac
jmp 0x12622
movq -0x30(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x126aa
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x52(%rbp)
je 0x1265b
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x30(%rbp), %rax
setne %al
movb %al, -0x52(%rbp)
movb -0x52(%rbp), %al
testb $0x1, %al
jne 0x12664
jmp 0x12672
movq -0x28(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x28(%rbp)
jmp 0x12639
movq -0x28(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x12697
movq -0x30(%rbp), %rcx
movq -0x28(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x30(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x30(%rbp)
jmp 0x126a5
movq -0x28(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x126aa
jmp 0x12622
jmp 0x126ac
jmp 0x125ba
jmp 0x126b3
cmpq $0x0, -0x40(%rbp)
je 0x127aa
movq -0x40(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x48(%rbp)
movq -0x20(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x100a0
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jne 0x126e3
jmp 0x12702
leaq 0x406f(%rip), %rdi      # 0x16759
leaq 0x3b0b(%rip), %rsi      # 0x161fc
movl $0xe07, %edx            # imm = 0xE07
leaq 0x42bb(%rip), %rcx      # 0x169b8
callq 0x1060
movq -0x40(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x40(%rbp)
cmpq $0x0, -0x40(%rbp)
je 0x127a5
jmp 0x1271b
movq -0x40(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x127a3
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x38(%rbp)
movq -0x38(%rbp), %rcx
xorl %eax, %eax
cmpq $0x0, 0x10(%rcx)
movb %al, -0x53(%rbp)
je 0x12754
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
cmpq -0x40(%rbp), %rax
setne %al
movb %al, -0x53(%rbp)
movb -0x53(%rbp), %al
testb $0x1, %al
jne 0x1275d
jmp 0x1276b
movq -0x38(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x38(%rbp)
jmp 0x12732
movq -0x38(%rbp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x12790
movq -0x40(%rbp), %rcx
movq -0x38(%rbp), %rax
movq %rcx, 0x10(%rax)
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq %rax, -0x40(%rbp)
jmp 0x1279e
movq -0x38(%rbp), %rax
movq $0x0, 0x10(%rax)
jmp 0x127a3
jmp 0x1271b
jmp 0x127a5
jmp 0x126b3
movq -0x20(%rbp), %rax
movq %rax, -0x8(%rbp)
movq -0x8(%rbp), %rax
addq $0x60, %rsp
popq %rbp
retq
nopl (%rax)