1 /* ----------------------------------------------------------------------- *
3 * Copyright 1996-2019 The NASM Authors - All Rights Reserved
4 * See the file AUTHORS included with the NASM distribution for
5 * the specific copyright holders.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
19 * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
20 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
21 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
23 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
26 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 * ----------------------------------------------------------------------- */
35 * error.c - error message handling routines for the assembler
44 /* Global error handling function */
47 /* Common function body */
48 #define nasm_do_error(s) \
51 nasm_verror((s), fmt, ap); \
54 void nasm_error(errflags severity
, const char *fmt
, ...)
56 nasm_do_error(severity
);
59 #define nasm_err_helpers(_type, _name, _sev) \
60 _type nasm_ ## _name ## f (errflags flags, const char *fmt, ...) \
62 nasm_do_error((_sev)|flags); \
63 if (_sev >= ERR_FATAL) \
66 _type nasm_ ## _name (const char *fmt, ...) \
68 nasm_do_error(_sev); \
69 if (_sev >= ERR_FATAL) \
73 nasm_err_helpers(void, debug
, ERR_DEBUG
)
74 nasm_err_helpers(void, note
, ERR_NOTE
)
75 nasm_err_helpers(void, nonfatal
, ERR_NONFATAL
)
76 nasm_err_helpers(fatal_func
, fatal
, ERR_FATAL
)
77 nasm_err_helpers(fatal_func
, panic
, ERR_PANIC
)
80 * Strongly discourage warnings without level by require flags on warnings.
81 * This means nasm_warn() is the equivalent of the -f variants of the
84 void nasm_warn(errflags severity
, const char *fmt
, ...)
86 nasm_do_error(ERR_WARNING
|severity
);
89 fatal_func
nasm_panic_from_macro(const char *file
, int line
)
91 nasm_panic("internal error at %s:%d\n", file
, line
);
94 fatal_func
nasm_assert_failed(const char *file
, int line
, const char *msg
)
96 nasm_panic("assertion %s failed at %s:%d", msg
, file
, line
);
101 * Warning stack management. Note that there is an implicit "push"
102 * after the command line has been parsed, but this particular push
105 struct warning_stack
{
106 struct warning_stack
*next
;
107 uint8_t state
[sizeof warning_state
];
109 static struct warning_stack
*warning_stack
, *warning_state_init
;
111 /* Push the warning status onto the warning stack */
112 void push_warnings(void)
114 struct warning_stack
*ws
;
116 ws
= nasm_malloc(sizeof *ws
);
117 memcpy(ws
->state
, warning_state
, sizeof warning_state
);
118 ws
->next
= warning_stack
;
122 /* Pop the warning status off the warning stack */
123 void pop_warnings(void)
125 struct warning_stack
*ws
= warning_stack
;
127 memcpy(warning_state
, ws
->state
, sizeof warning_state
);
130 *!warn-stack-empty [on] warning stack empty
131 *! a [WARNING POP] directive was executed when
132 *! the warning stack is empty. This is treated
133 *! as a [WARNING *all] directive.
135 nasm_warn(WARN_WARN_STACK_EMPTY
, "warning stack empty");
137 warning_stack
= ws
->next
;
142 /* Call after the command line is parsed, but before the first pass */
143 void init_warnings(void)
146 warning_state_init
= warning_stack
;
150 /* Call after each pass */
151 void reset_warnings(void)
153 struct warning_stack
*ws
= warning_stack
;
155 /* Unwind the warning stack. We do NOT delete the last entry! */
157 struct warning_stack
*wst
= ws
;
162 memcpy(warning_state
, ws
->state
, sizeof warning_state
);
166 * This is called when processing a -w or -W option, or a warning directive.
167 * Returns on if if the action was successful.
169 * Special pseudo-warnings:
171 *!other [on] any warning not specifially mentioned above
172 *! specifies any warning not included in any specific warning class.
174 *!all [all] all possible warnings
175 *! is an alias for \e{all} suppressible warning classes.
176 *! Thus, \c{-w+all} enables all available warnings, and \c{-w-all}
177 *! disables warnings entirely (since NASM 2.13).
179 bool set_warning_status(const char *value
)
181 enum warn_action
{ WID_OFF
, WID_ON
, WID_RESET
};
182 enum warn_action action
;
188 value
= nasm_skip_spaces(value
);
205 if (!nasm_strnicmp(value
, "no-", 3)) {
209 } else if (!nasm_stricmp(value
, "none")) {
214 /* else fall through */
220 mask
= WARN_ST_ENABLED
;
222 if (value
&& !nasm_strnicmp(value
, "error", 5)) {
225 mask
= WARN_ST_ERROR
;
229 mask
= WARN_ST_ERROR
;
233 /* Just an accidental prefix? */
238 name
= value
? value
: "<none>";
239 if (value
&& !nasm_stricmp(value
, "all"))
242 /* This is inefficient, but it shouldn't matter... */
243 for (i
= 1; i
< WARN_IDX_ALL
; i
++) {
244 if (!value
|| !nasm_stricmp(value
, warning_name
[i
])) {
245 ok
= true; /* At least one action taken */
248 warning_state
[i
] &= ~mask
;
251 warning_state
[i
] |= mask
;
254 warning_state
[i
] &= ~mask
;
256 warning_state_init
->state
[i
] & mask
;
264 *!unknown-warning [off] unknown warning in -W/-w or warning directive
265 *! warns about a \c{-w} or \c{-W} option or a \c{[WARNING]} directive
266 *! that contains an unknown warning name or is otherwise not possible to process.
268 nasm_warn(WARN_UNKNOWN_WARNING
, "unknown warning name: %s", name
);