Skip to content

Commit

Permalink
Add >>IMP INCLUDE directive
Browse files Browse the repository at this point in the history
  • Loading branch information
engboris committed May 3, 2024
1 parent 87c4fb2 commit 7b94002
Show file tree
Hide file tree
Showing 11 changed files with 183 additions and 4 deletions.
2 changes: 2 additions & 0 deletions NEWS
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ NEWS - user visible changes -*- outline -*-
calls to externals. The files are put into quotes, unless they start by
'<'. Quoted files are expected to have absolute paths, as the C compiler
is called in a temp directory instead of the project directory.
The directive >>IMP INCLUDE "FILE.h" or >>IMP INCLUDE <FILE.h> can be used
as an alternative to this compiler option.

** output of unlimited errors may be requested by -fmax-errors=0,
to stop compiliation at first error use -Wfatal-errors
Expand Down
6 changes: 6 additions & 0 deletions cobc/ChangeLog
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,12 @@
replace stream) and we use a circular buffer for the temporary
queue of tokens instead of a list.

2024-04-25 Boris Eng <boris.eng@ocamlpro.com>

* cobc.h, pplex.l, ppparse.y: new >>IMP INCLUDE directive to include
multiple header files in the C generated code. Has the same behavior as the
--include compiler option.

2024-03-17 Fabrice Le Fessant <fabrice.le_fessant@ocamlpro.com>
Emilien Lemaire <emilien.lemaire@ocamlpro.com>

Expand Down
1 change: 1 addition & 0 deletions cobc/cobc.c
Original file line number Diff line number Diff line change
Expand Up @@ -237,6 +237,7 @@ const char *cb_storage_file_name = NULL;
const char *cb_call_extfh = NULL;
struct cb_text_list *cb_copy_list = NULL;
struct cb_text_list *cb_include_file_list = NULL;
struct cb_text_list *cb_include_file_list_directive = NULL;
struct cb_text_list *cb_include_list = NULL;
struct cb_text_list *cb_depend_list = NULL;
struct cb_text_list *cb_intrinsic_list = NULL;
Expand Down
3 changes: 2 additions & 1 deletion cobc/cobc.h
Original file line number Diff line number Diff line change
Expand Up @@ -276,7 +276,7 @@ enum cb_sub_check {
struct cb_text_list {
struct cb_text_list *next; /* next pointer */
struct cb_text_list *last;
const char *text;
char *text;
};

/* Structure for extended filenames */
Expand Down Expand Up @@ -475,6 +475,7 @@ extern FILE *cb_depend_file;
extern struct cb_text_list *cb_depend_list;
extern struct cb_text_list *cb_copy_list;
extern struct cb_text_list *cb_include_file_list;
extern struct cb_text_list *cb_include_file_list_directive;
extern struct cb_text_list *cb_include_list;
extern struct cb_text_list *cb_intrinsic_list;
extern struct cb_text_list *cb_extension_list;
Expand Down
23 changes: 20 additions & 3 deletions cobc/codegen.c
Original file line number Diff line number Diff line change
Expand Up @@ -1830,14 +1830,31 @@ output_gnucobol_defines (const char *formatted_date)
output_line ("#define COB_MODULE_TIME\t\t%d", i);

{
struct cb_text_list *l = cb_include_file_list ;
for (;l;l=l->next){
if (l->text[0] == '<'){
struct cb_text_list *l = cb_include_file_list;
struct cb_text_list *ld = cb_include_file_list_directive;
struct cb_text_list *next;
for (;l;l=l->next) {
if (l->text[0] == '<') {
output_line ("#include %s", l->text);
} else {
output_line ("#include \"%s\"", l->text);
}
}
while (ld) {
if (ld->text[0] == '<') {
output_line ("#include %s", ld->text);
} else {
output_line ("#include \"%s\"", ld->text);
}
next = ld->next;
if (ld != NULL) {
cobc_free (ld);
cobc_free (ld->text);
ld = NULL;
}
ld = next;
}
cb_include_file_list_directive = NULL;
}

}
Expand Down
16 changes: 16 additions & 0 deletions cobc/pplex.l
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,7 @@ ALNUM_LITERAL_A "\'"([^''\n]|("\'"[0-9][0-9, ]+"\'"))*"\'"
ALNUM_LITERAL {ALNUM_LITERAL_Q}|{ALNUM_LITERAL_A}
SET_PAREN_LIT \([^()\n]*\)
DEFNUM_LITERAL [+-]?[0-9]*[\.]*[0-9]+
RAW_SEQ [^ \n]+

AREA_A [ ]?#
MAYBE_AREA_A [ ]?#?
Expand All @@ -227,6 +228,7 @@ MAYBE_AREA_A [ ]?#?
%x ALNUM_LITERAL_STATE
%x CONTROL_STATEMENT_STATE
%x DISPLAY_DIRECTIVE_STATE
%x IMP_DIRECTIVE_STATE

%%

Expand Down Expand Up @@ -360,6 +362,11 @@ MAYBE_AREA_A [ ]?#?
return CALL_DIRECTIVE;
}

^{MAYBE_AREA_A}[ ]*">>"[ ]?"IMP" {
BEGIN IMP_DIRECTIVE_STATE;
return IMP_DIRECTIVE;
}

^{MAYBE_AREA_A}[ ]*">>"[ ]*\n {
/* empty 2002+ style directive */
cb_plex_warning (COBC_WARN_FILLER, newline_count,
Expand Down Expand Up @@ -724,6 +731,7 @@ ELSE_DIRECTIVE_STATE,
ENDIF_DIRECTIVE_STATE,
ALNUM_LITERAL_STATE,
CONTROL_STATEMENT_STATE,
IMP_DIRECTIVE_STATE,
COBOL_WORDS_DIRECTIVE_STATE>{
\n {
BEGIN INITIAL;
Expand Down Expand Up @@ -993,6 +1001,14 @@ ENDIF_DIRECTIVE_STATE>{
}
}

<IMP_DIRECTIVE_STATE>{
"INCLUDE" { return INCLUDE; } /* GnuCOBOL 3.3 extension */
{RAW_SEQ} {
pplval.s = cobc_plex_strdup (yytext);
return TOKEN;
}
}

<IF_DIRECTIVE_STATE>{
"IS" { return IS; }
"NOT" { return NOT; }
Expand Down
28 changes: 28 additions & 0 deletions cobc/ppparse.y
Original file line number Diff line number Diff line change
Expand Up @@ -741,6 +741,9 @@ ppparse_clear_vars (const struct cb_define_struct *p)
%token WITH
%token LOCATION

%token IMP_DIRECTIVE
%token INCLUDE

%token TERMINATOR "end of line"

%token <s> TOKEN "Word or Literal"
Expand Down Expand Up @@ -768,6 +771,7 @@ ppparse_clear_vars (const struct cb_define_struct *p)
%type <l> alnum_equality_list
%type <l> ec_list
%type <s> unquoted_literal
%type <l> imp_include_sources

%type <r> _copy_replacing
%type <r> replacing_list
Expand Down Expand Up @@ -838,6 +842,7 @@ directive:
| TURN_DIRECTIVE turn_directive
| LISTING_DIRECTIVE listing_directive
| LEAP_SECOND_DIRECTIVE leap_second_directive
| IMP_DIRECTIVE imp_directive
| IF_DIRECTIVE
{
current_cmd = PLEX_ACT_IF;
Expand Down Expand Up @@ -1368,6 +1373,29 @@ leap_second_directive:
| OFF
;

imp_directive:
/* GnuCOBOL 3.3 extension */
INCLUDE imp_include_sources
{
struct cb_text_list *p = $2;
while (p != NULL) {
fprintf (ppout, "#INCLUDE %s\n", p->text);
p = p->next;
}
}
;

imp_include_sources:
TOKEN
{
$$ = ppp_list_add (NULL, fix_filename ($1));
}
| imp_include_sources TOKEN
{
$$ = ppp_list_add ($1, fix_filename ($2));
}
;

turn_directive:
ec_list CHECKING on_or_off
{
Expand Down
26 changes: 26 additions & 0 deletions cobc/scanner.l
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,7 @@ static void copy_two_words_in_quotes (char ** const, char ** const);
static void add_synonym (const int, const int);
static void make_synonym (void);
static void clear_constants (void);
static struct cb_text_list *scan_list_add (struct cb_text_list *, const char *);

%}

Expand Down Expand Up @@ -323,6 +324,13 @@ AREA_A "#AREA_A"\n
cobc_areacheck = 0;
}

<*>^[ ]?"#INCLUDE".*/\n {
cb_include_file_list_directive = scan_list_add (
cb_include_file_list_directive,
yytext + 9
);
}

<*>^{AREA_A}[ ]*/"." {
count_lines (yytext + 9); /* skip "\n#area_a\n" */
if (cobc_in_procedure && cobc_areacheck) {
Expand Down Expand Up @@ -2583,6 +2591,22 @@ clear_constants (void)
top_78_ptr = NULL;
}

static struct cb_text_list *
scan_list_add (struct cb_text_list *list, const char *text)
{
struct cb_text_list *p;

p = cobc_malloc (sizeof (struct cb_text_list));
p->text = cobc_strdup (text);
if (!list) {
p->last = p;
return p;
}
list->last->next = p;
list->last = p;
return list;
}

/* Global functions */

void
Expand Down Expand Up @@ -2772,3 +2796,5 @@ cb_find_defined_program_by_id (const char *orig_id)

return NULL;
}


2 changes: 2 additions & 0 deletions doc/gnucobol.texi
Original file line number Diff line number Diff line change
Expand Up @@ -383,6 +383,8 @@ Add a @code{#include} @file{file.h} at the beginning of the generated
C source file. The file name is put into quotes, unless it starts by
@code{<}. Quoted files should be absolute paths, since C files are compiled
in temporary directories.
The directive @code{>>IMP INCLUDE "FILE.h"} or @code{>>IMP INCLUDE <FILE.h>}
can be used as an alternative to this compiler option.
The option also implies @option{-fno-gen-c-decl-static-call}.
This option can be used to check function prototypes when
static calls are used. When this option is used, the source file is
Expand Down
49 changes: 49 additions & 0 deletions tests/testsuite.src/syn_misc.at
Original file line number Diff line number Diff line change
Expand Up @@ -8385,3 +8385,52 @@ prog.cob:18: error: ANY LENGTH items may only be BY REFERENCE formal parameters

AT_CLEANUP

AT_SETUP([IMP INCLUDE directive])
AT_KEYWORDS([IMP INCLUDE])

AT_DATA([prog.cob], [
>>IMP INCLUDE "file.h"
IDENTIFICATION DIVISION.
PROGRAM-ID. prog.
PROCEDURE DIVISION.
GOBACK.
])

AT_CHECK([$COMPILE_ONLY -fformat=fixed prog.cob], [0], [], [])

AT_DATA([prog.cob], [
>>IMP INCLUDE file.h
IDENTIFICATION DIVISION.
PROGRAM-ID. prog.
PROCEDURE DIVISION.
GOBACK.
])

AT_CHECK([$COMPILE_ONLY -fformat=fixed prog.cob], [0], [], [])

AT_DATA([prog.cob], [
>>IMP INCLUDE "file.h"
identification division.
program-id. prog.
procedure division.
goback.
])

AT_CHECK([$COMPILE_ONLY -fformat=free prog.cob], [0], [], [])

AT_CLEANUP

AT_SETUP([IMP INCLUDE directive multiple files])
AT_KEYWORDS([IMP INCLUDE])

AT_DATA([prog.cob], [
>>IMP INCLUDE "file1.h" "file2.h" "file3.h"
identification division.
program-id. prog.
procedure division.
goback.
])

AT_CHECK([$COMPILE_ONLY -fformat=free prog.cob], [0], [], [])

AT_CLEANUP
31 changes: 31 additions & 0 deletions tests/testsuite.src/used_binaries.at
Original file line number Diff line number Diff line change
Expand Up @@ -1139,3 +1139,34 @@ AT_CHECK([$COMPILE_MODULE -Wno-unfinished --copy "f.copy" -fstatic-call prog2.co
])

AT_CLEANUP

AT_SETUP([check include header file with directive])
#AT_KEYWORDS([imp include])

AT_DATA([file.h], [
COB_EXT_IMPORT void f (char *, long);
])
AT_DATA([prog.cob], [
>> IMP INCLUDE "file.h"
IDENTIFICATION DIVISION.
PROGRAM-ID. prog.
PROCEDURE DIVISION.
CALL "f" USING "Hello".
])

AT_CHECK([$COBC -m -I . -fstatic-call prog.cob], [1], [], [ignore])

AT_DATA([prog2.cob], [
>> IMP INCLUDE "file.h"
IDENTIFICATION DIVISION.
PROGRAM-ID. prog.
DATA DIVISION.
WORKING-STORAGE SECTION.
01 long USAGE BINARY-C-LONG.
PROCEDURE DIVISION.
CALL "f" USING "Hello" BY VALUE long RETURNING NOTHING.
])

AT_CHECK([$COBC -m -I . -fstatic-call prog2.cob], [0], [], [])

AT_CLEANUP

0 comments on commit 7b94002

Please sign in to comment.