// Code generated by modernc.org/undup from the per-target sqlite_*.go files; DO NOT EDIT.

//go:build (darwin && amd64) || (darwin && arm64) || (freebsd && amd64) || (freebsd && arm64) || (linux && amd64) || (linux && arm64) || (linux && loong64) || (linux && ppc64le) || (linux && riscv64) || (linux && s390x)

package sqlite3

import (
	"unsafe"

	"modernc.org/libc"
)

// C documentation
//
//	/*
//	** This API allows applications to modify the global configuration of
//	** the SQLite library at run-time.
//	**
//	** This routine should only be called when there are no outstanding
//	** database connections or memory allocations.  This routine is not
//	** threadsafe.  Failure to heed these warnings can lead to unpredictable
//	** behavior.
//	*/
func Xsqlite3_config(tls *libc.TLS, op int32, va uintptr) (r int32) {
	var ap Tva_list
	var bOpenUri, rc int32
	var mxMmap, szMmap Tsqlite3_int64
	var pLogArg, pVal, xLog uintptr
	_, _, _, _, _, _, _, _ = ap, bOpenUri, mxMmap, pLogArg, pVal, rc, szMmap, xLog
	rc = SQLITE_OK
	/* sqlite3_config() normally returns SQLITE_MISUSE if it is invoked while
	 ** the SQLite library is in use.  Except, a few selected opcodes
	 ** are allowed.
	 */
	if libc.AtomicLoadPInt32(uintptr(unsafe.Pointer(&_sqlite3Config))+340) != 0 {
		if op < 0 || op > int32(63) || libc.Uint64FromInt32(1)<<op&_mAnytimeConfigOption == uint64(0) {
			return _sqlite3MisuseError(tls, int32(187639))
		}
	}
	ap = va
	switch op {
	/* Mutex configuration options are only available in a threadsafe
	 ** compile.
	 */
	case int32(SQLITE_CONFIG_SINGLETHREAD):
		/* EVIDENCE-OF: R-02748-19096 This option sets the threading mode to
		 ** Single-thread. */
		_sqlite3Config.FbCoreMutex = uint8(0) /* Disable mutex on core */
		_sqlite3Config.FbFullMutex = uint8(0) /* Disable mutex on connections */
	case int32(SQLITE_CONFIG_MULTITHREAD):
		/* EVIDENCE-OF: R-14374-42468 This option sets the threading mode to
		 ** Multi-thread. */
		_sqlite3Config.FbCoreMutex = uint8(1) /* Enable mutex on core */
		_sqlite3Config.FbFullMutex = uint8(0) /* Disable mutex on connections */
	case int32(SQLITE_CONFIG_SERIALIZED):
		/* EVIDENCE-OF: R-41220-51800 This option sets the threading mode to
		 ** Serialized. */
		_sqlite3Config.FbCoreMutex = uint8(1) /* Enable mutex on core */
		_sqlite3Config.FbFullMutex = uint8(1) /* Enable mutex on connections */
	case int32(SQLITE_CONFIG_MUTEX):
		/* Specify an alternative mutex implementation */
		_sqlite3Config.Fmutex = **(**Tsqlite3_mutex_methods)(__ccgo_up(libc.VaUintptr(&ap)))
	case int32(SQLITE_CONFIG_GETMUTEX):
		/* Retrieve the current mutex implementation */
		**(**Tsqlite3_mutex_methods)(__ccgo_up(libc.VaUintptr(&ap))) = _sqlite3Config.Fmutex
	case int32(SQLITE_CONFIG_MALLOC):
		/* EVIDENCE-OF: R-55594-21030 The SQLITE_CONFIG_MALLOC option takes a
		 ** single argument which is a pointer to an instance of the
		 ** sqlite3_mem_methods structure. The argument specifies alternative
		 ** low-level memory allocation routines to be used in place of the memory
		 ** allocation routines built into SQLite. */
		_sqlite3Config.Fm = **(**Tsqlite3_mem_methods)(__ccgo_up(libc.VaUintptr(&ap)))
	case int32(SQLITE_CONFIG_GETMALLOC):
		/* EVIDENCE-OF: R-51213-46414 The SQLITE_CONFIG_GETMALLOC option takes a
		 ** single argument which is a pointer to an instance of the
		 ** sqlite3_mem_methods structure. The sqlite3_mem_methods structure is
		 ** filled with the currently defined memory allocation routines. */
		if _sqlite3Config.Fm.FxMalloc == uintptr(0) {
			_sqlite3MemSetDefault(tls)
		}
		**(**Tsqlite3_mem_methods)(__ccgo_up(libc.VaUintptr(&ap))) = _sqlite3Config.Fm
	case int32(SQLITE_CONFIG_MEMSTATUS):
		/* Cannot change at runtime */
		/* EVIDENCE-OF: R-61275-35157 The SQLITE_CONFIG_MEMSTATUS option takes
		 ** single argument of type int, interpreted as a boolean, which enables
		 ** or disables the collection of memory allocation statistics. */
		_sqlite3Config.FbMemstat = libc.VaInt32(&ap)
	case int32(SQLITE_CONFIG_SMALL_MALLOC):
		_sqlite3Config.FbSmallMalloc = libc.Uint8FromInt32(libc.VaInt32(&ap))
	case int32(SQLITE_CONFIG_PAGECACHE):
		/* EVIDENCE-OF: R-18761-36601 There are three arguments to
		 ** SQLITE_CONFIG_PAGECACHE: A pointer to 8-byte aligned memory (pMem),
		 ** the size of each page cache line (sz), and the number of cache lines
		 ** (N). */
		_sqlite3Config.FpPage = libc.VaUintptr(&ap)
		_sqlite3Config.FszPage = libc.VaInt32(&ap)
		_sqlite3Config.FnPage = libc.VaInt32(&ap)
	case int32(SQLITE_CONFIG_PCACHE_HDRSZ):
		/* EVIDENCE-OF: R-39100-27317 The SQLITE_CONFIG_PCACHE_HDRSZ option takes
		 ** a single parameter which is a pointer to an integer and writes into
		 ** that integer the number of extra bytes per page required for each page
		 ** in SQLITE_CONFIG_PAGECACHE. */
		**(**int32)(__ccgo_up(libc.VaUintptr(&ap))) = _sqlite3HeaderSizeBtree(tls) + _sqlite3HeaderSizePcache(tls) + _sqlite3HeaderSizePcache1(tls)
	case int32(SQLITE_CONFIG_PCACHE):
		/* no-op */
	case int32(SQLITE_CONFIG_GETPCACHE):
		/* now an error */
		rc = int32(SQLITE_ERROR)
	case int32(SQLITE_CONFIG_PCACHE2):
		/* EVIDENCE-OF: R-63325-48378 The SQLITE_CONFIG_PCACHE2 option takes a
		 ** single argument which is a pointer to an sqlite3_pcache_methods2
		 ** object. This object specifies the interface to a custom page cache
		 ** implementation. */
		_sqlite3Config.Fpcache2 = **(**Tsqlite3_pcache_methods2)(__ccgo_up(libc.VaUintptr(&ap)))
	case int32(SQLITE_CONFIG_GETPCACHE2):
		/* EVIDENCE-OF: R-22035-46182 The SQLITE_CONFIG_GETPCACHE2 option takes a
		 ** single argument which is a pointer to an sqlite3_pcache_methods2
		 ** object. SQLite copies of the current page cache implementation into
		 ** that object. */
		if _sqlite3Config.Fpcache2.FxInit == uintptr(0) {
			_sqlite3PCacheSetDefault(tls)
		}
		**(**Tsqlite3_pcache_methods2)(__ccgo_up(libc.VaUintptr(&ap))) = _sqlite3Config.Fpcache2
		break
		/* EVIDENCE-OF: R-06626-12911 The SQLITE_CONFIG_HEAP option is only
		 ** available if SQLite is compiled with either SQLITE_ENABLE_MEMSYS3 or
		 ** SQLITE_ENABLE_MEMSYS5 and returns SQLITE_ERROR if invoked otherwise. */
		fallthrough
	case int32(SQLITE_CONFIG_LOOKASIDE):
		_sqlite3Config.FszLookaside = libc.VaInt32(&ap)
		_sqlite3Config.FnLookaside = libc.VaInt32(&ap)
		break
		/* Record a pointer to the logger function and its first argument.
		 ** The default is NULL.  Logging is disabled if the function pointer is
		 ** NULL.
		 */
		fallthrough
	case int32(SQLITE_CONFIG_LOG):
		xLog = libc.VaUintptr(&ap)
		pLogArg = libc.VaUintptr(&ap)
		libc.AtomicStoreNUintptr(uintptr(unsafe.Pointer(&_sqlite3Config))+376, xLog, libc.Int32FromInt32(__ATOMIC_RELAXED))
		libc.AtomicStoreNUintptr(uintptr(unsafe.Pointer(&_sqlite3Config))+384, pLogArg, libc.Int32FromInt32(__ATOMIC_RELAXED))
		break
		/* EVIDENCE-OF: R-55548-33817 The compile-time setting for URI filenames
		 ** can be changed at start-time using the
		 ** sqlite3_config(SQLITE_CONFIG_URI,1) or
		 ** sqlite3_config(SQLITE_CONFIG_URI,0) configuration calls.
		 */
		fallthrough
	case int32(SQLITE_CONFIG_URI):
		/* EVIDENCE-OF: R-25451-61125 The SQLITE_CONFIG_URI option takes a single
		 ** argument of type int. If non-zero, then URI handling is globally
		 ** enabled. If the parameter is zero, then URI handling is globally
		 ** disabled. */
		bOpenUri = libc.VaInt32(&ap)
		libc.AtomicStoreNUint8(uintptr(unsafe.Pointer(&_sqlite3Config))+6, libc.Uint8FromInt32(bOpenUri), libc.Int32FromInt32(__ATOMIC_RELAXED))
	case int32(SQLITE_CONFIG_COVERING_INDEX_SCAN):
		/* EVIDENCE-OF: R-36592-02772 The SQLITE_CONFIG_COVERING_INDEX_SCAN
		 ** option takes a single integer argument which is interpreted as a
		 ** boolean in order to enable or disable the use of covering indices for
		 ** full table scans in the query optimizer. */
		_sqlite3Config.FbUseCis = libc.Uint8FromInt32(libc.VaInt32(&ap))
	case int32(SQLITE_CONFIG_MMAP_SIZE):
		/* EVIDENCE-OF: R-58063-38258 SQLITE_CONFIG_MMAP_SIZE takes two 64-bit
		 ** integer (sqlite3_int64) values that are the default mmap size limit
		 ** (the default setting for PRAGMA mmap_size) and the maximum allowed
		 ** mmap size limit. */
		szMmap = libc.VaInt64(&ap)
		mxMmap = libc.VaInt64(&ap)
		/* EVIDENCE-OF: R-53367-43190 If either argument to this option is
		 ** negative, then that argument is changed to its compile-time default.
		 **
		 ** EVIDENCE-OF: R-34993-45031 The maximum allowed mmap size will be
		 ** silently truncated if necessary so that it does not exceed the
		 ** compile-time maximum mmap size set by the SQLITE_MAX_MMAP_SIZE
		 ** compile-time option.
		 */
		if mxMmap < 0 || mxMmap > int64(SQLITE_MAX_MMAP_SIZE) {
			mxMmap = int64(SQLITE_MAX_MMAP_SIZE)
		}
		if szMmap < 0 {
			szMmap = SQLITE_DEFAULT_MMAP_SIZE
		}
		if szMmap > mxMmap {
			szMmap = mxMmap
		}
		_sqlite3Config.FmxMmap = mxMmap
		_sqlite3Config.FszMmap = szMmap
	case int32(SQLITE_CONFIG_PMASZ):
		_sqlite3Config.FszPma = libc.VaUint32(&ap)
	case int32(SQLITE_CONFIG_STMTJRNL_SPILL):
		_sqlite3Config.FnStmtSpill = libc.VaInt32(&ap)
	case int32(SQLITE_CONFIG_MEMDB_MAXSIZE):
		_sqlite3Config.FmxMemdbSize = libc.VaInt64(&ap)
	case int32(SQLITE_CONFIG_ROWID_IN_VIEW):
		pVal = libc.VaUintptr(&ap)
		**(**int32)(__ccgo_up(pVal)) = 0
	default:
		rc = int32(SQLITE_ERROR)
		break
	}
	_ = ap
	return rc
}

// C documentation
//
//	/* The page getter for when memory-mapped I/O is enabled */
func _getPageMMap(tls *libc.TLS, pPager uintptr, pgno TPgno, ppPage uintptr, flags int32) (r int32) {
	bp := tls.Alloc(32)
	defer tls.Free(32)
	var bMmapOk, rc int32
	var _ /* iFrame at bp+8 */ Tu32
	var _ /* pData at bp+16 */ uintptr
	var _ /* pPg at bp+0 */ uintptr
	_, _ = bMmapOk, rc
	rc = SQLITE_OK
	**(**uintptr)(__ccgo_up(bp)) = uintptr(0)
	**(**Tu32)(__ccgo_up(bp + 8)) = uint32(0) /* Frame to read from WAL file */
	/* It is acceptable to use a read-only (mmap) page for any page except
	 ** page 1 if there is no write-transaction open or the ACQUIRE_READONLY
	 ** flag was specified by the caller. And so long as the db is not a
	 ** temporary or in-memory database.  */
	bMmapOk = libc.BoolInt32(pgno > uint32(1) && (libc.Int32FromUint8((*TPager)(unsafe.Pointer(pPager)).FeState) == int32(PAGER_READER) || flags&int32(PAGER_GET_READONLY) != 0))
	/* Optimization note:  Adding the "pgno<=1" term before "pgno==0" here
	 ** allows the compiler optimizer to reuse the results of the "pgno>1"
	 ** test in the previous statement, and avoid testing pgno==0 in the
	 ** common case where pgno is large. */
	if pgno <= uint32(1) && pgno == uint32(0) {
		return _sqlite3CorruptError(tls, int32(65272))
	}
	if bMmapOk != 0 && (*TPager)(unsafe.Pointer(pPager)).FpWal != uintptr(0) {
		rc = _sqlite3WalFindFrame(tls, (*TPager)(unsafe.Pointer(pPager)).FpWal, pgno, bp+8)
		if rc != SQLITE_OK {
			**(**uintptr)(__ccgo_up(ppPage)) = uintptr(0)
			return rc
		}
	}
	if bMmapOk != 0 && **(**Tu32)(__ccgo_up(bp + 8)) == uint32(0) {
		**(**uintptr)(__ccgo_up(bp + 16)) = uintptr(0)
		rc = _sqlite3OsFetch(tls, (*TPager)(unsafe.Pointer(pPager)).Ffd, libc.Int64FromUint32(pgno-libc.Uint32FromInt32(1))*(*TPager)(unsafe.Pointer(pPager)).FpageSize, int32((*TPager)(unsafe.Pointer(pPager)).FpageSize), bp+16)
		if rc == SQLITE_OK && **(**uintptr)(__ccgo_up(bp + 16)) != 0 {
			if libc.Int32FromUint8((*TPager)(unsafe.Pointer(pPager)).FeState) > int32(PAGER_READER) || (*TPager)(unsafe.Pointer(pPager)).FtempFile != 0 {
				**(**uintptr)(__ccgo_up(bp)) = _sqlite3PagerLookup(tls, pPager, pgno)
			}
			if **(**uintptr)(__ccgo_up(bp)) == uintptr(0) {
				rc = _pagerAcquireMapPage(tls, pPager, pgno, **(**uintptr)(__ccgo_up(bp + 16)), bp)
			} else {
				_sqlite3OsUnfetch(tls, (*TPager)(unsafe.Pointer(pPager)).Ffd, libc.Int64FromUint32(pgno-libc.Uint32FromInt32(1))*(*TPager)(unsafe.Pointer(pPager)).FpageSize, **(**uintptr)(__ccgo_up(bp + 16)))
			}
			if **(**uintptr)(__ccgo_up(bp)) != 0 {
				**(**uintptr)(__ccgo_up(ppPage)) = **(**uintptr)(__ccgo_up(bp))
				return SQLITE_OK
			}
		}
		if rc != SQLITE_OK {
			**(**uintptr)(__ccgo_up(ppPage)) = uintptr(0)
			return rc
		}
	}
	return _getPageNormal(tls, pPager, pgno, ppPage, flags)
}

// C documentation
//
//	/*
//	** If pFd->sectorSize is non-zero when this function is called, it is a
//	** no-op. Otherwise, the values of pFd->sectorSize and
//	** pFd->deviceCharacteristics are set according to the file-system
//	** characteristics.
//	**
//	** There are two versions of this function. One for QNX and one for all
//	** other systems.
//	*/
func _setDeviceCharacteristics(tls *libc.TLS, pFd uintptr) {
	if (*TunixFile)(unsafe.Pointer(pFd)).FsectorSize == 0 {
		/* Set the POWERSAFE_OVERWRITE flag if requested. */
		if libc.Int32FromUint16((*TunixFile)(unsafe.Pointer(pFd)).FctrlFlags)&int32(UNIXFILE_PSOW) != 0 {
			**(**int32)(__ccgo_up(pFd + 116)) |= int32(SQLITE_IOCAP_POWERSAFE_OVERWRITE)
		}
		**(**int32)(__ccgo_up(pFd + 116)) |= int32(SQLITE_IOCAP_SUBPAGE_READ)
		(*TunixFile)(unsafe.Pointer(pFd)).FsectorSize = int32(SQLITE_DEFAULT_SECTOR_SIZE)
	}
}

// C documentation
//
//	/*
//	** If it is currently memory mapped, unmap file pFd.
//	*/
func _unixUnmapfile(tls *libc.TLS, pFd uintptr) {
	if (*TunixFile)(unsafe.Pointer(pFd)).FpMapRegion != 0 {
		(*(*func(*libc.TLS, uintptr, Tsize_t) int32)(unsafe.Pointer(&struct{ uintptr }{_aSyscall[int32(23)].FpCurrent})))(tls, (*TunixFile)(unsafe.Pointer(pFd)).FpMapRegion, libc.Uint64FromInt64((*TunixFile)(unsafe.Pointer(pFd)).FmmapSizeActual))
		(*TunixFile)(unsafe.Pointer(pFd)).FpMapRegion = uintptr(0)
		(*TunixFile)(unsafe.Pointer(pFd)).FmmapSize = 0
		(*TunixFile)(unsafe.Pointer(pFd)).FmmapSizeActual = 0
	}
}
