Un-Windows-ify newlines.

This commit is contained in:
Tom Lane 2005-08-02 14:07:27 +00:00
parent 2a4fad1a0e
commit 35c4764f88
1 changed files with 461 additions and 461 deletions

View File

@ -1,461 +1,461 @@
/* /*
* dbsize.c * dbsize.c
* object size functions * object size functions
* *
* Copyright (c) 2002-2005, PostgreSQL Global Development Group * Copyright (c) 2002-2005, PostgreSQL Global Development Group
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/utils/adt/dbsize.c,v 1.1 2005/07/29 14:46:57 momjian Exp $ * $PostgreSQL: pgsql/src/backend/utils/adt/dbsize.c,v 1.2 2005/08/02 14:07:27 tgl Exp $
* *
*/ */
#include "postgres.h" #include "postgres.h"
#include <sys/types.h> #include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/namespace.h" #include "catalog/namespace.h"
#include "catalog/pg_tablespace.h" #include "catalog/pg_tablespace.h"
#include "commands/dbcommands.h" #include "commands/dbcommands.h"
#include "commands/tablespace.h" #include "commands/tablespace.h"
#include "miscadmin.h" #include "miscadmin.h"
#include "storage/fd.h" #include "storage/fd.h"
#include "utils/builtins.h" #include "utils/builtins.h"
#include "utils/syscache.h" #include "utils/syscache.h"
#include "utils/relcache.h" #include "utils/relcache.h"
/* Return physical size of directory contents, or 0 if dir doesn't exist */ /* Return physical size of directory contents, or 0 if dir doesn't exist */
static int64 static int64
db_dir_size(const char *path) db_dir_size(const char *path)
{ {
int64 dirsize = 0; int64 dirsize = 0;
struct dirent *direntry; struct dirent *direntry;
DIR *dirdesc; DIR *dirdesc;
char filename[MAXPGPATH]; char filename[MAXPGPATH];
dirdesc = AllocateDir(path); dirdesc = AllocateDir(path);
if (!dirdesc) if (!dirdesc)
return 0; return 0;
while ((direntry = readdir(dirdesc)) != NULL) while ((direntry = readdir(dirdesc)) != NULL)
{ {
struct stat fst; struct stat fst;
if (strcmp(direntry->d_name, ".") == 0 || if (strcmp(direntry->d_name, ".") == 0 ||
strcmp(direntry->d_name, "..") == 0) strcmp(direntry->d_name, "..") == 0)
continue; continue;
snprintf(filename, MAXPGPATH, "%s/%s", path, direntry->d_name); snprintf(filename, MAXPGPATH, "%s/%s", path, direntry->d_name);
if (stat(filename, &fst) < 0) if (stat(filename, &fst) < 0)
ereport(ERROR, ereport(ERROR,
(errcode_for_file_access(), (errcode_for_file_access(),
errmsg("could not stat \"%s\": %m", filename))); errmsg("could not stat \"%s\": %m", filename)));
dirsize += fst.st_size; dirsize += fst.st_size;
} }
FreeDir(dirdesc); FreeDir(dirdesc);
return dirsize; return dirsize;
} }
/* /*
* calculate size of database in all tablespaces * calculate size of database in all tablespaces
*/ */
static int64 static int64
calculate_database_size(Oid dbOid) calculate_database_size(Oid dbOid)
{ {
int64 totalsize = 0; int64 totalsize = 0;
DIR *dirdesc; DIR *dirdesc;
struct dirent *direntry; struct dirent *direntry;
char pathname[MAXPGPATH]; char pathname[MAXPGPATH];
/* Shared storage in pg_global is not counted */ /* Shared storage in pg_global is not counted */
/* Include pg_default storage */ /* Include pg_default storage */
snprintf(pathname, MAXPGPATH, "%s/base/%u", DataDir, dbOid); snprintf(pathname, MAXPGPATH, "%s/base/%u", DataDir, dbOid);
totalsize += db_dir_size(pathname); totalsize += db_dir_size(pathname);
/* Scan the non-default tablespaces */ /* Scan the non-default tablespaces */
snprintf(pathname, MAXPGPATH, "%s/pg_tblspc", DataDir); snprintf(pathname, MAXPGPATH, "%s/pg_tblspc", DataDir);
dirdesc = AllocateDir(pathname); dirdesc = AllocateDir(pathname);
if (!dirdesc) if (!dirdesc)
ereport(ERROR, ereport(ERROR,
(errcode_for_file_access(), (errcode_for_file_access(),
errmsg("could not open tablespace directory \"%s\": %m", errmsg("could not open tablespace directory \"%s\": %m",
pathname))); pathname)));
while ((direntry = readdir(dirdesc)) != NULL) while ((direntry = readdir(dirdesc)) != NULL)
{ {
if (strcmp(direntry->d_name, ".") == 0 || if (strcmp(direntry->d_name, ".") == 0 ||
strcmp(direntry->d_name, "..") == 0) strcmp(direntry->d_name, "..") == 0)
continue; continue;
snprintf(pathname, MAXPGPATH, "%s/pg_tblspc/%s/%u", snprintf(pathname, MAXPGPATH, "%s/pg_tblspc/%s/%u",
DataDir, direntry->d_name, dbOid); DataDir, direntry->d_name, dbOid);
totalsize += db_dir_size(pathname); totalsize += db_dir_size(pathname);
} }
FreeDir(dirdesc); FreeDir(dirdesc);
/* Complain if we found no trace of the DB at all */ /* Complain if we found no trace of the DB at all */
if (!totalsize) if (!totalsize)
ereport(ERROR, ereport(ERROR,
(ERRCODE_UNDEFINED_DATABASE, (ERRCODE_UNDEFINED_DATABASE,
errmsg("database with OID %u does not exist", dbOid))); errmsg("database with OID %u does not exist", dbOid)));
return totalsize; return totalsize;
} }
Datum Datum
pg_database_size_oid(PG_FUNCTION_ARGS) pg_database_size_oid(PG_FUNCTION_ARGS)
{ {
Oid dbOid = PG_GETARG_OID(0); Oid dbOid = PG_GETARG_OID(0);
PG_RETURN_INT64(calculate_database_size(dbOid)); PG_RETURN_INT64(calculate_database_size(dbOid));
} }
Datum Datum
pg_database_size_name(PG_FUNCTION_ARGS) pg_database_size_name(PG_FUNCTION_ARGS)
{ {
Name dbName = PG_GETARG_NAME(0); Name dbName = PG_GETARG_NAME(0);
Oid dbOid = get_database_oid(NameStr(*dbName)); Oid dbOid = get_database_oid(NameStr(*dbName));
if (!OidIsValid(dbOid)) if (!OidIsValid(dbOid))
ereport(ERROR, ereport(ERROR,
(errcode(ERRCODE_UNDEFINED_DATABASE), (errcode(ERRCODE_UNDEFINED_DATABASE),
errmsg("database \"%s\" does not exist", errmsg("database \"%s\" does not exist",
NameStr(*dbName)))); NameStr(*dbName))));
PG_RETURN_INT64(calculate_database_size(dbOid)); PG_RETURN_INT64(calculate_database_size(dbOid));
} }
/* /*
* calculate total size of tablespace * calculate total size of tablespace
*/ */
static int64 static int64
calculate_tablespace_size(Oid tblspcOid) calculate_tablespace_size(Oid tblspcOid)
{ {
char tblspcPath[MAXPGPATH]; char tblspcPath[MAXPGPATH];
char pathname[MAXPGPATH]; char pathname[MAXPGPATH];
int64 totalsize=0; int64 totalsize=0;
DIR *dirdesc; DIR *dirdesc;
struct dirent *direntry; struct dirent *direntry;
if (tblspcOid == DEFAULTTABLESPACE_OID) if (tblspcOid == DEFAULTTABLESPACE_OID)
snprintf(tblspcPath, MAXPGPATH, "%s/base", DataDir); snprintf(tblspcPath, MAXPGPATH, "%s/base", DataDir);
else if (tblspcOid == GLOBALTABLESPACE_OID) else if (tblspcOid == GLOBALTABLESPACE_OID)
snprintf(tblspcPath, MAXPGPATH, "%s/global", DataDir); snprintf(tblspcPath, MAXPGPATH, "%s/global", DataDir);
else else
snprintf(tblspcPath, MAXPGPATH, "%s/pg_tblspc/%u", DataDir, tblspcOid); snprintf(tblspcPath, MAXPGPATH, "%s/pg_tblspc/%u", DataDir, tblspcOid);
dirdesc = AllocateDir(tblspcPath); dirdesc = AllocateDir(tblspcPath);
if (!dirdesc) if (!dirdesc)
ereport(ERROR, ereport(ERROR,
(errcode_for_file_access(), (errcode_for_file_access(),
errmsg("could not open tablespace directory \"%s\": %m", errmsg("could not open tablespace directory \"%s\": %m",
tblspcPath))); tblspcPath)));
while ((direntry = readdir(dirdesc)) != NULL) while ((direntry = readdir(dirdesc)) != NULL)
{ {
struct stat fst; struct stat fst;
if (strcmp(direntry->d_name, ".") == 0 || if (strcmp(direntry->d_name, ".") == 0 ||
strcmp(direntry->d_name, "..") == 0) strcmp(direntry->d_name, "..") == 0)
continue; continue;
snprintf(pathname, MAXPGPATH, "%s/%s", tblspcPath, direntry->d_name); snprintf(pathname, MAXPGPATH, "%s/%s", tblspcPath, direntry->d_name);
if (stat(pathname, &fst) < 0) if (stat(pathname, &fst) < 0)
ereport(ERROR, ereport(ERROR,
(errcode_for_file_access(), (errcode_for_file_access(),
errmsg("could not stat \"%s\": %m", pathname))); errmsg("could not stat \"%s\": %m", pathname)));
if (fst.st_mode & S_IFDIR) if (fst.st_mode & S_IFDIR)
totalsize += db_dir_size(pathname); totalsize += db_dir_size(pathname);
totalsize += fst.st_size; totalsize += fst.st_size;
} }
FreeDir(dirdesc); FreeDir(dirdesc);
return totalsize; return totalsize;
} }
Datum Datum
pg_tablespace_size_oid(PG_FUNCTION_ARGS) pg_tablespace_size_oid(PG_FUNCTION_ARGS)
{ {
Oid tblspcOid = PG_GETARG_OID(0); Oid tblspcOid = PG_GETARG_OID(0);
PG_RETURN_INT64(calculate_tablespace_size(tblspcOid)); PG_RETURN_INT64(calculate_tablespace_size(tblspcOid));
} }
Datum Datum
pg_tablespace_size_name(PG_FUNCTION_ARGS) pg_tablespace_size_name(PG_FUNCTION_ARGS)
{ {
Name tblspcName = PG_GETARG_NAME(0); Name tblspcName = PG_GETARG_NAME(0);
Oid tblspcOid = get_tablespace_oid(NameStr(*tblspcName)); Oid tblspcOid = get_tablespace_oid(NameStr(*tblspcName));
if (!OidIsValid(tblspcOid)) if (!OidIsValid(tblspcOid))
ereport(ERROR, ereport(ERROR,
(errcode(ERRCODE_UNDEFINED_OBJECT), (errcode(ERRCODE_UNDEFINED_OBJECT),
errmsg("tablespace \"%s\" does not exist", errmsg("tablespace \"%s\" does not exist",
NameStr(*tblspcName)))); NameStr(*tblspcName))));
PG_RETURN_INT64(calculate_tablespace_size(tblspcOid)); PG_RETURN_INT64(calculate_tablespace_size(tblspcOid));
} }
/* /*
* calculate size of a relation * calculate size of a relation
*/ */
static int64 static int64
calculate_relation_size(Oid tblspcOid, Oid relnodeOid) calculate_relation_size(Oid tblspcOid, Oid relnodeOid)
{ {
int64 totalsize=0; int64 totalsize=0;
unsigned int segcount=0; unsigned int segcount=0;
char dirpath[MAXPGPATH]; char dirpath[MAXPGPATH];
char pathname[MAXPGPATH]; char pathname[MAXPGPATH];
if (!tblspcOid) if (!tblspcOid)
tblspcOid = MyDatabaseTableSpace; tblspcOid = MyDatabaseTableSpace;
if (tblspcOid == DEFAULTTABLESPACE_OID) if (tblspcOid == DEFAULTTABLESPACE_OID)
snprintf(dirpath, MAXPGPATH, "%s/base/%u", DataDir, MyDatabaseId); snprintf(dirpath, MAXPGPATH, "%s/base/%u", DataDir, MyDatabaseId);
else if (tblspcOid == GLOBALTABLESPACE_OID) else if (tblspcOid == GLOBALTABLESPACE_OID)
snprintf(dirpath, MAXPGPATH, "%s/global", DataDir); snprintf(dirpath, MAXPGPATH, "%s/global", DataDir);
else else
snprintf(dirpath, MAXPGPATH, "%s/pg_tblspc/%u/%u", snprintf(dirpath, MAXPGPATH, "%s/pg_tblspc/%u/%u",
DataDir, tblspcOid, MyDatabaseId); DataDir, tblspcOid, MyDatabaseId);
for (segcount = 0 ;; segcount++) for (segcount = 0 ;; segcount++)
{ {
struct stat fst; struct stat fst;
if (segcount == 0) if (segcount == 0)
snprintf(pathname, MAXPGPATH, "%s/%u", snprintf(pathname, MAXPGPATH, "%s/%u",
dirpath, relnodeOid); dirpath, relnodeOid);
else else
snprintf(pathname, MAXPGPATH, "%s/%u.%u", snprintf(pathname, MAXPGPATH, "%s/%u.%u",
dirpath, relnodeOid, segcount); dirpath, relnodeOid, segcount);
if (stat(pathname, &fst) < 0) if (stat(pathname, &fst) < 0)
{ {
if (errno == ENOENT) if (errno == ENOENT)
break; break;
else else
ereport(ERROR, ereport(ERROR,
(errcode_for_file_access(), (errcode_for_file_access(),
errmsg("could not stat \"%s\": %m", pathname))); errmsg("could not stat \"%s\": %m", pathname)));
} }
totalsize += fst.st_size; totalsize += fst.st_size;
} }
return totalsize; return totalsize;
} }
Datum Datum
pg_relation_size_oid(PG_FUNCTION_ARGS) pg_relation_size_oid(PG_FUNCTION_ARGS)
{ {
Oid relOid=PG_GETARG_OID(0); Oid relOid=PG_GETARG_OID(0);
HeapTuple tuple; HeapTuple tuple;
Form_pg_class pg_class; Form_pg_class pg_class;
Oid relnodeOid; Oid relnodeOid;
Oid tblspcOid; Oid tblspcOid;
tuple = SearchSysCache(RELOID, tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(relOid), ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
ereport(ERROR, ereport(ERROR,
(ERRCODE_UNDEFINED_TABLE, (ERRCODE_UNDEFINED_TABLE,
errmsg("relation with OID %u does not exist", relOid))); errmsg("relation with OID %u does not exist", relOid)));
pg_class = (Form_pg_class) GETSTRUCT(tuple); pg_class = (Form_pg_class) GETSTRUCT(tuple);
relnodeOid = pg_class->relfilenode; relnodeOid = pg_class->relfilenode;
tblspcOid = pg_class->reltablespace; tblspcOid = pg_class->reltablespace;
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
PG_RETURN_INT64(calculate_relation_size(tblspcOid, relnodeOid)); PG_RETURN_INT64(calculate_relation_size(tblspcOid, relnodeOid));
} }
Datum Datum
pg_relation_size_name(PG_FUNCTION_ARGS) pg_relation_size_name(PG_FUNCTION_ARGS)
{ {
text *relname = PG_GETARG_TEXT_P(0); text *relname = PG_GETARG_TEXT_P(0);
RangeVar *relrv; RangeVar *relrv;
Relation relation; Relation relation;
Oid relnodeOid; Oid relnodeOid;
Oid tblspcOid; Oid tblspcOid;
relrv = makeRangeVarFromNameList(textToQualifiedNameList(relname)); relrv = makeRangeVarFromNameList(textToQualifiedNameList(relname));
relation = relation_openrv(relrv, AccessShareLock); relation = relation_openrv(relrv, AccessShareLock);
tblspcOid = relation->rd_rel->reltablespace; tblspcOid = relation->rd_rel->reltablespace;
relnodeOid = relation->rd_rel->relfilenode; relnodeOid = relation->rd_rel->relfilenode;
relation_close(relation, AccessShareLock); relation_close(relation, AccessShareLock);
PG_RETURN_INT64(calculate_relation_size(tblspcOid, relnodeOid)); PG_RETURN_INT64(calculate_relation_size(tblspcOid, relnodeOid));
} }
/* /*
* Compute on-disk size of files for 'relation' according to the stat function, * Compute on-disk size of files for 'relation' according to the stat function,
* optionally including heap data, index data, and/or toast data. * optionally including heap data, index data, and/or toast data.
*/ */
static int64 static int64
calculate_complete_relation_size(Oid tblspcOid, Oid relnodeOid) calculate_complete_relation_size(Oid tblspcOid, Oid relnodeOid)
{ {
Relation heapRelation; Relation heapRelation;
Relation idxRelation; Relation idxRelation;
Relation toastRelation; Relation toastRelation;
Oid idxOid; Oid idxOid;
Oid idxTblspcOid; Oid idxTblspcOid;
Oid toastOid; Oid toastOid;
Oid toastTblspcOid; Oid toastTblspcOid;
bool hasIndices; bool hasIndices;
int64 size = 0; int64 size = 0;
List *indexoidlist; List *indexoidlist;
ListCell *idx; ListCell *idx;
heapRelation = relation_open(relnodeOid, AccessShareLock); heapRelation = relation_open(relnodeOid, AccessShareLock);
toastOid = heapRelation->rd_rel->reltoastrelid; toastOid = heapRelation->rd_rel->reltoastrelid;
hasIndices = heapRelation->rd_rel->relhasindex; hasIndices = heapRelation->rd_rel->relhasindex;
/* Get the heap size */ /* Get the heap size */
size += calculate_relation_size(tblspcOid, relnodeOid); size += calculate_relation_size(tblspcOid, relnodeOid);
/* Get Index size */ /* Get Index size */
if ( hasIndices ) { if ( hasIndices ) {
/* recursively include any dependent indexes ... */ /* recursively include any dependent indexes ... */
indexoidlist = RelationGetIndexList(heapRelation); indexoidlist = RelationGetIndexList(heapRelation);
foreach(idx, indexoidlist) { foreach(idx, indexoidlist) {
idxOid = lfirst_oid(idx); idxOid = lfirst_oid(idx);
idxRelation = relation_open(idxOid, AccessShareLock); idxRelation = relation_open(idxOid, AccessShareLock);
idxTblspcOid = idxRelation->rd_rel->reltablespace; idxTblspcOid = idxRelation->rd_rel->reltablespace;
size += calculate_relation_size(idxTblspcOid, idxOid); size += calculate_relation_size(idxTblspcOid, idxOid);
relation_close(idxRelation, AccessShareLock); relation_close(idxRelation, AccessShareLock);
} }
list_free(indexoidlist); list_free(indexoidlist);
} }
/* Close heapReleation now we no longer need it */ /* Close heapReleation now we no longer need it */
relation_close(heapRelation, AccessShareLock); relation_close(heapRelation, AccessShareLock);
/* Get toast table size */ /* Get toast table size */
if ( toastOid != 0 ) { if ( toastOid != 0 ) {
/* recursively include any toast relations ... */ /* recursively include any toast relations ... */
toastRelation = relation_open(toastOid, AccessShareLock); toastRelation = relation_open(toastOid, AccessShareLock);
toastTblspcOid = toastRelation->rd_rel->reltablespace; toastTblspcOid = toastRelation->rd_rel->reltablespace;
size += calculate_relation_size(toastTblspcOid, toastOid); size += calculate_relation_size(toastTblspcOid, toastOid);
relation_close(toastRelation, AccessShareLock); relation_close(toastRelation, AccessShareLock);
} }
return size; return size;
} }
/* /*
* Compute on-disk size of files for 'relation' including * Compute on-disk size of files for 'relation' including
* heap data, index data, and toasted data. * heap data, index data, and toasted data.
*/ */
Datum Datum
pg_complete_relation_size_oid(PG_FUNCTION_ARGS) pg_complete_relation_size_oid(PG_FUNCTION_ARGS)
{ {
Oid relOid=PG_GETARG_OID(0); Oid relOid=PG_GETARG_OID(0);
HeapTuple tuple; HeapTuple tuple;
Form_pg_class pg_class; Form_pg_class pg_class;
Oid relnodeOid; Oid relnodeOid;
Oid tblspcOid; Oid tblspcOid;
tuple = SearchSysCache(RELOID, tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(relOid), ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
ereport(ERROR, ereport(ERROR,
(ERRCODE_UNDEFINED_TABLE, (ERRCODE_UNDEFINED_TABLE,
errmsg("relation with OID %u does not exist", relOid))); errmsg("relation with OID %u does not exist", relOid)));
pg_class = (Form_pg_class) GETSTRUCT(tuple); pg_class = (Form_pg_class) GETSTRUCT(tuple);
relnodeOid = pg_class->relfilenode; relnodeOid = pg_class->relfilenode;
tblspcOid = pg_class->reltablespace; tblspcOid = pg_class->reltablespace;
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
PG_RETURN_INT64(calculate_complete_relation_size(tblspcOid, relnodeOid)); PG_RETURN_INT64(calculate_complete_relation_size(tblspcOid, relnodeOid));
} }
Datum Datum
pg_complete_relation_size_name(PG_FUNCTION_ARGS) pg_complete_relation_size_name(PG_FUNCTION_ARGS)
{ {
text *relname = PG_GETARG_TEXT_P(0); text *relname = PG_GETARG_TEXT_P(0);
RangeVar *relrv; RangeVar *relrv;
Relation relation; Relation relation;
Oid relnodeOid; Oid relnodeOid;
Oid tblspcOid; Oid tblspcOid;
relrv = makeRangeVarFromNameList(textToQualifiedNameList(relname)); relrv = makeRangeVarFromNameList(textToQualifiedNameList(relname));
relation = relation_openrv(relrv, AccessShareLock); relation = relation_openrv(relrv, AccessShareLock);
tblspcOid = relation->rd_rel->reltablespace; tblspcOid = relation->rd_rel->reltablespace;
relnodeOid = relation->rd_rel->relfilenode; relnodeOid = relation->rd_rel->relfilenode;
relation_close(relation, AccessShareLock); relation_close(relation, AccessShareLock);
PG_RETURN_INT64(calculate_complete_relation_size(tblspcOid, relnodeOid)); PG_RETURN_INT64(calculate_complete_relation_size(tblspcOid, relnodeOid));
} }
/* /*
* formatting with size units * formatting with size units
*/ */
Datum Datum
pg_size_pretty(PG_FUNCTION_ARGS) pg_size_pretty(PG_FUNCTION_ARGS)
{ {
int64 size=PG_GETARG_INT64(0); int64 size=PG_GETARG_INT64(0);
char *result=palloc(50+VARHDRSZ); char *result=palloc(50+VARHDRSZ);
int64 limit = 10*1024; int64 limit = 10*1024;
int64 mult=1; int64 mult=1;
if (size < limit*mult) if (size < limit*mult)
snprintf(VARDATA(result), 50, INT64_FORMAT" bytes", snprintf(VARDATA(result), 50, INT64_FORMAT" bytes",
size); size);
else else
{ {
mult *= 1024; mult *= 1024;
if (size < limit*mult) if (size < limit*mult)
snprintf(VARDATA(result), 50, INT64_FORMAT " kB", snprintf(VARDATA(result), 50, INT64_FORMAT " kB",
(size+mult/2) / mult); (size+mult/2) / mult);
else else
{ {
mult *= 1024; mult *= 1024;
if (size < limit*mult) if (size < limit*mult)
snprintf(VARDATA(result), 50, INT64_FORMAT " MB", snprintf(VARDATA(result), 50, INT64_FORMAT " MB",
(size+mult/2) / mult); (size+mult/2) / mult);
else else
{ {
mult *= 1024; mult *= 1024;
if (size < limit*mult) if (size < limit*mult)
snprintf(VARDATA(result), 50, INT64_FORMAT " GB", snprintf(VARDATA(result), 50, INT64_FORMAT " GB",
(size+mult/2) / mult); (size+mult/2) / mult);
else else
{ {
mult *= 1024; mult *= 1024;
snprintf(VARDATA(result), 50, INT64_FORMAT " TB", snprintf(VARDATA(result), 50, INT64_FORMAT " TB",
(size+mult/2) / mult); (size+mult/2) / mult);
} }
} }
} }
} }
VARATT_SIZEP(result) = strlen(VARDATA(result)) + VARHDRSZ; VARATT_SIZEP(result) = strlen(VARDATA(result)) + VARHDRSZ;
PG_RETURN_TEXT_P(result); PG_RETURN_TEXT_P(result);
} }