0030091: Configuration - allow cross-compilation from Linux (case sensitive filesyste...
[occt.git] / src / OSD / OSD_Error.cxx
1 // Copyright (c) 1998-1999 Matra Datavision
2 // Copyright (c) 1999-2014 OPEN CASCADE SAS
3 //
4 // This file is part of Open CASCADE Technology software library.
5 //
6 // This library is free software; you can redistribute it and/or modify it under
7 // the terms of the GNU Lesser General Public License version 2.1 as published
8 // by the Free Software Foundation, with special exception defined in the file
9 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
10 // distribution for complete text of the license and disclaimer of any warranty.
11 //
12 // Alternatively, this file may be used under the terms of Open CASCADE
13 // commercial license or contractual agreement.
14
15 #ifndef _WIN32
16
17
18 #include <OSD_Error.hxx>
19 #include <OSD_ErrorList.hxx>
20 #include <OSD_OSDError.hxx>
21 #include <TCollection_AsciiString.hxx>
22
23 #include <stdio.h>
24 /* Created by Stephan GARNAUD (ARM) 1992 for Matra Datavision */
25 OSD_Error::OSD_Error(){
26  myErrno = 0;
27 }
28
29
30 void OSD_Error::Reset(){
31  myErrno = 0;
32 }
33
34 Standard_Boolean OSD_Error::Failed()const{
35  if (myErrno == 0) return (Standard_False);
36               else return (Standard_True);
37 }
38
39
40
41 void OSD_Error::SetValue(const Standard_Integer errcode,
42                          const Standard_Integer from,
43                          const TCollection_AsciiString& message){
44  myErrno = errcode;
45  myCode  = (OSD_WhoAmI)from;
46  myMessage = message;
47 }
48
49
50
51 Standard_Integer OSD_Error::Error()const{
52  return(extCode);
53 }
54
55  
56 void OSD_Error::Perror() {
57  TCollection_AsciiString buffer;
58
59  if (myErrno == 0) return;
60
61  buffer += " :\n ";
62  extCode = ERR_SURPRISE;
63
64  switch (myErrno){
65   case EBADF  :
66    switch (myCode){
67     case OSD_WFile:
68       buffer += "Invalid file descriptor or bad mode";
69       extCode = ERR_FBADF;
70       break;
71     default:
72       break;
73     }
74     break;
75
76
77 #ifdef SUN
78   case EBADMSG:
79    switch (myCode){
80     case OSD_WFile:
81      buffer += 
82      "The message waiting to be read on stream is not a data message";
83      extCode = ERR_FBADMSG;
84      break;
85     default:
86       break;
87    }
88    break;
89 #endif
90
91   case EINVAL: 
92    switch (myCode){
93     case OSD_WFileNode:
94       buffer += "Can't unlink '.' or '..'";
95       extCode = ERR_FNINVAL;
96       break;
97     case OSD_WFile:
98       buffer += "Invalid file descriptor";
99       extCode = ERR_FINVAL;
100       break;
101     default :
102       buffer += "User error : Bad parameter";
103       extCode = ERR_INVAL;
104       break;
105    }
106    break;
107 #if !defined(sun) && !defined(SOLARIS)
108   case EDQUOT :
109    switch (myCode){
110     case OSD_WDirectory:
111     case OSD_WFileNode:
112     case OSD_WFile :
113      buffer += "Exceed quota of disk blocks";
114      extCode = ERR_QUOT;
115      break;
116     default:
117       break;
118    }
119    break;
120 #endif
121
122 #ifdef SUN
123   case EDEADLK:
124    switch (myCode){
125     case OSD_WFile:
126      buffer += "Lock is already blocked by another process";
127      extCode = ERR_FDEADLK;
128      break;
129     default:
130       break;
131    }
132    break;
133 #endif
134
135   case ENOLCK:
136    switch (myCode){
137     case OSD_WFile:
138      buffer += "No more file lock entries available";
139      extCode = ERR_FNOLCK;
140      break;
141     default:
142       break;
143    }
144    break;
145   case EOPNOTSUPP:
146    switch (myCode){
147     case OSD_WFile:
148      buffer += "File descriptor doesn't refer to a file";
149      extCode = ERR_FWFD;
150      break;
151     default:
152      break;
153    }
154    break;
155   case EACCES: 
156     buffer += "Permission denied";
157     extCode = ERR_ACCESS;
158     break;
159   case EBUSY:
160    switch (myCode){
161     case OSD_WFileNode:
162      buffer += "Still used by system or a process";
163      extCode = ERR_FNBUSY;
164      break;
165     default:
166       break;
167    }
168    break;
169   case ERANGE:
170    switch (myCode){
171     case OSD_WFile:
172      buffer += "Not enough or too many bytes written";
173      extCode = ERR_FRANGE;
174      break;
175     default:
176       break;
177    }
178    break;
179   case EPERM: 
180    switch (myCode){
181     case OSD_WPackage:
182      buffer += "Permission denied";
183      extCode = ERR_PPERM;
184      break;
185     case OSD_WFileNode:
186      buffer += "Permission denied or can't unlink directory";
187      extCode = ERR_FPERM;
188      break;
189     default : 
190      buffer += "abnormal error : you modified OSD library";
191      extCode = ERR_PERM;
192      break;
193     }
194     break;
195   case EROFS:
196    switch (myCode){
197     case OSD_WFileNode:
198     case OSD_WFile:
199      buffer += "Read only file system";
200      extCode = ERR_ROFS;
201      break;
202     default:
203      break;
204    }
205    break;
206   case ENXIO:
207   case EIO :
208    switch (myCode){
209     case OSD_WDirectory:
210     case OSD_WFileNode:
211      buffer += "I/O error";
212      extCode = ERR_IO;
213      break;
214     case OSD_WFile :
215      buffer += "I/O error or Hang up from terminal";
216      extCode = ERR_FIO;
217      break;
218     default:
219      break;
220    }
221    break;
222   case EISDIR :
223    switch (myCode){
224     case OSD_WFileNode:
225     case OSD_WFile :
226      buffer += "The File is a Directory";
227      extCode = ERR_ISDIR;
228      break;
229     default:
230      break;
231     }
232     break;
233
234 #ifdef SUN
235   case EWOULDBLOCK:
236    switch (myCode){
237     case OSD_WFile:
238      buffer += "File is locked";
239      extCode = ERR_FLOCKED;
240      break;
241     default:
242      break;
243    }
244    break;
245 #endif
246
247 #ifdef IRIX4
248   case EWOULDBLOCK:
249    switch (myCode){
250     case OSD_WFile:
251      buffer += "File is locked";
252      extCode = ERR_FLOCKED;
253      break;
254     default:
255      break;
256    }
257    break;
258 #endif
259
260   case EAGAIN:
261    switch (myCode){
262     case OSD_WFile:
263      buffer += "No data ready to be read/written";
264      extCode = ERR_FAGAIN;
265      break;
266     default:
267      break;
268    }
269    break;
270   case ENOTDIR:
271    switch(myCode){
272     case OSD_WDirectory:
273     case OSD_WFileNode:
274     case OSD_WFile:
275      buffer += "A component of path is not a Directory";
276      extCode = ERR_NOTDIR;
277      break;
278     default:
279      break;
280    }
281    break;
282   case EMLINK:
283    switch (myCode){
284     case OSD_WDirectory:
285     buffer += "Too many links";
286     extCode = ERR_DMLINK;
287     break;
288     default:
289      break;
290    }
291    break;
292   case ELOOP :
293    switch (myCode){
294     case OSD_WDirectory:
295     case OSD_WFileNode:
296     case OSD_WFile :
297      buffer += "Too many symbolic links";
298      break;
299     default:
300      break;
301    }
302    break;
303   case EFAULT:
304    buffer += "User error : arguments point to an illegal address";
305    extCode = ERR_FAULT;
306    break;
307   case EFBIG:
308    switch (myCode){
309     case OSD_WFile:
310      buffer += "Exceed process's file size limit or the maximum file size";
311      extCode = ERR_FFBIG; 
312      break;
313     default:
314      break;
315    }
316    break;
317   case EINTR:
318    buffer += "operation breaked by a signal";
319    extCode = ERR_INTR;
320    break;
321   case ENOMEM: 
322    buffer += "Not enough memory";
323    extCode = ERR_NOMEM;
324    break;
325   case EMFILE : 
326    switch(myCode){   
327     case OSD_WFile :
328        buffer += "Too many file descriptors are currently in use by this process";
329        extCode = ERR_FMFILE;
330        break;
331     default:
332      break;
333     }
334     break;
335   case ENAMETOOLONG :
336    buffer += "File name too long";
337    extCode = ERR_NAMETOOLONG;
338    break;
339   case ENFILE :
340    switch (myCode){
341     case OSD_WFile:
342      buffer += "Too many files are currently open in the system";
343      extCode = ERR_FNFILE;
344      break;
345     default:
346      break;
347    }
348    break;
349   case EXDEV:
350    switch (myCode){
351     case OSD_WFileNode:
352      buffer += "The link named by path2 and the file named by path1 are\n";
353      buffer += "on different logical devices (file systems)";
354      extCode = ERR_FNXDEV;
355      break;
356     default:
357      break;
358    }
359    break;
360   case ENOENT:
361    switch (myCode){
362     case OSD_WFileNode:
363     case OSD_WFile:
364      if (myMessage != "Open") buffer += "File doesn't exist or";
365       buffer += "Invalid path (empty string)";
366      extCode = ERR_NOENT;
367      break;
368     case OSD_WDirectory:
369      buffer += "A component of the path prefix of path does not exist";
370      extCode = ERR_DNOENT;
371      break;
372     default:
373      break;
374     }
375     break;
376   case ENOSPC: {
377    switch (myCode){
378     case OSD_WDirectory:
379     case OSD_WFile:
380      buffer += "No more free space on file system";
381      extCode = ERR_FNOSPC;
382      break;
383     default:
384      break;
385    }
386    break;
387  }
388
389 //
390 // AIX maps ENOTEMPTY to EEXIST.  Move this case block to
391 // the EEXIST case block.
392 //
393 #if (!defined(_AIX)) && (!defined(AIX))
394   case ENOTEMPTY:
395    switch (myCode){
396     case OSD_WFileNode:
397      buffer += "Directory not empty";
398      extCode = ERR_FNNOTEMPTY;
399      break;
400     default:
401      break;
402    }
403    break;
404 #endif
405
406   case EEXIST: 
407    switch(myCode){
408     case OSD_WFileNode:
409      buffer += "Directory not empty";
410      extCode = ERR_FNNOTEMPTY;
411      break;
412     case OSD_WFile:
413      buffer += "OSD_Create and OSD_Exclude are set and the named file exists";
414      extCode = ERR_FEXIST;
415      break;
416     default:
417      buffer += "Identifier already exists for this key";
418      extCode = ERR_EXIST;
419      break;
420    }
421    break;
422   case E2BIG: 
423    buffer += "Too many Semaphore/Shared memory for a process.";
424    buffer += "Reconfigure Kernel with greater values";
425    extCode = ERR_TOOBIG;
426    break;
427    default: {
428      Standard_Character buf[255];
429      //
430      sprintf(buf,"%sUnknowm error #%d",buffer.ToCString(),myErrno);
431      TCollection_AsciiString interm(buf);
432      buffer = interm;
433      extCode = ERR_UNKNOWN;
434    }
435  }
436  buffer += ".\n\n";
437  throw OSD_OSDError(buffer.ToCString());
438 }
439
440 #else
441
442 //------------------------------------------------------------------------
443 //-------------------  Windows NT sources for OSD_Error ------------------
444 //------------------------------------------------------------------------
445
446 #include <OSD_Error.hxx>
447 #include <OSD_ErrorList.hxx>
448 #include <TCollection_ExtendedString.hxx>
449
450 #include <windows.h>
451 #include <strsafe.h>
452
453 typedef struct _error_table {
454
455                 DWORD            wnt_error;
456                 Standard_Integer csf_error;
457
458                } ERROR_TABLE;
459
460 static ERROR_TABLE commErrorTable [] = {
461
462  { ERROR_INVALID_FUNCTION,      ERR_INVAL       },
463  { ERROR_FILE_NOT_FOUND,        ERR_NOENT       },
464  { ERROR_PATH_NOT_FOUND,        ERR_NOENT       },
465  { ERROR_ACCESS_DENIED,         ERR_ACCESS      },
466  { ERROR_ARENA_TRASHED,         ERR_NOMEM       },
467  { ERROR_NOT_ENOUGH_MEMORY,     ERR_NOMEM       },
468  { ERROR_INVALID_BLOCK,         ERR_NOMEM       },
469  { ERROR_BAD_ENVIRONMENT,       ERR_TOOBIG      },
470  { ERROR_INVALID_ACCESS,        ERR_INVAL       },
471  { ERROR_INVALID_DATA,          ERR_INVAL       },
472  { ERROR_INVALID_DRIVE,         ERR_NOENT       },
473  { ERROR_CURRENT_DIRECTORY,     ERR_ACCESS      },
474  { ERROR_NO_MORE_FILES,         ERR_NOENT       },
475  { ERROR_LOCK_VIOLATION,        ERR_ACCESS      },
476  { ERROR_SHARING_VIOLATION,     ERR_ACCESS      },
477  { ERROR_BAD_NETPATH,           ERR_NOENT       },
478  { ERROR_NETWORK_ACCESS_DENIED, ERR_ACCESS      },
479  { ERROR_BAD_NET_NAME,          ERR_NOENT       },
480  { ERROR_FILE_EXISTS,           ERR_EXIST       },
481  { ERROR_CANNOT_MAKE,           ERR_ACCESS      },
482  { ERROR_FAIL_I24,              ERR_ACCESS      },
483  { ERROR_INVALID_PARAMETER,     ERR_INVAL       },
484  { ERROR_DRIVE_LOCKED,          ERR_ACCESS      },
485  { ERROR_INVALID_HANDLE,        ERR_INVAL       },
486  { ERROR_NEGATIVE_SEEK,         ERR_INVAL       },
487  { ERROR_SEEK_ON_DEVICE,        ERR_ACCESS      },
488  { ERROR_NOT_LOCKED,            ERR_ACCESS      },
489  { ERROR_BAD_PATHNAME,          ERR_NOENT       },
490  { ERROR_LOCK_FAILED,           ERR_ACCESS      },
491  { ERROR_ALREADY_EXISTS,        ERR_EXIST       },
492  { ERROR_FILENAME_EXCED_RANGE,  ERR_NOENT       },
493  { ERROR_NOT_ENOUGH_QUOTA,      ERR_QUOT        },
494  { ERROR_IO_DEVICE,             ERR_IO          },
495  { ERROR_INVALID_BLOCK,         ERR_FAULT       },
496  { ERROR_BAD_THREADID_ADDR,     ERR_FAULT       },
497  { ERROR_INVALID_ADDRESS,       ERR_FAULT       },
498  { ERROR_MAPPED_ALIGNMENT,      ERR_FAULT       },
499  { ERROR_BUFFER_OVERFLOW,       ERR_NAMETOOLONG }
500
501 };
502
503 #define COMM_ERR_TABLE_SIZE (int)(sizeof(commErrorTable) / sizeof(commErrorTable[0]))
504
505 static ERROR_TABLE dirErrorTable[] = {
506
507  { ERROR_FILE_NOT_FOUND,       ERR_NOENT },
508  { ERROR_PATH_NOT_FOUND,       ERR_NOENT },
509  { ERROR_INVALID_DRIVE,        ERR_NOENT },
510  { ERROR_NO_MORE_FILES,        ERR_NOENT },
511  { ERROR_BAD_NETPATH,          ERR_NOENT },
512  { ERROR_BAD_NET_NAME,         ERR_NOENT },
513  { ERROR_BAD_PATHNAME,         ERR_NOENT },
514  { ERROR_FILENAME_EXCED_RANGE, ERR_NOENT }
515
516 };
517
518 #define DIR_ERR_TABLE_SIZE (int)(sizeof(dirErrorTable) / sizeof(dirErrorTable[0]))
519
520 static ERROR_TABLE fileErrorTable[] = {
521
522  { ERROR_INVALID_HANDLE,        ERR_FBADF   },
523  { ERROR_INVALID_TARGET_HANDLE, ERR_FBADF   },
524  { ERROR_DIRECT_ACCESS_HANDLE,  ERR_FBADF   },
525  { ERROR_FILE_EXISTS,           ERR_EXIST   },
526  { ERROR_ALREADY_EXISTS,        ERR_EXIST   },
527  { ERROR_TOO_MANY_OPEN_FILES,   ERR_FMFILE  },
528  { ERROR_INVALID_FUNCTION,      ERR_FINVAL  },
529  { ERROR_INVALID_ACCESS,        ERR_FINVAL  },
530  { ERROR_INVALID_DATA,          ERR_FINVAL  },
531  { ERROR_INVALID_PARAMETER,     ERR_FINVAL  },
532  { ERROR_INVALID_HANDLE,        ERR_FINVAL  },
533  { ERROR_NEGATIVE_SEEK,         ERR_FINVAL  },
534  { ERROR_IO_PENDING,            ERR_FAGAIN  },
535  { ERROR_WRITE_FAULT,           ERR_FIO     },
536  { ERROR_READ_FAULT,            ERR_FIO     },
537  { ERROR_NET_WRITE_FAULT,       ERR_FIO     },
538  { ERROR_IO_DEVICE,             ERR_FIO     },
539  { ERROR_LOCK_VIOLATION,        ERR_FLOCKED },
540  { ERROR_LOCK_FAILED,           ERR_FLOCKED }
541
542 };
543
544 #define FILE_ERR_TABLE_SIZE (int)(sizeof(fileErrorTable) / sizeof(fileErrorTable[0]))
545
546 static ERROR_TABLE fileNodeErrorTable[] = {
547
548  { ERROR_INVALID_FUNCTION,      ERR_FNINVAL    },
549  { ERROR_INVALID_ACCESS,        ERR_FNINVAL    },
550  { ERROR_INVALID_DATA,          ERR_FNINVAL    },
551  { ERROR_INVALID_PARAMETER,     ERR_FNINVAL    },
552  { ERROR_INVALID_HANDLE,        ERR_FNINVAL    },
553  { ERROR_NEGATIVE_SEEK,         ERR_FNINVAL    },
554  { ERROR_DISK_FULL,             ERR_FNOSPC     },
555  { ERROR_DIR_NOT_EMPTY,         ERR_FNNOTEMPTY },
556  { ERROR_NOT_SAME_DEVICE,       ERR_FNXDEV     }
557
558 };
559
560 #define FILE_NODE_ERR_TABLE_SIZE (int)(sizeof(fileNodeErrorTable) / sizeof(fileNodeErrorTable[0]))
561
562 static Standard_Integer _get_comm_error ( DWORD );
563
564 OSD_Error :: OSD_Error () : 
565    myCode((OSD_WhoAmI)0),
566    extCode(0)
567 {
568  Reset ();
569 }  // end constructor ( 1 )
570
571 void OSD_Error :: Perror () {
572
573  wchar_t buff[32];
574
575   StringCchCopyW(buff, _countof(buff), L"Error ( ");
576
577   switch ( myCode ) {
578   
579    case OSD_WDirectoryIterator:
580      StringCchCatW(buff, _countof(buff), L"OSD_DirectoryIterator");
581    break;
582
583    case OSD_WDirectory:
584     StringCchCatW(buff, _countof(buff), L"OSD_Directory");
585    break;
586
587    case OSD_WFileIterator:
588     StringCchCatW(buff, _countof(buff), L"OSD_FileIterator");
589    break;
590
591    case OSD_WFile:
592     StringCchCatW(buff, _countof(buff), L"OSD_File");
593    break;
594
595    case OSD_WFileNode:
596     StringCchCatW(buff, _countof(buff), L"OSD_FileNode");
597    break;
598
599    case OSD_WHost:
600     StringCchCatW(buff, _countof(buff), L"OSD_Host");
601    break;
602
603    case OSD_WProcess:
604     StringCchCatW(buff, _countof(buff), L"OSD_Environment");
605    break;
606
607    case OSD_WEnvironmentIterator:
608      StringCchCatW(buff, _countof(buff), L"OSD_EnvironmentIterator");
609    break;
610
611    case OSD_WEnvironment:
612      StringCchCatW(buff, _countof(buff), L"OSD_Environment");
613    break;
614
615    case OSD_WDisk:
616      StringCchCatW(buff, _countof(buff), L"OSD_Disk");
617    break;
618
619    default:
620      StringCchCatW(buff, _countof(buff), L"Unknown");
621
622   }  // end switch
623
624   StringCchCatW(buff, _countof(buff), L" )");
625
626   std::wcerr << buff;
627  
628  std::cerr << myMessage.ToCString() << std::endl << std::flush;
629
630 }  // end OSD_Error :: Perror
631
632 void OSD_Error :: SetValue (
633                    const Standard_Integer Errcode,
634                    const Standard_Integer From,
635                    const TCollection_AsciiString& Message
636                   ) {
637
638  int i;
639
640  myErrno   = Errcode;
641  myCode    = ( OSD_WhoAmI )From;
642  myMessage = Message;
643
644  switch ( From ) {
645  
646   case OSD_WDirectory:
647
648    for ( i = 0; i < DIR_ERR_TABLE_SIZE; ++i )
649
650     if ( dirErrorTable[ i ].wnt_error == ( DWORD )Errcode ) {
651
652      extCode = dirErrorTable[ i ].csf_error;
653      break;
654
655    }  // end if
656
657   if ( i == DIR_ERR_TABLE_SIZE ) extCode = _get_comm_error ( Errcode );
658
659   break;
660
661   case OSD_WFile:
662
663    for ( i = 0; i < FILE_ERR_TABLE_SIZE; ++i )
664
665     if ( fileErrorTable[ i ].wnt_error == ( DWORD )Errcode ) {
666
667      extCode = fileErrorTable[ i ].csf_error;
668      break;
669
670    }  // end if
671
672   if ( i == FILE_ERR_TABLE_SIZE ) extCode = _get_comm_error ( Errcode );
673
674   break;
675  
676   case OSD_WFileNode:
677
678    for ( i = 0; i < FILE_NODE_ERR_TABLE_SIZE; ++i )
679
680     if ( fileNodeErrorTable[ i ].wnt_error == ( DWORD )Errcode ) {
681
682      extCode = fileNodeErrorTable[ i ].csf_error;
683      break;
684
685    }  // end if
686
687   if ( i == FILE_NODE_ERR_TABLE_SIZE ) extCode = _get_comm_error ( Errcode );
688
689   break;
690
691   default:
692
693    extCode = _get_comm_error ( Errcode );
694
695  }  // end switch
696
697 }  // end OSD_Error :: SetValue
698
699 Standard_Integer OSD_Error :: Error () const {
700
701  return extCode;
702
703 }  // end OSD_Error :: Error
704
705 Standard_Boolean OSD_Error :: Failed () const {
706
707  return myErrno == ERROR_SUCCESS ? Standard_False : Standard_True;
708
709 }  // end OSD_Error :: Failed
710
711 void OSD_Error :: Reset ()
712 {
713   myErrno = ERROR_SUCCESS;
714 }  // end OSD_Error :: Reset
715
716 static Standard_Integer _get_comm_error ( DWORD dwCode ) {
717
718  int              i;
719  Standard_Integer retVal = ERR_SURPRISE;
720
721  for ( i = 0; i < COMM_ERR_TABLE_SIZE; ++i )
722
723   if ( commErrorTable[ i ].wnt_error == ( DWORD )dwCode ) {
724
725    retVal = commErrorTable[ i ].csf_error;
726    break;
727
728   }  // end if
729
730  return retVal;
731
732 }  // end _get_comm_error
733
734 #endif