📄 infofile.c
字号:
/* * Amanda, The Advanced Maryland Automatic Network Disk Archiver * Copyright (c) 1991-1998 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. * * Author: James da Silva, Systems Design and Analysis Group * Computer Science Department * University of Maryland at College Park *//* * $Id: infofile.c,v 1.64 2006/07/25 18:18:48 martinea Exp $ * * manage current info file */#include "amanda.h"#include "conffile.h"#include "infofile.h"#include "token.h"static void zero_info(info_t *); static char *infodir = (char *)0; static char *infofile = (char *)0; static char *newinfofile; static int writing; static FILE *open_txinfofile(char *, char *, char *); static int close_txinfofile(FILE *); static int read_txinfofile(FILE *, info_t *); static int write_txinfofile(FILE *, info_t *); static int delete_txinfofile(char *, char *);static FILE *open_txinfofile( char * host, char * disk, char * mode){ FILE *infof; char *myhost; char *mydisk; assert(infofile == (char *)0); writing = (*mode == 'w'); myhost = sanitise_filename(host); mydisk = sanitise_filename(disk); infofile = vstralloc(infodir, "/", myhost, "/", mydisk, "/info", NULL); amfree(myhost); amfree(mydisk); /* create the directory structure if in write mode */ if (writing) { if (mkpdir(infofile, 0755, (uid_t)-1, (gid_t)-1) == -1) { amfree(infofile); return NULL; } } newinfofile = stralloc2(infofile, ".new"); if(writing) { infof = fopen(newinfofile, mode); if(infof != NULL) amflock(fileno(infof), "info"); } else { infof = fopen(infofile, mode); /* no need to lock readers */ } if(infof == (FILE *)0) { amfree(infofile); amfree(newinfofile); return NULL; } return infof;}static intclose_txinfofile( FILE *infof){ int rc = 0; assert(infofile != (char *)0); if(writing) { rc = rename(newinfofile, infofile); amfunlock(fileno(infof), "info"); } amfree(infofile); amfree(newinfofile); rc = rc || fclose(infof); infof = NULL; if (rc) rc = -1; return rc;}/* XXX - code assumes AVG_COUNT == 3 */static intread_txinfofile( FILE * infof, info_t * info){ char *line = NULL; int version; int rc; perf_t *pp; char *s; int ch; int nb_history; int i; /* get version: command: lines */ while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, _("version: %d"), &version); amfree(line); if(rc != 1) return -2; while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, _("command: %u"), &info->command); amfree(line); if(rc != 1) return -2; /* get rate: and comp: lines for full dumps */ pp = &info->full; while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, "full-rate: %lf %lf %lf", &pp->rate[0], &pp->rate[1], &pp->rate[2]); amfree(line); if(rc > 3) return -2; while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, "full-comp: %lf %lf %lf", &pp->comp[0], &pp->comp[1], &pp->comp[2]); amfree(line); if(rc > 3) return -2; /* get rate: and comp: lines for incr dumps */ pp = &info->incr; while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, "incr-rate: %lf %lf %lf", &pp->rate[0], &pp->rate[1], &pp->rate[2]); amfree(line); if(rc > 3) return -2; while ((line = agets(infof)) != NULL) { if (line[0] != '\0') break; amfree(line); } if (line == NULL) return -1; rc = sscanf(line, "incr-comp: %lf %lf %lf", &pp->comp[0], &pp->comp[1], &pp->comp[2]); amfree(line); if(rc > 3) return -2; /* get stats for dump levels */ for(rc = -2; (line = agets(infof)) != NULL; free(line)) { stats_t onestat; /* one stat record */ int level = 0; long long off_t_tmp; intmax_t time_t_tmp; if (line[0] == '\0') continue; if(line[0] == '/' && line[1] == '/') { rc = 0; amfree(line); return 0; /* normal end of record */ } else if (strncmp_const(line,"last_level:") == 0) { break; /* normal */ } else if (strncmp_const(line,"history:") == 0) { break; /* normal */ } memset(&onestat, 0, SIZEOF(onestat)); s = line; ch = *s++; if(strncmp_const_skip(line, "stats:", s, ch) != 0) { break; } skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%d", &level) != 1) { break; } skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%lld", &off_t_tmp) != 1) { break; } onestat.size = (off_t)off_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%lld", &off_t_tmp) != 1) { break; } onestat.csize = (off_t)off_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%jd", &time_t_tmp) != 1) { break; } onestat.secs = (time_t)time_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%jd", &time_t_tmp) != 1) { break; } onestat.date = (time_t)time_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch != '\0') { if(sscanf((s - 1), "%lld", &off_t_tmp) != 1) { break; } onestat.filenum = (off_t)off_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0') { break; } strncpy(onestat.label, s-1, SIZEOF(onestat.label)-1); onestat.label[SIZEOF(onestat.label)-1] = '\0'; } if(level < 0 || level > DUMP_LEVELS-1) break; info->inf[level] = onestat; } if(line == NULL) return -1; rc = sscanf(line, "last_level: %d %d", &info->last_level, &info->consecutive_runs); amfree(line); if(rc > 2) return -2; rc = 0; nb_history = 0; for(i=0;i<=NB_HISTORY;i++) { info->history[i].level = -2; } for(rc = -2; (line = agets(infof)) != NULL; free(line)) { history_t onehistory; /* one history record */ long long off_t_tmp; intmax_t time_t_tmp; if (line[0] == '\0') continue; if(line[0] == '/' && line[1] == '/') { info->history[nb_history].level = -2; rc = 0; amfree(line); return 0; /* normal end of record */ } memset(&onehistory, 0, SIZEOF(onehistory)); s = line; ch = *s++; if(strncmp_const_skip(line, "history:", s, ch) != 0) { amfree(line); break; } skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%d", &onehistory.level) != 1) { amfree(line); break; } skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%lld", &off_t_tmp) != 1) { amfree(line); break; } onehistory.size = (off_t)off_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%lld", &off_t_tmp) != 1) { amfree(line); break; } onehistory.csize = (off_t)off_t_tmp; skip_integer(s, ch); skip_whitespace(s, ch); if(ch == '\0' || sscanf((s - 1), "%jd", &time_t_tmp) != 1) { amfree(line); break; } onehistory.date = (time_t)time_t_tmp; skip_integer(s, ch); onehistory.secs = (unsigned long)-1; skip_whitespace(s, ch);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -