1/*
2 * Copyright (c) 2010 Apple Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 *
10 * 1.  Redistributions of source code must retain the above copyright
11 *     notice, this list of conditions and the following disclaimer.
12 * 2.  Redistributions in binary form must reproduce the above copyright
13 *     notice, this list of conditions and the following disclaimer in the
14 *     documentation and/or other materials provided with the distribution.
15 * 3.  Neither the name of Apple Inc. ("Apple") nor the names of its
16 *     contributors may be used to endorse or promote products derived from
17 *     this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
20 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
23 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
26 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 *
30 * Portions of this software have been released under the following terms:
31 *
32 * (c) Copyright 1989-1993 OPEN SOFTWARE FOUNDATION, INC.
33 * (c) Copyright 1989-1993 HEWLETT-PACKARD COMPANY
34 * (c) Copyright 1989-1993 DIGITAL EQUIPMENT CORPORATION
35 *
36 * To anyone who acknowledges that this file is provided "AS IS"
37 * without any express or implied warranty:
38 * permission to use, copy, modify, and distribute this file for any
39 * purpose is hereby granted without fee, provided that the above
40 * copyright notices and this notice appears in all source code copies,
41 * and that none of the names of Open Software Foundation, Inc., Hewlett-
42 * Packard Company or Digital Equipment Corporation be used
43 * in advertising or publicity pertaining to distribution of the software
44 * without specific, written prior permission.  Neither Open Software
45 * Foundation, Inc., Hewlett-Packard Company nor Digital
46 * Equipment Corporation makes any representations about the suitability
47 * of this software for any purpose.
48 *
49 * Copyright (c) 2007, Novell, Inc. All rights reserved.
50 * Redistribution and use in source and binary forms, with or without
51 * modification, are permitted provided that the following conditions
52 * are met:
53 *
54 * 1.  Redistributions of source code must retain the above copyright
55 *     notice, this list of conditions and the following disclaimer.
56 * 2.  Redistributions in binary form must reproduce the above copyright
57 *     notice, this list of conditions and the following disclaimer in the
58 *     documentation and/or other materials provided with the distribution.
59 * 3.  Neither the name of Novell Inc. nor the names of its contributors
60 *     may be used to endorse or promote products derived from this
61 *     this software without specific prior written permission.
62 *
63 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY
64 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
65 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
66 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY
67 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
68 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
69 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
70 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
71 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
72 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
73 *
74 * @APPLE_LICENSE_HEADER_END@
75 */
76
77/*
78**
79**  NAME
80**
81**      MESSAGE.C
82**
83**  FACILITY:
84**
85**      Interface Definition Language (IDL) Compiler
86**      UUID Generator Tool
87**
88**  ABSTRACT:
89**
90**      International error message primitive routines.
91**
92**  VERSION: DCE 1.0
93**
94*/
95
96#ifdef HAVE_CONFIG_H
97#include <config.h>
98#endif
99
100#ifdef UUIDGEN  /* Building for uuidgen, so include whatever's needed from nidl.h. */
101#   if defined __STDC__
102#       include <limits.h>
103#       include <stdlib.h>
104#   endif
105#   include <uuidmsg.h>
106#   define MESSAGE_VERSION      UUIDGEN_MESSAGE_VERSION
107#   define MESSAGE_VERSION_USED UUIDGEN_MESSAGE_VERSION_USED
108#   define MESSAGE_CATALOG_DIR  "/usr/bin/"
109#   define NLSCATVER            UUIDGEN_NLSCATVER
110#   define NLSWRONG             UUIDGEN_NLSWRONG
111#   ifdef _AIX
112#       define NL_VFPRINTF NLvfprintf
113#   else
114#       define NL_VFPRINTF vfprintf
115#   endif
116#   define BRANCHCHAR '/'
117#else   /* Building for nidl. */
118#   include <nidl.h>
119#   include <nidlmsg.h>
120#   define MESSAGE_VERSION      NIDL_MESSAGE_VERSION
121#   define MESSAGE_VERSION_USED NIDL_MESSAGE_VERSION_USED
122#   define NLSCATVER            NIDL_NLSCATVER
123#   define NLSWRONG             NIDL_NLSWRONG
124#endif
125
126#include <stdio.h>
127#include <string.h>
128
129#   define MAX_FMT_TEXT   512      /* Max size of formatted output string */
130#   ifdef HAVE_NL_TYPES_H
131#       include <nl_types.h>
132#   else
133#       warning Message catalog support disabled
134#   endif
135#   ifdef __STDC__
136#       include <stdarg.h>  /* New! Improved! Method */
137#       define VA_START(L, A, T) va_start(L, A)
138#   else
139#       include <varargs.h> /* Traditional Method */
140#       define VA_START(L, A, T) T A; va_start(L); A = va_arg(L,T)
141#   endif
142
143#ifdef UUIDGEN
144#   ifndef PATH_MAX
145#       define PATH_MAX 256
146#   endif
147#endif
148
149#ifdef HAVE_NL_TYPES_H
150    static nl_catd cat_handle;
151#endif /* HAVE_NL_TYPES_H */
152/*
153** Declare an array to hold the default messages.  The text of the messages is
154** read from a file generated from the message catalog.
155*/
156const char *default_messages[] = {
157"Internal idl compiler error: Invalid message number",
158#include <default_msg.h>
159};
160static long max_message_number		/* Compute number of messages. */
161	= (long)(sizeof(default_messages)/sizeof(char *) - 1);
162#   define def_message(id) \
163	default_messages[(id<0||id>max_message_number)?0:id]
164
165#include <message.h>
166static char     msg_prefix[PATH_MAX+3];
167
168
169/*
170 *  m e s s a g e _ o p e n
171 *
172 *  Function:   Opens message database.
173 */
174
175void message_open
176(
177    char *image_name __attribute__((unused))
178)
179{
180#ifdef HAVE_NL_TYPES_H
181    char cat_name[PATH_MAX] = CATALOG_DIR "idl.cat";
182
183    strlcpy(msg_prefix, "idl: ", sizeof (msg_prefix));
184
185    /*
186     * Open the message catalog using the image name.
187     */
188#ifdef AIX32
189    setlocale(LC_ALL, "");
190#endif
191    cat_handle = catopen(cat_name, 0);
192
193    /* Sucessful open, check version information */
194    if (cat_handle != (nl_catd)-1)
195    {
196          char  *version_text;
197          version_text = catgets(cat_handle,CAT_SET,MESSAGE_VERSION,NULL);
198          if (version_text != NULL && atoi(version_text) != MESSAGE_VERSION_USED)
199          {
200              fprintf(stderr, def_message(NLSCATVER),
201                  msg_prefix, cat_name, MESSAGE_VERSION_USED, version_text);
202              fprintf(stderr, "\n");
203              fprintf(stderr, def_message(NLSWRONG), msg_prefix);
204              fprintf(stderr, "\n");
205          }
206    }
207#endif /* HAVE_NL_TYPES_H */
208    return;
209}
210
211/*
212 *  m e s s a g e _ c l o s e
213 *
214 *  Function:   Closes message database.
215 */
216
217void message_close
218(
219    void
220)
221
222{
223#ifdef HAVE_NL_TYPES_H
224    if (cat_handle != (nl_catd)-1) catclose(cat_handle);
225#endif
226    return;
227}
228
229
230/*
231 *  m e s s a g e _ p r i n t
232 *
233 *  Function:   Fetches message from database, then formats and prints message.
234 *
235 *  Inputs:     msgid - message ID
236 *              [arg1,...,arg5] - Optional arguments for message formatting
237 *
238 *  Outputs:    message printed to stderr.
239 */
240
241void vmessage_print
242(long msgid, va_list arglist)
243{
244    char format[MAX_FMT_TEXT];     /* Format string */
245
246#ifdef HAVE_NL_TYPES_H
247    /*
248     * Output message prefix on all errors that identify the input file,
249     * or on every line for UUIDGEN
250     */
251    format[0]='\0';
252    switch (msgid)
253    {
254#ifndef UUIDGEN
255        case NIDL_EOF:
256        case NIDL_EOFNEAR:
257        case NIDL_SYNTAXNEAR:
258        case NIDL_FILESOURCE:
259        case NIDL_LINEFILE:
260#else
261        default:
262#endif
263            strlcpy(format, msg_prefix, sizeof (format));
264    }
265
266    strlcat(format,catgets(cat_handle, CAT_SET, msgid, def_message(msgid)), sizeof(format));
267    strlcat(format,"\n", sizeof(format));
268#else
269    snprintf(format, sizeof(format), "%s%s\n", msg_prefix, def_message(msgid));
270#endif /* HAVE_NL_TYPES_H */
271    NL_VFPRINTF(stderr, format, arglist);
272}
273
274void message_print
275#ifdef __STDC__
276(long msgid, ...)
277#else
278(va_alist) va_dcl
279#endif
280{
281    va_list arglist;
282
283    VA_START(arglist, msgid, long);
284    vmessage_print (msgid, arglist);
285    va_end(arglist);
286}
287
288
289#ifndef UUIDGEN
290/*
291 *  m e s s a g e _ s p r i n t
292 *
293 *  Function:   Fetches message from database and formats message.
294 *
295 *  Inputs:     str - Address of buffer for formatted message
296 *              msgid - message ID
297 *              [arg1,...,arg5] - Optional arguments for message formatting
298 *
299 *  Outputs:    str
300 */
301
302void message_sprint
303(
304    char *str,
305	size_t str_len,
306    long msgid,
307    char *arg1,
308    char *arg2,
309    char *arg3,
310    char *arg4,
311    char *arg5
312)
313{
314    char *msg_text;     /* Ptr to message text (storage owned by catgets) */
315
316#ifdef HAVE_NL_TYPES_H
317    msg_text = catgets(cat_handle, CAT_SET, msgid, def_message(msgid));
318#else
319    msg_text = def_message(msgid);
320#endif /* HAVE_NL_TYPES_H */
321    /*
322     * Output message prefix on all errors that identify the input file
323     */
324    switch (msgid)
325    {
326        case NIDL_EOF:
327        case NIDL_EOFNEAR:
328        case NIDL_SYNTAXNEAR:
329        case NIDL_FILESOURCE:
330        case NIDL_LINEFILE:
331            strlcpy(str,msg_prefix,str_len);         /* Add prefix to messages */
332            str +=  strlen(msg_prefix);
333            break;
334    }
335
336    NL_SPRINTF(str, msg_text, arg1, arg2, arg3, arg4, arg5);
337}
338
339/*
340 *  m e s s a g e _ f p r i n t
341 *
342 *  Function:   Fetches message from database, then formats and prints message.
343 *
344 *  Inputs:     fid - file handle of file for output message
345 *              msgid - message ID
346 *              [arg1,...,arg5] - Optional arguments for message formatting
347 *
348 *  Outputs:    message printed to file indicated by fid not including
349 *		any system-dependant prefix information such as the compiler
350 *		executable name, facility, severity, etc.
351 */
352
353void message_fprint
354(
355    FILE *fid,
356    long msgid,
357    char *arg1,
358    char *arg2,
359    char *arg3,
360    char *arg4,
361    char *arg5
362)
363{
364    char            str[MAX_FMT_TEXT];     /* Formatted message text */
365    char *msg_text;     /* Ptr to message text (storage owned by catgets) */
366
367#ifdef HAVE_NL_TYPES_H
368    msg_text = catgets(cat_handle, CAT_SET, msgid, def_message(msgid));
369#else
370    msg_text = def_message(msgid);
371#endif /* HAVE_NL_TYPES_H */
372    NL_SPRINTF(str, msg_text, arg1, arg2, arg3, arg4, arg5);
373    fprintf(fid, "%s\n", str);
374}
375
376#endif
377