Today I've tried to configure multiple filesystem quotas, with some strange results. These are my two filesystems; both using quotas: * /dev/mail mounted to /var/spool/mail using AIX quotas for all users. Mailbox format is 'mbox' and they are named '/var/spool/mail/<logname>' * filer0:/vol/home mounted to /home/f0 via nfs using netapp quotas for all users. Mailboxes are all 'mbox' and located in '~<logname>/Mail' I've configured _two_ quota roots as described here: http://wiki.dovecot.org/Quota/FS?highlight=(two%20filesystems) plugin { quota = fs:Home:mount=/home/f0 quota2 = fs:Spool:mount=/var/spool/mail } This works like a charm, but when testing the configuration, the result was just surprising: * OK [CAPABILITY IMAP4rev1 SASL-IR SORT THREAD=REFERENCES MULTIAPPEND UNSELECT LITERAL+ IDLE CHILDREN NAMESPACE LOGIN-REFERRALS UIDPLUS LIST-EXTENDED I18NLEVEL=1 QUOTA AUTH=PLAIN] Dovecot ready. . login rfttest XXX . OK Logged in. . getquotaroot "INBOX" * QUOTAROOT "INBOX" "Home" "Spool" * QUOTA "Home" (STORAGE 310360 1048576) * QUOTA "Spool" (STORAGE 89708 1000000) . OK Getquotaroot completed. . getquotaroot "Trash" * QUOTAROOT "Trash" "Home" "Spool" * QUOTA "Home" (STORAGE 310360 1048576) * QUOTA "Spool" (STORAGE 89708 1000000) . OK Getquotaroot completed. . logout * BYE Logging out . OK Logout completed. You see, that _always_ both quota roots are reported, whether the references mailbox is actually placed on this filesystem or not. However reading RFC2087 confirms me in the idea, that just the _related_ quota roots should be listed: -------------------------------8<----------------------------------------- 4.3. GETQUOTAROOT Command Arguments: mailbox name Data: untagged responses: QUOTAROOT, QUOTA Result: OK - getquota completed NO - getquota error: no such mailbox, permission denied BAD - command unknown or arguments invalid The GETQUOTAROOT command takes the name of a mailbox and returns the list of quota roots for the mailbox in an untagged QUOTAROOT response. For each listed quota root, it also returns the quota root's resource usage and limits in an untagged QUOTA response. Example: C: A003 GETQUOTAROOT INBOX S: * QUOTAROOT INBOX "" S: * QUOTA "" (STORAGE 10 512) S: A003 OK Getquota completed ------------------------------->8----------------------------------------- So in my opinion correctly reported quota roots should look like this: * OK [CAPABILITY IMAP4rev1 SASL-IR SORT THREAD=REFERENCES MULTIAPPEND UNSELECT LITERAL+ IDLE CHILDREN NAMESPACE LOGIN-REFERRALS UIDPLUS LIST-EXTENDED I18NLEVEL=1 QUOTA AUTH=PLAIN] Dovecot ready. . login rfttest XXX . OK Logged in. . getquotaroot "INBOX" * QUOTAROOT "INBOX" "Spool" * QUOTA "Spool" (STORAGE 89708 1000000) . OK Getquotaroot completed. . getquotaroot "Trash" * QUOTAROOT "Trash" "Home" * QUOTA "Home" (STORAGE 310360 1048576) . OK Getquotaroot completed. . logout * BYE Logging out . OK Logout completed. Now I known what I want... but how to get it :-) While I see no way to use namespaces and/or quota rules to configure this behavior, patching quota.c, quota-fs.c and quota-private.h seems to be an option. A downside of this is, that I've to extend the quota plugin interface (quota_backend_vfuncs) defined in quota-private.h by adding an new callback function. Since all other quota backends don't have this new function, they have to initialize it with NULL. So there are side effects to other quota backends. This is the reason why I want to discuss the above described problem (and solution) before posting my patch :-) Regards, Ralf -- ______________________________________________________________________ Dipl.-Inform. (FH) Ralf Becker Rechenzentrum (r/ft) der FH Trier (Network|Mail|Web|Firewall) University of applied sciences Administrator Schneidershof, D-54293 Trier Mail: beckerr at fh-trier.de Fon: +49 651 8103 499 WWW: http://www.fh-trier.de/~beckerr Fax: +49 651 8103 214 ______________________________________________________________________ -------------- next part -------------- A non-text attachment was scrubbed... Name: smime.p7s Type: application/x-pkcs7-signature Size: 6087 bytes Desc: S/MIME Cryptographic Signature URL: <http://dovecot.org/pipermail/dovecot/attachments/20080708/d0e87c90/attachment-0002.bin>
Hello Stewart,> You have to previously know or have determined: > a) what FS's are under quotaThat's easy in my case, because each filesystem is listed in dovecot.conf: quota = fs:"Spool":mount=/var/spool/mail quota2 = fs:"Home0":mount=/home/f0 quota3 = fs:"Home1":mount=/home/f1 quota4 = fs:"Home2":mount=/home/f2 quota5 = fs:"Home3":mount=/home/f3 ...> AND > b) know which ones the user usesThat should be easy to, because they are listed in mail_location. In my case this is: mail_location = mbox:~/Mail:INBOX=/var/spool/mail/%n> AND > c) then make multiple calls, one for each FS that the user has stuff in >Let take 'quota_transaction_set_limits' as example: If I understand Timo's source code correctly this is done by looping through the mountpoints of all quota roots. But then, and this is a problem, the lowest quota limit is used, because it is not checked, if the mbox file acctually _resides_ in this filesystem. Well... I think what this behavior could be "fixed" in the same way I've used for GETQUOTAROOT: I've just implemented a callback function 'root_match_box' that returns 'true', if a Mailbox resides on the filesystem defined "mount=" in quota definition and 'false' if not. This optional function is used in 'quota_root_iter_next' to filter the list of all quota roots. From the source code: ----------------------8<---------------------------------------------- roots = array_get(&iter->quota->roots, &count); if (iter->i >= count) return NULL; for (; iter->i < count; iter->i++) { if (roots[iter->i]->backend.v.root_match_box != NULL) { if (!roots[iter->i]->backend.v.root_match_box(roots[iter->i], iter->box)) continue; } ... } ---------------------->8---------------------------------------------- The same should be correct in quota_transaction_set_limits, quota_transaction_commit and quota_default_test_alloc But I should have a deeper look at this... :-) BTW: If this behavior is indeed AIX specific, that's no problem, In this case the function should always returning 'true' or just not be included in the list of callback functions. Regards, Ralf -- ______________________________________________________________________ Dipl.-Inform. (FH) Ralf Becker Rechenzentrum (r/ft) der FH Trier (Network|Mail|Web|Firewall) University of applied sciences Administrator Schneidershof, D-54293 Trier Mail: beckerr at fh-trier.de Fon: +49 651 8103 499 WWW: http://www.fh-trier.de/~beckerr Fax: +49 651 8103 214 ______________________________________________________________________ -------------- next part -------------- A non-text attachment was scrubbed... Name: smime.p7s Type: application/x-pkcs7-signature Size: 6087 bytes Desc: S/MIME Cryptographic Signature URL: <http://dovecot.org/pipermail/dovecot/attachments/20080708/4d12181a/attachment-0002.bin>
On Tue, 2008-07-08 at 16:49 +0200, Ralf Becker wrote:> You see, that _always_ both quota roots are reported, whether > the references mailbox is actually placed on this filesystem or not. > > However reading RFC2087 confirms me in the idea, that just the > _related_ quota roots should be listed:Right.> While I see no way to use namespaces and/or quota rules to configure > this behavior, patching quota.c, quota-fs.c and quota-private.h seems > to be an option. > > A downside of this is, that I've to extend the quota plugin interface > (quota_backend_vfuncs) defined in quota-private.h by adding an new > callback function. Since all other quota backends don't have this new > function, they have to initialize it with NULL. So there are side > effects to other quota backends.Right. If you'll write this code I can include it to v1.2 release. -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 197 bytes Desc: This is a digitally signed message part URL: <http://dovecot.org/pipermail/dovecot/attachments/20080712/e3f147d0/attachment-0002.bin>