// File: /workspace/github_cpp_makefile_star2_O1/codebrainz[P]libutfxx/utf/utf.cxx
// Function: ConvertUTF8toUTF16
ConversionResult ConvertUTF8toUTF16 (
	const UTF8** sourceStart, const UTF8* sourceEnd,
	UTF16** targetStart, UTF16* targetEnd, ConversionFlags flags) {
	ConversionResult result = conversionOK;
	const UTF8* source = *sourceStart;
	UTF16* target = *targetStart;
	while (source < sourceEnd) {
	UTF32 ch = 0;
	unsigned short extraBytesToRead = trailingBytesForUTF8[*source];
	if (source + extraBytesToRead >= sourceEnd) {
		result = sourceExhausted; break;
	}
	/* Do this check whether lenient or strict */
	if (! isLegalUTF8(source, extraBytesToRead+1)) {
		result = sourceIllegal;
		break;
	}
	/*
	 * The cases all fall through. See "Note A" below.
	 */
	switch (extraBytesToRead) {
		case 5: ch += *source++; ch <<= 6; /* remember, illegal UTF-8 */
		case 4: ch += *source++; ch <<= 6; /* remember, illegal UTF-8 */
		case 3: ch += *source++; ch <<= 6;
		case 2: ch += *source++; ch <<= 6;
		case 1: ch += *source++; ch <<= 6;
		case 0: ch += *source++;
	}
	ch -= offsetsFromUTF8[extraBytesToRead];

	if (target >= targetEnd) {
		source -= (extraBytesToRead+1); /* Back up source pointer! */
		result = targetExhausted; break;
	}
	if (ch <= UNI_MAX_BMP) { /* Target is a character <= 0xFFFF */
		/* UTF-16 surrogate values are illegal in UTF-32 */
		if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END) {
		if (flags == strictConversion) {
			source -= (extraBytesToRead+1); /* return to the illegal value itself */
			result = sourceIllegal;
			break;
		} else {
			*target++ = UNI_REPLACEMENT_CHAR;
		}
		} else {
		*target++ = (UTF16)ch; /* normal case */
		}
	} else if (ch > UNI_MAX_UTF16) {
		if (flags == strictConversion) {
		result = sourceIllegal;
		source -= (extraBytesToRead+1); /* return to the start */
		break; /* Bail out; shouldn't continue */
		} else {
		*target++ = UNI_REPLACEMENT_CHAR;
		}
	} else {
		/* target is a character in range 0xFFFF - 0x10FFFF. */
		if (target + 1 >= targetEnd) {
		source -= (extraBytesToRead+1); /* Back up source pointer! */
		result = targetExhausted; break;
		}
		ch -= halfBase;
		*target++ = (UTF16)((ch >> halfShift) + UNI_SUR_HIGH_START);
		*target++ = (UTF16)((ch & halfMask) + UNI_SUR_LOW_START);
	}
	}
	*sourceStart = source;
	*targetStart = target;
	return result;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
movq (%rdi), %r9
movq (%rdx), %r10
xorl %ebp, %ebp
leaq 0x28d1(%rip), %r11      # 0x6060
leaq 0x287a(%rip), %r14      # 0x6010
cmpq %rsi, %r9
jae 0x390a
movsbq (%r9), %r13
movsbl (%r13,%r11), %eax
movzwl %ax, %r12d
leaq (%r9,%r12), %rax
cmpq %rsi, %rax
jae 0x3803
movzbl %r12b, %ebx
movl $0x3, %eax
testb %r12b, %r12b
je 0x3854
cmpl $0x1, %ebx
jne 0x38f2
xorl %r15d, %r15d
cmpb $-0xc, %r13b
je 0x37ea
movzbl %r13b, %ebx
cmpl $0xed, %ebx
jne 0x38f5
cmpb $0x5, %r12b
ja 0x385e
movzbl %r12b, %ebx
movslq (%r14,%rbx,4), %rbx
addq %r14, %rbx
jmpq *%rbx
movzbl %r12b, %ebx
jmp 0x3854
movl $0x1, %eax
jmp 0x38f2
incq %r9
shll $0x6, %r13d
movl %r13d, %r15d
movsbl (%r9), %ebx
incq %r9
addl %r15d, %ebx
shll $0x6, %ebx
movl %ebx, %r15d
movsbl (%r9), %ebx
incq %r9
addl %r15d, %ebx
shll $0x6, %ebx
movl %ebx, %r15d
movsbl (%r9), %ebx
incq %r9
addl %r15d, %ebx
shll $0x6, %ebx
movl %ebx, %r15d
movsbl (%r9), %ebx
incq %r9
addl %r15d, %ebx
shll $0x6, %ebx
movsbl (%r9), %r15d
incq %r9
addl %ebx, %r15d
leal 0x1(%r12), %r13d
cmpq %rcx, %r10
jae 0x38e7
leaq 0x28f1(%rip), %rbx      # 0x6160
subl (%rbx,%r12,4), %r15d
cmpl $0xffff, %r15d          # imm = 0xFFFF
ja 0x3893
movl %r15d, %ebx
andl $0xf800, %ebx           # imm = 0xF800
cmpl $0xd800, %ebx           # imm = 0xD800
je 0x389c
movw %r15w, (%r10)
jmp 0x38a7
cmpl $0x110000, %r15d        # imm = 0x110000
jb 0x38b2
testl %r8d, %r8d
je 0x3902
movw $0xfffd, (%r10)         # imm = 0xFFFD
addq $0x2, %r10
movb $0x1, %r15b
movl %ebp, %eax
jmp 0x38f5
leaq 0x2(%r10), %rax
cmpq %rcx, %rax
jae 0x38e7
leal 0x3ff0000(%r15), %eax
shrl $0xa, %eax
addl $0xffffd800, %eax       # imm = 0xFFFFD800
movw %ax, (%r10)
andl $0x3ff, %r15d           # imm = 0x3FF
orl $0xdc00, %r15d          # imm = 0xDC00
movw %r15w, 0x2(%r10)
addq $0x4, %r10
jmp 0x38ab
movl %r13d, %eax
subq %rax, %r9
movl $0x2, %eax
xorl %r15d, %r15d
movl %eax, %ebp
testb %r15b, %r15b
jne 0x3796
jmp 0x390c
movl %r13d, %ebx
subq %rbx, %r9
jmp 0x38f2
movl %ebp, %eax
movq %r9, (%rdi)
movq %r10, (%rdx)
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq