// File: /workspace/github_c_makefile_star2_O2/haxlang[P]hax/haxParse.c
// Function: Hax_ParseVar
char *
Hax_ParseVar(
    Hax_Interp *interp,			/* Context for looking up variable. */
    char *string,		/* String containing variable name.
					 * First character must be "$". */
    char **termPtr			/* If non-NULL, points to word to fill
					 * in with character just after last
					 * one in the variable specifier. */)
{
    Interp *iPtr = (Interp *) interp;
    Hax_Memoryp *memoryp = iPtr->memoryp;
    char *name1, *name1End, c, *result;
    char *name2;
#define NUM_CHARS 200
    char copyStorage[NUM_CHARS];
    ParseValue pv;
    const char *ellipsis = "";		/* Used in setting errorInfo variable;
					 * set to "..." to indicate that not
					 * all of offending command is included
					 * in errorInfo.  "" means that the
					 * command is all there. */

    /*
     * There are three cases:
     * 1. The $ sign is followed by an open curly brace.  Then the variable
     *    name is everything up to the next close curly brace, and the
     *    variable is a scalar variable.
     * 2. The $ sign is not followed by an open curly brace.  Then the
     *    variable name is everything up to the next character that isn't
     *    a letter, digit, or underscore.  If the following character is an
     *    open parenthesis, then the information between parentheses is
     *    the array element name, which can include any of the substitutions
     *    permissible between quotes.
     * 3. The $ sign is followed by something that isn't a letter, digit,
     *    or underscore:  in this case, there is no variable name, and "$"
     *    is returned.
     */

    name2 = NULL;
    string++;
    if (*string == '{') {
	string++;
	name1 = string;
	while (*string != '}') {
	    if (*string == 0) {
		Hax_SetResult(interp,
			(char *) "missing close-brace for variable name",
			HAX_STATIC);
		if (termPtr != 0) {
		    *termPtr = string;
		}
		return NULL;
	    }
	    string++;
	}
	name1End = string;
	string++;
    } else {
	name1 = string;
	while (isalnum(*string) || (*string == '_')) {
	    string++;
	}
	if (string == name1) {
	    if (termPtr != 0) {
		*termPtr = string;
	    }
	    return (char *) "$";
	}
	name1End = string;
	if (*string == '(') {
	    char *end;

	    /*
	     * Perform substitutions on the array element name, just as
	     * is done for quotes.
	     */

	    pv.buffer = pv.next = copyStorage;
	    pv.end = copyStorage + NUM_CHARS - 1;
	    pv.expandProc = HaxExpandParseValue;
	    pv.clientData = (ClientData) NULL;
	    if (HaxParseQuotes(interp, string+1, ')', 0, &end, &pv)
		    != HAX_OK) {
		char msg[100];
		int n = (int) (string - name1);
		if (n > sizeof(msg)) {
			n = sizeof(msg);
			ellipsis = " ...";
		}
		sprintf(msg, "\n    (parsing index for array \"%.*s%s\")",
			n, name1, ellipsis);
		Hax_AddErrorInfo(interp, msg);
		result = NULL;
		name2 = pv.buffer;
		if (termPtr != 0) {
		    *termPtr = end;
		}
		goto done;
	    }
	    string = end;
	    name2 = pv.buffer;
	}
    }
    if (termPtr != 0) {
	*termPtr = string;
    }

    if (((Interp *) interp)->noEval) {
	return (char *) "";
    }
    c = *name1End;
    *name1End = 0;
    result = Hax_GetVar2(interp, name1, name2, HAX_LEAVE_ERR_MSG);
    *name1End = c;

    done:
    if ((name2 != NULL) && (pv.buffer != copyStorage)) {
	ckfree(memoryp, pv.buffer);
    }
    return result;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x178, %rsp            # imm = 0x178
movq %rdx, %r14
movq %rsi, %r12
movq %rdi, %r15
movq 0x280(%rdi), %rbp
cmpb $0x7b, 0x1(%rsi)
jne 0xe795
addq $0x2, %r12
movq %r12, %rbx
movzbl (%rbx), %eax
cmpl $0x7d, %eax
je 0xe8b9
testl %eax, %eax
je 0xe891
incq %rbx
jmp 0xe77c
leaq 0x1(%r12), %rax
movq %rax, (%rsp)
callq 0x4660
movq (%rax), %rax
incq %r12
pushq $0x1
popq %rbx
movsbq (%r12), %rcx
incq %r12
decq %rbx
cmpq $0x5f, %rcx
je 0xe7ac
movzwl (%rax,%rcx,2), %edx
andl $0x8, %edx
jne 0xe7ac
leaq -0x1(%r12), %r13
testq %rbx, %rbx
je 0xe8c6
cmpb $0x28, %cl
movq %rbp, 0x8(%rsp)
jne 0xe8de
leaq 0x40(%rsp), %rax
leaq 0x18(%rsp), %r9
movq %rax, 0x8(%r9)
movq %rax, (%r9)
leaq 0x107(%rsp), %rax
movq %rax, 0x10(%r9)
movq 0xc7d2(%rip), %rax      # 0x1afd8
movq %rax, 0x18(%r9)
andq $0x0, 0x20(%r9)
pushq $0x29
popq %rdx
leaq 0x10(%rsp), %r8
movq %r15, %rdi
movq %r12, %rsi
xorl %ecx, %ecx
callq 0x4490
testl %eax, %eax
je 0xe8e9
negl %ebx
cmpl $0x65, %ebx
leaq 0x4ade(%rip), %rax      # 0x13316
leaq 0x63c8(%rip), %r8       # 0x14c07
cmovaeq %rax, %r8
cmpl $0x64, %ebx
pushq $0x64
popq %rdx
cmovbl %ebx, %edx
leaq 0x668f(%rip), %rsi      # 0x14ee2
leaq 0x110(%rsp), %r12
movq %r12, %rdi
movq (%rsp), %rcx
xorl %eax, %eax
callq 0x45f0
movq %r15, %rdi
movq %r12, %rsi
callq 0x4420
testq %r14, %r14
je 0xe881
movq 0x10(%rsp), %rax
movq %rax, (%r14)
movq 0x18(%rsp), %rsi
xorl %r12d, %r12d
movq %rsi, %rbp
jmp 0xe939
leaq 0x6622(%rip), %rsi      # 0x14eba
xorl %r12d, %r12d
movq %r15, %rdi
xorl %edx, %edx
callq 0x4500
testq %r14, %r14
je 0xe967
movq %rbx, (%r14)
xorl %r12d, %r12d
jmp 0xe967
movq %rbp, 0x8(%rsp)
leaq 0x1(%rbx), %r13
xorl %ebp, %ebp
jmp 0xe8fa
leaq 0x6613(%rip), %r12      # 0x14ee0
testq %r14, %r14
je 0xe967
movq %r13, (%r14)
jmp 0xe967
xorl %ebp, %ebp
movq (%rsp), %r12
movq %r13, %rbx
jmp 0xe8fa
movq %r13, %rbx
movq 0x10(%rsp), %r13
movq 0x18(%rsp), %rbp
movq (%rsp), %r12
testq %r14, %r14
je 0xe902
movq %r13, (%r14)
cmpl $0x0, 0x194(%r15)
je 0xe915
leaq 0x62f4(%rip), %r12      # 0x14c07
jmp 0xe967
movb (%rbx), %r14b
movb $0x0, (%rbx)
movq %r15, %rdi
movq %r12, %rsi
movq %rbp, %rdx
movl $0x200, %ecx            # imm = 0x200
callq 0x44c0
movq %rax, %r12
movb %r14b, (%rbx)
movq 0x18(%rsp), %rsi
testq %rbp, %rbp
setne %al
leaq 0x40(%rsp), %rcx
cmpq %rcx, %rsi
setne %cl
andb %al, %cl
cmpb $0x1, %cl
jne 0xe967
leaq 0x64e7(%rip), %rdx      # 0x14e3f
movq 0x8(%rsp), %rdi
movl $0x4c2, %ecx            # imm = 0x4C2
callq 0x4280
movq %r12, %rax
addq $0x178, %rsp            # imm = 0x178
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq