145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/*
245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * Error and warning reporting and related functions.
345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *
445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *  Copyright (C) 2001-2007  Peter Johnson
545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *
645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * Redistribution and use in source and binary forms, with or without
745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * modification, are permitted provided that the following conditions
845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * are met:
945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * 1. Redistributions of source code must retain the above copyright
1045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *    notice, this list of conditions and the following disclaimer.
1145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * 2. Redistributions in binary form must reproduce the above copyright
1245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *    notice, this list of conditions and the following disclaimer in the
1345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *    documentation and/or other materials provided with the distribution.
1445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org *
1545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND OTHER CONTRIBUTORS ``AS IS''
1645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
1745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
1845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR OTHER CONTRIBUTORS BE
1945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
2545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * POSSIBILITY OF SUCH DAMAGE.
2645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org */
2745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include "util.h"
2845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
2945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include <ctype.h>
3045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include <stdarg.h>
3145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
3245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include "coretype.h"
3345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
3445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include "linemap.h"
3545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#include "errwarn.h"
3645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
3745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
3845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#define MSG_MAXSIZE     1024
3945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
4045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#if !defined(HAVE_TOASCII) || defined(lint)
4145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org# define toascii(c) ((c) & 0x7F)
4245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#endif
4345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
4445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Default handlers for replacable functions */
4545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic /*@exits@*/ void def_internal_error_
4645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    (const char *file, unsigned int line, const char *message);
4745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic /*@exits@*/ void def_fatal(const char *message, va_list va);
4845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic const char *def_gettext_hook(const char *msgid);
4945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
5045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Storage for errwarn's "extern" functions */
5145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/*@exits@*/ void (*yasm_internal_error_)
5245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    (const char *file, unsigned int line, const char *message)
5345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    = def_internal_error_;
5445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/*@exits@*/ void (*yasm_fatal) (const char *message, va_list va) = def_fatal;
5545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgconst char * (*yasm_gettext_hook) (const char *msgid) = def_gettext_hook;
5645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
5745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Error indicator */
5845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* yasm_eclass is not static so that yasm_error_occurred macro can access it */
5945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_class yasm_eclass;
6045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic /*@only@*/ /*@null@*/ char *yasm_estr;
6145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic unsigned long yasm_exrefline;
6245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic /*@only@*/ /*@null@*/ char *yasm_exrefstr;
6345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
6445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Warning indicator */
6545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgtypedef struct warn {
6645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@reldef@*/ STAILQ_ENTRY(warn) link;
6745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
6845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_warn_class wclass;
6945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@owned@*/ /*@null@*/ char *wstr;
7045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org} warn;
71a1b5233e6d340f45f4846131fec9d0b92e203ce4hbono@chromium.orgstatic STAILQ_HEAD(warn_head, warn) yasm_warns;
7245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
7345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Enabled warnings.  See errwarn.h for a list. */
7445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic unsigned long warn_class_enabled;
7545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
7645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgtypedef struct errwarn_data {
7745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@reldef@*/ SLIST_ENTRY(errwarn_data) link;
7845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
7945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    enum { WE_UNKNOWN, WE_ERROR, WE_WARNING, WE_PARSERERROR } type;
8045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
8145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unsigned long line;
8245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unsigned long xrefline;
8345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@owned@*/ char *msg;
8445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@owned@*/ char *xrefmsg;
8545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org} errwarn_data;
8645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
8745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstruct yasm_errwarns {
88a1b5233e6d340f45f4846131fec9d0b92e203ce4hbono@chromium.org    /*@reldef@*/ SLIST_HEAD(errwarn_head, errwarn_data) errwarns;
8945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
9045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Total error count */
9145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unsigned int ecount;
9245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
9345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Total warning count */
9445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unsigned int wcount;
9545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
9645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Last inserted error/warning.  Used to speed up insertions. */
9745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@null@*/ errwarn_data *previous_we;
9845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org};
9945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
10045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Static buffer for use by conv_unprint(). */
10145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic char unprint[5];
10245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
10345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
10445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic const char *
10545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgdef_gettext_hook(const char *msgid)
10645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
10745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return msgid;
10845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
10945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
11045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
11145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarn_initialize(void)
11245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
11345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Default enabled warnings.  See errwarn.h for a list. */
11445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn_class_enabled =
11545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        (1UL<<YASM_WARN_GENERAL) | (1UL<<YASM_WARN_UNREC_CHAR) |
11645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        (1UL<<YASM_WARN_PREPROC) | (0UL<<YASM_WARN_ORPHAN_LABEL) |
11745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        (1UL<<YASM_WARN_UNINIT_CONTENTS) | (0UL<<YASM_WARN_SIZE_OVERRIDE) |
11845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        (1UL<<YASM_WARN_IMPLICIT_SIZE_OVERRIDE);
11945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
12045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_eclass = YASM_ERROR_NONE;
12145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_estr = NULL;
12245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefline = 0;
12345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefstr = NULL;
12445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
12545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    STAILQ_INIT(&yasm_warns);
12645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
12745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
12845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
12945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarn_cleanup(void)
13045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
13145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_error_clear();
13245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_warn_clear();
13345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
13445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
13545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Convert a possibly unprintable character into a printable string, using
13645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * standard cat(1) convention for unprintable characters.
13745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org */
13845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgchar *
13945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm__conv_unprint(int ch)
14045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
14145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    int pos = 0;
14245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
14345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (((ch & ~0x7F) != 0) /*!isascii(ch)*/ && !isprint(ch)) {
14445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        unprint[pos++] = 'M';
14545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        unprint[pos++] = '-';
14645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        ch &= toascii(ch);
14745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
14845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (iscntrl(ch)) {
14945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        unprint[pos++] = '^';
15045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        unprint[pos++] = (ch == '\177') ? '?' : ch | 0100;
15145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    } else
15245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        unprint[pos++] = ch;
15345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unprint[pos] = '\0';
15445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
15545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return unprint;
15645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
15745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
15845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Report an internal error.  Essentially a fatal error with trace info.
15945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * Exit immediately because it's essentially an assert() trap.
16045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org */
16145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic void
16245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgdef_internal_error_(const char *file, unsigned int line, const char *message)
16345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
16445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    fprintf(stderr,
16545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_gettext_hook(N_("INTERNAL ERROR at %s, line %u: %s\n")),
16645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            file, line, yasm_gettext_hook(message));
16745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#ifdef HAVE_ABORT
16845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    abort();
16945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#else
17045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    exit(EXIT_FAILURE);
17145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#endif
17245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
17345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
17445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Report a fatal error.  These are unrecoverable (such as running out of
17545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * memory), so just exit immediately.
17645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org */
17745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic void
17845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgdef_fatal(const char *fmt, va_list va)
17945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
18045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    fprintf(stderr, "%s: ", yasm_gettext_hook(N_("FATAL")));
18145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vfprintf(stderr, yasm_gettext_hook(fmt), va);
18245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    fputc('\n', stderr);
18345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    exit(EXIT_FAILURE);
18445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
18545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
18645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org/* Create an errwarn structure in the correct linked list location.
18745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * If replace_parser_error is nonzero, overwrites the last error if its
18845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org * type is WE_PARSERERROR.
18945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org */
19045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgstatic errwarn_data *
19145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgerrwarn_data_new(yasm_errwarns *errwarns, unsigned long line,
19245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                 int replace_parser_error)
19345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
19445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarn_data *first, *next, *ins_we, *we;
19545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    enum { INS_NONE, INS_HEAD, INS_AFTER } action = INS_NONE;
19645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
19745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Find the entry with either line=line or the last one with line<line.
19845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org     * Start with the last entry added to speed the search.
19945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org     */
20045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    ins_we = errwarns->previous_we;
20145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    first = SLIST_FIRST(&errwarns->errwarns);
20245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (!ins_we || !first)
20345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        action = INS_HEAD;
20445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    while (action == INS_NONE) {
20545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        next = SLIST_NEXT(ins_we, link);
20645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (line < ins_we->line) {
20745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            if (ins_we == first)
20845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                action = INS_HEAD;
20945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            else
21045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                ins_we = first;
21145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        } else if (!next)
21245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            action = INS_AFTER;
21345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else if (line >= ins_we->line && line < next->line)
21445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            action = INS_AFTER;
21545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else
21645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            ins_we = next;
21745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
21845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
21945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (replace_parser_error && ins_we && ins_we->type == WE_PARSERERROR) {
22045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        /* overwrite last error */
22145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we = ins_we;
22245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    } else {
22345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        /* add a new error */
22445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we = yasm_xmalloc(sizeof(errwarn_data));
22545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
22645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->type = WE_UNKNOWN;
22745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->line = line;
22845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->xrefline = 0;
22945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->msg = NULL;
23045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->xrefmsg = NULL;
23145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
23245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (action == INS_HEAD)
23345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            SLIST_INSERT_HEAD(&errwarns->errwarns, we, link);
23445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else if (action == INS_AFTER) {
23545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            assert(ins_we != NULL);
23645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            SLIST_INSERT_AFTER(ins_we, we, link);
23745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        } else
23845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_internal_error(N_("Unexpected errwarn insert action"));
23945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
24045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
24145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Remember previous err/warn */
24245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarns->previous_we = we;
24345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
24445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return we;
24545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
24645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
24745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
24845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_clear(void)
24945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
25045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_estr)
25145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_xfree(yasm_estr);
25245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_exrefstr)
25345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_xfree(yasm_exrefstr);
25445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_eclass = YASM_ERROR_NONE;
25545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_estr = NULL;
25645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefline = 0;
25745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefstr = NULL;
25845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
25945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
26045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgint
26145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_matches(yasm_error_class eclass)
26245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
26345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_eclass == YASM_ERROR_NONE)
26445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return eclass == YASM_ERROR_NONE;
26545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_eclass == YASM_ERROR_GENERAL)
26645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return eclass == YASM_ERROR_GENERAL;
26745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return (yasm_eclass & eclass) == eclass;
26845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
26945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
27045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
27145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_set_va(yasm_error_class eclass, const char *format, va_list va)
27245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
27345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_eclass != YASM_ERROR_NONE)
27445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return;
27545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
27645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_eclass = eclass;
27745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_estr = yasm_xmalloc(MSG_MAXSIZE+1);
27845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#ifdef HAVE_VSNPRINTF
27945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsnprintf(yasm_estr, MSG_MAXSIZE, yasm_gettext_hook(format), va);
28045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#else
28145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsprintf(yasm_estr, yasm_gettext_hook(format), va);
28245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#endif
28345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
28445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
28545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
28645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_set(yasm_error_class eclass, const char *format, ...)
28745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
28845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_list va;
28945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_start(va, format);
29045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_error_set_va(eclass, format, va);
29145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_end(va);
29245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
29345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
29445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
29545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_set_xref_va(unsigned long xrefline, const char *format, va_list va)
29645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
29745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_eclass != YASM_ERROR_NONE)
29845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return;
29945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
30045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefline = xrefline;
30145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
30245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefstr = yasm_xmalloc(MSG_MAXSIZE+1);
30345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#ifdef HAVE_VSNPRINTF
30445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsnprintf(yasm_exrefstr, MSG_MAXSIZE, yasm_gettext_hook(format), va);
30545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#else
30645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsprintf(yasm_exrefstr, yasm_gettext_hook(format), va);
30745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#endif
30845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
30945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
31045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
31145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_set_xref(unsigned long xrefline, const char *format, ...)
31245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
31345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_list va;
31445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_start(va, format);
31545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_error_set_xref_va(xrefline, format, va);
31645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_end(va);
31745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
31845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
31945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
32045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_error_fetch(yasm_error_class *eclass, char **str, unsigned long *xrefline,
32145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                 char **xrefstr)
32245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
32345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *eclass = yasm_eclass;
32445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *str = yasm_estr;
32545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *xrefline = yasm_exrefline;
32645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *xrefstr = yasm_exrefstr;
32745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_eclass = YASM_ERROR_NONE;
32845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_estr = NULL;
32945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefline = 0;
33045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_exrefstr = NULL;
33145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
33245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
33345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid yasm_warn_clear(void)
33445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
33545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Delete all error/warnings */
33645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    while (!STAILQ_EMPTY(&yasm_warns)) {
33745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        warn *w = STAILQ_FIRST(&yasm_warns);
33845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
33945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (w->wstr)
34045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_xfree(w->wstr);
34145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
34245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        STAILQ_REMOVE_HEAD(&yasm_warns, link);
34345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_xfree(w);
34445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
34545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
34645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
34745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_class
34845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_occurred(void)
34945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
35045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (STAILQ_EMPTY(&yasm_warns))
35145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return YASM_WARN_NONE;
35245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return STAILQ_FIRST(&yasm_warns)->wclass;
35345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
35445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
35545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
35645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_set_va(yasm_warn_class wclass, const char *format, va_list va)
35745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
35845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn *w;
35945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
36045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (!(warn_class_enabled & (1UL<<wclass)))
36145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return;     /* warning is part of disabled class */
36245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
36345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    w = yasm_xmalloc(sizeof(warn));
36445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    w->wclass = wclass;
36545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    w->wstr = yasm_xmalloc(MSG_MAXSIZE+1);
36645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#ifdef HAVE_VSNPRINTF
36745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsnprintf(w->wstr, MSG_MAXSIZE, yasm_gettext_hook(format), va);
36845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#else
36945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    vsprintf(w->wstr, yasm_gettext_hook(format), va);
37045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org#endif
37145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    STAILQ_INSERT_TAIL(&yasm_warns, w, link);
37245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
37345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
37445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
37545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_set(yasm_warn_class wclass, const char *format, ...)
37645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
37745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_list va;
37845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_start(va, format);
37945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_warn_set_va(wclass, format, va);
38045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_end(va);
38145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
38245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
38345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
38445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_fetch(yasm_warn_class *wclass, char **str)
38545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
38645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn *w = STAILQ_FIRST(&yasm_warns);
38745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
38845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (!w) {
38945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        *wclass = YASM_WARN_NONE;
39045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        *str = NULL;
39145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return;
39245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
39345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
39445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *wclass = w->wclass;
39545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    *str = w->wstr;
39645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
39745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    STAILQ_REMOVE_HEAD(&yasm_warns, link);
39845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_xfree(w);
39945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
40045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
40145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
40245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_enable(yasm_warn_class num)
40345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
40445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn_class_enabled |= (1UL<<num);
40545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
40645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
40745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
40845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_disable(yasm_warn_class num)
40945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
41045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn_class_enabled &= ~(1UL<<num);
41145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
41245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
41345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
41445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_warn_disable_all(void)
41545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
41645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    warn_class_enabled = 0;
41745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
41845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
41945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarns *
42045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarns_create(void)
42145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
42245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_errwarns *errwarns = yasm_xmalloc(sizeof(yasm_errwarns));
42345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    SLIST_INIT(&errwarns->errwarns);
42445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarns->ecount = 0;
42545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarns->wcount = 0;
42645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarns->previous_we = NULL;
42745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    return errwarns;
42845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
42945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
43045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
43145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarns_destroy(yasm_errwarns *errwarns)
43245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
43345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarn_data *we;
43445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
43545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Delete all error/warnings */
43645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    while (!SLIST_EMPTY(&errwarns->errwarns)) {
43745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we = SLIST_FIRST(&errwarns->errwarns);
43845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (we->msg)
43945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_xfree(we->msg);
44045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (we->xrefmsg)
44145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_xfree(we->xrefmsg);
44245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
44345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        SLIST_REMOVE_HEAD(&errwarns->errwarns, link);
44445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_xfree(we);
44545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
44645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
44745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_xfree(errwarns);
44845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
44945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
45045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
45145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarn_propagate(yasm_errwarns *errwarns, unsigned long line)
45245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
45345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (yasm_eclass != YASM_ERROR_NONE) {
45445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        errwarn_data *we = errwarn_data_new(errwarns, line, 1);
45545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_error_class eclass;
45645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
45745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_error_fetch(&eclass, &we->msg, &we->xrefline, &we->xrefmsg);
45845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (eclass != YASM_ERROR_GENERAL
45945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            && (eclass & YASM_ERROR_PARSE) == YASM_ERROR_PARSE)
46045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            we->type = WE_PARSERERROR;
46145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else
46245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            we->type = WE_ERROR;
46345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        errwarns->ecount++;
46445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
46545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
46645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    while (!STAILQ_EMPTY(&yasm_warns)) {
46745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        errwarn_data *we = errwarn_data_new(errwarns, line, 0);
46845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_warn_class wclass;
46945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
47045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_warn_fetch(&wclass, &we->msg);
47145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        we->type = WE_WARNING;
47245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        errwarns->wcount++;
47345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
47445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
47545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
47645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgunsigned int
47745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarns_num_errors(yasm_errwarns *errwarns, int warning_as_error)
47845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
47945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (warning_as_error)
48045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return errwarns->ecount+errwarns->wcount;
48145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    else
48245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        return errwarns->ecount;
48345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
48445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
48545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
48645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm_errwarns_output_all(yasm_errwarns *errwarns, yasm_linemap *lm,
48745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                         int warning_as_error,
48845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                         yasm_print_error_func print_error,
48945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                         yasm_print_warning_func print_warning)
49045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
49145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    errwarn_data *we;
49245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    const char *filename, *xref_filename;
49345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    unsigned long line, xref_line;
49445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
49545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* If we're treating warnings as errors, tell the user about it. */
49645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    if (warning_as_error && warning_as_error != 2) {
49745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        print_error("", 0,
49845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                    yasm_gettext_hook(N_("warnings being treated as errors")),
49945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                    NULL, 0, NULL);
50045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        warning_as_error = 2;
50145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
50245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
50345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /* Output error/warnings. */
50445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    SLIST_FOREACH(we, &errwarns->errwarns, link) {
50545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        /* Output error/warning */
50645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        yasm_linemap_lookup(lm, we->line, &filename, &line);
50745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (we->xrefline)
50845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            yasm_linemap_lookup(lm, we->xrefline, &xref_filename, &xref_line);
50945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else {
51045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            xref_filename = NULL;
51145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            xref_line = 0;
51245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        }
51345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        if (we->type == WE_ERROR || we->type == WE_PARSERERROR)
51445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            print_error(filename, line, we->msg, xref_filename, xref_line,
51545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org                        we->xrefmsg);
51645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org        else
51745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org            print_warning(filename, line, we->msg);
51845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    }
51945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
52045afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org
52145afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgvoid
52245afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.orgyasm__fatal(const char *message, ...)
52345afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org{
52445afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_list va;
52545afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_start(va, message);
52645afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    yasm_fatal(message, va);
52745afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    /*@notreached@*/
52845afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org    va_end(va);
52945afe016bed87b9c6946184709058b39ede3f77ajwong@chromium.org}
530