mirror of
https://github.com/postgres/postgres.git
synced 2025-09-29 00:02:14 -04:00
Compare commits
152 Commits
master
...
REL_18_BET
Author | SHA1 | Date | |
---|---|---|---|
|
ab844ce378 | ||
|
67a2fbb8f9 | ||
|
13a67ce603 | ||
|
605fdb989b | ||
|
64f77c6a65 | ||
|
0d2734eac3 | ||
|
9110d81641 | ||
|
762fed90bf | ||
|
41aac1483a | ||
|
e507e08acf | ||
|
16b0c48583 | ||
|
ff181d1f87 | ||
|
4cd9d5fc15 | ||
|
992a18f516 | ||
|
bba6a6fafc | ||
|
e3764229e6 | ||
|
ce88170227 | ||
|
ab74ce4dc9 | ||
|
a9ffb35274 | ||
|
31c09ef456 | ||
|
f15c00e909 | ||
|
5cfbff48a4 | ||
|
2ae8280d16 | ||
|
dd29262077 | ||
|
1084e76f3c | ||
|
67ffe1987d | ||
|
074db8604a | ||
|
ce13bb96fb | ||
|
3e65e77f76 | ||
|
9b681e2397 | ||
|
f71ad5b082 | ||
|
d185161e47 | ||
|
06697909b6 | ||
|
e5d04aedaf | ||
|
7c3a036f5c | ||
|
0e6b791846 | ||
|
347b6a1fff | ||
|
2d81a246f4 | ||
|
7b1053a577 | ||
|
fee46ab4f2 | ||
|
a3e8dc1438 | ||
|
d0c12b98f2 | ||
|
5a900d6482 | ||
|
11de339aad | ||
|
7b9674a8b1 | ||
|
60121890f7 | ||
|
42b1480eb2 | ||
|
d9f01a287a | ||
|
88914332ea | ||
|
72c437f6e4 | ||
|
c0ae03384f | ||
|
da103c7bc8 | ||
|
3a954813a0 | ||
|
4a9ee867bf | ||
|
cd2d52cc6b | ||
|
a60691eb20 | ||
|
fce7da1e73 | ||
|
8e5e3ff556 | ||
|
d5f014d897 | ||
|
1fe9e3822c | ||
|
637ead2e1a | ||
|
44e135ad57 | ||
|
13eb6bb76d | ||
|
bae5078217 | ||
|
75f633f54a | ||
|
f7dfccf960 | ||
|
2973b1cd3a | ||
|
33f74b806c | ||
|
a8acfb133c | ||
|
3d039b53a1 | ||
|
7b98c55368 | ||
|
0e8c656551 | ||
|
282b10cb05 | ||
|
0ded7615d8 | ||
|
f9545e95c5 | ||
|
6cf5b10ce9 | ||
|
226c567454 | ||
|
c71c702f06 | ||
|
5449d5b7ae | ||
|
27c7c11366 | ||
|
bfa9b25c94 | ||
|
e0d3f3cfb6 | ||
|
c4b5cd0956 | ||
|
02d21cfd4b | ||
|
4fcbe06aa8 | ||
|
409c63f9f6 | ||
|
dca0e9693b | ||
|
973caf7291 | ||
|
40c66f8585 | ||
|
ac7c044831 | ||
|
da9a888da2 | ||
|
f8ce5dea43 | ||
|
0b6dfce0ce | ||
|
c33e55ac91 | ||
|
8bd92fc514 | ||
|
3c9aafb775 | ||
|
7d11f36e71 | ||
|
b4c19da93a | ||
|
b2afb06763 | ||
|
20b8b5dab9 | ||
|
ccacaf4fae | ||
|
3d23f68c55 | ||
|
f36e577451 | ||
|
a1973e5466 | ||
|
afb64a56d9 | ||
|
37c76aeb9a | ||
|
39f01083fa | ||
|
36026b0fe3 | ||
|
99fd638ba0 | ||
|
7bd752c1fb | ||
|
765a4c94cc | ||
|
5d9e675b36 | ||
|
601a3133ae | ||
|
fc3edb52fb | ||
|
075554ec6c | ||
|
330db576f8 | ||
|
9a5334c0b4 | ||
|
3a797c2491 | ||
|
440c5ee202 | ||
|
8d1071e7da | ||
|
1e007722fa | ||
|
5aba3e637d | ||
|
07da2985d6 | ||
|
29a4b63c6b | ||
|
3d7a96871c | ||
|
0cd7fcaa85 | ||
|
8af310b331 | ||
|
f0151e2a4e | ||
|
5d0800000e | ||
|
4938737d54 | ||
|
e16c9cd331 | ||
|
4cb889d21f | ||
|
7c365eb504 | ||
|
87f0d3cd8d | ||
|
7c6ededac8 | ||
|
3e73d87353 | ||
|
d09d137934 | ||
|
b897a58556 | ||
|
3386b2fe7a | ||
|
c8b9f75111 | ||
|
399997d8cc | ||
|
b71351e1f2 | ||
|
581305a465 | ||
|
45c5276628 | ||
|
07448b3969 | ||
|
54ac4944c3 | ||
|
14e52227e5 | ||
|
45879f48f1 | ||
|
eb37fe716a | ||
|
95163cbe11 | ||
|
b2a57747ba | ||
|
42625ecda2 |
88
.cirrus.star
88
.cirrus.star
@ -7,7 +7,7 @@ https://github.com/bazelbuild/starlark/blob/master/spec.md
|
||||
See also .cirrus.yml and src/tools/ci/README
|
||||
"""
|
||||
|
||||
load("cirrus", "env", "fs", "re", "yaml")
|
||||
load("cirrus", "env", "fs")
|
||||
|
||||
|
||||
def main():
|
||||
@ -18,36 +18,19 @@ def main():
|
||||
|
||||
1) the contents of .cirrus.yml
|
||||
|
||||
2) computed environment variables
|
||||
|
||||
3) if defined, the contents of the file referenced by the, repository
|
||||
2) if defined, the contents of the file referenced by the, repository
|
||||
level, REPO_CI_CONFIG_GIT_URL variable (see
|
||||
https://cirrus-ci.org/guide/programming-tasks/#fs for the accepted
|
||||
format)
|
||||
|
||||
4) .cirrus.tasks.yml
|
||||
3) .cirrus.tasks.yml
|
||||
"""
|
||||
|
||||
output = ""
|
||||
|
||||
# 1) is evaluated implicitly
|
||||
|
||||
|
||||
# Add 2)
|
||||
additional_env = compute_environment_vars()
|
||||
env_fmt = """
|
||||
###
|
||||
# Computed environment variables start here
|
||||
###
|
||||
{0}
|
||||
###
|
||||
# Computed environment variables end here
|
||||
###
|
||||
"""
|
||||
output += env_fmt.format(yaml.dumps({'env': additional_env}))
|
||||
|
||||
|
||||
# Add 3)
|
||||
repo_config_url = env.get("REPO_CI_CONFIG_GIT_URL")
|
||||
if repo_config_url != None:
|
||||
print("loading additional configuration from \"{}\"".format(repo_config_url))
|
||||
@ -55,75 +38,12 @@ def main():
|
||||
else:
|
||||
output += "\n# REPO_CI_CONFIG_URL was not set\n"
|
||||
|
||||
|
||||
# Add 4)
|
||||
# Add 3)
|
||||
output += config_from(".cirrus.tasks.yml")
|
||||
|
||||
|
||||
return output
|
||||
|
||||
|
||||
def compute_environment_vars():
|
||||
cenv = {}
|
||||
|
||||
###
|
||||
# Some tasks are manually triggered by default because they might use too
|
||||
# many resources for users of free Cirrus credits, but they can be
|
||||
# triggered automatically by naming them in an environment variable e.g.
|
||||
# REPO_CI_AUTOMATIC_TRIGGER_TASKS="task_name other_task" under "Repository
|
||||
# Settings" on Cirrus CI's website.
|
||||
|
||||
default_manual_trigger_tasks = ['mingw', 'netbsd', 'openbsd']
|
||||
|
||||
repo_ci_automatic_trigger_tasks = env.get('REPO_CI_AUTOMATIC_TRIGGER_TASKS', '')
|
||||
for task in default_manual_trigger_tasks:
|
||||
name = 'CI_TRIGGER_TYPE_' + task.upper()
|
||||
if repo_ci_automatic_trigger_tasks.find(task) != -1:
|
||||
value = 'automatic'
|
||||
else:
|
||||
value = 'manual'
|
||||
cenv[name] = value
|
||||
###
|
||||
|
||||
###
|
||||
# Parse "ci-os-only:" tag in commit message and set
|
||||
# CI_{$OS}_ENABLED variable for each OS
|
||||
|
||||
# We want to disable SanityCheck if testing just a specific OS. This
|
||||
# shortens push-wait-for-ci cycle time a bit when debugging operating
|
||||
# system specific failures. Just treating it as an OS in that case
|
||||
# suffices.
|
||||
|
||||
operating_systems = [
|
||||
'compilerwarnings',
|
||||
'freebsd',
|
||||
'linux',
|
||||
'macos',
|
||||
'mingw',
|
||||
'netbsd',
|
||||
'openbsd',
|
||||
'sanitycheck',
|
||||
'windows',
|
||||
]
|
||||
commit_message = env.get('CIRRUS_CHANGE_MESSAGE')
|
||||
match_re = r"(^|.*\n)ci-os-only: ([^\n]+)($|\n.*)"
|
||||
|
||||
# re.match() returns an array with a tuple of (matched-string, match_1, ...)
|
||||
m = re.match(match_re, commit_message)
|
||||
if m and len(m) > 0:
|
||||
os_only = m[0][2]
|
||||
os_only_list = re.split(r'[, ]+', os_only)
|
||||
else:
|
||||
os_only_list = operating_systems
|
||||
|
||||
for os in operating_systems:
|
||||
os_enabled = os in os_only_list
|
||||
cenv['CI_{0}_ENABLED'.format(os.upper())] = os_enabled
|
||||
###
|
||||
|
||||
return cenv
|
||||
|
||||
|
||||
def config_from(config_src):
|
||||
"""return contents of config file `config_src`, surrounded by markers
|
||||
indicating start / end of the included file
|
||||
|
@ -31,31 +31,6 @@ env:
|
||||
TEMP_CONFIG: ${CIRRUS_WORKING_DIR}/src/tools/ci/pg_ci_base.conf
|
||||
PG_TEST_EXTRA: kerberos ldap ssl libpq_encryption load_balance oauth
|
||||
|
||||
# Postgres config args for the meson builds, shared between all meson tasks
|
||||
# except the 'SanityCheck' task
|
||||
MESON_COMMON_PG_CONFIG_ARGS: -Dcassert=true -Dinjection_points=true
|
||||
|
||||
# Meson feature flags shared by all meson tasks, except:
|
||||
# SanityCheck: uses almost no dependencies.
|
||||
# Windows - VS: has fewer dependencies than listed here, so defines its own.
|
||||
# Linux: uses the 'auto' feature option to test meson feature autodetection.
|
||||
MESON_COMMON_FEATURES: >-
|
||||
-Dauto_features=disabled
|
||||
-Dldap=enabled
|
||||
-Dssl=openssl
|
||||
-Dtap_tests=enabled
|
||||
-Dplperl=enabled
|
||||
-Dplpython=enabled
|
||||
-Ddocs=enabled
|
||||
-Dicu=enabled
|
||||
-Dlibxml=enabled
|
||||
-Dlibxslt=enabled
|
||||
-Dlz4=enabled
|
||||
-Dpltcl=enabled
|
||||
-Dreadline=enabled
|
||||
-Dzlib=enabled
|
||||
-Dzstd=enabled
|
||||
|
||||
|
||||
# What files to preserve in case tests fail
|
||||
on_failure_ac: &on_failure_ac
|
||||
@ -97,7 +72,7 @@ task:
|
||||
# push-wait-for-ci cycle time a bit when debugging operating system specific
|
||||
# failures. Uses skip instead of only_if, as cirrus otherwise warns about
|
||||
# only_if conditions not matching.
|
||||
skip: $CI_SANITYCHECK_ENABLED == false
|
||||
skip: $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:.*'
|
||||
|
||||
env:
|
||||
CPUS: 4
|
||||
@ -189,19 +164,10 @@ task:
|
||||
-c debug_parallel_query=regress
|
||||
PG_TEST_PG_UPGRADE_MODE: --link
|
||||
|
||||
MESON_FEATURES: >-
|
||||
-Ddtrace=enabled
|
||||
-Dgssapi=enabled
|
||||
-Dlibcurl=enabled
|
||||
-Dnls=enabled
|
||||
-Dpam=enabled
|
||||
-Dtcl_version=tcl86
|
||||
-Duuid=bsd
|
||||
|
||||
<<: *freebsd_task_template
|
||||
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_FREEBSD_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*freebsd.*'
|
||||
|
||||
sysinfo_script: |
|
||||
id
|
||||
@ -230,10 +196,10 @@ task:
|
||||
configure_script: |
|
||||
su postgres <<-EOF
|
||||
meson setup \
|
||||
${MESON_COMMON_PG_CONFIG_ARGS} \
|
||||
--buildtype=debug \
|
||||
-Dcassert=true -Dinjection_points=true \
|
||||
-Duuid=bsd -Dtcl_version=tcl86 -Ddtrace=auto \
|
||||
-Dextra_lib_dirs=/usr/local/lib -Dextra_include_dirs=/usr/local/include/ \
|
||||
${MESON_COMMON_FEATURES} ${MESON_FEATURES} \
|
||||
build
|
||||
EOF
|
||||
build_script: su postgres -c 'ninja -C build -j${BUILD_JOBS} ${MBUILD_TARGET}'
|
||||
@ -273,6 +239,7 @@ task:
|
||||
|
||||
task:
|
||||
depends_on: SanityCheck
|
||||
trigger_type: manual
|
||||
|
||||
env:
|
||||
# Below are experimentally derived to be a decent choice.
|
||||
@ -290,9 +257,7 @@ task:
|
||||
|
||||
matrix:
|
||||
- name: NetBSD - Meson
|
||||
# See REPO_CI_AUTOMATIC_TRIGGER_TASKS in .cirrus.star
|
||||
trigger_type: $CI_TRIGGER_TYPE_NETBSD
|
||||
only_if: $CI_NETBSD_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*netbsd.*'
|
||||
env:
|
||||
OS_NAME: netbsd
|
||||
IMAGE_FAMILY: pg-ci-netbsd-postgres
|
||||
@ -304,31 +269,18 @@ task:
|
||||
LC_ALL: "C"
|
||||
# -Duuid is not set for the NetBSD, see the comment below, above
|
||||
# configure_script, for more information.
|
||||
MESON_FEATURES: >-
|
||||
-Dgssapi=enabled
|
||||
-Dlibcurl=enabled
|
||||
-Dnls=enabled
|
||||
-Dpam=enabled
|
||||
|
||||
setup_additional_packages_script: |
|
||||
#pkgin -y install ...
|
||||
<<: *netbsd_task_template
|
||||
|
||||
- name: OpenBSD - Meson
|
||||
# See REPO_CI_AUTOMATIC_TRIGGER_TASKS in .cirrus.star
|
||||
trigger_type: $CI_TRIGGER_TYPE_OPENBSD
|
||||
only_if: $CI_OPENBSD_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*openbsd.*'
|
||||
env:
|
||||
OS_NAME: openbsd
|
||||
IMAGE_FAMILY: pg-ci-openbsd-postgres
|
||||
PKGCONFIG_PATH: '/usr/lib/pkgconfig:/usr/local/lib/pkgconfig'
|
||||
|
||||
MESON_FEATURES: >-
|
||||
-Dbsd_auth=enabled
|
||||
-Dlibcurl=enabled
|
||||
-Dtcl_version=tcl86
|
||||
-Duuid=e2fs
|
||||
|
||||
UUID: -Duuid=e2fs
|
||||
TCL: -Dtcl_version=tcl86
|
||||
setup_additional_packages_script: |
|
||||
#pkg_add -I ...
|
||||
# Always core dump to ${CORE_DUMP_DIR}
|
||||
@ -362,10 +314,11 @@ task:
|
||||
configure_script: |
|
||||
su postgres <<-EOF
|
||||
meson setup \
|
||||
${MESON_COMMON_PG_CONFIG_ARGS} \
|
||||
--buildtype=debugoptimized \
|
||||
--pkg-config-path ${PKGCONFIG_PATH} \
|
||||
${MESON_COMMON_FEATURES} ${MESON_FEATURES} \
|
||||
-Dcassert=true -Dinjection_points=true \
|
||||
-Dssl=openssl ${UUID} ${TCL} \
|
||||
-DPG_TEST_EXTRA="$PG_TEST_EXTRA" \
|
||||
build
|
||||
EOF
|
||||
|
||||
@ -412,6 +365,10 @@ LINUX_CONFIGURE_FEATURES: &LINUX_CONFIGURE_FEATURES >-
|
||||
--with-uuid=ossp
|
||||
--with-zstd
|
||||
|
||||
LINUX_MESON_FEATURES: &LINUX_MESON_FEATURES >-
|
||||
-Dllvm=enabled
|
||||
-Duuid=e2fs
|
||||
|
||||
|
||||
# Check SPECIAL in the matrix: below
|
||||
task:
|
||||
@ -452,13 +409,12 @@ task:
|
||||
LLVM_CONFIG: llvm-config-16
|
||||
|
||||
LINUX_CONFIGURE_FEATURES: *LINUX_CONFIGURE_FEATURES
|
||||
LINUX_MESON_FEATURES: >-
|
||||
-Duuid=e2fs
|
||||
LINUX_MESON_FEATURES: *LINUX_MESON_FEATURES
|
||||
|
||||
<<: *linux_task_template
|
||||
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_LINUX_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*linux.*'
|
||||
|
||||
ccache_cache:
|
||||
folder: ${CCACHE_DIR}
|
||||
@ -539,7 +495,6 @@ task:
|
||||
# are typically printed in the server log
|
||||
# - Test both 64bit and 32 bit builds
|
||||
# - uses io_method=io_uring
|
||||
# - Uses meson feature autodetection
|
||||
- name: Linux - Debian Bookworm - Meson
|
||||
|
||||
env:
|
||||
@ -551,9 +506,9 @@ task:
|
||||
configure_script: |
|
||||
su postgres <<-EOF
|
||||
meson setup \
|
||||
${MESON_COMMON_PG_CONFIG_ARGS} \
|
||||
--buildtype=debug \
|
||||
${LINUX_MESON_FEATURES} -Dllvm=enabled \
|
||||
-Dcassert=true -Dinjection_points=true \
|
||||
${LINUX_MESON_FEATURES} \
|
||||
build
|
||||
EOF
|
||||
|
||||
@ -563,11 +518,13 @@ task:
|
||||
su postgres <<-EOF
|
||||
export CC='ccache gcc -m32'
|
||||
meson setup \
|
||||
${MESON_COMMON_PG_CONFIG_ARGS} \
|
||||
--buildtype=debug \
|
||||
-Dcassert=true -Dinjection_points=true \
|
||||
${LINUX_MESON_FEATURES} \
|
||||
-Dllvm=disabled \
|
||||
--pkg-config-path /usr/lib/i386-linux-gnu/pkgconfig/ \
|
||||
-DPERL=perl5.36-i386-linux-gnu \
|
||||
${LINUX_MESON_FEATURES} -Dlibnuma=disabled \
|
||||
-Dlibnuma=disabled \
|
||||
build-32
|
||||
EOF
|
||||
|
||||
@ -631,14 +588,6 @@ task:
|
||||
CCACHE_DIR: ${HOME}/ccache
|
||||
MACPORTS_CACHE: ${HOME}/macports-cache
|
||||
|
||||
MESON_FEATURES: >-
|
||||
-Dbonjour=enabled
|
||||
-Ddtrace=enabled
|
||||
-Dgssapi=enabled
|
||||
-Dlibcurl=enabled
|
||||
-Dnls=enabled
|
||||
-Duuid=e2fs
|
||||
|
||||
MACOS_PACKAGE_LIST: >-
|
||||
ccache
|
||||
icu
|
||||
@ -664,7 +613,7 @@ task:
|
||||
<<: *macos_task_template
|
||||
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_MACOS_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*(macos|darwin|osx).*'
|
||||
|
||||
sysinfo_script: |
|
||||
id
|
||||
@ -708,11 +657,11 @@ task:
|
||||
configure_script: |
|
||||
export PKG_CONFIG_PATH="/opt/local/lib/pkgconfig/"
|
||||
meson setup \
|
||||
${MESON_COMMON_PG_CONFIG_ARGS} \
|
||||
--buildtype=debug \
|
||||
-Dextra_include_dirs=/opt/local/include \
|
||||
-Dextra_lib_dirs=/opt/local/lib \
|
||||
${MESON_COMMON_FEATURES} ${MESON_FEATURES} \
|
||||
-Dcassert=true -Dinjection_points=true \
|
||||
-Duuid=e2fs -Ddtrace=auto \
|
||||
build
|
||||
|
||||
build_script: ninja -C build -j${BUILD_JOBS} ${MBUILD_TARGET}
|
||||
@ -767,18 +716,10 @@ task:
|
||||
# 0x8001 is SEM_FAILCRITICALERRORS | SEM_NOOPENFILEERRORBOX
|
||||
CIRRUS_WINDOWS_ERROR_MODE: 0x8001
|
||||
|
||||
MESON_FEATURES:
|
||||
-Dauto_features=disabled
|
||||
-Dldap=enabled
|
||||
-Dssl=openssl
|
||||
-Dtap_tests=enabled
|
||||
-Dplperl=enabled
|
||||
-Dplpython=enabled
|
||||
|
||||
<<: *windows_task_template
|
||||
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_WINDOWS_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*windows.*'
|
||||
|
||||
setup_additional_packages_script: |
|
||||
REM choco install -y --no-progress ...
|
||||
@ -789,9 +730,10 @@ task:
|
||||
echo 127.0.0.3 pg-loadbalancetest >> c:\Windows\System32\Drivers\etc\hosts
|
||||
type c:\Windows\System32\Drivers\etc\hosts
|
||||
|
||||
# Use /DEBUG:FASTLINK to avoid high memory usage during linking
|
||||
configure_script: |
|
||||
vcvarsall x64
|
||||
meson setup --backend ninja %MESON_COMMON_PG_CONFIG_ARGS% --buildtype debug -Db_pch=true -Dextra_lib_dirs=c:\openssl\1.1\lib -Dextra_include_dirs=c:\openssl\1.1\include -DTAR=%TAR% %MESON_FEATURES% build
|
||||
meson setup --backend ninja --buildtype debug -Dc_link_args=/DEBUG:FASTLINK -Dcassert=true -Dinjection_points=true -Db_pch=true -Dextra_lib_dirs=c:\openssl\1.1\lib -Dextra_include_dirs=c:\openssl\1.1\include -DTAR=%TAR% build
|
||||
|
||||
build_script: |
|
||||
vcvarsall x64
|
||||
@ -813,11 +755,13 @@ task:
|
||||
<< : *WINDOWS_ENVIRONMENT_BASE
|
||||
name: Windows - Server 2019, MinGW64 - Meson
|
||||
|
||||
# See REPO_CI_AUTOMATIC_TRIGGER_TASKS in .cirrus.star.
|
||||
trigger_type: $CI_TRIGGER_TYPE_MINGW
|
||||
|
||||
# due to resource constraints we don't run this task by default for now
|
||||
trigger_type: manual
|
||||
# worth using only_if despite being manual, otherwise this task will show up
|
||||
# when e.g. ci-os-only: linux is used.
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*' || $CIRRUS_CHANGE_MESSAGE =~ '.*\nci-os-only:[^\n]*mingw.*'
|
||||
# otherwise it'll be sorted before other tasks
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_MINGW_ENABLED
|
||||
|
||||
env:
|
||||
TEST_JOBS: 4 # higher concurrency causes occasional failures
|
||||
@ -833,11 +777,6 @@ task:
|
||||
CHERE_INVOKING: 1
|
||||
BASH: C:\msys64\usr\bin\bash.exe -l
|
||||
|
||||
# Keep -Dnls explicitly disabled, as the number of files it creates causes a
|
||||
# noticeable slowdown.
|
||||
MESON_FEATURES: >-
|
||||
-Dnls=disabled
|
||||
|
||||
<<: *windows_task_template
|
||||
|
||||
ccache_cache:
|
||||
@ -852,8 +791,9 @@ task:
|
||||
%BASH% -c "where perl"
|
||||
%BASH% -c "perl --version"
|
||||
|
||||
# disable -Dnls as the number of files it creates cause a noticable slowdown
|
||||
configure_script: |
|
||||
%BASH% -c "meson setup %MESON_COMMON_PG_CONFIG_ARGS% -Ddebug=true -Doptimization=g -Db_pch=true %MESON_COMMON_FEATURES% %MESON_FEATURES% -DTAR=%TAR% build"
|
||||
%BASH% -c "meson setup -Ddebug=true -Doptimization=g -Dcassert=true -Dinjection_points=true -Db_pch=true -Dnls=disabled -DTAR=%TAR% build"
|
||||
|
||||
build_script: |
|
||||
%BASH% -c "ninja -C build ${MBUILD_TARGET}"
|
||||
@ -875,9 +815,10 @@ task:
|
||||
|
||||
# To limit unnecessary work only run this once the SanityCheck
|
||||
# succeeds. This is particularly important for this task as we intentionally
|
||||
# use always: to continue after failures.
|
||||
# use always: to continue after failures. Task that did not run count as a
|
||||
# success, so we need to recheck SanityChecks's condition here ...
|
||||
depends_on: SanityCheck
|
||||
only_if: $CI_COMPILERWARNINGS_ENABLED
|
||||
only_if: $CIRRUS_CHANGE_MESSAGE !=~ '.*\nci-os-only:.*'
|
||||
|
||||
env:
|
||||
CPUS: 4
|
||||
@ -890,6 +831,7 @@ task:
|
||||
CCACHE_DIR: "/tmp/ccache_dir"
|
||||
|
||||
LINUX_CONFIGURE_FEATURES: *LINUX_CONFIGURE_FEATURES
|
||||
LINUX_MESON_FEATURES: *LINUX_MESON_FEATURES
|
||||
|
||||
# GCC emits a warning for llvm-14, so switch to a newer one.
|
||||
LLVM_CONFIG: llvm-config-16
|
||||
|
12
.cirrus.yml
12
.cirrus.yml
@ -10,20 +10,12 @@
|
||||
#
|
||||
# 1) the contents of this file
|
||||
#
|
||||
# 2) computed environment variables
|
||||
#
|
||||
# Used to enable/disable tasks based on the execution environment. See
|
||||
# .cirrus.star: compute_environment_vars()
|
||||
#
|
||||
# 3) if defined, the contents of the file referenced by the, repository
|
||||
# 2) if defined, the contents of the file referenced by the, repository
|
||||
# level, REPO_CI_CONFIG_GIT_URL variable (see
|
||||
# https://cirrus-ci.org/guide/programming-tasks/#fs for the accepted
|
||||
# format)
|
||||
#
|
||||
# This allows running tasks in a different execution environment than the
|
||||
# default, e.g. to have sufficient resources for cfbot.
|
||||
#
|
||||
# 4) .cirrus.tasks.yml
|
||||
# 3) .cirrus.tasks.yml
|
||||
#
|
||||
# This composition is done by .cirrus.star
|
||||
|
||||
|
@ -14,16 +14,7 @@
|
||||
#
|
||||
# $ git log --pretty=format:"%H # %cd%n# %s" $PGINDENTGITHASH -1 --date=iso
|
||||
|
||||
7e9c216b5236cc61f677787b35e8c8f28f5f6959 # 2025-09-13 14:50:02 -0500
|
||||
# Re-pgindent nbtpreprocesskeys.c after commit 796962922e.
|
||||
|
||||
1d1612aec7688139e1a5506df1366b4b6a69605d # 2025-07-29 09:10:41 -0400
|
||||
# Run pgindent.
|
||||
|
||||
73873805fb3627cb23937c750fa83ffd8f16fc6c # 2025-07-25 16:36:44 -0400
|
||||
# Run pgindent on the changes of the previous patch.
|
||||
|
||||
9e345415bcd3c4358350b89edfd710469b8bfaf9 # 2025-07-01 15:23:07 +0200
|
||||
07448b3969d55a2081cdafafc23f68df3392f220 # 2025-07-01 15:24:19 +0200
|
||||
# Fix indentation in pg_numa code
|
||||
|
||||
b27644bade0348d0dafd3036c47880a349fe9332 # 2025-06-15 13:04:24 -0400
|
||||
|
4
.gitattributes
vendored
4
.gitattributes
vendored
@ -12,8 +12,8 @@
|
||||
*.xsl whitespace=space-before-tab,trailing-space,tab-in-indent
|
||||
|
||||
# Avoid confusing ASCII underlines with leftover merge conflict markers
|
||||
README conflict-marker-size=48
|
||||
README.* conflict-marker-size=48
|
||||
README conflict-marker-size=32
|
||||
README.* conflict-marker-size=32
|
||||
|
||||
# Certain data files that contain special whitespace, and other special cases
|
||||
*.data -whitespace
|
||||
|
2
Makefile
2
Makefile
@ -20,7 +20,7 @@ all:
|
||||
all check install installdirs installcheck installcheck-parallel uninstall clean distclean maintainer-clean dist distcheck world check-world install-world installcheck-world:
|
||||
@if [ ! -f GNUmakefile ] ; then \
|
||||
echo "You need to run the 'configure' program first. Please see"; \
|
||||
echo "<https://www.postgresql.org/docs/devel/installation.html>" ; \
|
||||
echo "<https://www.postgresql.org/docs/18/installation.html>" ; \
|
||||
false ; \
|
||||
fi
|
||||
@IFS=':' ; \
|
||||
|
@ -12,9 +12,9 @@ and functions. This distribution also contains C language bindings.
|
||||
Copyright and license information can be found in the file COPYRIGHT.
|
||||
|
||||
General documentation about this version of PostgreSQL can be found at
|
||||
<https://www.postgresql.org/docs/devel/>. In particular, information
|
||||
<https://www.postgresql.org/docs/18/>. In particular, information
|
||||
about building PostgreSQL from the source code can be found at
|
||||
<https://www.postgresql.org/docs/devel/installation.html>.
|
||||
<https://www.postgresql.org/docs/18/installation.html>.
|
||||
|
||||
The latest version of this software, and related software, may be
|
||||
obtained at <https://www.postgresql.org/download/>. For more information
|
||||
|
@ -83,7 +83,7 @@ if test x"$pgac_cv__128bit_int" = xyes ; then
|
||||
AC_CACHE_CHECK([for __int128 alignment bug], [pgac_cv__128bit_int_bug],
|
||||
[AC_RUN_IFELSE([AC_LANG_PROGRAM([
|
||||
/* This must match the corresponding code in c.h: */
|
||||
#if defined(__GNUC__)
|
||||
#if defined(__GNUC__) || defined(__SUNPRO_C)
|
||||
#define pg_attribute_aligned(a) __attribute__((aligned(a)))
|
||||
#elif defined(_MSC_VER)
|
||||
#define pg_attribute_aligned(a) __declspec(align(a))
|
||||
|
@ -22,14 +22,18 @@ sourcetree=`cd $1 && pwd`
|
||||
|
||||
buildtree=`cd ${2:-'.'} && pwd`
|
||||
|
||||
for item in `find "$sourcetree"/config "$sourcetree"/contrib "$sourcetree"/doc "$sourcetree"/src -type d -print`; do
|
||||
# We must not auto-create the subdirectories holding built documentation.
|
||||
# If we did, it would interfere with installation of prebuilt docs from
|
||||
# the source tree, if a VPATH build is done from a distribution tarball.
|
||||
# See bug #5595.
|
||||
for item in `find "$sourcetree" -type d \( \( -name CVS -prune \) -o \( -name .git -prune \) -o -print \) | grep -v "$sourcetree/doc/src/sgml/\+"`; do
|
||||
subdir=`expr "$item" : "$sourcetree\(.*\)"`
|
||||
if test ! -d "$buildtree/$subdir"; then
|
||||
mkdir -p "$buildtree/$subdir" || exit 1
|
||||
fi
|
||||
done
|
||||
|
||||
for item in "$sourcetree"/Makefile `find "$sourcetree"/config "$sourcetree"/contrib "$sourcetree"/doc "$sourcetree"/src -name Makefile -print -o -name GNUmakefile -print`; do
|
||||
for item in `find "$sourcetree" -name Makefile -print -o -name GNUmakefile -print | grep -v "$sourcetree/doc/src/sgml/images/"`; do
|
||||
filename=`expr "$item" : "$sourcetree\(.*\)"`
|
||||
if test ! -f "${item}.in"; then
|
||||
if cmp "$item" "$buildtree/$filename" >/dev/null 2>&1; then : ; else
|
||||
|
275
configure
vendored
275
configure
vendored
@ -1,6 +1,6 @@
|
||||
#! /bin/sh
|
||||
# Guess values for system-dependent variables and create Makefiles.
|
||||
# Generated by GNU Autoconf 2.69 for PostgreSQL 19devel.
|
||||
# Generated by GNU Autoconf 2.69 for PostgreSQL 18beta3.
|
||||
#
|
||||
# Report bugs to <pgsql-bugs@lists.postgresql.org>.
|
||||
#
|
||||
@ -582,8 +582,8 @@ MAKEFLAGS=
|
||||
# Identity of this package.
|
||||
PACKAGE_NAME='PostgreSQL'
|
||||
PACKAGE_TARNAME='postgresql'
|
||||
PACKAGE_VERSION='19devel'
|
||||
PACKAGE_STRING='PostgreSQL 19devel'
|
||||
PACKAGE_VERSION='18beta3'
|
||||
PACKAGE_STRING='PostgreSQL 18beta3'
|
||||
PACKAGE_BUGREPORT='pgsql-bugs@lists.postgresql.org'
|
||||
PACKAGE_URL='https://www.postgresql.org/'
|
||||
|
||||
@ -739,6 +739,7 @@ PKG_CONFIG_LIBDIR
|
||||
PKG_CONFIG_PATH
|
||||
PKG_CONFIG
|
||||
DLSUFFIX
|
||||
TAS
|
||||
GCC
|
||||
CPP
|
||||
CFLAGS_SL
|
||||
@ -759,6 +760,7 @@ CLANG
|
||||
LLVM_CONFIG
|
||||
AWK
|
||||
with_llvm
|
||||
SUN_STUDIO_CC
|
||||
ac_ct_CXX
|
||||
CXXFLAGS
|
||||
CXX
|
||||
@ -1466,7 +1468,7 @@ if test "$ac_init_help" = "long"; then
|
||||
# Omit some internal or obsolete options to make the list less imposing.
|
||||
# This message is too long to be a string in the A/UX 3.1 sh.
|
||||
cat <<_ACEOF
|
||||
\`configure' configures PostgreSQL 19devel to adapt to many kinds of systems.
|
||||
\`configure' configures PostgreSQL 18beta3 to adapt to many kinds of systems.
|
||||
|
||||
Usage: $0 [OPTION]... [VAR=VALUE]...
|
||||
|
||||
@ -1531,7 +1533,7 @@ fi
|
||||
|
||||
if test -n "$ac_init_help"; then
|
||||
case $ac_init_help in
|
||||
short | recursive ) echo "Configuration of PostgreSQL 19devel:";;
|
||||
short | recursive ) echo "Configuration of PostgreSQL 18beta3:";;
|
||||
esac
|
||||
cat <<\_ACEOF
|
||||
|
||||
@ -1722,7 +1724,7 @@ fi
|
||||
test -n "$ac_init_help" && exit $ac_status
|
||||
if $ac_init_version; then
|
||||
cat <<\_ACEOF
|
||||
PostgreSQL configure 19devel
|
||||
PostgreSQL configure 18beta3
|
||||
generated by GNU Autoconf 2.69
|
||||
|
||||
Copyright (C) 2012 Free Software Foundation, Inc.
|
||||
@ -2475,7 +2477,7 @@ cat >config.log <<_ACEOF
|
||||
This file contains any messages produced by compilers while
|
||||
running configure, to aid debugging if configure makes a mistake.
|
||||
|
||||
It was created by PostgreSQL $as_me 19devel, which was
|
||||
It was created by PostgreSQL $as_me 18beta3, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
$ $0 $@
|
||||
@ -3057,6 +3059,12 @@ $as_echo "$template" >&6; }
|
||||
PORTNAME=$template
|
||||
|
||||
|
||||
# Initialize default assumption that we do not need separate assembly code
|
||||
# for TAS (test-and-set). This can be overridden by the template file
|
||||
# when it's executed.
|
||||
need_tas=no
|
||||
tas_file=dummy.s
|
||||
|
||||
# Default, works for most platforms, override in template file if needed
|
||||
DLSUFFIX=".so"
|
||||
|
||||
@ -4467,48 +4475,189 @@ ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
|
||||
ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
|
||||
ac_compiler_gnu=$ac_cv_c_compiler_gnu
|
||||
|
||||
|
||||
# Detect option needed for C11
|
||||
# loosely modeled after code in later Autoconf versions
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C11" >&5
|
||||
$as_echo_n "checking for $CC option to accept ISO C11... " >&6; }
|
||||
|
||||
if ${pgac_cv_prog_cc_c11+:} false; then :
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C99" >&5
|
||||
$as_echo_n "checking for $CC option to accept ISO C99... " >&6; }
|
||||
if ${ac_cv_prog_cc_c99+:} false; then :
|
||||
$as_echo_n "(cached) " >&6
|
||||
else
|
||||
pgac_cv_prog_cc_c11=no
|
||||
pgac_save_CC=$CC
|
||||
for pgac_arg in '' '-std=gnu11' '-std=c11'; do
|
||||
CC="$pgac_save_CC $pgac_arg"
|
||||
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
ac_cv_prog_cc_c99=no
|
||||
ac_save_CC=$CC
|
||||
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
/* end confdefs.h. */
|
||||
#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 201112L
|
||||
# error "Compiler does not advertise C11 conformance"
|
||||
#include <stdarg.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdlib.h>
|
||||
#include <wchar.h>
|
||||
#include <stdio.h>
|
||||
|
||||
// Check varargs macros. These examples are taken from C99 6.10.3.5.
|
||||
#define debug(...) fprintf (stderr, __VA_ARGS__)
|
||||
#define showlist(...) puts (#__VA_ARGS__)
|
||||
#define report(test,...) ((test) ? puts (#test) : printf (__VA_ARGS__))
|
||||
static void
|
||||
test_varargs_macros (void)
|
||||
{
|
||||
int x = 1234;
|
||||
int y = 5678;
|
||||
debug ("Flag");
|
||||
debug ("X = %d\n", x);
|
||||
showlist (The first, second, and third items.);
|
||||
report (x>y, "x is %d but y is %d", x, y);
|
||||
}
|
||||
|
||||
// Check long long types.
|
||||
#define BIG64 18446744073709551615ull
|
||||
#define BIG32 4294967295ul
|
||||
#define BIG_OK (BIG64 / BIG32 == 4294967297ull && BIG64 % BIG32 == 0)
|
||||
#if !BIG_OK
|
||||
your preprocessor is broken;
|
||||
#endif
|
||||
#if BIG_OK
|
||||
#else
|
||||
your preprocessor is broken;
|
||||
#endif
|
||||
static long long int bignum = -9223372036854775807LL;
|
||||
static unsigned long long int ubignum = BIG64;
|
||||
|
||||
struct incomplete_array
|
||||
{
|
||||
int datasize;
|
||||
double data[];
|
||||
};
|
||||
|
||||
struct named_init {
|
||||
int number;
|
||||
const wchar_t *name;
|
||||
double average;
|
||||
};
|
||||
|
||||
typedef const char *ccp;
|
||||
|
||||
static inline int
|
||||
test_restrict (ccp restrict text)
|
||||
{
|
||||
// See if C++-style comments work.
|
||||
// Iterate through items via the restricted pointer.
|
||||
// Also check for declarations in for loops.
|
||||
for (unsigned int i = 0; *(text+i) != '\0'; ++i)
|
||||
continue;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Check varargs and va_copy.
|
||||
static void
|
||||
test_varargs (const char *format, ...)
|
||||
{
|
||||
va_list args;
|
||||
va_start (args, format);
|
||||
va_list args_copy;
|
||||
va_copy (args_copy, args);
|
||||
|
||||
const char *str;
|
||||
int number;
|
||||
float fnumber;
|
||||
|
||||
while (*format)
|
||||
{
|
||||
switch (*format++)
|
||||
{
|
||||
case 's': // string
|
||||
str = va_arg (args_copy, const char *);
|
||||
break;
|
||||
case 'd': // int
|
||||
number = va_arg (args_copy, int);
|
||||
break;
|
||||
case 'f': // float
|
||||
fnumber = va_arg (args_copy, double);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
va_end (args_copy);
|
||||
va_end (args);
|
||||
}
|
||||
|
||||
int
|
||||
main ()
|
||||
{
|
||||
|
||||
// Check bool.
|
||||
_Bool success = false;
|
||||
|
||||
// Check restrict.
|
||||
if (test_restrict ("String literal") == 0)
|
||||
success = true;
|
||||
char *restrict newvar = "Another string";
|
||||
|
||||
// Check varargs.
|
||||
test_varargs ("s, d' f .", "string", 65, 34.234);
|
||||
test_varargs_macros ();
|
||||
|
||||
// Check flexible array members.
|
||||
struct incomplete_array *ia =
|
||||
malloc (sizeof (struct incomplete_array) + (sizeof (double) * 10));
|
||||
ia->datasize = 10;
|
||||
for (int i = 0; i < ia->datasize; ++i)
|
||||
ia->data[i] = i * 1.234;
|
||||
|
||||
// Check named initializers.
|
||||
struct named_init ni = {
|
||||
.number = 34,
|
||||
.name = L"Test wide string",
|
||||
.average = 543.34343,
|
||||
};
|
||||
|
||||
ni.number = 58;
|
||||
|
||||
int dynamic_array[ni.number];
|
||||
dynamic_array[ni.number - 1] = 543;
|
||||
|
||||
// work around unused variable warnings
|
||||
return (!success || bignum == 0LL || ubignum == 0uLL || newvar[0] == 'x'
|
||||
|| dynamic_array[ni.number - 1] != 543);
|
||||
|
||||
;
|
||||
return 0;
|
||||
}
|
||||
_ACEOF
|
||||
if ac_fn_c_try_compile "$LINENO"; then :
|
||||
pgac_cv_prog_cc_c11=$pgac_arg
|
||||
for ac_arg in '' -std=gnu99 -std=c99 -c99 -AC99 -D_STDC_C99= -qlanglvl=extc99
|
||||
do
|
||||
CC="$ac_save_CC $ac_arg"
|
||||
if ac_fn_c_try_compile "$LINENO"; then :
|
||||
ac_cv_prog_cc_c99=$ac_arg
|
||||
fi
|
||||
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
test x"$pgac_cv_prog_cc_c11" != x"no" && break
|
||||
rm -f core conftest.err conftest.$ac_objext
|
||||
test "x$ac_cv_prog_cc_c99" != "xno" && break
|
||||
done
|
||||
CC=$pgac_save_CC
|
||||
rm -f conftest.$ac_ext
|
||||
CC=$ac_save_CC
|
||||
|
||||
fi
|
||||
# AC_CACHE_VAL
|
||||
case "x$ac_cv_prog_cc_c99" in
|
||||
x)
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5
|
||||
$as_echo "none needed" >&6; } ;;
|
||||
xno)
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5
|
||||
$as_echo "unsupported" >&6; } ;;
|
||||
*)
|
||||
CC="$CC $ac_cv_prog_cc_c99"
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c99" >&5
|
||||
$as_echo "$ac_cv_prog_cc_c99" >&6; } ;;
|
||||
esac
|
||||
if test "x$ac_cv_prog_cc_c99" != xno; then :
|
||||
|
||||
fi
|
||||
|
||||
|
||||
if test x"$pgac_cv_prog_cc_c11" = x"no"; then
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5
|
||||
$as_echo "unsupported" >&6; }
|
||||
as_fn_error $? "C compiler \"$CC\" does not support C11" "$LINENO" 5
|
||||
elif test x"$pgac_cv_prog_cc_c11" = x""; then
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5
|
||||
$as_echo "none needed" >&6; }
|
||||
else
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $pgac_cv_prog_cc_c11" >&5
|
||||
$as_echo "$pgac_cv_prog_cc_c11" >&6; }
|
||||
CC="$CC $pgac_cv_prog_cc_c11"
|
||||
fi
|
||||
|
||||
# Error out if the compiler does not support C99, as the codebase
|
||||
# relies on that.
|
||||
if test "$ac_cv_prog_cc_c99" = no; then
|
||||
as_fn_error $? "C compiler \"$CC\" does not support C99" "$LINENO" 5
|
||||
fi
|
||||
|
||||
ac_ext=cpp
|
||||
ac_cpp='$CXXCPP $CPPFLAGS'
|
||||
@ -4771,6 +4920,7 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu
|
||||
# Check if it's Intel's compiler, which (usually) pretends to be gcc,
|
||||
# but has idiosyncrasies of its own. We assume icc will define
|
||||
# __INTEL_COMPILER regardless of CFLAGS.
|
||||
|
||||
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
/* end confdefs.h. */
|
||||
|
||||
@ -4791,6 +4941,30 @@ else
|
||||
fi
|
||||
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
|
||||
# Check if it's Sun Studio compiler. We assume that
|
||||
# __SUNPRO_C will be defined for Sun Studio compilers
|
||||
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
/* end confdefs.h. */
|
||||
|
||||
int
|
||||
main ()
|
||||
{
|
||||
#ifndef __SUNPRO_C
|
||||
choke me
|
||||
#endif
|
||||
;
|
||||
return 0;
|
||||
}
|
||||
_ACEOF
|
||||
if ac_fn_c_try_compile "$LINENO"; then :
|
||||
SUN_STUDIO_CC=yes
|
||||
else
|
||||
SUN_STUDIO_CC=no
|
||||
fi
|
||||
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
|
||||
|
||||
|
||||
|
||||
#
|
||||
# LLVM
|
||||
@ -6716,7 +6890,7 @@ fi
|
||||
# __attribute__((visibility("hidden"))) is supported, if we encounter a
|
||||
# compiler that supports one of the supported variants of -fvisibility=hidden
|
||||
# but uses a different syntax to mark a symbol as exported.
|
||||
if test "$GCC" = yes; then
|
||||
if test "$GCC" = yes -o "$SUN_STUDIO_CC" = yes ; then
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ${CC} supports -fvisibility=hidden, for CFLAGS_SL_MODULE" >&5
|
||||
$as_echo_n "checking whether ${CC} supports -fvisibility=hidden, for CFLAGS_SL_MODULE... " >&6; }
|
||||
if ${pgac_cv_prog_CC_cflags__fvisibility_hidden+:} false; then :
|
||||
@ -7699,6 +7873,20 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu
|
||||
|
||||
|
||||
|
||||
#
|
||||
# Set up TAS assembly code if needed; the template file has now had its
|
||||
# chance to request this.
|
||||
#
|
||||
ac_config_links="$ac_config_links src/backend/port/tas.s:src/backend/port/tas/${tas_file}"
|
||||
|
||||
|
||||
if test "$need_tas" = yes ; then
|
||||
TAS=tas.o
|
||||
else
|
||||
TAS=""
|
||||
fi
|
||||
|
||||
|
||||
|
||||
cat >>confdefs.h <<_ACEOF
|
||||
#define DLSUFFIX "$DLSUFFIX"
|
||||
@ -17095,7 +17283,7 @@ else
|
||||
/* end confdefs.h. */
|
||||
|
||||
/* This must match the corresponding code in c.h: */
|
||||
#if defined(__GNUC__)
|
||||
#if defined(__GNUC__) || defined(__SUNPRO_C)
|
||||
#define pg_attribute_aligned(a) __attribute__((aligned(a)))
|
||||
#elif defined(_MSC_VER)
|
||||
#define pg_attribute_aligned(a) __declspec(align(a))
|
||||
@ -19298,6 +19486,8 @@ fi
|
||||
if test x"$GCC" = x"yes" ; then
|
||||
cc_string=`${CC} --version | sed q`
|
||||
case $cc_string in [A-Za-z]*) ;; *) cc_string="GCC $cc_string";; esac
|
||||
elif test x"$SUN_STUDIO_CC" = x"yes" ; then
|
||||
cc_string=`${CC} -V 2>&1 | sed q`
|
||||
else
|
||||
cc_string=$CC
|
||||
fi
|
||||
@ -19899,7 +20089,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
|
||||
# report actual input values of CONFIG_FILES etc. instead of their
|
||||
# values after options handling.
|
||||
ac_log="
|
||||
This file was extended by PostgreSQL $as_me 19devel, which was
|
||||
This file was extended by PostgreSQL $as_me 18beta3, which was
|
||||
generated by GNU Autoconf 2.69. Invocation command line was
|
||||
|
||||
CONFIG_FILES = $CONFIG_FILES
|
||||
@ -19970,7 +20160,7 @@ _ACEOF
|
||||
cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
|
||||
ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
|
||||
ac_cs_version="\\
|
||||
PostgreSQL config.status 19devel
|
||||
PostgreSQL config.status 18beta3
|
||||
configured by $0, generated by GNU Autoconf 2.69,
|
||||
with options \\"\$ac_cs_config\\"
|
||||
|
||||
@ -20094,6 +20284,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
|
||||
for ac_config_target in $ac_config_targets
|
||||
do
|
||||
case $ac_config_target in
|
||||
"src/backend/port/tas.s") CONFIG_LINKS="$CONFIG_LINKS src/backend/port/tas.s:src/backend/port/tas/${tas_file}" ;;
|
||||
"GNUmakefile") CONFIG_FILES="$CONFIG_FILES GNUmakefile" ;;
|
||||
"src/Makefile.global") CONFIG_FILES="$CONFIG_FILES src/Makefile.global" ;;
|
||||
"src/backend/port/pg_sema.c") CONFIG_LINKS="$CONFIG_LINKS src/backend/port/pg_sema.c:${SEMA_IMPLEMENTATION}" ;;
|
||||
|
62
configure.ac
62
configure.ac
@ -17,7 +17,7 @@ dnl Read the Autoconf manual for details.
|
||||
dnl
|
||||
m4_pattern_forbid(^PGAC_)dnl to catch undefined macros
|
||||
|
||||
AC_INIT([PostgreSQL], [19devel], [pgsql-bugs@lists.postgresql.org], [], [https://www.postgresql.org/])
|
||||
AC_INIT([PostgreSQL], [18beta3], [pgsql-bugs@lists.postgresql.org], [], [https://www.postgresql.org/])
|
||||
|
||||
m4_if(m4_defn([m4_PACKAGE_VERSION]), [2.69], [], [m4_fatal([Autoconf version 2.69 is required.
|
||||
Untested combinations of 'autoconf' and PostgreSQL versions are not
|
||||
@ -95,6 +95,12 @@ AC_MSG_RESULT([$template])
|
||||
PORTNAME=$template
|
||||
AC_SUBST(PORTNAME)
|
||||
|
||||
# Initialize default assumption that we do not need separate assembly code
|
||||
# for TAS (test-and-set). This can be overridden by the template file
|
||||
# when it's executed.
|
||||
need_tas=no
|
||||
tas_file=dummy.s
|
||||
|
||||
# Default, works for most platforms, override in template file if needed
|
||||
DLSUFFIX=".so"
|
||||
|
||||
@ -358,33 +364,14 @@ pgac_cc_list="gcc cc"
|
||||
pgac_cxx_list="g++ c++"
|
||||
|
||||
AC_PROG_CC([$pgac_cc_list])
|
||||
AC_PROG_CC_C99()
|
||||
|
||||
# Detect option needed for C11
|
||||
# loosely modeled after code in later Autoconf versions
|
||||
AC_MSG_CHECKING([for $CC option to accept ISO C11])
|
||||
AC_CACHE_VAL([pgac_cv_prog_cc_c11],
|
||||
[pgac_cv_prog_cc_c11=no
|
||||
pgac_save_CC=$CC
|
||||
for pgac_arg in '' '-std=gnu11' '-std=c11'; do
|
||||
CC="$pgac_save_CC $pgac_arg"
|
||||
AC_COMPILE_IFELSE([AC_LANG_SOURCE([[#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 201112L
|
||||
# error "Compiler does not advertise C11 conformance"
|
||||
#endif]])], [[pgac_cv_prog_cc_c11=$pgac_arg]])
|
||||
test x"$pgac_cv_prog_cc_c11" != x"no" && break
|
||||
done
|
||||
CC=$pgac_save_CC])
|
||||
|
||||
if test x"$pgac_cv_prog_cc_c11" = x"no"; then
|
||||
AC_MSG_RESULT([unsupported])
|
||||
AC_MSG_ERROR([C compiler "$CC" does not support C11])
|
||||
elif test x"$pgac_cv_prog_cc_c11" = x""; then
|
||||
AC_MSG_RESULT([none needed])
|
||||
else
|
||||
AC_MSG_RESULT([$pgac_cv_prog_cc_c11])
|
||||
CC="$CC $pgac_cv_prog_cc_c11"
|
||||
# Error out if the compiler does not support C99, as the codebase
|
||||
# relies on that.
|
||||
if test "$ac_cv_prog_cc_c99" = no; then
|
||||
AC_MSG_ERROR([C compiler "$CC" does not support C99])
|
||||
fi
|
||||
|
||||
|
||||
AC_PROG_CXX([$pgac_cxx_list])
|
||||
|
||||
# Check if it's Intel's compiler, which (usually) pretends to be gcc,
|
||||
@ -394,6 +381,14 @@ AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], [@%:@ifndef __INTEL_COMPILER
|
||||
choke me
|
||||
@%:@endif])], [ICC=yes], [ICC=no])
|
||||
|
||||
# Check if it's Sun Studio compiler. We assume that
|
||||
# __SUNPRO_C will be defined for Sun Studio compilers
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([], [@%:@ifndef __SUNPRO_C
|
||||
choke me
|
||||
@%:@endif])], [SUN_STUDIO_CC=yes], [SUN_STUDIO_CC=no])
|
||||
|
||||
AC_SUBST(SUN_STUDIO_CC)
|
||||
|
||||
|
||||
#
|
||||
# LLVM
|
||||
@ -604,7 +599,7 @@ fi
|
||||
# __attribute__((visibility("hidden"))) is supported, if we encounter a
|
||||
# compiler that supports one of the supported variants of -fvisibility=hidden
|
||||
# but uses a different syntax to mark a symbol as exported.
|
||||
if test "$GCC" = yes; then
|
||||
if test "$GCC" = yes -o "$SUN_STUDIO_CC" = yes ; then
|
||||
PGAC_PROG_CC_VAR_OPT(CFLAGS_SL_MODULE, [-fvisibility=hidden])
|
||||
# For C++ we additionally want -fvisibility-inlines-hidden
|
||||
PGAC_PROG_VARCXX_VARFLAGS_OPT(CXX, CXXFLAGS_SL_MODULE, [-fvisibility=hidden])
|
||||
@ -760,6 +755,19 @@ AC_PROG_CPP
|
||||
AC_SUBST(GCC)
|
||||
|
||||
|
||||
#
|
||||
# Set up TAS assembly code if needed; the template file has now had its
|
||||
# chance to request this.
|
||||
#
|
||||
AC_CONFIG_LINKS([src/backend/port/tas.s:src/backend/port/tas/${tas_file}])
|
||||
|
||||
if test "$need_tas" = yes ; then
|
||||
TAS=tas.o
|
||||
else
|
||||
TAS=""
|
||||
fi
|
||||
AC_SUBST(TAS)
|
||||
|
||||
AC_SUBST(DLSUFFIX)dnl
|
||||
AC_DEFINE_UNQUOTED([DLSUFFIX], ["$DLSUFFIX"],
|
||||
[Define to the file name extension of dynamically-loadable modules.])
|
||||
@ -2451,6 +2459,8 @@ AC_SUBST(LDFLAGS_EX_BE)
|
||||
if test x"$GCC" = x"yes" ; then
|
||||
cc_string=`${CC} --version | sed q`
|
||||
case $cc_string in [[A-Za-z]]*) ;; *) cc_string="GCC $cc_string";; esac
|
||||
elif test x"$SUN_STUDIO_CC" = x"yes" ; then
|
||||
cc_string=`${CC} -V 2>&1 | sed q`
|
||||
else
|
||||
cc_string=$CC
|
||||
fi
|
||||
|
@ -60,14 +60,6 @@ SELECT bt_index_parent_check('bttest_a_brin_idx');
|
||||
ERROR: expected "btree" index as targets for verification
|
||||
DETAIL: Relation "bttest_a_brin_idx" is a brin index.
|
||||
ROLLBACK;
|
||||
-- verify partitioned indexes are rejected (error)
|
||||
BEGIN;
|
||||
CREATE TABLE bttest_partitioned (a int, b int) PARTITION BY list (a);
|
||||
CREATE INDEX bttest_btree_partitioned_idx ON bttest_partitioned USING btree (b);
|
||||
SELECT bt_index_parent_check('bttest_btree_partitioned_idx');
|
||||
ERROR: expected index as targets for verification
|
||||
DETAIL: This operation is not supported for partitioned indexes.
|
||||
ROLLBACK;
|
||||
-- normal check outside of xact
|
||||
SELECT bt_index_check('bttest_a_idx');
|
||||
bt_index_check
|
||||
|
@ -52,13 +52,6 @@ CREATE INDEX bttest_a_brin_idx ON bttest_a USING brin(id);
|
||||
SELECT bt_index_parent_check('bttest_a_brin_idx');
|
||||
ROLLBACK;
|
||||
|
||||
-- verify partitioned indexes are rejected (error)
|
||||
BEGIN;
|
||||
CREATE TABLE bttest_partitioned (a int, b int) PARTITION BY list (a);
|
||||
CREATE INDEX bttest_btree_partitioned_idx ON bttest_partitioned USING btree (b);
|
||||
SELECT bt_index_parent_check('bttest_btree_partitioned_idx');
|
||||
ROLLBACK;
|
||||
|
||||
-- normal check outside of xact
|
||||
SELECT bt_index_check('bttest_a_idx');
|
||||
-- more expansive tests
|
||||
|
@ -18,13 +18,11 @@
|
||||
#include "verify_common.h"
|
||||
#include "catalog/index.h"
|
||||
#include "catalog/pg_am.h"
|
||||
#include "commands/defrem.h"
|
||||
#include "commands/tablecmds.h"
|
||||
#include "utils/guc.h"
|
||||
#include "utils/syscache.h"
|
||||
|
||||
static bool amcheck_index_mainfork_expected(Relation rel);
|
||||
static bool index_checkable(Relation rel, Oid am_id);
|
||||
|
||||
|
||||
/*
|
||||
@ -157,21 +155,23 @@ amcheck_lock_relation_and_check(Oid indrelid,
|
||||
* callable by non-superusers. If granted, it's useful to be able to check a
|
||||
* whole cluster.
|
||||
*/
|
||||
static bool
|
||||
bool
|
||||
index_checkable(Relation rel, Oid am_id)
|
||||
{
|
||||
if (rel->rd_rel->relkind != RELKIND_INDEX)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
|
||||
errmsg("expected index as targets for verification"),
|
||||
errdetail_relkind_not_supported(rel->rd_rel->relkind)));
|
||||
if (rel->rd_rel->relkind != RELKIND_INDEX ||
|
||||
rel->rd_rel->relam != am_id)
|
||||
{
|
||||
HeapTuple amtup;
|
||||
HeapTuple amtuprel;
|
||||
|
||||
if (rel->rd_rel->relam != am_id)
|
||||
amtup = SearchSysCache1(AMOID, ObjectIdGetDatum(am_id));
|
||||
amtuprel = SearchSysCache1(AMOID, ObjectIdGetDatum(rel->rd_rel->relam));
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
|
||||
errmsg("expected \"%s\" index as targets for verification", get_am_name(am_id)),
|
||||
errmsg("expected \"%s\" index as targets for verification", NameStr(((Form_pg_am) GETSTRUCT(amtup))->amname)),
|
||||
errdetail("Relation \"%s\" is a %s index.",
|
||||
RelationGetRelationName(rel), get_am_name(rel->rd_rel->relam))));
|
||||
RelationGetRelationName(rel), NameStr(((Form_pg_am) GETSTRUCT(amtuprel))->amname))));
|
||||
}
|
||||
|
||||
if (RELATION_IS_OTHER_TEMP(rel))
|
||||
ereport(ERROR,
|
||||
@ -182,7 +182,7 @@ index_checkable(Relation rel, Oid am_id)
|
||||
|
||||
if (!rel->rd_index->indisvalid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
|
||||
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
|
||||
errmsg("cannot check index \"%s\"",
|
||||
RelationGetRelationName(rel)),
|
||||
errdetail("Index is not valid.")));
|
||||
|
@ -1,12 +1,12 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* verify_common.h
|
||||
* amcheck.h
|
||||
* Shared routines for amcheck verifications.
|
||||
*
|
||||
* Copyright (c) 2016-2025, PostgreSQL Global Development Group
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* contrib/amcheck/verify_common.h
|
||||
* contrib/amcheck/amcheck.h
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -16,7 +16,8 @@
|
||||
#include "utils/relcache.h"
|
||||
#include "miscadmin.h"
|
||||
|
||||
/* Typedef for callback function for amcheck_lock_relation_and_check */
|
||||
/* Typedefs for callback functions for amcheck_lock_relation_and_check */
|
||||
typedef void (*IndexCheckableCallback) (Relation index);
|
||||
typedef void (*IndexDoCheckCallback) (Relation rel,
|
||||
Relation heaprel,
|
||||
void *state,
|
||||
@ -26,3 +27,5 @@ extern void amcheck_lock_relation_and_check(Oid indrelid,
|
||||
Oid am_id,
|
||||
IndexDoCheckCallback check,
|
||||
LOCKMODE lockmode, void *state);
|
||||
|
||||
extern bool index_checkable(Relation rel, Oid am_id);
|
||||
|
@ -174,7 +174,7 @@ gin_check_posting_tree_parent_keys_consistency(Relation rel, BlockNumber posting
|
||||
buffer = ReadBufferExtended(rel, MAIN_FORKNUM, stack->blkno,
|
||||
RBM_NORMAL, strategy);
|
||||
LockBuffer(buffer, GIN_SHARE);
|
||||
page = BufferGetPage(buffer);
|
||||
page = (Page) BufferGetPage(buffer);
|
||||
|
||||
Assert(GinPageIsData(page));
|
||||
|
||||
@ -434,7 +434,7 @@ gin_check_parent_keys_consistency(Relation rel,
|
||||
buffer = ReadBufferExtended(rel, MAIN_FORKNUM, stack->blkno,
|
||||
RBM_NORMAL, strategy);
|
||||
LockBuffer(buffer, GIN_SHARE);
|
||||
page = BufferGetPage(buffer);
|
||||
page = (Page) BufferGetPage(buffer);
|
||||
maxoff = PageGetMaxOffsetNumber(page);
|
||||
rightlink = GinPageGetOpaque(page)->rightlink;
|
||||
|
||||
|
@ -1942,7 +1942,7 @@ check_tuple(HeapCheckContext *ctx, bool *xmin_commit_status_ok,
|
||||
if (RelationGetDescr(ctx->rel)->natts < ctx->natts)
|
||||
{
|
||||
report_corruption(ctx,
|
||||
psprintf("number of attributes %u exceeds maximum %u expected for table",
|
||||
psprintf("number of attributes %u exceeds maximum expected for table %u",
|
||||
ctx->natts,
|
||||
RelationGetDescr(ctx->rel)->natts));
|
||||
return;
|
||||
|
@ -913,7 +913,7 @@ bt_report_duplicate(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("index uniqueness is violated for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail("Index %s%s and%s%s (point to heap %s and %s) page lsn=%X/%08X.",
|
||||
errdetail("Index %s%s and%s%s (point to heap %s and %s) page lsn=%X/%X.",
|
||||
itid, pposting, nitid, pnposting, htid, nhtid,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -1058,7 +1058,7 @@ bt_leftmost_ignoring_half_dead(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_NO_DATA),
|
||||
errmsg_internal("harmless interrupted page deletion detected in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Block=%u right block=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Block=%u right block=%u page lsn=%X/%X.",
|
||||
reached, reached_from,
|
||||
LSN_FORMAT_ARGS(pagelsn))));
|
||||
|
||||
@ -1283,7 +1283,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("wrong number of high key index tuple attributes in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index block=%u natts=%u block type=%s page lsn=%X/%08X.",
|
||||
errdetail_internal("Index block=%u natts=%u block type=%s page lsn=%X/%X.",
|
||||
state->targetblock,
|
||||
BTreeTupleGetNAtts(itup, state->rel),
|
||||
P_ISLEAF(topaque) ? "heap" : "index",
|
||||
@ -1332,7 +1332,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("index tuple size does not equal lp_len in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=(%u,%u) tuple size=%zu lp_len=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=(%u,%u) tuple size=%zu lp_len=%u page lsn=%X/%X.",
|
||||
state->targetblock, offset,
|
||||
tupsize, ItemIdGetLength(itemid),
|
||||
LSN_FORMAT_ARGS(state->targetlsn)),
|
||||
@ -1356,7 +1356,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("wrong number of index tuple attributes in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=%s natts=%u points to %s tid=%s page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=%s natts=%u points to %s tid=%s page lsn=%X/%X.",
|
||||
itid,
|
||||
BTreeTupleGetNAtts(itup, state->rel),
|
||||
P_ISLEAF(topaque) ? "heap" : "index",
|
||||
@ -1406,7 +1406,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("could not find tuple using search from root page in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=%s points to heap tid=%s page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=%s points to heap tid=%s page lsn=%X/%X.",
|
||||
itid, htid,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -1435,7 +1435,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg_internal("posting list contains misplaced TID in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=%s posting list offset=%d page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=%s posting list offset=%d page lsn=%X/%X.",
|
||||
itid, i,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -1488,7 +1488,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("index row size %zu exceeds maximum for index \"%s\"",
|
||||
tupsize, RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=%s points to %s tid=%s page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=%s points to %s tid=%s page lsn=%X/%X.",
|
||||
itid,
|
||||
P_ISLEAF(topaque) ? "heap" : "index",
|
||||
htid,
|
||||
@ -1595,7 +1595,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("high key invariant violated for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Index tid=%s points to %s tid=%s page lsn=%X/%08X.",
|
||||
errdetail_internal("Index tid=%s points to %s tid=%s page lsn=%X/%X.",
|
||||
itid,
|
||||
P_ISLEAF(topaque) ? "heap" : "index",
|
||||
htid,
|
||||
@ -1641,7 +1641,9 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("item order invariant violated for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Lower index tid=%s (points to %s tid=%s) higher index tid=%s (points to %s tid=%s) page lsn=%X/%08X.",
|
||||
errdetail_internal("Lower index tid=%s (points to %s tid=%s) "
|
||||
"higher index tid=%s (points to %s tid=%s) "
|
||||
"page lsn=%X/%X.",
|
||||
itid,
|
||||
P_ISLEAF(topaque) ? "heap" : "index",
|
||||
htid,
|
||||
@ -1758,7 +1760,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("cross page item order invariant violated for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Last item on page tid=(%u,%u) page lsn=%X/%08X.",
|
||||
errdetail_internal("Last item on page tid=(%u,%u) page lsn=%X/%X.",
|
||||
state->targetblock, offset,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -1811,7 +1813,7 @@ bt_target_page_check(BtreeCheckState *state)
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("right block of leaf block is non-leaf for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Block=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Block=%u page lsn=%X/%X.",
|
||||
state->targetblock,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
|
||||
@ -2235,7 +2237,7 @@ bt_child_highkey_check(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("the first child of leftmost target page is not leftmost of its level in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%08X.",
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%X.",
|
||||
state->targetblock, blkno,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
|
||||
@ -2321,7 +2323,7 @@ bt_child_highkey_check(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("child high key is greater than rightmost pivot key on target level in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%08X.",
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%X.",
|
||||
state->targetblock, blkno,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
pivotkey_offset = P_HIKEY;
|
||||
@ -2351,7 +2353,7 @@ bt_child_highkey_check(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("can't find left sibling high key in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%08X.",
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%X.",
|
||||
state->targetblock, blkno,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
itup = state->lowkey;
|
||||
@ -2363,7 +2365,7 @@ bt_child_highkey_check(BtreeCheckState *state,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("mismatch between parent key and child high key in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%08X.",
|
||||
errdetail_internal("Target block=%u child block=%u target page lsn=%X/%X.",
|
||||
state->targetblock, blkno,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -2503,7 +2505,7 @@ bt_child_check(BtreeCheckState *state, BTScanInsert targetkey,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("downlink to deleted page found in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Parent block=%u child block=%u parent page lsn=%X/%08X.",
|
||||
errdetail_internal("Parent block=%u child block=%u parent page lsn=%X/%X.",
|
||||
state->targetblock, childblock,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
|
||||
@ -2544,7 +2546,7 @@ bt_child_check(BtreeCheckState *state, BTScanInsert targetkey,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("down-link lower bound invariant violated for index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Parent block=%u child index tid=(%u,%u) parent page lsn=%X/%08X.",
|
||||
errdetail_internal("Parent block=%u child index tid=(%u,%u) parent page lsn=%X/%X.",
|
||||
state->targetblock, childblock, offset,
|
||||
LSN_FORMAT_ARGS(state->targetlsn))));
|
||||
}
|
||||
@ -2614,7 +2616,7 @@ bt_downlink_missing_check(BtreeCheckState *state, bool rightsplit,
|
||||
(errcode(ERRCODE_NO_DATA),
|
||||
errmsg_internal("harmless interrupted page split detected in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Block=%u level=%u left sibling=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Block=%u level=%u left sibling=%u page lsn=%X/%X.",
|
||||
blkno, opaque->btpo_level,
|
||||
opaque->btpo_prev,
|
||||
LSN_FORMAT_ARGS(pagelsn))));
|
||||
@ -2636,7 +2638,7 @@ bt_downlink_missing_check(BtreeCheckState *state, bool rightsplit,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("leaf index block lacks downlink in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Block=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Block=%u page lsn=%X/%X.",
|
||||
blkno,
|
||||
LSN_FORMAT_ARGS(pagelsn))));
|
||||
|
||||
@ -2702,7 +2704,7 @@ bt_downlink_missing_check(BtreeCheckState *state, bool rightsplit,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg_internal("downlink to deleted leaf page found in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Top parent/target block=%u leaf block=%u top parent/under check lsn=%X/%08X.",
|
||||
errdetail_internal("Top parent/target block=%u leaf block=%u top parent/under check lsn=%X/%X.",
|
||||
blkno, childblk,
|
||||
LSN_FORMAT_ARGS(pagelsn))));
|
||||
|
||||
@ -2728,7 +2730,7 @@ bt_downlink_missing_check(BtreeCheckState *state, bool rightsplit,
|
||||
(errcode(ERRCODE_INDEX_CORRUPTED),
|
||||
errmsg("internal index block lacks downlink in index \"%s\"",
|
||||
RelationGetRelationName(state->rel)),
|
||||
errdetail_internal("Block=%u level=%u page lsn=%X/%08X.",
|
||||
errdetail_internal("Block=%u level=%u page lsn=%X/%X.",
|
||||
blkno, opaque->btpo_level,
|
||||
LSN_FORMAT_ARGS(pagelsn))));
|
||||
}
|
||||
|
@ -24,7 +24,7 @@ tests += {
|
||||
'tests': [
|
||||
't/001_basic.pl',
|
||||
],
|
||||
'env': {'GZIP_PROGRAM': gzip.found() ? gzip.full_path() : '',
|
||||
'TAR': tar.found() ? tar.full_path() : '' },
|
||||
'env': {'GZIP_PROGRAM': gzip.found() ? gzip.path() : '',
|
||||
'TAR': tar.found() ? tar.path() : '' },
|
||||
},
|
||||
}
|
||||
|
@ -65,7 +65,7 @@ void
|
||||
_PG_init(void)
|
||||
{
|
||||
DefineCustomStringVariable("basic_archive.archive_directory",
|
||||
"Archive file destination directory.",
|
||||
gettext_noop("Archive file destination directory."),
|
||||
NULL,
|
||||
&archive_directory,
|
||||
"",
|
||||
|
@ -192,7 +192,7 @@ blvacuumcleanup(IndexVacuumInfo *info, IndexBulkDeleteResult *stats)
|
||||
buffer = ReadBufferExtended(index, MAIN_FORKNUM, blkno,
|
||||
RBM_NORMAL, info->strategy);
|
||||
LockBuffer(buffer, BUFFER_LOCK_SHARE);
|
||||
page = BufferGetPage(buffer);
|
||||
page = (Page) BufferGetPage(buffer);
|
||||
|
||||
if (PageIsNew(page) || BloomPageIsDeleted(page))
|
||||
{
|
||||
|
@ -7,7 +7,7 @@ OBJS = \
|
||||
|
||||
EXTENSION = btree_gin
|
||||
DATA = btree_gin--1.0.sql btree_gin--1.0--1.1.sql btree_gin--1.1--1.2.sql \
|
||||
btree_gin--1.2--1.3.sql btree_gin--1.3--1.4.sql
|
||||
btree_gin--1.2--1.3.sql
|
||||
PGFILEDESC = "btree_gin - B-tree equivalent GIN operator classes"
|
||||
|
||||
REGRESS = install_btree_gin int2 int4 int8 float4 float8 money oid \
|
||||
|
@ -1,151 +0,0 @@
|
||||
/* contrib/btree_gin/btree_gin--1.3--1.4.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via CREATE EXTENSION
|
||||
\echo Use "ALTER EXTENSION btree_gin UPDATE TO '1.4'" to load this file. \quit
|
||||
|
||||
--
|
||||
-- Cross-type operator support is new in 1.4. We only need to worry
|
||||
-- about this for cross-type operators that exist in core.
|
||||
--
|
||||
-- Because the opclass extractQuery and consistent methods don't directly
|
||||
-- get any information about the datatype of the RHS value, we have to
|
||||
-- encode that in the operator strategy numbers. The strategy numbers
|
||||
-- are the operator's normal btree strategy (1-5) plus 16 times a code
|
||||
-- for the RHS datatype.
|
||||
--
|
||||
|
||||
ALTER OPERATOR FAMILY int2_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is int4
|
||||
OPERATOR 0x11 < (int2, int4),
|
||||
OPERATOR 0x12 <= (int2, int4),
|
||||
OPERATOR 0x13 = (int2, int4),
|
||||
OPERATOR 0x14 >= (int2, int4),
|
||||
OPERATOR 0x15 > (int2, int4),
|
||||
-- Code 2: RHS is int8
|
||||
OPERATOR 0x21 < (int2, int8),
|
||||
OPERATOR 0x22 <= (int2, int8),
|
||||
OPERATOR 0x23 = (int2, int8),
|
||||
OPERATOR 0x24 >= (int2, int8),
|
||||
OPERATOR 0x25 > (int2, int8)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY int4_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is int2
|
||||
OPERATOR 0x11 < (int4, int2),
|
||||
OPERATOR 0x12 <= (int4, int2),
|
||||
OPERATOR 0x13 = (int4, int2),
|
||||
OPERATOR 0x14 >= (int4, int2),
|
||||
OPERATOR 0x15 > (int4, int2),
|
||||
-- Code 2: RHS is int8
|
||||
OPERATOR 0x21 < (int4, int8),
|
||||
OPERATOR 0x22 <= (int4, int8),
|
||||
OPERATOR 0x23 = (int4, int8),
|
||||
OPERATOR 0x24 >= (int4, int8),
|
||||
OPERATOR 0x25 > (int4, int8)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY int8_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is int2
|
||||
OPERATOR 0x11 < (int8, int2),
|
||||
OPERATOR 0x12 <= (int8, int2),
|
||||
OPERATOR 0x13 = (int8, int2),
|
||||
OPERATOR 0x14 >= (int8, int2),
|
||||
OPERATOR 0x15 > (int8, int2),
|
||||
-- Code 2: RHS is int4
|
||||
OPERATOR 0x21 < (int8, int4),
|
||||
OPERATOR 0x22 <= (int8, int4),
|
||||
OPERATOR 0x23 = (int8, int4),
|
||||
OPERATOR 0x24 >= (int8, int4),
|
||||
OPERATOR 0x25 > (int8, int4)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY float4_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is float8
|
||||
OPERATOR 0x11 < (float4, float8),
|
||||
OPERATOR 0x12 <= (float4, float8),
|
||||
OPERATOR 0x13 = (float4, float8),
|
||||
OPERATOR 0x14 >= (float4, float8),
|
||||
OPERATOR 0x15 > (float4, float8)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY float8_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is float4
|
||||
OPERATOR 0x11 < (float8, float4),
|
||||
OPERATOR 0x12 <= (float8, float4),
|
||||
OPERATOR 0x13 = (float8, float4),
|
||||
OPERATOR 0x14 >= (float8, float4),
|
||||
OPERATOR 0x15 > (float8, float4)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY text_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is name
|
||||
OPERATOR 0x11 < (text, name),
|
||||
OPERATOR 0x12 <= (text, name),
|
||||
OPERATOR 0x13 = (text, name),
|
||||
OPERATOR 0x14 >= (text, name),
|
||||
OPERATOR 0x15 > (text, name)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY name_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is text
|
||||
OPERATOR 0x11 < (name, text),
|
||||
OPERATOR 0x12 <= (name, text),
|
||||
OPERATOR 0x13 = (name, text),
|
||||
OPERATOR 0x14 >= (name, text),
|
||||
OPERATOR 0x15 > (name, text)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY date_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is timestamp
|
||||
OPERATOR 0x11 < (date, timestamp),
|
||||
OPERATOR 0x12 <= (date, timestamp),
|
||||
OPERATOR 0x13 = (date, timestamp),
|
||||
OPERATOR 0x14 >= (date, timestamp),
|
||||
OPERATOR 0x15 > (date, timestamp),
|
||||
-- Code 2: RHS is timestamptz
|
||||
OPERATOR 0x21 < (date, timestamptz),
|
||||
OPERATOR 0x22 <= (date, timestamptz),
|
||||
OPERATOR 0x23 = (date, timestamptz),
|
||||
OPERATOR 0x24 >= (date, timestamptz),
|
||||
OPERATOR 0x25 > (date, timestamptz)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY timestamp_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is date
|
||||
OPERATOR 0x11 < (timestamp, date),
|
||||
OPERATOR 0x12 <= (timestamp, date),
|
||||
OPERATOR 0x13 = (timestamp, date),
|
||||
OPERATOR 0x14 >= (timestamp, date),
|
||||
OPERATOR 0x15 > (timestamp, date),
|
||||
-- Code 2: RHS is timestamptz
|
||||
OPERATOR 0x21 < (timestamp, timestamptz),
|
||||
OPERATOR 0x22 <= (timestamp, timestamptz),
|
||||
OPERATOR 0x23 = (timestamp, timestamptz),
|
||||
OPERATOR 0x24 >= (timestamp, timestamptz),
|
||||
OPERATOR 0x25 > (timestamp, timestamptz)
|
||||
;
|
||||
|
||||
ALTER OPERATOR FAMILY timestamptz_ops USING gin
|
||||
ADD
|
||||
-- Code 1: RHS is date
|
||||
OPERATOR 0x11 < (timestamptz, date),
|
||||
OPERATOR 0x12 <= (timestamptz, date),
|
||||
OPERATOR 0x13 = (timestamptz, date),
|
||||
OPERATOR 0x14 >= (timestamptz, date),
|
||||
OPERATOR 0x15 > (timestamptz, date),
|
||||
-- Code 2: RHS is timestamp
|
||||
OPERATOR 0x21 < (timestamptz, timestamp),
|
||||
OPERATOR 0x22 <= (timestamptz, timestamp),
|
||||
OPERATOR 0x23 = (timestamptz, timestamp),
|
||||
OPERATOR 0x24 >= (timestamptz, timestamp),
|
||||
OPERATOR 0x25 > (timestamptz, timestamp)
|
||||
;
|
@ -6,7 +6,6 @@
|
||||
#include <limits.h>
|
||||
|
||||
#include "access/stratnum.h"
|
||||
#include "mb/pg_wchar.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/date.h"
|
||||
#include "utils/float.h"
|
||||
@ -14,36 +13,20 @@
|
||||
#include "utils/numeric.h"
|
||||
#include "utils/timestamp.h"
|
||||
#include "utils/uuid.h"
|
||||
#include "varatt.h"
|
||||
|
||||
PG_MODULE_MAGIC_EXT(
|
||||
.name = "btree_gin",
|
||||
.version = PG_VERSION
|
||||
);
|
||||
|
||||
/*
|
||||
* Our opclasses use the same strategy numbers as btree (1-5) for same-type
|
||||
* comparison operators. For cross-type comparison operators, the
|
||||
* low 4 bits of our strategy numbers are the btree strategy number,
|
||||
* and the upper bits are a code for the right-hand-side data type.
|
||||
*/
|
||||
#define BTGIN_GET_BTREE_STRATEGY(strat) ((strat) & 0x0F)
|
||||
#define BTGIN_GET_RHS_TYPE_CODE(strat) ((strat) >> 4)
|
||||
|
||||
/* extra data passed from gin_btree_extract_query to gin_btree_compare_prefix */
|
||||
typedef struct QueryInfo
|
||||
{
|
||||
StrategyNumber strategy; /* operator strategy number */
|
||||
Datum orig_datum; /* original query (comparison) datum */
|
||||
Datum entry_datum; /* datum we reported as the entry value */
|
||||
PGFunction typecmp; /* appropriate btree comparison function */
|
||||
StrategyNumber strategy;
|
||||
Datum datum;
|
||||
bool is_varlena;
|
||||
Datum (*typecmp) (FunctionCallInfo);
|
||||
} QueryInfo;
|
||||
|
||||
typedef Datum (*btree_gin_convert_function) (Datum input);
|
||||
|
||||
typedef Datum (*btree_gin_leftmost_function) (void);
|
||||
|
||||
|
||||
/*** GIN support functions shared by all datatypes ***/
|
||||
|
||||
static Datum
|
||||
@ -53,7 +36,6 @@ gin_btree_extract_value(FunctionCallInfo fcinfo, bool is_varlena)
|
||||
int32 *nentries = (int32 *) PG_GETARG_POINTER(1);
|
||||
Datum *entries = (Datum *) palloc(sizeof(Datum));
|
||||
|
||||
/* Ensure that values stored in the index are not toasted */
|
||||
if (is_varlena)
|
||||
datum = PointerGetDatum(PG_DETOAST_DATUM(datum));
|
||||
entries[0] = datum;
|
||||
@ -62,12 +44,19 @@ gin_btree_extract_value(FunctionCallInfo fcinfo, bool is_varlena)
|
||||
PG_RETURN_POINTER(entries);
|
||||
}
|
||||
|
||||
/*
|
||||
* For BTGreaterEqualStrategyNumber, BTGreaterStrategyNumber, and
|
||||
* BTEqualStrategyNumber we want to start the index scan at the
|
||||
* supplied query datum, and work forward. For BTLessStrategyNumber
|
||||
* and BTLessEqualStrategyNumber, we need to start at the leftmost
|
||||
* key, and work forward until the supplied query datum (which must be
|
||||
* sent along inside the QueryInfo structure).
|
||||
*/
|
||||
static Datum
|
||||
gin_btree_extract_query(FunctionCallInfo fcinfo,
|
||||
btree_gin_leftmost_function leftmostvalue,
|
||||
const bool *rhs_is_varlena,
|
||||
const btree_gin_convert_function *cvt_fns,
|
||||
const PGFunction *cmp_fns)
|
||||
bool is_varlena,
|
||||
Datum (*leftmostvalue) (void),
|
||||
Datum (*typecmp) (FunctionCallInfo))
|
||||
{
|
||||
Datum datum = PG_GETARG_DATUM(0);
|
||||
int32 *nentries = (int32 *) PG_GETARG_POINTER(1);
|
||||
@ -76,40 +65,21 @@ gin_btree_extract_query(FunctionCallInfo fcinfo,
|
||||
Pointer **extra_data = (Pointer **) PG_GETARG_POINTER(4);
|
||||
Datum *entries = (Datum *) palloc(sizeof(Datum));
|
||||
QueryInfo *data = (QueryInfo *) palloc(sizeof(QueryInfo));
|
||||
bool *ptr_partialmatch = (bool *) palloc(sizeof(bool));
|
||||
int btree_strat,
|
||||
rhs_code;
|
||||
bool *ptr_partialmatch;
|
||||
|
||||
/*
|
||||
* Extract the btree strategy code and the RHS data type code from the
|
||||
* given strategy number.
|
||||
*/
|
||||
btree_strat = BTGIN_GET_BTREE_STRATEGY(strategy);
|
||||
rhs_code = BTGIN_GET_RHS_TYPE_CODE(strategy);
|
||||
|
||||
/*
|
||||
* Detoast the comparison datum. This isn't necessary for correctness,
|
||||
* but it can save repeat detoastings within the comparison function.
|
||||
*/
|
||||
if (rhs_is_varlena[rhs_code])
|
||||
datum = PointerGetDatum(PG_DETOAST_DATUM(datum));
|
||||
|
||||
/* Prep single comparison key with possible partial-match flag */
|
||||
*nentries = 1;
|
||||
*partialmatch = ptr_partialmatch;
|
||||
ptr_partialmatch = *partialmatch = (bool *) palloc(sizeof(bool));
|
||||
*ptr_partialmatch = false;
|
||||
if (is_varlena)
|
||||
datum = PointerGetDatum(PG_DETOAST_DATUM(datum));
|
||||
data->strategy = strategy;
|
||||
data->datum = datum;
|
||||
data->is_varlena = is_varlena;
|
||||
data->typecmp = typecmp;
|
||||
*extra_data = (Pointer *) palloc(sizeof(Pointer));
|
||||
**extra_data = (Pointer) data;
|
||||
|
||||
/*
|
||||
* For BTGreaterEqualStrategyNumber, BTGreaterStrategyNumber, and
|
||||
* BTEqualStrategyNumber we want to start the index scan at the supplied
|
||||
* query datum, and work forward. For BTLessStrategyNumber and
|
||||
* BTLessEqualStrategyNumber, we need to start at the leftmost key, and
|
||||
* work forward until the supplied query datum (which we'll send along
|
||||
* inside the QueryInfo structure). Use partial match rules except for
|
||||
* BTEqualStrategyNumber without a conversion function. (If there is a
|
||||
* conversion function, comparison to the entry value is not trustworthy.)
|
||||
*/
|
||||
switch (btree_strat)
|
||||
switch (strategy)
|
||||
{
|
||||
case BTLessStrategyNumber:
|
||||
case BTLessEqualStrategyNumber:
|
||||
@ -121,106 +91,75 @@ gin_btree_extract_query(FunctionCallInfo fcinfo,
|
||||
*ptr_partialmatch = true;
|
||||
/* FALLTHROUGH */
|
||||
case BTEqualStrategyNumber:
|
||||
/* If we have a conversion function, apply it */
|
||||
if (cvt_fns && cvt_fns[rhs_code])
|
||||
{
|
||||
entries[0] = (*cvt_fns[rhs_code]) (datum);
|
||||
*ptr_partialmatch = true;
|
||||
}
|
||||
else
|
||||
entries[0] = datum;
|
||||
entries[0] = datum;
|
||||
break;
|
||||
default:
|
||||
elog(ERROR, "unrecognized strategy number: %d", strategy);
|
||||
}
|
||||
|
||||
/* Fill "extra" data */
|
||||
data->strategy = strategy;
|
||||
data->orig_datum = datum;
|
||||
data->entry_datum = entries[0];
|
||||
data->typecmp = cmp_fns[rhs_code];
|
||||
*extra_data = (Pointer *) palloc(sizeof(Pointer));
|
||||
**extra_data = (Pointer) data;
|
||||
|
||||
PG_RETURN_POINTER(entries);
|
||||
}
|
||||
|
||||
/*
|
||||
* Datum a is a value from extract_query method and for BTLess*
|
||||
* strategy it is a left-most value. So, use original datum from QueryInfo
|
||||
* to decide to stop scanning or not. Datum b is always from index.
|
||||
*/
|
||||
static Datum
|
||||
gin_btree_compare_prefix(FunctionCallInfo fcinfo)
|
||||
{
|
||||
Datum partial_key PG_USED_FOR_ASSERTS_ONLY = PG_GETARG_DATUM(0);
|
||||
Datum key = PG_GETARG_DATUM(1);
|
||||
Datum a = PG_GETARG_DATUM(0);
|
||||
Datum b = PG_GETARG_DATUM(1);
|
||||
QueryInfo *data = (QueryInfo *) PG_GETARG_POINTER(3);
|
||||
int32 res,
|
||||
cmp;
|
||||
|
||||
/*
|
||||
* partial_key is only an approximation to the real comparison value,
|
||||
* especially if it's a leftmost value. We can get an accurate answer by
|
||||
* doing a possibly-cross-type comparison to the real comparison value.
|
||||
* (Note that partial_key and key are of the indexed datatype while
|
||||
* orig_datum is of the query operator's RHS datatype.)
|
||||
*
|
||||
* But just to be sure that things are what we expect, let's assert that
|
||||
* partial_key is indeed what gin_btree_extract_query reported, so that
|
||||
* we'll notice if anyone ever changes the core code in a way that breaks
|
||||
* our assumptions.
|
||||
*/
|
||||
Assert(partial_key == data->entry_datum);
|
||||
|
||||
cmp = DatumGetInt32(CallerFInfoFunctionCall2(data->typecmp,
|
||||
fcinfo->flinfo,
|
||||
PG_GET_COLLATION(),
|
||||
data->orig_datum,
|
||||
key));
|
||||
(data->strategy == BTLessStrategyNumber ||
|
||||
data->strategy == BTLessEqualStrategyNumber)
|
||||
? data->datum : a,
|
||||
b));
|
||||
|
||||
/*
|
||||
* Convert the comparison result to the correct thing for the search
|
||||
* operator strategy. When dealing with cross-type comparisons, an
|
||||
* imprecise entry datum could lead GIN to start the scan just before the
|
||||
* first possible match, so we must continue the scan if the current index
|
||||
* entry doesn't satisfy the search condition for >= and > cases. But if
|
||||
* that happens in an = search we can stop, because an imprecise entry
|
||||
* datum means that the search value is unrepresentable in the indexed
|
||||
* data type, so that there will be no exact matches.
|
||||
*/
|
||||
switch (BTGIN_GET_BTREE_STRATEGY(data->strategy))
|
||||
switch (data->strategy)
|
||||
{
|
||||
case BTLessStrategyNumber:
|
||||
/* If original datum > indexed one then return match */
|
||||
if (cmp > 0)
|
||||
res = 0;
|
||||
else
|
||||
res = 1; /* end scan */
|
||||
res = 1;
|
||||
break;
|
||||
case BTLessEqualStrategyNumber:
|
||||
/* If original datum >= indexed one then return match */
|
||||
/* The same except equality */
|
||||
if (cmp >= 0)
|
||||
res = 0;
|
||||
else
|
||||
res = 1; /* end scan */
|
||||
res = 1;
|
||||
break;
|
||||
case BTEqualStrategyNumber:
|
||||
/* If original datum = indexed one then return match */
|
||||
/* See above about why we can end scan when cmp < 0 */
|
||||
if (cmp == 0)
|
||||
res = 0;
|
||||
if (cmp != 0)
|
||||
res = 1;
|
||||
else
|
||||
res = 1; /* end scan */
|
||||
res = 0;
|
||||
break;
|
||||
case BTGreaterEqualStrategyNumber:
|
||||
/* If original datum <= indexed one then return match */
|
||||
if (cmp <= 0)
|
||||
res = 0;
|
||||
else
|
||||
res = -1; /* keep scanning */
|
||||
res = 1;
|
||||
break;
|
||||
case BTGreaterStrategyNumber:
|
||||
/* If original datum < indexed one then return match */
|
||||
/* If original datum <= indexed one then return match */
|
||||
/* If original datum == indexed one then continue scan */
|
||||
if (cmp < 0)
|
||||
res = 0;
|
||||
else if (cmp == 0)
|
||||
res = -1;
|
||||
else
|
||||
res = -1; /* keep scanning */
|
||||
res = 1;
|
||||
break;
|
||||
default:
|
||||
elog(ERROR, "unrecognized strategy number: %d",
|
||||
@ -243,20 +182,19 @@ gin_btree_consistent(PG_FUNCTION_ARGS)
|
||||
|
||||
/*** GIN_SUPPORT macro defines the datatype specific functions ***/
|
||||
|
||||
#define GIN_SUPPORT(type, leftmostvalue, is_varlena, cvtfns, cmpfns) \
|
||||
#define GIN_SUPPORT(type, is_varlena, leftmostvalue, typecmp) \
|
||||
PG_FUNCTION_INFO_V1(gin_extract_value_##type); \
|
||||
Datum \
|
||||
gin_extract_value_##type(PG_FUNCTION_ARGS) \
|
||||
{ \
|
||||
return gin_btree_extract_value(fcinfo, is_varlena[0]); \
|
||||
return gin_btree_extract_value(fcinfo, is_varlena); \
|
||||
} \
|
||||
PG_FUNCTION_INFO_V1(gin_extract_query_##type); \
|
||||
Datum \
|
||||
gin_extract_query_##type(PG_FUNCTION_ARGS) \
|
||||
{ \
|
||||
return gin_btree_extract_query(fcinfo, \
|
||||
leftmostvalue, is_varlena, \
|
||||
cvtfns, cmpfns); \
|
||||
is_varlena, leftmostvalue, typecmp); \
|
||||
} \
|
||||
PG_FUNCTION_INFO_V1(gin_compare_prefix_##type); \
|
||||
Datum \
|
||||
@ -268,66 +206,13 @@ gin_compare_prefix_##type(PG_FUNCTION_ARGS) \
|
||||
|
||||
/*** Datatype specifications ***/
|
||||
|
||||
/* Function to produce the least possible value of the indexed datatype */
|
||||
static Datum
|
||||
leftmostvalue_int2(void)
|
||||
{
|
||||
return Int16GetDatum(SHRT_MIN);
|
||||
}
|
||||
|
||||
/*
|
||||
* For cross-type support, we must provide conversion functions that produce
|
||||
* a Datum of the indexed datatype, since GIN requires the "entry" datums to
|
||||
* be of that type. If an exact conversion is not possible, produce a value
|
||||
* that will lead GIN to find the first index entry that is greater than
|
||||
* or equal to the actual comparison value. (But rounding down is OK, so
|
||||
* sometimes we might find an index entry that's just less than the
|
||||
* comparison value.)
|
||||
*
|
||||
* For integer values, it's sufficient to clamp the input to be in-range.
|
||||
*
|
||||
* Note: for out-of-range input values, we could in theory detect that the
|
||||
* search condition matches all or none of the index, and avoid a useless
|
||||
* index descent in the latter case. Such searches are probably rare though,
|
||||
* so we don't contort this code enough to do that.
|
||||
*/
|
||||
static Datum
|
||||
cvt_int4_int2(Datum input)
|
||||
{
|
||||
int32 val = DatumGetInt32(input);
|
||||
|
||||
val = Max(val, SHRT_MIN);
|
||||
val = Min(val, SHRT_MAX);
|
||||
return Int16GetDatum((int16) val);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_int8_int2(Datum input)
|
||||
{
|
||||
int64 val = DatumGetInt64(input);
|
||||
|
||||
val = Max(val, SHRT_MIN);
|
||||
val = Min(val, SHRT_MAX);
|
||||
return Int16GetDatum((int16) val);
|
||||
}
|
||||
|
||||
/*
|
||||
* RHS-type-is-varlena flags, conversion and comparison function arrays,
|
||||
* indexed by high bits of the operator strategy number. A NULL in the
|
||||
* conversion function array indicates that no conversion is needed, which
|
||||
* will always be the case for the zero'th entry. Note that the cross-type
|
||||
* comparison functions should be the ones with the indexed datatype second.
|
||||
*/
|
||||
static const bool int2_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function int2_cvt_fns[] =
|
||||
{NULL, cvt_int4_int2, cvt_int8_int2};
|
||||
|
||||
static const PGFunction int2_cmp_fns[] =
|
||||
{btint2cmp, btint42cmp, btint82cmp};
|
||||
|
||||
GIN_SUPPORT(int2, leftmostvalue_int2, int2_rhs_is_varlena, int2_cvt_fns, int2_cmp_fns)
|
||||
GIN_SUPPORT(int2, false, leftmostvalue_int2, btint2cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_int4(void)
|
||||
@ -335,34 +220,7 @@ leftmostvalue_int4(void)
|
||||
return Int32GetDatum(INT_MIN);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_int2_int4(Datum input)
|
||||
{
|
||||
int16 val = DatumGetInt16(input);
|
||||
|
||||
return Int32GetDatum((int32) val);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_int8_int4(Datum input)
|
||||
{
|
||||
int64 val = DatumGetInt64(input);
|
||||
|
||||
val = Max(val, INT_MIN);
|
||||
val = Min(val, INT_MAX);
|
||||
return Int32GetDatum((int32) val);
|
||||
}
|
||||
|
||||
static const bool int4_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function int4_cvt_fns[] =
|
||||
{NULL, cvt_int2_int4, cvt_int8_int4};
|
||||
|
||||
static const PGFunction int4_cmp_fns[] =
|
||||
{btint4cmp, btint24cmp, btint84cmp};
|
||||
|
||||
GIN_SUPPORT(int4, leftmostvalue_int4, int4_rhs_is_varlena, int4_cvt_fns, int4_cmp_fns)
|
||||
GIN_SUPPORT(int4, false, leftmostvalue_int4, btint4cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_int8(void)
|
||||
@ -370,32 +228,7 @@ leftmostvalue_int8(void)
|
||||
return Int64GetDatum(PG_INT64_MIN);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_int2_int8(Datum input)
|
||||
{
|
||||
int16 val = DatumGetInt16(input);
|
||||
|
||||
return Int64GetDatum((int64) val);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_int4_int8(Datum input)
|
||||
{
|
||||
int32 val = DatumGetInt32(input);
|
||||
|
||||
return Int64GetDatum((int64) val);
|
||||
}
|
||||
|
||||
static const bool int8_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function int8_cvt_fns[] =
|
||||
{NULL, cvt_int2_int8, cvt_int4_int8};
|
||||
|
||||
static const PGFunction int8_cmp_fns[] =
|
||||
{btint8cmp, btint28cmp, btint48cmp};
|
||||
|
||||
GIN_SUPPORT(int8, leftmostvalue_int8, int8_rhs_is_varlena, int8_cvt_fns, int8_cmp_fns)
|
||||
GIN_SUPPORT(int8, false, leftmostvalue_int8, btint8cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_float4(void)
|
||||
@ -403,34 +236,7 @@ leftmostvalue_float4(void)
|
||||
return Float4GetDatum(-get_float4_infinity());
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_float8_float4(Datum input)
|
||||
{
|
||||
float8 val = DatumGetFloat8(input);
|
||||
float4 result;
|
||||
|
||||
/*
|
||||
* Assume that ordinary C conversion will produce a usable result.
|
||||
* (Compare dtof(), which raises error conditions that we don't need.)
|
||||
* Note that for inputs that aren't exactly representable as float4, it
|
||||
* doesn't matter whether the conversion rounds up or down. That might
|
||||
* cause us to scan a few index entries that we'll reject as not matching,
|
||||
* but we won't miss any that should match.
|
||||
*/
|
||||
result = (float4) val;
|
||||
return Float4GetDatum(result);
|
||||
}
|
||||
|
||||
static const bool float4_rhs_is_varlena[] =
|
||||
{false, false};
|
||||
|
||||
static const btree_gin_convert_function float4_cvt_fns[] =
|
||||
{NULL, cvt_float8_float4};
|
||||
|
||||
static const PGFunction float4_cmp_fns[] =
|
||||
{btfloat4cmp, btfloat84cmp};
|
||||
|
||||
GIN_SUPPORT(float4, leftmostvalue_float4, float4_rhs_is_varlena, float4_cvt_fns, float4_cmp_fns)
|
||||
GIN_SUPPORT(float4, false, leftmostvalue_float4, btfloat4cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_float8(void)
|
||||
@ -438,24 +244,7 @@ leftmostvalue_float8(void)
|
||||
return Float8GetDatum(-get_float8_infinity());
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_float4_float8(Datum input)
|
||||
{
|
||||
float4 val = DatumGetFloat4(input);
|
||||
|
||||
return Float8GetDatum((float8) val);
|
||||
}
|
||||
|
||||
static const bool float8_rhs_is_varlena[] =
|
||||
{false, false};
|
||||
|
||||
static const btree_gin_convert_function float8_cvt_fns[] =
|
||||
{NULL, cvt_float4_float8};
|
||||
|
||||
static const PGFunction float8_cmp_fns[] =
|
||||
{btfloat8cmp, btfloat48cmp};
|
||||
|
||||
GIN_SUPPORT(float8, leftmostvalue_float8, float8_rhs_is_varlena, float8_cvt_fns, float8_cmp_fns)
|
||||
GIN_SUPPORT(float8, false, leftmostvalue_float8, btfloat8cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_money(void)
|
||||
@ -463,13 +252,7 @@ leftmostvalue_money(void)
|
||||
return Int64GetDatum(PG_INT64_MIN);
|
||||
}
|
||||
|
||||
static const bool money_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction money_cmp_fns[] =
|
||||
{cash_cmp};
|
||||
|
||||
GIN_SUPPORT(money, leftmostvalue_money, money_rhs_is_varlena, NULL, money_cmp_fns)
|
||||
GIN_SUPPORT(money, false, leftmostvalue_money, cash_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_oid(void)
|
||||
@ -477,13 +260,7 @@ leftmostvalue_oid(void)
|
||||
return ObjectIdGetDatum(0);
|
||||
}
|
||||
|
||||
static const bool oid_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction oid_cmp_fns[] =
|
||||
{btoidcmp};
|
||||
|
||||
GIN_SUPPORT(oid, leftmostvalue_oid, oid_rhs_is_varlena, NULL, oid_cmp_fns)
|
||||
GIN_SUPPORT(oid, false, leftmostvalue_oid, btoidcmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_timestamp(void)
|
||||
@ -491,75 +268,9 @@ leftmostvalue_timestamp(void)
|
||||
return TimestampGetDatum(DT_NOBEGIN);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_date_timestamp(Datum input)
|
||||
{
|
||||
DateADT val = DatumGetDateADT(input);
|
||||
Timestamp result;
|
||||
int overflow;
|
||||
GIN_SUPPORT(timestamp, false, leftmostvalue_timestamp, timestamp_cmp)
|
||||
|
||||
result = date2timestamp_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return TimestampGetDatum(result);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_timestamptz_timestamp(Datum input)
|
||||
{
|
||||
TimestampTz val = DatumGetTimestampTz(input);
|
||||
Timestamp result;
|
||||
int overflow;
|
||||
|
||||
result = timestamptz2timestamp_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return TimestampGetDatum(result);
|
||||
}
|
||||
|
||||
static const bool timestamp_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function timestamp_cvt_fns[] =
|
||||
{NULL, cvt_date_timestamp, cvt_timestamptz_timestamp};
|
||||
|
||||
static const PGFunction timestamp_cmp_fns[] =
|
||||
{timestamp_cmp, date_cmp_timestamp, timestamptz_cmp_timestamp};
|
||||
|
||||
GIN_SUPPORT(timestamp, leftmostvalue_timestamp, timestamp_rhs_is_varlena, timestamp_cvt_fns, timestamp_cmp_fns)
|
||||
|
||||
static Datum
|
||||
cvt_date_timestamptz(Datum input)
|
||||
{
|
||||
DateADT val = DatumGetDateADT(input);
|
||||
TimestampTz result;
|
||||
int overflow;
|
||||
|
||||
result = date2timestamptz_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return TimestampTzGetDatum(result);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_timestamp_timestamptz(Datum input)
|
||||
{
|
||||
Timestamp val = DatumGetTimestamp(input);
|
||||
TimestampTz result;
|
||||
int overflow;
|
||||
|
||||
result = timestamp2timestamptz_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return TimestampTzGetDatum(result);
|
||||
}
|
||||
|
||||
static const bool timestamptz_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function timestamptz_cvt_fns[] =
|
||||
{NULL, cvt_date_timestamptz, cvt_timestamp_timestamptz};
|
||||
|
||||
static const PGFunction timestamptz_cmp_fns[] =
|
||||
{timestamp_cmp, date_cmp_timestamptz, timestamp_cmp_timestamptz};
|
||||
|
||||
GIN_SUPPORT(timestamptz, leftmostvalue_timestamp, timestamptz_rhs_is_varlena, timestamptz_cvt_fns, timestamptz_cmp_fns)
|
||||
GIN_SUPPORT(timestamptz, false, leftmostvalue_timestamp, timestamp_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_time(void)
|
||||
@ -567,13 +278,7 @@ leftmostvalue_time(void)
|
||||
return TimeADTGetDatum(0);
|
||||
}
|
||||
|
||||
static const bool time_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction time_cmp_fns[] =
|
||||
{time_cmp};
|
||||
|
||||
GIN_SUPPORT(time, leftmostvalue_time, time_rhs_is_varlena, NULL, time_cmp_fns)
|
||||
GIN_SUPPORT(time, false, leftmostvalue_time, time_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_timetz(void)
|
||||
@ -586,13 +291,7 @@ leftmostvalue_timetz(void)
|
||||
return TimeTzADTPGetDatum(v);
|
||||
}
|
||||
|
||||
static const bool timetz_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction timetz_cmp_fns[] =
|
||||
{timetz_cmp};
|
||||
|
||||
GIN_SUPPORT(timetz, leftmostvalue_timetz, timetz_rhs_is_varlena, NULL, timetz_cmp_fns)
|
||||
GIN_SUPPORT(timetz, false, leftmostvalue_timetz, timetz_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_date(void)
|
||||
@ -600,40 +299,7 @@ leftmostvalue_date(void)
|
||||
return DateADTGetDatum(DATEVAL_NOBEGIN);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_timestamp_date(Datum input)
|
||||
{
|
||||
Timestamp val = DatumGetTimestamp(input);
|
||||
DateADT result;
|
||||
int overflow;
|
||||
|
||||
result = timestamp2date_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return DateADTGetDatum(result);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_timestamptz_date(Datum input)
|
||||
{
|
||||
TimestampTz val = DatumGetTimestampTz(input);
|
||||
DateADT result;
|
||||
int overflow;
|
||||
|
||||
result = timestamptz2date_opt_overflow(val, &overflow);
|
||||
/* We can ignore the overflow result, since result is useful as-is */
|
||||
return DateADTGetDatum(result);
|
||||
}
|
||||
|
||||
static const bool date_rhs_is_varlena[] =
|
||||
{false, false, false};
|
||||
|
||||
static const btree_gin_convert_function date_cvt_fns[] =
|
||||
{NULL, cvt_timestamp_date, cvt_timestamptz_date};
|
||||
|
||||
static const PGFunction date_cmp_fns[] =
|
||||
{date_cmp, timestamp_cmp_date, timestamptz_cmp_date};
|
||||
|
||||
GIN_SUPPORT(date, leftmostvalue_date, date_rhs_is_varlena, date_cvt_fns, date_cmp_fns)
|
||||
GIN_SUPPORT(date, false, leftmostvalue_date, date_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_interval(void)
|
||||
@ -645,13 +311,7 @@ leftmostvalue_interval(void)
|
||||
return IntervalPGetDatum(v);
|
||||
}
|
||||
|
||||
static const bool interval_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction interval_cmp_fns[] =
|
||||
{interval_cmp};
|
||||
|
||||
GIN_SUPPORT(interval, leftmostvalue_interval, interval_rhs_is_varlena, NULL, interval_cmp_fns)
|
||||
GIN_SUPPORT(interval, false, leftmostvalue_interval, interval_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_macaddr(void)
|
||||
@ -661,13 +321,7 @@ leftmostvalue_macaddr(void)
|
||||
return MacaddrPGetDatum(v);
|
||||
}
|
||||
|
||||
static const bool macaddr_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction macaddr_cmp_fns[] =
|
||||
{macaddr_cmp};
|
||||
|
||||
GIN_SUPPORT(macaddr, leftmostvalue_macaddr, macaddr_rhs_is_varlena, NULL, macaddr_cmp_fns)
|
||||
GIN_SUPPORT(macaddr, false, leftmostvalue_macaddr, macaddr_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_macaddr8(void)
|
||||
@ -677,13 +331,7 @@ leftmostvalue_macaddr8(void)
|
||||
return Macaddr8PGetDatum(v);
|
||||
}
|
||||
|
||||
static const bool macaddr8_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction macaddr8_cmp_fns[] =
|
||||
{macaddr8_cmp};
|
||||
|
||||
GIN_SUPPORT(macaddr8, leftmostvalue_macaddr8, macaddr8_rhs_is_varlena, NULL, macaddr8_cmp_fns)
|
||||
GIN_SUPPORT(macaddr8, false, leftmostvalue_macaddr8, macaddr8_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_inet(void)
|
||||
@ -691,21 +339,9 @@ leftmostvalue_inet(void)
|
||||
return DirectFunctionCall1(inet_in, CStringGetDatum("0.0.0.0/0"));
|
||||
}
|
||||
|
||||
static const bool inet_rhs_is_varlena[] =
|
||||
{true};
|
||||
GIN_SUPPORT(inet, true, leftmostvalue_inet, network_cmp)
|
||||
|
||||
static const PGFunction inet_cmp_fns[] =
|
||||
{network_cmp};
|
||||
|
||||
GIN_SUPPORT(inet, leftmostvalue_inet, inet_rhs_is_varlena, NULL, inet_cmp_fns)
|
||||
|
||||
static const bool cidr_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction cidr_cmp_fns[] =
|
||||
{network_cmp};
|
||||
|
||||
GIN_SUPPORT(cidr, leftmostvalue_inet, cidr_rhs_is_varlena, NULL, cidr_cmp_fns)
|
||||
GIN_SUPPORT(cidr, true, leftmostvalue_inet, network_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_text(void)
|
||||
@ -713,32 +349,9 @@ leftmostvalue_text(void)
|
||||
return PointerGetDatum(cstring_to_text_with_len("", 0));
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_name_text(Datum input)
|
||||
{
|
||||
Name val = DatumGetName(input);
|
||||
GIN_SUPPORT(text, true, leftmostvalue_text, bttextcmp)
|
||||
|
||||
return PointerGetDatum(cstring_to_text(NameStr(*val)));
|
||||
}
|
||||
|
||||
static const bool text_rhs_is_varlena[] =
|
||||
{true, false};
|
||||
|
||||
static const btree_gin_convert_function text_cvt_fns[] =
|
||||
{NULL, cvt_name_text};
|
||||
|
||||
static const PGFunction text_cmp_fns[] =
|
||||
{bttextcmp, btnametextcmp};
|
||||
|
||||
GIN_SUPPORT(text, leftmostvalue_text, text_rhs_is_varlena, text_cvt_fns, text_cmp_fns)
|
||||
|
||||
static const bool bpchar_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction bpchar_cmp_fns[] =
|
||||
{bpcharcmp};
|
||||
|
||||
GIN_SUPPORT(bpchar, leftmostvalue_text, bpchar_rhs_is_varlena, NULL, bpchar_cmp_fns)
|
||||
GIN_SUPPORT(bpchar, true, leftmostvalue_text, bpcharcmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_char(void)
|
||||
@ -746,21 +359,9 @@ leftmostvalue_char(void)
|
||||
return CharGetDatum(0);
|
||||
}
|
||||
|
||||
static const bool char_rhs_is_varlena[] =
|
||||
{false};
|
||||
GIN_SUPPORT(char, false, leftmostvalue_char, btcharcmp)
|
||||
|
||||
static const PGFunction char_cmp_fns[] =
|
||||
{btcharcmp};
|
||||
|
||||
GIN_SUPPORT(char, leftmostvalue_char, char_rhs_is_varlena, NULL, char_cmp_fns)
|
||||
|
||||
static const bool bytea_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction bytea_cmp_fns[] =
|
||||
{byteacmp};
|
||||
|
||||
GIN_SUPPORT(bytea, leftmostvalue_text, bytea_rhs_is_varlena, NULL, bytea_cmp_fns)
|
||||
GIN_SUPPORT(bytea, true, leftmostvalue_text, byteacmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_bit(void)
|
||||
@ -771,13 +372,7 @@ leftmostvalue_bit(void)
|
||||
Int32GetDatum(-1));
|
||||
}
|
||||
|
||||
static const bool bit_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction bit_cmp_fns[] =
|
||||
{bitcmp};
|
||||
|
||||
GIN_SUPPORT(bit, leftmostvalue_bit, bit_rhs_is_varlena, NULL, bit_cmp_fns)
|
||||
GIN_SUPPORT(bit, true, leftmostvalue_bit, bitcmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_varbit(void)
|
||||
@ -788,13 +383,7 @@ leftmostvalue_varbit(void)
|
||||
Int32GetDatum(-1));
|
||||
}
|
||||
|
||||
static const bool varbit_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction varbit_cmp_fns[] =
|
||||
{bitcmp};
|
||||
|
||||
GIN_SUPPORT(varbit, leftmostvalue_varbit, varbit_rhs_is_varlena, NULL, varbit_cmp_fns)
|
||||
GIN_SUPPORT(varbit, true, leftmostvalue_varbit, bitcmp)
|
||||
|
||||
/*
|
||||
* Numeric type hasn't a real left-most value, so we use PointerGetDatum(NULL)
|
||||
@ -839,13 +428,7 @@ leftmostvalue_numeric(void)
|
||||
return PointerGetDatum(NULL);
|
||||
}
|
||||
|
||||
static const bool numeric_rhs_is_varlena[] =
|
||||
{true};
|
||||
|
||||
static const PGFunction numeric_cmp_fns[] =
|
||||
{gin_numeric_cmp};
|
||||
|
||||
GIN_SUPPORT(numeric, leftmostvalue_numeric, numeric_rhs_is_varlena, NULL, numeric_cmp_fns)
|
||||
GIN_SUPPORT(numeric, true, leftmostvalue_numeric, gin_numeric_cmp)
|
||||
|
||||
/*
|
||||
* Use a similar trick to that used for numeric for enums, since we don't
|
||||
@ -894,13 +477,7 @@ leftmostvalue_enum(void)
|
||||
return ObjectIdGetDatum(InvalidOid);
|
||||
}
|
||||
|
||||
static const bool enum_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction enum_cmp_fns[] =
|
||||
{gin_enum_cmp};
|
||||
|
||||
GIN_SUPPORT(anyenum, leftmostvalue_enum, enum_rhs_is_varlena, NULL, enum_cmp_fns)
|
||||
GIN_SUPPORT(anyenum, false, leftmostvalue_enum, gin_enum_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_uuid(void)
|
||||
@ -914,13 +491,7 @@ leftmostvalue_uuid(void)
|
||||
return UUIDPGetDatum(retval);
|
||||
}
|
||||
|
||||
static const bool uuid_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction uuid_cmp_fns[] =
|
||||
{uuid_cmp};
|
||||
|
||||
GIN_SUPPORT(uuid, leftmostvalue_uuid, uuid_rhs_is_varlena, NULL, uuid_cmp_fns)
|
||||
GIN_SUPPORT(uuid, false, leftmostvalue_uuid, uuid_cmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_name(void)
|
||||
@ -930,37 +501,7 @@ leftmostvalue_name(void)
|
||||
return NameGetDatum(result);
|
||||
}
|
||||
|
||||
static Datum
|
||||
cvt_text_name(Datum input)
|
||||
{
|
||||
text *val = DatumGetTextPP(input);
|
||||
NameData *result = (NameData *) palloc0(NAMEDATALEN);
|
||||
int len = VARSIZE_ANY_EXHDR(val);
|
||||
|
||||
/*
|
||||
* Truncate oversize input. We're assuming this will produce a result
|
||||
* considered less than the original. That could be a bad assumption in
|
||||
* some collations, but fortunately an index on "name" is generally going
|
||||
* to use C collation.
|
||||
*/
|
||||
if (len >= NAMEDATALEN)
|
||||
len = pg_mbcliplen(VARDATA_ANY(val), len, NAMEDATALEN - 1);
|
||||
|
||||
memcpy(NameStr(*result), VARDATA_ANY(val), len);
|
||||
|
||||
return NameGetDatum(result);
|
||||
}
|
||||
|
||||
static const bool name_rhs_is_varlena[] =
|
||||
{false, true};
|
||||
|
||||
static const btree_gin_convert_function name_cvt_fns[] =
|
||||
{NULL, cvt_text_name};
|
||||
|
||||
static const PGFunction name_cmp_fns[] =
|
||||
{btnamecmp, bttextnamecmp};
|
||||
|
||||
GIN_SUPPORT(name, leftmostvalue_name, name_rhs_is_varlena, name_cvt_fns, name_cmp_fns)
|
||||
GIN_SUPPORT(name, false, leftmostvalue_name, btnamecmp)
|
||||
|
||||
static Datum
|
||||
leftmostvalue_bool(void)
|
||||
@ -968,10 +509,4 @@ leftmostvalue_bool(void)
|
||||
return BoolGetDatum(false);
|
||||
}
|
||||
|
||||
static const bool bool_rhs_is_varlena[] =
|
||||
{false};
|
||||
|
||||
static const PGFunction bool_cmp_fns[] =
|
||||
{btboolcmp};
|
||||
|
||||
GIN_SUPPORT(bool, leftmostvalue_bool, bool_rhs_is_varlena, NULL, bool_cmp_fns)
|
||||
GIN_SUPPORT(bool, false, leftmostvalue_bool, btboolcmp)
|
||||
|
@ -1,6 +1,6 @@
|
||||
# btree_gin extension
|
||||
comment = 'support for indexing common datatypes in GIN'
|
||||
default_version = '1.4'
|
||||
default_version = '1.3'
|
||||
module_pathname = '$libdir/btree_gin'
|
||||
relocatable = true
|
||||
trusted = true
|
||||
|
@ -49,365 +49,3 @@ SELECT * FROM test_date WHERE i>'2004-10-26'::date ORDER BY i;
|
||||
10-28-2004
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamp ORDER BY i;
|
||||
QUERY PLAN
|
||||
-----------------------------------------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_date
|
||||
Recheck Cond: (i < 'Tue Oct 26 00:00:00 2004'::timestamp without time zone)
|
||||
-> Bitmap Index Scan on idx_date
|
||||
Index Cond: (i < 'Tue Oct 26 00:00:00 2004'::timestamp without time zone)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='2004-10-26'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i='2004-10-26'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='2004-10-26'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'2004-10-26'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamptz ORDER BY i;
|
||||
QUERY PLAN
|
||||
------------------------------------------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_date
|
||||
Recheck Cond: (i < 'Tue Oct 26 00:00:00 2004 PDT'::timestamp with time zone)
|
||||
-> Bitmap Index Scan on idx_date
|
||||
Index Cond: (i < 'Tue Oct 26 00:00:00 2004 PDT'::timestamp with time zone)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='2004-10-26'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i='2004-10-26'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='2004-10-26'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'2004-10-26'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(2 rows)
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
INSERT INTO test_date VALUES ('-infinity'), ('infinity');
|
||||
SELECT gin_clean_pending_list('idx_date');
|
||||
gin_clean_pending_list
|
||||
------------------------
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'-infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='-infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i='-infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='-infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'-infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i='infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'infinity'::timestamp ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<'infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i<='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_date WHERE i>'infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
-- Check rounding cases
|
||||
-- '2004-10-25 00:00:01' rounds to '2004-10-25' for date.
|
||||
-- '2004-10-25 23:59:59' also rounds to '2004-10-25',
|
||||
-- so it's the same case as '2004-10-25 00:00:01'
|
||||
SELECT * FROM test_date WHERE i < '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i <= '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i = '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i > '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i >= '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i < '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i <= '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
-infinity
|
||||
10-23-2004
|
||||
10-24-2004
|
||||
10-25-2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i = '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i > '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_date WHERE i >= '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------
|
||||
10-26-2004
|
||||
10-27-2004
|
||||
10-28-2004
|
||||
infinity
|
||||
(4 rows)
|
||||
|
||||
|
@ -42,324 +42,3 @@ SELECT * FROM test_float4 WHERE i>1::float4 ORDER BY i;
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_float4 WHERE i<1::float8 ORDER BY i;
|
||||
QUERY PLAN
|
||||
-------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_float4
|
||||
Recheck Cond: (i < '1'::double precision)
|
||||
-> Bitmap Index Scan on idx_float4
|
||||
Index Cond: (i < '1'::double precision)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<1::float8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<=1::float8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i=1::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>=1::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>1::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
INSERT INTO test_float4 VALUES ('NaN'), ('Inf'), ('-Inf');
|
||||
SELECT gin_clean_pending_list('idx_float4');
|
||||
gin_clean_pending_list
|
||||
------------------------
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'-Inf'::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<='-Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i='-Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>='-Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(9 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>'-Inf'::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<='Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i='Inf'::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
Infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>='Inf'::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
Infinity
|
||||
NaN
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>'Inf'::float8 ORDER BY i;
|
||||
i
|
||||
-----
|
||||
NaN
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'1e300'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<='1e300'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i='1e300'::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>='1e300'::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
Infinity
|
||||
NaN
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>'1e300'::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
Infinity
|
||||
NaN
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'NaN'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<='NaN'::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(9 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i='NaN'::float8 ORDER BY i;
|
||||
i
|
||||
-----
|
||||
NaN
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>='NaN'::float8 ORDER BY i;
|
||||
i
|
||||
-----
|
||||
NaN
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i>'NaN'::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
-- Check rounding cases
|
||||
-- 1e-300 rounds to 0 for float4 but not for float8
|
||||
SELECT * FROM test_float4 WHERE i < -1e-300::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i <= -1e-300::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i = -1e-300::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i > -1e-300::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i >= -1e-300::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i < 1e-300::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i <= 1e-300::float8 ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-Infinity
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i = 1e-300::float8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i > 1e-300::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(5 rows)
|
||||
|
||||
SELECT * FROM test_float4 WHERE i >= 1e-300::float8 ORDER BY i;
|
||||
i
|
||||
----------
|
||||
1
|
||||
2
|
||||
3
|
||||
Infinity
|
||||
NaN
|
||||
(5 rows)
|
||||
|
||||
|
@ -42,53 +42,3 @@ SELECT * FROM test_float8 WHERE i>1::float8 ORDER BY i;
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_float8 WHERE i<1::float4 ORDER BY i;
|
||||
QUERY PLAN
|
||||
---------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_float8
|
||||
Recheck Cond: (i < '1'::real)
|
||||
-> Bitmap Index Scan on idx_float8
|
||||
Index Cond: (i < '1'::real)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_float8 WHERE i<1::float4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float8 WHERE i<=1::float4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_float8 WHERE i=1::float4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_float8 WHERE i>=1::float4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_float8 WHERE i>1::float4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
|
@ -42,193 +42,3 @@ SELECT * FROM test_int2 WHERE i>1::int2 ORDER BY i;
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int2 WHERE i<1::int4 ORDER BY i;
|
||||
QUERY PLAN
|
||||
-------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int2
|
||||
Recheck Cond: (i < 1)
|
||||
-> Bitmap Index Scan on idx_int2
|
||||
Index Cond: (i < 1)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<1::int4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<=1::int4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i=1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>=1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int2 WHERE i<1::int8 ORDER BY i;
|
||||
QUERY PLAN
|
||||
---------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int2
|
||||
Recheck Cond: (i < '1'::bigint)
|
||||
-> Bitmap Index Scan on idx_int2
|
||||
Index Cond: (i < '1'::bigint)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<1::int8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<=1::int8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i=1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>=1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
INSERT INTO test_int2 VALUES ((-32768)::int2),(32767);
|
||||
SELECT gin_clean_pending_list('idx_int2');
|
||||
gin_clean_pending_list
|
||||
------------------------
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<(-32769)::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<=(-32769)::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i=(-32769)::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>=(-32769)::int4 ORDER BY i;
|
||||
i
|
||||
--------
|
||||
-32768
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
32767
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>(-32769)::int4 ORDER BY i;
|
||||
i
|
||||
--------
|
||||
-32768
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
32767
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<32768::int4 ORDER BY i;
|
||||
i
|
||||
--------
|
||||
-32768
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
32767
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<=32768::int4 ORDER BY i;
|
||||
i
|
||||
--------
|
||||
-32768
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
2
|
||||
3
|
||||
32767
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i=32768::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>=32768::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_int2 WHERE i>32768::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
|
@ -42,103 +42,3 @@ SELECT * FROM test_int4 WHERE i>1::int4 ORDER BY i;
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int4 WHERE i<1::int2 ORDER BY i;
|
||||
QUERY PLAN
|
||||
-----------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int4
|
||||
Recheck Cond: (i < '1'::smallint)
|
||||
-> Bitmap Index Scan on idx_int4
|
||||
Index Cond: (i < '1'::smallint)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<1::int2 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<=1::int2 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i=1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i>=1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i>1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int4 WHERE i<1::int8 ORDER BY i;
|
||||
QUERY PLAN
|
||||
---------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int4
|
||||
Recheck Cond: (i < '1'::bigint)
|
||||
-> Bitmap Index Scan on idx_int4
|
||||
Index Cond: (i < '1'::bigint)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<1::int8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<=1::int8 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i=1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i>=1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int4 WHERE i>1::int8 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
|
@ -42,103 +42,3 @@ SELECT * FROM test_int8 WHERE i>1::int8 ORDER BY i;
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int8 WHERE i<1::int2 ORDER BY i;
|
||||
QUERY PLAN
|
||||
-----------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int8
|
||||
Recheck Cond: (i < '1'::smallint)
|
||||
-> Bitmap Index Scan on idx_int8
|
||||
Index Cond: (i < '1'::smallint)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<1::int2 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<=1::int2 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i=1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i>=1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i>1::int2 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int8 WHERE i<1::int4 ORDER BY i;
|
||||
QUERY PLAN
|
||||
-------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_int8
|
||||
Recheck Cond: (i < 1)
|
||||
-> Bitmap Index Scan on idx_int8
|
||||
Index Cond: (i < 1)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<1::int4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<=1::int4 ORDER BY i;
|
||||
i
|
||||
----
|
||||
-2
|
||||
-1
|
||||
0
|
||||
1
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i=1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i>=1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
1
|
||||
2
|
||||
3
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_int8 WHERE i>1::int4 ORDER BY i;
|
||||
i
|
||||
---
|
||||
2
|
||||
3
|
||||
(2 rows)
|
||||
|
||||
|
@ -95,62 +95,3 @@ EXPLAIN (COSTS OFF) SELECT * FROM test_name WHERE i>'abc' ORDER BY i;
|
||||
Index Cond: (i > 'abc'::name)
|
||||
(6 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_name WHERE i<'abc'::text ORDER BY i;
|
||||
QUERY PLAN
|
||||
---------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_name
|
||||
Recheck Cond: (i < 'abc'::text)
|
||||
-> Bitmap Index Scan on idx_name
|
||||
Index Cond: (i < 'abc'::text)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_name WHERE i<'abc'::text ORDER BY i;
|
||||
i
|
||||
-----
|
||||
a
|
||||
ab
|
||||
abb
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_name WHERE i<='abc'::text ORDER BY i;
|
||||
i
|
||||
-----
|
||||
a
|
||||
ab
|
||||
abb
|
||||
abc
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_name WHERE i='abc'::text ORDER BY i;
|
||||
i
|
||||
-----
|
||||
abc
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_name WHERE i>='abc'::text ORDER BY i;
|
||||
i
|
||||
-----
|
||||
abc
|
||||
axy
|
||||
xyz
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_name WHERE i>'abc'::text ORDER BY i;
|
||||
i
|
||||
-----
|
||||
axy
|
||||
xyz
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_name WHERE i<=repeat('abc', 100) ORDER BY i;
|
||||
i
|
||||
-----
|
||||
a
|
||||
ab
|
||||
abb
|
||||
abc
|
||||
(4 rows)
|
||||
|
||||
|
@ -42,53 +42,3 @@ SELECT * FROM test_text WHERE i>'abc' ORDER BY i;
|
||||
xyz
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_text WHERE i<'abc'::name COLLATE "default" ORDER BY i;
|
||||
QUERY PLAN
|
||||
---------------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_text
|
||||
Recheck Cond: (i < 'abc'::name COLLATE "default")
|
||||
-> Bitmap Index Scan on idx_text
|
||||
Index Cond: (i < 'abc'::name COLLATE "default")
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_text WHERE i<'abc'::name COLLATE "default" ORDER BY i;
|
||||
i
|
||||
-----
|
||||
a
|
||||
ab
|
||||
abb
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_text WHERE i<='abc'::name COLLATE "default" ORDER BY i;
|
||||
i
|
||||
-----
|
||||
a
|
||||
ab
|
||||
abb
|
||||
abc
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_text WHERE i='abc'::name COLLATE "default" ORDER BY i;
|
||||
i
|
||||
-----
|
||||
abc
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_text WHERE i>='abc'::name COLLATE "default" ORDER BY i;
|
||||
i
|
||||
-----
|
||||
abc
|
||||
axy
|
||||
xyz
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_text WHERE i>'abc'::name COLLATE "default" ORDER BY i;
|
||||
i
|
||||
-----
|
||||
axy
|
||||
xyz
|
||||
(2 rows)
|
||||
|
||||
|
@ -7,8 +7,8 @@ INSERT INTO test_timestamp VALUES
|
||||
( '2004-10-26 04:55:08' ),
|
||||
( '2004-10-26 05:55:08' ),
|
||||
( '2004-10-26 08:55:08' ),
|
||||
( '2004-10-27 09:55:08' ),
|
||||
( '2004-10-27 10:55:08' )
|
||||
( '2004-10-26 09:55:08' ),
|
||||
( '2004-10-26 10:55:08' )
|
||||
;
|
||||
CREATE INDEX idx_timestamp ON test_timestamp USING gin (i);
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
@ -38,308 +38,14 @@ SELECT * FROM test_timestamp WHERE i>='2004-10-26 08:55:08'::timestamp ORDER BY
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
Tue Oct 26 09:55:08 2004
|
||||
Tue Oct 26 10:55:08 2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
Tue Oct 26 09:55:08 2004
|
||||
Tue Oct 26 10:55:08 2004
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
QUERY PLAN
|
||||
----------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_timestamp
|
||||
Recheck Cond: (i < '10-27-2004'::date)
|
||||
-> Bitmap Index Scan on idx_timestamp
|
||||
Index Cond: (i < '10-27-2004'::date)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
QUERY PLAN
|
||||
------------------------------------------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_timestamp
|
||||
Recheck Cond: (i < 'Tue Oct 26 08:55:08 2004 PDT'::timestamp with time zone)
|
||||
-> Bitmap Index Scan on idx_timestamp
|
||||
Index Cond: (i < 'Tue Oct 26 08:55:08 2004 PDT'::timestamp with time zone)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 08:55:08 2004
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(2 rows)
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
INSERT INTO test_timestamp VALUES ('-infinity'), ('infinity');
|
||||
SELECT gin_clean_pending_list('idx_timestamp');
|
||||
gin_clean_pending_list
|
||||
------------------------
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'-infinity'::date ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='-infinity'::date ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='-infinity'::date ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='-infinity'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'-infinity'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'infinity'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='infinity'::date ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='infinity'::date ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='infinity'::date ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'infinity'::date ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'-infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
(7 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
-infinity
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(8 rows)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>='infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
----------
|
||||
infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'infinity'::timestamptz ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
-- This PST timestamptz will underflow if converted to timestamp
|
||||
SELECT * FROM test_timestamp WHERE i<='4714-11-23 17:00 BC'::timestamptz ORDER BY i;
|
||||
i
|
||||
-----------
|
||||
-infinity
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i>'4714-11-23 17:00 BC'::timestamptz ORDER BY i;
|
||||
i
|
||||
--------------------------
|
||||
Tue Oct 26 03:55:08 2004
|
||||
Tue Oct 26 04:55:08 2004
|
||||
Tue Oct 26 05:55:08 2004
|
||||
Tue Oct 26 08:55:08 2004
|
||||
Wed Oct 27 09:55:08 2004
|
||||
Wed Oct 27 10:55:08 2004
|
||||
infinity
|
||||
(7 rows)
|
||||
|
||||
|
@ -7,8 +7,8 @@ INSERT INTO test_timestamptz VALUES
|
||||
( '2004-10-26 04:55:08' ),
|
||||
( '2004-10-26 05:55:08' ),
|
||||
( '2004-10-26 08:55:08' ),
|
||||
( '2004-10-27 09:55:08' ),
|
||||
( '2004-10-27 10:55:08' )
|
||||
( '2004-10-26 09:55:08' ),
|
||||
( '2004-10-26 10:55:08' )
|
||||
;
|
||||
CREATE INDEX idx_timestamptz ON test_timestamptz USING gin (i);
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
@ -38,113 +38,14 @@ SELECT * FROM test_timestamptz WHERE i>='2004-10-26 08:55:08'::timestamptz ORDER
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
Tue Oct 26 09:55:08 2004 PDT
|
||||
Tue Oct 26 10:55:08 2004 PDT
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
QUERY PLAN
|
||||
----------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_timestamptz
|
||||
Recheck Cond: (i < '10-27-2004'::date)
|
||||
-> Bitmap Index Scan on idx_timestamptz
|
||||
Index Cond: (i < '10-27-2004'::date)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 03:55:08 2004 PDT
|
||||
Tue Oct 26 04:55:08 2004 PDT
|
||||
Tue Oct 26 05:55:08 2004 PDT
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 03:55:08 2004 PDT
|
||||
Tue Oct 26 04:55:08 2004 PDT
|
||||
Tue Oct 26 05:55:08 2004 PDT
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
---
|
||||
(0 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i>='2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
(2 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-27'::date ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
(2 rows)
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
QUERY PLAN
|
||||
-----------------------------------------------------------------------------------------
|
||||
Sort
|
||||
Sort Key: i
|
||||
-> Bitmap Heap Scan on test_timestamptz
|
||||
Recheck Cond: (i < 'Tue Oct 26 08:55:08 2004'::timestamp without time zone)
|
||||
-> Bitmap Index Scan on idx_timestamptz
|
||||
Index Cond: (i < 'Tue Oct 26 08:55:08 2004'::timestamp without time zone)
|
||||
(6 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 03:55:08 2004 PDT
|
||||
Tue Oct 26 04:55:08 2004 PDT
|
||||
Tue Oct 26 05:55:08 2004 PDT
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 03:55:08 2004 PDT
|
||||
Tue Oct 26 04:55:08 2004 PDT
|
||||
Tue Oct 26 05:55:08 2004 PDT
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
(4 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i>='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Tue Oct 26 08:55:08 2004 PDT
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
(3 rows)
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
i
|
||||
------------------------------
|
||||
Wed Oct 27 09:55:08 2004 PDT
|
||||
Wed Oct 27 10:55:08 2004 PDT
|
||||
Tue Oct 26 09:55:08 2004 PDT
|
||||
Tue Oct 26 10:55:08 2004 PDT
|
||||
(2 rows)
|
||||
|
||||
|
@ -22,7 +22,6 @@ install_data(
|
||||
'btree_gin--1.0--1.1.sql',
|
||||
'btree_gin--1.1--1.2.sql',
|
||||
'btree_gin--1.2--1.3.sql',
|
||||
'btree_gin--1.3--1.4.sql',
|
||||
kwargs: contrib_data_args,
|
||||
)
|
||||
|
||||
|
@ -20,67 +20,3 @@ SELECT * FROM test_date WHERE i<='2004-10-26'::date ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='2004-10-26'::date ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='2004-10-26'::date ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'2004-10-26'::date ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamp ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='2004-10-26'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='2004-10-26'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='2004-10-26'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'2004-10-26'::timestamp ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamptz ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i<'2004-10-26'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='2004-10-26'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='2004-10-26'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='2004-10-26'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'2004-10-26'::timestamptz ORDER BY i;
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
|
||||
INSERT INTO test_date VALUES ('-infinity'), ('infinity');
|
||||
SELECT gin_clean_pending_list('idx_date');
|
||||
|
||||
SELECT * FROM test_date WHERE i<'-infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='-infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='-infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='-infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'-infinity'::timestamp ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i<'infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='infinity'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'infinity'::timestamp ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i<'-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'-infinity'::timestamptz ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i<'infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i<='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i>'infinity'::timestamptz ORDER BY i;
|
||||
|
||||
-- Check rounding cases
|
||||
-- '2004-10-25 00:00:01' rounds to '2004-10-25' for date.
|
||||
-- '2004-10-25 23:59:59' also rounds to '2004-10-25',
|
||||
-- so it's the same case as '2004-10-25 00:00:01'
|
||||
|
||||
SELECT * FROM test_date WHERE i < '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i <= '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i = '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i > '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i >= '2004-10-25 00:00:01'::timestamp ORDER BY i;
|
||||
|
||||
SELECT * FROM test_date WHERE i < '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i <= '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i = '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i > '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_date WHERE i >= '2004-10-25 00:00:01'::timestamptz ORDER BY i;
|
||||
|
@ -13,56 +13,3 @@ SELECT * FROM test_float4 WHERE i<=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>1::float4 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_float4 WHERE i<1::float8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i<=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>1::float8 ORDER BY i;
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
|
||||
INSERT INTO test_float4 VALUES ('NaN'), ('Inf'), ('-Inf');
|
||||
SELECT gin_clean_pending_list('idx_float4');
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'-Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i<='-Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i='-Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>='-Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>'-Inf'::float8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i<='Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i='Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>='Inf'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>'Inf'::float8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'1e300'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i<='1e300'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i='1e300'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>='1e300'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>'1e300'::float8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float4 WHERE i<'NaN'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i<='NaN'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i='NaN'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>='NaN'::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i>'NaN'::float8 ORDER BY i;
|
||||
|
||||
-- Check rounding cases
|
||||
-- 1e-300 rounds to 0 for float4 but not for float8
|
||||
|
||||
SELECT * FROM test_float4 WHERE i < -1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i <= -1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i = -1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i > -1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i >= -1e-300::float8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float4 WHERE i < 1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i <= 1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i = 1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i > 1e-300::float8 ORDER BY i;
|
||||
SELECT * FROM test_float4 WHERE i >= 1e-300::float8 ORDER BY i;
|
||||
|
@ -13,12 +13,3 @@ SELECT * FROM test_float8 WHERE i<=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i>=1::float8 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i>1::float8 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_float8 WHERE i<1::float4 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_float8 WHERE i<1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i<=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i>=1::float4 ORDER BY i;
|
||||
SELECT * FROM test_float8 WHERE i>1::float4 ORDER BY i;
|
||||
|
@ -13,38 +13,3 @@ SELECT * FROM test_int2 WHERE i<=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>1::int2 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int2 WHERE i<1::int4 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i<=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>1::int4 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int2 WHERE i<1::int8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i<=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>1::int8 ORDER BY i;
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
|
||||
INSERT INTO test_int2 VALUES ((-32768)::int2),(32767);
|
||||
SELECT gin_clean_pending_list('idx_int2');
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<(-32769)::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i<=(-32769)::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i=(-32769)::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>=(-32769)::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>(-32769)::int4 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int2 WHERE i<32768::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i<=32768::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i=32768::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>=32768::int4 ORDER BY i;
|
||||
SELECT * FROM test_int2 WHERE i>32768::int4 ORDER BY i;
|
||||
|
@ -13,21 +13,3 @@ SELECT * FROM test_int4 WHERE i<=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>1::int4 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int4 WHERE i<1::int2 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i<=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>1::int2 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int4 WHERE i<1::int8 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int4 WHERE i<1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i<=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int4 WHERE i>1::int8 ORDER BY i;
|
||||
|
@ -13,21 +13,3 @@ SELECT * FROM test_int8 WHERE i<=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>=1::int8 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>1::int8 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int8 WHERE i<1::int2 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i<=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>=1::int2 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>1::int2 ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_int8 WHERE i<1::int4 ORDER BY i;
|
||||
|
||||
SELECT * FROM test_int8 WHERE i<1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i<=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>=1::int4 ORDER BY i;
|
||||
SELECT * FROM test_int8 WHERE i>1::int4 ORDER BY i;
|
||||
|
@ -19,14 +19,3 @@ EXPLAIN (COSTS OFF) SELECT * FROM test_name WHERE i<='abc' ORDER BY i;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_name WHERE i='abc' ORDER BY i;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_name WHERE i>='abc' ORDER BY i;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_name WHERE i>'abc' ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_name WHERE i<'abc'::text ORDER BY i;
|
||||
|
||||
SELECT * FROM test_name WHERE i<'abc'::text ORDER BY i;
|
||||
SELECT * FROM test_name WHERE i<='abc'::text ORDER BY i;
|
||||
SELECT * FROM test_name WHERE i='abc'::text ORDER BY i;
|
||||
SELECT * FROM test_name WHERE i>='abc'::text ORDER BY i;
|
||||
SELECT * FROM test_name WHERE i>'abc'::text ORDER BY i;
|
||||
|
||||
SELECT * FROM test_name WHERE i<=repeat('abc', 100) ORDER BY i;
|
||||
|
@ -13,12 +13,3 @@ SELECT * FROM test_text WHERE i<='abc' ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i='abc' ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i>='abc' ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i>'abc' ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_text WHERE i<'abc'::name COLLATE "default" ORDER BY i;
|
||||
|
||||
SELECT * FROM test_text WHERE i<'abc'::name COLLATE "default" ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i<='abc'::name COLLATE "default" ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i='abc'::name COLLATE "default" ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i>='abc'::name COLLATE "default" ORDER BY i;
|
||||
SELECT * FROM test_text WHERE i>'abc'::name COLLATE "default" ORDER BY i;
|
||||
|
@ -9,8 +9,8 @@ INSERT INTO test_timestamp VALUES
|
||||
( '2004-10-26 04:55:08' ),
|
||||
( '2004-10-26 05:55:08' ),
|
||||
( '2004-10-26 08:55:08' ),
|
||||
( '2004-10-27 09:55:08' ),
|
||||
( '2004-10-27 10:55:08' )
|
||||
( '2004-10-26 09:55:08' ),
|
||||
( '2004-10-26 10:55:08' )
|
||||
;
|
||||
|
||||
CREATE INDEX idx_timestamp ON test_timestamp USING gin (i);
|
||||
@ -20,54 +20,3 @@ SELECT * FROM test_timestamp WHERE i<='2004-10-26 08:55:08'::timestamp ORDER BY
|
||||
SELECT * FROM test_timestamp WHERE i='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-27'::date ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
|
||||
-- Check endpoint and out-of-range cases
|
||||
|
||||
INSERT INTO test_timestamp VALUES ('-infinity'), ('infinity');
|
||||
SELECT gin_clean_pending_list('idx_timestamp');
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'-infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='-infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='-infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='-infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'-infinity'::date ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='infinity'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'infinity'::date ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='-infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'-infinity'::timestamptz ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamp WHERE i<'infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i<='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>='infinity'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'infinity'::timestamptz ORDER BY i;
|
||||
|
||||
-- This PST timestamptz will underflow if converted to timestamp
|
||||
SELECT * FROM test_timestamp WHERE i<='4714-11-23 17:00 BC'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamp WHERE i>'4714-11-23 17:00 BC'::timestamptz ORDER BY i;
|
||||
|
@ -9,8 +9,8 @@ INSERT INTO test_timestamptz VALUES
|
||||
( '2004-10-26 04:55:08' ),
|
||||
( '2004-10-26 05:55:08' ),
|
||||
( '2004-10-26 08:55:08' ),
|
||||
( '2004-10-27 09:55:08' ),
|
||||
( '2004-10-27 10:55:08' )
|
||||
( '2004-10-26 09:55:08' ),
|
||||
( '2004-10-26 10:55:08' )
|
||||
;
|
||||
|
||||
CREATE INDEX idx_timestamptz ON test_timestamptz USING gin (i);
|
||||
@ -20,21 +20,3 @@ SELECT * FROM test_timestamptz WHERE i<='2004-10-26 08:55:08'::timestamptz ORDER
|
||||
SELECT * FROM test_timestamptz WHERE i='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>='2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-26 08:55:08'::timestamptz ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i<='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>='2004-10-27'::date ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-27'::date ORDER BY i;
|
||||
|
||||
explain (costs off)
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
|
||||
SELECT * FROM test_timestamptz WHERE i<'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i<='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>='2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
SELECT * FROM test_timestamptz WHERE i>'2004-10-26 08:55:08'::timestamp ORDER BY i;
|
||||
|
@ -5,7 +5,6 @@
|
||||
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct boolkey
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "common/int.h"
|
||||
#include "utils/cash.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/date.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
|
@ -8,7 +8,6 @@
|
||||
#include "fmgr.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/fmgroids.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
/* enums are really Oids, so we just use the same structure */
|
||||
@ -194,8 +193,8 @@ gbt_enum_ssup_cmp(Datum x, Datum y, SortSupport ssup)
|
||||
return DatumGetInt32(CallerFInfoFunctionCall2(enum_cmp,
|
||||
ssup->ssup_extra,
|
||||
InvalidOid,
|
||||
ObjectIdGetDatum(arg1->lower),
|
||||
ObjectIdGetDatum(arg2->lower)));
|
||||
arg1->lower,
|
||||
arg2->lower));
|
||||
}
|
||||
|
||||
Datum
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/float.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct float4key
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/float.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct float8key
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "catalog/pg_type.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct inetkey
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "common/int.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct int16key
|
||||
|
@ -5,7 +5,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "common/int.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct int32key
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "common/int.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct int64key
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
#include "utils/timestamp.h"
|
||||
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/inet.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/inet.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
|
@ -192,7 +192,7 @@ gbt_numeric_penalty(PG_FUNCTION_ARGS)
|
||||
|
||||
*result = 0.0;
|
||||
|
||||
if (DatumGetBool(DirectFunctionCall2(numeric_gt, NumericGetDatum(ds), NumericGetDatum(nul))))
|
||||
if (DirectFunctionCall2(numeric_gt, NumericGetDatum(ds), NumericGetDatum(nul)))
|
||||
{
|
||||
*result += FLT_MIN;
|
||||
os = DatumGetNumeric(DirectFunctionCall2(numeric_div,
|
||||
|
@ -5,7 +5,6 @@
|
||||
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "btree_utils_num.h"
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/date.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
#include "utils/timestamp.h"
|
||||
|
||||
@ -32,6 +31,13 @@ PG_FUNCTION_INFO_V1(gbt_time_sortsupport);
|
||||
PG_FUNCTION_INFO_V1(gbt_timetz_sortsupport);
|
||||
|
||||
|
||||
#ifdef USE_FLOAT8_BYVAL
|
||||
#define TimeADTGetDatumFast(X) TimeADTGetDatum(X)
|
||||
#else
|
||||
#define TimeADTGetDatumFast(X) PointerGetDatum(&(X))
|
||||
#endif
|
||||
|
||||
|
||||
static bool
|
||||
gbt_timegt(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
{
|
||||
@ -39,8 +45,8 @@ gbt_timegt(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const TimeADT *bb = (const TimeADT *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(time_gt,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -50,8 +56,8 @@ gbt_timege(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const TimeADT *bb = (const TimeADT *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(time_ge,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -61,8 +67,8 @@ gbt_timeeq(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const TimeADT *bb = (const TimeADT *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(time_eq,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -72,8 +78,8 @@ gbt_timele(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const TimeADT *bb = (const TimeADT *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(time_le,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -83,8 +89,8 @@ gbt_timelt(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const TimeADT *bb = (const TimeADT *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(time_lt,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static int
|
||||
@ -94,9 +100,9 @@ gbt_timekey_cmp(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
timeKEY *ib = (timeKEY *) (((const Nsrt *) b)->t);
|
||||
int res;
|
||||
|
||||
res = DatumGetInt32(DirectFunctionCall2(time_cmp, TimeADTGetDatum(ia->lower), TimeADTGetDatum(ib->lower)));
|
||||
res = DatumGetInt32(DirectFunctionCall2(time_cmp, TimeADTGetDatumFast(ia->lower), TimeADTGetDatumFast(ib->lower)));
|
||||
if (res == 0)
|
||||
return DatumGetInt32(DirectFunctionCall2(time_cmp, TimeADTGetDatum(ia->upper), TimeADTGetDatum(ib->upper)));
|
||||
return DatumGetInt32(DirectFunctionCall2(time_cmp, TimeADTGetDatumFast(ia->upper), TimeADTGetDatumFast(ib->upper)));
|
||||
|
||||
return res;
|
||||
}
|
||||
@ -109,8 +115,8 @@ gbt_time_dist(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
Interval *i;
|
||||
|
||||
i = DatumGetIntervalP(DirectFunctionCall2(time_mi_time,
|
||||
TimeADTGetDatum(*aa),
|
||||
TimeADTGetDatum(*bb)));
|
||||
TimeADTGetDatumFast(*aa),
|
||||
TimeADTGetDatumFast(*bb)));
|
||||
return fabs(INTERVAL_TO_SEC(i));
|
||||
}
|
||||
|
||||
@ -273,14 +279,14 @@ gbt_time_penalty(PG_FUNCTION_ARGS)
|
||||
double res2;
|
||||
|
||||
intr = DatumGetIntervalP(DirectFunctionCall2(time_mi_time,
|
||||
TimeADTGetDatum(newentry->upper),
|
||||
TimeADTGetDatum(origentry->upper)));
|
||||
TimeADTGetDatumFast(newentry->upper),
|
||||
TimeADTGetDatumFast(origentry->upper)));
|
||||
res = INTERVAL_TO_SEC(intr);
|
||||
res = Max(res, 0);
|
||||
|
||||
intr = DatumGetIntervalP(DirectFunctionCall2(time_mi_time,
|
||||
TimeADTGetDatum(origentry->lower),
|
||||
TimeADTGetDatum(newentry->lower)));
|
||||
TimeADTGetDatumFast(origentry->lower),
|
||||
TimeADTGetDatumFast(newentry->lower)));
|
||||
res2 = INTERVAL_TO_SEC(intr);
|
||||
res2 = Max(res2, 0);
|
||||
|
||||
@ -291,8 +297,8 @@ gbt_time_penalty(PG_FUNCTION_ARGS)
|
||||
if (res > 0)
|
||||
{
|
||||
intr = DatumGetIntervalP(DirectFunctionCall2(time_mi_time,
|
||||
TimeADTGetDatum(origentry->upper),
|
||||
TimeADTGetDatum(origentry->lower)));
|
||||
TimeADTGetDatumFast(origentry->upper),
|
||||
TimeADTGetDatumFast(origentry->lower)));
|
||||
*result += FLT_MIN;
|
||||
*result += (float) (res / (res + INTERVAL_TO_SEC(intr)));
|
||||
*result *= (FLT_MAX / (((GISTENTRY *) PG_GETARG_POINTER(0))->rel->rd_att->natts + 1));
|
||||
@ -328,8 +334,8 @@ gbt_timekey_ssup_cmp(Datum x, Datum y, SortSupport ssup)
|
||||
|
||||
/* for leaf items we expect lower == upper, so only compare lower */
|
||||
return DatumGetInt32(DirectFunctionCall2(time_cmp,
|
||||
TimeADTGetDatum(arg1->lower),
|
||||
TimeADTGetDatum(arg2->lower)));
|
||||
TimeADTGetDatumFast(arg1->lower),
|
||||
TimeADTGetDatumFast(arg2->lower)));
|
||||
}
|
||||
|
||||
Datum
|
||||
|
@ -10,7 +10,6 @@
|
||||
#include "utils/fmgrprotos.h"
|
||||
#include "utils/timestamp.h"
|
||||
#include "utils/float.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
|
||||
typedef struct
|
||||
@ -34,6 +33,13 @@ PG_FUNCTION_INFO_V1(gbt_ts_same);
|
||||
PG_FUNCTION_INFO_V1(gbt_ts_sortsupport);
|
||||
|
||||
|
||||
#ifdef USE_FLOAT8_BYVAL
|
||||
#define TimestampGetDatumFast(X) TimestampGetDatum(X)
|
||||
#else
|
||||
#define TimestampGetDatumFast(X) PointerGetDatum(&(X))
|
||||
#endif
|
||||
|
||||
|
||||
/* define for comparison */
|
||||
|
||||
static bool
|
||||
@ -43,8 +49,8 @@ gbt_tsgt(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const Timestamp *bb = (const Timestamp *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(timestamp_gt,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -54,8 +60,8 @@ gbt_tsge(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const Timestamp *bb = (const Timestamp *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(timestamp_ge,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -65,8 +71,8 @@ gbt_tseq(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const Timestamp *bb = (const Timestamp *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(timestamp_eq,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -76,8 +82,8 @@ gbt_tsle(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const Timestamp *bb = (const Timestamp *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(timestamp_le,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static bool
|
||||
@ -87,8 +93,8 @@ gbt_tslt(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
const Timestamp *bb = (const Timestamp *) b;
|
||||
|
||||
return DatumGetBool(DirectFunctionCall2(timestamp_lt,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
}
|
||||
|
||||
static int
|
||||
@ -98,9 +104,9 @@ gbt_tskey_cmp(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
tsKEY *ib = (tsKEY *) (((const Nsrt *) b)->t);
|
||||
int res;
|
||||
|
||||
res = DatumGetInt32(DirectFunctionCall2(timestamp_cmp, TimestampGetDatum(ia->lower), TimestampGetDatum(ib->lower)));
|
||||
res = DatumGetInt32(DirectFunctionCall2(timestamp_cmp, TimestampGetDatumFast(ia->lower), TimestampGetDatumFast(ib->lower)));
|
||||
if (res == 0)
|
||||
return DatumGetInt32(DirectFunctionCall2(timestamp_cmp, TimestampGetDatum(ia->upper), TimestampGetDatum(ib->upper)));
|
||||
return DatumGetInt32(DirectFunctionCall2(timestamp_cmp, TimestampGetDatumFast(ia->upper), TimestampGetDatumFast(ib->upper)));
|
||||
|
||||
return res;
|
||||
}
|
||||
@ -116,8 +122,8 @@ gbt_ts_dist(const void *a, const void *b, FmgrInfo *flinfo)
|
||||
return get_float8_infinity();
|
||||
|
||||
i = DatumGetIntervalP(DirectFunctionCall2(timestamp_mi,
|
||||
TimestampGetDatum(*aa),
|
||||
TimestampGetDatum(*bb)));
|
||||
TimestampGetDatumFast(*aa),
|
||||
TimestampGetDatumFast(*bb)));
|
||||
return fabs(INTERVAL_TO_SEC(i));
|
||||
}
|
||||
|
||||
@ -398,8 +404,8 @@ gbt_ts_ssup_cmp(Datum x, Datum y, SortSupport ssup)
|
||||
|
||||
/* for leaf items we expect lower == upper, so only compare lower */
|
||||
return DatumGetInt32(DirectFunctionCall2(timestamp_cmp,
|
||||
TimestampGetDatum(arg1->lower),
|
||||
TimestampGetDatum(arg2->lower)));
|
||||
TimestampGetDatumFast(arg1->lower),
|
||||
TimestampGetDatumFast(arg2->lower)));
|
||||
}
|
||||
|
||||
Datum
|
||||
|
@ -119,38 +119,38 @@ gbt_num_fetch(GISTENTRY *entry, const gbtree_ninfo *tinfo)
|
||||
switch (tinfo->t)
|
||||
{
|
||||
case gbt_t_bool:
|
||||
datum = BoolGetDatum(*(bool *) DatumGetPointer(entry->key));
|
||||
datum = BoolGetDatum(*(bool *) entry->key);
|
||||
break;
|
||||
case gbt_t_int2:
|
||||
datum = Int16GetDatum(*(int16 *) DatumGetPointer(entry->key));
|
||||
datum = Int16GetDatum(*(int16 *) entry->key);
|
||||
break;
|
||||
case gbt_t_int4:
|
||||
datum = Int32GetDatum(*(int32 *) DatumGetPointer(entry->key));
|
||||
datum = Int32GetDatum(*(int32 *) entry->key);
|
||||
break;
|
||||
case gbt_t_int8:
|
||||
datum = Int64GetDatum(*(int64 *) DatumGetPointer(entry->key));
|
||||
datum = Int64GetDatum(*(int64 *) entry->key);
|
||||
break;
|
||||
case gbt_t_oid:
|
||||
case gbt_t_enum:
|
||||
datum = ObjectIdGetDatum(*(Oid *) DatumGetPointer(entry->key));
|
||||
datum = ObjectIdGetDatum(*(Oid *) entry->key);
|
||||
break;
|
||||
case gbt_t_float4:
|
||||
datum = Float4GetDatum(*(float4 *) DatumGetPointer(entry->key));
|
||||
datum = Float4GetDatum(*(float4 *) entry->key);
|
||||
break;
|
||||
case gbt_t_float8:
|
||||
datum = Float8GetDatum(*(float8 *) DatumGetPointer(entry->key));
|
||||
datum = Float8GetDatum(*(float8 *) entry->key);
|
||||
break;
|
||||
case gbt_t_date:
|
||||
datum = DateADTGetDatum(*(DateADT *) DatumGetPointer(entry->key));
|
||||
datum = DateADTGetDatum(*(DateADT *) entry->key);
|
||||
break;
|
||||
case gbt_t_time:
|
||||
datum = TimeADTGetDatum(*(TimeADT *) DatumGetPointer(entry->key));
|
||||
datum = TimeADTGetDatum(*(TimeADT *) entry->key);
|
||||
break;
|
||||
case gbt_t_ts:
|
||||
datum = TimestampGetDatum(*(Timestamp *) DatumGetPointer(entry->key));
|
||||
datum = TimestampGetDatum(*(Timestamp *) entry->key);
|
||||
break;
|
||||
case gbt_t_cash:
|
||||
datum = CashGetDatum(*(Cash *) DatumGetPointer(entry->key));
|
||||
datum = CashGetDatum(*(Cash *) entry->key);
|
||||
break;
|
||||
default:
|
||||
datum = entry->key;
|
||||
|
@ -11,7 +11,6 @@
|
||||
#include "btree_utils_var.h"
|
||||
#include "mb/pg_wchar.h"
|
||||
#include "utils/rel.h"
|
||||
#include "varatt.h"
|
||||
|
||||
/* used for key sorting */
|
||||
typedef struct
|
||||
|
@ -6,7 +6,6 @@
|
||||
#include "btree_gist.h"
|
||||
#include "btree_utils_num.h"
|
||||
#include "port/pg_bswap.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/sortsupport.h"
|
||||
#include "utils/uuid.h"
|
||||
|
||||
|
@ -62,7 +62,10 @@ typedef struct NDBOX
|
||||
/* for cubescan.l and cubeparse.y */
|
||||
/* All grammar constructs return strings */
|
||||
#define YYSTYPE char *
|
||||
#ifndef YY_TYPEDEF_YY_SCANNER_T
|
||||
#define YY_TYPEDEF_YY_SCANNER_T
|
||||
typedef void *yyscan_t;
|
||||
#endif
|
||||
|
||||
/* in cubescan.l */
|
||||
extern int cube_yylex(YYSTYPE *yylval_param, yyscan_t yyscanner);
|
||||
|
@ -101,8 +101,8 @@ static void materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
const char *conname,
|
||||
const char *sql,
|
||||
bool fail);
|
||||
static PGresult *storeQueryResult(storeInfo *sinfo, PGconn *conn, const char *sql);
|
||||
static void storeRow(storeInfo *sinfo, PGresult *res, bool first);
|
||||
static PGresult *storeQueryResult(volatile storeInfo *sinfo, PGconn *conn, const char *sql);
|
||||
static void storeRow(volatile storeInfo *sinfo, PGresult *res, bool first);
|
||||
static remoteConn *getConnectionByName(const char *name);
|
||||
static HTAB *createConnHash(void);
|
||||
static remoteConn *createNewConnection(const char *name);
|
||||
@ -169,6 +169,14 @@ typedef struct remoteConnHashEnt
|
||||
/* initial number of connection hashes */
|
||||
#define NUMCONN 16
|
||||
|
||||
static char *
|
||||
xpstrdup(const char *in)
|
||||
{
|
||||
if (in == NULL)
|
||||
return NULL;
|
||||
return pstrdup(in);
|
||||
}
|
||||
|
||||
pg_noreturn static void
|
||||
dblink_res_internalerror(PGconn *conn, PGresult *res, const char *p2)
|
||||
{
|
||||
@ -232,10 +240,6 @@ dblink_get_conn(char *conname_or_str,
|
||||
errmsg("could not establish connection"),
|
||||
errdetail_internal("%s", msg)));
|
||||
}
|
||||
|
||||
PQsetNoticeReceiver(conn, libpqsrv_notice_receiver,
|
||||
"received message via remote connection");
|
||||
|
||||
dblink_security_check(conn, NULL, connstr);
|
||||
if (PQclientEncoding(conn) != GetDatabaseEncoding())
|
||||
PQsetClientEncoding(conn, GetDatabaseEncodingName());
|
||||
@ -334,9 +338,6 @@ dblink_connect(PG_FUNCTION_ARGS)
|
||||
errdetail_internal("%s", msg)));
|
||||
}
|
||||
|
||||
PQsetNoticeReceiver(conn, libpqsrv_notice_receiver,
|
||||
"received message via remote connection");
|
||||
|
||||
/* check password actually used if not superuser */
|
||||
dblink_security_check(conn, connname, connstr);
|
||||
|
||||
@ -862,123 +863,131 @@ static void
|
||||
materializeResult(FunctionCallInfo fcinfo, PGconn *conn, PGresult *res)
|
||||
{
|
||||
ReturnSetInfo *rsinfo = (ReturnSetInfo *) fcinfo->resultinfo;
|
||||
TupleDesc tupdesc;
|
||||
bool is_sql_cmd;
|
||||
int ntuples;
|
||||
int nfields;
|
||||
|
||||
/* prepTuplestoreResult must have been called previously */
|
||||
Assert(rsinfo->returnMode == SFRM_Materialize);
|
||||
|
||||
if (PQresultStatus(res) == PGRES_COMMAND_OK)
|
||||
PG_TRY();
|
||||
{
|
||||
is_sql_cmd = true;
|
||||
TupleDesc tupdesc;
|
||||
bool is_sql_cmd;
|
||||
int ntuples;
|
||||
int nfields;
|
||||
|
||||
if (PQresultStatus(res) == PGRES_COMMAND_OK)
|
||||
{
|
||||
is_sql_cmd = true;
|
||||
|
||||
/*
|
||||
* need a tuple descriptor representing one TEXT column to return
|
||||
* the command status string as our result tuple
|
||||
*/
|
||||
tupdesc = CreateTemplateTupleDesc(1);
|
||||
TupleDescInitEntry(tupdesc, (AttrNumber) 1, "status",
|
||||
TEXTOID, -1, 0);
|
||||
ntuples = 1;
|
||||
nfields = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
Assert(PQresultStatus(res) == PGRES_TUPLES_OK);
|
||||
|
||||
is_sql_cmd = false;
|
||||
|
||||
/* get a tuple descriptor for our result type */
|
||||
switch (get_call_result_type(fcinfo, NULL, &tupdesc))
|
||||
{
|
||||
case TYPEFUNC_COMPOSITE:
|
||||
/* success */
|
||||
break;
|
||||
case TYPEFUNC_RECORD:
|
||||
/* failed to determine actual type of RECORD */
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
|
||||
errmsg("function returning record called in context "
|
||||
"that cannot accept type record")));
|
||||
break;
|
||||
default:
|
||||
/* result type isn't composite */
|
||||
elog(ERROR, "return type must be a row type");
|
||||
break;
|
||||
}
|
||||
|
||||
/* make sure we have a persistent copy of the tupdesc */
|
||||
tupdesc = CreateTupleDescCopy(tupdesc);
|
||||
ntuples = PQntuples(res);
|
||||
nfields = PQnfields(res);
|
||||
}
|
||||
|
||||
/*
|
||||
* need a tuple descriptor representing one TEXT column to return the
|
||||
* command status string as our result tuple
|
||||
* check result and tuple descriptor have the same number of columns
|
||||
*/
|
||||
tupdesc = CreateTemplateTupleDesc(1);
|
||||
TupleDescInitEntry(tupdesc, (AttrNumber) 1, "status",
|
||||
TEXTOID, -1, 0);
|
||||
ntuples = 1;
|
||||
nfields = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
Assert(PQresultStatus(res) == PGRES_TUPLES_OK);
|
||||
if (nfields != tupdesc->natts)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("remote query result rowtype does not match "
|
||||
"the specified FROM clause rowtype")));
|
||||
|
||||
is_sql_cmd = false;
|
||||
|
||||
/* get a tuple descriptor for our result type */
|
||||
switch (get_call_result_type(fcinfo, NULL, &tupdesc))
|
||||
if (ntuples > 0)
|
||||
{
|
||||
case TYPEFUNC_COMPOSITE:
|
||||
/* success */
|
||||
break;
|
||||
case TYPEFUNC_RECORD:
|
||||
/* failed to determine actual type of RECORD */
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
|
||||
errmsg("function returning record called in context "
|
||||
"that cannot accept type record")));
|
||||
break;
|
||||
default:
|
||||
/* result type isn't composite */
|
||||
elog(ERROR, "return type must be a row type");
|
||||
break;
|
||||
}
|
||||
AttInMetadata *attinmeta;
|
||||
int nestlevel = -1;
|
||||
Tuplestorestate *tupstore;
|
||||
MemoryContext oldcontext;
|
||||
int row;
|
||||
char **values;
|
||||
|
||||
/* make sure we have a persistent copy of the tupdesc */
|
||||
tupdesc = CreateTupleDescCopy(tupdesc);
|
||||
ntuples = PQntuples(res);
|
||||
nfields = PQnfields(res);
|
||||
}
|
||||
|
||||
/*
|
||||
* check result and tuple descriptor have the same number of columns
|
||||
*/
|
||||
if (nfields != tupdesc->natts)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("remote query result rowtype does not match "
|
||||
"the specified FROM clause rowtype")));
|
||||
|
||||
if (ntuples > 0)
|
||||
{
|
||||
AttInMetadata *attinmeta;
|
||||
int nestlevel = -1;
|
||||
Tuplestorestate *tupstore;
|
||||
MemoryContext oldcontext;
|
||||
int row;
|
||||
char **values;
|
||||
|
||||
attinmeta = TupleDescGetAttInMetadata(tupdesc);
|
||||
|
||||
/* Set GUCs to ensure we read GUC-sensitive data types correctly */
|
||||
if (!is_sql_cmd)
|
||||
nestlevel = applyRemoteGucs(conn);
|
||||
|
||||
oldcontext = MemoryContextSwitchTo(rsinfo->econtext->ecxt_per_query_memory);
|
||||
tupstore = tuplestore_begin_heap(true, false, work_mem);
|
||||
rsinfo->setResult = tupstore;
|
||||
rsinfo->setDesc = tupdesc;
|
||||
MemoryContextSwitchTo(oldcontext);
|
||||
|
||||
values = palloc_array(char *, nfields);
|
||||
|
||||
/* put all tuples into the tuplestore */
|
||||
for (row = 0; row < ntuples; row++)
|
||||
{
|
||||
HeapTuple tuple;
|
||||
attinmeta = TupleDescGetAttInMetadata(tupdesc);
|
||||
|
||||
/* Set GUCs to ensure we read GUC-sensitive data types correctly */
|
||||
if (!is_sql_cmd)
|
||||
{
|
||||
int i;
|
||||
nestlevel = applyRemoteGucs(conn);
|
||||
|
||||
for (i = 0; i < nfields; i++)
|
||||
oldcontext = MemoryContextSwitchTo(rsinfo->econtext->ecxt_per_query_memory);
|
||||
tupstore = tuplestore_begin_heap(true, false, work_mem);
|
||||
rsinfo->setResult = tupstore;
|
||||
rsinfo->setDesc = tupdesc;
|
||||
MemoryContextSwitchTo(oldcontext);
|
||||
|
||||
values = palloc_array(char *, nfields);
|
||||
|
||||
/* put all tuples into the tuplestore */
|
||||
for (row = 0; row < ntuples; row++)
|
||||
{
|
||||
HeapTuple tuple;
|
||||
|
||||
if (!is_sql_cmd)
|
||||
{
|
||||
if (PQgetisnull(res, row, i))
|
||||
values[i] = NULL;
|
||||
else
|
||||
values[i] = PQgetvalue(res, row, i);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < nfields; i++)
|
||||
{
|
||||
if (PQgetisnull(res, row, i))
|
||||
values[i] = NULL;
|
||||
else
|
||||
values[i] = PQgetvalue(res, row, i);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
values[0] = PQcmdStatus(res);
|
||||
else
|
||||
{
|
||||
values[0] = PQcmdStatus(res);
|
||||
}
|
||||
|
||||
/* build the tuple and put it into the tuplestore. */
|
||||
tuple = BuildTupleFromCStrings(attinmeta, values);
|
||||
tuplestore_puttuple(tupstore, tuple);
|
||||
}
|
||||
|
||||
/* build the tuple and put it into the tuplestore. */
|
||||
tuple = BuildTupleFromCStrings(attinmeta, values);
|
||||
tuplestore_puttuple(tupstore, tuple);
|
||||
/* clean up GUC settings, if we changed any */
|
||||
restoreLocalGucs(nestlevel);
|
||||
}
|
||||
|
||||
/* clean up GUC settings, if we changed any */
|
||||
restoreLocalGucs(nestlevel);
|
||||
}
|
||||
|
||||
PQclear(res);
|
||||
PG_FINALLY();
|
||||
{
|
||||
/* be sure to release the libpq result */
|
||||
PQclear(res);
|
||||
}
|
||||
PG_END_TRY();
|
||||
}
|
||||
|
||||
/*
|
||||
@ -997,17 +1006,16 @@ materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
bool fail)
|
||||
{
|
||||
ReturnSetInfo *rsinfo = (ReturnSetInfo *) fcinfo->resultinfo;
|
||||
PGresult *volatile res = NULL;
|
||||
volatile storeInfo sinfo = {0};
|
||||
|
||||
/* prepTuplestoreResult must have been called previously */
|
||||
Assert(rsinfo->returnMode == SFRM_Materialize);
|
||||
|
||||
/* Use a PG_TRY block to ensure we pump libpq dry of results */
|
||||
sinfo.fcinfo = fcinfo;
|
||||
|
||||
PG_TRY();
|
||||
{
|
||||
storeInfo sinfo = {0};
|
||||
PGresult *res;
|
||||
|
||||
sinfo.fcinfo = fcinfo;
|
||||
/* Create short-lived memory context for data conversions */
|
||||
sinfo.tmpcontext = AllocSetContextCreate(CurrentMemoryContext,
|
||||
"dblink temporary context",
|
||||
@ -1020,7 +1028,14 @@ materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
(PQresultStatus(res) != PGRES_COMMAND_OK &&
|
||||
PQresultStatus(res) != PGRES_TUPLES_OK))
|
||||
{
|
||||
dblink_res_error(conn, conname, res, fail,
|
||||
/*
|
||||
* dblink_res_error will clear the passed PGresult, so we need
|
||||
* this ugly dance to avoid doing so twice during error exit
|
||||
*/
|
||||
PGresult *res1 = res;
|
||||
|
||||
res = NULL;
|
||||
dblink_res_error(conn, conname, res1, fail,
|
||||
"while executing query");
|
||||
/* if fail isn't set, we'll return an empty query result */
|
||||
}
|
||||
@ -1059,6 +1074,7 @@ materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
tuplestore_puttuple(tupstore, tuple);
|
||||
|
||||
PQclear(res);
|
||||
res = NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1067,20 +1083,26 @@ materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
Assert(rsinfo->setResult != NULL);
|
||||
|
||||
PQclear(res);
|
||||
res = NULL;
|
||||
}
|
||||
|
||||
/* clean up data conversion short-lived memory context */
|
||||
if (sinfo.tmpcontext != NULL)
|
||||
MemoryContextDelete(sinfo.tmpcontext);
|
||||
sinfo.tmpcontext = NULL;
|
||||
|
||||
PQclear(sinfo.last_res);
|
||||
sinfo.last_res = NULL;
|
||||
PQclear(sinfo.cur_res);
|
||||
sinfo.cur_res = NULL;
|
||||
}
|
||||
PG_CATCH();
|
||||
{
|
||||
PGresult *res;
|
||||
|
||||
/* be sure to clear out any pending data in libpq */
|
||||
/* be sure to release any libpq result we collected */
|
||||
PQclear(res);
|
||||
PQclear(sinfo.last_res);
|
||||
PQclear(sinfo.cur_res);
|
||||
/* and clear out any pending data in libpq */
|
||||
while ((res = libpqsrv_get_result(conn, dblink_we_get_result)) !=
|
||||
NULL)
|
||||
PQclear(res);
|
||||
@ -1093,7 +1115,7 @@ materializeQueryResult(FunctionCallInfo fcinfo,
|
||||
* Execute query, and send any result rows to sinfo->tuplestore.
|
||||
*/
|
||||
static PGresult *
|
||||
storeQueryResult(storeInfo *sinfo, PGconn *conn, const char *sql)
|
||||
storeQueryResult(volatile storeInfo *sinfo, PGconn *conn, const char *sql)
|
||||
{
|
||||
bool first = true;
|
||||
int nestlevel = -1;
|
||||
@ -1161,7 +1183,7 @@ storeQueryResult(storeInfo *sinfo, PGconn *conn, const char *sql)
|
||||
* (in this case the PGresult might contain either zero or one row).
|
||||
*/
|
||||
static void
|
||||
storeRow(storeInfo *sinfo, PGresult *res, bool first)
|
||||
storeRow(volatile storeInfo *sinfo, PGresult *res, bool first)
|
||||
{
|
||||
int nfields = PQnfields(res);
|
||||
HeapTuple tuple;
|
||||
@ -2766,13 +2788,10 @@ dblink_connstr_check(const char *connstr)
|
||||
/*
|
||||
* Report an error received from the remote server
|
||||
*
|
||||
* res: the received error result
|
||||
* res: the received error result (will be freed)
|
||||
* fail: true for ERROR ereport, false for NOTICE
|
||||
* fmt and following args: sprintf-style format and values for errcontext;
|
||||
* the resulting string should be worded like "while <some action>"
|
||||
*
|
||||
* If "res" is not NULL, it'll be PQclear'ed here (unless we throw error,
|
||||
* in which case memory context cleanup will clear it eventually).
|
||||
*/
|
||||
static void
|
||||
dblink_res_error(PGconn *conn, const char *conname, PGresult *res,
|
||||
@ -2780,11 +2799,15 @@ dblink_res_error(PGconn *conn, const char *conname, PGresult *res,
|
||||
{
|
||||
int level;
|
||||
char *pg_diag_sqlstate = PQresultErrorField(res, PG_DIAG_SQLSTATE);
|
||||
char *message_primary = PQresultErrorField(res, PG_DIAG_MESSAGE_PRIMARY);
|
||||
char *message_detail = PQresultErrorField(res, PG_DIAG_MESSAGE_DETAIL);
|
||||
char *message_hint = PQresultErrorField(res, PG_DIAG_MESSAGE_HINT);
|
||||
char *message_context = PQresultErrorField(res, PG_DIAG_CONTEXT);
|
||||
char *pg_diag_message_primary = PQresultErrorField(res, PG_DIAG_MESSAGE_PRIMARY);
|
||||
char *pg_diag_message_detail = PQresultErrorField(res, PG_DIAG_MESSAGE_DETAIL);
|
||||
char *pg_diag_message_hint = PQresultErrorField(res, PG_DIAG_MESSAGE_HINT);
|
||||
char *pg_diag_context = PQresultErrorField(res, PG_DIAG_CONTEXT);
|
||||
int sqlstate;
|
||||
char *message_primary;
|
||||
char *message_detail;
|
||||
char *message_hint;
|
||||
char *message_context;
|
||||
va_list ap;
|
||||
char dblink_context_msg[512];
|
||||
|
||||
@ -2802,6 +2825,11 @@ dblink_res_error(PGconn *conn, const char *conname, PGresult *res,
|
||||
else
|
||||
sqlstate = ERRCODE_CONNECTION_FAILURE;
|
||||
|
||||
message_primary = xpstrdup(pg_diag_message_primary);
|
||||
message_detail = xpstrdup(pg_diag_message_detail);
|
||||
message_hint = xpstrdup(pg_diag_message_hint);
|
||||
message_context = xpstrdup(pg_diag_context);
|
||||
|
||||
/*
|
||||
* If we don't get a message from the PGresult, try the PGconn. This is
|
||||
* needed because for connection-level failures, PQgetResult may just
|
||||
@ -2810,6 +2838,14 @@ dblink_res_error(PGconn *conn, const char *conname, PGresult *res,
|
||||
if (message_primary == NULL)
|
||||
message_primary = pchomp(PQerrorMessage(conn));
|
||||
|
||||
/*
|
||||
* Now that we've copied all the data we need out of the PGresult, it's
|
||||
* safe to free it. We must do this to avoid PGresult leakage. We're
|
||||
* leaking all the strings too, but those are in palloc'd memory that will
|
||||
* get cleaned up eventually.
|
||||
*/
|
||||
PQclear(res);
|
||||
|
||||
/*
|
||||
* Format the basic errcontext string. Below, we'll add on something
|
||||
* about the connection name. That's a violation of the translatability
|
||||
@ -2834,7 +2870,6 @@ dblink_res_error(PGconn *conn, const char *conname, PGresult *res,
|
||||
dblink_context_msg, conname)) :
|
||||
(errcontext("%s on unnamed dblink connection",
|
||||
dblink_context_msg))));
|
||||
PQclear(res);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -34,7 +34,7 @@ tests += {
|
||||
'sql': [
|
||||
'dblink',
|
||||
],
|
||||
'regress_args': ['--dlpath', meson.project_build_root() / 'src/test/regress'],
|
||||
'regress_args': ['--dlpath', meson.build_root() / 'src/test/regress'],
|
||||
},
|
||||
'tap': {
|
||||
'tests': [
|
||||
|
@ -322,7 +322,6 @@ SET constraint_exclusion = 'on';
|
||||
SELECT explain_filter('EXPLAIN (VERBOSE, COSTS FALSE) SELECT * FROM agg_csv WHERE a < 0');
|
||||
Result
|
||||
Output: a, b
|
||||
Replaces: Scan on agg_csv
|
||||
One-Time Filter: false
|
||||
|
||||
\t off
|
||||
|
@ -127,7 +127,7 @@ gin_extract_hstore_query(PG_FUNCTION_ARGS)
|
||||
/* Nulls in the array are ignored, cf hstoreArrayToPairs */
|
||||
if (key_nulls[i])
|
||||
continue;
|
||||
item = makeitem(VARDATA(DatumGetPointer(key_datums[i])), VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ, KEYFLAG);
|
||||
item = makeitem(VARDATA(key_datums[i]), VARSIZE(key_datums[i]) - VARHDRSZ, KEYFLAG);
|
||||
entries[j++] = PointerGetDatum(item);
|
||||
}
|
||||
|
||||
|
@ -576,7 +576,7 @@ ghstore_consistent(PG_FUNCTION_ARGS)
|
||||
|
||||
if (key_nulls[i])
|
||||
continue;
|
||||
crc = crc32_sz(VARDATA(DatumGetPointer(key_datums[i])), VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ);
|
||||
crc = crc32_sz(VARDATA(key_datums[i]), VARSIZE(key_datums[i]) - VARHDRSZ);
|
||||
if (!(GETBIT(sign, HASHVAL(crc, siglen))))
|
||||
res = false;
|
||||
}
|
||||
@ -599,7 +599,7 @@ ghstore_consistent(PG_FUNCTION_ARGS)
|
||||
|
||||
if (key_nulls[i])
|
||||
continue;
|
||||
crc = crc32_sz(VARDATA(DatumGetPointer(key_datums[i])), VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ);
|
||||
crc = crc32_sz(VARDATA(key_datums[i]), VARSIZE(key_datums[i]) - VARHDRSZ);
|
||||
if (GETBIT(sign, HASHVAL(crc, siglen)))
|
||||
res = true;
|
||||
}
|
||||
|
@ -684,22 +684,22 @@ hstore_from_arrays(PG_FUNCTION_ARGS)
|
||||
|
||||
if (!value_nulls || value_nulls[i])
|
||||
{
|
||||
pairs[i].key = VARDATA(DatumGetPointer(key_datums[i]));
|
||||
pairs[i].key = VARDATA(key_datums[i]);
|
||||
pairs[i].val = NULL;
|
||||
pairs[i].keylen =
|
||||
hstoreCheckKeyLen(VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ);
|
||||
hstoreCheckKeyLen(VARSIZE(key_datums[i]) - VARHDRSZ);
|
||||
pairs[i].vallen = 4;
|
||||
pairs[i].isnull = true;
|
||||
pairs[i].needfree = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
pairs[i].key = VARDATA(DatumGetPointer(key_datums[i]));
|
||||
pairs[i].val = VARDATA(DatumGetPointer(value_datums[i]));
|
||||
pairs[i].key = VARDATA(key_datums[i]);
|
||||
pairs[i].val = VARDATA(value_datums[i]);
|
||||
pairs[i].keylen =
|
||||
hstoreCheckKeyLen(VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ);
|
||||
hstoreCheckKeyLen(VARSIZE(key_datums[i]) - VARHDRSZ);
|
||||
pairs[i].vallen =
|
||||
hstoreCheckValLen(VARSIZE(DatumGetPointer(value_datums[i])) - VARHDRSZ);
|
||||
hstoreCheckValLen(VARSIZE(value_datums[i]) - VARHDRSZ);
|
||||
pairs[i].isnull = false;
|
||||
pairs[i].needfree = false;
|
||||
}
|
||||
@ -778,22 +778,22 @@ hstore_from_array(PG_FUNCTION_ARGS)
|
||||
|
||||
if (in_nulls[i * 2 + 1])
|
||||
{
|
||||
pairs[i].key = VARDATA(DatumGetPointer(in_datums[i * 2]));
|
||||
pairs[i].key = VARDATA(in_datums[i * 2]);
|
||||
pairs[i].val = NULL;
|
||||
pairs[i].keylen =
|
||||
hstoreCheckKeyLen(VARSIZE(DatumGetPointer(in_datums[i * 2])) - VARHDRSZ);
|
||||
hstoreCheckKeyLen(VARSIZE(in_datums[i * 2]) - VARHDRSZ);
|
||||
pairs[i].vallen = 4;
|
||||
pairs[i].isnull = true;
|
||||
pairs[i].needfree = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
pairs[i].key = VARDATA(DatumGetPointer(in_datums[i * 2]));
|
||||
pairs[i].val = VARDATA(DatumGetPointer(in_datums[i * 2 + 1]));
|
||||
pairs[i].key = VARDATA(in_datums[i * 2]);
|
||||
pairs[i].val = VARDATA(in_datums[i * 2 + 1]);
|
||||
pairs[i].keylen =
|
||||
hstoreCheckKeyLen(VARSIZE(DatumGetPointer(in_datums[i * 2])) - VARHDRSZ);
|
||||
hstoreCheckKeyLen(VARSIZE(in_datums[i * 2]) - VARHDRSZ);
|
||||
pairs[i].vallen =
|
||||
hstoreCheckValLen(VARSIZE(DatumGetPointer(in_datums[i * 2 + 1])) - VARHDRSZ);
|
||||
hstoreCheckValLen(VARSIZE(in_datums[i * 2 + 1]) - VARHDRSZ);
|
||||
pairs[i].isnull = false;
|
||||
pairs[i].needfree = false;
|
||||
}
|
||||
|
@ -107,8 +107,8 @@ hstoreArrayToPairs(ArrayType *a, int *npairs)
|
||||
{
|
||||
if (!key_nulls[i])
|
||||
{
|
||||
key_pairs[j].key = VARDATA(DatumGetPointer(key_datums[i]));
|
||||
key_pairs[j].keylen = VARSIZE(DatumGetPointer(key_datums[i])) - VARHDRSZ;
|
||||
key_pairs[j].key = VARDATA(key_datums[i]);
|
||||
key_pairs[j].keylen = VARSIZE(key_datums[i]) - VARHDRSZ;
|
||||
key_pairs[j].val = NULL;
|
||||
key_pairs[j].vallen = 0;
|
||||
key_pairs[j].needfree = 0;
|
||||
|
@ -108,7 +108,7 @@ _int_overlap(PG_FUNCTION_ARGS)
|
||||
CHECKARRVALID(a);
|
||||
CHECKARRVALID(b);
|
||||
if (ARRISEMPTY(a) || ARRISEMPTY(b))
|
||||
PG_RETURN_BOOL(false);
|
||||
return false;
|
||||
|
||||
SORT(a);
|
||||
SORT(b);
|
||||
|
@ -210,8 +210,8 @@ _int_matchsel(PG_FUNCTION_ARGS)
|
||||
*/
|
||||
if (sslot.nnumbers == sslot.nvalues + 3)
|
||||
{
|
||||
/* Grab the minimal MCE frequency. */
|
||||
minfreq = sslot.numbers[sslot.nvalues];
|
||||
/* Grab the lowest frequency. */
|
||||
minfreq = sslot.numbers[sslot.nnumbers - (sslot.nnumbers - sslot.nvalues)];
|
||||
|
||||
mcelems = sslot.values;
|
||||
mcefreqs = sslot.numbers;
|
||||
@ -269,11 +269,8 @@ int_query_opr_selec(ITEM *item, Datum *mcelems, float4 *mcefreqs,
|
||||
else
|
||||
{
|
||||
/*
|
||||
* The element is not in MCELEM. Estimate its frequency as half
|
||||
* that of the least-frequent MCE. (We know it cannot be more
|
||||
* than minfreq, and it could be a great deal less. Half seems
|
||||
* like a good compromise.) For probably-historical reasons,
|
||||
* clamp to not more than DEFAULT_EQ_SEL.
|
||||
* The element is not in MCELEM. Punt, but assume that the
|
||||
* selectivity cannot be more than minfreq / 2.
|
||||
*/
|
||||
selec = Min(DEFAULT_EQ_SEL, minfreq / 2);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* UPC.h
|
||||
* ISSN.h
|
||||
* PostgreSQL type definitions for ISNs (ISBN, ISMN, ISSN, EAN13, UPC)
|
||||
*
|
||||
* No information available for UPC prefixes
|
||||
|
@ -726,7 +726,7 @@ string2ean(const char *str, struct Node *escontext, ean13 *result,
|
||||
if (type != INVALID)
|
||||
goto eaninvalid;
|
||||
type = ISSN;
|
||||
*aux1++ = pg_ascii_toupper((unsigned char) *aux2);
|
||||
*aux1++ = toupper((unsigned char) *aux2);
|
||||
length++;
|
||||
}
|
||||
else if (length == 9 && (digit || *aux2 == 'X' || *aux2 == 'x') && last)
|
||||
@ -736,7 +736,7 @@ string2ean(const char *str, struct Node *escontext, ean13 *result,
|
||||
goto eaninvalid;
|
||||
if (type == INVALID)
|
||||
type = ISBN; /* ISMN must start with 'M' */
|
||||
*aux1++ = pg_ascii_toupper((unsigned char) *aux2);
|
||||
*aux1++ = toupper((unsigned char) *aux2);
|
||||
length++;
|
||||
}
|
||||
else if (length == 11 && digit && last)
|
||||
|
@ -84,7 +84,7 @@ _ltree_compress(PG_FUNCTION_ARGS)
|
||||
entry->rel, entry->page,
|
||||
entry->offset, false);
|
||||
}
|
||||
else if (!LTG_ISALLTRUE(DatumGetPointer(entry->key)))
|
||||
else if (!LTG_ISALLTRUE(entry->key))
|
||||
{
|
||||
int32 i;
|
||||
ltree_gist *key;
|
||||
|
@ -506,7 +506,7 @@ bt_page_print_tuples(ua_page_items *uargs)
|
||||
|
||||
j = 0;
|
||||
memset(nulls, 0, sizeof(nulls));
|
||||
values[j++] = Int16GetDatum(offset);
|
||||
values[j++] = DatumGetInt16(offset);
|
||||
values[j++] = ItemPointerGetDatum(&itup->t_tid);
|
||||
values[j++] = Int32GetDatum((int) IndexTupleSize(itup));
|
||||
values[j++] = BoolGetDatum(IndexTupleHasNulls(itup));
|
||||
|
@ -5,21 +5,21 @@ CREATE UNLOGGED TABLE test_gist AS SELECT point(i,i) p, i::text t FROM
|
||||
CREATE INDEX test_gist_idx ON test_gist USING gist (p);
|
||||
-- Page 0 is the root, the rest are leaf pages
|
||||
SELECT * FROM gist_page_opaque_info(get_raw_page('test_gist_idx', 0));
|
||||
lsn | nsn | rightlink | flags
|
||||
------------+------------+------------+-------
|
||||
0/00000001 | 0/00000000 | 4294967295 | {}
|
||||
lsn | nsn | rightlink | flags
|
||||
-----+-----+------------+-------
|
||||
0/1 | 0/0 | 4294967295 | {}
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM gist_page_opaque_info(get_raw_page('test_gist_idx', 1));
|
||||
lsn | nsn | rightlink | flags
|
||||
------------+------------+------------+--------
|
||||
0/00000001 | 0/00000000 | 4294967295 | {leaf}
|
||||
lsn | nsn | rightlink | flags
|
||||
-----+-----+------------+--------
|
||||
0/1 | 0/0 | 4294967295 | {leaf}
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM gist_page_opaque_info(get_raw_page('test_gist_idx', 2));
|
||||
lsn | nsn | rightlink | flags
|
||||
------------+------------+-----------+--------
|
||||
0/00000001 | 0/00000000 | 1 | {leaf}
|
||||
lsn | nsn | rightlink | flags
|
||||
-----+-----+-----------+--------
|
||||
0/1 | 0/0 | 1 | {leaf}
|
||||
(1 row)
|
||||
|
||||
SELECT * FROM gist_page_items(get_raw_page('test_gist_idx', 0), 'test_gist_idx');
|
||||
|
@ -265,9 +265,9 @@ SELECT fsm_page_contents(decode(repeat('00', :block_size), 'hex'));
|
||||
(1 row)
|
||||
|
||||
SELECT page_header(decode(repeat('00', :block_size), 'hex'));
|
||||
page_header
|
||||
------------------------------
|
||||
(0/00000000,0,0,0,0,0,0,0,0)
|
||||
page_header
|
||||
-----------------------
|
||||
(0/0,0,0,0,0,0,0,0,0)
|
||||
(1 row)
|
||||
|
||||
SELECT page_checksum(decode(repeat('00', :block_size), 'hex'), 1);
|
||||
|
@ -174,7 +174,7 @@ gist_page_items_bytea(PG_FUNCTION_ARGS)
|
||||
|
||||
memset(nulls, 0, sizeof(nulls));
|
||||
|
||||
values[0] = Int16GetDatum(offset);
|
||||
values[0] = DatumGetInt16(offset);
|
||||
values[1] = ItemPointerGetDatum(&itup->t_tid);
|
||||
values[2] = Int32GetDatum((int) IndexTupleSize(itup));
|
||||
|
||||
@ -281,7 +281,7 @@ gist_page_items(PG_FUNCTION_ARGS)
|
||||
|
||||
memset(nulls, 0, sizeof(nulls));
|
||||
|
||||
values[0] = Int16GetDatum(offset);
|
||||
values[0] = DatumGetInt16(offset);
|
||||
values[1] = ItemPointerGetDatum(&itup->t_tid);
|
||||
values[2] = Int32GetDatum((int) IndexTupleSize(itup));
|
||||
values[3] = BoolGetDatum(ItemIdIsDead(id));
|
||||
|
@ -256,7 +256,7 @@ heap_page_items(PG_FUNCTION_ARGS)
|
||||
nulls[11] = true;
|
||||
|
||||
if (tuphdr->t_infomask & HEAP_HASOID_OLD)
|
||||
values[12] = ObjectIdGetDatum(HeapTupleHeaderGetOidOld(tuphdr));
|
||||
values[12] = HeapTupleHeaderGetOidOld(tuphdr);
|
||||
else
|
||||
nulls[12] = true;
|
||||
|
||||
|
@ -282,7 +282,7 @@ page_header(PG_FUNCTION_ARGS)
|
||||
{
|
||||
char lsnchar[64];
|
||||
|
||||
snprintf(lsnchar, sizeof(lsnchar), "%X/%08X", LSN_FORMAT_ARGS(lsn));
|
||||
snprintf(lsnchar, sizeof(lsnchar), "%X/%X", LSN_FORMAT_ARGS(lsn));
|
||||
values[0] = CStringGetTextDatum(lsnchar);
|
||||
}
|
||||
else
|
||||
|
@ -194,8 +194,6 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
|
||||
BufferDesc *bufHdr;
|
||||
uint32 buf_state;
|
||||
|
||||
CHECK_FOR_INTERRUPTS();
|
||||
|
||||
bufHdr = GetBufferDescriptor(i);
|
||||
/* Lock each buffer header before inspecting. */
|
||||
buf_state = LockBufHdr(bufHdr);
|
||||
@ -562,8 +560,6 @@ pg_buffercache_summary(PG_FUNCTION_ARGS)
|
||||
BufferDesc *bufHdr;
|
||||
uint32 buf_state;
|
||||
|
||||
CHECK_FOR_INTERRUPTS();
|
||||
|
||||
/*
|
||||
* This function summarizes the state of all headers. Locking the
|
||||
* buffer headers wouldn't provide an improved result as the state of
|
||||
@ -624,8 +620,6 @@ pg_buffercache_usage_counts(PG_FUNCTION_ARGS)
|
||||
uint32 buf_state = pg_atomic_read_u32(&bufHdr->state);
|
||||
int usage_count;
|
||||
|
||||
CHECK_FOR_INTERRUPTS();
|
||||
|
||||
usage_count = BUF_STATE_GET_USAGECOUNT(buf_state);
|
||||
usage_counts[usage_count]++;
|
||||
|
||||
|
@ -44,10 +44,9 @@ EXPLAIN (RANGE_TABLE) SELECT 1;
|
||||
QUERY PLAN
|
||||
------------------------------------------
|
||||
Result (cost=0.00..0.01 rows=1 width=4)
|
||||
RTIs: 1
|
||||
RTI 1 (result):
|
||||
Eref: "*RESULT*" ()
|
||||
(4 rows)
|
||||
(3 rows)
|
||||
|
||||
-- Create a partitioned table.
|
||||
CREATE TABLE vegetables (id serial, name text, genus text)
|
||||
@ -476,7 +475,6 @@ INSERT INTO vegetables (name, genus) VALUES ('broccoflower', 'brassica');
|
||||
Nominal RTI: 1
|
||||
Exclude Relation RTI: 0
|
||||
-> Result
|
||||
RTIs: 2
|
||||
RTI 1 (relation):
|
||||
Eref: vegetables (id, name, genus)
|
||||
Relation: vegetables
|
||||
@ -487,5 +485,5 @@ INSERT INTO vegetables (name, genus) VALUES ('broccoflower', 'brassica');
|
||||
Eref: "*RESULT*" ()
|
||||
Unprunable RTIs: 1
|
||||
Result RTIs: 1
|
||||
(15 rows)
|
||||
(14 rows)
|
||||
|
||||
|
@ -236,18 +236,6 @@ overexplain_per_node_hook(PlanState *planstate, List *ancestors,
|
||||
((MergeAppend *) plan)->apprelids,
|
||||
es);
|
||||
break;
|
||||
case T_Result:
|
||||
|
||||
/*
|
||||
* 'relids' is only meaningful when plan->lefttree is NULL,
|
||||
* but if somehow it ends up set when plan->lefttree is not
|
||||
* NULL, print it anyway.
|
||||
*/
|
||||
if (plan->lefttree == NULL ||
|
||||
((Result *) plan)->relids != NULL)
|
||||
overexplain_bitmapset("RTIs",
|
||||
((Result *) plan)->relids,
|
||||
es);
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -370,15 +370,6 @@ apw_load_buffers(void)
|
||||
apw_state->prewarm_start_idx = apw_state->prewarm_stop_idx = 0;
|
||||
apw_state->prewarmed_blocks = 0;
|
||||
|
||||
/* Don't prewarm more than we can fit. */
|
||||
if (num_elements > NBuffers)
|
||||
{
|
||||
num_elements = NBuffers;
|
||||
ereport(LOG,
|
||||
(errmsg("autoprewarm capping prewarmed blocks to %d (shared_buffers size)",
|
||||
NBuffers)));
|
||||
}
|
||||
|
||||
/* Get the info position of the first block of the next database. */
|
||||
while (apw_state->prewarm_start_idx < num_elements)
|
||||
{
|
||||
@ -419,6 +410,10 @@ apw_load_buffers(void)
|
||||
apw_state->database = current_db;
|
||||
Assert(apw_state->prewarm_start_idx < apw_state->prewarm_stop_idx);
|
||||
|
||||
/* If we've run out of free buffers, don't launch another worker. */
|
||||
if (!have_free_buffer())
|
||||
break;
|
||||
|
||||
/*
|
||||
* Likewise, don't launch if we've already been told to shut down.
|
||||
* (The launch would fail anyway, but we might as well skip it.)
|
||||
@ -467,6 +462,12 @@ apw_read_stream_next_block(ReadStream *stream,
|
||||
{
|
||||
BlockInfoRecord blk = p->block_info[p->pos];
|
||||
|
||||
if (!have_free_buffer())
|
||||
{
|
||||
p->pos = apw_state->prewarm_stop_idx;
|
||||
return InvalidBlockNumber;
|
||||
}
|
||||
|
||||
if (blk.tablespace != p->tablespace)
|
||||
return InvalidBlockNumber;
|
||||
|
||||
@ -522,10 +523,10 @@ autoprewarm_database_main(Datum main_arg)
|
||||
blk = block_info[i];
|
||||
|
||||
/*
|
||||
* Loop until we run out of blocks to prewarm or until we run out of
|
||||
* Loop until we run out of blocks to prewarm or until we run out of free
|
||||
* buffers.
|
||||
*/
|
||||
while (i < apw_state->prewarm_stop_idx)
|
||||
while (i < apw_state->prewarm_stop_idx && have_free_buffer())
|
||||
{
|
||||
Oid tablespace = blk.tablespace;
|
||||
RelFileNumber filenumber = blk.filenumber;
|
||||
@ -567,13 +568,14 @@ autoprewarm_database_main(Datum main_arg)
|
||||
|
||||
/*
|
||||
* We have a relation; now let's loop until we find a valid fork of
|
||||
* the relation or we run out of buffers. Once we've read from all
|
||||
* valid forks or run out of options, we'll close the relation and
|
||||
* the relation or we run out of free buffers. Once we've read from
|
||||
* all valid forks or run out of options, we'll close the relation and
|
||||
* move on.
|
||||
*/
|
||||
while (i < apw_state->prewarm_stop_idx &&
|
||||
blk.tablespace == tablespace &&
|
||||
blk.filenumber == filenumber)
|
||||
blk.filenumber == filenumber &&
|
||||
have_free_buffer())
|
||||
{
|
||||
ForkNumber forknum = blk.forknum;
|
||||
BlockNumber nblocks;
|
||||
@ -862,7 +864,7 @@ apw_init_state(void *ptr)
|
||||
{
|
||||
AutoPrewarmSharedState *state = (AutoPrewarmSharedState *) ptr;
|
||||
|
||||
LWLockInitialize(&state->lock, LWLockNewTrancheId("autoprewarm"));
|
||||
LWLockInitialize(&state->lock, LWLockNewTrancheId());
|
||||
state->bgworker_pid = InvalidPid;
|
||||
state->pid_using_dumpfile = InvalidPid;
|
||||
}
|
||||
@ -881,6 +883,7 @@ apw_init_shmem(void)
|
||||
sizeof(AutoPrewarmSharedState),
|
||||
apw_init_state,
|
||||
&found);
|
||||
LWLockRegisterTranche(apw_state->lock.tranche, "autoprewarm");
|
||||
|
||||
return found;
|
||||
}
|
||||
|
@ -7,7 +7,6 @@ OBJS = \
|
||||
|
||||
EXTENSION = pg_stat_statements
|
||||
DATA = pg_stat_statements--1.4.sql \
|
||||
pg_stat_statements--1.12--1.13.sql \
|
||||
pg_stat_statements--1.11--1.12.sql pg_stat_statements--1.10--1.11.sql \
|
||||
pg_stat_statements--1.9--1.10.sql pg_stat_statements--1.8--1.9.sql \
|
||||
pg_stat_statements--1.7--1.8.sql pg_stat_statements--1.6--1.7.sql \
|
||||
@ -21,7 +20,7 @@ LDFLAGS_SL += $(filter -lm, $(LIBS))
|
||||
REGRESS_OPTS = --temp-config $(top_srcdir)/contrib/pg_stat_statements/pg_stat_statements.conf
|
||||
REGRESS = select dml cursors utility level_tracking planning \
|
||||
user_activity wal entry_timestamp privileges extended \
|
||||
parallel plancache cleanup oldextversions squashing
|
||||
parallel cleanup oldextversions squashing
|
||||
# Disabled because these tests require "shared_preload_libraries=pg_stat_statements",
|
||||
# which typical installcheck users do not have (e.g. buildfarm clients).
|
||||
NO_INSTALLCHECK = 1
|
||||
|
@ -57,8 +57,8 @@ SELECT calls, rows, query FROM pg_stat_statements ORDER BY query COLLATE "C";
|
||||
1 | 0 | COMMIT
|
||||
1 | 0 | DECLARE cursor_stats_1 CURSOR WITH HOLD FOR SELECT $1
|
||||
1 | 0 | DECLARE cursor_stats_2 CURSOR WITH HOLD FOR SELECT $1
|
||||
1 | 1 | FETCH $1 IN cursor_stats_1
|
||||
1 | 1 | FETCH $1 IN cursor_stats_2
|
||||
1 | 1 | FETCH 1 IN cursor_stats_1
|
||||
1 | 1 | FETCH 1 IN cursor_stats_2
|
||||
1 | 1 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
(9 rows)
|
||||
|
||||
@ -68,140 +68,3 @@ SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
(1 row)
|
||||
|
||||
-- Normalization of FETCH statements
|
||||
BEGIN;
|
||||
DECLARE pgss_cursor CURSOR FOR SELECT FROM generate_series(1, 10);
|
||||
-- implicit directions
|
||||
FETCH pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH 1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH 2 pgss_cursor;
|
||||
--
|
||||
(2 rows)
|
||||
|
||||
FETCH -1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit NEXT
|
||||
FETCH NEXT pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit PRIOR
|
||||
FETCH PRIOR pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit FIRST
|
||||
FETCH FIRST pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit LAST
|
||||
FETCH LAST pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit ABSOLUTE
|
||||
FETCH ABSOLUTE 1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH ABSOLUTE 2 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH ABSOLUTE -1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit RELATIVE
|
||||
FETCH RELATIVE 1 pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
FETCH RELATIVE 2 pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
FETCH RELATIVE -1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit FORWARD
|
||||
FETCH ALL pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
-- explicit FORWARD ALL
|
||||
FETCH FORWARD ALL pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
-- explicit FETCH FORWARD
|
||||
FETCH FORWARD pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
FETCH FORWARD 1 pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
FETCH FORWARD 2 pgss_cursor;
|
||||
--
|
||||
(0 rows)
|
||||
|
||||
FETCH FORWARD -1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit FETCH BACKWARD
|
||||
FETCH BACKWARD pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH BACKWARD 1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
FETCH BACKWARD 2 pgss_cursor;
|
||||
--
|
||||
(2 rows)
|
||||
|
||||
FETCH BACKWARD -1 pgss_cursor;
|
||||
--
|
||||
(1 row)
|
||||
|
||||
-- explicit BACKWARD ALL
|
||||
FETCH BACKWARD ALL pgss_cursor;
|
||||
--
|
||||
(6 rows)
|
||||
|
||||
COMMIT;
|
||||
SELECT calls, query FROM pg_stat_statements ORDER BY query COLLATE "C";
|
||||
calls | query
|
||||
-------+--------------------------------------------------------------------
|
||||
1 | BEGIN
|
||||
1 | COMMIT
|
||||
1 | DECLARE pgss_cursor CURSOR FOR SELECT FROM generate_series($1, $2)
|
||||
3 | FETCH ABSOLUTE $1 pgss_cursor
|
||||
1 | FETCH ALL pgss_cursor
|
||||
1 | FETCH BACKWARD ALL pgss_cursor
|
||||
4 | FETCH BACKWARD pgss_cursor
|
||||
1 | FETCH FIRST pgss_cursor
|
||||
1 | FETCH FORWARD ALL pgss_cursor
|
||||
4 | FETCH FORWARD pgss_cursor
|
||||
1 | FETCH LAST pgss_cursor
|
||||
1 | FETCH NEXT pgss_cursor
|
||||
1 | FETCH PRIOR pgss_cursor
|
||||
3 | FETCH RELATIVE $1 pgss_cursor
|
||||
4 | FETCH pgss_cursor
|
||||
1 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
(16 rows)
|
||||
|
||||
|
@ -1147,7 +1147,7 @@ SELECT toplevel, calls, query FROM pg_stat_statements
|
||||
t | 1 | COMMIT
|
||||
t | 1 | DECLARE FOOCUR CURSOR FOR SELECT * from stats_track_tab
|
||||
f | 1 | DECLARE FOOCUR CURSOR FOR SELECT * from stats_track_tab;
|
||||
t | 1 | FETCH FORWARD $1 FROM foocur
|
||||
t | 1 | FETCH FORWARD 1 FROM foocur
|
||||
t | 1 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
(7 rows)
|
||||
|
||||
@ -1176,7 +1176,7 @@ SELECT toplevel, calls, query FROM pg_stat_statements
|
||||
t | 1 | CLOSE foocur
|
||||
t | 1 | COMMIT
|
||||
t | 1 | DECLARE FOOCUR CURSOR FOR SELECT * FROM stats_track_tab
|
||||
t | 1 | FETCH FORWARD $1 FROM foocur
|
||||
t | 1 | FETCH FORWARD 1 FROM foocur
|
||||
t | 1 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
(6 rows)
|
||||
|
||||
|
@ -407,71 +407,4 @@ SELECT count(*) > 0 AS has_data FROM pg_stat_statements;
|
||||
t
|
||||
(1 row)
|
||||
|
||||
-- New functions and views for pg_stat_statements in 1.13
|
||||
AlTER EXTENSION pg_stat_statements UPDATE TO '1.13';
|
||||
\d pg_stat_statements
|
||||
View "public.pg_stat_statements"
|
||||
Column | Type | Collation | Nullable | Default
|
||||
----------------------------+--------------------------+-----------+----------+---------
|
||||
userid | oid | | |
|
||||
dbid | oid | | |
|
||||
toplevel | boolean | | |
|
||||
queryid | bigint | | |
|
||||
query | text | | |
|
||||
plans | bigint | | |
|
||||
total_plan_time | double precision | | |
|
||||
min_plan_time | double precision | | |
|
||||
max_plan_time | double precision | | |
|
||||
mean_plan_time | double precision | | |
|
||||
stddev_plan_time | double precision | | |
|
||||
calls | bigint | | |
|
||||
total_exec_time | double precision | | |
|
||||
min_exec_time | double precision | | |
|
||||
max_exec_time | double precision | | |
|
||||
mean_exec_time | double precision | | |
|
||||
stddev_exec_time | double precision | | |
|
||||
rows | bigint | | |
|
||||
shared_blks_hit | bigint | | |
|
||||
shared_blks_read | bigint | | |
|
||||
shared_blks_dirtied | bigint | | |
|
||||
shared_blks_written | bigint | | |
|
||||
local_blks_hit | bigint | | |
|
||||
local_blks_read | bigint | | |
|
||||
local_blks_dirtied | bigint | | |
|
||||
local_blks_written | bigint | | |
|
||||
temp_blks_read | bigint | | |
|
||||
temp_blks_written | bigint | | |
|
||||
shared_blk_read_time | double precision | | |
|
||||
shared_blk_write_time | double precision | | |
|
||||
local_blk_read_time | double precision | | |
|
||||
local_blk_write_time | double precision | | |
|
||||
temp_blk_read_time | double precision | | |
|
||||
temp_blk_write_time | double precision | | |
|
||||
wal_records | bigint | | |
|
||||
wal_fpi | bigint | | |
|
||||
wal_bytes | numeric | | |
|
||||
wal_buffers_full | bigint | | |
|
||||
jit_functions | bigint | | |
|
||||
jit_generation_time | double precision | | |
|
||||
jit_inlining_count | bigint | | |
|
||||
jit_inlining_time | double precision | | |
|
||||
jit_optimization_count | bigint | | |
|
||||
jit_optimization_time | double precision | | |
|
||||
jit_emission_count | bigint | | |
|
||||
jit_emission_time | double precision | | |
|
||||
jit_deform_count | bigint | | |
|
||||
jit_deform_time | double precision | | |
|
||||
parallel_workers_to_launch | bigint | | |
|
||||
parallel_workers_launched | bigint | | |
|
||||
generic_plan_calls | bigint | | |
|
||||
custom_plan_calls | bigint | | |
|
||||
stats_since | timestamp with time zone | | |
|
||||
minmax_stats_since | timestamp with time zone | | |
|
||||
|
||||
SELECT count(*) > 0 AS has_data FROM pg_stat_statements;
|
||||
has_data
|
||||
----------
|
||||
t
|
||||
(1 row)
|
||||
|
||||
DROP EXTENSION pg_stat_statements;
|
||||
|
@ -1,224 +0,0 @@
|
||||
--
|
||||
-- Tests with plan cache
|
||||
--
|
||||
-- Setup
|
||||
CREATE OR REPLACE FUNCTION select_one_func(int) RETURNS VOID AS $$
|
||||
DECLARE
|
||||
ret INT;
|
||||
BEGIN
|
||||
SELECT $1 INTO ret;
|
||||
END;
|
||||
$$ LANGUAGE plpgsql;
|
||||
CREATE OR REPLACE PROCEDURE select_one_proc(int) AS $$
|
||||
DECLARE
|
||||
ret INT;
|
||||
BEGIN
|
||||
SELECT $1 INTO ret;
|
||||
END;
|
||||
$$ LANGUAGE plpgsql;
|
||||
-- Prepared statements
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
---
|
||||
t
|
||||
(1 row)
|
||||
|
||||
PREPARE p1 AS SELECT $1 AS a;
|
||||
SET plan_cache_mode TO force_generic_plan;
|
||||
EXECUTE p1(1);
|
||||
a
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SET plan_cache_mode TO force_custom_plan;
|
||||
EXECUTE p1(1);
|
||||
a
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT calls, generic_plan_calls, custom_plan_calls, query FROM pg_stat_statements
|
||||
ORDER BY query COLLATE "C";
|
||||
calls | generic_plan_calls | custom_plan_calls | query
|
||||
-------+--------------------+-------------------+----------------------------------------------------
|
||||
2 | 1 | 1 | PREPARE p1 AS SELECT $1 AS a
|
||||
1 | 0 | 0 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
2 | 0 | 0 | SET plan_cache_mode TO $1
|
||||
(3 rows)
|
||||
|
||||
DEALLOCATE p1;
|
||||
-- Extended query protocol
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
---
|
||||
t
|
||||
(1 row)
|
||||
|
||||
SELECT $1 AS a \parse p1
|
||||
SET plan_cache_mode TO force_generic_plan;
|
||||
\bind_named p1 1
|
||||
;
|
||||
a
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SET plan_cache_mode TO force_custom_plan;
|
||||
\bind_named p1 1
|
||||
;
|
||||
a
|
||||
---
|
||||
1
|
||||
(1 row)
|
||||
|
||||
SELECT calls, generic_plan_calls, custom_plan_calls, query FROM pg_stat_statements
|
||||
ORDER BY query COLLATE "C";
|
||||
calls | generic_plan_calls | custom_plan_calls | query
|
||||
-------+--------------------+-------------------+----------------------------------------------------
|
||||
2 | 1 | 1 | SELECT $1 AS a
|
||||
1 | 0 | 0 | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
2 | 0 | 0 | SET plan_cache_mode TO $1
|
||||
(3 rows)
|
||||
|
||||
\close_prepared p1
|
||||
-- EXPLAIN [ANALYZE] EXECUTE
|
||||
SET pg_stat_statements.track = 'all';
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
---
|
||||
t
|
||||
(1 row)
|
||||
|
||||
PREPARE p1 AS SELECT $1;
|
||||
SET plan_cache_mode TO force_generic_plan;
|
||||
EXPLAIN (COSTS OFF) EXECUTE p1(1);
|
||||
QUERY PLAN
|
||||
------------
|
||||
Result
|
||||
(1 row)
|
||||
|
||||
EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) EXECUTE p1(1);
|
||||
QUERY PLAN
|
||||
-----------------------------------
|
||||
Result (actual rows=1.00 loops=1)
|
||||
(1 row)
|
||||
|
||||
SET plan_cache_mode TO force_custom_plan;
|
||||
EXPLAIN (COSTS OFF) EXECUTE p1(1);
|
||||
QUERY PLAN
|
||||
------------
|
||||
Result
|
||||
(1 row)
|
||||
|
||||
EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) EXECUTE p1(1);
|
||||
QUERY PLAN
|
||||
-----------------------------------
|
||||
Result (actual rows=1.00 loops=1)
|
||||
(1 row)
|
||||
|
||||
SELECT calls, generic_plan_calls, custom_plan_calls, toplevel, query FROM pg_stat_statements
|
||||
ORDER BY query COLLATE "C";
|
||||
calls | generic_plan_calls | custom_plan_calls | toplevel | query
|
||||
-------+--------------------+-------------------+----------+----------------------------------------------------------------------------------
|
||||
2 | 0 | 0 | t | EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) EXECUTE p1(1)
|
||||
2 | 0 | 0 | t | EXPLAIN (COSTS OFF) EXECUTE p1(1)
|
||||
4 | 2 | 2 | f | PREPARE p1 AS SELECT $1
|
||||
1 | 0 | 0 | t | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
2 | 0 | 0 | t | SET plan_cache_mode TO $1
|
||||
(5 rows)
|
||||
|
||||
RESET pg_stat_statements.track;
|
||||
DEALLOCATE p1;
|
||||
-- Functions/procedures
|
||||
SET pg_stat_statements.track = 'all';
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
---
|
||||
t
|
||||
(1 row)
|
||||
|
||||
SET plan_cache_mode TO force_generic_plan;
|
||||
SELECT select_one_func(1);
|
||||
select_one_func
|
||||
-----------------
|
||||
|
||||
(1 row)
|
||||
|
||||
CALL select_one_proc(1);
|
||||
SET plan_cache_mode TO force_custom_plan;
|
||||
SELECT select_one_func(1);
|
||||
select_one_func
|
||||
-----------------
|
||||
|
||||
(1 row)
|
||||
|
||||
CALL select_one_proc(1);
|
||||
SELECT calls, generic_plan_calls, custom_plan_calls, toplevel, query FROM pg_stat_statements
|
||||
ORDER BY query COLLATE "C";
|
||||
calls | generic_plan_calls | custom_plan_calls | toplevel | query
|
||||
-------+--------------------+-------------------+----------+----------------------------------------------------
|
||||
2 | 0 | 0 | t | CALL select_one_proc($1)
|
||||
4 | 2 | 2 | f | SELECT $1
|
||||
1 | 0 | 0 | t | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
2 | 0 | 0 | t | SELECT select_one_func($1)
|
||||
2 | 0 | 0 | t | SET plan_cache_mode TO $1
|
||||
(5 rows)
|
||||
|
||||
--
|
||||
-- EXPLAIN [ANALYZE] EXECUTE + functions/procedures
|
||||
--
|
||||
SET pg_stat_statements.track = 'all';
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
t
|
||||
---
|
||||
t
|
||||
(1 row)
|
||||
|
||||
SET plan_cache_mode TO force_generic_plan;
|
||||
EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) SELECT select_one_func(1);
|
||||
QUERY PLAN
|
||||
-----------------------------------
|
||||
Result (actual rows=1.00 loops=1)
|
||||
(1 row)
|
||||
|
||||
EXPLAIN (COSTS OFF) SELECT select_one_func(1);
|
||||
QUERY PLAN
|
||||
------------
|
||||
Result
|
||||
(1 row)
|
||||
|
||||
CALL select_one_proc(1);
|
||||
SET plan_cache_mode TO force_custom_plan;
|
||||
EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) SELECT select_one_func(1);
|
||||
QUERY PLAN
|
||||
-----------------------------------
|
||||
Result (actual rows=1.00 loops=1)
|
||||
(1 row)
|
||||
|
||||
EXPLAIN (COSTS OFF) SELECT select_one_func(1);
|
||||
QUERY PLAN
|
||||
------------
|
||||
Result
|
||||
(1 row)
|
||||
|
||||
CALL select_one_proc(1);
|
||||
SELECT calls, generic_plan_calls, custom_plan_calls, toplevel, query FROM pg_stat_statements
|
||||
ORDER BY query COLLATE "C", toplevel;
|
||||
calls | generic_plan_calls | custom_plan_calls | toplevel | query
|
||||
-------+--------------------+-------------------+----------+------------------------------------------------------------------------------------------------
|
||||
2 | 0 | 0 | t | CALL select_one_proc($1)
|
||||
2 | 0 | 0 | t | EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) SELECT select_one_func($1)
|
||||
4 | 0 | 0 | f | EXPLAIN (ANALYZE, COSTS OFF, SUMMARY OFF, TIMING OFF, BUFFERS OFF) SELECT select_one_func($1);
|
||||
2 | 0 | 0 | t | EXPLAIN (COSTS OFF) SELECT select_one_func($1)
|
||||
4 | 2 | 2 | f | SELECT $1
|
||||
1 | 0 | 0 | t | SELECT pg_stat_statements_reset() IS NOT NULL AS t
|
||||
2 | 0 | 0 | t | SET plan_cache_mode TO $1
|
||||
(7 rows)
|
||||
|
||||
RESET pg_stat_statements.track;
|
||||
--
|
||||
-- Cleanup
|
||||
--
|
||||
DROP FUNCTION select_one_func(int);
|
||||
DROP PROCEDURE select_one_proc(int);
|
@ -702,7 +702,7 @@ SELECT calls, rows, query FROM pg_stat_statements ORDER BY query COLLATE "C";
|
||||
1 | 13 | CREATE MATERIALIZED VIEW pgss_matv AS SELECT * FROM pgss_ctas
|
||||
1 | 10 | CREATE TABLE pgss_ctas AS SELECT a, $1 b FROM generate_series($2, $3) a
|
||||
1 | 0 | DECLARE pgss_cursor CURSOR FOR SELECT * FROM pgss_matv
|
||||
1 | 5 | FETCH FORWARD $1 pgss_cursor
|
||||
1 | 5 | FETCH FORWARD 5 pgss_cursor
|
||||
1 | 7 | FETCH FORWARD ALL pgss_cursor
|
||||
1 | 1 | FETCH NEXT pgss_cursor
|
||||
1 | 13 | REFRESH MATERIALIZED VIEW pgss_matv
|
||||
|
@ -21,7 +21,6 @@ contrib_targets += pg_stat_statements
|
||||
install_data(
|
||||
'pg_stat_statements.control',
|
||||
'pg_stat_statements--1.4.sql',
|
||||
'pg_stat_statements--1.12--1.13.sql',
|
||||
'pg_stat_statements--1.11--1.12.sql',
|
||||
'pg_stat_statements--1.10--1.11.sql',
|
||||
'pg_stat_statements--1.9--1.10.sql',
|
||||
@ -55,7 +54,6 @@ tests += {
|
||||
'privileges',
|
||||
'extended',
|
||||
'parallel',
|
||||
'plancache',
|
||||
'cleanup',
|
||||
'oldextversions',
|
||||
'squashing',
|
||||
|
@ -1,78 +0,0 @@
|
||||
/* contrib/pg_stat_statements/pg_stat_statements--1.12--1.13.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via ALTER EXTENSION
|
||||
\echo Use "ALTER EXTENSION pg_stat_statements UPDATE TO '1.13'" to load this file. \quit
|
||||
|
||||
/* First we have to remove them from the extension */
|
||||
ALTER EXTENSION pg_stat_statements DROP VIEW pg_stat_statements;
|
||||
ALTER EXTENSION pg_stat_statements DROP FUNCTION pg_stat_statements(boolean);
|
||||
|
||||
/* Then we can drop them */
|
||||
DROP VIEW pg_stat_statements;
|
||||
DROP FUNCTION pg_stat_statements(boolean);
|
||||
|
||||
/* Now redefine */
|
||||
CREATE FUNCTION pg_stat_statements(IN showtext boolean,
|
||||
OUT userid oid,
|
||||
OUT dbid oid,
|
||||
OUT toplevel bool,
|
||||
OUT queryid bigint,
|
||||
OUT query text,
|
||||
OUT plans int8,
|
||||
OUT total_plan_time float8,
|
||||
OUT min_plan_time float8,
|
||||
OUT max_plan_time float8,
|
||||
OUT mean_plan_time float8,
|
||||
OUT stddev_plan_time float8,
|
||||
OUT calls int8,
|
||||
OUT total_exec_time float8,
|
||||
OUT min_exec_time float8,
|
||||
OUT max_exec_time float8,
|
||||
OUT mean_exec_time float8,
|
||||
OUT stddev_exec_time float8,
|
||||
OUT rows int8,
|
||||
OUT shared_blks_hit int8,
|
||||
OUT shared_blks_read int8,
|
||||
OUT shared_blks_dirtied int8,
|
||||
OUT shared_blks_written int8,
|
||||
OUT local_blks_hit int8,
|
||||
OUT local_blks_read int8,
|
||||
OUT local_blks_dirtied int8,
|
||||
OUT local_blks_written int8,
|
||||
OUT temp_blks_read int8,
|
||||
OUT temp_blks_written int8,
|
||||
OUT shared_blk_read_time float8,
|
||||
OUT shared_blk_write_time float8,
|
||||
OUT local_blk_read_time float8,
|
||||
OUT local_blk_write_time float8,
|
||||
OUT temp_blk_read_time float8,
|
||||
OUT temp_blk_write_time float8,
|
||||
OUT wal_records int8,
|
||||
OUT wal_fpi int8,
|
||||
OUT wal_bytes numeric,
|
||||
OUT wal_buffers_full int8,
|
||||
OUT jit_functions int8,
|
||||
OUT jit_generation_time float8,
|
||||
OUT jit_inlining_count int8,
|
||||
OUT jit_inlining_time float8,
|
||||
OUT jit_optimization_count int8,
|
||||
OUT jit_optimization_time float8,
|
||||
OUT jit_emission_count int8,
|
||||
OUT jit_emission_time float8,
|
||||
OUT jit_deform_count int8,
|
||||
OUT jit_deform_time float8,
|
||||
OUT parallel_workers_to_launch int8,
|
||||
OUT parallel_workers_launched int8,
|
||||
OUT generic_plan_calls int8,
|
||||
OUT custom_plan_calls int8,
|
||||
OUT stats_since timestamp with time zone,
|
||||
OUT minmax_stats_since timestamp with time zone
|
||||
)
|
||||
RETURNS SETOF record
|
||||
AS 'MODULE_PATHNAME', 'pg_stat_statements_1_13'
|
||||
LANGUAGE C STRICT VOLATILE PARALLEL SAFE;
|
||||
|
||||
CREATE VIEW pg_stat_statements AS
|
||||
SELECT * FROM pg_stat_statements(true);
|
||||
|
||||
GRANT SELECT ON pg_stat_statements TO PUBLIC;
|
@ -85,7 +85,7 @@ PG_MODULE_MAGIC_EXT(
|
||||
#define PGSS_TEXT_FILE PG_STAT_TMP_DIR "/pgss_query_texts.stat"
|
||||
|
||||
/* Magic number identifying the stats file format */
|
||||
static const uint32 PGSS_FILE_HEADER = 0x20250731;
|
||||
static const uint32 PGSS_FILE_HEADER = 0x20220408;
|
||||
|
||||
/* PostgreSQL major version number, changes in which invalidate all entries */
|
||||
static const uint32 PGSS_PG_MAJOR_VERSION = PG_VERSION_NUM / 100;
|
||||
@ -114,7 +114,6 @@ typedef enum pgssVersion
|
||||
PGSS_V1_10,
|
||||
PGSS_V1_11,
|
||||
PGSS_V1_12,
|
||||
PGSS_V1_13,
|
||||
} pgssVersion;
|
||||
|
||||
typedef enum pgssStoreKind
|
||||
@ -139,6 +138,7 @@ typedef enum pgssStoreKind
|
||||
* If you add a new key to this struct, make sure to teach pgss_store() to
|
||||
* zero the padding bytes. Otherwise, things will break, because pgss_hash is
|
||||
* created using HASH_BLOBS, and thus tag_hash is used to hash this.
|
||||
|
||||
*/
|
||||
typedef struct pgssHashKey
|
||||
{
|
||||
@ -210,8 +210,6 @@ typedef struct Counters
|
||||
* to be launched */
|
||||
int64 parallel_workers_launched; /* # of parallel workers actually
|
||||
* launched */
|
||||
int64 generic_plan_calls; /* number of calls using a generic plan */
|
||||
int64 custom_plan_calls; /* number of calls using a custom plan */
|
||||
} Counters;
|
||||
|
||||
/*
|
||||
@ -325,7 +323,6 @@ PG_FUNCTION_INFO_V1(pg_stat_statements_1_9);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements_1_10);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements_1_11);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements_1_12);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements_1_13);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_statements_info);
|
||||
|
||||
@ -358,8 +355,7 @@ static void pgss_store(const char *query, int64 queryId,
|
||||
const struct JitInstrumentation *jitusage,
|
||||
JumbleState *jstate,
|
||||
int parallel_workers_to_launch,
|
||||
int parallel_workers_launched,
|
||||
PlannedStmtOrigin planOrigin);
|
||||
int parallel_workers_launched);
|
||||
static void pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
pgssVersion api_version,
|
||||
bool showtext);
|
||||
@ -881,8 +877,7 @@ pgss_post_parse_analyze(ParseState *pstate, Query *query, JumbleState *jstate)
|
||||
NULL,
|
||||
jstate,
|
||||
0,
|
||||
0,
|
||||
PLAN_STMT_UNKNOWN);
|
||||
0);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -962,8 +957,7 @@ pgss_planner(Query *parse,
|
||||
NULL,
|
||||
NULL,
|
||||
0,
|
||||
0,
|
||||
result->planOrigin);
|
||||
0);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1097,8 +1091,7 @@ pgss_ExecutorEnd(QueryDesc *queryDesc)
|
||||
queryDesc->estate->es_jit ? &queryDesc->estate->es_jit->instr : NULL,
|
||||
NULL,
|
||||
queryDesc->estate->es_parallel_workers_to_launch,
|
||||
queryDesc->estate->es_parallel_workers_launched,
|
||||
queryDesc->plannedstmt->planOrigin);
|
||||
queryDesc->estate->es_parallel_workers_launched);
|
||||
}
|
||||
|
||||
if (prev_ExecutorEnd)
|
||||
@ -1231,8 +1224,7 @@ pgss_ProcessUtility(PlannedStmt *pstmt, const char *queryString,
|
||||
NULL,
|
||||
NULL,
|
||||
0,
|
||||
0,
|
||||
pstmt->planOrigin);
|
||||
0);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1295,8 +1287,7 @@ pgss_store(const char *query, int64 queryId,
|
||||
const struct JitInstrumentation *jitusage,
|
||||
JumbleState *jstate,
|
||||
int parallel_workers_to_launch,
|
||||
int parallel_workers_launched,
|
||||
PlannedStmtOrigin planOrigin)
|
||||
int parallel_workers_launched)
|
||||
{
|
||||
pgssHashKey key;
|
||||
pgssEntry *entry;
|
||||
@ -1504,12 +1495,6 @@ pgss_store(const char *query, int64 queryId,
|
||||
entry->counters.parallel_workers_to_launch += parallel_workers_to_launch;
|
||||
entry->counters.parallel_workers_launched += parallel_workers_launched;
|
||||
|
||||
/* plan cache counters */
|
||||
if (planOrigin == PLAN_STMT_CACHE_GENERIC)
|
||||
entry->counters.generic_plan_calls++;
|
||||
else if (planOrigin == PLAN_STMT_CACHE_CUSTOM)
|
||||
entry->counters.custom_plan_calls++;
|
||||
|
||||
SpinLockRelease(&entry->mutex);
|
||||
}
|
||||
|
||||
@ -1577,8 +1562,7 @@ pg_stat_statements_reset(PG_FUNCTION_ARGS)
|
||||
#define PG_STAT_STATEMENTS_COLS_V1_10 43
|
||||
#define PG_STAT_STATEMENTS_COLS_V1_11 49
|
||||
#define PG_STAT_STATEMENTS_COLS_V1_12 52
|
||||
#define PG_STAT_STATEMENTS_COLS_V1_13 54
|
||||
#define PG_STAT_STATEMENTS_COLS 54 /* maximum of above */
|
||||
#define PG_STAT_STATEMENTS_COLS 52 /* maximum of above */
|
||||
|
||||
/*
|
||||
* Retrieve statement statistics.
|
||||
@ -1590,16 +1574,6 @@ pg_stat_statements_reset(PG_FUNCTION_ARGS)
|
||||
* expected API version is identified by embedding it in the C name of the
|
||||
* function. Unfortunately we weren't bright enough to do that for 1.1.
|
||||
*/
|
||||
Datum
|
||||
pg_stat_statements_1_13(PG_FUNCTION_ARGS)
|
||||
{
|
||||
bool showtext = PG_GETARG_BOOL(0);
|
||||
|
||||
pg_stat_statements_internal(fcinfo, PGSS_V1_13, showtext);
|
||||
|
||||
return (Datum) 0;
|
||||
}
|
||||
|
||||
Datum
|
||||
pg_stat_statements_1_12(PG_FUNCTION_ARGS)
|
||||
{
|
||||
@ -1758,10 +1732,6 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
if (api_version != PGSS_V1_12)
|
||||
elog(ERROR, "incorrect number of output arguments");
|
||||
break;
|
||||
case PG_STAT_STATEMENTS_COLS_V1_13:
|
||||
if (api_version != PGSS_V1_13)
|
||||
elog(ERROR, "incorrect number of output arguments");
|
||||
break;
|
||||
default:
|
||||
elog(ERROR, "incorrect number of output arguments");
|
||||
}
|
||||
@ -2014,11 +1984,6 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
values[i++] = Int64GetDatumFast(tmp.parallel_workers_to_launch);
|
||||
values[i++] = Int64GetDatumFast(tmp.parallel_workers_launched);
|
||||
}
|
||||
if (api_version >= PGSS_V1_13)
|
||||
{
|
||||
values[i++] = Int64GetDatumFast(tmp.generic_plan_calls);
|
||||
values[i++] = Int64GetDatumFast(tmp.custom_plan_calls);
|
||||
}
|
||||
if (api_version >= PGSS_V1_11)
|
||||
{
|
||||
values[i++] = TimestampTzGetDatum(stats_since);
|
||||
@ -2034,7 +1999,6 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
api_version == PGSS_V1_10 ? PG_STAT_STATEMENTS_COLS_V1_10 :
|
||||
api_version == PGSS_V1_11 ? PG_STAT_STATEMENTS_COLS_V1_11 :
|
||||
api_version == PGSS_V1_12 ? PG_STAT_STATEMENTS_COLS_V1_12 :
|
||||
api_version == PGSS_V1_13 ? PG_STAT_STATEMENTS_COLS_V1_13 :
|
||||
-1 /* fail if you forget to update this assert */ ));
|
||||
|
||||
tuplestore_putvalues(rsinfo->setResult, rsinfo->setDesc, values, nulls);
|
||||
@ -2712,8 +2676,8 @@ entry_reset(Oid userid, Oid dbid, int64 queryid, bool minmax_only)
|
||||
HASH_SEQ_STATUS hash_seq;
|
||||
pgssEntry *entry;
|
||||
FILE *qfile;
|
||||
int64 num_entries;
|
||||
int64 num_remove = 0;
|
||||
long num_entries;
|
||||
long num_remove = 0;
|
||||
pgssHashKey key;
|
||||
TimestampTz stats_reset;
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
# pg_stat_statements extension
|
||||
comment = 'track planning and execution statistics of all SQL statements executed'
|
||||
default_version = '1.13'
|
||||
default_version = '1.12'
|
||||
module_pathname = '$libdir/pg_stat_statements'
|
||||
relocatable = true
|
||||
|
@ -28,46 +28,3 @@ COMMIT;
|
||||
|
||||
SELECT calls, rows, query FROM pg_stat_statements ORDER BY query COLLATE "C";
|
||||
SELECT pg_stat_statements_reset() IS NOT NULL AS t;
|
||||
|
||||
-- Normalization of FETCH statements
|
||||
BEGIN;
|
||||
DECLARE pgss_cursor CURSOR FOR SELECT FROM generate_series(1, 10);
|
||||
-- implicit directions
|
||||
FETCH pgss_cursor;
|
||||
FETCH 1 pgss_cursor;
|
||||
FETCH 2 pgss_cursor;
|
||||
FETCH -1 pgss_cursor;
|
||||
-- explicit NEXT
|
||||
FETCH NEXT pgss_cursor;
|
||||
-- explicit PRIOR
|
||||
FETCH PRIOR pgss_cursor;
|
||||
-- explicit FIRST
|
||||
FETCH FIRST pgss_cursor;
|
||||
-- explicit LAST
|
||||
FETCH LAST pgss_cursor;
|
||||
-- explicit ABSOLUTE
|
||||
FETCH ABSOLUTE 1 pgss_cursor;
|
||||
FETCH ABSOLUTE 2 pgss_cursor;
|
||||
FETCH ABSOLUTE -1 pgss_cursor;
|
||||
-- explicit RELATIVE
|
||||
FETCH RELATIVE 1 pgss_cursor;
|
||||
FETCH RELATIVE 2 pgss_cursor;
|
||||
FETCH RELATIVE -1 pgss_cursor;
|
||||
-- explicit FORWARD
|
||||
FETCH ALL pgss_cursor;
|
||||
-- explicit FORWARD ALL
|
||||
FETCH FORWARD ALL pgss_cursor;
|
||||
-- explicit FETCH FORWARD
|
||||
FETCH FORWARD pgss_cursor;
|
||||
FETCH FORWARD 1 pgss_cursor;
|
||||
FETCH FORWARD 2 pgss_cursor;
|
||||
FETCH FORWARD -1 pgss_cursor;
|
||||
-- explicit FETCH BACKWARD
|
||||
FETCH BACKWARD pgss_cursor;
|
||||
FETCH BACKWARD 1 pgss_cursor;
|
||||
FETCH BACKWARD 2 pgss_cursor;
|
||||
FETCH BACKWARD -1 pgss_cursor;
|
||||
-- explicit BACKWARD ALL
|
||||
FETCH BACKWARD ALL pgss_cursor;
|
||||
COMMIT;
|
||||
SELECT calls, query FROM pg_stat_statements ORDER BY query COLLATE "C";
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user