1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_cli_ure.hxx" 30 31 #include "climaker_share.h" 32 33 #include "rtl/string.hxx" 34 #include "rtl/ustrbuf.hxx" 35 #include "com/sun/star/reflection/XIndirectTypeDescription.hpp" 36 #include "com/sun/star/reflection/XStructTypeDescription.hpp" 37 #include "com/sun/star/reflection/XInterfaceTypeDescription2.hpp" 38 #include "com/sun/star/reflection/XInterfaceMethodTypeDescription.hpp" 39 #include "com/sun/star/reflection/XInterfaceAttributeTypeDescription.hpp" 40 #include "com/sun/star/reflection/XInterfaceAttributeTypeDescription2.hpp" 41 #include <vector> 42 43 using namespace ::System::Reflection; 44 45 using namespace ::rtl; 46 using namespace ::com::sun::star; 47 using namespace ::com::sun::star::uno; 48 49 namespace climaker 50 { 51 System::String* mapUnoPolymorphicName(System::String* unoName); 52 //------------------------------------------------------------------------------ 53 static inline ::System::String * to_cts_name( 54 OUString const & uno_name ) 55 { 56 OUStringBuffer buf( 7 + uno_name.getLength() ); 57 buf.appendAscii( RTL_CONSTASCII_STRINGPARAM("unoidl.") ); 58 buf.append( uno_name ); 59 return ustring_to_String( buf.makeStringAndClear() ); 60 } 61 62 //------------------------------------------------------------------------------ 63 static inline ::System::Object * to_cli_constant( Any const & value ) 64 { 65 switch (value.getValueTypeClass()) 66 { 67 case TypeClass_CHAR: 68 return __box 69 ((::System::Char) *reinterpret_cast< sal_Unicode const * >( 70 value.getValue() )); 71 case TypeClass_BOOLEAN: 72 return __box 73 ((::System::Boolean) 74 sal_False != *reinterpret_cast< sal_Bool const * >( 75 value.getValue() )); 76 case TypeClass_BYTE: 77 return __box 78 ((::System::Byte) *reinterpret_cast< sal_Int8 const * >( 79 value.getValue() )); 80 case TypeClass_SHORT: 81 return __box 82 ((::System::Int16) *reinterpret_cast< sal_Int16 const * >( 83 value.getValue() )); 84 case TypeClass_UNSIGNED_SHORT: 85 return __box 86 ((::System::UInt16) *reinterpret_cast< sal_uInt16 const * >( 87 value.getValue() )); 88 case TypeClass_LONG: 89 return __box 90 ((::System::Int32) *reinterpret_cast< sal_Int32 const * >( 91 value.getValue() )); 92 case TypeClass_UNSIGNED_LONG: 93 return __box 94 ((::System::UInt32) *reinterpret_cast< sal_uInt32 const * >( 95 value.getValue() )); 96 case TypeClass_HYPER: 97 return __box 98 ((::System::Int64) *reinterpret_cast< sal_Int64 const * >( 99 value.getValue() )); 100 case TypeClass_UNSIGNED_HYPER: 101 return __box 102 ((::System::UInt64) *reinterpret_cast< sal_uInt64 const * >( 103 value.getValue() )); 104 case TypeClass_FLOAT: 105 return __box 106 ((::System::Single) *reinterpret_cast< float const * >( 107 value.getValue() )); 108 case TypeClass_DOUBLE: 109 return __box 110 ((::System::Double) *reinterpret_cast< double const * >( 111 value.getValue() )); 112 default: 113 throw RuntimeException( 114 OUSTR("unexpected constant type ") + 115 value.getValueType().getTypeName(), 116 Reference< XInterface >() ); 117 } 118 } 119 120 //------------------------------------------------------------------------------ 121 static inline void emit_ldarg( Emit::ILGenerator * code, ::System::Int32 index ) 122 { 123 switch (index) 124 { 125 case 0: 126 code->Emit( Emit::OpCodes::Ldarg_0 ); 127 break; 128 case 1: 129 code->Emit( Emit::OpCodes::Ldarg_1 ); 130 break; 131 case 2: 132 code->Emit( Emit::OpCodes::Ldarg_2 ); 133 break; 134 case 3: 135 code->Emit( Emit::OpCodes::Ldarg_3 ); 136 break; 137 default: 138 if (index < 0x100) 139 code->Emit( Emit::OpCodes::Ldarg_S, (::System::Byte) index ); 140 else if (index < 0x8000) 141 code->Emit( Emit::OpCodes::Ldarg_S, (::System::Int16) index ); 142 else 143 code->Emit( Emit::OpCodes::Ldarg, index ); 144 break; 145 } 146 } 147 148 void polymorphicStructNameToStructName(::System::String ** sPolyName) 149 { 150 if ((*sPolyName)->EndsWith(S">") == false) 151 return; 152 153 int index = (*sPolyName)->IndexOf('<'); 154 OSL_ASSERT(index != -1); 155 *sPolyName = (*sPolyName)->Substring(0, index); 156 } 157 158 159 System::String* mapUnoTypeName(System::String * typeName) 160 { 161 ::System::Text::StringBuilder* buf= new System::Text::StringBuilder(); 162 ::System::String * sUnoName = ::System::String::Copy(typeName); 163 //determine if the type is a sequence and its dimensions 164 int dims= 0; 165 if (typeName->StartsWith(S"["))//if (usUnoName[0] == '[') 166 { 167 int index= 1; 168 while (true) 169 { 170 if (typeName->get_Chars(index++) == ']')//if (usUnoName[index++] == ']') 171 dims++; 172 if (typeName->get_Chars(index++) != '[')//usUnoName[index++] != '[') 173 break; 174 } 175 sUnoName = sUnoName->Substring(index - 1);//usUnoName = usUnoName.copy(index - 1); 176 } 177 if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoBool))) 178 buf->Append(const_cast<System::String*>(Constants::sBoolean)); 179 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoChar))) 180 buf->Append(const_cast<System::String*>(Constants::sChar)); 181 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoByte))) 182 buf->Append(const_cast<System::String*>(Constants::sByte)); 183 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoShort))) 184 buf->Append(const_cast<System::String*>(Constants::sInt16)); 185 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoUShort))) 186 buf->Append(const_cast<System::String*>(Constants::sUInt16)); 187 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoLong))) 188 buf->Append(const_cast<System::String*>(Constants::sInt32)); 189 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoULong))) 190 buf->Append(const_cast<System::String*>(Constants::sUInt32)); 191 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoHyper))) 192 buf->Append(const_cast<System::String*>(Constants::sInt64)); 193 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoUHyper))) 194 buf->Append(const_cast<System::String*>(Constants::sUInt64)); 195 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoFloat))) 196 buf->Append(const_cast<System::String*>(Constants::sSingle)); 197 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoDouble))) 198 buf->Append(const_cast<System::String*>(Constants::sDouble)); 199 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoString))) 200 buf->Append(const_cast<System::String*>(Constants::sString)); 201 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoVoid))) 202 buf->Append(const_cast<System::String*>(Constants::sVoid)); 203 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoType))) 204 buf->Append(const_cast<System::String*>(Constants::sType)); 205 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoXInterface))) 206 buf->Append(const_cast<System::String*>(Constants::sObject)); 207 else if (sUnoName->Equals(const_cast<System::String*>(Constants::sUnoAny))) 208 { 209 buf->Append(const_cast<System::String*>(Constants::sAny)); 210 } 211 else 212 { 213 //put "unoidl." at the beginning 214 buf->Append(const_cast<System::String*>(Constants::sUnoidl)); 215 buf->Append(mapUnoPolymorphicName(sUnoName)); 216 } 217 // apend [] 218 for (;dims--;) 219 buf->Append(const_cast<System::String*>(Constants::sBrackets)); 220 221 return buf->ToString(); 222 } 223 224 225 /** For example, there is a uno type 226 com.sun.star.Foo<char, long>. 227 The values in the type list 228 are uno types and are replaced by cli types, such as System.Char, 229 System.Int32, etc. 230 231 Strings can be as complicated as this 232 test.MyStruct<char,test.MyStruct<long, []string>> 233 */ 234 System::String* mapUnoPolymorphicName(System::String* unoName) 235 { 236 int index = unoName->IndexOf('<'); 237 if (index == -1) 238 return unoName; 239 240 System::Text::StringBuilder * builder = 241 new System::Text::StringBuilder(unoName->Substring(0, index +1 )); 242 243 //Find the first occurrence of ',' 244 //If the parameter is a polymorphic struct then we neede to ignore everything 245 //between the brackets because it can also contain commas 246 //get the type list within < and > 247 int endIndex = unoName->Length - 1; 248 index++; 249 int cur = index; 250 int countParams = 0; 251 while (cur <= endIndex) 252 { 253 System::Char c = unoName->Chars[cur]; 254 if (c == ',' || c == '>') 255 { 256 //insert a comma if needed 257 if (countParams != 0) 258 builder->Append(S","); 259 countParams++; 260 System::String * sParam = unoName->Substring(index, cur - index); 261 //skip the comma 262 cur++; 263 //the the index to the beginning of the next param 264 index = cur; 265 builder->Append(mapUnoTypeName(sParam)); 266 } 267 else if (c == '<') 268 { 269 cur++; 270 //continue until the matching '>' 271 int numNested = 0; 272 for (;;cur++) 273 { 274 System::Char curChar = unoName->Chars[cur]; 275 if (curChar == '<') 276 { 277 numNested ++; 278 } 279 else if (curChar == '>') 280 { 281 if (numNested > 0) 282 numNested--; 283 else 284 break; 285 } 286 } 287 } 288 cur++; 289 } 290 291 builder->Append((System::Char) '>'); 292 return builder->ToString(); 293 } 294 295 296 297 //______________________________________________________________________________ 298 Assembly * TypeEmitter::type_resolve( 299 ::System::Object *, ::System::ResolveEventArgs * args ) 300 { 301 ::System::String * cts_name = args->get_Name(); 302 ::System::Type * ret_type = m_module_builder->GetType( 303 cts_name, false /* no exc */ ); 304 if (0 == ret_type) 305 { 306 iface_entry * entry = dynamic_cast< iface_entry * >( 307 m_incomplete_ifaces->get_Item( cts_name ) ); 308 if (0 != entry) 309 ret_type = entry->m_type_builder; 310 } 311 if (0 == ret_type) 312 { 313 sal_Int32 len = m_extra_assemblies->get_Length(); 314 for ( sal_Int32 pos = 0; pos < len; ++pos ) 315 { 316 ret_type = m_extra_assemblies[ pos ]->GetType( 317 cts_name, false /* no exc */ ); 318 if (0 != ret_type) 319 { 320 if (g_verbose) 321 { 322 ::System::Console::WriteLine( 323 "> resolving type {0} from {1}.", 324 cts_name, ret_type->get_Assembly()->get_FullName() ); 325 } 326 break; 327 } 328 } 329 } 330 if (0 != ret_type) 331 return ret_type->get_Assembly(); 332 return 0; 333 } 334 335 //______________________________________________________________________________ 336 ::System::Type * TypeEmitter::get_type( 337 ::System::String * cts_name, bool throw_exc ) 338 { 339 ::System::Type * ret_type = m_module_builder->GetType( cts_name, false ); 340 //We get the type from the ModuleBuilder even if the type is not complete 341 //but have been defined. 342 //if (ret_type == 0) 343 //{ 344 // iface_entry * entry = dynamic_cast< iface_entry * >( 345 // m_incomplete_ifaces->get_Item( cts_name ) ); 346 // if (0 != entry) 347 // ret_type = entry->m_type_builder; 348 //} 349 //try the cli_basetypes assembly 350 if (ret_type == 0) 351 { 352 ::System::Text::StringBuilder * builder = new ::System::Text::StringBuilder(cts_name); 353 builder->Append(S",cli_basetypes"); 354 ret_type = ::System::Type::GetType(builder->ToString()); 355 } 356 357 if (ret_type == 0) 358 { 359 try 360 { 361 // may call on type_resolve() 362 return ::System::Type::GetType( cts_name, throw_exc ); 363 } 364 catch (::System::Exception* exc) 365 { 366 //If the type is not found one may have forgotten to specify assemblies with 367 //additional types 368 ::System::Text::StringBuilder * sb = new ::System::Text::StringBuilder(); 369 sb->Append(new ::System::String(S"\nThe type ")); 370 sb->Append(cts_name); 371 sb->Append(new ::System::String(S" \n could not be found. Did you forget to " \ 372 S"specify an additional assembly with the --reference option?\n")); 373 if (throw_exc) 374 throw new ::System::Exception(sb->ToString(), exc); 375 } 376 } 377 else 378 { 379 return ret_type; 380 } 381 } 382 383 //______________________________________________________________________________ 384 ::System::Type * TypeEmitter::get_type_Exception() 385 { 386 if (0 == m_type_Exception) 387 { 388 m_type_Exception = get_type( 389 S"unoidl.com.sun.star.uno.Exception", false /* no exc */ ); 390 if (0 == m_type_Exception) 391 { 392 // define hardcoded type unoidl.com.sun.star.uno.Exception 393 Emit::TypeBuilder * type_builder = 394 m_module_builder->DefineType( 395 S"unoidl.com.sun.star.uno.Exception", 396 (TypeAttributes) (TypeAttributes::Public | 397 TypeAttributes::BeforeFieldInit | 398 TypeAttributes::AnsiClass), 399 __typeof (::System::Exception) ); 400 Emit::FieldBuilder * field_Context = type_builder->DefineField( 401 S"Context", __typeof (::System::Object), 402 FieldAttributes::Public ); 403 // default .ctor 404 type_builder->DefineDefaultConstructor( c_ctor_method_attr ); 405 // .ctor 406 ::System::Type * param_types[] = 407 new ::System::Type *[ 2 ]; 408 param_types[ 0 ] = __typeof (::System::String); 409 param_types[ 1 ] = __typeof (::System::Object); 410 Emit::ConstructorBuilder * ctor_builder = 411 type_builder->DefineConstructor( 412 c_ctor_method_attr, CallingConventions::Standard, 413 param_types ); 414 ctor_builder->DefineParameter( 415 1, ParameterAttributes::In, S"Message" ); 416 ctor_builder->DefineParameter( 417 2, ParameterAttributes::In, S"Context" ); 418 Emit::ILGenerator * code = ctor_builder->GetILGenerator(); 419 code->Emit( Emit::OpCodes::Ldarg_0 ); 420 code->Emit( Emit::OpCodes::Ldarg_1 ); 421 param_types = new ::System::Type * [ 1 ]; 422 param_types[ 0 ] = __typeof (::System::String); 423 code->Emit( 424 Emit::OpCodes::Call, 425 __typeof (::System::Exception) 426 ->GetConstructor( param_types ) ); 427 code->Emit( Emit::OpCodes::Ldarg_0 ); 428 code->Emit( Emit::OpCodes::Ldarg_2 ); 429 code->Emit( Emit::OpCodes::Stfld, field_Context ); 430 code->Emit( Emit::OpCodes::Ret ); 431 432 if (g_verbose) 433 { 434 ::System::Console::WriteLine( 435 "> emitting exception type " 436 "unoidl.com.sun.star.uno.Exception" ); 437 } 438 m_type_Exception = type_builder->CreateType(); 439 } 440 } 441 return m_type_Exception; 442 } 443 444 //______________________________________________________________________________ 445 ::System::Type * TypeEmitter::get_type_RuntimeException() 446 { 447 if (0 == m_type_RuntimeException) 448 { 449 m_type_RuntimeException = get_type( 450 S"unoidl.com.sun.star.uno.RuntimeException", false /* no exc */ ); 451 if (0 == m_type_RuntimeException) 452 { 453 // define hardcoded type unoidl.com.sun.star.uno.RuntimeException 454 ::System::Type * type_Exception = get_type_Exception(); 455 Emit::TypeBuilder * type_builder = 456 m_module_builder->DefineType( 457 S"unoidl.com.sun.star.uno.RuntimeException", 458 (TypeAttributes) (TypeAttributes::Public | 459 TypeAttributes::BeforeFieldInit | 460 TypeAttributes::AnsiClass), 461 type_Exception ); 462 // default .ctor 463 type_builder->DefineDefaultConstructor( c_ctor_method_attr ); 464 // .ctor 465 ::System::Type * param_types [] = 466 new ::System::Type * [ 2 ]; 467 param_types[ 0 ] = __typeof (::System::String); 468 param_types[ 1 ] = __typeof (::System::Object); 469 Emit::ConstructorBuilder * ctor_builder = 470 type_builder->DefineConstructor( 471 c_ctor_method_attr, CallingConventions::Standard, 472 param_types ); 473 ctor_builder->DefineParameter( 474 1, ParameterAttributes::In, S"Message" ); 475 ctor_builder->DefineParameter( 476 2, ParameterAttributes::In, S"Context" ); 477 Emit::ILGenerator * code = ctor_builder->GetILGenerator(); 478 code->Emit( Emit::OpCodes::Ldarg_0 ); 479 code->Emit( Emit::OpCodes::Ldarg_1 ); 480 code->Emit( Emit::OpCodes::Ldarg_2 ); 481 code->Emit( 482 Emit::OpCodes::Call, 483 type_Exception->GetConstructor( param_types ) ); 484 code->Emit( Emit::OpCodes::Ret ); 485 486 if (g_verbose) 487 { 488 ::System::Console::WriteLine( 489 "> emitting exception type " 490 "unoidl.com.sun.star.uno.RuntimeException" ); 491 } 492 m_type_RuntimeException = type_builder->CreateType(); 493 } 494 } 495 return m_type_RuntimeException; 496 } 497 498 //______________________________________________________________________________ 499 ::System::Type * TypeEmitter::get_type( 500 Reference< reflection::XConstantTypeDescription > const & xType ) 501 { 502 ::System::String * cts_name = to_cts_name( xType->getName() ); 503 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 504 if (0 == ret_type) 505 { 506 Reference< reflection::XConstantTypeDescription > xConstant( 507 xType, UNO_QUERY_THROW ); 508 ::System::Object * constant = 509 to_cli_constant( xConstant->getConstantValue() ); 510 Emit::TypeBuilder * type_builder = 511 m_module_builder->DefineType( 512 cts_name, 513 (TypeAttributes) (TypeAttributes::Public | 514 TypeAttributes::Sealed | 515 TypeAttributes::BeforeFieldInit | 516 TypeAttributes::AnsiClass) ); 517 518 Emit::FieldBuilder * field_builder = type_builder->DefineField( 519 cts_name->Substring( cts_name->LastIndexOf( '.' ) +1 ), 520 constant->GetType(), 521 (FieldAttributes) (FieldAttributes::Public | 522 FieldAttributes::Static | 523 FieldAttributes::Literal) ); 524 field_builder->SetConstant( constant ); 525 526 if (g_verbose) 527 { 528 ::System::Console::WriteLine( 529 "> emitting constant type {0}", cts_name ); 530 } 531 ret_type = type_builder->CreateType(); 532 } 533 return ret_type; 534 } 535 536 //______________________________________________________________________________ 537 ::System::Type * TypeEmitter::get_type( 538 Reference< reflection::XConstantsTypeDescription > const & xType ) 539 { 540 ::System::String * cts_name = to_cts_name( xType->getName() ); 541 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 542 if (0 == ret_type) 543 { 544 Emit::TypeBuilder * type_builder = 545 m_module_builder->DefineType( 546 cts_name, 547 (TypeAttributes) (TypeAttributes::Public | 548 TypeAttributes::Sealed | 549 TypeAttributes::BeforeFieldInit | 550 TypeAttributes::AnsiClass) ); 551 552 Sequence< Reference< 553 reflection::XConstantTypeDescription > > seq_constants( 554 xType->getConstants() ); 555 Reference< reflection::XConstantTypeDescription > const * constants = 556 seq_constants.getConstArray(); 557 sal_Int32 constants_length = seq_constants.getLength(); 558 for ( sal_Int32 constants_pos = 0; 559 constants_pos < constants_length; ++constants_pos ) 560 { 561 Reference< 562 reflection::XConstantTypeDescription > const & xConstant = 563 constants[ constants_pos ]; 564 ::System::Object * constant = 565 to_cli_constant( xConstant->getConstantValue() ); 566 ::System::String * uno_name = 567 ustring_to_String( xConstant->getName() ); 568 Emit::FieldBuilder * field_builder = type_builder->DefineField( 569 uno_name->Substring( uno_name->LastIndexOf( '.' ) +1 ), 570 constant->GetType(), 571 (FieldAttributes) (FieldAttributes::Public | 572 FieldAttributes::Static | 573 FieldAttributes::Literal) ); 574 field_builder->SetConstant( constant ); 575 } 576 577 if (g_verbose) 578 { 579 ::System::Console::WriteLine( 580 "> emitting constants group type {0}", cts_name ); 581 } 582 ret_type = type_builder->CreateType(); 583 } 584 return ret_type; 585 } 586 587 //______________________________________________________________________________ 588 ::System::Type * TypeEmitter::get_type( 589 Reference< reflection::XEnumTypeDescription > const & xType ) 590 { 591 ::System::String * cts_name = to_cts_name( xType->getName() ); 592 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 593 if (0 == ret_type) 594 { 595 // Emit::EnumBuilder * enum_builder = 596 // m_module_builder->DefineEnum( 597 // cts_name, 598 // (TypeAttributes) (TypeAttributes::Public | 599 // // TypeAttributes::Sealed | 600 // TypeAttributes::AnsiClass), 601 // __typeof (::System::Int32) ); 602 // workaround enum builder bug 603 Emit::TypeBuilder * enum_builder = 604 m_module_builder->DefineType( 605 cts_name, 606 (TypeAttributes) (TypeAttributes::Public | 607 TypeAttributes::Sealed), 608 __typeof (::System::Enum) ); 609 enum_builder->DefineField( 610 S"value__", __typeof (::System::Int32), 611 (FieldAttributes) (FieldAttributes::Private | 612 FieldAttributes::SpecialName | 613 FieldAttributes::RTSpecialName) ); 614 Sequence< OUString > seq_enum_names( xType->getEnumNames() ); 615 Sequence< sal_Int32 > seq_enum_values( xType->getEnumValues() ); 616 sal_Int32 enum_length = seq_enum_names.getLength(); 617 OSL_ASSERT( enum_length == seq_enum_values.getLength() ); 618 OUString const * enum_names = seq_enum_names.getConstArray(); 619 sal_Int32 const * enum_values = seq_enum_values.getConstArray(); 620 for ( sal_Int32 enum_pos = 0; enum_pos < enum_length; ++enum_pos ) 621 { 622 // enum_builder->DefineLiteral( 623 // ustring_to_String( enum_names[ enum_pos ] ), 624 // __box ((::System::Int32) enum_values[ enum_pos ]) ); 625 Emit::FieldBuilder * field_builder = 626 enum_builder->DefineField( 627 ustring_to_String( enum_names[ enum_pos ] ), 628 enum_builder, 629 (FieldAttributes) (FieldAttributes::Public | 630 FieldAttributes::Static | 631 FieldAttributes::Literal) ); 632 field_builder->SetConstant( 633 __box ((::System::Int32) enum_values[ enum_pos ]) ); 634 } 635 636 if (g_verbose) 637 { 638 ::System::Console::WriteLine( 639 "> emitting enum type {0}", cts_name ); 640 } 641 ret_type = enum_builder->CreateType(); 642 } 643 return ret_type; 644 } 645 646 //______________________________________________________________________________ 647 ::System::Type * TypeEmitter::get_type( 648 Reference< reflection::XCompoundTypeDescription > const & xType ) 649 { 650 OUString uno_name( xType->getName() ); 651 if (TypeClass_EXCEPTION == xType->getTypeClass()) 652 { 653 if (uno_name.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( 654 "com.sun.star.uno.Exception") )) 655 { 656 return get_type_Exception(); 657 } 658 if (uno_name.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( 659 "com.sun.star.uno.RuntimeException") )) 660 { 661 return get_type_RuntimeException(); 662 } 663 } 664 ::System::String * cts_name = to_cts_name( uno_name ); 665 // if the struct is an instantiated polymorpic struct then we create the simple struct name 666 // For example: 667 // void func ([in] PolyStruct<boolean> arg); 668 //PolyStruct<boolean> will be converted to PolyStruct 669 polymorphicStructNameToStructName( & cts_name); 670 671 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 672 if (0 == ret_type) 673 { 674 Reference< reflection::XCompoundTypeDescription > xBaseType( 675 xType->getBaseType(), UNO_QUERY ); 676 ::System::Type * base_type = (xBaseType.is() 677 ? get_type( xBaseType ) 678 : __typeof (::System::Object)); 679 Emit::TypeBuilder * type_builder = 680 m_module_builder->DefineType( 681 cts_name, 682 (TypeAttributes) (TypeAttributes::Public | 683 TypeAttributes::BeforeFieldInit | 684 TypeAttributes::AnsiClass), 685 base_type ); 686 687 688 // insert to be completed 689 struct_entry * entry = new struct_entry(); 690 xType->acquire(); 691 entry->m_xType = xType.get(); 692 entry->m_type_builder = type_builder; 693 entry->m_base_type = base_type; 694 m_incomplete_structs->Add( cts_name, entry ); 695 696 // type is incomplete 697 ret_type = type_builder; 698 } 699 700 //In case of an instantiated polymorphic struct we want to return a 701 //uno.PolymorphicType (inherits Type) rather then Type. This is neaded for constructing 702 //the service code. We can only do that if the struct is completed. 703 if (m_generated_structs->get_Item(cts_name)) 704 { 705 Reference< reflection::XStructTypeDescription> xStructTypeDesc( 706 xType, UNO_QUERY); 707 708 if (xStructTypeDesc.is()) 709 { 710 Sequence< Reference< reflection::XTypeDescription > > seqTypeArgs = xStructTypeDesc->getTypeArguments(); 711 sal_Int32 numTypes = seqTypeArgs.getLength(); 712 if (numTypes > 0) 713 { 714 //it is an instantiated polymorphic struct 715 ::System::String * sCliName = mapUnoTypeName(ustring_to_String(xType->getName())); 716 ret_type = ::uno::PolymorphicType::GetType(ret_type, sCliName); 717 } 718 } 719 } 720 return ret_type; 721 } 722 723 //______________________________________________________________________________ 724 ::System::Type * TypeEmitter::get_type( 725 Reference< reflection::XInterfaceTypeDescription2 > const & xType ) 726 { 727 OUString uno_name( xType->getName() ); 728 if (uno_name.equalsAsciiL( 729 RTL_CONSTASCII_STRINGPARAM("com.sun.star.uno.XInterface") )) 730 { 731 return __typeof (::System::Object); 732 } 733 734 ::System::String * cts_name = to_cts_name( xType->getName() ); 735 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 736 if (0 == ret_type) 737 { 738 Emit::TypeBuilder * type_builder; 739 740 TypeAttributes attr = (TypeAttributes) (TypeAttributes::Public | 741 TypeAttributes::Interface | 742 TypeAttributes::Abstract | 743 TypeAttributes::AnsiClass); 744 745 std::vector<Reference<reflection::XInterfaceTypeDescription2> > vecBaseTypes; 746 Sequence<Reference< reflection::XTypeDescription > > seqBaseTypes = 747 xType->getBaseTypes(); 748 if (seqBaseTypes.getLength() > 0) 749 { 750 for (int i = 0; i < seqBaseTypes.getLength(); i++) 751 { 752 Reference<reflection::XInterfaceTypeDescription2> xIfaceTd = 753 resolveInterfaceTypedef(seqBaseTypes[i]); 754 755 if (xIfaceTd->getName().equalsAsciiL( 756 RTL_CONSTASCII_STRINGPARAM("com.sun.star.uno.XInterface") ) == sal_False) 757 { 758 vecBaseTypes.push_back(xIfaceTd); 759 } 760 } 761 762 ::System::Type * base_interfaces [] = 763 new ::System::Type * [ vecBaseTypes.size() ]; 764 765 typedef std::vector<Reference<reflection::XInterfaceTypeDescription2> >::const_iterator it; 766 int index = 0; 767 for (it i = vecBaseTypes.begin(); i != vecBaseTypes.end(); i++, index++) 768 base_interfaces[ index ] = get_type( *i ); 769 type_builder = m_module_builder->DefineType( 770 cts_name, attr, 0, base_interfaces ); 771 } 772 else 773 { 774 ::System::Console::WriteLine( 775 "warning: IDL interface {0} is not derived from " 776 "com.sun.star.uno.XInterface!", 777 ustring_to_String( uno_name ) ); 778 779 type_builder = m_module_builder->DefineType( cts_name, attr ); 780 } 781 782 // insert to be completed 783 iface_entry * entry = new iface_entry(); 784 xType->acquire(); 785 entry->m_xType = xType.get(); 786 entry->m_type_builder = type_builder; 787 m_incomplete_ifaces->Add( cts_name, entry ); 788 789 // type is incomplete 790 ret_type = type_builder; 791 } 792 return ret_type; 793 } 794 795 796 //______________________________________________________________________________ 797 ::System::Type * TypeEmitter::get_type( 798 Reference< reflection::XServiceTypeDescription2 > const & xType ) 799 { 800 if (xType->isSingleInterfaceBased() == sal_False) 801 return NULL; 802 803 System::String * cts_name = to_cts_name( xType->getName() ); 804 System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 805 if (ret_type != NULL) 806 return ret_type; 807 808 TypeAttributes attr = (TypeAttributes) (TypeAttributes::Public | 809 TypeAttributes::Sealed | 810 TypeAttributes::BeforeFieldInit | 811 TypeAttributes::AnsiClass); 812 813 Emit::TypeBuilder * type_builder = m_module_builder->DefineType( 814 cts_name, attr); 815 816 // insert to be completed 817 service_entry * entry = new service_entry(); 818 xType->acquire(); 819 entry->m_xType = xType.get(); 820 entry->m_type_builder = type_builder; 821 m_incomplete_services->Add(cts_name,entry ); 822 823 return type_builder; 824 } 825 826 ::System::Type * TypeEmitter::get_type( 827 Reference<reflection::XSingletonTypeDescription2 > const & xType ) 828 { 829 if (xType->isInterfaceBased() == sal_False) 830 return NULL; 831 832 ::System::String* cts_name = to_cts_name( xType->getName() ); 833 ::System::Type * ret_type = get_type( cts_name, false /* no exc */ ); 834 if (ret_type != NULL) 835 return ret_type; 836 837 TypeAttributes attr = static_cast<TypeAttributes>( 838 TypeAttributes::Public | 839 TypeAttributes::Sealed | 840 TypeAttributes::BeforeFieldInit | 841 TypeAttributes::AnsiClass); 842 843 Emit::TypeBuilder * type_builder = m_module_builder->DefineType( 844 cts_name, attr); 845 846 // insert to be completed 847 singleton_entry * entry = new singleton_entry(); 848 xType->acquire(); 849 entry->m_xType = xType.get(); 850 entry->m_type_builder = type_builder; 851 m_incomplete_singletons->Add(cts_name,entry ); 852 853 return type_builder; 854 855 } 856 857 //______________________________________________________________________________ 858 ::System::Type * TypeEmitter::complete_iface_type( iface_entry * entry ) 859 { 860 Emit::TypeBuilder * type_builder = entry->m_type_builder; 861 reflection::XInterfaceTypeDescription2 * xType = entry->m_xType; 862 863 Sequence<Reference< reflection::XTypeDescription > > seqBaseTypes( xType->getBaseTypes() ); 864 if (seqBaseTypes.getLength() > 0) 865 { 866 for (int i = 0; i < seqBaseTypes.getLength(); i++) 867 { 868 //make sure we get the interface rather then a typedef 869 Reference<reflection::XInterfaceTypeDescription2> aBaseType = 870 resolveInterfaceTypedef( seqBaseTypes[i]); 871 872 if (aBaseType->getName().equalsAsciiL( 873 RTL_CONSTASCII_STRINGPARAM("com.sun.star.uno.XInterface") ) == sal_False) 874 { 875 ::System::String * basetype_name = to_cts_name( aBaseType->getName() ); 876 iface_entry * base_entry = dynamic_cast< iface_entry * >( 877 m_incomplete_ifaces->get_Item( basetype_name ) ); 878 if (0 != base_entry) 879 { 880 // complete uncompleted base type first 881 complete_iface_type( base_entry ); 882 } 883 } 884 } 885 } 886 887 Sequence< 888 Reference< reflection::XInterfaceMemberTypeDescription > > seq_members( 889 xType->getMembers() ); 890 Reference< reflection::XInterfaceMemberTypeDescription > const * members = 891 seq_members.getConstArray(); 892 sal_Int32 members_length = seq_members.getLength(); 893 for ( sal_Int32 members_pos = 0; 894 members_pos < members_length; ++members_pos ) 895 { 896 Reference< 897 reflection::XInterfaceMemberTypeDescription > const & xMember = 898 members[ members_pos ]; 899 Sequence< Reference< reflection::XTypeDescription > > seq_exceptions; 900 Emit::MethodBuilder * method_builder; 901 902 const MethodAttributes c_method_attr = (MethodAttributes) 903 (MethodAttributes::Public | 904 MethodAttributes::Abstract | 905 MethodAttributes::Virtual | 906 MethodAttributes::NewSlot | 907 MethodAttributes::HideBySig); 908 //#if defined(_MSC_VER) && (_MSC_VER < 1400) 909 // MethodAttributes::Instance); 910 //#else 911 // Instance); 912 //#endif 913 914 if (TypeClass_INTERFACE_METHOD == xMember->getTypeClass()) 915 { 916 Reference< reflection::XInterfaceMethodTypeDescription > xMethod( 917 xMember, UNO_QUERY_THROW ); 918 919 Sequence< 920 Reference< reflection::XMethodParameter > > seq_parameters( 921 xMethod->getParameters() ); 922 sal_Int32 params_length = seq_parameters.getLength(); 923 ::System::Type * param_types [] = 924 new ::System::Type * [ params_length ]; 925 Reference< reflection::XMethodParameter > const * parameters = 926 seq_parameters.getConstArray(); 927 // first determine all types 928 //Make the first param type as return type 929 sal_Int32 params_pos = 0; 930 for ( ; params_pos < params_length; ++params_pos ) 931 { 932 Reference< reflection::XMethodParameter > const & xParam = 933 parameters[ params_pos ]; 934 ::System::Type * param_type = get_type( xParam->getType() ); 935 ::System::String * param_type_name = param_type->get_FullName(); 936 if (xParam->isOut()) 937 { 938 param_type = get_type( 939 ::System::String::Concat( 940 param_type_name, S"&" ), true ); 941 } 942 param_types[ xParam->getPosition() ] = param_type; 943 } 944 945 946 // create method 947 // if (tb) 948 // method_builder = type_builder->DefineMethod( 949 // ustring_to_String( xMethod->getMemberName() ), 950 // c_method_attr, tb, 951 // param_types ); 952 // else 953 method_builder = type_builder->DefineMethod( 954 ustring_to_String( xMethod->getMemberName() ), 955 c_method_attr, get_type( xMethod->getReturnType() ), 956 param_types ); 957 // then define parameter infos 958 params_pos = 0; 959 for ( ; params_pos < params_length; ++params_pos ) 960 { 961 Reference< reflection::XMethodParameter > const & xParam = 962 parameters[ params_pos ]; 963 long param_flags = 0; 964 if (xParam->isIn()) 965 param_flags |= ParameterAttributes::In; 966 if (xParam->isOut()) 967 param_flags |= ParameterAttributes::Out; 968 OSL_ASSERT( 0 != param_flags ); 969 method_builder->DefineParameter( 970 xParam->getPosition() +1 /* starts with 1 */, 971 (ParameterAttributes) param_flags, 972 ustring_to_String( xParam->getName() ) ); 973 } 974 //Apply attribute TypeParametersAttribute to return value if it 975 //is a parameterized Type. Currently only structs can have parameters. 976 Reference<reflection::XStructTypeDescription> xReturnStruct( 977 xMethod->getReturnType(), UNO_QUERY); 978 979 if (xReturnStruct.is()) 980 { 981 Sequence<Reference<reflection::XTypeDescription> > seq_type_args = 982 xReturnStruct->getTypeArguments(); 983 if (seq_type_args.getLength() != 0) 984 { 985 //get th ctor of the attribute 986 ::System::Type * arCtor[] = {::System::Type::GetType(S"System.Type[]")}; 987 //Get the arguments for the attribute's ctor 988 Reference<reflection::XTypeDescription> const * arXTypeArgs = 989 seq_type_args.getConstArray(); 990 int numTypes = seq_type_args.getLength(); 991 ::System::Type * arCtsTypes[] = new ::System::Type*[numTypes]; 992 for (int i = 0; i < numTypes; i++) 993 arCtsTypes[i] = get_type(arXTypeArgs[i]); 994 ::System::Object * arArgs[] = {arCtsTypes}; 995 996 Emit::CustomAttributeBuilder * attrBuilder = 997 new Emit::CustomAttributeBuilder( 998 __typeof(::uno::TypeArgumentsAttribute) 999 ->GetConstructor( arCtor), 1000 arArgs); 1001 1002 method_builder->SetCustomAttribute(attrBuilder); 1003 } 1004 } 1005 1006 //define UNO exception attribute (exceptions)-------------------------------------- 1007 Emit::CustomAttributeBuilder* attrBuilder = 1008 get_iface_method_exception_attribute(xMethod); 1009 if (attrBuilder != NULL) 1010 method_builder->SetCustomAttribute(attrBuilder); 1011 1012 // oneway attribute 1013 if (xMethod->isOneway()) 1014 { 1015 ::System::Type * arCtorOneway[] = new ::System::Type*[0]; 1016 ::System::Object * arArgs[] = new ::System::Object*[0]; 1017 Emit::CustomAttributeBuilder * attrBuilder = 1018 new Emit::CustomAttributeBuilder( 1019 __typeof(::uno::OnewayAttribute)->GetConstructor( arCtorOneway), 1020 arArgs); 1021 method_builder->SetCustomAttribute(attrBuilder); 1022 } 1023 } 1024 else // attribute 1025 { 1026 OSL_ASSERT( 1027 TypeClass_INTERFACE_ATTRIBUTE == xMember->getTypeClass() ); 1028 Reference< 1029 reflection::XInterfaceAttributeTypeDescription2 > xAttribute( 1030 xMember, UNO_QUERY_THROW ); 1031 1032 const MethodAttributes c_property_method_attr = (MethodAttributes) 1033 (c_method_attr | MethodAttributes::SpecialName); 1034 1035 ::System::Type * attribute_type = get_type( xAttribute->getType() ); 1036 ::System::Type * parameters [] = 1037 new ::System::Type * [ 0 ]; 1038 1039 Emit::PropertyBuilder * property_builder = 1040 type_builder->DefineProperty( 1041 ustring_to_String( xAttribute->getMemberName() ), 1042 PropertyAttributes::None, 1043 attribute_type, parameters ); 1044 1045 //set BoundAttribute, if necessary 1046 if (xAttribute->isBound()) 1047 { 1048 ConstructorInfo * ctorBoundAttr = 1049 __typeof(::uno::BoundAttribute)->GetConstructor( 1050 new System::Type*[0]); 1051 Emit::CustomAttributeBuilder * attrBuilderBound = 1052 new Emit::CustomAttributeBuilder( 1053 ctorBoundAttr, new ::System::Object*[0]); 1054 property_builder->SetCustomAttribute(attrBuilderBound); 1055 } 1056 1057 // getter 1058 Emit::MethodBuilder * method_builder = 1059 type_builder->DefineMethod( 1060 ustring_to_String( OUSTR("get_") + 1061 xAttribute->getMemberName() ), 1062 c_property_method_attr, attribute_type, parameters ); 1063 1064 //define UNO exception attribute (exceptions)-------------------------------------- 1065 Emit::CustomAttributeBuilder* attrBuilder = 1066 get_exception_attribute(xAttribute->getGetExceptions()); 1067 if (attrBuilder != NULL) 1068 method_builder->SetCustomAttribute(attrBuilder); 1069 1070 property_builder->SetGetMethod( method_builder ); 1071 1072 if (! xAttribute->isReadOnly()) 1073 { 1074 // setter 1075 parameters = new ::System::Type * [ 1 ]; 1076 parameters[ 0 ] = attribute_type; 1077 method_builder = 1078 type_builder->DefineMethod( 1079 ustring_to_String( OUSTR("set_") + 1080 xAttribute->getMemberName() ), 1081 c_property_method_attr, 0, parameters ); 1082 // define parameter info 1083 method_builder->DefineParameter( 1084 1 /* starts with 1 */, ParameterAttributes::In, S"value" ); 1085 //define UNO exception attribute (exceptions)-------------------------------------- 1086 Emit::CustomAttributeBuilder* attrBuilder = 1087 get_exception_attribute(xAttribute->getSetExceptions()); 1088 if (attrBuilder != NULL) 1089 method_builder->SetCustomAttribute(attrBuilder); 1090 1091 property_builder->SetSetMethod( method_builder ); 1092 } 1093 } 1094 } 1095 1096 // remove from incomplete types map 1097 ::System::String * cts_name = type_builder->get_FullName(); 1098 m_incomplete_ifaces->Remove( cts_name ); 1099 xType->release(); 1100 1101 if (g_verbose) 1102 { 1103 ::System::Console::WriteLine( 1104 "> emitting interface type {0}", cts_name ); 1105 } 1106 return type_builder->CreateType(); 1107 } 1108 1109 ::System::Type * TypeEmitter::complete_struct_type( struct_entry * entry ) 1110 { 1111 OSL_ASSERT(entry); 1112 ::System::String * cts_name = entry->m_type_builder->get_FullName(); 1113 1114 //Polymorphic struct, define uno.TypeParametersAttribute 1115 //A polymorphic struct cannot have a basetype. 1116 //When we create the template of the struct then we have no exact types 1117 //and the name does not contain a parameter list 1118 Sequence< OUString > seq_type_parameters; 1119 Reference< reflection::XStructTypeDescription> xStructTypeDesc( 1120 entry->m_xType, UNO_QUERY); 1121 if (xStructTypeDesc.is()) 1122 { 1123 seq_type_parameters = xStructTypeDesc->getTypeParameters(); 1124 int numTypes = 0; 1125 if ((numTypes = seq_type_parameters.getLength()) > 0) 1126 { 1127 ::System::Object * aArg[] = new ::System::Object*[numTypes]; 1128 for (int i = 0; i < numTypes; i++) 1129 aArg[i] = ustring_to_String(seq_type_parameters.getConstArray()[i]); 1130 ::System::Object * args[] = {aArg}; 1131 1132 ::System::Type * arTypesCtor[] = 1133 {::System::Type::GetType(S"System.String[]")}; 1134 Emit::CustomAttributeBuilder * attrBuilder = 1135 new Emit::CustomAttributeBuilder( 1136 __typeof(::uno::TypeParametersAttribute)->GetConstructor(arTypesCtor), 1137 args); 1138 entry->m_type_builder->SetCustomAttribute(attrBuilder); 1139 } 1140 } 1141 1142 // optional: lookup base type whether generated entry of this session 1143 struct_entry * base_type_entry = 0; 1144 if (0 != entry->m_base_type) 1145 { 1146 //ToDo maybe get from incomplete structs 1147 base_type_entry = 1148 dynamic_cast< struct_entry * >( 1149 m_generated_structs->get_Item( 1150 entry->m_base_type->get_FullName() ) ); 1151 } 1152 1153 // members 1154 Sequence< Reference< reflection::XTypeDescription > > seq_members( 1155 entry->m_xType->getMemberTypes() ); 1156 Sequence< OUString > seq_member_names( entry->m_xType->getMemberNames() ); 1157 sal_Int32 members_length = seq_members.getLength(); 1158 OSL_ASSERT( seq_member_names.getLength() == members_length ); 1159 //check if we have a XTypeDescription for every member. If not then the user may 1160 //have forgotten to specify additional rdbs with the --extra option. 1161 Reference< reflection::XTypeDescription > const * pseq_members = 1162 seq_members.getConstArray(); 1163 OUString const * pseq_member_names = 1164 seq_member_names.getConstArray(); 1165 for (int i = 0; i < members_length; i++) 1166 { 1167 const OUString sType(entry->m_xType->getName()); 1168 const OUString sMemberName(pseq_member_names[i]); 1169 if ( ! pseq_members[i].is()) 1170 throw RuntimeException(OUSTR("Missing type description . Check if you need to " \ 1171 "specify additional RDBs with the --extra option. Type missing for: ") + sType + 1172 OUSTR("::") + sMemberName,0); 1173 } 1174 1175 sal_Int32 all_members_length = 0; 1176 sal_Int32 member_pos; 1177 sal_Int32 type_param_pos = 0; 1178 1179 // collect base types; wrong order 1180 ::System::Collections::ArrayList * base_types_list = 1181 new ::System::Collections::ArrayList( 3 /* initial capacity */ ); 1182 for (::System::Type * base_type_pos = entry->m_base_type; 1183 ! base_type_pos->Equals( __typeof (::System::Object) ); 1184 base_type_pos = base_type_pos->get_BaseType() ) 1185 { 1186 base_types_list->Add( base_type_pos ); 1187 if (base_type_pos->Equals( __typeof (::System::Exception) )) 1188 { 1189 // special Message member 1190 all_members_length += 1; 1191 break; // don't include System.Exception base classes 1192 } 1193 else 1194 { 1195 //ensure the base type is complete. Otherwise GetFields won't work 1196 get_complete_struct(base_type_pos->get_FullName()); 1197 all_members_length += 1198 base_type_pos->GetFields( 1199 (BindingFlags) (BindingFlags::Instance | 1200 BindingFlags::Public | 1201 BindingFlags::DeclaredOnly) ) 1202 ->get_Length(); 1203 } 1204 } 1205 1206 // create all_members arrays; right order 1207 ::System::String * all_member_names[] = 1208 new ::System::String * [all_members_length + members_length ]; 1209 ::System::Type * all_param_types[] = 1210 new ::System::Type * [all_members_length + members_length ]; 1211 member_pos = 0; 1212 for ( sal_Int32 pos = base_types_list->get_Count(); pos--; ) 1213 { 1214 ::System::Type * base_type = __try_cast< ::System::Type * >( 1215 base_types_list->get_Item( pos ) ); 1216 if (base_type->Equals( __typeof (::System::Exception) )) 1217 { 1218 all_member_names[ member_pos ] = S"Message"; 1219 all_param_types[ member_pos ] = __typeof (::System::String); 1220 ++member_pos; 1221 } 1222 else 1223 { 1224 ::System::String * base_type_name = base_type->get_FullName(); 1225 1226 //ToDo m_generated_structs? 1227 struct_entry * entry = 1228 dynamic_cast< struct_entry * >( 1229 m_generated_structs->get_Item( base_type_name ) ); 1230 if (0 == entry) 1231 { 1232 // complete type 1233 FieldInfo * fields [] = 1234 base_type->GetFields( 1235 (BindingFlags) (BindingFlags::Instance | 1236 BindingFlags::Public | 1237 BindingFlags::DeclaredOnly) ); 1238 sal_Int32 len = fields->get_Length(); 1239 for ( sal_Int32 pos = 0; pos < len; ++pos ) 1240 { 1241 FieldInfo * field = fields[ pos ]; 1242 all_member_names[ member_pos ] = field->get_Name(); 1243 all_param_types[ member_pos ] = field->get_FieldType(); 1244 ++member_pos; 1245 } 1246 } 1247 else // generated during this session: 1248 // members may be incomplete ifaces 1249 { 1250 sal_Int32 len = entry->m_member_names->get_Length(); 1251 for ( sal_Int32 pos = 0; pos < len; ++pos ) 1252 { 1253 all_member_names[ member_pos ] = 1254 entry->m_member_names[ pos ]; 1255 all_param_types[ member_pos ] = 1256 entry->m_param_types[ pos ]; 1257 ++member_pos; 1258 } 1259 } 1260 } 1261 } 1262 OSL_ASSERT( all_members_length == member_pos ); 1263 1264 // build up entry 1265 // struct_entry * entry = new struct_entry(); 1266 entry->m_member_names = new ::System::String * [ members_length ]; 1267 entry->m_param_types = new ::System::Type * [ members_length ]; 1268 1269 // add members 1270 Emit::FieldBuilder * members[] = new Emit::FieldBuilder * [ members_length ]; 1271 //Reference< reflection::XTypeDescription > const * pseq_members = 1272 // seq_members.getConstArray(); 1273 //OUString const * pseq_member_names = 1274 // seq_member_names.getConstArray(); 1275 1276 int curParamIndex = 0; //count the fields which have parameterized types 1277 for ( member_pos = 0; member_pos < members_length; ++member_pos ) 1278 { 1279 ::System::String * field_name = 1280 ustring_to_String( pseq_member_names[ member_pos ] ); 1281 ::System::Type * field_type; 1282 //Special handling of struct parameter types 1283 bool bParameterizedType = false; 1284 if (pseq_members[ member_pos ]->getTypeClass() == TypeClass_UNKNOWN) 1285 { 1286 bParameterizedType = true; 1287 if (type_param_pos < seq_type_parameters.getLength()) 1288 { 1289 field_type = __typeof(::System::Object); 1290 type_param_pos++; 1291 } 1292 else 1293 { 1294 throw RuntimeException( 1295 OUSTR("unexpected member type in ") + entry->m_xType->getName(), 1296 Reference< XInterface >() ); 1297 } 1298 } 1299 else 1300 { 1301 field_type = 1302 get_type( pseq_members[ member_pos ] ); 1303 } 1304 members[ member_pos ] = 1305 entry->m_type_builder->DefineField( 1306 field_name, field_type, FieldAttributes::Public ); 1307 1308 //parameterized type (polymorphic struct) ? 1309 if (bParameterizedType && xStructTypeDesc.is()) 1310 { 1311 //get the name 1312 OSL_ASSERT(seq_type_parameters.getLength() > curParamIndex); 1313 ::System::String* sTypeName = ustring_to_String( 1314 seq_type_parameters.getConstArray()[curParamIndex++]); 1315 ::System::Object * args[] = {sTypeName}; 1316 //set ParameterizedTypeAttribute 1317 ::System::Type * arCtorTypes[] = {__typeof(::System::String)}; 1318 1319 Emit::CustomAttributeBuilder * attrBuilder = 1320 new Emit::CustomAttributeBuilder( 1321 __typeof(::uno::ParameterizedTypeAttribute) 1322 ->GetConstructor(arCtorTypes), 1323 args); 1324 1325 members[member_pos]->SetCustomAttribute(attrBuilder); 1326 } 1327 // add to all_members 1328 all_member_names[ all_members_length + member_pos ] = field_name; 1329 all_param_types[ all_members_length + member_pos ] = field_type; 1330 // add to entry 1331 entry->m_member_names[ member_pos ] = field_name; 1332 entry->m_param_types[ member_pos ] = field_type; 1333 } 1334 all_members_length += members_length; 1335 1336 // default .ctor 1337 Emit::ConstructorBuilder * ctor_builder = 1338 entry->m_type_builder->DefineConstructor( 1339 c_ctor_method_attr, CallingConventions::Standard, 1340 new ::System::Type * [ 0 ] ); 1341 Emit::ILGenerator * code = ctor_builder->GetILGenerator(); 1342 code->Emit( Emit::OpCodes::Ldarg_0 ); 1343 code->Emit( 1344 Emit::OpCodes::Call, 1345 0 == base_type_entry 1346 ? entry->m_base_type->GetConstructor( new ::System::Type * [ 0 ] ) 1347 : base_type_entry->m_default_ctor ); 1348 // default initialize members 1349 for ( member_pos = 0; member_pos < members_length; ++member_pos ) 1350 { 1351 FieldInfo * field = members[ member_pos ]; 1352 ::System::Type * field_type = field->get_FieldType(); 1353 // ::System::Type * new_field_type = m_module_builder->GetType(field_type->FullName, false); 1354 // default initialize: 1355 // string, type, enum, sequence, struct, exception, any 1356 if (field_type->Equals( __typeof (::System::String) )) 1357 { 1358 code->Emit( Emit::OpCodes::Ldarg_0 ); 1359 code->Emit( Emit::OpCodes::Ldstr, S"" ); 1360 code->Emit( Emit::OpCodes::Stfld, field ); 1361 } 1362 else if (field_type->Equals( __typeof (::System::Type) )) 1363 { 1364 code->Emit( Emit::OpCodes::Ldarg_0 ); 1365 code->Emit( 1366 Emit::OpCodes::Ldtoken, __typeof (::System::Void) ); 1367 code->Emit( 1368 Emit::OpCodes::Call, m_method_info_Type_GetTypeFromHandle ); 1369 code->Emit( Emit::OpCodes::Stfld, field ); 1370 } 1371 else if (field_type->get_IsArray()) 1372 { 1373 //Find the value type. In case of sequence<sequence< ... > > find the actual value type 1374 ::System::Type * value = field_type; 1375 while ((value = value->GetElementType())->get_IsArray()); 1376 //If the value type is a struct then make sure it is fully created. 1377 get_complete_struct(value->get_FullName()); 1378 1379 code->Emit( Emit::OpCodes::Ldarg_0 ); 1380 code->Emit( Emit::OpCodes::Ldc_I4_0 ); 1381 code->Emit( 1382 Emit::OpCodes::Newarr, field_type->GetElementType() ); 1383 code->Emit( Emit::OpCodes::Stfld, field ); 1384 } 1385 else if (field_type->get_IsValueType()) 1386 { 1387 if (field_type->get_FullName()->Equals( S"uno.Any" )) 1388 { 1389 code->Emit( Emit::OpCodes::Ldarg_0 ); 1390 code->Emit( Emit::OpCodes::Ldsfld, __typeof(::uno::Any)->GetField(S"VOID")); 1391 code->Emit( Emit::OpCodes::Stfld, field ); 1392 } 1393 } 1394 else if (field_type->get_IsClass()) 1395 { 1396 /* may be XInterface */ 1397 if (! field_type->Equals( __typeof (::System::Object) )) 1398 { 1399 // struct, exception 1400 //make sure the struct is already complete. 1401 get_complete_struct(field_type->get_FullName()); 1402 code->Emit( Emit::OpCodes::Ldarg_0 ); 1403 code->Emit( 1404 Emit::OpCodes::Newobj, 1405 //GetConstructor requies that the member types of the object which is to be constructed are already known. 1406 field_type->GetConstructor( 1407 new ::System::Type * [ 0 ] ) ); 1408 code->Emit( Emit::OpCodes::Stfld, field ); 1409 } 1410 } 1411 } 1412 code->Emit( Emit::OpCodes::Ret ); 1413 entry->m_default_ctor = ctor_builder; 1414 1415 // parameterized .ctor including all base members 1416 ctor_builder = entry->m_type_builder->DefineConstructor( 1417 c_ctor_method_attr, CallingConventions::Standard, all_param_types ); 1418 for ( member_pos = 0; member_pos < all_members_length; ++member_pos ) 1419 { 1420 ctor_builder->DefineParameter( 1421 member_pos +1 /* starts with 1 */, ParameterAttributes::In, 1422 all_member_names[ member_pos ] ); 1423 } 1424 code = ctor_builder->GetILGenerator(); 1425 // call base .ctor 1426 code->Emit( Emit::OpCodes::Ldarg_0 ); // push this 1427 sal_Int32 base_members_length = all_members_length - members_length; 1428 ::System::Type * param_types [] = 1429 new ::System::Type * [ base_members_length ]; 1430 for ( member_pos = 0; member_pos < base_members_length; ++member_pos ) 1431 { 1432 emit_ldarg( code, member_pos +1 ); 1433 param_types[ member_pos ] = all_param_types[ member_pos ]; 1434 } 1435 code->Emit( 1436 Emit::OpCodes::Call, 1437 0 == base_type_entry 1438 ? entry->m_base_type->GetConstructor( param_types ) 1439 : base_type_entry->m_ctor ); 1440 // initialize members 1441 for ( member_pos = 0; member_pos < members_length; ++member_pos ) 1442 { 1443 code->Emit( Emit::OpCodes::Ldarg_0 ); // push this 1444 emit_ldarg( code, member_pos + base_members_length +1 ); 1445 code->Emit( Emit::OpCodes::Stfld, members[ member_pos ] ); 1446 } 1447 code->Emit( Emit::OpCodes::Ret ); 1448 entry->m_ctor = ctor_builder; 1449 1450 if (g_verbose) 1451 { 1452 ::System::Console::WriteLine( 1453 "> emitting {0} type {1}", 1454 TypeClass_STRUCT == entry->m_xType->getTypeClass() 1455 ? S"struct" 1456 : S"exception", 1457 cts_name); 1458 } 1459 // new entry 1460 m_generated_structs->Add(cts_name, entry ); 1461 ::System::Type * ret_type = entry->m_type_builder->CreateType(); 1462 1463 // remove from incomplete types map 1464 m_incomplete_structs->Remove( cts_name ); 1465 entry->m_xType->release(); 1466 1467 if (g_verbose) 1468 { 1469 ::System::Console::WriteLine( 1470 "> emitting struct type {0}", cts_name); 1471 } 1472 return ret_type; 1473 } 1474 1475 //Examples of generated code 1476 // public static XWeak constructor1(XComponentContext ctx) 1477 // { 1478 // XMultiComponentFactory factory = ctx.getServiceManager(); 1479 // if (factory == null) 1480 // throw new com.sun.star.uno.DeploymentException("bla", null); 1481 // return (XWeak) factory.createInstanceWithContext("service_specifier", ctx); 1482 // } 1483 // public static XWeak constructor2(XComponentContext ctx, int a, int b, Any c) 1484 // { 1485 // XMultiComponentFactory factory = ctx.getServiceManager(); 1486 // if (factory == null) 1487 // throw new com.sun.star.uno.DeploymentException("bla", null); 1488 // Any[] arAny = new Any[3]; 1489 // arAny[0] = new Any(typeof(int), a); 1490 // arAny[1] = new Any(typeof(int), b); 1491 // arAny[2] = new Any(c.Type, c.Value); 1492 // return (XWeak) factory.createInstanceWithArgumentsAndContext("service_specifier", arAny, ctx); 1493 // } 1494 // Notice that a any parameter is NOT wrapped by another any. Instead the new any is created with the type and value 1495 // of the parameter. 1496 1497 // public static XWeak constructor3(XComponentContext ctx, params Any[] c) 1498 // { 1499 // XMultiComponentFactory factory = ctx.getServiceManager(); 1500 // if (factory == null) 1501 // throw new com.sun.star.uno.DeploymentException("bla", null); 1502 // return (XWeak) factory.createInstanceWithArgumentsAndContext("service_specifier", c, ctx); 1503 // } 1504 ::System::Type * TypeEmitter::complete_service_type(service_entry * entry) 1505 { 1506 Emit::TypeBuilder * type_builder = entry->m_type_builder; 1507 reflection::XServiceTypeDescription2 * xServiceType = entry->m_xType; 1508 1509 //Create the private default constructor 1510 Emit::ConstructorBuilder* ctor_builder = 1511 type_builder->DefineConstructor( 1512 (MethodAttributes) (MethodAttributes::Private | 1513 MethodAttributes::HideBySig | 1514 MethodAttributes::SpecialName | 1515 MethodAttributes::RTSpecialName), 1516 CallingConventions::Standard, NULL); 1517 1518 Emit::ILGenerator* ilGen = ctor_builder->GetILGenerator(); 1519 ilGen->Emit( Emit::OpCodes::Ldarg_0 ); // push this 1520 ilGen->Emit( 1521 Emit::OpCodes::Call, 1522 type_builder->BaseType->GetConstructor(new ::System::Type*[0])); 1523 ilGen->Emit( Emit::OpCodes::Ret ); 1524 1525 1526 //Create the service constructors. 1527 //obtain the interface which makes up this service, it is the return 1528 //type of the constructor functions 1529 Reference<reflection::XInterfaceTypeDescription2> xIfaceType( 1530 xServiceType->getInterface(), UNO_QUERY); 1531 if (xIfaceType.is () == sal_False) 1532 xIfaceType = resolveInterfaceTypedef(xServiceType->getInterface()); 1533 System::Type * retType = get_type(xIfaceType); 1534 1535 //Create the ConstructorInfo for a DeploymentException 1536 ::System::Type * typeDeploymentExc = 1537 get_type(S"unoidl.com.sun.star.uno.DeploymentException", true); 1538 1539 ::System::Type * arTypeCtor[] = {__typeof(::System::String), 1540 __typeof(::System::Object)}; 1541 ::System::Reflection::ConstructorInfo * ctorDeploymentException = 1542 typeDeploymentExc->GetConstructor(arTypeCtor); 1543 1544 Sequence<Reference<reflection::XServiceConstructorDescription> > seqCtors = 1545 xServiceType->getConstructors(); 1546 1547 ::System::Type * type_uno_exception = get_type(S"unoidl.com.sun.star.uno.Exception", true); 1548 1549 for (int i = seqCtors.getLength() - 1; i >= 0; i--) 1550 { 1551 bool bParameterArray = false; 1552 ::System::Type * typeAny = __typeof(::uno::Any); 1553 const Reference<reflection::XServiceConstructorDescription> & ctorDes = 1554 seqCtors[i]; 1555 //obtain the parameter types 1556 Sequence<Reference<reflection::XParameter> > seqParams = 1557 ctorDes->getParameters(); 1558 Reference<reflection::XParameter> const * arXParams = seqParams.getConstArray(); 1559 sal_Int32 cParams = seqParams.getLength(); 1560 ::System::Type * arTypeParameters[] = new ::System::Type* [cParams + 1]; 1561 arTypeParameters[0] = get_type(S"unoidl.com.sun.star.uno.XComponentContext", true); 1562 for (int iparam = 0; iparam != cParams; iparam++) 1563 { 1564 if (arXParams[iparam]->isRestParameter()) 1565 arTypeParameters[iparam + 1] = __typeof(::uno::Any[]); 1566 else 1567 arTypeParameters[iparam + 1] = get_type(arXParams[iparam]->getType()); 1568 } 1569 //The array arTypeParameters can contain: 1570 //System.Type and uno.PolymorphicType. 1571 //Passing PolymorphicType to MethodBuilder.DefineMethod will cause a problem. 1572 //The exception will read something like no on information for parameter # d 1573 //Maybe we need no override another Type method in PolymorphicType ... 1574 //Until we have figured this out, we will create another array of System.Type which 1575 //we pass on to DefineMethod. 1576 ::System::Type * arParamTypes[] = new ::System::Type * [cParams + 1]; 1577 // arParamTypes[0] = get_type(S"unoidl.com.sun.star.uno.XComponentContext", true); 1578 for (int i = 0; i < cParams + 1; i++) 1579 { 1580 ::uno::PolymorphicType * pT = dynamic_cast< ::uno::PolymorphicType * >(arTypeParameters[i]); 1581 if (pT) 1582 arParamTypes[i] = pT->OriginalType; 1583 else 1584 arParamTypes[i] = arTypeParameters[i]; 1585 } 1586 //define method 1587 System::String * ctorName; 1588 if (ctorDes->isDefaultConstructor()) 1589 ctorName = new ::System::String(S"create"); 1590 else 1591 ctorName = ustring_to_String(ctorDes->getName()); 1592 Emit::MethodBuilder* method_builder = type_builder->DefineMethod( 1593 ctorName, 1594 static_cast<MethodAttributes>(MethodAttributes::Public | MethodAttributes::HideBySig | 1595 MethodAttributes::Static), 1596 retType, 1597 // arTypeParameters); 1598 arParamTypes); 1599 1600 //define UNO exception attribute (exceptions)-------------------------------------- 1601 Emit::CustomAttributeBuilder* attrBuilder = get_service_exception_attribute(ctorDes); 1602 if (attrBuilder != NULL) 1603 method_builder->SetCustomAttribute(attrBuilder); 1604 1605 //------------------------------------------------------------- 1606 //define parameter attributes (paramarray), names etc. 1607 //The first parameter is the XComponentContext, which cannot be obtained 1608 //from reflection. 1609 //The context is not part of the idl description 1610 method_builder->DefineParameter( 1611 1, ParameterAttributes::In, S"the_context"); 1612 1613 Emit::ParameterBuilder * arParameterBuilder[] = 1614 new Emit::ParameterBuilder * [cParams]; 1615 for (int iparam = 0; iparam != cParams; iparam++) 1616 { 1617 Reference<reflection::XParameter> const & aParam = arXParams[iparam]; 1618 ::System::String * sParamName = ustring_to_String(aParam->getName()); 1619 1620 arParameterBuilder[iparam] = method_builder->DefineParameter( 1621 iparam + 2, ParameterAttributes::In, sParamName); 1622 1623 if (aParam->isRestParameter()) 1624 { 1625 bParameterArray = true; 1626 //set the ParameterArrayAttribute 1627 ::System::Reflection::ConstructorInfo* ctor_info = 1628 __typeof(System::ParamArrayAttribute)->GetConstructor( 1629 new ::System::Type*[0]); 1630 Emit::CustomAttributeBuilder * attr_builder = 1631 new Emit::CustomAttributeBuilder(ctor_info, new ::System::Object*[0]); 1632 arParameterBuilder[iparam]->SetCustomAttribute(attr_builder); 1633 break; 1634 } 1635 } 1636 1637 Emit::ILGenerator * ilGen = method_builder->GetILGenerator(); 1638 1639 //Define locals --------------------------------- 1640 //XMultiComponentFactory 1641 Emit::LocalBuilder* local_factory = 1642 ilGen->DeclareLocal( 1643 get_type(S"unoidl.com.sun.star.lang.XMultiComponentFactory", true)); 1644 1645 //The return type 1646 Emit::LocalBuilder* local_return_val = 1647 ilGen->DeclareLocal(retType); 1648 1649 //Obtain the XMultiComponentFactory and throw an exception if we do not get one 1650 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1651 1652 ::System::Reflection::MethodInfo * methodGetServiceManager = get_type( 1653 S"unoidl.com.sun.star.uno.XComponentContext", true) 1654 ->GetMethod(S"getServiceManager"); 1655 ilGen->Emit(Emit::OpCodes::Callvirt, methodGetServiceManager); 1656 ilGen->Emit(Emit::OpCodes::Stloc, local_factory); 1657 ilGen->Emit(Emit::OpCodes::Ldloc, local_factory); 1658 Emit::Label label1 = ilGen->DefineLabel(); 1659 ilGen->Emit(Emit::OpCodes::Brtrue, label1); 1660 //The string for the exception 1661 ::System::Text::StringBuilder * strbuilder = new ::System::Text::StringBuilder(256); 1662 strbuilder->Append(S"The service "); 1663 strbuilder->Append(to_cts_name(xServiceType->getName())); 1664 strbuilder->Append(S" could not be created. The context failed to supply the service manager."); 1665 1666 ilGen->Emit(Emit::OpCodes::Ldstr, strbuilder->ToString()); 1667 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1668 ilGen->Emit(Emit::OpCodes::Newobj, ctorDeploymentException); 1669 ilGen->Emit(Emit::OpCodes::Throw); 1670 ilGen->MarkLabel(label1); 1671 1672 //We create a try/ catch around the createInstanceWithContext, etc. functions 1673 //There are 3 cases 1674 //1. function do not specify exceptions. Then RuntimeExceptions are retrhown and other 1675 // exceptions produce a DeploymentException. 1676 //2. function specify Exception. Then all exceptions fly through 1677 //3. function specifies exceptions but no Exception. Then these are rethrown 1678 // and other exceptions, except RuntimeException, produce a deployment exception. 1679 //In case there are no parameters we call 1680 //XMultiComponentFactory.createInstanceWithContext 1681 1682 ::System::Collections::ArrayList * arExceptionTypes = 1683 get_service_ctor_method_exceptions_reduced(ctorDes->getExceptions()); 1684 if (arExceptionTypes->Contains( 1685 type_uno_exception) == false) 1686 { 1687 ilGen->BeginExceptionBlock(); 1688 } 1689 if (cParams == 0) 1690 { 1691 ilGen->Emit(Emit::OpCodes::Ldloc, local_factory); 1692 ilGen->Emit(Emit::OpCodes::Ldstr, ustring_to_String(xServiceType->getName())); 1693 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1694 1695 ::System::Reflection::MethodInfo * methodCreate = 1696 local_factory->get_LocalType()->GetMethod(S"createInstanceWithContext"); 1697 ilGen->Emit(Emit::OpCodes::Callvirt, methodCreate); 1698 } 1699 else if(bParameterArray) 1700 { 1701 //Service constructor with parameter array 1702 ilGen->Emit(Emit::OpCodes::Ldloc, local_factory); 1703 ilGen->Emit(Emit::OpCodes::Ldstr, ustring_to_String(xServiceType->getName())); 1704 ilGen->Emit(Emit::OpCodes::Ldarg_1); 1705 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1706 ::System::Reflection::MethodInfo * methodCreate = 1707 local_factory->get_LocalType()->GetMethod(S"createInstanceWithArgumentsAndContext"); 1708 ilGen->Emit(Emit::OpCodes::Callvirt, methodCreate); 1709 } 1710 else 1711 { 1712 // Any param1, Any param2, etc. 1713 // For each parameter,except the component context, and parameter array 1714 // and Any is created. 1715 Emit::LocalBuilder * arLocalAny[] = new Emit::LocalBuilder* [cParams]; 1716 1717 for (int iParam = 0; iParam < cParams; iParam ++) 1718 { 1719 arLocalAny[iParam] = ilGen->DeclareLocal(typeAny); 1720 } 1721 1722 //Any[]. This array is filled with the created Anys which contain the parameters 1723 //and the values contained in the parameter array 1724 Emit::LocalBuilder * local_anyParams = 1725 ilGen->DeclareLocal(__typeof(::uno::Any[])); 1726 1727 //Create the Any for every argument, except for the parameter array 1728 //arLocalAny contains the LocalBuilder for all these parameters. 1729 //we call the ctor Any(Type, Object) 1730 //If the parameter is an Any then the Any is created with Any(param.Type, param.Value); 1731 ::System::Type * arTypesCtorAny[] = {__typeof(::System::Type), 1732 __typeof(::System::Object)}; 1733 ::System::Reflection::ConstructorInfo * ctorAny = 1734 typeAny->GetConstructor( arTypesCtorAny); 1735 ::System::Reflection::MethodInfo * methodAnyGetType = 1736 typeAny->GetProperty(S"Type")->GetGetMethod(); 1737 ::System::Reflection::MethodInfo * methodAnyGetValue = 1738 typeAny->GetProperty(S"Value")->GetGetMethod(); 1739 for (int i = 0; i < arLocalAny->Length; i ++) 1740 { 1741 //check if the parameter is a polymorphic struct 1742 ::uno::PolymorphicType *polyType = dynamic_cast< ::uno::PolymorphicType* >(arTypeParameters[i+1]); 1743 //arTypeParameters[i+1] = polyType->OriginalType; 1744 if (polyType) 1745 { 1746 //It is a polymorphic struct 1747 //Load the uninitialized local Any on which we will call the ctor 1748 ilGen->Emit(Emit::OpCodes::Ldloca, arLocalAny[i]); 1749 // Call PolymorphicType PolymorphicType::GetType(Type t, String polyName) 1750 // Prepare the first parameter 1751 ilGen->Emit(Emit::OpCodes::Ldtoken, polyType->get_OriginalType()); 1752 ::System::Type * arTypeParams[] = {__typeof(::System::RuntimeTypeHandle)}; 1753 ilGen->Emit(Emit::OpCodes::Call, 1754 __typeof(::System::Type)->GetMethod( 1755 S"GetTypeFromHandle", arTypeParams)); 1756 // Prepare the second parameter 1757 ilGen->Emit(Emit::OpCodes::Ldstr, polyType->get_PolymorphicName()); 1758 // Make the actual call 1759 ::System::Type * arTypeParam_GetType[] = { 1760 __typeof(::System::Type), __typeof(::System::String) }; 1761 ilGen->Emit(Emit::OpCodes::Call, 1762 __typeof(::uno::PolymorphicType)->GetMethod(new System::String(S"GetType"), 1763 arTypeParam_GetType)); 1764 1765 //Stack is: localAny, PolymorphicType 1766 //Call Any::Any(Type, Object) 1767 //Prepare the second parameter for the any ctor 1768 ilGen->Emit(Emit::OpCodes::Ldarg, i + 1); 1769 // if the parameter is a value type then we need to box it, because 1770 // the Any ctor takes an Object 1771 if (arTypeParameters[i+1]->IsValueType) 1772 ilGen->Emit(Emit::OpCodes::Box, arTypeParameters[i+1]); 1773 ilGen->Emit(Emit::OpCodes::Call, ctorAny); 1774 } 1775 else if (arTypeParameters[i+1] == typeAny) 1776 { 1777 //Create the call new Any(param.Type,param,Value) 1778 //Stack must be Any,Type,Value 1779 //First load the Any which is to be constructed 1780 ilGen->Emit(Emit::OpCodes::Ldloca, arLocalAny[i]); 1781 //Load the Type, which is obtained by calling param.Type 1782 ilGen->Emit(Emit::OpCodes::Ldarga, i + 1); 1783 ilGen->Emit(Emit::OpCodes::Call, methodAnyGetType); 1784 //Load the Value, which is obtained by calling param.Value 1785 ilGen->Emit(Emit::OpCodes::Ldarga, i + 1); 1786 ilGen->Emit(Emit::OpCodes::Call, methodAnyGetValue); 1787 //Call the Any ctor. 1788 ilGen->Emit(Emit::OpCodes::Call, ctorAny); 1789 } 1790 else 1791 { 1792 ilGen->Emit(Emit::OpCodes::Ldloca, arLocalAny[i]); 1793 ilGen->Emit(Emit::OpCodes::Ldtoken, arTypeParameters[i+1]); 1794 1795 ::System::Type * arTypeParams[] = {__typeof(::System::RuntimeTypeHandle)}; 1796 ilGen->Emit(Emit::OpCodes::Call, 1797 __typeof(::System::Type)->GetMethod( 1798 S"GetTypeFromHandle", arTypeParams)); 1799 ilGen->Emit(Emit::OpCodes::Ldarg, i + 1); 1800 // if the parameter is a value type then we need to box it, because 1801 // the Any ctor takes an Object 1802 if (arTypeParameters[i+1]->IsValueType) 1803 ilGen->Emit(Emit::OpCodes::Box, arTypeParameters[i+1]); 1804 ilGen->Emit(Emit::OpCodes::Call, ctorAny); 1805 } 1806 } 1807 1808 //Create the Any[] that is passed to the 1809 //createInstanceWithContext[AndArguments] function 1810 ilGen->Emit(Emit::OpCodes::Ldc_I4, arLocalAny->Length); 1811 ilGen->Emit(Emit::OpCodes::Newarr, typeAny); 1812 ilGen->Emit(Emit::OpCodes::Stloc, local_anyParams); 1813 1814 //Assign all anys created from the parameters 1815 //array to the Any[] 1816 for (int i = 0; i < arLocalAny->Length; i++) 1817 { 1818 ilGen->Emit(Emit::OpCodes::Ldloc, local_anyParams); 1819 ilGen->Emit(Emit::OpCodes::Ldc_I4, i); 1820 ilGen->Emit(Emit::OpCodes::Ldelema, typeAny); 1821 ilGen->Emit(Emit::OpCodes::Ldloc, arLocalAny[i]); 1822 ilGen->Emit(Emit::OpCodes::Stobj, typeAny); 1823 } 1824 // call createInstanceWithContextAndArguments 1825 ilGen->Emit(Emit::OpCodes::Ldloc, local_factory); 1826 ilGen->Emit(Emit::OpCodes::Ldstr, ustring_to_String(xServiceType->getName())); 1827 ilGen->Emit(Emit::OpCodes::Ldloc, local_anyParams); 1828 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1829 ::System::Reflection::MethodInfo * methodCreate = 1830 local_factory->get_LocalType()->GetMethod(S"createInstanceWithArgumentsAndContext"); 1831 ilGen->Emit(Emit::OpCodes::Callvirt, methodCreate); 1832 } 1833 //cast the object returned by the functions createInstanceWithContext or 1834 //createInstanceWithArgumentsAndContext to the interface type 1835 ilGen->Emit(Emit::OpCodes::Castclass, retType); 1836 ilGen->Emit(Emit::OpCodes::Stloc, local_return_val); 1837 1838 //catch exceptions thrown by createInstanceWithArgumentsAndContext and createInstanceWithContext 1839 if (arExceptionTypes->Contains(type_uno_exception) == false) 1840 { 1841 // catch (unoidl.com.sun.star.uno.RuntimeException) {throw;} 1842 ilGen->BeginCatchBlock(get_type(S"unoidl.com.sun.star.uno.RuntimeException", true)); 1843 ilGen->Emit(Emit::OpCodes::Pop); 1844 ilGen->Emit(Emit::OpCodes::Rethrow); 1845 1846 //catch and rethrow all other defined Exceptions 1847 for (int i = 0; i < arExceptionTypes->Count; i++) 1848 { 1849 ::System::Type * excType = __try_cast< ::System::Type* >( 1850 arExceptionTypes->get_Item(i)); 1851 if (excType->IsInstanceOfType( 1852 get_type(S"unoidl.com.sun.star.uno.RuntimeException", true))) 1853 {// we have a catch for RuntimeException already defined 1854 continue; 1855 } 1856 1857 //catch Exception and rethrow 1858 ilGen->BeginCatchBlock(excType); 1859 ilGen->Emit(Emit::OpCodes::Pop); 1860 ilGen->Emit(Emit::OpCodes::Rethrow); 1861 } 1862 //catch (unoidl.com.sun.star.uno.Exception) {throw DeploymentException...} 1863 ilGen->BeginCatchBlock(type_uno_exception); 1864 1865 //Define the local variabe that keeps the exception 1866 Emit::LocalBuilder * local_exception = ilGen->DeclareLocal( 1867 type_uno_exception); 1868 1869 //Store the exception 1870 ilGen->Emit(Emit::OpCodes::Stloc, local_exception); 1871 1872 //prepare the construction of the exception 1873 strbuilder = new ::System::Text::StringBuilder(256); 1874 strbuilder->Append(S"The context (com.sun.star.uno.XComponentContext) failed to supply the service "); 1875 strbuilder->Append(to_cts_name(xServiceType->getName())); 1876 strbuilder->Append(S": "); 1877 1878 ilGen->Emit(Emit::OpCodes::Ldstr, strbuilder->ToString()); 1879 1880 //add to the string the Exception.Message 1881 ilGen->Emit(Emit::OpCodes::Ldloc, local_exception); 1882 ilGen->Emit(Emit::OpCodes::Callvirt, 1883 type_uno_exception->GetProperty(S"Message")->GetGetMethod()); 1884 ::System::Type * arConcatParams [] = {__typeof(System::String), 1885 __typeof(System::String)}; 1886 ilGen->Emit(Emit::OpCodes::Call, 1887 __typeof(System::String)->GetMethod(S"Concat", arConcatParams)); 1888 //load contex argument 1889 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1890 ilGen->Emit(Emit::OpCodes::Newobj, ctorDeploymentException); 1891 ilGen->Emit(Emit::OpCodes::Throw);//Exception(typeDeploymentExc); 1892 1893 ilGen->EndExceptionBlock(); 1894 } 1895 1896 1897 //Check if the service instance was create and throw a exception if not. 1898 Emit::Label label_service_created = ilGen->DefineLabel(); 1899 ilGen->Emit(Emit::OpCodes::Ldloc, local_return_val); 1900 ilGen->Emit(Emit::OpCodes::Brtrue_S, label_service_created); 1901 1902 strbuilder = new ::System::Text::StringBuilder(256); 1903 strbuilder->Append(S"The context (com.sun.star.uno.XComponentContext) failed to supply the service "); 1904 strbuilder->Append(to_cts_name(xServiceType->getName())); 1905 strbuilder->Append(S"."); 1906 ilGen->Emit(Emit::OpCodes::Ldstr, strbuilder->ToString()); 1907 ilGen->Emit(Emit::OpCodes::Ldarg_0); 1908 ilGen->Emit(Emit::OpCodes::Newobj, ctorDeploymentException); 1909 ilGen->Emit(Emit::OpCodes::Throw);//Exception(typeDeploymentExc); 1910 1911 ilGen->MarkLabel(label_service_created); 1912 ilGen->Emit(Emit::OpCodes::Ldloc, local_return_val); 1913 ilGen->Emit(Emit::OpCodes::Ret); 1914 1915 } 1916 // remove from incomplete types map 1917 ::System::String * cts_name = type_builder->get_FullName(); 1918 m_incomplete_services->Remove( cts_name ); 1919 xServiceType->release(); 1920 if (g_verbose) 1921 { 1922 ::System::Console::WriteLine( 1923 "> emitting service type {0}", cts_name ); 1924 } 1925 return type_builder->CreateType(); 1926 } 1927 1928 1929 Emit::CustomAttributeBuilder* TypeEmitter::get_service_exception_attribute( 1930 const Reference<reflection::XServiceConstructorDescription> & ctorDes ) 1931 { 1932 return get_exception_attribute(ctorDes->getExceptions()); 1933 } 1934 1935 Emit::CustomAttributeBuilder* TypeEmitter::get_iface_method_exception_attribute( 1936 const Reference< reflection::XInterfaceMethodTypeDescription >& xMethod ) 1937 { 1938 1939 const Sequence<Reference<reflection::XTypeDescription> > seqTD = xMethod->getExceptions(); 1940 int len = seqTD.getLength(); 1941 Sequence<Reference<reflection::XCompoundTypeDescription> > seqCTD(len); 1942 Reference<reflection::XCompoundTypeDescription> * arCTD = seqCTD.getArray(); 1943 for (int i = 0; i < len; i++) 1944 arCTD[i] = Reference<reflection::XCompoundTypeDescription>(seqTD[i], UNO_QUERY_THROW); 1945 return get_exception_attribute(seqCTD); 1946 } 1947 1948 Emit::CustomAttributeBuilder* TypeEmitter::get_exception_attribute( 1949 1950 const Sequence<Reference< reflection::XCompoundTypeDescription > >& seq_exceptionsTd ) 1951 { 1952 Emit::CustomAttributeBuilder * attr_builder = NULL; 1953 1954 Reference< reflection::XCompoundTypeDescription > const * exceptions = 1955 seq_exceptionsTd.getConstArray(); 1956 1957 ::System::Type * arTypesCtor[] = {::System::Type::GetType(S"System.Type[]")}; 1958 ConstructorInfo * ctor_ExceptionAttribute = 1959 __typeof(::uno::ExceptionAttribute)->GetConstructor(arTypesCtor); 1960 1961 sal_Int32 exc_length = seq_exceptionsTd.getLength(); 1962 if (exc_length != 0) // opt 1963 { 1964 ::System::Type * exception_types [] = 1965 new ::System::Type * [ exc_length ]; 1966 for ( sal_Int32 exc_pos = 0; exc_pos < exc_length; ++exc_pos ) 1967 { 1968 Reference< reflection::XCompoundTypeDescription > const & xExc = 1969 exceptions[ exc_pos ]; 1970 exception_types[ exc_pos ] = get_type( xExc ); 1971 } 1972 ::System::Object * args [] = {exception_types}; 1973 attr_builder = new Emit::CustomAttributeBuilder( 1974 ctor_ExceptionAttribute, args ); 1975 } 1976 return attr_builder; 1977 } 1978 1979 1980 ::System::Type * TypeEmitter::complete_singleton_type(singleton_entry * entry) 1981 { 1982 Emit::TypeBuilder * type_builder = entry->m_type_builder; 1983 reflection::XSingletonTypeDescription2 * xSingletonType = entry->m_xType; 1984 ::System::String* sSingletonName = to_cts_name(xSingletonType->getName()); 1985 1986 //Create the private default constructor 1987 Emit::ConstructorBuilder* ctor_builder = 1988 type_builder->DefineConstructor( 1989 static_cast<MethodAttributes>(MethodAttributes::Private | 1990 MethodAttributes::HideBySig | 1991 MethodAttributes::SpecialName | 1992 MethodAttributes::RTSpecialName), 1993 CallingConventions::Standard, NULL); 1994 1995 Emit::ILGenerator* ilGen = ctor_builder->GetILGenerator(); 1996 ilGen->Emit( Emit::OpCodes::Ldarg_0 ); // push this 1997 ilGen->Emit( 1998 Emit::OpCodes::Call, 1999 type_builder->BaseType->GetConstructor(new ::System::Type*[0])); 2000 ilGen->Emit( Emit::OpCodes::Ret ); 2001 2002 2003 //obtain the interface which makes up this service, it is the return 2004 //type of the constructor functions 2005 Reference<reflection::XInterfaceTypeDescription2> xIfaceType( 2006 xSingletonType->getInterface(), UNO_QUERY); 2007 if (xIfaceType.is () == sal_False) 2008 xIfaceType = resolveInterfaceTypedef(xSingletonType->getInterface()); 2009 System::Type * retType = get_type(xIfaceType); 2010 2011 //define method 2012 ::System::Type * arTypeParameters[] = {get_type(S"unoidl.com.sun.star.uno.XComponentContext", true)}; 2013 Emit::MethodBuilder* method_builder = type_builder->DefineMethod( 2014 new System::String(S"get"), 2015 static_cast<MethodAttributes>(MethodAttributes::Public | MethodAttributes::HideBySig | 2016 MethodAttributes::Static), 2017 retType, 2018 arTypeParameters); 2019 2020 2021 // method_builder->SetCustomAttribute(get_service_ctor_method_attribute(ctorDes)); 2022 2023 //The first parameter is the XComponentContext, which cannot be obtained 2024 //from reflection. 2025 //The context is not part of the idl description 2026 method_builder->DefineParameter(1, ParameterAttributes::In, S"the_context"); 2027 2028 2029 ilGen = method_builder->GetILGenerator(); 2030 //Define locals --------------------------------- 2031 // Any, returned by XComponentContext.getValueByName 2032 Emit::LocalBuilder* local_any = 2033 ilGen->DeclareLocal(__typeof(::uno::Any)); 2034 2035 //Call XContext::getValueByName 2036 ilGen->Emit(Emit::OpCodes::Ldarg_0); 2037 // build the singleton name : /singleton/unoidl.com.sun.star.XXX 2038 ::System::Text::StringBuilder* sBuilder = 2039 new ::System::Text::StringBuilder(S"/singletons/"); 2040 sBuilder->Append(sSingletonName); 2041 ilGen->Emit(Emit::OpCodes::Ldstr, sBuilder->ToString()); 2042 2043 ::System::Reflection::MethodInfo * methodGetValueByName = 2044 get_type(S"unoidl.com.sun.star.uno.XComponentContext", true)->GetMethod(S"getValueByName"); 2045 ilGen->Emit(Emit::OpCodes::Callvirt, methodGetValueByName); 2046 ilGen->Emit(Emit::OpCodes::Stloc_0); 2047 2048 //Contains the returned Any a value? 2049 ilGen->Emit(Emit::OpCodes::Ldloca_S, local_any); 2050 ::System::Reflection::MethodInfo * methodHasValue = 2051 __typeof(::uno::Any)->GetMethod(S"hasValue"); 2052 ilGen->Emit(Emit::OpCodes::Call, methodHasValue); 2053 2054 //If not, then throw an DeploymentException 2055 Emit::Label label_singleton_exists = ilGen->DefineLabel(); 2056 ilGen->Emit(Emit::OpCodes::Brtrue_S, label_singleton_exists); 2057 sBuilder = new ::System::Text::StringBuilder( 2058 S"Component context fails to supply singleton "); 2059 sBuilder->Append(sSingletonName); 2060 sBuilder->Append(S" of type "); 2061 sBuilder->Append(retType->FullName); 2062 sBuilder->Append(S"."); 2063 ilGen->Emit(Emit::OpCodes::Ldstr, sBuilder->ToString()); 2064 ilGen->Emit(Emit::OpCodes::Ldarg_0); 2065 ::System::Type * arTypesCtorDeploymentException[] = { 2066 __typeof(::System::String), __typeof(::System::Object)}; 2067 ilGen->Emit(Emit::OpCodes::Newobj, 2068 get_type(S"unoidl.com.sun.star.uno.DeploymentException",true) 2069 ->GetConstructor(arTypesCtorDeploymentException)); 2070 ilGen->Emit(Emit::OpCodes::Throw); 2071 ilGen->MarkLabel(label_singleton_exists); 2072 2073 //Cast the singleton contained in the Any to the expected interface and return it. 2074 ilGen->Emit(Emit::OpCodes::Ldloca_S, local_any); 2075 ilGen->Emit(Emit::OpCodes::Call, __typeof(::uno::Any)->GetProperty(S"Value")->GetGetMethod()); 2076 ilGen->Emit(Emit::OpCodes::Castclass, retType); 2077 ilGen->Emit(Emit::OpCodes::Ret); 2078 2079 // remove from incomplete types map 2080 ::System::String * cts_name = type_builder->get_FullName(); 2081 m_incomplete_singletons->Remove( cts_name ); 2082 xSingletonType->release(); 2083 if (g_verbose) 2084 { 2085 ::System::Console::WriteLine( 2086 "> emitting singleton type {0}", cts_name ); 2087 } 2088 return type_builder->CreateType(); 2089 } 2090 2091 2092 //______________________________________________________________________________ 2093 ::System::Type * TypeEmitter::get_type( 2094 Reference< reflection::XTypeDescription > const & xType ) 2095 { 2096 switch (xType->getTypeClass()) 2097 { 2098 case TypeClass_VOID: 2099 return __typeof (::System::Void); 2100 case TypeClass_CHAR: 2101 return __typeof (::System::Char); 2102 case TypeClass_BOOLEAN: 2103 return __typeof (::System::Boolean); 2104 case TypeClass_BYTE: 2105 return __typeof (::System::Byte); 2106 case TypeClass_SHORT: 2107 return __typeof (::System::Int16); 2108 case TypeClass_UNSIGNED_SHORT: 2109 return __typeof (::System::UInt16); 2110 case TypeClass_LONG: 2111 return __typeof (::System::Int32); 2112 case TypeClass_UNSIGNED_LONG: 2113 return __typeof (::System::UInt32); 2114 case TypeClass_HYPER: 2115 return __typeof (::System::Int64); 2116 case TypeClass_UNSIGNED_HYPER: 2117 return __typeof (::System::UInt64); 2118 case TypeClass_FLOAT: 2119 return __typeof (::System::Single); 2120 case TypeClass_DOUBLE: 2121 return __typeof (::System::Double); 2122 case TypeClass_STRING: 2123 return __typeof (::System::String); 2124 case TypeClass_TYPE: 2125 return __typeof (::System::Type); 2126 case TypeClass_ANY: 2127 return __typeof(::uno::Any); 2128 case TypeClass_ENUM: 2129 return get_type( Reference< reflection::XEnumTypeDescription >( 2130 xType, UNO_QUERY_THROW ) ); 2131 case TypeClass_TYPEDEF: 2132 // unwind typedefs 2133 return get_type( 2134 Reference< reflection::XIndirectTypeDescription >( 2135 xType, UNO_QUERY_THROW )->getReferencedType() ); 2136 case TypeClass_STRUCT: 2137 case TypeClass_EXCEPTION: 2138 return get_type( 2139 Reference< reflection::XCompoundTypeDescription >( 2140 xType, UNO_QUERY_THROW ) ); 2141 case TypeClass_SEQUENCE: 2142 { 2143 ::System::Type * element_type = get_type( 2144 Reference< reflection::XIndirectTypeDescription >( 2145 xType, UNO_QUERY_THROW )->getReferencedType() ); 2146 ::System::Type * retType = get_type( 2147 ::System::String::Concat( 2148 element_type->get_FullName(), S"[]" ), true ); 2149 2150 ::uno::PolymorphicType * pt = dynamic_cast< ::uno::PolymorphicType * >(element_type); 2151 if (pt) 2152 { 2153 ::System::String * sName = ::System::String::Concat(pt->PolymorphicName, S"[]"); 2154 retType = ::uno::PolymorphicType::GetType(retType, sName); 2155 } 2156 return retType; 2157 } 2158 case TypeClass_INTERFACE: 2159 return get_type( 2160 Reference< reflection::XInterfaceTypeDescription2 >( 2161 xType, UNO_QUERY_THROW ) ); 2162 case TypeClass_CONSTANT: 2163 return get_type( 2164 Reference< reflection::XConstantTypeDescription >( 2165 xType, UNO_QUERY_THROW ) ); 2166 case TypeClass_CONSTANTS: 2167 return get_type( 2168 Reference< reflection::XConstantsTypeDescription >( 2169 xType, UNO_QUERY_THROW ) ); 2170 case TypeClass_SERVICE: 2171 return get_type( 2172 Reference< reflection::XServiceTypeDescription2 >( 2173 xType, UNO_QUERY_THROW) ); 2174 case TypeClass_SINGLETON: 2175 return get_type( 2176 Reference< reflection::XSingletonTypeDescription2 >( 2177 xType, UNO_QUERY_THROW) ); 2178 case TypeClass_MODULE: 2179 // ignore these 2180 return 0; 2181 default: 2182 throw RuntimeException( 2183 OUSTR("unexpected type ") + xType->getName(), 2184 Reference< XInterface >() ); 2185 } 2186 } 2187 2188 //______________________________________________________________________________ 2189 ::System::Type * TypeEmitter::get_complete_struct( ::System::String * sName) 2190 { 2191 struct_entry * pStruct = __try_cast< struct_entry *>( 2192 m_incomplete_structs->get_Item(sName)); 2193 if (pStruct) 2194 { 2195 complete_struct_type(pStruct); 2196 } 2197 //get_type will asked the module builder for the type or otherwise all known assemblies. 2198 return get_type(sName, true); 2199 } 2200 void TypeEmitter::Dispose() 2201 { 2202 while (true) 2203 { 2204 ::System::Collections::IDictionaryEnumerator * enumerator = 2205 m_incomplete_ifaces->GetEnumerator(); 2206 if (! enumerator->MoveNext()) 2207 break; 2208 complete_iface_type( 2209 __try_cast< iface_entry * >( enumerator->get_Value() ) ); 2210 } 2211 2212 while (true) 2213 { 2214 ::System::Collections::IDictionaryEnumerator * enumerator = 2215 m_incomplete_structs->GetEnumerator(); 2216 if (! enumerator->MoveNext()) 2217 break; 2218 complete_struct_type( 2219 __try_cast< struct_entry * >( enumerator->get_Value() ) ); 2220 } 2221 2222 2223 while (true) 2224 { 2225 ::System::Collections::IDictionaryEnumerator * enumerator = 2226 m_incomplete_services->GetEnumerator(); 2227 if (! enumerator->MoveNext()) 2228 break; 2229 complete_service_type( 2230 __try_cast< service_entry * >( enumerator->get_Value() ) ); 2231 } 2232 2233 while (true) 2234 { 2235 ::System::Collections::IDictionaryEnumerator * enumerator = 2236 m_incomplete_singletons->GetEnumerator(); 2237 if (! enumerator->MoveNext()) 2238 break; 2239 complete_singleton_type( 2240 __try_cast< singleton_entry * >( enumerator->get_Value() ) ); 2241 } 2242 } 2243 //______________________________________________________________________________ 2244 TypeEmitter::TypeEmitter( 2245 ::System::Reflection::Emit::ModuleBuilder * module_builder, 2246 ::System::Reflection::Assembly * extra_assemblies [] ) 2247 : m_module_builder( module_builder ), 2248 m_extra_assemblies( extra_assemblies ), 2249 m_method_info_Type_GetTypeFromHandle( 0 ), 2250 m_type_Exception( 0 ), 2251 m_type_RuntimeException( 0 ), 2252 m_incomplete_ifaces( new ::System::Collections::Hashtable() ), 2253 m_incomplete_structs( new ::System::Collections::Hashtable() ), 2254 m_incomplete_services(new ::System::Collections::Hashtable() ), 2255 m_incomplete_singletons(new ::System::Collections::Hashtable() ), 2256 m_generated_structs( new ::System::Collections::Hashtable() ) 2257 { 2258 ::System::Type * param_types[] = new ::System::Type * [ 1 ]; 2259 param_types[ 0 ] = __typeof (::System::RuntimeTypeHandle); 2260 m_method_info_Type_GetTypeFromHandle = 2261 __typeof (::System::Type) 2262 ->GetMethod( "GetTypeFromHandle", param_types ); 2263 } 2264 2265 ::System::Collections::ArrayList * TypeEmitter::get_service_ctor_method_exceptions_reduced( 2266 const Sequence<Reference<reflection::XCompoundTypeDescription> > & seqExceptionsTd) 2267 { 2268 if (seqExceptionsTd.getLength() == 0) 2269 return new ::System::Collections::ArrayList(); 2270 2271 ::System::Collections::ArrayList * arTypes = new ::System::Collections::ArrayList(); 2272 for (int i = 0; i < seqExceptionsTd.getLength(); i++) 2273 arTypes->Add(get_type(to_cts_name(seqExceptionsTd[i]->getName()), true)); 2274 2275 int start = 0; 2276 while (true) 2277 { 2278 bool bRemove = false; 2279 for (int i = start; i < arTypes->Count; i++) 2280 { 2281 ::System::Type * t = __try_cast< ::System::Type* >(arTypes->get_Item(i)); 2282 for (int j = 0; j < arTypes->Count; j++) 2283 { 2284 if (t->IsSubclassOf(__try_cast< ::System::Type* >(arTypes->get_Item(j)))) 2285 { 2286 arTypes->RemoveAt(i); 2287 bRemove = true; 2288 break; 2289 } 2290 } 2291 if (bRemove) 2292 break; 2293 start++; 2294 } 2295 2296 if (bRemove == false) 2297 break; 2298 } 2299 return arTypes; 2300 } 2301 2302 2303 css::uno::Reference< css::reflection::XInterfaceTypeDescription2 > 2304 resolveInterfaceTypedef( 2305 const css::uno::Reference<css::reflection::XTypeDescription>& type) 2306 { 2307 Reference<reflection::XInterfaceTypeDescription2> 2308 xIfaceTd(type, UNO_QUERY); 2309 2310 if (xIfaceTd.is()) 2311 return xIfaceTd; 2312 2313 Reference<reflection::XIndirectTypeDescription> xIndTd( 2314 type, UNO_QUERY); 2315 if (xIndTd.is() == sal_False) 2316 throw css::uno::Exception( 2317 OUSTR("resolveInterfaceTypedef was called with an invalid argument"), 0); 2318 2319 return resolveInterfaceTypedef(xIndTd->getReferencedType()); 2320 } 2321 2322 2323 } 2324