Environment.cpp

Go to the documentation of this file.
00001 #include "tao/Environment.h"
00002 #include "tao/ORB_Core.h"
00003 #include "tao/SystemException.h"
00004 #include "tao/default_environment.h"
00005 
00006 #include "ace/OS_NS_string.h"
00007 
00008 #if !defined (__ACE_INLINE__)
00009 # include "tao/Environment.i"
00010 #endif /* __ACE_INLINE__ */
00011 
00012 
00013 ACE_RCSID (tao,
00014            Environment,
00015            "Environment.cpp,v 1.52 2006/03/10 07:19:05 jtc Exp")
00016 
00017 
00018 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00019 
00020 CORBA::Environment::Environment (void)
00021   : exception_ (0)
00022   , previous_ (0)
00023 {
00024 }
00025 
00026 CORBA::Environment::Environment (const CORBA::Environment& rhs)
00027   : exception_ (0)
00028   , previous_ (0)
00029 {
00030   if (rhs.exception_)
00031     this->exception_ = rhs.exception_->_tao_duplicate ();
00032 }
00033 
00034 CORBA::Environment::Environment (TAO_ORB_Core* orb_core)
00035   : exception_ (0)
00036   , previous_ (orb_core->default_environment ())
00037 {
00038   orb_core->default_environment (this);
00039 }
00040 
00041 CORBA::Environment&
00042 CORBA::Environment::operator= (const CORBA::Environment& rhs)
00043 {
00044   CORBA::Environment tmp (rhs);
00045   {
00046     CORBA::Exception *tmp_ex = this->exception_;
00047     this->exception_ = tmp.exception_;
00048     tmp.exception_ = tmp_ex;
00049   }
00050   {
00051     CORBA::Environment *tmp_env = this->previous_;
00052     this->previous_ = rhs.previous_;
00053     tmp.previous_ = tmp_env;
00054   }
00055   return *this;
00056 }
00057 
00058 CORBA::Environment::~Environment (void)
00059 {
00060   this->clear ();
00061 
00062   // If previous is 0 then this is the first Environment, allocated
00063   // with the ORB, it shouldn't try to pop because the ORB is beign
00064   // destroyed also.
00065   if (this->previous_ != 0)
00066     TAO_ORB_Core_instance ()->default_environment (this->previous_);
00067 }
00068 
00069 void
00070 CORBA::Environment::exception (CORBA::Exception *ex)
00071 {
00072   // @@ This does not look right, setting the exception to the
00073   //    contained exception is a bug,  the application is only
00074   //    supposed to pass in a pointer to an exception that it (the
00075   //    application) owns, however, if we contain the exception then
00076   //    *WE* own it.
00077   //    Normally I (coryan) would remove code like this, but I feel
00078   //    that it is a typical example of defensive programming for the
00079   //    *BAD*, i.e. we are not helping the application to get better
00080   //    and only making the ORB bigger and slower.
00081 #if 0
00082   if (ex != this->exception_)
00083     {
00084       this->clear ();
00085     }
00086 #else
00087   ACE_ASSERT (ex != this->exception_);
00088   this->clear ();
00089 #endif /* 0 */
00090 
00091   this->exception_ = ex;
00092 
00093 #if defined (TAO_HAS_EXCEPTIONS)
00094   if (this->exception_ != 0)
00095     this->exception_->_raise ();
00096 #endif /* TAO_HAS_EXCEPTIONS */
00097 }
00098 
00099 void
00100 CORBA::Environment::clear (void)
00101 {
00102   delete this->exception_;
00103   this->exception_ = 0;
00104 }
00105 
00106 CORBA::Environment&
00107 CORBA::Environment::default_environment ()
00108 {
00109 #if defined (TAO_HAS_EXCEPTIONS)
00110   //
00111   // If we are using native C++ exceptions the user is *not* supposed
00112   // to clear the environment every time she calls into TAO.  In fact
00113   // the user is not supposed to use the environment at all!
00114   //
00115   // But TAO is using the default environment internally, thus
00116   // somebody has to clear it. Since TAO passes the environment around
00117   // this function should only be called when going from the user code
00118   // into TAO's code.
00119   //
00120   // This is not an issue when using the alternative C++ mapping (with
00121   // the Environment argument) because then the user is supposed to
00122   // clear the environment before calling into the ORB.
00123   //
00124   TAO_ORB_Core_instance ()->default_environment ()->clear ();
00125 #endif /* TAO_HAS_EXCEPTIONS */
00126 
00127   return TAO_default_environment ();;
00128 }
00129 
00130 // Convenience -- say if the exception is a system exception or not.
00131 
00132 int
00133 CORBA::Environment::exception_type (void) const
00134 {
00135   // @@ Carlos, is this stuff that's properly "transformed" for EBCDIC
00136   //    platforms?!
00137   // @@ Doug: Yes, they are used to compare against the _id() of the
00138   //    exception, which should have been mappend to the native
00139   //    codeset.  Notice the "should" we haven't tried that stuff yet,
00140   //    and i find it hard to keep track of all the transformations
00141   //    going on, specially for the TypeCodes that are generated by
00142   //    the IDL compiler vs. the ones hard-coded in
00143   //    $TAO_ROOT/tao/Typecode_Constants.cpp
00144 
00145   static char sysex_prefix [] = "IDL:omg.org/CORBA/";
00146   static char typecode_extra [] = "TypeCode/";
00147 
00148   if (!this->exception_)
00149     {
00150       return CORBA::NO_EXCEPTION;
00151     }
00152 
00153   // All exceptions currently (CORBA 2.0) defined in the CORBA scope
00154   // are system exceptions ... except for a couple that are related to
00155   // TypeCodes.
00156 
00157   const char *id = this->exception_->_rep_id ();
00158 
00159   if ((ACE_OS::strncmp (id,
00160                         sysex_prefix,
00161                         sizeof sysex_prefix - 1) == 0
00162        && ACE_OS::strncmp (id + sizeof sysex_prefix - 1,
00163                            typecode_extra,
00164                            sizeof typecode_extra - 1) != 0))
00165     return CORBA::SYSTEM_EXCEPTION;
00166   else
00167     return CORBA::USER_EXCEPTION;
00168 }
00169 
00170 const char*
00171 CORBA::Environment::exception_id (void) const
00172 {
00173   if (this->exception_ == 0)
00174     return 0;
00175 
00176   return this->exception_->_rep_id ();
00177 }
00178 
00179 // Diagnostic utility routine: describe the exception onto the
00180 // standard I/O stream passed as a parameter.
00181 
00182 void
00183 CORBA::Environment::print_exception (const char *info,
00184                                      FILE *) const
00185 {
00186   if (this->exception_)
00187     {
00188       const char *id = this->exception_->_rep_id ();
00189 
00190       ACE_DEBUG ((LM_ERROR,
00191                   ACE_TEXT ("TAO: (%P|%t) EXCEPTION, %s\n"),
00192                   ACE_TEXT_CHAR_TO_TCHAR (info)));
00193 
00194       CORBA::SystemException *x2 =
00195         CORBA::SystemException::_downcast (this->exception_);
00196 
00197       if (x2 != 0)
00198         x2->_tao_print_system_exception ();
00199       else
00200         // @@ we can use the exception's typecode to dump all the data
00201         // held within it ...
00202 
00203         ACE_DEBUG ((LM_ERROR,
00204                     ACE_TEXT ("TAO: (%P|%t) user exception, ID '%s'\n"),
00205                     ACE_TEXT_CHAR_TO_TCHAR (id)));
00206     }
00207   else
00208     ACE_DEBUG ((LM_ERROR,
00209                 ACE_TEXT ("TAO: (%P|%t) no exception, %s\n"), ACE_TEXT_CHAR_TO_TCHAR (info)));
00210 }
00211 
00212 TAO_END_VERSIONED_NAMESPACE_DECL

Generated on Thu Nov 9 11:54:11 2006 for TAO by doxygen 1.3.6