1 /* PSPP - a program for statistical analysis.
2 Copyright (C) 1997-9, 2000, 2006, 2007, 2009, 2010, 2011, 2015 Free Software Foundation, Inc.
4 This program is free software: you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation, either version 3 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program. If not, see <http://www.gnu.org/licenses/>. */
19 #include "data/settings.h"
24 #include "data/case.h"
25 #include "data/format.h"
26 #include "data/value.h"
27 #include "libpspp/i18n.h"
28 #include "libpspp/integer-format.h"
29 #include "libpspp/message.h"
31 #include "gl/minmax.h"
32 #include "gl/xalloc.h"
35 #define _(msgid) gettext (msgid)
39 /* Integer format used for IB and PIB input. */
40 enum integer_format input_integer_format;
42 /* Floating-point format used for RB and RBHEX input. */
43 enum float_format input_float_format;
45 /* Format of integers in output (SET WIB). */
46 enum integer_format output_integer_format;
48 /* Format of reals in output (SET WRB). */
49 enum float_format output_float_format;
51 /* MATRIX...END MATRIX settings. */
52 enum settings_mdisplay mdisplay;
58 bool route_errors_to_terminal;
59 bool route_errors_to_listing;
63 int max_messages[MSG_N_SEVERITIES];
67 bool mexpand; /* Expand macros? */
68 bool mprint; /* Print macro expansions? */
69 int miterate; /* Maximum iterations of !FOR. */
70 int mnest; /* Maximum nested macro expansion levels. */
74 struct fmt_spec default_format;
83 struct fmt_settings styles;
86 enum settings_output_devices output_routing[SETTINGS_N_OUTPUT_TYPES];
88 enum settings_value_show show_values;
89 enum settings_value_show show_variables;
92 static struct settings the_settings = {
93 .input_integer_format = INTEGER_NATIVE,
94 .input_float_format = FLOAT_NATIVE_DOUBLE,
95 .output_integer_format = INTEGER_NATIVE,
96 .output_float_format = FLOAT_NATIVE_DOUBLE,
97 .mdisplay = SETTINGS_MDISPLAY_TEXT,
102 .route_errors_to_terminal = true,
103 .route_errors_to_listing = true,
110 [MSG_S_WARNING] = 100,
122 .workspace = 64L * 1024 * 1024,
123 .default_format = { .type = FMT_F, .w = 8, .d = 2 },
124 .testing_mode = false,
127 .cmd_algorithm = ENHANCED,
128 .global_algorithm = ENHANCED,
130 .styles = FMT_SETTINGS_INIT,
135 #define LT (SETTINGS_DEVICE_LISTING | SETTINGS_DEVICE_TERMINAL)
136 [SETTINGS_OUTPUT_ERROR] = LT,
137 [SETTINGS_OUTPUT_NOTE] = LT,
138 [SETTINGS_OUTPUT_SYNTAX] = 0,
139 [SETTINGS_OUTPUT_RESULT] = LT
143 .show_values = SETTINGS_VALUE_SHOW_LABEL,
144 .show_variables = SETTINGS_VALUE_SHOW_LABEL,
147 /* Initializes the settings module. */
151 settings_set_decimal_char (get_system_decimal ());
154 /* Cleans up the settings module. */
158 settings_destroy (&the_settings);
162 settings_copy (struct settings *dst, const struct settings *src)
165 dst->styles = fmt_settings_copy (&src->styles);
168 /* Returns a copy of the current settings. */
172 struct settings *s = xmalloc (sizeof *s);
173 settings_copy (s, &the_settings);
177 /* Replaces the current settings by those in S. The caller retains ownership
180 settings_set (const struct settings *s)
182 settings_destroy (&the_settings);
183 settings_copy (&the_settings, s);
188 settings_destroy (struct settings *s)
192 fmt_settings_uninit (&s->styles);
193 if (s != &the_settings)
198 /* Returns the floating-point format used for RB and RBHEX
201 settings_get_input_float_format (void)
203 return the_settings.input_float_format;
206 /* Sets the floating-point format used for RB and RBHEX input to
209 settings_set_input_float_format (enum float_format format)
211 the_settings.input_float_format = format;
214 /* Returns the integer format used for IB and PIB input. */
216 settings_get_input_integer_format (void)
218 return the_settings.input_integer_format;
221 /* Sets the integer format used for IB and PIB input to
224 settings_set_input_integer_format (enum integer_format format)
226 the_settings.input_integer_format = format;
229 /* Returns the current output integer format. */
231 settings_get_output_integer_format (void)
233 return the_settings.output_integer_format;
236 /* Sets the output integer format to INTEGER_FORMAT. */
238 settings_set_output_integer_format (
239 enum integer_format integer_format)
241 the_settings.output_integer_format = integer_format;
244 /* Returns the current output float format. */
246 settings_get_output_float_format (void)
248 return the_settings.output_float_format;
251 /* Sets the output float format to FLOAT_FORMAT. */
253 settings_set_output_float_format (enum float_format float_format)
255 the_settings.output_float_format = float_format;
258 /* Screen length in lines. */
260 settings_get_viewlength (void)
262 return the_settings.viewlength;
265 /* Sets the view length. */
267 settings_set_viewlength (int viewlength_)
269 the_settings.viewlength = viewlength_;
274 settings_get_viewwidth(void)
276 return the_settings.viewwidth;
279 /* Sets the screen width. */
281 settings_set_viewwidth (int viewwidth_)
283 the_settings.viewwidth = viewwidth_;
286 /* Whether PSPP can erase and overwrite files. */
288 settings_get_safer_mode (void)
290 return the_settings.safer_mode;
293 /* Set safer mode. */
295 settings_set_safer_mode (void)
297 the_settings.safer_mode = true;
300 /* If echo is on, whether commands from include files are echoed. */
302 settings_get_include (void)
304 return the_settings.include;
307 /* Set include file echo. */
309 settings_set_include (bool include)
311 the_settings.include = include;
314 /* Returns the year that starts the epoch. */
316 settings_get_epoch (void)
318 return the_settings.styles.epoch;
321 /* Sets the year that starts the epoch. */
323 settings_set_epoch (int epoch)
325 the_settings.styles.epoch = epoch;
328 /* Compress system files by default? */
330 settings_get_scompression (void)
332 return the_settings.scompress;
335 /* Set system file default compression. */
337 settings_set_scompression (bool scompress)
339 the_settings.scompress = scompress;
342 /* Whether to warn on undefined values in numeric data. */
344 settings_get_undefined (void)
346 return the_settings.undefined;
349 /* Set whether to warn on undefined values. */
351 settings_set_undefined (bool undefined)
353 the_settings.undefined = undefined;
356 /* The value that blank numeric fields are set to when read in. */
358 settings_get_blanks (void)
360 return the_settings.blanks;
363 /* Set the value that blank numeric fields are set to when read
366 settings_set_blanks (double blanks)
368 the_settings.blanks = blanks;
371 /* Returns the maximum number of messages to show of the given SEVERITY before
372 aborting. (The value for MSG_S_WARNING is interpreted as maximum number of
373 warnings and errors combined.) */
375 settings_get_max_messages (enum msg_severity severity)
377 assert (severity < MSG_N_SEVERITIES);
378 return the_settings.max_messages[severity];
381 /* Sets the maximum number of messages to show of the given SEVERITY before
382 aborting to MAX. (The value for MSG_S_WARNING is interpreted as maximum
383 number of warnings and errors combined.) In addition, in the case of
384 warnings the special value of zero indicates that no warnings are to be
388 settings_set_max_messages (enum msg_severity severity, int max)
390 assert (severity < MSG_N_SEVERITIES);
392 if (severity == MSG_S_WARNING)
397 _("MXWARNS set to zero. No further warnings will be given even when potentially problematic situations are encountered."));
398 msg_ui_disable_warnings (true);
400 else if (the_settings.max_messages [MSG_S_WARNING] == 0)
402 msg_ui_disable_warnings (false);
403 the_settings.max_messages[MSG_S_WARNING] = max;
404 msg (MW, _("Warnings re-enabled. %d warnings will be issued before aborting syntax processing."), max);
408 the_settings.max_messages[severity] = max;
411 /* Returns whether to expand macro invocations. */
413 settings_get_mexpand (void)
415 return the_settings.mexpand;
418 /* Sets whether to expand macro invocations. */
420 settings_set_mexpand (bool mexpand)
422 the_settings.mexpand = mexpand;
425 /* Independent of get_printback, controls whether the commands
426 generated by macro invocations are displayed. */
428 settings_get_mprint (void)
430 return the_settings.mprint;
433 /* Sets whether the commands generated by macro invocations are
436 settings_set_mprint (bool mprint)
438 the_settings.mprint = mprint;
441 /* Returns the limit for loop iterations within a macro. */
443 settings_get_miterate (void)
445 return the_settings.miterate;
448 /* Sets the limit for loop iterations within a macro. */
450 settings_set_miterate (int miterate)
452 the_settings.miterate = miterate;
455 /* Returns the limit for recursion macro expansions. */
456 int settings_get_mnest (void)
458 return the_settings.mnest;
461 /* Sets the limit for recursion macro expansions. */
463 settings_set_mnest (int mnest)
465 the_settings.mnest = mnest;
468 int settings_get_mxloops (void);
469 void settings_set_mxloops (int);
470 /* Implied limit of unbounded loop. */
472 settings_get_mxloops (void)
474 return the_settings.mxloops;
477 /* Set implied limit of unbounded loop. */
479 settings_set_mxloops (int mxloops)
481 the_settings.mxloops = mxloops;
484 /* Approximate maximum amount of memory to use for cases, in
487 settings_get_workspace (void)
489 return the_settings.workspace;
492 /* Approximate maximum number of cases to allocate in-core, given
493 that each case has the format given in PROTO. */
495 settings_get_workspace_cases (const struct caseproto *proto)
497 size_t n_cases = settings_get_workspace () / case_get_cost (proto);
498 return MAX (n_cases, 4);
501 /* Set approximate maximum amount of memory to use for cases, in
505 settings_set_workspace (size_t workspace)
507 the_settings.workspace = workspace;
510 /* Default format for variables created by transformations and by
511 DATA LIST {FREE,LIST}. */
513 settings_get_format (void)
515 return the_settings.default_format;
518 /* Set default format for variables created by transformations
519 and by DATA LIST {FREE,LIST}. */
521 settings_set_format (const struct fmt_spec default_format)
523 the_settings.default_format = default_format;
526 /* Are we in testing mode? (e.g. --testing-mode command line
529 settings_get_testing_mode (void)
531 return the_settings.testing_mode;
534 /* Set testing mode. */
536 settings_set_testing_mode (bool testing_mode)
538 the_settings.testing_mode = testing_mode;
542 settings_get_fuzzbits (void)
544 return the_settings.fuzzbits;
548 settings_set_fuzzbits (int fuzzbits)
550 the_settings.fuzzbits = fuzzbits;
554 settings_get_scalemin (void)
556 return the_settings.scalemin;
560 settings_set_scalemin (int scalemin)
562 the_settings.scalemin = scalemin;
565 /* Return the current algorithm setting */
567 settings_get_algorithm (void)
569 return the_settings.cmd_algorithm;
572 /* Set the algorithm option globally. */
574 settings_set_algorithm (enum behavior_mode mode)
576 the_settings.global_algorithm = the_settings.cmd_algorithm = mode;
579 /* Set the algorithm option for this command only */
581 settings_set_cmd_algorithm (enum behavior_mode mode)
583 the_settings.cmd_algorithm = mode;
586 /* Unset the algorithm option for this command */
588 unset_cmd_algorithm (void)
590 the_settings.cmd_algorithm = the_settings.global_algorithm;
593 /* Get the current syntax setting */
595 settings_get_syntax (void)
597 return the_settings.syntax;
600 /* Set the syntax option */
602 settings_set_syntax (enum behavior_mode mode)
604 the_settings.syntax = mode;
608 /* Sets custom currency specifier CC having name CC_NAME ('A' through 'E') to
609 correspond to the settings in CC_STRING. Returns NULL if successful,
610 otherwise an error message that the caller must free. */
611 char * WARN_UNUSED_RESULT
612 settings_set_cc (const char *cc_string, enum fmt_type type)
614 struct fmt_number_style *style = fmt_number_style_from_string (cc_string);
616 return xasprintf (_("Custom currency string `%s' for %s does not contain "
617 "exactly three periods or commas (or it contains "
619 fmt_name (type), cc_string);
621 fmt_settings_set_cc (&the_settings.styles, type, style);
626 settings_set_decimal_char (char decimal)
628 the_settings.styles.decimal = decimal;
632 settings_set_include_leading_zero (bool include_leading_zero)
634 the_settings.styles.include_leading_zero = include_leading_zero;
637 const struct fmt_settings *
638 settings_get_fmt_settings (void)
640 return &the_settings.styles;
644 settings_get_small (void)
646 return the_settings.small;
650 settings_set_small (double small)
652 the_settings.small = small;
655 /* Returns a string of the form "$#,###.##" according to FMT,
656 which must be of type FMT_DOLLAR. The caller must free the
659 settings_dollar_template (const struct fmt_spec fmt)
661 struct string str = DS_EMPTY_INITIALIZER;
663 const struct fmt_number_style *fns ;
665 assert (fmt.type == FMT_DOLLAR);
667 fns = fmt_settings_get_style (&the_settings.styles, fmt.type);
669 ds_put_byte (&str, '$');
670 for (c = MAX (fmt.w - fmt.d - 1, 0); c > 0;)
672 ds_put_byte (&str, '#');
673 if (--c % 4 == 0 && c > 0)
675 ds_put_byte (&str, fns->grouping);
681 ds_put_byte (&str, fns->decimal);
682 ds_put_byte_multiple (&str, '#', fmt.d);
685 return ds_cstr (&str);
689 settings_set_output_routing (enum settings_output_type type,
690 enum settings_output_devices devices)
692 assert (type < SETTINGS_N_OUTPUT_TYPES);
693 the_settings.output_routing[type] = devices;
696 enum settings_output_devices
697 settings_get_output_routing (enum settings_output_type type)
699 assert (type < SETTINGS_N_OUTPUT_TYPES);
700 return the_settings.output_routing[type] | SETTINGS_DEVICE_UNFILTERED;
703 enum settings_value_show
704 settings_get_show_values (void)
706 return the_settings.show_values;
710 settings_set_show_values (enum settings_value_show s)
712 the_settings.show_values = s;
716 enum settings_value_show
717 settings_get_show_variables (void)
719 return the_settings.show_variables;
723 settings_set_show_variables (enum settings_value_show s)
725 the_settings.show_variables = s;
728 enum settings_mdisplay
729 settings_get_mdisplay (void)
731 return the_settings.mdisplay;
735 settings_set_mdisplay (enum settings_mdisplay mdisplay)
737 the_settings.mdisplay = mdisplay;