The branch, master has been updated
       via  e053aad s3/utils: fix regression where specifying -Unetbios/root 
works
       via  705086d s3/smbd: allow set quota for non root user (when built with 
--enable-selftest)
       via  801c185 s3/script/tests: Add simple (smb1 & smb2) get/set/list 
tests for smbcquotas
       via  90da2e5 s3/script/test: modify existing smbcquota test to use SMB2 
in addition to SMB1.
       via  9070384 s3/smbd: smb2 server implementation for query get/set info.
       via  b8802e2 s3/smbd: adjust smb1 server to use idl structs and 
generated ndr push/pull funcs
       via  dd21b4f s3/libsmb: adjust smb2 code for new idl structs & generated 
ndr push/pull funcs.
       via  07e9113 s3/libsmb: adjust smb1 cli code to use idl structs and ndr 
push/pull funcs.
       via  fd7c6f9 librpc/idl Add some query [getset]info quota related 
structures
       via  1033dd9 s3/smbd: Don't stat when doing a quota operation (as it's a 
fake file)
       via  b934082 s3/libsmb: Avoid potential smbpanic calling 
parse_user_quota_list.
       via  2bfb9b4 s3/lib: Fix misleading typo in debug message
      from  8dac16e smb2_query_directory: make 'return true' explicit in 
smb2_query_directory_next_entry()

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


- Log -----------------------------------------------------------------
commit e053aad4ae46dfcda6143d55e8e913e923fa34be
Author: Noel Power <[email protected]>
Date:   Thu Jun 28 16:04:24 2018 +0100

    s3/utils: fix regression where specifying -Unetbios/root works
    
    Usually you need to be root on a linux server to modify quotas. Even
    with a linux server joined to a windows AD you could always log in as
    local root with smbcquotas. However in recent builds this has changed.
    This patch fixes this
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>
    
    Autobuild-User(master): Noel Power <[email protected]>
    Autobuild-Date(master): Tue Jul 31 19:45:59 CEST 2018 on sn-devel-144

commit 705086d83c847c707e8230ce6a58e840a70d93c3
Author: Noel Power <[email protected]>
Date:   Wed Mar 22 20:06:13 2017 +0000

    s3/smbd: allow set quota for non root user (when built with 
--enable-selftest)
    
    Currently it appears you need to be root to set quotas, for test purposes
    this requirement needs to be relaxed.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 801c1856a39cbc2fd65183a7d6d8b7526dbc251e
Author: Noel Power <[email protected]>
Date:   Tue Mar 21 08:29:59 2017 +0000

    s3/script/tests: Add simple (smb1 & smb2) get/set/list tests for smbcquotas
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 90da2e599b1e46beea1d3dc4b6e9338786250882
Author: Noel Power <[email protected]>
Date:   Wed Mar 8 14:27:27 2017 +0000

    s3/script/test: modify existing smbcquota test to use SMB2 in addition to 
SMB1.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 907038417673dc0076838586e620b88513d78cb0
Author: Noel Power <[email protected]>
Date:   Fri May 26 16:02:33 2017 +0100

    s3/smbd: smb2 server implementation for query get/set info.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit b8802e271337e5cec4f13ad4f505ae1905e09ca7
Author: Noel Power <[email protected]>
Date:   Fri May 26 16:01:53 2017 +0100

    s3/smbd: adjust smb1 server to use idl structs and generated ndr push/pull 
funcs
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit dd21b4fcfef4a663c43cf8e8601da350cbb0cfd3
Author: Noel Power <[email protected]>
Date:   Fri May 26 15:50:18 2017 +0100

    s3/libsmb: adjust smb2 code for new idl structs & generated ndr push/pull 
funcs.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 07e9113291213831f489aac7cffe3ee99dfb3cea
Author: Noel Power <[email protected]>
Date:   Fri May 26 15:01:17 2017 +0100

    s3/libsmb: adjust smb1 cli code to use idl structs and ndr push/pull funcs.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit fd7c6f9bc7eb2de565ae9dc0aae6932904d53ec9
Author: Noel Power <[email protected]>
Date:   Thu Mar 2 09:20:24 2017 +0000

    librpc/idl Add some query [getset]info quota related structures
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 1033dd9e303fc91b97e2054713b714ed5f356eb8
Author: Noel Power <[email protected]>
Date:   Tue Feb 28 11:36:47 2017 +0000

    s3/smbd: Don't stat when doing a quota operation (as it's a fake file)
    
    calling SMB_VFS_STAT on the quota fake file fails and caused
    FS_INFO/FileFsControlInfo request to error out early, in turn stopped a
    Win8.1 client from proceeding with quota queries.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit b93408246252fe1e3a72de33bcaa8ebb5fe7a1d2
Author: Noel Power <[email protected]>
Date:   Tue Feb 28 15:04:16 2017 +0000

    s3/libsmb: Avoid potential smbpanic calling parse_user_quota_list.
    
    Calling parse_user_quota_list with a NULL buffer can cause a panic, while
    this shouldn't happen, I managed to trigger this with an early 
implementation
    of SMB2 quota support in smbd which didn't pass back 
NT_STATUS_NO_MORE_ENTRIES
    when handling a SMB2_0_INFO_QUOTA GETINFO message.
    OTHOH the Windows client handled the same situation gracefully.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

commit 2bfb9b4081fff1ef816bbfdd3ebb989d1c56ec1b
Author: Noel Power <[email protected]>
Date:   Wed Mar 22 14:53:22 2017 +0000

    s3/lib: Fix misleading typo in debug message
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13553
    
    Signed-off-by: Noel Power <[email protected]>
    Reviewed-by: Jeremy Allison <[email protected]>

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

Summary of changes:
 librpc/idl/quota.idl                               |  54 ++
 librpc/idl/wscript_build                           |   1 +
 librpc/wscript_build                               |   5 +
 selftest/target/Samba3.pm                          |   9 +
 source3/lib/sysquotas.c                            |   2 +-
 source3/libsmb/cli_smb2_fnum.c                     |  94 ++-
 source3/libsmb/cliquota.c                          | 392 ++++++------
 source3/libsmb/proto.h                             |   6 +
 source3/script/tests/getset_quota.py               | 154 +++++
 source3/script/tests/test_dfree_quota.sh           |  14 +-
 source3/script/tests/test_smbcquota.py             | 244 ++++++++
 .../script/tests/test_smbcquota.sh                 |  42 +-
 source3/selftest/tests.py                          |   1 +
 source3/smbd/nttrans.c                             | 662 ++++++++++++---------
 source3/smbd/proto.h                               |  14 +
 source3/smbd/smb2_getinfo.c                        |  86 ++-
 source3/smbd/smb2_setinfo.c                        |  36 ++
 source3/smbd/trans2.c                              |   3 +-
 source3/utils/smbcquotas.c                         |   3 +-
 source3/wscript_build                              |   2 +
 20 files changed, 1313 insertions(+), 511 deletions(-)
 create mode 100644 librpc/idl/quota.idl
 create mode 100755 source3/script/tests/getset_quota.py
 create mode 100755 source3/script/tests/test_smbcquota.py
 copy python/samba/tests/policy.py => source3/script/tests/test_smbcquota.sh 
(52%)
 mode change 100644 => 100755


Changeset truncated at 500 lines:

diff --git a/librpc/idl/quota.idl b/librpc/idl/quota.idl
new file mode 100644
index 0000000..7c4d00a
--- /dev/null
+++ b/librpc/idl/quota.idl
@@ -0,0 +1,54 @@
+#include "idl_types.h"
+
+import "security.idl";
+
+[
+       pointer_default(unique)
+]
+
+interface file_quota {
+
+       /* MS-FSCC 2.4.33.1 */
+       typedef [public] struct {
+               uint32 next_entry_offset;
+               uint32 sid_length;
+               dom_sid sid;
+       } file_get_quota_info;
+
+       /* MS-FSCC 2.4.33 */
+       typedef [public] struct {
+               uint32 next_entry_offset;
+               uint32 sid_length;
+               hyper change_time;
+               hyper quota_used;
+               hyper quota_threshold;
+               hyper quota_limit;
+               dom_sid sid;
+       } file_quota_information;
+}
+
+interface smb2_query_quoata
+{
+       /* MS-SMB2 2.2.37.1 */
+       typedef [public] struct {
+               uint8 return_single;
+               uint8 restart_scan;
+               uint16 reserved;
+               uint32 sid_list_length;
+               uint32 start_sid_length;
+               uint32 start_sid_offset;
+       } smb2_query_quota_info;
+}
+
+interface smb1_nt_transact_query_quota
+{
+       /* MS-SMB 2.2.7.5.1 */
+       typedef [public] struct {
+               uint16 fid;
+               uint8 return_single_entry;
+               uint8 restart_scan;
+               uint32 sid_list_length;
+               uint32 start_sid_length;
+               uint32 start_sid_offset;
+       } nttrans_query_quota_params;
+}
diff --git a/librpc/idl/wscript_build b/librpc/idl/wscript_build
index 75eba7d..f1588cd 100644
--- a/librpc/idl/wscript_build
+++ b/librpc/idl/wscript_build
@@ -38,6 +38,7 @@ bld.SAMBA_PIDL_LIST('PIDL',
                     fsrvp_state.idl
                     cab.idl
                     nfs4acl.idl
+                    quota.idl
                     ''',
                     options='--header --ndr-parser',
                     output_dir='../gen_ndr')
diff --git a/librpc/wscript_build b/librpc/wscript_build
index 36414fb..824c0f9 100644
--- a/librpc/wscript_build
+++ b/librpc/wscript_build
@@ -399,6 +399,11 @@ bld.SAMBA_SUBSYSTEM('NDR_SMB2_LEASE_STRUCT',
     public_headers='gen_ndr/smb2_lease_struct.h'
     )
 
+bld.SAMBA_SUBSYSTEM('NDR_QUOTA',
+    source='gen_ndr/ndr_quota.c',
+    public_deps='ndr',
+    )
+
 bld.SAMBA_SUBSYSTEM('NDR_SCHANNEL',
     source='ndr/ndr_schannel.c gen_ndr/ndr_schannel.c',
     public_deps='ndr ndr_nbt'
diff --git a/selftest/target/Samba3.pm b/selftest/target/Samba3.pm
index 5b8cf9e..447c1e8 100755
--- a/selftest/target/Samba3.pm
+++ b/selftest/target/Samba3.pm
@@ -885,6 +885,9 @@ sub setup_fileserver
        push(@dirs, "$dfree_share_dir/subdir2");
        push(@dirs, "$dfree_share_dir/subdir3");
 
+       my $quotadir_dir="$share_dir/quota";
+       push(@dirs, $quotadir_dir);
+
        my $valid_users_sharedir="$share_dir/valid_users";
        push(@dirs,$valid_users_sharedir);
 
@@ -911,6 +914,8 @@ sub setup_fileserver
        usershare allow guests = yes
        usershare prefix allow list = $usershare_sharedir
 
+       get quota command = $prefix_abs/getset_quota.py
+       set quota command = $prefix_abs/getset_quota.py
 [lowercase]
        path = $lower_case_share_dir
        comment = smb username is [%U]
@@ -2170,6 +2175,10 @@ sub provision($$$$$$$$$)
        vfs objects = acl_xattr fake_acls xattr_tdb fake_dfq
        inherit owner = yes
        include = $dfqconffile
+[quotadir]
+       path = $shrdir/quota
+       admin users = $unix_name
+
 [acl_xattr_ign_sysacl_posix]
        copy = tmp
        acl_xattr:ignore system acls = yes
diff --git a/source3/lib/sysquotas.c b/source3/lib/sysquotas.c
index eef87be..9b2d37b 100644
--- a/source3/lib/sysquotas.c
+++ b/source3/lib/sysquotas.c
@@ -418,7 +418,7 @@ static int command_set_quota(const char *path, enum 
SMB_QUOTA_TYPE qtype, unid_t
                        return -1;
                }
 
-               DEBUG (3, ("get_quota: Running command %s\n", syscmd));
+               DBG_NOTICE("set_quota: Running command %s\n", syscmd);
 
                lines = file_lines_pload(talloc_tos(), syscmd, NULL);
                SAFE_FREE(syscmd);
diff --git a/source3/libsmb/cli_smb2_fnum.c b/source3/libsmb/cli_smb2_fnum.c
index 4b9871c..3537932 100644
--- a/source3/libsmb/cli_smb2_fnum.c
+++ b/source3/libsmb/cli_smb2_fnum.c
@@ -41,6 +41,7 @@
 #include "lib/util_ea.h"
 #include "librpc/gen_ndr/ndr_ioctl.h"
 #include "ntioctl.h"
+#include "librpc/gen_ndr/ndr_quota.h"
 
 struct smb2_hnd {
        uint64_t fid_persistent;
@@ -2910,12 +2911,16 @@ NTSTATUS cli_smb2_get_user_quota(struct cli_state *cli,
 {
        NTSTATUS status;
        DATA_BLOB inbuf = data_blob_null;
+       DATA_BLOB info_blob = data_blob_null;
        DATA_BLOB outbuf = data_blob_null;
        struct smb2_hnd *ph = NULL;
        TALLOC_CTX *frame = talloc_stackframe();
        unsigned sid_len;
        unsigned int offset;
-       uint8_t *buf;
+       struct smb2_query_quota_info query = {0};
+       struct file_get_quota_info info = {0};
+       enum ndr_err_code err;
+       struct ndr_push *ndr_push = NULL;
 
        if (smbXcli_conn_has_async_calls(cli->conn)) {
                /*
@@ -2937,27 +2942,52 @@ NTSTATUS cli_smb2_get_user_quota(struct cli_state *cli,
 
        sid_len = ndr_size_dom_sid(&pqt->sid, 0);
 
-       inbuf = data_blob_talloc_zero(frame, 24 + sid_len);
-       if (inbuf.data == NULL) {
+       query.return_single = 1;
+       if (sid_len < 0) {
+               status = NT_STATUS_INVALID_PARAMETER;
+               goto fail;
+       }
+
+       info.next_entry_offset = 0;
+       info.sid_length = sid_len;
+       info.sid = pqt->sid;
+
+       err = ndr_push_struct_blob(
+                       &info_blob,
+                       frame,
+                       &info,
+                       (ndr_push_flags_fn_t)ndr_push_file_get_quota_info);
+
+       if (!NDR_ERR_CODE_IS_SUCCESS(err)) {
+               status = NT_STATUS_INTERNAL_ERROR;
+               goto fail;
+       }
+
+       query.sid_list_length = info_blob.length;
+       ndr_push = ndr_push_init_ctx(frame);
+       if (!ndr_push) {
                status = NT_STATUS_NO_MEMORY;
                goto fail;
        }
 
-       buf = inbuf.data;
+       err = ndr_push_smb2_query_quota_info(ndr_push,
+                                            NDR_SCALARS | NDR_BUFFERS,
+                                            &query);
 
-       SCVAL(buf, 0, 1);          /* ReturnSingle */
-       SCVAL(buf, 1, 0);          /* RestartScan */
-       SSVAL(buf, 2, 0);          /* Reserved */
-       if (8 + sid_len < 8) {
-               status = NT_STATUS_INVALID_PARAMETER;
+       if (!NDR_ERR_CODE_IS_SUCCESS(err)) {
+               status = NT_STATUS_INTERNAL_ERROR;
+               goto fail;
+       }
+
+       err = ndr_push_array_uint8(ndr_push, NDR_SCALARS, info_blob.data,
+                                  info_blob.length);
+
+       if (!NDR_ERR_CODE_IS_SUCCESS(err)) {
+               status = NT_STATUS_INTERNAL_ERROR;
                goto fail;
        }
-       SIVAL(buf, 4, 8 + sid_len); /* SidListLength */
-       SIVAL(buf, 8, 0);          /* StartSidLength */
-       SIVAL(buf, 12, 0);        /* StartSidOffset */
-       SIVAL(buf, 16, 0);        /* NextEntryOffset */
-       SIVAL(buf, 20, sid_len);    /* SidLength */
-       sid_linearize(buf + 24, sid_len, &pqt->sid);
+       inbuf.data = ndr_push->data;
+       inbuf.length = ndr_push->offset;
 
        status = smb2cli_query_info(cli->conn, cli->timeout, cli->smb2.session,
                                    cli->smb2.tcon, 4, /* in_info_type */
@@ -3002,7 +3032,8 @@ NTSTATUS cli_smb2_list_user_quota_step(struct cli_state 
*cli,
        DATA_BLOB outbuf = data_blob_null;
        struct smb2_hnd *ph = NULL;
        TALLOC_CTX *frame = talloc_stackframe();
-       uint8_t *buf;
+       struct smb2_query_quota_info info = {0};
+       enum ndr_err_code err;
 
        if (smbXcli_conn_has_async_calls(cli->conn)) {
                /*
@@ -3022,20 +3053,19 @@ NTSTATUS cli_smb2_list_user_quota_step(struct cli_state 
*cli,
                goto cleanup;
        }
 
-       inbuf = data_blob_talloc_zero(frame, 16);
-       if (inbuf.data == NULL) {
-               status = NT_STATUS_NO_MEMORY;
-               goto cleanup;
-       }
 
-       buf = inbuf.data;
+       info.restart_scan = first ? 1 : 0;
 
-       SCVAL(buf, 0, 0);            /* ReturnSingle */
-       SCVAL(buf, 1, first ? 1 : 0); /* RestartScan */
-       SSVAL(buf, 2, 0);            /* Reserved */
-       SIVAL(buf, 4, 0);            /* SidListLength */
-       SIVAL(buf, 8, 0);            /* StartSidLength */
-       SIVAL(buf, 12, 0);          /* StartSidOffset */
+       err = ndr_push_struct_blob(
+                       &inbuf,
+                       frame,
+                       &info,
+                       (ndr_push_flags_fn_t)ndr_push_smb2_query_quota_info);
+
+       if (!NDR_ERR_CODE_IS_SUCCESS(err)) {
+               status = NT_STATUS_INTERNAL_ERROR;
+               goto cleanup;
+       }
 
        status = smb2cli_query_info(cli->conn, cli->timeout, cli->smb2.session,
                                    cli->smb2.tcon, 4, /* in_info_type */
@@ -3047,6 +3077,14 @@ NTSTATUS cli_smb2_list_user_quota_step(struct cli_state 
*cli,
                                    ph->fid_persistent, ph->fid_volatile, frame,
                                    &outbuf);
 
+       /*
+        * safeguard against panic from calling parse_user_quota_list with
+        * NULL buffer
+        */
+       if (NT_STATUS_IS_OK(status) && outbuf.length == 0) {
+               status = NT_STATUS_NO_MORE_ENTRIES;
+       }
+
        if (!NT_STATUS_IS_OK(status)) {
                goto cleanup;
        }
diff --git a/source3/libsmb/cliquota.c b/source3/libsmb/cliquota.c
index e22ccdd..8efd2bb 100644
--- a/source3/libsmb/cliquota.c
+++ b/source3/libsmb/cliquota.c
@@ -24,6 +24,7 @@
 #include "../libcli/security/security.h"
 #include "trans2.h"
 #include "../libcli/smb/smbXcli_base.h"
+#include "librpc/gen_ndr/ndr_quota.h"
 
 NTSTATUS cli_get_quota_handle(struct cli_state *cli, uint16_t *quota_fnum)
 {
@@ -75,61 +76,39 @@ bool parse_user_quota_record(const uint8_t *rdata,
                             unsigned int *offset,
                             SMB_NTQUOTA_STRUCT *pqt)
 {
-       int sid_len;
-       SMB_NTQUOTA_STRUCT qt;
-
-       ZERO_STRUCT(qt);
-
-       if (!rdata||!offset||!pqt) {
-               smb_panic("parse_quota_record: called with NULL POINTER!");
-       }
-
-       if (rdata_count < 40) {
-               return False;
-       }
+       struct file_quota_information info = {0};
+       TALLOC_CTX *frame = talloc_stackframe();
+       DATA_BLOB blob;
+       enum ndr_err_code err;
+       bool result = false;
 
-       /* offset to next quota record.
-        * 4 bytes IVAL(rdata,0)
-        * unused here...
-        */
-       *offset = IVAL(rdata,0);
-
-       /* sid len */
-       sid_len = IVAL(rdata,4);
-       if (40 + sid_len < 40) {
-               return false;
-       }
-
-       if (rdata_count < 40+sid_len) {
-               return False;           
-       }
+       blob.data = discard_const_p(uint8_t, rdata);
+       blob.length = rdata_count;
+       err = ndr_pull_struct_blob(
+                       &blob,
+                       frame,
+                       &info,
+                       (ndr_pull_flags_fn_t)ndr_pull_file_quota_information);
 
-       if (*offset != 0 && *offset < 40 + sid_len) {
-               return false;
+       if (!NDR_ERR_CODE_IS_SUCCESS(err)) {
+               goto out;
        }
 
-       /* unknown 8 bytes in pdata 
-        * maybe its the change time in NTTIME
-        */
+       *offset = info.next_entry_offset;
 
-       /* the used space 8 bytes (uint64_t)*/
-       qt.usedspace = BVAL(rdata,16);
+       ZERO_STRUCTP(pqt);
+       pqt->usedspace = info.quota_used;
 
-       /* the soft quotas 8 bytes (uint64_t)*/
-       qt.softlim = BVAL(rdata,24);
+       pqt->softlim = info.quota_threshold;
 
-       /* the hard quotas 8 bytes (uint64_t)*/
-       qt.hardlim = BVAL(rdata,32);
-
-       if (!sid_parse(rdata+40,sid_len,&qt.sid)) {
-               return false;
-       }
+       pqt->hardlim = info.quota_limit;
 
-       qt.qtype = SMB_USER_QUOTA_TYPE;
-
-       *pqt = qt;
-
-       return True;
+       pqt->qtype = SMB_USER_QUOTA_TYPE;
+       pqt->sid = info.sid;
+       result = true;
+out:
+       TALLOC_FREE(frame);
+       return result;
 }
 
 NTSTATUS parse_user_quota_list(const uint8_t *curdata,
@@ -217,111 +196,12 @@ NTSTATUS build_user_quota_buffer(SMB_NTQUOTA_LIST 
*qt_list,
                                 DATA_BLOB *outbuf,
                                 SMB_NTQUOTA_LIST **end_ptr)
 {
-       uint32_t qt_len = 0;
-       uint8_t *entry;
-       uint32_t entry_len;
-       int sid_len;
-       SMB_NTQUOTA_LIST *qtl;
-       DATA_BLOB qbuf = data_blob_null;
-       NTSTATUS status = NT_STATUS_UNSUCCESSFUL;
-
-       if (qt_list == NULL) {
-               status = NT_STATUS_OK;
-               *outbuf = data_blob_null;
-               if (end_ptr) {
-                       *end_ptr = NULL;
-               }
-               return NT_STATUS_OK;
-       }
-
-       for (qtl = qt_list; qtl != NULL; qtl = qtl->next) {
-
-               sid_len = ndr_size_dom_sid(&qtl->quotas->sid, 0);
-               if (47 + sid_len < 47) {
-                       status = NT_STATUS_INVALID_PARAMETER;
-                       goto fail;
-               }
-               entry_len = 40 + sid_len;
-               entry_len = ((entry_len + 7) / 8) * 8;
-
-               if (qt_len + entry_len < qt_len) {
-                       status = NT_STATUS_INVALID_PARAMETER;
-                       goto fail;
-               }
-               qt_len += entry_len;
-       }
-
-       if (maxlen > 0 && qt_len > maxlen) {
-               qt_len = maxlen;
-       }
-
-       qbuf = data_blob_talloc_zero(mem_ctx, qt_len);
-       if (qbuf.data == NULL) {
-               status = NT_STATUS_NO_MEMORY;
-               goto fail;
-       }
-
-       for (qt_len = 0, entry = qbuf.data; qt_list != NULL;
-            qt_list = qt_list->next, qt_len += entry_len, entry += entry_len) {
-
-               sid_len = ndr_size_dom_sid(&qt_list->quotas->sid, 0);
-               entry_len = 40 + sid_len;
-               entry_len = ((entry_len + 7) / 8) * 8;
-
-               if (qt_len + entry_len > qbuf.length) {
-                       /* check for not-enough room even for a single
-                        * entry
-                        */
-                       if (qt_len == 0) {
-                               status = NT_STATUS_BUFFER_TOO_SMALL;
-                               goto fail;
-                       }
-
-                       break;
-               }
-
-               /* nextoffset entry 4 bytes */
-               SIVAL(entry, 0, entry_len);
-
-               /* then the len of the SID 4 bytes */
-               SIVAL(entry, 4, sid_len);
-
-               /* NTTIME of last record change */
-               SBIG_UINT(entry, 8, (uint64_t)0);
-
-               /* the used disk space 8 bytes uint64_t */
-               SBIG_UINT(entry, 16, qt_list->quotas->usedspace);
-
-               /* the soft quotas 8 bytes uint64_t */
-               SBIG_UINT(entry, 24, qt_list->quotas->softlim);
-
-               /* the hard quotas 8 bytes uint64_t */
-               SBIG_UINT(entry, 32, qt_list->quotas->hardlim);
-
-               /* and now the SID */
-               sid_linearize((uint8_t *)(entry + 40), sid_len,
-                             &qt_list->quotas->sid);
-       }
-
-       /* overwrite the offset of the last entry */
-       SIVAL(entry - entry_len, 0, 0);
-
-       /*potentially shrink the buffer if max was given
-        * and we haven't quite reached the max
-        */
-       qbuf.length = qt_len;
-       *outbuf = qbuf;
-       qbuf = data_blob_null;
-       status = NT_STATUS_OK;
-
-       if (end_ptr) {
-               *end_ptr = qt_list;
-       }
-
-fail:
-       data_blob_free(&qbuf);
-
-       return status;
+       return fill_quota_buffer(mem_ctx,
+                                qt_list,
+                                false,


-- 
Samba Shared Repository

Reply via email to