Add hash operator class
The uri = uri operator was marked as HASHES, but no hash function or hash operator class was defined. Hash joins would therefore fail. Bug report and original patch by Grégoire HUBERT (@chanmix51). closes #3
This commit is contained in:
parent
cf854ebea1
commit
cd80642413
3
Makefile
3
Makefile
|
@ -1,11 +1,12 @@
|
|||
PG_CONFIG = pg_config
|
||||
PKG_CONFIG = pkg-config
|
||||
|
||||
extension_version = 0
|
||||
extension_version = 1
|
||||
|
||||
EXTENSION = uri
|
||||
MODULE_big = uri
|
||||
OBJS = uri.o
|
||||
DATA = uri--0--1.sql
|
||||
DATA_built = uri--$(extension_version).sql
|
||||
|
||||
ifeq (no,$(shell $(PKG_CONFIG) liburiparser || echo no))
|
||||
|
|
|
@ -289,3 +289,14 @@ SELECT DISTINCT b FROM test ORDER BY b;
|
|||
ssh://username@review.openstack.org:29418/openstack/nova.git
|
||||
(17 rows)
|
||||
|
||||
CREATE TABLE test2 (x text, y uri);
|
||||
INSERT INTO test2 VALUES ('foo', 'http://www.postgresql.org/');
|
||||
-- check hashing (issue petere/pguri#3)
|
||||
SET enable_nestloop = off;
|
||||
SET enable_mergejoin = off;
|
||||
SELECT * FROM test JOIN test2 ON b = y AND a = 1;
|
||||
a | b | x | y
|
||||
---+----------------------------+-----+----------------------------
|
||||
1 | http://www.postgresql.org/ | foo | http://www.postgresql.org/
|
||||
(1 row)
|
||||
|
||||
|
|
|
@ -48,3 +48,12 @@ SELECT b AS uri,
|
|||
\x off
|
||||
|
||||
SELECT DISTINCT b FROM test ORDER BY b;
|
||||
|
||||
|
||||
CREATE TABLE test2 (x text, y uri);
|
||||
INSERT INTO test2 VALUES ('foo', 'http://www.postgresql.org/');
|
||||
|
||||
-- check hashing (issue petere/pguri#3)
|
||||
SET enable_nestloop = off;
|
||||
SET enable_mergejoin = off;
|
||||
SELECT * FROM test JOIN test2 ON b = y AND a = 1;
|
||||
|
|
|
@ -0,0 +1,10 @@
|
|||
CREATE FUNCTION uri_hash(uri) RETURNS integer
|
||||
IMMUTABLE
|
||||
STRICT
|
||||
LANGUAGE C
|
||||
AS '$libdir/uri';
|
||||
|
||||
CREATE OPERATOR CLASS uri_ops_hash
|
||||
DEFAULT FOR TYPE uri USING hash AS
|
||||
OPERATOR 1 =,
|
||||
FUNCTION 1 uri_hash(uri);
|
19
uri.c
19
uri.c
|
@ -1,4 +1,5 @@
|
|||
#include <postgres.h>
|
||||
#include <access/hash.h>
|
||||
#include <catalog/pg_type.h>
|
||||
#include <fmgr.h>
|
||||
#include <lib/stringinfo.h>
|
||||
|
@ -16,9 +17,11 @@ typedef struct varlena uritype;
|
|||
|
||||
|
||||
#define DatumGetUriP(X) ((uritype *) PG_DETOAST_DATUM(X))
|
||||
#define DatumGetUriPP(X) ((uritype *) PG_DETOAST_DATUM_PACKED(X))
|
||||
#define UriPGetDatum(X) PointerGetDatum(X)
|
||||
|
||||
#define PG_GETARG_URI_P(n) DatumGetUriP(PG_GETARG_DATUM(n))
|
||||
#define PG_GETARG_URI_PP(n) DatumGetUriPP(PG_GETARG_DATUM(n))
|
||||
#define PG_RETURN_URI_P(x) PG_RETURN_POINTER(x)
|
||||
|
||||
|
||||
|
@ -436,3 +439,19 @@ uri_cmp(PG_FUNCTION_ARGS)
|
|||
|
||||
PG_RETURN_INT32(_uri_cmp(arg1, arg2));
|
||||
}
|
||||
|
||||
PG_FUNCTION_INFO_V1(uri_hash);
|
||||
Datum
|
||||
uri_hash(PG_FUNCTION_ARGS)
|
||||
{
|
||||
uritype *key = PG_GETARG_URI_PP(0);
|
||||
Datum result;
|
||||
|
||||
result = hash_any((unsigned char *) VARDATA_ANY(key),
|
||||
VARSIZE_ANY_EXHDR(key));
|
||||
|
||||
/* Avoid leaking memory for toasted inputs */
|
||||
PG_FREE_IF_COPY(key, 0);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
comment = 'uri type'
|
||||
default_version = 0
|
||||
default_version = 1
|
||||
module_pathname = '$libdir/uri'
|
||||
relocatable = true
|
||||
|
|
11
uri.sql
11
uri.sql
|
@ -130,6 +130,12 @@ CREATE FUNCTION uri_cmp(uri, uri) RETURNS integer
|
|||
LANGUAGE C
|
||||
AS '$libdir/uri';
|
||||
|
||||
CREATE FUNCTION uri_hash(uri) RETURNS integer
|
||||
IMMUTABLE
|
||||
STRICT
|
||||
LANGUAGE C
|
||||
AS '$libdir/uri';
|
||||
|
||||
CREATE OPERATOR < (
|
||||
LEFTARG = uri,
|
||||
RIGHTARG = uri,
|
||||
|
@ -200,3 +206,8 @@ CREATE OPERATOR CLASS uri_ops
|
|||
OPERATOR 4 >= ,
|
||||
OPERATOR 5 > ,
|
||||
FUNCTION 1 uri_cmp(uri, uri);
|
||||
|
||||
CREATE OPERATOR CLASS uri_ops_hash
|
||||
DEFAULT FOR TYPE uri USING hash AS
|
||||
OPERATOR 1 =,
|
||||
FUNCTION 1 uri_hash(uri);
|
||||
|
|
Loading…
Reference in New Issue