absyntax_utils/array_dimension_iterator.cc
author Mario de Sousa <msousa@fe.up.pt>
Wed, 13 Feb 2019 14:40:26 +0000
changeset 1087 d9e47e018320
parent 1041 56ebe2a31b5b
permissions -rw-r--r--
add default NULL value to references (as suggested by anonymous in issue 62)
(Not really needed, but it is good practise...)
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     1
/*
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     2
 *  matiec - a compiler for the programming languages defined in IEC 61131-3
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     3
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     4
 *  Copyright (C) 2003-2011  Mario de Sousa (msousa@fe.up.pt)
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     5
 *  Copyright (C) 2007-2011  Laurent Bessard and Edouard Tisserant
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     6
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     7
 *  This program is free software: you can redistribute it and/or modify
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     8
 *  it under the terms of the GNU General Public License as published by
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
     9
 *  the Free Software Foundation, either version 3 of the License, or
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    10
 *  (at your option) any later version.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    11
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    12
 *  This program is distributed in the hope that it will be useful,
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    13
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    14
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    15
 *  GNU General Public License for more details.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    16
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    17
 *  You should have received a copy of the GNU General Public License
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    18
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    19
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    20
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    21
 * This code is made available on the understanding that it will not be
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    22
 * used in safety-critical situations without a full and competent review.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    23
 */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    24
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    25
/*
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    26
 * An IEC 61131-3 compiler.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    27
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    28
 * Based on the
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    29
 * FINAL DRAFT - IEC 61131-3, 2nd Ed. (2001-12-10)
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    30
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    31
 */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    32
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    33
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    34
/*
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    35
 * Array dimension iterator.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    36
 * Iterate through the dimensions of array specification.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    37
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    38
 * This is part of the 4th stage that generates
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    39
 * a c++ source program equivalent to the IL and ST
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    40
 * code.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    41
 */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    42
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    43
/* Given a array_specification_c, iterate through
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    44
 * each subrange, returning the symbol of each subrange
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    45
 * ...array_dimension_iterator_c
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    46
 */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    47
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    48
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    49
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    50
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    51
#include "array_dimension_iterator.hh"
596
4efb11e44065 Add ERROR_MSG macro && move extract_XXX() functions to constant_folding.cc
Mario de Sousa <msousa@fe.up.pt>
parents: 562
diff changeset
    52
#include "../main.hh" // required for ERROR() and ERROR_MSG() macros.
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    53
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    54
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    55
//#define DEBUG
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    56
#ifdef DEBUG
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    57
#define TRACE(classname) printf("\n____%s____\n",classname);
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    58
#else
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    59
#define TRACE(classname)
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    60
#endif
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    61
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    62
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    63
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    64
void* array_dimension_iterator_c::iterate_list(list_c *list) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    65
  void *res;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    66
  for (int i = 0; i < list->n; i++) {
1041
56ebe2a31b5b Access elements[] in list_c through a new get_element() method.
Mario de Sousa <msousa@fe.up.pt>
parents: 840
diff changeset
    67
    res = list->get_element(i)->accept(*this);
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    68
    if (res != NULL)
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    69
        return res;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    70
  }
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    71
  return NULL;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    72
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    73
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    74
/* start off at the first case element once again... */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    75
void array_dimension_iterator_c::reset(void) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    76
  current_array_dimension = NULL;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    77
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    78
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    79
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    80
/* initialize the iterator object.
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    81
 * We must be given a reference to a array_specification_c that will be analyzed...
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    82
 */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    83
array_dimension_iterator_c::array_dimension_iterator_c(symbol_c *symbol) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    84
  /* do some consistency check... */
830
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    85
  /* NOTE: We comment out the consistency check so the compiler does not bork when it encounters buggy source code.
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    86
   *        e.g. Code that handles a non array variable as an array!
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    87
   *               VAR  v1, v2: int; END_VAR
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    88
   *               v1 := v2[33, 45];
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    89
   *       The above error will be caught by the datatype checking algorithms!
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    90
   */
840
60cea9fea6e6 Allow array_dimension_iterator to accept an array_spec_init_c.
mjsousa
parents: 830
diff changeset
    91
  array_spec_init_c    * array_spec_init = dynamic_cast<array_spec_init_c    *>(symbol); 
60cea9fea6e6 Allow array_dimension_iterator to accept an array_spec_init_c.
mjsousa
parents: 830
diff changeset
    92
  if (NULL != array_spec_init)    symbol = array_spec_init->array_specification;
60cea9fea6e6 Allow array_dimension_iterator to accept an array_spec_init_c.
mjsousa
parents: 830
diff changeset
    93
  array_specification_c* array_spec      = dynamic_cast<array_specification_c*>(symbol);
830
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    94
  // if (NULL == array_spec) ERROR;
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    95
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    96
  /* OK. Now initialize this object... */
830
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
    97
  this->array_specification = array_spec; // Set to array_spec and not symbol => will be NULL if not an array_specification_c* !!
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    98
  reset();
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
    99
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   100
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   101
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   102
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   103
/* Skip to the next subrange. After object creation,
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   104
 * the object references on subrange _before_ the first, so
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   105
 * this function must be called once to get the object to
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   106
 * reference the first subrange...
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   107
 *
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   108
 * Returns the subrange symbol!
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   109
 */
562
044238931066 Change return data type of array_dimension_iterator_c.next()
Mario de Sousa <msousa@fe.up.pt>
parents: 377
diff changeset
   110
subrange_c *array_dimension_iterator_c::next(void) {
830
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
   111
  if (NULL == array_specification) return NULL; /* The source code probably has a bug which will be caught somewhere else! */
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   112
  void *res = array_specification->accept(*this);
830
6f45ec6ed011 Handle buggy source code gracefully (do not bork when non-array variable is used as an array. e.g: int_var[42]:= 33)
mjsousa
parents: 596
diff changeset
   113
  if (NULL == res)                 return NULL;
377
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   114
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   115
  return current_array_dimension;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   116
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   117
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   118
/********************************/
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   119
/* B 1.3.3 - Derived data types */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   120
/********************************/
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   121
/*  signed_integer DOTDOT signed_integer */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   122
void *array_dimension_iterator_c::visit(subrange_c *symbol) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   123
  if (current_array_dimension == symbol) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   124
	current_array_dimension = NULL;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   125
  }
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   126
  else if (current_array_dimension == NULL) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   127
	current_array_dimension = symbol;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   128
	return symbol;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   129
  }
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   130
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   131
  /* Not found! */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   132
  return NULL;
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   133
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   134
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   135
/* ARRAY '[' array_subrange_list ']' OF non_generic_type_name */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   136
void *array_dimension_iterator_c::visit(array_specification_c *symbol) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   137
  return symbol->array_subrange_list->accept(*this);
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   138
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   139
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   140
/* array_subrange_list ',' subrange */
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   141
void *array_dimension_iterator_c::visit(array_subrange_list_c *symbol) {
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   142
  return iterate_list(symbol);
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   143
}
60b012b7793f Adding support for compiling direct array specification inside variable declaration
laurent
parents:
diff changeset
   144