⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 amrecover.c

📁 开源备份软件源码 AMANDA, the Advanced Maryland Automatic Network Disk Archiver, is a backup system that a
💻 C
📖 第 1 页 / 共 2 页
字号:
/* * Amanda, The Advanced Maryland Automatic Network Disk Archiver * Copyright (c) 1991-1998, 2000 University of Maryland at College Park * All Rights Reserved. * * Permission to use, copy, modify, distribute, and sell this software and its * documentation for any purpose is hereby granted without fee, provided that * the above copyright notice appear in all copies and that both that * copyright notice and this permission notice appear in supporting * documentation, and that the name of U.M. not be used in advertising or * publicity pertaining to distribution of the software without specific, * written prior permission.  U.M. makes no representations about the * suitability of this software for any purpose.  It is provided "as is" * without express or implied warranty. * * U.M. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL U.M. * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Authors: the Amanda Development Team.  Its members are listed in a * file named AUTHORS, in the root directory of this distribution. *//* * $Id: amrecover.c,v 1.73 2006/07/25 18:27:57 martinea Exp $ * * an interactive program for recovering backed-up files */#include "amanda.h"#include "version.h"#include "stream.h"#include "amfeatures.h"#include "amrecover.h"#include "getfsent.h"#include "dgram.h"#include "util.h"#include "conffile.h"#include "protocol.h"#include "event.h"#include "security.h"#define amrecover_debug(i, ...) do {	\	if ((i) <= debug_amrecover) {	\	    dbprintf(__VA_ARGS__);	\	}				\} while (0)extern int process_line(char *line);int get_line(void);int grab_reply(int show);void sigint_handler(int signum);int main(int argc, char **argv);#define USAGE _("Usage: amrecover [[-C] <config>] [-s <index-server>] [-t <tape-server>] [-d <tape-device>] [-o <clientconfigoption>]*\n")char *server_name = NULL;int server_socket;char *server_line = NULL;char *dump_datestamp = NULL;		/* date we are restoring */char *dump_hostname;			/* which machine we are restoring */char *disk_name = NULL;			/* disk we are restoring */char *mount_point = NULL;		/* where disk was mounted */char *disk_path = NULL;			/* path relative to mount point */char dump_date[STR_SIZE];		/* date on which we are restoring */int quit_prog;				/* set when time to exit parser */char *tape_server_name = NULL;int tape_server_socket;char *tape_device_name = NULL;am_feature_t *our_features = NULL;char *our_features_string = NULL;am_feature_t *indexsrv_features = NULL;am_feature_t *tapesrv_features = NULL;static char *errstr = NULL;char *authopt;int amindexd_alive = 0;static struct {    const char *name;    security_stream_t *fd;} streams[] = {#define MESGFD  0    { "MESG", NULL },};#define NSTREAMS        (int)(sizeof(streams) / sizeof(streams[0]))static void amindexd_response(void *, pkt_t *, security_handle_t *);void stop_amindexd(void);char *amindexd_client_get_security_conf(char *, void *);static char* mesg_buffer = NULL;/* gets a "line" from server and put in server_line *//* server_line is terminated with \0, \r\n is striped *//* returns -1 if error */intget_line(void){    ssize_t size;    char *newbuf, *s;    void *buf;    if (!mesg_buffer)	mesg_buffer = stralloc("");     while (!strstr(mesg_buffer,"\r\n")) {	buf = NULL;	size = security_stream_read_sync(streams[MESGFD].fd, &buf);	if(size < 0) {	    amrecover_debug(1, "amrecover: get_line size < 0 (%zd)\n", size);	    return -1;	}	else if(size == 0) {	    amrecover_debug(1, "amrecover: get_line size == 0 (%zd)\n", size);	    return -1;	}	else if (buf == NULL) {	    amrecover_debug(1, "amrecover: get_line buf == NULL\n");	    return -1;	}        amrecover_debug(1, "amrecover: get_line size = %zd\n", size);	newbuf = alloc(strlen(mesg_buffer)+size+1);	strncpy(newbuf, mesg_buffer, (size_t)(strlen(mesg_buffer) + size));	memcpy(newbuf+strlen(mesg_buffer), buf, (size_t)size);	newbuf[strlen(mesg_buffer)+size] = '\0';	amfree(mesg_buffer);	mesg_buffer = newbuf;    }    s = strstr(mesg_buffer,"\r\n");    *s = '\0';    newbuf = stralloc(s+2);    server_line = newstralloc(server_line, mesg_buffer);    amfree(mesg_buffer);    mesg_buffer = newbuf;    return 0;}/* get reply from server and print to screen *//* handle multi-line reply *//* return -1 if error *//* return code returned by server always occupies first 3 bytes of global   variable server_line */intgrab_reply(    int show){    do {	if (get_line() == -1) {	    return -1;	}	if(show) puts(server_line);    } while (server_line[3] == '-');    if(show) fflush(stdout);    return 0;}/* get 1 line of reply *//* returns -1 if error, 0 if last (or only) line, 1 if more to follow */intget_reply_line(void){    if (get_line() == -1)	return -1;    return server_line[3] == '-';}/* returns pointer to returned line */char *reply_line(void){    return server_line;}/* returns 0 if server returned an error code (ie code starting with 5)   and non-zero otherwise */intserver_happy(void){    return server_line[0] != '5';}intsend_command(    char *	cmd){    /*     * NOTE: this routine is called from sigint_handler, so we must be     * **very** careful about what we do since there is no way to know     * our state at the time the interrupt happened.  For instance,     * do not use any stdio or malloc routines here.     */    char *buffer;    buffer = alloc(strlen(cmd)+3);    strncpy(buffer, cmd, strlen(cmd));    buffer[strlen(cmd)] = '\r';    buffer[strlen(cmd)+1] = '\n';    buffer[strlen(cmd)+2] = '\0';    if(security_stream_write(streams[MESGFD].fd, buffer, strlen(buffer)) < 0) {	return -1;    }    amfree(buffer);    return (0);}/* send a command to the server, get reply and print to screen */intconverse(    char *	cmd){    if (send_command(cmd) == -1) return -1;    if (grab_reply(1) == -1) return -1;    return 0;}/* same as converse() but reply not echoed to stdout */intexchange(    char *	cmd){    if (send_command(cmd) == -1) return -1;    if (grab_reply(0) == -1) return -1;    return 0;}/* basic interrupt handler for when user presses ^C *//* Bale out, letting server know before doing so */voidsigint_handler(    int	signum){    /*     * NOTE: we must be **very** careful about what we do here since there     * is no way to know our state at the time the interrupt happened.     * For instance, do not use any stdio routines here or in any called     * routines.  Also, use _exit() instead of exit() to make sure stdio     * buffer flushing is not attempted.     */    (void)signum;	/* Quiet unused parameter warning */    if (extract_restore_child_pid != -1)	(void)kill(extract_restore_child_pid, SIGKILL);    extract_restore_child_pid = -1;    if(amindexd_alive) 	(void)send_command("QUIT");    _exit(1);}voidclean_pathname(    char *	s){    size_t length;    length = strlen(s);    /* remove "/" at end of path */    if(length>1 && s[length-1]=='/')	s[length-1]='\0';    /* change "/." to "/" */    if(strcmp(s,"/.")==0)	s[1]='\0';    /* remove "/." at end of path */    if(strcmp(&(s[length-2]),"/.")==0)	s[length-2]='\0';}voidquit(void){    quit_prog = 1;    (void)converse("QUIT");    stop_amindexd();}char *localhost = NULL;#ifdef DEFAULT_TAPE_SERVER# define DEFAULT_TAPE_SERVER_FAILOVER (DEFAULT_TAPE_SERVER)#else# define DEFAULT_TAPE_SERVER_FAILOVER (NULL)#endifintmain(    int		argc,    char **	argv){    int i;    time_t timer;    char *lineread = NULL;    struct sigaction act, oact;    extern char *optarg;    extern int optind;    char *line = NULL;    const security_driver_t *secdrv;    char *req = NULL;    int response_error;    struct tm *tm;    config_overwrites_t *cfg_ovr;    /*     * Configure program for internationalization:     *   1) Only set the message locale for now.     *   2) Set textdomain for all amanda related programs to "amanda"     *      We don't want to be forced to support dozens of message catalogs.     */      setlocale(LC_MESSAGES, "C");    textdomain("amanda");     safe_fd(-1, 0);    set_pname("amrecover");    /* Don't die when child closes pipe */    signal(SIGPIPE, SIG_IGN);    dbopen(DBG_SUBDIR_CLIENT);    localhost = alloc(MAX_HOSTNAME_LENGTH+1);    if (gethostname(localhost, MAX_HOSTNAME_LENGTH) != 0) {	error(_("cannot determine local host name\n"));	/*NOTREACHED*/    }    localhost[MAX_HOSTNAME_LENGTH] = '\0';    /* load the base client configuration */    config_init(CONFIG_INIT_CLIENT, NULL);    /* treat amrecover-specific command line options as the equivalent     * -o command-line options to set configuration values */    cfg_ovr = new_config_overwrites(argc/2);    /* If the first argument is not an option flag, then we assume     * it is a configuration name to match the syntax of the other     * Amanda utilities. */    if (argc > 1 && argv[1][0] != '-') {	add_config_overwrite(cfg_ovr, "conf", argv[1]);	/* remove that option from the command line */	argv[1] = argv[0];	argv++; argc--;    }    /* now parse regular command-line '-' options */    while ((i = getopt(argc, argv, "o:C:s:t:d:U")) != EOF) {	switch (i) {	    case 'C':		add_config_overwrite(cfg_ovr, "conf", optarg);		break;	    case 's':		add_config_overwrite(cfg_ovr, "index_server", optarg);		break;	    case 't':		add_config_overwrite(cfg_ovr, "tape_server", optarg);		break;	    case 'd':		add_config_overwrite(cfg_ovr, "tapedev", optarg);		break;	    case 'o':		add_config_overwrite_opt(cfg_ovr, optarg);		break;	    case 'U':	    case '?':		(void)g_printf(USAGE);		return 0;	}    }    if (optind != argc) {	(void)g_fprintf(stderr, USAGE);	exit(1);    }    /* and now try to load the configuration named in that file */    apply_config_overwrites(cfg_ovr);    config_init(CONFIG_INIT_CLIENT | CONFIG_INIT_EXPLICIT_NAME | CONFIG_INIT_OVERLAY,		getconf_str(CNF_CONF));    check_running_as(RUNNING_AS_ROOT);    dbrename(config_name, DBG_SUBDIR_CLIENT);    our_features = am_init_feature_set();    our_features_string = am_feature_to_string(our_features);    server_name = NULL;    if (getconf_seen(CNF_INDEX_SERVER) == -2) { /* command line argument */	server_name = getconf_str(CNF_INDEX_SERVER);    }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -