// File: /workspace/github_c_makefile_star2_O0/chatziko-k08[P]lecture-code/programs/set_example/../../modules/UsingAVL/ADTSet.c
// Function: node_is_avl
bool node_is_avl(SetNode node, CompareFunc compare) {
	if (node == NULL)
		return true;

	// Ελέγχουμε την ιδιότητα:
	// κάθε κόμβος είναι > αριστερό παιδί, > δεξιότερο κόμβο του αριστερού υποδέντρου, < δεξί παιδί, < αριστερότερο κόμβο του δεξιού υποδέντρου.
	// Είναι ισοδύναμη με την BST ιδιότητα (κάθε κόμβος είναι > αριστερό υποδέντρο και < δεξί υποδέντρο) αλλά ευκολότερο να ελεγθεί.
	bool res = true;
	if(node->left != NULL)
		res = res && compare(node->left->value, node->value) < 0 && compare(node_find_max(node->left)->value, node->value) < 0;
	if(node->right != NULL)
		res = res && compare(node->right->value, node->value) > 0 && compare(node_find_min(node->right)->value, node->value) > 0;

	// Το ύψος είναι σωστό
	res = res && node->height == 1 + int_max(node_height(node->left), node_height(node->right));

	// Ο κόμβος έχει την AVL ιδιότητα
	int balance = node_balance(node);
	res = res && balance >= -1 && balance <= 1;

	// Τα υποδέντρα είναι σωστά
	res = res &&
		node_is_avl(node->left, compare) &&
		node_is_avl(node->right, compare);

	return res;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x50, %rsp
movq %rdi, -0x10(%rbp)
movq %rsi, -0x18(%rbp)
cmpq $0x0, -0x10(%rbp)
jne 0x6500
movb $0x1, -0x1(%rbp)
jmp 0x66c3
movb $0x1, -0x19(%rbp)
movq -0x10(%rbp), %rax
cmpq $0x0, (%rax)
je 0x6578
xorl %eax, %eax
testb $0x1, -0x19(%rbp)
movb %al, -0x21(%rbp)
je 0x6570
movq -0x18(%rbp), %rax
movq -0x10(%rbp), %rcx
movq (%rcx), %rcx
movq 0x10(%rcx), %rdi
movq -0x10(%rbp), %rcx
movq 0x10(%rcx), %rsi
callq *%rax
movl %eax, %ecx
xorl %eax, %eax
cmpl $0x0, %ecx
movb %al, -0x21(%rbp)
jge 0x6570
movq -0x18(%rbp), %rax
movq %rax, -0x30(%rbp)
movq -0x10(%rbp), %rax
movq (%rax), %rdi
callq 0x6280
movq %rax, %rcx
movq -0x30(%rbp), %rax
movq 0x10(%rcx), %rdi
movq -0x10(%rbp), %rcx
movq 0x10(%rcx), %rsi
callq *%rax
cmpl $0x0, %eax
setl %al
movb %al, -0x21(%rbp)
movb -0x21(%rbp), %al
andb $0x1, %al
movb %al, -0x19(%rbp)
movq -0x10(%rbp), %rax
cmpq $0x0, 0x8(%rax)
je 0x65ef
xorl %eax, %eax
testb $0x1, -0x19(%rbp)
movb %al, -0x31(%rbp)
je 0x65e7
movq -0x18(%rbp), %rax
movq -0x10(%rbp), %rcx
movq 0x8(%rcx), %rcx
movq 0x10(%rcx), %rdi
movq -0x10(%rbp), %rcx
movq 0x10(%rcx), %rsi
callq *%rax
movl %eax, %ecx
xorl %eax, %eax
cmpl $0x0, %ecx
movb %al, -0x31(%rbp)
jle 0x65e7
movq -0x18(%rbp), %rax
movq %rax, -0x40(%rbp)
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
callq 0x6210
movq %rax, %rcx
movq -0x40(%rbp), %rax
movq 0x10(%rcx), %rdi
movq -0x10(%rbp), %rcx
movq 0x10(%rcx), %rsi
callq *%rax
cmpl $0x0, %eax
setg %al
movb %al, -0x31(%rbp)
movb -0x31(%rbp), %al
andb $0x1, %al
movb %al, -0x19(%rbp)
xorl %eax, %eax
testb $0x1, -0x19(%rbp)
movb %al, -0x41(%rbp)
je 0x663a
movq -0x10(%rbp), %rax
movl 0x18(%rax), %eax
movl %eax, -0x48(%rbp)
movq -0x10(%rbp), %rax
movq (%rax), %rdi
callq 0x6700
movl %eax, -0x4c(%rbp)
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
callq 0x6700
movl -0x4c(%rbp), %edi
movl %eax, %esi
callq 0x66d0
movl %eax, %ecx
movl -0x48(%rbp), %eax
addl $0x1, %ecx
cmpl %ecx, %eax
sete %al
movb %al, -0x41(%rbp)
movb -0x41(%rbp), %al
andb $0x1, %al
movb %al, -0x19(%rbp)
movq -0x10(%rbp), %rdi
callq 0x6730
movl %eax, -0x20(%rbp)
xorl %eax, %eax
testb $0x1, -0x19(%rbp)
movb %al, -0x4d(%rbp)
je 0x666e
xorl %eax, %eax
cmpl $-0x1, -0x20(%rbp)
movb %al, -0x4d(%rbp)
jl 0x666e
cmpl $0x1, -0x20(%rbp)
setle %al
movb %al, -0x4d(%rbp)
movb -0x4d(%rbp), %al
andb $0x1, %al
movb %al, -0x19(%rbp)
xorl %eax, %eax
testb $0x1, -0x19(%rbp)
movb %al, -0x4e(%rbp)
je 0x66b3
movq -0x10(%rbp), %rax
movq (%rax), %rdi
movq -0x18(%rbp), %rsi
callq 0x64e0
movb %al, %cl
xorl %eax, %eax
testb $0x1, %cl
movb %al, -0x4e(%rbp)
jne 0x669f
jmp 0x66b3
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
movq -0x18(%rbp), %rsi
callq 0x64e0
movb %al, -0x4e(%rbp)
movb -0x4e(%rbp), %al
andb $0x1, %al
movb %al, -0x19(%rbp)
movb -0x19(%rbp), %al
andb $0x1, %al
movb %al, -0x1(%rbp)
movb -0x1(%rbp), %al
andb $0x1, %al
addq $0x50, %rsp
popq %rbp
retq
nop