Beispiel #1
0
/* Parse a dump header, including its tagged attributes, and call the
 * dump-header callback, if one is defined.
 */
static afs_uint32
parse_dumphdr(XFILE * X, unsigned char *tag, tagged_field * field,
	      afs_uint32 value, tag_parse_info * pi, void *g_refcon,
	      void *l_refcon)
{
    dump_parser *p = (dump_parser *) g_refcon;
    afs_dump_header hdr;
    dt_uint64 where;
    afs_uint32 r;

    memset(&hdr, 0, sizeof(hdr));
    if ((r = xftell(X, &where)))
	return r;
    sub64_32(hdr.offset, where, 1);

    if ((r = ReadInt32(X, &hdr.magic)))
	return r;
    if ((r = ReadInt32(X, &hdr.version)))
	return r;

    if (hdr.magic != DUMPBEGINMAGIC) {
	if (p->cb_error)
	    (p->cb_error) (DSERR_MAGIC, 1, p->err_refcon,
			   "Invalid magic number (0x%08x) in dump header",
			   hdr.magic);
	return DSERR_MAGIC;
    }
    if (hdr.version != DUMPVERSION) {
	if (p->cb_error)
	    (p->cb_error) (DSERR_MAGIC, 1, p->err_refcon,
			   "Unknown dump format version (%d) in dump header",
			   hdr.version);
	return DSERR_MAGIC;
    }

    if (p->print_flags & DSPRINT_DUMPHDR)
	printf("%s [%s = 0x%s]\n", field->label,
	       decimate_int64(&hdr.offset, 0), hexify_int64(&hdr.offset, 0));
    if (p->print_flags & DSPRINT_DUMPHDR) {
	printf(" Magic number: 0x%08x\n", hdr.magic);
	printf(" Version:      %d\n", hdr.version);
    }
    r = ParseTaggedData(X, dumphdr_fields, tag, pi, g_refcon, (void *)&hdr);

    if (!r && p->cb_dumphdr) {
	r = xftell(X, &where);
	if (!r)
	    r = (p->cb_dumphdr) (&hdr, X, p->refcon);
	if (p->flags & DSFLAG_SEEK) {
	    if (!r)
		r = xfseek(X, &where);
	    else
		xfseek(X, &where);
	}
    }
    if (hdr.field_mask & F_DUMPHDR_VOLNAME)
	free(hdr.volname);
    return r;
}
Beispiel #2
0
afs_uint32
ParseDumpFile(XFILE * X, dump_parser * p)
{
    tag_parse_info pi;
    unsigned char tag;
    afs_uint32 r;

    prep_pi(p, &pi);
    r = ParseTaggedData(X, top_fields, &tag, &pi, (void *)p, 0);
    return handle_return(r, X, tag, p);
}
Beispiel #3
0
/* Parse a volume header, including any tagged attributes, and call the
 * volume-header callback, if one is defined.
 */
afs_uint32
parse_volhdr(XFILE * X, unsigned char *tag, tagged_field * field,
	     afs_uint32 value, tag_parse_info * pi, void *g_refcon,
	     void *l_refcon)
{
    dump_parser *p = (dump_parser *) g_refcon;
    afs_vol_header hdr;
    u_int64 where;
    afs_uint32 r;

    memset(&hdr, 0, sizeof(hdr));
    if (r = xftell(X, &where))
	return r;
    sub64_32(hdr.offset, where, 1);
    if (p->print_flags & DSPRINT_VOLHDR)
	printf("%s [%s = 0x%s]\n", field->label,
	       decimate_int64(&hdr.offset, 0), hexify_int64(&hdr.offset, 0));

    r = ParseTaggedData(X, volhdr_fields, tag, pi, g_refcon, (void *)&hdr);

    if (!r && p->cb_volhdr) {
	if (r = xftell(X, &where))
	    return r;
	r = (p->cb_volhdr) (&hdr, X, p->refcon);
	if (p->flags & DSFLAG_SEEK) {
	    if (!r)
		r = xfseek(X, &where);
	    else
		xfseek(X, &where);
	}
    }
    if (hdr.field_mask & F_VOLHDR_VOLUNIQ)
	p->vol_uniquifier = hdr.voluniq;
    if (hdr.field_mask & F_VOLHDR_VOLNAME)
	free(hdr.volname);
    if (hdr.field_mask & F_VOLHDR_OFFLINE_MSG)
	free(hdr.offline_msg);
    if (hdr.field_mask & F_VOLHDR_MOTD)
	free(hdr.motd_msg);
    return r;
}
Beispiel #4
0
/* Parse a VNode, including any tagged attributes and data, and call the
 * appropriate callback, if one is defined.
 */
afs_uint32
parse_vnode(XFILE * X, unsigned char *tag, tagged_field * field,
	    afs_uint32 value, tag_parse_info * pi, void *g_refcon,
	    void *l_refcon)
{
    dump_parser *p = (dump_parser *) g_refcon;
    afs_uint32(*cb) (afs_vnode *, XFILE *, void *);
    dt_uint64 where, offset2k;
    afs_vnode v;
    afs_uint32 r;


    if ((r = xftell(X, &where)))
	return r;
    memset(&v, 0, sizeof(v));
    sub64_32(v.offset, where, 1);
    if ((r = ReadInt32(X, &v.vnode)))
	return r;
    if ((r = ReadInt32(X, &v.vuniq)))
	return r;

    mk64(offset2k, 0, 2048);
    if (!LastGoodVNode
	|| ((p->flags & DSFLAG_SEEK) && v.vnode == 1
	    && lt64(v.offset, offset2k)))
	LastGoodVNode = -1;

    if (p->print_flags & DSPRINT_ITEM) {
	printf("%s %d/%d [%s = 0x%s]\n", field->label, v.vnode, v.vuniq,
	       decimate_int64(&where, 0), hexify_int64(&where, 0));
    }

    r = ParseTaggedData(X, vnode_fields, tag, pi, g_refcon, (void *)&v);

    /* Try to resync, if requested */
    if (!r && (p->repair_flags & DSFIX_VFSYNC)) {
	afs_uint32 drop;
	dt_uint64 xwhere;

	if ((r = xftell(X, &where)))
	    return r;
	sub64_32(xwhere, where, 1);

	/* Are we at the start of a valid vnode (or dump end)? */
	r = match_next_vnode(X, p, &xwhere, v.vnode);
	if (r && r != DSERR_FMT)
	    return r;
	if (r) {		/* Nope. */
	    /* Was _this_ a valid vnode?  If so, we can keep it and search for
	     * the next one.  Otherwise, we throw it out, and start the search
	     * at the starting point of this vnode.
	     */
	    drop = r = match_next_vnode(X, p, &v.offset, LastGoodVNode);
	    if (r && r != DSERR_FMT)
		return r;
	    if (!r) {
		add64_32(where, v.offset, 1);
		if ((r = xfseek(X, &v.offset)))
		    return r;
	    } else {
		if ((r = xfseek(X, &xwhere)))
		    return r;
	    }
	    if ((r = resync_vnode(X, p, &v, 0, 1024)))
		return r;
	    if ((r = ReadByte(X, tag)))
		return r;
	    if (drop) {
		if (p->cb_error)
		    (p->cb_error) (DSERR_FMT, 0, p->err_refcon,
				   "Dropping vnode %d", v.vnode);
		return 0;
	    }
	} else {
	    if ((r = xfseek(X, &where)))
		return r;
	}
    }
    LastGoodVNode = v.vnode;

    if (!r) {
	if (v.field_mask & F_VNODE_TYPE)
	    switch (v.type) {
	    case vFile:
		cb = p->cb_vnode_file;
		break;
	    case vDirectory:
		cb = p->cb_vnode_dir;
		break;
	    case vSymlink:
		cb = p->cb_vnode_link;
		break;
	    default:
		cb = p->cb_vnode_wierd;
		break;
	} else
	    cb = p->cb_vnode_empty;
	if (cb) {
	    dt_uint64 where;

	    if ((r = xftell(X, &where)))
		return r;
	    r = (cb) (&v, X, p->refcon);
	    if (p->flags & DSFLAG_SEEK) {
		if (!r)
		    r = xfseek(X, &where);
		else
		    xfseek(X, &where);
	    }
	}
    }
    return r;
}