summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Baumann <abaumann@yahoo.com>2013-04-17 09:46:27 +0200
committerAndreas Baumann <abaumann@yahoo.com>2013-04-17 09:46:27 +0200
commit0ca43761e7ed260055c692d7f2cf804bcaa647b3 (patch)
tree2901eeebc3bb0af27209939451267ada7b60b4a0
parent80208e2c59fc426e2dc2ea4c9af2fa7f064a3331 (diff)
downloadpgfuse-0ca43761e7ed260055c692d7f2cf804bcaa647b3.tar.gz
pgfuse-0ca43761e7ed260055c692d7f2cf804bcaa647b3.tar.bz2
some code rearrangments around statfs functions
-rw-r--r--TODO29
-rw-r--r--pgfuse.c55
-rw-r--r--pgsql.c42
-rw-r--r--pgsql.h4
4 files changed, 59 insertions, 71 deletions
diff --git a/TODO b/TODO
index 8a38be1..bff7c24 100644
--- a/TODO
+++ b/TODO
@@ -2,35 +2,6 @@ TODO list (in order of priority)
---------
- integrate statfs patch:
-
-The real df -k:
-
-#include <mntent.h>
-#include <stdio.h>
-#include <sys/stat.h>
-#include <sys/types.h>
-#include <sys/vfs.h>
-#include <unistd.h>
-
-int main(void) {
- FILE* mtab = setmntent("/etc/mtab", "r");
- struct mntent* m;
- struct mntent mnt;
- char strings[4096];
- while ((m = getmntent_r(mtab, &mnt, strings, sizeof(strings)))) {
- struct statfs fs;
- if ((mnt.mnt_dir != NULL) && (statfs(mnt.mnt_dir, &fs) == 0)) {
- unsigned long long int size = fs.f_blocks * fs.f_bsize;
- unsigned long long int free = fs.f_bfree * fs.f_bsize;
- unsigned long long int avail = fs.f_bavail * fs.f_bsize;
- printf("%s %s size=%lld free=%lld avail=%lld\n",
- mnt.mnt_fsname, mnt.mnt_dir, size, free, avail);
- }
- }
-
- endmntent(mtab);
-}
-
- no Perl, Shell, Posix df dependency
- handling of most file system metadata
- ownership: how is this done depending on
diff --git a/pgfuse.c b/pgfuse.c
index e5e8f13..ac42615 100644
--- a/pgfuse.c
+++ b/pgfuse.c
@@ -28,6 +28,8 @@
#include <values.h> /* for INT_MAX */
#include <stdint.h> /* for uint64_t */
#include <inttypes.h> /* for PRIxxx macros */
+#include <mntent.h> /* for iterating mount entries */
+#include <sys/vfs.h> /* for statfs */
#include <fuse.h> /* for user-land filesystem */
#include <fuse_opt.h> /* fuse command line parser */
@@ -935,11 +937,13 @@ static int pgfuse_ftruncate( const char *path, off_t offset, struct fuse_file_in
static int pgfuse_statfs( const char *path, struct statvfs *buf )
{
PgFuseData *data = (PgFuseData *)fuse_get_context( )->private_data;
-
PGconn *conn;
-
int64_t blocks_total, blocks_used, blocks_free, blocks_avail;
int64_t files_total, files_used, files_free, files_avail;
+ int res;
+ int i;
+ size_t nof_locations = MAX_TABLESPACE_OIDS;
+ char *location[MAX_TABLESPACE_OIDS];
if( data->verbose ) {
syslog( LOG_INFO, "Statfs called on '%s', thread #%u",
@@ -952,17 +956,44 @@ static int pgfuse_statfs( const char *path, struct statvfs *buf )
PSQL_BEGIN( conn );
/* blocks */
+
+ res = psql_get_tablespace_locations( conn, location, &nof_locations, data->verbose );
+ if( res < 0 ) {
+ return res;
+ }
- blocks_free = psql_get_fs_blocks_free( conn, data->verbose );
- if( blocks_free < 0 ) {
- PSQL_ROLLBACK( conn ); RELEASE( conn );
- return -blocks_free;
+ /* iterate over mount entries and try to match to the tablespace locations */
+
+/*
+int main(void) {
+ FILE* mtab = setmntent("/etc/mtab", "r");
+ struct mntent* m;
+ struct mntent mnt;
+ char strings[4096];
+ while ((m = getmntent_r(mtab, &mnt, strings, sizeof(strings)))) {
+ struct statfs fs;
+ if ((mnt.mnt_dir != NULL) && (statfs(mnt.mnt_dir, &fs) == 0)) {
+ unsigned long long int size = fs.f_blocks * fs.f_bsize;
+ unsigned long long int free = fs.f_bfree * fs.f_bsize;
+ unsigned long long int avail = fs.f_bavail * fs.f_bsize;
+ printf("%s %s size=%lld free=%lld avail=%lld\n",
+ mnt.mnt_fsname, mnt.mnt_dir, size, free, avail);
+ }
+ }
+
+ endmntent(mtab);
+}
+*/
+ for( i = 0; i < nof_locations; i++ ) {
+ if( location[i] ) free( location[i] );
}
+
+ blocks_free = 9999;
blocks_used = psql_get_fs_blocks_used( conn );
if( blocks_used < 0 ) {
PSQL_ROLLBACK( conn ); RELEASE( conn );
- return -blocks_used;
+ return blocks_used;
}
blocks_total = blocks_free + blocks_used;
@@ -970,16 +1001,14 @@ static int pgfuse_statfs( const char *path, struct statvfs *buf )
/* inodes */
- files_free = psql_get_fs_files_free( conn );
- if( files_free < 0 ) {
- PSQL_ROLLBACK( conn ); RELEASE( conn );
- return -files_free;
- }
+ /* no restriction on the number of files storable, we could
+ add some limits later */
+ files_free = INT64_MAX;
files_used = psql_get_fs_files_used( conn );
if( files_used < 0 ) {
PSQL_ROLLBACK( conn ); RELEASE( conn );
- return -files_used;
+ return files_used;
}
files_total = files_free + files_used;
diff --git a/pgsql.c b/pgsql.c
index 8750054..4a2e776 100644
--- a/pgsql.c
+++ b/pgsql.c
@@ -1016,14 +1016,17 @@ static char *get_tablespace_location( PGconn *conn, const int oid, int verbose )
return data;
}
-int64_t psql_get_fs_blocks_free( PGconn *conn, int verbose )
+int psql_get_tablespace_locations( PGconn *conn, char **location, size_t *nof_oids, int verbose )
{
PGresult *res;
char *data;
int i;
- int nof_oids;
int oid[MAX_TABLESPACE_OIDS];
- char *location[MAX_TABLESPACE_OIDS];
+
+ if( *nof_oids > MAX_TABLESPACE_OIDS ) {
+ syslog( LOG_ERR, "Error in psql_get_fs_blocks_free, called with location array bigger than MAX_TABLESPACE_OIDS");
+ return -EIO;
+ }
/* Get a list of oids containing the tablespaces of PgFuse tables and indexes */
res = PQexec( conn, "select distinct reltablespace::int4 FROM pg_class WHERE relname in ( 'dir', 'data', 'data_dir_id_idx', 'data_block_no_idx', 'dir_parent_id_idx' )" );
@@ -1041,14 +1044,14 @@ int64_t psql_get_fs_blocks_free( PGconn *conn, int verbose )
return -EIO;
}
- nof_oids = PQntuples( res ) ;
- if( nof_oids > MAX_TABLESPACE_OIDS ) {
+ *nof_oids = PQntuples( res ) ;
+ if( *nof_oids > MAX_TABLESPACE_OIDS ) {
syslog( LOG_ERR, "Error in psql_get_fs_blocks_free, too many tablespace OIDs found, increase MAX_TABLESPACE_OIDS");
PQclear( res );
return -EIO;
}
- for( i = 0; i < nof_oids; i++ ) {
+ for( i = 0; i < *nof_oids; i++ ) {
data = PQgetvalue( res, i, 0 );
oid[i] = atoi( data );
}
@@ -1058,7 +1061,7 @@ int64_t psql_get_fs_blocks_free( PGconn *conn, int verbose )
/* we have a OID = 0 in the list, so have a look at the default
* tablespace of the current database and replace the value
*/
- for( i = 0; i < nof_oids; i++ ) {
+ for( i = 0; i < *nof_oids; i++ ) {
if( oid[i] == 0 ) {
int res = get_default_tablespace( conn, verbose );
if( res < 0 ) {
@@ -1071,28 +1074,25 @@ int64_t psql_get_fs_blocks_free( PGconn *conn, int verbose )
/* Get table space locations, since 9.2 there is a function for
* this, before we must hunt system tables for the information
*/
- for( i = 0; i < nof_oids; i++ ) {
+ for( i = 0; i < *nof_oids; i++ ) {
location[i] = get_tablespace_location( conn, oid[i], verbose );
}
-
- for( i = 0; i < nof_oids; i++ ) {
+
+ /* TODO: */
+ for( i = 0; i < *nof_oids; i++ ) {
if( !location[i] ) {
/* No location, tablespace resides in PGDATA */
}
}
- for( i = 0; i < nof_oids; i++ ) {
+ for( i = 0; i < *nof_oids; i++ ) {
if( verbose ) {
syslog( LOG_DEBUG, "Free blocks calculation, seen tablespace OID %d, %s",
oid[i], location[i] );
}
}
-
- for( i = 0; i < nof_oids; i++ ) {
- if( location[i] ) free( location[i] );
- }
- return 9999;
+ return 0;
}
int64_t psql_get_fs_files_used( PGconn *conn )
@@ -1115,13 +1115,3 @@ int64_t psql_get_fs_files_used( PGconn *conn )
return used;
}
-
-int64_t psql_get_fs_files_free( PGconn *conn )
-{
- /* no restriction on the number of files storable, we could
- * add some limits later, so we would calculate the difference
- * here and not in pgfuse.c.
- */
- return INT64_MAX;
-}
-
diff --git a/pgsql.h b/pgsql.h
index 4cdef32..abb58ec 100644
--- a/pgsql.h
+++ b/pgsql.h
@@ -100,10 +100,8 @@ size_t psql_get_block_size( PGconn *conn, const size_t block_size );
int64_t psql_get_fs_blocks_used( PGconn *conn );
-int64_t psql_get_fs_blocks_free( PGconn *conn, int verbose );
+int psql_get_tablespace_locations( PGconn *conn, char **location, size_t *nof_oids, int verbose );
int64_t psql_get_fs_files_used( PGconn *conn );
-int64_t psql_get_fs_files_free( PGconn *conn );
-
#endif