0033661: Data Exchange, Step Import - Tessellated GDTs are not imported
[occt.git] / src / Interface / Interface_FileReaderTool.cxx
CommitLineData
973c2be1 1// Copyright (c) 1999-2014 OPEN CASCADE SAS
b311480e 2//
973c2be1 3// This file is part of Open CASCADE Technology software library.
b311480e 4//
d5f74e42 5// This library is free software; you can redistribute it and/or modify it under
6// the terms of the GNU Lesser General Public License version 2.1 as published
973c2be1 7// by the Free Software Foundation, with special exception defined in the file
8// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
9// distribution for complete text of the license and disclaimer of any warranty.
b311480e 10//
973c2be1 11// Alternatively, this file may be used under the terms of Open CASCADE
12// commercial license or contractual agreement.
b311480e 13
7fd59977 14// dce 21/01/99 S3767 : Suppression of general messages
42cf5bc1 15
16#include <Interface_Check.hxx>
7fd59977 17#include <Interface_CheckFailure.hxx>
42cf5bc1 18#include <Interface_FileReaderData.hxx>
19#include <Interface_FileReaderTool.hxx>
20#include <Interface_GeneralLib.hxx>
7fd59977 21#include <Interface_GeneralModule.hxx>
42cf5bc1 22#include <Interface_InterfaceModel.hxx>
23#include <Interface_Protocol.hxx>
24#include <Interface_ReaderLib.hxx>
7fd59977 25#include <Interface_ReaderModule.hxx>
42cf5bc1 26#include <Interface_ReportEntity.hxx>
27#include <Message.hxx>
7fd59977 28#include <Message_Messenger.hxx>
7fd59977 29#include <Standard_ErrorHandler.hxx>
30#include <Standard_Failure.hxx>
42cf5bc1 31#include <Standard_Transient.hxx>
42cf5bc1 32
57c28b61 33#ifdef _WIN32
7fd59977 34#include <OSD_Exception.hxx>
35#else
36#include <OSD_Signal.hxx>
37#endif
38#include <stdio.h>
39
40// MGE 16/06/98
41// To use Msg class
42#include <Message_Msg.hxx>
43// To use TCollectionHAsciiString
44#include <TCollection_HAsciiString.hxx>
45
46// Failure pour recuperer erreur en lecture fichier,
47// TypeMismatch pour message d erreur circonstancie (cas particulier important)
48
49
50// Gere le chargement d un Fichier, prealablement transforme en FileReaderData
51// (de la bonne norme), dans un Modele
52
53
54//=======================================================================
55//function : Interface_FileReaderTool
56//purpose :
57//=======================================================================
58
59Interface_FileReaderTool::Interface_FileReaderTool ()
60{
61 themessenger = Message::DefaultMessenger();
62 theerrhand = Standard_True;
f9c58d7c 63 thetrace = 0;
7fd59977 64 thenbrep0 = thenbreps = 0;
65}
66
67//=======================================================================
68//function : SetData
69//purpose :
70//=======================================================================
71
72void Interface_FileReaderTool::SetData(const Handle(Interface_FileReaderData)& reader,
73 const Handle(Interface_Protocol)& protocol)
74{
75 thereader = reader;
76 theproto = protocol;
77}
78
79
80//=======================================================================
81//function : Protocol
82//purpose :
83//=======================================================================
84
85Handle(Interface_Protocol) Interface_FileReaderTool::Protocol () const
86{
87 return theproto;
88}
89
90
91//=======================================================================
92//function : Data
93//purpose :
94//=======================================================================
95
96Handle(Interface_FileReaderData) Interface_FileReaderTool::Data () const
97{
98 return thereader;
99}
100
101
102//=======================================================================
103//function : SetModel
104//purpose :
105//=======================================================================
106
107void Interface_FileReaderTool::SetModel
108 (const Handle(Interface_InterfaceModel)& amodel)
109{
110 themodel = amodel;
111}
112
113
114//=======================================================================
115//function : Model
116//purpose :
117//=======================================================================
118
119Handle(Interface_InterfaceModel) Interface_FileReaderTool::Model () const
120{
121 return themodel;
122}
123
124//=======================================================================
125//function : SetMessenger
126//purpose :
127//=======================================================================
128
129void Interface_FileReaderTool::SetMessenger (const Handle(Message_Messenger)& messenger)
130{
131 if ( messenger.IsNull() )
132 themessenger = Message::DefaultMessenger();
133 else
134 themessenger = messenger;
135}
136
137//=======================================================================
138//function : Messenger
139//purpose :
140//=======================================================================
141
142Handle(Message_Messenger) Interface_FileReaderTool::Messenger () const
143{
144 return themessenger;
145}
146
147//=======================================================================
148//function : SetTraceLevel
149//purpose :
150//=======================================================================
151
152void Interface_FileReaderTool::SetTraceLevel (const Standard_Integer tracelev)
153{
154 thetrace = tracelev;
155}
156
157//=======================================================================
158//function : TraceLevel
159//purpose :
160//=======================================================================
161
162Standard_Integer Interface_FileReaderTool::TraceLevel () const
163{
164 return thetrace;
165}
166
167//=======================================================================
168//function : SetErrorHandle
169//purpose :
170//=======================================================================
171
172void Interface_FileReaderTool::SetErrorHandle(const Standard_Boolean err)
173{
174 theerrhand = err;
175}
176
177
178//=======================================================================
179//function : ErrorHandle
180//purpose :
181//=======================================================================
182
183Standard_Boolean Interface_FileReaderTool::ErrorHandle() const
184{
185 return theerrhand;
186}
187
188// .... Actions Connexes au CHARGEMENT DU MODELE ....
189
190// SetEntities fait appel a des methodes a fournir :
191// s appuyant sur un Recognizer adapte a l interface :
192// - Recognize fait reco->Evaluate(... : selon record no num)
193// et recupere le resultat
194// ainsi que la definition de l entite inconnue de l interface
195
196
197//=======================================================================
198//function : SetEntities
199//purpose :
200//=======================================================================
201
202void Interface_FileReaderTool::SetEntities ()
203{
204 Standard_Integer num;
205 thenbreps = 0; thenbrep0 = 0;
206
207 for (num = thereader->FindNextRecord(0); num > 0;
208 num = thereader->FindNextRecord(num)) {
209 Handle(Standard_Transient) newent;
210 Handle(Interface_Check) ach = new Interface_Check;
211 if (!Recognize (num,ach,newent)) {
212 newent = UnknownEntity();
213 if (thereports.IsNull()) thereports =
214 new TColStd_HArray1OfTransient (1,thereader->NbRecords());
215 thenbreps ++; thenbrep0 ++;
216 thereports->SetValue (num,new Interface_ReportEntity(ach,newent));
217 }
218 else if ((ach->NbFails() + ach->NbWarnings() > 0) && !newent.IsNull()) {
219 if (thereports.IsNull()) thereports =
220 new TColStd_HArray1OfTransient (1,thereader->NbRecords());
221 thenbreps ++; thenbrep0 ++;
222 thereports->SetValue (num,new Interface_ReportEntity(ach,newent));
223 }
224 thereader->BindEntity (num,newent);
225 }
226}
227
228
229//=======================================================================
230//function : RecognizeByLib
231//purpose :
232//=======================================================================
233
234Standard_Boolean Interface_FileReaderTool::RecognizeByLib(const Standard_Integer num,
235 Interface_GeneralLib& glib,
236 Interface_ReaderLib& rlib,
237 Handle(Interface_Check)& ach,
238 Handle(Standard_Transient)& ent) const
239{
240 Handle(Interface_GeneralModule) gmod;
241 Handle(Interface_ReaderModule) rmod;
242 Handle(Interface_Protocol) proto;
243 Standard_Integer CN = 0;
244// Chercher dans ReaderLib : Reconnaissance de cas -> CN , proto
245 for (rlib.Start(); rlib.More(); rlib.Next()) {
246 rmod = rlib.Module();
247 if (rmod.IsNull()) continue;
248 CN = rmod->CaseNum(thereader,num);
249 if (CN > 0) { proto = rlib.Protocol(); break; }
250 }
251 if (CN <= 0 || proto.IsNull()) return Standard_False;
252// Se recaler dans GeneralLib : Creation de l entite vide
253 Handle(Standard_Type) typrot = proto->DynamicType();
254 for (glib.Start(); glib.More(); glib.Next()) {
255 proto = glib.Protocol();
256 if (proto.IsNull()) continue;
257 if (proto->DynamicType() != typrot) continue;
258 Standard_Boolean res = glib.Module()->NewVoid(CN,ent);
259 if (res) return res;
260 if (!rmod.IsNull()) return rmod->NewRead (CN,thereader,num,ach,ent);
261// return res;
262 }
263 return Standard_False;
264}
265
266
267//=======================================================================
268//function : UnknownEntity
269//purpose :
270//=======================================================================
271
272Handle(Standard_Transient) Interface_FileReaderTool::UnknownEntity() const
273{
274 return theproto->UnknownEntity();
275}
276
277
278//=======================================================================
279//function : NewModel
280//purpose :
281//=======================================================================
282
283Handle(Interface_InterfaceModel) Interface_FileReaderTool::NewModel() const
284{
285 return theproto->NewModel();
286}
287
288
289//=======================================================================
290//function : EndRead
291//purpose :
292//=======================================================================
293
294void Interface_FileReaderTool::EndRead(const Handle(Interface_InterfaceModel)& )
295{
296} // par defaut, ne fait rien; redefinissable selon besoin
297
298
299// .... (Sa Majeste le) CHARGEMENT DU MODELE ....
300
301
302//=======================================================================
303//function : LoadModel
304//purpose :
305//=======================================================================
306
307void Interface_FileReaderTool::LoadModel
308 (const Handle(Interface_InterfaceModel)& amodel)
309//
310// Methode generale de lecture d un fichier : il est lu via un FileReaderData
311// qui doit y donner acces de la facon la plus performante possible
312// chaque interface definit son FileHeader avec ses methodes, appelees ici
313{
314 // MGE 16/06/98
315 // Building of Messages
316 //====================================
317 Handle(Message_Messenger) TF = Messenger();
318 //====================================
319 Handle(Interface_Check) ach = new Interface_Check;
320
321 SetModel(amodel);
322
323// .. Demarrage : Lecture du Header ..
324 if (theerrhand) {
325 try {
326 OCC_CATCH_SIGNALS
327 BeginRead(amodel); // selon la norme
328 }
a738b534 329 catch (Standard_Failure const&) {
7fd59977 330 // Sendinf of message : Internal error during the header reading
f9c58d7c 331 if (!TF.IsNull())
332 {
333 Message_Msg Msg11("XSTEP_11");
334 TF->Send(Msg11, Message_Info);
335 }
7fd59977 336 }
337 }
338 else
339 BeginRead(amodel); // selon la norme
340
341 // .. Lecture des Entites ..
342
343 amodel->Reservate (thereader->NbEntities());
344
345 Standard_Integer num, num0 = thereader->FindNextRecord(0);
346 num = num0;
347
348 while (num > 0) {
349 Standard_Integer ierr = 0; // erreur sur analyse d une entite
350 Handle(Standard_Transient) anent;
351 try {
352 OCC_CATCH_SIGNALS
353 for (num = num0; num > 0; num = thereader->FindNextRecord(num)) {
354 num0 = num;
355
356 // Lecture sous protection contre crash
357 // (fait aussi AddEntity mais pas SetReportEntity)
358 anent = LoadedEntity(num);
359
360 // Lecture non protegee : utile pour travailler avec dbx
361//// else
362//// anent = LoadedEntity(num);
363
364 // .. Fin Lecture ..
365 if (anent.IsNull()) {
366 // Sending of message : Number of ignored Null Entities
f9c58d7c 367 if (!TF.IsNull())
368 {
369 Message_Msg Msg21("XSTEP_21");
370 Msg21.Arg(amodel->NbEntities());
371 TF->Send(Msg21, Message_Info);
372 }
7fd59977 373 continue;
374 }
375 // LoadedEntity fait AddEntity MAIS PAS SetReport (en bloc a la fin)
376
377 } // ---- fin boucle sur entites
378 num0 = 0; // plus rien
379 } // ---- fin du try, le catch suit
380
381 // En cas d erreur NON PREVUE par l analyse, recuperation par defaut
382 // Attention : la recuperation peut elle-meme planter ... (cf ierr)
9775fa61 383 catch (Standard_Failure const& anException) {
7fd59977 384 // Au passage suivant, on attaquera le record suivant
385 num0 = thereader->FindNextRecord(num); //:g9 abv 28 May 98: tr8_as2_ug.stp - infinite cycle: (0);
386
57c28b61 387#ifdef _WIN32
9775fa61 388 if (anException.IsKind(STANDARD_TYPE(OSD_Exception))) ierr = 2;
7fd59977 389#else
9775fa61 390 if (anException.IsKind(STANDARD_TYPE(OSD_Signal))) ierr = 2;
7fd59977 391#endif
392//:abv 03Apr00: anent is actually a previous one: if (anent.IsNull())
393 anent = thereader->BoundEntity(num);
394 if (anent.IsNull()) {
f9c58d7c 395 if (thetrace > 0)
396 {
397 // Sending of message : Number of ignored Null Entities
398 if (!TF.IsNull())
399 {
400
401 Message_Msg Msg21("XSTEP_21");
402 Msg21.Arg(amodel->NbEntities() + 1);
403
404 TF->Send(Msg21, Message_Info);
405 }
406 continue;
7fd59977 407 }
408 }
409 /*Handle(Interface_Check)*/ ach = new Interface_Check(anent);
410 //: abv 03 Apr 00: trj3_s1-tc-214.stp: generate a message on exception
411 Message_Msg Msg278("XSTEP_278");
412 Msg278.Arg(amodel->StringLabel(anent));
413 ach->SendFail (Msg278);
414
415 if (ierr == 2) {
f9c58d7c 416 // Sending of message : reading of entity failed
417 if (!TF.IsNull())
418 {
419 Message_Msg Msg22("XSTEP_22");
420 Msg22.Arg(amodel->StringLabel(anent));
421 TF->Send(Msg22, Message_Info);
422 }
7fd59977 423 return;
424 }
425
426 if (!ierr) {
427 //char mess[100]; svv #2
428 ierr = 1;
429// ce qui serait bien ici serait de recuperer le texte de l erreur pour ach ...
430 if (thetrace > 0) {
f9c58d7c 431 // Sending of message : recovered entity
432 if (!TF.IsNull())
433 {
434 Message_Msg Msg23("XSTEP_23");
435 Msg23.Arg(num);
436 TF->Send(Msg23, Message_Info);
437 }
7fd59977 438 }
439
440// Finalement, on charge une Entite Inconnue
441 thenbreps ++;
442 Handle(Interface_ReportEntity) rep =
443 new Interface_ReportEntity(ach,anent);
444 Handle(Standard_Transient) undef = UnknownEntity();
445 AnalyseRecord(num,undef,ach);
446 rep->SetContent(undef);
447
448 if (thereports.IsNull()) thereports =
449 new TColStd_HArray1OfTransient (1,thereader->NbRecords());
450 thenbreps ++;
451 thereports->SetValue (num,rep);
452 //if(isValid)
453 amodel->AddEntity (anent); // pas fait par LoadedEntity ...
454 }
455 else {
456 if (thetrace > 0) {
457 // Sending of message : reading of entity failed
f9c58d7c 458 if (!TF.IsNull())
459 {
460 Message_Msg Msg22("XSTEP_22");
461 Msg22.Arg(amodel->StringLabel(anent));
462 TF->Send(Msg22, Message_Info);
463 }
7fd59977 464 }
465// On garde <rep> telle quelle : pas d analyse fichier supplementaire,
466// Mais la phase preliminaire eventuelle est conservee
467// (en particulier, on garde trace du Type lu du fichier, etc...)
468 }
469 } // ----- fin complete du try/catch
470 } // ----- fin du while
471
472// .. Ajout des Reports, silya
473 if (!thereports.IsNull()) {
474 if (thetrace > 0)
475 {
476 // Sending of message : report
f9c58d7c 477 if (!TF.IsNull())
478 {
479 Message_Msg Msg24("XSTEP_24");
480 Msg24.Arg(thenbreps);
481 TF->Send(Msg24, Message_Info);
482 }
7fd59977 483 }
484 amodel->Reservate (-thenbreps-10);
485 thenbreps = thereports->Upper();
486 for (Standard_Integer nr = 1; nr <= thenbreps; nr ++) {
487 if (thereports->Value(nr).IsNull()) continue;
488 Handle(Standard_Transient) anent = thereader->BoundEntity (nr);
489 Handle(Interface_ReportEntity) rep =
490 Handle(Interface_ReportEntity)::DownCast(thereports->Value(nr));
491 amodel->SetReportEntity (-amodel->Number(anent),rep);
492 }
493 }
494
495// Conclusion : peut ne rien faire : selon necessite
496 if (theerrhand) {
497 try {
498 OCC_CATCH_SIGNALS
499 EndRead(amodel); // selon la norme
500 }
a738b534 501 catch (Standard_Failure const&) {
7fd59977 502 // Sendinf of message : Internal error during the header reading
f9c58d7c 503 if (!TF.IsNull())
504 {
505 Message_Msg Msg11("XSTEP_11");
506 TF->Send(Msg11, Message_Info);
507 }
7fd59977 508 }
509 }
510 else
511 EndRead(amodel); // selon la norme
512}
513
514
515//=======================================================================
516//function : LoadedEntity
517//purpose :
518//=======================================================================
519
520Handle(Standard_Transient) Interface_FileReaderTool::LoadedEntity
521 (const Standard_Integer num)
522{
523 Handle(Standard_Transient) anent = thereader->BoundEntity(num);
524 Handle(Interface_Check) ach = new Interface_Check(anent);
525 Handle(Interface_ReportEntity) rep; // entite Report, s il y a lieu
526 Standard_Integer irep = 0;
527 //Standard_Integer nbe = 0; svv #2
528 if (thenbrep0 > 0) {
529 rep = Handle(Interface_ReportEntity)::DownCast(thereports->Value(num));
530 if (!rep.IsNull()) { irep = num; ach = rep->Check(); }
531 }
532
533// Trace Entite Inconnue
534 if (thetrace >= 2 && theproto->IsUnknownEntity(anent)) {
535 Handle(Message_Messenger) TF = Messenger();
f9c58d7c 536 if (!TF.IsNull())
537 {
538 Message_Msg Msg22("XSTEP_22");
539 // Sending of message : reading of entity failed
540 Msg22.Arg(themodel->StringLabel(anent)->String());
541 TF->Send(Msg22, Message_Info);
542 }
7fd59977 543 }
544// .. Chargement proprement dit : Specifique de la Norme ..
545 AnalyseRecord(num,anent,ach);
546
547// .. Ajout dans le modele de l entite telle quelle ..
548// ATTENTION, ReportEntity traitee en bloc apres les Load
549 themodel->AddEntity(anent);
550
551// Erreur ou Correction : On cree une ReportEntity qui memorise le Check,
552// l Entite, et en cas d Erreur une UndefinedEntity pour les Parametres
553
554// On exploite ici le flag IsLoadError : s il a ete defini (a vrai ou faux)
555// il a priorite sur les fails du check. Sinon, ce sont les fails qui parlent
556
557 Standard_Integer nbf = ach->NbFails();
558 Standard_Integer nbw = ach->NbWarnings();
559 if (nbf + nbw > 0) {
560 //Standard_Integer n0; svv #2
561 themodel->NbEntities();
562 rep = new Interface_ReportEntity(ach,anent);
563 if (irep == 0) {
564 if (thereports.IsNull()) thereports =
565 new TColStd_HArray1OfTransient (1,thereader->NbRecords());
566 irep = num;
567 thenbreps ++;
568 }
569 thereports->SetValue(irep,rep);
570
f9c58d7c 571 if ( thetrace >= 2 && !Messenger().IsNull())
0ebe5b0a 572 {
573 Message_Messenger::StreamBuffer sout = Messenger()->SendInfo();
574 ach->Print (sout,2);
575 }
7fd59977 576 }
577
578// Rechargement ? si oui, dans une UnknownEntity fournie par le protocole
579 if (thereader->IsErrorLoad()) nbf = (thereader->ResetErrorLoad() ? 1 : 0);
580 if (nbf > 0) {
581 Handle(Standard_Transient) undef = UnknownEntity();
582 AnalyseRecord(num,undef,ach);
583 rep->SetContent(undef);
584 }
585
586// Conclusion (Unknown : traite en externe because traitement Raise)
587//// if (irep > 0) themodel->SetReportEntity (nbe,rep); en bloc a la fin
588
589 return anent;
590}
591
592
593//=======================================================================
e6f550da 594//function : ~Interface_FileReaderTool
7fd59977 595//purpose :
596//=======================================================================
597
e6f550da 598Interface_FileReaderTool::~Interface_FileReaderTool()
bc650d41 599{}
7fd59977 600
bc650d41
G
601void Interface_FileReaderTool::Clear()
602{
603 theproto.Nullify();
604 thereader.Nullify();
605 themodel.Nullify();
606 thereports.Nullify();
973c2be1 607}