Whole document tree vec.ccGo to the documentation of this file.00001 // New abi Support -*- C++ -*- 00002 00003 // Copyright (C) 2000, 2001 Free Software Foundation, Inc. 00004 // 00005 // This file is part of GNU CC. 00006 // 00007 // GNU CC is free software; you can redistribute it and/or modify 00008 // it under the terms of the GNU General Public License as published by 00009 // the Free Software Foundation; either version 2, or (at your option) 00010 // any later version. 00011 00012 // GNU CC is distributed in the hope that it will be useful, 00013 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 // GNU General Public License for more details. 00016 00017 // You should have received a copy of the GNU General Public License 00018 // along with GNU CC; see the file COPYING. If not, write to 00019 // the Free Software Foundation, 59 Temple Place - Suite 330, 00020 // Boston, MA 02111-1307, USA. 00021 00022 // As a special exception, you may use this file as part of a free software 00023 // library without restriction. Specifically, if other files instantiate 00024 // templates or use macros or inline functions from this file, or you compile 00025 // this file and link it with other files to produce an executable, this 00026 // file does not by itself cause the resulting executable to be covered by 00027 // the GNU General Public License. This exception does not however 00028 // invalidate any other reasons why the executable file might be covered by 00029 // the GNU General Public License. 00030 00031 // Written by Nathan Sidwell, Codesourcery LLC, <nathan@codesourcery.com> 00032 00033 #include <cxxabi.h> 00034 #include <new> 00035 #include <exception> 00036 #include <exception_defines.h> 00037 00038 #include "unwind-cxx.h" 00039 00040 namespace __cxxabiv1 00041 { 00042 namespace 00043 { 00044 struct uncatch_exception 00045 { 00046 uncatch_exception (); 00047 ~uncatch_exception () { __cxa_begin_catch (&p->unwindHeader); } 00048 00049 __cxa_exception *p; 00050 }; 00051 00052 uncatch_exception::uncatch_exception () 00053 { 00054 __cxa_eh_globals *globals = __cxa_get_globals_fast (); 00055 00056 p = globals->caughtExceptions; 00057 p->handlerCount -= 1; 00058 globals->caughtExceptions = p->nextException; 00059 globals->uncaughtExceptions += 1; 00060 } 00061 } 00062 00063 // Allocate and construct array. 00064 extern "C" void * 00065 __cxa_vec_new(std::size_t element_count, 00066 std::size_t element_size, 00067 std::size_t padding_size, 00068 void (*constructor) (void *), 00069 void (*destructor) (void *)) 00070 { 00071 return __cxa_vec_new2(element_count, element_size, padding_size, 00072 constructor, destructor, 00073 &operator new[], &operator delete []); 00074 } 00075 00076 extern "C" void * 00077 __cxa_vec_new2(std::size_t element_count, 00078 std::size_t element_size, 00079 std::size_t padding_size, 00080 void (*constructor) (void *), 00081 void (*destructor) (void *), 00082 void *(*alloc) (std::size_t), 00083 void (*dealloc) (void *)) 00084 { 00085 std::size_t size = element_count * element_size + padding_size; 00086 char *base = static_cast <char *> (alloc (size)); 00087 00088 if (padding_size) 00089 { 00090 base += padding_size; 00091 reinterpret_cast <std::size_t *> (base)[-1] = element_count; 00092 } 00093 try 00094 { 00095 __cxa_vec_ctor(base, element_count, element_size, 00096 constructor, destructor); 00097 } 00098 catch (...) 00099 { 00100 { 00101 uncatch_exception ue; 00102 dealloc(base - padding_size); 00103 } 00104 __throw_exception_again; 00105 } 00106 return base; 00107 } 00108 00109 extern "C" void * 00110 __cxa_vec_new3(std::size_t element_count, 00111 std::size_t element_size, 00112 std::size_t padding_size, 00113 void (*constructor) (void *), 00114 void (*destructor) (void *), 00115 void *(*alloc) (std::size_t), 00116 void (*dealloc) (void *, std::size_t)) 00117 { 00118 std::size_t size = element_count * element_size + padding_size; 00119 char *base = static_cast<char *>(alloc (size)); 00120 00121 if (padding_size) 00122 { 00123 base += padding_size; 00124 reinterpret_cast<std::size_t *>(base)[-1] = element_count; 00125 } 00126 try 00127 { 00128 __cxa_vec_ctor(base, element_count, element_size, 00129 constructor, destructor); 00130 } 00131 catch (...) 00132 { 00133 { 00134 uncatch_exception ue; 00135 dealloc(base - padding_size, size); 00136 } 00137 __throw_exception_again; 00138 } 00139 return base; 00140 } 00141 00142 // Construct array. 00143 extern "C" void 00144 __cxa_vec_ctor(void *array_address, 00145 std::size_t element_count, 00146 std::size_t element_size, 00147 void (*constructor) (void *), 00148 void (*destructor) (void *)) 00149 { 00150 std::size_t ix = 0; 00151 char *ptr = static_cast<char *>(array_address); 00152 00153 try 00154 { 00155 if (constructor) 00156 for (; ix != element_count; ix++, ptr += element_size) 00157 constructor(ptr); 00158 } 00159 catch (...) 00160 { 00161 { 00162 uncatch_exception ue; 00163 __cxa_vec_cleanup(array_address, ix, element_size, destructor); 00164 } 00165 __throw_exception_again; 00166 } 00167 } 00168 00169 // Construct an array by copying. 00170 extern "C" void 00171 __cxa_vec_cctor(void *dest_array, 00172 void *src_array, 00173 std::size_t element_count, 00174 std::size_t element_size, 00175 void (*constructor) (void *, void *), 00176 void (*destructor) (void *)) 00177 { 00178 std::size_t ix = 0; 00179 char *dest_ptr = static_cast<char *>(dest_array); 00180 char *src_ptr = static_cast<char *>(src_array); 00181 00182 try 00183 { 00184 if (constructor) 00185 for (; ix != element_count; 00186 ix++, src_ptr += element_size, dest_ptr += element_size) 00187 constructor(dest_ptr, src_ptr); 00188 } 00189 catch (...) 00190 { 00191 { 00192 uncatch_exception ue; 00193 __cxa_vec_cleanup(dest_array, ix, element_size, destructor); 00194 } 00195 __throw_exception_again; 00196 } 00197 } 00198 00199 // Destruct array. 00200 extern "C" void 00201 __cxa_vec_dtor(void *array_address, 00202 std::size_t element_count, 00203 std::size_t element_size, 00204 void (*destructor) (void *)) 00205 { 00206 if (destructor) 00207 { 00208 char *ptr = static_cast<char *>(array_address); 00209 std::size_t ix = element_count; 00210 00211 ptr += element_count * element_size; 00212 00213 try 00214 { 00215 while (ix--) 00216 { 00217 ptr -= element_size; 00218 destructor(ptr); 00219 } 00220 } 00221 catch (...) 00222 { 00223 { 00224 uncatch_exception ue; 00225 __cxa_vec_cleanup(array_address, ix, element_size, destructor); 00226 } 00227 __throw_exception_again; 00228 } 00229 } 00230 } 00231 00232 // Destruct array as a result of throwing an exception. 00233 // [except.ctor]/3 If a destructor called during stack unwinding 00234 // exits with an exception, terminate is called. 00235 extern "C" void 00236 __cxa_vec_cleanup(void *array_address, 00237 std::size_t element_count, 00238 std::size_t element_size, 00239 void (*destructor) (void *)) 00240 { 00241 if (destructor) 00242 { 00243 char *ptr = static_cast <char *> (array_address); 00244 std::size_t ix = element_count; 00245 00246 ptr += element_count * element_size; 00247 00248 try 00249 { 00250 while (ix--) 00251 { 00252 ptr -= element_size; 00253 destructor(ptr); 00254 } 00255 } 00256 catch (...) 00257 { 00258 std::terminate(); 00259 } 00260 } 00261 } 00262 00263 // Destruct and release array. 00264 extern "C" void 00265 __cxa_vec_delete(void *array_address, 00266 std::size_t element_size, 00267 std::size_t padding_size, 00268 void (*destructor) (void *)) 00269 { 00270 __cxa_vec_delete2(array_address, element_size, padding_size, 00271 destructor, 00272 &operator delete []); 00273 } 00274 00275 extern "C" void 00276 __cxa_vec_delete2(void *array_address, 00277 std::size_t element_size, 00278 std::size_t padding_size, 00279 void (*destructor) (void *), 00280 void (*dealloc) (void *)) 00281 { 00282 char *base = static_cast<char *>(array_address); 00283 00284 if (padding_size) 00285 { 00286 std::size_t element_count = reinterpret_cast<std::size_t *>(base)[-1]; 00287 base -= padding_size; 00288 try 00289 { 00290 __cxa_vec_dtor(array_address, element_count, element_size, 00291 destructor); 00292 } 00293 catch (...) 00294 { 00295 { 00296 uncatch_exception ue; 00297 dealloc(base); 00298 } 00299 __throw_exception_again; 00300 } 00301 } 00302 dealloc(base); 00303 } 00304 00305 extern "C" void 00306 __cxa_vec_delete3(void *array_address, 00307 std::size_t element_size, 00308 std::size_t padding_size, 00309 void (*destructor) (void *), 00310 void (*dealloc) (void *, std::size_t)) 00311 { 00312 char *base = static_cast <char *> (array_address); 00313 std::size_t size = 0; 00314 00315 if (padding_size) 00316 { 00317 std::size_t element_count = reinterpret_cast<std::size_t *> (base)[-1]; 00318 base -= padding_size; 00319 size = element_count * element_size + padding_size; 00320 try 00321 { 00322 __cxa_vec_dtor(array_address, element_count, element_size, 00323 destructor); 00324 } 00325 catch (...) 00326 { 00327 { 00328 uncatch_exception ue; 00329 dealloc(base, size); 00330 } 00331 __throw_exception_again; 00332 } 00333 } 00334 dealloc(base, size); 00335 } 00336 } // namespace __cxxabiv1 00337 Generated on Mon Apr 8 03:11:48 2002 for libstdc++-v3 Source by ![]() |