aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatt Whitlock <busybox@mattwhitlock.name>2014-03-22 19:21:01 -0400
committerDenys Vlasenko <vda.linux@googlemail.com>2014-03-23 18:36:23 +0100
commit0a53b203f9e7157136c8ab4e8753008a63a56660 (patch)
treec99d5a423ba2e598b9ac19aca39f90dc59cad088
parentb9bbd4ddf622bc365726af4f2424210762e74b32 (diff)
downloadbusybox-w32-0a53b203f9e7157136c8ab4e8753008a63a56660.tar.gz
busybox-w32-0a53b203f9e7157136c8ab4e8753008a63a56660.tar.bz2
busybox-w32-0a53b203f9e7157136c8ab4e8753008a63a56660.zip
add discard option -d to swapon
Signed-off-by: Matt Whitlock <busybox@mattwhitlock.name> Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--util-linux/Config.src9
-rw-r--r--util-linux/swaponoff.c85
2 files changed, 85 insertions, 9 deletions
diff --git a/util-linux/Config.src b/util-linux/Config.src
index 5a8b0063b..c1cd6daa4 100644
--- a/util-linux/Config.src
+++ b/util-linux/Config.src
@@ -599,6 +599,15 @@ config SWAPONOFF
599 space. If you are not using any swap space, you can leave this 599 space. If you are not using any swap space, you can leave this
600 option disabled. 600 option disabled.
601 601
602config FEATURE_SWAPON_DISCARD
603 bool "Support discard option -d"
604 default y
605 depends on SWAPONOFF
606 help
607 Enable support for discarding swap area blocks at swapon and/or as
608 the kernel frees them. This option enables both the -d option on
609 'swapon' and the 'discard' option for swap entries in /etc/fstab.
610
602config FEATURE_SWAPON_PRI 611config FEATURE_SWAPON_PRI
603 bool "Support priority option -p" 612 bool "Support priority option -p"
604 default y 613 default y
diff --git a/util-linux/swaponoff.c b/util-linux/swaponoff.c
index d5bfe1888..a7ad6db79 100644
--- a/util-linux/swaponoff.c
+++ b/util-linux/swaponoff.c
@@ -8,10 +8,14 @@
8 */ 8 */
9 9
10//usage:#define swapon_trivial_usage 10//usage:#define swapon_trivial_usage
11//usage: "[-a]" IF_FEATURE_SWAPON_PRI(" [-p PRI]") " [DEVICE]" 11//usage: "[-a]" IF_FEATURE_SWAPON_DISCARD(" [-d[POL]]") IF_FEATURE_SWAPON_PRI(" [-p PRI]") " [DEVICE]"
12//usage:#define swapon_full_usage "\n\n" 12//usage:#define swapon_full_usage "\n\n"
13//usage: "Start swapping on DEVICE\n" 13//usage: "Start swapping on DEVICE\n"
14//usage: "\n -a Start swapping on all swap devices" 14//usage: "\n -a Start swapping on all swap devices"
15//usage: IF_FEATURE_SWAPON_DISCARD(
16//usage: "\n -d[POL] Discard blocks at swapon (POL=once),"
17//usage: "\n as freed (POL=pages), or both (POL omitted)"
18//usage: )
15//usage: IF_FEATURE_SWAPON_PRI( 19//usage: IF_FEATURE_SWAPON_PRI(
16//usage: "\n -p PRI Set swap device priority" 20//usage: "\n -p PRI Set swap device priority"
17//usage: ) 21//usage: )
@@ -38,7 +42,22 @@
38# define MNTTYPE_SWAP "swap" 42# define MNTTYPE_SWAP "swap"
39#endif 43#endif
40 44
41#if ENABLE_FEATURE_SWAPON_PRI 45#if ENABLE_FEATURE_SWAPON_DISCARD
46#ifndef SWAP_FLAG_DISCARD
47#define SWAP_FLAG_DISCARD 0x10000
48#endif
49#ifndef SWAP_FLAG_DISCARD_ONCE
50#define SWAP_FLAG_DISCARD_ONCE 0x20000
51#endif
52#ifndef SWAP_FLAG_DISCARD_PAGES
53#define SWAP_FLAG_DISCARD_PAGES 0x40000
54#endif
55#define SWAP_FLAG_DISCARD_MASK \
56 (SWAP_FLAG_DISCARD | SWAP_FLAG_DISCARD_ONCE | SWAP_FLAG_DISCARD_PAGES)
57#endif
58
59
60#if ENABLE_FEATURE_SWAPON_DISCARD || ENABLE_FEATURE_SWAPON_PRI
42struct globals { 61struct globals {
43 int flags; 62 int flags;
44} FIX_ALIASING; 63} FIX_ALIASING;
@@ -98,9 +117,23 @@ static int do_em_all(void)
98 if (applet_name[5] != 'n' 117 if (applet_name[5] != 'n'
99 || hasmntopt(m, MNTOPT_NOAUTO) == NULL 118 || hasmntopt(m, MNTOPT_NOAUTO) == NULL
100 ) { 119 ) {
101#if ENABLE_FEATURE_SWAPON_PRI 120#if ENABLE_FEATURE_SWAPON_DISCARD || ENABLE_FEATURE_SWAPON_PRI
102 char *p; 121 char *p;
103 g_flags = cl_flags; /* each swap space might have different flags */ 122 g_flags = cl_flags; /* each swap space might have different flags */
123#if ENABLE_FEATURE_SWAPON_DISCARD
124 p = hasmntopt(m, "discard");
125 if (p) {
126 if (p[7] == '=') {
127 if (strncmp(p + 8, "once", 4) == 0 && (p[12] == ',' || p[12] == '\0'))
128 g_flags = (g_flags & ~SWAP_FLAG_DISCARD_MASK) | SWAP_FLAG_DISCARD | SWAP_FLAG_DISCARD_ONCE;
129 else if (strncmp(p + 8, "pages", 5) == 0 && (p[13] == ',' || p[13] == '\0'))
130 g_flags = (g_flags & ~SWAP_FLAG_DISCARD_MASK) | SWAP_FLAG_DISCARD | SWAP_FLAG_DISCARD_PAGES;
131 }
132 else if (p[7] == ',' || p[7] == '\0')
133 g_flags = (g_flags & ~SWAP_FLAG_DISCARD_MASK) | SWAP_FLAG_DISCARD;
134 }
135#endif
136#if ENABLE_FEATURE_SWAPON_PRI
104 p = hasmntopt(m, "pri"); 137 p = hasmntopt(m, "pri");
105 if (p) { 138 if (p) {
106 /* Max allowed 32767 (== SWAP_FLAG_PRIO_MASK) */ 139 /* Max allowed 32767 (== SWAP_FLAG_PRIO_MASK) */
@@ -112,6 +145,7 @@ static int do_em_all(void)
112 } 145 }
113 } 146 }
114#endif 147#endif
148#endif
115 err += swap_enable_disable(m->mnt_fsname); 149 err += swap_enable_disable(m->mnt_fsname);
116 } 150 }
117 } 151 }
@@ -127,24 +161,57 @@ int swap_on_off_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
127int swap_on_off_main(int argc UNUSED_PARAM, char **argv) 161int swap_on_off_main(int argc UNUSED_PARAM, char **argv)
128{ 162{
129 int ret; 163 int ret;
164#if ENABLE_FEATURE_SWAPON_DISCARD
165 char *discard = NULL;
166#endif
130#if ENABLE_FEATURE_SWAPON_PRI 167#if ENABLE_FEATURE_SWAPON_PRI
131 unsigned prio; 168 unsigned prio;
132#endif 169#endif
133 170
134 INIT_G(); 171 INIT_G();
135 172
136#if !ENABLE_FEATURE_SWAPON_PRI 173#if !ENABLE_FEATURE_SWAPON_DISCARD && !ENABLE_FEATURE_SWAPON_PRI
137 ret = getopt32(argv, "a"); 174 ret = getopt32(argv, "a");
138#else 175#else
176#if ENABLE_FEATURE_SWAPON_PRI
139 if (applet_name[5] == 'n') 177 if (applet_name[5] == 'n')
140 opt_complementary = "p+"; 178 opt_complementary = "p+";
141 ret = getopt32(argv, (applet_name[5] == 'n') ? "ap:" : "a", &prio); 179#endif
180 ret = getopt32(argv, (applet_name[5] == 'n') ?
181#if ENABLE_FEATURE_SWAPON_DISCARD
182 "d::"
183#endif
184#if ENABLE_FEATURE_SWAPON_PRI
185 "p:"
186#endif
187 "a" : "a"
188#if ENABLE_FEATURE_SWAPON_DISCARD
189 , &discard
190#endif
191#if ENABLE_FEATURE_SWAPON_PRI
192 , &prio
193#endif
194 );
195#endif
142 196
143 if (ret & 2) { // -p 197#if ENABLE_FEATURE_SWAPON_DISCARD
144 g_flags = SWAP_FLAG_PREFER | 198 if (ret & 1) { // -d
145 MIN(prio, SWAP_FLAG_PRIO_MASK); 199 if (!discard)
146 ret &= 1; 200 g_flags |= SWAP_FLAG_DISCARD;
201 else if (strcmp(discard, "once") == 0)
202 g_flags |= SWAP_FLAG_DISCARD | SWAP_FLAG_DISCARD_ONCE;
203 else if (strcmp(discard, "pages") == 0)
204 g_flags |= SWAP_FLAG_DISCARD | SWAP_FLAG_DISCARD_PAGES;
205 else
206 bb_show_usage();
147 } 207 }
208 ret >>= 1;
209#endif
210#if ENABLE_FEATURE_SWAPON_PRI
211 if (ret & 1) // -p
212 g_flags |= SWAP_FLAG_PREFER |
213 MIN(prio, SWAP_FLAG_PRIO_MASK);
214 ret >>= 1;
148#endif 215#endif
149 216
150 if (ret /* & 1: not needed */) // -a 217 if (ret /* & 1: not needed */) // -a