Add "maxfilesize" mount option for tmpfs to allow specifying the
maximum file size limit. Default is UINT64_MAX when the option is not specified. It was useless to set the limit to the total amount of memory and swap in the system. Use tmpfs_mem_info() rather than get_swpgtotal() in tmpfs_mount() to check if there is enough memory available. Remove now unused get_swpgtotal(). Reviewed by: Gleb Kurtsou Approved by: trasz (mentor)
This commit is contained in:
parent
992a6ccc1f
commit
dec3772ee4
@ -70,6 +70,8 @@ permissions in octal format.
|
|||||||
maximum number of inodes.
|
maximum number of inodes.
|
||||||
.It Cm size
|
.It Cm size
|
||||||
maximum size (in bytes) for the file system.
|
maximum size (in bytes) for the file system.
|
||||||
|
.It Cm maxfilesize
|
||||||
|
maximum file size (in bytes).
|
||||||
.El
|
.El
|
||||||
.Sh EXAMPLES
|
.Sh EXAMPLES
|
||||||
To mount a
|
To mount a
|
||||||
|
@ -77,62 +77,12 @@ static int tmpfs_statfs(struct mount *, struct statfs *);
|
|||||||
/* --------------------------------------------------------------------- */
|
/* --------------------------------------------------------------------- */
|
||||||
|
|
||||||
static const char *tmpfs_opts[] = {
|
static const char *tmpfs_opts[] = {
|
||||||
"from", "size", "inodes", "uid", "gid", "mode", "export",
|
"from", "size", "maxfilesize", "inodes", "uid", "gid", "mode", "export",
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
|
|
||||||
/* --------------------------------------------------------------------- */
|
/* --------------------------------------------------------------------- */
|
||||||
|
|
||||||
#define SWI_MAXMIB 3
|
|
||||||
|
|
||||||
static u_int
|
|
||||||
get_swpgtotal(void)
|
|
||||||
{
|
|
||||||
struct xswdev xsd;
|
|
||||||
char *sname = "vm.swap_info";
|
|
||||||
int soid[SWI_MAXMIB], oid[2];
|
|
||||||
u_int unswdev, total, dmmax, nswapdev;
|
|
||||||
size_t mibi, len;
|
|
||||||
|
|
||||||
total = 0;
|
|
||||||
|
|
||||||
len = sizeof(dmmax);
|
|
||||||
if (kernel_sysctlbyname(curthread, "vm.dmmax", &dmmax, &len,
|
|
||||||
NULL, 0, NULL, 0) != 0)
|
|
||||||
return total;
|
|
||||||
|
|
||||||
len = sizeof(nswapdev);
|
|
||||||
if (kernel_sysctlbyname(curthread, "vm.nswapdev",
|
|
||||||
&nswapdev, &len,
|
|
||||||
NULL, 0, NULL, 0) != 0)
|
|
||||||
return total;
|
|
||||||
|
|
||||||
mibi = (SWI_MAXMIB - 1) * sizeof(int);
|
|
||||||
oid[0] = 0;
|
|
||||||
oid[1] = 3;
|
|
||||||
|
|
||||||
if (kernel_sysctl(curthread, oid, 2,
|
|
||||||
soid, &mibi, (void *)sname, strlen(sname),
|
|
||||||
NULL, 0) != 0)
|
|
||||||
return total;
|
|
||||||
|
|
||||||
mibi = (SWI_MAXMIB - 1);
|
|
||||||
for (unswdev = 0; unswdev < nswapdev; ++unswdev) {
|
|
||||||
soid[mibi] = unswdev;
|
|
||||||
len = sizeof(struct xswdev);
|
|
||||||
if (kernel_sysctl(curthread,
|
|
||||||
soid, mibi + 1, &xsd, &len, NULL, 0,
|
|
||||||
NULL, 0) != 0)
|
|
||||||
return total;
|
|
||||||
if (len == sizeof(struct xswdev))
|
|
||||||
total += (xsd.xsw_nblks - dmmax);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Not Reached */
|
|
||||||
return total;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* --------------------------------------------------------------------- */
|
|
||||||
static int
|
static int
|
||||||
tmpfs_node_ctor(void *mem, int size, void *arg, int flags)
|
tmpfs_node_ctor(void *mem, int size, void *arg, int flags)
|
||||||
{
|
{
|
||||||
@ -181,12 +131,12 @@ tmpfs_mount(struct mount *mp)
|
|||||||
{
|
{
|
||||||
struct tmpfs_mount *tmp;
|
struct tmpfs_mount *tmp;
|
||||||
struct tmpfs_node *root;
|
struct tmpfs_node *root;
|
||||||
size_t pages, mem_size;
|
size_t pages;
|
||||||
uint32_t nodes;
|
uint32_t nodes;
|
||||||
int error;
|
int error;
|
||||||
/* Size counters. */
|
/* Size counters. */
|
||||||
u_int nodes_max;
|
u_int nodes_max;
|
||||||
u_quad_t size_max;
|
u_quad_t size_max, maxfilesize;
|
||||||
|
|
||||||
/* Root node attributes. */
|
/* Root node attributes. */
|
||||||
uid_t root_uid;
|
uid_t root_uid;
|
||||||
@ -227,12 +177,13 @@ tmpfs_mount(struct mount *mp)
|
|||||||
nodes_max = 0;
|
nodes_max = 0;
|
||||||
if (vfs_scanopt(mp->mnt_optnew, "size", "%qu", &size_max) != 1)
|
if (vfs_scanopt(mp->mnt_optnew, "size", "%qu", &size_max) != 1)
|
||||||
size_max = 0;
|
size_max = 0;
|
||||||
|
if (vfs_scanopt(mp->mnt_optnew, "maxfilesize", "%qu",
|
||||||
|
&maxfilesize) != 1)
|
||||||
|
maxfilesize = 0;
|
||||||
|
|
||||||
/* Do not allow mounts if we do not have enough memory to preserve
|
/* Do not allow mounts if we do not have enough memory to preserve
|
||||||
* the minimum reserved pages. */
|
* the minimum reserved pages. */
|
||||||
mem_size = cnt.v_free_count + cnt.v_inactive_count + get_swpgtotal();
|
if (tmpfs_mem_info() < TMPFS_PAGES_RESERVED)
|
||||||
mem_size -= mem_size > cnt.v_wire_count ? cnt.v_wire_count : mem_size;
|
|
||||||
if (mem_size < TMPFS_PAGES_RESERVED)
|
|
||||||
return ENOSPC;
|
return ENOSPC;
|
||||||
|
|
||||||
/* Get the maximum number of memory pages this file system is
|
/* Get the maximum number of memory pages this file system is
|
||||||
@ -261,7 +212,7 @@ tmpfs_mount(struct mount *mp)
|
|||||||
mtx_init(&tmp->allnode_lock, "tmpfs allnode lock", NULL, MTX_DEF);
|
mtx_init(&tmp->allnode_lock, "tmpfs allnode lock", NULL, MTX_DEF);
|
||||||
tmp->tm_nodes_max = nodes;
|
tmp->tm_nodes_max = nodes;
|
||||||
tmp->tm_nodes_inuse = 0;
|
tmp->tm_nodes_inuse = 0;
|
||||||
tmp->tm_maxfilesize = (u_int64_t)(cnt.v_page_count + get_swpgtotal()) * PAGE_SIZE;
|
tmp->tm_maxfilesize = maxfilesize > 0 ? maxfilesize : UINT64_MAX;
|
||||||
LIST_INIT(&tmp->tm_nodes_used);
|
LIST_INIT(&tmp->tm_nodes_used);
|
||||||
|
|
||||||
tmp->tm_pages_max = pages;
|
tmp->tm_pages_max = pages;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user