// File: /workspace/github_c_makefile_star2_O3/genometools[P]genometools/src/external/sqlite-3.33.0/sqlite3.c
// Function: sqlite3ConnectionUnlocked
SQLITE_PRIVATE void sqlite3ConnectionUnlocked(sqlite3 *db){
  void (*xUnlockNotify)(void **, int) = 0; /* Unlock-notify cb to invoke */
  int nArg = 0;                            /* Number of entries in aArg[] */
  sqlite3 **pp;                            /* Iterator variable */
  void **aArg;               /* Arguments to the unlock callback */
  void **aDyn = 0;           /* Dynamically allocated space for aArg[] */
  void *aStatic[16];         /* Starter space for aArg[].  No malloc required */

  aArg = aStatic;
  enterMutex();         /* Enter STATIC_MAIN mutex */

  /* This loop runs once for each entry in the blocked-connections list. */
  for(pp=&sqlite3BlockedList; *pp; /* no-op */ ){
    sqlite3 *p = *pp;

    /* Step 1. */
    if( p->pBlockingConnection==db ){
      p->pBlockingConnection = 0;
    }

    /* Step 2. */
    if( p->pUnlockConnection==db ){
      assert( p->xUnlockNotify );
      if( p->xUnlockNotify!=xUnlockNotify && nArg!=0 ){
        xUnlockNotify(aArg, nArg);
        nArg = 0;
      }

      sqlite3BeginBenignMalloc();
      assert( aArg==aDyn || (aDyn==0 && aArg==aStatic) );
      assert( nArg<=(int)ArraySize(aStatic) || aArg==aDyn );
      if( (!aDyn && nArg==(int)ArraySize(aStatic))
       || (aDyn && nArg==(int)(sqlite3MallocSize(aDyn)/sizeof(void*)))
      ){
        /* The aArg[] array needs to grow. */
        void **pNew = (void **)sqlite3Malloc(nArg*sizeof(void *)*2);
        if( pNew ){
          memcpy(pNew, aArg, nArg*sizeof(void *));
          sqlite3_free(aDyn);
          aDyn = aArg = pNew;
        }else{
          /* This occurs when the array of context pointers that need to
          ** be passed to the unlock-notify callback is larger than the
          ** aStatic[] array allocated on the stack and the attempt to
          ** allocate a larger array from the heap has failed.
          **
          ** This is a difficult situation to handle. Returning an error
          ** code to the caller is insufficient, as even if an error code
          ** is returned the transaction on connection db will still be
          ** closed and the unlock-notify callbacks on blocked connections
          ** will go unissued. This might cause the application to wait
          ** indefinitely for an unlock-notify callback that will never
          ** arrive.
          **
          ** Instead, invoke the unlock-notify callback with the context
          ** array already accumulated. We can then clear the array and
          ** begin accumulating any further context pointers without
          ** requiring any dynamic allocation. This is sub-optimal because
          ** it means that instead of one callback with a large array of
          ** context pointers the application will receive two or more
          ** callbacks with smaller arrays of context pointers, which will
          ** reduce the applications ability to prioritize multiple
          ** connections. But it is the best that can be done under the
          ** circumstances.
          */
          xUnlockNotify(aArg, nArg);
          nArg = 0;
        }
      }
      sqlite3EndBenignMalloc();

      aArg[nArg++] = p->pUnlockArg;
      xUnlockNotify = p->xUnlockNotify;
      p->pUnlockConnection = 0;
      p->xUnlockNotify = 0;
      p->pUnlockArg = 0;
    }

    /* Step 3. */
    if( p->pBlockingConnection==0 && p->pUnlockConnection==0 ){
      /* Remove connection p from the blocked connections list. */
      *pp = p->pNextBlocked;
      p->pNextBlocked = 0;
    }else{
      pp = &p->pNextBlocked;
    }
  }

  if( nArg!=0 ){
    xUnlockNotify(aArg, nArg);
  }
  sqlite3_free(aDyn);
  leaveMutex();         /* Leave STATIC_MAIN mutex */
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0xa8, %rsp
movq 0x22e3b0(%rip), %r12    # 0x4bee58
xorl %r14d, %r14d
testq %r12, %r12
je 0x290c52
movq %rdi, %rbx
leaq 0x22e39a(%rip), %r15    # 0x4bee58
leaq 0x20(%rsp), %rbp
xorl %edx, %edx
xorl %r13d, %r13d
movq %rdi, 0x8(%rsp)
movq 0x2d8(%r12), %rcx
cmpq %rbx, %rcx
je 0x290aee
movq 0x2e0(%r12), %rax
cmpq %rbx, %rax
je 0x290b1f
testq %rcx, %rcx
jne 0x290b10
jmp 0x290b07
movq $0x0, 0x2d8(%r12)
movq 0x2e0(%r12), %rax
cmpq %rbx, %rax
je 0x290b1f
testq %rax, %rax
je 0x290c20
addq $0x2f8, %r12            # imm = 0x2F8
movq %r12, %r15
jmp 0x290c37
cmpq %rdx, 0x2f0(%r12)
movq %rdx, 0x18(%rsp)
je 0x290b3e
testl %r14d, %r14d
je 0x290b3e
movq %rbp, %rdi
movl %r14d, %esi
callq *%rdx
xorl %r14d, %r14d
movq 0x22e303(%rip), %rax    # 0x4bee48
testq %rax, %rax
je 0x290b4c
callq *%rax
testq %r13, %r13
jne 0x290b57
cmpl $0x10, %r14d
je 0x290b6d
testq %r13, %r13
je 0x290bcd
movq %r13, %rdi
callq *0x22ab33(%rip)         # 0x4bb698
sarl $0x3, %eax
cmpl %eax, %r14d
jne 0x290bd0
movq %r15, 0x10(%rsp)
movq %rbp, %r15
movq %r13, %rbx
movslq %r14d, %rbp
movq %rbp, %rdi
shlq $0x4, %rdi
callq 0x272ae6
testq %rax, %rax
je 0x290bae
movq %rax, %r13
shlq $0x3, %rbp
movq %rax, %rdi
movq %r15, %rsi
movq %rbp, %rdx
callq 0x17660
movq %rbx, %rdi
callq 0x272c00
movq %r13, %rbp
jmp 0x290bc1
movq %r15, %rbp
movq %r15, %rdi
movl %r14d, %esi
callq *0x18(%rsp)
xorl %r14d, %r14d
movq %rbx, %r13
movq 0x8(%rsp), %rbx
movq 0x10(%rsp), %r15
jmp 0x290bd0
xorl %r13d, %r13d
movq 0x22e279(%rip), %rax    # 0x4bee50
testq %rax, %rax
je 0x290bde
callq *%rax
movq 0x2e8(%r12), %rax
movslq %r14d, %rcx
incl %r14d
movq %rax, (%rbp,%rcx,8)
movq 0x2f0(%r12), %rdx
movq $0x0, 0x2e0(%r12)
xorps %xmm0, %xmm0
movups %xmm0, 0x2e8(%r12)
cmpq $0x0, 0x2d8(%r12)
jne 0x290b10
movq 0x2f8(%r12), %rax
movq %rax, (%r15)
movq $0x0, 0x2f8(%r12)
movq (%r15), %r12
testq %r12, %r12
jne 0x290acd
testl %r14d, %r14d
je 0x290c55
movq %rbp, %rdi
movl %r14d, %esi
callq *%rdx
jmp 0x290c55
xorl %r13d, %r13d
movq %r13, %rdi
callq 0x272c00
addq $0xa8, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq