Exemplo n.º 1
0
int security_load_booleans(char *path)
{
	FILE *boolf;
	char *inbuf;
	char localbools[BUFSIZ];
	size_t len = 0, errors = 0;
	int val;
	char name[BUFSIZ];

	boolf = fopen(path ? path : selinux_booleans_path(), "r");
	if (boolf == NULL)
		goto localbool;

	__fsetlocking(boolf, FSETLOCKING_BYCALLER);
	while (getline(&inbuf, &len, boolf) > 0) {
		int ret = process_boolean(inbuf, name, sizeof(name), &val);
		if (ret == -1)
			errors++;
		if (ret == 1)
			if (security_set_boolean(name, val) < 0) {
				errors++;
			}
	}
	fclose(boolf);
      localbool:
	snprintf(localbools, sizeof(localbools), "%s.local",
		 (path ? path : selinux_booleans_path()));
	boolf = fopen(localbools, "r");

	if (boolf != NULL) {
		int ret;
		__fsetlocking(boolf, FSETLOCKING_BYCALLER);
		while (getline(&inbuf, &len, boolf) > 0) {
			ret = process_boolean(inbuf, name, sizeof(name), &val);
			if (ret == -1)
				errors++;
			if (ret == 1)
				if (security_set_boolean(name, val) < 0) {
					errors++;
				}
		}
		fclose(boolf);
	}
	if (security_commit_booleans() < 0)
		return -1;

	if (errors)
		errno = EINVAL;
	return errors ? -1 : 0;
}
Exemplo n.º 2
0
/*
 *  Called from db_walk_tree().
 *
 *  This routine must be prepared to run in parallel.
 */
union tree *do_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, void *UNUSED(client_data))
{
    union tree		*ret_tree;
    struct bu_list		vhead;
    struct nmgregion	*r;

    RT_CK_FULL_PATH(pathp);
    RT_CK_TREE(curtree);
    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);

    BU_LIST_INIT(&vhead);

    {
	char	*sofar = db_path_to_string(pathp);
	bu_log("\ndo_region_end(%d %d%%) %s\n",
	       regions_tried,
	       regions_tried>0 ? (regions_converted * 100) / regions_tried : 0,
	       sofar);
	bu_free(sofar, "path string");
    }

    if (curtree->tr_op == OP_NOP)
	return curtree;

    regions_tried++;

    if (verbose)
	bu_log("Attempting to process region %s\n", db_path_to_string(pathp));

    ret_tree= process_boolean(curtree, tsp, pathp);

    if (ret_tree)
	r = ret_tree->tr_d.td_r;
    else
    {
	if (verbose)
	    bu_log("\tNothing left of this region after Boolean evaluation\n");
	regions_written++; /* don't count as a failure */
	r = (struct nmgregion *)NULL;
    }

    regions_converted++;

    if (r != (struct nmgregion *)NULL)
    {
	struct shell *s;
	int empty_region=0;
	int empty_model=0;

	/* Kill cracks */
	s = BU_LIST_FIRST(shell, &r->s_hd);
	while (BU_LIST_NOT_HEAD(&s->l, &r->s_hd))
	{
	    struct shell *next_s;

	    next_s = BU_LIST_PNEXT(shell, &s->l);
	    if (nmg_kill_cracks(s))
	    {
		if (nmg_ks(s))
		{
		    empty_region = 1;
		    break;
		}
	    }
	    s = next_s;
	}

	/* kill zero length edgeuses */
	if (!empty_region) {
	    empty_model = nmg_kill_zero_length_edgeuses(*tsp->ts_m);
	}

	if (!empty_region && !empty_model) {
	    process_triangulation(r, pathp, tsp);

	    regions_written++;
	}

	if (!empty_model)
	    nmg_kr(r);
    }

    /*
     *  Dispose of original tree, so that all associated dynamic
     *  memory is released now, not at the end of all regions.
     *  A return of TREE_NULL from this routine signals an error,
     *  and there is no point to adding _another_ message to our output,
     *  so we need to cons up an OP_NOP node to return.
     */


    db_free_tree(curtree, &rt_uniresource);		/* Does an nmg_kr() */

    BU_ALLOC(curtree, union tree);
    RT_TREE_INIT(curtree);
    curtree->tr_op = OP_NOP;
    return curtree;
}
Exemplo n.º 3
0
static int save_booleans(size_t boolcnt, SELboolean * boollist)
{
	ssize_t len;
	size_t i;
	char outbuf[BUFSIZ];
	char *inbuf = NULL;

	/* Open file */
	const char *bool_file = selinux_booleans_path();
	char local_bool_file[PATH_MAX];
	char tmp_bool_file[PATH_MAX];
	FILE *boolf;
	int fd;
	int *used = (int *)malloc(sizeof(int) * boolcnt);
	if (!used) {
		return -1;
	}
	/* zero out used field */
	for (i = 0; i < boolcnt; i++)
		used[i] = 0;

	snprintf(tmp_bool_file, sizeof(tmp_bool_file), "%s.XXXXXX", bool_file);
	fd = mkstemp(tmp_bool_file);
	if (fd < 0) {
		free(used);
		return -1;
	}

	snprintf(local_bool_file, sizeof(local_bool_file), "%s.local",
		 bool_file);
	boolf = fopen(local_bool_file, "r");
	if (boolf != NULL) {
		ssize_t ret;
		size_t size = 0;
		int val;
		char boolname[BUFSIZ];
		char *buffer;
		inbuf = NULL;
		__fsetlocking(boolf, FSETLOCKING_BYCALLER);
		while ((len = getline(&inbuf, &size, boolf)) > 0) {
			buffer = strdup(inbuf);
			if (!buffer)
				goto close_remove_fail;
			ret =
			    process_boolean(inbuf, boolname, sizeof(boolname),
					    &val);
			if (ret != 1) {
				ret = write(fd, buffer, len);
				free(buffer);
				if (ret != len)
					goto close_remove_fail;
			} else {
				free(buffer);
				for (i = 0; i < boolcnt; i++) {
					if (strcmp(boollist[i].name, boolname)
					    == 0) {
						snprintf(outbuf, sizeof(outbuf),
							 "%s=%d\n", boolname,
							 boollist[i].value);
						len = strlen(outbuf);
						used[i] = 1;
						if (write(fd, outbuf, len) !=
						    len)
							goto close_remove_fail;
						else
							break;
					}
				}
				if (i == boolcnt) {
					snprintf(outbuf, sizeof(outbuf),
						 "%s=%d\n", boolname, val);
					len = strlen(outbuf);
					if (write(fd, outbuf, len) != len)
						goto close_remove_fail;
				}
			}
			free(inbuf);
			inbuf = NULL;
		}
		fclose(boolf);
	}

	for (i = 0; i < boolcnt; i++) {
		if (used[i] == 0) {
			snprintf(outbuf, sizeof(outbuf), "%s=%d\n",
				 boollist[i].name, boollist[i].value);
			len = strlen(outbuf);
			if (write(fd, outbuf, len) != len) {
			      close_remove_fail:
				free(inbuf);
				close(fd);
			      remove_fail:
				unlink(tmp_bool_file);
				free(used);
				return -1;
			}
		}

	}
	if (fchmod(fd, S_IRUSR | S_IWUSR) != 0)
		goto close_remove_fail;
	close(fd);
	if (rename(tmp_bool_file, local_bool_file) != 0)
		goto remove_fail;

	free(used);
	return 0;
}
Exemplo n.º 4
0
static int load_booleans(struct policydb *policydb, const char *path,
			 int *changesp)
{
	FILE *boolf;
	char *buffer = NULL;
	size_t size = 0;
	char localbools[BUFSIZ];
	char name[BUFSIZ];
	int val;
	int errors = 0, changes = 0;
	struct cond_bool_datum *datum;

	boolf = fopen(path, "r");
	if (boolf == NULL)
		goto localbool;

#ifdef DARWIN
        if ((buffer = (char *)malloc(255 * sizeof(char))) == NULL) {
          ERR(NULL, "out of memory");
	  return -1;
	}

        while(fgets(buffer, 255, boolf) != NULL) {
#else
	while (getline(&buffer, &size, boolf) > 0) {
#endif
		int ret = process_boolean(buffer, name, sizeof(name), &val);
		if (ret == -1)
			errors++;
		if (ret == 1) {
			datum = hashtab_search(policydb->p_bools.table, name);
			if (!datum) {
				ERR(NULL, "unknown boolean %s", name);
				errors++;
				continue;
			}
			if (datum->state != val) {
				datum->state = val;
				changes++;
			}
		}
	}
	fclose(boolf);
      localbool:
	snprintf(localbools, sizeof(localbools), "%s.local", path);
	boolf = fopen(localbools, "r");
	if (boolf != NULL) {

#ifdef DARWIN

	  while(fgets(buffer, 255, boolf) != NULL) {
#else

	    while (getline(&buffer, &size, boolf) > 0) {
#endif
			int ret =
			    process_boolean(buffer, name, sizeof(name), &val);
			if (ret == -1)
				errors++;
			if (ret == 1) {
				datum =
				    hashtab_search(policydb->p_bools.table,
						   name);
				if (!datum) {
					ERR(NULL, "unknown boolean %s", name);
					errors++;
					continue;
				}
				if (datum->state != val) {
					datum->state = val;
					changes++;
				}
			}
		}
		fclose(boolf);
	}
	free(buffer);
	if (errors)
		errno = EINVAL;
	*changesp = changes;
	return errors ? -1 : 0;
}

int sepol_genbools(void *data, size_t len, char *booleans)
{
	struct policydb policydb;
	struct policy_file pf;
	int rc, changes = 0;

	if (policydb_init(&policydb))
		goto err;
	if (policydb_from_image(NULL, data, len, &policydb) < 0)
		goto err;

	if (load_booleans(&policydb, booleans, &changes) < 0) {
		WARN(NULL, "error while reading %s", booleans);
	}

	if (!changes)
		goto out;

	if (evaluate_conds(&policydb) < 0) {
		ERR(NULL, "error while re-evaluating conditionals");
		errno = EINVAL;
		goto err_destroy;
	}

	policy_file_init(&pf);
	pf.type = PF_USE_MEMORY;
	pf.data = data;
	pf.len = len;
	rc = policydb_write(&policydb, &pf);
	if (rc) {
		ERR(NULL, "unable to write new binary policy image");
		errno = EINVAL;
		goto err_destroy;
	}

      out:
	policydb_destroy(&policydb);
	return 0;

      err_destroy:
	policydb_destroy(&policydb);

      err:
	return -1;
}

int hidden sepol_genbools_policydb(policydb_t * policydb, const char *booleans)
{
	int rc, changes = 0;

	rc = load_booleans(policydb, booleans, &changes);
	if (!rc && changes)
		rc = evaluate_conds(policydb);
	if (rc)
		errno = EINVAL;
	return rc;
}

/* -- End Deprecated -- */

int sepol_genbools_array(void *data, size_t len, char **names, int *values,
			 int nel)
{
	struct policydb policydb;
	struct policy_file pf;
	int rc, i, errors = 0;
	struct cond_bool_datum *datum;

	/* Create policy database from image */
	if (policydb_init(&policydb))
		goto err;
	if (policydb_from_image(NULL, data, len, &policydb) < 0)
		goto err;

	for (i = 0; i < nel; i++) {
		datum = hashtab_search(policydb.p_bools.table, names[i]);
		if (!datum) {
			ERR(NULL, "boolean %s no longer in policy", names[i]);
			errors++;
			continue;
		}
		if (values[i] != 0 && values[i] != 1) {
			ERR(NULL, "illegal value %d for boolean %s",
			    values[i], names[i]);
			errors++;
			continue;
		}
		datum->state = values[i];
	}

	if (evaluate_conds(&policydb) < 0) {
		ERR(NULL, "error while re-evaluating conditionals");
		errno = EINVAL;
		goto err_destroy;
	}

	policy_file_init(&pf);
	pf.type = PF_USE_MEMORY;
	pf.data = data;
	pf.len = len;
	rc = policydb_write(&policydb, &pf);
	if (rc) {
		ERR(NULL, "unable to write binary policy");
		errno = EINVAL;
		goto err_destroy;
	}
	if (errors) {
		errno = EINVAL;
		goto err_destroy;
	}

	policydb_destroy(&policydb);
	return 0;

      err_destroy:
	policydb_destroy(&policydb);

      err:
	return -1;
}
Exemplo n.º 5
0
static int global_ini_callback(const char *section, const char *name, const char *value)
{
    //fprintf(stdout, "[%s] '%s'='%s'\n", section, name, value);

    #define check_ini_section(section_name)    (strcasecmp(section, section_name) == 0)

    // Make sure that we return successfully as soon as name matches the correct option_name
    #define process_word(option_name, target, value_names)                           \
    if (ini_process_word(name, value, option_name, target, value_names)) return 1;

    #define process_short(option_name, target, value_names)                           \
    if (ini_process_short(name, value, option_name, target, value_names)) return 1;

    #define process_byte(option_name, target, value_names)                           \
    if (ini_process_byte(name, value, option_name, target, value_names)) return 1;

    #define process_boolean(option_name, target)                        \
    if (ini_process_boolean(name, value, option_name, target)) return 1;

    if (check_ini_section("General")) {
        process_boolean("enable_copyprot", &options.enable_copyprot);
        process_boolean("enable_mixer", &options.enable_mixer);
        process_boolean("enable_fade", &options.enable_fade);
        process_boolean("enable_flash", &options.enable_flash);
        process_boolean("enable_text", &options.enable_text);
        process_boolean("start_fullscreen", &start_fullscreen);
        process_word("pop_window_width", &pop_window_width, NULL);
        process_word("pop_window_height", &pop_window_height, NULL);
        process_boolean("use_correct_aspect_ratio", &options.use_correct_aspect_ratio);

        if (strcasecmp(name, "levelset") == 0) {
            if (value[0] == '\0' || strcasecmp(value, "original") == 0 || strcasecmp(value, "default") == 0) {
                use_custom_levelset = 0;
            } else {
                use_custom_levelset = 1;
                strcpy(levelset_name, value);
            }
            return 1;
        }
    }

    if (check_ini_section("AdditionalFeatures")) {
        process_boolean("enable_quicksave", &options.enable_quicksave);
        process_boolean("enable_quicksave_penalty", &options.enable_quicksave_penalty);
        process_boolean("enable_replay", &options.enable_replay);
    }

    if (check_ini_section("Enhancements")) {
        if (strcasecmp(name, "use_fixes_and_enhancements") == 0) {
            if (strcasecmp(value, "true") == 0) options.use_fixes_and_enhancements = 1;
            else if (strcasecmp(value, "false") == 0) options.use_fixes_and_enhancements = 0;
            else if (strcasecmp(value, "prompt") == 0) options.use_fixes_and_enhancements = 2;
            return 1;
        }
        process_boolean("enable_crouch_after_climbing", &options.enable_crouch_after_climbing);
        process_boolean("enable_freeze_time_during_end_music", &options.enable_freeze_time_during_end_music);
        process_boolean("enable_remember_guard_hp", &options.enable_remember_guard_hp);
        process_boolean("fix_gate_sounds", &options.fix_gate_sounds);
        process_boolean("fix_two_coll_bug", &options.fix_two_coll_bug);
        process_boolean("fix_infinite_down_bug", &options.fix_infinite_down_bug);
        process_boolean("fix_gate_drawing_bug", &options.fix_gate_drawing_bug);
        process_boolean("fix_bigpillar_climb", &options.fix_bigpillar_climb);
        process_boolean("fix_jump_distance_at_edge", &options.fix_jump_distance_at_edge);
        process_boolean("fix_edge_distance_check_when_climbing", &options.fix_edge_distance_check_when_climbing);
        process_boolean("fix_painless_fall_on_guard", &options.fix_painless_fall_on_guard);
        process_boolean("fix_wall_bump_triggers_tile_below", &options.fix_wall_bump_triggers_tile_below);
        process_boolean("fix_stand_on_thin_air", &options.fix_stand_on_thin_air);
        process_boolean("fix_press_through_closed_gates", &options.fix_press_through_closed_gates);
        process_boolean("fix_grab_falling_speed", &options.fix_grab_falling_speed);
        process_boolean("fix_skeleton_chomper_blood", &options.fix_skeleton_chomper_blood);
        process_boolean("fix_move_after_drink", &options.fix_move_after_drink);
        process_boolean("fix_loose_left_of_potion", &options.fix_loose_left_of_potion);
        process_boolean("fix_guard_following_through_closed_gates", &options.fix_guard_following_through_closed_gates);
        process_boolean("fix_safe_landing_on_spikes", &options.fix_safe_landing_on_spikes);
        process_boolean("fix_glide_through_wall", &options.fix_glide_through_wall);
        process_boolean("fix_drop_through_tapestry", &options.fix_drop_through_tapestry);
        process_boolean("fix_land_against_gate_or_tapestry", &options.fix_land_against_gate_or_tapestry);
    }

    if (check_ini_section("CustomGameplay")) {
        process_word("start_minutes_left", &start_minutes_left, NULL);
        process_word("start_ticks_left", &start_ticks_left, NULL);
        process_word("start_hitp", &start_hitp, NULL);
        process_word("max_hitp_allowed", &max_hitp_allowed, NULL);
        process_word("saving_allowed_first_level", &saving_allowed_first_level, NULL);
        process_word("saving_allowed_last_level", &saving_allowed_last_level, NULL);
        process_boolean("allow_triggering_any_tile", &allow_triggering_any_tile);
    }

    // [Level 1], etc.
    int ini_level = -1;
    if (strncasecmp(section, "Level ", 6) == 0 && sscanf(section+6, "%d", &ini_level) == 1) {
        if (ini_level >= 0 && ini_level <= 15) {
            // TODO: And maybe allow new types in addition to the existing ones.
            process_byte("level_type", &tbl_level_type[ini_level], &level_type_names_list);
            process_word("level_color", &tbl_level_color[ini_level], NULL);
            process_short("guard_type", &tbl_guard_type[ini_level], &guard_type_names_list);
            process_byte("guard_hp", &tbl_guard_hp[ini_level], NULL);
        } else {
            // TODO: warning?
        }
    }
    return 0;
}
Exemplo n.º 6
0
/*
 *			D O _ R E G I O N _ E N D
 *
 *  Called from db_walk_tree().
 *
 *  This routine must be prepared to run in parallel.
 */
union tree *do_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, genptr_t UNUSED(client_data))
{
    union tree		*ret_tree;
    struct nmgregion	*r;

    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);

    if (RT_G_DEBUG&DEBUG_TREEWALK || verbose) {
	char	*sofar = db_path_to_string(pathp);
	bu_log("\ndo_region_end(%d %d%%) %s\n",
	       regions_tried,
	       regions_tried>0 ? (regions_done * 100) / regions_tried : 0,
	       sofar);
	bu_free(sofar, "path string");
    }

    if (curtree->tr_op == OP_NOP)
	return curtree;

    regions_tried++;

    ret_tree = process_boolean(curtree, tsp, pathp);

    if ( ret_tree )
	r = ret_tree->tr_d.td_r;
    else
	r = (struct nmgregion *)NULL;

    regions_done++;

    if (r != 0) {
	FILE	*fp_psurf;
	size_t	i;
	struct bu_vls	file_base = BU_VLS_INIT_ZERO;
	struct bu_vls	file = BU_VLS_INIT_ZERO;

	bu_vls_strcpy(&file_base, prefix);
	bu_vls_strcat(&file_base, DB_FULL_PATH_CUR_DIR(pathp)->d_namep);
	/* Dots confuse Jack's Peabody language.  Change to '_'. */
	for (i = 0; i < file_base.vls_len; i++)
	    if (file_base.vls_str[i] == '.')
		file_base.vls_str[i] = '_';

	/* Write color attribute to .fig figure file. */
	if (tsp->ts_mater.ma_color_valid != 0) {
	    fprintf(fp_fig, "\tattribute %s {\n",
		    bu_vls_addr(&file_base));
	    fprintf(fp_fig, "\t\trgb = (%f, %f, %f);\n",
		    V3ARGS(tsp->ts_mater.ma_color));
	    fprintf(fp_fig, "\t\tambient = 0.18;\n");
	    fprintf(fp_fig, "\t\tdiffuse = 0.72;\n");
	    fprintf(fp_fig, "\t}\n");
	}

	/* Write segment attributes to .fig figure file. */
	fprintf(fp_fig, "\tsegment %s_seg {\n", bu_vls_addr(&file_base));
	fprintf(fp_fig, "\t\tpsurf=\"%s.pss\";\n", bu_vls_addr(&file_base));
	if (tsp->ts_mater.ma_color_valid != 0)
	    fprintf(fp_fig,
		    "\t\tattribute=%s;\n", bu_vls_addr(&file_base));
	fprintf(fp_fig, "\t\tsite base->location=trans(0, 0, 0);\n");
	fprintf(fp_fig, "\t}\n");

	if ( bu_vls_strlen(&base_seg) <= 0 )  {
	    bu_vls_vlscat( &base_seg, &file_base );
	} else {
	    fprintf(fp_fig, "\tjoint %s_jt {\n",
		    bu_vls_addr(&file_base));
	    fprintf(fp_fig,
		    "\t\tconnect %s_seg.base to %s_seg.base;\n",
		    bu_vls_addr(&file_base),
		    bu_vls_addr(&base_seg) );
	    fprintf(fp_fig, "\t}\n");
	}

	bu_vls_vlscat(&file, &file_base);
	bu_vls_strcat(&file, ".pss");	/* Required Jack suffix. */

	/* Write psurf to .pss file. */
	if ((fp_psurf = fopen(bu_vls_addr(&file), "wb")) == NULL)
	    perror(bu_vls_addr(&file));
	else {
	    nmg_to_psurf(r, fp_psurf);
	    fclose(fp_psurf);
	    if (verbose) bu_log("*** Wrote %s\n", bu_vls_addr(&file));
	}
	bu_vls_free(&file);

	/* Also write as UNIX-plot file, if desired */
	if ( debug_plots )  {
	    FILE	*fp;
	    bu_vls_vlscat(&file, &file_base);
	    bu_vls_strcat(&file, ".pl");

	    if ((fp = fopen(bu_vls_addr(&file), "wb")) == NULL)
		perror(bu_vls_addr(&file));
	    else {
		struct bu_list	vhead;
		pl_color( fp,
			  (int)(tsp->ts_mater.ma_color[0] * 255),
			  (int)(tsp->ts_mater.ma_color[1] * 255),
			  (int)(tsp->ts_mater.ma_color[2] * 255) );
		/* nmg_pl_r( fp, r ); */
		BU_LIST_INIT( &vhead );
		nmg_r_to_vlist( &vhead, r, 0 );
		rt_vlist_to_uplot( fp, &vhead );
		fclose(fp);
		if (verbose) bu_log("*** Wrote %s\n", bu_vls_addr(&file));
	    }
	    bu_vls_free(&file);
	}

	/* NMG region is no longer necessary */
	nmg_kr(r);
    }

    /*
     *  Dispose of original tree, so that all associated dynamic
     *  memory is released now, not at the end of all regions.
     *  A return of TREE_NULL from this routine signals an error,
     *  so we need to cons up an OP_NOP node to return.
     */
    db_free_tree(curtree, &rt_uniresource);		/* Does an nmg_kr() */

    BU_ALLOC(curtree, union tree);
    RT_TREE_INIT(curtree);
    curtree->tr_op = OP_NOP;
    return curtree;
}
Exemplo n.º 7
0
union tree *
nmg_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, void *UNUSED(client_data))
{
    struct nmgregion	*r;
    struct bu_list		vhead;
    union tree		*ret_tree;
    char			*name;

    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);

    BARRIER_CHECK;
    BU_LIST_INIT(&vhead);

    if (RT_G_DEBUG&DEBUG_TREEWALK || verbose) {
	bu_log("\nConverted %d%% so far (%d of %d)\n",
	       regions_tried>0 ? (regions_converted * 100) / regions_tried : 0,
	       regions_converted, regions_tried );
    }

    if (curtree->tr_op == OP_NOP)
	return curtree;

    name = db_path_to_string( pathp );
    bu_log( "Attempting %s\n", name );

    regions_tried++;

    ret_tree = process_boolean(curtree, tsp, pathp);

    if ( ret_tree )
	r = ret_tree->tr_d.td_r;
    else
	r = (struct nmgregion *)NULL;

    bu_free( name, "db_path_to_string" );
    regions_converted++;
    if (r != (struct nmgregion *)NULL)
    {
	struct shell *s;
	int empty_region=0;
	int empty_model=0;

	/* Kill cracks */
	s = BU_LIST_FIRST( shell, &r->s_hd );
	while ( BU_LIST_NOT_HEAD( &s->l, &r->s_hd ) )
	{
	    struct shell *next_s;

	    next_s = BU_LIST_PNEXT( shell, &s->l );
	    if ( nmg_kill_cracks( s ) )
	    {
		if ( nmg_ks( s ) )
		{
		    empty_region = 1;
		    break;
		}
	    }
	    s = next_s;
	}

	/* kill zero length edgeuses */
	if ( !empty_region )
	{
	    empty_model = nmg_kill_zero_length_edgeuses( *tsp->ts_m );
	}

	if ( !empty_region && !empty_model )
	{
	    /* Write the nmgregion to the output file */
	    nmg_2_vrml( outfp, pathp, r->m_p, &tsp->ts_mater );
	}

	/* NMG region is no longer necessary */
	if ( !empty_model )
	    nmg_kr(r);

    }
    else
	bu_log( "WARNING: Nothing left after Boolean evaluation of %s\n",
		db_path_to_string( pathp ) );

    /*
     *  Dispose of original tree, so that all associated dynamic
     *  memory is released now, not at the end of all regions.
     *  A return of TREE_NULL from this routine signals an error,
     *  so we need to cons up an OP_NOP node to return.
     */
    db_free_tree(curtree, &rt_uniresource);		/* Does an nmg_kr() */

    BU_ALLOC(curtree, union tree);
    RT_TREE_INIT(curtree);
    curtree->tr_op = OP_NOP;
    BARRIER_CHECK;
    return curtree;
}
Exemplo n.º 8
0
/*
 *  Called from db_walk_tree().
 *
 *  This routine must be prepared to run in parallel.
 */
union tree *
do_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, void *UNUSED(client_data))
{
    struct nmgregion	*r;
    struct bu_list	vhead;
    union tree		*ret_tree;

    if (verbose)
	bu_log("do_region_end: regionid = %d\n", tsp->ts_regionid);

    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);

    BU_LIST_INIT(&vhead);

    if (RT_G_DEBUG&DEBUG_TREEWALK || verbose) {
	char	*sofar = db_path_to_string(pathp);
	bu_log("\ndo_region_end(%d %d%%) %s\n",
	       regions_tried,
	       regions_tried>0 ? (regions_converted * 100) / regions_tried : 0,
	       sofar);
	bu_free(sofar, "path string");
    }

    if (curtree->tr_op == OP_NOP)
	return curtree;

    regions_tried++;

    if (verbose)
	bu_log("\tEvaluating region\n");

    ret_tree = process_boolean(curtree, tsp, pathp);

    if (ret_tree)
	r = ret_tree->tr_d.td_r;
    else
	r = (struct nmgregion *)NULL;

    regions_converted++;
    if (r != (struct nmgregion *)NULL) {
	struct shell *s;
	int empty_region = 0;
	int empty_model = 0;

	/* Kill cracks */
	s = BU_LIST_FIRST(shell, &r->s_hd);
	while (BU_LIST_NOT_HEAD(&s->l, &r->s_hd)) {
	    struct shell *next_s;

	    next_s = BU_LIST_PNEXT(shell, &s->l);
	    if (nmg_kill_cracks(s)) {
		if (nmg_ks(s)) {
		    empty_region = 1;
		    break;
		}
	    }
	    s = next_s;
	}

	/* kill zero length edgeuses */
	if (!empty_region) {
	    empty_model = nmg_kill_zero_length_edgeuses(*tsp->ts_m);
	}

	if (!empty_region && !empty_model) {
	    /* Write the region to the EUCLID file */
	    Write_euclid_region(r, tsp);
	}

	if (!empty_model)
	    nmg_kr(r);
    }

    /*
     *  Dispose of original tree, so that all associated dynamic
     *  memory is released now, not at the end of all regions.
     *  A return of TREE_NULL from this routine signals an error,
     *  so we need to cons up an OP_NOP node to return.
     */
    db_free_tree(curtree, &rt_uniresource);		/* Does an nmg_kr() */

    BU_ALLOC(curtree, union tree);
    RT_TREE_INIT(curtree);
    curtree->tr_op = OP_NOP;
    return curtree;
}
Exemplo n.º 9
0
/*
 * Called from db_walk_tree().
 *
 * This routine must be prepared to run in parallel.
 */
union tree *
do_nmg_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, void *UNUSED(client_data))
{
    union tree *result;
    struct nmgregion *r;
    struct bu_list vhead;
    struct directory *dp;
    int dependent;
    size_t i;

    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);

    BU_LIST_INIT(&vhead);

    if (RT_G_DEBUG&DEBUG_TREEWALK || verbose) {
	char *sofar = db_path_to_string(pathp);
	bu_log("\ndo_nmg_region_end(%d %d%%) %s\n",
	       regions_tried,
	       regions_tried>0 ? (regions_done * 100) / regions_tried : 0,
	       sofar);
	bu_free(sofar, "path string");
    }

    if (curtree->tr_op == OP_NOP)
	return curtree;

    regions_tried++;

    if (verbose)
	bu_log("\ndoing boolean tree evaluate...\n");

    /* evaluate the boolean */
    result = process_boolean(tsp, curtree, pathp);

    if (result)
	r = result->tr_d.td_r;
    else
	r = (struct nmgregion *)NULL;

    if (verbose)
	bu_log("\nfinished boolean tree evaluate...\n");

    regions_done++;
    if (r != NULL) {

	dp = DB_FULL_PATH_CUR_DIR(pathp);

	if (multi_file) {
	    /* Open the output file */
	    if (output_file == NULL)
		fp_dir = stdout;
	    else {
		char *multi_name;
		size_t len;
		int unique = 0;
		char suffix[SUFFIX_LEN+1];

		/* construct a unique file name */
		len = strlen(output_file) + strlen(dp->d_namep) + 6 + SUFFIX_LEN;
		multi_name = (char *)bu_malloc(sizeof(char)*len, "multi_name");
		snprintf(multi_name, len, "%s/%s.igs", output_file, dp->d_namep);
		bu_strlcpy(suffix, "a", sizeof(suffix));
		suffix[0]--;
		while (!unique) {
		    if (bu_file_readable(multi_name)) {
			unique = 1;
			break;
		    }

		    /* not unique, try adding a suffix */
		    len = strlen(suffix);
		    i = len - 1;
		    suffix[i]++;
		    while (suffix[i] > 'z' && i > 0) {
			suffix[i] = 'a';
			i--;
			suffix[i]++;
		    }

		    if (suffix[0] > 'z' && len < SUFFIX_LEN) {
			for (i = 0; i <= len; i++)
			    suffix[i] = 'a';
		    } else if (suffix[0] > 'z' && len >= SUFFIX_LEN) {
			bu_log("too many files with the same name (%s)\n", dp->d_namep);
			bu_exit(1, "Cannot create a unique filename, \n");
		    }
		    snprintf(multi_name, len, "%s/%s%s.igs", output_file, dp->d_namep, suffix);
		}
		if ((fp_dir = fopen(multi_name, "wb")) == NULL) {
		    perror("g-iges");
		    bu_exit(1, "Cannot open output file: %s\n", multi_name);
		}
	    }

	    /* Open the temporary file for the parameter section */
	    if ((fp_param = bu_temp_file(NULL, 0)) == NULL) {
		perror("g-iges");
		bu_exit(1, "Cannot open temporary file\n");
	    }

	    /* let the IGES routines know the selected tolerances and the database pointer */
	    iges_init(&tol, &ttol, verbose, DBIP);

	    /* Write start and global sections of the IGES file */
	    w_start_global(fp_dir, fp_param, db_name, prog_name, output_file, __DATE__, brlcad_version());
	}

	if (mode == FACET_MODE) {
	    dependent = 1;
	    for (i = 0; i < no_of_indeps; i++) {
		if (!bu_strncmp(dp->d_namep, independent[i], NAMESIZE+1)) {
		    dependent = 0;
		    break;
		}
	    }

	    dp->d_uses = (-nmgregion_to_iges(dp->d_namep, r, dependent, fp_dir, fp_param));
	} else if (mode == TRIMMED_SURF_MODE)
	    dp->d_uses = (-nmgregion_to_tsurf(dp->d_namep, r, fp_dir, fp_param));

	/* NMG region is no longer necessary */
	nmg_kr(r);

	if (multi_file) {
	    char copy_buffer[CP_BUF_SIZE] = {0};

	    /* Copy the parameter section from the temporary file to the output file */
	    if ((bu_fseek(fp_param, 0, 0))) {
		perror("g-iges");
		bu_exit(1, "Cannot seek to start of temporary file\n");
	    }

	    while ((i = fread(copy_buffer, 1, CP_BUF_SIZE, fp_param)))
		if (fwrite(copy_buffer, 1, i, fp_dir) != i) {
		    perror("g-iges");
		    bu_exit(1, "Error in copying parameter data to %s\n", output_file);
		}

	    /* Write the terminate section */
	    w_terminate(fp_dir);
	    fclose(fp_dir);
	    fclose(fp_param);
	}
    }

    /*
     * Dispose of original tree, so that all associated dynamic
     * memory is released now, not at the end of all regions.
     * A return of TREE_NULL from this routine signals an error,
     * so we need to cons up an OP_NOP node to return.
     */
    db_free_tree(curtree, &rt_uniresource);		/* Does an nmg_kr() */

    BU_ALLOC(curtree, union tree);
    RT_TREE_INIT(curtree);
    curtree->tr_op = OP_NOP;
    return curtree;
}
Exemplo n.º 10
0
/**
 * This routine must be prepared to run in parallel.
 */
static union tree *
draw_nmg_region_end(struct db_tree_state *tsp, const struct db_full_path *pathp, union tree *curtree, void *client_data)
{
    struct nmgregion *r;
    struct bu_list vhead;
    int failed;
    struct _ged_client_data *dgcdp = (struct _ged_client_data *)client_data;

    RT_CK_TESS_TOL(tsp->ts_ttol);
    BN_CK_TOL(tsp->ts_tol);
    NMG_CK_MODEL(*tsp->ts_m);
    RT_CK_RESOURCE(tsp->ts_resp);

    BU_LIST_INIT(&vhead);

    if (RT_G_DEBUG&DEBUG_TREEWALK) {
	char *sofar = db_path_to_string(pathp);

	bu_vls_printf(dgcdp->gedp->ged_result_str, "nmg_region_end() path='%s'\n", sofar);
	bu_free((void *)sofar, "path string");
    } else {
	char *sofar = db_path_to_string(pathp);

	bu_vls_printf(dgcdp->gedp->ged_result_str, "%s:\n", sofar);
	bu_free((void *)sofar, "path string");
    }

    if (curtree->tr_op == OP_NOP) return curtree;

    failed = 1;
    if (!dgcdp->draw_nmg_only) {

	failed = process_boolean(curtree, tsp, pathp, dgcdp);
	if (failed) {
	    db_free_tree(curtree, tsp->ts_resp);
	    return (union tree *)NULL;
	}

    } else if (curtree->tr_op != OP_NMG_TESS) {
	bu_vls_printf(dgcdp->gedp->ged_result_str, "Cannot use '-d' option when Boolean evaluation is required\n");
	db_free_tree(curtree, tsp->ts_resp);
	return (union tree *)NULL;
    }
    r = curtree->tr_d.td_r;
    NMG_CK_REGION(r);

    if (dgcdp->do_not_draw_nmg_solids_during_debugging && r) {
	db_free_tree(curtree, tsp->ts_resp);
	return (union tree *)NULL;
    }

    if (dgcdp->nmg_triangulate) {
	failed = process_triangulation(tsp, pathp, dgcdp);
	if (failed) {
	    db_free_tree(curtree, tsp->ts_resp);
	    return (union tree *)NULL;
	}
    }

    if (r != 0) {
	int style;
	/* Convert NMG to vlist */
	NMG_CK_REGION(r);

	if (dgcdp->draw_wireframes) {
	    /* Draw in vector form */
	    style = NMG_VLIST_STYLE_VECTOR;
	} else {
	    /* Default -- draw polygons */
	    style = NMG_VLIST_STYLE_POLYGON;
	}
	if (dgcdp->draw_normals) {
	    style |= NMG_VLIST_STYLE_VISUALIZE_NORMALS;
	}
	if (dgcdp->shade_per_vertex_normals) {
	    style |= NMG_VLIST_STYLE_USE_VU_NORMALS;
	}
	if (dgcdp->draw_no_surfaces) {
	    style |= NMG_VLIST_STYLE_NO_SURFACES;
	}
	nmg_r_to_vlist(&vhead, r, style);

	_ged_drawH_part2(0, &vhead, pathp, tsp, dgcdp);

	if (dgcdp->draw_edge_uses) {
	    nmg_vlblock_r(dgcdp->draw_edge_uses_vbp, r, 1);
	}
	/* NMG region is no longer necessary, only vlist remains */
	db_free_tree(curtree, tsp->ts_resp);
	return (union tree *)NULL;
    }

    /* Return tree -- it needs to be freed (by caller) */
    return curtree;
}