Merge pull request #77 from balaskoa/master
[deliverable/titan.core.git] / xsdconvert / TTCN3ModuleInventory.cc
CommitLineData
d44e3c4f 1/******************************************************************************
2 * Copyright (c) 2000-2016 Ericsson Telecom AB
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
7 *
8 * Contributors:
9 * Balasko, Jeno
10 * Godar, Marton
11 * Raduly, Csaba
12 * Szabados, Kristof
13 * Szabo, Bence Janos
14 * Szalay, Akos
15 *
16 ******************************************************************************/
970ed795
EL
17#include "XMLParser.hh"
18#include "TTCN3ModuleInventory.hh"
19
20#include "GeneralFunctions.hh"
21
22#include "TTCN3Module.hh"
23#include "SimpleType.hh"
24#include "ComplexType.hh"
970ed795
EL
25
26extern bool h_flag_used;
27extern bool q_flag_used;
28
29
30
31unsigned int TTCN3ModuleInventory::num_errors = 0;
32unsigned int TTCN3ModuleInventory::num_warnings = 0;
33
970ed795
EL
34TTCN3ModuleInventory::TTCN3ModuleInventory()
35: definedModules()
36, writtenImports()
3abe9331 37, typenames() {
38}
970ed795 39
3abe9331 40TTCN3ModuleInventory::~TTCN3ModuleInventory() {
970ed795
EL
41 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
42 delete(module->Data);
43 }
44}
45
3abe9331 46TTCN3ModuleInventory& TTCN3ModuleInventory::getInstance() {
970ed795
EL
47 // Singleton, see Meyers, More Effective C++, Item 26 (page 131)
48 static TTCN3ModuleInventory instance;
49 return instance;
50}
51
3abe9331 52TTCN3Module * TTCN3ModuleInventory::addModule(const char * xsd_filename, XMLParser * a_parser) {
970ed795
EL
53 TTCN3Module * module = new TTCN3Module(xsd_filename, a_parser);
54 definedModules.push_back(module);
55 return definedModules.back();
56}
57
3abe9331 58void TTCN3ModuleInventory::modulenameConversion() {
970ed795
EL
59 definedModules.sort(compareModules);
60
3abe9331 61 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
970ed795
EL
62 module->Data->TargetNamespace2ModuleName();
63 }
64}
65
3abe9331 66void TTCN3ModuleInventory::referenceResolving() {
970ed795
EL
67 /**
68 * Reference resolving for include and import statements
69 */
3abe9331 70 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
71 for (List<RootType*>::iterator type = module->Data->getDefinedTypes().begin(); type; type = type->Next) {
72 if (type->Data->getName().convertedValue == "import" || type->Data->getName().convertedValue == "include") {
970ed795
EL
73 type->Data->referenceResolving();
74 }
75 }
76 }
77
78 /**
79 * Reference resolving for all others
80 */
81 bool there_is_unresolved_reference_somewhere = false;
3abe9331 82 do {
970ed795
EL
83 there_is_unresolved_reference_somewhere = false;
84
3abe9331 85 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
86 for (List<RootType*>::iterator type = module->Data->getDefinedTypes().begin(); type; type = type->Next) {
87 if (type->Data->getName().convertedValue != "import" && type->Data->getName().convertedValue != "include") {
970ed795 88 type->Data->referenceResolving();
3abe9331 89 if (type->Data->hasUnresolvedReference()) {
970ed795
EL
90 there_is_unresolved_reference_somewhere = true;
91 }
92 }
93 }
94 }
3abe9331 95 } while (there_is_unresolved_reference_somewhere);
970ed795
EL
96}
97
3abe9331 98void TTCN3ModuleInventory::finalModification() {
99 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
100 for (List<RootType*>::iterator type = module->Data->getDefinedTypes().begin(); type; type = type->Next) {
970ed795
EL
101 type->Data->finalModification();
102 }
103 }
104}
105
3abe9331 106void TTCN3ModuleInventory::nameConversion() {
970ed795
EL
107 /**
108 * Sort of types and fields
109 */
970ed795
EL
110
111 definedModules.sort(compareModules);
112 /********************************************************
113 * Conversion of the name of types
114 * ******************************************************/
3abe9331 115 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
970ed795
EL
116 if (module->Data->isnotIntoNameConversion()) continue;
117
118 List<RootType*> definedElements_inABC;
119 List<RootType*> definedAttributes_inABC;
120 List<RootType*> definedSimpleTypes_inABC;
121 List<RootType*> definedComplexTypes_inABC;
122 List<RootType*> definedAttributeGroups_inABC;
123 List<RootType*> definedGroups_inABC;
124
3abe9331 125 for (List<TTCN3Module*>::iterator module2 = module; module2; module2 = module2->Next) {
970ed795
EL
126 if (module2->Data->getModulename() != module->Data->getModulename()) continue;
127
3abe9331 128 for (List<RootType*>::iterator type = module2->Data->getDefinedTypes().begin(); type; type = type->Next) {
129 switch (type->Data->getConstruct()) {
130 case c_simpleType:
131 definedSimpleTypes_inABC.push_back(type->Data);
132 break;
133 case c_element:
134 definedElements_inABC.push_back(type->Data);
135 break;
136 case c_attribute:
137 definedAttributes_inABC.push_back(type->Data);
138 break;
139 case c_complexType:
140 definedComplexTypes_inABC.push_back(type->Data);
141 break;
142 case c_group:
143 definedGroups_inABC.push_back(type->Data);
144 break;
145 case c_attributeGroup:
146 definedAttributeGroups_inABC.push_back(type->Data);
147 break;
148 default:
149 break;
970ed795
EL
150 }
151 }
152 module2->Data->notIntoNameConversion();
153 }
154
155 definedElements_inABC.sort(compareTypes);
156 definedAttributes_inABC.sort(compareTypes);
157 definedSimpleTypes_inABC.sort(compareTypes);
158 definedComplexTypes_inABC.sort(compareTypes);
159 definedAttributeGroups_inABC.sort(compareTypes);
160 definedGroups_inABC.sort(compareTypes);
161
3abe9331 162 typenames.push_back(QualifiedName(module->Data->getTargetNamespace(), module->Data->getModulename()));
163 for(List<const TTCN3Module*>::iterator mod = module->Data->getImportedModules().begin(); mod; mod = mod->Next){
164 typenames.push_back(QualifiedName(module->Data->getTargetNamespace(), mod->Data->getModulename()));
165 }
166
167 for (List<RootType*>::iterator type = definedElements_inABC.begin(); type; type = type->Next) {
970ed795
EL
168 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
169 }
3abe9331 170 for (List<RootType*>::iterator type = definedAttributes_inABC.begin(); type; type = type->Next) {
970ed795
EL
171 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
172 }
3abe9331 173 for (List<RootType*>::iterator type = definedSimpleTypes_inABC.begin(); type; type = type->Next) {
970ed795
EL
174 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
175 }
3abe9331 176 for (List<RootType*>::iterator type = definedComplexTypes_inABC.begin(); type; type = type->Next) {
970ed795
EL
177 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
178 }
3abe9331 179 for (List<RootType*>::iterator type = definedAttributeGroups_inABC.begin(); type; type = type->Next) {
970ed795
EL
180 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
181 }
3abe9331 182 for (List<RootType*>::iterator type = definedGroups_inABC.begin(); type; type = type->Next) {
970ed795
EL
183 type->Data->nameConversion(nameMode, module->Data->getDeclaredNamespaces());
184 }
3abe9331 185 typenames.clear();
970ed795
EL
186 }
187 /********************************************************
188 * Conversion of the type of types
189 * ******************************************************/
3abe9331 190 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
191 for (List<RootType*>::iterator type = module->Data->getDefinedTypes().begin(); type; type = type->Next) {
970ed795
EL
192 type->Data->nameConversion(typeMode, module->Data->getDeclaredNamespaces());
193 }
194 }
195 /********************************************************
196 * Conversion of the names and the types of the fields
197 * ******************************************************/
3abe9331 198 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
199 for (List<RootType*>::iterator type = module->Data->getDefinedTypes().begin(); type; type = type->Next) {
970ed795
EL
200 type->Data->nameConversion(fieldMode, module->Data->getDeclaredNamespaces());
201 }
202 }
203}
204
3abe9331 205void TTCN3ModuleInventory::moduleGeneration() {
206 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
207 if (module->Data->isnotIntoFile()) {
208 continue;
209 }
970ed795
EL
210
211 List<NamespaceType> used_namespaces;
212 NamespaceType targetns;
213 targetns.uri = module->Data->getTargetNamespace();
214 used_namespaces.push_back(targetns);
215
216 // Now search for other modules with the same module name.
217 // They must have had the same targetNamespace.
3abe9331 218 for (List<TTCN3Module*>::iterator module2 = module; module2; module2 = module2->Next) {
219 if (module2->Data->getModulename() != module->Data->getModulename()) {
220 continue;
221 }
970ed795 222
3abe9331 223 for (List<NamespaceType>::iterator declNS = module2->Data->getDeclaredNamespaces().begin(); declNS; declNS = declNS->Next) {
970ed795
EL
224 used_namespaces.push_back(declNS->Data);
225 }
226 module2->Data->notIntoFile(); // first module gets the TTCN-3 file
227 }
228
229 Mstring filename_s = module->Data->getModulename() + ".ttcn";
230 FILE * file = fopen(filename_s.c_str(), "w");
231 if (file == NULL) {
232 Mstring cannot_write("Cannot write file ");
233 perror((cannot_write + filename_s).c_str());
234 ++num_errors;
235 return;
236 }
237#ifndef NDEBUG
238 // In debug mode, set the output stream to unbuffered.
239 // This allows watching the output as it appears (e.g. with tail -f).
240 setvbuf(file, NULL, _IONBF, 0);
241#endif
242
feade998 243 generate_TTCN3_header(file, module->Data->getModulename().c_str());
970ed795
EL
244
245 fprintf(file, "//\tGenerated from file(s):\n");
246
3abe9331 247 for (List<TTCN3Module*>::iterator module2 = module; module2; module2 = module2->Next) {
248 if (module2->Data->getModulename() == module->Data->getModulename()) {
970ed795
EL
249 module2->Data->generate_TTCN3_fileinfo(file);
250 }
251 }
252
253 fprintf(file,
254 "////////////////////////////////////////////////////////////////////////////////\n"
255 "// Modification header(s):\n"
256 "//-----------------------------------------------------------------------------\n"
257 "// Modified by:\n"
258 "// Modification date:\n"
259 "// Description:\n"
260 "// Modification contact:\n"
261 "//------------------------------------------------------------------------------\n"
262 "////////////////////////////////////////////////////////////////////////////////\n"
263 "\n"
264 "\n");
265
266 module->Data->generate_TTCN3_modulestart(file);
267
3abe9331 268 for (List<TTCN3Module*>::iterator module2 = module; module2; module2 = module2->Next) {
269 if (module2->Data->getModulename() == module->Data->getModulename()) {
970ed795
EL
270 module2->Data->generate_TTCN3_import_statements(file);
271 }
272 }
273
274 writtenImports.clear();
275
3abe9331 276 for (List<TTCN3Module*>::iterator module2 = module; module2; module2 = module2->Next) {
277 if (module2->Data->getModulename() == module->Data->getModulename()) {
970ed795
EL
278 module2->Data->generate_TTCN3_included_types(file);
279 module2->Data->generate_TTCN3_types(file);
280 }
281 }
282
283 fprintf(file, "}\n");
284
285 module->Data->generate_with_statement(file, used_namespaces);
286
287 if (!q_flag_used) fprintf(stderr, "Notify: File '%s' was generated.\n", filename_s.c_str());
288
289 fclose(file);
290 }
291}
292
3abe9331 293RootType * TTCN3ModuleInventory::lookup(const RootType* ref, const Mstring& reference, wanted w) const {
294 Mstring uri = reference.getPrefix(':');
295 const Mstring& name = reference.getValueWithoutPrefix(':');
296 if(uri.empty()){
297 for(List<NamespaceType>::iterator qname = ref->getModule()->getDeclaredNamespaces().begin(); qname; qname = qname->Next){
298 if(qname->Data.prefix.empty()){
299 uri = qname->Data.uri;
300 break;
301 }
302 }
51fa56b9 303 if(uri.empty()){
304 //If the targetnamespace is NoTargetNamespace therefore no prefix connector used
305 uri = ref->getModule()->getTargetNamespace();
306 }
3abe9331 307 }else {
308 uri = getNameSpaceByPrefix(ref, uri);
309 }
310 return lookup(name, uri, NULL, w);
311}
312
313RootType * TTCN3ModuleInventory::lookup(const SimpleType * reference, wanted w) const {
314 const Mstring& uri = reference->getReference().get_uri();
315 const Mstring& name = reference->getReference().get_val();
316
317 return lookup(name, uri, reference, w);
318}
319
320RootType * TTCN3ModuleInventory::lookup(const ComplexType * reference, wanted w) const {
970ed795
EL
321 const Mstring& uri = reference->getReference().get_uri();
322 const Mstring& name = reference->getReference().get_val();
323
324 return lookup(name, uri, reference, w);
325}
326
327RootType * TTCN3ModuleInventory::lookup(const Mstring& name, const Mstring& nsuri,
3abe9331 328 const RootType *reference, wanted w) const {
970ed795
EL
329 return ::lookup(definedModules, name, nsuri, reference, w);
330}
331
3abe9331 332void TTCN3ModuleInventory::dump() const {
333 fprintf(stderr, "Dumping %lu modules.\n", (unsigned long) definedModules.size());
334 for (List<TTCN3Module*>::iterator module = definedModules.begin(); module; module = module->Next) {
970ed795
EL
335 module->Data->dump();
336 }
337
3abe9331 338 fprintf(stderr, "Dumping %lu types\n", (unsigned long) typenames.size());
970ed795
EL
339
340 Item<QualifiedName> *o = typenames.begin();
3abe9331 341 for (; o != NULL; o = o->Next) {
970ed795
EL
342 fprintf(stderr, "{%s}%s,\n",
343 o->Data.nsuri.c_str(), o->Data.name.c_str());
344 }
345}
This page took 0.038476 seconds and 5 git commands to generate.