// File: /workspace/github_c_makefile_star2_O2/deplinenoise[P]tundra/src/TerminalIo.cpp
// Function: t2::TerminalIoEmit(int, int, int, char const*, int)
void TerminalIoEmit(int job_id, int is_stderr, int sort_key, const char *data, int len)
{
	int result;
	LineBuffer *buf = NULL;

  MutexLock(&s_LineLock);

	while (len > 0)
	{
		/* Wait for a line buffer to become available, or for the tty to become free. */
		for (;;)
		{
			/* If we already have the tty, or we can get it: break */
			if (-1 == s_PrintingJobIndex || job_id == s_PrintingJobIndex)
				break;

			/* If we can allocate a buffer: break */

			if (NULL != (buf = AllocLineBuffer()))
				break;

			/* Otherwise wait */
      CondWait(&s_CanPrint, &s_LineLock);
		}

		if (-1 == s_PrintingJobIndex)
		{
			/* Let this job own the output channel */
			TTY_PRINTF(("job %d is taking the tty\n", job_id));
			s_PrintingJobIndex = job_id;

			FlushOutputQueue(job_id);
		}
		else if (job_id != s_PrintingJobIndex)
		{
			assert(buf);
		}

		if (!buf)
		{
			/* This thread owns the TTY, so just print. We don't need to keep the
			 * mutex locked as this job will not finsh and reset the currently
			 * printing job until later. Releasing the mutex now means other
			 * threads can come in and buffer their data. */

			MutexUnlock(&s_LineLock);

			TTY_PRINTF(("copying %d bytes of data from job_id %d, stderr=%d, sort_key %d\n",
						len, job_id, is_stderr, sort_key));

			result = write(is_stderr ? STDERR_FILENO : STDOUT_FILENO, data, len);
			(void) result; /* tty disappeared; not fatal */
			return; /* finish the loop immediately */
		}
		else
		{
			/* We can't print this data as we don't own the TTY so we buffer it. */
			TTY_PRINTF(("buffering %d bytes of data from job_id %d, stderr=%d, sort_key %d\n",
						len, job_id, is_stderr, sort_key));

			/* PERF: Could release mutex around this memcpy, not sure if it's a win. */
			buf->m_JobId = job_id;
			buf->m_SortKey = sort_key;
			buf->m_Len = len > kLineBufSize - 1 ? kLineBufSize - 1 : len;
			buf->m_IsStderr = is_stderr;
			memcpy(buf->m_Data, data, buf->m_Len);
			buf->m_Data[buf->m_Len] = '\0';

			len -= buf->m_Len;
			data += buf->m_Len;

			/* Queue this line for output */
			s_QueuedLinebufs[s_QueuedLinebufCount++] = buf;
		}
	}

	MutexUnlock(&s_LineLock);

	return;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movl %r8d, %ebp
movq %rcx, 0x8(%rsp)
movl %edx, 0x14(%rsp)
movl %esi, 0x4(%rsp)
movl %edi, %r12d
leaq 0x8b9db(%rip), %r13     # 0x9dee8
movq %r13, %rdi
callq 0x549a
xorl %ebx, %ebx
leaq 0x8b9f2(%rip), %r14     # 0x9df10
leaq 0xb7bb(%rip), %r15      # 0x1dce0
testl %ebp, %ebp
jle 0x1262a
movl 0xae45(%rip), %eax      # 0x1d378
cmpl $-0x1, %eax
je 0x1257c
cmpl %r12d, %eax
je 0x1257c
movslq 0x8b99c(%rip), %rax     # 0x9dee0
movl 0x8b99a(%rip), %ecx     # 0x9dee4
addl %eax, %ecx
cmpl $0x40, %ecx
jne 0x12675
testl %eax, %eax
je 0x1256d
leaq -0x1(%rax), %rcx
movl %ecx, 0x8b97d(%rip)     # 0x9dee0
movq -0x8(%r15,%rax,8), %rbx
testq %rbx, %rbx
jne 0x125ae
movq %r14, %rdi
movq %r13, %rsi
callq 0x5549
xorl %ebx, %ebx
jmp 0x1252d
cmpl $-0x1, %eax
je 0x12596
cmpl %r12d, %eax
sete %al
testq %rbx, %rbx
setne %cl
orb %al, %cl
jne 0x125a5
jmp 0x12694
movl %r12d, 0xaddb(%rip)     # 0x1d378
movl %r12d, %edi
callq 0x126b3
testq %rbx, %rbx
je 0x12644
movl %r12d, (%rbx)
movl $0x1fff, %eax           # imm = 0x1FFF
cmpl %eax, %ebp
movl $0x1fff, %edx           # imm = 0x1FFF
cmovll %ebp, %edx
movl 0x14(%rsp), %eax
movl %eax, 0x4(%rbx)
movl %edx, 0xc(%rbx)
movl 0x4(%rsp), %eax
movl %eax, 0x8(%rbx)
movq 0x10(%rbx), %rdi
movl %ebp, %r15d
movq 0x8(%rsp), %rbp
movq %rbp, %rsi
callq 0x3290
movq 0x10(%rbx), %rax
movslq 0xc(%rbx), %rcx
movb $0x0, (%rax,%rcx)
movslq 0xc(%rbx), %rax
subl %eax, %r15d
addq %rax, %rbp
movq %rbp, 0x8(%rsp)
movl %r15d, %ebp
leaq 0xb6d6(%rip), %r15      # 0x1dce0
movslq 0x8b8d3(%rip), %rax     # 0x9dee4
leal 0x1(%rax), %ecx
movl %ecx, 0x8b8ca(%rip)     # 0x9dee4
leaq 0x8b91f(%rip), %rcx     # 0x9df40
movq %rbx, (%rcx,%rax,8)
jmp 0x12525
leaq 0x8b8b7(%rip), %rdi     # 0x9dee8
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
jmp 0x54b4
leaq 0x8b89d(%rip), %rdi     # 0x9dee8
callq 0x54b4
cmpl $0x1, 0x4(%rsp)
pushq $0x2
popq %rdi
sbbl $0x0, %edi
movl %ebp, %edx
movq 0x8(%rsp), %rsi
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
jmp 0x3120
leaq 0x2d80(%rip), %rdi      # 0x153fc
leaq 0x2d2c(%rip), %rsi      # 0x153af
leaq 0x2dad(%rip), %rcx      # 0x15437
movl $0x98, %edx
callq 0x3220
leaq 0x2d10(%rip), %rdi      # 0x153ab
leaq 0x2d0d(%rip), %rsi      # 0x153af
leaq 0x2d19(%rip), %rcx      # 0x153c2
movl $0x11c, %edx            # imm = 0x11C
callq 0x3220