summaryrefslogtreecommitdiffstats
path: root/usr.bin/compile_et
diff options
context:
space:
mode:
authorwollman <wollman@FreeBSD.org>1995-01-14 22:29:34 +0000
committerwollman <wollman@FreeBSD.org>1995-01-14 22:29:34 +0000
commit479760c2d1e817f812fa71973482213f15d0a540 (patch)
treeb01b2a189f9952f13c52aad71fdcd992d8148f0a /usr.bin/compile_et
parent93bd3ddd3ca7c6ac68b55ec30b39a3930a084aba (diff)
downloadFreeBSD-src-479760c2d1e817f812fa71973482213f15d0a540.zip
FreeBSD-src-479760c2d1e817f812fa71973482213f15d0a540.tar.gz
Upgrade to latest released SIPB version I can find. (Unfortunately, the
original releases were not numbered.)
Diffstat (limited to 'usr.bin/compile_et')
-rw-r--r--usr.bin/compile_et/Makefile21
-rw-r--r--usr.bin/compile_et/compile_et.179
-rw-r--r--usr.bin/compile_et/compile_et.c408
-rw-r--r--usr.bin/compile_et/compiler.h20
-rw-r--r--usr.bin/compile_et/error_table.y75
-rw-r--r--usr.bin/compile_et/et_lex.lex.l15
-rw-r--r--usr.bin/compile_et/mit-sipb-copyright.h19
7 files changed, 450 insertions, 187 deletions
diff --git a/usr.bin/compile_et/Makefile b/usr.bin/compile_et/Makefile
index 843e005..e8bb5a2 100644
--- a/usr.bin/compile_et/Makefile
+++ b/usr.bin/compile_et/Makefile
@@ -1,14 +1,17 @@
-# From: @(#)Makefile 5.1 (Berkeley) 6/25/90
-# $Id: Makefile,v 1.1.1.1 1994/09/30 14:49:49 csgr Exp $
+# $Id$
PROG= compile_et
-CFLAGS+=-I. -I${.CURDIR}
-SRCS= compile_et.c error_message.c et_name.c init_et.c perror.c error_table.c
-DPADD= ${LIBL}
-LDADD= -ll
-CLEANFILES=et_lex.lex.c y.tab.c y.tab.h error_table.c
-NOMAN= noman
+SRCS= compile_et.c error_table.y
+CFLAGS+= -I. -I${.CURDIR}/../libcom_err
+CLEANFILES+= et_lex.lex.c
+DPADD+= ${LIBL}
+LDADD+= -ll
-error_table.c: et_lex.lex.c
+beforedepend: et_lex.lex.c
+error_table.o: et_lex.lex.c
+
+.l.c:
+ ${LEX} -l -t ${.IMPSRC} > ${.TARGET}
.include <bsd.prog.mk>
+
diff --git a/usr.bin/compile_et/compile_et.1 b/usr.bin/compile_et/compile_et.1
new file mode 100644
index 0000000..f17a278
--- /dev/null
+++ b/usr.bin/compile_et/compile_et.1
@@ -0,0 +1,79 @@
+.\" Copyright (c) 1988 Massachusetts Institute of Technology,
+.\" Student Information Processing Board. All rights reserved.
+.\"
+.\" $Header$
+.\"
+.TH COMPILE_ET 1 "22 Nov 1988" SIPB
+.SH NAME
+compile_et \- error table compiler
+.SH SYNOPSIS
+.B compile_et
+file
+.SH DESCRIPTION
+.B Compile_et
+converts a table listing error-code names and associated messages into
+a C source file suitable for use with the
+.IR com_err (3)
+library.
+
+The source file name must end with a suffix of ``.et''; the file
+consists of a declaration supplying the name (up to four characters
+long) of the error-code table:
+
+.B error_table
+.I name
+
+followed by up to 256 entries of the form:
+
+.B error_code
+.I name,
+"
+.I string
+"
+
+and a final
+
+.B end
+
+to indicate the end of the table.
+
+The name of the table is used to construct the name of a subroutine
+.I initialize_XXXX_error_table
+which must be called in order for the
+.I com_err
+library to recognize the error table.
+
+The various error codes defined are assigned sequentially increasing
+numbers (starting with a large number computed as a hash function of
+the name of the table); thus for compatibility it is suggested that
+new codes be added only to the end of an existing table, and that no
+codes be removed from tables.
+
+The names defined in the table are placed into a C header file with
+preprocessor directives defining them as integer constants of up to
+32 bits in magnitude.
+
+A C source file is also generated which should be compiled and linked
+with the object files which reference these error codes; it contains
+the text of the messages and the initialization subroutine. Both C
+files have names derived from that of the original source file, with
+the ``.et'' suffix replaced by ``.c'' and ``.h''.
+
+A ``#'' in the source file is treated as a comment character, and all
+remaining text to the end of the source line will be ignored.
+
+.SH BUGS
+
+Since
+.B compile_et
+uses a very simple parser based on
+.IR yacc (1),
+its error recovery leaves much to be desired.
+
+.\" .IR for manual entries
+.\" .PP for paragraph breaks
+
+.SH "SEE ALSO"
+com_err (3).
+
+Ken Raeburn, "A Common Error Description Library for UNIX".
diff --git a/usr.bin/compile_et/compile_et.c b/usr.bin/compile_et/compile_et.c
index 25be70b..8e3f492 100644
--- a/usr.bin/compile_et/compile_et.c
+++ b/usr.bin/compile_et/compile_et.c
@@ -1,17 +1,30 @@
/*
*
- * Copyright 1986, 1987 by MIT Student Information Processing Board
- * For copyright info, see "Copyright.SIPB".
+ * Copyright 1986, 1987, 1988
+ * by MIT Student Information Processing Board.
+ *
+ * For copyright info, see "mit-sipb-copyright.h".
*
- * $Id: compile_et.c,v 1.2 1994/07/19 19:21:24 g89r4222 Exp $
*/
#include <stdio.h>
#include <sys/file.h>
-#include <strings.h>
+#include <string.h>
#include <sys/param.h>
+#include "mit-sipb-copyright.h"
+#include "compiler.h"
+
+#ifndef __STDC__
+#define const
+#endif
+
+#ifndef lint
+static const char copyright[] =
+ "Copyright 1987,1988 by MIT Student Information Processing Board";
-static char copyright[] = "Copyright 1987 by MIT Student Information Processing Board";
+static const char rcsid_compile_et_c[] =
+ "$Header: /afs/rel-eng.athena.mit.edu/project/release/current/source/athena/athena.lib/et/RCS/compile_et.c,v 1.3 91/02/28 15:15:23 epeisach Exp $";
+#endif
extern char *gensym();
extern char *current_token;
@@ -19,154 +32,259 @@ extern int table_number, current;
char buffer[BUFSIZ];
char *table_name = (char *)NULL;
FILE *hfile, *cfile;
-
+
/* C library */
extern char *malloc();
extern int errno;
-
+
/* lex stuff */
extern FILE *yyin;
extern int yylineno;
-
+
+char * xmalloc (size) unsigned int size; {
+ char * p = malloc (size);
+ if (!p) {
+ perror (whoami);
+ exit (1);
+ }
+ return p;
+}
+
+static int check_arg (str_list, arg) char const *const *str_list, *arg; {
+ while (*str_list)
+ if (!strcmp(arg, *str_list++))
+ return 1;
+ return 0;
+}
+
+static const char *const debug_args[] = {
+ "d",
+ "debug",
+ 0,
+};
+
+static const char *const lang_args[] = {
+ "lang",
+ "language",
+ 0,
+};
+
+static const char *const language_names[] = {
+ "C",
+ "K&R C",
+ "C++",
+ 0,
+};
+
+static const char * const c_src_prolog[] = {
+ "static const char * const text[] = {\n",
+ 0,
+};
+
+static const char * const krc_src_prolog[] = {
+ "#ifdef __STDC__\n",
+ "#define NOARGS void\n",
+ "#else\n",
+ "#define NOARGS\n",
+ "#define const\n",
+ "#endif\n\n",
+ "static const char * const text[] = {\n",
+ 0,
+};
+
+static const char *const struct_def[] = {
+ "struct error_table {\n",
+ " char const * const * msgs;\n",
+ " long base;\n",
+ " int n_msgs;\n",
+ "};\n",
+ "struct et_list {\n",
+ " struct et_list *next;\n",
+ " const struct error_table * table;\n",
+ "};\n",
+ "extern struct et_list *_et_list;\n",
+ "\n", 0,
+};
+
+static const char warning[] =
+ "/*\n * %s:\n * This file is automatically generated; please do not edit it.\n */\n";
+
/* pathnames */
-char c_file[MAXPATHLEN]; /* temporary file */
+char c_file[MAXPATHLEN]; /* output file */
char h_file[MAXPATHLEN]; /* output */
-char o_file[MAXPATHLEN]; /* output */
-char et_file[MAXPATHLEN]; /* input */
-
-main(argc, argv)
- int argc;
- char **argv;
-{
- register char *p;
- int n_flag = 0, debug = 0;
-
- while (argc > 2) {
- register char *arg, ch;
- arg = argv[--argc];
- if (strlen(arg) != 2 || arg[0] != '-')
- goto usage;
- ch = arg[1];
- if (ch == 'n')
- n_flag++;
- else if (ch == 'd')
- debug++;
- else
- goto usage;
- }
-
- if (argc != 2) {
- usage:
- fprintf(stderr, "Usage: %s et_file [-n]\n", argv[0]);
- exit(1);
- }
-
- strcpy(et_file, argv[1]);
- p = rindex(et_file, '/');
- if (p == (char *)NULL)
- p = et_file;
- else
- p++;
- p = rindex(p, '.');
- if (!strcmp(p, ".et"))
- *++p = '\0';
- else {
- if (!p)
- p = et_file;
- while (*p)
- p++;
- *p++ = '.';
- *p = '\0';
- }
- /* p points at null where suffix should be */
- strcpy(p, "et.c");
- strcpy(c_file, et_file);
- p[0] = 'h';
- p[1] = '\0';
- strcpy(h_file, et_file);
- p[0] = 'o';
- strcpy(o_file, et_file);
- p[0] = 'e';
- p[1] = 't';
- p[2] = '\0';
-
- yyin = fopen(et_file, "r");
- if (!yyin) {
- perror(et_file);
- exit(1);
- }
-
- hfile = fopen(h_file, "w");
- if (hfile == (FILE *)NULL) {
- perror(h_file);
- exit(1);
- }
-
- cfile = fopen(c_file, "w");
- if (cfile == (FILE *)NULL) {
- perror("Can't open temp file");
- exit(1);
- }
-
- /* parse it */
- fputs("#define NULL 0\n", cfile);
- fputs("static char *_et[] = {\n", cfile);
-
- yyparse();
- fclose(yyin); /* bye bye input file */
-
- fputs("\t(char *)0\n};\n", cfile);
- fputs("extern int init_error_table();\n\n", cfile);
- fprintf(cfile, "int %s_err_base = %d;\n\n", table_name, table_number);
- fprintf(cfile, "int\ninit_%s_err_tbl()\n", table_name);
- fprintf(cfile, "{\n\treturn(init_error_table(_et, %d, %d));\n}\n",
- table_number, current);
- fclose(cfile);
-
- fputs("extern int init_", hfile);
- fputs(table_name, hfile);
- fputs("_err_tbl();\nextern int ", hfile);
- fputs(table_name, hfile);
- fputs("_err_base;\n", hfile);
- fclose(hfile); /* bye bye hfile */
-
- if (n_flag)
- exit(0);
-
- if (!fork()) {
- p = rindex(c_file, '/');
- if (p) {
- *p++ = '\0';
- chdir(c_file);
- }
- else
- p = c_file;
- execlp("cc", "cc", "-c", "-R", "-O", p, 0);
- perror("cc");
- exit(1);
- }
- else wait(0);
-
- if (!debug)
- (void) unlink(c_file);
- /* make it .o file name */
- c_file[strlen(c_file)-1] = 'o';
- if (!fork()) {
- execlp("cp", "cp", c_file, o_file, 0);
- perror("cp");
- exit(1);
- }
- else wait(0);
- if (!debug)
- (void) unlink(c_file);
-
- exit(0);
+
+static void usage () {
+ fprintf (stderr, "%s: usage: %s ERROR_TABLE\n",
+ whoami, whoami);
+ exit (1);
+}
+
+static void dup_err (type, one, two) char const *type, *one, *two; {
+ fprintf (stderr, "%s: multiple %s specified: `%s' and `%s'\n",
+ whoami, type, one, two);
+ usage ();
+}
+
+int main (argc, argv) int argc; char **argv; {
+ char *p, *ename;
+ int len;
+ char const * const *cpp;
+ int got_language = 0;
+
+ /* argument parsing */
+ debug = 0;
+ filename = 0;
+ whoami = argv[0];
+ p = strrchr (whoami, '/');
+ if (p)
+ whoami = p+1;
+ while (argv++, --argc) {
+ char *arg = *argv;
+ if (arg[0] != '-') {
+ if (filename)
+ dup_err ("filenames", filename, arg);
+ filename = arg;
+ }
+ else {
+ arg++;
+ if (check_arg (debug_args, arg))
+ debug++;
+ else if (check_arg (lang_args, arg)) {
+ got_language++;
+ arg = *++argv, argc--;
+ if (!arg)
+ usage ();
+ if (language)
+ dup_err ("languanges", language_names[(int)language], arg);
+#define check_lang(x,v) else if (!strcasecmp(arg,x)) language = v
+ check_lang ("c", lang_C);
+ check_lang ("ansi_c", lang_C);
+ check_lang ("ansi-c", lang_C);
+ check_lang ("krc", lang_KRC);
+ check_lang ("kr_c", lang_KRC);
+ check_lang ("kr-c", lang_KRC);
+ check_lang ("k&r-c", lang_KRC);
+ check_lang ("k&r_c", lang_KRC);
+ check_lang ("c++", lang_CPP);
+ check_lang ("cplusplus", lang_CPP);
+ check_lang ("c-plus-plus", lang_CPP);
+#undef check_lang
+ else {
+ fprintf (stderr, "%s: unknown language name `%s'\n",
+ whoami, arg);
+ fprintf (stderr, "\tpick one of: C K&R-C\n");
+ exit (1);
+ }
+ }
+ else {
+ fprintf (stderr, "%s: unknown control argument -`%s'\n",
+ whoami, arg);
+ usage ();
+ }
+ }
+ }
+ if (!filename)
+ usage ();
+ if (!got_language)
+ language = lang_KRC;
+ else if (language == lang_CPP) {
+ fprintf (stderr, "%s: Sorry, C++ support is not yet finished.\n",
+ whoami);
+ exit (1);
+ }
+
+ p = xmalloc (strlen (filename) + 5);
+ strcpy (p, filename);
+ filename = p;
+ p = strrchr(filename, '/');
+ if (p == (char *)NULL)
+ p = filename;
+ else
+ p++;
+ ename = p;
+ len = strlen (ename);
+ p += len - 3;
+ if (strcmp (p, ".et"))
+ p += 3;
+ *p++ = '.';
+ /* now p points to where "et" suffix should start */
+ /* generate new filenames */
+ strcpy (p, "c");
+ strcpy (c_file, ename);
+ *p = 'h';
+ strcpy (h_file, ename);
+ strcpy (p, "et");
+
+ yyin = fopen(filename, "r");
+ if (!yyin) {
+ perror(filename);
+ exit(1);
+ }
+
+ hfile = fopen(h_file, "w");
+ if (hfile == (FILE *)NULL) {
+ perror(h_file);
+ exit(1);
+ }
+ fprintf (hfile, warning, h_file);
+
+ cfile = fopen(c_file, "w");
+ if (cfile == (FILE *)NULL) {
+ perror(c_file);
+ exit(1);
+ }
+ fprintf (cfile, warning, c_file);
+
+ /* prologue */
+ if (language == lang_C)
+ cpp = c_src_prolog;
+ else if (language == lang_KRC)
+ cpp = krc_src_prolog;
+ else
+ abort ();
+ while (*cpp)
+ fputs (*cpp++, cfile);
+
+ /* parse it */
+ yyparse();
+ fclose(yyin); /* bye bye input file */
+
+ fputs (" 0\n};\n\n", cfile);
+ for (cpp = struct_def; *cpp; cpp++)
+ fputs (*cpp, cfile);
+ fprintf(cfile,
+ "static const struct error_table et = { text, %ldL, %d };\n\n",
+ table_number, current);
+ fputs("static struct et_list link = { 0, 0 };\n\n",
+ cfile);
+ fprintf(cfile, "void initialize_%s_error_table (%s) {\n",
+ table_name, (language == lang_C) ? "void" : "NOARGS");
+ fputs(" if (!link.table) {\n", cfile);
+ fputs(" link.next = _et_list;\n", cfile);
+ fputs(" link.table = &et;\n", cfile);
+ fputs(" _et_list = &link;\n", cfile);
+ fputs(" }\n", cfile);
+ fputs("}\n", cfile);
+ fclose(cfile);
+
+ fprintf (hfile, "extern void initialize_%s_error_table ();\n",
+ table_name);
+ fprintf (hfile, "#define ERROR_TABLE_BASE_%s (%ldL)\n",
+ table_name, table_number);
+ /* compatibility... */
+ fprintf (hfile, "\n/* for compatibility with older versions... */\n");
+ fprintf (hfile, "#define init_%s_err_tbl initialize_%s_error_table\n",
+ table_name, table_name);
+ fprintf (hfile, "#define %s_err_base ERROR_TABLE_BASE_%s\n", table_name,
+ table_name);
+ fclose(hfile); /* bye bye include file */
+
+ return 0;
}
-yyerror(s)
- char *s;
-{
- fputs(s, stderr);
- fprintf(stderr, "\nLine number %d; last token was '%s'\n",
- yylineno, current_token);
+int yyerror(s) char *s; {
+ fputs(s, stderr);
+ fprintf(stderr, "\nLine number %d; last token was '%s'\n",
+ yylineno, current_token);
}
+
diff --git a/usr.bin/compile_et/compiler.h b/usr.bin/compile_et/compiler.h
new file mode 100644
index 0000000..43752e2
--- /dev/null
+++ b/usr.bin/compile_et/compiler.h
@@ -0,0 +1,20 @@
+/*
+ * definitions common to the source files of the error table compiler
+ */
+
+#ifndef __STDC__
+/* loser */
+#undef const
+#define const
+#endif
+
+enum lang {
+ lang_C, /* ANSI C (default) */
+ lang_KRC, /* C: ANSI + K&R */
+ lang_CPP /* C++ */
+};
+
+int debug; /* dump debugging info? */
+char *filename; /* error table source */
+enum lang language;
+const char *whoami;
diff --git a/usr.bin/compile_et/error_table.y b/usr.bin/compile_et/error_table.y
index 3913a84..11a8b2d 100644
--- a/usr.bin/compile_et/error_table.y
+++ b/usr.bin/compile_et/error_table.y
@@ -56,23 +56,33 @@ description : QUOTED_STRING
%%
/*
+ *
* Copyright 1986, 1987 by the MIT Student Information Processing Board
- * For copyright info, see Copyright.SIPB.
+ *
+ * For copyright info, see mit-sipb-copyright.h.
*/
-#include <stdlib.h>
-#include <strings.h>
+#include <string.h>
+#include <assert.h>
#include <ctype.h>
#include <sys/types.h>
#include <sys/time.h>
+#include "internal.h"
#include "error_table.h"
+#include "mit-sipb-copyright.h"
+#ifndef lint
+static char const rcsid_error_table_y[] =
+ "$Header: error_table.y,v 1.7 89/01/01 07:23:17 raeburn Locked $";
+#endif
+
+char *malloc(), *realloc();
extern FILE *hfile, *cfile;
static long gensym_n = 0;
char *
gensym(x)
- char *x;
+ char const *x;
{
char *symbol;
if (!gensym_n) {
@@ -89,7 +99,7 @@ gensym(x)
char *
ds(string)
- char *string;
+ char const *string;
{
char *rv;
rv = malloc(strlen(string)+1);
@@ -99,7 +109,7 @@ ds(string)
char *
quote(string)
- char *string;
+ char const *string;
{
char *rv;
rv = malloc(strlen(string)+3);
@@ -109,12 +119,12 @@ quote(string)
return(rv);
}
-int table_number;
+long table_number;
int current = 0;
char **error_codes = (char **)NULL;
add_ec(name, description)
- char *name, *description;
+ char const *name, *description;
{
fprintf(cfile, "\t\"%s\",\n", description);
if (error_codes == (char **)NULL) {
@@ -128,9 +138,9 @@ add_ec(name, description)
}
add_ec_val(name, val, description)
- char *name, *val, *description;
+ char const *name, *val, *description;
{
- int ncurrent = atoi(val);
+ const int ncurrent = atoi(val);
if (ncurrent < current) {
printf("Error code %s (%d) out of order", name,
current);
@@ -156,8 +166,8 @@ put_ecs()
int i;
for (i = 0; i < current; i++) {
if (error_codes[i] != (char *)NULL)
- fprintf(hfile, "#define %-40s ((%s)%d)\n",
- error_codes[i], ERROR_CODE, table_number + i);
+ fprintf(hfile, "#define %-40s (%ldL)\n",
+ error_codes[i], table_number + i);
}
}
@@ -168,26 +178,43 @@ put_ecs()
* digits -> 53-62
* underscore-> 63
*/
-int
-char_to_num(c)
+
+static const char char_set[] =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_";
+
+int char_to_num(c)
char c;
{
- if (isupper(c))
- return(c-'A'+1);
- else if (islower(c))
- return(c-'a'+27);
- else if (isdigit(c))
- return(c-'0'+53);
- else {
- fprintf(stderr, "Illegal character in name: %c\n", c);
- exit(1);
- /*NOTREACHED*/
+ const char *where;
+ int diff;
+
+ where = strchr (char_set, c);
+ if (where) {
+ diff = where - char_set + 1;
+ assert (diff < (1 << ERRCODE_RANGE));
+ return diff;
}
+ else if (isprint (c))
+ fprintf (stderr,
+ "Illegal character `%c' in error table name\n",
+ c);
+ else
+ fprintf (stderr,
+ "Illegal character %03o in error table name\n",
+ c);
+ exit (1);
}
set_table_num(string)
char *string;
{
+ if (char_to_num (string[0]) > char_to_num ('z')) {
+ fprintf (stderr, "%s%s%s%s",
+ "First character of error table name must be ",
+ "a letter; name ``",
+ string, "'' rejected\n");
+ exit (1);
+ }
if (strlen(string) > 4) {
fprintf(stderr, "Table name %s too long, truncated ",
string);
diff --git a/usr.bin/compile_et/et_lex.lex.l b/usr.bin/compile_et/et_lex.lex.l
index c041819..0c848de 100644
--- a/usr.bin/compile_et/et_lex.lex.l
+++ b/usr.bin/compile_et/et_lex.lex.l
@@ -1,9 +1,4 @@
-%{
-extern int yylineno;
-int yylineno = 1;
-%}
-
-PC [^\"\n]
+PC [^\"]
AN [A-Z_a-z0-9]
%%
@@ -13,8 +8,7 @@ error_code return ERROR_CODE_ENTRY;
ec return ERROR_CODE_ENTRY;
end return END;
-[\t ]+ ;
-\n ++yylineno;
+[\t\n ] ;
\"{PC}*\" { register char *p; yylval.dynstr = ds(yytext+1);
if (p=rindex(yylval.dynstr, '"')) *p='\0';
@@ -23,7 +17,10 @@ end return END;
{AN}* { yylval.dynstr = ds(yytext); return STRING; }
-#.*\n ++yylineno;
+#.*\n ;
. { return (*yytext); }
%%
+#ifndef lint
+static char rcsid_et_lex_lex_l[] = "$Header: et_lex.lex.l,v 1.3 87/10/31 06:28:05 raeburn Exp $";
+#endif
diff --git a/usr.bin/compile_et/mit-sipb-copyright.h b/usr.bin/compile_et/mit-sipb-copyright.h
new file mode 100644
index 0000000..2f7eb29
--- /dev/null
+++ b/usr.bin/compile_et/mit-sipb-copyright.h
@@ -0,0 +1,19 @@
+/*
+
+Copyright 1987, 1988 by the Student Information Processing Board
+ of the Massachusetts Institute of Technology
+
+Permission to use, copy, modify, and distribute this software
+and its documentation for any purpose and without fee is
+hereby granted, provided that the above copyright notice
+appear in all copies and that both that copyright notice and
+this permission notice appear in supporting documentation,
+and that the names of M.I.T. and the M.I.T. S.I.P.B. not be
+used in advertising or publicity pertaining to distribution
+of the software without specific, written prior permission.
+M.I.T. and the M.I.T. S.I.P.B. make no representations about
+the suitability of this software for any purpose. It is
+provided "as is" without express or implied warranty.
+
+*/
+
OpenPOWER on IntegriCloud