Helle,

I've added visibility map information to pg_freespace for my
utility.

This looks like this,

postgres=# select * from pg_freespace('t'::regclass);
 blkno | avail | all_visible 
-------+-------+-------------
     0 |  7424 | t
     1 |  7424 | t
     2 |  7424 | t
     3 |  7424 | t
     4 |  7424 | t
     5 |  7424 | t
     6 |  7424 | t
     7 |  7424 | t
...

What do you think about this?


regards,

-- 
Kyotaro Horiguchi
NTT Open Source Software Center
diff --git a/contrib/pg_freespacemap/pg_freespacemap--1.0.sql b/contrib/pg_freespacemap/pg_freespacemap--1.0.sql
index 2adb52a..e38b466 100644
--- a/contrib/pg_freespacemap/pg_freespacemap--1.0.sql
+++ b/contrib/pg_freespacemap/pg_freespacemap--1.0.sql
@@ -9,12 +9,17 @@ RETURNS int2
 AS 'MODULE_PATHNAME', 'pg_freespace'
 LANGUAGE C STRICT;
 
+CREATE FUNCTION pg_is_all_visible(regclass, bigint)
+RETURNS bool
+AS 'MODULE_PATHNAME', 'pg_is_all_visible'
+LANGUAGE C STRICT;
+
 -- pg_freespace shows the recorded space avail at each block in a relation
 CREATE FUNCTION
-  pg_freespace(rel regclass, blkno OUT bigint, avail OUT int2)
+  pg_freespace(rel regclass, blkno OUT bigint, avail OUT int2, all_visible OUT bool)
 RETURNS SETOF RECORD
 AS $$
-  SELECT blkno, pg_freespace($1, blkno) AS avail
+  SELECT blkno, pg_freespace($1, blkno) AS avail, pg_is_all_visible($1, blkno) AS all_visible
   FROM generate_series(0, pg_relation_size($1) / current_setting('block_size')::bigint - 1) AS blkno;
 $$
 LANGUAGE SQL;
diff --git a/contrib/pg_freespacemap/pg_freespacemap.c b/contrib/pg_freespacemap/pg_freespacemap.c
index f6f7d2e..de4eff7 100644
--- a/contrib/pg_freespacemap/pg_freespacemap.c
+++ b/contrib/pg_freespacemap/pg_freespacemap.c
@@ -10,17 +10,20 @@
 
 #include "funcapi.h"
 #include "storage/freespace.h"
+#include "access/visibilitymap.h"
 
 
 PG_MODULE_MAGIC;
 
 Datum		pg_freespace(PG_FUNCTION_ARGS);
+Datum		pg_is_all_visible(PG_FUNCTION_ARGS);
 
 /*
  * Returns the amount of free space on a given page, according to the
  * free space map.
  */
 PG_FUNCTION_INFO_V1(pg_freespace);
+PG_FUNCTION_INFO_V1(pg_is_all_visible);
 
 Datum
 pg_freespace(PG_FUNCTION_ARGS)
@@ -38,7 +41,32 @@ pg_freespace(PG_FUNCTION_ARGS)
 				 errmsg("invalid block number")));
 
 	freespace = GetRecordedFreeSpace(rel, blkno);
-
 	relation_close(rel, AccessShareLock);
 	PG_RETURN_INT16(freespace);
 }
+
+Datum
+pg_is_all_visible(PG_FUNCTION_ARGS)
+{
+	Oid			relid = PG_GETARG_OID(0);
+	int64		blkno = PG_GETARG_INT64(1);
+	Buffer      vmbuffer = InvalidBuffer;
+	int			all_visible;
+	Relation	rel;
+
+	rel = relation_open(relid, AccessShareLock);
+
+	if (blkno < 0 || blkno > MaxBlockNumber)
+		ereport(ERROR,
+				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+				 errmsg("invalid block number")));
+
+	all_visible = visibilitymap_test(rel, blkno, &vmbuffer);
+	if (vmbuffer != InvalidBuffer)
+	{
+		ReleaseBuffer(vmbuffer);
+		vmbuffer = InvalidBuffer;
+	}
+	relation_close(rel, AccessShareLock);
+	PG_RETURN_BOOL(all_visible);
+}
diff --git a/contrib/pg_freespacemap/pg_freespacemap.control b/contrib/pg_freespacemap/pg_freespacemap.control
index 34b695f..395350a 100644
--- a/contrib/pg_freespacemap/pg_freespacemap.control
+++ b/contrib/pg_freespacemap/pg_freespacemap.control
@@ -1,5 +1,5 @@
 # pg_freespacemap extension
-comment = 'examine the free space map (FSM)'
+comment = 'examine the free space map (FSM) and visibility map (VM)'
 default_version = '1.0'
 module_pathname = '$libdir/pg_freespacemap'
 relocatable = true
-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

Reply via email to