View | Details | Raw Unified | Return to bug 198863 | Differences between
and this patch

Collapse All | Expand All

(-)sbin/geom/class/eli/geli.8 (-4 / +26 lines)
Lines 24-30 Link Here
24
.\"
24
.\"
25
.\" $FreeBSD$
25
.\" $FreeBSD$
26
.\"
26
.\"
27
.Dd June 18, 2014
27
.Dd March 14, 2015
28
.Dt GELI 8
28
.Dt GELI 8
29
.Os
29
.Os
30
.Sh NAME
30
.Sh NAME
Lines 51-57 Link Here
51
.Pp
51
.Pp
52
.Nm
52
.Nm
53
.Cm init
53
.Cm init
54
.Op Fl bPv
54
.Op Fl bPtv
55
.Op Fl a Ar aalgo
55
.Op Fl a Ar aalgo
56
.Op Fl B Ar backupfile
56
.Op Fl B Ar backupfile
57
.Op Fl e Ar ealgo
57
.Op Fl e Ar ealgo
Lines 80-86 Link Here
80
.Cm detach
80
.Cm detach
81
.Nm
81
.Nm
82
.Cm onetime
82
.Cm onetime
83
.Op Fl d
83
.Op Fl dt
84
.Op Fl a Ar aalgo
84
.Op Fl a Ar aalgo
85
.Op Fl e Ar ealgo
85
.Op Fl e Ar ealgo
86
.Op Fl l Ar keylen
86
.Op Fl l Ar keylen
Lines 88-94 Link Here
88
.Ar prov
88
.Ar prov
89
.Nm
89
.Nm
90
.Cm configure
90
.Cm configure
91
.Op Fl bB
91
.Op Fl bBtT
92
.Ar prov ...
92
.Ar prov ...
93
.Nm
93
.Nm
94
.Cm setkey
94
.Cm setkey
Lines 351-356 Link Here
351
Increasing the sector size allows increased performance,
351
Increasing the sector size allows increased performance,
352
because encryption/decryption which requires an initialization vector
352
because encryption/decryption which requires an initialization vector
353
is done per sector; fewer sectors means less computational work.
353
is done per sector; fewer sectors means less computational work.
354
.It Fl t
355
Pass through
356
.Dv BIO_DELETE
357
calls (i.e., TRIM/UNMAP).
358
This can be useful when encrypting on a SSD, by allowing it to clean up
359
sectors you're no longer using.
360
It will, however, provide some information (how much space is actually
361
used, and which sectors contain real data) to an attacker.
362
The underlying provider may or may not actually obliterate the deleted
363
sectors, so this should not be considered to add any security.
354
.It Fl V Ar version
364
.It Fl V Ar version
355
Metadata version to use.
365
Metadata version to use.
356
This option is helpful when creating a provider that may be used by older
366
This option is helpful when creating a provider that may be used by older
Lines 456-461 Link Here
456
For more information, see the description of the
466
For more information, see the description of the
457
.Cm init
467
.Cm init
458
subcommand.
468
subcommand.
469
.It Fl t
470
Enable TRIM/UNMAP passthru.
471
For more information, see the description of the
472
.Cm init
473
subcommand.
459
.El
474
.El
460
.It Cm configure
475
.It Cm configure
461
Change configuration of the given providers.
476
Change configuration of the given providers.
Lines 469-474 Link Here
469
subcommand.
484
subcommand.
470
.It Fl B
485
.It Fl B
471
Remove the BOOT flag from the given providers.
486
Remove the BOOT flag from the given providers.
487
.It Fl t
488
Enable TRIM/UNMAP passthru.
489
For more information, see the description of the
490
.Cm init
491
subcommand.
492
.It Fl T
493
Disable TRIM/UNMAP passthru.
472
.El
494
.El
473
.It Cm setkey
495
.It Cm setkey
474
Install a copy of the Master Key into the selected slot, encrypted with
496
Install a copy of the Master Key into the selected slot, encrypted with
(-)sbin/geom/class/eli/geom_eli.c (-11 / +55 lines)
Lines 114-123 Link Here
114
		{ 'l', "keylen", "0", G_TYPE_NUMBER },
114
		{ 'l', "keylen", "0", G_TYPE_NUMBER },
115
		{ 'P', "nonewpassphrase", NULL, G_TYPE_BOOL },
115
		{ 'P', "nonewpassphrase", NULL, G_TYPE_BOOL },
116
		{ 's', "sectorsize", "0", G_TYPE_NUMBER },
116
		{ 's', "sectorsize", "0", G_TYPE_NUMBER },
117
		{ 't', "trim", NULL, G_TYPE_BOOL },
117
		{ 'V', "mdversion", "-1", G_TYPE_NUMBER },
118
		{ 'V', "mdversion", "-1", G_TYPE_NUMBER },
118
		G_OPT_SENTINEL
119
		G_OPT_SENTINEL
119
	    },
120
	    },
120
	    "[-bPv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-s sectorsize] [-V version] prov"
121
	    "[-bPtv] [-a aalgo] [-B backupfile] [-e ealgo] [-i iterations] [-l keylen] [-J newpassfile] [-K newkeyfile] [-s sectorsize] [-V version] prov"
121
	},
122
	},
122
	{ "label", G_FLAG_VERBOSE, eli_main,
123
	{ "label", G_FLAG_VERBOSE, eli_main,
123
	    {
124
	    {
Lines 170-186 Link Here
170
		{ 'e', "ealgo", GELI_ENC_ALGO, G_TYPE_STRING },
171
		{ 'e', "ealgo", GELI_ENC_ALGO, G_TYPE_STRING },
171
		{ 'l', "keylen", "0", G_TYPE_NUMBER },
172
		{ 'l', "keylen", "0", G_TYPE_NUMBER },
172
		{ 's', "sectorsize", "0", G_TYPE_NUMBER },
173
		{ 's', "sectorsize", "0", G_TYPE_NUMBER },
174
		{ 't', "trim", NULL, G_TYPE_BOOL },
173
		G_OPT_SENTINEL
175
		G_OPT_SENTINEL
174
	    },
176
	    },
175
	    "[-d] [-a aalgo] [-e ealgo] [-l keylen] [-s sectorsize] prov"
177
	    "[-dt] [-a aalgo] [-e ealgo] [-l keylen] [-s sectorsize] prov"
176
	},
178
	},
177
	{ "configure", G_FLAG_VERBOSE, eli_main,
179
	{ "configure", G_FLAG_VERBOSE, eli_main,
178
	    {
180
	    {
179
		{ 'b', "boot", NULL, G_TYPE_BOOL },
181
		{ 'b', "boot", NULL, G_TYPE_BOOL },
180
		{ 'B', "noboot", NULL, G_TYPE_BOOL },
182
		{ 'B', "noboot", NULL, G_TYPE_BOOL },
183
		{ 't', "trim", NULL, G_TYPE_BOOL },
184
		{ 'T', "notrim", NULL, G_TYPE_BOOL },
181
		G_OPT_SENTINEL
185
		G_OPT_SENTINEL
182
	    },
186
	    },
183
	    "[-bB] prov ..."
187
	    "[-bBtT] prov ..."
184
	},
188
	},
185
	{ "setkey", G_FLAG_VERBOSE, eli_main,
189
	{ "setkey", G_FLAG_VERBOSE, eli_main,
186
	    {
190
	    {
Lines 698-703 Link Here
698
	md.md_flags = 0;
702
	md.md_flags = 0;
699
	if (gctl_get_int(req, "boot"))
703
	if (gctl_get_int(req, "boot"))
700
		md.md_flags |= G_ELI_FLAG_BOOT;
704
		md.md_flags |= G_ELI_FLAG_BOOT;
705
	if (gctl_get_int(req, "trim"))
706
		md.md_flags |= G_ELI_FLAG_DELETE;
701
	md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1;
707
	md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1;
702
	str = gctl_get_ascii(req, "aalgo");
708
	str = gctl_get_ascii(req, "aalgo");
703
	if (*str != '\0') {
709
	if (*str != '\0') {
Lines 899-924 Link Here
899
}
905
}
900
906
901
static void
907
static void
902
eli_configure_detached(struct gctl_req *req, const char *prov, bool boot)
908
eli_configure_detached(struct gctl_req *req, const char *prov, int boot,
909
 int trim)
903
{
910
{
904
	struct g_eli_metadata md;
911
	struct g_eli_metadata md;
912
	bool changed = 0;
905
913
906
	if (eli_metadata_read(req, prov, &md) == -1)
914
	if (eli_metadata_read(req, prov, &md) == -1)
907
		return;
915
		return;
908
916
909
	if (boot && (md.md_flags & G_ELI_FLAG_BOOT)) {
917
	if (boot == 1 && (md.md_flags & G_ELI_FLAG_BOOT)) {
910
		if (verbose)
918
		if (verbose)
911
			printf("BOOT flag already configured for %s.\n", prov);
919
			printf("BOOT flag already configured for %s.\n", prov);
912
	} else if (!boot && !(md.md_flags & G_ELI_FLAG_BOOT)) {
920
	} else if (boot == 0 && !(md.md_flags & G_ELI_FLAG_BOOT)) {
913
		if (verbose)
921
		if (verbose)
914
			printf("BOOT flag not configured for %s.\n", prov);
922
			printf("BOOT flag not configured for %s.\n", prov);
915
	} else {
923
	} else if (boot >= 0) {
916
		if (boot)
924
		if (boot)
917
			md.md_flags |= G_ELI_FLAG_BOOT;
925
			md.md_flags |= G_ELI_FLAG_BOOT;
918
		else
926
		else
919
			md.md_flags &= ~G_ELI_FLAG_BOOT;
927
			md.md_flags &= ~G_ELI_FLAG_BOOT;
928
		changed = 1;
929
	}
930
931
	if (trim == 1 && (md.md_flags & G_ELI_FLAG_DELETE)) {
932
		if (verbose)
933
			printf("TRIM flag already configured for %s.\n", prov);
934
	} else if (trim == 0 && !(md.md_flags & G_ELI_FLAG_DELETE)) {
935
		if (verbose)
936
			printf("TRIM flag not configured for %s.\n", prov);
937
	} else if (trim >= 0) {
938
		if (trim)
939
			md.md_flags |= G_ELI_FLAG_DELETE;
940
		else
941
			md.md_flags &= ~G_ELI_FLAG_DELETE;
942
		changed = 1;
943
	}
944
945
	if (changed)
920
		eli_metadata_store(req, prov, &md);
946
		eli_metadata_store(req, prov, &md);
921
	}
922
	bzero(&md, sizeof(md));
947
	bzero(&md, sizeof(md));
923
}
948
}
924
949
Lines 926-932 Link Here
926
eli_configure(struct gctl_req *req)
951
eli_configure(struct gctl_req *req)
927
{
952
{
928
	const char *prov;
953
	const char *prov;
929
	bool boot, noboot;
954
	bool boot, noboot, trim, notrim;
955
	int doboot, dotrim;
930
	int i, nargs;
956
	int i, nargs;
931
957
932
	nargs = gctl_get_int(req, "nargs");
958
	nargs = gctl_get_int(req, "nargs");
Lines 937-948 Link Here
937
963
938
	boot = gctl_get_int(req, "boot");
964
	boot = gctl_get_int(req, "boot");
939
	noboot = gctl_get_int(req, "noboot");
965
	noboot = gctl_get_int(req, "noboot");
966
	trim = gctl_get_int(req, "trim");
967
	notrim = gctl_get_int(req, "notrim");
940
968
969
	doboot = -1;
941
	if (boot && noboot) {
970
	if (boot && noboot) {
942
		gctl_error(req, "Options -b and -B are mutually exclusive.");
971
		gctl_error(req, "Options -b and -B are mutually exclusive.");
943
		return;
972
		return;
944
	}
973
	}
945
	if (!boot && !noboot) {
974
	if (boot)
975
		doboot = 1;
976
	else if (noboot)
977
		doboot = 0;
978
979
	dotrim = -1;
980
	if (trim && notrim) {
981
		gctl_error(req, "Options -t and -T are mutually exclusive.");
982
		return;
983
	}
984
	if (trim)
985
		dotrim = 1;
986
	else if (notrim)
987
		dotrim = 0;
988
989
	if (doboot == -1 && dotrim == -1) {
946
		gctl_error(req, "No option given.");
990
		gctl_error(req, "No option given.");
947
		return;
991
		return;
948
	}
992
	}
Lines 953-959 Link Here
953
	for (i = 0; i < nargs; i++) {
997
	for (i = 0; i < nargs; i++) {
954
		prov = gctl_get_ascii(req, "arg%d", i);
998
		prov = gctl_get_ascii(req, "arg%d", i);
955
		if (!eli_is_attached(prov))
999
		if (!eli_is_attached(prov))
956
			eli_configure_detached(req, prov, boot);
1000
			eli_configure_detached(req, prov, doboot, dotrim);
957
	}
1001
	}
958
}
1002
}
959
1003
(-)sys/geom/eli/g_eli.c (-3 / +10 lines)
Lines 312-321 Link Here
312
		break;
312
		break;
313
	case BIO_DELETE:
313
	case BIO_DELETE:
314
		/*
314
		/*
315
		 * We could eventually support BIO_DELETE request.
315
		 * If the user has set the DELETE flag, we just pass it
316
		 * It could be done by overwritting requested sector with
316
		 * down the stack and let the layers beneath us do (or
317
		 * random data g_eli_overwrites number of times.
317
		 * not) whatever they do with it.  Else we currently just
318
		 * reject it.  A possible extension would be to take it
319
		 * as a hint to shred the data with [multiple?]
320
		 * overwrites.
318
		 */
321
		 */
322
		if (sc->sc_flags & G_ELI_FLAG_DELETE)
323
			break;
319
	default:
324
	default:
320
		g_io_deliver(bp, EOPNOTSUPP);
325
		g_io_deliver(bp, EOPNOTSUPP);
321
		return;
326
		return;
Lines 342-347 Link Here
342
		break;
347
		break;
343
	case BIO_GETATTR:
348
	case BIO_GETATTR:
344
	case BIO_FLUSH:
349
	case BIO_FLUSH:
350
	case BIO_DELETE:
345
		cbp->bio_done = g_std_done;
351
		cbp->bio_done = g_std_done;
346
		cp = LIST_FIRST(&sc->sc_geom->consumer);
352
		cp = LIST_FIRST(&sc->sc_geom->consumer);
347
		cbp->bio_to = cp->provider;
353
		cbp->bio_to = cp->provider;
Lines 1245-1250 Link Here
1245
		ADD_FLAG(G_ELI_FLAG_WOPEN, "W-OPEN");
1251
		ADD_FLAG(G_ELI_FLAG_WOPEN, "W-OPEN");
1246
		ADD_FLAG(G_ELI_FLAG_DESTROY, "DESTROY");
1252
		ADD_FLAG(G_ELI_FLAG_DESTROY, "DESTROY");
1247
		ADD_FLAG(G_ELI_FLAG_RO, "READ-ONLY");
1253
		ADD_FLAG(G_ELI_FLAG_RO, "READ-ONLY");
1254
		ADD_FLAG(G_ELI_FLAG_DELETE, "DELETE");
1248
#undef  ADD_FLAG
1255
#undef  ADD_FLAG
1249
	}
1256
	}
1250
	sbuf_printf(sb, "</Flags>\n");
1257
	sbuf_printf(sb, "</Flags>\n");
(-)sys/geom/eli/g_eli.h (+2 lines)
Lines 94-99 Link Here
94
#define	G_ELI_FLAG_AUTH			0x00000010
94
#define	G_ELI_FLAG_AUTH			0x00000010
95
/* Provider is read-only, we should deny all write attempts. */
95
/* Provider is read-only, we should deny all write attempts. */
96
#define	G_ELI_FLAG_RO			0x00000020
96
#define	G_ELI_FLAG_RO			0x00000020
97
/* Pass through BIO_DELETE requests. */
98
#define	G_ELI_FLAG_DELETE		0x00000040
97
/* RUNTIME FLAGS. */
99
/* RUNTIME FLAGS. */
98
/* Provider was open for writing. */
100
/* Provider was open for writing. */
99
#define	G_ELI_FLAG_WOPEN		0x00010000
101
#define	G_ELI_FLAG_WOPEN		0x00010000
(-)sys/geom/eli/g_eli_ctl.c (-32 / +80 lines)
Lines 236-242 Link Here
236
	const char *name;
236
	const char *name;
237
	intmax_t *keylen, *sectorsize;
237
	intmax_t *keylen, *sectorsize;
238
	u_char mkey[G_ELI_DATAIVKEYLEN];
238
	u_char mkey[G_ELI_DATAIVKEYLEN];
239
	int *nargs, *detach;
239
	int *nargs, *detach, *trim;
240
240
241
	g_topology_assert();
241
	g_topology_assert();
242
	bzero(&md, sizeof(md));
242
	bzero(&md, sizeof(md));
Lines 251-267 Link Here
251
		return;
251
		return;
252
	}
252
	}
253
253
254
	detach = gctl_get_paraml(req, "detach", sizeof(*detach));
255
	if (detach == NULL) {
256
		gctl_error(req, "No '%s' argument.", "detach");
257
		return;
258
	}
259
260
	strlcpy(md.md_magic, G_ELI_MAGIC, sizeof(md.md_magic));
254
	strlcpy(md.md_magic, G_ELI_MAGIC, sizeof(md.md_magic));
261
	md.md_version = G_ELI_VERSION;
255
	md.md_version = G_ELI_VERSION;
262
	md.md_flags |= G_ELI_FLAG_ONETIME;
256
	md.md_flags |= G_ELI_FLAG_ONETIME;
263
	if (*detach)
257
258
	detach = gctl_get_paraml(req, "detach", sizeof(*detach));
259
	if (detach != NULL && *detach)
264
		md.md_flags |= G_ELI_FLAG_WO_DETACH;
260
		md.md_flags |= G_ELI_FLAG_WO_DETACH;
261
	trim = gctl_get_paraml(req, "trim", sizeof(*trim));
262
	if (trim != NULL && *trim)
263
		md.md_flags |= G_ELI_FLAG_DELETE;
265
264
266
	md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1;
265
	md.md_ealgo = CRYPTO_ALGORITHM_MIN - 1;
267
	name = gctl_get_asciiparam(req, "aalgo");
266
	name = gctl_get_asciiparam(req, "aalgo");
Lines 377-388 Link Here
377
	char param[16];
376
	char param[16];
378
	const char *prov;
377
	const char *prov;
379
	u_char *sector;
378
	u_char *sector;
380
	int *nargs, *boot, *noboot;
379
	int *nargs, *boot, *noboot, *trim, *notrim;
381
	int error;
380
	int zero, error, changed;
382
	u_int i;
381
	u_int i;
383
382
384
	g_topology_assert();
383
	g_topology_assert();
385
384
385
	changed = 0;
386
	zero = 0;
387
386
	nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs));
388
	nargs = gctl_get_paraml(req, "nargs", sizeof(*nargs));
387
	if (nargs == NULL) {
389
	if (nargs == NULL) {
388
		gctl_error(req, "No '%s' argument.", "nargs");
390
		gctl_error(req, "No '%s' argument.", "nargs");
Lines 394-413 Link Here
394
	}
396
	}
395
397
396
	boot = gctl_get_paraml(req, "boot", sizeof(*boot));
398
	boot = gctl_get_paraml(req, "boot", sizeof(*boot));
397
	if (boot == NULL) {
399
	if (boot == NULL)
398
		gctl_error(req, "No '%s' argument.", "boot");
400
		boot = &zero;
399
		return;
400
	}
401
	noboot = gctl_get_paraml(req, "noboot", sizeof(*noboot));
401
	noboot = gctl_get_paraml(req, "noboot", sizeof(*noboot));
402
	if (noboot == NULL) {
402
	if (noboot == NULL)
403
		gctl_error(req, "No '%s' argument.", "noboot");
403
		noboot = &zero;
404
		return;
405
	}
406
	if (*boot && *noboot) {
404
	if (*boot && *noboot) {
407
		gctl_error(req, "Options -b and -B are mutually exclusive.");
405
		gctl_error(req, "Options -b and -B are mutually exclusive.");
408
		return;
406
		return;
409
	}
407
	}
410
	if (!*boot && !*noboot) {
408
	if (*boot || *noboot)
409
		changed = 1;
410
411
	trim = gctl_get_paraml(req, "trim", sizeof(*trim));
412
	if (trim == NULL)
413
		trim = &zero;
414
	notrim = gctl_get_paraml(req, "notrim", sizeof(*notrim));
415
	if (notrim == NULL)
416
		notrim = &zero;
417
	if (*trim && *notrim) {
418
		gctl_error(req, "Options -t and -T are mutually exclusive.");
419
		return;
420
	}
421
	if (*trim || *notrim)
422
		changed = 1;
423
424
	if (!changed) {
411
		gctl_error(req, "No option given.");
425
		gctl_error(req, "No option given.");
412
		return;
426
		return;
413
	}
427
	}
Lines 429-466 Link Here
429
			    "provider %s.", prov);
443
			    "provider %s.", prov);
430
			continue;
444
			continue;
431
		}
445
		}
446
		if (sc->sc_flags & G_ELI_FLAG_RO) {
447
			gctl_error(req, "Cannot change configuration of "
448
			    "read-only provider %s.", prov);
449
			continue;
450
		}
451
432
		if (*boot && (sc->sc_flags & G_ELI_FLAG_BOOT)) {
452
		if (*boot && (sc->sc_flags & G_ELI_FLAG_BOOT)) {
433
			G_ELI_DEBUG(1, "BOOT flag already configured for %s.",
453
			G_ELI_DEBUG(1, "BOOT flag already configured for %s.",
434
			    prov);
454
			    prov);
435
			continue;
455
			continue;
436
		} else if (!*boot && !(sc->sc_flags & G_ELI_FLAG_BOOT)) {
456
		} else if (*noboot && !(sc->sc_flags & G_ELI_FLAG_BOOT)) {
437
			G_ELI_DEBUG(1, "BOOT flag not configured for %s.",
457
			G_ELI_DEBUG(1, "BOOT flag not configured for %s.",
438
			    prov);
458
			    prov);
439
			continue;
459
			continue;
440
		}
460
		}
441
		if (sc->sc_flags & G_ELI_FLAG_RO) {
461
442
			gctl_error(req, "Cannot change configuration of "
462
		if (*trim && (sc->sc_flags & G_ELI_FLAG_DELETE)) {
443
			    "read-only provider %s.", prov);
463
			G_ELI_DEBUG(1, "TRIM flag already configured for %s.",
464
			    prov);
444
			continue;
465
			continue;
445
		}
466
		} else if (*notrim && !(sc->sc_flags & G_ELI_FLAG_DELETE)) {
446
		cp = LIST_FIRST(&sc->sc_geom->consumer);
467
			G_ELI_DEBUG(1, "TRIM flag not configured for %s.",
447
		pp = cp->provider;
468
			    prov);
448
		error = g_eli_read_metadata(mp, pp, &md);
449
		if (error != 0) {
450
			gctl_error(req,
451
			    "Cannot read metadata from %s (error=%d).",
452
			    prov, error);
453
			continue;
469
			continue;
454
		}
470
		}
455
471
472
		if (!(sc->sc_flags & G_ELI_FLAG_ONETIME)) {
473
			/*
474
			 * ONETIME providers don't write metadata to
475
			 * disk, so don't try reading it.  This means
476
			 * we're bit-flipping uninitialized memory in md
477
			 * below, but that's OK; we don't do anything
478
			 * with it later.
479
			 */
480
			cp = LIST_FIRST(&sc->sc_geom->consumer);
481
			pp = cp->provider;
482
			error = g_eli_read_metadata(mp, pp, &md);
483
			if (error != 0) {
484
			    gctl_error(req,
485
				"Cannot read metadata from %s (error=%d).",
486
				prov, error);
487
			    continue;
488
			}
489
		}
490
456
		if (*boot) {
491
		if (*boot) {
457
			md.md_flags |= G_ELI_FLAG_BOOT;
492
			md.md_flags |= G_ELI_FLAG_BOOT;
458
			sc->sc_flags |= G_ELI_FLAG_BOOT;
493
			sc->sc_flags |= G_ELI_FLAG_BOOT;
459
		} else {
494
		} else if (*noboot) {
460
			md.md_flags &= ~G_ELI_FLAG_BOOT;
495
			md.md_flags &= ~G_ELI_FLAG_BOOT;
461
			sc->sc_flags &= ~G_ELI_FLAG_BOOT;
496
			sc->sc_flags &= ~G_ELI_FLAG_BOOT;
462
		}
497
		}
463
498
499
		if (*trim) {
500
			md.md_flags |= G_ELI_FLAG_DELETE;
501
			sc->sc_flags |= G_ELI_FLAG_DELETE;
502
		} else if (*notrim) {
503
			md.md_flags &= ~G_ELI_FLAG_DELETE;
504
			sc->sc_flags &= ~G_ELI_FLAG_DELETE;
505
		}
506
507
		if (sc->sc_flags & G_ELI_FLAG_ONETIME) {
508
			/* There's no metadata on disk so we are done here. */
509
			continue;
510
		}
511
464
		sector = malloc(pp->sectorsize, M_ELI, M_WAITOK | M_ZERO);
512
		sector = malloc(pp->sectorsize, M_ELI, M_WAITOK | M_ZERO);
465
		eli_metadata_encode(&md, sector);
513
		eli_metadata_encode(&md, sector);
466
		error = g_write_data(cp, pp->mediasize - pp->sectorsize, sector,
514
		error = g_write_data(cp, pp->mediasize - pp->sectorsize, sector,

Return to bug 198863