8
0
mirror of https://github.com/FirebirdSQL/firebird.git synced 2025-01-27 06:43:04 +01:00
firebird-mirror/src/misc/codes.epp

1007 lines
29 KiB
Plaintext
Raw Normal View History

2001-05-23 15:26:42 +02:00
/*
* PROGRAM: JRD Access Method
* MODULE: codes.epp
2001-05-23 15:26:42 +02:00
* DESCRIPTION: Code and message include file generator
*
* The contents of this file are subject to the Interbase Public
* License Version 1.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy
* of the License at http://www.Inprise.com/IPL.html
*
* Software distributed under the License is distributed on an
* "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either express
* or implied. See the License for the specific language governing
* rights and limitations under the License.
*
* The Original Code was created by Inprise Corporation
* and its predecessors. Portions created by Inprise Corporation are
* Copyright (C) Inprise Corporation.
*
* All Rights Reserved.
* Contributor(s): ______________________________________.
* Mark O'Donohue skywalker@users.sourceforge.net
2001-05-23 15:26:42 +02:00
*/
#include "firebird.h"
2004-04-29 00:36:29 +02:00
#include <stdio.h>
2001-05-23 15:26:42 +02:00
#include <stdlib.h>
2003-04-13 19:02:54 +02:00
#ifdef HAVE_UNISTD_H
#include <unistd.h>
2003-04-13 14:08:52 +02:00
#endif
2001-05-23 15:26:42 +02:00
#include "../jrd/common.h"
2003-11-08 17:40:17 +01:00
#include "../jrd/ibase.h"
2001-05-23 15:26:42 +02:00
#include "../jrd/msg_encode.h"
/* The MSG.GDB database is found under the /msgs component subdirectory.
2001-05-23 15:26:42 +02:00
Use links or logicals to point it there, thanks! AMG */
DATABASE DB = FILENAME "msg.fdb";
2001-05-23 15:26:42 +02:00
#define CODES_PAS "gds_codes.pas"
#define CODES_FTN "gds_codes.ftn"
#define CODES_H "codes.h"
#define IBERROR_H "iberror.h"
#define CODETEXT_H "codetext.h"
#define MSGS_H "msgs.h"
#define RDBCODES_H "rdb_codes.h"
#define SQL_CODES_H "sql_code.h"
#define MSGFAC_H "msg_facs.h"
enum formatStyle
{
CSTYLE = 1,
PASSTYLE = 2,
FTNSTYLE = 3,
CPPSTYLE = 4
};
2001-05-23 15:26:42 +02:00
static void build_codes_h(void);
static void build_iberror_h(void);
static void build_other_headers(void);
static void build_msgfac_h(void);
static void move_if_not_identical(const char *, const char *, const char*);
2004-04-29 00:36:29 +02:00
static void add_text(FILE*, formatStyle, const char **);
2001-05-23 15:26:42 +02:00
static const char* genDirectory = NULL;
static const char* genFtnPasDirectory = NULL;
static void check_open(FILE*& f, const char* name, const char* tmp, const char* mode)
{
2004-04-29 00:36:29 +02:00
f = fopen(tmp, mode);
if (!f)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr, "CODES: Unable to open %s in filemode %s for %s\n",
tmp, mode, name);
exit(FINI_ERROR);
}
}
2001-05-23 15:26:42 +02:00
static void check_close(FILE* f, const char* name, const char* tmp, const char* mode,
const char* directory)
{
2004-04-29 00:36:29 +02:00
fclose(f);
move_if_not_identical(name, tmp, directory);
}
2001-05-23 15:26:42 +02:00
const int FAC_SQL_POSITIVE = 14; // facility for positive SQL codes
const int FAC_SQL_NEGATIVE = 13; // ditto for negative codes
2001-05-23 15:26:42 +02:00
const int gds_facility_local = 20;
const SLONG gds_base_local = (SLONG) gds_facility_local << 24;
const SLONG gds_factor_local = 1;
2001-05-23 15:26:42 +02:00
static const char *license[] = {
"The contents of this file are subject to the Interbase Public",
"License Version 1.0 (the \"License\"); you may not use this file",
"except in compliance with the License. You may obtain a copy",
"of the License at http://www.Inprise.com/IPL.html",
"",
"Software distributed under the License is distributed on an",
"\"AS IS\" basis, WITHOUT WARRANTY OF ANY KIND, either express",
"or implied. See the License for the specific language governing",
"rights and limitations under the License.",
"",
"The content of this file was generated by the Firebird project",
"using the program jrd/codes.epp",
2001-05-23 15:26:42 +02:00
0
};
static const char *warn[] = {
"",
"*** WARNING *** - This file is automatically generated by codes.epp - do not edit!",
2001-05-23 15:26:42 +02:00
"",
0
};
static const SCHAR *gds_c_boiler_plate[] = {
2001-05-23 15:26:42 +02:00
"#define gds_arg_end 0 /* end of argument list */",
"#define gds_arg_gds 1 /* generic DSRI status value */",
"#define gds_arg_string 2 /* string argument */",
"#define gds_arg_cstring 3 /* count & string argument */",
"#define gds_arg_number 4 /* numeric argument (long) */",
"#define gds_arg_interpreted 5 /* interpreted status code (string) */",
"#define gds_arg_vms 6 /* VAX/VMS status code (long) */",
"#define gds_arg_unix 7 /* UNIX error code */",
"#define gds_arg_domain 8 /* Apollo/Domain error code */",
"#define gds_arg_dos 9 /* MSDOS/OS2 error code */",
"#define gds_arg_mpexl 10 /* HP MPE/XL error code */",
"#define gds_arg_mpexl_ipc 11 /* HP MPE/XL IPC error code */",
// #'s 12-14 WERE USED BY TWIN SUN AND THUS MUST BE SKIPPED BY US!
2003-02-09 12:39:07 +01:00
"#define gds_arg_next_mach 15 /* NeXT/Mach error code */",
2001-05-23 15:26:42 +02:00
"#define gds_arg_netware 16 /* NetWare error code */",
"#define gds_arg_win32 17 /* Win32 error code */",
"#define gds_arg_warning 18 /* warning argument */",
"",
};
static const SCHAR *gds_cpp_boiler_plate[] = {
"const SLONG gds_arg_end = 0; // end of argument list",
"const SLONG gds_arg_gds = 1; // generic DSRI status value",
"const SLONG gds_arg_string = 2; // string argument",
"const SLONG gds_arg_cstring = 3; // count & string argument",
"const SLONG gds_arg_number = 4; // numeric argument (long)",
"const SLONG gds_arg_interpreted = 5; // interpreted status code (string)",
"const SLONG gds_arg_vms = 6; // VAX/VMS status code (long)",
"const SLONG gds_arg_unix = 7; // UNIX error code",
"const SLONG gds_arg_domain = 8; // Apollo/Domain error code",
"const SLONG gds_arg_dos = 9; // MSDOS/OS2 error code",
"const SLONG gds_arg_mpexl = 10; // HP MPE/XL error code",
"const SLONG gds_arg_mpexl_ipc = 11; // HP MPE/XL IPC error code",
// #'s 12-14 WERE USED BY TWIN SUN AND THUS MUST BE SKIPPED BY US!
"const SLONG gds_arg_next_mach = 15; // NeXT/Mach error code",
"const SLONG gds_arg_netware = 16; // NetWare error code",
"const SLONG gds_arg_win32 = 17; // Win32 error code",
"const SLONG gds_arg_warning = 18; // warning argument",
"",
};
// At first glance, it wasn't evident why isc_facility had to be undefined,
2004-04-23 03:44:05 +02:00
// but it turns that this file includes ibase.h,
// but ibase.h includes iberror.h that's generated by this program!
// The solution is that iberror.h adopts a C++ section like codes.h does.
// Appending "_local" here saves us from any clash.
const int isc_facility_local = 20;
const SLONG isc_base_local = (SLONG) isc_facility_local << 24;
const SLONG isc_factor_local = 1;
2001-05-23 15:26:42 +02:00
2003-02-13 11:11:35 +01:00
static const SCHAR *isc_c_boiler_plate[] = {
2001-05-23 15:26:42 +02:00
"#define isc_arg_end 0 /* end of argument list */",
"#define isc_arg_gds 1 /* generic DSRI status value */",
"#define isc_arg_string 2 /* string argument */",
"#define isc_arg_cstring 3 /* count & string argument */",
"#define isc_arg_number 4 /* numeric argument (long) */",
"#define isc_arg_interpreted 5 /* interpreted status code (string) */",
"#define isc_arg_vms 6 /* VAX/VMS status code (long) */",
"#define isc_arg_unix 7 /* UNIX error code */",
"#define isc_arg_domain 8 /* Apollo/Domain error code */",
"#define isc_arg_dos 9 /* MSDOS/OS2 error code */",
"#define isc_arg_mpexl 10 /* HP MPE/XL error code */",
"#define isc_arg_mpexl_ipc 11 /* HP MPE/XL IPC error code */",
// #'s 12-14 WERE USED BY TWIN SUN AND THUS MUST BE SKIPPED BY US!
2001-05-23 15:26:42 +02:00
2003-02-09 12:39:07 +01:00
"#define isc_arg_next_mach 15 /* NeXT/Mach error code */",
2001-05-23 15:26:42 +02:00
"#define isc_arg_netware 16 /* NetWare error code */",
"#define isc_arg_win32 17 /* Win32 error code */",
"#define isc_arg_warning 18 /* warning argument */",
"",
};
static const SCHAR *isc_cpp_boiler_plate[] = {
"const SLONG isc_arg_end = 0; // end of argument list ",
"const SLONG isc_arg_gds = 1; // generic DSRI status value ",
"const SLONG isc_arg_string = 2; // string argument ",
"const SLONG isc_arg_cstring = 3; // count & string argument ",
"const SLONG isc_arg_number = 4; // numeric argument (long) ",
"const SLONG isc_arg_interpreted = 5; // interpreted status code (string) ",
"const SLONG isc_arg_vms = 6; // VAX/VMS status code (long) ",
"const SLONG isc_arg_unix = 7; // UNIX error code ",
"const SLONG isc_arg_domain = 8; // Apollo/Domain error code ",
"const SLONG isc_arg_dos = 9; // MSDOS/OS2 error code ",
"const SLONG isc_arg_mpexl = 10; // HP MPE/XL error code ",
"const SLONG isc_arg_mpexl_ipc = 11; // HP MPE/XL IPC error code ",
// #'s 12-14 WERE USED BY TWIN SUN AND THUS MUST BE SKIPPED BY US!
"const SLONG isc_arg_next_mach = 15; // NeXT/Mach error code ",
"const SLONG isc_arg_netware = 16; // NetWare error code ",
"const SLONG isc_arg_win32 = 17; // Win32 error code ",
"const SLONG isc_arg_warning = 18; // warning argument ",
"",
};
2003-02-13 11:11:35 +01:00
static const SCHAR *pas_boiler_plate[] = {
2001-05-23 15:26:42 +02:00
"\tgds_arg_end\t\t= 0;\t(* end of argument list *)",
"\tgds_arg_gds\t\t= 1;\t(* generic DSRI status value *)",
"\tgds_arg_string\t\t= 2;\t(* string argument *)",
"\tgds_arg_cstring\t\t= 3;\t(* count & string argument *)",
"\tgds_arg_number\t\t= 4;\t(* numeric argument (long) *)",
"\tgds_arg_interpreted\t= 5;\t(* interpreted status code (string) *)",
"\tgds_arg_vms\t\t= 6;\t(* VAX/VMS status code (long) *)",
"\tgds_arg_unix\t\t= 7;\t(* UNIX error code *)",
"\tgds_arg_domain\t\t= 8;\t(* Apollo/Domain error code *)",
"\tgds_arg_dos\t\t= 9;\t(* MSDOS/OS2 error code *)",
"",
};
2003-02-13 11:11:35 +01:00
static const SCHAR *ftn_boiler_plate_data[] = {
2001-05-23 15:26:42 +02:00
"",
" PARAMETER (",
" + GDS_ARG_END = 0, { end of argument list }",
" + GDS_ARG_GDS = 1, { generic DSRI status value }",
" + GDS_ARG_STRING = 2, { string argument }",
" + GDS_ARG_CSTRING = 3, { count & string argument }",
" + GDS_ARG_NUMBER = 4, { numeric argument (long) }",
" + GDS_ARG_INTERPRETED = 5, { interpreted status code (string) }",
" + GDS_ARG_VMS = 6, { VAX/VMS status code (long) }",
" + GDS_ARG_UNIX = 7, { UNIX error code }",
" + GDS_ARG_DOMAIN = 8, { Apollo/Domain error code }",
" + GDS_ARG_DOS = 9) { Apollo/Domain error code }",
"",
};
2003-02-13 11:11:35 +01:00
static const SCHAR *ftn_boiler_plate_decls[] = {
2001-05-23 15:26:42 +02:00
" INTEGER*4",
" + GDS_ARG_END, { end of argument list }",
" + GDS_ARG_GDS, { generic DSRI status value }",
" + GDS_ARG_STRING, { string argument }",
" + GDS_ARG_CSTRING, { count & string argument }",
" + GDS_ARG_NUMBER, { numeric argument (long) }",
" + GDS_ARG_INTERPRETED, { interpreted status code (string) }",
" + GDS_ARG_VMS, { VAX/VMS status code (long) }",
" + GDS_ARG_UNIX, { UNIX error code }",
" + GDS_ARG_DOMAIN, { Apollo/Domain error code }",
" + GDS_ARG_DOS { MSDOS/OS2 error code }",
"",
};
2003-02-13 11:11:35 +01:00
static const SCHAR sql_code_boiler_plate[] =
2003-02-28 13:57:13 +01:00
"static const SSHORT gds__sql_code [] = {";
2001-05-23 15:26:42 +02:00
int CLIB_ROUTINE main( int argc, char *argv[])
2001-05-23 15:26:42 +02:00
{
/*************************************
*
* m a i n
*
**************************************
*
* Functional description
* Generate both code definition
* include file and message text
2001-05-23 15:26:42 +02:00
* include file.
*
**************************************/
READY
ON_ERROR
2004-04-29 00:36:29 +02:00
printf("Attach failed.\n");
2003-11-08 17:40:17 +01:00
isc_print_status(gds_status);
2001-05-23 15:26:42 +02:00
exit(FINI_ERROR);
END_ERROR;
// See if the user has specified an optional output directory
if (argc >= 1 ) {
genDirectory = argv[1];
}
if (argc >= 2 ) {
genFtnPasDirectory = argv[2];
}
2001-05-23 15:26:42 +02:00
START_TRANSACTION;
build_iberror_h();
build_codes_h();
build_msgfac_h();
build_other_headers();
COMMIT;
FINISH;
// exit(0);
return 0;
2001-05-23 15:26:42 +02:00
}
static void build_msgfac_h(void)
{
/*******************************************
*
* b u i l d _ m s g f a c _ h
*
*******************************************
*
* Functional desciption
* Function creates the msgfac.h
2001-05-23 15:26:42 +02:00
* file which contains a listing of valid
* facilities for the error codes.
*
*******************************************/
2004-04-29 00:36:29 +02:00
FILE *msgfac = NULL;
2001-05-23 15:26:42 +02:00
/* Open msgfac.h in the current directory */
check_open(msgfac, MSGFAC_H, "tmpcode1", "w");
2001-05-23 15:26:42 +02:00
add_text(msgfac, CSTYLE, license);
add_text(msgfac, CSTYLE, warn);
2004-04-29 00:36:29 +02:00
fprintf(msgfac, "/*\n");
fprintf(msgfac, " * MODULE: msg_facs.h\n");
fprintf(msgfac, " * DESCRIPTION: ISC message facilities\n");
fprintf(msgfac, " *\n");
fprintf(msgfac, " */\n");
fprintf(msgfac, "\n\n\n");
fprintf(msgfac, "/******************************/\n");
fprintf(msgfac, "/* ISC message facilities */\n");
fprintf(msgfac, "/******************************/\n");
fprintf(msgfac, "\n");
2004-05-09 07:48:33 +02:00
fprintf(msgfac, "struct _facilities {\n");
2004-04-29 00:36:29 +02:00
fprintf(msgfac, "\tint fac_code;\n");
fprintf(msgfac, "\tchar *facility;\n");
fprintf(msgfac, "\t};\n\n");
fprintf(msgfac, "static const struct _facilities facilities[] = {\n");
2001-05-23 15:26:42 +02:00
FOR F IN FACILITIES WITH ANY FAC_CODE IN SYSTEM_ERRORS OVER FAC_CODE
2004-04-29 00:36:29 +02:00
fprintf(msgfac, "\t{%d, \"%-10.10s\"},\n", F.FAC_CODE, F.FACILITY);
2001-05-23 15:26:42 +02:00
END_FOR;
2004-04-29 00:36:29 +02:00
fprintf(msgfac, "\t{0, NULL}\n};\n\n");
fprintf(msgfac, "\n");
check_close(msgfac, MSGFAC_H, "tmpcode1", "w", genDirectory);
2001-05-23 15:26:42 +02:00
}
static void build_iberror_h(void)
{
/*******************************************
*
* b u i l d _ i b e r r o r _ h
*
*******************************************
*
* Functional desciption
* Function creates the iberror.h
2001-05-23 15:26:42 +02:00
* file which contains c and isc_
* style error codes.
*
*******************************************/
2004-04-29 00:36:29 +02:00
FILE *iberror = NULL;
int i, code = 1, last_code = code - 1;
2001-05-23 15:26:42 +02:00
unsigned long new_code = 0L;
/* Open iberror.h in the current directory. */
check_open(iberror, IBERROR_H, "tmpcode2", "w");
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
fprintf(iberror, "\n#ifndef JRD_GEN_IBERROR_H\n");
fprintf(iberror, "#define JRD_GEN_IBERROR_H\n");
2001-05-23 15:26:42 +02:00
add_text(iberror, CSTYLE, license);
add_text(iberror, CSTYLE, warn);
2004-04-29 00:36:29 +02:00
fprintf(iberror, "/*\n");
fprintf(iberror, " * MODULE: iberror.h\n");
fprintf(iberror, " * DESCRIPTION: ISC error codes\n");
fprintf(iberror, " *\n");
fprintf(iberror, " */\n");
fprintf(iberror, "\n\n\n");
fprintf(iberror, "/***********************/\n");
fprintf(iberror, "/* ISC Error Codes */\n");
fprintf(iberror, "/***********************/\n");
fprintf(iberror, "\n");
fprintf(iberror, "\n#ifdef __cplusplus /* c++ definitions */\n\n");
2004-04-29 00:36:29 +02:00
fprintf(iberror,
"const SLONG isc_facility = %d;\n", isc_facility_local);
2004-04-29 00:36:29 +02:00
fprintf(iberror,
2003-09-14 02:26:30 +02:00
"const SLONG isc_base = %"SLONGFORMAT"L;\n", isc_base_local);
2004-04-29 00:36:29 +02:00
fprintf(iberror,
2003-09-14 02:26:30 +02:00
"const SLONG isc_factor = %"SLONGFORMAT";\n", isc_factor_local);
// Append the ISC C++ boiler plate
int numLines = FB_NELEM(isc_cpp_boiler_plate);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(iberror, "%s\n", isc_cpp_boiler_plate[i]);
}
// Fetch error codes from SYSTEM_ERRORS relation.
// Write them out using the ISC prefix.
FOR S IN SYSTEM_ERRORS CROSS N IN MESSAGES OVER NUMBER WITH
N.FAC_CODE = S.FAC_CODE SORTED BY N.FAC_CODE, S.NUMBER
// The only facility that is guaranteed to have all codes in
// system errors is JRD
if (last_code + 1 != N.CODE && N.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
"Warning: missing codes between %d and %d (exclusive)\n",
last_code, (int) N.CODE);
}
last_code = N.CODE;
new_code = ENCODE_ISC_MSG(S.NUMBER, N.FAC_CODE);
2004-04-29 00:36:29 +02:00
fprintf(iberror, "const SLONG isc_%-32.32s = %luL;\n", S.GDS_SYMBOL,
new_code);
++code;
END_FOR;
--code;
2004-04-29 00:36:29 +02:00
fprintf(iberror, "const SLONG isc_%-32.32s = %d;\n", "err_max", code);
fprintf(iberror, "\n");
2004-04-29 00:36:29 +02:00
fprintf(iberror, "#else /* c definitions */\n\n");
// Reset counters for a new iteration.
code = 1;
last_code = code - 1;
new_code = 0L;
2004-04-29 00:36:29 +02:00
fprintf(iberror, "#define isc_facility %d\n", isc_facility_local);
fprintf(iberror, "#define isc_base %"SLONGFORMAT"L\n", isc_base_local);
fprintf(iberror, "#define isc_factor %"SLONGFORMAT"\n", isc_factor_local);
fprintf(iberror, "\n");
// Append the ISC C boiler plate
numLines = FB_NELEM(isc_c_boiler_plate);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(iberror, "%s\n", isc_c_boiler_plate[i]);
}
// Fetch error codes from SYSTEM_ERRORS relation.
// Write them out using the ISC prefix.
2001-05-23 15:26:42 +02:00
FOR S IN SYSTEM_ERRORS CROSS N IN MESSAGES OVER NUMBER WITH
N.FAC_CODE = S.FAC_CODE SORTED BY N.FAC_CODE, S.NUMBER
// The only facility that is guaranteed to have all codes in
// system errors is JRD
if (last_code + 1 != N.CODE && N.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
"Warning: missing codes between %d and %d (exclusive)\n",
last_code, (int) N.CODE);
}
2001-05-23 15:26:42 +02:00
last_code = N.CODE;
new_code = ENCODE_ISC_MSG(S.NUMBER, N.FAC_CODE);
2004-04-29 00:36:29 +02:00
fprintf(iberror, "#define isc_%-32.32s %luL\n", S.GDS_SYMBOL,
2001-05-23 15:26:42 +02:00
new_code);
++code;
END_FOR;
2001-05-23 15:26:42 +02:00
--code;
2004-04-29 00:36:29 +02:00
fprintf(iberror, "#define isc_%-32.32s %d\n", "err_max", code);
fprintf(iberror, "\n");
fprintf(iberror, "#endif\n\n");
fprintf(iberror, "#endif /* JRD_GEN_IBERROR_H */\n");
check_close(iberror, IBERROR_H, "tmpcode2", "w", genDirectory);
2001-05-23 15:26:42 +02:00
}
static void build_codes_h(void)
{
/*******************************************
*
* b u i l d _ c o d e s _ h
*
*******************************************
*
* Functional desciption
* Function creates the codes.h
2001-05-23 15:26:42 +02:00
* file which contains c and isc_
* style error codes.
*
*******************************************/
2004-04-29 00:36:29 +02:00
FILE *c_codes = NULL;
2003-04-13 14:08:52 +02:00
int i, code = 1, last_code = code - 1;
2001-05-23 15:26:42 +02:00
unsigned long new_code = 0L;
// Open codes.h in the current directory.
2001-05-23 15:26:42 +02:00
check_open(c_codes, CODES_H, "tmpcode3", "w");
2001-05-23 15:26:42 +02:00
add_text(c_codes, CSTYLE, license);
add_text(c_codes, CSTYLE, warn);
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "\n#ifndef JRD_GEN_CODES_H\n");
fprintf(c_codes, "#define JRD_GEN_CODES_H\n");
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "\n#ifdef __cplusplus /* c++ definitions */\n\n");
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "const SLONG gds_facility = %d;\n", gds_facility_local);
fprintf(c_codes, "const SLONG gds_err_base = %ldL;\n", gds_base_local);
fprintf(c_codes, "const SLONG gds_err_factor = %ld;\n", gds_factor_local);
2001-05-23 15:26:42 +02:00
// Append the C++ boiler plate
int numLines = FB_NELEM(gds_cpp_boiler_plate);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "%s\n", gds_cpp_boiler_plate[i]);
}
2001-05-23 15:26:42 +02:00
FOR S IN SYSTEM_ERRORS CROSS N IN MESSAGES OVER NUMBER WITH
N.FAC_CODE = S.FAC_CODE SORTED BY N.FAC_CODE, S.NUMBER
// The only facility that is guaranteed to have all codes in
// system errors is JRD
if (last_code + 1 != N.CODE && N.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
2001-05-23 15:26:42 +02:00
"Warning: missing codes between %d and %d (exclusive)\n",
last_code, (int) N.CODE);
}
2001-05-23 15:26:42 +02:00
last_code = N.CODE;
new_code = ENCODE_ISC_MSG(S.NUMBER, N.FAC_CODE);
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "const SLONG gds_%-32.32s = %luL;\n", S.GDS_SYMBOL,
2001-05-23 15:26:42 +02:00
new_code);
++code;
/* make sure that the SQL code is also present in the SQLERR facility */
/**** this part really should be done via a trigger on the database--
commented out for now - deej
got_it = 0;
if (S.SQL_CODE < 0)
2001-05-23 15:26:42 +02:00
{
srchnum = 1000 + S.SQL_CODE;
**FOR M IN MESSAGES WITH M.FAC_CODE = FAC_SQL_NEGATIVE
AND M.NUMBER = srchnum
got_it = 1;
**END_FOR;
2001-05-23 15:26:42 +02:00
}
else
2001-05-23 15:26:42 +02:00
{
srchnum = S.SQL_CODE;
**FOR M IN MESSAGES WITH M.FAC_CODE = FAC_SQL_POSITIVE
AND M.NUMBER = srchnum
got_it = 1;
**END_FOR;
2001-05-23 15:26:42 +02:00
}
if (!got_it)
2001-05-23 15:26:42 +02:00
{
2004-04-29 00:36:29 +02:00
printf ("codes: msg %d: sql-code %d, is not in the SQLERR facility\n",
N.NUMBER, S.SQL_CODE);
ROLLBACK;
FINISH;
exit (FINI_ERROR);
2001-05-23 15:26:42 +02:00
} ****/
END_FOR;
2001-05-23 15:26:42 +02:00
--code;
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "const SLONG gds_%-32.32s = %dL;\n", "err_max", code);
fprintf(c_codes, "\n");
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#else /* c definitions */\n\n");
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#define gds_facility %d\n", gds_facility_local);
fprintf(c_codes, "#define gds_err_base %ldL\n", gds_base_local);
fprintf(c_codes, "#define gds_err_factor %ld\n", gds_factor_local);
2001-05-23 15:26:42 +02:00
// Reset the variables for another trip round the loop.
2001-05-23 15:26:42 +02:00
code = 1;
last_code = code - 1;
new_code = 0L;
// Append the C boiler plate
numLines = FB_NELEM(gds_c_boiler_plate);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "%s\n", gds_c_boiler_plate[i]);
}
2001-05-23 15:26:42 +02:00
FOR S IN SYSTEM_ERRORS CROSS N IN MESSAGES OVER NUMBER WITH
N.FAC_CODE = S.FAC_CODE SORTED BY N.FAC_CODE, S.NUMBER
// The only facility that is guaranteed to have all codes in
// system errors is JRD
if (last_code + 1 != N.CODE && N.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
2001-05-23 15:26:42 +02:00
"Warning: missing codes between %d and %d (exclusive)\n",
last_code, (int) N.CODE);
}
2001-05-23 15:26:42 +02:00
last_code = N.CODE;
new_code = ENCODE_ISC_MSG(S.NUMBER, N.FAC_CODE);
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#define gds__%-32.32s %luL\n", S.GDS_SYMBOL,
2001-05-23 15:26:42 +02:00
new_code);
++code;
/* make sure that the SQL code is also present in the SQLERR facility */
/**** this part really should be done via a trigger on the database--
commented out for now - deej
got_it = 0;
if (S.SQL_CODE < 0)
{
srchnum = 1000 + S.SQL_CODE;
**FOR M IN MESSAGES WITH M.FAC_CODE = FAC_SQL_NEGATIVE
AND M.NUMBER = srchnum
got_it = 1;
**END_FOR;
}
else
{
srchnum = S.SQL_CODE;
**FOR M IN MESSAGES WITH M.FAC_CODE = FAC_SQL_POSITIVE
AND M.NUMBER = srchnum
got_it = 1;
**END_FOR;
}
if (!got_it)
{
2004-04-29 00:36:29 +02:00
printf ("codes: msg %d: sql-code %d, is not in the SQLERR facility\n",
N.NUMBER, S.SQL_CODE);
ROLLBACK;
FINISH;
exit (FINI_ERROR);
} ****/
END_FOR;
2001-05-23 15:26:42 +02:00
--code;
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#define gds_%-32.32s %d\n", "err_max", code);
fprintf(c_codes, "\n");
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#endif\n\n");
// Append the ISC error codes
/* I have removed the isc errors from codes.h since they are all now placed
into iberror.h - If it needs to be replaced then it can be copied back
from gen iberror routine. I now do the include of that file.
MOD 17-07-2001
*/
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#include \"iberror.h\"\n\n");
2004-04-29 00:36:29 +02:00
fprintf(c_codes, "#endif /* JRD_GEN_CODES_H */\n");
check_close(c_codes, CODES_H, "tmpcode3", "w", genDirectory);
2001-05-23 15:26:42 +02:00
}
static void build_other_headers(void)
{
/********************************************
*
* b u i l d _ o t h e r _ h e a d e r s
*
*********************************************
*
* Functional desciption
* Function creates the other header
* files.
2001-05-23 15:26:42 +02:00
*
*********************************************/
SCHAR text[128];
2001-05-23 15:26:42 +02:00
int last_code, code, i;
unsigned long new_code = 0L;
/* Use the check_open function to open header files in current directory. */
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
FILE* pas_codes = NULL;
check_open(pas_codes, CODES_PAS, "tmpcode4", "w");
2004-04-29 00:36:29 +02:00
FILE* ftn_codes = NULL;
check_open(ftn_codes, CODES_FTN, "tmpcode5", "w");
2004-04-29 00:36:29 +02:00
FILE* code_text = NULL;
check_open(code_text, CODETEXT_H, "tmpcode6", "w");
2004-04-29 00:36:29 +02:00
FILE* msgs = NULL;
check_open(msgs, MSGS_H, "tmpcode7", "w");
2004-04-29 00:36:29 +02:00
FILE* rdbcodes = NULL;
check_open(rdbcodes, RDBCODES_H, "tmpcode8", "w");
2001-05-23 15:26:42 +02:00
/* Add license */
add_text(pas_codes, PASSTYLE, license);
add_text(pas_codes, PASSTYLE, warn);
add_text(ftn_codes, FTNSTYLE, license);
add_text(ftn_codes, FTNSTYLE, warn);
add_text(code_text, CSTYLE, license);
add_text(code_text, CSTYLE, warn);
add_text(msgs, CSTYLE, license);
add_text(msgs, CSTYLE, warn);
add_text(rdbcodes, CSTYLE, license);
add_text(rdbcodes, CSTYLE, warn);
/* Start the PASCAL codes file */
2004-04-29 00:36:29 +02:00
fprintf(pas_codes, "\n"
"const\n"
"\tgds_facility\t\t= %d;\n"
"\tgds_err_base\t\t= %ld;\n"
"\tgds_err_factor\t\t= %ld;\n",
gds_facility_local, gds_base_local, gds_factor_local);
2001-05-23 15:26:42 +02:00
int numLines = FB_NELEM(pas_boiler_plate);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(pas_codes, "%s\n", pas_boiler_plate[i]);
}
2001-05-23 15:26:42 +02:00
/* Start the FORTRAN codes file */
2004-04-29 00:36:29 +02:00
fprintf(ftn_codes, "\n"
" INTEGER*4\n"
" + GDS_FACILITY,\n"
" + GDS_ERR_BASE,\n"
" + GDS_ERR_FACTOR\n");
2001-05-23 15:26:42 +02:00
numLines = FB_NELEM(ftn_boiler_plate_decls);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(ftn_codes, "%s\n", ftn_boiler_plate_decls[i]);
}
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
fprintf(ftn_codes, "\n"
" PARAMETER (\n"
" + GDS_FACILITY = %d,\n"
" + GDS_ERR_BASE = %ld,\n"
" + GDS_ERR_FACTOR = %ld)\n",
gds_facility_local, gds_base_local, gds_factor_local);
2001-05-23 15:26:42 +02:00
numLines = FB_NELEM(ftn_boiler_plate_data);
for (i = 0; i < numLines; i++) {
2004-04-29 00:36:29 +02:00
fprintf(ftn_codes, "%s\n", ftn_boiler_plate_data[i]);
}
/* Start the rdb_codes.h */
2004-04-29 00:36:29 +02:00
fprintf(rdbcodes, "static SLONG user_codes[] = {\n");
fprintf(rdbcodes, "1,\n");
/* Start the codetext.h */
2004-04-29 00:36:29 +02:00
fprintf(code_text, "static const struct {\n");
fprintf(code_text, "\tconst SCHAR *code_string;\n");
fprintf(code_text, "\tSLONG code_number;\n");
fprintf(code_text, "} codes[] =\n{\n");
2001-05-23 15:26:42 +02:00
/* Start the MSGS file */
2004-04-29 00:36:29 +02:00
fprintf(msgs, "static const SCHAR * const messages[] = {\n");
fprintf(msgs, "\t\"unassigned code\",\n");
2001-05-23 15:26:42 +02:00
/* Fetch error codes from SYSTEM_ERRORS relation. Write them
out to the pascal, fortran, and rdb header files */
code = 1;
last_code = code - 1;
FOR S IN SYSTEM_ERRORS CROSS N IN MESSAGES OVER NUMBER WITH
N.FAC_CODE = S.FAC_CODE SORTED BY N.FAC_CODE, S.NUMBER
// The only facility that is guaranteed to have all codes in
// system errors is JRD
if (last_code + 1 != N.CODE && N.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
2001-05-23 15:26:42 +02:00
"Warning: missing codes between %d and %d (exclusive)\n",
last_code, (int) N.CODE);
}
2001-05-23 15:26:42 +02:00
last_code = N.CODE;
new_code = ENCODE_ISC_MSG(N.NUMBER, N.FAC_CODE);
2004-04-29 00:36:29 +02:00
fprintf(pas_codes, "\tgds_%-32.32s = %lu;\n", S.GDS_SYMBOL,
2001-05-23 15:26:42 +02:00
new_code);
2004-04-29 00:36:29 +02:00
fprintf(ftn_codes,
2003-04-01 23:59:31 +02:00
" INTEGER*4 GDS__%-32.32s\n PARAMETER (GDS__%-32.32s = %lu)\n",
2001-05-23 15:26:42 +02:00
S.GDS_SYMBOL, S.GDS_SYMBOL, new_code);
2004-04-29 00:36:29 +02:00
fprintf(rdbcodes, "%ld,\n", S.VMS_CODE);
2001-05-23 15:26:42 +02:00
SCHAR* q = text;
SCHAR* end = q;
for (const SCHAR* p = N.TEXT; *p && p < N.TEXT + sizeof(N.TEXT); p++)
{
2001-05-23 15:26:42 +02:00
if (*p == '"')
*q++ = '\\';
*q++ = *p;
if (*p != ' ')
end = q;
}
*end = 0;
q = S.GDS_SYMBOL;
while (*q && *q != ' ' && q < S.GDS_SYMBOL + sizeof(S.GDS_SYMBOL) - 1)
q++;
*q = 0;
// CVC: Restore this line if something strange happen.
2004-04-29 00:36:29 +02:00
//fprintf(msgs, "\t\"%s\",\t\t/*%d, %-32.32s*/\n",
fprintf(msgs, "\t\"%s\",\t\t/* %d, %s */\n",
2001-05-23 15:26:42 +02:00
text, code, S.GDS_SYMBOL);
2004-04-29 00:36:29 +02:00
fprintf(code_text, "\t{\"%s\", %lu},\n", S.GDS_SYMBOL, new_code);
2001-05-23 15:26:42 +02:00
++code;
END_FOR;
/* end the rdb_codes.h */
2004-04-29 00:36:29 +02:00
fprintf(rdbcodes, "};\n");
/* end the codetext.h */
2004-04-29 00:36:29 +02:00
fprintf(code_text, "\t{NULL, 0}\n");
fprintf(code_text, "};\n");
/* end the msgs.h */
2004-04-29 00:36:29 +02:00
fprintf(msgs, "\t0\t\t\t\t\t\t/* Null entry to terminate list */\n");
fprintf(msgs, "};\n");
check_close(pas_codes, CODES_PAS, "tmpcode4", "w", genFtnPasDirectory);
check_close(ftn_codes, CODES_FTN, "tmpcode5", "w", genFtnPasDirectory);
check_close(code_text, CODETEXT_H, "tmpcode6", "w", genDirectory);
check_close(msgs, MSGS_H, "tmpcode7", "w", genDirectory);
check_close(rdbcodes, RDBCODES_H, "tmpcode8", "w", genDirectory);
2001-05-23 15:26:42 +02:00
// build sql_code.h
2001-05-23 15:26:42 +02:00
2004-04-29 00:36:29 +02:00
FILE* sql_codes = NULL;
check_open(sql_codes, SQL_CODES_H, "tmpcode9", "w");
2001-05-23 15:26:42 +02:00
add_text(sql_codes, CSTYLE, license);
add_text(sql_codes, CSTYLE, warn);
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, "%s\n", sql_code_boiler_plate);
const int DEFAULT_SQL_CODE = -999; // InterBase error
2001-05-23 15:26:42 +02:00
i = 0;
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, "%4d /* No Error */", 0);
2001-05-23 15:26:42 +02:00
FOR E IN SYSTEM_ERRORS SORTED BY E.FAC_CODE, E.NUMBER
// The only facility that is guaranteed to have all codes
// in system errors is JRD
2001-05-23 15:26:42 +02:00
if (E.NUMBER != (SSHORT) i + 1 && E.FAC_CODE == 0)
{
2004-04-29 00:36:29 +02:00
fprintf(stderr,
2001-05-23 15:26:42 +02:00
"Warning: Sequence of error numbers is bad %d!\n",
E.NUMBER);
}
i = E.NUMBER;
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, ",\n");
if (E.SQL_CODE.NULL)
{
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, "%4d /* %3d %-32.32s (default) */",
DEFAULT_SQL_CODE, E.NUMBER, E.GDS_SYMBOL);
}
else {
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, "%4d /* %3d %-32.32s */",
(int) E.SQL_CODE, E.NUMBER, E.GDS_SYMBOL);
2001-05-23 15:26:42 +02:00
}
END_FOR;
--code;
2004-04-29 00:36:29 +02:00
fprintf(sql_codes, "\n};\n");
check_close(sql_codes, SQL_CODES_H, "tmpcode9", "w", genDirectory);
2001-05-23 15:26:42 +02:00
}
static void move_if_not_identical( const char* original, const char* new_file,
const char *directory)
2001-05-23 15:26:42 +02:00
{
char origName[1000];
char buffer[1000];
#if defined(WIN_NT) && !defined(__GNUC__)
if ( directory != NULL) {
sprintf(origName,"%s\\%s", directory, original);
}
else {
sprintf(origName,".\\%s", original);
}
/*
* This is a trick to make on systems previous to W2K were apparently
* fc does not return a errorlevel, but find return it (1 found 0 not found)
* FC: appear only where there are no differences (and the switch /B is not used)
*/
sprintf(buffer, "fc %s %s | find \"FC:\" > nul", new_file, origName);
#else
if ( directory != NULL) {
sprintf(origName,"%s/%s", directory, original);
}
else {
sprintf(origName,"./%s", original);
}
sprintf(buffer, "cmp -s %s %s", new_file, origName);
#endif
2001-05-23 15:26:42 +02:00
/* If the new file is identical to the original, then don't update
the original */
if (system(buffer) == 0) {
2004-04-29 00:36:29 +02:00
fprintf(stdout, "No need to update %s\n", origName);
2001-05-23 15:26:42 +02:00
unlink(new_file);
}
else {
/* Original file is missing or different */
#if defined(WIN_NT) && !defined(__GNUC__)
sprintf(buffer, "move %s %s > nul", new_file, origName);
#else
sprintf(buffer, "mv -f %s %s", new_file, origName);
#endif
2001-05-23 15:26:42 +02:00
if (system(buffer) != 0) {
2004-04-29 00:36:29 +02:00
fprintf(stderr, "Error moving %s to %s!\n",
new_file, origName);
2001-05-23 15:26:42 +02:00
exit(FINI_ERROR);
}
else
2004-04-29 00:36:29 +02:00
fprintf(stdout, "Updated %s\n", origName);
2001-05-23 15:26:42 +02:00
}
}
2004-04-29 00:36:29 +02:00
static void add_text(FILE * fd, formatStyle style, const char **text)
2001-05-23 15:26:42 +02:00
{
/*******************************************
*
* a d d _ t e x t
*
*******************************************
*
* Functional desciption
* Function adds text as comment
* in 'style' language
*
*******************************************/
switch (style) {
case CSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "/*\n");
2001-05-23 15:26:42 +02:00
break;
case PASSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "(*\n");
2001-05-23 15:26:42 +02:00
break;
case FTNSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "C --\n");
2001-05-23 15:26:42 +02:00
break;
case CPPSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "//\n");
break;
2001-05-23 15:26:42 +02:00
default:
2004-04-29 00:36:29 +02:00
fprintf(stderr, "Error writing license\n");
2001-05-23 15:26:42 +02:00
exit(FINI_ERROR);
break;
}
for (const char** ptr = text; *ptr; ++ptr)
{
2001-05-23 15:26:42 +02:00
switch (style) {
case CSTYLE:
case PASSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, " * ");
2001-05-23 15:26:42 +02:00
break;
case FTNSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "C -- ");
2001-05-23 15:26:42 +02:00
break;
case CPPSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "// ");
break;
2001-05-23 15:26:42 +02:00
}
2004-04-29 00:36:29 +02:00
fprintf(fd, "%s\n", *ptr);
2001-05-23 15:26:42 +02:00
}
switch (style) {
case CSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, " */\n");
2001-05-23 15:26:42 +02:00
break;
case PASSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, " *)\n");
2001-05-23 15:26:42 +02:00
break;
case FTNSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "C --\n");
2001-05-23 15:26:42 +02:00
break;
case CPPSTYLE:
2004-04-29 00:36:29 +02:00
fprintf(fd, "//\n");
break;
2001-05-23 15:26:42 +02:00
}
}