12654012fSReza Sabdar /* 28c4f9701SJanice Chang * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved. 32654012fSReza Sabdar */ 42654012fSReza Sabdar 52654012fSReza Sabdar /* 62654012fSReza Sabdar * BSD 3 Clause License 72654012fSReza Sabdar * 82654012fSReza Sabdar * Copyright (c) 2007, The Storage Networking Industry Association. 92654012fSReza Sabdar * 102654012fSReza Sabdar * Redistribution and use in source and binary forms, with or without 112654012fSReza Sabdar * modification, are permitted provided that the following conditions 122654012fSReza Sabdar * are met: 132654012fSReza Sabdar * - Redistributions of source code must retain the above copyright 142654012fSReza Sabdar * notice, this list of conditions and the following disclaimer. 152654012fSReza Sabdar * 162654012fSReza Sabdar * - Redistributions in binary form must reproduce the above copyright 172654012fSReza Sabdar * notice, this list of conditions and the following disclaimer in 182654012fSReza Sabdar * the documentation and/or other materials provided with the 192654012fSReza Sabdar * distribution. 202654012fSReza Sabdar * 212654012fSReza Sabdar * - Neither the name of The Storage Networking Industry Association (SNIA) 222654012fSReza Sabdar * nor the names of its contributors may be used to endorse or promote 232654012fSReza Sabdar * products derived from this software without specific prior written 242654012fSReza Sabdar * permission. 252654012fSReza Sabdar * 262654012fSReza Sabdar * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 272654012fSReza Sabdar * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 282654012fSReza Sabdar * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 292654012fSReza Sabdar * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 302654012fSReza Sabdar * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 312654012fSReza Sabdar * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 322654012fSReza Sabdar * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 332654012fSReza Sabdar * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 342654012fSReza Sabdar * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 352654012fSReza Sabdar * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 362654012fSReza Sabdar * POSSIBILITY OF SUCH DAMAGE. 372654012fSReza Sabdar */ 388c4f9701SJanice Chang /* Copyright (c) 2007, The Storage Networking Industry Association. */ 398c4f9701SJanice Chang /* Copyright (c) 1996, 1997 PDC, Network Appliance. All Rights Reserved */ 40*a23888a3SJan Kryl /* Copyright 2014 Nexenta Systems, Inc. All rights reserved. */ 41*a23888a3SJan Kryl 422654012fSReza Sabdar #include <sys/stat.h> 432654012fSReza Sabdar #include <sys/types.h> 442654012fSReza Sabdar #include <sys/time.h> 452654012fSReza Sabdar #include <ctype.h> 462654012fSReza Sabdar #include <sys/socket.h> 472654012fSReza Sabdar #include <sys/acl.h> 482654012fSReza Sabdar #include <netinet/in.h> 492654012fSReza Sabdar #include <arpa/inet.h> 502654012fSReza Sabdar #include <errno.h> 512654012fSReza Sabdar #include <stdio.h> 522654012fSReza Sabdar #include <string.h> 532654012fSReza Sabdar #include <time.h> 542654012fSReza Sabdar #include <cstack.h> 552654012fSReza Sabdar #include "ndmp.h" 562654012fSReza Sabdar #include "ndmpd.h" 572654012fSReza Sabdar #include <bitmap.h> 582654012fSReza Sabdar #include <traverse.h> 592654012fSReza Sabdar 602654012fSReza Sabdar 612654012fSReza Sabdar /* 622654012fSReza Sabdar * Maximum length of the string-representation of u_longlong_t type. 632654012fSReza Sabdar */ 642654012fSReza Sabdar #define QUAD_DECIMAL_LEN 20 652654012fSReza Sabdar 662654012fSReza Sabdar 67416eec61SReza Sabdar /* Is Y=yes or T=true */ 682654012fSReza Sabdar #define IS_YORT(c) (strchr("YT", toupper(c))) 692654012fSReza Sabdar 70416eec61SReza Sabdar /* Is F=file format (vs D=node-dir format) */ 71416eec61SReza Sabdar #define IS_F(c) (toupper(c) == 'F') 722654012fSReza Sabdar 732654012fSReza Sabdar /* 742654012fSReza Sabdar * If path is defined. 752654012fSReza Sabdar */ 762654012fSReza Sabdar #define ISDEFINED(cp) ((cp) && *(cp)) 772654012fSReza Sabdar #define SHOULD_LBRBK(bpp) (!((bpp)->bp_opr & TLM_OP_CHOOSE_ARCHIVE)) 782654012fSReza Sabdar 792654012fSReza Sabdar /* 802654012fSReza Sabdar * Component boundary means end of path or on a '/'. At this 812654012fSReza Sabdar * point both paths should be on component boundary. 822654012fSReza Sabdar */ 832654012fSReza Sabdar #define COMPBNDRY(p) (!*(p) || (*p) == '/') 842654012fSReza Sabdar 852654012fSReza Sabdar typedef struct bk_param_v3 { 862654012fSReza Sabdar ndmpd_session_t *bp_session; 872654012fSReza Sabdar ndmp_lbr_params_t *bp_nlp; 882654012fSReza Sabdar tlm_job_stats_t *bp_js; 892654012fSReza Sabdar tlm_cmd_t *bp_lcmd; 902654012fSReza Sabdar tlm_commands_t *bp_cmds; 912654012fSReza Sabdar tlm_acls_t *bp_tlmacl; 922654012fSReza Sabdar int bp_opr; 932654012fSReza Sabdar char *bp_tmp; 942654012fSReza Sabdar char *bp_chkpnm; 952654012fSReza Sabdar char **bp_excls; 962654012fSReza Sabdar char *bp_unchkpnm; 972654012fSReza Sabdar } bk_param_v3_t; 982654012fSReza Sabdar 992654012fSReza Sabdar 1002654012fSReza Sabdar /* 1012654012fSReza Sabdar * Multiple destination restore mode 1022654012fSReza Sabdar */ 1032654012fSReza Sabdar #define MULTIPLE_DEST_DIRS 128 1042654012fSReza Sabdar 1052654012fSReza Sabdar int multiple_dest_restore = 0; 1062654012fSReza Sabdar 1072654012fSReza Sabdar /* 1082654012fSReza Sabdar * Plug-in module ops 1092654012fSReza Sabdar */ 1102654012fSReza Sabdar ndmp_plugin_t *ndmp_pl; 1112654012fSReza Sabdar 1122654012fSReza Sabdar /* 1132654012fSReza Sabdar * NDMP exclusion list 1142654012fSReza Sabdar */ 1152654012fSReza Sabdar char **ndmp_excl_list = NULL; 1162654012fSReza Sabdar 1172654012fSReza Sabdar /* 1182654012fSReza Sabdar * split_env 1192654012fSReza Sabdar * 1202654012fSReza Sabdar * Splits the string into list of sections separated by the 1212654012fSReza Sabdar * sep character. 1222654012fSReza Sabdar * 1232654012fSReza Sabdar * Parameters: 1242654012fSReza Sabdar * envp (input) - the environment variable that should be broken 1252654012fSReza Sabdar * sep (input) - the separator character 1262654012fSReza Sabdar * 1272654012fSReza Sabdar * Returns: 1282654012fSReza Sabdar * Array of character pointers: On success. The array is allocated 1292654012fSReza Sabdar * as well as all its entries. They all should be freed by the 1302654012fSReza Sabdar * caller. 1312654012fSReza Sabdar * NULL: on error 1322654012fSReza Sabdar */ 1332654012fSReza Sabdar static char ** 1342654012fSReza Sabdar split_env(char *envp, char sep) 1352654012fSReza Sabdar { 1362654012fSReza Sabdar char *bp, *cp, *ep; 1372654012fSReza Sabdar char *save; 1382654012fSReza Sabdar char **cpp; 1392654012fSReza Sabdar int n; 1402654012fSReza Sabdar 1412654012fSReza Sabdar if (!envp) 1422654012fSReza Sabdar return (NULL); 1432654012fSReza Sabdar 1442654012fSReza Sabdar while (isspace(*envp)) 1452654012fSReza Sabdar envp++; 1462654012fSReza Sabdar 1472654012fSReza Sabdar if (!*envp) 1482654012fSReza Sabdar return (NULL); 1492654012fSReza Sabdar 1502654012fSReza Sabdar bp = save = strdup(envp); 1512654012fSReza Sabdar if (!bp) 1522654012fSReza Sabdar return (NULL); 1532654012fSReza Sabdar 1542654012fSReza Sabdar /* 1552654012fSReza Sabdar * Since the env variable is not empty, it contains at least one 1562654012fSReza Sabdar * component 1572654012fSReza Sabdar */ 1582654012fSReza Sabdar n = 1; 1592654012fSReza Sabdar while ((cp = strchr(bp, sep))) { 1602654012fSReza Sabdar if (cp > save && *(cp-1) != '\\') 1612654012fSReza Sabdar n++; 1622654012fSReza Sabdar 1632654012fSReza Sabdar bp = cp + 1; 1642654012fSReza Sabdar } 1652654012fSReza Sabdar 1662654012fSReza Sabdar n++; /* for the terminating NULL pointer */ 1672654012fSReza Sabdar cpp = ndmp_malloc(sizeof (char *) * n); 1682654012fSReza Sabdar if (!cpp) { 1692654012fSReza Sabdar free(save); 1702654012fSReza Sabdar return (NULL); 1712654012fSReza Sabdar } 1722654012fSReza Sabdar 1732654012fSReza Sabdar (void) memset(cpp, 0, n * sizeof (char *)); 1742654012fSReza Sabdar n = 0; 1752654012fSReza Sabdar cp = bp = ep = save; 1762654012fSReza Sabdar while (*cp) 1772654012fSReza Sabdar if (*cp == sep) { 1782654012fSReza Sabdar *ep = '\0'; 1792654012fSReza Sabdar if (strlen(bp) > 0) { 1802654012fSReza Sabdar cpp[n] = strdup(bp); 1812654012fSReza Sabdar if (!cpp[n++]) { 1822654012fSReza Sabdar tlm_release_list(cpp); 1832654012fSReza Sabdar cpp = NULL; 1842654012fSReza Sabdar break; 1852654012fSReza Sabdar } 1862654012fSReza Sabdar } 1872654012fSReza Sabdar ep = bp = ++cp; 1882654012fSReza Sabdar } else if (*cp == '\\') { 1892654012fSReza Sabdar ++cp; 1902654012fSReza Sabdar if (*cp == 'n') { /* "\n" */ 1912654012fSReza Sabdar *ep++ = '\n'; 1922654012fSReza Sabdar cp++; 1932654012fSReza Sabdar } else if (*cp == 't') { /* "\t" */ 1942654012fSReza Sabdar *ep++ = '\t'; 1952654012fSReza Sabdar cp++; 1962654012fSReza Sabdar } else 1972654012fSReza Sabdar *ep++ = *cp++; 1982654012fSReza Sabdar } else 1992654012fSReza Sabdar *ep++ = *cp++; 2002654012fSReza Sabdar 2012654012fSReza Sabdar *ep = '\0'; 2022654012fSReza Sabdar if (cpp) { 2032654012fSReza Sabdar if (strlen(bp) > 0) { 2042654012fSReza Sabdar cpp[n] = strdup(bp); 2052654012fSReza Sabdar if (!cpp[n++]) { 2062654012fSReza Sabdar tlm_release_list(cpp); 2072654012fSReza Sabdar cpp = NULL; 2082654012fSReza Sabdar } else 2092654012fSReza Sabdar cpp[n] = NULL; 2102654012fSReza Sabdar } 2112654012fSReza Sabdar 2122654012fSReza Sabdar if (n == 0 && cpp != NULL) { 2132654012fSReza Sabdar tlm_release_list(cpp); 2142654012fSReza Sabdar cpp = NULL; 2152654012fSReza Sabdar } 2162654012fSReza Sabdar } 2172654012fSReza Sabdar 2182654012fSReza Sabdar free(save); 2192654012fSReza Sabdar return (cpp); 2202654012fSReza Sabdar } 2212654012fSReza Sabdar 2222654012fSReza Sabdar 2232654012fSReza Sabdar /* 2242654012fSReza Sabdar * prl 2252654012fSReza Sabdar * 2262654012fSReza Sabdar * Print the array of character pointers passed to it. This is 2272654012fSReza Sabdar * used for debugging purpose. 2282654012fSReza Sabdar * 2292654012fSReza Sabdar * Parameters: 2302654012fSReza Sabdar * lpp (input) - pointer to the array of strings 2312654012fSReza Sabdar * 2322654012fSReza Sabdar * Returns: 2332654012fSReza Sabdar * void 2342654012fSReza Sabdar */ 2352654012fSReza Sabdar static void 2362654012fSReza Sabdar prl(char **lpp) 2372654012fSReza Sabdar { 2382654012fSReza Sabdar if (!lpp) { 2392654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "empty"); 2402654012fSReza Sabdar return; 2412654012fSReza Sabdar } 2422654012fSReza Sabdar 2432654012fSReza Sabdar while (*lpp) 2442654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "\"%s\"", *lpp++); 2452654012fSReza Sabdar } 2462654012fSReza Sabdar 2472654012fSReza Sabdar 2482654012fSReza Sabdar /* 2492654012fSReza Sabdar * inlist 2502654012fSReza Sabdar * 2512654012fSReza Sabdar * Looks through all the strings of the array to see if the ent 2522654012fSReza Sabdar * matches any of the strings. The strings are patterns. 2532654012fSReza Sabdar * 2542654012fSReza Sabdar * Parameters: 2552654012fSReza Sabdar * lpp (input) - pointer to the array of strings 2562654012fSReza Sabdar * ent (input) - the entry to be matched 2572654012fSReza Sabdar * 2582654012fSReza Sabdar * Returns: 2592654012fSReza Sabdar * TRUE: if there is a match 2602654012fSReza Sabdar * FALSE: invalid argument or no match 2612654012fSReza Sabdar */ 2622654012fSReza Sabdar static boolean_t 2632654012fSReza Sabdar inlist(char **lpp, char *ent) 2642654012fSReza Sabdar { 2652654012fSReza Sabdar if (!lpp || !ent) { 2662654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "empty list"); 2672654012fSReza Sabdar return (FALSE); 2682654012fSReza Sabdar } 2692654012fSReza Sabdar 2702654012fSReza Sabdar while (*lpp) { 2712654012fSReza Sabdar /* 2722654012fSReza Sabdar * Fixing the sync_sort NDMPV3 problem, it sends the inclusion 2732654012fSReza Sabdar * like "./" which we should skip the "./" 2742654012fSReza Sabdar */ 2752654012fSReza Sabdar char *pattern = *lpp; 2762654012fSReza Sabdar if (strncmp(pattern, "./", 2) == 0) 2772654012fSReza Sabdar pattern += 2; 2782654012fSReza Sabdar 2792654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "pattern %s, ent %s", pattern, ent); 2802654012fSReza Sabdar 2812654012fSReza Sabdar if (match(pattern, ent)) { 2822654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "match(%s,%s)", pattern, ent); 2832654012fSReza Sabdar return (TRUE); 2842654012fSReza Sabdar } 2852654012fSReza Sabdar lpp++; 2862654012fSReza Sabdar } 2872654012fSReza Sabdar 2882654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "no match"); 2892654012fSReza Sabdar return (FALSE); 2902654012fSReza Sabdar } 2912654012fSReza Sabdar 2922654012fSReza Sabdar 2932654012fSReza Sabdar /* 2942654012fSReza Sabdar * inexl 2952654012fSReza Sabdar * 2962654012fSReza Sabdar * Checks if the entry is in the list. This is used for exclusion 2972654012fSReza Sabdar * list. If the exclusion list is empty, FALSE should be returned 2982654012fSReza Sabdar * showing that nothing should be excluded by default. 2992654012fSReza Sabdar * 3002654012fSReza Sabdar * Parameters: 3012654012fSReza Sabdar * lpp (input) - pointer to the array of strings 3022654012fSReza Sabdar * ent (input) - the entry to be matched 3032654012fSReza Sabdar * 3042654012fSReza Sabdar * Returns: 3052654012fSReza Sabdar * TRUE: if there is a match 3062654012fSReza Sabdar * FALSE: invalid argument or no match 3072654012fSReza Sabdar * 3082654012fSReza Sabdar */ 3092654012fSReza Sabdar static boolean_t 3102654012fSReza Sabdar inexl(char **lpp, char *ent) 3112654012fSReza Sabdar { 3122654012fSReza Sabdar if (!lpp || !ent) 3132654012fSReza Sabdar return (FALSE); 3142654012fSReza Sabdar 3152654012fSReza Sabdar return (inlist(lpp, ent)); 3162654012fSReza Sabdar } 3172654012fSReza Sabdar 3182654012fSReza Sabdar 3192654012fSReza Sabdar /* 3202654012fSReza Sabdar * ininc 3212654012fSReza Sabdar * 3222654012fSReza Sabdar * Checks if the entry is in the list. This is used for inclusion 3232654012fSReza Sabdar * list. If the inclusion list is empty, TRUE should be returned 3242654012fSReza Sabdar * showing that everything should be included by default. 3252654012fSReza Sabdar * 3262654012fSReza Sabdar * Parameters: 3272654012fSReza Sabdar * lpp (input) - pointer to the array of strings 3282654012fSReza Sabdar * ent (input) - the entry to be matched 3292654012fSReza Sabdar * 3302654012fSReza Sabdar * Returns: 3312654012fSReza Sabdar * TRUE: if there is a match or the list is empty 3322654012fSReza Sabdar * FALSE: no match 3332654012fSReza Sabdar */ 3342654012fSReza Sabdar static boolean_t 3352654012fSReza Sabdar ininc(char **lpp, char *ent) 3362654012fSReza Sabdar { 3372654012fSReza Sabdar if (!lpp || !ent || !*ent) 3382654012fSReza Sabdar return (TRUE); 3392654012fSReza Sabdar 3402654012fSReza Sabdar return (inlist(lpp, ent)); 3412654012fSReza Sabdar } 3422654012fSReza Sabdar 3432654012fSReza Sabdar 3442654012fSReza Sabdar /* 3452654012fSReza Sabdar * setupsels 3462654012fSReza Sabdar * 3472654012fSReza Sabdar * Set up the selection list for Local B/R functions. A new array of 3482654012fSReza Sabdar * "char *" is created and the pointers point to the original paths of 3492654012fSReza Sabdar * the Nlist. 3502654012fSReza Sabdar * 3512654012fSReza Sabdar * Parameters: 3522654012fSReza Sabdar * session (input) - pointer to the session 3532654012fSReza Sabdar * params (input) - pointer to the parameters structure 3542654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 3552654012fSReza Sabdar * index(input) - If not zero is the DAR entry position 3562654012fSReza Sabdar * 3572654012fSReza Sabdar * Returns: 3582654012fSReza Sabdar * list pointer: on success 3592654012fSReza Sabdar * NULL: on error 3602654012fSReza Sabdar */ 3612654012fSReza Sabdar /*ARGSUSED*/ 3622654012fSReza Sabdar char ** 3632654012fSReza Sabdar setupsels(ndmpd_session_t *session, ndmpd_module_params_t *params, 3642654012fSReza Sabdar ndmp_lbr_params_t *nlp, int index) 3652654012fSReza Sabdar { 3662654012fSReza Sabdar char **lpp, **save; 3672654012fSReza Sabdar int i, n; 3682654012fSReza Sabdar int len; 3692654012fSReza Sabdar int start, end; 3702654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 3712654012fSReza Sabdar 3722654012fSReza Sabdar n = session->ns_data.dd_nlist_len; 3732654012fSReza Sabdar 3742654012fSReza Sabdar save = lpp = ndmp_malloc(sizeof (char *) * (n + 1)); 3752654012fSReza Sabdar if (!lpp) { 3762654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, "Insufficient memory.\n"); 3772654012fSReza Sabdar return (NULL); 3782654012fSReza Sabdar } 3792654012fSReza Sabdar 3802654012fSReza Sabdar if (index) { /* DAR, just one entry */ 3812654012fSReza Sabdar /* 3822654012fSReza Sabdar * We have to setup a list of strings that will not match any 3832654012fSReza Sabdar * file. One DAR entry will be added in the right position later 3842654012fSReza Sabdar * in this function. 3852654012fSReza Sabdar * When the match is called from tar_getdir the 3862654012fSReza Sabdar * location of the selection that matches the entry is 3872654012fSReza Sabdar * important 3882654012fSReza Sabdar */ 3892654012fSReza Sabdar for (i = 0; i < n; ++i) 3902654012fSReza Sabdar *(lpp+i) = " "; 3912654012fSReza Sabdar n = 1; 3922654012fSReza Sabdar start = index-1; 3932654012fSReza Sabdar end = start+1; 3942654012fSReza Sabdar lpp += start; /* Next selection entry will be in lpp[start] */ 3952654012fSReza Sabdar } else { 3962654012fSReza Sabdar start = 0; 3972654012fSReza Sabdar end = n; 3982654012fSReza Sabdar } 3992654012fSReza Sabdar 4002654012fSReza Sabdar for (i = start; i < end; i++) { 4012654012fSReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i); 4022654012fSReza Sabdar if (!ep) 4032654012fSReza Sabdar continue; 4042654012fSReza Sabdar 4052654012fSReza Sabdar /* 4062654012fSReza Sabdar * Check for clients that send original path as "."(like 4072654012fSReza Sabdar * CA products). In this situation opath is something like 4082654012fSReza Sabdar * "/v1/." and we should change it to "/v1/" 4092654012fSReza Sabdar */ 4102654012fSReza Sabdar len = strlen(ep->nm3_opath); 4112654012fSReza Sabdar if (len > 1 && ep->nm3_opath[len-2] == '/' && 4122654012fSReza Sabdar ep->nm3_opath[len-1] == '.') { 4132654012fSReza Sabdar ep->nm3_opath[len-1] = '\0'; 4142654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 4152654012fSReza Sabdar "nm3_opath changed from %s. to %s", 4162654012fSReza Sabdar ep->nm3_opath, ep->nm3_opath); 4172654012fSReza Sabdar } 4182654012fSReza Sabdar *lpp++ = ep->nm3_opath; 4192654012fSReza Sabdar } 4202654012fSReza Sabdar 4212654012fSReza Sabdar /* list termination indicator is a null pointer */ 4222654012fSReza Sabdar *lpp = NULL; 4232654012fSReza Sabdar 4242654012fSReza Sabdar return (save); 4252654012fSReza Sabdar } 4262654012fSReza Sabdar 4272654012fSReza Sabdar 4282654012fSReza Sabdar /* 4292654012fSReza Sabdar * mkrsp 4302654012fSReza Sabdar * 4312654012fSReza Sabdar * Make Restore Path. 4322654012fSReza Sabdar * It gets a path, a selection (with which the path has matched) a new 4332654012fSReza Sabdar * name and makes a new name for the path. 4342654012fSReza Sabdar * All the components of the path and the selection are skipped as long 4352654012fSReza Sabdar * as they are the same. If either of the path or selection are not on 4362654012fSReza Sabdar * a component boundary, the match was reported falsefully and no new name 4372654012fSReza Sabdar * is generated(Except the situation in which both path and selection 4382654012fSReza Sabdar * end with trailing '/' and selection is the prefix of the path). 4392654012fSReza Sabdar * Otherwise, the remaining of the path is appended to the 4402654012fSReza Sabdar * new name. The result is saved in the buffer passed. 4412654012fSReza Sabdar * 4422654012fSReza Sabdar * Parameters: 4432654012fSReza Sabdar * bp (output) - pointer to the result buffer 4442654012fSReza Sabdar * pp (input) - pointer to the path 4452654012fSReza Sabdar * sp (input) - pointer to the selection 4462654012fSReza Sabdar * np (input) - pointer to the new name 4472654012fSReza Sabdar * 4482654012fSReza Sabdar * Returns: 4492654012fSReza Sabdar * pointer to the bp: on success 4502654012fSReza Sabdar * NULL: otherwise 4512654012fSReza Sabdar */ 4522654012fSReza Sabdar char * 4532654012fSReza Sabdar mkrsp(char *bp, char *pp, char *sp, char *np) 4542654012fSReza Sabdar { 4552654012fSReza Sabdar if (!bp || !pp) 4562654012fSReza Sabdar return (NULL); 4572654012fSReza Sabdar 4582654012fSReza Sabdar 4592654012fSReza Sabdar pp += strspn(pp, "/"); 4602654012fSReza Sabdar if (sp) { 4612654012fSReza Sabdar sp += strspn(sp, "/"); 4622654012fSReza Sabdar 4632654012fSReza Sabdar /* skip as much as match */ 4642654012fSReza Sabdar while (*sp && *pp && *sp == *pp) { 4652654012fSReza Sabdar sp++; 4662654012fSReza Sabdar pp++; 4672654012fSReza Sabdar } 4682654012fSReza Sabdar 4692654012fSReza Sabdar if (!COMPBNDRY(pp) || !COMPBNDRY(sp)) 4702654012fSReza Sabdar /* An exception to the boundary rule */ 4712654012fSReza Sabdar /* (!(!*sp && (*(pp - 1)) == '/')) */ 4722654012fSReza Sabdar if (*sp || (*(pp - 1)) != '/') 4732654012fSReza Sabdar return (NULL); 4742654012fSReza Sabdar 4752654012fSReza Sabdar /* if pp shorter than sp, it should not be restored */ 4762654012fSReza Sabdar if (!*pp && *sp) { 4772654012fSReza Sabdar sp += strspn(sp, "/"); 4782654012fSReza Sabdar if (strlen(sp) > 0) 4792654012fSReza Sabdar return (NULL); 4802654012fSReza Sabdar } 4812654012fSReza Sabdar } 4822654012fSReza Sabdar 4832654012fSReza Sabdar if (np) 4842654012fSReza Sabdar np += strspn(np, "/"); 4852654012fSReza Sabdar else 4862654012fSReza Sabdar np = ""; 4872654012fSReza Sabdar 4882654012fSReza Sabdar if (!tlm_cat_path(bp, np, pp)) { 4892654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Restore path too long %s/%s.", np, pp); 4902654012fSReza Sabdar return (NULL); 4912654012fSReza Sabdar } 4922654012fSReza Sabdar 4932654012fSReza Sabdar return (bp); 4942654012fSReza Sabdar } 4952654012fSReza Sabdar 4962654012fSReza Sabdar 4972654012fSReza Sabdar /* 4982654012fSReza Sabdar * mknewname 4992654012fSReza Sabdar * 5002654012fSReza Sabdar * This is used as callback for creating the restore path. This function 5012654012fSReza Sabdar * can handle both single destination and multiple restore paths. 5022654012fSReza Sabdar * 5032654012fSReza Sabdar * Make up the restore destination path for a particular file/directory, path, 5042654012fSReza Sabdar * based on nm3_opath and nm3_dpath. path should have matched nm3_opath 5052654012fSReza Sabdar * in some way. 5062654012fSReza Sabdar */ 5072654012fSReza Sabdar char * 5082654012fSReza Sabdar mknewname(struct rs_name_maker *rnp, char *buf, int idx, char *path) 5092654012fSReza Sabdar { 5102654012fSReza Sabdar char *rv; 5112654012fSReza Sabdar ndmp_lbr_params_t *nlp; 5122654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 5132654012fSReza Sabdar 5142654012fSReza Sabdar rv = NULL; 5152654012fSReza Sabdar if (!buf) { 5162654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "buf is NULL"); 5172654012fSReza Sabdar } else if (!path) { 5182654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "path is NULL"); 5192654012fSReza Sabdar } else if ((nlp = rnp->rn_nlp) == 0) { 5202654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "rnp->rn_nlp is NULL"); 5212654012fSReza Sabdar } else if (!nlp->nlp_params) { 5222654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp->nlp_params is NULL"); 5232654012fSReza Sabdar } else 5242654012fSReza Sabdar if (!ndmp_full_restore_path) { 5252654012fSReza Sabdar if (idx < 0 || idx >= (int)nlp->nlp_nfiles) { 5262654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5272654012fSReza Sabdar "Invalid idx %d range (0, %d)", 5282654012fSReza Sabdar idx, nlp->nlp_nfiles); 5292654012fSReza Sabdar } else if (!(ep = (mem_ndmp_name_v3_t *)MOD_GETNAME( 5302654012fSReza Sabdar nlp->nlp_params, idx))) { 5312654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5322654012fSReza Sabdar "nlist entry %d is NULL", idx); 5332654012fSReza Sabdar } else { 5342654012fSReza Sabdar rv = mkrsp(buf, path, ep->nm3_opath, 5352654012fSReza Sabdar ep->nm3_dpath); 5362654012fSReza Sabdar 5372654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5382654012fSReza Sabdar "idx %d org \"%s\" dst \"%s\"", 5392654012fSReza Sabdar idx, ep->nm3_opath, ep->nm3_dpath); 5402654012fSReza Sabdar if (rv) { 5412654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5422654012fSReza Sabdar "path \"%s\": \"%s\"", path, rv); 5432654012fSReza Sabdar } else { 5442654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5452654012fSReza Sabdar "path \"%s\": NULL", path); 5462654012fSReza Sabdar } 5472654012fSReza Sabdar } 5482654012fSReza Sabdar } else { 5492654012fSReza Sabdar if (!tlm_cat_path(buf, nlp->nlp_restore_path, path)) { 5502654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Path too long %s/%s.", 5512654012fSReza Sabdar nlp->nlp_restore_path, path); 5522654012fSReza Sabdar rv = NULL; 5532654012fSReza Sabdar } else { 5542654012fSReza Sabdar rv = buf; 5552654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 5562654012fSReza Sabdar "path \"%s\": \"%s\"", path, rv); 5572654012fSReza Sabdar } 5582654012fSReza Sabdar } 5592654012fSReza Sabdar 5602654012fSReza Sabdar return (rv); 5612654012fSReza Sabdar } 5622654012fSReza Sabdar 5632654012fSReza Sabdar 5642654012fSReza Sabdar /* 5652654012fSReza Sabdar * chopslash 5662654012fSReza Sabdar * 5672654012fSReza Sabdar * Remove the slash from the end of the given path 5682654012fSReza Sabdar */ 5692654012fSReza Sabdar static void 5702654012fSReza Sabdar chopslash(char *cp) 5712654012fSReza Sabdar { 5722654012fSReza Sabdar int ln; 5732654012fSReza Sabdar 5742654012fSReza Sabdar if (!cp || !*cp) 5752654012fSReza Sabdar return; 5762654012fSReza Sabdar 5772654012fSReza Sabdar ln = strlen(cp); 5782654012fSReza Sabdar cp += ln - 1; /* end of the string */ 5792654012fSReza Sabdar while (ln > 0 && *cp == '/') { 5802654012fSReza Sabdar *cp-- = '\0'; 5812654012fSReza Sabdar ln--; 5822654012fSReza Sabdar } 5832654012fSReza Sabdar } 5842654012fSReza Sabdar 5852654012fSReza Sabdar 5862654012fSReza Sabdar /* 5872654012fSReza Sabdar * joinpath 5882654012fSReza Sabdar * 5892654012fSReza Sabdar * Join two given paths 5902654012fSReza Sabdar */ 5912654012fSReza Sabdar static char * 5922654012fSReza Sabdar joinpath(char *bp, char *pp, char *np) 5932654012fSReza Sabdar { 5942654012fSReza Sabdar if (pp && *pp) { 5952654012fSReza Sabdar if (np && *np) 5962654012fSReza Sabdar (void) tlm_cat_path(bp, pp, np); 5972654012fSReza Sabdar else 5982654012fSReza Sabdar (void) strlcpy(bp, pp, TLM_MAX_PATH_NAME); 5992654012fSReza Sabdar } else { 6002654012fSReza Sabdar if (np && *np) 6012654012fSReza Sabdar (void) strlcpy(bp, np, TLM_MAX_PATH_NAME); 6022654012fSReza Sabdar else 6032654012fSReza Sabdar bp = NULL; 6042654012fSReza Sabdar } 6052654012fSReza Sabdar 6062654012fSReza Sabdar return (bp); 6072654012fSReza Sabdar } 6082654012fSReza Sabdar 6092654012fSReza Sabdar 6102654012fSReza Sabdar /* 6112654012fSReza Sabdar * voliswr 6122654012fSReza Sabdar * 6132654012fSReza Sabdar * Is the volume writable? 6142654012fSReza Sabdar */ 6152654012fSReza Sabdar static int 6162654012fSReza Sabdar voliswr(char *path) 6172654012fSReza Sabdar { 6182654012fSReza Sabdar int rv; 6192654012fSReza Sabdar 6202654012fSReza Sabdar if (!path) 6212654012fSReza Sabdar return (0); 6222654012fSReza Sabdar 6232654012fSReza Sabdar rv = !fs_is_rdonly(path) && !fs_is_chkpntvol(path); 6242654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "%d path \"%s\"", rv, path); 6252654012fSReza Sabdar return (rv); 6262654012fSReza Sabdar 6272654012fSReza Sabdar } 6282654012fSReza Sabdar 6292654012fSReza Sabdar 6302654012fSReza Sabdar /* 6312654012fSReza Sabdar * is_valid_backup_dir_v3 6322654012fSReza Sabdar * 6332654012fSReza Sabdar * Checks the validity of the backup path. Backup path should 6342654012fSReza Sabdar * have the following characteristics to be valid: 6352654012fSReza Sabdar * 1) It should be an absolute path. 6362654012fSReza Sabdar * 2) It should be a directory. 6372654012fSReza Sabdar * 3) It should not be checkpoint root directory 6382654012fSReza Sabdar * 4) If the file system is read-only, the backup path 6392654012fSReza Sabdar * should be a checkpointed path. Checkpoint cannot 6402654012fSReza Sabdar * be created on a read-only file system. 6412654012fSReza Sabdar * 6422654012fSReza Sabdar * Parameters: 6432654012fSReza Sabdar * params (input) - pointer to the parameters structure. 6442654012fSReza Sabdar * bkpath (input) - the backup path 6452654012fSReza Sabdar * 6462654012fSReza Sabdar * Returns: 6472654012fSReza Sabdar * TRUE: if everything's OK 6482654012fSReza Sabdar * FALSE: otherwise. 6492654012fSReza Sabdar */ 6502654012fSReza Sabdar static boolean_t 6512654012fSReza Sabdar is_valid_backup_dir_v3(ndmpd_module_params_t *params, char *bkpath) 6522654012fSReza Sabdar { 6532654012fSReza Sabdar char *msg; 6542654012fSReza Sabdar struct stat64 st; 6552654012fSReza Sabdar 6562654012fSReza Sabdar if (*bkpath != '/') { 6572654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 6582654012fSReza Sabdar "Relative backup path not allowed \"%s\".\n", bkpath); 6592654012fSReza Sabdar return (FALSE); 6602654012fSReza Sabdar } 6612654012fSReza Sabdar if (stat64(bkpath, &st) < 0) { 6622654012fSReza Sabdar msg = strerror(errno); 6632654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, "\"%s\" %s.\n", 6642654012fSReza Sabdar bkpath, msg); 6652654012fSReza Sabdar return (FALSE); 6662654012fSReza Sabdar } 6672654012fSReza Sabdar if (!S_ISDIR(st.st_mode)) { 6682654012fSReza Sabdar /* only directories can be specified as the backup path */ 6692654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 6702654012fSReza Sabdar "\"%s\" is not a directory.\n", bkpath); 6712654012fSReza Sabdar return (FALSE); 6722654012fSReza Sabdar } 6732654012fSReza Sabdar if (fs_is_rdonly(bkpath) && !fs_is_chkpntvol(bkpath) && 6742654012fSReza Sabdar fs_is_chkpnt_enabled(bkpath)) { 6752654012fSReza Sabdar /* it is not a chkpnted path */ 6762654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 6772654012fSReza Sabdar "\"%s\" is not a checkpointed path.\n", bkpath); 6782654012fSReza Sabdar return (FALSE); 6792654012fSReza Sabdar } 6802654012fSReza Sabdar 6812654012fSReza Sabdar return (TRUE); 6822654012fSReza Sabdar } 6832654012fSReza Sabdar 6842654012fSReza Sabdar 6852654012fSReza Sabdar /* 6862654012fSReza Sabdar * log_date_token_v3 6872654012fSReza Sabdar * 6882654012fSReza Sabdar * Log the token sequence number and also the date of the 6892654012fSReza Sabdar * last backup for token-based backup in the system log 6902654012fSReza Sabdar * and also send them as normal log to the client. 6912654012fSReza Sabdar * 6922654012fSReza Sabdar * Parameters: 6932654012fSReza Sabdar * params (input) - pointer to the parameters structure 6942654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 6952654012fSReza Sabdar * 6962654012fSReza Sabdar * Returns: 6972654012fSReza Sabdar * void 6982654012fSReza Sabdar */ 6992654012fSReza Sabdar static void 7002654012fSReza Sabdar log_date_token_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 7012654012fSReza Sabdar { 7022654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Token sequence counter: %d.\n", 7032654012fSReza Sabdar nlp->nlp_tokseq); 7042654012fSReza Sabdar 7052654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Date of the last backup: %s.\n", 7062654012fSReza Sabdar cctime(&nlp->nlp_tokdate)); 7072654012fSReza Sabdar 7082654012fSReza Sabdar if (nlp->nlp_dmpnm) { 7092654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7102654012fSReza Sabdar "Backup date log file name: \"%s\".\n", nlp->nlp_dmpnm); 7112654012fSReza Sabdar } 7122654012fSReza Sabdar } 7132654012fSReza Sabdar 7142654012fSReza Sabdar 7152654012fSReza Sabdar /* 7162654012fSReza Sabdar * log_lbr_bk_v3 7172654012fSReza Sabdar * 7182654012fSReza Sabdar * Log the backup level and data of the backup for LBR-type 7192654012fSReza Sabdar * backup in the system log and also send them as normal log 7202654012fSReza Sabdar * to the client. 7212654012fSReza Sabdar * 7222654012fSReza Sabdar * Parameters: 7232654012fSReza Sabdar * params (input) - pointer to the parameters structure 7242654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 7252654012fSReza Sabdar * 7262654012fSReza Sabdar * Returns: 7272654012fSReza Sabdar * void 7282654012fSReza Sabdar */ 7292654012fSReza Sabdar static void 7302654012fSReza Sabdar log_lbr_bk_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 7312654012fSReza Sabdar { 7322654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7332654012fSReza Sabdar "Date of this level '%c': %s.\n", nlp->nlp_clevel, 7342654012fSReza Sabdar cctime(&nlp->nlp_cdate)); 7352654012fSReza Sabdar 7362654012fSReza Sabdar if (nlp->nlp_dmpnm) { 7372654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7382654012fSReza Sabdar "Backup date log file name: \"%s\".\n", nlp->nlp_dmpnm); 7392654012fSReza Sabdar } 7402654012fSReza Sabdar } 7412654012fSReza Sabdar 7422654012fSReza Sabdar 7432654012fSReza Sabdar /* 7442654012fSReza Sabdar * log_level_v3 7452654012fSReza Sabdar * 7462654012fSReza Sabdar * Log the backup level and date of the last and the current 7472654012fSReza Sabdar * backup for level-type backup in the system log and also 7482654012fSReza Sabdar * send them as normal log to the client. 7492654012fSReza Sabdar * 7502654012fSReza Sabdar * Parameters: 7512654012fSReza Sabdar * params (input) - pointer to the parameters structure 7522654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 7532654012fSReza Sabdar * 7542654012fSReza Sabdar * Returns: 7552654012fSReza Sabdar * void 7562654012fSReza Sabdar */ 7572654012fSReza Sabdar static void 7582654012fSReza Sabdar log_level_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 7592654012fSReza Sabdar { 7602654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7612654012fSReza Sabdar "Date of the last level '%u': %s.\n", nlp->nlp_llevel, 7622654012fSReza Sabdar cctime(&nlp->nlp_ldate)); 7632654012fSReza Sabdar 7642654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7652654012fSReza Sabdar "Date of this level '%u': %s.\n", nlp->nlp_clevel, 7662654012fSReza Sabdar cctime(&nlp->nlp_cdate)); 7672654012fSReza Sabdar 7682654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Update: %s.\n", 7692654012fSReza Sabdar NDMP_TORF(NLP_ISSET(nlp, NLPF_UPDATE))); 7702654012fSReza Sabdar } 7712654012fSReza Sabdar 7722654012fSReza Sabdar 7732654012fSReza Sabdar /* 7742654012fSReza Sabdar * log_bk_params_v3 7752654012fSReza Sabdar * 7762654012fSReza Sabdar * Dispatcher function which calls the appropriate function 7772654012fSReza Sabdar * for logging the backup date and level in the system log 7782654012fSReza Sabdar * and also send them as normal log message to the client. 7792654012fSReza Sabdar * 7802654012fSReza Sabdar * Parameters: 7812654012fSReza Sabdar * session (input) - pointer to the session 7822654012fSReza Sabdar * params (input) - pointer to the parameters structure 7832654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 7842654012fSReza Sabdar * 7852654012fSReza Sabdar * Returns: 7862654012fSReza Sabdar * void 7872654012fSReza Sabdar */ 7882654012fSReza Sabdar static void 7892654012fSReza Sabdar log_bk_params_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 7902654012fSReza Sabdar ndmp_lbr_params_t *nlp) 7912654012fSReza Sabdar { 7922654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Backing up \"%s\".\n", 7932654012fSReza Sabdar nlp->nlp_backup_path); 7942654012fSReza Sabdar 7952654012fSReza Sabdar if (session->ns_mover.md_data_addr.addr_type == NDMP_ADDR_LOCAL) 7962654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 7972654012fSReza Sabdar "Tape record size: %d.\n", 7982654012fSReza Sabdar session->ns_mover.md_record_size); 7992654012fSReza Sabdar 8002654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "File history: %c.\n", 8012654012fSReza Sabdar NDMP_YORN(NLP_ISSET(nlp, NLPF_FH))); 8022654012fSReza Sabdar 8032654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_TOKENBK)) 8042654012fSReza Sabdar log_date_token_v3(params, nlp); 8052654012fSReza Sabdar else if (NLP_ISSET(nlp, NLPF_LBRBK)) 8062654012fSReza Sabdar log_lbr_bk_v3(params, nlp); 8072654012fSReza Sabdar else if (NLP_ISSET(nlp, NLPF_LEVELBK)) 8082654012fSReza Sabdar log_level_v3(params, nlp); 8092654012fSReza Sabdar else { 8102654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 8112654012fSReza Sabdar "Internal error: backup level not defined for \"%s\".\n", 8122654012fSReza Sabdar nlp->nlp_backup_path); 8132654012fSReza Sabdar } 8142654012fSReza Sabdar } 8152654012fSReza Sabdar 8162654012fSReza Sabdar 8172654012fSReza Sabdar /* 8182654012fSReza Sabdar * get_update_env_v3 8192654012fSReza Sabdar * 8202654012fSReza Sabdar * Is the UPDATE environment variable specified? If it is 8212654012fSReza Sabdar * the corresponding flag is set in the flags field of the 8222654012fSReza Sabdar * nlp structure, otherwise the flag is cleared. 8232654012fSReza Sabdar * 8242654012fSReza Sabdar * Parameters: 8252654012fSReza Sabdar * params (input) - pointer to the parameters structure 8262654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 8272654012fSReza Sabdar * 8282654012fSReza Sabdar * Returns: 8292654012fSReza Sabdar * void 8302654012fSReza Sabdar */ 8312654012fSReza Sabdar static void 8322654012fSReza Sabdar get_update_env_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 8332654012fSReza Sabdar { 8342654012fSReza Sabdar char *envp; 8352654012fSReza Sabdar 8362654012fSReza Sabdar envp = MOD_GETENV(params, "UPDATE"); 8372654012fSReza Sabdar if (!envp) { 8382654012fSReza Sabdar NLP_SET(nlp, NLPF_UPDATE); 8392654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 8402654012fSReza Sabdar "env(UPDATE) not defined, default to TRUE"); 8412654012fSReza Sabdar } else { 8422654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(UPDATE): \"%s\"", envp); 8432654012fSReza Sabdar if (IS_YORT(*envp)) 8442654012fSReza Sabdar NLP_SET(nlp, NLPF_UPDATE); 8452654012fSReza Sabdar else 8462654012fSReza Sabdar NLP_UNSET(nlp, NLPF_UPDATE); 8472654012fSReza Sabdar } 8482654012fSReza Sabdar } 8492654012fSReza Sabdar 8502654012fSReza Sabdar 8512654012fSReza Sabdar /* 8522654012fSReza Sabdar * get_hist_env_v3 8532654012fSReza Sabdar * 8542654012fSReza Sabdar * Is backup history requested? If it is, the corresponding 8552654012fSReza Sabdar * flag is set in the flags field of the nlp structure, otherwise 8562654012fSReza Sabdar * the flag is cleared. 8572654012fSReza Sabdar * 8582654012fSReza Sabdar * Parameters: 8592654012fSReza Sabdar * params (input) - pointer to the parameters structure 8602654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 8612654012fSReza Sabdar * 8622654012fSReza Sabdar * Returns: 8632654012fSReza Sabdar * void 8642654012fSReza Sabdar */ 8652654012fSReza Sabdar static void 8662654012fSReza Sabdar get_hist_env_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 8672654012fSReza Sabdar { 8682654012fSReza Sabdar char *envp; 8692654012fSReza Sabdar 8702654012fSReza Sabdar envp = MOD_GETENV(params, "HIST"); 8712654012fSReza Sabdar if (!envp) { 8722654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(HIST) not defined"); 8732654012fSReza Sabdar NLP_UNSET(nlp, NLPF_FH); 8742654012fSReza Sabdar } else { 8752654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(HIST): \"%s\"", envp); 876416eec61SReza Sabdar if (IS_YORT(*envp) || IS_F(*envp)) 8772654012fSReza Sabdar NLP_SET(nlp, NLPF_FH); 8782654012fSReza Sabdar else 8792654012fSReza Sabdar NLP_UNSET(nlp, NLPF_FH); 880416eec61SReza Sabdar 881416eec61SReza Sabdar /* Force file format if specified */ 882416eec61SReza Sabdar if (IS_F(*envp)) { 883416eec61SReza Sabdar params->mp_file_history_path_func = 884416eec61SReza Sabdar ndmpd_api_file_history_file_v3; 885416eec61SReza Sabdar params->mp_file_history_dir_func = 0; 886416eec61SReza Sabdar params->mp_file_history_node_func = 0; 887416eec61SReza Sabdar } 8882654012fSReza Sabdar } 8892654012fSReza Sabdar } 8902654012fSReza Sabdar 8912654012fSReza Sabdar 8922654012fSReza Sabdar /* 8932654012fSReza Sabdar * get_exc_env_v3 8942654012fSReza Sabdar * 8952654012fSReza Sabdar * Gets the EXCLUDE environment variable and breaks it 8962654012fSReza Sabdar * into strings. The separator of the EXCLUDE environment 8972654012fSReza Sabdar * variable is the ',' character. 8982654012fSReza Sabdar * 8992654012fSReza Sabdar * Parameters: 9002654012fSReza Sabdar * params (input) - pointer to the parameters structure 9012654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 9022654012fSReza Sabdar * 9032654012fSReza Sabdar * Returns: 9042654012fSReza Sabdar * void 9052654012fSReza Sabdar */ 9062654012fSReza Sabdar static void 9072654012fSReza Sabdar get_exc_env_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 9082654012fSReza Sabdar { 9092654012fSReza Sabdar char *envp; 9102654012fSReza Sabdar 9112654012fSReza Sabdar envp = MOD_GETENV(params, "EXCLUDE"); 9122654012fSReza Sabdar if (!envp) { 9132654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(EXCLUDE) not defined"); 9142654012fSReza Sabdar nlp->nlp_exl = NULL; 9152654012fSReza Sabdar } else { 9162654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(EXCLUDE): \"%s\"", envp); 9172654012fSReza Sabdar nlp->nlp_exl = split_env(envp, ','); 9182654012fSReza Sabdar prl(nlp->nlp_exl); 9192654012fSReza Sabdar } 9202654012fSReza Sabdar } 9212654012fSReza Sabdar 9222654012fSReza Sabdar 9232654012fSReza Sabdar /* 9242654012fSReza Sabdar * get_inc_env_v3 9252654012fSReza Sabdar * 9262654012fSReza Sabdar * Gets the FILES environment variable that shows which files 9272654012fSReza Sabdar * should be backed up, and breaks it into strings. The 9282654012fSReza Sabdar * separator of the FILES environment variable is the space 9292654012fSReza Sabdar * character. 9302654012fSReza Sabdar * 9312654012fSReza Sabdar * Parameters: 9322654012fSReza Sabdar * params (input) - pointer to the parameters structure 9332654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 9342654012fSReza Sabdar * 9352654012fSReza Sabdar * Returns: 9362654012fSReza Sabdar * void 9372654012fSReza Sabdar */ 9382654012fSReza Sabdar static void 9392654012fSReza Sabdar get_inc_env_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 9402654012fSReza Sabdar { 9412654012fSReza Sabdar char *envp; 9422654012fSReza Sabdar 9432654012fSReza Sabdar envp = MOD_GETENV(params, "FILES"); 9442654012fSReza Sabdar if (!envp) { 9452654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(FILES) not defined"); 9462654012fSReza Sabdar nlp->nlp_inc = NULL; 9472654012fSReza Sabdar } else { 9482654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(FILES): \"%s\"", envp); 9492654012fSReza Sabdar nlp->nlp_inc = split_env(envp, ' '); 9502654012fSReza Sabdar prl(nlp->nlp_inc); 9512654012fSReza Sabdar } 9522654012fSReza Sabdar } 9532654012fSReza Sabdar 9542654012fSReza Sabdar 9552654012fSReza Sabdar /* 9562654012fSReza Sabdar * get_direct_env_v3 9572654012fSReza Sabdar * 9582654012fSReza Sabdar * Gets the DIRECT environment variable that shows if the fh_info should 9592654012fSReza Sabdar * be sent to the client or not. 9602654012fSReza Sabdar * 9612654012fSReza Sabdar * Parameters: 9622654012fSReza Sabdar * params (input) - pointer to the parameters structure 9632654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 9642654012fSReza Sabdar * 9652654012fSReza Sabdar * Returns: 9662654012fSReza Sabdar * void 9672654012fSReza Sabdar */ 9682654012fSReza Sabdar static void 9692654012fSReza Sabdar get_direct_env_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 9702654012fSReza Sabdar { 9712654012fSReza Sabdar char *envp; 9722654012fSReza Sabdar 9732654012fSReza Sabdar /* 9742654012fSReza Sabdar * We should send the fh_info to the DMA, unless it is specified 9752654012fSReza Sabdar * in the request that we should not send fh_info. 9762654012fSReza Sabdar * At the moment we do not support DAR on directories, so if the user 9772654012fSReza Sabdar * needs to restore a directory they should disable the DAR. 9782654012fSReza Sabdar */ 9792654012fSReza Sabdar if (params->mp_operation == NDMP_DATA_OP_RECOVER && !ndmp_dar_support) { 9802654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Direct Access Restore Disabled"); 9812654012fSReza Sabdar NLP_UNSET(nlp, NLPF_DIRECT); 9822654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 9832654012fSReza Sabdar "DAR is disabled. Running Restore without DAR"); 9842654012fSReza Sabdar return; 9852654012fSReza Sabdar } 9862654012fSReza Sabdar 9872654012fSReza Sabdar /* 9882654012fSReza Sabdar * Regardless of whether DIRECT is defined at backup time we send 9892654012fSReza Sabdar * back the fh_info, for some clients do not use get_backup_attrs. 9902654012fSReza Sabdar * If operation is restore we have to unset the DIRECT, for 9912654012fSReza Sabdar * some clients do not set the MOVER window. 9922654012fSReza Sabdar */ 9932654012fSReza Sabdar if (params->mp_operation == NDMP_DATA_OP_BACKUP) { 9942654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "backup default env(DIRECT): YES"); 9952654012fSReza Sabdar NLP_SET(nlp, NLPF_DIRECT); 9962654012fSReza Sabdar } else { 9972654012fSReza Sabdar 9982654012fSReza Sabdar envp = MOD_GETENV(params, "DIRECT"); 9992654012fSReza Sabdar if (!envp) { 10002654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(DIRECT) not defined"); 10012654012fSReza Sabdar NLP_UNSET(nlp, NLPF_DIRECT); 10022654012fSReza Sabdar } else { 10032654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(DIRECT): \"%s\"", envp); 10042654012fSReza Sabdar if (IS_YORT(*envp)) { 10052654012fSReza Sabdar NLP_SET(nlp, NLPF_DIRECT); 10062654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 10072654012fSReza Sabdar "Direct Access Restore Enabled"); 10082654012fSReza Sabdar } else { 10092654012fSReza Sabdar NLP_UNSET(nlp, NLPF_DIRECT); 10102654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 10112654012fSReza Sabdar "Direct Access Restore Disabled"); 10122654012fSReza Sabdar } 10132654012fSReza Sabdar } 10142654012fSReza Sabdar } 10152654012fSReza Sabdar 10162654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_DIRECT)) { 10172654012fSReza Sabdar if (params->mp_operation == NDMP_DATA_OP_BACKUP) 10182654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 10192654012fSReza Sabdar "Direct Access Restore information is supported"); 10202654012fSReza Sabdar else 10212654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 10222654012fSReza Sabdar "Running Restore with Direct Access Restore"); 10232654012fSReza Sabdar } else { 10242654012fSReza Sabdar if (params->mp_operation == NDMP_DATA_OP_BACKUP) 10252654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 10262654012fSReza Sabdar "Direct Access Restore is not supported"); 10272654012fSReza Sabdar else 10282654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 10292654012fSReza Sabdar "Running Restore without Direct Access Restore"); 10302654012fSReza Sabdar } 10312654012fSReza Sabdar } 10322654012fSReza Sabdar 10332654012fSReza Sabdar 10342654012fSReza Sabdar /* 10352654012fSReza Sabdar * get_date_token_v3 10362654012fSReza Sabdar * 10372654012fSReza Sabdar * Parse the token passed as the argument. Evaluate it and 10382654012fSReza Sabdar * issue any warning or error if needed. Save the date and 10392654012fSReza Sabdar * token sequence in the nlp structure fields. The sequence 10402654012fSReza Sabdar * number in the token should be less than hard-limit. If 10412654012fSReza Sabdar * it's between soft and hard limit, a warning is issued. 10422654012fSReza Sabdar * There is a configurable limit which should be less than 10432654012fSReza Sabdar * the soft-limit saved in ndmp_max_tok_seq variable. 10442654012fSReza Sabdar * 10452654012fSReza Sabdar * The NLPF_TOKENBK flag is set in the nlp flags field to 10462654012fSReza Sabdar * show that the backup type is token-based. 10472654012fSReza Sabdar * 10482654012fSReza Sabdar * Parameters: 10492654012fSReza Sabdar * params (input) - pointer to the parameters structure 10502654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 10512654012fSReza Sabdar * basedate (input) - the value of the BASE_DATE environment 10522654012fSReza Sabdar * variable. 10532654012fSReza Sabdar * 10542654012fSReza Sabdar * Returns: 10552654012fSReza Sabdar * NDMP_NO_ERR: on success 10562654012fSReza Sabdar * != NDMP_NO_ERR: Otherwise 10572654012fSReza Sabdar * 10582654012fSReza Sabdar */ 10592654012fSReza Sabdar static ndmp_error 10602654012fSReza Sabdar get_date_token_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp, 10612654012fSReza Sabdar char *basedate) 10622654012fSReza Sabdar { 10632654012fSReza Sabdar char *endp; 10642654012fSReza Sabdar uint_t seq; 10652654012fSReza Sabdar ndmp_error rv; 10662654012fSReza Sabdar time_t tstamp; 10672654012fSReza Sabdar u_longlong_t tok; 10682654012fSReza Sabdar 10692654012fSReza Sabdar if (!params || !nlp || !basedate || !*basedate) 10702654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 10712654012fSReza Sabdar 10722654012fSReza Sabdar if (MOD_GETENV(params, "LEVEL")) { 10732654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_WARNING, 10742654012fSReza Sabdar "Both BASE_DATE and LEVEL environment variables " 10752654012fSReza Sabdar "defined.\n"); 10762654012fSReza Sabdar MOD_LOGCONTV3(params, NDMP_LOG_WARNING, 10772654012fSReza Sabdar "BASE_DATE is being used for this backup.\n"); 10782654012fSReza Sabdar } 10792654012fSReza Sabdar 10802654012fSReza Sabdar tok = strtoll(basedate, &endp, 10); 10812654012fSReza Sabdar if (endp == basedate) { 10822654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 10832654012fSReza Sabdar "Invalid BASE_DATE environment variable: \"%s\".\n", 10842654012fSReza Sabdar basedate); 10852654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 10862654012fSReza Sabdar } 10872654012fSReza Sabdar 10882654012fSReza Sabdar tstamp = tok & 0xffffffff; 10892654012fSReza Sabdar seq = (tok >> 32) & 0xffffffff; 10902654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "basedate \"%s\" %lld seq %u tstamp %u", 10912654012fSReza Sabdar basedate, tok, seq, tstamp); 10922654012fSReza Sabdar 10932654012fSReza Sabdar if ((int)seq > ndmp_get_max_tok_seq()) { 10942654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 10952654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 10962654012fSReza Sabdar "The sequence counter of the token exceeds the " 10972654012fSReza Sabdar "maximum permitted value.\n"); 10982654012fSReza Sabdar MOD_LOGCONTV3(params, NDMP_LOG_ERROR, 10992654012fSReza Sabdar "Token sequence: %u, maxiumum value: %u.\n", 11002654012fSReza Sabdar seq, ndmp_get_max_tok_seq()); 11012654012fSReza Sabdar } else if (seq >= NDMP_TOKSEQ_HLIMIT) { 11022654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 11032654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 11042654012fSReza Sabdar "The sequence counter the of token exceeds the " 11052654012fSReza Sabdar "hard-limit.\n"); 11062654012fSReza Sabdar MOD_LOGCONTV3(params, NDMP_LOG_ERROR, 11072654012fSReza Sabdar "Token sequence: %u, hard-limit: %u.\n", 11082654012fSReza Sabdar seq, NDMP_TOKSEQ_HLIMIT); 11092654012fSReza Sabdar } else { 11102654012fSReza Sabdar rv = NDMP_NO_ERR; 11112654012fSReza Sabdar /* 11122654012fSReza Sabdar * Issue a warning if the seq is equal to the maximum 11132654012fSReza Sabdar * permitted seq number or equal to the soft-limit. 11142654012fSReza Sabdar */ 11152654012fSReza Sabdar if (seq == NDMP_TOKSEQ_SLIMIT) { 11162654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_WARNING, 11172654012fSReza Sabdar "The sequence counter of the token has reached " 11182654012fSReza Sabdar "the soft-limit.\n"); 11192654012fSReza Sabdar MOD_LOGCONTV3(params, NDMP_LOG_WARNING, 11202654012fSReza Sabdar "Token sequence: %u, soft-limit: %u.\n", 11212654012fSReza Sabdar seq, NDMP_TOKSEQ_SLIMIT); 11222654012fSReza Sabdar } else if ((int)seq == ndmp_get_max_tok_seq()) { 11232654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_WARNING, 11242654012fSReza Sabdar "The sequence counter of the token has reached " 11252654012fSReza Sabdar "the maximum permitted value.\n"); 11262654012fSReza Sabdar MOD_LOGCONTV3(params, NDMP_LOG_WARNING, 11272654012fSReza Sabdar "Token sequence: %u, maxiumum value: %u.\n", 11282654012fSReza Sabdar seq, ndmp_get_max_tok_seq()); 11292654012fSReza Sabdar } 11302654012fSReza Sabdar 11312654012fSReza Sabdar /* 11322654012fSReza Sabdar * The current seq is equal to the seq field of the 11332654012fSReza Sabdar * token. It will be increased after successful backup 11342654012fSReza Sabdar * before setting the DUMP_DATE environment variable. 11352654012fSReza Sabdar */ 11362654012fSReza Sabdar nlp->nlp_dmpnm = MOD_GETENV(params, "DMP_NAME"); 11372654012fSReza Sabdar NLP_SET(nlp, NLPF_TOKENBK); 11382654012fSReza Sabdar NLP_UNSET(nlp, NLPF_LEVELBK); 11392654012fSReza Sabdar NLP_UNSET(nlp, NLPF_LBRBK); 11402654012fSReza Sabdar nlp->nlp_tokseq = seq; 11412654012fSReza Sabdar nlp->nlp_tokdate = tstamp; 11422654012fSReza Sabdar /* 11432654012fSReza Sabdar * The value of nlp_cdate will be set to the checkpoint 11442654012fSReza Sabdar * creation time after it is created. 11452654012fSReza Sabdar */ 11462654012fSReza Sabdar } 11472654012fSReza Sabdar 11482654012fSReza Sabdar return (rv); 11492654012fSReza Sabdar } 11502654012fSReza Sabdar 11512654012fSReza Sabdar 11522654012fSReza Sabdar /* 11532654012fSReza Sabdar * get_lbr_bk_v3 11542654012fSReza Sabdar * 11552654012fSReza Sabdar * Sets the level fields of the nlp structures for 11562654012fSReza Sabdar * LBR-type backup. The NLPF_LBRBK flag of the 11572654012fSReza Sabdar * nlp flags is also set to show the backup type. 11582654012fSReza Sabdar * 11592654012fSReza Sabdar * Parameters: 11602654012fSReza Sabdar * params (input) - pointer to the parameters structure 11612654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 11622654012fSReza Sabdar * type (input) - the backup level: 'F', 'A', 'I', 'D' or 11632654012fSReza Sabdar * their lower-case values. 11642654012fSReza Sabdar * 11652654012fSReza Sabdar * Returns: 11662654012fSReza Sabdar * NDMP_NO_ERR: on success 11672654012fSReza Sabdar * != NDMP_NO_ERR: Otherwise 11682654012fSReza Sabdar */ 11692654012fSReza Sabdar static ndmp_error 11702654012fSReza Sabdar get_lbr_bk_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp, char *type) 11712654012fSReza Sabdar { 11722654012fSReza Sabdar if (!params || !nlp || !type || !*type) 11732654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 11742654012fSReza Sabdar 11752654012fSReza Sabdar NLP_SET(nlp, NLPF_LBRBK); 11762654012fSReza Sabdar NLP_UNSET(nlp, NLPF_TOKENBK); 11772654012fSReza Sabdar NLP_UNSET(nlp, NLPF_LEVELBK); 11782654012fSReza Sabdar nlp->nlp_dmpnm = MOD_GETENV(params, "DMP_NAME"); 11792654012fSReza Sabdar nlp->nlp_llevel = toupper(*type); 11802654012fSReza Sabdar nlp->nlp_ldate = (time_t)0; 11812654012fSReza Sabdar nlp->nlp_clevel = nlp->nlp_llevel; 11822654012fSReza Sabdar (void) time(&nlp->nlp_cdate); 11832654012fSReza Sabdar 11842654012fSReza Sabdar return (NDMP_NO_ERR); 11852654012fSReza Sabdar } 11862654012fSReza Sabdar 11872654012fSReza Sabdar 11882654012fSReza Sabdar /* 11892654012fSReza Sabdar * get_backup_level_v3 11902654012fSReza Sabdar * 11912654012fSReza Sabdar * Gets the backup level from the environment variables. If 11922654012fSReza Sabdar * BASE_DATE is specified, it will be used, otherwise LEVEL 11932654012fSReza Sabdar * will be used. If neither is specified, LEVEL = '0' is 11942654012fSReza Sabdar * assumed. 11952654012fSReza Sabdar * 11962654012fSReza Sabdar * Parameters: 11972654012fSReza Sabdar * params (input) - pointer to the parameters structure 11982654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 11992654012fSReza Sabdar * 12002654012fSReza Sabdar * Returns: 12012654012fSReza Sabdar * NDMP_NO_ERR: on success 12022654012fSReza Sabdar * != NDMP_NO_ERR: Otherwise 12032654012fSReza Sabdar */ 12042654012fSReza Sabdar static ndmp_error 12052654012fSReza Sabdar get_backup_level_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 12062654012fSReza Sabdar { 12072654012fSReza Sabdar char *envp; 12082654012fSReza Sabdar ndmp_error rv; 12092654012fSReza Sabdar 12102654012fSReza Sabdar /* 12112654012fSReza Sabdar * If the BASE_DATE env variable is specified use it, otherwise 12122654012fSReza Sabdar * look to see if LEVEL is specified. If LEVEL is not 12132654012fSReza Sabdar * specified either, backup level '0' must be made. Level backup 12142654012fSReza Sabdar * does not clear the archive bit. 12152654012fSReza Sabdar * 12162654012fSReza Sabdar * If LEVEL environment varaible is specified, values for 12172654012fSReza Sabdar * 'F', 'D', 'I' and 'A' (for 'Full', 'Differential', 12182654012fSReza Sabdar * 'Incremental', and 'Archive' is checked first. Then 12192654012fSReza Sabdar * level '0' to '9' will be checked. 12202654012fSReza Sabdar * 12212654012fSReza Sabdar * LEVEL environment variable can hold only one character. 12222654012fSReza Sabdar * If its length is longer than 1, an error is returned. 12232654012fSReza Sabdar */ 12242654012fSReza Sabdar envp = MOD_GETENV(params, "BASE_DATE"); 12252654012fSReza Sabdar if (envp) 12262654012fSReza Sabdar return (get_date_token_v3(params, nlp, envp)); 12272654012fSReza Sabdar 12282654012fSReza Sabdar 12292654012fSReza Sabdar envp = MOD_GETENV(params, "LEVEL"); 12302654012fSReza Sabdar if (!envp) { 12312654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "env(LEVEL) not defined, default to 0"); 12322654012fSReza Sabdar NLP_SET(nlp, NLPF_LEVELBK); 12332654012fSReza Sabdar NLP_UNSET(nlp, NLPF_LBRBK); 12342654012fSReza Sabdar NLP_UNSET(nlp, NLPF_TOKENBK); 12352654012fSReza Sabdar nlp->nlp_llevel = 0; 12362654012fSReza Sabdar nlp->nlp_ldate = 0; 12372654012fSReza Sabdar nlp->nlp_clevel = 0; 12382654012fSReza Sabdar /* 12392654012fSReza Sabdar * The value of nlp_cdate will be set to the checkpoint 12402654012fSReza Sabdar * creation time after it is created. 12412654012fSReza Sabdar */ 12422654012fSReza Sabdar return (NDMP_NO_ERR); 12432654012fSReza Sabdar } 12442654012fSReza Sabdar 12452654012fSReza Sabdar if (*(envp+1) != '\0') { 12462654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 12472654012fSReza Sabdar "Invalid backup level \"%s\".\n", envp); 12482654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 12492654012fSReza Sabdar } 12502654012fSReza Sabdar 12512654012fSReza Sabdar if (IS_LBR_BKTYPE(*envp)) 12522654012fSReza Sabdar return (get_lbr_bk_v3(params, nlp, envp)); 12532654012fSReza Sabdar 12542654012fSReza Sabdar if (!isdigit(*envp)) { 12552654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 12562654012fSReza Sabdar "Invalid backup level \"%s\".\n", envp); 12572654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 12582654012fSReza Sabdar } 12592654012fSReza Sabdar 12602654012fSReza Sabdar NLP_SET(nlp, NLPF_LEVELBK); 12612654012fSReza Sabdar NLP_UNSET(nlp, NLPF_LBRBK); 12622654012fSReza Sabdar NLP_UNSET(nlp, NLPF_TOKENBK); 12632654012fSReza Sabdar nlp->nlp_llevel = *envp - '0'; 12642654012fSReza Sabdar nlp->nlp_ldate = 0; 12652654012fSReza Sabdar nlp->nlp_clevel = nlp->nlp_llevel; 12662654012fSReza Sabdar /* 12672654012fSReza Sabdar * The value of nlp_cdate will be set to the checkpoint 12682654012fSReza Sabdar * creation time after it is created. 12692654012fSReza Sabdar */ 12702654012fSReza Sabdar if (ndmpd_get_dumptime(nlp->nlp_backup_path, &nlp->nlp_llevel, 12712654012fSReza Sabdar &nlp->nlp_ldate) < 0) { 12722654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 12732654012fSReza Sabdar "Getting dumpdates for %s level '%c'.\n", 12742654012fSReza Sabdar nlp->nlp_backup_path, *envp); 12752654012fSReza Sabdar return (NDMP_NO_MEM_ERR); 12762654012fSReza Sabdar } else { 12772654012fSReza Sabdar get_update_env_v3(params, nlp); 12782654012fSReza Sabdar rv = NDMP_NO_ERR; 12792654012fSReza Sabdar } 12802654012fSReza Sabdar 12812654012fSReza Sabdar return (rv); 12822654012fSReza Sabdar } 12832654012fSReza Sabdar 12842654012fSReza Sabdar 12852654012fSReza Sabdar /* 12862654012fSReza Sabdar * save_date_token_v3 12872654012fSReza Sabdar * 12882654012fSReza Sabdar * Make the value of DUMP_DATE env variable and append the values 12892654012fSReza Sabdar * of the current backup in the file specified with the DMP_NAME 12902654012fSReza Sabdar * env variable if any file is specified. The file will be 12912654012fSReza Sabdar * relative name in the backup directory path. 12922654012fSReza Sabdar * 12932654012fSReza Sabdar * Parameters: 12942654012fSReza Sabdar * params (input) - pointer to the parameters structure 12952654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 12962654012fSReza Sabdar * 12972654012fSReza Sabdar * Returns: 12982654012fSReza Sabdar * void 12992654012fSReza Sabdar */ 13002654012fSReza Sabdar static void 13012654012fSReza Sabdar save_date_token_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 13022654012fSReza Sabdar { 13032654012fSReza Sabdar char val[QUAD_DECIMAL_LEN]; 13042654012fSReza Sabdar u_longlong_t tok; 13052654012fSReza Sabdar 13062654012fSReza Sabdar if (!params || !nlp) 13072654012fSReza Sabdar return; 13082654012fSReza Sabdar 13092654012fSReza Sabdar nlp->nlp_tokseq++; 13102654012fSReza Sabdar tok = ((u_longlong_t)nlp->nlp_tokseq << 32) | nlp->nlp_cdate; 13112654012fSReza Sabdar (void) snprintf(val, sizeof (val), "%llu", tok); 13122654012fSReza Sabdar 13132654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "tok: %lld %s", tok, val); 13142654012fSReza Sabdar 13152654012fSReza Sabdar if (MOD_SETENV(params, "DUMP_DATE", val) != 0) { 13162654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 13172654012fSReza Sabdar "Could not set DUMP_DATE to %s", val); 13182654012fSReza Sabdar } else if (!nlp->nlp_dmpnm) { 13192654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "No log file defined"); 13202654012fSReza Sabdar } else if (ndmpd_append_dumptime(nlp->nlp_dmpnm, nlp->nlp_backup_path, 13212654012fSReza Sabdar nlp->nlp_tokseq, nlp->nlp_tokdate) < 0) { 13222654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 13232654012fSReza Sabdar "Saving backup date for \"%s\" in \"%s\".\n", 13242654012fSReza Sabdar nlp->nlp_backup_path, nlp->nlp_dmpnm); 13252654012fSReza Sabdar } 13262654012fSReza Sabdar } 13272654012fSReza Sabdar 13282654012fSReza Sabdar 13292654012fSReza Sabdar /* 13302654012fSReza Sabdar * save_lbr_bk_v3 13312654012fSReza Sabdar * 13322654012fSReza Sabdar * Append the backup type and date in the DMP_NAME file for 13332654012fSReza Sabdar * LBR-type backup if any file is specified. 13342654012fSReza Sabdar * 13352654012fSReza Sabdar * Parameters: 13362654012fSReza Sabdar * params (input) - pointer to the parameters structure 13372654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 13382654012fSReza Sabdar * 13392654012fSReza Sabdar * Returns: 13402654012fSReza Sabdar * void 13412654012fSReza Sabdar */ 13422654012fSReza Sabdar static void 13432654012fSReza Sabdar save_lbr_bk_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 13442654012fSReza Sabdar { 13452654012fSReza Sabdar if (!params || !nlp) 13462654012fSReza Sabdar return; 13472654012fSReza Sabdar 13482654012fSReza Sabdar if (!nlp->nlp_dmpnm) { 13492654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "No log file defined"); 13502654012fSReza Sabdar } else if (ndmpd_append_dumptime(nlp->nlp_dmpnm, nlp->nlp_backup_path, 13512654012fSReza Sabdar nlp->nlp_clevel, nlp->nlp_cdate) < 0) { 13522654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 13532654012fSReza Sabdar "Saving backup date for \"%s\" in \"%s\".\n", 13542654012fSReza Sabdar nlp->nlp_backup_path, nlp->nlp_dmpnm); 13552654012fSReza Sabdar } 13562654012fSReza Sabdar } 13572654012fSReza Sabdar 13582654012fSReza Sabdar 13592654012fSReza Sabdar /* 13602654012fSReza Sabdar * save_level_v3 13612654012fSReza Sabdar * 13622654012fSReza Sabdar * Save the date and level of the current backup in the dumpdates 13632654012fSReza Sabdar * file. 13642654012fSReza Sabdar * 13652654012fSReza Sabdar * Parameters: 13662654012fSReza Sabdar * params (input) - pointer to the parameters structure 13672654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 13682654012fSReza Sabdar * 13692654012fSReza Sabdar * Returns: 13702654012fSReza Sabdar * void 13712654012fSReza Sabdar */ 13722654012fSReza Sabdar static void 13732654012fSReza Sabdar save_level_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 13742654012fSReza Sabdar { 13752654012fSReza Sabdar if (!params || !nlp) 13762654012fSReza Sabdar return; 13772654012fSReza Sabdar 13782654012fSReza Sabdar if (!NLP_SHOULD_UPDATE(nlp)) { 13792654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "update not requested"); 13802654012fSReza Sabdar } else if (ndmpd_put_dumptime(nlp->nlp_backup_path, nlp->nlp_clevel, 13812654012fSReza Sabdar nlp->nlp_cdate) < 0) { 13822654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, "Logging backup date.\n"); 13832654012fSReza Sabdar } 13842654012fSReza Sabdar } 13852654012fSReza Sabdar 13862654012fSReza Sabdar 13872654012fSReza Sabdar /* 13882654012fSReza Sabdar * save_backup_date_v3 13892654012fSReza Sabdar * 13902654012fSReza Sabdar * A dispatcher function to call the corresponding save function 13912654012fSReza Sabdar * based on the backup type. 13922654012fSReza Sabdar * 13932654012fSReza Sabdar * Parameters: 13942654012fSReza Sabdar * params (input) - pointer to the parameters structure 13952654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 13962654012fSReza Sabdar * 13972654012fSReza Sabdar * Returns: 13982654012fSReza Sabdar * void 13992654012fSReza Sabdar */ 14002654012fSReza Sabdar static void 14012654012fSReza Sabdar save_backup_date_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 14022654012fSReza Sabdar { 14032654012fSReza Sabdar if (!params || !nlp) 14042654012fSReza Sabdar return; 14052654012fSReza Sabdar 14062654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_TOKENBK)) 14072654012fSReza Sabdar save_date_token_v3(params, nlp); 14082654012fSReza Sabdar else if (NLP_ISSET(nlp, NLPF_LBRBK)) 14092654012fSReza Sabdar save_lbr_bk_v3(params, nlp); 14102654012fSReza Sabdar else if (NLP_ISSET(nlp, NLPF_LEVELBK)) 14112654012fSReza Sabdar save_level_v3(params, nlp); 14122654012fSReza Sabdar else { 14132654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 14142654012fSReza Sabdar "Internal error: lost backup level type for \"%s\".\n", 14152654012fSReza Sabdar nlp->nlp_backup_path); 14162654012fSReza Sabdar } 14172654012fSReza Sabdar } 14182654012fSReza Sabdar 14192654012fSReza Sabdar 14202654012fSReza Sabdar /* 14212654012fSReza Sabdar * backup_alloc_structs_v3 14222654012fSReza Sabdar * 14232654012fSReza Sabdar * Create the structures for V3 backup. This includes: 14242654012fSReza Sabdar * Job stats 14252654012fSReza Sabdar * Reader writer IPC 14262654012fSReza Sabdar * File history callback structure 14272654012fSReza Sabdar * 14282654012fSReza Sabdar * Parameters: 14292654012fSReza Sabdar * session (input) - pointer to the session 14302654012fSReza Sabdar * jname (input) - name assigned to the current backup for 14312654012fSReza Sabdar * job stats strucure 14322654012fSReza Sabdar * 14332654012fSReza Sabdar * Returns: 14342654012fSReza Sabdar * 0: on success 14352654012fSReza Sabdar * -1: otherwise 14362654012fSReza Sabdar */ 14372654012fSReza Sabdar static int 14382654012fSReza Sabdar backup_alloc_structs_v3(ndmpd_session_t *session, char *jname) 14392654012fSReza Sabdar { 14402654012fSReza Sabdar int n; 14412654012fSReza Sabdar long xfer_size; 14422654012fSReza Sabdar ndmp_lbr_params_t *nlp; 14432654012fSReza Sabdar tlm_commands_t *cmds; 14442654012fSReza Sabdar 14452654012fSReza Sabdar nlp = ndmp_get_nlp(session); 14462654012fSReza Sabdar if (!nlp) { 14472654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 14482654012fSReza Sabdar return (-1); 14492654012fSReza Sabdar } 14502654012fSReza Sabdar 14512654012fSReza Sabdar nlp->nlp_jstat = tlm_new_job_stats(jname); 14522654012fSReza Sabdar if (!nlp->nlp_jstat) { 14532654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Creating job stats"); 14542654012fSReza Sabdar return (-1); 14552654012fSReza Sabdar } 14562654012fSReza Sabdar 14572654012fSReza Sabdar cmds = &nlp->nlp_cmds; 14582654012fSReza Sabdar (void) memset(cmds, 0, sizeof (*cmds)); 14592654012fSReza Sabdar 14602654012fSReza Sabdar xfer_size = ndmp_buffer_get_size(session); 14612654012fSReza Sabdar if (xfer_size < 512*KILOBYTE) { 14622654012fSReza Sabdar /* 14632654012fSReza Sabdar * Read multiple of mover_record_size near to 512K. This 14642654012fSReza Sabdar * will prevent the data being copied in the mover buffer 14652654012fSReza Sabdar * when we write the data. 14662654012fSReza Sabdar */ 14672654012fSReza Sabdar n = 512 * KILOBYTE / xfer_size; 14682654012fSReza Sabdar if (n <= 0) 14692654012fSReza Sabdar n = 1; 14702654012fSReza Sabdar xfer_size *= n; 14712654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Adjusted read size: %d", 14722654012fSReza Sabdar xfer_size); 14732654012fSReza Sabdar } 14742654012fSReza Sabdar 14752654012fSReza Sabdar cmds->tcs_command = tlm_create_reader_writer_ipc(TRUE, xfer_size); 14762654012fSReza Sabdar if (!cmds->tcs_command) { 14772654012fSReza Sabdar tlm_un_ref_job_stats(jname); 14782654012fSReza Sabdar return (-1); 14792654012fSReza Sabdar } 14802654012fSReza Sabdar 14812654012fSReza Sabdar nlp->nlp_logcallbacks = lbrlog_callbacks_init(session, 14822654012fSReza Sabdar ndmpd_fhpath_v3_cb, ndmpd_fhdir_v3_cb, ndmpd_fhnode_v3_cb); 14832654012fSReza Sabdar if (!nlp->nlp_logcallbacks) { 14842654012fSReza Sabdar tlm_release_reader_writer_ipc(cmds->tcs_command); 14852654012fSReza Sabdar tlm_un_ref_job_stats(jname); 14862654012fSReza Sabdar return (-1); 14872654012fSReza Sabdar } 14882654012fSReza Sabdar nlp->nlp_jstat->js_callbacks = (void *)(nlp->nlp_logcallbacks); 14892654012fSReza Sabdar nlp->nlp_restored = NULL; 14902654012fSReza Sabdar 14912654012fSReza Sabdar return (0); 14922654012fSReza Sabdar } 14932654012fSReza Sabdar 14942654012fSReza Sabdar 14952654012fSReza Sabdar /* 14962654012fSReza Sabdar * restore_alloc_structs_v3 14972654012fSReza Sabdar * 14982654012fSReza Sabdar * Create the structures for V3 Restore. This includes: 14992654012fSReza Sabdar * Job stats 15002654012fSReza Sabdar * Reader writer IPC 15012654012fSReza Sabdar * File recovery callback structure 15022654012fSReza Sabdar * 15032654012fSReza Sabdar * Parameters: 15042654012fSReza Sabdar * session (input) - pointer to the session 15052654012fSReza Sabdar * jname (input) - name assigned to the current backup for 15062654012fSReza Sabdar * job stats strucure 15072654012fSReza Sabdar * 15082654012fSReza Sabdar * Returns: 15092654012fSReza Sabdar * 0: on success 15102654012fSReza Sabdar * -1: otherwise 15112654012fSReza Sabdar */ 15122654012fSReza Sabdar int 15132654012fSReza Sabdar restore_alloc_structs_v3(ndmpd_session_t *session, char *jname) 15142654012fSReza Sabdar { 15152654012fSReza Sabdar long xfer_size; 15162654012fSReza Sabdar ndmp_lbr_params_t *nlp; 15172654012fSReza Sabdar tlm_commands_t *cmds; 15182654012fSReza Sabdar 15192654012fSReza Sabdar nlp = ndmp_get_nlp(session); 15202654012fSReza Sabdar if (!nlp) { 15212654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 15222654012fSReza Sabdar return (-1); 15232654012fSReza Sabdar } 15242654012fSReza Sabdar 15252654012fSReza Sabdar /* this is used in ndmpd_path_restored_v3() */ 15262654012fSReza Sabdar nlp->nlp_lastidx = -1; 15272654012fSReza Sabdar 15282654012fSReza Sabdar nlp->nlp_jstat = tlm_new_job_stats(jname); 15292654012fSReza Sabdar if (!nlp->nlp_jstat) { 15302654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Creating job stats"); 15312654012fSReza Sabdar return (-1); 15322654012fSReza Sabdar } 15332654012fSReza Sabdar 15342654012fSReza Sabdar cmds = &nlp->nlp_cmds; 15352654012fSReza Sabdar (void) memset(cmds, 0, sizeof (*cmds)); 15362654012fSReza Sabdar 15372654012fSReza Sabdar xfer_size = ndmp_buffer_get_size(session); 15382654012fSReza Sabdar cmds->tcs_command = tlm_create_reader_writer_ipc(FALSE, xfer_size); 15392654012fSReza Sabdar if (!cmds->tcs_command) { 15402654012fSReza Sabdar tlm_un_ref_job_stats(jname); 15412654012fSReza Sabdar return (-1); 15422654012fSReza Sabdar } 15432654012fSReza Sabdar 15442654012fSReza Sabdar nlp->nlp_logcallbacks = lbrlog_callbacks_init(session, 15452654012fSReza Sabdar ndmpd_path_restored_v3, NULL, NULL); 15462654012fSReza Sabdar if (!nlp->nlp_logcallbacks) { 15472654012fSReza Sabdar tlm_release_reader_writer_ipc(cmds->tcs_command); 15482654012fSReza Sabdar tlm_un_ref_job_stats(jname); 15492654012fSReza Sabdar return (-1); 15502654012fSReza Sabdar } 15512654012fSReza Sabdar nlp->nlp_jstat->js_callbacks = (void *)(nlp->nlp_logcallbacks); 15522654012fSReza Sabdar 15532654012fSReza Sabdar nlp->nlp_rsbm = bm_alloc(nlp->nlp_nfiles, 0); 15542654012fSReza Sabdar if (nlp->nlp_rsbm < 0) { 15552654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Out of memory."); 15562654012fSReza Sabdar lbrlog_callbacks_done(nlp->nlp_logcallbacks); 15572654012fSReza Sabdar tlm_release_reader_writer_ipc(cmds->tcs_command); 15582654012fSReza Sabdar tlm_un_ref_job_stats(jname); 15592654012fSReza Sabdar return (-1); 15602654012fSReza Sabdar } 15612654012fSReza Sabdar 15622654012fSReza Sabdar return (0); 15632654012fSReza Sabdar } 15642654012fSReza Sabdar 15652654012fSReza Sabdar 15662654012fSReza Sabdar /* 15672654012fSReza Sabdar * free_structs_v3 15682654012fSReza Sabdar * 15692654012fSReza Sabdar * Release the resources allocated by backup_alloc_structs_v3 15702654012fSReza Sabdar * function. 15712654012fSReza Sabdar * 15722654012fSReza Sabdar * Parameters: 15732654012fSReza Sabdar * session (input) - pointer to the session 15742654012fSReza Sabdar * jname (input) - name assigned to the current backup for 15752654012fSReza Sabdar * job stats strucure 15762654012fSReza Sabdar * 15772654012fSReza Sabdar * Returns: 15782654012fSReza Sabdar * void 15792654012fSReza Sabdar */ 15802654012fSReza Sabdar /*ARGSUSED*/ 15812654012fSReza Sabdar static void 15822654012fSReza Sabdar free_structs_v3(ndmpd_session_t *session, char *jname) 15832654012fSReza Sabdar { 15842654012fSReza Sabdar ndmp_lbr_params_t *nlp; 15852654012fSReza Sabdar tlm_commands_t *cmds; 15862654012fSReza Sabdar 15872654012fSReza Sabdar nlp = ndmp_get_nlp(session); 15882654012fSReza Sabdar if (!nlp) { 15892654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 15902654012fSReza Sabdar return; 15912654012fSReza Sabdar } 15922654012fSReza Sabdar cmds = &nlp->nlp_cmds; 15932654012fSReza Sabdar if (!cmds) { 15942654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "cmds == NULL"); 15952654012fSReza Sabdar return; 15962654012fSReza Sabdar } 15972654012fSReza Sabdar 15982654012fSReza Sabdar if (nlp->nlp_logcallbacks) { 15992654012fSReza Sabdar lbrlog_callbacks_done(nlp->nlp_logcallbacks); 16002654012fSReza Sabdar nlp->nlp_logcallbacks = NULL; 16012654012fSReza Sabdar } else 16022654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "FH CALLBACKS == NULL"); 16032654012fSReza Sabdar 16042654012fSReza Sabdar if (cmds->tcs_command) { 16052654012fSReza Sabdar if (cmds->tcs_command->tc_buffers != NULL) 16062654012fSReza Sabdar tlm_release_reader_writer_ipc(cmds->tcs_command); 16072654012fSReza Sabdar else 16082654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "BUFFERS == NULL"); 16092654012fSReza Sabdar cmds->tcs_command = NULL; 16102654012fSReza Sabdar } else 16112654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "COMMAND == NULL"); 16122654012fSReza Sabdar 16132654012fSReza Sabdar if (nlp->nlp_bkmap >= 0) { 16142654012fSReza Sabdar (void) dbm_free(nlp->nlp_bkmap); 16152654012fSReza Sabdar nlp->nlp_bkmap = -1; 16162654012fSReza Sabdar } 16172654012fSReza Sabdar 16182654012fSReza Sabdar if (session->ns_data.dd_operation == NDMP_DATA_OP_RECOVER) { 16192654012fSReza Sabdar if (nlp->nlp_rsbm < 0) { 16202654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp_rsbm < 0 %d", nlp->nlp_rsbm); 16212654012fSReza Sabdar } else { 16222654012fSReza Sabdar (void) bm_free(nlp->nlp_rsbm); 16232654012fSReza Sabdar nlp->nlp_rsbm = -1; 16242654012fSReza Sabdar } 16252654012fSReza Sabdar } 16262654012fSReza Sabdar } 16272654012fSReza Sabdar 16282654012fSReza Sabdar 16292654012fSReza Sabdar /* 16302654012fSReza Sabdar * backup_dirv3 16312654012fSReza Sabdar * 16322654012fSReza Sabdar * Backup a directory and update the bytes processed field of the 16332654012fSReza Sabdar * data server. 16342654012fSReza Sabdar * 16352654012fSReza Sabdar * Parameters: 16362654012fSReza Sabdar * bpp (input) - pointer to the backup parameters structure 16372654012fSReza Sabdar * pnp (input) - pointer to the path node 16382654012fSReza Sabdar * enp (input) - pointer to the entry node 16392654012fSReza Sabdar * 16402654012fSReza Sabdar * Returns: 16412654012fSReza Sabdar * 0: on success 16422654012fSReza Sabdar * != 0: otherwise 16432654012fSReza Sabdar */ 16442654012fSReza Sabdar static int 16452654012fSReza Sabdar backup_dirv3(bk_param_v3_t *bpp, fst_node_t *pnp, 16462654012fSReza Sabdar fst_node_t *enp) 16472654012fSReza Sabdar { 16482654012fSReza Sabdar longlong_t apos, bpos; 16492654012fSReza Sabdar acl_t *aclp = NULL; 16502654012fSReza Sabdar char *acltp; 16512654012fSReza Sabdar struct stat64 st; 16522654012fSReza Sabdar char fullpath[TLM_MAX_PATH_NAME]; 16532654012fSReza Sabdar char *p; 16542654012fSReza Sabdar 16552654012fSReza Sabdar if (!bpp || !pnp || !enp) { 16562654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Invalid argument"); 16572654012fSReza Sabdar return (-1); 16582654012fSReza Sabdar } 16592654012fSReza Sabdar 16602654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "d(%s)", bpp->bp_tmp); 16612654012fSReza Sabdar 16622654012fSReza Sabdar if (lstat64(bpp->bp_tmp, &st) != 0) 16632654012fSReza Sabdar return (0); 16642654012fSReza Sabdar 16652654012fSReza Sabdar if (acl_get(bpp->bp_tmp, ACL_NO_TRIVIAL, &aclp) != 0) { 16662654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "acl_get error errno=%d", errno); 16672654012fSReza Sabdar return (-1); 16682654012fSReza Sabdar } 16692654012fSReza Sabdar if (aclp && (acltp = acl_totext(aclp, 16702654012fSReza Sabdar ACL_APPEND_ID | ACL_SID_FMT | ACL_COMPACT_FMT)) != NULL) { 16712654012fSReza Sabdar (void) strlcpy(bpp->bp_tlmacl->acl_info.attr_info, 16722654012fSReza Sabdar acltp, TLM_MAX_ACL_TXT); 16732654012fSReza Sabdar acl_free(aclp); 16742654012fSReza Sabdar free(acltp); 16752654012fSReza Sabdar } else { 16762654012fSReza Sabdar *bpp->bp_tlmacl->acl_info.attr_info = '\0'; 16772654012fSReza Sabdar } 16782654012fSReza Sabdar 16792654012fSReza Sabdar bpos = tlm_get_data_offset(bpp->bp_lcmd); 16802654012fSReza Sabdar 16812654012fSReza Sabdar p = bpp->bp_tmp + strlen(bpp->bp_chkpnm); 16827bc22e45SReza Sabdar if (*p == '/') 16837bc22e45SReza Sabdar (void) snprintf(fullpath, TLM_MAX_PATH_NAME, "%s%s", 16847bc22e45SReza Sabdar bpp->bp_unchkpnm, p); 16857bc22e45SReza Sabdar else 16862654012fSReza Sabdar (void) snprintf(fullpath, TLM_MAX_PATH_NAME, "%s/%s", 16872654012fSReza Sabdar bpp->bp_unchkpnm, p); 16882654012fSReza Sabdar 16892654012fSReza Sabdar if (tm_tar_ops.tm_putdir != NULL) 16902654012fSReza Sabdar (void) (tm_tar_ops.tm_putdir)(fullpath, bpp->bp_tlmacl, 16912654012fSReza Sabdar bpp->bp_lcmd, bpp->bp_js); 16922654012fSReza Sabdar 16932654012fSReza Sabdar apos = tlm_get_data_offset(bpp->bp_lcmd); 16942654012fSReza Sabdar bpp->bp_session->ns_data.dd_module.dm_stats.ms_bytes_processed += 16952654012fSReza Sabdar apos - bpos; 16962654012fSReza Sabdar 16972654012fSReza Sabdar return (0); 16982654012fSReza Sabdar } 16992654012fSReza Sabdar 17002654012fSReza Sabdar 17012654012fSReza Sabdar /* 17022654012fSReza Sabdar * backup_filev3 17032654012fSReza Sabdar * 17042654012fSReza Sabdar * Backup a file and update the bytes processed field of the 17052654012fSReza Sabdar * data server. 17062654012fSReza Sabdar * 17072654012fSReza Sabdar * Parameters: 17082654012fSReza Sabdar * bpp (input) - pointer to the backup parameters structure 17092654012fSReza Sabdar * pnp (input) - pointer to the path node 17102654012fSReza Sabdar * enp (input) - pointer to the entry node 17112654012fSReza Sabdar * 17122654012fSReza Sabdar * Returns: 17132654012fSReza Sabdar * 0: on success 17142654012fSReza Sabdar * != 0: otherwise 17152654012fSReza Sabdar */ 17162654012fSReza Sabdar static int 17172654012fSReza Sabdar backup_filev3(bk_param_v3_t *bpp, fst_node_t *pnp, 17182654012fSReza Sabdar fst_node_t *enp) 17192654012fSReza Sabdar { 17202654012fSReza Sabdar char *ent; 17212654012fSReza Sabdar longlong_t rv; 17222654012fSReza Sabdar longlong_t apos, bpos; 17232654012fSReza Sabdar acl_t *aclp = NULL; 17242654012fSReza Sabdar char *acltp; 17252654012fSReza Sabdar struct stat64 st; 17262654012fSReza Sabdar char fullpath[TLM_MAX_PATH_NAME]; 17272654012fSReza Sabdar char *p; 17282654012fSReza Sabdar 17292654012fSReza Sabdar if (!bpp || !pnp || !enp) { 17302654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Invalid argument"); 17312654012fSReza Sabdar return (-1); 17322654012fSReza Sabdar } 17332654012fSReza Sabdar 17342654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "f(%s)", bpp->bp_tmp); 17352654012fSReza Sabdar 17362654012fSReza Sabdar if (lstat64(bpp->bp_tmp, &st) != 0) 17372654012fSReza Sabdar return (0); 17382654012fSReza Sabdar 17392654012fSReza Sabdar if (!S_ISLNK(bpp->bp_tlmacl->acl_attr.st_mode)) { 17402654012fSReza Sabdar if (acl_get(bpp->bp_tmp, ACL_NO_TRIVIAL, &aclp) != 0) { 17412654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "acl_get error"); 17422654012fSReza Sabdar return (-1); 17432654012fSReza Sabdar } 17442654012fSReza Sabdar 17452654012fSReza Sabdar if (aclp && 17462654012fSReza Sabdar (acltp = acl_totext(aclp, 17472654012fSReza Sabdar ACL_APPEND_ID | ACL_SID_FMT | ACL_COMPACT_FMT)) != NULL) { 17482654012fSReza Sabdar (void) strlcpy(bpp->bp_tlmacl->acl_info.attr_info, 17492654012fSReza Sabdar acltp, TLM_MAX_ACL_TXT); 17502654012fSReza Sabdar acl_free(aclp); 17512654012fSReza Sabdar free(acltp); 17522654012fSReza Sabdar } else { 17532654012fSReza Sabdar *bpp->bp_tlmacl->acl_info.attr_info = '\0'; 17542654012fSReza Sabdar } 17552654012fSReza Sabdar } 17562654012fSReza Sabdar 17572654012fSReza Sabdar bpos = tlm_get_data_offset(bpp->bp_lcmd); 17582654012fSReza Sabdar ent = enp->tn_path ? enp->tn_path : ""; 17592654012fSReza Sabdar 17602654012fSReza Sabdar p = pnp->tn_path + strlen(bpp->bp_chkpnm); 17617bc22e45SReza Sabdar if (*p == '/') 17627bc22e45SReza Sabdar (void) snprintf(fullpath, TLM_MAX_PATH_NAME, "%s%s", 17637bc22e45SReza Sabdar bpp->bp_unchkpnm, p); 17647bc22e45SReza Sabdar else 17652654012fSReza Sabdar (void) snprintf(fullpath, TLM_MAX_PATH_NAME, "%s/%s", 17662654012fSReza Sabdar bpp->bp_unchkpnm, p); 17672654012fSReza Sabdar 17682654012fSReza Sabdar if (tm_tar_ops.tm_putfile != NULL) 17692654012fSReza Sabdar rv = (tm_tar_ops.tm_putfile)(fullpath, ent, pnp->tn_path, 17702654012fSReza Sabdar bpp->bp_tlmacl, bpp->bp_cmds, bpp->bp_lcmd, bpp->bp_js, 17712654012fSReza Sabdar bpp->bp_session->hardlink_q); 17722654012fSReza Sabdar 17732654012fSReza Sabdar apos = tlm_get_data_offset(bpp->bp_lcmd); 17742654012fSReza Sabdar bpp->bp_session->ns_data.dd_module.dm_stats.ms_bytes_processed += 17752654012fSReza Sabdar apos - bpos; 17762654012fSReza Sabdar 17772654012fSReza Sabdar return (rv < 0 ? rv : 0); 17782654012fSReza Sabdar } 17792654012fSReza Sabdar 17802654012fSReza Sabdar 17812654012fSReza Sabdar /* 17822654012fSReza Sabdar * check_bk_args 17832654012fSReza Sabdar * 17842654012fSReza Sabdar * Check the argument of the bpp. This is shared function between 17852654012fSReza Sabdar * timebk_v3 and lbrbk_v3 functions. The checks include: 17862654012fSReza Sabdar * - The bpp itself. 17872654012fSReza Sabdar * - If the session pointer of the bpp is valid. 17882654012fSReza Sabdar * - If the session connection to the DMA is closed. 17892654012fSReza Sabdar * - If the nlp pointer of the bpp is valid. 17902654012fSReza Sabdar * - If the backup is aborted. 17912654012fSReza Sabdar * 17922654012fSReza Sabdar * Parameters: 17932654012fSReza Sabdar * bpp (input) - pointer to the backup parameters structure 17942654012fSReza Sabdar * 17952654012fSReza Sabdar * Returns: 17962654012fSReza Sabdar * 0: if everything's OK 17972654012fSReza Sabdar * != 0: otherwise 17982654012fSReza Sabdar */ 17992654012fSReza Sabdar static int 18002654012fSReza Sabdar check_bk_args(bk_param_v3_t *bpp) 18012654012fSReza Sabdar { 18022654012fSReza Sabdar int rv; 18032654012fSReza Sabdar 18042654012fSReza Sabdar if (!bpp) { 18052654012fSReza Sabdar rv = -1; 18062654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Lost bpp"); 18072654012fSReza Sabdar } else if (!bpp->bp_session) { 18082654012fSReza Sabdar rv = -1; 18092654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Session is NULL"); 18102654012fSReza Sabdar } else if (bpp->bp_session->ns_eof) { 18112654012fSReza Sabdar rv = -1; 18122654012fSReza Sabdar NDMP_LOG(LOG_INFO, 18132654012fSReza Sabdar "Connection client is closed for backup \"%s\"", 18142654012fSReza Sabdar bpp->bp_nlp->nlp_backup_path); 18152654012fSReza Sabdar } else if (!bpp->bp_nlp) { 18162654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Lost nlp"); 18172654012fSReza Sabdar return (-1); 18182654012fSReza Sabdar } else if (bpp->bp_session->ns_data.dd_abort) { 18192654012fSReza Sabdar rv = -1; 18202654012fSReza Sabdar NDMP_LOG(LOG_INFO, "Backup aborted \"%s\"", 18212654012fSReza Sabdar bpp->bp_nlp->nlp_backup_path); 18222654012fSReza Sabdar } else 18232654012fSReza Sabdar rv = 0; 18242654012fSReza Sabdar 18252654012fSReza Sabdar return (rv); 18262654012fSReza Sabdar } 18272654012fSReza Sabdar 18282654012fSReza Sabdar 18292654012fSReza Sabdar /* 18302654012fSReza Sabdar * shouldskip 18312654012fSReza Sabdar * 18322654012fSReza Sabdar * Determines if the current entry should be skipped or it 18332654012fSReza Sabdar * should be backed up. 18342654012fSReza Sabdar * 18352654012fSReza Sabdar * Parameters: 18362654012fSReza Sabdar * bpp (input) - pointer to the backup parameters structure 18372654012fSReza Sabdar * pnp (input) - pointer to the path node 18382654012fSReza Sabdar * enp (input) - pointer to the entry node 18392654012fSReza Sabdar * errp (output) - pointer to the error value that should be 18402654012fSReza Sabdar * returned by the caller 18412654012fSReza Sabdar * 18422654012fSReza Sabdar * Returns: 18432654012fSReza Sabdar * TRUE: if the entry should not be backed up 18442654012fSReza Sabdar * FALSE: otherwise 18452654012fSReza Sabdar */ 18462654012fSReza Sabdar static boolean_t 18472654012fSReza Sabdar shouldskip(bk_param_v3_t *bpp, fst_node_t *pnp, 18482654012fSReza Sabdar fst_node_t *enp, int *errp) 18492654012fSReza Sabdar { 18502654012fSReza Sabdar char *ent; 18512654012fSReza Sabdar boolean_t rv; 18522654012fSReza Sabdar struct stat64 *estp; 18532654012fSReza Sabdar 18542654012fSReza Sabdar if (!bpp || !pnp || !enp || !errp) { 18552654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Invalid argument"); 18562654012fSReza Sabdar return (TRUE); 18572654012fSReza Sabdar } 18582654012fSReza Sabdar 18592654012fSReza Sabdar if (!enp->tn_path) { 18602654012fSReza Sabdar ent = ""; 18612654012fSReza Sabdar estp = pnp->tn_st; 18622654012fSReza Sabdar } else { 18632654012fSReza Sabdar ent = enp->tn_path; 18642654012fSReza Sabdar estp = enp->tn_st; 18652654012fSReza Sabdar } 18662654012fSReza Sabdar 18672654012fSReza Sabdar /* 18682654012fSReza Sabdar * When excluding or skipping entries, FST_SKIP should be 18692654012fSReza Sabdar * returned, otherwise, 0 should be returned to 18702654012fSReza Sabdar * get other entries in the directory of this entry. 18712654012fSReza Sabdar */ 18722654012fSReza Sabdar if (!dbm_getone(bpp->bp_nlp->nlp_bkmap, (u_longlong_t)estp->st_ino)) { 18732654012fSReza Sabdar rv = TRUE; 18742654012fSReza Sabdar *errp = S_ISDIR(estp->st_mode) ? FST_SKIP : 0; 18752654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Skipping %d %s/%s", 18762654012fSReza Sabdar *errp, pnp->tn_path, ent); 18772654012fSReza Sabdar } else if (tlm_is_excluded(pnp->tn_path, ent, bpp->bp_excls)) { 18782654012fSReza Sabdar rv = TRUE; 18792654012fSReza Sabdar *errp = S_ISDIR(estp->st_mode) ? FST_SKIP : 0; 18802654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "excl %d \"%s/%s\"", 18812654012fSReza Sabdar *errp, pnp->tn_path, ent); 18822654012fSReza Sabdar } else if (inexl(bpp->bp_nlp->nlp_exl, ent)) { 18832654012fSReza Sabdar rv = TRUE; 18842654012fSReza Sabdar *errp = S_ISDIR(estp->st_mode) ? FST_SKIP : 0; 18852654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "out %d \"%s/%s\"", 18862654012fSReza Sabdar *errp, pnp->tn_path, ent); 18872654012fSReza Sabdar } else if (!S_ISDIR(estp->st_mode) && 18882654012fSReza Sabdar !ininc(bpp->bp_nlp->nlp_inc, ent)) { 18892654012fSReza Sabdar rv = TRUE; 18902654012fSReza Sabdar *errp = 0; 18912654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "!in \"%s/%s\"", pnp->tn_path, ent); 18922654012fSReza Sabdar } else 18932654012fSReza Sabdar rv = FALSE; 18942654012fSReza Sabdar 18952654012fSReza Sabdar return (rv); 18962654012fSReza Sabdar } 18972654012fSReza Sabdar 18982654012fSReza Sabdar 18992654012fSReza Sabdar /* 19002654012fSReza Sabdar * ischngd 19012654012fSReza Sabdar * 19022654012fSReza Sabdar * Check if the object specified should be backed up or not. 19032654012fSReza Sabdar * If stp belongs to a directory and if it is marked in the 19042654012fSReza Sabdar * bitmap vector, it shows that either the directory itself is 19052654012fSReza Sabdar * modified or there is something below it that will be backed 19062654012fSReza Sabdar * up. 19072654012fSReza Sabdar * 19082654012fSReza Sabdar * By setting ndmp_force_bk_dirs global variable to a non-zero 19092654012fSReza Sabdar * value, directories are backed up anyways. 19102654012fSReza Sabdar * 19112654012fSReza Sabdar * Backing up the directories unconditionally helps 19122654012fSReza Sabdar * restoring the metadata of directories as well, when one 19132654012fSReza Sabdar * of the objects below them are being restored. 19142654012fSReza Sabdar * 19152654012fSReza Sabdar * For non-directory objects, if the modification or change 19162654012fSReza Sabdar * time of the object is after the date specified by the 19172654012fSReza Sabdar * bk_selector_t, the the object must be backed up. 19182654012fSReza Sabdar */ 19192654012fSReza Sabdar static boolean_t 19202654012fSReza Sabdar ischngd(struct stat64 *stp, time_t t, ndmp_lbr_params_t *nlp) 19212654012fSReza Sabdar { 19222654012fSReza Sabdar boolean_t rv; 19232654012fSReza Sabdar 19242654012fSReza Sabdar if (!stp) { 19252654012fSReza Sabdar rv = FALSE; 19262654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "stp is NULL"); 19272654012fSReza Sabdar } else if (!nlp) { 19282654012fSReza Sabdar rv = FALSE; 19292654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp is NULL"); 19302654012fSReza Sabdar } else if (t == 0) { 19312654012fSReza Sabdar /* 19322654012fSReza Sabdar * if we are doing base backup then we do not need to 19332654012fSReza Sabdar * check the time, for we should backup everything. 19342654012fSReza Sabdar */ 19352654012fSReza Sabdar rv = TRUE; 19362654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Base Backup"); 19372654012fSReza Sabdar } else if (S_ISDIR(stp->st_mode) && ndmp_force_bk_dirs) { 19382654012fSReza Sabdar rv = TRUE; 19392654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "d(%lu)", (uint_t)stp->st_ino); 19402654012fSReza Sabdar } else if (S_ISDIR(stp->st_mode) && 19412654012fSReza Sabdar dbm_getone(nlp->nlp_bkmap, (u_longlong_t)stp->st_ino) && 19422654012fSReza Sabdar ((NLP_ISDUMP(nlp) && ndmp_dump_path_node) || 19432654012fSReza Sabdar (NLP_ISTAR(nlp) && ndmp_tar_path_node))) { 19442654012fSReza Sabdar /* 19452654012fSReza Sabdar * If the object is a directory and it leads to a modified 19462654012fSReza Sabdar * object (that should be backed up) and for that type of 19472654012fSReza Sabdar * backup the path nodes should be backed up, then return 19482654012fSReza Sabdar * TRUE. 19492654012fSReza Sabdar * 19502654012fSReza Sabdar * This is required by some DMAs like Backup Express, which 19512654012fSReza Sabdar * needs to receive ADD_NODE (for dump) or ADD_PATH (for tar) 19522654012fSReza Sabdar * for the intermediate directories of a modified object. 19532654012fSReza Sabdar * Other DMAs, like net_backup and net_worker, do not have such 19542654012fSReza Sabdar * requirement. This requirement makes sense for dump format 19552654012fSReza Sabdar * but for 'tar' format, it does not. In provision to the 19562654012fSReza Sabdar * NDMP-v4 spec, for 'tar' format the intermediate directories 19572654012fSReza Sabdar * need not to be reported. 19582654012fSReza Sabdar */ 19592654012fSReza Sabdar rv = TRUE; 19602654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "p(%lu)", (u_longlong_t)stp->st_ino); 19612654012fSReza Sabdar } else if (stp->st_mtime > t) { 19622654012fSReza Sabdar rv = TRUE; 19632654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "m(%lu): %lu > %lu", 19642654012fSReza Sabdar (uint_t)stp->st_ino, (uint_t)stp->st_mtime, (uint_t)t); 19652654012fSReza Sabdar } else if (stp->st_ctime > t) { 19662654012fSReza Sabdar if (NLP_IGNCTIME(nlp)) { 19672654012fSReza Sabdar rv = FALSE; 19682654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "ign c(%lu): %lu > %lu", 19692654012fSReza Sabdar (uint_t)stp->st_ino, (uint_t)stp->st_ctime, 19702654012fSReza Sabdar (uint_t)t); 19712654012fSReza Sabdar } else { 19722654012fSReza Sabdar rv = TRUE; 19732654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "c(%lu): %lu > %lu", 19742654012fSReza Sabdar (uint_t)stp->st_ino, (uint_t)stp->st_ctime, 19752654012fSReza Sabdar (uint_t)t); 19762654012fSReza Sabdar } 19772654012fSReza Sabdar } else { 19782654012fSReza Sabdar rv = FALSE; 19792654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "mc(%lu): (%lu,%lu) < %lu", 19802654012fSReza Sabdar (uint_t)stp->st_ino, (uint_t)stp->st_mtime, 19812654012fSReza Sabdar (uint_t)stp->st_ctime, (uint_t)t); 19822654012fSReza Sabdar } 19832654012fSReza Sabdar 19842654012fSReza Sabdar return (rv); 19852654012fSReza Sabdar } 19862654012fSReza Sabdar 19872654012fSReza Sabdar 19882654012fSReza Sabdar /* 19892654012fSReza Sabdar * iscreated 19902654012fSReza Sabdar * 19912654012fSReza Sabdar * This function is used to check last mtime (currently inside the ACL 19922654012fSReza Sabdar * structure) instead of ctime for checking if the file is to be backed up 19932654012fSReza Sabdar * or not. See option "inc.lmtime" for more details 19942654012fSReza Sabdar */ 19952654012fSReza Sabdar /*ARGSUSED*/ 19962654012fSReza Sabdar int iscreated(ndmp_lbr_params_t *nlp, char *name, tlm_acls_t *tacl, 19972654012fSReza Sabdar time_t t) 19982654012fSReza Sabdar { 19992654012fSReza Sabdar int ret; 20002654012fSReza Sabdar acl_t *aclp = NULL; 20012654012fSReza Sabdar char *acltp; 20022654012fSReza Sabdar 20032654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "flags %x", nlp->nlp_flags); 20042654012fSReza Sabdar if (NLP_INCLMTIME(nlp) == FALSE) 20052654012fSReza Sabdar return (0); 20062654012fSReza Sabdar 20072654012fSReza Sabdar ret = acl_get(name, ACL_NO_TRIVIAL, &aclp); 20082654012fSReza Sabdar if (ret != 0) { 20092654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 20102654012fSReza Sabdar "Error getting the acl information: err %d", ret); 20112654012fSReza Sabdar return (0); 20122654012fSReza Sabdar } 20132654012fSReza Sabdar if (aclp && (acltp = acl_totext(aclp, 20142654012fSReza Sabdar ACL_APPEND_ID | ACL_SID_FMT | ACL_COMPACT_FMT)) != NULL) { 20152654012fSReza Sabdar (void) strlcpy(tacl->acl_info.attr_info, acltp, 20162654012fSReza Sabdar TLM_MAX_ACL_TXT); 20172654012fSReza Sabdar acl_free(aclp); 20182654012fSReza Sabdar free(acltp); 20192654012fSReza Sabdar } 20202654012fSReza Sabdar 20212654012fSReza Sabdar /* Need to add support for last mtime */ 20222654012fSReza Sabdar 20232654012fSReza Sabdar return (0); 20242654012fSReza Sabdar } 20252654012fSReza Sabdar 20262654012fSReza Sabdar /* 20272654012fSReza Sabdar * size_cb 20282654012fSReza Sabdar * 20292654012fSReza Sabdar * The callback function for calculating the size of 20302654012fSReza Sabdar * the backup path. This is used to get an estimate 20312654012fSReza Sabdar * of the progress of backup during NDMP backup 20322654012fSReza Sabdar */ 20332654012fSReza Sabdar static int 20342654012fSReza Sabdar size_cb(void *arg, fst_node_t *pnp, fst_node_t *enp) 20352654012fSReza Sabdar { 20362654012fSReza Sabdar struct stat64 *stp; 20372654012fSReza Sabdar 20382654012fSReza Sabdar stp = enp->tn_path ? enp->tn_st : pnp->tn_st; 20392654012fSReza Sabdar *((u_longlong_t *)arg) += stp->st_size; 20402654012fSReza Sabdar 20412654012fSReza Sabdar return (0); 20422654012fSReza Sabdar } 20432654012fSReza Sabdar 20442654012fSReza Sabdar /* 20452654012fSReza Sabdar * timebk_v3 20462654012fSReza Sabdar * 20472654012fSReza Sabdar * The callback function for backing up objects based on 20482654012fSReza Sabdar * their time stamp. This is shared between token-based 20492654012fSReza Sabdar * and level-based backup, which look at the time stamps 20502654012fSReza Sabdar * of the objects to determine if they should be backed 20512654012fSReza Sabdar * up. 20522654012fSReza Sabdar * 20532654012fSReza Sabdar * Parameters: 20542654012fSReza Sabdar * arg (input) - pointer to the backup parameters structure 20552654012fSReza Sabdar * pnp (input) - pointer to the path node 20562654012fSReza Sabdar * enp (input) - pointer to the entry node 20572654012fSReza Sabdar * 20582654012fSReza Sabdar * Returns: 20592654012fSReza Sabdar * 0: if backup should continue 20602654012fSReza Sabdar * -1: if the backup should be stopped 20612654012fSReza Sabdar * FST_SKIP: if backing up the current directory is enough 20622654012fSReza Sabdar */ 20632654012fSReza Sabdar static int 20642654012fSReza Sabdar timebk_v3(void *arg, fst_node_t *pnp, fst_node_t *enp) 20652654012fSReza Sabdar { 20662654012fSReza Sabdar char *ent; 20672654012fSReza Sabdar int rv; 20682654012fSReza Sabdar time_t t; 20692654012fSReza Sabdar bk_param_v3_t *bpp; 20702654012fSReza Sabdar struct stat64 *stp; 20712654012fSReza Sabdar fs_fhandle_t *fhp; 20722654012fSReza Sabdar 20732654012fSReza Sabdar bpp = (bk_param_v3_t *)arg; 20742654012fSReza Sabdar 20752654012fSReza Sabdar rv = check_bk_args(bpp); 20762654012fSReza Sabdar if (rv != 0) 20772654012fSReza Sabdar return (rv); 20782654012fSReza Sabdar 20792654012fSReza Sabdar stp = enp->tn_path ? enp->tn_st : pnp->tn_st; 20802654012fSReza Sabdar if (shouldskip(bpp, pnp, enp, &rv)) 20812654012fSReza Sabdar return (rv); 20822654012fSReza Sabdar 20832654012fSReza Sabdar if (enp->tn_path) { 20842654012fSReza Sabdar ent = enp->tn_path; 20852654012fSReza Sabdar stp = enp->tn_st; 20862654012fSReza Sabdar fhp = enp->tn_fh; 20872654012fSReza Sabdar } else { 20882654012fSReza Sabdar ent = ""; 20892654012fSReza Sabdar stp = pnp->tn_st; 20902654012fSReza Sabdar fhp = pnp->tn_fh; 20912654012fSReza Sabdar } 20922654012fSReza Sabdar 20932654012fSReza Sabdar 20942654012fSReza Sabdar if (!tlm_cat_path(bpp->bp_tmp, pnp->tn_path, ent)) { 20952654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Path too long %s/%s.", pnp->tn_path, ent); 20962654012fSReza Sabdar return (FST_SKIP); 20972654012fSReza Sabdar } 20982654012fSReza Sabdar if (NLP_ISSET(bpp->bp_nlp, NLPF_TOKENBK)) 20992654012fSReza Sabdar t = bpp->bp_nlp->nlp_tokdate; 21002654012fSReza Sabdar else if (NLP_ISSET(bpp->bp_nlp, NLPF_LEVELBK)) { 21012654012fSReza Sabdar t = bpp->bp_nlp->nlp_ldate; 21022654012fSReza Sabdar } else { 21032654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Unknown backup type on \"%s/%s\"", 21042654012fSReza Sabdar pnp->tn_path, ent); 21052654012fSReza Sabdar return (-1); 21062654012fSReza Sabdar } 21072654012fSReza Sabdar 21082654012fSReza Sabdar if (S_ISDIR(stp->st_mode)) { 21092654012fSReza Sabdar bpp->bp_tlmacl->acl_dir_fh = *fhp; 21102654012fSReza Sabdar (void) ndmpd_fhdir_v3_cb(bpp->bp_nlp->nlp_logcallbacks, 21112654012fSReza Sabdar bpp->bp_tmp, stp); 21122654012fSReza Sabdar 21132654012fSReza Sabdar if (ischngd(stp, t, bpp->bp_nlp)) { 21142654012fSReza Sabdar (void) memcpy(&bpp->bp_tlmacl->acl_attr, stp, 21152654012fSReza Sabdar sizeof (struct stat64)); 21162654012fSReza Sabdar rv = backup_dirv3(bpp, pnp, enp); 21172654012fSReza Sabdar } 21182654012fSReza Sabdar } else { 21192654012fSReza Sabdar if (ischngd(stp, t, bpp->bp_nlp) || 21202654012fSReza Sabdar iscreated(bpp->bp_nlp, bpp->bp_tmp, bpp->bp_tlmacl, t)) { 21212654012fSReza Sabdar rv = 0; 21222654012fSReza Sabdar (void) memcpy(&bpp->bp_tlmacl->acl_attr, stp, 21232654012fSReza Sabdar sizeof (struct stat64)); 21242654012fSReza Sabdar bpp->bp_tlmacl->acl_fil_fh = *fhp; 21252654012fSReza Sabdar (void) backup_filev3(bpp, pnp, enp); 21262654012fSReza Sabdar } 21272654012fSReza Sabdar } 21282654012fSReza Sabdar 21292654012fSReza Sabdar return (rv); 21302654012fSReza Sabdar } 21312654012fSReza Sabdar 21322654012fSReza Sabdar 21332654012fSReza Sabdar /* 21342654012fSReza Sabdar * lbrbk_v3 21352654012fSReza Sabdar * 21362654012fSReza Sabdar * The callback function for backing up objects based on 21372654012fSReza Sabdar * their archive directory bit. This is used in LBR-type 21382654012fSReza Sabdar * backup. In which the objects are backed up if their 21392654012fSReza Sabdar * archive bit is set. 21402654012fSReza Sabdar * 21412654012fSReza Sabdar * Parameters: 21422654012fSReza Sabdar * arg (input) - pointer to the backup parameters structure 21432654012fSReza Sabdar * pnp (input) - pointer to the path node 21442654012fSReza Sabdar * enp (input) - pointer to the entry node 21452654012fSReza Sabdar * 21462654012fSReza Sabdar * Returns: 21472654012fSReza Sabdar * 0: if backup should continue 21482654012fSReza Sabdar * -1: if the backup should be stopped 21492654012fSReza Sabdar * FST_SKIP: if backing up the current directory is enough 21502654012fSReza Sabdar */ 21512654012fSReza Sabdar static int 21522654012fSReza Sabdar lbrbk_v3(void *arg, fst_node_t *pnp, fst_node_t *enp) 21532654012fSReza Sabdar { 21542654012fSReza Sabdar char *ent; 21552654012fSReza Sabdar int rv; 21562654012fSReza Sabdar bk_param_v3_t *bpp; 21572654012fSReza Sabdar struct stat64 *stp; 21582654012fSReza Sabdar fs_fhandle_t *fhp; 21592654012fSReza Sabdar 21602654012fSReza Sabdar bpp = (bk_param_v3_t *)arg; 21612654012fSReza Sabdar rv = check_bk_args(bpp); 21622654012fSReza Sabdar if (rv != 0) 21632654012fSReza Sabdar return (rv); 21642654012fSReza Sabdar 21652654012fSReza Sabdar stp = enp->tn_path ? enp->tn_st : pnp->tn_st; 21662654012fSReza Sabdar if (shouldskip(bpp, pnp, enp, &rv)) 21672654012fSReza Sabdar return (rv); 21682654012fSReza Sabdar 21692654012fSReza Sabdar if (enp->tn_path) { 21702654012fSReza Sabdar ent = enp->tn_path; 21712654012fSReza Sabdar stp = enp->tn_st; 21722654012fSReza Sabdar fhp = enp->tn_fh; 21732654012fSReza Sabdar } else { 21742654012fSReza Sabdar ent = ""; 21752654012fSReza Sabdar stp = pnp->tn_st; 21762654012fSReza Sabdar fhp = pnp->tn_fh; 21772654012fSReza Sabdar } 21782654012fSReza Sabdar 21792654012fSReza Sabdar if (!tlm_cat_path(bpp->bp_tmp, pnp->tn_path, ent)) { 21802654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Path too long %s/%s.", pnp->tn_path, ent); 21812654012fSReza Sabdar return (FST_SKIP); 21822654012fSReza Sabdar } 21832654012fSReza Sabdar if (!NLP_ISSET(bpp->bp_nlp, NLPF_LBRBK)) { 21842654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "!NLPF_LBRBK"); 21852654012fSReza Sabdar return (-1); 21862654012fSReza Sabdar } 21872654012fSReza Sabdar 21882654012fSReza Sabdar if (S_ISDIR(stp->st_mode)) { 21892654012fSReza Sabdar bpp->bp_tlmacl->acl_dir_fh = *fhp; 21902654012fSReza Sabdar (void) ndmpd_fhdir_v3_cb(bpp->bp_nlp->nlp_logcallbacks, 21912654012fSReza Sabdar bpp->bp_tmp, stp); 21922654012fSReza Sabdar 21932654012fSReza Sabdar if (SHOULD_LBRBK(bpp)) { 21942654012fSReza Sabdar bpp->bp_tlmacl->acl_attr = *stp; 21952654012fSReza Sabdar rv = backup_dirv3(bpp, pnp, enp); 21962654012fSReza Sabdar } 21972654012fSReza Sabdar } else if (SHOULD_LBRBK(bpp)) { 21982654012fSReza Sabdar rv = 0; 21992654012fSReza Sabdar bpp->bp_tlmacl->acl_attr = *stp; 22002654012fSReza Sabdar bpp->bp_tlmacl->acl_fil_fh = *fhp; 22012654012fSReza Sabdar (void) backup_filev3(bpp, pnp, enp); 22022654012fSReza Sabdar } 22032654012fSReza Sabdar 22042654012fSReza Sabdar return (rv); 22052654012fSReza Sabdar } 22062654012fSReza Sabdar 22072654012fSReza Sabdar 22082654012fSReza Sabdar /* 22092654012fSReza Sabdar * backup_reader_v3 22102654012fSReza Sabdar * 22112654012fSReza Sabdar * The reader thread for the backup. It sets up the callback 22122654012fSReza Sabdar * parameters and traverses the backup hierarchy in level-order 22132654012fSReza Sabdar * way. 22142654012fSReza Sabdar * 22152654012fSReza Sabdar * Parameters: 22162654012fSReza Sabdar * jname (input) - name assigned to the current backup for 22172654012fSReza Sabdar * job stats strucure 22182654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 22192654012fSReza Sabdar * cmds (input) - pointer to the tlm_commands_t structure 22202654012fSReza Sabdar * 22212654012fSReza Sabdar * Returns: 22222654012fSReza Sabdar * 0: on success 22232654012fSReza Sabdar * != 0: otherwise 22242654012fSReza Sabdar */ 22252654012fSReza Sabdar static int 22262654012fSReza Sabdar backup_reader_v3(backup_reader_arg_t *argp) 22272654012fSReza Sabdar { 22282654012fSReza Sabdar int rv; 22292654012fSReza Sabdar tlm_cmd_t *lcmd; 22302654012fSReza Sabdar tlm_acls_t tlm_acls; 22312654012fSReza Sabdar longlong_t bpos, n; 22322654012fSReza Sabdar bk_param_v3_t bp; 22332654012fSReza Sabdar fs_traverse_t ft; 22342654012fSReza Sabdar char *jname; 22352654012fSReza Sabdar ndmp_lbr_params_t *nlp; 22362654012fSReza Sabdar tlm_commands_t *cmds; 22372654012fSReza Sabdar 22382654012fSReza Sabdar if (!argp) 22392654012fSReza Sabdar return (-1); 22402654012fSReza Sabdar 22412654012fSReza Sabdar jname = argp->br_jname; 22422654012fSReza Sabdar nlp = argp->br_nlp; 22432654012fSReza Sabdar cmds = argp->br_cmds; 22442654012fSReza Sabdar 22452654012fSReza Sabdar rv = 0; 22462654012fSReza Sabdar lcmd = cmds->tcs_command; 22472654012fSReza Sabdar lcmd->tc_ref++; 22482654012fSReza Sabdar cmds->tcs_reader_count++; 22492654012fSReza Sabdar 22502654012fSReza Sabdar (void) memset(&tlm_acls, 0, sizeof (tlm_acls)); 22512654012fSReza Sabdar 22522654012fSReza Sabdar /* NDMP parameters */ 22532654012fSReza Sabdar bp.bp_session = nlp->nlp_session; 22542654012fSReza Sabdar bp.bp_nlp = nlp; 22552654012fSReza Sabdar 22562654012fSReza Sabdar /* LBR-related parameters */ 22572654012fSReza Sabdar bp.bp_js = tlm_ref_job_stats(jname); 22582654012fSReza Sabdar bp.bp_cmds = cmds; 22592654012fSReza Sabdar bp.bp_lcmd = lcmd; 22602654012fSReza Sabdar bp.bp_tlmacl = &tlm_acls; 22612654012fSReza Sabdar bp.bp_opr = 0; 22622654012fSReza Sabdar 22632654012fSReza Sabdar /* release the parent thread, after referencing the job stats */ 22642654012fSReza Sabdar (void) pthread_barrier_wait(&argp->br_barrier); 22652654012fSReza Sabdar 22662654012fSReza Sabdar bp.bp_tmp = ndmp_malloc(sizeof (char) * TLM_MAX_PATH_NAME); 22672654012fSReza Sabdar if (!bp.bp_tmp) 22682654012fSReza Sabdar return (-1); 22692654012fSReza Sabdar 22702654012fSReza Sabdar /* 22712654012fSReza Sabdar * Make the checkpointed paths for traversing the 22722654012fSReza Sabdar * backup hierarchy, if we make the checkpoint. 22732654012fSReza Sabdar */ 22742654012fSReza Sabdar bp.bp_unchkpnm = nlp->nlp_backup_path; 22752654012fSReza Sabdar if (!NLP_ISCHKPNTED(nlp)) { 22762654012fSReza Sabdar tlm_acls.acl_checkpointed = TRUE; 22772654012fSReza Sabdar bp.bp_chkpnm = ndmp_malloc(sizeof (char) * TLM_MAX_PATH_NAME); 22782654012fSReza Sabdar if (!bp.bp_chkpnm) { 22792654012fSReza Sabdar NDMP_FREE(bp.bp_tmp); 22802654012fSReza Sabdar return (-1); 22812654012fSReza Sabdar } 22822654012fSReza Sabdar (void) tlm_build_snapshot_name(nlp->nlp_backup_path, 22832654012fSReza Sabdar bp.bp_chkpnm, nlp->nlp_jstat->js_job_name); 22842654012fSReza Sabdar } else { 22852654012fSReza Sabdar tlm_acls.acl_checkpointed = FALSE; 22862654012fSReza Sabdar bp.bp_chkpnm = nlp->nlp_backup_path; 22872654012fSReza Sabdar } 22882654012fSReza Sabdar bp.bp_excls = ndmpd_make_exc_list(); 22892654012fSReza Sabdar 22902654012fSReza Sabdar /* set traversing arguments */ 22912654012fSReza Sabdar ft.ft_path = nlp->nlp_backup_path; 22922654012fSReza Sabdar ft.ft_lpath = bp.bp_chkpnm; 22932654012fSReza Sabdar 22942654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "path %s lpath %s", ft.ft_path, ft.ft_lpath); 22952654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_TOKENBK) || NLP_ISSET(nlp, NLPF_LEVELBK)) { 22962654012fSReza Sabdar ft.ft_callbk = timebk_v3; 22972654012fSReza Sabdar tlm_acls.acl_clear_archive = FALSE; 22982654012fSReza Sabdar } else if (NLP_ISSET(nlp, NLPF_LBRBK)) { 22992654012fSReza Sabdar ft.ft_callbk = lbrbk_v3; 23002654012fSReza Sabdar tlm_acls.acl_clear_archive = FALSE; 23012654012fSReza Sabdar 23022654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "bp_opr %x clr_arc %c", 23032654012fSReza Sabdar bp.bp_opr, NDMP_YORN(tlm_acls.acl_clear_archive)); 23042654012fSReza Sabdar } else { 23052654012fSReza Sabdar rv = -1; 23062654012fSReza Sabdar MOD_LOGV3(nlp->nlp_params, NDMP_LOG_ERROR, 23072654012fSReza Sabdar "Unknow backup type.\n"); 23082654012fSReza Sabdar } 23092654012fSReza Sabdar ft.ft_arg = &bp; 23102654012fSReza Sabdar ft.ft_logfp = (ft_log_t)ndmp_log; 2311876b86efSReza Sabdar ft.ft_flags = FST_VERBOSE | FST_STOP_ONERR; 23122654012fSReza Sabdar 23132654012fSReza Sabdar /* take into account the header written to the stream so far */ 23142654012fSReza Sabdar n = tlm_get_data_offset(lcmd); 23152654012fSReza Sabdar nlp->nlp_session->ns_data.dd_module.dm_stats.ms_bytes_processed = n; 23162654012fSReza Sabdar 23172654012fSReza Sabdar if (rv == 0) { 23182654012fSReza Sabdar /* start traversing the hierarchy and actual backup */ 23192654012fSReza Sabdar rv = traverse_level(&ft); 23202654012fSReza Sabdar if (rv == 0) { 23212654012fSReza Sabdar /* write the trailer and update the bytes processed */ 23222654012fSReza Sabdar bpos = tlm_get_data_offset(lcmd); 23232654012fSReza Sabdar (void) write_tar_eof(lcmd); 23242654012fSReza Sabdar n = tlm_get_data_offset(lcmd) - bpos; 23252654012fSReza Sabdar nlp->nlp_session-> 23262654012fSReza Sabdar ns_data.dd_module.dm_stats.ms_bytes_processed += n; 2327876b86efSReza Sabdar } else { 2328876b86efSReza Sabdar MOD_LOGV3(nlp->nlp_params, NDMP_LOG_ERROR, 2329876b86efSReza Sabdar "Filesystem traverse error.\n"); 2330876b86efSReza Sabdar ndmpd_data_error(nlp->nlp_session, 2331876b86efSReza Sabdar NDMP_DATA_HALT_INTERNAL_ERROR); 23322654012fSReza Sabdar } 23332654012fSReza Sabdar } 23342654012fSReza Sabdar 23352654012fSReza Sabdar if (!NLP_ISCHKPNTED(nlp)) 23362654012fSReza Sabdar NDMP_FREE(bp.bp_chkpnm); 23372654012fSReza Sabdar NDMP_FREE(bp.bp_tmp); 23382654012fSReza Sabdar NDMP_FREE(bp.bp_excls); 23392654012fSReza Sabdar 23402654012fSReza Sabdar cmds->tcs_reader_count--; 23412654012fSReza Sabdar lcmd->tc_writer = TLM_STOP; 23422654012fSReza Sabdar tlm_release_reader_writer_ipc(lcmd); 23432654012fSReza Sabdar tlm_un_ref_job_stats(jname); 23442654012fSReza Sabdar return (rv); 23452654012fSReza Sabdar 23462654012fSReza Sabdar } 23472654012fSReza Sabdar 23482654012fSReza Sabdar 23492654012fSReza Sabdar /* 23502654012fSReza Sabdar * tar_backup_v3 23512654012fSReza Sabdar * 23522654012fSReza Sabdar * Traverse the backup hierarchy if needed and make the bitmap. 23532654012fSReza Sabdar * Then launch reader and writer threads to do the actual backup. 23542654012fSReza Sabdar * 23552654012fSReza Sabdar * Parameters: 23562654012fSReza Sabdar * session (input) - pointer to the session 23572654012fSReza Sabdar * params (input) - pointer to the parameters structure 23582654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 23592654012fSReza Sabdar * jname (input) - job name 23602654012fSReza Sabdar * 23612654012fSReza Sabdar * Returns: 23622654012fSReza Sabdar * 0: on success 23632654012fSReza Sabdar * != 0: otherwise 23642654012fSReza Sabdar */ 23652654012fSReza Sabdar static int 23662654012fSReza Sabdar tar_backup_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 23672654012fSReza Sabdar ndmp_lbr_params_t *nlp, char *jname) 23682654012fSReza Sabdar { 23692654012fSReza Sabdar tlm_commands_t *cmds; 23702654012fSReza Sabdar backup_reader_arg_t arg; 23712654012fSReza Sabdar pthread_t rdtp; 23722654012fSReza Sabdar char info[256]; 23732654012fSReza Sabdar int result; 23742654012fSReza Sabdar ndmp_context_t nctx; 23752654012fSReza Sabdar int err; 23762654012fSReza Sabdar 23772654012fSReza Sabdar if (ndmp_get_bk_dir_ino(nlp)) 23782654012fSReza Sabdar return (-1); 23792654012fSReza Sabdar 23802654012fSReza Sabdar result = err = 0; 23812654012fSReza Sabdar 23822654012fSReza Sabdar /* exit as if there was an internal error */ 23832654012fSReza Sabdar if (session->ns_eof) 23842654012fSReza Sabdar return (-1); 23852654012fSReza Sabdar 23862654012fSReza Sabdar if (!session->ns_data.dd_abort) { 23872654012fSReza Sabdar if (backup_alloc_structs_v3(session, jname) < 0) { 23882654012fSReza Sabdar nlp->nlp_bkmap = -1; 23892654012fSReza Sabdar return (-1); 23902654012fSReza Sabdar } 23912654012fSReza Sabdar 23922654012fSReza Sabdar if (ndmpd_mark_inodes_v3(session, nlp) != 0) { 23932654012fSReza Sabdar if (nlp->nlp_bkmap != -1) { 23942654012fSReza Sabdar (void) dbm_free(nlp->nlp_bkmap); 23952654012fSReza Sabdar nlp->nlp_bkmap = -1; 23962654012fSReza Sabdar } 23972654012fSReza Sabdar free_structs_v3(session, jname); 23982654012fSReza Sabdar return (-1); 23992654012fSReza Sabdar } 24002654012fSReza Sabdar 24012654012fSReza Sabdar nlp->nlp_jstat->js_start_ltime = time(NULL); 24022654012fSReza Sabdar nlp->nlp_jstat->js_start_time = nlp->nlp_jstat->js_start_ltime; 24032654012fSReza Sabdar nlp->nlp_jstat->js_chkpnt_time = nlp->nlp_cdate; 24042654012fSReza Sabdar 24052654012fSReza Sabdar cmds = &nlp->nlp_cmds; 24062654012fSReza Sabdar cmds->tcs_reader = cmds->tcs_writer = TLM_BACKUP_RUN; 24072654012fSReza Sabdar cmds->tcs_command->tc_reader = TLM_BACKUP_RUN; 24082654012fSReza Sabdar cmds->tcs_command->tc_writer = TLM_BACKUP_RUN; 24092654012fSReza Sabdar 24102654012fSReza Sabdar if (ndmp_write_utf8magic(cmds->tcs_command) < 0) { 24112654012fSReza Sabdar free_structs_v3(session, jname); 24122654012fSReza Sabdar return (-1); 24132654012fSReza Sabdar } 24142654012fSReza Sabdar 24152654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 24162654012fSReza Sabdar "Backing up \"%s\" started.", nlp->nlp_backup_path); 24172654012fSReza Sabdar 24182654012fSReza Sabdar /* Plug-in module */ 24192654012fSReza Sabdar if (ndmp_pl != NULL && 24202654012fSReza Sabdar ndmp_pl->np_pre_backup != NULL) { 24212654012fSReza Sabdar (void) memset(&nctx, 0, sizeof (ndmp_context_t)); 24222654012fSReza Sabdar nctx.nc_plversion = ndmp_pl->np_plversion; 24232654012fSReza Sabdar nctx.nc_plname = ndmpd_get_prop(NDMP_PLUGIN_PATH); 24242654012fSReza Sabdar nctx.nc_cmds = cmds; 242542ed7838SReza Sabdar nctx.nc_params = params; 24268c4f9701SJanice Chang nctx.nc_ddata = (void *) session; 24272654012fSReza Sabdar if ((err = ndmp_pl->np_pre_backup(ndmp_pl, &nctx, 24282654012fSReza Sabdar nlp->nlp_backup_path)) != 0) { 242942ed7838SReza Sabdar NDMP_LOG(LOG_ERR, "Pre-backup plug-in: %m"); 24302654012fSReza Sabdar goto backup_out; 24312654012fSReza Sabdar } 24322654012fSReza Sabdar } 24332654012fSReza Sabdar 24342654012fSReza Sabdar (void) memset(&arg, 0, sizeof (backup_reader_arg_t)); 24352654012fSReza Sabdar arg.br_jname = jname; 24362654012fSReza Sabdar arg.br_nlp = nlp; 24372654012fSReza Sabdar arg.br_cmds = cmds; 24382654012fSReza Sabdar 24392654012fSReza Sabdar (void) pthread_barrier_init(&arg.br_barrier, 0, 2); 24402654012fSReza Sabdar 24412654012fSReza Sabdar err = pthread_create(&rdtp, NULL, (funct_t)backup_reader_v3, 24422654012fSReza Sabdar (void *)&arg); 24432654012fSReza Sabdar if (err == 0) { 24442654012fSReza Sabdar (void) pthread_barrier_wait(&arg.br_barrier); 24452654012fSReza Sabdar (void) pthread_barrier_destroy(&arg.br_barrier); 24462654012fSReza Sabdar } else { 24472654012fSReza Sabdar (void) pthread_barrier_destroy(&arg.br_barrier); 24482654012fSReza Sabdar free_structs_v3(session, jname); 24492654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Launch backup_reader_v3: %m"); 24502654012fSReza Sabdar return (-1); 24512654012fSReza Sabdar } 24522654012fSReza Sabdar 24532654012fSReza Sabdar if ((err = ndmp_tar_writer(session, params, cmds)) != 0) 24542654012fSReza Sabdar result = EIO; 24552654012fSReza Sabdar 24562654012fSReza Sabdar nlp->nlp_jstat->js_stop_time = time(NULL); 24572654012fSReza Sabdar 24582654012fSReza Sabdar (void) snprintf(info, sizeof (info), 24592654012fSReza Sabdar "Runtime [%s] %llu bytes (%llu): %d seconds\n", 24602654012fSReza Sabdar nlp->nlp_backup_path, 24612654012fSReza Sabdar session->ns_data.dd_module.dm_stats.ms_bytes_processed, 24622654012fSReza Sabdar session->ns_data.dd_module.dm_stats.ms_bytes_processed, 24632654012fSReza Sabdar nlp->nlp_jstat->js_stop_time - 24642654012fSReza Sabdar nlp->nlp_jstat->js_start_ltime); 24652654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, info); 24662654012fSReza Sabdar 24672654012fSReza Sabdar ndmp_wait_for_reader(cmds); 24682654012fSReza Sabdar (void) pthread_join(rdtp, NULL); 24692654012fSReza Sabdar 24702654012fSReza Sabdar /* exit as if there was an internal error */ 24712654012fSReza Sabdar if (session->ns_eof) { 24722654012fSReza Sabdar result = EPIPE; 24732654012fSReza Sabdar err = -1; 24742654012fSReza Sabdar } 24752654012fSReza Sabdar if (!session->ns_data.dd_abort) { 24762654012fSReza Sabdar ndmpd_audit_backup(session->ns_connection, 24772654012fSReza Sabdar nlp->nlp_backup_path, 24782654012fSReza Sabdar session->ns_data.dd_data_addr.addr_type, 24792654012fSReza Sabdar session->ns_tape.td_adapter_name, result); 24802654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Backing up \"%s\" Finished.", 24812654012fSReza Sabdar nlp->nlp_backup_path); 24822654012fSReza Sabdar } 24832654012fSReza Sabdar } 24842654012fSReza Sabdar 24852654012fSReza Sabdar if (session->ns_data.dd_abort) { 24862654012fSReza Sabdar ndmpd_audit_backup(session->ns_connection, 24872654012fSReza Sabdar nlp->nlp_backup_path, 24882654012fSReza Sabdar session->ns_data.dd_data_addr.addr_type, 24892654012fSReza Sabdar session->ns_tape.td_adapter_name, EINTR); 24902654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 24912654012fSReza Sabdar "Backing up \"%s\" aborted.", nlp->nlp_backup_path); 24922654012fSReza Sabdar err = -1; 24932654012fSReza Sabdar } else { 24942654012fSReza Sabdar 24952654012fSReza Sabdar backup_out: 24962654012fSReza Sabdar /* Plug-in module */ 24972654012fSReza Sabdar if (ndmp_pl != NULL && 24982654012fSReza Sabdar ndmp_pl->np_post_backup != NULL && 24992654012fSReza Sabdar ndmp_pl->np_post_backup(ndmp_pl, &nctx, err) == -1) { 25002654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Post-backup plug-in: %m"); 25012654012fSReza Sabdar return (-1); 25022654012fSReza Sabdar } 25032654012fSReza Sabdar } 25042654012fSReza Sabdar 25052654012fSReza Sabdar free_structs_v3(session, jname); 25062654012fSReza Sabdar return (err); 25072654012fSReza Sabdar } 25082654012fSReza Sabdar 25092654012fSReza Sabdar /* 25102654012fSReza Sabdar * get_backup_size 25112654012fSReza Sabdar * 25122654012fSReza Sabdar * Find the estimate of backup size. This is used to get an estimate 25132654012fSReza Sabdar * of the progress of backup during NDMP backup. 25142654012fSReza Sabdar */ 25152654012fSReza Sabdar void 2516416eec61SReza Sabdar get_backup_size(ndmp_bkup_size_arg_t *sarg) 25172654012fSReza Sabdar { 25182654012fSReza Sabdar fs_traverse_t ft; 25192654012fSReza Sabdar u_longlong_t bk_size; 2520416eec61SReza Sabdar char spath[PATH_MAX]; 25212654012fSReza Sabdar int rv; 25222654012fSReza Sabdar 25232654012fSReza Sabdar bk_size = 0; 2524416eec61SReza Sabdar if (fs_is_chkpntvol(sarg->bs_path)) { 2525416eec61SReza Sabdar ft.ft_path = sarg->bs_path; 2526416eec61SReza Sabdar } else { 2527416eec61SReza Sabdar (void) tlm_build_snapshot_name(sarg->bs_path, 2528416eec61SReza Sabdar spath, sarg->bs_jname); 2529416eec61SReza Sabdar ft.ft_path = spath; 2530416eec61SReza Sabdar } 25312654012fSReza Sabdar 2532416eec61SReza Sabdar ft.ft_lpath = ft.ft_path; 25332654012fSReza Sabdar ft.ft_callbk = size_cb; 25342654012fSReza Sabdar ft.ft_arg = &bk_size; 25352654012fSReza Sabdar ft.ft_logfp = (ft_log_t)ndmp_log; 2536416eec61SReza Sabdar ft.ft_flags = FST_VERBOSE; 25372654012fSReza Sabdar 25382654012fSReza Sabdar if ((rv = traverse_level(&ft)) != 0) { 25392654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "bksize err=%d", rv); 25402654012fSReza Sabdar bk_size = 0; 25412654012fSReza Sabdar } else { 25422654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "bksize %lld, %lldKB, %lldMB\n", 25432654012fSReza Sabdar bk_size, bk_size / 1024, bk_size /(1024 * 1024)); 25442654012fSReza Sabdar } 2545416eec61SReza Sabdar sarg->bs_session->ns_data.dd_data_size = bk_size; 25462654012fSReza Sabdar } 25472654012fSReza Sabdar 25482654012fSReza Sabdar /* 25492654012fSReza Sabdar * get_rs_path_v3 25502654012fSReza Sabdar * 25512654012fSReza Sabdar * Find the restore path 25522654012fSReza Sabdar */ 25532654012fSReza Sabdar ndmp_error 25542654012fSReza Sabdar get_rs_path_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 25552654012fSReza Sabdar { 25562654012fSReza Sabdar char *dp; 25572654012fSReza Sabdar ndmp_error rv; 25582654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 25592654012fSReza Sabdar int i, nm_cnt; 25602654012fSReza Sabdar char *nm_dpath_list[MULTIPLE_DEST_DIRS]; 25612654012fSReza Sabdar static char mdest_buf[256]; 25622654012fSReza Sabdar 25632654012fSReza Sabdar *mdest_buf = 0; 25642654012fSReza Sabdar *nm_dpath_list = ""; 25652654012fSReza Sabdar for (i = 0, nm_cnt = 0; i < (int)nlp->nlp_nfiles; i++) { 25662654012fSReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i); 25672654012fSReza Sabdar if (!ep) { 25682654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Can't get Nlist[%d]", i); 25692654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 25702654012fSReza Sabdar } 25712654012fSReza Sabdar if (strcmp(nm_dpath_list[nm_cnt], ep->nm3_dpath) != 0 && 25722654012fSReza Sabdar nm_cnt < MULTIPLE_DEST_DIRS - 1) 25732654012fSReza Sabdar nm_dpath_list[++nm_cnt] = ep->nm3_dpath; 25742654012fSReza Sabdar } 25752654012fSReza Sabdar 25762654012fSReza Sabdar multiple_dest_restore = (nm_cnt > 1); 25772654012fSReza Sabdar nlp->nlp_restore_path = mdest_buf; 25782654012fSReza Sabdar 25792654012fSReza Sabdar for (i = 1; i < nm_cnt + 1; i++) { 25802654012fSReza Sabdar if (ISDEFINED(nm_dpath_list[i])) 25812654012fSReza Sabdar dp = nm_dpath_list[i]; 25822654012fSReza Sabdar else 25832654012fSReza Sabdar /* the default destination path is backup directory */ 25842654012fSReza Sabdar dp = nlp->nlp_backup_path; 25852654012fSReza Sabdar 25862654012fSReza Sabdar /* check the destination directory exists and is writable */ 25872654012fSReza Sabdar if (!fs_volexist(dp)) { 25882654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 25892654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 25902654012fSReza Sabdar "Invalid destination path volume \"%s\".\n", dp); 25912654012fSReza Sabdar } else if (!voliswr(dp)) { 25922654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 25932654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 25942654012fSReza Sabdar "The destination path volume" 25952654012fSReza Sabdar " is not writable \"%s\".\n", dp); 25962654012fSReza Sabdar } else { 25972654012fSReza Sabdar rv = NDMP_NO_ERR; 25982654012fSReza Sabdar (void) strlcat(nlp->nlp_restore_path, dp, 25992654012fSReza Sabdar sizeof (mdest_buf)); 26002654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "rspath: \"%s\"", dp); 26012654012fSReza Sabdar } 26022654012fSReza Sabdar 26032654012fSReza Sabdar /* 26042654012fSReza Sabdar * Exit if there is an error or it is not a multiple 26052654012fSReza Sabdar * destination restore mode 26062654012fSReza Sabdar */ 26072654012fSReza Sabdar if (rv != NDMP_NO_ERR || !multiple_dest_restore) 26082654012fSReza Sabdar break; 26092654012fSReza Sabdar 26102654012fSReza Sabdar if (i < nm_cnt) 26112654012fSReza Sabdar (void) strlcat(nlp->nlp_restore_path, ", ", 26122654012fSReza Sabdar sizeof (mdest_buf)); 26132654012fSReza Sabdar } 26142654012fSReza Sabdar 26152654012fSReza Sabdar return (rv); 26162654012fSReza Sabdar } 26172654012fSReza Sabdar 26182654012fSReza Sabdar 26192654012fSReza Sabdar /* 26202654012fSReza Sabdar * fix_nlist_v3 26212654012fSReza Sabdar * 26222654012fSReza Sabdar * Check if the recovery list is valid and fix it if there are some 26232654012fSReza Sabdar * unspecified entries in it. It checks for original, destination 26242654012fSReza Sabdar * and new path for all NDMP names provided inside the list. 26252654012fSReza Sabdar * 26262654012fSReza Sabdar * V3: dpath is the destination directory. If newnm is not NULL, the 26272654012fSReza Sabdar * destination path is dpath/newnm. Otherwise the destination path is 26282654012fSReza Sabdar * dpath/opath_last_node, where opath_last_node is the last node in opath. 26292654012fSReza Sabdar * 26302654012fSReza Sabdar * V4: If newnm is not NULL, dpath is the destination directory, and 26312654012fSReza Sabdar * dpath/newnm is the destination path. If newnm is NULL, dpath is 26322654012fSReza Sabdar * the destination path (opath is not involved in forming destination path). 26332654012fSReza Sabdar */ 26342654012fSReza Sabdar ndmp_error 26352654012fSReza Sabdar fix_nlist_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 26362654012fSReza Sabdar ndmp_lbr_params_t *nlp) 26372654012fSReza Sabdar { 26382654012fSReza Sabdar char *cp, *buf, *bp; 26392654012fSReza Sabdar int i, n; 26402654012fSReza Sabdar int iswrbk; 26412654012fSReza Sabdar int bvexists; 26422654012fSReza Sabdar ndmp_error rv; 26432654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 26442654012fSReza Sabdar char *dp; 26452654012fSReza Sabdar char *nm; 26462654012fSReza Sabdar int existsvol; 26472654012fSReza Sabdar int isrwdst; 26482654012fSReza Sabdar 26492654012fSReza Sabdar buf = ndmp_malloc(TLM_MAX_PATH_NAME); 26502654012fSReza Sabdar if (!buf) { 26512654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, "Insufficient memory.\n"); 26522654012fSReza Sabdar return (NDMP_NO_MEM_ERR); 26532654012fSReza Sabdar } 26542654012fSReza Sabdar 26552654012fSReza Sabdar bvexists = fs_volexist(nlp->nlp_backup_path); 26562654012fSReza Sabdar iswrbk = voliswr(nlp->nlp_backup_path); 26572654012fSReza Sabdar 26582654012fSReza Sabdar rv = NDMP_NO_ERR; 26592654012fSReza Sabdar n = session->ns_data.dd_nlist_len; 26602654012fSReza Sabdar for (i = 0; i < n; i++) { 26612654012fSReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i); 26622654012fSReza Sabdar if (!ep) 26632654012fSReza Sabdar continue; 26642654012fSReza Sabdar 26652654012fSReza Sabdar /* chop off the trailing slashes */ 26662654012fSReza Sabdar chopslash(ep->nm3_opath); 26672654012fSReza Sabdar 26682654012fSReza Sabdar chopslash(ep->nm3_dpath); 26692654012fSReza Sabdar chopslash(ep->nm3_newnm); 26702654012fSReza Sabdar 26712654012fSReza Sabdar /* existing and non-empty destination path */ 26722654012fSReza Sabdar if (ISDEFINED(ep->nm3_dpath)) { 26732654012fSReza Sabdar dp = ep->nm3_dpath; 26742654012fSReza Sabdar existsvol = fs_volexist(dp); 26752654012fSReza Sabdar isrwdst = voliswr(dp); 26762654012fSReza Sabdar } else { 26772654012fSReza Sabdar /* the default destination path is backup directory */ 26782654012fSReza Sabdar dp = nlp->nlp_backup_path; 26792654012fSReza Sabdar existsvol = bvexists; 26802654012fSReza Sabdar isrwdst = iswrbk; 26812654012fSReza Sabdar } 26822654012fSReza Sabdar 26832654012fSReza Sabdar /* check the destination directory exists and is writable */ 26842654012fSReza Sabdar if (!existsvol) { 26852654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 26862654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 26872654012fSReza Sabdar "Invalid destination path volume " 26882654012fSReza Sabdar "\"%s\".\n", dp); 26892654012fSReza Sabdar break; 26902654012fSReza Sabdar } 26912654012fSReza Sabdar if (!isrwdst) { 26922654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 26932654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 26942654012fSReza Sabdar "The destination path volume is not " 26952654012fSReza Sabdar "writable \"%s\".\n", dp); 26962654012fSReza Sabdar break; 26972654012fSReza Sabdar } 26982654012fSReza Sabdar 26992654012fSReza Sabdar /* 27002654012fSReza Sabdar * If new name is not specified, the default new name is 27012654012fSReza Sabdar * the last component of the original path, if any 27022654012fSReza Sabdar * (except in V4). 27032654012fSReza Sabdar */ 27042654012fSReza Sabdar if (ISDEFINED(ep->nm3_newnm)) { 27052654012fSReza Sabdar nm = ep->nm3_newnm; 27062654012fSReza Sabdar } else { 2707c9fd6b31SReza Sabdar char *p, *q; 2708c9fd6b31SReza Sabdar 27092654012fSReza Sabdar /* 27102654012fSReza Sabdar * Find the last component of nm3_opath. 27112654012fSReza Sabdar * nm3_opath has no trailing '/'. 27122654012fSReza Sabdar */ 2713c9fd6b31SReza Sabdar p = strrchr(ep->nm3_opath, '/'); 2714c9fd6b31SReza Sabdar nm = p ? p + 1 : ep->nm3_opath; 2715c9fd6b31SReza Sabdar 2716c9fd6b31SReza Sabdar /* 2717c9fd6b31SReza Sabdar * In DDAR the last component could 2718c9fd6b31SReza Sabdar * be repeated in nm3_dpath 2719c9fd6b31SReza Sabdar */ 2720c9fd6b31SReza Sabdar q = strrchr(ep->nm3_dpath, '/'); 2721c9fd6b31SReza Sabdar q = q ? q + 1 : ep->nm3_dpath; 2722c9fd6b31SReza Sabdar if (strcmp(nm, q) == 0) 2723c9fd6b31SReza Sabdar nm = NULL; 2724c9fd6b31SReza Sabdar 27252654012fSReza Sabdar } 27262654012fSReza Sabdar 27272654012fSReza Sabdar bp = joinpath(buf, dp, nm); 27282654012fSReza Sabdar if (!bp) { 27292654012fSReza Sabdar /* 27302654012fSReza Sabdar * Note: What should be done with this entry? 27312654012fSReza Sabdar * We leave it untouched for now, hence no path in 27322654012fSReza Sabdar * the backup image matches with this entry and will 27332654012fSReza Sabdar * be reported as not found. 27342654012fSReza Sabdar */ 27352654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 27362654012fSReza Sabdar "Destination path too long(%s/%s)", dp, nm); 27372654012fSReza Sabdar continue; 27382654012fSReza Sabdar } 27392654012fSReza Sabdar cp = strdup(bp); 27402654012fSReza Sabdar if (!cp) { 27412654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 27422654012fSReza Sabdar "Insufficient memory.\n"); 27432654012fSReza Sabdar rv = NDMP_NO_MEM_ERR; 27442654012fSReza Sabdar break; 27452654012fSReza Sabdar } 27462654012fSReza Sabdar free(ep->nm3_dpath); 27472654012fSReza Sabdar ep->nm3_dpath = cp; 27482654012fSReza Sabdar NDMP_FREE(ep->nm3_newnm); 27492654012fSReza Sabdar 27502654012fSReza Sabdar bp = joinpath(buf, nlp->nlp_backup_path, ep->nm3_opath); 27512654012fSReza Sabdar if (!bp) { 27522654012fSReza Sabdar /* 27532654012fSReza Sabdar * Note: The same problem of above with long path. 27542654012fSReza Sabdar */ 27552654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 27562654012fSReza Sabdar "Path too long(%s/%s)", 27572654012fSReza Sabdar nlp->nlp_backup_path, ep->nm3_opath); 27582654012fSReza Sabdar continue; 27592654012fSReza Sabdar } 27602654012fSReza Sabdar cp = strdup(bp); 27612654012fSReza Sabdar if (!cp) { 27622654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 27632654012fSReza Sabdar "Insufficient memory.\n"); 27642654012fSReza Sabdar rv = NDMP_NO_MEM_ERR; 27652654012fSReza Sabdar break; 27662654012fSReza Sabdar } 27672654012fSReza Sabdar NDMP_FREE(ep->nm3_opath); 27682654012fSReza Sabdar ep->nm3_opath = cp; 27692654012fSReza Sabdar 27702654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "orig[%d]: \"%s\"", i, ep->nm3_opath); 27712654012fSReza Sabdar if (ep->nm3_dpath) { 27722654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 27732654012fSReza Sabdar "dest[%d]: \"%s\"", i, ep->nm3_dpath); 27742654012fSReza Sabdar } else { 27752654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "dest[%d]: \"%s\"", i, "NULL"); 27762654012fSReza Sabdar } 27772654012fSReza Sabdar } 27782654012fSReza Sabdar 27792654012fSReza Sabdar free(buf); 27802654012fSReza Sabdar 27812654012fSReza Sabdar return (rv); 27822654012fSReza Sabdar } 27832654012fSReza Sabdar 27842654012fSReza Sabdar 27852654012fSReza Sabdar /* 27862654012fSReza Sabdar * allvalidfh 27872654012fSReza Sabdar * 27882654012fSReza Sabdar * Run a sanity check on the file history info. The file history 27892654012fSReza Sabdar * info is the offset of the record starting the entry on the tape 27902654012fSReza Sabdar * and is used in DAR (direct access restore mode). 27912654012fSReza Sabdar */ 27922654012fSReza Sabdar static boolean_t 27932654012fSReza Sabdar allvalidfh(ndmpd_session_t *session, ndmpd_module_params_t *params) 27942654012fSReza Sabdar { 27952654012fSReza Sabdar int i, n; 27962654012fSReza Sabdar boolean_t rv; 27972654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 27982654012fSReza Sabdar 27992654012fSReza Sabdar rv = TRUE; 28002654012fSReza Sabdar n = session->ns_data.dd_nlist_len; 28012654012fSReza Sabdar for (i = 0; i < n; i++) { 28022654012fSReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i); 28032654012fSReza Sabdar if (!ep) 28042654012fSReza Sabdar continue; 28052654012fSReza Sabdar /* 28062654012fSReza Sabdar * The fh_info's sent from the client are multiples 28072654012fSReza Sabdar * of RECORDSIZE which is 512 bytes. 28082654012fSReza Sabdar * 28092654012fSReza Sabdar * All our fh_info's are at the RECORDSIZE boundary. If there 28102654012fSReza Sabdar * is any fh_info that is less than RECORDSIZE (this covers 0 28112654012fSReza Sabdar * and -1 values too), then the result is that DAR cannot be 28122654012fSReza Sabdar * done. 28132654012fSReza Sabdar */ 28142654012fSReza Sabdar if (ep->nm3_fh_info < RECORDSIZE || 28152654012fSReza Sabdar ep->nm3_fh_info % RECORDSIZE != 0) { 28162654012fSReza Sabdar rv = FALSE; 28172654012fSReza Sabdar break; 28182654012fSReza Sabdar } 28192654012fSReza Sabdar } 28202654012fSReza Sabdar 28212654012fSReza Sabdar return (rv); 28222654012fSReza Sabdar } 28232654012fSReza Sabdar 28242654012fSReza Sabdar 28252654012fSReza Sabdar /* 28262654012fSReza Sabdar * log_rs_params_v3 28272654012fSReza Sabdar * 28282654012fSReza Sabdar * Log a copy of all values of the restore parameters 28292654012fSReza Sabdar */ 28302654012fSReza Sabdar void 28312654012fSReza Sabdar log_rs_params_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 28322654012fSReza Sabdar ndmp_lbr_params_t *nlp) 28332654012fSReza Sabdar { 28342654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Restoring to \"%s\".\n", 28352654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : "NULL"); 28362654012fSReza Sabdar 28372654012fSReza Sabdar if (session->ns_data.dd_data_addr.addr_type == NDMP_ADDR_LOCAL) { 28382654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, "Tape server: local.\n"); 28392654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 28402654012fSReza Sabdar "Tape record size: %d.\n", 28412654012fSReza Sabdar session->ns_mover.md_record_size); 28422654012fSReza Sabdar } else if (session->ns_data.dd_data_addr.addr_type == NDMP_ADDR_TCP) 28432654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 28442654012fSReza Sabdar "Tape server: remote at %s:%d.\n", 28452654012fSReza Sabdar inet_ntoa(IN_ADDR(session->ns_data.dd_data_addr.tcp_ip_v3)), 28462654012fSReza Sabdar session->ns_data.dd_data_addr.tcp_port_v3); 28472654012fSReza Sabdar else 28482654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 28492654012fSReza Sabdar "Unknown tape server address type.\n"); 28502654012fSReza Sabdar 28512654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_DIRECT)) 28522654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_NORMAL, 28532654012fSReza Sabdar "Direct Access Restore.\n"); 28542654012fSReza Sabdar } 28552654012fSReza Sabdar 28562654012fSReza Sabdar 28572654012fSReza Sabdar /* 28582654012fSReza Sabdar * send_unrecovered_list_v3 28592654012fSReza Sabdar * 28602654012fSReza Sabdar * Create the list of files that were in restore list but 28612654012fSReza Sabdar * not recovered due to some errors. 28622654012fSReza Sabdar */ 28632654012fSReza Sabdar int 28642654012fSReza Sabdar send_unrecovered_list_v3(ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp) 28652654012fSReza Sabdar { 28662654012fSReza Sabdar int i, rv; 28672654012fSReza Sabdar int err; 28682654012fSReza Sabdar 28692654012fSReza Sabdar if (!params) { 28702654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "params == NULL"); 28712654012fSReza Sabdar return (-1); 28722654012fSReza Sabdar } 28732654012fSReza Sabdar if (!nlp) { 28742654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 28752654012fSReza Sabdar return (-1); 28762654012fSReza Sabdar } 28772654012fSReza Sabdar 28782654012fSReza Sabdar if (nlp->nlp_lastidx != -1) { 28792654012fSReza Sabdar if (!bm_getone(nlp->nlp_rsbm, (u_longlong_t)nlp->nlp_lastidx)) 28802654012fSReza Sabdar err = ENOENT; 28812654012fSReza Sabdar else 28822654012fSReza Sabdar err = 0; 28832654012fSReza Sabdar (void) ndmp_send_recovery_stat_v3(params, nlp, 28842654012fSReza Sabdar nlp->nlp_lastidx, err); 28852654012fSReza Sabdar nlp->nlp_lastidx = -1; 28862654012fSReza Sabdar } 28872654012fSReza Sabdar 28882654012fSReza Sabdar rv = 0; 28892654012fSReza Sabdar for (i = 0; i < (int)nlp->nlp_nfiles; i++) { 28902654012fSReza Sabdar if (!bm_getone(nlp->nlp_rsbm, (u_longlong_t)i)) { 28912654012fSReza Sabdar rv = ndmp_send_recovery_stat_v3(params, nlp, i, ENOENT); 28922654012fSReza Sabdar if (rv < 0) 28932654012fSReza Sabdar break; 28942654012fSReza Sabdar } 28952654012fSReza Sabdar } 28962654012fSReza Sabdar 28972654012fSReza Sabdar return (rv); 28982654012fSReza Sabdar } 28992654012fSReza Sabdar 29002654012fSReza Sabdar 29012654012fSReza Sabdar 29022654012fSReza Sabdar /* 29032654012fSReza Sabdar * restore_dar_alloc_structs_v3 29042654012fSReza Sabdar * 29052654012fSReza Sabdar * Allocates the necessary structures for running DAR restore. 29062654012fSReza Sabdar * It just creates the reader writer IPC. 29072654012fSReza Sabdar * This function is called for each entry in the restore entry list. 29082654012fSReza Sabdar * 29092654012fSReza Sabdar * Parameters: 29102654012fSReza Sabdar * session (input) - pointer to the session 29112654012fSReza Sabdar * jname (input) - Job name 29122654012fSReza Sabdar * 29132654012fSReza Sabdar * Returns: 29142654012fSReza Sabdar * 0: on success 29152654012fSReza Sabdar * -1: on error 29162654012fSReza Sabdar */ 29172654012fSReza Sabdar int 29182654012fSReza Sabdar restore_dar_alloc_structs_v3(ndmpd_session_t *session, char *jname) 29192654012fSReza Sabdar { 29202654012fSReza Sabdar long xfer_size; 29212654012fSReza Sabdar ndmp_lbr_params_t *nlp; 29222654012fSReza Sabdar tlm_commands_t *cmds; 29232654012fSReza Sabdar 29242654012fSReza Sabdar nlp = ndmp_get_nlp(session); 29252654012fSReza Sabdar if (!nlp) { 29262654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 29272654012fSReza Sabdar return (-1); 29282654012fSReza Sabdar } 29292654012fSReza Sabdar 29302654012fSReza Sabdar cmds = &nlp->nlp_cmds; 29312654012fSReza Sabdar (void) memset(cmds, 0, sizeof (*cmds)); 29322654012fSReza Sabdar 29332654012fSReza Sabdar xfer_size = ndmp_buffer_get_size(session); 29342654012fSReza Sabdar cmds->tcs_command = tlm_create_reader_writer_ipc(FALSE, xfer_size); 29352654012fSReza Sabdar if (!cmds->tcs_command) { 29362654012fSReza Sabdar tlm_un_ref_job_stats(jname); 29372654012fSReza Sabdar return (-1); 29382654012fSReza Sabdar } 29392654012fSReza Sabdar 29402654012fSReza Sabdar return (0); 29412654012fSReza Sabdar } 29422654012fSReza Sabdar 29432654012fSReza Sabdar 29442654012fSReza Sabdar /* 29452654012fSReza Sabdar * free_dar_structs_v3 29462654012fSReza Sabdar * 29472654012fSReza Sabdar * To free the structures were created by restore_dar_alloc_structs_v3. 29482654012fSReza Sabdar * This funnction is called for each entry in restore entry list. 29492654012fSReza Sabdar * 29502654012fSReza Sabdar * Parameters: 29512654012fSReza Sabdar * session (input) - pointer to the session 29522654012fSReza Sabdar * jname (input) - job name 29532654012fSReza Sabdar * 29542654012fSReza Sabdar * Returns: 29552654012fSReza Sabdar * NONE 29562654012fSReza Sabdar */ 29572654012fSReza Sabdar /*ARGSUSED*/ 29582654012fSReza Sabdar static void 29592654012fSReza Sabdar free_dar_structs_v3(ndmpd_session_t *session, char *jname) 29602654012fSReza Sabdar { 29612654012fSReza Sabdar ndmp_lbr_params_t *nlp; 29622654012fSReza Sabdar tlm_commands_t *cmds; 29632654012fSReza Sabdar 29642654012fSReza Sabdar nlp = ndmp_get_nlp(session); 29652654012fSReza Sabdar if (!nlp) { 29662654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 29672654012fSReza Sabdar return; 29682654012fSReza Sabdar } 29692654012fSReza Sabdar cmds = &nlp->nlp_cmds; 29702654012fSReza Sabdar if (!cmds) { 29712654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "cmds == NULL"); 29722654012fSReza Sabdar return; 29732654012fSReza Sabdar } 29742654012fSReza Sabdar 29752654012fSReza Sabdar if (cmds->tcs_command) { 29762654012fSReza Sabdar if (cmds->tcs_command->tc_buffers != NULL) 29772654012fSReza Sabdar tlm_release_reader_writer_ipc(cmds->tcs_command); 29782654012fSReza Sabdar else 29792654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "BUFFERS == NULL"); 29802654012fSReza Sabdar cmds->tcs_command = NULL; 29812654012fSReza Sabdar } else 29822654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "COMMAND == NULL"); 29832654012fSReza Sabdar } 29842654012fSReza Sabdar 29852654012fSReza Sabdar 29862654012fSReza Sabdar /* 29872654012fSReza Sabdar * ndmp_dar_tar_init_v3 29882654012fSReza Sabdar * 29892654012fSReza Sabdar * Constructor for the DAR restore. Creates job name, allocates structures 29902654012fSReza Sabdar * needed for keeping the statistics, and reports the start of restore action. 29912654012fSReza Sabdar * It is called once for each DAR restore request. 29922654012fSReza Sabdar * 29932654012fSReza Sabdar * Parameters: 29942654012fSReza Sabdar * session (input) - pointer to the session 29952654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 29962654012fSReza Sabdar * 29972654012fSReza Sabdar * Returns: 29982654012fSReza Sabdar * char pointer: on success 29992654012fSReza Sabdar * NULL: on error 30002654012fSReza Sabdar */ 30012654012fSReza Sabdar static char *ndmpd_dar_tar_init_v3(ndmpd_session_t *session, 30022654012fSReza Sabdar ndmp_lbr_params_t *nlp) 30032654012fSReza Sabdar { 30042654012fSReza Sabdar char *jname; 30052654012fSReza Sabdar 30062654012fSReza Sabdar jname = ndmp_malloc(TLM_MAX_BACKUP_JOB_NAME); 30072654012fSReza Sabdar 30082654012fSReza Sabdar if (!jname) 30092654012fSReza Sabdar return (NULL); 30102654012fSReza Sabdar 30112654012fSReza Sabdar (void) ndmp_new_job_name(jname); 30122654012fSReza Sabdar 30132654012fSReza Sabdar if (!nlp) { 30142654012fSReza Sabdar free(jname); 30152654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp == NULL"); 30162654012fSReza Sabdar return (NULL); 30172654012fSReza Sabdar } 30182654012fSReza Sabdar 30192654012fSReza Sabdar nlp->nlp_jstat = tlm_new_job_stats(jname); 30202654012fSReza Sabdar if (!nlp->nlp_jstat) { 30212654012fSReza Sabdar free(jname); 30222654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Creating job stats"); 30232654012fSReza Sabdar return (NULL); 30242654012fSReza Sabdar } 30252654012fSReza Sabdar 30262654012fSReza Sabdar nlp->nlp_jstat->js_start_ltime = time(NULL); 30272654012fSReza Sabdar nlp->nlp_jstat->js_start_time = nlp->nlp_jstat->js_start_ltime; 30282654012fSReza Sabdar 30292654012fSReza Sabdar nlp->nlp_logcallbacks = lbrlog_callbacks_init(session, 30302654012fSReza Sabdar ndmpd_path_restored_v3, NULL, NULL); 30312654012fSReza Sabdar if (!nlp->nlp_logcallbacks) { 30322654012fSReza Sabdar tlm_un_ref_job_stats(jname); 30332654012fSReza Sabdar free(jname); 30342654012fSReza Sabdar return (NULL); 30352654012fSReza Sabdar } 30362654012fSReza Sabdar nlp->nlp_jstat->js_callbacks = (void *)(nlp->nlp_logcallbacks); 30372654012fSReza Sabdar 30382654012fSReza Sabdar nlp->nlp_rsbm = bm_alloc(nlp->nlp_nfiles, 0); 30392654012fSReza Sabdar if (nlp->nlp_rsbm < 0) { 30402654012fSReza Sabdar NDMP_LOG(LOG_ERR, "Out of memory."); 30412654012fSReza Sabdar lbrlog_callbacks_done(nlp->nlp_logcallbacks); 30422654012fSReza Sabdar tlm_un_ref_job_stats(jname); 30432654012fSReza Sabdar free(jname); 30442654012fSReza Sabdar return (NULL); 30452654012fSReza Sabdar } 30462654012fSReza Sabdar 30472654012fSReza Sabdar /* this is used in ndmpd_path_restored_v3() */ 30482654012fSReza Sabdar nlp->nlp_lastidx = -1; 30492654012fSReza Sabdar 30502654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring from %s tape(s).", 30512654012fSReza Sabdar ndmp_data_get_mover_mode(session)); 30522654012fSReza Sabdar 30532654012fSReza Sabdar return (jname); 30542654012fSReza Sabdar } 30552654012fSReza Sabdar 30562654012fSReza Sabdar /* 30572654012fSReza Sabdar * ndmpd_dar_tar_end_v3 30582654012fSReza Sabdar * 30592654012fSReza Sabdar * Deconstructor for the DAR restore. This function is called once per 30602654012fSReza Sabdar * DAR request. It deallocates memories allocated by ndmpd_dar_tar_init_v3. 30612654012fSReza Sabdar * 30622654012fSReza Sabdar * Parameters: 30632654012fSReza Sabdar * session (input) - pointer to the session 30642654012fSReza Sabdar * params (input) - pointer to the parameters structure 30652654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 30662654012fSReza Sabdar * jname(input) - job name 30672654012fSReza Sabdar * 30682654012fSReza Sabdar * Returns: 30692654012fSReza Sabdar * 0: on success 30702654012fSReza Sabdar * -1: on error 30712654012fSReza Sabdar */ 30722654012fSReza Sabdar static int ndmpd_dar_tar_end_v3(ndmpd_session_t *session, 30732654012fSReza Sabdar ndmpd_module_params_t *params, ndmp_lbr_params_t *nlp, char *jname) 30742654012fSReza Sabdar { 30752654012fSReza Sabdar int err = 0; 30762654012fSReza Sabdar 30772654012fSReza Sabdar 30782654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "lastidx %d", nlp->nlp_lastidx); 30792654012fSReza Sabdar 30802654012fSReza Sabdar /* nothing restored. */ 30812654012fSReza Sabdar (void) send_unrecovered_list_v3(params, nlp); 30822654012fSReza Sabdar 30832654012fSReza Sabdar if (nlp->nlp_jstat) { 30842654012fSReza Sabdar nlp->nlp_bytes_total = 30852654012fSReza Sabdar (u_longlong_t)nlp->nlp_jstat->js_bytes_total; 30862654012fSReza Sabdar tlm_un_ref_job_stats(jname); 30872654012fSReza Sabdar nlp->nlp_jstat = NULL; 30882654012fSReza Sabdar } else { 30892654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "JSTAT == NULL"); 30902654012fSReza Sabdar } 30912654012fSReza Sabdar 30922654012fSReza Sabdar if (nlp->nlp_logcallbacks) { 30932654012fSReza Sabdar lbrlog_callbacks_done(nlp->nlp_logcallbacks); 30942654012fSReza Sabdar nlp->nlp_logcallbacks = NULL; 30952654012fSReza Sabdar } else { 30962654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "FH CALLBACKS == NULL"); 30972654012fSReza Sabdar } 30982654012fSReza Sabdar 30992654012fSReza Sabdar if (session->ns_data.dd_abort) { 31002654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring to \"%s\" aborted.", 31012654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : "NULL"); 31022654012fSReza Sabdar err = EINTR; 31032654012fSReza Sabdar } else { 31042654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring to \"%s\" finished. (%d)", 31052654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : 31062654012fSReza Sabdar "NULL", err); 31072654012fSReza Sabdar } 31082654012fSReza Sabdar 31092654012fSReza Sabdar if (session->ns_data.dd_operation == NDMP_DATA_OP_RECOVER) { 31102654012fSReza Sabdar if (nlp->nlp_rsbm < 0) { 31112654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp_rsbm < 0 %d", nlp->nlp_rsbm); 31122654012fSReza Sabdar } else { 31132654012fSReza Sabdar (void) bm_free(nlp->nlp_rsbm); 31142654012fSReza Sabdar nlp->nlp_rsbm = -1; 31152654012fSReza Sabdar } 31162654012fSReza Sabdar } 31172654012fSReza Sabdar 31182654012fSReza Sabdar free(jname); 31192654012fSReza Sabdar 31202654012fSReza Sabdar return (err); 31212654012fSReza Sabdar } 31222654012fSReza Sabdar 31232654012fSReza Sabdar 31242654012fSReza Sabdar /* 31252654012fSReza Sabdar * ndmpd_dar_tar_v3 31262654012fSReza Sabdar * 31272654012fSReza Sabdar * This function is called for each entry in DAR entry list. The window 31282654012fSReza Sabdar * is already located and we should be in the right position to read 31292654012fSReza Sabdar * the data from the tape. 31302654012fSReza Sabdar * For each entry we setup selection list; so that, if the file name from 31312654012fSReza Sabdar * tape is not as the name client asked for, error be returned. 31322654012fSReza Sabdar * 31332654012fSReza Sabdar * Parameters: 31342654012fSReza Sabdar * session (input) - pointer to the session 31352654012fSReza Sabdar * params (input) - pointer to the parameters structure 31362654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 31372654012fSReza Sabdar * jname (input) - job name 31382654012fSReza Sabdar * dar_index(input) - Index of this entry in the restore list 31392654012fSReza Sabdar * 31402654012fSReza Sabdar * Returns: 31412654012fSReza Sabdar * 0: on success 31422654012fSReza Sabdar * -1: on error 31432654012fSReza Sabdar */ 31442654012fSReza Sabdar static int 31452654012fSReza Sabdar ndmpd_dar_tar_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 31462654012fSReza Sabdar ndmp_lbr_params_t *nlp, char *jname, int dar_index) 31472654012fSReza Sabdar { 31482654012fSReza Sabdar char *excl; 31492654012fSReza Sabdar char **sels; 31502654012fSReza Sabdar int flags; 31512654012fSReza Sabdar int err; 31522654012fSReza Sabdar tlm_commands_t *cmds; 31532654012fSReza Sabdar struct rs_name_maker rn; 31542654012fSReza Sabdar int data_addr_type = session->ns_data.dd_data_addr.addr_type; 31552654012fSReza Sabdar ndmp_tar_reader_arg_t arg; 31562654012fSReza Sabdar pthread_t rdtp; 31572654012fSReza Sabdar ndmp_context_t nctx; 31587bc22e45SReza Sabdar mem_ndmp_name_v3_t *ep; 31592654012fSReza Sabdar 31602654012fSReza Sabdar err = 0; 31612654012fSReza Sabdar 31622654012fSReza Sabdar /* 31632654012fSReza Sabdar * We have to allocate and deallocate buffers every time we 31642654012fSReza Sabdar * run the restore, for we need to flush the buffers. 31652654012fSReza Sabdar */ 31662654012fSReza Sabdar if (restore_dar_alloc_structs_v3(session, jname) < 0) 31672654012fSReza Sabdar return (-1); 31682654012fSReza Sabdar 31692654012fSReza Sabdar sels = setupsels(session, params, nlp, dar_index); 31702654012fSReza Sabdar if (!sels) { 31712654012fSReza Sabdar free_dar_structs_v3(session, jname); 31722654012fSReza Sabdar return (-1); 31732654012fSReza Sabdar } 31742654012fSReza Sabdar excl = NULL; 31752654012fSReza Sabdar flags = RSFLG_OVR_ALWAYS; 31762654012fSReza Sabdar rn.rn_nlp = nlp; 31772654012fSReza Sabdar rn.rn_fp = mknewname; 31782654012fSReza Sabdar 31792654012fSReza Sabdar if (!session->ns_data.dd_abort) { 31802654012fSReza Sabdar cmds = &nlp->nlp_cmds; 31812654012fSReza Sabdar cmds->tcs_reader = cmds->tcs_writer = TLM_RESTORE_RUN; 31822654012fSReza Sabdar cmds->tcs_command->tc_reader = TLM_RESTORE_RUN; 31832654012fSReza Sabdar cmds->tcs_command->tc_writer = TLM_RESTORE_RUN; 31842654012fSReza Sabdar 31852654012fSReza Sabdar arg.tr_session = session; 31862654012fSReza Sabdar arg.tr_mod_params = params; 31872654012fSReza Sabdar arg.tr_cmds = cmds; 31882654012fSReza Sabdar 31892654012fSReza Sabdar err = pthread_create(&rdtp, NULL, (funct_t)ndmp_tar_reader, 31902654012fSReza Sabdar (void *)&arg); 31912654012fSReza Sabdar if (err == 0) { 31922654012fSReza Sabdar tlm_cmd_wait(cmds->tcs_command, TLM_TAR_READER); 31932654012fSReza Sabdar } else { 31942654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "launch ndmp_tar_reader: %m"); 31952654012fSReza Sabdar return (-1); 31962654012fSReza Sabdar } 31972654012fSReza Sabdar 31982654012fSReza Sabdar cmds->tcs_command->tc_ref++; 31992654012fSReza Sabdar cmds->tcs_writer_count++; 32002654012fSReza Sabdar 32012654012fSReza Sabdar /* Plug-in module */ 32022654012fSReza Sabdar if (ndmp_pl != NULL && 32032654012fSReza Sabdar ndmp_pl->np_pre_restore != NULL) { 32048c4f9701SJanice Chang (void) memset(&nctx, 0, sizeof (ndmp_context_t)); 32052654012fSReza Sabdar nctx.nc_cmds = cmds; 320642ed7838SReza Sabdar nctx.nc_params = params; 32078c4f9701SJanice Chang nctx.nc_ddata = (void *) session; 32087bc22e45SReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, 32097bc22e45SReza Sabdar dar_index - 1); 32107bc22e45SReza Sabdar 32112654012fSReza Sabdar if ((err = ndmp_pl->np_pre_restore(ndmp_pl, &nctx, 32127bc22e45SReza Sabdar ep->nm3_opath, ep->nm3_dpath)) 32132654012fSReza Sabdar != 0) { 321442ed7838SReza Sabdar NDMP_LOG(LOG_ERR, "Pre-restore plug-in: %m"); 32152654012fSReza Sabdar ndmp_stop_local_reader(session, cmds); 32162654012fSReza Sabdar ndmp_wait_for_reader(cmds); 32172654012fSReza Sabdar (void) pthread_join(rdtp, NULL); 32182654012fSReza Sabdar ndmp_stop_remote_reader(session); 32192654012fSReza Sabdar goto restore_out; 32202654012fSReza Sabdar } 32212654012fSReza Sabdar } 32222654012fSReza Sabdar 32232654012fSReza Sabdar if (tm_tar_ops.tm_getdir != NULL) { 32242efb3bf9SJan Kryl char errbuf[256]; 32252efb3bf9SJan Kryl 32262654012fSReza Sabdar err = (tm_tar_ops.tm_getdir)(cmds, cmds->tcs_command, 32272654012fSReza Sabdar nlp->nlp_jstat, &rn, 1, 1, sels, &excl, flags, 3228fb4eb4e8SReza Sabdar dar_index, nlp->nlp_backup_path, 3229fb4eb4e8SReza Sabdar session->hardlink_q); 32302efb3bf9SJan Kryl /* 32312efb3bf9SJan Kryl * If the fatal error from tm_getdir looks like an 32322efb3bf9SJan Kryl * errno code, we send the error description to DMA. 32332efb3bf9SJan Kryl */ 32342efb3bf9SJan Kryl if (err > 0 && strerror_r(err, errbuf, 32352efb3bf9SJan Kryl sizeof (errbuf)) == 0) { 32362efb3bf9SJan Kryl MOD_LOGV3(params, NDMP_LOG_ERROR, 32372efb3bf9SJan Kryl "Fatal error during the restore: %s\n", 32382efb3bf9SJan Kryl errbuf); 32392efb3bf9SJan Kryl } 32402654012fSReza Sabdar } 32412654012fSReza Sabdar 32422654012fSReza Sabdar cmds->tcs_writer_count--; 32432654012fSReza Sabdar cmds->tcs_command->tc_ref--; 32442654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "stop local reader."); 32452654012fSReza Sabdar ndmp_stop_local_reader(session, cmds); 32462654012fSReza Sabdar 32472654012fSReza Sabdar ndmp_wait_for_reader(cmds); 32482654012fSReza Sabdar (void) pthread_join(rdtp, NULL); 32492654012fSReza Sabdar 32502654012fSReza Sabdar /* 32512654012fSReza Sabdar * If this is the last DAR entry and it is a three-way 32522654012fSReza Sabdar * restore then we should close the connection. 32532654012fSReza Sabdar */ 32542654012fSReza Sabdar if ((data_addr_type == NDMP_ADDR_TCP) && 32552654012fSReza Sabdar (dar_index == (int)session->ns_data.dd_nlist_len)) { 32562654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "stop remote reader."); 32572654012fSReza Sabdar ndmp_stop_remote_reader(session); 32582654012fSReza Sabdar } 32592654012fSReza Sabdar 32602654012fSReza Sabdar /* exit as if there was an internal error */ 32612654012fSReza Sabdar if (session->ns_eof) 32622654012fSReza Sabdar err = -1; 32632654012fSReza Sabdar restore_out: 32642654012fSReza Sabdar /* Plug-in module */ 32652654012fSReza Sabdar if (ndmp_pl != NULL && 32662654012fSReza Sabdar ndmp_pl->np_post_restore != NULL && 32672654012fSReza Sabdar ndmp_pl->np_post_restore(ndmp_pl, &nctx, err) == -1) { 32682654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Post-restore plug-in: %m"); 32692654012fSReza Sabdar err = -1; 32702654012fSReza Sabdar } 32712654012fSReza Sabdar } 32722654012fSReza Sabdar 32732654012fSReza Sabdar NDMP_FREE(sels); 32742654012fSReza Sabdar 32752654012fSReza Sabdar free_dar_structs_v3(session, jname); 32762654012fSReza Sabdar 32772654012fSReza Sabdar return (err); 32782654012fSReza Sabdar } 32792654012fSReza Sabdar 32802654012fSReza Sabdar /* 32812654012fSReza Sabdar * ndmpd_dar_locate_windwos_v3 32822654012fSReza Sabdar * 32832654012fSReza Sabdar * Locating the right window in which the requested file is backed up. 32842654012fSReza Sabdar * We should go through windows to find the exact location, for the 32852654012fSReza Sabdar * file can be located in for example 10th window after the current window. 32862654012fSReza Sabdar * 32872654012fSReza Sabdar * Parameters: 32882654012fSReza Sabdar * session (input) - pointer to the session 32892654012fSReza Sabdar * params (input) - pointer to the parameters structure 32902654012fSReza Sabdar * fh_info (input) - index from the beginning of the backup stream 32912654012fSReza Sabdar * len (input) - Length of the mover window 32922654012fSReza Sabdar * 32932654012fSReza Sabdar * Returns: 32942654012fSReza Sabdar * 0: on success 32952654012fSReza Sabdar * -1: on error 32962654012fSReza Sabdar */ 32977bc22e45SReza Sabdar static int 32987bc22e45SReza Sabdar ndmpd_dar_locate_window_v3(ndmpd_session_t *session, 32997bc22e45SReza Sabdar ndmpd_module_params_t *params, u_longlong_t fh_info, u_longlong_t len) 33002654012fSReza Sabdar { 33012654012fSReza Sabdar int ret = 0; 33022654012fSReza Sabdar 33032654012fSReza Sabdar 33042654012fSReza Sabdar for (; ; ) { 33052654012fSReza Sabdar ret = (*params->mp_seek_func)(session, fh_info, len); 33062654012fSReza Sabdar 33072654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "ret %d", ret); 33082654012fSReza Sabdar if (ret == 0) /* Seek was done successfully */ 33092654012fSReza Sabdar break; 33102654012fSReza Sabdar else if (ret < 0) { 33112654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Seek error"); 33122654012fSReza Sabdar break; 33132654012fSReza Sabdar } 33142654012fSReza Sabdar 33152654012fSReza Sabdar /* 33162654012fSReza Sabdar * DMA moved to a new window. 33172654012fSReza Sabdar * If we are reading the remainig of the file from 33182654012fSReza Sabdar * new window, seek is handled by ndmpd_local_read_v3. 33192654012fSReza Sabdar * Here we should continue the seek inside the new 33202654012fSReza Sabdar * window. 33212654012fSReza Sabdar */ 33222654012fSReza Sabdar continue; 33232654012fSReza Sabdar } 33242654012fSReza Sabdar return (ret); 33252654012fSReza Sabdar } 33262654012fSReza Sabdar 33272654012fSReza Sabdar /* 33282654012fSReza Sabdar * ndmpd_rs_dar_tar_v3 33292654012fSReza Sabdar * 33302654012fSReza Sabdar * Main DAR function. It calls the constructor, then for each entry it 33312654012fSReza Sabdar * calls the locate_window_v3 to find the exact position of the file. Then 33322654012fSReza Sabdar * it restores the file. 33332654012fSReza Sabdar * When all restore requests are done it calls the deconstructor to clean 33342654012fSReza Sabdar * everything up. 33352654012fSReza Sabdar * 33362654012fSReza Sabdar * Parameters: 33372654012fSReza Sabdar * session (input) - pointer to the session 33382654012fSReza Sabdar * params (input) - pointer to the parameters structure 33392654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 33402654012fSReza Sabdar * 33412654012fSReza Sabdar * Returns: 33422654012fSReza Sabdar * 0: on success 33432654012fSReza Sabdar * -1: on error 33442654012fSReza Sabdar */ 33452654012fSReza Sabdar static int 33462654012fSReza Sabdar ndmpd_rs_dar_tar_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 33472654012fSReza Sabdar ndmp_lbr_params_t *nlp) 33482654012fSReza Sabdar { 33492654012fSReza Sabdar mem_ndmp_name_v3_t *ep; 33502654012fSReza Sabdar u_longlong_t len; 33512654012fSReza Sabdar char *jname; 33522654012fSReza Sabdar int n = session->ns_data.dd_nlist_len; 33532654012fSReza Sabdar int i, ret = 0; 33542654012fSReza Sabdar int result = 0; 33552654012fSReza Sabdar 33562654012fSReza Sabdar jname = ndmpd_dar_tar_init_v3(session, nlp); 33572654012fSReza Sabdar 33582654012fSReza Sabdar if (!jname) 33592654012fSReza Sabdar return (-1); 33602654012fSReza Sabdar 33612654012fSReza Sabdar /* 33622654012fSReza Sabdar * We set the length = sizeof (tlm_tar_hdr_t) 33632654012fSReza Sabdar * This is important for three-way DAR restore, for we should 33642654012fSReza Sabdar * read the header first (If we ask for more data then we have 33652654012fSReza Sabdar * to read and discard the remaining data in the socket) 33662654012fSReza Sabdar */ 33672654012fSReza Sabdar len = tlm_tarhdr_size(); 33682654012fSReza Sabdar 33692654012fSReza Sabdar for (i = 0; i < n; ++i) { 33702654012fSReza Sabdar ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i); 33712654012fSReza Sabdar if (!ep) { 33722654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "ep NULL, i %d", i); 33732654012fSReza Sabdar continue; 33742654012fSReza Sabdar } 33752654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 33762654012fSReza Sabdar "restoring opath %s, dpath %s, fh_info %lld", 33772654012fSReza Sabdar ep->nm3_opath ? ep->nm3_opath : "NULL", 33782654012fSReza Sabdar ep->nm3_dpath ? ep->nm3_dpath : "NULL", 33792654012fSReza Sabdar ep->nm3_fh_info); 33802654012fSReza Sabdar 33812654012fSReza Sabdar /* 33822654012fSReza Sabdar * We should seek till finding the window in which file 33832654012fSReza Sabdar * is located. 33842654012fSReza Sabdar */ 33852654012fSReza Sabdar ret = ndmpd_dar_locate_window_v3(session, params, 33862654012fSReza Sabdar ep->nm3_fh_info, len); 33872654012fSReza Sabdar 33882654012fSReza Sabdar if (ret < 0) /* If seek fails, restore should be aborted */ 33892654012fSReza Sabdar break; 33902654012fSReza Sabdar /* 33912654012fSReza Sabdar * We are inside the target window. 33922654012fSReza Sabdar * for each restore we will use one entry as selection list 33932654012fSReza Sabdar */ 33942654012fSReza Sabdar if ((ret = ndmpd_dar_tar_v3(session, params, nlp, jname, i+1)) 33952654012fSReza Sabdar != 0) 33962654012fSReza Sabdar result = EIO; 33972654012fSReza Sabdar ndmpd_audit_restore(session->ns_connection, 33982654012fSReza Sabdar ep->nm3_opath ? ep->nm3_opath : "NULL", 33992654012fSReza Sabdar session->ns_data.dd_data_addr.addr_type, 34002654012fSReza Sabdar session->ns_tape.td_adapter_name, result); 34012654012fSReza Sabdar } 34022654012fSReza Sabdar 34032654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "End of restore list"); 34042654012fSReza Sabdar 34052654012fSReza Sabdar (void) ndmpd_dar_tar_end_v3(session, params, nlp, jname); 34062654012fSReza Sabdar 34072654012fSReza Sabdar return (ret); 34082654012fSReza Sabdar } 34092654012fSReza Sabdar 34102654012fSReza Sabdar /* 34112654012fSReza Sabdar * ndmp_plugin_pre_restore 34122654012fSReza Sabdar * 34132654012fSReza Sabdar * Wrapper for pre-restore callback with multiple path 34142654012fSReza Sabdar */ 34152654012fSReza Sabdar static int 34167bc22e45SReza Sabdar ndmp_plugin_pre_restore(ndmp_context_t *ctxp, ndmpd_module_params_t *params, 34177bc22e45SReza Sabdar int ncount) 34182654012fSReza Sabdar { 34197bc22e45SReza Sabdar mem_ndmp_name_v3_t *ep; 34202654012fSReza Sabdar int err; 34217bc22e45SReza Sabdar int i; 34222654012fSReza Sabdar 34237bc22e45SReza Sabdar for (i = 0; i < ncount; i++) { 34247bc22e45SReza Sabdar if (!(ep = (mem_ndmp_name_v3_t *)MOD_GETNAME(params, i))) 34257bc22e45SReza Sabdar continue; 34262654012fSReza Sabdar if ((err = ndmp_pl->np_pre_restore(ndmp_pl, ctxp, 34277bc22e45SReza Sabdar ep->nm3_opath, ep->nm3_dpath)) != 0) 34282654012fSReza Sabdar return (err); 34292654012fSReza Sabdar } 34307bc22e45SReza Sabdar 34312654012fSReza Sabdar return (0); 34322654012fSReza Sabdar } 34332654012fSReza Sabdar 343442ed7838SReza Sabdar /* 3435fb4eb4e8SReza Sabdar * get_absolute_path 3436fb4eb4e8SReza Sabdar * 3437fb4eb4e8SReza Sabdar * Get resolved path name which does not involve ".", ".." or extra 3438fb4eb4e8SReza Sabdar * "/" or symbolic links. 3439fb4eb4e8SReza Sabdar * 3440fb4eb4e8SReza Sabdar * e.g. 3441fb4eb4e8SReza Sabdar * 3442fb4eb4e8SReza Sabdar * /backup/path/ -> /backup/path 3443fb4eb4e8SReza Sabdar * /backup/path/. -> /backup/path 3444fb4eb4e8SReza Sabdar * /backup/path/../path/ -> /backup/path 3445fb4eb4e8SReza Sabdar * /link-to-backup-path -> /backup/path 3446fb4eb4e8SReza Sabdar * 3447fb4eb4e8SReza Sabdar * Returns: 3448fb4eb4e8SReza Sabdar * Pointer to the new path (allocated) 3449fb4eb4e8SReza Sabdar * NULL if the path doesnt exist 3450fb4eb4e8SReza Sabdar */ 3451fb4eb4e8SReza Sabdar static char * 3452fb4eb4e8SReza Sabdar get_absolute_path(const char *bkpath) 3453fb4eb4e8SReza Sabdar { 3454fb4eb4e8SReza Sabdar char *pbuf; 3455fb4eb4e8SReza Sabdar char *rv; 3456fb4eb4e8SReza Sabdar 3457fb4eb4e8SReza Sabdar if (!(pbuf = ndmp_malloc(TLM_MAX_PATH_NAME))) 3458fb4eb4e8SReza Sabdar return (NULL); 3459fb4eb4e8SReza Sabdar 3460fb4eb4e8SReza Sabdar if ((rv = realpath(bkpath, pbuf)) == NULL) { 3461fb4eb4e8SReza Sabdar NDMP_LOG(LOG_DEBUG, "Invalid path [%s] err=%d", 3462fb4eb4e8SReza Sabdar bkpath, errno); 3463fb4eb4e8SReza Sabdar } 3464fb4eb4e8SReza Sabdar return (rv); 3465fb4eb4e8SReza Sabdar } 3466fb4eb4e8SReza Sabdar 3467fb4eb4e8SReza Sabdar /* 346842ed7838SReza Sabdar * Expands the format string and logs the resulting message to the 346942ed7838SReza Sabdar * remote DMA 347042ed7838SReza Sabdar */ 347142ed7838SReza Sabdar void 347242ed7838SReza Sabdar ndmp_log_dma(ndmp_context_t *nctx, ndmp_log_dma_type_t lt, const char *fmt, ...) 347342ed7838SReza Sabdar { 347442ed7838SReza Sabdar va_list ap; 347542ed7838SReza Sabdar char buf[256]; 347642ed7838SReza Sabdar ndmpd_module_params_t *params; 347742ed7838SReza Sabdar 347842ed7838SReza Sabdar if (nctx == NULL || 347942ed7838SReza Sabdar (params = (ndmpd_module_params_t *)nctx->nc_params) == NULL) 348042ed7838SReza Sabdar return; 348142ed7838SReza Sabdar 348242ed7838SReza Sabdar va_start(ap, fmt); 348342ed7838SReza Sabdar (void) vsnprintf(buf, sizeof (buf), fmt, ap); 348442ed7838SReza Sabdar va_end(ap); 348542ed7838SReza Sabdar 348642ed7838SReza Sabdar MOD_LOGV3(params, (ndmp_log_type)lt, "%s", buf); 348742ed7838SReza Sabdar } 348842ed7838SReza Sabdar 34892654012fSReza Sabdar 34902654012fSReza Sabdar /* 34912654012fSReza Sabdar * ndmpd_rs_sar_tar_v3 34922654012fSReza Sabdar * 34932654012fSReza Sabdar * Main non-DAR restore function. It will try to restore all the entries 34942654012fSReza Sabdar * that have been backed up. 34952654012fSReza Sabdar * 34962654012fSReza Sabdar * Parameters: 34972654012fSReza Sabdar * session (input) - pointer to the session 34982654012fSReza Sabdar * params (input) - pointer to the parameters structure 34992654012fSReza Sabdar * nlp (input) - pointer to the nlp structure 35002654012fSReza Sabdar * 35012654012fSReza Sabdar * Returns: 35022654012fSReza Sabdar * 0: on success 35032654012fSReza Sabdar * -1: on error 35042654012fSReza Sabdar */ 35052654012fSReza Sabdar static int 35062654012fSReza Sabdar ndmpd_rs_sar_tar_v3(ndmpd_session_t *session, ndmpd_module_params_t *params, 35072654012fSReza Sabdar ndmp_lbr_params_t *nlp) 35082654012fSReza Sabdar { 35092654012fSReza Sabdar char jname[TLM_MAX_BACKUP_JOB_NAME]; 35102654012fSReza Sabdar char *excl; 35112654012fSReza Sabdar char **sels; 35122654012fSReza Sabdar int flags; 35132654012fSReza Sabdar int err; 35142654012fSReza Sabdar tlm_commands_t *cmds; 35152654012fSReza Sabdar struct rs_name_maker rn; 35162654012fSReza Sabdar ndmp_tar_reader_arg_t arg; 35172654012fSReza Sabdar pthread_t rdtp; 35182654012fSReza Sabdar int result; 35192654012fSReza Sabdar ndmp_context_t nctx; 35202654012fSReza Sabdar 35212654012fSReza Sabdar result = err = 0; 35222654012fSReza Sabdar (void) ndmp_new_job_name(jname); 35232654012fSReza Sabdar if (restore_alloc_structs_v3(session, jname) < 0) 35242654012fSReza Sabdar return (-1); 35252654012fSReza Sabdar 35262654012fSReza Sabdar sels = setupsels(session, params, nlp, 0); 35272654012fSReza Sabdar if (!sels) { 35282654012fSReza Sabdar free_structs_v3(session, jname); 35292654012fSReza Sabdar return (-1); 35302654012fSReza Sabdar } 35312654012fSReza Sabdar excl = NULL; 35322654012fSReza Sabdar flags = RSFLG_OVR_ALWAYS; 35332654012fSReza Sabdar rn.rn_nlp = nlp; 35342654012fSReza Sabdar rn.rn_fp = mknewname; 35352654012fSReza Sabdar 35362654012fSReza Sabdar nlp->nlp_jstat->js_start_ltime = time(NULL); 35372654012fSReza Sabdar nlp->nlp_jstat->js_start_time = nlp->nlp_jstat->js_start_ltime; 35382654012fSReza Sabdar 35392654012fSReza Sabdar if (!session->ns_data.dd_abort && !session->ns_data.dd_abort) { 35402654012fSReza Sabdar cmds = &nlp->nlp_cmds; 35412654012fSReza Sabdar cmds->tcs_reader = cmds->tcs_writer = TLM_RESTORE_RUN; 35422654012fSReza Sabdar cmds->tcs_command->tc_reader = TLM_RESTORE_RUN; 35432654012fSReza Sabdar cmds->tcs_command->tc_writer = TLM_RESTORE_RUN; 35442654012fSReza Sabdar 35452654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring to \"%s\" started.", 35462654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : "NULL"); 35472654012fSReza Sabdar 35482654012fSReza Sabdar arg.tr_session = session; 35492654012fSReza Sabdar arg.tr_mod_params = params; 35502654012fSReza Sabdar arg.tr_cmds = cmds; 35512654012fSReza Sabdar err = pthread_create(&rdtp, NULL, (funct_t)ndmp_tar_reader, 35522654012fSReza Sabdar (void *)&arg); 35532654012fSReza Sabdar if (err == 0) { 35542654012fSReza Sabdar tlm_cmd_wait(cmds->tcs_command, TLM_TAR_READER); 35552654012fSReza Sabdar } else { 35562654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Launch ndmp_tar_reader: %m"); 35572654012fSReza Sabdar free_structs_v3(session, jname); 35582654012fSReza Sabdar return (-1); 35592654012fSReza Sabdar } 35602654012fSReza Sabdar 35612654012fSReza Sabdar if (!ndmp_check_utf8magic(cmds->tcs_command)) { 35622654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "UTF8Magic not found!"); 35632654012fSReza Sabdar } else { 35642654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "UTF8Magic found"); 35652654012fSReza Sabdar } 35662654012fSReza Sabdar 35672654012fSReza Sabdar /* Plug-in module */ 35682654012fSReza Sabdar if (ndmp_pl != NULL && 35692654012fSReza Sabdar ndmp_pl->np_pre_restore != NULL) { 35708c4f9701SJanice Chang (void) memset(&nctx, 0, sizeof (ndmp_context_t)); 35712654012fSReza Sabdar nctx.nc_cmds = cmds; 357242ed7838SReza Sabdar nctx.nc_params = params; 35738c4f9701SJanice Chang nctx.nc_ddata = (void *) session; 35747bc22e45SReza Sabdar if ((err = ndmp_plugin_pre_restore(&nctx, params, 35757bc22e45SReza Sabdar nlp->nlp_nfiles)) 35762654012fSReza Sabdar != 0) { 357742ed7838SReza Sabdar NDMP_LOG(LOG_ERR, "Pre-restore plug-in: %m"); 35782654012fSReza Sabdar ndmp_stop_local_reader(session, cmds); 35792654012fSReza Sabdar ndmp_wait_for_reader(cmds); 35802654012fSReza Sabdar (void) pthread_join(rdtp, NULL); 35812654012fSReza Sabdar ndmp_stop_remote_reader(session); 35822654012fSReza Sabdar goto restore_out; 35832654012fSReza Sabdar } 35842654012fSReza Sabdar } 35852654012fSReza Sabdar 35862654012fSReza Sabdar cmds->tcs_command->tc_ref++; 35872654012fSReza Sabdar cmds->tcs_writer_count++; 35882654012fSReza Sabdar 35892efb3bf9SJan Kryl if (tm_tar_ops.tm_getdir != NULL) { 35902efb3bf9SJan Kryl char errbuf[256]; 35912efb3bf9SJan Kryl 35922654012fSReza Sabdar err = (tm_tar_ops.tm_getdir)(cmds, cmds->tcs_command, 35932654012fSReza Sabdar nlp->nlp_jstat, &rn, 1, 1, sels, &excl, flags, 0, 3594fb4eb4e8SReza Sabdar nlp->nlp_backup_path, session->hardlink_q); 35952efb3bf9SJan Kryl /* 35962efb3bf9SJan Kryl * If the fatal error from tm_getdir looks like an 35972efb3bf9SJan Kryl * errno code, we send the error description to DMA. 35982efb3bf9SJan Kryl */ 35992efb3bf9SJan Kryl if (err > 0 && strerror_r(err, errbuf, 36002efb3bf9SJan Kryl sizeof (errbuf)) == 0) { 36012efb3bf9SJan Kryl MOD_LOGV3(params, NDMP_LOG_ERROR, 36022efb3bf9SJan Kryl "Fatal error during the restore: %s\n", 36032efb3bf9SJan Kryl errbuf); 36042efb3bf9SJan Kryl } 36052efb3bf9SJan Kryl } 36062654012fSReza Sabdar 36072654012fSReza Sabdar cmds->tcs_writer_count--; 36082654012fSReza Sabdar cmds->tcs_command->tc_ref--; 36092654012fSReza Sabdar nlp->nlp_jstat->js_stop_time = time(NULL); 36102654012fSReza Sabdar 36112654012fSReza Sabdar /* Send the list of un-recovered files/dirs to the client. */ 36122654012fSReza Sabdar (void) send_unrecovered_list_v3(params, nlp); 36132654012fSReza Sabdar 36142654012fSReza Sabdar ndmp_stop_local_reader(session, cmds); 36152654012fSReza Sabdar ndmp_wait_for_reader(cmds); 36162654012fSReza Sabdar (void) pthread_join(rdtp, NULL); 36172654012fSReza Sabdar 36182654012fSReza Sabdar ndmp_stop_remote_reader(session); 36192654012fSReza Sabdar 36202654012fSReza Sabdar /* exit as if there was an internal error */ 36212654012fSReza Sabdar if (session->ns_eof) 36222654012fSReza Sabdar err = -1; 36232654012fSReza Sabdar if (err == -1) 36242654012fSReza Sabdar result = EIO; 36252654012fSReza Sabdar } 36262654012fSReza Sabdar 36272654012fSReza Sabdar (void) send_unrecovered_list_v3(params, nlp); /* nothing restored. */ 36282654012fSReza Sabdar if (session->ns_data.dd_abort) { 36292654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring to \"%s\" aborted.", 36302654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : "NULL"); 36312654012fSReza Sabdar result = EINTR; 36322654012fSReza Sabdar ndmpd_audit_restore(session->ns_connection, 36332654012fSReza Sabdar nlp->nlp_restore_path, 36342654012fSReza Sabdar session->ns_data.dd_data_addr.addr_type, 36352654012fSReza Sabdar session->ns_tape.td_adapter_name, result); 36362654012fSReza Sabdar err = -1; 36372654012fSReza Sabdar } else { 36382654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Restoring to \"%s\" finished. (%d)", 36392654012fSReza Sabdar (nlp->nlp_restore_path) ? nlp->nlp_restore_path : "NULL", 36402654012fSReza Sabdar err); 36412654012fSReza Sabdar ndmpd_audit_restore(session->ns_connection, 36422654012fSReza Sabdar nlp->nlp_restore_path, 36432654012fSReza Sabdar session->ns_data.dd_data_addr.addr_type, 36442654012fSReza Sabdar session->ns_tape.td_adapter_name, result); 36452654012fSReza Sabdar 36462654012fSReza Sabdar restore_out: 36472654012fSReza Sabdar /* Plug-in module */ 36482654012fSReza Sabdar if (ndmp_pl != NULL && 36492654012fSReza Sabdar ndmp_pl->np_post_restore != NULL && 36502654012fSReza Sabdar ndmp_pl->np_post_restore(ndmp_pl, &nctx, err) == -1) { 36512654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "Post-restore plug-in: %m"); 36522654012fSReza Sabdar err = -1; 36532654012fSReza Sabdar } 36542654012fSReza Sabdar } 36552654012fSReza Sabdar 36562654012fSReza Sabdar NDMP_FREE(sels); 36572654012fSReza Sabdar free_structs_v3(session, jname); 36582654012fSReza Sabdar 36592654012fSReza Sabdar return (err); 36602654012fSReza Sabdar } 36612654012fSReza Sabdar 36622654012fSReza Sabdar 36632654012fSReza Sabdar /* 36642654012fSReza Sabdar * ndmp_backup_get_params_v3 36652654012fSReza Sabdar * 36662654012fSReza Sabdar * Get the backup parameters from the NDMP env variables 36672654012fSReza Sabdar * and log them in the system log and as normal messages 36682654012fSReza Sabdar * to the DMA. 36692654012fSReza Sabdar * 36702654012fSReza Sabdar * Parameters: 36712654012fSReza Sabdar * session (input) - pointer to the session 36722654012fSReza Sabdar * params (input) - pointer to the parameters structure 36732654012fSReza Sabdar * 36742654012fSReza Sabdar * Returns: 36752654012fSReza Sabdar * NDMP_NO_ERR: on success 36762654012fSReza Sabdar * != NDMP_NO_ERR: otherwise 36772654012fSReza Sabdar */ 36782654012fSReza Sabdar ndmp_error 36792654012fSReza Sabdar ndmp_backup_get_params_v3(ndmpd_session_t *session, 36802654012fSReza Sabdar ndmpd_module_params_t *params) 36812654012fSReza Sabdar { 36822654012fSReza Sabdar ndmp_lbr_params_t *nlp; 36832654012fSReza Sabdar 36842654012fSReza Sabdar if (!session || !params) 36852654012fSReza Sabdar return (NDMP_ILLEGAL_ARGS_ERR); 36862654012fSReza Sabdar 36872654012fSReza Sabdar nlp = ndmp_get_nlp(session); 36882654012fSReza Sabdar if (!nlp) { 36892654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 36902654012fSReza Sabdar "Internal error: NULL nlp.\n"); 3691a8039bf3SJan Kryl return (NDMP_ILLEGAL_ARGS_ERR); 36922654012fSReza Sabdar } else { 3693a8039bf3SJan Kryl if (!(nlp->nlp_backup_path = get_backup_path_v3(params)) || 3694a8039bf3SJan Kryl !is_valid_backup_dir_v3(params, nlp->nlp_backup_path)) 3695a8039bf3SJan Kryl return (NDMP_ILLEGAL_ARGS_ERR); 36962654012fSReza Sabdar } 36972654012fSReza Sabdar 3698fb4eb4e8SReza Sabdar nlp->nlp_backup_path = get_absolute_path(nlp->nlp_backup_path); 3699fb4eb4e8SReza Sabdar if (!nlp->nlp_backup_path) 3700a8039bf3SJan Kryl return (NDMP_ILLEGAL_ARGS_ERR); 37012654012fSReza Sabdar 37022654012fSReza Sabdar if (fs_is_chkpntvol(nlp->nlp_backup_path) || 37032654012fSReza Sabdar fs_is_rdonly(nlp->nlp_backup_path) || 37042654012fSReza Sabdar !fs_is_chkpnt_enabled(nlp->nlp_backup_path)) 37052654012fSReza Sabdar NLP_SET(nlp, NLPF_CHKPNTED_PATH); 37062654012fSReza Sabdar else 37072654012fSReza Sabdar NLP_UNSET(nlp, NLPF_CHKPNTED_PATH); 37082654012fSReza Sabdar 37092654012fSReza Sabdar /* Should the st_ctime be ignored when backing up? */ 37102654012fSReza Sabdar if (ndmp_ignore_ctime) { 37112654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "ignoring st_ctime"); 37122654012fSReza Sabdar NLP_SET(nlp, NLPF_IGNCTIME); 37132654012fSReza Sabdar } else { 37142654012fSReza Sabdar NLP_UNSET(nlp, NLPF_IGNCTIME); 37152654012fSReza Sabdar } 37162654012fSReza Sabdar 37172654012fSReza Sabdar if (ndmp_include_lmtime == TRUE) { 37182654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "including st_lmtime"); 37192654012fSReza Sabdar NLP_SET(nlp, NLPF_INCLMTIME); 37202654012fSReza Sabdar } else { 37212654012fSReza Sabdar NLP_UNSET(nlp, NLPF_INCLMTIME); 37222654012fSReza Sabdar } 37232654012fSReza Sabdar 37242654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "flags %x", nlp->nlp_flags); 37252654012fSReza Sabdar 37262654012fSReza Sabdar get_hist_env_v3(params, nlp); 37272654012fSReza Sabdar get_exc_env_v3(params, nlp); 37282654012fSReza Sabdar get_inc_env_v3(params, nlp); 37292654012fSReza Sabdar get_direct_env_v3(params, nlp); 3730a8039bf3SJan Kryl return (get_backup_level_v3(params, nlp)); 37312654012fSReza Sabdar } 37322654012fSReza Sabdar 37332654012fSReza Sabdar 37342654012fSReza Sabdar /* 37352654012fSReza Sabdar * ndmpd_tar_backup_starter_v3 37362654012fSReza Sabdar * 37372654012fSReza Sabdar * Create the checkpoint for the backup and do the backup, 37382654012fSReza Sabdar * then remove the backup checkpoint if we created it. 37392654012fSReza Sabdar * Save the backup time information based on the backup 37402654012fSReza Sabdar * type and stop the data server. 37412654012fSReza Sabdar * 37422654012fSReza Sabdar * Parameters: 37432654012fSReza Sabdar * params (input) - pointer to the parameters structure 37442654012fSReza Sabdar * 37452654012fSReza Sabdar * Returns: 37462654012fSReza Sabdar * 0: on success 37472654012fSReza Sabdar * != 0: otherwise 37482654012fSReza Sabdar */ 37492654012fSReza Sabdar int 37508c4f9701SJanice Chang ndmpd_tar_backup_starter_v3(void *arg) 37512654012fSReza Sabdar { 37528c4f9701SJanice Chang ndmpd_module_params_t *params = arg; 37532654012fSReza Sabdar int err; 37542654012fSReza Sabdar ndmpd_session_t *session; 37552654012fSReza Sabdar ndmp_lbr_params_t *nlp; 37562654012fSReza Sabdar char jname[TLM_MAX_BACKUP_JOB_NAME]; 3757416eec61SReza Sabdar ndmp_bkup_size_arg_t sarg; 3758416eec61SReza Sabdar pthread_t tid; 37592654012fSReza Sabdar 37602654012fSReza Sabdar session = (ndmpd_session_t *)(params->mp_daemon_cookie); 37612654012fSReza Sabdar *(params->mp_module_cookie) = nlp = ndmp_get_nlp(session); 37622654012fSReza Sabdar ndmp_session_ref(session); 37632654012fSReza Sabdar (void) ndmp_new_job_name(jname); 37642654012fSReza Sabdar 37652654012fSReza Sabdar err = 0; 37662654012fSReza Sabdar if (!NLP_ISCHKPNTED(nlp) && 3767876b86efSReza Sabdar ndmp_create_snapshot(nlp->nlp_backup_path, jname) < 0) { 37682654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_ERROR, 37692654012fSReza Sabdar "Creating checkpoint on \"%s\".\n", 37702654012fSReza Sabdar nlp->nlp_backup_path); 37712654012fSReza Sabdar err = -1; 37722654012fSReza Sabdar } 37732654012fSReza Sabdar 37742654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "err %d, chkpnted %c", 37752654012fSReza Sabdar err, NDMP_YORN(NLP_ISCHKPNTED(nlp))); 37762654012fSReza Sabdar 37772654012fSReza Sabdar if (err == 0) { 3778416eec61SReza Sabdar sarg.bs_session = session; 3779416eec61SReza Sabdar sarg.bs_jname = jname; 3780416eec61SReza Sabdar sarg.bs_path = nlp->nlp_backup_path; 3781416eec61SReza Sabdar 3782416eec61SReza Sabdar /* Get an estimate of the data size */ 3783416eec61SReza Sabdar if (pthread_create(&tid, NULL, (funct_t)get_backup_size, 3784416eec61SReza Sabdar (void *)&sarg) == 0) 3785416eec61SReza Sabdar (void) pthread_detach(tid); 3786416eec61SReza Sabdar 37872654012fSReza Sabdar err = ndmp_get_cur_bk_time(nlp, &nlp->nlp_cdate, jname); 37882654012fSReza Sabdar if (err != 0) { 37892654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "err %d", err); 37902654012fSReza Sabdar } else { 37912654012fSReza Sabdar log_bk_params_v3(session, params, nlp); 37922654012fSReza Sabdar err = tar_backup_v3(session, params, nlp, jname); 37932654012fSReza Sabdar } 37942654012fSReza Sabdar } 37952654012fSReza Sabdar 37962654012fSReza Sabdar if (!NLP_ISCHKPNTED(nlp)) 3797876b86efSReza Sabdar (void) ndmp_remove_snapshot(nlp->nlp_backup_path, jname); 37982654012fSReza Sabdar 37992654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "err %d, update %c", 38002654012fSReza Sabdar err, NDMP_YORN(NLP_SHOULD_UPDATE(nlp))); 38012654012fSReza Sabdar 38022654012fSReza Sabdar if (err == 0) 38032654012fSReza Sabdar save_backup_date_v3(params, nlp); 38042654012fSReza Sabdar 38052654012fSReza Sabdar MOD_DONE(params, err); 38062654012fSReza Sabdar 38072654012fSReza Sabdar /* nlp_params is allocated in start_backup_v3() */ 38082654012fSReza Sabdar NDMP_FREE(nlp->nlp_params); 3809fb4eb4e8SReza Sabdar NDMP_FREE(nlp->nlp_backup_path); 38102654012fSReza Sabdar 38112654012fSReza Sabdar NS_DEC(nbk); 38122654012fSReza Sabdar ndmp_session_unref(session); 38132654012fSReza Sabdar return (err); 38142654012fSReza Sabdar 38152654012fSReza Sabdar } 38162654012fSReza Sabdar 38172654012fSReza Sabdar 38182654012fSReza Sabdar /* 38192654012fSReza Sabdar * ndmpd_tar_backup_abort_v3 38202654012fSReza Sabdar * 38212654012fSReza Sabdar * Abort the backup operation and stop the reader thread. 38222654012fSReza Sabdar * 38232654012fSReza Sabdar * Parameters: 38242654012fSReza Sabdar * module_cookie (input) - pointer to the nlp structure 38252654012fSReza Sabdar * 38262654012fSReza Sabdar * Returns: 38272654012fSReza Sabdar * 0: always 38282654012fSReza Sabdar */ 38292654012fSReza Sabdar int 38302654012fSReza Sabdar ndmpd_tar_backup_abort_v3(void *module_cookie) 38312654012fSReza Sabdar { 38322654012fSReza Sabdar ndmp_lbr_params_t *nlp; 38332654012fSReza Sabdar 38342654012fSReza Sabdar nlp = (ndmp_lbr_params_t *)module_cookie; 38352654012fSReza Sabdar if (nlp && nlp->nlp_session) { 38362654012fSReza Sabdar if (nlp->nlp_session->ns_data.dd_data_addr.addr_type == 38372654012fSReza Sabdar NDMP_ADDR_TCP && 38382654012fSReza Sabdar nlp->nlp_session->ns_data.dd_sock != -1) { 38392654012fSReza Sabdar (void) close(nlp->nlp_session->ns_data.dd_sock); 38402654012fSReza Sabdar nlp->nlp_session->ns_data.dd_sock = -1; 38412654012fSReza Sabdar } 38422654012fSReza Sabdar ndmp_stop_reader_thread(nlp->nlp_session); 38432654012fSReza Sabdar } 38442654012fSReza Sabdar 38452654012fSReza Sabdar return (0); 38462654012fSReza Sabdar } 38472654012fSReza Sabdar 38482654012fSReza Sabdar 38492654012fSReza Sabdar /* 38502654012fSReza Sabdar * ndmp_restore_get_params_v3 38512654012fSReza Sabdar * 38522654012fSReza Sabdar * Get the parameters specified for recovery such as restore path, type 38532654012fSReza Sabdar * of restore (DAR, non-DAR) etc 38542654012fSReza Sabdar * 38552654012fSReza Sabdar * Parameters: 38562654012fSReza Sabdar * session (input) - pointer to the session 38572654012fSReza Sabdar * params (input) - pointer to the parameters structure 38582654012fSReza Sabdar * 38592654012fSReza Sabdar * Returns: 38602654012fSReza Sabdar * NDMP_NO_ERR: on success 38612654012fSReza Sabdar * != NDMP_NO_ERR: otherwise 38622654012fSReza Sabdar */ 38632654012fSReza Sabdar ndmp_error 38642654012fSReza Sabdar ndmp_restore_get_params_v3(ndmpd_session_t *session, 38652654012fSReza Sabdar ndmpd_module_params_t *params) 38662654012fSReza Sabdar { 38672654012fSReza Sabdar ndmp_error rv; 38682654012fSReza Sabdar ndmp_lbr_params_t *nlp; 38692654012fSReza Sabdar 38702654012fSReza Sabdar if (!(nlp = ndmp_get_nlp(session))) { 38712654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nlp is NULL"); 38722654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 38738c4f9701SJanice Chang } else if (!(nlp->nlp_backup_path = get_backup_path_v3(params))) 38742654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 38752654012fSReza Sabdar else if ((nlp->nlp_nfiles = session->ns_data.dd_nlist_len) == 0) { 38762654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "nfiles: %d", nlp->nlp_nfiles); 38772654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 38782654012fSReza Sabdar } else if (get_rs_path_v3(params, nlp) != NDMP_NO_ERR) { 38792654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 38802654012fSReza Sabdar } else if ((rv = fix_nlist_v3(session, params, nlp)) != NDMP_NO_ERR) { 38812654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, "fix_nlist_v3: %d", rv); 38822654012fSReza Sabdar } else { 38832654012fSReza Sabdar rv = NDMP_NO_ERR; 38842654012fSReza Sabdar get_direct_env_v3(params, nlp); 38852654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_DIRECT)) { 38862654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_RECURSIVE)) { 38872654012fSReza Sabdar /* Currently we dont support DAR on directory */ 38882654012fSReza Sabdar NDMP_LOG(LOG_DEBUG, 38892654012fSReza Sabdar "Can't have RECURSIVE and DIRECT together"); 38902654012fSReza Sabdar rv = NDMP_ILLEGAL_ARGS_ERR; 38912654012fSReza Sabdar return (rv); 38922654012fSReza Sabdar } 38932654012fSReza Sabdar 38942654012fSReza Sabdar /* 38952654012fSReza Sabdar * DAR can be done if all the fh_info's are valid. 38962654012fSReza Sabdar */ 38972654012fSReza Sabdar if (allvalidfh(session, params)) { 38982654012fSReza Sabdar ndmp_sort_nlist_v3(session); 38992654012fSReza Sabdar } else { 39002654012fSReza Sabdar MOD_LOGV3(params, NDMP_LOG_WARNING, 39012654012fSReza Sabdar "Cannot do direct access recovery. " 39022654012fSReza Sabdar "Some 'fh_info'es are not valid.\n"); 39032654012fSReza Sabdar NLP_UNSET(nlp, NLPF_DIRECT); 39042654012fSReza Sabdar } 39052654012fSReza Sabdar } 39062654012fSReza Sabdar 39072654012fSReza Sabdar log_rs_params_v3(session, params, nlp); 39082654012fSReza Sabdar } 39092654012fSReza Sabdar 39102654012fSReza Sabdar return (rv); 39112654012fSReza Sabdar } 39122654012fSReza Sabdar 39132654012fSReza Sabdar 39142654012fSReza Sabdar /* 39152654012fSReza Sabdar * ndmpd_tar_restore_starter_v3 39162654012fSReza Sabdar * 39172654012fSReza Sabdar * The main restore starter function. It will start a DAR or 39182654012fSReza Sabdar * non-DAR recovery based on the parameters. (V3 and V4 only) 39192654012fSReza Sabdar * 39202654012fSReza Sabdar * Parameters: 39212654012fSReza Sabdar * params (input) - pointer to the parameters structure 39222654012fSReza Sabdar * 39232654012fSReza Sabdar * Returns: 39242654012fSReza Sabdar * NDMP_NO_ERR: on success 39252654012fSReza Sabdar * != NDMP_NO_ERR: otherwise 39262654012fSReza Sabdar */ 39272654012fSReza Sabdar int 39288c4f9701SJanice Chang ndmpd_tar_restore_starter_v3(void *arg) 39292654012fSReza Sabdar { 39308c4f9701SJanice Chang ndmpd_module_params_t *params = arg; 39312654012fSReza Sabdar int err; 39322654012fSReza Sabdar ndmpd_session_t *session; 39332654012fSReza Sabdar ndmp_lbr_params_t *nlp; 39342654012fSReza Sabdar 39352654012fSReza Sabdar 39362654012fSReza Sabdar session = (ndmpd_session_t *)(params->mp_daemon_cookie); 39372654012fSReza Sabdar *(params->mp_module_cookie) = nlp = ndmp_get_nlp(session); 39382654012fSReza Sabdar ndmp_session_ref(session); 39392654012fSReza Sabdar 39402654012fSReza Sabdar if (NLP_ISSET(nlp, NLPF_DIRECT)) 39412654012fSReza Sabdar err = ndmpd_rs_dar_tar_v3(session, params, nlp); 39422654012fSReza Sabdar else 39432654012fSReza Sabdar err = ndmpd_rs_sar_tar_v3(session, params, nlp); 39442654012fSReza Sabdar 39452654012fSReza Sabdar MOD_DONE(params, err); 39462654012fSReza Sabdar 39472654012fSReza Sabdar NS_DEC(nrs); 39482654012fSReza Sabdar /* nlp_params is allocated in start_recover() */ 39492654012fSReza Sabdar NDMP_FREE(nlp->nlp_params); 39502654012fSReza Sabdar ndmp_session_unref(session); 39512654012fSReza Sabdar return (err); 39522654012fSReza Sabdar 39532654012fSReza Sabdar } 39542654012fSReza Sabdar 39552654012fSReza Sabdar /* 39562654012fSReza Sabdar * ndmp_tar_restore_abort_v3 39572654012fSReza Sabdar * 39582654012fSReza Sabdar * Restore abort function (V3 and V4 only) 39592654012fSReza Sabdar * 39602654012fSReza Sabdar * Parameters: 39612654012fSReza Sabdar * module_cookie (input) - pointer to nlp 39622654012fSReza Sabdar * 39632654012fSReza Sabdar * Returns: 39642654012fSReza Sabdar * 0 39652654012fSReza Sabdar */ 39662654012fSReza Sabdar int 39672654012fSReza Sabdar ndmpd_tar_restore_abort_v3(void *module_cookie) 39682654012fSReza Sabdar { 39692654012fSReza Sabdar ndmp_lbr_params_t *nlp; 39702654012fSReza Sabdar 39712654012fSReza Sabdar nlp = (ndmp_lbr_params_t *)module_cookie; 39722654012fSReza Sabdar if (nlp != NULL && nlp->nlp_session != NULL) { 39732654012fSReza Sabdar if (nlp->nlp_session->ns_data.dd_mover.addr_type == 39742654012fSReza Sabdar NDMP_ADDR_TCP && 39752654012fSReza Sabdar nlp->nlp_session->ns_data.dd_sock != -1) { 39762654012fSReza Sabdar (void) close(nlp->nlp_session->ns_data.dd_sock); 39772654012fSReza Sabdar nlp->nlp_session->ns_data.dd_sock = -1; 39782654012fSReza Sabdar } 39792654012fSReza Sabdar ndmp_stop_writer_thread(nlp->nlp_session); 39802654012fSReza Sabdar } 39812654012fSReza Sabdar 39822654012fSReza Sabdar return (0); 39832654012fSReza Sabdar } 3984