[PATCH] support quota on Solaris 10

Uri Simchoni uri at samba.org
Sat Mar 12 18:35:22 UTC 2016


Hi,

A while back, Andrew Morgan <morgan at orst.edu> reported an issue with 
quota support on Solaris 10. In essence this was a degradation from the 
autoconf build, where configure test is not setting WITH_QUOTAS due to a 
missing test.

Andy and I worked out a fix for this, which he now tested on a 
production system after upgrading to Samba 4.3.6 due to the latest 
security fixes.

The autoconf build simply tried compiling disk_quotas.c. I had 
difficulties doing that with the waf build, so this patch introduces a 
stripped-down version of disk_quotas.c, tests/oldquotas.c, and configure 
tries to build it.

Please review.
Thanks,
Uri.
-------------- next part --------------
From 21a5e4df9cf5de84bdedb5f43535523b68f4e5b3 Mon Sep 17 00:00:00 2001
From: Uri Simchoni <uri at samba.org>
Date: Wed, 3 Feb 2016 06:41:42 +0200
Subject: [PATCH] build: fix disk-free quota support on Solaris 10

Samba has no code to support quota on Solaris 10 (and possibly other
os's such as AIX) using the new quota interface. The new interface
serves both disk size/free space reporting (clamping the underlying
file system numbers with quota), and direct manipulation of the user's
quota.

However, there's legacy code that supports only disk size/free space on
Solaris 10. In the waf build, this code is not compiled because there is
no test for it.

This patch adds a test to see whether the legacy code can be used.

Issue reported and fix tested by Andrew Morgan <morgan at orst.edu>.

BUG: https://bugzilla.samba.org/show_bug.cgi?id=11788

Signed-off-by: Uri Simchoni <uri at samba.org>
---
 source3/wscript       |  24 +++++++
 source3/wscript_build |   1 +
 tests/oldquotas.c     | 174 ++++++++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 199 insertions(+)
 create mode 100644 tests/oldquotas.c

diff --git a/source3/wscript b/source3/wscript
index c6504c6..c23f621 100644
--- a/source3/wscript
+++ b/source3/wscript
@@ -1455,6 +1455,30 @@ main() {
             conf.DEFINE('HAVE_SYS_QUOTAS', '1')
             conf.DEFINE('WITH_QUOTAS', '1')
 
+        #
+        # check if Legacy quota code can be brought in
+        # if standard interfaces are not supported
+        #
+        legacy_quota_libs = ''
+        if not conf.CONFIG_SET('WITH_QUOTAS'):
+            if host_os.rfind('sunos5') > -1:
+                conf.DEFINE('SUNOS5', '1')
+                legacy_quota_libs = 'nsl'
+            conf.CHECK_CODE('''
+            #define WITH_QUOTAS 1
+            #define AUTOCONF_TEST 1
+            #include "../tests/oldquotas.c"
+            ''',
+                            cflags=conf.env['WERROR_CFLAGS'],
+                            define='WITH_QUOTAS',
+                            lib=legacy_quota_libs,
+                            msg='Checking whether legacy quota code can be used',
+                            execute=False,
+                            addmain=False)
+            if not conf.CONFIG_SET('WITH_QUOTAS'):
+                legacy_quota_libs = ''
+        conf.env['legacy_quota_libs'] = legacy_quota_libs
+
     #
     # cluster support (CTDB)
     #
diff --git a/source3/wscript_build b/source3/wscript_build
index 9dc93bf..dce0238 100755
--- a/source3/wscript_build
+++ b/source3/wscript_build
@@ -634,6 +634,7 @@ bld.SAMBA3_LIBRARY('smbd_base',
                    notifyd
                    ''' +
                    bld.env['dmapi_lib'] +
+                   bld.env['legacy_quota_libs'] +
                    NOTIFY_DEPS,
                    private_library=True)
 
diff --git a/tests/oldquotas.c b/tests/oldquotas.c
new file mode 100644
index 0000000..bdb2beb
--- /dev/null
+++ b/tests/oldquotas.c
@@ -0,0 +1,174 @@
+/* this test should find out whether legacy quota code in disk_quotas.c
+ * compiles. It is a stripped-down version of disk_quotas.c, with samba
+ * stuff removed and only system calls, header files, and constants left.
+ */
+
+#ifndef HAVE_SYS_QUOTAS
+
+/* just a quick hack because sysquotas.h is included before linux/quota.h */
+#ifdef QUOTABLOCK_SIZE
+#undef QUOTABLOCK_SIZE
+#endif
+
+#ifdef WITH_QUOTAS
+
+#if defined(VXFS_QUOTA)
+
+bool disk_quotas_vxfs(const char *name, char *path, uint64_t *bsize,
+		      uint64_t *dfree, uint64_t *dsize);
+
+#endif /* VXFS_QUOTA */
+
+#if defined(SUNOS5) || defined(SUNOS4)
+
+#include <fcntl.h>
+#include <sys/param.h>
+#if defined(SUNOS5)
+#include <sys/fs/ufs_quota.h>
+#include <sys/mnttab.h>
+#include <sys/mntent.h>
+#else /* defined(SUNOS4) */
+#include <ufs/quota.h>
+#include <mntent.h>
+#endif
+
+#if defined(SUNOS5)
+
+/****************************************************************************
+ Allows querying of remote hosts for quotas on NFS mounted shares.
+ Supports normal NFS and AMD mounts.
+ Alan Romeril <a.romeril at ic.ac.uk> July 2K.
+****************************************************************************/
+
+#include <rpc/rpc.h>
+#include <rpc/types.h>
+#include <rpcsvc/rquota.h>
+#include <rpc/nettype.h>
+#include <rpc/xdr.h>
+
+static bool nfs_quotas(char *nfspath, uid_t euser_id, uint64_t *bsize,
+		       uint64_t *dfree, uint64_t *dsize)
+{
+	CLIENT *clnt;
+	clnt = clnt_create("host", RQUOTAPROG, RQUOTAVERS, "udp");
+	return true;
+}
+#endif
+
+/****************************************************************************
+try to get the disk space from disk quotas (SunOS & Solaris2 version)
+Quota code by Peter Urbanec (amiga at cse.unsw.edu.au).
+****************************************************************************/
+
+bool disk_quotas(const char *path, uint64_t *bsize, uint64_t *dfree,
+		 uint64_t *dsize)
+{
+	int ret;
+#if defined(SUNOS5)
+	struct quotctl command;
+#else /* SunOS4 */
+	struct mntent *mnt;
+#endif
+#if defined(SUNOS5)
+	nfs_quotas("", 0, bsize, dfree, dsize);
+
+	command.op = Q_GETQUOTA;
+	command.uid = 0;
+	command.addr = NULL;
+	ret = ioctl(1, Q_QUOTACTL, &command);
+#else
+	ret = quotactl(Q_GETQUOTA, "", 0, NULL);
+#endif
+
+#if defined(SUNOS5) && defined(VXFS_QUOTA)
+	disk_quotas_vxfs("", path, bsize, dfree, dsize);
+#endif
+	return true;
+}
+
+#else
+
+#if AIX
+/* AIX quota patch from Ole Holm Nielsen <ohnielse at fysik.dtu.dk> */
+#include <jfs/quota.h>
+/* AIX 4.X: Rename members of the dqblk structure (ohnielse at fysik.dtu.dk) */
+#define dqb_curfiles dqb_curinodes
+#define dqb_fhardlimit dqb_ihardlimit
+#define dqb_fsoftlimit dqb_isoftlimit
+#ifdef _AIXVERSION_530
+#include <sys/statfs.h>
+#include <sys/vmount.h>
+#endif /* AIX 5.3 */
+#else  /* !AIX */
+#include <sys/quota.h>
+#include <devnm.h>
+#endif
+
+/****************************************************************************
+try to get the disk space from disk quotas - default version
+****************************************************************************/
+
+bool disk_quotas(const char *path, uint64_t *bsize, uint64_t *dfree,
+		 uint64_t *dsize)
+{
+	struct dqblk D;
+#if defined(AIX)
+#ifdef _AIXVERSION_530
+	quota64_t user_quota;
+	quotactl(path, QCMD(Q_J2GETQUOTA, USRQUOTA), 0, (char *)&user_quota);
+#endif /* AIX 5.3 */
+	quotactl(path, QCMD(Q_GETQUOTA, USRQUOTA), 0, (char *)&D);
+#else  /* !AIX */
+	quotactl(Q_GETQUOTA, "", 0, &D);
+#endif /* !AIX */
+	return (true);
+}
+
+#endif
+
+#if defined(VXFS_QUOTA)
+
+#if defined(SUNOS5)
+
+#include <sys/fs/vx_solaris.h>
+#include <sys/fs/vx_machdep.h>
+#include <sys/fs/vx_layout.h>
+#include <sys/fs/vx_quota.h>
+#include <sys/fs/vx_aioctl.h>
+#include <sys/fs/vx_ioctl.h>
+
+bool disk_quotas_vxfs(const char *name, char *path, uint64_t *bsize,
+		      uint64_t *dfree, uint64_t *dsize)
+{
+	struct vx_dqblk D;
+	struct vx_quotctl quotabuf;
+	struct vx_genioctl genbuf;
+
+	genbuf.ioc_cmd = VX_QUOTACTL;
+	genbuf.ioc_up = (void *)"abuf;
+
+	quotabuf.cmd = VX_GETQUOTA;
+	quotabuf.uid = 0;
+	quotabuf.addr = (caddr_t)&D;
+	ret = ioctl(1, VX_ADMIN_IOCTL, &genbuf);
+
+	return true;
+}
+
+#endif /* SUNOS5 || ... */
+
+#endif /* VXFS_QUOTA */
+
+#else /* WITH_QUOTAS */
+
+#error "This test should be called with WITH_QUOTAS defined"
+
+#endif /* WITH_QUOTAS */
+
+#else /* HAVE_SYS_QUOTAS */
+
+#error "This test should not be called for systems with new quota interface"
+
+#endif /* HAVE_SYS_QUOTAS */
+
+int main() { return disk_quotas(NULL, NULL, NULL, NULL); }
-- 
2.5.0



More information about the samba-technical mailing list