aboutsummaryrefslogtreecommitdiff
path: root/gcc/cobol/util.cc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/cobol/util.cc')
-rw-r--r--gcc/cobol/util.cc214
1 files changed, 192 insertions, 22 deletions
diff --git a/gcc/cobol/util.cc b/gcc/cobol/util.cc
index 23f605d..c85b4cb 100644
--- a/gcc/cobol/util.cc
+++ b/gcc/cobol/util.cc
@@ -34,29 +34,32 @@
* header files.
*/
-#include "cobol-system.h"
-#include "coretypes.h"
-#include "tree.h"
+#include <cobol-system.h>
+#include <coretypes.h>
+#include <tree.h>
#undef yy_flex_debug
#include <langinfo.h>
-#include "coretypes.h"
-#include "version.h"
-#include "demangle.h"
-#include "intl.h"
-#include "backtrace.h"
-#include "diagnostic.h"
-#include "diagnostic-color.h"
-#include "diagnostic-url.h"
-#include "diagnostic-metadata.h"
-#include "diagnostic-path.h"
-#include "edit-context.h"
-#include "selftest.h"
-#include "selftest-diagnostic.h"
-#include "opts.h"
+#include <coretypes.h>
+#include <version.h>
+#include <demangle.h>
+#include <intl.h>
+#include <backtrace.h>
+#include <diagnostic.h>
+#include <diagnostic-color.h>
+#include <diagnostic-url.h>
+#include <diagnostic-metadata.h>
+#include <diagnostic-path.h>
+#include <edit-context.h>
+#include <selftest.h>
+#include <selftest-diagnostic.h>
+#include <opts.h>
+
#include "util.h"
+
#include "cbldiag.h"
+#include "cdfval.h"
#include "lexio.h"
#include "../../libgcobol/ec.h"
@@ -111,6 +114,159 @@ gb4( size_t input ) {
return input;
}
+/*
+ * Most CDF Directives -- those that have state -- can be pushed and popped.
+ * This class maintains stacks of them, with each stack having a "default
+ * value" that may be updated, without push/pop, via a CDF directive or
+ * command-line option. A push to a stack pushes the default value onto it; a
+ * pop copies the top of the stack to the default value.
+ *
+ * Supported:
+ * CALL-CONVENTION
+ * COBOL-WORDS
+ * DEFINE
+ * DISPLAY
+ * IF
+ * POP
+ * PUSH
+ * SOURCE FORMAT
+ * TURN
+ * not supported
+ * EVALUATE
+ * FLAG-02
+ * FLAG-14
+ * LEAP-SECOND
+ * LISTING
+ * PAGE
+ * PROPAGATE
+ * REF-MOD-ZERO-LENGTH
+ *
+ * >>PUSH ALL calls the class's push() method.
+ * >>POP ALL calls the class's pop() method.
+ */
+class cdf_directives_t
+{
+ template <typename T>
+ class cdf_stack_t : private std::stack<T> {
+ T default_value;
+ const T& top() const { return std::stack<T>::top(); }
+ bool empty() const { return std::stack<T>::empty(); }
+ public:
+ void value( const T& value ) {
+ T& output( empty()? default_value : std::stack<T>::top() );
+ output = value;
+ dbgmsg("cdf_directives_t::%s: %s", __func__, str(output).c_str());
+ }
+ T& value() {
+ return empty()? default_value : std::stack<T>::top();
+ }
+ void push() {
+ std::stack<T>::push(value());
+ dbgmsg("cdf_directives_t::%s: %s", __func__, str(top()).c_str());
+ }
+ void pop() {
+ if( empty() ) {
+ error_msg(YYLTYPE(), "CDF stack empty");
+ return;
+ }
+ default_value = top();
+ std::stack<T>::pop();
+ dbgmsg("cdf_directives_t::%s: %s", __func__, str(default_value).c_str());
+ }
+ protected:
+ static std::string str(cbl_call_convention_t arg) {
+ char output[2] = { static_cast<char>(arg) };
+ return std::string("call-convention ") + output;
+ }
+ static std::string str(current_tokens_t) {
+ return "<cobol-words>";
+ }
+ static std::string str(cdf_values_t) {
+ return "<dictionary>";
+ }
+ static std::string str(source_format_t arg) {
+ return arg.description();
+ }
+ static std::string str(cbl_enabled_exceptions_t) {
+ return "<enabled_exceptions>";
+ }
+
+ };
+
+ public:
+ cdf_stack_t<cbl_call_convention_t> call_convention;
+ cdf_stack_t<current_tokens_t> cobol_words;
+ cdf_stack_t<cdf_values_t> dictionary; // DEFINE
+ cdf_stack_t<source_format_t> source_format;
+ cdf_stack_t<cbl_enabled_exceptions_t> enabled_exceptions;
+
+ cdf_directives_t() {
+ call_convention.value() = cbl_call_cobol_e;
+ }
+
+ void push() {
+ call_convention.push();
+ cobol_words.push();
+ dictionary.push();
+ source_format.push();
+ enabled_exceptions.push();
+ }
+ void pop() {
+ call_convention.pop();
+ cobol_words.pop();
+ dictionary.pop();
+ source_format.pop();
+ enabled_exceptions.pop();
+ }
+};
+static cdf_directives_t cdf_directives;
+
+void
+current_call_convention( cbl_call_convention_t convention) {
+ cdf_directives.call_convention.value(convention);
+}
+cbl_call_convention_t
+current_call_convention() {
+ return cdf_directives.call_convention.value();
+}
+
+current_tokens_t&
+cdf_current_tokens() {
+ return cdf_directives.cobol_words.value();
+}
+
+cdf_values_t&
+cdf_dictionary() {
+ return cdf_directives.dictionary.value();
+}
+
+void
+cobol_set_indicator_column( int column ) {
+ cdf_directives.source_format.value().indicator_column_set(column);
+}
+source_format_t& cdf_source_format() {
+ return cdf_directives.source_format.value();
+}
+
+cbl_enabled_exceptions_t&
+cdf_enabled_exceptions() {
+ return cdf_directives.enabled_exceptions.value();
+}
+
+void cdf_push() { cdf_directives.push(); }
+void cdf_push_call_convention() { cdf_directives.call_convention.push(); }
+void cdf_push_current_tokens() { cdf_directives.cobol_words.push(); }
+void cdf_push_dictionary() { cdf_directives.dictionary.push(); }
+void cdf_push_enabled_exceptions() { cdf_directives.enabled_exceptions.push(); }
+void cdf_push_source_format() { cdf_directives.source_format.push(); }
+
+void cdf_pop() { cdf_directives.pop(); }
+void cdf_pop_call_convention() { cdf_directives.call_convention.pop(); }
+void cdf_pop_current_tokens() { cdf_directives.cobol_words.pop(); }
+void cdf_pop_dictionary() { cdf_directives.dictionary.pop(); }
+void cdf_pop_enabled_exceptions() { cdf_directives.enabled_exceptions.pop(); }
+void cdf_pop_source_format() { cdf_directives.source_format.pop(); }
+
const char *
symbol_type_str( enum symbol_type_t type )
{
@@ -1927,7 +2083,8 @@ location_t location_from_lineno() { return token_location; }
template <typename LOC>
static void
gcc_location_set_impl( const LOC& loc ) {
- token_location = linemap_line_start( line_table, loc.last_line, 80 );
+ // Set the position to the first line & column in the location.
+ token_location = linemap_line_start( line_table, loc.first_line, 80 );
token_location = linemap_position_for_column( line_table, loc.first_column);
location_dump(__func__, __LINE__, "parser", loc);
}
@@ -1972,6 +2129,11 @@ verify_format( const char gmsgid[] ) {
static const diagnostic_option_id option_zero;
size_t parse_error_inc();
+void gcc_location_dump() {
+ linemap_dump_location( line_table, token_location, stderr );
+}
+
+
void ydferror( const char gmsgid[], ... ) ATTRIBUTE_GCOBOL_DIAG(1, 2);
void
@@ -2008,10 +2170,7 @@ class temp_loc_t {
gcc_location_set(loc);
}
explicit temp_loc_t( const YDFLTYPE& loc) : orig(token_location) {
- YYLTYPE lloc = {
- loc.first_line, loc.first_column,
- loc.last_line, loc.last_column };
- gcc_location_set(lloc);
+ gcc_location_set(loc);
}
~temp_loc_t() {
if( orig != token_location ) {
@@ -2057,6 +2216,17 @@ void error_msg( const YDFLTYPE& loc, const char gmsgid[], ... ) {
ERROR_MSG_BODY
}
+void error_msg_direct( const char gmsgid[], ... ) {
+ verify_format(gmsgid);
+ parse_error_inc();
+ auto_diagnostic_group d;
+ va_list ap;
+ va_start (ap, gmsgid);
+ auto ret = emit_diagnostic_valist( DK_ERROR, token_location,
+ option_zero, gmsgid, &ap );
+ va_end (ap);
+}
+
void
yyerror( const char gmsgid[], ... ) {
temp_loc_t looker;