/*
 *	Copyright 1994 Matti Aarnio
 *	This is part of the ZMailer (2.99+), and available with
 *	the rules of the main program itself
 */

#include "hostenv.h"
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/file.h>
#include <sys/param.h>


#ifdef	HAVE_STATVFS
# include <sys/statvfs.h>
# define FSTATFS fstatvfs
#else	/* !HAVE_STATVFS */
#if defined(SYSV) || defined(RISC6000)
# include <sys/statfs.h>
# define FSTATFS fstatfs /* Existence of this means (usually) SYSV code */
#else /* Hmm.. Assuming it appears on all NON-SysV systems.. */
#ifdef ULTRIX
	/* From: James S MacKinnon <jmack@Phys.UAlberta.Ca> */
# include <sys/mount.h>
# include <netinet/in.h>
# include <nfs/nfs_clnt.h>
# include <nfs/vfs.h>
# define FSTATFS statfs	/* Existence of this means (usually) SYSV code */
#else /* !ULTRIX */
#ifdef BSD4_4
# include <sys/mount.h>
/* # define FSTATFS fstatfs */ /* nonexistence of this means BSD code */
#else /* !BSD4_4 */
# include <sys/vfs.h>
/* # define FSTATFS fstatfs */ /* nonexistence of this means BSD code */
#endif /* !BSD4_4 */
#endif /* !ULTRIX */
#endif /* !SYSV */
#endif /* !HAVE_STATVFS */

long fd_statfs(fd)
int fd;
{
	long availspace = 0;
	int rc;

	/* Query the available space on the filesystem where the
	   currently open (int fd) file is located.  This call
	   should be available on all systems, and given valid
	   parametrization, never fail... */

#ifdef HAVE_STATVFS
	struct statvfs statbuf;	/* SysV and BSD definitions differ..	*/
	if ((rc = fstatvfs(fd, &statbuf)) == 0) {
	  availspace = statbuf.f_bavail * statbuf.f_frsize;
	}
#else
#if defined(__linux__) || (defined(BSD4_4) && !defined(bsdi)) || \
    defined(ULTRIX) || defined(RISC6000)
	struct statfs statbuf;
	if ((rc = fstatfs(fd, &statbuf)) == 0) {
	  availspace = statbuf.f_bavail * statbuf.f_bsize;
	}
#else /* none of the previous  -- SVR3 stuff... */
	struct statfs statbuf;
	if ((rc = fstatfs(fd, &statbuf,sizeof statbuf, 0)) == 0){
	  availspace = statbuf.f_bfree * statbuf.f_bsize;
	}
#endif
#endif
	return availspace;
}
