int
rt_db_get_internal(
    struct rt_db_internal *ip,
    const struct directory *dp,
    const struct db_i *dbip,
    const mat_t mat,
    struct resource *resp)
{
    struct bu_external ext;
    int id;
    int ret;

    RT_DB_INTERNAL_INIT(ip);

    if (dbip->dbi_version > 4)
	return rt_db_get_internal5(ip, dp, dbip, mat, resp);

    BU_EXTERNAL_INIT(&ext);

    if (db_get_external(&ext, dp, dbip) < 0)
	return -2;		/* FAIL */

    if (dp->d_flags & RT_DIR_COMB) {
	id = ID_COMBINATION;
    } else {
	/* As a convenience to older ft_import4 routines */
	if (mat == NULL) mat = bn_mat_identity;
	id = rt_id_solid(&ext);
    }

    /* ip is already initialized and should not be re-initialized */
    ret = -1;
    if (OBJ[id].ft_import4) {
	ret = OBJ[id].ft_import4(ip, &ext, mat, dbip, resp);
    }
    if (ret < 0) {
	bu_log("rt_db_get_internal(%s):  import failure\n",
	       dp->d_namep);
	rt_db_free_internal(ip);
	bu_free_external(&ext);
	return -1;		/* FAIL */
    }
    bu_free_external(&ext);
    RT_CK_DB_INTERNAL(ip);
    ip->idb_meth = &OBJ[id];

    /* prior to version 5, there are no attributes ... */
    bu_avs_init_empty(&ip->idb_avs);

    /* ... but this isn't the whole story: */
    if (id == ID_COMBINATION) {
	const struct rt_comb_internal *comb = (const struct rt_comb_internal *)ip->idb_ptr;
	RT_CK_COMB(comb);

	db5_sync_comb_to_attr(&ip->idb_avs, comb);
    }

    return id;			/* OK */
}
Beispiel #2
0
/*
 *  Process pixels from 'a' to 'b' inclusive.
 *  The results are sent back all at once.
 *  Limitation:  may not do more than 'width' pixels at once,
 *  because that is the size of the buffer (for now).
 */
void
ph_lines(struct pkg_conn *UNUSED(pc), char *buf)
{
    int		a, b, fr;
    struct line_info	info;
    struct rt_i	*rtip = APP.a_rt_i;
    struct	bu_external	ext;

    RT_CK_RTI(rtip);

    if (debug > 1)  fprintf(stderr, "ph_lines: %s\n", buf);
    if (!seen_gettrees)  {
	bu_log("ph_lines:  no MSG_GETTREES yet\n");
	return;
    }
    if (!seen_matrix)  {
	bu_log("ph_lines:  no MSG_MATRIX yet\n");
	return;
    }

    a=0;
    b=0;
    fr=0;
    if (sscanf(buf, "%d %d %d", &a, &b, &fr) != 3)
	bu_exit(2, "ph_lines:  %s conversion error\n", buf);

    srv_startpix = a;		/* buffer un-offset for view_pixel */
    if (b-a+1 > srv_scanlen)  b = a + srv_scanlen - 1;

    rtip->rti_nrays = 0;
    info.li_startpix = a;
    info.li_endpix = b;
    info.li_frame = fr;

    rt_prep_timer();
    do_run(a, b);
    info.li_nrays = rtip->rti_nrays;
    info.li_cpusec = rt_read_timer((char *)0, 0);
    info.li_percent = 42.0;	/* for now */

    if (!bu_struct_export(&ext, (void *)&info, desc_line_info))
	bu_exit(98, "ph_lines: bu_struct_export failure\n");

    if (debug)  {
	fprintf(stderr, "PIXELS fr=%d pix=%d..%d, rays=%d, cpu=%g\n",
		info.li_frame,
		info.li_startpix, info.li_endpix,
		info.li_nrays, info.li_cpusec);
    }
    if (pkg_2send(MSG_PIXELS, (const char *)ext.ext_buf, ext.ext_nbytes, (const char *)scanbuf, (b-a+1)*3, pcsrv) < 0)  {
	fprintf(stderr, "MSG_PIXELS send error\n");
	bu_free_external(&ext);
    }

    bu_free_external(&ext);
}
Beispiel #3
0
int
ged_copy(struct ged *gedp, int argc, const char *argv[])
{
    struct directory *from_dp;
    struct bu_external external;
    static const char *usage = "from to";

    GED_CHECK_DATABASE_OPEN(gedp, GED_ERROR);
    GED_CHECK_READ_ONLY(gedp, GED_ERROR);
    GED_CHECK_ARGC_GT_0(gedp, argc, GED_ERROR);

    /* initialize result */
    bu_vls_trunc(gedp->ged_result_str, 0);

    /* must be wanting help */
    if (argc == 1) {
	bu_vls_printf(gedp->ged_result_str, "Usage: %s %s", argv[0], usage);
	return GED_HELP;
    }

    if (argc != 3) {
	bu_vls_printf(gedp->ged_result_str, "Usage: %s %s", argv[0], usage);
	return GED_ERROR;
    }

    GED_DB_LOOKUP(gedp, from_dp, argv[1], LOOKUP_NOISY, GED_ERROR & GED_QUIET);
    GED_CHECK_EXISTS(gedp, argv[2], LOOKUP_QUIET, GED_ERROR);

    if (db_get_external(&external, from_dp, gedp->ged_wdbp->dbip)) {
	bu_vls_printf(gedp->ged_result_str, "Database read error, aborting\n");
	return GED_ERROR;
    }

    if (wdb_export_external(gedp->ged_wdbp, &external, argv[2],
			    from_dp->d_flags,  from_dp->d_minor_type) < 0) {
	bu_free_external(&external);
	bu_vls_printf(gedp->ged_result_str,
		      "Failed to write new object (%s) to database - aborting!!\n",
		      argv[2]);
	return GED_ERROR;
    }

    bu_free_external(&external);

    return GED_OK;
}
int
rt_db_put_internal(
    struct directory *dp,
    struct db_i *dbip,
    struct rt_db_internal *ip,
    struct resource *resp)
{
    struct bu_external ext;
    int ret;

    RT_CK_DB_INTERNAL(ip);

    if (db_version(dbip) > 4)
	return rt_db_put_internal5(dp, dbip, ip, resp,
				   DB5_MAJORTYPE_BRLCAD);

    BU_EXTERNAL_INIT(&ext);

    /* Scale change on export is 1.0 -- no change */
    ret = -1;
    if (ip->idb_meth->ft_export4) {
	ret = ip->idb_meth->ft_export4(&ext, ip, 1.0, dbip, resp);
    }
    if (ret < 0) {
	bu_log("rt_db_put_internal(%s):  solid export failure\n",
	       dp->d_namep);
	rt_db_free_internal(ip);
	bu_free_external(&ext);
	return -2;		/* FAIL */
    }
    rt_db_free_internal(ip);

    if (db_put_external(&ext, dp, dbip) < 0) {
	bu_free_external(&ext);
	return -1;		/* FAIL */
    }

    bu_free_external(&ext);
    return 0;			/* OK */
}
int
rt_fwrite_internal(
    FILE *fp,
    const char *name,
    const struct rt_db_internal *ip,
    double conv2mm)
{
    struct bu_external ext;
    int ret;

    RT_CK_DB_INTERNAL(ip);
    RT_CK_FUNCTAB(ip->idb_meth);

    BU_EXTERNAL_INIT(&ext);

    ret = -1;
    if (ip->idb_meth->ft_export4) {
	ret = ip->idb_meth->ft_export4(&ext, ip, conv2mm, NULL /*dbip*/, &rt_uniresource);
    }
    if (ret < 0) {
	bu_log("rt_file_put_internal(%s): solid export failure\n",
	       name);
	bu_free_external(&ext);
	return -2;				/* FAIL */
    }
    BU_CK_EXTERNAL(&ext);

    if (db_fwrite_external(fp, name, &ext) < 0) {
	bu_log("rt_fwrite_internal(%s): db_fwrite_external() error\n",
	       name);
	bu_free_external(&ext);
	return -3;
    }
    bu_free_external(&ext);
    return 0;

}
Beispiel #6
0
int
db_dump(struct rt_wdb *wdbp, struct db_i *dbip)
/* output */
/* input */
{
    register int i;
    register struct directory *dp;
    struct bu_external ext;

    RT_CK_DBI(dbip);
    RT_CK_WDB(wdbp);

    /* just in case since we don't actually handle it below */
    if (db_version(dbip) != db_version(wdbp->dbip)) {
	bu_log("Internal Error: dumping a v%d database into a v%d database is untested\n", db_version(dbip), db_version(wdbp->dbip));
	return -1;
    }

    /* Output all directory entries */
    for (i = 0; i < RT_DBNHASH; i++) {
	for (dp = dbip->dbi_Head[i]; dp != RT_DIR_NULL; dp = dp->d_forw) {
	    RT_CK_DIR(dp);
	    /* XXX Need to go to internal form, if database versions don't match */
	    if (db_get_external(&ext, dp, dbip) < 0) {
		bu_log("db_dump() read failed on %s, skipping\n", dp->d_namep);
		continue;
	    }
	    if (wdb_export_external(wdbp, &ext, dp->d_namep, dp->d_flags & ~(RT_DIR_INMEM), dp->d_minor_type) < 0) {
		bu_log("db_dump() write failed on %s, aborting\n", dp->d_namep);
		bu_free_external(&ext);
		return -1;
	    }
	    bu_free_external(&ext);
	}
    }
    return 0;
}
Beispiel #7
0
int
ged_unhide(struct ged *gedp, int argc, const char *argv[])
{
    struct directory *dp;
    struct db_i *dbip;
    struct bu_external ext;
    struct bu_external tmp;
    struct db5_raw_internal raw;
    int i;
    static const char *usage = "object(s)";

    GED_CHECK_DATABASE_OPEN(gedp, GED_ERROR);
    GED_CHECK_READ_ONLY(gedp, GED_ERROR);
    GED_CHECK_ARGC_GT_0(gedp, argc, GED_ERROR);

    /* initialize result */
    bu_vls_trunc(gedp->ged_result_str, 0);

    /* must be wanting help */
    if (argc == 1) {
	bu_vls_printf(gedp->ged_result_str, "Usage: %s %s", argv[0], usage);
	return GED_HELP;
    }

    dbip = gedp->ged_wdbp->dbip;

    if (db_version(dbip) < 5) {
	bu_vls_printf(gedp->ged_result_str, "Database was created with a previous release of BRL-CAD.\nSelect \"Tools->Upgrade Database...\" to enable support for this feature.");
	return GED_ERROR;
    }

    for (i = 1; i < argc; i++) {
	if ((dp = db_lookup(dbip, argv[i], LOOKUP_NOISY)) == RT_DIR_NULL) {
	    continue;
	}

	RT_CK_DIR(dp);

	BU_EXTERNAL_INIT(&ext);

	if (db_get_external(&ext, dp, dbip) < 0) {
	    bu_vls_printf(gedp->ged_result_str, "db_get_external failed for %s\n", dp->d_namep);
	    continue;
	}

	if (db5_get_raw_internal_ptr(&raw, ext.ext_buf) == NULL) {
	    bu_vls_printf(gedp->ged_result_str, "db5_get_raw_internal_ptr() failed for %s\n", dp->d_namep);
	    bu_free_external(&ext);
	    continue;
	}

	raw.h_name_hidden = (unsigned char)(0x0);

	BU_EXTERNAL_INIT(&tmp);
	db5_export_object3(&tmp, DB5HDR_HFLAGS_DLI_APPLICATION_DATA_OBJECT,
			   dp->d_namep,
			   raw.h_name_hidden,
			   &raw.attributes,
			   &raw.body,
			   raw.major_type, raw.minor_type,
			   raw.a_zzz, raw.b_zzz);
	bu_free_external(&ext);

	if (db_put_external(&tmp, dp, dbip)) {
	    bu_vls_printf(gedp->ged_result_str, "db_put_external() failed for %s\n", dp->d_namep);
	    bu_free_external(&tmp);
	    continue;
	}
	bu_free_external(&tmp);
	dp->d_flags &= (~RT_DIR_HIDDEN);
    }

    return GED_OK;
}
Beispiel #8
0
int
rt_mk_binunif(struct rt_wdb *wdbp, const char *obj_name, const char *file_name, unsigned int minor_type, size_t max_count)
{
    int ret;
    struct stat st;
    size_t num_items = 0;
    size_t obj_length = 0;
    size_t item_length = 0;
    unsigned int major_type = DB5_MAJORTYPE_BINARY_UNIF;
    struct directory *dp = NULL;
    struct bu_mapped_file *bu_fd = NULL;
    struct rt_binunif_internal *bip = NULL;
    struct bu_external body;
    struct bu_external bin_ext;
    struct rt_db_internal intern;

    item_length = db5_type_sizeof_h_binu(minor_type);
    if (item_length == 0) {
	bu_log("Unrecognized minor type (%d)!\n", minor_type);
	return -1;
    }

    if (bu_stat(file_name, &st)) {
	bu_log("Cannot stat input file (%s)", file_name);
	return -1;
    }

    bu_fd = bu_open_mapped_file(file_name, NULL);
    if (bu_fd == NULL) {
	bu_log("Cannot open input file (%s) for reading", file_name);
	return -1;
    }

    /* create the rt_binunif internal form */
    BU_ALLOC(bip, struct rt_binunif_internal);
    bip->magic = RT_BINUNIF_INTERNAL_MAGIC;
    bip->type = minor_type;

    num_items = (size_t)(st.st_size / item_length);

    /* maybe only a partial file read */
    if (max_count > 0 && max_count < num_items) {
	num_items = max_count;
    }

    obj_length = num_items * item_length;
    if (obj_length < 1) {
	obj_length = 1;
    }

    /* just copy the bytes */
    bip->count = (long)num_items;
    bip->u.int8 = (char *)bu_malloc(obj_length, "binary uniform object");
    memcpy(bip->u.int8, bu_fd->buf, obj_length);

    bu_close_mapped_file(bu_fd);

    /* create the rt_internal form */
    RT_DB_INTERNAL_INIT(&intern);
    intern.idb_major_type = major_type;
    intern.idb_minor_type = minor_type;
    intern.idb_ptr = (genptr_t)bip;
    intern.idb_meth = &rt_functab[ID_BINUNIF];

    /* create body portion of external form */
    ret = -1;
    if (intern.idb_meth->ft_export5) {
	ret = intern.idb_meth->ft_export5(&body, &intern, 1.0, wdbp->dbip, wdbp->wdb_resp);
    }
    if (ret != 0) {
	bu_log("Error while attempting to export %s\n", obj_name);
	rt_db_free_internal(&intern);
	return -1;
    }

    /* create entire external form */
    db5_export_object3(&bin_ext, DB5HDR_HFLAGS_DLI_APPLICATION_DATA_OBJECT,
		       obj_name, 0, NULL, &body,
		       intern.idb_major_type, intern.idb_minor_type,
		       DB5_ZZZ_UNCOMPRESSED, DB5_ZZZ_UNCOMPRESSED);

    rt_db_free_internal(&intern);
    bu_free_external(&body);

    /* make sure the database directory is initialized */
    if (wdbp->dbip->dbi_eof == RT_DIR_PHONY_ADDR) {
	ret = db_dirbuild(wdbp->dbip);
	if (ret) {
	    return -1;
	}
    }

    /* add this (phony until written) object to the directory */
    if ((dp=db_diradd5(wdbp->dbip, obj_name, RT_DIR_PHONY_ADDR, major_type,
		       minor_type, 0, 0, NULL)) == RT_DIR_NULL) {
	bu_log("Error while attempting to add new name (%s) to the database",
	       obj_name);
	bu_free_external(&bin_ext);
	return -1;
    }

    /* and write it to the database */
    if (db_put_external5(&bin_ext, dp, wdbp->dbip)) {
	bu_log("Error while adding new binary object (%s) to the database",
	       obj_name);
	bu_free_external(&bin_ext);
	return -1;
    }

    bu_free_external(&bin_ext);

    return 0;
}
Beispiel #9
0
/**
 * Apply a 4x4 transformation matrix to the internal form of a solid.
 *
 * If "free" flag is non-zero, storage for the original solid is
 * released.  If "os" is same as "is", storage for the original solid
 * is overwritten with the new, transformed solid.
 *
 * Returns -
 * -1 FAIL
 *  0 OK
 */
int
rt_generic_xform(
    struct rt_db_internal *op,
    const mat_t mat,
    struct rt_db_internal *ip,
    int release,
    struct db_i *dbip,
    struct resource *resp)
{
    struct bu_external ext;
    int id;
    struct bu_attribute_value_set avs;

    RT_CK_DB_INTERNAL(ip);
    RT_CK_DBI(dbip);
    RT_CK_RESOURCE(resp);

    memset(&avs, 0, sizeof(struct bu_attribute_value_set));

    id = ip->idb_type;
    BU_EXTERNAL_INIT(&ext);
    /* Scale change on export is 1.0 -- no change */
    switch (db_version(dbip)) {
	case 4:
	    if (OBJ[id].ft_export4(&ext, ip, 1.0, dbip, resp) < 0) {
		bu_log("rt_generic_xform():  %s export failure\n",
		       OBJ[id].ft_name);
		return -1;			/* FAIL */
	    }
	    if ((release || op == ip)) rt_db_free_internal(ip);

	    RT_DB_INTERNAL_INIT(op);
	    if (OBJ[id].ft_import4(op, &ext, mat, dbip, resp) < 0) {
		bu_log("rt_generic_xform():  solid import failure\n");
		return -1;			/* FAIL */
	    }
	    break;
	case 5:
	    if (OBJ[id].ft_export5(&ext, ip, 1.0, dbip, resp) < 0) {
		bu_log("rt_generic_xform():  %s export failure\n",
		       OBJ[id].ft_name);
		return -1;			/* FAIL */
	    }

	    if ((release || op == ip)) {
		if (ip->idb_avs.magic == BU_AVS_MAGIC) {
		    /* grab the attributes before they are lost
		     * by rt_db_free_internal or RT_DB_INTERNAL_INIT
		     */
		    bu_avs_init(&avs, ip->idb_avs.count, "avs");
		    bu_avs_merge(&avs, &ip->idb_avs);
		}
		rt_db_free_internal(ip);
	    }

	    RT_DB_INTERNAL_INIT(op);

	    if (!release && op != ip) {
		/* just copy the attributes from ip to op */
		if (ip->idb_avs.magic == BU_AVS_MAGIC) {
		    bu_avs_init(&op->idb_avs, ip->idb_avs.count, "avs");
		    bu_avs_merge(&op->idb_avs, &ip->idb_avs);
		}
	    } else if (avs.magic == BU_AVS_MAGIC) {
		/* put the saved attributes in the output */
		bu_avs_init(&op->idb_avs, avs.count, "avs");
		bu_avs_merge(&op->idb_avs, &avs);
		bu_avs_free(&avs);
	    }

	    if (OBJ[id].ft_import5(op, &ext, mat, dbip, resp) < 0) {
		bu_log("rt_generic_xform():  solid import failure\n");
		return -1;			/* FAIL */
	    }
	    break;
    }

    bu_free_external(&ext);

    RT_CK_DB_INTERNAL(op);
    return 0;				/* OK */
}
Beispiel #10
0
   or  poly-bot file_poly.g file_bot.g\n\
 Convert polysolids to BOT solids in v4 database format only\n";

int
main(int argc, char **argv)
{
    FILE *ifp;
    FILE *ofp;
    union record record;
    union record *poly;
    long poly_limit=0;
    long curr_poly=0;
    struct bn_tol		tol;
    int polys=0;
    int frees=0;
    int others=0;
    int bots=0;
    int i;
    int num_rec;
    int first=1;

    bu_setprogname(argv[0]);

    ifp = stdin;
    ofp = stdout;

    /* FIXME: These need to be improved */
    tol.magic = BN_TOL_MAGIC;
    tol.dist = 0.0005;
    tol.dist_sq = tol.dist * tol.dist;
    tol.perp = 1e-6;
    tol.para = 1 - tol.perp;

    if (argc >= 3) {
	ifp = fopen(argv[1], "rb");
	if (!ifp)
	    perror(argv[1]);

	ofp = fopen(argv[2], "wb");
	if (!ofp)
	    perror(argv[2]);

	if (ifp == NULL || ofp == NULL) {
	    bu_exit(1, "poly-bot: can't open files.");
	}
#if defined(_WIN32) && !defined(__CYGWIN__)
    } else {
	setmode(fileno(ifp), O_BINARY);
	setmode(fileno(ofp), O_BINARY);
#endif
    }
    if (isatty(fileno(ifp))) {
	bu_exit(1, "%s", usage);
    }

    poly = (union record *)bu_malloc( POLY_BLOCK * sizeof( union record ), "poly" );
    poly_limit = POLY_BLOCK;

    /* Read database file */
    while ( fread( (char *)&record, sizeof record, 1, ifp ) == 1  && !feof(ifp) )
    {
    top:
	switch ( record.u_id )
	{
	    case ID_FREE:
		frees++;
		continue;

	    case DBID_SKETCH:
		num_rec = ntohl(*(uint32_t *)&record.skt.skt_count);
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying a SKETCH\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_EXTR:
		num_rec = ntohl(*(uint32_t *)&record.extr.ex_count);
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying an EXTRUSION\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_NMG:
		num_rec = ntohl(*(uint32_t *)&record.nmg.N_count);
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying an ARBN\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_PIPE:
		num_rec = ntohl(*(uint32_t *)&record.pwr.pwr_count);
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying a PIPE\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_ARBN:
		num_rec = ntohl(*(uint32_t *)&record.n.n_grans);
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying an ARBN\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_STRSOL:
		num_rec = DB_SS_NGRAN - 1;
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying a STRSOL\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case ID_BSURF:
		num_rec = record.d.d_nknots + record.d.d_nctls;
		others += num_rec + 1;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying a NURB\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case DBID_BOT:
		bots++;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
		num_rec = ntohl(*(uint32_t *)&record.bot.bot_nrec);
		for ( i=0; i<num_rec; i++ )
		{
		    if ( fread( (char *)&record, sizeof record, 1, ifp ) != 1 )
			bu_exit(1, "Unexpected EOF encountered while copying a BOT\n" );
		    if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
			bu_exit(1, "Write failed!\n" );
		}
		break;
	    case ID_P_HEAD:
	    {
		struct rt_db_internal intern;
		struct bu_external ext;
		struct bu_external ext2;

		polys++;
		curr_poly = 0;
		poly[curr_poly++] = record;	/* struct copy */
		bu_log( "Converting %s\n", poly[0].p.p_name );
		while ( fread( (char *)&record, sizeof record, 1, ifp ) == 1  &&
			!feof(ifp) &&
			record.u_id == ID_P_DATA )
		{
		    if ( curr_poly >= poly_limit )
		    {
			poly_limit += POLY_BLOCK;
			poly = (union record *)bu_realloc( poly, poly_limit*sizeof( union record ), "poly realloc" );
		    }
		    poly[curr_poly++] = record;	/* struct copy */
		}
		BU_EXTERNAL_INIT( &ext );
		ext.ext_nbytes = curr_poly * sizeof( union record );
		ext.ext_buf = (uint8_t *)poly;
		if ( rt_functab[ID_POLY].ft_import4( &intern, &ext, bn_mat_identity, (struct db_i *)NULL, &rt_uniresource ) )
		{
		    bu_exit(1, "Import failed for polysolid %s\n", poly[0].p.p_name );
		}
		/* Don't free this ext buffer! */

		if ( rt_pg_to_bot( &intern, &tol, &rt_uniresource ) < 0 )  {
		    bu_exit(1, "Unable to convert polysolid %s\n", poly[0].p.p_name );
		}

		BU_EXTERNAL_INIT( &ext2 );
		if ( rt_functab[ID_POLY].ft_export4( &ext2, &intern, 1.0, (struct db_i *)NULL, &rt_uniresource ) < 0 )  {
		    bu_exit(1, "Unable to export v4 BoT %s\n", poly[0].p.p_name );
		}
		rt_db_free_internal(&intern);
		if ( db_fwrite_external( ofp, poly[0].p.p_name, &ext2 ) < 0 )  {
		    bu_exit(1, "Unable to fwrite v4 BoT %s\n", poly[0].p.p_name );
		}
		bu_free_external( &ext2 );

		if ( feof( ifp ) )
		    break;
		goto top;
	    }
	    case ID_P_DATA:
		/* This should not happen! */
		bu_log( "ERROR: Unattached polysolid data record!\n" );
		continue;
	    default:
		if ( first )
		{
		    if ( record.u_id != ID_IDENT ) {
			bu_exit(1, "This is not a BRL-CAD 'v4' database, aborting.\n" );
		    }
		    first = 0;
		}
		others++;
		if ( fwrite( &record, sizeof( union record ), 1, ofp ) < 1 )
		    bu_exit(1, "Write failed!\n" );
	}
    }

    bu_log( "%d polysolids converted to BOT solids\n", polys );
    bu_log( "%d BOT solids copied without change\n", bots );
    bu_log( "%d other records copied without change\n", others );
    bu_log( "%d free records skipped\n", frees );

    fclose(ofp);
    return 0;
}
Beispiel #11
0
int
ged_dbcopy(struct ged *from_gedp, struct ged *to_gedp, const char *from, const char *to, int fflag)
{
    struct directory *from_dp;
    struct bu_external external;

    GED_CHECK_DATABASE_OPEN(from_gedp, GED_ERROR);
    GED_CHECK_DATABASE_OPEN(to_gedp, GED_ERROR);
    GED_CHECK_READ_ONLY(to_gedp, GED_ERROR);

    /* initialize result */
    bu_vls_trunc(from_gedp->ged_result_str, 0);
    bu_vls_trunc(to_gedp->ged_result_str, 0);

    GED_DB_LOOKUP(from_gedp, from_dp, from, LOOKUP_NOISY, GED_ERROR & GED_QUIET);

    if (!fflag && db_lookup(to_gedp->ged_wdbp->dbip, to, LOOKUP_QUIET) != RT_DIR_NULL) {
	bu_vls_printf(from_gedp->ged_result_str, "%s already exists.", to);
	return GED_ERROR;
    }

    if (db_get_external(&external, from_dp, from_gedp->ged_wdbp->dbip)) {
	bu_vls_printf(from_gedp->ged_result_str, "Database read error, aborting\n");
	return GED_ERROR;
    }

    if (wdb_export_external(to_gedp->ged_wdbp, &external, to,
			    from_dp->d_flags,  from_dp->d_minor_type) < 0) {
	bu_free_external(&external);
	bu_vls_printf(from_gedp->ged_result_str,
		      "Failed to write new object (%s) to database - aborting!!\n",
		      to);
	return GED_ERROR;
    }

    bu_free_external(&external);

    /* Need to do something extra for _GLOBAL */
    if (db_version(to_gedp->ged_wdbp->dbip) > 4 && BU_STR_EQUAL(to, DB5_GLOBAL_OBJECT_NAME)) {
	struct directory *to_dp;
	struct bu_attribute_value_set avs;
	const char *val;

	GED_DB_LOOKUP(to_gedp, to_dp, to, LOOKUP_NOISY, GED_ERROR & GED_QUIET);

	bu_avs_init_empty(&avs);
	if (db5_get_attributes(to_gedp->ged_wdbp->dbip, &avs, to_dp)) {
	    bu_vls_printf(from_gedp->ged_result_str, "Cannot get attributes for object %s\n", to_dp->d_namep);
	    return GED_ERROR;
	}

	if ((val = bu_avs_get(&avs, "title")) != NULL)
	    to_gedp->ged_wdbp->dbip->dbi_title = strdup(val);

	if ((val = bu_avs_get(&avs, "units")) != NULL) {
	    double loc2mm;

	    if ((loc2mm = bu_mm_value(val)) > 0) {
		to_gedp->ged_wdbp->dbip->dbi_local2base = loc2mm;
		to_gedp->ged_wdbp->dbip->dbi_base2local = 1.0 / loc2mm;
	    }
	}

	if ((val = bu_avs_get(&avs, "regionid_colortable")) != NULL) {
	    rt_color_free();
	    db5_import_color_table((char *)val);
	}

	bu_avs_free(&avs);
    }

    return GED_OK;
}
Beispiel #12
0
static int
db_corrupt_handler(struct db_i *dbip, const char *name, off_t offset, size_t size, int UNUSED(type), void *data)
{
    struct counter *cnt = (struct counter *)data;
    struct bu_external ext;
    union record *rp = NULL;
    mat_t diskmat = MAT_INIT_ZERO;
    size_t nodecount;
    size_t j;
    int ret;

    RT_CK_DBI(dbip);

    /* get into position */
    ret = bu_fseek(dbip->dbi_fp, offset, 0);
    if (ret) {
	bu_log("Database seek failure, unable to seek [%s]\n", name);
	return 0;
    }

    /* set up our buffer */
    BU_EXTERNAL_INIT(&ext);
    ext.ext_nbytes = size * sizeof(union record);
    ext.ext_buf = (uint8_t *)bu_calloc(ext.ext_nbytes, 1, "db_corrupt");

    /* read into the buffer */
    j = (size_t)fread(ext.ext_buf, 1, ext.ext_nbytes, dbip->dbi_fp);
    if (j != ext.ext_nbytes) {
	bu_log("Database read failure, unable to read [%s]\n", name);
	bu_free_external(&ext);
	return 0;
    }

    rp = (union record *)ext.ext_buf;
    if (rp[0].u_id != ID_COMB) {
	/* skip non-combination */
	bu_free_external(&ext);
	return 0;
    }

    /* iterate over combination members, looking for bad matrices */
    nodecount = ext.ext_nbytes/sizeof(union record) - 1;
    for (j = 0; j < nodecount; j++) {

	/* try without flipping */
	flip_mat_dbmat(diskmat, rp[j+1].M.m_mat, 0);
	if ((bn_mat_ck(name, diskmat) < 0)
	    || fabs(diskmat[0]) > 1 || fabs(diskmat[1]) > 1 || fabs(diskmat[2]) > 1
	    || fabs(diskmat[4]) > 1 || fabs(diskmat[5]) > 1 || fabs(diskmat[6]) > 1
	    || fabs(diskmat[8]) > 1 || fabs(diskmat[9]) > 1 || fabs(diskmat[10]) > 1) {
	    /* corruption detected */
	    cnt->found++;

	    /* invalid, so try flipped */
	    flip_mat_dbmat(diskmat, rp[j+1].M.m_mat, 1);
	    if ((bn_mat_ck(name, diskmat) < 0)
		|| fabs(diskmat[0]) > 1 || fabs(diskmat[1]) > 1 || fabs(diskmat[2]) > 1
		|| fabs(diskmat[4]) > 1 || fabs(diskmat[5]) > 1 || fabs(diskmat[6]) > 1
		|| fabs(diskmat[8]) > 1 || fabs(diskmat[9]) > 1 || fabs(diskmat[10]) > 1)
	    {
		bu_log("WARNING: Invalid matrix detected within %s\n", name);
	    } else {
		/* flipping helped */
		cnt->fixed++;
	    }

	    break;
	}
    }

    bu_free_external(&ext);

    return 0;
}
Beispiel #13
0
int
rt_binunif_tclget(Tcl_Interp *interp, const struct rt_db_internal *intern, const char *attr )
{
    register struct rt_binunif_internal *bip=(struct rt_binunif_internal *)intern->idb_ptr;
    struct bu_external	ext;
    Tcl_DString		ds;
    struct bu_vls		vls;
    int			status=TCL_OK;
    int			i;
    unsigned char		*c;

    RT_CHECK_BINUNIF( bip );

    Tcl_DStringInit( &ds );
    bu_vls_init( &vls );

    if ( attr == (char *)NULL )
    {
	/* export the object to get machine independent form */
	if ( rt_binunif_export5( &ext, intern, 1.0, NULL, NULL, intern->idb_minor_type ) ) {
	    bu_vls_strcpy( &vls, "Failed to export binary object!!\n" );
	    status = TCL_ERROR;
	} else {
	    bu_vls_strcpy( &vls, "binunif" );
	    bu_vls_printf( &vls, " T %d D {", bip->type );
	    c = ext.ext_buf;
	    for ( i=0; i<ext.ext_nbytes; i++, c++ ) {
		if ( i%40 == 0 ) bu_vls_strcat( &vls, "\n" );
		bu_vls_printf( &vls, "%2.2x", *c );
	    }
	    bu_vls_strcat( &vls, "}" );
	    bu_free_external( &ext );
	}

    } else {
	if ( !strcmp( attr, "T" ) ) {
	    bu_vls_printf( &vls, "%d", bip->type );
	} else if ( !strcmp( attr, "D" ) ) {
	    /* export the object to get machine independent form */
	    if ( rt_binunif_export5( &ext, intern, 1.0, NULL, NULL,
				     intern->idb_minor_type ) ) {
		bu_vls_strcpy( &vls, "Failed to export binary object!!\n" );
		status = TCL_ERROR;
	    } else {
		c = ext.ext_buf;
		for ( i=0; i<ext.ext_nbytes; i++, c++ ) {
		    if ( i != 0 && i%40 == 0 ) bu_vls_strcat( &vls, "\n" );
		    bu_vls_printf( &vls, "%2.2x", *c );
		}
		bu_free_external( &ext );
	    }
	} else {
	    bu_vls_printf( &vls, "Binary object has no attribute '%s'", attr );
	    status = TCL_ERROR;
	}
    }

    Tcl_DStringAppend( &ds, bu_vls_addr( &vls ), -1 );
    Tcl_DStringResult( interp, &ds );
    Tcl_DStringFree( &ds );
    bu_vls_free( &vls );

    return( status );
}
Beispiel #14
0
int
rt_retrieve_binunif(struct rt_db_internal *intern,
		    struct db_i	*dbip,
		    char *name)
{
    register struct directory	*dp;
    struct rt_binunif_internal	*bip;
    struct bu_external		ext;
    struct db5_raw_internal		raw;
    char				*tmp;

    /*
     *Find the guy we're told to write
     */
    if ( (dp = db_lookup( dbip, name, LOOKUP_NOISY)) == DIR_NULL )
	return -1;

    RT_INIT_DB_INTERNAL(intern);
    if ( rt_db_get_internal5( intern, dp, dbip, NULL, &rt_uniresource)
	 != ID_BINUNIF     || db_get_external( &ext, dp, dbip ) < 0 )
	return -1;

    if (db5_get_raw_internal_ptr(&raw, ext.ext_buf) == NULL) {
	bu_log("%s:%d\n", __FILE__, __LINE__);
	bu_free_external( &ext );
	return -1;
    }
    if (db5_type_descrip_from_codes(&tmp, raw.major_type, raw.minor_type))
	tmp = 0;

    if (RT_G_DEBUG & DEBUG_VOL)
	bu_log("get_body() sees type (%d, %d)='%s'\n",
	       raw.major_type, raw.minor_type, tmp);

    if (raw.major_type != DB5_MAJORTYPE_BINARY_UNIF)
	return -1;

    bip = intern->idb_ptr;
    RT_CK_BINUNIF(bip);
    if (RT_G_DEBUG & DEBUG_HF)
	rt_binunif_dump(bip);

    if (RT_G_DEBUG & DEBUG_VOL)
	bu_log("cmd_export_body() thinks bip->count=%d\n",
	       bip->count);

    switch (bip -> type) {
	case DB5_MINORTYPE_BINU_FLOAT:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... float");
	    break;
	case DB5_MINORTYPE_BINU_DOUBLE:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... double");
	    break;
	case DB5_MINORTYPE_BINU_8BITINT:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 8bitint");
	    break;
	case DB5_MINORTYPE_BINU_8BITINT_U:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 8bituint");
	    break;
	case DB5_MINORTYPE_BINU_16BITINT:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 16bituint");
	    break;
	case DB5_MINORTYPE_BINU_16BITINT_U:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 16bitint");
	    break;
	case DB5_MINORTYPE_BINU_32BITINT:
	case DB5_MINORTYPE_BINU_32BITINT_U:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 32bitint");
	    break;
	case DB5_MINORTYPE_BINU_64BITINT:
	case DB5_MINORTYPE_BINU_64BITINT_U:
	    if (RT_G_DEBUG & DEBUG_VOL)
		bu_log("bip->type switch... 64bitint");
	    break;
	default:
	    /* XXX	This shouln't happen!!    */
	    bu_log("bip->type switch... default");
	    break;
    }

    bu_free_external( &ext );

    return 0;
}
Beispiel #15
0
/*
 *		C M D _ E X P O R T _ B O D Y ( )
 *
 *	Write an object's body to disk file
 *
 */
int
cmd_export_body(ClientData clientData, Tcl_Interp *interp, int argc, char **argv)
{
    register struct directory	*dp;
    int				fd;
    void			*bufp;
    size_t			nbytes = 0;
    long int			written;
    struct bu_external		ext;
    struct db5_raw_internal	raw;
    struct rt_db_internal	intern;
    struct rt_binunif_internal	*bip;
    struct bu_vls		vls;
#if 0
    int				status;
#endif
    char			*tmp;

    CHECK_DBI_NULL;

    if (argc != 3) {
	bu_vls_init(&vls);
	bu_vls_printf(&vls, "help %s", argv[0]);
	Tcl_Eval(interp, bu_vls_addr(&vls));
	bu_vls_free(&vls);
	return TCL_ERROR;
    }

    /*
     *	Find the guy we're told to write
     */
    if ( (dp = db_lookup( dbip, argv[2], LOOKUP_NOISY)) == DIR_NULL ) {
	bu_vls_init( &vls );
	bu_vls_printf( &vls,
		       "Cannot find object %s for writing\n", argv[2] );
	Tcl_SetResult(interp, bu_vls_addr( &vls ), TCL_VOLATILE );
	bu_vls_free( &vls );
	mged_print_result( TCL_ERROR );
	return TCL_ERROR;
    }
    RT_INIT_DB_INTERNAL(&intern);
    if ( rt_db_get_internal5( &intern, dp, dbip, NULL, &rt_uniresource)
	 != ID_BINUNIF
	 || db_get_external( &ext, dp, dbip ) < 0 ) {
	(void)signal( SIGINT, SIG_IGN );
	TCL_READ_ERR_return;
    }
    if (db5_get_raw_internal_ptr(&raw, ext.ext_buf) == NULL)
    {
	bu_free_external( &ext );
	(void)signal( SIGINT, SIG_IGN );
	TCL_READ_ERR_return;
    }

    /*
     *	Do the writing
     */
#ifndef _WIN32
    if ( (fd = creat( argv[1], S_IRWXU | S_IRGRP | S_IROTH  )) == -1 ) {
#else
	if ( (fd = creat( argv[1], _S_IREAD | _S_IWRITE  )) == -1 ) {
#endif
	    bu_free_external( &ext );
	    bu_vls_init( &vls );
	    bu_vls_printf( &vls,
			   "Cannot open file %s for writing\n", argv[1] );
	    Tcl_SetResult(interp, bu_vls_addr( &vls ), TCL_VOLATILE );
	    bu_vls_free( &vls );
	    mged_print_result( TCL_ERROR );
	    return TCL_ERROR;
	}
	if (db5_type_descrip_from_codes(&tmp, raw.major_type, raw.minor_type))
	    tmp = 0;

	if (RT_G_DEBUG & DEBUG_VOL)
	    bu_log("cmd_export_body() sees type (%d, %d)='%s'\n",
		   raw.major_type, raw.minor_type, tmp);
	switch (raw.major_type) {
	    case DB5_MAJORTYPE_BINARY_UNIF:
#if 0
		if ( rt_binunif_import5( &intern, &ext, 0, dbip,
					 &rt_uniresource, raw.minor_type  ) ) {
		    (void)signal( SIGINT, SIG_IGN );
		    TCL_READ_ERR_return;
		}
#endif
		bip = (struct rt_binunif_internal *) intern.idb_ptr;
		RT_CK_BINUNIF(bip);
		rt_binunif_dump(bip);
		bufp = (void *) bip->u.uint8;
		bu_log("cmd_export_body() thinks bip->count=%d\n", bip->count);
		switch (bip -> type) {
		    case DB5_MINORTYPE_BINU_FLOAT:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... float");
			nbytes = (size_t) (bip->count * sizeof(float));
			break;
		    case DB5_MINORTYPE_BINU_DOUBLE:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... double");
			nbytes = (size_t) (bip->count * sizeof(double));
			break;
		    case DB5_MINORTYPE_BINU_8BITINT:
		    case DB5_MINORTYPE_BINU_8BITINT_U:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... 8bitint");
			nbytes = (size_t) (bip->count);
			break;
		    case DB5_MINORTYPE_BINU_16BITINT:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... 16bitint");
			nbytes = (size_t) (bip->count * 2);
			bu_log("data[0] = %u\n", bip->u.uint16[0]);
			break;
		    case DB5_MINORTYPE_BINU_16BITINT_U:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... 16bituint");
			nbytes = (size_t) (bip->count * 2);
			bu_log("data[0] = %u\n", bip->u.uint16[0]);
			break;
		    case DB5_MINORTYPE_BINU_32BITINT:
		    case DB5_MINORTYPE_BINU_32BITINT_U:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... 32bitint");
			nbytes = (size_t) (bip->count * 4);
			break;
		    case DB5_MINORTYPE_BINU_64BITINT:
		    case DB5_MINORTYPE_BINU_64BITINT_U:
			if (RT_G_DEBUG & DEBUG_VOL)
			    bu_log("bip->type switch... 64bitint");
			nbytes = (size_t) (bip->count * 8);
			break;
		    default:
			/* XXX	This shouln't happen!!    */
			bu_log("bip->type switch... default");
			break;
		}
		break;
	    default:
		if (RT_G_DEBUG & DEBUG_VOL)
		    bu_log("I'm in the default\n");
		bufp = (void *) ext.ext_buf;
		nbytes = (size_t) ext.ext_nbytes;
		break;
	}
	if (RT_G_DEBUG & DEBUG_VOL)
	    bu_log("going to write %ld bytes\n", nbytes);

	if ( (written = write(fd, bufp, nbytes) ) != nbytes ) {
	    perror(argv[1]);
	    bu_log("%s:%d\n", __FILE__, __LINE__);
	    bu_free_external( &ext );
	    bu_vls_init( &vls );
	    bu_vls_printf( &vls,
			   "Incomplete write of object %s to file %s, got %ld, s/b=%ld\n",
			   argv[2], argv[1], written, nbytes );
	    Tcl_SetResult(interp, bu_vls_addr( &vls ), TCL_VOLATILE );
	    bu_vls_free( &vls );
	    mged_print_result( TCL_ERROR );
	    return TCL_ERROR;
	}

	bu_free_external( &ext );
	return TCL_OK;
    }
Beispiel #16
0
int
rt_mk_binunif(struct rt_wdb *wdbp, const char *obj_name, const char *file_name, unsigned int minor_type, long max_count)
{
    struct stat st;
    unsigned int major_type=DB5_MAJORTYPE_BINARY_UNIF;
#if defined(_WIN32) && !defined(__CYGWIN__)
    __int64 num_items=-1;
    __int64 obj_length=-1;
#else
    long long num_items=-1;
    long long obj_length=-1;
#endif
    int item_length=0;
    struct bu_mapped_file *bu_fd;
    struct rt_binunif_internal *bip;
    struct rt_db_internal intern;
    struct bu_external body;
    struct bu_external bin_ext;
    struct directory *dp;

    if ( (item_length=db5_type_sizeof_h_binu( minor_type ) ) <= 0 ) {
	bu_log( "Unrecognized minor type!!!\n" );
	return -1;
    }

    if ( stat( file_name, &st ) ) {
	bu_log( "Cannot stat input file(%s)", file_name );
	return -1;
    }

    if ( (bu_fd=bu_open_mapped_file( file_name, NULL)) == NULL ) {
	bu_log( "Cannot open input file(%s) for reading",
		file_name );
	return -1;
    }

    /* create the rt_binunif internal form */
    BU_GETSTRUCT( bip, rt_binunif_internal );
    bip->magic = RT_BINUNIF_INTERNAL_MAGIC;
    bip->type = minor_type;

    num_items = (long)(st.st_size / item_length);

    /* maybe only a partial file read */
    if (max_count > 0 && max_count < num_items) {
	num_items = max_count;
    }

    obj_length = num_items * item_length;

    if (obj_length > __LONG_MAX__) {
	bu_log("Unable to create binary objects larger than %ld bytes\n", __LONG_MAX__);
	return -1;
    }

    /* just copy the bytes */
    bip->count = num_items;
    bip->u.int8 = (char *)bu_malloc( obj_length, "binary uniform object" );
    memcpy(bip->u.int8, bu_fd->buf, obj_length);

    bu_close_mapped_file( bu_fd );

    /* create the rt_internal form */
    RT_INIT_DB_INTERNAL( &intern );
    intern.idb_major_type = major_type;
    intern.idb_minor_type = minor_type;
    intern.idb_ptr = (genptr_t)bip;
    intern.idb_meth = &rt_functab[ID_BINUNIF];

    /* create body portion of external form */
    if ( intern.idb_meth->ft_export5( &body, &intern, 1.0, wdbp->dbip, wdbp->wdb_resp, intern.idb_minor_type ) ) {

	bu_log( "Error while attemptimg to export %s\n", obj_name );
	rt_db_free_internal( &intern, wdbp->wdb_resp );
	return -1;
    }

    /* create entire external form */
    db5_export_object3( &bin_ext, DB5HDR_HFLAGS_DLI_APPLICATION_DATA_OBJECT,
			obj_name, 0, NULL, &body,
			intern.idb_major_type, intern.idb_minor_type,
			DB5_ZZZ_UNCOMPRESSED, DB5_ZZZ_UNCOMPRESSED );

    rt_db_free_internal( &intern, wdbp->wdb_resp );
    bu_free_external( &body );

    /* add this object to the directory */
    if ( (dp=db_diradd5( wdbp->dbip, obj_name, -1, major_type,
			 minor_type, 0, 0, NULL )) == DIR_NULL ) {
	bu_log( "Error while attemptimg to add new name (%s) to the database",
		obj_name );
	bu_free_external( &bin_ext );
	return -1;
    }

    /* and write it to the database */
    if ( db_put_external5( &bin_ext, dp, wdbp->dbip ) ) {
	bu_log( "Error while adding new binary object (%s) to the database",
		obj_name );
	bu_free_external( &bin_ext );
	return -1;
    }

    bu_free_external( &bin_ext );

    return 0;
}