Commit 04ad9084 authored by balaskoa's avatar balaskoa
Browse files

Merge github.com:eclipse/titan.core

parents 2ab24328 515dcdb2
......@@ -104,8 +104,8 @@ Compressed update site and SHA512 checksum:
* https://github.com/eclipse/titan.ProtocolModules.UDP
* https://github.com/eclipse/titan.ProtocolModules.WebSocket
* https://github.com/eclipse/titan.ProtocolModules.XMPP
* http://git.eclipse.org/c/titan/titan.ProtocolModules.CoAP.git
* http://git.eclipse.org/c/titan/titan.ProtocolModules.MQTT.git
* http://git.eclipse.org/gitroot/titan/titan.ProtocolModules.CoAP
* http://git.eclipse.org/gitroot/titan/titan.ProtocolModules.MQTT
## Libraries:
......@@ -114,4 +114,4 @@ Compressed update site and SHA512 checksum:
## Miscellaneous projects:
* https://github.com/eclipse/titan.misc
(VSBOT, SIP_ETSI,DIAMETER_Rx_ETSI, CoAP and MQTT protocol modules for IOT, more to come...)
(VSBOT, SIP_ETSI,DIAMETER_Rx_ETSI, CoAP Conformance test cases, CoAP and MQTT protocol modules for IOT-moved to Eclipse git, more to come...)
......@@ -2254,6 +2254,8 @@ void Type::generate_code_done(output_struct *target)
"if (!component_reference.is_bound()) "
"TTCN_error(\"Performing a done operation on an unbound component "
"reference.\");\n"
"if (value_template.get_selection() == ANY_OR_OMIT) "
"TTCN_error(\"Done operation using '*' as matching template\");\n"
"Text_Buf *text_buf;\n"
"alt_status ret_val = TTCN_Runtime::component_done("
"(component)component_reference, \"%s\", text_buf);\n"
......
......@@ -78,6 +78,7 @@ using namespace Common;
const char *output_dir = NULL;
const char *tcov_file_name = NULL;
const char *profiler_file_name = NULL;
const char *file_list_file_name = NULL;
tcov_file_list *tcov_files = NULL;
expstring_t effective_module_lines = NULL;
expstring_t effective_module_functions = NULL;
......@@ -384,7 +385,7 @@ static boolean is_valid_asn1_filename(const char* file_name)
static void usage()
{
fprintf(stderr, "\n"
"usage: %s [-abcdEfgijlLMnOpqrRsStuwxXyY] [-K file] [-z file] [-V verb_level]\n"
"usage: %s [-abcdEfgijlLMnOpqrRsStuwxXyY] [-J file] [-K file] [-z file] [-V verb_level]\n"
" [-o dir] [-U none|type|'number'] [-P modulename.top_level_pdu_name] [-Q number] ...\n"
" [-T] module.ttcn [-A] module.asn ...\n"
" or %s -v\n"
......@@ -401,6 +402,7 @@ static void usage()
" -g: emulate GCC error/warning message format\n"
" -i: use only line numbers in error/warning messages\n"
" -j: disable JSON encoder/decoder functions\n"
" -J file: read input files from file\n"
" -K file: enable selective code coverage\n"
" -l: include source line info in C++ code\n"
" -L: add source line info for logging\n"
......@@ -494,6 +496,8 @@ int main(int argc, char *argv[])
size_t n_modules = 0;
module_struct *module_list = NULL;
char* json_schema_name = NULL;
size_t n_files_from_file = 0;
char ** files_from_file = NULL;
if (0 == strcmp(argv[1], "--ttcn2json")) {
ttcn2json = true;
......@@ -575,7 +579,7 @@ int main(int argc, char *argv[])
if (!ttcn2json) {
for ( ; ; ) {
int c = getopt(argc, argv, "aA:bBcC:dEfFgijK:lLMno:pP:qQ:rRsStT:uU:vV:wxXyYz:0-");
int c = getopt(argc, argv, "aA:bBcC:dEfFgijJ:K:lLMno:pP:qQ:rRsStT:uU:vV:wxXyYz:0-");
if (c == -1) break;
switch (c) {
case 'a':
......@@ -645,6 +649,9 @@ int main(int argc, char *argv[])
SET_FLAG(i);
output_only_linenum = TRUE;
break;
case 'J':
file_list_file_name = optarg;
break;
case 'K':
SET_FLAG(K);
tcov_file_name = optarg;
......@@ -832,7 +839,70 @@ int main(int argc, char *argv[])
output_dir);
errflag = true;
}
if (optind == argc && n_modules == 0) {
if (file_list_file_name != NULL) {
FILE *fp = fopen(file_list_file_name, "r");
if (fp != NULL) {
char buff[1024];
// We store the -A and -T here too
while (fscanf(fp, "%s", buff) == 1) {
n_files_from_file++;
files_from_file = (char**)
Realloc(files_from_file, n_files_from_file * sizeof(*files_from_file));
files_from_file[n_files_from_file - 1] = mcopystr(buff);
}
fclose(fp);
} else {
ERROR("Cannot open file `%s' for reading: %s", file_list_file_name,
strerror(errno));
errno = 0;
errflag = true;
}
bool next_is_asn1 = false;
bool next_is_ttcn = false;
for (size_t i = 0; i < n_files_from_file; i++) {
// Check if -A or -T is present and continue to the next word if yes
if (next_is_ttcn == false && next_is_asn1 == false) {
if (strcmp(files_from_file[i], "-A") == 0) {
next_is_asn1 = true;
continue;
} else if (strcmp(files_from_file[i], "-T") == 0) {
next_is_ttcn = true;
continue;
}
}
Module::moduletype_t module_type = Module::MOD_UNKNOWN;
const char* file = files_from_file[i];
if (next_is_asn1) {
module_type = Module::MOD_ASN;
next_is_asn1 = false;
} else if(next_is_ttcn) {
module_type = Module::MOD_TTCN;
next_is_ttcn = false;
} else if (strlen(files_from_file[i]) > 2) {
// The -A or -T can be given as -TMyTtcnfile.ttcn too
if (files_from_file[i][0] == '-') {
if (files_from_file[i][1] == 'A') {
file = files_from_file[i] + 2;
module_type = Module::MOD_ASN;
} else if (files_from_file[i][1] == 'T') {
file = files_from_file[i] + 2;
module_type = Module::MOD_TTCN;
}
}
}
if (module_type == Module::MOD_TTCN) {
#ifdef LICENSE
ttcn3_modules_present = true;
#endif
} else if (module_type == Module::MOD_ASN) {
asn1_modules_present = true;
}
add_module(n_modules, module_list, file, module_type);
}
}
if (optind == argc && n_modules == 0 && n_files_from_file == 0) {
ERROR("No input TTCN-3 or ASN.1 module was given.");
errflag = true;
}
......@@ -1156,6 +1226,10 @@ int main(int argc, char *argv[])
if (zflag) {
free_profiler_data();
}
for (size_t i = 0; i < n_files_from_file; i++) {
Free(files_from_file[i]);
}
Free(files_from_file);
// dbgnew.hh already does it: check_mem_leak(argv[0]);
......
......@@ -4590,7 +4590,7 @@ static void usage(void)
{
fprintf(stderr, "\n"
"usage: %s [-abc" C_flag "dDEfFglLmMnprRsStTVwWXZ] [-K file] [-z file ] [-P dir]"
" [-j file] [-U none|type|'number'] [-e ets_name] [-o dir|file]\n"
" [-J file] [-U none|type|'number'] [-e ets_name] [-o dir|file]\n"
" [-t project_descriptor.tpd [-b buildconfig]]\n"
" [-O file] ... module_name ... testport_name ...\n"
" or %s -v\n"
......@@ -4607,7 +4607,7 @@ static void usage(void)
" -f: force overwriting of the output Makefile\n"
" -g: generate Makefile for use with GNU make\n"
" -I path: Add path to the search paths when using TPD files\n"
" -j file: The names of files taken from file instead of command line"
" -J file: The names of files taken from file instead of command line"
" -K file: enable selective code coverage\n"
" -l: use dynamic linking\n"
" -L: create makefile with library archive as the default target\n"
......@@ -4720,7 +4720,7 @@ int main(int argc, char *argv[])
}
for ( ; ; ) {
int c = getopt(argc, argv, "O:ab:c" C_flag "dDe:EfFgI:j:K:o:lLmMnpP:rRsSt:TU:vVwWXYz:ZH");
int c = getopt(argc, argv, "O:ab:c" C_flag "dDe:EfFgI:J:K:o:lLmMnpP:rRsSt:TU:vVwWXYz:ZH");
if (c == -1) break;
switch (c) {
case 'O':
......@@ -4779,7 +4779,7 @@ int main(int argc, char *argv[])
case 'H':
SET_FLAG(H);
break;
case 'j':
case 'J':
file_list_file_name = optarg;
break;
case 'o':
......
......@@ -3318,7 +3318,7 @@ error:
msg_type = out_msgs->get_type_byIndex(0);
} else {
// there are more than one outgoing message types
msg_type = get_outgoing_type(port_op.s.sendpar);
msg_type = get_msg_sig_type(port_op.s.sendpar);
if (msg_type) {
size_t nof_comp_types =
out_msgs->get_nof_compatible_types(msg_type);
......@@ -3351,7 +3351,7 @@ error:
}
// determining the message type if it is not done so far
if (!msg_type_determined) {
msg_type = get_outgoing_type(port_op.s.sendpar);
msg_type = get_msg_sig_type(port_op.s.sendpar);
}
if (!msg_type) msg_type = Type::get_pooltype(Type::T_ERROR);
// checking the parameter (template instance)
......@@ -3396,7 +3396,7 @@ error:
signature = out_sigs->get_type_byIndex(0);
} else {
// there are more than one outgoing signatures
signature = get_outgoing_type(port_op.s.sendpar);
signature = get_msg_sig_type(port_op.s.sendpar);
if (signature) {
if (!out_sigs->has_type(signature)) {
port_op.s.sendpar->error("Signature `%s' is not present on the "
......@@ -3421,7 +3421,7 @@ error:
}
}
if (!signature_determined)
signature = get_outgoing_type(port_op.s.sendpar);
signature = get_msg_sig_type(port_op.s.sendpar);
if (!signature) signature = Type::get_pooltype(Type::T_ERROR);
// checking the parameter (template instance)
port_op.s.sendpar->chk(signature);
......@@ -3504,7 +3504,7 @@ error:
signature = in_sigs->get_type_byIndex(0);
} else {
// there are more than one incoming signatures
signature = get_outgoing_type(port_op.s.sendpar);
signature = get_msg_sig_type(port_op.s.sendpar);
if (signature) {
if (!in_sigs->has_type(signature)) {
port_op.s.sendpar->error("Signature `%s' is not present on the "
......@@ -3529,7 +3529,7 @@ error:
}
}
if (!signature_determined)
signature = get_outgoing_type(port_op.s.sendpar);
signature = get_msg_sig_type(port_op.s.sendpar);
if (!signature) signature = Type::get_pooltype(Type::T_ERROR);
// checking the parameter (template instance)
port_op.s.sendpar->chk(signature);
......@@ -3625,7 +3625,7 @@ error:
exc_type = exceptions->get_type_byIndex(0);
} else {
// the signature has more than one exception types
exc_type = get_outgoing_type(port_op.s.sendpar);
exc_type = get_msg_sig_type(port_op.s.sendpar);
if (exc_type) {
size_t nof_comp_types =
exceptions->get_nof_compatible_types(exc_type);
......@@ -3653,7 +3653,7 @@ error:
}
// determining the type of exception if it is not done so far
if (!exc_type_determined) {
exc_type = get_outgoing_type(port_op.s.sendpar);
exc_type = get_msg_sig_type(port_op.s.sendpar);
}
if (!exc_type) exc_type = Type::get_pooltype(Type::T_ERROR);
// checking the exception template
......@@ -3707,7 +3707,7 @@ error:
msg_type = in_msgs->get_type_byIndex(0);
} else {
// there are more than one incoming message types
msg_type = get_incoming_type(port_op.r.rcvpar, port_op.r.redirect.value);
msg_type = get_msg_sig_type(port_op.r.rcvpar);
if (msg_type) {
size_t nof_comp_types =
in_msgs->get_nof_compatible_types(msg_type);
......@@ -3747,11 +3747,16 @@ error:
}
}
if (!msg_type_determined) {
msg_type = get_incoming_type(port_op.r.rcvpar, port_op.r.redirect.value);
msg_type = get_msg_sig_type(port_op.r.rcvpar);
}
if (!msg_type) msg_type = Type::get_pooltype(Type::T_ERROR);
// check the template instance using the message type
port_op.r.rcvpar->chk(msg_type);
if (port_op.r.rcvpar->get_Template()->get_template_refd_last()->
get_templatetype() == Template::ANY_OR_OMIT) {
port_op.r.rcvpar->error("'*' cannot be used as a matching template "
"for a '%s' operation", stmt_name);
}
// check the value redirect if it exists
if (port_op.r.redirect.value != NULL) {
port_op.r.redirect.value->chk(msg_type);
......@@ -3805,7 +3810,7 @@ error:
signature = in_sigs->get_type_byIndex(0);
} else {
// there are more than one incoming signatures
signature = get_outgoing_type(port_op.r.rcvpar);
signature = get_msg_sig_type(port_op.r.rcvpar);
if (signature) {
if (!in_sigs->has_type(signature)) {
port_op.r.rcvpar->error("Signature `%s' is not present on the "
......@@ -3838,7 +3843,7 @@ error:
}
}
if (!signature_determined)
signature = get_outgoing_type(port_op.r.rcvpar);
signature = get_msg_sig_type(port_op.r.rcvpar);
if (!signature) signature = Type::get_pooltype(Type::T_ERROR);
// checking the parameter (template instance)
port_op.r.rcvpar->chk(signature);
......@@ -3909,7 +3914,7 @@ error:
signature = out_sigs->get_type_byIndex(0);
} else {
// there are more than one outgoing signatures
signature = get_outgoing_type(port_op.r.rcvpar);
signature = get_msg_sig_type(port_op.r.rcvpar);
if (signature) {
if (!out_sigs->has_type(signature)) {
port_op.r.rcvpar->error("Signature `%s' is not present on the "
......@@ -3950,7 +3955,7 @@ error:
}
}
if (!signature_determined)
signature = get_outgoing_type(port_op.r.rcvpar);
signature = get_msg_sig_type(port_op.r.rcvpar);
if (!signature) signature = Type::get_pooltype(Type::T_ERROR);
// checking the parameter (template instance)
port_op.r.rcvpar->chk(signature);
......@@ -3992,9 +3997,14 @@ error:
}
// checking the value match if present
if (port_op.r.getreply_valuematch) {
Error_Context cntxt2(port_op.s.replyval, "In value match");
if (!return_type) return_type = Type::get_pooltype(Type::T_ERROR);
port_op.r.getreply_valuematch->chk(return_type);
Error_Context cntxt2(port_op.s.replyval, "In value match");
if (!return_type) return_type = Type::get_pooltype(Type::T_ERROR);
port_op.r.getreply_valuematch->chk(return_type);
if (port_op.r.getreply_valuematch->get_Template()->get_template_refd_last()->
get_templatetype() == Template::ANY_OR_OMIT) {
port_op.r.getreply_valuematch->error("'*' cannot be used as a return "
"value matching template for a '%s' operation", stmt_name);
}
}
// checking the value redirect if present
if (port_op.r.redirect.value != NULL) {
......@@ -4098,7 +4108,7 @@ error:
exc_type = exceptions->get_type_byIndex(0);
} else {
// the signature has more than one exception types
exc_type = get_incoming_type(port_op.r.rcvpar, port_op.r.redirect.value);
exc_type = get_msg_sig_type(port_op.r.rcvpar);
if (exc_type) {
size_t nof_comp_types =
exceptions->get_nof_compatible_types(exc_type);
......@@ -4125,11 +4135,16 @@ error:
}
}
if (!exc_type_determined) {
exc_type = get_incoming_type(port_op.r.rcvpar, port_op.r.redirect.value);
exc_type = get_msg_sig_type(port_op.r.rcvpar);
}
if (!exc_type) exc_type = Type::get_pooltype(Type::T_ERROR);
// check the template instance using the exception type
port_op.r.rcvpar->chk(exc_type);
if (port_op.r.rcvpar->get_Template()->get_template_refd_last()->
get_templatetype() == Template::ANY_OR_OMIT) {
port_op.r.rcvpar->error("'*' cannot be used as a matching template for "
"a '%s' operation", stmt_name);
}
// check the value redirect if it exists
if (port_op.r.redirect.value != NULL) {
port_op.r.redirect.value->chk(exc_type);
......@@ -4405,8 +4420,7 @@ error:
// specific component reference
if (comp_op.donereturn.donematch) {
// try to determine the type of the return value
Type *return_type = get_incoming_type(comp_op.donereturn.donematch,
comp_op.donereturn.redirect);
Type *return_type = get_msg_sig_type(comp_op.donereturn.donematch);
if (return_type) {
bool return_type_correct = false;
for (Type *t = return_type; ; t = t->get_type_refd()) {
......@@ -4426,6 +4440,11 @@ error:
return_type = Type::get_pooltype(Type::T_ERROR);
}
comp_op.donereturn.donematch->chk(return_type);
if (comp_op.donereturn.donematch->get_Template()->get_template_refd_last()->
get_templatetype() == Template::ANY_OR_OMIT) {
comp_op.donereturn.donematch->error("'*' cannot be used as a matching "
"template for a 'done' operation");
}
if (comp_op.donereturn.redirect != NULL) {
comp_op.donereturn.redirect->chk(return_type);
}
......@@ -4977,7 +4996,7 @@ error:
"not caught");
}
Type *Statement::get_outgoing_type(TemplateInstance *p_ti)
Type *Statement::get_msg_sig_type(TemplateInstance *p_ti)
{
// first analyze the template instance as is
Type *ret_val = p_ti->get_expr_governor(Type::EXPECTED_TEMPLATE);
......@@ -4990,27 +5009,6 @@ error:
return t_templ->get_expr_governor(Type::EXPECTED_TEMPLATE);
}
Type *Statement::get_incoming_type(TemplateInstance *p_ti,
ValueRedirect *p_val_redir)
{
// first analyze the template instance
Type *ret_val = p_ti->get_expr_governor(Type::EXPECTED_TEMPLATE);
// return if this step was successful
if (ret_val) return ret_val;
// try to convert the undef identifier in the template instance to
// a reference because it cannot be an enum value anymore
Template *t_templ = p_ti->get_Template();
t_templ->set_lowerid_to_ref();
ret_val = t_templ->get_expr_governor(Type::EXPECTED_TEMPLATE);
// return if this step was successful
if (ret_val) return ret_val;
// finally try to determine the type from the value redirect
if (p_val_redir != NULL) {
ret_val = p_val_redir->get_type();
}
return ret_val;
}
Type *Statement::chk_sender_redirect(Type *address_type)
{
if (!port_op.r.redirect.sender) return 0;
......
......@@ -700,13 +700,9 @@ namespace Ttcn {
* operation. Arguments \a port_type \a signature point to the
* port type and signature used in the call operation. */
void chk_call_body(Type *port_type, Type *signature);
/** Determines and returns the type of the outgoing message or
/** Determines and returns the type of the incoming or outgoing message or
* signature based on a template instance \a p_ti. */
static Type *get_outgoing_type(TemplateInstance *p_ti);
/** Determines and returns the type of the incoming message or
* signature based on a template instance \a p_ti and an optional
* value redirect \a p_val_redir. */
Type *get_incoming_type(TemplateInstance *p_ti, ValueRedirect *p_val_redir);
static Type *get_msg_sig_type(TemplateInstance *p_ti);
/** Checks the variable reference of a sender redirect. The type
* of the variable (or NULL in case of non-existent sender clause
* or error) is returned. The type of the variable is also
......
......@@ -1867,6 +1867,7 @@ namespace Ttcn {
signature->is_nonblocking_signature();
pdef.proc_in.elements[i].has_exceptions =
signature->get_signature_exceptions() ? TRUE : FALSE;
pdef.proc_in.elements[i].has_return_value = FALSE;
}
} else {
pdef.proc_in.nElements = 0;
......@@ -1886,6 +1887,8 @@ namespace Ttcn {
signature->is_nonblocking_signature();
pdef.proc_out.elements[i].has_exceptions =
signature->get_signature_exceptions() ? TRUE : FALSE;
pdef.proc_out.elements[i].has_return_value =
signature->get_signature_return_type() != NULL ? TRUE : FALSE;
}
} else {
pdef.proc_out.nElements = 0;
......
......@@ -573,6 +573,8 @@ static void generate_receive(char **def_ptr, char **src_ptr,
"value_template, %s_Redirect_Interface *value_redirect, const %s_template& "
"sender_template, %s *sender_ptr)\n"
"{\n"
"if (value_template.get_selection() == ANY_OR_OMIT) "
"TTCN_error(\"%s operation using '*' as matching template\");\n"
"msg_queue_item *my_head = (msg_queue_item*)msg_queue_head;\n"
"if (msg_queue_head == NULL) {\n"
"if (is_started) return ALT_MAYBE;\n"
......@@ -583,7 +585,7 @@ static void generate_receive(char **def_ptr, char **src_ptr,
"return ALT_NO;\n"
"}\n"
"} else ", class_name, function_name, message_type->name,
message_type->name_w_no_prefix, sender_type, sender_type);
message_type->name_w_no_prefix, sender_type, sender_type, operation_name);
if (is_address) {
src = mputprintf(src, "if (my_head->sender_component != "
"SYSTEM_COMPREF) {\n"
......@@ -1099,16 +1101,23 @@ static void generate_getreply(char **def_ptr, char **src_ptr,
src = mputprintf(src, "alt_status %s::%s(const %s_template& "
"getreply_template, const %s_template& sender_template, "
"const %s_reply_redirect& param_ref, %s *sender_ptr)\n"
"{\n"
"{\n", class_name, function_name, signature->name, sender_type,
signature->name, sender_type);
if (signature->has_return_value) {
src = mputprintf(src,
"if (getreply_template.return_value().get_selection() == ANY_OR_OMIT) "
"TTCN_error(\"%s operation using '*' as return value matching template\");\n",
operation_name);
}
src = mputstr(src,
"if (proc_queue_head == NULL) {\n"
"if (is_started) return ALT_MAYBE;\n"
"else {\n"
"TTCN_Logger::log(TTCN_Logger::MATCHING_PROBLEM, \"Matching on "
"port %%s failed: Port is not started and the queue is empty.\", "
"port %s failed: Port is not started and the queue is empty.\", "
"port_name);\n"
"return ALT_NO;\n"
"}\n", class_name, function_name, signature->name, sender_type,
signature->name, sender_type);
"}\n");
if (is_address) {
src = mputprintf(src,
"} else if (proc_queue_head->sender_component != SYSTEM_COMPREF) "
......@@ -1221,6 +1230,8 @@ static void generate_catch(char **def_ptr, char **src_ptr,
"catch_template, const %s_template& sender_template, "
"%s *sender_ptr)\n"
"{\n"
"if (catch_template.is_any_or_omit()) TTCN_error(\"%s operation using '*' "
"as matching template\");\n"
"if (proc_queue_head == NULL) {\n"
"if (is_started) return ALT_MAYBE;\n"
"else {\n"
......@@ -1229,7 +1240,7 @@ static void generate_catch(char **def_ptr, char **src_ptr,
"port_name);\n"
"return ALT_NO;\n"
"}\n", class_name, function_name, signature->name, sender_type,
sender_type);
sender_type, operation_name);
if (is_address) {
src = mputprintf(src,
"} else if (proc_queue_head->sender_component != SYSTEM_COMPREF) "
......
......@@ -76,6 +76,7 @@ typedef struct port_proc_signature_tag {
const char *dispname;
boolean is_noblock;
boolean has_exceptions;
boolean has_return_value;
} port_proc_signature;
typedef struct port_proc_signature_list_tag {
......
......@@ -689,7 +689,6 @@ void defSignatureClasses(const signature_def *sdef, output_struct *output)
/* value redirect base classes (interfaces) */
for (i = 0; i < sdef->exceptions.nElements; i++) {
def = mputprintf(def,
"public:\n"
"class %s_Redirect_Interface {\n"
"public:\n"
"virtual void set_values(const %s&) = 0;\n"
......@@ -852,6 +851,27 @@ void defSignatureClasses(const signature_def *sdef, output_struct *output)
"TTCN_error(\"Internal error: Invalid selector when performing "
"value redirect on an exception of signature %s.\");\n"
"}\n\n", dispname);
/* is_any_or_omit function */
def = mputprintf(def, "boolean is_any_or_omit() const;\n");
src = mputprintf(src,
"boolean %s_exception_template::is_any_or_omit() const\n"
"{\n"
"switch (exception_selection) {\n", name);
for (i = 0; i < sdef->exceptions.nElements; i++) {
src = mputprintf(src,
"case %s_%s:\n"
"return field_%s->get_selection() == ANY_OR_OMIT;\n",
selection_prefix, sdef->exceptions.elements[i].altname,
sdef->exceptions.elements[i].altname);
}
src = mputprintf(src,
"default:\n"
"break;\n"
"}\n"
"TTCN_error(\"Internal error: Invalid selector when checking for '*' in "
"an exception template of signature %s.\");\n"
"}\n\n", dispname);
def = mputstr(def, "};\n\n");
/* end of class xxx_exception_template */
......
......@@ -6863,7 +6863,7 @@ module ModuleA {
var MyCompType MyVar2;
}
// others should be covered in 'VariableRef'
altstep MyAltstep41() runs on MyCompType {[] MyPort2.catch(MyProc2, ?) -> value MyVar1 sender Nonexi41 {}}
altstep MyAltstep41() runs on MyCompType {[] MyPort2.catch(MyProc2, MyType1: ?) -> value MyVar1 sender Nonexi41 {}}
}
<END_MODULE>
<RESULT IF_PASS COUNT 1>
......
......@@ -565,14 +565,14 @@ testcase TC() runs on MyComponent {
var float F;
alt {
[]any port.receive(integer:?) -> value I { }
[]any port.check(receive(integer:*) -> value I) { }
[]any port.check(receive(integer:?) -> value I) { }
[]any port.getcall(Sig:{0}) -> param(I) { }
[]any port.getreply(Sig:{0}) -> value J param(I) { }
[]any port.catch(Sig, float:*) -> value F { }
[]any port.catch(Sig, float:?) -> value F { }
[]any port.check(getcall(Sig:{0}) -> param(I)) { }
[]any port.check(getreply(Sig:{0}) -> value J param(I)) { }
[]any port.check(catch(Sig, float:*) -> value F) { }
[]any port.check(catch(Sig, float:?) -> value F) { }
}
}
......@@ -1374,6 +1374,80 @@ testcase TC() runs on MyComponent {
:exmp.
.*---------------------------------------------------------------------*
:h3.Adhoc - port operation: '*' in matching template
.*---------------------------------------------------------------------*
:xmp tab=0.
<TC - Adhoc - port operation: '*' in matching template>
<COMPILE>
<VERDICT_LEAF PASS>
<MODULE TTCN Temp Temp.ttcn>