The branch, master has been updated
       via  10054c4 docs: Mention _NO_WINBINDD in idmap_script.8
       via  74f0a24 docs: build idmap_script.8 by default
       via  4f65fa9 pam_winbind: Avoid a use of sprintf
       via  9d6d620 smbcquotas: print "NO LIMIT" only if returned quota value 
is 0.
       via  0e01ed0 smbd: do not cover up VFS failures to get quota
       via  0124d3e nfs-quota: do not fail on ECONNREFUSED
       via  ce82f66 xfs-quota: do not fail if user has no quota
       via  faaaae3 sys-quotas: do not fail if user has no quota
       via  20a0d59 ntquotas - skip entry if the quota is zero
       via  78ae852 nt-quotas: return 0 as indication of no quota
       via  fcf6527 nt-quotas: vfs_get_ntquota() return NTSTATUS
      from  d378c85 winbind: Fix a typo in a wrong comment...

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 10054c4281d73652b641921b756eaaae14964e6b
Author: Volker Lendecke <[email protected]>
Date:   Thu Mar 31 17:10:39 2016 +0200

    docs: Mention _NO_WINBINDD in idmap_script.8
    
    Thanks to Joachim Achtzehnter <[email protected]> for pointing out 
this
    flaw!
    
    Signed-off-by: Volker Lendecke <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>
    
    Autobuild-User(master): Jeremy Allison <[email protected]>
    Autobuild-Date(master): Thu Mar 31 23:57:13 CEST 2016 on sn-devel-144

commit 74f0a2435b6f26135bfb4c25d297af5b2cc436c8
Author: Volker Lendecke <[email protected]>
Date:   Thu Mar 31 16:57:58 2016 +0200

    docs: build idmap_script.8 by default
    
    Signed-off-by: Volker Lendecke <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 4f65fa9c7b60264d71c8fe8ed715fb5c63e528ba
Author: Volker Lendecke <[email protected]>
Date:   Thu Mar 31 14:41:07 2016 +0200

    pam_winbind: Avoid a use of sprintf
    
    pam_winbind depends on talloc, which depends on libreplace, so we have 
asprintf
    available.
    
    Signed-off-by: Volker Lendecke <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 9d6d62010be2a54b6828cc4cc9c13b5657c8b4a0
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 14:20:44 2016 +0300

    smbcquotas: print "NO LIMIT" only if returned quota value is 0.
    
    If the user being queried has no quota, the server returns 0 as
    its quota. This is the observed smbd and Windows behavior, which
    is also documented in [MS-FSA] 2.5.1.20.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=11815
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 0e01ed06a40146d145ffe439a65fb9035ab7b1cf
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 14:02:31 2016 +0300

    smbd: do not cover up VFS failures to get quota
    
    Now that the VFS follows the convention that get-quota
    returns error only on error condition, and success
    with zero quota if there is no quota assigned,
    reply with an error if failing to obtain a user's
    quota.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 0124d3e6a537374c6639025934903ca03a08691e
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 13:21:58 2016 +0300

    nfs-quota: do not fail on ECONNREFUSED
    
    Trying to differentiate between "no quota" and real
    error conditions - if the connection to rpc.quotad
    is refused it could simply mean that the remote host
    has no quota and therefore report this as success with
    no quota.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit ce82f66b9fdc611124f7284e32e44ed3df2d7295
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 13:00:29 2016 +0300

    xfs-quota: do not fail if user has no quota
    
    XFS fails quotactl(Q_XGETQUOTA) with ENOENT if the user
    or group has no quota assigned to it. This is not an error
    condition - simply report 0 quota in this case.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit faaaae3c57977b6041d0bac99ff696c4760fdb01
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 14:05:49 2016 +0300

    sys-quotas: do not fail if user has no quota
    
    If the user/group has no quota, do not treat that as
    error condition. Instead, return zero quota.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 20a0d59d8c1d80b66a34611bffef1d43a9e1e2b4
Author: Uri Simchoni <[email protected]>
Date:   Wed Mar 30 13:59:39 2016 +0300

    ntquotas - skip entry if the quota is zero
    
    When listing user quotas, do not list the user
    if the driver returned success with zero quota -
    this signals that no quota is assigned for that
    user.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 78ae852dd7b6491e131d3a26f490bbcef53aa3d6
Author: Uri Simchoni <[email protected]>
Date:   Tue Mar 29 23:05:09 2016 +0300

    nt-quotas: return 0 as indication of no quota
    
    When getting user quota, the correct value to indicate "no quota"
    is 0, not -1.
    
    In [MS-FSCC] section 2.4.33 it is written that -1 designates no-quota.
    However, careful read of that section shows that this designation is only
    true when setting the quota, and this section says nothing about getting
    the quota.
    
    In [MS-FSA] section 2.1.5.20, it is written that "If SidList includes a SID
    that does not map to an existing SID in the 
Open.File.Volume.QuotaInformation
    list, the object store MUST return a FILE_QUOTA_INFORMATION structure
    (as specified in [MS-FSCC] section 2.4.33) that is filled with zeros.
    
    This is also verified experimentally and cleared with dochelp.
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit fcf6527202be9b1a913ebb93ef3ed1d01a0c26fa
Author: Uri Simchoni <[email protected]>
Date:   Tue Mar 29 23:30:23 2016 +0300

    nt-quotas: vfs_get_ntquota() return NTSTATUS
    
    Signed-off-by: Uri Simchoni <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

-----------------------------------------------------------------------

Summary of changes:
 docs-xml/manpages/idmap_script.8.xml | 18 ++++++++++++++++++
 docs-xml/wscript_build               |  1 +
 nsswitch/pam_winbind.c               |  6 +++---
 source3/lib/sysquotas_4A.c           | 16 ++--------------
 source3/lib/sysquotas_linux.c        |  9 +--------
 source3/lib/sysquotas_nfs.c          | 16 ++++++++++++++--
 source3/lib/sysquotas_xfs.c          | 16 ++++++++++++++--
 source3/smbd/ntquotas.c              | 32 +++++++++++++++++---------------
 source3/smbd/nttrans.c               | 11 ++++-------
 source3/smbd/proto.h                 |  3 ++-
 source3/smbd/trans2.c                |  6 ++++--
 source3/utils/smbcquotas.c           |  2 +-
 12 files changed, 81 insertions(+), 55 deletions(-)


Changeset truncated at 500 lines:

diff --git a/docs-xml/manpages/idmap_script.8.xml 
b/docs-xml/manpages/idmap_script.8.xml
index a378e7b..328a16b 100644
--- a/docs-xml/manpages/idmap_script.8.xml
+++ b/docs-xml/manpages/idmap_script.8.xml
@@ -148,6 +148,24 @@
        look up the mapping in a table or use some other mechanism for
        mapping SIDs to UIDs and etc.
        </para>
+
+       <para>
+         Please be aware that the script is called with the
+         _NO_WINBINDD environment variable set to 1. This prevents
+         recursive calls into winbind from the script both via
+         explicit calls to wbinfo and via implicit calls via
+         nss_winbind. For example a call to <command>ls -l</command>
+         could trigger such an infinite recursion.
+       </para>
+
+       <para>
+         It is safe to call <command>wbinfo -n</command> and
+         <command>wbinfo -s</command> from within an idmap script. To
+         do so, the script must unset the _NO_WINBINDD environment
+         variable right before the call to <command>wbinfo</command>
+         and set it to 1 again right after <command>wbinfo</command>
+         has returned to protect against the recursion.
+       </para>
 </refsect1>
 
 <refsect1>
diff --git a/docs-xml/wscript_build b/docs-xml/wscript_build
index 11b826b..2b3a180 100644
--- a/docs-xml/wscript_build
+++ b/docs-xml/wscript_build
@@ -15,6 +15,7 @@ manpages='''
          manpages/idmap_nss.8
          manpages/idmap_rfc2307.8
          manpages/idmap_rid.8
+         manpages/idmap_script.8
          manpages/idmap_tdb.8
          manpages/idmap_tdb2.8
          manpages/net.8
diff --git a/nsswitch/pam_winbind.c b/nsswitch/pam_winbind.c
index b2e1778..42c4f8e 100644
--- a/nsswitch/pam_winbind.c
+++ b/nsswitch/pam_winbind.c
@@ -191,17 +191,17 @@ static void _pam_log_int(const pam_handle_t *pamh,
 {
        char *format2 = NULL;
        const char *service;
+       int ret;
 
        pam_get_item(pamh, PAM_SERVICE, (const void **) &service);
 
-       format2 = (char 
*)malloc(strlen(MODULE_NAME)+strlen(format)+strlen(service)+5);
-       if (format2 == NULL) {
+       ret = asprintf(&format2, "%s(%s): %s", MODULE_NAME, service, format);
+       if (ret == -1) {
                /* what else todo ? */
                vsyslog(err, format, args);
                return;
        }
 
-       sprintf(format2, "%s(%s): %s", MODULE_NAME, service, format);
        vsyslog(err, format2, args);
        SAFE_FREE(format2);
 }
diff --git a/source3/lib/sysquotas_4A.c b/source3/lib/sysquotas_4A.c
index 244b612..674c4ee 100644
--- a/source3/lib/sysquotas_4A.c
+++ b/source3/lib/sysquotas_4A.c
@@ -104,13 +104,7 @@ int sys_get_vfs_quota(const char *path, const char *bdev, 
enum SMB_QUOTA_TYPE qt
                                return ret;
                        }
 
-                       if ((D.dqb_curblocks==0)&&
-                               (D.dqb_bsoftlimit==0)&&
-                               (D.dqb_bhardlimit==0)) {
-                               /* the upper layer functions don't want empty 
quota records...*/
-                               return -1;
-                       }
-
+                       ret = 0;
                        break;
 #ifdef HAVE_GROUP_QUOTA
                case SMB_GROUP_QUOTA_TYPE:
@@ -121,13 +115,7 @@ int sys_get_vfs_quota(const char *path, const char *bdev, 
enum SMB_QUOTA_TYPE qt
                                return ret;
                        }
 
-                       if ((D.dqb_curblocks==0)&&
-                               (D.dqb_bsoftlimit==0)&&
-                               (D.dqb_bhardlimit==0)) {
-                               /* the upper layer functions don't want empty 
quota records...*/
-                               return -1;
-                       }
-
+                       ret = 0;
                        break;
 #endif /* HAVE_GROUP_QUOTA */
                case SMB_USER_FS_QUOTA_TYPE:
diff --git a/source3/lib/sysquotas_linux.c b/source3/lib/sysquotas_linux.c
index bf3504a..5984626 100644
--- a/source3/lib/sysquotas_linux.c
+++ b/source3/lib/sysquotas_linux.c
@@ -447,14 +447,7 @@ int sys_get_vfs_quota(const char *path, const char *bdev, 
enum SMB_QUOTA_TYPE qt
                                        }
                                }
                        }
-
-                       if ((dp->curblocks==0)&&
-                               (dp->softlimit==0)&&
-                               (dp->hardlimit==0)) {
-                               /* the upper layer functions don't want empty 
quota records...*/
-                               return -1;
-                       }
-
+                       ret = 0;
                        break;
                case SMB_USER_FS_QUOTA_TYPE:
                        id.uid = getuid();
diff --git a/source3/lib/sysquotas_nfs.c b/source3/lib/sysquotas_nfs.c
index 4b37e34..fe46d3f 100644
--- a/source3/lib/sysquotas_nfs.c
+++ b/source3/lib/sysquotas_nfs.c
@@ -180,8 +180,20 @@ int sys_get_nfs_quota(const char *path, const char *bdev,
                              timeout);
 
        if (clnt_stat != RPC_SUCCESS) {
-               DEBUG(3, ("sys_get_nfs_quotas: clnt_call failed\n"));
-               ret = -1;
+               if (errno == ECONNREFUSED) {
+                       /* If we cannot connect with rpc.quotad, it may
+                        * simply be because there's no quota on the remote
+                        * system
+                        */
+                       DBG_INFO("clnt_call failed with ECONNREFUSED - "
+                                "assuming no quotas on server\n");
+                       ret = 0;
+               } else {
+                       int save_errno = errno;
+                       DBG_NOTICE("clnt_call failed - %s\n", strerror(errno));
+                       errno = save_errno;
+                       ret = -1;
+               }
                goto out;
        }
 
diff --git a/source3/lib/sysquotas_xfs.c b/source3/lib/sysquotas_xfs.c
index ccc7fc0..bea86d5 100644
--- a/source3/lib/sysquotas_xfs.c
+++ b/source3/lib/sysquotas_xfs.c
@@ -90,16 +90,28 @@ int sys_get_xfs_quota(const char *path, const char *bdev, 
enum SMB_QUOTA_TYPE qt
                        DEBUG(10,("sys_get_xfs_quota: path[%s] bdev[%s] 
SMB_USER_QUOTA_TYPE uid[%u]\n",
                                path, bdev, (unsigned)id.uid));
 
-                       if ((ret=quotactl(QCMD(Q_XGETQUOTA,USRQUOTA), bdev, 
id.uid, (caddr_t)&D)))
+                       ret=quotactl(QCMD(Q_XGETQUOTA,USRQUOTA), bdev, id.uid, 
(caddr_t)&D);
+                       /* XFS fails with ENOENT if the user has no
+                        * quota. Our protocol in that case is to
+                        * succeed and return 0 as quota.
+                        */
+                       if (ret != 0 && errno != ENOENT) {
                                return ret;
+                       }
                        break;
 #ifdef HAVE_GROUP_QUOTA
                case SMB_GROUP_QUOTA_TYPE:
                        DEBUG(10,("sys_get_xfs_quota: path[%s] bdev[%s] 
SMB_GROUP_QUOTA_TYPE gid[%u]\n",
                                path, bdev, (unsigned)id.gid));
 
-                       if ((ret=quotactl(QCMD(Q_XGETQUOTA,GRPQUOTA), bdev, 
id.gid, (caddr_t)&D)))
+                       ret=quotactl(QCMD(Q_XGETQUOTA,GRPQUOTA), bdev, id.gid, 
(caddr_t)&D);
+                       /* XFS fails with ENOENT if the user has no
+                        * quota. Our protocol in that case is to
+                        * succeed and return 0 as quota.
+                        */
+                       if (ret != 0 && errno != ENOENT) {
                                return ret;
+                       }
                        break;
 #endif /* HAVE_GROUP_QUOTA */
                case SMB_USER_FS_QUOTA_TYPE:
diff --git a/source3/smbd/ntquotas.c b/source3/smbd/ntquotas.c
index aa2ec3b..9b2e39a 100644
--- a/source3/smbd/ntquotas.c
+++ b/source3/smbd/ntquotas.c
@@ -53,14 +53,6 @@ static uint64_t limit_unix2nt(uint64_t in, uint64_t bsize)
 
        ret = (uint64_t)(in*bsize);
        
-       if (ret < in) {
-               /* we overflow */
-               ret = SMB_NTQUOTAS_NO_LIMIT;
-       }
-
-       if (in == SMB_QUOTAS_NO_LIMIT)
-               ret = SMB_NTQUOTAS_NO_LIMIT;
-
        return ret;
 }
 
@@ -76,7 +68,8 @@ static uint64_t limit_blk2inodes(uint64_t in)
        return ret;     
 }
 
-int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype, struct 
dom_sid *psid, SMB_NTQUOTA_STRUCT *qt)
+NTSTATUS vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype,
+                        struct dom_sid *psid, SMB_NTQUOTA_STRUCT *qt)
 {
        int ret;
        SMB_DISK_QUOTA D;
@@ -84,8 +77,9 @@ int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE 
qtype, struct dom_sid
 
        ZERO_STRUCT(D);
 
-       if (!fsp||!fsp->conn||!qt)
-               return (-1);
+       if (!fsp || !fsp->conn || !qt) {
+               return NT_STATUS_INTERNAL_ERROR;
+       }
 
        ZERO_STRUCT(*qt);
 
@@ -94,6 +88,7 @@ int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE 
qtype, struct dom_sid
        if (psid && !sid_to_uid(psid, &id.uid)) {
                DEBUG(0,("sid_to_uid: failed, SID[%s]\n",
                         sid_string_dbg(psid)));
+               return NT_STATUS_NO_SUCH_USER;
        }
 
        ret = SMB_VFS_GET_QUOTA(fsp->conn, ".", qtype, id, &D);
@@ -102,7 +97,7 @@ int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE 
qtype, struct dom_sid
                qt->sid    = *psid;
 
        if (ret!=0) {
-               return ret;
+               return map_nt_error_from_unix(errno);
        }
                
        qt->usedspace = (uint64_t)D.curblocks*D.bsize;
@@ -110,8 +105,7 @@ int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE 
qtype, struct dom_sid
        qt->hardlim = limit_unix2nt(D.hardlimit, D.bsize);
        qt->qflags = D.qflags;
 
-       
-       return 0;
+       return NT_STATUS_OK;
 }
 
 int vfs_set_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype, struct 
dom_sid *psid, SMB_NTQUOTA_STRUCT *qt)
@@ -181,6 +175,7 @@ int vfs_get_user_ntquota_list(files_struct *fsp, 
SMB_NTQUOTA_LIST **qt_list)
                SMB_NTQUOTA_STRUCT tmp_qt;
                SMB_NTQUOTA_LIST *tmp_list_ent;
                struct dom_sid  sid;
+               NTSTATUS status;
 
                ZERO_STRUCT(tmp_qt);
 
@@ -191,7 +186,14 @@ int vfs_get_user_ntquota_list(files_struct *fsp, 
SMB_NTQUOTA_LIST **qt_list)
 
                uid_to_sid(&sid, usr->pw_uid);
 
-               if (vfs_get_ntquota(fsp, SMB_USER_QUOTA_TYPE, &sid, 
&tmp_qt)!=0) {
+               status =
+                   vfs_get_ntquota(fsp, SMB_USER_QUOTA_TYPE, &sid, &tmp_qt);
+               if (!NT_STATUS_IS_OK(status)) {
+                       DEBUG(5, ("failed getting quota for uid[%ld] - %s\n",
+                                 (long)usr->pw_uid, nt_errstr(status)));
+                       continue;
+               }
+               if (tmp_qt.softlim == 0 && tmp_qt.hardlim == 0) {
                        DEBUG(5,("no quota entry for sid[%s] path[%s]\n",
                                 sid_string_dbg(&sid),
                                 fsp->conn->connectpath));
diff --git a/source3/smbd/nttrans.c b/source3/smbd/nttrans.c
index 3a2c35f..fa3f74c 100644
--- a/source3/smbd/nttrans.c
+++ b/source3/smbd/nttrans.c
@@ -2509,13 +2509,10 @@ static void 
call_nt_transact_get_user_quota(connection_struct *conn,
                                return;
                        }
 
-                       if (vfs_get_ntquota(fsp, SMB_USER_QUOTA_TYPE, &sid, 
&qt)!=0) {
-                               ZERO_STRUCT(qt);
-                               /*
-                                * we have to return zero's in all fields
-                                * instead of returning an error here
-                                * --metze
-                                */
+                       nt_status = vfs_get_ntquota(fsp, SMB_USER_QUOTA_TYPE,
+                                                   &sid, &qt);
+                       if (!NT_STATUS_IS_OK(nt_status)) {
+                               reply_nterror(req, nt_status);
                        }
 
                        /* Realloc the size of parameters and data we will 
return */
diff --git a/source3/smbd/proto.h b/source3/smbd/proto.h
index 8e8cbc3..3612034 100644
--- a/source3/smbd/proto.h
+++ b/source3/smbd/proto.h
@@ -600,7 +600,8 @@ NTSTATUS notify_walk(struct notify_context *notify,
 
 /* The following definitions come from smbd/ntquotas.c  */
 
-int vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype, struct 
dom_sid *psid, SMB_NTQUOTA_STRUCT *qt);
+NTSTATUS vfs_get_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype,
+                        struct dom_sid *psid, SMB_NTQUOTA_STRUCT *qt);
 int vfs_set_ntquota(files_struct *fsp, enum SMB_QUOTA_TYPE qtype, struct 
dom_sid *psid, SMB_NTQUOTA_STRUCT *qt);
 int vfs_get_user_ntquota_list(files_struct *fsp, SMB_NTQUOTA_LIST **qt_list);
 void *init_quota_handle(TALLOC_CTX *mem_ctx);
diff --git a/source3/smbd/trans2.c b/source3/smbd/trans2.c
index f351008..0e1c6d9 100644
--- a/source3/smbd/trans2.c
+++ b/source3/smbd/trans2.c
@@ -3712,9 +3712,11 @@ cBytesSector=%u, cUnitTotal=%u, cUnitAvail=%d\n", 
(unsigned int)bsize, (unsigned
                                return NT_STATUS_ACCESS_DENIED;
                        }
 
-                       if (vfs_get_ntquota(&fsp, SMB_USER_FS_QUOTA_TYPE, NULL, 
&quotas)!=0) {
+                       status = vfs_get_ntquota(&fsp, SMB_USER_FS_QUOTA_TYPE,
+                                                NULL, &quotas);
+                       if (!NT_STATUS_IS_OK(status)) {
                                DEBUG(0,("vfs_get_ntquota() failed for service 
[%s]\n",lp_servicename(talloc_tos(), SNUM(conn))));
-                               return map_nt_error_from_unix(errno);
+                               return status;
                        }
 
                        data_len = 48;
diff --git a/source3/utils/smbcquotas.c b/source3/utils/smbcquotas.c
index 9e64319..e6f1dfb 100644
--- a/source3/utils/smbcquotas.c
+++ b/source3/utils/smbcquotas.c
@@ -236,7 +236,7 @@ static const char *quota_str_static(uint64_t val, bool 
special, bool _numeric)
 {
        const char *result;
 
-       if (!_numeric&&special&&(val == SMB_NTQUOTAS_NO_LIMIT)) {
+       if (!_numeric && special && val == 0) {
                return "NO LIMIT";
        }
        result = talloc_asprintf(talloc_tos(), "%"PRIu64, val);


-- 
Samba Shared Repository

Reply via email to