Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/sys/contrib/openzfs/lib/libzfs/libzfs_sendrecv.c
108769 views
1
// SPDX-License-Identifier: CDDL-1.0
2
/*
3
* CDDL HEADER START
4
*
5
* The contents of this file are subject to the terms of the
6
* Common Development and Distribution License (the "License").
7
* You may not use this file except in compliance with the License.
8
*
9
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10
* or https://opensource.org/licenses/CDDL-1.0.
11
* See the License for the specific language governing permissions
12
* and limitations under the License.
13
*
14
* When distributing Covered Code, include this CDDL HEADER in each
15
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16
* If applicable, add the following below this CDDL HEADER, with the
17
* fields enclosed by brackets "[]" replaced with your own identifying
18
* information: Portions Copyright [yyyy] [name of copyright owner]
19
*
20
* CDDL HEADER END
21
*/
22
23
/*
24
* Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
25
* Copyright (c) 2011, 2020 by Delphix. All rights reserved.
26
* Copyright (c) 2012, Joyent, Inc. All rights reserved.
27
* Copyright (c) 2012 Pawel Jakub Dawidek <[email protected]>.
28
* All rights reserved
29
* Copyright (c) 2013 Steven Hartland. All rights reserved.
30
* Copyright 2015, OmniTI Computer Consulting, Inc. All rights reserved.
31
* Copyright 2016 Igor Kozhukhov <[email protected]>
32
* Copyright (c) 2018, loli10K <[email protected]>. All rights reserved.
33
* Copyright (c) 2019 Datto Inc.
34
* Copyright (c) 2024, Klara, Inc.
35
*/
36
37
#include <assert.h>
38
#include <ctype.h>
39
#include <errno.h>
40
#include <libintl.h>
41
#include <stdio.h>
42
#include <stdlib.h>
43
#include <string.h>
44
#include <unistd.h>
45
#include <stddef.h>
46
#include <fcntl.h>
47
#include <sys/mount.h>
48
#include <sys/mntent.h>
49
#include <sys/mnttab.h>
50
#include <sys/avl.h>
51
#include <sys/debug.h>
52
#include <sys/stat.h>
53
#include <pthread.h>
54
#include <umem.h>
55
#include <time.h>
56
57
#include <libzfs.h>
58
#include <libzfs_core.h>
59
#include <libzutil.h>
60
61
#include "zfs_namecheck.h"
62
#include "zfs_prop.h"
63
#include "zfs_fletcher.h"
64
#include "libzfs_impl.h"
65
#include <cityhash.h>
66
#include <zlib.h>
67
#include <sys/zio_checksum.h>
68
#include <sys/dsl_crypt.h>
69
#include <sys/ddt.h>
70
#include <sys/socket.h>
71
#include <sys/sha2.h>
72
73
static int zfs_receive_impl(libzfs_handle_t *, const char *, const char *,
74
recvflags_t *, int, const char *, nvlist_t *, avl_tree_t *, char **,
75
const char *, nvlist_t *);
76
static int guid_to_name_redact_snaps(libzfs_handle_t *hdl, const char *parent,
77
uint64_t guid, boolean_t bookmark_ok, uint64_t *redact_snap_guids,
78
uint64_t num_redact_snaps, char *name);
79
static int guid_to_name(libzfs_handle_t *, const char *,
80
uint64_t, boolean_t, char *);
81
82
typedef struct progress_arg {
83
zfs_handle_t *pa_zhp;
84
int pa_fd;
85
boolean_t pa_parsable;
86
boolean_t pa_estimate;
87
int pa_verbosity;
88
boolean_t pa_astitle;
89
boolean_t pa_progress;
90
uint64_t pa_size;
91
} progress_arg_t;
92
93
static int
94
dump_record(dmu_replay_record_t *drr, void *payload, size_t payload_len,
95
zio_cksum_t *zc, int outfd)
96
{
97
ASSERT3U(offsetof(dmu_replay_record_t, drr_u.drr_checksum.drr_checksum),
98
==, sizeof (dmu_replay_record_t) - sizeof (zio_cksum_t));
99
fletcher_4_incremental_native(drr,
100
offsetof(dmu_replay_record_t, drr_u.drr_checksum.drr_checksum), zc);
101
if (drr->drr_type != DRR_BEGIN) {
102
ASSERT(ZIO_CHECKSUM_IS_ZERO(&drr->drr_u.
103
drr_checksum.drr_checksum));
104
drr->drr_u.drr_checksum.drr_checksum = *zc;
105
}
106
fletcher_4_incremental_native(&drr->drr_u.drr_checksum.drr_checksum,
107
sizeof (zio_cksum_t), zc);
108
if (write(outfd, drr, sizeof (*drr)) == -1)
109
return (errno);
110
if (payload_len != 0) {
111
fletcher_4_incremental_native(payload, payload_len, zc);
112
if (write(outfd, payload, payload_len) == -1)
113
return (errno);
114
}
115
return (0);
116
}
117
118
/*
119
* Routines for dealing with the AVL tree of fs-nvlists
120
*/
121
typedef struct fsavl_node {
122
avl_node_t fn_node;
123
nvlist_t *fn_nvfs;
124
const char *fn_snapname;
125
uint64_t fn_guid;
126
} fsavl_node_t;
127
128
static int
129
fsavl_compare(const void *arg1, const void *arg2)
130
{
131
const fsavl_node_t *fn1 = (const fsavl_node_t *)arg1;
132
const fsavl_node_t *fn2 = (const fsavl_node_t *)arg2;
133
134
return (TREE_CMP(fn1->fn_guid, fn2->fn_guid));
135
}
136
137
/*
138
* Given the GUID of a snapshot, find its containing filesystem and
139
* (optionally) name.
140
*/
141
static nvlist_t *
142
fsavl_find(avl_tree_t *avl, uint64_t snapguid, const char **snapname)
143
{
144
fsavl_node_t fn_find;
145
fsavl_node_t *fn;
146
147
fn_find.fn_guid = snapguid;
148
149
fn = avl_find(avl, &fn_find, NULL);
150
if (fn) {
151
if (snapname)
152
*snapname = fn->fn_snapname;
153
return (fn->fn_nvfs);
154
}
155
return (NULL);
156
}
157
158
static void
159
fsavl_destroy(avl_tree_t *avl)
160
{
161
fsavl_node_t *fn;
162
void *cookie;
163
164
if (avl == NULL)
165
return;
166
167
cookie = NULL;
168
while ((fn = avl_destroy_nodes(avl, &cookie)) != NULL)
169
free(fn);
170
avl_destroy(avl);
171
free(avl);
172
}
173
174
/*
175
* Given an nvlist, produce an avl tree of snapshots, ordered by guid
176
*/
177
static avl_tree_t *
178
fsavl_create(nvlist_t *fss)
179
{
180
avl_tree_t *fsavl;
181
nvpair_t *fselem = NULL;
182
183
if ((fsavl = malloc(sizeof (avl_tree_t))) == NULL)
184
return (NULL);
185
186
avl_create(fsavl, fsavl_compare, sizeof (fsavl_node_t),
187
offsetof(fsavl_node_t, fn_node));
188
189
while ((fselem = nvlist_next_nvpair(fss, fselem)) != NULL) {
190
nvlist_t *nvfs, *snaps;
191
nvpair_t *snapelem = NULL;
192
193
nvfs = fnvpair_value_nvlist(fselem);
194
snaps = fnvlist_lookup_nvlist(nvfs, "snaps");
195
196
while ((snapelem =
197
nvlist_next_nvpair(snaps, snapelem)) != NULL) {
198
fsavl_node_t *fn;
199
200
if ((fn = malloc(sizeof (fsavl_node_t))) == NULL) {
201
fsavl_destroy(fsavl);
202
return (NULL);
203
}
204
fn->fn_nvfs = nvfs;
205
fn->fn_snapname = nvpair_name(snapelem);
206
fn->fn_guid = fnvpair_value_uint64(snapelem);
207
208
/*
209
* Note: if there are multiple snaps with the
210
* same GUID, we ignore all but one.
211
*/
212
avl_index_t where = 0;
213
if (avl_find(fsavl, fn, &where) == NULL)
214
avl_insert(fsavl, fn, where);
215
else
216
free(fn);
217
}
218
}
219
220
return (fsavl);
221
}
222
223
/*
224
* Routines for dealing with the giant nvlist of fs-nvlists, etc.
225
*/
226
typedef struct send_data {
227
/*
228
* assigned inside every recursive call,
229
* restored from *_save on return:
230
*
231
* guid of fromsnap snapshot in parent dataset
232
* txg of fromsnap snapshot in current dataset
233
* txg of tosnap snapshot in current dataset
234
*/
235
236
uint64_t parent_fromsnap_guid;
237
uint64_t fromsnap_txg;
238
uint64_t tosnap_txg;
239
240
/* the nvlists get accumulated during depth-first traversal */
241
nvlist_t *parent_snaps;
242
nvlist_t *fss;
243
nvlist_t *snapprops;
244
nvlist_t *snapholds; /* user holds */
245
246
/* send-receive configuration, does not change during traversal */
247
const char *fsname;
248
const char *fromsnap;
249
const char *tosnap;
250
boolean_t recursive;
251
boolean_t raw;
252
boolean_t doall;
253
boolean_t replicate;
254
boolean_t skipmissing;
255
boolean_t verbose;
256
boolean_t backup;
257
boolean_t seenfrom;
258
boolean_t seento;
259
boolean_t holds; /* were holds requested with send -h */
260
boolean_t props;
261
262
/*
263
* The header nvlist is of the following format:
264
* {
265
* "tosnap" -> string
266
* "fromsnap" -> string (if incremental)
267
* "fss" -> {
268
* id -> {
269
*
270
* "name" -> string (full name; for debugging)
271
* "parentfromsnap" -> number (guid of fromsnap in parent)
272
*
273
* "props" -> { name -> value (only if set here) }
274
* "snaps" -> { name (lastname) -> number (guid) }
275
* "snapprops" -> { name (lastname) -> { name -> value } }
276
* "snapholds" -> { name (lastname) -> { holdname -> crtime } }
277
*
278
* "origin" -> number (guid) (if clone)
279
* "is_encroot" -> boolean
280
* "sent" -> boolean (not on-disk)
281
* }
282
* }
283
* }
284
*
285
*/
286
} send_data_t;
287
288
static void
289
send_iterate_prop(zfs_handle_t *zhp, boolean_t received_only, nvlist_t *nv);
290
291
/*
292
* Collect guid, valid props, optionally holds, etc. of a snapshot.
293
* This interface is intended for use as a zfs_iter_snapshots_v2_sorted visitor.
294
*/
295
static int
296
send_iterate_snap(zfs_handle_t *zhp, void *arg)
297
{
298
send_data_t *sd = arg;
299
uint64_t guid = zhp->zfs_dmustats.dds_guid;
300
uint64_t txg = zhp->zfs_dmustats.dds_creation_txg;
301
boolean_t isfromsnap, istosnap, istosnapwithnofrom;
302
char *snapname;
303
const char *from = sd->fromsnap;
304
const char *to = sd->tosnap;
305
306
snapname = strrchr(zhp->zfs_name, '@');
307
assert(snapname != NULL);
308
++snapname;
309
310
isfromsnap = (from != NULL && strcmp(from, snapname) == 0);
311
istosnap = (to != NULL && strcmp(to, snapname) == 0);
312
istosnapwithnofrom = (istosnap && from == NULL);
313
314
if (sd->tosnap_txg != 0 && txg > sd->tosnap_txg) {
315
if (sd->verbose) {
316
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
317
"skipping snapshot %s because it was created "
318
"after the destination snapshot (%s)\n"),
319
zhp->zfs_name, to);
320
}
321
zfs_close(zhp);
322
return (0);
323
}
324
325
fnvlist_add_uint64(sd->parent_snaps, snapname, guid);
326
327
/*
328
* NB: if there is no fromsnap here (it's a newly created fs in
329
* an incremental replication), we will substitute the tosnap.
330
*/
331
if (isfromsnap || (sd->parent_fromsnap_guid == 0 && istosnap))
332
sd->parent_fromsnap_guid = guid;
333
334
if (!sd->recursive) {
335
/*
336
* To allow a doall stream to work properly
337
* with a NULL fromsnap
338
*/
339
if (sd->doall && from == NULL && !sd->seenfrom)
340
sd->seenfrom = B_TRUE;
341
342
if (!sd->seenfrom && isfromsnap) {
343
sd->seenfrom = B_TRUE;
344
zfs_close(zhp);
345
return (0);
346
}
347
348
if ((sd->seento || !sd->seenfrom) && !istosnapwithnofrom) {
349
zfs_close(zhp);
350
return (0);
351
}
352
353
if (istosnap)
354
sd->seento = B_TRUE;
355
}
356
357
nvlist_t *nv = fnvlist_alloc();
358
send_iterate_prop(zhp, sd->backup, nv);
359
fnvlist_add_nvlist(sd->snapprops, snapname, nv);
360
fnvlist_free(nv);
361
362
if (sd->holds) {
363
nvlist_t *holds;
364
if (lzc_get_holds(zhp->zfs_name, &holds) == 0) {
365
fnvlist_add_nvlist(sd->snapholds, snapname, holds);
366
fnvlist_free(holds);
367
}
368
}
369
370
zfs_close(zhp);
371
return (0);
372
}
373
374
/*
375
* Collect all valid props from the handle snap into an nvlist.
376
*/
377
static void
378
send_iterate_prop(zfs_handle_t *zhp, boolean_t received_only, nvlist_t *nv)
379
{
380
nvlist_t *props;
381
382
if (received_only)
383
props = zfs_get_recvd_props(zhp);
384
else
385
props = zhp->zfs_props;
386
387
nvpair_t *elem = NULL;
388
while ((elem = nvlist_next_nvpair(props, elem)) != NULL) {
389
const char *propname = nvpair_name(elem);
390
zfs_prop_t prop = zfs_name_to_prop(propname);
391
392
if (!zfs_prop_user(propname)) {
393
/*
394
* Realistically, this should never happen. However,
395
* we want the ability to add DSL properties without
396
* needing to make incompatible version changes. We
397
* need to ignore unknown properties to allow older
398
* software to still send datasets containing these
399
* properties, with the unknown properties elided.
400
*/
401
if (prop == ZPROP_INVAL)
402
continue;
403
404
if (zfs_prop_readonly(prop))
405
continue;
406
}
407
408
nvlist_t *propnv = fnvpair_value_nvlist(elem);
409
410
boolean_t isspacelimit = (prop == ZFS_PROP_QUOTA ||
411
prop == ZFS_PROP_RESERVATION ||
412
prop == ZFS_PROP_REFQUOTA ||
413
prop == ZFS_PROP_REFRESERVATION);
414
if (isspacelimit && zhp->zfs_type == ZFS_TYPE_SNAPSHOT)
415
continue;
416
417
const char *source;
418
if (nvlist_lookup_string(propnv, ZPROP_SOURCE, &source) == 0) {
419
if (strcmp(source, zhp->zfs_name) != 0 &&
420
strcmp(source, ZPROP_SOURCE_VAL_RECVD) != 0)
421
continue;
422
} else {
423
/*
424
* May have no source before SPA_VERSION_RECVD_PROPS,
425
* but is still modifiable.
426
*/
427
if (!isspacelimit)
428
continue;
429
}
430
431
if (zfs_prop_user(propname) ||
432
zfs_prop_get_type(prop) == PROP_TYPE_STRING) {
433
const char *value;
434
value = fnvlist_lookup_string(propnv, ZPROP_VALUE);
435
fnvlist_add_string(nv, propname, value);
436
} else {
437
uint64_t value;
438
value = fnvlist_lookup_uint64(propnv, ZPROP_VALUE);
439
fnvlist_add_uint64(nv, propname, value);
440
}
441
}
442
}
443
444
/*
445
* returns snapshot guid
446
* and returns 0 if the snapshot does not exist
447
*/
448
static uint64_t
449
get_snap_guid(libzfs_handle_t *hdl, const char *fs, const char *snap)
450
{
451
char name[MAXPATHLEN + 1];
452
uint64_t guid = 0;
453
454
if (fs == NULL || fs[0] == '\0' || snap == NULL || snap[0] == '\0')
455
return (guid);
456
457
(void) snprintf(name, sizeof (name), "%s@%s", fs, snap);
458
zfs_handle_t *zhp = zfs_open(hdl, name, ZFS_TYPE_SNAPSHOT);
459
if (zhp != NULL) {
460
guid = zfs_prop_get_int(zhp, ZFS_PROP_GUID);
461
zfs_close(zhp);
462
}
463
464
return (guid);
465
}
466
467
/*
468
* returns snapshot creation txg
469
* and returns 0 if the snapshot does not exist
470
*/
471
static uint64_t
472
get_snap_txg(libzfs_handle_t *hdl, const char *fs, const char *snap)
473
{
474
char name[ZFS_MAX_DATASET_NAME_LEN];
475
uint64_t txg = 0;
476
477
if (fs == NULL || fs[0] == '\0' || snap == NULL || snap[0] == '\0')
478
return (txg);
479
480
(void) snprintf(name, sizeof (name), "%s@%s", fs, snap);
481
if (zfs_dataset_exists(hdl, name, ZFS_TYPE_SNAPSHOT)) {
482
zfs_handle_t *zhp = zfs_open(hdl, name, ZFS_TYPE_SNAPSHOT);
483
if (zhp != NULL) {
484
txg = zfs_prop_get_int(zhp, ZFS_PROP_CREATETXG);
485
zfs_close(zhp);
486
}
487
}
488
489
return (txg);
490
}
491
492
/*
493
* Recursively generate nvlists describing datasets. See comment
494
* for the data structure send_data_t above for description of contents
495
* of the nvlist.
496
*/
497
static int
498
send_iterate_fs(zfs_handle_t *zhp, void *arg)
499
{
500
send_data_t *sd = arg;
501
nvlist_t *nvfs = NULL, *nv = NULL;
502
int rv = 0;
503
uint64_t min_txg = 0, max_txg = 0;
504
uint64_t txg = zhp->zfs_dmustats.dds_creation_txg;
505
uint64_t guid = zhp->zfs_dmustats.dds_guid;
506
uint64_t fromsnap_txg, tosnap_txg;
507
char guidstring[64];
508
509
/* These fields are restored on return from a recursive call. */
510
uint64_t parent_fromsnap_guid_save = sd->parent_fromsnap_guid;
511
uint64_t fromsnap_txg_save = sd->fromsnap_txg;
512
uint64_t tosnap_txg_save = sd->tosnap_txg;
513
514
fromsnap_txg = get_snap_txg(zhp->zfs_hdl, zhp->zfs_name, sd->fromsnap);
515
if (fromsnap_txg != 0)
516
sd->fromsnap_txg = fromsnap_txg;
517
518
tosnap_txg = get_snap_txg(zhp->zfs_hdl, zhp->zfs_name, sd->tosnap);
519
if (tosnap_txg != 0)
520
sd->tosnap_txg = tosnap_txg;
521
522
/*
523
* On the send side, if the current dataset does not have tosnap,
524
* perform two additional checks:
525
*
526
* - Skip sending the current dataset if it was created later than
527
* the parent tosnap.
528
* - Return error if the current dataset was created earlier than
529
* the parent tosnap, unless --skip-missing specified. Then
530
* just print a warning.
531
*/
532
if (sd->tosnap != NULL && tosnap_txg == 0) {
533
if (sd->tosnap_txg != 0 && txg > sd->tosnap_txg) {
534
if (sd->verbose) {
535
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
536
"skipping dataset %s: snapshot %s does "
537
"not exist\n"), zhp->zfs_name, sd->tosnap);
538
}
539
} else if (sd->skipmissing) {
540
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
541
"WARNING: skipping dataset %s and its children:"
542
" snapshot %s does not exist\n"),
543
zhp->zfs_name, sd->tosnap);
544
} else {
545
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
546
"cannot send %s@%s%s: snapshot %s@%s does not "
547
"exist\n"), sd->fsname, sd->tosnap, sd->recursive ?
548
dgettext(TEXT_DOMAIN, " recursively") : "",
549
zhp->zfs_name, sd->tosnap);
550
rv = EZFS_NOENT;
551
}
552
goto out;
553
}
554
555
nvfs = fnvlist_alloc();
556
fnvlist_add_string(nvfs, "name", zhp->zfs_name);
557
fnvlist_add_uint64(nvfs, "parentfromsnap", sd->parent_fromsnap_guid);
558
559
if (zhp->zfs_dmustats.dds_origin[0] != '\0') {
560
zfs_handle_t *origin = zfs_open(zhp->zfs_hdl,
561
zhp->zfs_dmustats.dds_origin, ZFS_TYPE_SNAPSHOT);
562
if (origin == NULL) {
563
rv = -1;
564
goto out;
565
}
566
fnvlist_add_uint64(nvfs, "origin",
567
origin->zfs_dmustats.dds_guid);
568
zfs_close(origin);
569
}
570
571
/* Iterate over props. */
572
if (sd->props || sd->backup || sd->recursive) {
573
nv = fnvlist_alloc();
574
send_iterate_prop(zhp, sd->backup, nv);
575
fnvlist_add_nvlist(nvfs, "props", nv);
576
}
577
if (zfs_prop_get_int(zhp, ZFS_PROP_ENCRYPTION) != ZIO_CRYPT_OFF) {
578
boolean_t encroot;
579
580
/* Determine if this dataset is an encryption root. */
581
if (zfs_crypto_get_encryption_root(zhp, &encroot, NULL) != 0) {
582
rv = -1;
583
goto out;
584
}
585
586
if (encroot)
587
fnvlist_add_boolean(nvfs, "is_encroot");
588
589
/*
590
* Encrypted datasets can only be sent with properties if
591
* the raw flag is specified because the receive side doesn't
592
* currently have a mechanism for recursively asking the user
593
* for new encryption parameters.
594
*/
595
if (!sd->raw) {
596
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
597
"cannot send %s@%s: encrypted dataset %s may not "
598
"be sent with properties without the raw flag\n"),
599
sd->fsname, sd->tosnap, zhp->zfs_name);
600
rv = -1;
601
goto out;
602
}
603
604
}
605
606
/*
607
* Iterate over snaps, and set sd->parent_fromsnap_guid.
608
*
609
* If this is a "doall" send, a replicate send or we're just trying
610
* to gather a list of previous snapshots, iterate through all the
611
* snaps in the txg range. Otherwise just look at the one we're
612
* interested in.
613
*/
614
sd->parent_fromsnap_guid = 0;
615
sd->parent_snaps = fnvlist_alloc();
616
sd->snapprops = fnvlist_alloc();
617
if (sd->holds)
618
sd->snapholds = fnvlist_alloc();
619
if (sd->doall || sd->replicate || sd->tosnap == NULL) {
620
if (!sd->replicate && fromsnap_txg != 0)
621
min_txg = fromsnap_txg;
622
if (!sd->replicate && tosnap_txg != 0)
623
max_txg = tosnap_txg;
624
(void) zfs_iter_snapshots_sorted_v2(zhp, 0, send_iterate_snap,
625
sd, min_txg, max_txg);
626
} else {
627
char snapname[MAXPATHLEN] = { 0 };
628
zfs_handle_t *snap;
629
630
(void) snprintf(snapname, sizeof (snapname), "%s@%s",
631
zhp->zfs_name, sd->tosnap);
632
if (sd->fromsnap != NULL)
633
sd->seenfrom = B_TRUE;
634
snap = zfs_open(zhp->zfs_hdl, snapname, ZFS_TYPE_SNAPSHOT);
635
if (snap != NULL)
636
(void) send_iterate_snap(snap, sd);
637
}
638
639
fnvlist_add_nvlist(nvfs, "snaps", sd->parent_snaps);
640
fnvlist_free(sd->parent_snaps);
641
fnvlist_add_nvlist(nvfs, "snapprops", sd->snapprops);
642
fnvlist_free(sd->snapprops);
643
if (sd->holds) {
644
fnvlist_add_nvlist(nvfs, "snapholds", sd->snapholds);
645
fnvlist_free(sd->snapholds);
646
}
647
648
/* Do not allow the size of the properties list to exceed the limit */
649
if ((fnvlist_size(nvfs) + fnvlist_size(sd->fss)) >
650
zhp->zfs_hdl->libzfs_max_nvlist) {
651
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
652
"warning: cannot send %s@%s: the size of the list of "
653
"snapshots and properties is too large to be received "
654
"successfully.\n"
655
"Select a smaller number of snapshots to send.\n"),
656
zhp->zfs_name, sd->tosnap);
657
rv = EZFS_NOSPC;
658
goto out;
659
}
660
/* Add this fs to nvlist. */
661
(void) snprintf(guidstring, sizeof (guidstring),
662
"0x%llx", (longlong_t)guid);
663
fnvlist_add_nvlist(sd->fss, guidstring, nvfs);
664
665
/* Iterate over children. */
666
if (sd->recursive)
667
rv = zfs_iter_filesystems_v2(zhp, 0, send_iterate_fs, sd);
668
669
out:
670
/* Restore saved fields. */
671
sd->parent_fromsnap_guid = parent_fromsnap_guid_save;
672
sd->fromsnap_txg = fromsnap_txg_save;
673
sd->tosnap_txg = tosnap_txg_save;
674
675
fnvlist_free(nv);
676
fnvlist_free(nvfs);
677
678
zfs_close(zhp);
679
return (rv);
680
}
681
682
static int
683
gather_nvlist(libzfs_handle_t *hdl, const char *fsname, const char *fromsnap,
684
const char *tosnap, boolean_t recursive, boolean_t raw, boolean_t doall,
685
boolean_t replicate, boolean_t skipmissing, boolean_t verbose,
686
boolean_t backup, boolean_t holds, boolean_t props, nvlist_t **nvlp,
687
avl_tree_t **avlp)
688
{
689
zfs_handle_t *zhp;
690
send_data_t sd = { 0 };
691
int error;
692
693
zhp = zfs_open(hdl, fsname, ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME);
694
if (zhp == NULL)
695
return (EZFS_BADTYPE);
696
697
sd.fss = fnvlist_alloc();
698
sd.fsname = fsname;
699
sd.fromsnap = fromsnap;
700
sd.tosnap = tosnap;
701
sd.recursive = recursive;
702
sd.raw = raw;
703
sd.doall = doall;
704
sd.replicate = replicate;
705
sd.skipmissing = skipmissing;
706
sd.verbose = verbose;
707
sd.backup = backup;
708
sd.holds = holds;
709
sd.props = props;
710
711
if ((error = send_iterate_fs(zhp, &sd)) != 0) {
712
fnvlist_free(sd.fss);
713
if (avlp != NULL)
714
*avlp = NULL;
715
*nvlp = NULL;
716
return (error);
717
}
718
719
if (avlp != NULL && (*avlp = fsavl_create(sd.fss)) == NULL) {
720
fnvlist_free(sd.fss);
721
*nvlp = NULL;
722
return (EZFS_NOMEM);
723
}
724
725
*nvlp = sd.fss;
726
return (0);
727
}
728
729
/*
730
* Routines specific to "zfs send"
731
*/
732
typedef struct send_dump_data {
733
/* these are all just the short snapname (the part after the @) */
734
const char *fromsnap;
735
const char *tosnap;
736
char prevsnap[ZFS_MAX_DATASET_NAME_LEN];
737
uint64_t prevsnap_obj;
738
boolean_t seenfrom, seento, replicate, doall, fromorigin;
739
boolean_t dryrun, parsable, progress, embed_data, std_out;
740
boolean_t large_block, compress, raw, holds;
741
boolean_t progressastitle;
742
int outfd;
743
boolean_t err;
744
nvlist_t *fss;
745
nvlist_t *snapholds;
746
avl_tree_t *fsavl;
747
snapfilter_cb_t *filter_cb;
748
void *filter_cb_arg;
749
nvlist_t *debugnv;
750
char holdtag[ZFS_MAX_DATASET_NAME_LEN];
751
int cleanup_fd;
752
int verbosity;
753
uint64_t size;
754
} send_dump_data_t;
755
756
static int
757
zfs_send_space(zfs_handle_t *zhp, const char *snapname, const char *from,
758
enum lzc_send_flags flags, uint64_t *spacep)
759
{
760
assert(snapname != NULL);
761
762
int error = lzc_send_space(snapname, from, flags, spacep);
763
if (error == 0)
764
return (0);
765
766
char errbuf[ERRBUFLEN];
767
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
768
"warning: cannot estimate space for '%s'"), snapname);
769
770
libzfs_handle_t *hdl = zhp->zfs_hdl;
771
switch (error) {
772
case EXDEV:
773
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
774
"not an earlier snapshot from the same fs"));
775
return (zfs_error(hdl, EZFS_CROSSTARGET, errbuf));
776
777
case ENOENT:
778
if (zfs_dataset_exists(hdl, snapname,
779
ZFS_TYPE_SNAPSHOT)) {
780
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
781
"incremental source (%s) does not exist"),
782
snapname);
783
}
784
return (zfs_error(hdl, EZFS_NOENT, errbuf));
785
786
case EDQUOT:
787
case EFBIG:
788
case EIO:
789
case ENOLINK:
790
case ENOSPC:
791
case ENOSTR:
792
case ENXIO:
793
case EPIPE:
794
case ERANGE:
795
case EFAULT:
796
case EROFS:
797
case EINVAL:
798
zfs_error_aux(hdl, "%s", zfs_strerror(error));
799
return (zfs_error(hdl, EZFS_BADBACKUP, errbuf));
800
801
default:
802
return (zfs_standard_error(hdl, error, errbuf));
803
}
804
}
805
806
/*
807
* Dumps a backup of the given snapshot (incremental from fromsnap if it's not
808
* NULL) to the file descriptor specified by outfd.
809
*/
810
static int
811
dump_ioctl(zfs_handle_t *zhp, const char *fromsnap, uint64_t fromsnap_obj,
812
boolean_t fromorigin, int outfd, enum lzc_send_flags flags,
813
nvlist_t *debugnv)
814
{
815
zfs_cmd_t zc = {"\0"};
816
libzfs_handle_t *hdl = zhp->zfs_hdl;
817
nvlist_t *thisdbg;
818
819
assert(zhp->zfs_type == ZFS_TYPE_SNAPSHOT);
820
assert(fromsnap_obj == 0 || !fromorigin);
821
822
(void) strlcpy(zc.zc_name, zhp->zfs_name, sizeof (zc.zc_name));
823
zc.zc_cookie = outfd;
824
zc.zc_obj = fromorigin;
825
zc.zc_sendobj = zfs_prop_get_int(zhp, ZFS_PROP_OBJSETID);
826
zc.zc_fromobj = fromsnap_obj;
827
zc.zc_flags = flags;
828
829
if (debugnv != NULL) {
830
thisdbg = fnvlist_alloc();
831
if (fromsnap != NULL && fromsnap[0] != '\0')
832
fnvlist_add_string(thisdbg, "fromsnap", fromsnap);
833
}
834
835
if (zfs_ioctl(zhp->zfs_hdl, ZFS_IOC_SEND, &zc) != 0) {
836
char errbuf[ERRBUFLEN];
837
int error = errno;
838
839
(void) snprintf(errbuf, sizeof (errbuf), "%s '%s'",
840
dgettext(TEXT_DOMAIN, "warning: cannot send"),
841
zhp->zfs_name);
842
843
if (debugnv != NULL) {
844
fnvlist_add_uint64(thisdbg, "error", error);
845
fnvlist_add_nvlist(debugnv, zhp->zfs_name, thisdbg);
846
fnvlist_free(thisdbg);
847
}
848
849
switch (error) {
850
case EXDEV:
851
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
852
"not an earlier snapshot from the same fs"));
853
return (zfs_error(hdl, EZFS_CROSSTARGET, errbuf));
854
855
case EACCES:
856
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
857
"source key must be loaded"));
858
return (zfs_error(hdl, EZFS_CRYPTOFAILED, errbuf));
859
860
case ENOENT:
861
if (zfs_dataset_exists(hdl, zc.zc_name,
862
ZFS_TYPE_SNAPSHOT)) {
863
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
864
"incremental source (@%s) does not exist"),
865
zc.zc_value);
866
}
867
return (zfs_error(hdl, EZFS_NOENT, errbuf));
868
869
case EDQUOT:
870
case EFBIG:
871
case EIO:
872
case ENOLINK:
873
case ENOSPC:
874
case ENOSTR:
875
case ENXIO:
876
case EPIPE:
877
case ERANGE:
878
case EFAULT:
879
case EROFS:
880
case EINVAL:
881
zfs_error_aux(hdl, "%s", zfs_strerror(errno));
882
return (zfs_error(hdl, EZFS_BADBACKUP, errbuf));
883
884
default:
885
return (zfs_standard_error(hdl, errno, errbuf));
886
}
887
}
888
889
if (debugnv != NULL) {
890
fnvlist_add_nvlist(debugnv, zhp->zfs_name, thisdbg);
891
fnvlist_free(thisdbg);
892
}
893
894
return (0);
895
}
896
897
static void
898
gather_holds(zfs_handle_t *zhp, send_dump_data_t *sdd)
899
{
900
assert(zhp->zfs_type == ZFS_TYPE_SNAPSHOT);
901
902
/*
903
* zfs_send() only sets snapholds for sends that need them,
904
* e.g. replication and doall.
905
*/
906
if (sdd->snapholds == NULL)
907
return;
908
909
fnvlist_add_string(sdd->snapholds, zhp->zfs_name, sdd->holdtag);
910
}
911
912
int
913
zfs_send_progress(zfs_handle_t *zhp, int fd, uint64_t *bytes_written,
914
uint64_t *blocks_visited)
915
{
916
zfs_cmd_t zc = {"\0"};
917
918
if (bytes_written != NULL)
919
*bytes_written = 0;
920
if (blocks_visited != NULL)
921
*blocks_visited = 0;
922
(void) strlcpy(zc.zc_name, zhp->zfs_name, sizeof (zc.zc_name));
923
zc.zc_cookie = fd;
924
if (zfs_ioctl(zhp->zfs_hdl, ZFS_IOC_SEND_PROGRESS, &zc) != 0)
925
return (errno);
926
if (bytes_written != NULL)
927
*bytes_written = zc.zc_cookie;
928
if (blocks_visited != NULL)
929
*blocks_visited = zc.zc_objset_type;
930
return (0);
931
}
932
933
static volatile boolean_t send_progress_thread_signal_duetotimer;
934
static void
935
send_progress_thread_act(int sig, siginfo_t *info, void *ucontext)
936
{
937
(void) sig, (void) ucontext;
938
send_progress_thread_signal_duetotimer = info->si_code == SI_TIMER;
939
}
940
941
struct timer_desirability {
942
timer_t timer;
943
boolean_t desired;
944
};
945
static void
946
timer_delete_cleanup(void *timer)
947
{
948
struct timer_desirability *td = timer;
949
if (td->desired)
950
timer_delete(td->timer);
951
}
952
953
#ifdef SIGINFO
954
#define SEND_PROGRESS_THREAD_PARENT_BLOCK_SIGINFO sigaddset(&new, SIGINFO)
955
#else
956
#define SEND_PROGRESS_THREAD_PARENT_BLOCK_SIGINFO
957
#endif
958
#define SEND_PROGRESS_THREAD_PARENT_BLOCK(old) { \
959
sigset_t new; \
960
sigemptyset(&new); \
961
sigaddset(&new, SIGUSR1); \
962
SEND_PROGRESS_THREAD_PARENT_BLOCK_SIGINFO; \
963
pthread_sigmask(SIG_BLOCK, &new, old); \
964
}
965
966
static void *
967
send_progress_thread(void *arg)
968
{
969
progress_arg_t *pa = arg;
970
zfs_handle_t *zhp = pa->pa_zhp;
971
uint64_t bytes;
972
uint64_t blocks;
973
uint64_t total = pa->pa_size / 100;
974
char buf[16];
975
time_t t;
976
struct tm tm;
977
int err;
978
979
const struct sigaction signal_action =
980
{.sa_sigaction = send_progress_thread_act, .sa_flags = SA_SIGINFO};
981
struct sigevent timer_cfg =
982
{.sigev_notify = SIGEV_SIGNAL, .sigev_signo = SIGUSR1};
983
const struct itimerspec timer_time =
984
{.it_value = {.tv_sec = 1}, .it_interval = {.tv_sec = 1}};
985
struct timer_desirability timer = {};
986
987
sigaction(SIGUSR1, &signal_action, NULL);
988
#ifdef SIGINFO
989
sigaction(SIGINFO, &signal_action, NULL);
990
#endif
991
992
if ((timer.desired = pa->pa_progress || pa->pa_astitle)) {
993
if (timer_create(CLOCK_MONOTONIC, &timer_cfg, &timer.timer))
994
return ((void *)(uintptr_t)errno);
995
(void) timer_settime(timer.timer, 0, &timer_time, NULL);
996
}
997
pthread_cleanup_push(timer_delete_cleanup, &timer);
998
999
if (!pa->pa_parsable && pa->pa_progress) {
1000
(void) fprintf(stderr,
1001
"TIME %s %sSNAPSHOT %s\n",
1002
pa->pa_estimate ? "BYTES" : " SENT",
1003
pa->pa_verbosity >= 2 ? " BLOCKS " : "",
1004
zhp->zfs_name);
1005
}
1006
1007
/*
1008
* Print the progress from ZFS_IOC_SEND_PROGRESS every second.
1009
*/
1010
for (;;) {
1011
pause();
1012
if ((err = zfs_send_progress(zhp, pa->pa_fd, &bytes,
1013
&blocks)) != 0) {
1014
if (err == EINTR || err == ENOENT)
1015
err = 0;
1016
/* Use break to reach pthread_cleanup_pop() below. */
1017
break;
1018
}
1019
1020
(void) time(&t);
1021
localtime_r(&t, &tm);
1022
1023
if (pa->pa_astitle) {
1024
char buf_bytes[16];
1025
char buf_size[16];
1026
int pct;
1027
zfs_nicenum(bytes, buf_bytes, sizeof (buf_bytes));
1028
zfs_nicenum(pa->pa_size, buf_size, sizeof (buf_size));
1029
pct = (total > 0) ? bytes / total : 100;
1030
zfs_setproctitle("sending %s (%d%%: %s/%s)",
1031
zhp->zfs_name, MIN(pct, 100), buf_bytes, buf_size);
1032
}
1033
1034
if (pa->pa_verbosity >= 2 && pa->pa_parsable) {
1035
(void) fprintf(stderr,
1036
"%02d:%02d:%02d\t%llu\t%llu\t%s\n",
1037
tm.tm_hour, tm.tm_min, tm.tm_sec,
1038
(u_longlong_t)bytes, (u_longlong_t)blocks,
1039
zhp->zfs_name);
1040
} else if (pa->pa_verbosity >= 2) {
1041
zfs_nicenum(bytes, buf, sizeof (buf));
1042
(void) fprintf(stderr,
1043
"%02d:%02d:%02d %5s %8llu %s\n",
1044
tm.tm_hour, tm.tm_min, tm.tm_sec,
1045
buf, (u_longlong_t)blocks, zhp->zfs_name);
1046
} else if (pa->pa_parsable) {
1047
(void) fprintf(stderr, "%02d:%02d:%02d\t%llu\t%s\n",
1048
tm.tm_hour, tm.tm_min, tm.tm_sec,
1049
(u_longlong_t)bytes, zhp->zfs_name);
1050
} else if (pa->pa_progress ||
1051
!send_progress_thread_signal_duetotimer) {
1052
zfs_nicebytes(bytes, buf, sizeof (buf));
1053
(void) fprintf(stderr, "%02d:%02d:%02d %5s %s\n",
1054
tm.tm_hour, tm.tm_min, tm.tm_sec,
1055
buf, zhp->zfs_name);
1056
}
1057
}
1058
pthread_cleanup_pop(B_TRUE);
1059
pthread_exit(((void *)(uintptr_t)err));
1060
}
1061
1062
static boolean_t
1063
send_progress_thread_exit(
1064
libzfs_handle_t *hdl, pthread_t ptid, sigset_t *oldmask)
1065
{
1066
void *status = NULL;
1067
(void) pthread_cancel(ptid);
1068
(void) pthread_join(ptid, &status);
1069
pthread_sigmask(SIG_SETMASK, oldmask, NULL);
1070
int error = (int)(uintptr_t)status;
1071
if (error != 0 && status != PTHREAD_CANCELED)
1072
return (zfs_standard_error(hdl, error,
1073
dgettext(TEXT_DOMAIN, "progress thread exited nonzero")));
1074
else
1075
return (B_FALSE);
1076
}
1077
1078
static void
1079
send_print_verbose(FILE *fout, const char *tosnap, const char *fromsnap,
1080
uint64_t size, boolean_t parsable)
1081
{
1082
if (parsable) {
1083
if (fromsnap != NULL) {
1084
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1085
"incremental\t%s\t%s"), fromsnap, tosnap);
1086
} else {
1087
/*
1088
* Workaround for GCC 12+ with UBSan enabled deficencies.
1089
*
1090
* GCC 12+ invoked with -fsanitize=undefined incorrectly reports the code
1091
* below as violating -Wformat-overflow.
1092
*/
1093
#if defined(__GNUC__) && !defined(__clang__) && \
1094
defined(ZFS_UBSAN_ENABLED) && defined(HAVE_FORMAT_OVERFLOW)
1095
#pragma GCC diagnostic push
1096
#pragma GCC diagnostic ignored "-Wformat-overflow"
1097
#endif
1098
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1099
"full\t%s"), tosnap);
1100
#if defined(__GNUC__) && !defined(__clang__) && \
1101
defined(ZFS_UBSAN_ENABLED) && defined(HAVE_FORMAT_OVERFLOW)
1102
#pragma GCC diagnostic pop
1103
#endif
1104
}
1105
(void) fprintf(fout, "\t%llu", (longlong_t)size);
1106
} else {
1107
if (fromsnap != NULL) {
1108
if (strchr(fromsnap, '@') == NULL &&
1109
strchr(fromsnap, '#') == NULL) {
1110
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1111
"send from @%s to %s"), fromsnap, tosnap);
1112
} else {
1113
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1114
"send from %s to %s"), fromsnap, tosnap);
1115
}
1116
} else {
1117
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1118
"full send of %s"), tosnap);
1119
}
1120
if (size != 0) {
1121
char buf[16];
1122
zfs_nicebytes(size, buf, sizeof (buf));
1123
/*
1124
* Workaround for GCC 12+ with UBSan enabled deficencies.
1125
*
1126
* GCC 12+ invoked with -fsanitize=undefined incorrectly reports the code
1127
* below as violating -Wformat-overflow.
1128
*/
1129
#if defined(__GNUC__) && !defined(__clang__) && \
1130
defined(ZFS_UBSAN_ENABLED) && defined(HAVE_FORMAT_OVERFLOW)
1131
#pragma GCC diagnostic push
1132
#pragma GCC diagnostic ignored "-Wformat-overflow"
1133
#endif
1134
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1135
" estimated size is %s"), buf);
1136
#if defined(__GNUC__) && !defined(__clang__) && \
1137
defined(ZFS_UBSAN_ENABLED) && defined(HAVE_FORMAT_OVERFLOW)
1138
#pragma GCC diagnostic pop
1139
#endif
1140
}
1141
}
1142
(void) fprintf(fout, "\n");
1143
}
1144
1145
/*
1146
* Send a single filesystem snapshot, updating the send dump data.
1147
* This interface is intended for use as a zfs_iter_snapshots_v2_sorted visitor.
1148
*/
1149
static int
1150
dump_snapshot(zfs_handle_t *zhp, void *arg)
1151
{
1152
send_dump_data_t *sdd = arg;
1153
progress_arg_t pa = { 0 };
1154
pthread_t tid;
1155
char *thissnap;
1156
enum lzc_send_flags flags = 0;
1157
int err;
1158
boolean_t isfromsnap, istosnap, fromorigin;
1159
boolean_t exclude = B_FALSE;
1160
FILE *fout = sdd->std_out ? stdout : stderr;
1161
1162
err = 0;
1163
thissnap = strchr(zhp->zfs_name, '@') + 1;
1164
isfromsnap = (sdd->fromsnap != NULL &&
1165
strcmp(sdd->fromsnap, thissnap) == 0);
1166
1167
if (!sdd->seenfrom && isfromsnap) {
1168
gather_holds(zhp, sdd);
1169
sdd->seenfrom = B_TRUE;
1170
(void) strlcpy(sdd->prevsnap, thissnap, sizeof (sdd->prevsnap));
1171
sdd->prevsnap_obj = zfs_prop_get_int(zhp, ZFS_PROP_OBJSETID);
1172
zfs_close(zhp);
1173
return (0);
1174
}
1175
1176
if (sdd->seento || !sdd->seenfrom) {
1177
zfs_close(zhp);
1178
return (0);
1179
}
1180
1181
istosnap = (strcmp(sdd->tosnap, thissnap) == 0);
1182
if (istosnap)
1183
sdd->seento = B_TRUE;
1184
1185
if (sdd->large_block)
1186
flags |= LZC_SEND_FLAG_LARGE_BLOCK;
1187
if (sdd->embed_data)
1188
flags |= LZC_SEND_FLAG_EMBED_DATA;
1189
if (sdd->compress)
1190
flags |= LZC_SEND_FLAG_COMPRESS;
1191
if (sdd->raw)
1192
flags |= LZC_SEND_FLAG_RAW;
1193
1194
if (!sdd->doall && !isfromsnap && !istosnap) {
1195
if (sdd->replicate) {
1196
const char *snapname;
1197
nvlist_t *snapprops;
1198
/*
1199
* Filter out all intermediate snapshots except origin
1200
* snapshots needed to replicate clones.
1201
*/
1202
nvlist_t *nvfs = fsavl_find(sdd->fsavl,
1203
zhp->zfs_dmustats.dds_guid, &snapname);
1204
1205
if (nvfs != NULL) {
1206
snapprops = fnvlist_lookup_nvlist(nvfs,
1207
"snapprops");
1208
snapprops = fnvlist_lookup_nvlist(snapprops,
1209
thissnap);
1210
exclude = !nvlist_exists(snapprops,
1211
"is_clone_origin");
1212
}
1213
} else {
1214
exclude = B_TRUE;
1215
}
1216
}
1217
1218
/*
1219
* If a filter function exists, call it to determine whether
1220
* this snapshot will be sent.
1221
*/
1222
if (exclude || (sdd->filter_cb != NULL &&
1223
sdd->filter_cb(zhp, sdd->filter_cb_arg) == B_FALSE)) {
1224
/*
1225
* This snapshot is filtered out. Don't send it, and don't
1226
* set prevsnap_obj, so it will be as if this snapshot didn't
1227
* exist, and the next accepted snapshot will be sent as
1228
* an incremental from the last accepted one, or as the
1229
* first (and full) snapshot in the case of a replication,
1230
* non-incremental send.
1231
*/
1232
zfs_close(zhp);
1233
return (0);
1234
}
1235
1236
gather_holds(zhp, sdd);
1237
fromorigin = sdd->prevsnap[0] == '\0' &&
1238
(sdd->fromorigin || sdd->replicate);
1239
1240
if (sdd->verbosity != 0) {
1241
uint64_t size = 0;
1242
char fromds[ZFS_MAX_DATASET_NAME_LEN];
1243
1244
if (sdd->prevsnap[0] != '\0') {
1245
(void) strlcpy(fromds, zhp->zfs_name, sizeof (fromds));
1246
*(strchr(fromds, '@') + 1) = '\0';
1247
(void) strlcat(fromds, sdd->prevsnap, sizeof (fromds));
1248
}
1249
if (zfs_send_space(zhp, zhp->zfs_name,
1250
sdd->prevsnap[0] ? fromds : NULL, flags, &size) == 0) {
1251
send_print_verbose(fout, zhp->zfs_name,
1252
sdd->prevsnap[0] ? sdd->prevsnap : NULL,
1253
size, sdd->parsable);
1254
sdd->size += size;
1255
}
1256
}
1257
1258
if (!sdd->dryrun) {
1259
/*
1260
* If progress reporting is requested, spawn a new thread to
1261
* poll ZFS_IOC_SEND_PROGRESS at a regular interval.
1262
*/
1263
sigset_t oldmask;
1264
{
1265
pa.pa_zhp = zhp;
1266
pa.pa_fd = sdd->outfd;
1267
pa.pa_parsable = sdd->parsable;
1268
pa.pa_estimate = B_FALSE;
1269
pa.pa_verbosity = sdd->verbosity;
1270
pa.pa_size = sdd->size;
1271
pa.pa_astitle = sdd->progressastitle;
1272
pa.pa_progress = sdd->progress;
1273
1274
if ((err = pthread_create(&tid, NULL,
1275
send_progress_thread, &pa)) != 0) {
1276
zfs_close(zhp);
1277
return (err);
1278
}
1279
SEND_PROGRESS_THREAD_PARENT_BLOCK(&oldmask);
1280
}
1281
1282
err = dump_ioctl(zhp, sdd->prevsnap, sdd->prevsnap_obj,
1283
fromorigin, sdd->outfd, flags, sdd->debugnv);
1284
1285
if (send_progress_thread_exit(zhp->zfs_hdl, tid, &oldmask))
1286
return (-1);
1287
}
1288
1289
(void) strlcpy(sdd->prevsnap, thissnap, sizeof (sdd->prevsnap));
1290
sdd->prevsnap_obj = zfs_prop_get_int(zhp, ZFS_PROP_OBJSETID);
1291
zfs_close(zhp);
1292
return (err);
1293
}
1294
1295
/*
1296
* Send all snapshots for a filesystem, updating the send dump data.
1297
*/
1298
static int
1299
dump_filesystem(zfs_handle_t *zhp, send_dump_data_t *sdd)
1300
{
1301
int rv = 0;
1302
boolean_t missingfrom = B_FALSE;
1303
zfs_cmd_t zc = {"\0"};
1304
uint64_t min_txg = 0, max_txg = 0;
1305
1306
/*
1307
* Make sure the tosnap exists.
1308
*/
1309
(void) snprintf(zc.zc_name, sizeof (zc.zc_name), "%s@%s",
1310
zhp->zfs_name, sdd->tosnap);
1311
if (zfs_ioctl(zhp->zfs_hdl, ZFS_IOC_OBJSET_STATS, &zc) != 0) {
1312
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
1313
"WARNING: could not send %s@%s: does not exist\n"),
1314
zhp->zfs_name, sdd->tosnap);
1315
sdd->err = B_TRUE;
1316
return (0);
1317
}
1318
1319
/*
1320
* If this fs does not have fromsnap, and we're doing
1321
* recursive, we need to send a full stream from the
1322
* beginning (or an incremental from the origin if this
1323
* is a clone). If we're doing non-recursive, then let
1324
* them get the error.
1325
*/
1326
if (sdd->replicate && sdd->fromsnap) {
1327
/*
1328
* Make sure the fromsnap exists.
1329
*/
1330
(void) snprintf(zc.zc_name, sizeof (zc.zc_name), "%s@%s",
1331
zhp->zfs_name, sdd->fromsnap);
1332
if (zfs_ioctl(zhp->zfs_hdl, ZFS_IOC_OBJSET_STATS, &zc) != 0)
1333
missingfrom = B_TRUE;
1334
}
1335
1336
sdd->seenfrom = sdd->seento = B_FALSE;
1337
sdd->prevsnap[0] = '\0';
1338
sdd->prevsnap_obj = 0;
1339
if (sdd->fromsnap == NULL || missingfrom)
1340
sdd->seenfrom = B_TRUE;
1341
1342
/*
1343
* Iterate through all snapshots and process the ones we will be
1344
* sending. If we only have a "from" and "to" snapshot to deal
1345
* with, we can avoid iterating through all the other snapshots.
1346
*/
1347
if (sdd->doall || sdd->replicate || sdd->tosnap == NULL) {
1348
if (!sdd->replicate) {
1349
if (sdd->fromsnap != NULL) {
1350
min_txg = get_snap_txg(zhp->zfs_hdl,
1351
zhp->zfs_name, sdd->fromsnap);
1352
}
1353
if (sdd->tosnap != NULL) {
1354
max_txg = get_snap_txg(zhp->zfs_hdl,
1355
zhp->zfs_name, sdd->tosnap);
1356
}
1357
}
1358
rv = zfs_iter_snapshots_sorted_v2(zhp, 0, dump_snapshot, sdd,
1359
min_txg, max_txg);
1360
} else {
1361
char snapname[MAXPATHLEN] = { 0 };
1362
zfs_handle_t *snap;
1363
1364
/* Dump fromsnap. */
1365
if (!sdd->seenfrom) {
1366
(void) snprintf(snapname, sizeof (snapname),
1367
"%s@%s", zhp->zfs_name, sdd->fromsnap);
1368
snap = zfs_open(zhp->zfs_hdl, snapname,
1369
ZFS_TYPE_SNAPSHOT);
1370
if (snap != NULL)
1371
rv = dump_snapshot(snap, sdd);
1372
else
1373
rv = errno;
1374
}
1375
1376
/* Dump tosnap. */
1377
if (rv == 0) {
1378
(void) snprintf(snapname, sizeof (snapname),
1379
"%s@%s", zhp->zfs_name, sdd->tosnap);
1380
snap = zfs_open(zhp->zfs_hdl, snapname,
1381
ZFS_TYPE_SNAPSHOT);
1382
if (snap != NULL)
1383
rv = dump_snapshot(snap, sdd);
1384
else
1385
rv = errno;
1386
}
1387
}
1388
1389
if (!sdd->seenfrom) {
1390
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
1391
"WARNING: could not send %s@%s:\n"
1392
"incremental source (%s@%s) does not exist\n"),
1393
zhp->zfs_name, sdd->tosnap,
1394
zhp->zfs_name, sdd->fromsnap);
1395
sdd->err = B_TRUE;
1396
} else if (!sdd->seento) {
1397
if (sdd->fromsnap) {
1398
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
1399
"WARNING: could not send %s@%s:\n"
1400
"incremental source (%s@%s) "
1401
"is not earlier than it\n"),
1402
zhp->zfs_name, sdd->tosnap,
1403
zhp->zfs_name, sdd->fromsnap);
1404
} else {
1405
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
1406
"WARNING: "
1407
"could not send %s@%s: does not exist\n"),
1408
zhp->zfs_name, sdd->tosnap);
1409
}
1410
sdd->err = B_TRUE;
1411
}
1412
1413
return (rv);
1414
}
1415
1416
/*
1417
* Send all snapshots for all filesystems in sdd.
1418
*/
1419
static int
1420
dump_filesystems(zfs_handle_t *rzhp, send_dump_data_t *sdd)
1421
{
1422
nvpair_t *fspair;
1423
boolean_t needagain, progress;
1424
1425
if (!sdd->replicate)
1426
return (dump_filesystem(rzhp, sdd));
1427
1428
/* Mark the clone origin snapshots. */
1429
for (fspair = nvlist_next_nvpair(sdd->fss, NULL); fspair;
1430
fspair = nvlist_next_nvpair(sdd->fss, fspair)) {
1431
nvlist_t *nvfs;
1432
uint64_t origin_guid = 0;
1433
1434
nvfs = fnvpair_value_nvlist(fspair);
1435
(void) nvlist_lookup_uint64(nvfs, "origin", &origin_guid);
1436
if (origin_guid != 0) {
1437
const char *snapname;
1438
nvlist_t *origin_nv = fsavl_find(sdd->fsavl,
1439
origin_guid, &snapname);
1440
if (origin_nv != NULL) {
1441
nvlist_t *snapprops;
1442
snapprops = fnvlist_lookup_nvlist(origin_nv,
1443
"snapprops");
1444
snapprops = fnvlist_lookup_nvlist(snapprops,
1445
snapname);
1446
fnvlist_add_boolean(snapprops,
1447
"is_clone_origin");
1448
}
1449
}
1450
}
1451
again:
1452
needagain = progress = B_FALSE;
1453
for (fspair = nvlist_next_nvpair(sdd->fss, NULL); fspair;
1454
fspair = nvlist_next_nvpair(sdd->fss, fspair)) {
1455
nvlist_t *fslist, *parent_nv;
1456
const char *fsname;
1457
zfs_handle_t *zhp;
1458
int err;
1459
uint64_t origin_guid = 0;
1460
uint64_t parent_guid = 0;
1461
1462
fslist = fnvpair_value_nvlist(fspair);
1463
if (nvlist_lookup_boolean(fslist, "sent") == 0)
1464
continue;
1465
1466
fsname = fnvlist_lookup_string(fslist, "name");
1467
(void) nvlist_lookup_uint64(fslist, "origin", &origin_guid);
1468
(void) nvlist_lookup_uint64(fslist, "parentfromsnap",
1469
&parent_guid);
1470
1471
if (parent_guid != 0) {
1472
parent_nv = fsavl_find(sdd->fsavl, parent_guid, NULL);
1473
if (!nvlist_exists(parent_nv, "sent")) {
1474
/* Parent has not been sent; skip this one. */
1475
needagain = B_TRUE;
1476
continue;
1477
}
1478
}
1479
1480
if (origin_guid != 0) {
1481
nvlist_t *origin_nv = fsavl_find(sdd->fsavl,
1482
origin_guid, NULL);
1483
if (origin_nv != NULL &&
1484
!nvlist_exists(origin_nv, "sent")) {
1485
/*
1486
* Origin has not been sent yet;
1487
* skip this clone.
1488
*/
1489
needagain = B_TRUE;
1490
continue;
1491
}
1492
}
1493
1494
zhp = zfs_open(rzhp->zfs_hdl, fsname, ZFS_TYPE_DATASET);
1495
if (zhp == NULL)
1496
return (-1);
1497
err = dump_filesystem(zhp, sdd);
1498
fnvlist_add_boolean(fslist, "sent");
1499
progress = B_TRUE;
1500
zfs_close(zhp);
1501
if (err)
1502
return (err);
1503
}
1504
if (needagain) {
1505
assert(progress);
1506
goto again;
1507
}
1508
1509
/* Clean out the sent flags in case we reuse this fss. */
1510
for (fspair = nvlist_next_nvpair(sdd->fss, NULL); fspair;
1511
fspair = nvlist_next_nvpair(sdd->fss, fspair)) {
1512
nvlist_t *fslist;
1513
1514
fslist = fnvpair_value_nvlist(fspair);
1515
(void) nvlist_remove_all(fslist, "sent");
1516
}
1517
1518
return (0);
1519
}
1520
1521
nvlist_t *
1522
zfs_send_resume_token_to_nvlist(libzfs_handle_t *hdl, const char *token)
1523
{
1524
unsigned int version;
1525
int nread, i;
1526
unsigned long long checksum, packed_len;
1527
1528
/*
1529
* Decode token header, which is:
1530
* <token version>-<checksum of payload>-<uncompressed payload length>
1531
* Note that the only supported token version is 1.
1532
*/
1533
nread = sscanf(token, "%u-%llx-%llx-",
1534
&version, &checksum, &packed_len);
1535
if (nread != 3) {
1536
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1537
"resume token is corrupt (invalid format)"));
1538
return (NULL);
1539
}
1540
1541
if (version != ZFS_SEND_RESUME_TOKEN_VERSION) {
1542
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1543
"resume token is corrupt (invalid version %u)"),
1544
version);
1545
return (NULL);
1546
}
1547
1548
/* Convert hexadecimal representation to binary. */
1549
token = strrchr(token, '-') + 1;
1550
int len = strlen(token) / 2;
1551
unsigned char *compressed = zfs_alloc(hdl, len);
1552
for (i = 0; i < len; i++) {
1553
nread = sscanf(token + i * 2, "%2hhx", compressed + i);
1554
if (nread != 1) {
1555
free(compressed);
1556
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1557
"resume token is corrupt "
1558
"(payload is not hex-encoded)"));
1559
return (NULL);
1560
}
1561
}
1562
1563
/* Verify checksum. */
1564
zio_cksum_t cksum;
1565
fletcher_4_native_varsize(compressed, len, &cksum);
1566
if (cksum.zc_word[0] != checksum) {
1567
free(compressed);
1568
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1569
"resume token is corrupt (incorrect checksum)"));
1570
return (NULL);
1571
}
1572
1573
/* Uncompress. */
1574
void *packed = zfs_alloc(hdl, packed_len);
1575
uLongf packed_len_long = packed_len;
1576
if (uncompress(packed, &packed_len_long, compressed, len) != Z_OK ||
1577
packed_len_long != packed_len) {
1578
free(packed);
1579
free(compressed);
1580
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1581
"resume token is corrupt (decompression failed)"));
1582
return (NULL);
1583
}
1584
1585
/* Unpack nvlist. */
1586
nvlist_t *nv;
1587
int error = nvlist_unpack(packed, packed_len, &nv, KM_SLEEP);
1588
free(packed);
1589
free(compressed);
1590
if (error != 0) {
1591
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1592
"resume token is corrupt (nvlist_unpack failed)"));
1593
return (NULL);
1594
}
1595
return (nv);
1596
}
1597
1598
static enum lzc_send_flags
1599
lzc_flags_from_sendflags(const sendflags_t *flags)
1600
{
1601
enum lzc_send_flags lzc_flags = 0;
1602
1603
if (flags->largeblock)
1604
lzc_flags |= LZC_SEND_FLAG_LARGE_BLOCK;
1605
if (flags->embed_data)
1606
lzc_flags |= LZC_SEND_FLAG_EMBED_DATA;
1607
if (flags->compress)
1608
lzc_flags |= LZC_SEND_FLAG_COMPRESS;
1609
if (flags->raw)
1610
lzc_flags |= LZC_SEND_FLAG_RAW;
1611
if (flags->saved)
1612
lzc_flags |= LZC_SEND_FLAG_SAVED;
1613
1614
return (lzc_flags);
1615
}
1616
1617
static int
1618
estimate_size(zfs_handle_t *zhp, const char *from, int fd, sendflags_t *flags,
1619
uint64_t resumeobj, uint64_t resumeoff, uint64_t bytes,
1620
const char *redactbook, char *errbuf, uint64_t *sizep)
1621
{
1622
uint64_t size;
1623
FILE *fout = flags->dryrun ? stdout : stderr;
1624
progress_arg_t pa = { 0 };
1625
int err = 0;
1626
pthread_t ptid;
1627
sigset_t oldmask;
1628
1629
{
1630
pa.pa_zhp = zhp;
1631
pa.pa_fd = fd;
1632
pa.pa_parsable = flags->parsable;
1633
pa.pa_estimate = B_TRUE;
1634
pa.pa_verbosity = flags->verbosity;
1635
1636
err = pthread_create(&ptid, NULL,
1637
send_progress_thread, &pa);
1638
if (err != 0) {
1639
zfs_error_aux(zhp->zfs_hdl, "%s", zfs_strerror(errno));
1640
return (zfs_error(zhp->zfs_hdl,
1641
EZFS_THREADCREATEFAILED, errbuf));
1642
}
1643
SEND_PROGRESS_THREAD_PARENT_BLOCK(&oldmask);
1644
}
1645
1646
err = lzc_send_space_resume_redacted(zhp->zfs_name, from,
1647
lzc_flags_from_sendflags(flags), resumeobj, resumeoff, bytes,
1648
redactbook, fd, &size);
1649
*sizep = size;
1650
1651
if (send_progress_thread_exit(zhp->zfs_hdl, ptid, &oldmask))
1652
return (-1);
1653
1654
if (!flags->progress && !flags->parsable)
1655
return (err);
1656
1657
if (err != 0) {
1658
zfs_error_aux(zhp->zfs_hdl, "%s", zfs_strerror(err));
1659
return (zfs_error(zhp->zfs_hdl, EZFS_BADBACKUP,
1660
errbuf));
1661
}
1662
send_print_verbose(fout, zhp->zfs_name, from, size,
1663
flags->parsable);
1664
1665
if (flags->parsable) {
1666
(void) fprintf(fout, "size\t%llu\n", (longlong_t)size);
1667
} else {
1668
char buf[16];
1669
zfs_nicenum(size, buf, sizeof (buf));
1670
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1671
"total estimated size is %s\n"), buf);
1672
}
1673
return (0);
1674
}
1675
1676
static boolean_t
1677
redact_snaps_contains(const uint64_t *snaps, uint64_t num_snaps, uint64_t guid)
1678
{
1679
for (int i = 0; i < num_snaps; i++) {
1680
if (snaps[i] == guid)
1681
return (B_TRUE);
1682
}
1683
return (B_FALSE);
1684
}
1685
1686
static boolean_t
1687
redact_snaps_equal(const uint64_t *snaps1, uint64_t num_snaps1,
1688
const uint64_t *snaps2, uint64_t num_snaps2)
1689
{
1690
if (num_snaps1 != num_snaps2)
1691
return (B_FALSE);
1692
for (int i = 0; i < num_snaps1; i++) {
1693
if (!redact_snaps_contains(snaps2, num_snaps2, snaps1[i]))
1694
return (B_FALSE);
1695
}
1696
return (B_TRUE);
1697
}
1698
1699
static int
1700
get_bookmarks(const char *path, nvlist_t **bmarksp)
1701
{
1702
nvlist_t *props = fnvlist_alloc();
1703
int error;
1704
1705
fnvlist_add_boolean(props, "redact_complete");
1706
fnvlist_add_boolean(props, zfs_prop_to_name(ZFS_PROP_REDACT_SNAPS));
1707
error = lzc_get_bookmarks(path, props, bmarksp);
1708
fnvlist_free(props);
1709
return (error);
1710
}
1711
1712
static nvpair_t *
1713
find_redact_pair(nvlist_t *bmarks, const uint64_t *redact_snap_guids,
1714
int num_redact_snaps)
1715
{
1716
nvpair_t *pair;
1717
1718
for (pair = nvlist_next_nvpair(bmarks, NULL); pair;
1719
pair = nvlist_next_nvpair(bmarks, pair)) {
1720
1721
nvlist_t *bmark = fnvpair_value_nvlist(pair);
1722
nvlist_t *vallist = fnvlist_lookup_nvlist(bmark,
1723
zfs_prop_to_name(ZFS_PROP_REDACT_SNAPS));
1724
uint_t len = 0;
1725
uint64_t *bmarksnaps = fnvlist_lookup_uint64_array(vallist,
1726
ZPROP_VALUE, &len);
1727
if (redact_snaps_equal(redact_snap_guids,
1728
num_redact_snaps, bmarksnaps, len)) {
1729
break;
1730
}
1731
}
1732
return (pair);
1733
}
1734
1735
static boolean_t
1736
get_redact_complete(nvpair_t *pair)
1737
{
1738
nvlist_t *bmark = fnvpair_value_nvlist(pair);
1739
nvlist_t *vallist = fnvlist_lookup_nvlist(bmark, "redact_complete");
1740
boolean_t complete = fnvlist_lookup_boolean_value(vallist,
1741
ZPROP_VALUE);
1742
1743
return (complete);
1744
}
1745
1746
/*
1747
* Check that the list of redaction snapshots in the bookmark matches the send
1748
* we're resuming, and return whether or not it's complete.
1749
*
1750
* Note that the caller needs to free the contents of *bookname with free() if
1751
* this function returns successfully.
1752
*/
1753
static int
1754
find_redact_book(libzfs_handle_t *hdl, const char *path,
1755
const uint64_t *redact_snap_guids, int num_redact_snaps,
1756
char **bookname)
1757
{
1758
char errbuf[ERRBUFLEN];
1759
nvlist_t *bmarks;
1760
1761
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
1762
"cannot resume send"));
1763
1764
int error = get_bookmarks(path, &bmarks);
1765
if (error != 0) {
1766
if (error == ESRCH) {
1767
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1768
"nonexistent redaction bookmark provided"));
1769
} else if (error == ENOENT) {
1770
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1771
"dataset to be sent no longer exists"));
1772
} else {
1773
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1774
"unknown error: %s"), zfs_strerror(error));
1775
}
1776
return (zfs_error(hdl, EZFS_BADPROP, errbuf));
1777
}
1778
nvpair_t *pair = find_redact_pair(bmarks, redact_snap_guids,
1779
num_redact_snaps);
1780
if (pair == NULL) {
1781
fnvlist_free(bmarks);
1782
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1783
"no appropriate redaction bookmark exists"));
1784
return (zfs_error(hdl, EZFS_BADPROP, errbuf));
1785
}
1786
boolean_t complete = get_redact_complete(pair);
1787
if (!complete) {
1788
fnvlist_free(bmarks);
1789
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1790
"incomplete redaction bookmark provided"));
1791
return (zfs_error(hdl, EZFS_BADPROP, errbuf));
1792
}
1793
*bookname = strndup(nvpair_name(pair), ZFS_MAX_DATASET_NAME_LEN);
1794
ASSERT3P(*bookname, !=, NULL);
1795
fnvlist_free(bmarks);
1796
return (0);
1797
}
1798
1799
static enum lzc_send_flags
1800
lzc_flags_from_resume_nvl(nvlist_t *resume_nvl)
1801
{
1802
enum lzc_send_flags lzc_flags = 0;
1803
1804
if (nvlist_exists(resume_nvl, "largeblockok"))
1805
lzc_flags |= LZC_SEND_FLAG_LARGE_BLOCK;
1806
if (nvlist_exists(resume_nvl, "embedok"))
1807
lzc_flags |= LZC_SEND_FLAG_EMBED_DATA;
1808
if (nvlist_exists(resume_nvl, "compressok"))
1809
lzc_flags |= LZC_SEND_FLAG_COMPRESS;
1810
if (nvlist_exists(resume_nvl, "rawok"))
1811
lzc_flags |= LZC_SEND_FLAG_RAW;
1812
if (nvlist_exists(resume_nvl, "savedok"))
1813
lzc_flags |= LZC_SEND_FLAG_SAVED;
1814
1815
return (lzc_flags);
1816
}
1817
1818
static int
1819
zfs_send_resume_impl_cb_impl(libzfs_handle_t *hdl, sendflags_t *flags,
1820
int outfd, nvlist_t *resume_nvl)
1821
{
1822
char errbuf[ERRBUFLEN];
1823
const char *toname;
1824
const char *fromname = NULL;
1825
uint64_t resumeobj, resumeoff, toguid, fromguid, bytes;
1826
zfs_handle_t *zhp;
1827
int error = 0;
1828
char name[ZFS_MAX_DATASET_NAME_LEN];
1829
FILE *fout = (flags->verbosity > 0 && flags->dryrun) ? stdout : stderr;
1830
uint64_t *redact_snap_guids = NULL;
1831
int num_redact_snaps = 0;
1832
char *redact_book = NULL;
1833
uint64_t size = 0;
1834
1835
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
1836
"cannot resume send"));
1837
1838
if (flags->verbosity != 0) {
1839
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
1840
"resume token contents:\n"));
1841
nvlist_print(fout, resume_nvl);
1842
}
1843
1844
if (nvlist_lookup_string(resume_nvl, "toname", &toname) != 0 ||
1845
nvlist_lookup_uint64(resume_nvl, "object", &resumeobj) != 0 ||
1846
nvlist_lookup_uint64(resume_nvl, "offset", &resumeoff) != 0 ||
1847
nvlist_lookup_uint64(resume_nvl, "bytes", &bytes) != 0 ||
1848
nvlist_lookup_uint64(resume_nvl, "toguid", &toguid) != 0) {
1849
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1850
"resume token is corrupt"));
1851
return (zfs_error(hdl, EZFS_FAULT, errbuf));
1852
}
1853
fromguid = 0;
1854
(void) nvlist_lookup_uint64(resume_nvl, "fromguid", &fromguid);
1855
1856
if (flags->saved) {
1857
(void) strlcpy(name, toname, sizeof (name));
1858
} else {
1859
error = guid_to_name(hdl, toname, toguid, B_FALSE, name);
1860
if (error != 0) {
1861
if (zfs_dataset_exists(hdl, toname, ZFS_TYPE_DATASET)) {
1862
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1863
"'%s' is no longer the same snapshot "
1864
"used in the initial send"), toname);
1865
} else {
1866
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1867
"'%s' used in the initial send no "
1868
"longer exists"), toname);
1869
}
1870
return (zfs_error(hdl, EZFS_BADPATH, errbuf));
1871
}
1872
}
1873
1874
zhp = zfs_open(hdl, name, ZFS_TYPE_DATASET);
1875
if (zhp == NULL) {
1876
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1877
"unable to access '%s'"), name);
1878
return (zfs_error(hdl, EZFS_BADPATH, errbuf));
1879
}
1880
1881
if (nvlist_lookup_uint64_array(resume_nvl, "book_redact_snaps",
1882
&redact_snap_guids, (uint_t *)&num_redact_snaps) != 0) {
1883
num_redact_snaps = -1;
1884
}
1885
1886
if (fromguid != 0) {
1887
if (guid_to_name_redact_snaps(hdl, toname, fromguid, B_TRUE,
1888
redact_snap_guids, num_redact_snaps, name) != 0) {
1889
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1890
"incremental source %#llx no longer exists"),
1891
(longlong_t)fromguid);
1892
return (zfs_error(hdl, EZFS_BADPATH, errbuf));
1893
}
1894
fromname = name;
1895
}
1896
1897
redact_snap_guids = NULL;
1898
1899
if (nvlist_lookup_uint64_array(resume_nvl,
1900
zfs_prop_to_name(ZFS_PROP_REDACT_SNAPS), &redact_snap_guids,
1901
(uint_t *)&num_redact_snaps) == 0) {
1902
char path[ZFS_MAX_DATASET_NAME_LEN];
1903
1904
(void) strlcpy(path, toname, sizeof (path));
1905
char *at = strchr(path, '@');
1906
ASSERT3P(at, !=, NULL);
1907
1908
*at = '\0';
1909
1910
if ((error = find_redact_book(hdl, path, redact_snap_guids,
1911
num_redact_snaps, &redact_book)) != 0) {
1912
return (error);
1913
}
1914
}
1915
1916
enum lzc_send_flags lzc_flags = lzc_flags_from_sendflags(flags) |
1917
lzc_flags_from_resume_nvl(resume_nvl);
1918
1919
if (flags->verbosity != 0 || flags->progressastitle) {
1920
/*
1921
* Some of these may have come from the resume token, set them
1922
* here for size estimate purposes.
1923
*/
1924
sendflags_t tmpflags = *flags;
1925
if (lzc_flags & LZC_SEND_FLAG_LARGE_BLOCK)
1926
tmpflags.largeblock = B_TRUE;
1927
if (lzc_flags & LZC_SEND_FLAG_COMPRESS)
1928
tmpflags.compress = B_TRUE;
1929
if (lzc_flags & LZC_SEND_FLAG_EMBED_DATA)
1930
tmpflags.embed_data = B_TRUE;
1931
if (lzc_flags & LZC_SEND_FLAG_RAW)
1932
tmpflags.raw = B_TRUE;
1933
if (lzc_flags & LZC_SEND_FLAG_SAVED)
1934
tmpflags.saved = B_TRUE;
1935
error = estimate_size(zhp, fromname, outfd, &tmpflags,
1936
resumeobj, resumeoff, bytes, redact_book, errbuf, &size);
1937
}
1938
1939
if (!flags->dryrun) {
1940
progress_arg_t pa = { 0 };
1941
pthread_t tid;
1942
sigset_t oldmask;
1943
/*
1944
* If progress reporting is requested, spawn a new thread to
1945
* poll ZFS_IOC_SEND_PROGRESS at a regular interval.
1946
*/
1947
{
1948
pa.pa_zhp = zhp;
1949
pa.pa_fd = outfd;
1950
pa.pa_parsable = flags->parsable;
1951
pa.pa_estimate = B_FALSE;
1952
pa.pa_verbosity = flags->verbosity;
1953
pa.pa_size = size;
1954
pa.pa_astitle = flags->progressastitle;
1955
pa.pa_progress = flags->progress;
1956
1957
error = pthread_create(&tid, NULL,
1958
send_progress_thread, &pa);
1959
if (error != 0) {
1960
if (redact_book != NULL)
1961
free(redact_book);
1962
zfs_close(zhp);
1963
return (error);
1964
}
1965
SEND_PROGRESS_THREAD_PARENT_BLOCK(&oldmask);
1966
}
1967
1968
error = lzc_send_resume_redacted(zhp->zfs_name, fromname, outfd,
1969
lzc_flags, resumeobj, resumeoff, redact_book);
1970
if (redact_book != NULL)
1971
free(redact_book);
1972
1973
if (send_progress_thread_exit(hdl, tid, &oldmask)) {
1974
zfs_close(zhp);
1975
return (-1);
1976
}
1977
1978
char errbuf[ERRBUFLEN];
1979
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
1980
"warning: cannot send '%s'"), zhp->zfs_name);
1981
1982
zfs_close(zhp);
1983
1984
switch (error) {
1985
case 0:
1986
return (0);
1987
case EACCES:
1988
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1989
"source key must be loaded"));
1990
return (zfs_error(hdl, EZFS_CRYPTOFAILED, errbuf));
1991
case ESRCH:
1992
if (lzc_exists(zhp->zfs_name)) {
1993
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1994
"incremental source could not be found"));
1995
}
1996
return (zfs_error(hdl, EZFS_NOENT, errbuf));
1997
1998
case EXDEV:
1999
case ENOENT:
2000
case EDQUOT:
2001
case EFBIG:
2002
case EIO:
2003
case ENOLINK:
2004
case ENOSPC:
2005
case ENOSTR:
2006
case ENXIO:
2007
case EPIPE:
2008
case ERANGE:
2009
case EFAULT:
2010
case EROFS:
2011
zfs_error_aux(hdl, "%s", zfs_strerror(errno));
2012
return (zfs_error(hdl, EZFS_BADBACKUP, errbuf));
2013
2014
default:
2015
return (zfs_standard_error(hdl, errno, errbuf));
2016
}
2017
} else {
2018
if (redact_book != NULL)
2019
free(redact_book);
2020
}
2021
2022
zfs_close(zhp);
2023
2024
return (error);
2025
}
2026
2027
struct zfs_send_resume_impl {
2028
libzfs_handle_t *hdl;
2029
sendflags_t *flags;
2030
nvlist_t *resume_nvl;
2031
};
2032
2033
static int
2034
zfs_send_resume_impl_cb(int outfd, void *arg)
2035
{
2036
struct zfs_send_resume_impl *zsri = arg;
2037
return (zfs_send_resume_impl_cb_impl(zsri->hdl, zsri->flags, outfd,
2038
zsri->resume_nvl));
2039
}
2040
2041
static int
2042
zfs_send_resume_impl(libzfs_handle_t *hdl, sendflags_t *flags, int outfd,
2043
nvlist_t *resume_nvl)
2044
{
2045
struct zfs_send_resume_impl zsri = {
2046
.hdl = hdl,
2047
.flags = flags,
2048
.resume_nvl = resume_nvl,
2049
};
2050
return (lzc_send_wrapper(zfs_send_resume_impl_cb, outfd, &zsri));
2051
}
2052
2053
int
2054
zfs_send_resume(libzfs_handle_t *hdl, sendflags_t *flags, int outfd,
2055
const char *resume_token)
2056
{
2057
int ret;
2058
char errbuf[ERRBUFLEN];
2059
nvlist_t *resume_nvl;
2060
2061
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2062
"cannot resume send"));
2063
2064
resume_nvl = zfs_send_resume_token_to_nvlist(hdl, resume_token);
2065
if (resume_nvl == NULL) {
2066
/*
2067
* zfs_error_aux has already been set by
2068
* zfs_send_resume_token_to_nvlist()
2069
*/
2070
return (zfs_error(hdl, EZFS_FAULT, errbuf));
2071
}
2072
2073
ret = zfs_send_resume_impl(hdl, flags, outfd, resume_nvl);
2074
fnvlist_free(resume_nvl);
2075
2076
return (ret);
2077
}
2078
2079
int
2080
zfs_send_saved(zfs_handle_t *zhp, sendflags_t *flags, int outfd,
2081
const char *resume_token)
2082
{
2083
int ret;
2084
libzfs_handle_t *hdl = zhp->zfs_hdl;
2085
nvlist_t *saved_nvl = NULL, *resume_nvl = NULL;
2086
uint64_t saved_guid = 0, resume_guid = 0;
2087
uint64_t obj = 0, off = 0, bytes = 0;
2088
char token_buf[ZFS_MAXPROPLEN];
2089
char errbuf[ERRBUFLEN];
2090
2091
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2092
"saved send failed"));
2093
2094
ret = zfs_prop_get(zhp, ZFS_PROP_RECEIVE_RESUME_TOKEN,
2095
token_buf, sizeof (token_buf), NULL, NULL, 0, B_TRUE);
2096
if (ret != 0)
2097
goto out;
2098
2099
saved_nvl = zfs_send_resume_token_to_nvlist(hdl, token_buf);
2100
if (saved_nvl == NULL) {
2101
/*
2102
* zfs_error_aux has already been set by
2103
* zfs_send_resume_token_to_nvlist()
2104
*/
2105
ret = zfs_error(hdl, EZFS_FAULT, errbuf);
2106
goto out;
2107
}
2108
2109
/*
2110
* If a resume token is provided we use the object and offset
2111
* from that instead of the default, which starts from the
2112
* beginning.
2113
*/
2114
if (resume_token != NULL) {
2115
resume_nvl = zfs_send_resume_token_to_nvlist(hdl,
2116
resume_token);
2117
if (resume_nvl == NULL) {
2118
ret = zfs_error(hdl, EZFS_FAULT, errbuf);
2119
goto out;
2120
}
2121
2122
if (nvlist_lookup_uint64(resume_nvl, "object", &obj) != 0 ||
2123
nvlist_lookup_uint64(resume_nvl, "offset", &off) != 0 ||
2124
nvlist_lookup_uint64(resume_nvl, "bytes", &bytes) != 0 ||
2125
nvlist_lookup_uint64(resume_nvl, "toguid",
2126
&resume_guid) != 0) {
2127
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2128
"provided resume token is corrupt"));
2129
ret = zfs_error(hdl, EZFS_FAULT, errbuf);
2130
goto out;
2131
}
2132
2133
if (nvlist_lookup_uint64(saved_nvl, "toguid",
2134
&saved_guid)) {
2135
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2136
"dataset's resume token is corrupt"));
2137
ret = zfs_error(hdl, EZFS_FAULT, errbuf);
2138
goto out;
2139
}
2140
2141
if (resume_guid != saved_guid) {
2142
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2143
"provided resume token does not match dataset"));
2144
ret = zfs_error(hdl, EZFS_BADBACKUP, errbuf);
2145
goto out;
2146
}
2147
}
2148
2149
(void) nvlist_remove_all(saved_nvl, "object");
2150
fnvlist_add_uint64(saved_nvl, "object", obj);
2151
2152
(void) nvlist_remove_all(saved_nvl, "offset");
2153
fnvlist_add_uint64(saved_nvl, "offset", off);
2154
2155
(void) nvlist_remove_all(saved_nvl, "bytes");
2156
fnvlist_add_uint64(saved_nvl, "bytes", bytes);
2157
2158
(void) nvlist_remove_all(saved_nvl, "toname");
2159
fnvlist_add_string(saved_nvl, "toname", zhp->zfs_name);
2160
2161
ret = zfs_send_resume_impl(hdl, flags, outfd, saved_nvl);
2162
2163
out:
2164
fnvlist_free(saved_nvl);
2165
fnvlist_free(resume_nvl);
2166
return (ret);
2167
}
2168
2169
/*
2170
* This function informs the target system that the recursive send is complete.
2171
* The record is also expected in the case of a send -p.
2172
*/
2173
static int
2174
send_conclusion_record(int fd, zio_cksum_t *zc)
2175
{
2176
dmu_replay_record_t drr;
2177
memset(&drr, 0, sizeof (dmu_replay_record_t));
2178
drr.drr_type = DRR_END;
2179
if (zc != NULL)
2180
drr.drr_u.drr_end.drr_checksum = *zc;
2181
if (write(fd, &drr, sizeof (drr)) == -1) {
2182
return (errno);
2183
}
2184
return (0);
2185
}
2186
2187
/*
2188
* This function is responsible for sending the records that contain the
2189
* necessary information for the target system's libzfs to be able to set the
2190
* properties of the filesystem being received, or to be able to prepare for
2191
* a recursive receive.
2192
*
2193
* The "zhp" argument is the handle of the snapshot we are sending
2194
* (the "tosnap"). The "from" argument is the short snapshot name (the part
2195
* after the @) of the incremental source.
2196
*/
2197
static int
2198
send_prelim_records(zfs_handle_t *zhp, const char *from, int fd,
2199
boolean_t gather_props, boolean_t recursive, boolean_t verbose,
2200
boolean_t dryrun, boolean_t raw, boolean_t replicate, boolean_t skipmissing,
2201
boolean_t backup, boolean_t holds, boolean_t props, boolean_t doall,
2202
nvlist_t **fssp, avl_tree_t **fsavlp)
2203
{
2204
int err = 0;
2205
char *packbuf = NULL;
2206
size_t buflen = 0;
2207
zio_cksum_t zc = { {0} };
2208
int featureflags = 0;
2209
/* name of filesystem/volume that contains snapshot we are sending */
2210
char tofs[ZFS_MAX_DATASET_NAME_LEN];
2211
/* short name of snap we are sending */
2212
const char *tosnap = "";
2213
2214
char errbuf[ERRBUFLEN];
2215
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2216
"warning: cannot send '%s'"), zhp->zfs_name);
2217
if (zhp->zfs_type == ZFS_TYPE_FILESYSTEM && zfs_prop_get_int(zhp,
2218
ZFS_PROP_VERSION) >= ZPL_VERSION_SA) {
2219
featureflags |= DMU_BACKUP_FEATURE_SA_SPILL;
2220
}
2221
2222
if (holds)
2223
featureflags |= DMU_BACKUP_FEATURE_HOLDS;
2224
2225
(void) strlcpy(tofs, zhp->zfs_name, ZFS_MAX_DATASET_NAME_LEN);
2226
char *at = strchr(tofs, '@');
2227
if (at != NULL) {
2228
*at = '\0';
2229
tosnap = at + 1;
2230
}
2231
2232
if (gather_props) {
2233
nvlist_t *hdrnv = fnvlist_alloc();
2234
nvlist_t *fss = NULL;
2235
2236
if (from != NULL)
2237
fnvlist_add_string(hdrnv, "fromsnap", from);
2238
fnvlist_add_string(hdrnv, "tosnap", tosnap);
2239
if (!recursive)
2240
fnvlist_add_boolean(hdrnv, "not_recursive");
2241
2242
if (raw) {
2243
fnvlist_add_boolean(hdrnv, "raw");
2244
}
2245
2246
if (gather_nvlist(zhp->zfs_hdl, tofs,
2247
from, tosnap, recursive, raw, doall, replicate, skipmissing,
2248
verbose, backup, holds, props, &fss, fsavlp) != 0) {
2249
return (zfs_error(zhp->zfs_hdl, EZFS_BADBACKUP,
2250
errbuf));
2251
}
2252
/*
2253
* Do not allow the size of the properties list to exceed
2254
* the limit
2255
*/
2256
if ((fnvlist_size(fss) + fnvlist_size(hdrnv)) >
2257
zhp->zfs_hdl->libzfs_max_nvlist) {
2258
(void) snprintf(errbuf, sizeof (errbuf),
2259
dgettext(TEXT_DOMAIN, "warning: cannot send '%s': "
2260
"the size of the list of snapshots and properties "
2261
"is too large to be received successfully.\n"
2262
"Select a smaller number of snapshots to send.\n"),
2263
zhp->zfs_name);
2264
return (zfs_error(zhp->zfs_hdl, EZFS_NOSPC,
2265
errbuf));
2266
}
2267
fnvlist_add_nvlist(hdrnv, "fss", fss);
2268
VERIFY0(nvlist_pack(hdrnv, &packbuf, &buflen, NV_ENCODE_XDR,
2269
0));
2270
if (fssp != NULL) {
2271
*fssp = fss;
2272
} else {
2273
fnvlist_free(fss);
2274
}
2275
fnvlist_free(hdrnv);
2276
}
2277
2278
if (!dryrun) {
2279
dmu_replay_record_t drr;
2280
memset(&drr, 0, sizeof (dmu_replay_record_t));
2281
/* write first begin record */
2282
drr.drr_type = DRR_BEGIN;
2283
drr.drr_u.drr_begin.drr_magic = DMU_BACKUP_MAGIC;
2284
DMU_SET_STREAM_HDRTYPE(drr.drr_u.drr_begin.
2285
drr_versioninfo, DMU_COMPOUNDSTREAM);
2286
DMU_SET_FEATUREFLAGS(drr.drr_u.drr_begin.
2287
drr_versioninfo, featureflags);
2288
if (snprintf(drr.drr_u.drr_begin.drr_toname,
2289
sizeof (drr.drr_u.drr_begin.drr_toname), "%s@%s", tofs,
2290
tosnap) >= sizeof (drr.drr_u.drr_begin.drr_toname)) {
2291
return (zfs_error(zhp->zfs_hdl, EZFS_BADBACKUP,
2292
errbuf));
2293
}
2294
drr.drr_payloadlen = buflen;
2295
2296
err = dump_record(&drr, packbuf, buflen, &zc, fd);
2297
free(packbuf);
2298
if (err != 0) {
2299
zfs_error_aux(zhp->zfs_hdl, "%s", zfs_strerror(err));
2300
return (zfs_error(zhp->zfs_hdl, EZFS_BADBACKUP,
2301
errbuf));
2302
}
2303
err = send_conclusion_record(fd, &zc);
2304
if (err != 0) {
2305
zfs_error_aux(zhp->zfs_hdl, "%s", zfs_strerror(err));
2306
return (zfs_error(zhp->zfs_hdl, EZFS_BADBACKUP,
2307
errbuf));
2308
}
2309
}
2310
return (0);
2311
}
2312
2313
/*
2314
* Generate a send stream. The "zhp" argument is the filesystem/volume
2315
* that contains the snapshot to send. The "fromsnap" argument is the
2316
* short name (the part after the '@') of the snapshot that is the
2317
* incremental source to send from (if non-NULL). The "tosnap" argument
2318
* is the short name of the snapshot to send.
2319
*
2320
* The content of the send stream is the snapshot identified by
2321
* 'tosnap'. Incremental streams are requested in two ways:
2322
* - from the snapshot identified by "fromsnap" (if non-null) or
2323
* - from the origin of the dataset identified by zhp, which must
2324
* be a clone. In this case, "fromsnap" is null and "fromorigin"
2325
* is TRUE.
2326
*
2327
* The send stream is recursive (i.e. dumps a hierarchy of snapshots) and
2328
* uses a special header (with a hdrtype field of DMU_COMPOUNDSTREAM)
2329
* if "replicate" is set. If "doall" is set, dump all the intermediate
2330
* snapshots. The DMU_COMPOUNDSTREAM header is used in the "doall"
2331
* case too. If "props" is set, send properties.
2332
*
2333
* Pre-wrapped (cf. lzc_send_wrapper()).
2334
*/
2335
static int
2336
zfs_send_cb_impl(zfs_handle_t *zhp, const char *fromsnap, const char *tosnap,
2337
sendflags_t *flags, int outfd, snapfilter_cb_t filter_func,
2338
void *cb_arg, nvlist_t **debugnvp)
2339
{
2340
char errbuf[ERRBUFLEN];
2341
send_dump_data_t sdd = { 0 };
2342
int err = 0;
2343
nvlist_t *fss = NULL;
2344
avl_tree_t *fsavl = NULL;
2345
static uint64_t holdseq;
2346
int spa_version;
2347
FILE *fout;
2348
2349
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2350
"cannot send '%s'"), zhp->zfs_name);
2351
2352
if (fromsnap && fromsnap[0] == '\0') {
2353
zfs_error_aux(zhp->zfs_hdl, dgettext(TEXT_DOMAIN,
2354
"zero-length incremental source"));
2355
return (zfs_error(zhp->zfs_hdl, EZFS_NOENT, errbuf));
2356
}
2357
2358
if (fromsnap) {
2359
char full_fromsnap_name[ZFS_MAX_DATASET_NAME_LEN];
2360
if (snprintf(full_fromsnap_name, sizeof (full_fromsnap_name),
2361
"%s@%s", zhp->zfs_name, fromsnap) >=
2362
sizeof (full_fromsnap_name)) {
2363
err = EINVAL;
2364
goto stderr_out;
2365
}
2366
zfs_handle_t *fromsnapn = zfs_open(zhp->zfs_hdl,
2367
full_fromsnap_name, ZFS_TYPE_SNAPSHOT);
2368
if (fromsnapn == NULL) {
2369
err = -1;
2370
goto err_out;
2371
}
2372
zfs_close(fromsnapn);
2373
}
2374
2375
if (flags->replicate || flags->doall || flags->props ||
2376
flags->holds || flags->backup) {
2377
char full_tosnap_name[ZFS_MAX_DATASET_NAME_LEN];
2378
if (snprintf(full_tosnap_name, sizeof (full_tosnap_name),
2379
"%s@%s", zhp->zfs_name, tosnap) >=
2380
sizeof (full_tosnap_name)) {
2381
err = EINVAL;
2382
goto stderr_out;
2383
}
2384
zfs_handle_t *tosnap = zfs_open(zhp->zfs_hdl,
2385
full_tosnap_name, ZFS_TYPE_SNAPSHOT);
2386
if (tosnap == NULL) {
2387
err = -1;
2388
goto err_out;
2389
}
2390
err = send_prelim_records(tosnap, fromsnap, outfd,
2391
flags->replicate || flags->props || flags->holds,
2392
flags->replicate, flags->verbosity > 0, flags->dryrun,
2393
flags->raw, flags->replicate, flags->skipmissing,
2394
flags->backup, flags->holds, flags->props, flags->doall,
2395
&fss, &fsavl);
2396
zfs_close(tosnap);
2397
if (err != 0)
2398
goto err_out;
2399
}
2400
2401
/* dump each stream */
2402
sdd.fromsnap = fromsnap;
2403
sdd.tosnap = tosnap;
2404
sdd.outfd = outfd;
2405
sdd.replicate = flags->replicate;
2406
sdd.doall = flags->doall;
2407
sdd.fromorigin = flags->fromorigin;
2408
sdd.fss = fss;
2409
sdd.fsavl = fsavl;
2410
sdd.verbosity = flags->verbosity;
2411
sdd.parsable = flags->parsable;
2412
sdd.progress = flags->progress;
2413
sdd.progressastitle = flags->progressastitle;
2414
sdd.dryrun = flags->dryrun;
2415
sdd.large_block = flags->largeblock;
2416
sdd.embed_data = flags->embed_data;
2417
sdd.compress = flags->compress;
2418
sdd.raw = flags->raw;
2419
sdd.holds = flags->holds;
2420
sdd.filter_cb = filter_func;
2421
sdd.filter_cb_arg = cb_arg;
2422
if (debugnvp)
2423
sdd.debugnv = *debugnvp;
2424
if (sdd.verbosity != 0 && sdd.dryrun)
2425
sdd.std_out = B_TRUE;
2426
fout = sdd.std_out ? stdout : stderr;
2427
2428
/*
2429
* Some flags require that we place user holds on the datasets that are
2430
* being sent so they don't get destroyed during the send. We can skip
2431
* this step if the pool is imported read-only since the datasets cannot
2432
* be destroyed.
2433
*/
2434
if (!flags->dryrun && !zpool_get_prop_int(zfs_get_pool_handle(zhp),
2435
ZPOOL_PROP_READONLY, NULL) &&
2436
zfs_spa_version(zhp, &spa_version) == 0 &&
2437
spa_version >= SPA_VERSION_USERREFS &&
2438
(flags->doall || flags->replicate)) {
2439
++holdseq;
2440
(void) snprintf(sdd.holdtag, sizeof (sdd.holdtag),
2441
".send-%d-%llu", getpid(), (u_longlong_t)holdseq);
2442
sdd.cleanup_fd = open(ZFS_DEV, O_RDWR | O_CLOEXEC);
2443
if (sdd.cleanup_fd < 0) {
2444
err = errno;
2445
goto stderr_out;
2446
}
2447
sdd.snapholds = fnvlist_alloc();
2448
} else {
2449
sdd.cleanup_fd = -1;
2450
sdd.snapholds = NULL;
2451
}
2452
2453
if (flags->verbosity != 0 || sdd.snapholds != NULL) {
2454
/*
2455
* Do a verbose no-op dry run to get all the verbose output
2456
* or to gather snapshot hold's before generating any data,
2457
* then do a non-verbose real run to generate the streams.
2458
*/
2459
sdd.dryrun = B_TRUE;
2460
err = dump_filesystems(zhp, &sdd);
2461
2462
if (err != 0)
2463
goto stderr_out;
2464
2465
if (flags->verbosity != 0) {
2466
if (flags->parsable) {
2467
(void) fprintf(fout, "size\t%llu\n",
2468
(longlong_t)sdd.size);
2469
} else {
2470
char buf[16];
2471
zfs_nicebytes(sdd.size, buf, sizeof (buf));
2472
(void) fprintf(fout, dgettext(TEXT_DOMAIN,
2473
"total estimated size is %s\n"), buf);
2474
}
2475
}
2476
2477
/* Ensure no snaps found is treated as an error. */
2478
if (!sdd.seento) {
2479
err = ENOENT;
2480
goto err_out;
2481
}
2482
2483
/* Skip the second run if dryrun was requested. */
2484
if (flags->dryrun)
2485
goto err_out;
2486
2487
if (sdd.snapholds != NULL) {
2488
err = zfs_hold_nvl(zhp, sdd.cleanup_fd, sdd.snapholds);
2489
if (err != 0)
2490
goto stderr_out;
2491
2492
fnvlist_free(sdd.snapholds);
2493
sdd.snapholds = NULL;
2494
}
2495
2496
sdd.dryrun = B_FALSE;
2497
sdd.verbosity = 0;
2498
}
2499
2500
err = dump_filesystems(zhp, &sdd);
2501
fsavl_destroy(fsavl);
2502
fnvlist_free(fss);
2503
2504
/* Ensure no snaps found is treated as an error. */
2505
if (err == 0 && !sdd.seento)
2506
err = ENOENT;
2507
2508
if (sdd.cleanup_fd != -1) {
2509
VERIFY0(close(sdd.cleanup_fd));
2510
sdd.cleanup_fd = -1;
2511
}
2512
2513
if (!flags->dryrun && (flags->replicate || flags->doall ||
2514
flags->props || flags->backup || flags->holds)) {
2515
/*
2516
* write final end record. NB: want to do this even if
2517
* there was some error, because it might not be totally
2518
* failed.
2519
*/
2520
int err2 = send_conclusion_record(outfd, NULL);
2521
if (err2 != 0)
2522
return (zfs_standard_error(zhp->zfs_hdl, err2, errbuf));
2523
}
2524
2525
return (err || sdd.err);
2526
2527
stderr_out:
2528
err = zfs_standard_error(zhp->zfs_hdl, err, errbuf);
2529
err_out:
2530
fsavl_destroy(fsavl);
2531
fnvlist_free(fss);
2532
fnvlist_free(sdd.snapholds);
2533
2534
if (sdd.cleanup_fd != -1)
2535
VERIFY0(close(sdd.cleanup_fd));
2536
return (err);
2537
}
2538
2539
struct zfs_send {
2540
zfs_handle_t *zhp;
2541
const char *fromsnap;
2542
const char *tosnap;
2543
sendflags_t *flags;
2544
snapfilter_cb_t *filter_func;
2545
void *cb_arg;
2546
nvlist_t **debugnvp;
2547
};
2548
2549
static int
2550
zfs_send_cb(int outfd, void *arg)
2551
{
2552
struct zfs_send *zs = arg;
2553
return (zfs_send_cb_impl(zs->zhp, zs->fromsnap, zs->tosnap, zs->flags,
2554
outfd, zs->filter_func, zs->cb_arg, zs->debugnvp));
2555
}
2556
2557
int
2558
zfs_send(zfs_handle_t *zhp, const char *fromsnap, const char *tosnap,
2559
sendflags_t *flags, int outfd, snapfilter_cb_t filter_func,
2560
void *cb_arg, nvlist_t **debugnvp)
2561
{
2562
struct zfs_send arg = {
2563
.zhp = zhp,
2564
.fromsnap = fromsnap,
2565
.tosnap = tosnap,
2566
.flags = flags,
2567
.filter_func = filter_func,
2568
.cb_arg = cb_arg,
2569
.debugnvp = debugnvp,
2570
};
2571
return (lzc_send_wrapper(zfs_send_cb, outfd, &arg));
2572
}
2573
2574
2575
static zfs_handle_t *
2576
name_to_dir_handle(libzfs_handle_t *hdl, const char *snapname)
2577
{
2578
char dirname[ZFS_MAX_DATASET_NAME_LEN];
2579
(void) strlcpy(dirname, snapname, ZFS_MAX_DATASET_NAME_LEN);
2580
char *c = strchr(dirname, '@');
2581
if (c != NULL)
2582
*c = '\0';
2583
return (zfs_open(hdl, dirname, ZFS_TYPE_DATASET));
2584
}
2585
2586
/*
2587
* Returns B_TRUE if earlier is an earlier snapshot in later's timeline; either
2588
* an earlier snapshot in the same filesystem, or a snapshot before later's
2589
* origin, or it's origin's origin, etc.
2590
*/
2591
static boolean_t
2592
snapshot_is_before(zfs_handle_t *earlier, zfs_handle_t *later)
2593
{
2594
boolean_t ret;
2595
uint64_t later_txg =
2596
(later->zfs_type == ZFS_TYPE_FILESYSTEM ||
2597
later->zfs_type == ZFS_TYPE_VOLUME ?
2598
UINT64_MAX : zfs_prop_get_int(later, ZFS_PROP_CREATETXG));
2599
uint64_t earlier_txg = zfs_prop_get_int(earlier, ZFS_PROP_CREATETXG);
2600
2601
if (earlier_txg >= later_txg)
2602
return (B_FALSE);
2603
2604
zfs_handle_t *earlier_dir = name_to_dir_handle(earlier->zfs_hdl,
2605
earlier->zfs_name);
2606
zfs_handle_t *later_dir = name_to_dir_handle(later->zfs_hdl,
2607
later->zfs_name);
2608
2609
if (strcmp(earlier_dir->zfs_name, later_dir->zfs_name) == 0) {
2610
zfs_close(earlier_dir);
2611
zfs_close(later_dir);
2612
return (B_TRUE);
2613
}
2614
2615
char clonename[ZFS_MAX_DATASET_NAME_LEN];
2616
if (zfs_prop_get(later_dir, ZFS_PROP_ORIGIN, clonename,
2617
ZFS_MAX_DATASET_NAME_LEN, NULL, NULL, 0, B_TRUE) != 0) {
2618
zfs_close(earlier_dir);
2619
zfs_close(later_dir);
2620
return (B_FALSE);
2621
}
2622
2623
zfs_handle_t *origin = zfs_open(earlier->zfs_hdl, clonename,
2624
ZFS_TYPE_DATASET);
2625
uint64_t origin_txg = zfs_prop_get_int(origin, ZFS_PROP_CREATETXG);
2626
2627
/*
2628
* If "earlier" is exactly the origin, then
2629
* snapshot_is_before(earlier, origin) will return false (because
2630
* they're the same).
2631
*/
2632
if (origin_txg == earlier_txg &&
2633
strcmp(origin->zfs_name, earlier->zfs_name) == 0) {
2634
zfs_close(earlier_dir);
2635
zfs_close(later_dir);
2636
zfs_close(origin);
2637
return (B_TRUE);
2638
}
2639
zfs_close(earlier_dir);
2640
zfs_close(later_dir);
2641
2642
ret = snapshot_is_before(earlier, origin);
2643
zfs_close(origin);
2644
return (ret);
2645
}
2646
2647
/*
2648
* The "zhp" argument is the handle of the dataset to send (typically a
2649
* snapshot). The "from" argument is the full name of the snapshot or
2650
* bookmark that is the incremental source.
2651
*
2652
* Pre-wrapped (cf. lzc_send_wrapper()).
2653
*/
2654
static int
2655
zfs_send_one_cb_impl(zfs_handle_t *zhp, const char *from, int fd,
2656
sendflags_t *flags, const char *redactbook)
2657
{
2658
int err;
2659
libzfs_handle_t *hdl = zhp->zfs_hdl;
2660
char *name = zhp->zfs_name;
2661
pthread_t ptid;
2662
progress_arg_t pa = { 0 };
2663
uint64_t size = 0;
2664
2665
char errbuf[ERRBUFLEN];
2666
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2667
"warning: cannot send '%s'"), name);
2668
2669
if (from != NULL && strchr(from, '@')) {
2670
zfs_handle_t *from_zhp = zfs_open(hdl, from,
2671
ZFS_TYPE_DATASET);
2672
if (from_zhp == NULL)
2673
return (-1);
2674
if (!snapshot_is_before(from_zhp, zhp)) {
2675
zfs_close(from_zhp);
2676
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2677
"not an earlier snapshot from the same fs"));
2678
return (zfs_error(hdl, EZFS_CROSSTARGET, errbuf));
2679
}
2680
zfs_close(from_zhp);
2681
}
2682
2683
if (redactbook != NULL) {
2684
char bookname[ZFS_MAX_DATASET_NAME_LEN];
2685
nvlist_t *redact_snaps;
2686
zfs_handle_t *book_zhp;
2687
char *at, *pound;
2688
int dsnamelen;
2689
2690
pound = strchr(redactbook, '#');
2691
if (pound != NULL)
2692
redactbook = pound + 1;
2693
at = strchr(name, '@');
2694
if (at == NULL) {
2695
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2696
"cannot do a redacted send to a filesystem"));
2697
return (zfs_error(hdl, EZFS_BADTYPE, errbuf));
2698
}
2699
dsnamelen = at - name;
2700
if (snprintf(bookname, sizeof (bookname), "%.*s#%s",
2701
dsnamelen, name, redactbook)
2702
>= sizeof (bookname)) {
2703
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2704
"invalid bookmark name"));
2705
return (zfs_error(hdl, EZFS_INVALIDNAME, errbuf));
2706
}
2707
book_zhp = zfs_open(hdl, bookname, ZFS_TYPE_BOOKMARK);
2708
if (book_zhp == NULL)
2709
return (-1);
2710
if (nvlist_lookup_nvlist(book_zhp->zfs_props,
2711
zfs_prop_to_name(ZFS_PROP_REDACT_SNAPS),
2712
&redact_snaps) != 0 || redact_snaps == NULL) {
2713
zfs_close(book_zhp);
2714
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2715
"not a redaction bookmark"));
2716
return (zfs_error(hdl, EZFS_BADTYPE, errbuf));
2717
}
2718
zfs_close(book_zhp);
2719
}
2720
2721
/*
2722
* Send fs properties
2723
*/
2724
if (flags->props || flags->holds || flags->backup) {
2725
/*
2726
* Note: the header generated by send_prelim_records()
2727
* assumes that the incremental source is in the same
2728
* filesystem/volume as the target (which is a requirement
2729
* when doing "zfs send -R"). But that isn't always the
2730
* case here (e.g. send from snap in origin, or send from
2731
* bookmark). We pass from=NULL, which will omit this
2732
* information from the prelim records; it isn't used
2733
* when receiving this type of stream.
2734
*/
2735
err = send_prelim_records(zhp, NULL, fd, B_TRUE, B_FALSE,
2736
flags->verbosity > 0, flags->dryrun, flags->raw,
2737
flags->replicate, B_FALSE, flags->backup, flags->holds,
2738
flags->props, flags->doall, NULL, NULL);
2739
if (err != 0)
2740
return (err);
2741
}
2742
2743
/*
2744
* Perform size estimate if verbose was specified.
2745
*/
2746
if (flags->verbosity != 0 || flags->progressastitle) {
2747
err = estimate_size(zhp, from, fd, flags, 0, 0, 0, redactbook,
2748
errbuf, &size);
2749
if (err != 0)
2750
return (err);
2751
}
2752
2753
if (flags->dryrun)
2754
return (0);
2755
2756
/*
2757
* If progress reporting is requested, spawn a new thread to poll
2758
* ZFS_IOC_SEND_PROGRESS at a regular interval.
2759
*/
2760
sigset_t oldmask;
2761
{
2762
pa.pa_zhp = zhp;
2763
pa.pa_fd = fd;
2764
pa.pa_parsable = flags->parsable;
2765
pa.pa_estimate = B_FALSE;
2766
pa.pa_verbosity = flags->verbosity;
2767
pa.pa_size = size;
2768
pa.pa_astitle = flags->progressastitle;
2769
pa.pa_progress = flags->progress;
2770
2771
err = pthread_create(&ptid, NULL,
2772
send_progress_thread, &pa);
2773
if (err != 0) {
2774
zfs_error_aux(zhp->zfs_hdl, "%s", zfs_strerror(errno));
2775
return (zfs_error(zhp->zfs_hdl,
2776
EZFS_THREADCREATEFAILED, errbuf));
2777
}
2778
SEND_PROGRESS_THREAD_PARENT_BLOCK(&oldmask);
2779
}
2780
2781
err = lzc_send_redacted(name, from, fd,
2782
lzc_flags_from_sendflags(flags), redactbook);
2783
2784
if (send_progress_thread_exit(hdl, ptid, &oldmask))
2785
return (-1);
2786
2787
if (err == 0 && (flags->props || flags->holds || flags->backup)) {
2788
/* Write the final end record. */
2789
err = send_conclusion_record(fd, NULL);
2790
if (err != 0)
2791
return (zfs_standard_error(hdl, err, errbuf));
2792
}
2793
if (err != 0) {
2794
switch (errno) {
2795
case EXDEV:
2796
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2797
"not an earlier snapshot from the same fs"));
2798
return (zfs_error(hdl, EZFS_CROSSTARGET, errbuf));
2799
2800
case ENOENT:
2801
case ESRCH:
2802
if (lzc_exists(name)) {
2803
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2804
"incremental source (%s) does not exist"),
2805
from);
2806
}
2807
return (zfs_error(hdl, EZFS_NOENT, errbuf));
2808
2809
case EACCES:
2810
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2811
"dataset key must be loaded"));
2812
return (zfs_error(hdl, EZFS_CRYPTOFAILED, errbuf));
2813
2814
case EBUSY:
2815
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2816
"target is busy; if a filesystem, "
2817
"it must not be mounted"));
2818
return (zfs_error(hdl, EZFS_BUSY, errbuf));
2819
2820
case EDQUOT:
2821
case EFAULT:
2822
case EFBIG:
2823
case EINVAL:
2824
case EIO:
2825
case ENOLINK:
2826
case ENOSPC:
2827
case ENOSTR:
2828
case ENXIO:
2829
case EPIPE:
2830
case ERANGE:
2831
case EROFS:
2832
zfs_error_aux(hdl, "%s", zfs_strerror(errno));
2833
return (zfs_error(hdl, EZFS_BADBACKUP, errbuf));
2834
case ZFS_ERR_STREAM_LARGE_MICROZAP:
2835
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2836
"source snapshot contains large microzaps, "
2837
"need -L (--large-block) or -w (--raw) to "
2838
"generate stream"));
2839
return (zfs_error(hdl, EZFS_BADBACKUP, errbuf));
2840
default:
2841
return (zfs_standard_error(hdl, errno, errbuf));
2842
}
2843
}
2844
return (err != 0);
2845
}
2846
2847
struct zfs_send_one {
2848
zfs_handle_t *zhp;
2849
const char *from;
2850
sendflags_t *flags;
2851
const char *redactbook;
2852
};
2853
2854
static int
2855
zfs_send_one_cb(int fd, void *arg)
2856
{
2857
struct zfs_send_one *zso = arg;
2858
return (zfs_send_one_cb_impl(zso->zhp, zso->from, fd, zso->flags,
2859
zso->redactbook));
2860
}
2861
2862
int
2863
zfs_send_one(zfs_handle_t *zhp, const char *from, int fd, sendflags_t *flags,
2864
const char *redactbook)
2865
{
2866
struct zfs_send_one zso = {
2867
.zhp = zhp,
2868
.from = from,
2869
.flags = flags,
2870
.redactbook = redactbook,
2871
};
2872
return (lzc_send_wrapper(zfs_send_one_cb, fd, &zso));
2873
}
2874
2875
/*
2876
* Routines specific to "zfs recv"
2877
*/
2878
2879
static int
2880
recv_read(libzfs_handle_t *hdl, int fd, void *buf, int ilen,
2881
boolean_t byteswap, zio_cksum_t *zc)
2882
{
2883
char *cp = buf;
2884
int rv;
2885
int len = ilen;
2886
2887
do {
2888
rv = read(fd, cp, len);
2889
cp += rv;
2890
len -= rv;
2891
} while (rv > 0);
2892
2893
if (rv < 0 || len != 0) {
2894
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2895
"failed to read from stream"));
2896
return (zfs_error(hdl, EZFS_BADSTREAM, dgettext(TEXT_DOMAIN,
2897
"cannot receive")));
2898
}
2899
2900
if (zc) {
2901
if (byteswap)
2902
fletcher_4_incremental_byteswap(buf, ilen, zc);
2903
else
2904
fletcher_4_incremental_native(buf, ilen, zc);
2905
}
2906
return (0);
2907
}
2908
2909
static int
2910
recv_read_nvlist(libzfs_handle_t *hdl, int fd, int len, nvlist_t **nvp,
2911
boolean_t byteswap, zio_cksum_t *zc)
2912
{
2913
char *buf;
2914
int err;
2915
2916
buf = zfs_alloc(hdl, len);
2917
2918
if (len > hdl->libzfs_max_nvlist) {
2919
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "nvlist too large"));
2920
free(buf);
2921
return (ENOMEM);
2922
}
2923
2924
err = recv_read(hdl, fd, buf, len, byteswap, zc);
2925
if (err != 0) {
2926
free(buf);
2927
return (err);
2928
}
2929
2930
err = nvlist_unpack(buf, len, nvp, 0);
2931
free(buf);
2932
if (err != 0) {
2933
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "invalid "
2934
"stream (malformed nvlist)"));
2935
return (EINVAL);
2936
}
2937
return (0);
2938
}
2939
2940
/*
2941
* Returns the grand origin (origin of origin of origin...) of a given handle.
2942
* If this dataset is not a clone, it simply returns a copy of the original
2943
* handle.
2944
*/
2945
static zfs_handle_t *
2946
recv_open_grand_origin(zfs_handle_t *zhp)
2947
{
2948
char origin[ZFS_MAX_DATASET_NAME_LEN];
2949
zprop_source_t src;
2950
zfs_handle_t *ozhp = zfs_handle_dup(zhp);
2951
2952
while (ozhp != NULL) {
2953
if (zfs_prop_get(ozhp, ZFS_PROP_ORIGIN, origin,
2954
sizeof (origin), &src, NULL, 0, B_FALSE) != 0)
2955
break;
2956
2957
(void) zfs_close(ozhp);
2958
ozhp = zfs_open(zhp->zfs_hdl, origin, ZFS_TYPE_FILESYSTEM);
2959
}
2960
2961
return (ozhp);
2962
}
2963
2964
static int
2965
recv_rename_impl(zfs_handle_t *zhp, const char *name, const char *newname)
2966
{
2967
int err;
2968
zfs_handle_t *ozhp = NULL;
2969
2970
/*
2971
* Attempt to rename the dataset. If it fails with EACCES we have
2972
* attempted to rename the dataset outside of its encryption root.
2973
* Force the dataset to become an encryption root and try again.
2974
*/
2975
err = lzc_rename(name, newname);
2976
if (err == EACCES) {
2977
ozhp = recv_open_grand_origin(zhp);
2978
if (ozhp == NULL) {
2979
err = ENOENT;
2980
goto out;
2981
}
2982
2983
err = lzc_change_key(ozhp->zfs_name, DCP_CMD_FORCE_NEW_KEY,
2984
NULL, NULL, 0);
2985
if (err != 0)
2986
goto out;
2987
2988
err = lzc_rename(name, newname);
2989
}
2990
2991
out:
2992
if (ozhp != NULL)
2993
zfs_close(ozhp);
2994
return (err);
2995
}
2996
2997
static int
2998
recv_rename(libzfs_handle_t *hdl, const char *name, const char *tryname,
2999
int baselen, char *newname, recvflags_t *flags)
3000
{
3001
static int seq;
3002
int err;
3003
prop_changelist_t *clp = NULL;
3004
zfs_handle_t *zhp = NULL;
3005
3006
zhp = zfs_open(hdl, name, ZFS_TYPE_DATASET);
3007
if (zhp == NULL) {
3008
err = -1;
3009
goto out;
3010
}
3011
clp = changelist_gather(zhp, ZFS_PROP_NAME, 0,
3012
flags->force ? MS_FORCE : 0);
3013
if (clp == NULL) {
3014
err = -1;
3015
goto out;
3016
}
3017
err = changelist_prefix(clp);
3018
if (err)
3019
goto out;
3020
3021
if (tryname) {
3022
(void) strlcpy(newname, tryname, ZFS_MAX_DATASET_NAME_LEN);
3023
if (flags->verbose) {
3024
(void) printf("attempting rename %s to %s\n",
3025
name, newname);
3026
}
3027
err = recv_rename_impl(zhp, name, newname);
3028
if (err == 0)
3029
changelist_rename(clp, name, tryname);
3030
} else {
3031
err = ENOENT;
3032
}
3033
3034
if (err != 0 && strncmp(name + baselen, "recv-", 5) != 0) {
3035
seq++;
3036
3037
(void) snprintf(newname, ZFS_MAX_DATASET_NAME_LEN,
3038
"%.*srecv-%u-%u", baselen, name, getpid(), seq);
3039
3040
if (flags->verbose) {
3041
(void) printf("failed - trying rename %s to %s\n",
3042
name, newname);
3043
}
3044
err = recv_rename_impl(zhp, name, newname);
3045
if (err == 0)
3046
changelist_rename(clp, name, newname);
3047
if (err && flags->verbose) {
3048
(void) printf("failed (%u) - "
3049
"will try again on next pass\n", errno);
3050
}
3051
err = EAGAIN;
3052
} else if (flags->verbose) {
3053
if (err == 0)
3054
(void) printf("success\n");
3055
else
3056
(void) printf("failed (%u)\n", errno);
3057
}
3058
3059
(void) changelist_postfix(clp);
3060
3061
out:
3062
if (clp != NULL)
3063
changelist_free(clp);
3064
if (zhp != NULL)
3065
zfs_close(zhp);
3066
3067
return (err);
3068
}
3069
3070
static int
3071
recv_promote(libzfs_handle_t *hdl, const char *fsname,
3072
const char *origin_fsname, recvflags_t *flags)
3073
{
3074
int err;
3075
zfs_cmd_t zc = {"\0"};
3076
zfs_handle_t *zhp = NULL, *ozhp = NULL;
3077
3078
if (flags->verbose)
3079
(void) printf("promoting %s\n", fsname);
3080
3081
(void) strlcpy(zc.zc_value, origin_fsname, sizeof (zc.zc_value));
3082
(void) strlcpy(zc.zc_name, fsname, sizeof (zc.zc_name));
3083
3084
/*
3085
* Attempt to promote the dataset. If it fails with EACCES the
3086
* promotion would cause this dataset to leave its encryption root.
3087
* Force the origin to become an encryption root and try again.
3088
*/
3089
err = zfs_ioctl(hdl, ZFS_IOC_PROMOTE, &zc);
3090
if (err == EACCES) {
3091
zhp = zfs_open(hdl, fsname, ZFS_TYPE_DATASET);
3092
if (zhp == NULL) {
3093
err = -1;
3094
goto out;
3095
}
3096
3097
ozhp = recv_open_grand_origin(zhp);
3098
if (ozhp == NULL) {
3099
err = -1;
3100
goto out;
3101
}
3102
3103
err = lzc_change_key(ozhp->zfs_name, DCP_CMD_FORCE_NEW_KEY,
3104
NULL, NULL, 0);
3105
if (err != 0)
3106
goto out;
3107
3108
err = zfs_ioctl(hdl, ZFS_IOC_PROMOTE, &zc);
3109
}
3110
3111
out:
3112
if (zhp != NULL)
3113
zfs_close(zhp);
3114
if (ozhp != NULL)
3115
zfs_close(ozhp);
3116
3117
return (err);
3118
}
3119
3120
static int
3121
recv_destroy(libzfs_handle_t *hdl, const char *name, int baselen,
3122
char *newname, recvflags_t *flags)
3123
{
3124
int err = 0;
3125
prop_changelist_t *clp;
3126
zfs_handle_t *zhp;
3127
boolean_t defer = B_FALSE;
3128
int spa_version;
3129
3130
zhp = zfs_open(hdl, name, ZFS_TYPE_DATASET);
3131
if (zhp == NULL)
3132
return (-1);
3133
zfs_type_t type = zfs_get_type(zhp);
3134
if (type == ZFS_TYPE_SNAPSHOT &&
3135
zfs_spa_version(zhp, &spa_version) == 0 &&
3136
spa_version >= SPA_VERSION_USERREFS)
3137
defer = B_TRUE;
3138
clp = changelist_gather(zhp, ZFS_PROP_NAME, 0,
3139
flags->force ? MS_FORCE : 0);
3140
zfs_close(zhp);
3141
if (clp == NULL)
3142
return (-1);
3143
3144
err = changelist_prefix(clp);
3145
if (err)
3146
return (err);
3147
3148
if (flags->verbose)
3149
(void) printf("attempting destroy %s\n", name);
3150
if (type == ZFS_TYPE_SNAPSHOT) {
3151
nvlist_t *nv = fnvlist_alloc();
3152
fnvlist_add_boolean(nv, name);
3153
err = lzc_destroy_snaps(nv, defer, NULL);
3154
fnvlist_free(nv);
3155
} else {
3156
err = lzc_destroy(name);
3157
}
3158
if (err == 0) {
3159
if (flags->verbose)
3160
(void) printf("success\n");
3161
changelist_remove(clp, name);
3162
}
3163
3164
(void) changelist_postfix(clp);
3165
changelist_free(clp);
3166
3167
/*
3168
* Deferred destroy might destroy the snapshot or only mark it to be
3169
* destroyed later, and it returns success in either case.
3170
*/
3171
if (err != 0 || (defer && zfs_dataset_exists(hdl, name,
3172
ZFS_TYPE_SNAPSHOT))) {
3173
err = recv_rename(hdl, name, NULL, baselen, newname, flags);
3174
}
3175
3176
return (err);
3177
}
3178
3179
typedef struct guid_to_name_data {
3180
uint64_t guid;
3181
boolean_t bookmark_ok;
3182
char *name;
3183
char *skip;
3184
uint64_t *redact_snap_guids;
3185
uint64_t num_redact_snaps;
3186
} guid_to_name_data_t;
3187
3188
static boolean_t
3189
redact_snaps_match(zfs_handle_t *zhp, guid_to_name_data_t *gtnd)
3190
{
3191
uint64_t *bmark_snaps;
3192
uint_t bmark_num_snaps;
3193
nvlist_t *nvl;
3194
if (zhp->zfs_type != ZFS_TYPE_BOOKMARK)
3195
return (B_FALSE);
3196
3197
nvl = fnvlist_lookup_nvlist(zhp->zfs_props,
3198
zfs_prop_to_name(ZFS_PROP_REDACT_SNAPS));
3199
bmark_snaps = fnvlist_lookup_uint64_array(nvl, ZPROP_VALUE,
3200
&bmark_num_snaps);
3201
if (bmark_num_snaps != gtnd->num_redact_snaps)
3202
return (B_FALSE);
3203
int i = 0;
3204
for (; i < bmark_num_snaps; i++) {
3205
int j = 0;
3206
for (; j < bmark_num_snaps; j++) {
3207
if (bmark_snaps[i] == gtnd->redact_snap_guids[j])
3208
break;
3209
}
3210
if (j == bmark_num_snaps)
3211
break;
3212
}
3213
return (i == bmark_num_snaps);
3214
}
3215
3216
static int
3217
guid_to_name_cb(zfs_handle_t *zhp, void *arg)
3218
{
3219
guid_to_name_data_t *gtnd = arg;
3220
const char *slash;
3221
int err;
3222
3223
if (gtnd->skip != NULL &&
3224
(slash = strrchr(zhp->zfs_name, '/')) != NULL &&
3225
strcmp(slash + 1, gtnd->skip) == 0) {
3226
zfs_close(zhp);
3227
return (0);
3228
}
3229
3230
if (zfs_prop_get_int(zhp, ZFS_PROP_GUID) == gtnd->guid &&
3231
(gtnd->num_redact_snaps == -1 || redact_snaps_match(zhp, gtnd))) {
3232
(void) strcpy(gtnd->name, zhp->zfs_name);
3233
zfs_close(zhp);
3234
return (EEXIST);
3235
}
3236
3237
err = zfs_iter_children_v2(zhp, 0, guid_to_name_cb, gtnd);
3238
if (err != EEXIST && gtnd->bookmark_ok)
3239
err = zfs_iter_bookmarks_v2(zhp, 0, guid_to_name_cb, gtnd);
3240
zfs_close(zhp);
3241
return (err);
3242
}
3243
3244
/*
3245
* Attempt to find the local dataset associated with this guid. In the case of
3246
* multiple matches, we attempt to find the "best" match by searching
3247
* progressively larger portions of the hierarchy. This allows one to send a
3248
* tree of datasets individually and guarantee that we will find the source
3249
* guid within that hierarchy, even if there are multiple matches elsewhere.
3250
*
3251
* If num_redact_snaps is not -1, we attempt to find a redaction bookmark with
3252
* the specified number of redaction snapshots. If num_redact_snaps isn't 0 or
3253
* -1, then redact_snap_guids will be an array of the guids of the snapshots the
3254
* redaction bookmark was created with. If num_redact_snaps is -1, then we will
3255
* attempt to find a snapshot or bookmark (if bookmark_ok is passed) with the
3256
* given guid. Note that a redaction bookmark can be returned if
3257
* num_redact_snaps == -1.
3258
*/
3259
static int
3260
guid_to_name_redact_snaps(libzfs_handle_t *hdl, const char *parent,
3261
uint64_t guid, boolean_t bookmark_ok, uint64_t *redact_snap_guids,
3262
uint64_t num_redact_snaps, char *name)
3263
{
3264
char pname[ZFS_MAX_DATASET_NAME_LEN];
3265
guid_to_name_data_t gtnd;
3266
3267
gtnd.guid = guid;
3268
gtnd.bookmark_ok = bookmark_ok;
3269
gtnd.name = name;
3270
gtnd.skip = NULL;
3271
gtnd.redact_snap_guids = redact_snap_guids;
3272
gtnd.num_redact_snaps = num_redact_snaps;
3273
3274
/*
3275
* Search progressively larger portions of the hierarchy, starting
3276
* with the filesystem specified by 'parent'. This will
3277
* select the "most local" version of the origin snapshot in the case
3278
* that there are multiple matching snapshots in the system.
3279
*/
3280
(void) strlcpy(pname, parent, sizeof (pname));
3281
char *cp = strrchr(pname, '@');
3282
if (cp == NULL)
3283
cp = strchr(pname, '\0');
3284
for (; cp != NULL; cp = strrchr(pname, '/')) {
3285
/* Chop off the last component and open the parent */
3286
*cp = '\0';
3287
zfs_handle_t *zhp = make_dataset_handle(hdl, pname);
3288
3289
if (zhp == NULL)
3290
continue;
3291
int err = guid_to_name_cb(zfs_handle_dup(zhp), &gtnd);
3292
if (err != EEXIST)
3293
err = zfs_iter_children_v2(zhp, 0, guid_to_name_cb,
3294
&gtnd);
3295
if (err != EEXIST && bookmark_ok)
3296
err = zfs_iter_bookmarks_v2(zhp, 0, guid_to_name_cb,
3297
&gtnd);
3298
zfs_close(zhp);
3299
if (err == EEXIST)
3300
return (0);
3301
3302
/*
3303
* Remember the last portion of the dataset so we skip it next
3304
* time through (as we've already searched that portion of the
3305
* hierarchy).
3306
*/
3307
gtnd.skip = strrchr(pname, '/') + 1;
3308
}
3309
3310
return (ENOENT);
3311
}
3312
3313
static int
3314
guid_to_name(libzfs_handle_t *hdl, const char *parent, uint64_t guid,
3315
boolean_t bookmark_ok, char *name)
3316
{
3317
return (guid_to_name_redact_snaps(hdl, parent, guid, bookmark_ok, NULL,
3318
-1, name));
3319
}
3320
3321
/*
3322
* Return +1 if guid1 is before guid2, 0 if they are the same, and -1 if
3323
* guid1 is after guid2.
3324
*/
3325
static int
3326
created_before(libzfs_handle_t *hdl, avl_tree_t *avl,
3327
uint64_t guid1, uint64_t guid2)
3328
{
3329
nvlist_t *nvfs;
3330
const char *fsname = NULL, *snapname = NULL;
3331
char buf[ZFS_MAX_DATASET_NAME_LEN];
3332
int rv;
3333
zfs_handle_t *guid1hdl, *guid2hdl;
3334
uint64_t create1, create2;
3335
3336
if (guid2 == 0)
3337
return (0);
3338
if (guid1 == 0)
3339
return (1);
3340
3341
nvfs = fsavl_find(avl, guid1, &snapname);
3342
fsname = fnvlist_lookup_string(nvfs, "name");
3343
(void) snprintf(buf, sizeof (buf), "%s@%s", fsname, snapname);
3344
guid1hdl = zfs_open(hdl, buf, ZFS_TYPE_SNAPSHOT);
3345
if (guid1hdl == NULL)
3346
return (-1);
3347
3348
nvfs = fsavl_find(avl, guid2, &snapname);
3349
fsname = fnvlist_lookup_string(nvfs, "name");
3350
(void) snprintf(buf, sizeof (buf), "%s@%s", fsname, snapname);
3351
guid2hdl = zfs_open(hdl, buf, ZFS_TYPE_SNAPSHOT);
3352
if (guid2hdl == NULL) {
3353
zfs_close(guid1hdl);
3354
return (-1);
3355
}
3356
3357
create1 = zfs_prop_get_int(guid1hdl, ZFS_PROP_CREATETXG);
3358
create2 = zfs_prop_get_int(guid2hdl, ZFS_PROP_CREATETXG);
3359
3360
if (create1 < create2)
3361
rv = -1;
3362
else if (create1 > create2)
3363
rv = +1;
3364
else
3365
rv = 0;
3366
3367
zfs_close(guid1hdl);
3368
zfs_close(guid2hdl);
3369
3370
return (rv);
3371
}
3372
3373
/*
3374
* This function reestablishes the hierarchy of encryption roots after a
3375
* recursive incremental receive has completed. This must be done after the
3376
* second call to recv_incremental_replication() has renamed and promoted all
3377
* sent datasets to their final locations in the dataset hierarchy.
3378
*/
3379
static int
3380
recv_fix_encryption_hierarchy(libzfs_handle_t *hdl, const char *top_zfs,
3381
nvlist_t *stream_nv, avl_tree_t *stream_avl)
3382
{
3383
int err;
3384
nvpair_t *fselem = NULL;
3385
nvlist_t *local_nv;
3386
avl_tree_t *local_avl;
3387
boolean_t recursive;
3388
3389
recursive = (nvlist_lookup_boolean(stream_nv, "not_recursive") ==
3390
ENOENT);
3391
3392
/* Using top_zfs, gather the nvlists for all local filesystems. */
3393
if ((err = gather_nvlist(hdl, top_zfs, NULL, NULL,
3394
recursive, B_TRUE, B_FALSE, recursive, B_FALSE, B_FALSE, B_FALSE,
3395
B_FALSE, B_TRUE, &local_nv, &local_avl)) != 0)
3396
return (err);
3397
3398
/*
3399
* Go through the nvlists of the local filesystems and check for
3400
* encryption roots.
3401
*/
3402
while ((fselem = nvlist_next_nvpair(local_nv, fselem)) != NULL) {
3403
zfs_handle_t *zhp = NULL;
3404
uint64_t crypt;
3405
nvlist_t *stream_props, *snaps, *stream_nvfs = NULL,
3406
*nvfs = NULL;
3407
boolean_t is_encroot, is_clone, stream_encroot;
3408
const char *stream_keylocation = NULL, *fsname;
3409
char keylocation[MAXNAMELEN];
3410
nvpair_t *snapelem;
3411
3412
nvfs = fnvpair_value_nvlist(fselem);
3413
snaps = fnvlist_lookup_nvlist(nvfs, "snaps");
3414
fsname = fnvlist_lookup_string(nvfs, "name");
3415
zhp = zfs_open(hdl, fsname, ZFS_TYPE_DATASET);
3416
if (zhp == NULL) {
3417
err = ENOENT;
3418
goto error;
3419
}
3420
3421
/* we don't need to do anything for unencrypted datasets */
3422
crypt = zfs_prop_get_int(zhp, ZFS_PROP_ENCRYPTION);
3423
if (crypt == ZIO_CRYPT_OFF) {
3424
zfs_close(zhp);
3425
continue;
3426
}
3427
3428
is_clone = zhp->zfs_dmustats.dds_origin[0] != '\0';
3429
(void) zfs_crypto_get_encryption_root(zhp, &is_encroot, NULL);
3430
keylocation[0] = '\0';
3431
3432
/*
3433
* Go through the snapshots of the local filesystem and find
3434
* the stream's filesystem.
3435
*/
3436
for (snapelem = nvlist_next_nvpair(snaps, NULL);
3437
snapelem; snapelem = nvlist_next_nvpair(snaps, snapelem)) {
3438
uint64_t thisguid;
3439
3440
thisguid = fnvpair_value_uint64(snapelem);
3441
stream_nvfs = fsavl_find(stream_avl, thisguid, NULL);
3442
3443
if (stream_nvfs != NULL)
3444
break;
3445
}
3446
3447
if (stream_nvfs == NULL)
3448
continue;
3449
3450
stream_props = fnvlist_lookup_nvlist(stream_nvfs, "props");
3451
stream_encroot = nvlist_exists(stream_nvfs, "is_encroot");
3452
3453
/*
3454
* If the dataset is flagged as an encryption root, was not
3455
* received as a clone and is not currently an encryption root,
3456
* force it to become one. Fixup the keylocation if necessary.
3457
*/
3458
if (stream_encroot) {
3459
if (!is_clone && !is_encroot) {
3460
err = lzc_change_key(fsname,
3461
DCP_CMD_FORCE_NEW_KEY, NULL, NULL, 0);
3462
if (err != 0) {
3463
zfs_close(zhp);
3464
goto error;
3465
}
3466
}
3467
3468
stream_keylocation = fnvlist_lookup_string(stream_props,
3469
zfs_prop_to_name(ZFS_PROP_KEYLOCATION));
3470
3471
/*
3472
* Refresh the properties in case the call to
3473
* lzc_change_key() changed the value.
3474
*/
3475
zfs_refresh_properties(zhp);
3476
err = zfs_prop_get(zhp, ZFS_PROP_KEYLOCATION,
3477
keylocation, sizeof (keylocation), NULL, NULL,
3478
0, B_TRUE);
3479
if (err != 0) {
3480
zfs_close(zhp);
3481
goto error;
3482
}
3483
3484
if (strcmp(keylocation, stream_keylocation) != 0) {
3485
err = zfs_prop_set(zhp,
3486
zfs_prop_to_name(ZFS_PROP_KEYLOCATION),
3487
stream_keylocation);
3488
if (err != 0) {
3489
zfs_close(zhp);
3490
goto error;
3491
}
3492
}
3493
}
3494
3495
/*
3496
* If the dataset is not flagged as an encryption root and is
3497
* currently an encryption root, force it to inherit from its
3498
* parent. The root of a raw send should never be
3499
* force-inherited.
3500
*/
3501
if (!stream_encroot && is_encroot &&
3502
strcmp(top_zfs, fsname) != 0) {
3503
err = lzc_change_key(fsname, DCP_CMD_FORCE_INHERIT,
3504
NULL, NULL, 0);
3505
if (err != 0) {
3506
zfs_close(zhp);
3507
goto error;
3508
}
3509
}
3510
3511
zfs_close(zhp);
3512
}
3513
3514
return (0);
3515
3516
error:
3517
return (err);
3518
}
3519
3520
static int
3521
recv_incremental_replication(libzfs_handle_t *hdl, const char *tofs,
3522
recvflags_t *flags, nvlist_t *stream_nv, avl_tree_t *stream_avl,
3523
nvlist_t *renamed)
3524
{
3525
nvlist_t *local_nv, *deleted = NULL;
3526
avl_tree_t *local_avl;
3527
nvpair_t *fselem, *nextfselem;
3528
const char *fromsnap;
3529
char newname[ZFS_MAX_DATASET_NAME_LEN];
3530
char guidname[32];
3531
int error;
3532
boolean_t needagain, progress, recursive;
3533
const char *s1, *s2;
3534
3535
if (flags->dryrun)
3536
return (0);
3537
3538
fromsnap = fnvlist_lookup_string(stream_nv, "fromsnap");
3539
3540
recursive = (nvlist_lookup_boolean(stream_nv, "not_recursive") ==
3541
ENOENT);
3542
3543
again:
3544
needagain = progress = B_FALSE;
3545
3546
deleted = fnvlist_alloc();
3547
3548
if ((error = gather_nvlist(hdl, tofs, fromsnap, NULL,
3549
recursive, B_TRUE, B_FALSE, recursive, B_FALSE, B_FALSE, B_FALSE,
3550
B_FALSE, B_TRUE, &local_nv, &local_avl)) != 0)
3551
return (error);
3552
3553
/*
3554
* Process deletes and renames
3555
*/
3556
for (fselem = nvlist_next_nvpair(local_nv, NULL);
3557
fselem; fselem = nextfselem) {
3558
nvlist_t *nvfs, *snaps;
3559
nvlist_t *stream_nvfs = NULL;
3560
nvpair_t *snapelem, *nextsnapelem;
3561
uint64_t fromguid = 0;
3562
uint64_t originguid = 0;
3563
uint64_t stream_originguid = 0;
3564
uint64_t parent_fromsnap_guid, stream_parent_fromsnap_guid;
3565
const char *fsname, *stream_fsname;
3566
3567
nextfselem = nvlist_next_nvpair(local_nv, fselem);
3568
3569
nvfs = fnvpair_value_nvlist(fselem);
3570
snaps = fnvlist_lookup_nvlist(nvfs, "snaps");
3571
fsname = fnvlist_lookup_string(nvfs, "name");
3572
parent_fromsnap_guid = fnvlist_lookup_uint64(nvfs,
3573
"parentfromsnap");
3574
(void) nvlist_lookup_uint64(nvfs, "origin", &originguid);
3575
3576
/*
3577
* First find the stream's fs, so we can check for
3578
* a different origin (due to "zfs promote")
3579
*/
3580
for (snapelem = nvlist_next_nvpair(snaps, NULL);
3581
snapelem; snapelem = nvlist_next_nvpair(snaps, snapelem)) {
3582
uint64_t thisguid;
3583
3584
thisguid = fnvpair_value_uint64(snapelem);
3585
stream_nvfs = fsavl_find(stream_avl, thisguid, NULL);
3586
3587
if (stream_nvfs != NULL)
3588
break;
3589
}
3590
3591
/* check for promote */
3592
(void) nvlist_lookup_uint64(stream_nvfs, "origin",
3593
&stream_originguid);
3594
if (stream_nvfs && originguid != stream_originguid) {
3595
switch (created_before(hdl, local_avl,
3596
stream_originguid, originguid)) {
3597
case 1: {
3598
/* promote it! */
3599
nvlist_t *origin_nvfs;
3600
const char *origin_fsname;
3601
3602
origin_nvfs = fsavl_find(local_avl, originguid,
3603
NULL);
3604
origin_fsname = fnvlist_lookup_string(
3605
origin_nvfs, "name");
3606
error = recv_promote(hdl, fsname, origin_fsname,
3607
flags);
3608
if (error == 0)
3609
progress = B_TRUE;
3610
break;
3611
}
3612
default:
3613
break;
3614
case -1:
3615
fsavl_destroy(local_avl);
3616
fnvlist_free(local_nv);
3617
return (-1);
3618
}
3619
/*
3620
* We had/have the wrong origin, therefore our
3621
* list of snapshots is wrong. Need to handle
3622
* them on the next pass.
3623
*/
3624
needagain = B_TRUE;
3625
continue;
3626
}
3627
3628
for (snapelem = nvlist_next_nvpair(snaps, NULL);
3629
snapelem; snapelem = nextsnapelem) {
3630
uint64_t thisguid;
3631
const char *stream_snapname;
3632
nvlist_t *found, *props;
3633
3634
nextsnapelem = nvlist_next_nvpair(snaps, snapelem);
3635
3636
thisguid = fnvpair_value_uint64(snapelem);
3637
found = fsavl_find(stream_avl, thisguid,
3638
&stream_snapname);
3639
3640
/* check for delete */
3641
if (found == NULL) {
3642
char name[ZFS_MAX_DATASET_NAME_LEN];
3643
3644
if (!flags->force)
3645
continue;
3646
3647
(void) snprintf(name, sizeof (name), "%s@%s",
3648
fsname, nvpair_name(snapelem));
3649
3650
error = recv_destroy(hdl, name,
3651
strlen(fsname)+1, newname, flags);
3652
if (error)
3653
needagain = B_TRUE;
3654
else
3655
progress = B_TRUE;
3656
sprintf(guidname, "%llu",
3657
(u_longlong_t)thisguid);
3658
nvlist_add_boolean(deleted, guidname);
3659
continue;
3660
}
3661
3662
stream_nvfs = found;
3663
3664
if (0 == nvlist_lookup_nvlist(stream_nvfs, "snapprops",
3665
&props) && 0 == nvlist_lookup_nvlist(props,
3666
stream_snapname, &props)) {
3667
zfs_cmd_t zc = {"\0"};
3668
3669
zc.zc_cookie = B_TRUE; /* received */
3670
(void) snprintf(zc.zc_name, sizeof (zc.zc_name),
3671
"%s@%s", fsname, nvpair_name(snapelem));
3672
zcmd_write_src_nvlist(hdl, &zc, props);
3673
(void) zfs_ioctl(hdl,
3674
ZFS_IOC_SET_PROP, &zc);
3675
zcmd_free_nvlists(&zc);
3676
}
3677
3678
/* check for different snapname */
3679
if (strcmp(nvpair_name(snapelem),
3680
stream_snapname) != 0) {
3681
char name[ZFS_MAX_DATASET_NAME_LEN];
3682
char tryname[ZFS_MAX_DATASET_NAME_LEN];
3683
3684
(void) snprintf(name, sizeof (name), "%s@%s",
3685
fsname, nvpair_name(snapelem));
3686
(void) snprintf(tryname, sizeof (name), "%s@%s",
3687
fsname, stream_snapname);
3688
3689
error = recv_rename(hdl, name, tryname,
3690
strlen(fsname)+1, newname, flags);
3691
if (error)
3692
needagain = B_TRUE;
3693
else
3694
progress = B_TRUE;
3695
}
3696
3697
if (strcmp(stream_snapname, fromsnap) == 0)
3698
fromguid = thisguid;
3699
}
3700
3701
/* check for delete */
3702
if (stream_nvfs == NULL) {
3703
if (!flags->force)
3704
continue;
3705
3706
error = recv_destroy(hdl, fsname, strlen(tofs)+1,
3707
newname, flags);
3708
if (error)
3709
needagain = B_TRUE;
3710
else
3711
progress = B_TRUE;
3712
sprintf(guidname, "%llu",
3713
(u_longlong_t)parent_fromsnap_guid);
3714
nvlist_add_boolean(deleted, guidname);
3715
continue;
3716
}
3717
3718
if (fromguid == 0) {
3719
if (flags->verbose) {
3720
(void) printf("local fs %s does not have "
3721
"fromsnap (%s in stream); must have "
3722
"been deleted locally; ignoring\n",
3723
fsname, fromsnap);
3724
}
3725
continue;
3726
}
3727
3728
stream_fsname = fnvlist_lookup_string(stream_nvfs, "name");
3729
stream_parent_fromsnap_guid = fnvlist_lookup_uint64(
3730
stream_nvfs, "parentfromsnap");
3731
3732
s1 = strrchr(fsname, '/');
3733
s2 = strrchr(stream_fsname, '/');
3734
3735
/*
3736
* Check if we're going to rename based on parent guid change
3737
* and the current parent guid was also deleted. If it was then
3738
* rename will fail and is likely unneeded, so avoid this and
3739
* force an early retry to determine the new
3740
* parent_fromsnap_guid.
3741
*/
3742
if (stream_parent_fromsnap_guid != 0 &&
3743
parent_fromsnap_guid != 0 &&
3744
stream_parent_fromsnap_guid != parent_fromsnap_guid) {
3745
sprintf(guidname, "%llu",
3746
(u_longlong_t)parent_fromsnap_guid);
3747
if (nvlist_exists(deleted, guidname)) {
3748
progress = B_TRUE;
3749
needagain = B_TRUE;
3750
goto doagain;
3751
}
3752
}
3753
3754
/*
3755
* Check for rename. If the exact receive path is specified, it
3756
* does not count as a rename, but we still need to check the
3757
* datasets beneath it.
3758
*/
3759
if ((stream_parent_fromsnap_guid != 0 &&
3760
parent_fromsnap_guid != 0 &&
3761
stream_parent_fromsnap_guid != parent_fromsnap_guid) ||
3762
((flags->isprefix || strcmp(tofs, fsname) != 0) &&
3763
(s1 != NULL) && (s2 != NULL) && strcmp(s1, s2) != 0)) {
3764
nvlist_t *parent;
3765
char tryname[ZFS_MAX_DATASET_NAME_LEN];
3766
3767
parent = fsavl_find(local_avl,
3768
stream_parent_fromsnap_guid, NULL);
3769
/*
3770
* NB: parent might not be found if we used the
3771
* tosnap for stream_parent_fromsnap_guid,
3772
* because the parent is a newly-created fs;
3773
* we'll be able to rename it after we recv the
3774
* new fs.
3775
*/
3776
if (parent != NULL) {
3777
const char *pname;
3778
3779
pname = fnvlist_lookup_string(parent, "name");
3780
(void) snprintf(tryname, sizeof (tryname),
3781
"%s%s", pname, strrchr(stream_fsname, '/'));
3782
} else {
3783
tryname[0] = '\0';
3784
if (flags->verbose) {
3785
(void) printf("local fs %s new parent "
3786
"not found\n", fsname);
3787
}
3788
}
3789
3790
newname[0] = '\0';
3791
3792
error = recv_rename(hdl, fsname, tryname,
3793
strlen(tofs)+1, newname, flags);
3794
3795
if (renamed != NULL && newname[0] != '\0') {
3796
fnvlist_add_boolean(renamed, newname);
3797
}
3798
3799
if (error)
3800
needagain = B_TRUE;
3801
else
3802
progress = B_TRUE;
3803
}
3804
}
3805
3806
doagain:
3807
fsavl_destroy(local_avl);
3808
fnvlist_free(local_nv);
3809
fnvlist_free(deleted);
3810
3811
if (needagain && progress) {
3812
/* do another pass to fix up temporary names */
3813
if (flags->verbose)
3814
(void) printf("another pass:\n");
3815
goto again;
3816
}
3817
3818
return (needagain || error != 0);
3819
}
3820
3821
static int
3822
zfs_receive_package(libzfs_handle_t *hdl, int fd, const char *destname,
3823
recvflags_t *flags, dmu_replay_record_t *drr, zio_cksum_t *zc,
3824
char **top_zfs, nvlist_t *cmdprops)
3825
{
3826
nvlist_t *stream_nv = NULL;
3827
avl_tree_t *stream_avl = NULL;
3828
const char *fromsnap = NULL;
3829
const char *sendsnap = NULL;
3830
char *cp;
3831
char tofs[ZFS_MAX_DATASET_NAME_LEN];
3832
char sendfs[ZFS_MAX_DATASET_NAME_LEN];
3833
char errbuf[ERRBUFLEN];
3834
dmu_replay_record_t drre;
3835
int error;
3836
boolean_t anyerr = B_FALSE;
3837
boolean_t softerr = B_FALSE;
3838
boolean_t recursive, raw;
3839
3840
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
3841
"cannot receive"));
3842
3843
assert(drr->drr_type == DRR_BEGIN);
3844
assert(drr->drr_u.drr_begin.drr_magic == DMU_BACKUP_MAGIC);
3845
assert(DMU_GET_STREAM_HDRTYPE(drr->drr_u.drr_begin.drr_versioninfo) ==
3846
DMU_COMPOUNDSTREAM);
3847
3848
/*
3849
* Read in the nvlist from the stream.
3850
*/
3851
if (drr->drr_payloadlen != 0) {
3852
error = recv_read_nvlist(hdl, fd, drr->drr_payloadlen,
3853
&stream_nv, flags->byteswap, zc);
3854
if (error) {
3855
error = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
3856
goto out;
3857
}
3858
}
3859
3860
recursive = (nvlist_lookup_boolean(stream_nv, "not_recursive") ==
3861
ENOENT);
3862
raw = (nvlist_lookup_boolean(stream_nv, "raw") == 0);
3863
3864
if (recursive && strchr(destname, '@')) {
3865
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
3866
"cannot specify snapshot name for multi-snapshot stream"));
3867
error = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
3868
goto out;
3869
}
3870
3871
/*
3872
* Read in the end record and verify checksum.
3873
*/
3874
if (0 != (error = recv_read(hdl, fd, &drre, sizeof (drre),
3875
flags->byteswap, NULL)))
3876
goto out;
3877
if (flags->byteswap) {
3878
drre.drr_type = BSWAP_32(drre.drr_type);
3879
drre.drr_u.drr_end.drr_checksum.zc_word[0] =
3880
BSWAP_64(drre.drr_u.drr_end.drr_checksum.zc_word[0]);
3881
drre.drr_u.drr_end.drr_checksum.zc_word[1] =
3882
BSWAP_64(drre.drr_u.drr_end.drr_checksum.zc_word[1]);
3883
drre.drr_u.drr_end.drr_checksum.zc_word[2] =
3884
BSWAP_64(drre.drr_u.drr_end.drr_checksum.zc_word[2]);
3885
drre.drr_u.drr_end.drr_checksum.zc_word[3] =
3886
BSWAP_64(drre.drr_u.drr_end.drr_checksum.zc_word[3]);
3887
}
3888
if (drre.drr_type != DRR_END) {
3889
error = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
3890
goto out;
3891
}
3892
if (!ZIO_CHECKSUM_EQUAL(drre.drr_u.drr_end.drr_checksum, *zc)) {
3893
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
3894
"incorrect header checksum"));
3895
error = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
3896
goto out;
3897
}
3898
3899
(void) nvlist_lookup_string(stream_nv, "fromsnap", &fromsnap);
3900
3901
if (drr->drr_payloadlen != 0) {
3902
nvlist_t *stream_fss;
3903
3904
stream_fss = fnvlist_lookup_nvlist(stream_nv, "fss");
3905
if ((stream_avl = fsavl_create(stream_fss)) == NULL) {
3906
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
3907
"couldn't allocate avl tree"));
3908
error = zfs_error(hdl, EZFS_NOMEM, errbuf);
3909
goto out;
3910
}
3911
3912
if (fromsnap != NULL && recursive) {
3913
nvlist_t *renamed = NULL;
3914
nvpair_t *pair = NULL;
3915
3916
(void) strlcpy(tofs, destname, sizeof (tofs));
3917
if (flags->isprefix) {
3918
struct drr_begin *drrb = &drr->drr_u.drr_begin;
3919
int i;
3920
3921
if (flags->istail) {
3922
cp = strrchr(drrb->drr_toname, '/');
3923
if (cp == NULL) {
3924
(void) strlcat(tofs, "/",
3925
sizeof (tofs));
3926
i = 0;
3927
} else {
3928
i = (cp - drrb->drr_toname);
3929
}
3930
} else {
3931
i = strcspn(drrb->drr_toname, "/@");
3932
}
3933
/* zfs_receive_one() will create_parents() */
3934
(void) strlcat(tofs, &drrb->drr_toname[i],
3935
sizeof (tofs));
3936
*strchr(tofs, '@') = '\0';
3937
}
3938
3939
if (!flags->dryrun && !flags->nomount) {
3940
renamed = fnvlist_alloc();
3941
}
3942
3943
softerr = recv_incremental_replication(hdl, tofs, flags,
3944
stream_nv, stream_avl, renamed);
3945
3946
/* Unmount renamed filesystems before receiving. */
3947
while ((pair = nvlist_next_nvpair(renamed,
3948
pair)) != NULL) {
3949
zfs_handle_t *zhp;
3950
prop_changelist_t *clp = NULL;
3951
3952
zhp = zfs_open(hdl, nvpair_name(pair),
3953
ZFS_TYPE_FILESYSTEM);
3954
if (zhp != NULL) {
3955
clp = changelist_gather(zhp,
3956
ZFS_PROP_MOUNTPOINT, 0,
3957
flags->forceunmount ? MS_FORCE : 0);
3958
zfs_close(zhp);
3959
if (clp != NULL) {
3960
softerr |=
3961
changelist_prefix(clp);
3962
changelist_free(clp);
3963
}
3964
}
3965
}
3966
3967
fnvlist_free(renamed);
3968
}
3969
}
3970
3971
/*
3972
* Get the fs specified by the first path in the stream (the top level
3973
* specified by 'zfs send') and pass it to each invocation of
3974
* zfs_receive_one().
3975
*/
3976
(void) strlcpy(sendfs, drr->drr_u.drr_begin.drr_toname,
3977
sizeof (sendfs));
3978
if ((cp = strchr(sendfs, '@')) != NULL) {
3979
*cp = '\0';
3980
/*
3981
* Find the "sendsnap", the final snapshot in a replication
3982
* stream. zfs_receive_one() handles certain errors
3983
* differently, depending on if the contained stream is the
3984
* last one or not.
3985
*/
3986
sendsnap = (cp + 1);
3987
}
3988
3989
/* Finally, receive each contained stream */
3990
do {
3991
/*
3992
* we should figure out if it has a recoverable
3993
* error, in which case do a recv_skip() and drive on.
3994
* Note, if we fail due to already having this guid,
3995
* zfs_receive_one() will take care of it (ie,
3996
* recv_skip() and return 0).
3997
*/
3998
error = zfs_receive_impl(hdl, destname, NULL, flags, fd,
3999
sendfs, stream_nv, stream_avl, top_zfs, sendsnap, cmdprops);
4000
if (error == ENODATA) {
4001
error = 0;
4002
break;
4003
}
4004
anyerr |= error;
4005
} while (error == 0);
4006
4007
if (drr->drr_payloadlen != 0 && recursive && fromsnap != NULL) {
4008
/*
4009
* Now that we have the fs's they sent us, try the
4010
* renames again.
4011
*/
4012
softerr = recv_incremental_replication(hdl, tofs, flags,
4013
stream_nv, stream_avl, NULL);
4014
}
4015
4016
if (raw && *top_zfs != NULL && !flags->dryrun) {
4017
softerr = recv_fix_encryption_hierarchy(hdl, *top_zfs,
4018
stream_nv, stream_avl);
4019
}
4020
4021
out:
4022
fsavl_destroy(stream_avl);
4023
fnvlist_free(stream_nv);
4024
if (softerr)
4025
error = -2;
4026
if (anyerr)
4027
error = -1;
4028
return (error);
4029
}
4030
4031
static void
4032
trunc_prop_errs(int truncated)
4033
{
4034
ASSERT(truncated != 0);
4035
4036
if (truncated == 1)
4037
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
4038
"1 more property could not be set\n"));
4039
else
4040
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
4041
"%d more properties could not be set\n"), truncated);
4042
}
4043
4044
static int
4045
recv_skip(libzfs_handle_t *hdl, int fd, boolean_t byteswap)
4046
{
4047
dmu_replay_record_t *drr;
4048
void *buf = zfs_alloc(hdl, SPA_MAXBLOCKSIZE);
4049
uint64_t payload_size;
4050
char errbuf[ERRBUFLEN];
4051
4052
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
4053
"cannot receive"));
4054
4055
/* XXX would be great to use lseek if possible... */
4056
drr = buf;
4057
4058
while (recv_read(hdl, fd, drr, sizeof (dmu_replay_record_t),
4059
byteswap, NULL) == 0) {
4060
if (byteswap)
4061
drr->drr_type = BSWAP_32(drr->drr_type);
4062
4063
switch (drr->drr_type) {
4064
case DRR_BEGIN:
4065
if (drr->drr_payloadlen != 0) {
4066
(void) recv_read(hdl, fd, buf,
4067
drr->drr_payloadlen, B_FALSE, NULL);
4068
}
4069
break;
4070
4071
case DRR_END:
4072
free(buf);
4073
return (0);
4074
4075
case DRR_OBJECT:
4076
if (byteswap) {
4077
drr->drr_u.drr_object.drr_bonuslen =
4078
BSWAP_32(drr->drr_u.drr_object.
4079
drr_bonuslen);
4080
drr->drr_u.drr_object.drr_raw_bonuslen =
4081
BSWAP_32(drr->drr_u.drr_object.
4082
drr_raw_bonuslen);
4083
}
4084
4085
payload_size =
4086
DRR_OBJECT_PAYLOAD_SIZE(&drr->drr_u.drr_object);
4087
(void) recv_read(hdl, fd, buf, payload_size,
4088
B_FALSE, NULL);
4089
break;
4090
4091
case DRR_WRITE:
4092
if (byteswap) {
4093
drr->drr_u.drr_write.drr_logical_size =
4094
BSWAP_64(
4095
drr->drr_u.drr_write.drr_logical_size);
4096
drr->drr_u.drr_write.drr_compressed_size =
4097
BSWAP_64(
4098
drr->drr_u.drr_write.drr_compressed_size);
4099
}
4100
payload_size =
4101
DRR_WRITE_PAYLOAD_SIZE(&drr->drr_u.drr_write);
4102
assert(payload_size <= SPA_MAXBLOCKSIZE);
4103
(void) recv_read(hdl, fd, buf,
4104
payload_size, B_FALSE, NULL);
4105
break;
4106
case DRR_SPILL:
4107
if (byteswap) {
4108
drr->drr_u.drr_spill.drr_length =
4109
BSWAP_64(drr->drr_u.drr_spill.drr_length);
4110
drr->drr_u.drr_spill.drr_compressed_size =
4111
BSWAP_64(drr->drr_u.drr_spill.
4112
drr_compressed_size);
4113
}
4114
4115
payload_size =
4116
DRR_SPILL_PAYLOAD_SIZE(&drr->drr_u.drr_spill);
4117
(void) recv_read(hdl, fd, buf, payload_size,
4118
B_FALSE, NULL);
4119
break;
4120
case DRR_WRITE_EMBEDDED:
4121
if (byteswap) {
4122
drr->drr_u.drr_write_embedded.drr_psize =
4123
BSWAP_32(drr->drr_u.drr_write_embedded.
4124
drr_psize);
4125
}
4126
(void) recv_read(hdl, fd, buf,
4127
P2ROUNDUP(drr->drr_u.drr_write_embedded.drr_psize,
4128
8), B_FALSE, NULL);
4129
break;
4130
case DRR_OBJECT_RANGE:
4131
case DRR_WRITE_BYREF:
4132
case DRR_FREEOBJECTS:
4133
case DRR_FREE:
4134
break;
4135
4136
default:
4137
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4138
"invalid record type"));
4139
free(buf);
4140
return (zfs_error(hdl, EZFS_BADSTREAM, errbuf));
4141
}
4142
}
4143
4144
free(buf);
4145
return (-1);
4146
}
4147
4148
static void
4149
recv_ecksum_set_aux(libzfs_handle_t *hdl, const char *target_snap,
4150
boolean_t resumable, boolean_t checksum)
4151
{
4152
char target_fs[ZFS_MAX_DATASET_NAME_LEN];
4153
4154
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, (checksum ?
4155
"checksum mismatch" : "incomplete stream")));
4156
4157
if (!resumable)
4158
return;
4159
(void) strlcpy(target_fs, target_snap, sizeof (target_fs));
4160
*strchr(target_fs, '@') = '\0';
4161
zfs_handle_t *zhp = zfs_open(hdl, target_fs,
4162
ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME);
4163
if (zhp == NULL)
4164
return;
4165
4166
char token_buf[ZFS_MAXPROPLEN];
4167
int error = zfs_prop_get(zhp, ZFS_PROP_RECEIVE_RESUME_TOKEN,
4168
token_buf, sizeof (token_buf),
4169
NULL, NULL, 0, B_TRUE);
4170
if (error == 0) {
4171
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4172
"checksum mismatch or incomplete stream.\n"
4173
"Partially received snapshot is saved.\n"
4174
"A resuming stream can be generated on the sending "
4175
"system by running:\n"
4176
" zfs send -t %s"),
4177
token_buf);
4178
}
4179
zfs_close(zhp);
4180
}
4181
4182
/*
4183
* Prepare a new nvlist of properties that are to override (-o) or be excluded
4184
* (-x) from the received dataset
4185
* recvprops: received properties from the send stream
4186
* cmdprops: raw input properties from command line
4187
* origprops: properties, both locally-set and received, currently set on the
4188
* target dataset if it exists, NULL otherwise.
4189
* oxprops: valid output override (-o) and excluded (-x) properties
4190
*/
4191
static int
4192
zfs_setup_cmdline_props(libzfs_handle_t *hdl, zfs_type_t type,
4193
char *fsname, boolean_t zoned, boolean_t recursive, boolean_t newfs,
4194
boolean_t raw, boolean_t toplevel, nvlist_t *recvprops, nvlist_t *cmdprops,
4195
nvlist_t *origprops, nvlist_t **oxprops, uint8_t **wkeydata_out,
4196
uint_t *wkeylen_out, const char *errbuf)
4197
{
4198
nvpair_t *nvp;
4199
nvlist_t *oprops, *voprops;
4200
zfs_handle_t *zhp = NULL;
4201
zpool_handle_t *zpool_hdl = NULL;
4202
char *cp;
4203
int ret = 0;
4204
char namebuf[ZFS_MAX_DATASET_NAME_LEN];
4205
4206
if (nvlist_empty(cmdprops))
4207
return (0); /* No properties to override or exclude */
4208
4209
*oxprops = fnvlist_alloc();
4210
oprops = fnvlist_alloc();
4211
4212
strlcpy(namebuf, fsname, ZFS_MAX_DATASET_NAME_LEN);
4213
4214
/*
4215
* Get our dataset handle. The target dataset may not exist yet.
4216
*/
4217
if (zfs_dataset_exists(hdl, namebuf, ZFS_TYPE_DATASET)) {
4218
zhp = zfs_open(hdl, namebuf, ZFS_TYPE_DATASET);
4219
if (zhp == NULL) {
4220
ret = -1;
4221
goto error;
4222
}
4223
}
4224
4225
/* open the zpool handle */
4226
cp = strchr(namebuf, '/');
4227
if (cp != NULL)
4228
*cp = '\0';
4229
zpool_hdl = zpool_open(hdl, namebuf);
4230
if (zpool_hdl == NULL) {
4231
ret = -1;
4232
goto error;
4233
}
4234
4235
/* restore namebuf to match fsname for later use */
4236
if (cp != NULL)
4237
*cp = '/';
4238
4239
/*
4240
* first iteration: process excluded (-x) properties now and gather
4241
* added (-o) properties to be later processed by zfs_valid_proplist()
4242
*/
4243
nvp = NULL;
4244
while ((nvp = nvlist_next_nvpair(cmdprops, nvp)) != NULL) {
4245
const char *name = nvpair_name(nvp);
4246
zfs_prop_t prop = zfs_name_to_prop(name);
4247
4248
/*
4249
* It turns out, if we don't normalize "aliased" names
4250
* e.g. compress= against the "real" names (e.g. compression)
4251
* here, then setting/excluding them does not work as
4252
* intended.
4253
*
4254
* But since user-defined properties wouldn't have a valid
4255
* mapping here, we do this conditional dance.
4256
*/
4257
const char *newname = name;
4258
if (prop >= ZFS_PROP_TYPE)
4259
newname = zfs_prop_to_name(prop);
4260
4261
/* "origin" is processed separately, don't handle it here */
4262
if (prop == ZFS_PROP_ORIGIN)
4263
continue;
4264
4265
/* raw streams can't override encryption properties */
4266
if ((zfs_prop_encryption_key_param(prop) ||
4267
prop == ZFS_PROP_ENCRYPTION) && raw) {
4268
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4269
"encryption property '%s' cannot "
4270
"be set or excluded for raw streams."), name);
4271
ret = zfs_error(hdl, EZFS_BADPROP, errbuf);
4272
goto error;
4273
}
4274
4275
/*
4276
* For plain replicated send, we can ignore encryption
4277
* properties other than first stream
4278
*/
4279
if ((zfs_prop_encryption_key_param(prop) || prop ==
4280
ZFS_PROP_ENCRYPTION) && !newfs && recursive && !raw) {
4281
continue;
4282
}
4283
4284
/* incremental streams can only exclude encryption properties */
4285
if ((zfs_prop_encryption_key_param(prop) ||
4286
prop == ZFS_PROP_ENCRYPTION) && !newfs &&
4287
nvpair_type(nvp) != DATA_TYPE_BOOLEAN) {
4288
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4289
"encryption property '%s' cannot "
4290
"be set for incremental streams."), name);
4291
ret = zfs_error(hdl, EZFS_BADPROP, errbuf);
4292
goto error;
4293
}
4294
4295
switch (nvpair_type(nvp)) {
4296
case DATA_TYPE_BOOLEAN: /* -x property */
4297
/*
4298
* DATA_TYPE_BOOLEAN is the way we're asked to "exclude"
4299
* a property: this is done by forcing an explicit
4300
* inherit on the destination so the effective value is
4301
* not the one we received from the send stream.
4302
*/
4303
if (!zfs_prop_valid_for_type(prop, type, B_FALSE) &&
4304
!zfs_prop_user(name)) {
4305
(void) fprintf(stderr, dgettext(TEXT_DOMAIN,
4306
"Warning: %s: property '%s' does not "
4307
"apply to datasets of this type\n"),
4308
fsname, name);
4309
continue;
4310
}
4311
/*
4312
* We do this only if the property is not already
4313
* locally-set, in which case its value will take
4314
* priority over the received anyway.
4315
*/
4316
if (nvlist_exists(origprops, newname)) {
4317
nvlist_t *attrs;
4318
const char *source = NULL;
4319
4320
attrs = fnvlist_lookup_nvlist(origprops,
4321
newname);
4322
if (nvlist_lookup_string(attrs,
4323
ZPROP_SOURCE, &source) == 0 &&
4324
strcmp(source, ZPROP_SOURCE_VAL_RECVD) != 0)
4325
continue;
4326
}
4327
/*
4328
* We can't force an explicit inherit on non-inheritable
4329
* properties: if we're asked to exclude this kind of
4330
* values we remove them from "recvprops" input nvlist.
4331
*/
4332
if (!zfs_prop_user(name) && /* can be inherited too */
4333
!zfs_prop_inheritable(prop) &&
4334
nvlist_exists(recvprops, newname))
4335
fnvlist_remove(recvprops, newname);
4336
else
4337
fnvlist_add_boolean(*oxprops, newname);
4338
break;
4339
case DATA_TYPE_STRING: /* -o property=value */
4340
/*
4341
* we're trying to override a property that does not
4342
* make sense for this type of dataset, but we don't
4343
* want to fail if the receive is recursive: this comes
4344
* in handy when the send stream contains, for
4345
* instance, a child ZVOL and we're trying to receive
4346
* it with "-o atime=on"
4347
*/
4348
if (!zfs_prop_valid_for_type(prop, type, B_FALSE) &&
4349
!zfs_prop_user(name)) {
4350
if (recursive)
4351
continue;
4352
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4353
"property '%s' does not apply to datasets "
4354
"of this type"), name);
4355
ret = zfs_error(hdl, EZFS_BADPROP, errbuf);
4356
goto error;
4357
}
4358
fnvlist_add_string(oprops, newname,
4359
fnvpair_value_string(nvp));
4360
break;
4361
default:
4362
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4363
"property '%s' must be a string or boolean"), name);
4364
ret = zfs_error(hdl, EZFS_BADPROP, errbuf);
4365
goto error;
4366
}
4367
}
4368
4369
if (toplevel) {
4370
/* convert override strings properties to native */
4371
if ((voprops = zfs_valid_proplist(hdl, ZFS_TYPE_DATASET,
4372
oprops, zoned, zhp, zpool_hdl, B_FALSE, errbuf)) == NULL) {
4373
ret = zfs_error(hdl, EZFS_BADPROP, errbuf);
4374
goto error;
4375
}
4376
4377
/*
4378
* zfs_crypto_create() requires the parent name. Get it
4379
* by truncating the fsname copy stored in namebuf.
4380
*/
4381
cp = strrchr(namebuf, '/');
4382
if (cp != NULL)
4383
*cp = '\0';
4384
4385
if (!raw && !(!newfs && recursive) &&
4386
zfs_crypto_create(hdl, namebuf, voprops, NULL,
4387
B_FALSE, wkeydata_out, wkeylen_out) != 0) {
4388
fnvlist_free(voprops);
4389
ret = zfs_error(hdl, EZFS_CRYPTOFAILED, errbuf);
4390
goto error;
4391
}
4392
4393
/* second pass: process "-o" properties */
4394
fnvlist_merge(*oxprops, voprops);
4395
fnvlist_free(voprops);
4396
} else {
4397
/* override props on child dataset are inherited */
4398
nvp = NULL;
4399
while ((nvp = nvlist_next_nvpair(oprops, nvp)) != NULL) {
4400
const char *name = nvpair_name(nvp);
4401
fnvlist_add_boolean(*oxprops, name);
4402
}
4403
}
4404
4405
error:
4406
if (zhp != NULL)
4407
zfs_close(zhp);
4408
if (zpool_hdl != NULL)
4409
zpool_close(zpool_hdl);
4410
fnvlist_free(oprops);
4411
return (ret);
4412
}
4413
4414
/*
4415
* Restores a backup of tosnap from the file descriptor specified by infd.
4416
*/
4417
static int
4418
zfs_receive_one(libzfs_handle_t *hdl, int infd, const char *tosnap,
4419
const char *originsnap, recvflags_t *flags, dmu_replay_record_t *drr,
4420
dmu_replay_record_t *drr_noswap, const char *sendfs, nvlist_t *stream_nv,
4421
avl_tree_t *stream_avl, char **top_zfs,
4422
const char *finalsnap, nvlist_t *cmdprops)
4423
{
4424
struct timespec begin_time;
4425
int ioctl_err, ioctl_errno, err;
4426
char *cp;
4427
struct drr_begin *drrb = &drr->drr_u.drr_begin;
4428
char errbuf[ERRBUFLEN];
4429
const char *chopprefix;
4430
boolean_t newfs = B_FALSE;
4431
boolean_t stream_wantsnewfs, stream_resumingnewfs;
4432
boolean_t newprops = B_FALSE;
4433
uint64_t read_bytes = 0;
4434
uint64_t errflags = 0;
4435
uint64_t parent_snapguid = 0;
4436
prop_changelist_t *clp = NULL;
4437
nvlist_t *snapprops_nvlist = NULL;
4438
nvlist_t *snapholds_nvlist = NULL;
4439
zprop_errflags_t prop_errflags;
4440
nvlist_t *prop_errors = NULL;
4441
boolean_t recursive;
4442
const char *snapname = NULL;
4443
char destsnap[MAXPATHLEN * 2];
4444
char origin[MAXNAMELEN] = {0};
4445
char name[MAXPATHLEN];
4446
char tmp_keylocation[MAXNAMELEN] = {0};
4447
nvlist_t *rcvprops = NULL; /* props received from the send stream */
4448
nvlist_t *oxprops = NULL; /* override (-o) and exclude (-x) props */
4449
nvlist_t *origprops = NULL; /* original props (if destination exists) */
4450
zfs_type_t type = ZFS_TYPE_INVALID;
4451
boolean_t toplevel = B_FALSE;
4452
boolean_t zoned = B_FALSE;
4453
boolean_t hastoken = B_FALSE;
4454
boolean_t redacted;
4455
uint8_t *wkeydata = NULL;
4456
uint_t wkeylen = 0;
4457
4458
#ifndef CLOCK_MONOTONIC_RAW
4459
#define CLOCK_MONOTONIC_RAW CLOCK_MONOTONIC
4460
#endif
4461
clock_gettime(CLOCK_MONOTONIC_RAW, &begin_time);
4462
4463
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
4464
"cannot receive"));
4465
4466
recursive = (nvlist_lookup_boolean(stream_nv, "not_recursive") ==
4467
ENOENT);
4468
4469
/* Did the user request holds be skipped via zfs recv -k? */
4470
boolean_t holds = flags->holds && !flags->skipholds;
4471
4472
if (stream_avl != NULL) {
4473
const char *keylocation = NULL;
4474
nvlist_t *lookup = NULL;
4475
nvlist_t *fs = fsavl_find(stream_avl, drrb->drr_toguid,
4476
&snapname);
4477
4478
(void) nvlist_lookup_uint64(fs, "parentfromsnap",
4479
&parent_snapguid);
4480
err = nvlist_lookup_nvlist(fs, "props", &rcvprops);
4481
if (err) {
4482
rcvprops = fnvlist_alloc();
4483
newprops = B_TRUE;
4484
}
4485
4486
/*
4487
* The keylocation property may only be set on encryption roots,
4488
* but this dataset might not become an encryption root until
4489
* recv_fix_encryption_hierarchy() is called. That function
4490
* will fixup the keylocation anyway, so we temporarily unset
4491
* the keylocation for now to avoid any errors from the receive
4492
* ioctl.
4493
*/
4494
err = nvlist_lookup_string(rcvprops,
4495
zfs_prop_to_name(ZFS_PROP_KEYLOCATION), &keylocation);
4496
if (err == 0) {
4497
strlcpy(tmp_keylocation, keylocation, MAXNAMELEN);
4498
(void) nvlist_remove_all(rcvprops,
4499
zfs_prop_to_name(ZFS_PROP_KEYLOCATION));
4500
}
4501
4502
if (flags->canmountoff) {
4503
fnvlist_add_uint64(rcvprops,
4504
zfs_prop_to_name(ZFS_PROP_CANMOUNT), 0);
4505
} else if (newprops) { /* nothing in rcvprops, eliminate it */
4506
fnvlist_free(rcvprops);
4507
rcvprops = NULL;
4508
newprops = B_FALSE;
4509
}
4510
if (0 == nvlist_lookup_nvlist(fs, "snapprops", &lookup)) {
4511
snapprops_nvlist = fnvlist_lookup_nvlist(lookup,
4512
snapname);
4513
}
4514
if (holds) {
4515
if (0 == nvlist_lookup_nvlist(fs, "snapholds",
4516
&lookup)) {
4517
snapholds_nvlist = fnvlist_lookup_nvlist(
4518
lookup, snapname);
4519
}
4520
}
4521
}
4522
4523
cp = NULL;
4524
4525
/*
4526
* Determine how much of the snapshot name stored in the stream
4527
* we are going to tack on to the name they specified on the
4528
* command line, and how much we are going to chop off.
4529
*
4530
* If they specified a snapshot, chop the entire name stored in
4531
* the stream.
4532
*/
4533
if (flags->istail) {
4534
/*
4535
* A filesystem was specified with -e. We want to tack on only
4536
* the tail of the sent snapshot path.
4537
*/
4538
if (strchr(tosnap, '@')) {
4539
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "invalid "
4540
"argument - snapshot not allowed with -e"));
4541
err = zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
4542
goto out;
4543
}
4544
4545
chopprefix = strrchr(sendfs, '/');
4546
4547
if (chopprefix == NULL) {
4548
/*
4549
* The tail is the poolname, so we need to
4550
* prepend a path separator.
4551
*/
4552
int len = strlen(drrb->drr_toname);
4553
cp = umem_alloc(len + 2, UMEM_NOFAIL);
4554
cp[0] = '/';
4555
(void) strcpy(&cp[1], drrb->drr_toname);
4556
chopprefix = cp;
4557
} else {
4558
chopprefix = drrb->drr_toname + (chopprefix - sendfs);
4559
}
4560
} else if (flags->isprefix) {
4561
/*
4562
* A filesystem was specified with -d. We want to tack on
4563
* everything but the first element of the sent snapshot path
4564
* (all but the pool name).
4565
*/
4566
if (strchr(tosnap, '@')) {
4567
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "invalid "
4568
"argument - snapshot not allowed with -d"));
4569
err = zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
4570
goto out;
4571
}
4572
4573
chopprefix = strchr(drrb->drr_toname, '/');
4574
if (chopprefix == NULL)
4575
chopprefix = strchr(drrb->drr_toname, '@');
4576
} else if (strchr(tosnap, '@') == NULL) {
4577
/*
4578
* If a filesystem was specified without -d or -e, we want to
4579
* tack on everything after the fs specified by 'zfs send'.
4580
*/
4581
chopprefix = drrb->drr_toname + strlen(sendfs);
4582
} else {
4583
/* A snapshot was specified as an exact path (no -d or -e). */
4584
if (recursive) {
4585
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4586
"cannot specify snapshot name for multi-snapshot "
4587
"stream"));
4588
err = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
4589
goto out;
4590
}
4591
chopprefix = drrb->drr_toname + strlen(drrb->drr_toname);
4592
}
4593
4594
ASSERT(strstr(drrb->drr_toname, sendfs) == drrb->drr_toname);
4595
ASSERT(chopprefix > drrb->drr_toname || strchr(sendfs, '/') == NULL);
4596
ASSERT(chopprefix <= drrb->drr_toname + strlen(drrb->drr_toname) ||
4597
strchr(sendfs, '/') == NULL);
4598
ASSERT(chopprefix[0] == '/' || chopprefix[0] == '@' ||
4599
chopprefix[0] == '\0');
4600
4601
/*
4602
* Determine name of destination snapshot.
4603
*/
4604
(void) strlcpy(destsnap, tosnap, sizeof (destsnap));
4605
(void) strlcat(destsnap, chopprefix, sizeof (destsnap));
4606
if (cp != NULL)
4607
umem_free(cp, strlen(cp) + 1);
4608
if (!zfs_name_valid(destsnap, ZFS_TYPE_SNAPSHOT)) {
4609
err = zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
4610
goto out;
4611
}
4612
4613
/*
4614
* Determine the name of the origin snapshot.
4615
*/
4616
if (originsnap) {
4617
(void) strlcpy(origin, originsnap, sizeof (origin));
4618
if (flags->verbose)
4619
(void) printf("using provided clone origin %s\n",
4620
origin);
4621
} else if (drrb->drr_flags & DRR_FLAG_CLONE) {
4622
if (guid_to_name(hdl, destsnap,
4623
drrb->drr_fromguid, B_FALSE, origin) != 0) {
4624
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4625
"local origin for clone %s does not exist"),
4626
destsnap);
4627
err = zfs_error(hdl, EZFS_NOENT, errbuf);
4628
goto out;
4629
}
4630
if (flags->verbose)
4631
(void) printf("found clone origin %s\n", origin);
4632
}
4633
4634
if ((DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo) &
4635
DMU_BACKUP_FEATURE_DEDUP)) {
4636
(void) fprintf(stderr,
4637
gettext("ERROR: \"zfs receive\" no longer supports "
4638
"deduplicated send streams. Use\n"
4639
"the \"zstream redup\" command to convert this stream "
4640
"to a regular,\n"
4641
"non-deduplicated stream.\n"));
4642
err = zfs_error(hdl, EZFS_NOTSUP, errbuf);
4643
goto out;
4644
}
4645
4646
boolean_t resuming = DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo) &
4647
DMU_BACKUP_FEATURE_RESUMING;
4648
boolean_t raw = DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo) &
4649
DMU_BACKUP_FEATURE_RAW;
4650
boolean_t embedded = DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo) &
4651
DMU_BACKUP_FEATURE_EMBED_DATA;
4652
stream_wantsnewfs = (drrb->drr_fromguid == 0 ||
4653
(drrb->drr_flags & DRR_FLAG_CLONE) || originsnap) && !resuming;
4654
stream_resumingnewfs = (drrb->drr_fromguid == 0 ||
4655
(drrb->drr_flags & DRR_FLAG_CLONE) || originsnap) && resuming;
4656
4657
if (stream_wantsnewfs) {
4658
/*
4659
* if the parent fs does not exist, look for it based on
4660
* the parent snap GUID
4661
*/
4662
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
4663
"cannot receive new filesystem stream"));
4664
4665
(void) strlcpy(name, destsnap, sizeof (name));
4666
cp = strrchr(name, '/');
4667
if (cp)
4668
*cp = '\0';
4669
if (cp &&
4670
!zfs_dataset_exists(hdl, name, ZFS_TYPE_DATASET)) {
4671
char suffix[ZFS_MAX_DATASET_NAME_LEN];
4672
(void) strlcpy(suffix, strrchr(destsnap, '/'),
4673
sizeof (suffix));
4674
if (guid_to_name(hdl, name, parent_snapguid,
4675
B_FALSE, destsnap) == 0) {
4676
*strchr(destsnap, '@') = '\0';
4677
(void) strlcat(destsnap, suffix,
4678
sizeof (destsnap));
4679
}
4680
}
4681
} else {
4682
/*
4683
* If the fs does not exist, look for it based on the
4684
* fromsnap GUID.
4685
*/
4686
if (resuming) {
4687
(void) snprintf(errbuf, sizeof (errbuf),
4688
dgettext(TEXT_DOMAIN,
4689
"cannot receive resume stream"));
4690
} else {
4691
(void) snprintf(errbuf, sizeof (errbuf),
4692
dgettext(TEXT_DOMAIN,
4693
"cannot receive incremental stream"));
4694
}
4695
4696
(void) strlcpy(name, destsnap, sizeof (name));
4697
*strchr(name, '@') = '\0';
4698
4699
/*
4700
* If the exact receive path was specified and this is the
4701
* topmost path in the stream, then if the fs does not exist we
4702
* should look no further.
4703
*/
4704
if ((flags->isprefix || (*(chopprefix = drrb->drr_toname +
4705
strlen(sendfs)) != '\0' && *chopprefix != '@')) &&
4706
!zfs_dataset_exists(hdl, name, ZFS_TYPE_DATASET)) {
4707
char snap[ZFS_MAX_DATASET_NAME_LEN];
4708
(void) strlcpy(snap, strchr(destsnap, '@'),
4709
sizeof (snap));
4710
if (guid_to_name(hdl, name, drrb->drr_fromguid,
4711
B_FALSE, destsnap) == 0) {
4712
*strchr(destsnap, '@') = '\0';
4713
(void) strlcat(destsnap, snap,
4714
sizeof (destsnap));
4715
}
4716
}
4717
}
4718
4719
(void) strlcpy(name, destsnap, sizeof (name));
4720
*strchr(name, '@') = '\0';
4721
4722
redacted = DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo) &
4723
DMU_BACKUP_FEATURE_REDACTED;
4724
4725
if (flags->heal) {
4726
if (flags->isprefix || flags->istail || flags->force ||
4727
flags->canmountoff || flags->resumable || flags->nomount ||
4728
flags->skipholds) {
4729
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4730
"corrective recv can not be used when combined with"
4731
" this flag"));
4732
err = zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
4733
goto out;
4734
}
4735
uint64_t guid =
4736
get_snap_guid(hdl, name, strchr(destsnap, '@') + 1);
4737
if (guid == 0) {
4738
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4739
"corrective recv must specify an existing snapshot"
4740
" to heal"));
4741
err = zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
4742
goto out;
4743
} else if (guid != drrb->drr_toguid) {
4744
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4745
"local snapshot doesn't match the snapshot"
4746
" in the provided stream"));
4747
err = zfs_error(hdl, EZFS_WRONG_PARENT, errbuf);
4748
goto out;
4749
}
4750
} else if (zfs_dataset_exists(hdl, name, ZFS_TYPE_DATASET)) {
4751
zfs_cmd_t zc = {"\0"};
4752
zfs_handle_t *zhp = NULL;
4753
boolean_t encrypted;
4754
4755
(void) strcpy(zc.zc_name, name);
4756
4757
/*
4758
* Destination fs exists. It must be one of these cases:
4759
* - an incremental send stream
4760
* - the stream specifies a new fs (full stream or clone)
4761
* and they want us to blow away the existing fs (and
4762
* have therefore specified -F and removed any snapshots)
4763
* - we are resuming a failed receive.
4764
*/
4765
if (stream_wantsnewfs) {
4766
boolean_t is_volume = drrb->drr_type == DMU_OST_ZVOL;
4767
if (!flags->force) {
4768
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4769
"destination '%s' exists\n"
4770
"must specify -F to overwrite it"), name);
4771
err = zfs_error(hdl, EZFS_EXISTS, errbuf);
4772
goto out;
4773
}
4774
if (zfs_ioctl(hdl, ZFS_IOC_SNAPSHOT_LIST_NEXT,
4775
&zc) == 0) {
4776
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4777
"destination has snapshots (eg. %s)\n"
4778
"must destroy them to overwrite it"),
4779
zc.zc_name);
4780
err = zfs_error(hdl, EZFS_EXISTS, errbuf);
4781
goto out;
4782
}
4783
if (is_volume && strrchr(name, '/') == NULL) {
4784
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4785
"destination %s is the root dataset\n"
4786
"cannot overwrite with a ZVOL"),
4787
name);
4788
err = zfs_error(hdl, EZFS_EXISTS, errbuf);
4789
goto out;
4790
}
4791
if (is_volume &&
4792
zfs_ioctl(hdl, ZFS_IOC_DATASET_LIST_NEXT,
4793
&zc) == 0) {
4794
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4795
"destination has children (eg. %s)\n"
4796
"cannot overwrite with a ZVOL"),
4797
zc.zc_name);
4798
err = zfs_error(hdl, EZFS_WRONG_PARENT, errbuf);
4799
goto out;
4800
}
4801
}
4802
4803
if ((zhp = zfs_open(hdl, name,
4804
ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME)) == NULL) {
4805
err = -1;
4806
goto out;
4807
}
4808
4809
/*
4810
* When receiving full/newfs on existing dataset, then it
4811
* should be done with "-F" flag. Its enforced for initial
4812
* receive in previous checks in this function.
4813
* Similarly, on resuming full/newfs recv on existing dataset,
4814
* it should be done with "-F" flag.
4815
*
4816
* When dataset doesn't exist, then full/newfs recv is done on
4817
* newly created dataset and it's marked INCONSISTENT. But
4818
* When receiving on existing dataset, recv is first done on
4819
* %recv and its marked INCONSISTENT. Existing dataset is not
4820
* marked INCONSISTENT.
4821
* Resume of full/newfs receive with dataset not INCONSISTENT
4822
* indicates that its resuming newfs on existing dataset. So,
4823
* enforce "-F" flag in this case.
4824
*/
4825
if (stream_resumingnewfs &&
4826
!zfs_prop_get_int(zhp, ZFS_PROP_INCONSISTENT) &&
4827
!flags->force) {
4828
zfs_close(zhp);
4829
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4830
"Resuming recv on existing destination '%s'\n"
4831
"must specify -F to overwrite it"), name);
4832
err = zfs_error(hdl, EZFS_RESUME_EXISTS, errbuf);
4833
goto out;
4834
}
4835
4836
if (stream_wantsnewfs &&
4837
zhp->zfs_dmustats.dds_origin[0]) {
4838
zfs_close(zhp);
4839
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4840
"destination '%s' is a clone\n"
4841
"must destroy it to overwrite it"), name);
4842
err = zfs_error(hdl, EZFS_EXISTS, errbuf);
4843
goto out;
4844
}
4845
4846
/*
4847
* Raw sends can not be performed as an incremental on top
4848
* of existing unencrypted datasets. zfs recv -F can't be
4849
* used to blow away an existing encrypted filesystem. This
4850
* is because it would require the dsl dir to point to the
4851
* new key (or lack of a key) and the old key at the same
4852
* time. The -F flag may still be used for deleting
4853
* intermediate snapshots that would otherwise prevent the
4854
* receive from working.
4855
*/
4856
encrypted = zfs_prop_get_int(zhp, ZFS_PROP_ENCRYPTION) !=
4857
ZIO_CRYPT_OFF;
4858
if (!stream_wantsnewfs && !encrypted && raw) {
4859
zfs_close(zhp);
4860
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4861
"cannot perform raw receive on top of "
4862
"existing unencrypted dataset"));
4863
err = zfs_error(hdl, EZFS_BADRESTORE, errbuf);
4864
goto out;
4865
}
4866
4867
if (stream_wantsnewfs && flags->force &&
4868
((raw && !encrypted) || encrypted)) {
4869
zfs_close(zhp);
4870
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4871
"zfs receive -F cannot be used to destroy an "
4872
"encrypted filesystem or overwrite an "
4873
"unencrypted one with an encrypted one"));
4874
err = zfs_error(hdl, EZFS_BADRESTORE, errbuf);
4875
goto out;
4876
}
4877
4878
if (!flags->dryrun && zhp->zfs_type == ZFS_TYPE_FILESYSTEM &&
4879
(stream_wantsnewfs || stream_resumingnewfs)) {
4880
/* We can't do online recv in this case */
4881
clp = changelist_gather(zhp, ZFS_PROP_NAME, 0,
4882
flags->forceunmount ? MS_FORCE : 0);
4883
if (clp == NULL) {
4884
zfs_close(zhp);
4885
err = -1;
4886
goto out;
4887
}
4888
if (changelist_prefix(clp) != 0) {
4889
changelist_free(clp);
4890
zfs_close(zhp);
4891
err = -1;
4892
goto out;
4893
}
4894
}
4895
4896
/*
4897
* If we are resuming a newfs, set newfs here so that we will
4898
* mount it if the recv succeeds this time. We can tell
4899
* that it was a newfs on the first recv because the fs
4900
* itself will be inconsistent (if the fs existed when we
4901
* did the first recv, we would have received it into
4902
* .../%recv).
4903
*/
4904
if (resuming && zfs_prop_get_int(zhp, ZFS_PROP_INCONSISTENT))
4905
newfs = B_TRUE;
4906
4907
/* we want to know if we're zoned when validating -o|-x props */
4908
zoned = zfs_prop_get_int(zhp, ZFS_PROP_ZONED);
4909
4910
/* may need this info later, get it now we have zhp around */
4911
if (zfs_prop_get(zhp, ZFS_PROP_RECEIVE_RESUME_TOKEN, NULL, 0,
4912
NULL, NULL, 0, B_TRUE) == 0)
4913
hastoken = B_TRUE;
4914
4915
/* gather existing properties on destination */
4916
origprops = fnvlist_alloc();
4917
fnvlist_merge(origprops, zhp->zfs_props);
4918
fnvlist_merge(origprops, zhp->zfs_user_props);
4919
4920
zfs_close(zhp);
4921
} else {
4922
zfs_handle_t *zhp;
4923
4924
/*
4925
* Destination filesystem does not exist. Therefore we better
4926
* be creating a new filesystem (either from a full backup, or
4927
* a clone). It would therefore be invalid if the user
4928
* specified only the pool name (i.e. if the destination name
4929
* contained no slash character).
4930
*/
4931
cp = strrchr(name, '/');
4932
4933
if (!stream_wantsnewfs || cp == NULL) {
4934
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4935
"destination '%s' does not exist"), name);
4936
err = zfs_error(hdl, EZFS_NOENT, errbuf);
4937
goto out;
4938
}
4939
4940
/*
4941
* Trim off the final dataset component so we perform the
4942
* recvbackup ioctl to the filesystems's parent.
4943
*/
4944
*cp = '\0';
4945
4946
if (flags->isprefix && !flags->istail && !flags->dryrun &&
4947
create_parents(hdl, destsnap, strlen(tosnap)) != 0) {
4948
err = zfs_error(hdl, EZFS_BADRESTORE, errbuf);
4949
goto out;
4950
}
4951
4952
/* validate parent */
4953
zhp = zfs_open(hdl, name, ZFS_TYPE_DATASET);
4954
if (zhp == NULL) {
4955
err = zfs_error(hdl, EZFS_BADRESTORE, errbuf);
4956
goto out;
4957
}
4958
if (zfs_get_type(zhp) != ZFS_TYPE_FILESYSTEM) {
4959
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4960
"parent '%s' is not a filesystem"), name);
4961
err = zfs_error(hdl, EZFS_WRONG_PARENT, errbuf);
4962
zfs_close(zhp);
4963
goto out;
4964
}
4965
4966
zfs_close(zhp);
4967
4968
newfs = B_TRUE;
4969
*cp = '/';
4970
}
4971
4972
if (flags->verbose) {
4973
(void) printf("%s %s%s stream of %s into %s\n",
4974
flags->dryrun ? "would receive" : "receiving",
4975
flags->heal ? "corrective " : "",
4976
drrb->drr_fromguid ? "incremental" : "full",
4977
drrb->drr_toname, destsnap);
4978
(void) fflush(stdout);
4979
}
4980
4981
/*
4982
* If this is the top-level dataset, record it so we can use it
4983
* for recursive operations later.
4984
*/
4985
if (top_zfs != NULL &&
4986
(*top_zfs == NULL || strcmp(*top_zfs, name) == 0)) {
4987
toplevel = B_TRUE;
4988
if (*top_zfs == NULL)
4989
*top_zfs = zfs_strdup(hdl, name);
4990
}
4991
4992
if (drrb->drr_type == DMU_OST_ZVOL) {
4993
type = ZFS_TYPE_VOLUME;
4994
} else if (drrb->drr_type == DMU_OST_ZFS) {
4995
type = ZFS_TYPE_FILESYSTEM;
4996
} else {
4997
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
4998
"invalid record type: 0x%d"), drrb->drr_type);
4999
err = zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5000
goto out;
5001
}
5002
if ((err = zfs_setup_cmdline_props(hdl, type, name, zoned, recursive,
5003
stream_wantsnewfs, raw, toplevel, rcvprops, cmdprops, origprops,
5004
&oxprops, &wkeydata, &wkeylen, errbuf)) != 0)
5005
goto out;
5006
5007
/*
5008
* When sending with properties (zfs send -p), the encryption property
5009
* is not included because it is a SETONCE property and therefore
5010
* treated as read only. However, we are always able to determine its
5011
* value because raw sends will include it in the DRR_BDEGIN payload
5012
* and non-raw sends with properties are not allowed for encrypted
5013
* datasets. Therefore, if this is a non-raw properties stream, we can
5014
* infer that the value should be ZIO_CRYPT_OFF and manually add that
5015
* to the received properties.
5016
*/
5017
if (stream_wantsnewfs && !raw && rcvprops != NULL &&
5018
!nvlist_exists(cmdprops, zfs_prop_to_name(ZFS_PROP_ENCRYPTION))) {
5019
if (oxprops == NULL)
5020
oxprops = fnvlist_alloc();
5021
fnvlist_add_uint64(oxprops,
5022
zfs_prop_to_name(ZFS_PROP_ENCRYPTION), ZIO_CRYPT_OFF);
5023
}
5024
5025
if (flags->dryrun) {
5026
void *buf = zfs_alloc(hdl, SPA_MAXBLOCKSIZE);
5027
5028
/*
5029
* We have read the DRR_BEGIN record, but we have
5030
* not yet read the payload. For non-dryrun sends
5031
* this will be done by the kernel, so we must
5032
* emulate that here, before attempting to read
5033
* more records.
5034
*/
5035
err = recv_read(hdl, infd, buf, drr->drr_payloadlen,
5036
flags->byteswap, NULL);
5037
free(buf);
5038
if (err != 0)
5039
goto out;
5040
5041
err = recv_skip(hdl, infd, flags->byteswap);
5042
goto out;
5043
}
5044
5045
if (flags->heal) {
5046
err = ioctl_err = lzc_receive_with_heal(destsnap, rcvprops,
5047
oxprops, wkeydata, wkeylen, origin, flags->force,
5048
flags->heal, flags->resumable, raw, infd, drr_noswap, -1,
5049
&read_bytes, &errflags, NULL, &prop_errors);
5050
} else {
5051
err = ioctl_err = lzc_receive_with_cmdprops(destsnap, rcvprops,
5052
oxprops, wkeydata, wkeylen, origin, flags->force,
5053
flags->resumable, raw, infd, drr_noswap, -1, &read_bytes,
5054
&errflags, NULL, &prop_errors);
5055
}
5056
ioctl_errno = ioctl_err;
5057
prop_errflags = errflags;
5058
5059
if (err == 0) {
5060
nvpair_t *prop_err = NULL;
5061
5062
while ((prop_err = nvlist_next_nvpair(prop_errors,
5063
prop_err)) != NULL) {
5064
char tbuf[1024];
5065
zfs_prop_t prop;
5066
int intval;
5067
5068
prop = zfs_name_to_prop(nvpair_name(prop_err));
5069
(void) nvpair_value_int32(prop_err, &intval);
5070
if (strcmp(nvpair_name(prop_err),
5071
ZPROP_N_MORE_ERRORS) == 0) {
5072
trunc_prop_errs(intval);
5073
break;
5074
} else if (snapname == NULL || finalsnap == NULL ||
5075
strcmp(finalsnap, snapname) == 0 ||
5076
strcmp(nvpair_name(prop_err),
5077
zfs_prop_to_name(ZFS_PROP_REFQUOTA)) != 0) {
5078
/*
5079
* Skip the special case of, for example,
5080
* "refquota", errors on intermediate
5081
* snapshots leading up to a final one.
5082
* That's why we have all of the checks above.
5083
*
5084
* See zfs_ioctl.c's extract_delay_props() for
5085
* a list of props which can fail on
5086
* intermediate snapshots, but shouldn't
5087
* affect the overall receive.
5088
*/
5089
(void) snprintf(tbuf, sizeof (tbuf),
5090
dgettext(TEXT_DOMAIN,
5091
"cannot receive %s property on %s"),
5092
nvpair_name(prop_err), name);
5093
zfs_setprop_error(hdl, prop, intval, tbuf);
5094
}
5095
}
5096
}
5097
5098
if (err == 0 && snapprops_nvlist) {
5099
zfs_cmd_t zc = {"\0"};
5100
5101
(void) strlcpy(zc.zc_name, destsnap, sizeof (zc.zc_name));
5102
zc.zc_cookie = B_TRUE; /* received */
5103
zcmd_write_src_nvlist(hdl, &zc, snapprops_nvlist);
5104
(void) zfs_ioctl(hdl, ZFS_IOC_SET_PROP, &zc);
5105
zcmd_free_nvlists(&zc);
5106
}
5107
if (err == 0 && snapholds_nvlist) {
5108
nvpair_t *pair;
5109
nvlist_t *holds, *errors = NULL;
5110
int cleanup_fd = -1;
5111
5112
VERIFY0(nvlist_alloc(&holds, 0, KM_SLEEP));
5113
for (pair = nvlist_next_nvpair(snapholds_nvlist, NULL);
5114
pair != NULL;
5115
pair = nvlist_next_nvpair(snapholds_nvlist, pair)) {
5116
fnvlist_add_string(holds, destsnap, nvpair_name(pair));
5117
}
5118
(void) lzc_hold(holds, cleanup_fd, &errors);
5119
fnvlist_free(snapholds_nvlist);
5120
fnvlist_free(holds);
5121
}
5122
5123
if (err && (ioctl_errno == ENOENT || ioctl_errno == EEXIST)) {
5124
/*
5125
* It may be that this snapshot already exists,
5126
* in which case we want to consume & ignore it
5127
* rather than failing.
5128
*/
5129
avl_tree_t *local_avl;
5130
nvlist_t *local_nv, *fs;
5131
cp = strchr(destsnap, '@');
5132
5133
/*
5134
* XXX Do this faster by just iterating over snaps in
5135
* this fs. Also if zc_value does not exist, we will
5136
* get a strange "does not exist" error message.
5137
*/
5138
*cp = '\0';
5139
if (gather_nvlist(hdl, destsnap, NULL, NULL, B_FALSE, B_TRUE,
5140
B_FALSE, B_FALSE, B_FALSE, B_FALSE, B_FALSE, B_FALSE,
5141
B_TRUE, &local_nv, &local_avl) == 0) {
5142
*cp = '@';
5143
fs = fsavl_find(local_avl, drrb->drr_toguid, NULL);
5144
fsavl_destroy(local_avl);
5145
fnvlist_free(local_nv);
5146
5147
if (fs != NULL) {
5148
if (flags->verbose) {
5149
(void) printf("snap %s already exists; "
5150
"ignoring\n", destsnap);
5151
}
5152
err = ioctl_err = recv_skip(hdl, infd,
5153
flags->byteswap);
5154
}
5155
}
5156
*cp = '@';
5157
}
5158
5159
if (ioctl_err != 0) {
5160
switch (ioctl_errno) {
5161
case ENODEV:
5162
cp = strchr(destsnap, '@');
5163
*cp = '\0';
5164
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5165
"most recent snapshot of %s does not\n"
5166
"match incremental source"), destsnap);
5167
(void) zfs_error(hdl, EZFS_BADRESTORE, errbuf);
5168
*cp = '@';
5169
break;
5170
case ETXTBSY:
5171
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5172
"destination %s has been modified\n"
5173
"since most recent snapshot"), name);
5174
(void) zfs_error(hdl, EZFS_BADRESTORE, errbuf);
5175
break;
5176
case EACCES:
5177
if (flags->heal) {
5178
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5179
"key must be loaded to do a non-raw "
5180
"corrective recv on an encrypted "
5181
"dataset."));
5182
} else if (raw && stream_wantsnewfs) {
5183
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5184
"failed to create encryption key"));
5185
} else if (raw && !stream_wantsnewfs) {
5186
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5187
"encryption key does not match "
5188
"existing key"));
5189
} else {
5190
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5191
"inherited key must be loaded"));
5192
}
5193
(void) zfs_error(hdl, EZFS_CRYPTOFAILED, errbuf);
5194
break;
5195
case EEXIST:
5196
cp = strchr(destsnap, '@');
5197
if (newfs) {
5198
/* it's the containing fs that exists */
5199
*cp = '\0';
5200
}
5201
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5202
"destination already exists"));
5203
(void) zfs_error_fmt(hdl, EZFS_EXISTS,
5204
dgettext(TEXT_DOMAIN, "cannot restore to %s"),
5205
destsnap);
5206
*cp = '@';
5207
break;
5208
case EINVAL:
5209
if (embedded && !raw) {
5210
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5211
"incompatible embedded data stream "
5212
"feature with encrypted receive."));
5213
} else if (flags->resumable) {
5214
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5215
"kernel modules must be upgraded to "
5216
"receive this stream."));
5217
}
5218
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5219
break;
5220
case ECKSUM:
5221
case ZFS_ERR_STREAM_TRUNCATED:
5222
if (flags->heal)
5223
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5224
"corrective receive was not able to "
5225
"reconstruct the data needed for "
5226
"healing."));
5227
else
5228
recv_ecksum_set_aux(hdl, destsnap,
5229
flags->resumable, ioctl_err == ECKSUM);
5230
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5231
break;
5232
case ZFS_ERR_STREAM_LARGE_BLOCK_MISMATCH:
5233
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5234
"incremental send stream requires -L "
5235
"(--large-block), to match previous receive."));
5236
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5237
break;
5238
case ENOTSUP:
5239
if (flags->heal)
5240
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5241
"stream is not compatible with the "
5242
"data in the pool."));
5243
else
5244
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5245
"pool must be upgraded to receive this "
5246
"stream."));
5247
(void) zfs_error(hdl, EZFS_BADVERSION, errbuf);
5248
break;
5249
case ZFS_ERR_CRYPTO_NOTSUP:
5250
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5251
"stream uses crypto parameters not compatible with "
5252
"this pool"));
5253
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5254
break;
5255
case EDQUOT:
5256
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5257
"destination %s space quota exceeded."), name);
5258
(void) zfs_error(hdl, EZFS_NOSPC, errbuf);
5259
break;
5260
case ZFS_ERR_FROM_IVSET_GUID_MISSING:
5261
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5262
"IV set guid missing. See errata %u at "
5263
"https://openzfs.github.io/openzfs-docs/msg/"
5264
"ZFS-8000-ER."),
5265
ZPOOL_ERRATA_ZOL_8308_ENCRYPTION);
5266
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5267
break;
5268
case ZFS_ERR_FROM_IVSET_GUID_MISMATCH:
5269
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5270
"IV set guid mismatch. See the 'zfs receive' "
5271
"man page section\n discussing the limitations "
5272
"of raw encrypted send streams."));
5273
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5274
break;
5275
case ZFS_ERR_SPILL_BLOCK_FLAG_MISSING:
5276
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5277
"Spill block flag missing for raw send.\n"
5278
"The zfs software on the sending system must "
5279
"be updated."));
5280
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5281
break;
5282
case ZFS_ERR_RESUME_EXISTS:
5283
cp = strchr(destsnap, '@');
5284
if (newfs) {
5285
/* it's the containing fs that exists */
5286
*cp = '\0';
5287
}
5288
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5289
"Resuming recv on existing dataset without force"));
5290
(void) zfs_error_fmt(hdl, EZFS_RESUME_EXISTS,
5291
dgettext(TEXT_DOMAIN, "cannot resume recv %s"),
5292
destsnap);
5293
*cp = '@';
5294
break;
5295
case E2BIG:
5296
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5297
"zfs receive required kernel memory allocation "
5298
"larger than the system can support. Please file "
5299
"an issue at the OpenZFS issue tracker:\n"
5300
"https://github.com/openzfs/zfs/issues/new"));
5301
(void) zfs_error(hdl, EZFS_BADSTREAM, errbuf);
5302
break;
5303
case EBUSY:
5304
if (hastoken) {
5305
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5306
"destination %s contains "
5307
"partially-complete state from "
5308
"\"zfs receive -s\"."), name);
5309
(void) zfs_error(hdl, EZFS_BUSY, errbuf);
5310
break;
5311
}
5312
zfs_fallthrough;
5313
default:
5314
(void) zfs_standard_error(hdl, ioctl_errno, errbuf);
5315
}
5316
}
5317
5318
/*
5319
* Mount the target filesystem (if created). Also mount any
5320
* children of the target filesystem if we did a replication
5321
* receive (indicated by stream_avl being non-NULL).
5322
*/
5323
if (clp) {
5324
if (!flags->nomount)
5325
err |= changelist_postfix(clp);
5326
changelist_free(clp);
5327
}
5328
5329
if ((newfs || stream_avl) && type == ZFS_TYPE_FILESYSTEM && !redacted)
5330
flags->domount = B_TRUE;
5331
5332
if (prop_errflags & ZPROP_ERR_NOCLEAR) {
5333
(void) fprintf(stderr, dgettext(TEXT_DOMAIN, "Warning: "
5334
"failed to clear unreceived properties on %s"), name);
5335
(void) fprintf(stderr, "\n");
5336
}
5337
if (prop_errflags & ZPROP_ERR_NORESTORE) {
5338
(void) fprintf(stderr, dgettext(TEXT_DOMAIN, "Warning: "
5339
"failed to restore original properties on %s"), name);
5340
(void) fprintf(stderr, "\n");
5341
}
5342
5343
if (err || ioctl_err) {
5344
err = -1;
5345
goto out;
5346
}
5347
5348
if (flags->verbose) {
5349
char buf1[64];
5350
char buf2[64];
5351
uint64_t bytes = read_bytes;
5352
struct timespec delta;
5353
clock_gettime(CLOCK_MONOTONIC_RAW, &delta);
5354
if (begin_time.tv_nsec > delta.tv_nsec) {
5355
delta.tv_nsec =
5356
1000000000 + delta.tv_nsec - begin_time.tv_nsec;
5357
delta.tv_sec -= 1;
5358
} else
5359
delta.tv_nsec -= begin_time.tv_nsec;
5360
delta.tv_sec -= begin_time.tv_sec;
5361
if (delta.tv_sec == 0 && delta.tv_nsec == 0)
5362
delta.tv_nsec = 1;
5363
double delta_f = delta.tv_sec + (delta.tv_nsec / 1e9);
5364
zfs_nicebytes(bytes, buf1, sizeof (buf1));
5365
zfs_nicebytes(bytes / delta_f, buf2, sizeof (buf2));
5366
5367
(void) printf("received %s stream in %.2f seconds (%s/sec)\n",
5368
buf1, delta_f, buf2);
5369
}
5370
5371
err = 0;
5372
out:
5373
if (prop_errors != NULL)
5374
fnvlist_free(prop_errors);
5375
5376
if (tmp_keylocation[0] != '\0') {
5377
fnvlist_add_string(rcvprops,
5378
zfs_prop_to_name(ZFS_PROP_KEYLOCATION), tmp_keylocation);
5379
}
5380
5381
if (newprops)
5382
fnvlist_free(rcvprops);
5383
5384
fnvlist_free(oxprops);
5385
fnvlist_free(origprops);
5386
5387
return (err);
5388
}
5389
5390
/*
5391
* Check properties we were asked to override (both -o|-x)
5392
*/
5393
static boolean_t
5394
zfs_receive_checkprops(libzfs_handle_t *hdl, nvlist_t *props,
5395
const char *errbuf)
5396
{
5397
nvpair_t *nvp = NULL;
5398
zfs_prop_t prop;
5399
const char *name;
5400
5401
while ((nvp = nvlist_next_nvpair(props, nvp)) != NULL) {
5402
name = nvpair_name(nvp);
5403
prop = zfs_name_to_prop(name);
5404
5405
if (prop == ZPROP_USERPROP) {
5406
if (!zfs_prop_user(name)) {
5407
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5408
"%s: invalid property '%s'"), errbuf, name);
5409
return (B_FALSE);
5410
}
5411
continue;
5412
}
5413
/*
5414
* "origin" is readonly but is used to receive datasets as
5415
* clones so we don't raise an error here
5416
*/
5417
if (prop == ZFS_PROP_ORIGIN)
5418
continue;
5419
5420
/* encryption params have their own verification later */
5421
if (prop == ZFS_PROP_ENCRYPTION ||
5422
zfs_prop_encryption_key_param(prop))
5423
continue;
5424
5425
/*
5426
* cannot override readonly, set-once and other specific
5427
* settable properties
5428
*/
5429
if (zfs_prop_readonly(prop) || prop == ZFS_PROP_VERSION ||
5430
prop == ZFS_PROP_VOLSIZE) {
5431
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5432
"%s: invalid property '%s'"), errbuf, name);
5433
return (B_FALSE);
5434
}
5435
}
5436
5437
return (B_TRUE);
5438
}
5439
5440
static int
5441
zfs_receive_impl(libzfs_handle_t *hdl, const char *tosnap,
5442
const char *originsnap, recvflags_t *flags, int infd, const char *sendfs,
5443
nvlist_t *stream_nv, avl_tree_t *stream_avl, char **top_zfs,
5444
const char *finalsnap, nvlist_t *cmdprops)
5445
{
5446
int err;
5447
dmu_replay_record_t drr, drr_noswap;
5448
struct drr_begin *drrb = &drr.drr_u.drr_begin;
5449
char errbuf[ERRBUFLEN];
5450
zio_cksum_t zcksum = { { 0 } };
5451
uint64_t featureflags;
5452
int hdrtype;
5453
5454
(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
5455
"cannot receive"));
5456
5457
/* check cmdline props, raise an error if they cannot be received */
5458
if (!zfs_receive_checkprops(hdl, cmdprops, errbuf))
5459
return (zfs_error(hdl, EZFS_BADPROP, errbuf));
5460
5461
if (flags->isprefix &&
5462
!zfs_dataset_exists(hdl, tosnap, ZFS_TYPE_DATASET)) {
5463
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "specified fs "
5464
"(%s) does not exist"), tosnap);
5465
return (zfs_error(hdl, EZFS_NOENT, errbuf));
5466
}
5467
if (originsnap &&
5468
!zfs_dataset_exists(hdl, originsnap, ZFS_TYPE_DATASET)) {
5469
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "specified origin fs "
5470
"(%s) does not exist"), originsnap);
5471
return (zfs_error(hdl, EZFS_NOENT, errbuf));
5472
}
5473
5474
/* read in the BEGIN record */
5475
if (0 != (err = recv_read(hdl, infd, &drr, sizeof (drr), B_FALSE,
5476
&zcksum)))
5477
return (err);
5478
5479
if (drr.drr_type == DRR_END || drr.drr_type == BSWAP_32(DRR_END)) {
5480
/* It's the double end record at the end of a package */
5481
return (ENODATA);
5482
}
5483
5484
/* the kernel needs the non-byteswapped begin record */
5485
drr_noswap = drr;
5486
5487
flags->byteswap = B_FALSE;
5488
if (drrb->drr_magic == BSWAP_64(DMU_BACKUP_MAGIC)) {
5489
/*
5490
* We computed the checksum in the wrong byteorder in
5491
* recv_read() above; do it again correctly.
5492
*/
5493
memset(&zcksum, 0, sizeof (zio_cksum_t));
5494
fletcher_4_incremental_byteswap(&drr, sizeof (drr), &zcksum);
5495
flags->byteswap = B_TRUE;
5496
5497
drr.drr_type = BSWAP_32(drr.drr_type);
5498
drr.drr_payloadlen = BSWAP_32(drr.drr_payloadlen);
5499
drrb->drr_magic = BSWAP_64(drrb->drr_magic);
5500
drrb->drr_versioninfo = BSWAP_64(drrb->drr_versioninfo);
5501
drrb->drr_creation_time = BSWAP_64(drrb->drr_creation_time);
5502
drrb->drr_type = BSWAP_32(drrb->drr_type);
5503
drrb->drr_flags = BSWAP_32(drrb->drr_flags);
5504
drrb->drr_toguid = BSWAP_64(drrb->drr_toguid);
5505
drrb->drr_fromguid = BSWAP_64(drrb->drr_fromguid);
5506
}
5507
5508
if (drrb->drr_magic != DMU_BACKUP_MAGIC || drr.drr_type != DRR_BEGIN) {
5509
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "invalid "
5510
"stream (bad magic number)"));
5511
return (zfs_error(hdl, EZFS_BADSTREAM, errbuf));
5512
}
5513
5514
featureflags = DMU_GET_FEATUREFLAGS(drrb->drr_versioninfo);
5515
hdrtype = DMU_GET_STREAM_HDRTYPE(drrb->drr_versioninfo);
5516
5517
if (!DMU_STREAM_SUPPORTED(featureflags) ||
5518
(hdrtype != DMU_SUBSTREAM && hdrtype != DMU_COMPOUNDSTREAM)) {
5519
/*
5520
* Let's be explicit about this one, since rather than
5521
* being a new feature we can't know, it's an old
5522
* feature we dropped.
5523
*/
5524
if (featureflags & DMU_BACKUP_FEATURE_DEDUP) {
5525
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5526
"stream has deprecated feature: dedup, try "
5527
"'zstream redup [send in a file] | zfs recv "
5528
"[...]'"));
5529
} else {
5530
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
5531
"stream has unsupported feature, feature flags = "
5532
"%llx (unknown flags = %llx)"),
5533
(u_longlong_t)featureflags,
5534
(u_longlong_t)((featureflags) &
5535
~DMU_BACKUP_FEATURE_MASK));
5536
}
5537
return (zfs_error(hdl, EZFS_BADSTREAM, errbuf));
5538
}
5539
5540
/* Holds feature is set once in the compound stream header. */
5541
if (featureflags & DMU_BACKUP_FEATURE_HOLDS)
5542
flags->holds = B_TRUE;
5543
5544
if (strchr(drrb->drr_toname, '@') == NULL) {
5545
zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "invalid "
5546
"stream (bad snapshot name)"));
5547
return (zfs_error(hdl, EZFS_BADSTREAM, errbuf));
5548
}
5549
5550
if (DMU_GET_STREAM_HDRTYPE(drrb->drr_versioninfo) == DMU_SUBSTREAM) {
5551
char nonpackage_sendfs[ZFS_MAX_DATASET_NAME_LEN];
5552
if (sendfs == NULL) {
5553
/*
5554
* We were not called from zfs_receive_package(). Get
5555
* the fs specified by 'zfs send'.
5556
*/
5557
char *cp;
5558
(void) strlcpy(nonpackage_sendfs,
5559
drr.drr_u.drr_begin.drr_toname,
5560
sizeof (nonpackage_sendfs));
5561
if ((cp = strchr(nonpackage_sendfs, '@')) != NULL)
5562
*cp = '\0';
5563
sendfs = nonpackage_sendfs;
5564
VERIFY0P(finalsnap);
5565
}
5566
return (zfs_receive_one(hdl, infd, tosnap, originsnap, flags,
5567
&drr, &drr_noswap, sendfs, stream_nv, stream_avl, top_zfs,
5568
finalsnap, cmdprops));
5569
} else {
5570
assert(DMU_GET_STREAM_HDRTYPE(drrb->drr_versioninfo) ==
5571
DMU_COMPOUNDSTREAM);
5572
return (zfs_receive_package(hdl, infd, tosnap, flags, &drr,
5573
&zcksum, top_zfs, cmdprops));
5574
}
5575
}
5576
5577
/*
5578
* Restores a backup of tosnap from the file descriptor specified by infd.
5579
* Return 0 on total success, -2 if some things couldn't be
5580
* destroyed/renamed/promoted, -1 if some things couldn't be received.
5581
* (-1 will override -2, if -1 and the resumable flag was specified the
5582
* transfer can be resumed if the sending side supports it).
5583
*/
5584
int
5585
zfs_receive(libzfs_handle_t *hdl, const char *tosnap, nvlist_t *props,
5586
recvflags_t *flags, int infd, avl_tree_t *stream_avl)
5587
{
5588
char *top_zfs = NULL;
5589
int err;
5590
struct stat sb;
5591
const char *originsnap = NULL;
5592
5593
/*
5594
* The only way fstat can fail is if we do not have a valid file
5595
* descriptor.
5596
*/
5597
if (fstat(infd, &sb) == -1) {
5598
perror("fstat");
5599
return (-2);
5600
}
5601
5602
if (props) {
5603
err = nvlist_lookup_string(props, "origin", &originsnap);
5604
if (err && err != ENOENT)
5605
return (err);
5606
}
5607
5608
err = zfs_receive_impl(hdl, tosnap, originsnap, flags, infd, NULL, NULL,
5609
stream_avl, &top_zfs, NULL, props);
5610
5611
if (err == 0 && !flags->nomount && flags->domount && top_zfs) {
5612
zfs_handle_t *zhp = NULL;
5613
prop_changelist_t *clp = NULL;
5614
5615
zhp = zfs_open(hdl, top_zfs,
5616
ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME);
5617
if (zhp == NULL) {
5618
err = -1;
5619
goto out;
5620
} else {
5621
if (zhp->zfs_type == ZFS_TYPE_VOLUME) {
5622
zfs_close(zhp);
5623
goto out;
5624
}
5625
5626
clp = changelist_gather(zhp, ZFS_PROP_MOUNTPOINT,
5627
CL_GATHER_MOUNT_ALWAYS,
5628
flags->forceunmount ? MS_FORCE : 0);
5629
zfs_close(zhp);
5630
if (clp == NULL) {
5631
err = -1;
5632
goto out;
5633
}
5634
5635
/* mount and share received datasets */
5636
err = changelist_postfix(clp);
5637
changelist_free(clp);
5638
if (err != 0)
5639
err = -1;
5640
}
5641
}
5642
5643
out:
5644
if (top_zfs)
5645
free(top_zfs);
5646
5647
return (err);
5648
}
5649
5650