diff --git a/compiler2/ttcn3/TtcnTemplate.cc b/compiler2/ttcn3/TtcnTemplate.cc
index bb13b36b80132024644db3a28a1b6c2d887d0f98..3aedcec5a0b356a7057ba6f4a29e82d7d45b3134 100644
--- a/compiler2/ttcn3/TtcnTemplate.cc
+++ b/compiler2/ttcn3/TtcnTemplate.cc
@@ -3914,56 +3914,30 @@ end:
         //   ^^^^^^^--- these ------------------------^^^^^
         //   are known at compile time, but the length of the "all from"
         //   is only known at run time.
-        // Collect the indices where there is an "all from".
-        
-        // variables.size() and templates.size() will be equal.
-        // templates[i] contains the variables[i] template.
-        dynamic_array<size_t> variables;
-        dynamic_array<size_t> templates;
+          
         size_t fixed_part = 0;
-        if (has_permutation) {
-          for (size_t i = 0; i < nof_ts; i++) {
+        char* str_set_size = NULL;
+        char* str_preamble = NULL;
+        char* str_body = NULL;
+        string counter = get_temporary_id();
+        
+        if (has_permutation || has_allfrom()) {
+          str_body = mputprintf(str_body, "int %s = %lld;\n", counter.c_str(), index_offset);
+          for (size_t i = 0; i < nof_ts; ++i) {
             Template *t = u.templates->get_t_byIndex(i);
-            if (t->templatetype == PERMUTATION_MATCH) {
-              size_t num_p = t->u.templates->get_nof_ts();
-              // t->u.templates is 2: "hello" and all from ...
-              for (size_t j = 0; j < num_p; ++j) {
-                Template *subt = t->u.templates->get_t_byIndex(j);
-                if (subt->templatetype == ALL_FROM) {
-                  templates.add(i);
-                  variables.add(j);
-                }
-                else fixed_part++;
-              }
-            }
-            else fixed_part++;
-          }
-
-          char* str_preamble = 0;
-          char* str_set_size = mputprintf(0, "%s.set_size(%lu", name,
-            (unsigned long)fixed_part);
-
-          // variable part
-          for (size_t i = 0, v = variables.size(); i < v; ++i) {
-            Template *t = u.templates->get_t_byIndex(templates[i]);
-            if (t->templatetype != PERMUTATION_MATCH) continue; // ?? really nothing to do ??
-            Template *subt = t->u.templates->get_t_byIndex(variables[i]);
-            if (subt->templatetype == ALL_FROM) {
-              Value *refv = subt->u.all_from->u.specific_value;
+            if (t->templatetype == ALL_FROM) {
+              Value *refv = t->u.all_from->u.specific_value;
               // don't call get_Value(), it rips out the value from the template
-
               if (refv->get_valuetype()!=Value::V_REFD) FATAL_ERROR("%s", __FUNCTION__);
               Common::Reference  *ref = refv->get_reference();
               FieldOrArrayRefs   *subrefs = ref->get_subrefs();
               Common::Assignment *ass = ref->get_refd_assignment();
-
               str_set_size = mputstrn(str_set_size, " + ", 3);
-
               Ref_pard* ref_pard = dynamic_cast<Ref_pard*>(ref);
               if (ref_pard) {
-                // in case of parametrised references:
-                //  - temporary parameters need to be declared (stored in str_preamble)
-                //  - the same temporary needs to be used at each call (generate_code_cached call)
+                 // in case of parametrised references:
+                 //  - temporary parameters need to be declared (stored in str_preamble)
+                 //  - the same temporary needs to be used at each call (generate_code_cached call)
                 expression_struct expr;
                 Code::init_expr(&expr);
 
@@ -3971,18 +3945,14 @@ end:
                 str_set_size = mputprintf(str_set_size, "%s", expr.expr);
                 if (expr.preamble)
                   str_preamble = mputstr(str_preamble, expr.preamble);
-
                 Code::free_expr(&expr);
-              }
-              else {
+              } else {
                 str_set_size = mputstr (str_set_size, ass->get_id().get_name().c_str());
                 if (subrefs) {
                   expression_struct expr;
                   Code::init_expr(&expr);
-
                   subrefs->generate_code(&expr, ass);
                   str_set_size = mputprintf(str_set_size, "%s", expr.expr);
-
                   Code::free_expr(&expr);
                 }
               }
@@ -4006,39 +3976,133 @@ end:
               }
 
               str_set_size = mputstr(str_set_size, ".n_elem()");
-            }
-          }
-
-          str = mputstr(str, str_preamble);
-          str = mputstr(str, str_set_size);
+              expression_struct expr;
+              Code::init_expr(&expr);
+              switch (t->u.all_from->templatetype) {
+                case SPECIFIC_VALUE: {
+                  Value *spec = t->u.all_from->u.specific_value;
+                  switch (spec->get_valuetype()) {
+                  case Common::Value::V_REFD: {
+                    ref = spec->get_reference();
+                    ref_pard = dynamic_cast<Ref_pard*>(ref);
+                    if (ref_pard)
+                      ref_pard->generate_code_cached(&expr);
+                    else
+                      ref->generate_code(&expr);
 
-          Free(str_preamble);
-          Free(str_set_size);
+                    ass = ref->get_refd_assignment();
+                    switch(ass->get_asstype()) {
+                    case Common::Assignment::A_CONST:
+                    case Common::Assignment::A_EXT_CONST:
+                    case Common::Assignment::A_MODULEPAR:
+                    case Common::Assignment::A_VAR:
+                    case Common::Assignment::A_PAR_VAL_IN:
+                    case Common::Assignment::A_PAR_VAL_OUT:
+                    case Common::Assignment::A_PAR_VAL_INOUT:
+                    case Common::Assignment::A_FUNCTION_RVAL:
+                    case Common::Assignment::A_EXT_FUNCTION_RVAL:
+                      if (ass->get_Type()->field_is_optional(ref->get_subrefs())) {
+                        expr.expr = mputstrn(expr.expr, "()", 2);
+                      }
+                      break;
+                    default:
+                      break;
+                    }
 
-          str = mputstrn(str, ");\n", 3); // finally done set_size
-          
-          size_t index = 0;
-          string skipper, hopper;
-          for (size_t i = 0; i < nof_ts; i++) {
-            Template *t = u.templates->get_t_byIndex(i);
-            switch (t->templatetype) {
-            case ALL_FROM: {
-              break; }
-            case PERMUTATION_MATCH: {
+                    break; }
+                  default:
+                    FATAL_ERROR("vtype %d", spec->get_valuetype());
+                    break;
+                  }
+                  break; }
+                default: {
+                  FATAL_ERROR("ttype %d", t->u.all_from->templatetype);
+                  break; }
+              }
+              str_body = mputprintf(str_body,
+                "for (int i_i = 0, i_lim = %s.n_elem(); i_i < i_lim; ++i_i) {\n",
+                expr.expr);
+              str_body = t->generate_code_init_seof_element(str_body, name,
+                (counter + " + i_i").c_str(),
+                oftype_name_str);
+              str_body = mputstrn(str_body, "}\n", 2);
+              str_body = mputprintf(str_body, "%s += %s.n_elem();\n", counter.c_str(), expr.expr);
+              Code::free_expr(&expr);
+              t->set_code_generated();
+            } else if (t->templatetype == PERMUTATION_MATCH) {
+              string permutation_start = get_temporary_id();
+              str_body = mputprintf(str_body, "int %s = %s;\n",
+                permutation_start.c_str(), counter.c_str());
               size_t nof_perm_ts = t->u.templates->get_nof_ts();
               for (size_t j = 0; j < nof_perm_ts; j++) {
-                Int ix(index_offset + index + j);
-                Template *permut_elem = t->u.templates->get_t_byIndex(j);
-                if (permut_elem->templatetype == ALL_FROM) {
+                Template *subt = t->u.templates->get_t_byIndex(j);
+                if (subt->templatetype == ALL_FROM) {
+                  Value *refv = subt->u.all_from->u.specific_value;
+                  // don't call get_Value(), it rips out the value from the template
+                  if (refv->get_valuetype()!=Value::V_REFD) FATAL_ERROR("%s", __FUNCTION__);
+                  Common::Reference  *ref = refv->get_reference();
+                  FieldOrArrayRefs   *subrefs = ref->get_subrefs();
+                  Common::Assignment *ass = ref->get_refd_assignment();
+                  str_set_size = mputstrn(str_set_size, " + ", 3);
+                  Ref_pard* ref_pard = dynamic_cast<Ref_pard*>(ref);
+                  if (ref_pard) {
+                    // in case of parametrised references:
+                    //  - temporary parameters need to be declared (stored in str_preamble)
+                    //  - the same temporary needs to be used at each call (generate_code_cached call)
+                    expression_struct expr;
+                    Code::init_expr(&expr);
+
+                    ref_pard->generate_code_cached(&expr);
+                    str_set_size = mputprintf(str_set_size, "%s", expr.expr);
+                    if (expr.preamble)
+                      str_preamble = mputstr(str_preamble, expr.preamble);
+                    Code::free_expr(&expr);
+                  }
+                  else {
+                    str_set_size = mputstr (str_set_size, ass->get_id().get_name().c_str());
+                    if (subrefs) {
+                      expression_struct expr;
+                      Code::init_expr(&expr);
+                      subrefs->generate_code(&expr, ass);
+                      str_set_size = mputprintf(str_set_size, "%s", expr.expr);
+                      Code::free_expr(&expr);
+                    }
+                  }
+
+                  switch(ass->get_asstype()) {
+                  case Common::Assignment::A_CONST:
+                  case Common::Assignment::A_EXT_CONST:
+                  case Common::Assignment::A_MODULEPAR:
+                  case Common::Assignment::A_VAR:
+                  case Common::Assignment::A_PAR_VAL_IN:
+                  case Common::Assignment::A_PAR_VAL_OUT:
+                  case Common::Assignment::A_PAR_VAL_INOUT:
+                  case Common::Assignment::A_FUNCTION_RVAL:
+                  case Common::Assignment::A_EXT_FUNCTION_RVAL:
+                    if (ass->get_Type()->field_is_optional(subrefs)) {
+                      str_set_size = mputstrn(str_set_size, "()", 2);
+                    }
+                    break;
+                  default:
+                    break;
+                  }
+                  
+                  str_set_size = mputstr(str_set_size, ".n_elem()");
+                } else {
+                  fixed_part++;
+                  str_body = subt->generate_code_init_seof_element(str_body, name,
+                    counter.c_str(), oftype_name_str);
+                }
+                
+                if (subt->templatetype == ALL_FROM) {
                   expression_struct expr;
                   Code::init_expr(&expr);
-                  switch (permut_elem->u.all_from->templatetype) {
+                  switch (subt->u.all_from->templatetype) {
                   case SPECIFIC_VALUE: {
-                    Value *spec = permut_elem->u.all_from->u.specific_value;
+                    Value *spec = subt->u.all_from->u.specific_value;
                     switch (spec->get_valuetype()) {
                     case Common::Value::V_REFD: {
                       Common::Reference  *ref = spec->get_reference();
-                      
                       Ref_pard* ref_pard = dynamic_cast<Ref_pard*>(ref);
                       if (ref_pard)
                         ref_pard->generate_code_cached(&expr);
@@ -4063,221 +4127,63 @@ end:
                       default:
                         break;
                       }
-                      
+
                       break; }
                     default:
                       FATAL_ERROR("vtype %d", spec->get_valuetype());
                       break;
                     }
                     break; }
-
-
                   default:
-                    FATAL_ERROR("ttype %d", permut_elem->u.all_from->templatetype);
+                    FATAL_ERROR("ttype %d", subt->u.all_from->templatetype);
                     break;
                   }
-                  str = mputprintf(str,
+                  str_body = mputprintf(str_body,
                     "for (int i_i = 0, i_lim = %s.n_elem(); i_i < i_lim; ++i_i) {\n",
                     expr.expr);
 
-                  str = permut_elem->generate_code_init_seof_element(str, name,
-                    (Int2string(ix) + skipper + " + i_i").c_str(),
+                  str_body = subt->generate_code_init_seof_element(str_body, name,
+                    (counter + " + i_i").c_str(),
                     oftype_name_str);
 
-                  str = mputstrn(str, "}\n", 2);
-                  skipper += "-1+";
-                  skipper += expr.expr;
-                  skipper += ".n_elem() /* 3005 */ ";
+                  str_body = mputstrn(str_body, "}\n", 2);
+                  str_body = mputprintf(str_body, "%s += %s.n_elem();\n", counter.c_str(), expr.expr);
                   Code::free_expr(&expr);
                 }
                 else {
-                  str = permut_elem->generate_code_init_seof_element(str, name,
-                    (Int2string(ix) + skipper).c_str(), oftype_name_str);
+                  str_body = subt->generate_code_init_seof_element(str_body, name,
+                    counter.c_str(), oftype_name_str);
+                  str_body = mputprintf(str_body, "%s++;\n", counter.c_str());
                 }
+                  
               }
               // do not consider index_offset in case of permutation indicators
-              str = mputprintf(str, "%s.add_permutation(%lu%s, %lu%s);\n", name,
-                (unsigned long)index,                     hopper.c_str(),
-                (unsigned long)(index + nof_perm_ts - 1), skipper.c_str());
-              hopper = skipper;
+              str_body = mputprintf(str_body, "%s.add_permutation(%s-%lld, %s-%lld-1);\n", name,
+                permutation_start.c_str(), index_offset, counter.c_str(), index_offset);
               t->set_code_generated();
-              index += nof_perm_ts;
-              break; }
-
-            default:
-              str = t->generate_code_init_seof_element(str, name,
-                (Int2string(index_offset + index) + skipper).c_str(), oftype_name_str);
-              // no break
-            case TEMPLATE_NOTUSED:
-              index++;
-              break;
-            }
-          }
-
-          break;
-
-        }
-
-
-        if (!has_permutation && has_allfrom()) {
-          for (size_t i = 0; i < nof_ts; i++) {
-            Template *t = u.templates->get_t_byIndex(i);
-            if (t->templatetype == ALL_FROM) {
-              variables.add(i);
-            }
-            else {
+            } else {
               fixed_part++;
-            }
-          }
-          char* str_preamble = 0;
-          char* str_set_size = mputprintf(0, "%s.set_size(%lu", name,
-            (unsigned long)fixed_part);
-
-          // variable part
-          for (size_t i = 0, v = variables.size(); i < v; ++i) {
-            Template *t = u.templates->get_t_byIndex(variables[i]);
-            if (t->templatetype == ALL_FROM) {
-              Value *refv = t->u.all_from->u.specific_value;
-              // don't call get_Value(), it rips out the value from the template
-              if (refv->get_valuetype()!=Value::V_REFD) FATAL_ERROR("%s", __FUNCTION__);
-              Common::Reference  *ref = refv->get_reference();
-              FieldOrArrayRefs   *subrefs = ref->get_subrefs();
-              Common::Assignment *ass = ref->get_refd_assignment();
-              str_set_size = mputstrn(str_set_size, " + ", 3);
-              Ref_pard* ref_pard = dynamic_cast<Ref_pard*>(ref);
-              if (ref_pard) {
-                 // in case of parametrised references:
-                 //  - temporary parameters need to be declared (stored in str_preamble)
-                 //  - the same temporary needs to be used at each call (generate_code_cached call)
-                expression_struct expr;
-                Code::init_expr(&expr);
-
-                ref_pard->generate_code_cached(&expr);
-                str_set_size = mputprintf(str_set_size, "%s", expr.expr);
-                if (expr.preamble)
-                  str_preamble = mputstr(str_preamble, expr.preamble);
-                Code::free_expr(&expr);
-              }
-              else {
-                str_set_size = mputstr (str_set_size, ass->get_id().get_name().c_str());
-                if (subrefs) {
-                  expression_struct expr;
-                  Code::init_expr(&expr);
-                  subrefs->generate_code(&expr, ass);
-                  str_set_size = mputprintf(str_set_size, "%s", expr.expr);
-                  Code::free_expr(&expr);
-                }
-              }
-
-              switch(ass->get_asstype()) {
-              case Common::Assignment::A_CONST:
-              case Common::Assignment::A_EXT_CONST:
-              case Common::Assignment::A_MODULEPAR:
-              case Common::Assignment::A_VAR:
-              case Common::Assignment::A_PAR_VAL_IN:
-              case Common::Assignment::A_PAR_VAL_OUT:
-              case Common::Assignment::A_PAR_VAL_INOUT:
-              case Common::Assignment::A_FUNCTION_RVAL:
-              case Common::Assignment::A_EXT_FUNCTION_RVAL:
-                if (ass->get_Type()->field_is_optional(subrefs)) {
-                  str_set_size = mputstrn(str_set_size, "()", 2);
-                }
-                break;
-              default:
-                break;
-              }
-
-              str_set_size = mputstr(str_set_size, ".n_elem()");
+              str_body = t->generate_code_init_seof_element(str_body, name,
+                      counter.c_str(), oftype_name_str);
+              str_body = mputprintf(str_body, "%s++;\n", counter.c_str());
             }
           }
           str = mputstr(str, str_preamble);
-          str = mputstr(str, str_set_size);
+          str = mputprintf(str, "%s.set_size(%lu", name, fixed_part);
+          if (str_set_size != NULL) {
+            str = mputstr(str, str_set_size);
+          }
+          str = mputstr(str, ");\n");
+          str = mputstr(str, str_body);
           Free(str_preamble);
           Free(str_set_size);
-          str = mputstrn(str, ");\n", 3); // finally done set_size
-
-          size_t index = 0;
-          string skipper;
-          for (size_t i = 0; i < nof_ts; i++) {
-            Template *t = u.templates->get_t_byIndex(i);
-            Int ix(index_offset + i);
-            switch (t->templatetype) {
-            case ALL_FROM: {
-              expression_struct expr;
-              Code::init_expr(&expr);
-              switch (t->u.all_from->templatetype) {
-                case SPECIFIC_VALUE: {
-                  Value *spec = t->u.all_from->u.specific_value;
-                  switch (spec->get_valuetype()) {
-                  case Common::Value::V_REFD: {
-                    Common::Reference  *ref = spec->get_reference();
-                    Ref_pard* ref_pard = dynamic_cast<Ref_pard*>(ref);
-                    if (ref_pard)
-                      ref_pard->generate_code_cached(&expr);
-                    else
-                      ref->generate_code(&expr);
-
-                    Common::Assignment* ass = ref->get_refd_assignment();
-                    switch(ass->get_asstype()) {
-                    case Common::Assignment::A_CONST:
-                    case Common::Assignment::A_EXT_CONST:
-                    case Common::Assignment::A_MODULEPAR:
-                    case Common::Assignment::A_VAR:
-                    case Common::Assignment::A_PAR_VAL_IN:
-                    case Common::Assignment::A_PAR_VAL_OUT:
-                    case Common::Assignment::A_PAR_VAL_INOUT:
-                    case Common::Assignment::A_FUNCTION_RVAL:
-                    case Common::Assignment::A_EXT_FUNCTION_RVAL:
-                      if (ass->get_Type()->field_is_optional(ref->get_subrefs())) {
-                        expr.expr = mputstrn(expr.expr, "()", 2);
-                      }
-                      break;
-                    default:
-                      break;
-                    }
-
-                    break; }
-                  default:
-                    FATAL_ERROR("vtype %d", spec->get_valuetype());
-                    break;
-                  }
-                  break; }
-                default: {
-                  FATAL_ERROR("ttype %d", t->u.all_from->templatetype);
-                  break; }
-              }
-              str = mputprintf(str,
-                "for (int i_i = 0, i_lim = %s.n_elem(); i_i < i_lim; ++i_i) {\n",
-                expr.expr);
-              str = t->generate_code_init_seof_element(str, name,
-                (Int2string(ix) + skipper + " + i_i").c_str(),
-                oftype_name_str);
-              str = mputstrn(str, "}\n", 2);
-              skipper += "-1+";
-              skipper += expr.expr;
-              skipper += ".n_elem() ";
-              Code::free_expr(&expr);
-              t->set_code_generated();
-              ++index;
-              break; }
-            default: {
-               str = t->generate_code_init_seof_element(str, name,
-                 (Int2string(index_offset + index) + skipper).c_str(), oftype_name_str);
-               // no break
-            case TEMPLATE_NOTUSED:
-               ++index;
-               break; }
-            }
-          }
-          break;
+          Free(str_body);
+          return str;
         }
-
-        // else carry on
       }
 compile_time:
       // setting the size first
-      if (!has_allfrom())
-        str = mputprintf(str, "%s.set_size(%lu);\n", name, (unsigned long) get_nof_listitems());
+      str = mputprintf(str, "%s.set_size(%lu);\n", name, (unsigned long) get_nof_listitems());
       // determining the index offset based on the governor
 
       size_t index = 0;
diff --git a/regression_test/all_from/all_from_permutation.ttcn b/regression_test/all_from/all_from_permutation.ttcn
index e4688229e3c86aa780f2780eec1b4cde2b520a03..b627857d41c57596d3b8755159a8056836668ce8 100644
--- a/regression_test/all_from/all_from_permutation.ttcn
+++ b/regression_test/all_from/all_from_permutation.ttcn
@@ -1803,5 +1803,16 @@ testcase tc_perm_varTemplate_two_var_unfoldable() runs on A
   f_checkRoITemplateEquivalence(tl_len_res, tl_len_res_eq);
 }
 
+testcase tc_perm_varTemplate_array_unfoldable() runs on A
+{
+  var template RoI tl_unfoldable4 := { 6 };
+  var template IntArray tl_arr_res := { 1, permutation ( 2, all from tl_unfoldable4, 3), 4, 5 };
+  var template IntArray tl_arr_res_eq := { 1, permutation ( 2, 6, 3 ), 4, 5 };
+  if (log2str(tl_arr_res) != log2str(tl_arr_res_eq)) {
+    setverdict(fail, match(log2str(tl_arr_res), log2str(tl_arr_res_eq)));
+  }
+  setverdict(pass);
+}
+
 
 }  // end of module
diff --git a/regression_test/all_from/types.ttcn b/regression_test/all_from/types.ttcn
index 83d90eaba43e2bd97b743ba113dc4c3f9a343fa7..90e5ed67af7fdccd31c6b78d9f4d18b54c980348 100644
--- a/regression_test/all_from/types.ttcn
+++ b/regression_test/all_from/types.ttcn
@@ -9,6 +9,7 @@
  *   Balasko, Jeno
  *   Baranyi, Botond
  *   Raduly, Csaba
+ *   Szabo, Bence Janos
  *
  ******************************************************************************/
 module types {
@@ -57,6 +58,8 @@ type union MyUnion {
 type record of MyRecord RoMyRec;
 type record of MyUnion RoMyUnion;
 
+type integer IntArray[3..8];
+
 //==== Function Reference ====
 //this is just a dummy type to test all from for function references
 type function F_int2int(in integer pl_i) return integer;