// File: /workspace/github_cpp_makefile_star2_O1/rpavlik[P]edid-decode/parse-displayid-block.cpp
// Function: edid_state::parse_displayid_transfer_characteristics(unsigned char const*)
void edid_state::parse_displayid_transfer_characteristics(const unsigned char *x)
{
	check_displayid_datablock_revision(x[1], 0xf0, 1);

	unsigned xfer_id = x[1] >> 4;
	bool first_is_white = x[3] & 0x80;
	bool four_param = x[3] & 0x20;

	if (xfer_id) {
		printf("    Transfer Characteristics Data Block Identifier: %u\n", xfer_id);
		if (!(dispid.preparsed_color_ids & (1 << xfer_id)))
			fail("Missing Color Characteristics Data Block using Identifier %u.\n", xfer_id);
	}
	if (first_is_white)
		printf("    The first curve is the 'white' transfer characteristic\n");
	if (x[3] & 0x40)
		printf("    Individual response curves\n");

	unsigned offset = 4;
	unsigned len = x[2] - 1;

	for (unsigned i = 0; len; i++) {
		if ((x[3] & 0x80) && !i)
			printf("    White curve:      ");
		else
			printf("    Response curve #%u:",
			       i - first_is_white);
		unsigned samples = x[offset];
		if (four_param) {
			if (samples != 5)
				fail("Expected 5 samples.\n");
			printf(" A0=%u A1=%u A2=%u A3=%u Gamma=%.2f\n",
			       x[offset + 1], x[offset + 2], x[offset + 3], x[offset + 4],
			       (double)(x[offset + 5] + 100.0) / 100.0);
			samples++;
		} else {
			double sum = 0;

			// The spec is not very clear about the number of samples:
			// should this be interpreted as the actual number of
			// samples stored in this Data Block, or as the number of
			// samples in the curve, but where the last sample is not
			// actually stored since it is always 0x3ff.
			//
			// The ATP Manager interprets this as the latter, so that's
			// what we implement here.
			for (unsigned j = offset + 1; j < offset + samples; j++) {
				sum += x[j];
				printf(" %.2f", sum * 100.0 / 1023.0);
			}
			printf(" 100.00\n");
		}
		offset += samples;
		len -= samples;
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x28, %rsp
movq %rsi, %rbx
movq %rdi, %r14
movzbl 0x1(%rsi), %esi
movl $0xf0, %edx
movl $0x1, %ecx
callq 0x1627c
movzbl 0x1(%rbx), %ebp
movzbl 0x3(%rbx), %r15d
cmpl $0x10, %ebp
jb 0x1811d
shrl $0x4, %ebp
leaq 0x171a2(%rip), %rdi     # 0x2f297
movl %ebp, %esi
xorl %eax, %eax
callq 0x3030
movzwl 0x912(%r14), %eax
btl %ebp, %eax
jb 0x1811d
leaq 0x171bd(%rip), %rsi     # 0x2f2cf
xorl %edi, %edi
movl %ebp, %edx
xorl %eax, %eax
callq 0x37ec
testb %r15b, %r15b
jns 0x1812e
leaq 0x191b7(%rip), %rdi     # 0x312e0
callq 0x3380
testb $0x40, 0x3(%rbx)
je 0x18140
leaq 0x191e0(%rip), %rdi     # 0x3131b
callq 0x3380
movzbl 0x2(%rbx), %r14d
decl %r14d
je 0x182d0
movl %r15d, %eax
shrl $0x7, %eax
movl %eax, 0x4(%rsp)
movl $0x4, %ebp
xorl %r13d, %r13d
movq %rbx, 0x10(%rsp)
movl %r15d, 0x8(%rsp)
cmpb $0x0, 0x3(%rbx)
setns %al
testl %r13d, %r13d
setne %cl
orb %al, %cl
je 0x18192
movl %r13d, %esi
subl 0x4(%rsp), %esi
leaq 0x1719c(%rip), %rdi     # 0x2f325
xorl %eax, %eax
callq 0x3030
jmp 0x181a0
leaq 0x17175(%rip), %rdi     # 0x2f30e
xorl %eax, %eax
callq 0x3030
movl %ebp, %eax
movzbl (%rbx,%rax), %r12d
testb $0x20, %r15b
jne 0x1825f
movl %r14d, 0xc(%rsp)
movq %r12, 0x18(%rsp)
leal (%r12,%rbp), %ecx
leal 0x1(%rbp), %eax
cmpl %ecx, %eax
movsd 0x7e4c(%rip), %xmm1     # 0x20018
movsd 0x16434(%rip), %xmm2    # 0x2e608
leaq 0xd56f(%rip), %r12      # 0x2574a
jae 0x1823d
movl %eax, %ebx
addq 0x10(%rsp), %rbx
movl 0x18(%rsp), %r15d
decq %r15
xorpd %xmm3, %xmm3
xorl %r14d, %r14d
movzbl (%rbx,%r14), %eax
xorps %xmm0, %xmm0
cvtsi2sd %eax, %xmm0
addsd %xmm0, %xmm3
movsd %xmm3, 0x20(%rsp)
movapd %xmm3, %xmm0
mulsd %xmm1, %xmm0
divsd %xmm2, %xmm0
movq %r12, %rdi
movb $0x1, %al
callq 0x3030
movsd 0x20(%rsp), %xmm3
movsd 0x163db(%rip), %xmm2    # 0x2e608
movsd 0x7de3(%rip), %xmm1     # 0x20018
incq %r14
cmpl %r14d, %r15d
jne 0x181f3
leaq 0x190f6(%rip), %rdi     # 0x3133a
callq 0x3380
movq 0x10(%rsp), %rbx
movl 0x8(%rsp), %r15d
movl 0xc(%rsp), %r14d
movq 0x18(%rsp), %r12
jmp 0x182c1
cmpl $0x5, %r12d
je 0x18275
xorl %edi, %edi
leaq 0x170cf(%rip), %rsi     # 0x2f33d
xorl %eax, %eax
callq 0x37ec
leal 0x1(%rbp), %eax
movzbl (%rbx,%rax), %esi
leal 0x2(%rbp), %eax
movzbl (%rbx,%rax), %edx
leal 0x3(%rbp), %eax
movzbl (%rbx,%rax), %ecx
leal 0x4(%rbp), %eax
movzbl (%rbx,%rax), %r8d
leal 0x5(%rbp), %eax
movzbl (%rbx,%rax), %eax
xorps %xmm0, %xmm0
cvtsi2sd %eax, %xmm0
movsd 0x7d70(%rip), %xmm1     # 0x20018
addsd %xmm1, %xmm0
divsd %xmm1, %xmm0
leaq 0x1709b(%rip), %rdi     # 0x2f352
movb $0x1, %al
callq 0x3030
incl %r12d
addl %r12d, %ebp
incl %r13d
subl %r12d, %r14d
jne 0x1816a
addq $0x28, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
nop