LCOV - code coverage report
Current view: top level - codemaker/source/javamaker - javatype.cxx (source / functions) Hit Total Coverage
Test: commit 0e63ca4fde4e446f346e35849c756a30ca294aab Lines: 1164 1211 96.1 %
Date: 2014-04-11 Functions: 47 47 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include "sal/config.h"
      21             : 
      22             : #include <algorithm>
      23             : #include <cassert>
      24             : #include <list>
      25             : #include <map>
      26             : #include <memory>
      27             : #include <set>
      28             : #include <utility>
      29             : #include <vector>
      30             : 
      31             : #include "codemaker/codemaker.hxx"
      32             : #include "codemaker/exceptiontree.hxx"
      33             : #include "codemaker/generatedtypeset.hxx"
      34             : #include "codemaker/global.hxx"
      35             : #include "codemaker/options.hxx"
      36             : #include "codemaker/typemanager.hxx"
      37             : #include "codemaker/unotype.hxx"
      38             : #include "codemaker/commonjava.hxx"
      39             : #include "rtl/ref.hxx"
      40             : #include "rtl/strbuf.hxx"
      41             : #include "rtl/string.hxx"
      42             : #include "rtl/ustrbuf.hxx"
      43             : #include "rtl/ustring.hxx"
      44             : #include "sal/types.h"
      45             : #include "unoidl/unoidl.hxx"
      46             : 
      47             : #include "classfile.hxx"
      48             : #include "javaoptions.hxx"
      49             : #include "javatype.hxx"
      50             : 
      51             : using codemaker::javamaker::ClassFile;
      52             : 
      53             : namespace {
      54             : 
      55         234 : void appendUnoName(
      56             :     rtl::Reference< TypeManager > const & manager, OUString const & nucleus,
      57             :     sal_Int32 rank, std::vector< OUString > const & arguments,
      58             :     OUStringBuffer * buffer)
      59             : {
      60             :     assert(manager.is());
      61             :     assert(rank >= 0);
      62             :     assert(buffer != 0);
      63         294 :     for (sal_Int32 i = 0; i != rank; ++i) {
      64          60 :         buffer->append("[]");
      65             :     }
      66         234 :     buffer->append(nucleus);
      67         234 :     if (!arguments.empty()) {
      68         105 :         buffer->append('<');
      69         720 :         for (std::vector< OUString >::const_iterator i(arguments.begin());
      70         480 :              i != arguments.end(); ++i)
      71             :         {
      72         135 :             if (i != arguments.begin()) {
      73          30 :                 buffer->append(',');
      74             :             }
      75         135 :             OUString n;
      76             :             sal_Int32 k;
      77         270 :             std::vector< OUString > args;
      78         135 :             manager->decompose(*i, false, &n, &k, &args, 0);
      79         135 :             appendUnoName(manager, n, k, args, buffer);
      80         135 :         }
      81         105 :         buffer->append('>');
      82             :     }
      83         234 : }
      84             : 
      85             : // Translate the name of a UNOIDL entity (enum type, plain struct type,
      86             : // polymorphic struct type template, or interface type, decomposed into nucleus,
      87             : // sequence rank, and template arguments) into a core UNO type name:
      88          99 : OUString createUnoName(
      89             :     rtl::Reference< TypeManager > const & manager, OUString const & nucleus,
      90             :     sal_Int32 rank, std::vector< OUString > const & arguments)
      91             : {
      92          99 :     OUStringBuffer buf;
      93          99 :     appendUnoName(manager, nucleus, rank, arguments, &buf);
      94          99 :     return buf.makeStringAndClear();
      95             : }
      96             : 
      97             : typedef std::set< OUString > Dependencies;
      98             : 
      99             : enum SpecialType {
     100             :     SPECIAL_TYPE_NONE,
     101             :     SPECIAL_TYPE_ANY,
     102             :     SPECIAL_TYPE_UNSIGNED,
     103             :     SPECIAL_TYPE_INTERFACE
     104             : };
     105             : 
     106        5650 : bool isSpecialType(SpecialType special) {
     107        5650 :     return special >= SPECIAL_TYPE_UNSIGNED;
     108             : }
     109             : 
     110         370 : OString translateUnoidlEntityNameToJavaFullyQualifiedName(
     111             :     OUString const & name, OString const & prefix)
     112             : {
     113             :     assert(!name.startsWith("[]"));
     114             :     assert(name.indexOf('<') == -1);
     115         370 :     sal_Int32 i = name.lastIndexOf('.') + 1;
     116             :     return codemaker::convertString(name.copy(0, i)).replace('.', '/')
     117         740 :         + codemaker::java::translateUnoToJavaIdentifier(
     118        1110 :             codemaker::convertString(name.copy(i)), prefix);
     119             : }
     120             : 
     121       62623 : struct PolymorphicUnoType {
     122       13697 :     PolymorphicUnoType(): kind(KIND_NONE) {}
     123             : 
     124             :     enum Kind { KIND_NONE, KIND_STRUCT, KIND_SEQUENCE };
     125             :     Kind kind;
     126             :     OUString name;
     127             : };
     128             : 
     129             : SpecialType translateUnoTypeToDescriptor(
     130             :     rtl::Reference< TypeManager > const & manager, OUString const & type,
     131             :     bool array, bool classType, Dependencies * dependencies,
     132             :     OStringBuffer * descriptor, OStringBuffer * signature,
     133             :     bool * needsSignature, PolymorphicUnoType * polymorphicUnoType);
     134             : 
     135       24132 : SpecialType translateUnoTypeToDescriptor(
     136             :     rtl::Reference< TypeManager > const & manager,
     137             :     codemaker::UnoType::Sort sort, OUString const & nucleus, sal_Int32 rank,
     138             :     std::vector< OUString > const & arguments, bool array, bool classType,
     139             :     Dependencies * dependencies, OStringBuffer * descriptor,
     140             :     OStringBuffer * signature, bool * needsSignature,
     141             :     PolymorphicUnoType * polymorphicUnoType)
     142             : {
     143             :     assert(rank >= 0);
     144             :     assert((signature == 0) == (needsSignature == 0));
     145             :     assert(
     146             :         arguments.empty()
     147             :         == (sort
     148             :             != codemaker::UnoType::SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE));
     149       24132 :     if (rank > 0xFF - (array ? 1 : 0)) {
     150             :         throw CannotDumpException(
     151           0 :             "Too many array dimensions for Java class file format");
     152             :     }
     153       24132 :     if (array) {
     154         158 :         ++rank;
     155             :     }
     156       25936 :     for (sal_Int32 i = 0; i != rank; ++i) {
     157        1804 :         if (descriptor != 0) {
     158        1780 :             descriptor->append('[');
     159             :         }
     160        1804 :         if (signature != 0) {
     161        1674 :             signature->append('[');
     162             :         }
     163             :     }
     164       24132 :     if (polymorphicUnoType != 0) {
     165       13689 :         if (sort
     166             :             == codemaker::UnoType::SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE)
     167             :         {
     168             :             polymorphicUnoType->kind = rank == 0
     169             :                 ? PolymorphicUnoType::KIND_STRUCT
     170          30 :                 : PolymorphicUnoType::KIND_SEQUENCE;
     171          60 :             polymorphicUnoType->name = createUnoName(
     172          30 :                 manager, nucleus, rank, arguments);
     173             :         } else {
     174       13659 :             polymorphicUnoType->kind = PolymorphicUnoType::KIND_NONE;
     175             :         }
     176             :     }
     177       24132 :     switch (sort) {
     178             :     case codemaker::UnoType::SORT_VOID:
     179             :     case codemaker::UnoType::SORT_BOOLEAN:
     180             :     case codemaker::UnoType::SORT_BYTE:
     181             :     case codemaker::UnoType::SORT_SHORT:
     182             :     case codemaker::UnoType::SORT_UNSIGNED_SHORT:
     183             :     case codemaker::UnoType::SORT_LONG:
     184             :     case codemaker::UnoType::SORT_UNSIGNED_LONG:
     185             :     case codemaker::UnoType::SORT_HYPER:
     186             :     case codemaker::UnoType::SORT_UNSIGNED_HYPER:
     187             :     case codemaker::UnoType::SORT_FLOAT:
     188             :     case codemaker::UnoType::SORT_DOUBLE:
     189             :     case codemaker::UnoType::SORT_CHAR:
     190             :     case codemaker::UnoType::SORT_STRING:
     191             :     case codemaker::UnoType::SORT_TYPE:
     192             :     case codemaker::UnoType::SORT_ANY:
     193             :         {
     194             :             static char const * const
     195             :                 simpleTypeDescriptors[codemaker::UnoType::SORT_ANY + 1][2] = {
     196             :                 { "V", "Ljava/lang/Void;" },
     197             :                 { "Z", "Ljava/lang/Boolean;" },
     198             :                 { "B", "Ljava/lang/Byte;" },
     199             :                 { "S", "Ljava/lang/Short;" },
     200             :                 { "S", "Ljava/lang/Short;" },
     201             :                 { "I", "Ljava/lang/Integer;" },
     202             :                 { "I", "Ljava/lang/Integer;" },
     203             :                 { "J", "Ljava/lang/Long;" },
     204             :                 { "J", "Ljava/lang/Long;" },
     205             :                 { "F", "Ljava/lang/Float;" },
     206             :                 { "D", "Ljava/lang/Double;" },
     207             :                 { "C", "Ljava/lang/Character;" },
     208             :                 { "Ljava/lang/String;", "Ljava/lang/String;" },
     209             :                 { "Lcom/sun/star/uno/Type;", "Lcom/sun/star/uno/Type;" },
     210             :                 { "Ljava/lang/Object;", "Ljava/lang/Object;" } };
     211             :             char const * s
     212       17719 :                 = simpleTypeDescriptors[sort][rank == 0 && classType];
     213       17719 :             if (descriptor != 0) {
     214       17612 :                 descriptor->append(s);
     215             :             }
     216       17719 :             if (signature != 0) {
     217       17653 :                 signature->append(s);
     218             :             }
     219             :             static SpecialType const
     220             :                 simpleTypeSpecials[codemaker::UnoType::SORT_ANY + 1] = {
     221             :                 SPECIAL_TYPE_NONE, SPECIAL_TYPE_NONE, SPECIAL_TYPE_NONE,
     222             :                 SPECIAL_TYPE_NONE, SPECIAL_TYPE_UNSIGNED, SPECIAL_TYPE_NONE,
     223             :                 SPECIAL_TYPE_UNSIGNED, SPECIAL_TYPE_NONE, SPECIAL_TYPE_UNSIGNED,
     224             :                 SPECIAL_TYPE_NONE, SPECIAL_TYPE_NONE, SPECIAL_TYPE_NONE,
     225             :                 SPECIAL_TYPE_NONE, SPECIAL_TYPE_NONE, SPECIAL_TYPE_ANY };
     226       17719 :             return simpleTypeSpecials[sort];
     227             :         }
     228             :     case codemaker::UnoType::SORT_INTERFACE_TYPE:
     229        3901 :         if (nucleus == "com.sun.star.uno.XInterface") {
     230         495 :             if (descriptor != 0) {
     231         493 :                 descriptor->append("Ljava/lang/Object;");
     232             :             }
     233         495 :             if (signature != 0) {
     234         494 :                 signature->append("Ljava/lang/Object;");
     235             :             }
     236         495 :             return SPECIAL_TYPE_INTERFACE;
     237             :         }
     238             :         // fall through
     239             :     case codemaker::UnoType::SORT_SEQUENCE_TYPE:
     240             :     case codemaker::UnoType::SORT_ENUM_TYPE:
     241             :     case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
     242             :     case codemaker::UnoType::SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE:
     243        5918 :         if (dependencies != 0) {
     244        5521 :             dependencies->insert(nucleus);
     245             :         }
     246        5918 :         if (descriptor != 0) {
     247             :             descriptor->append(
     248       11768 :                 "L" + codemaker::convertString(nucleus).replace('.', '/')
     249        5884 :                 + ";");
     250             :         }
     251        5918 :         if (signature != 0) {
     252             :             signature->append(
     253        5701 :                 "L" + codemaker::convertString(nucleus).replace('.', '/'));
     254        5701 :             if (!arguments.empty()) {
     255         113 :                 signature->append('<');
     256         768 :                 for (std::vector< OUString >::const_iterator i(
     257         113 :                          arguments.begin());
     258         512 :                      i != arguments.end(); ++i)
     259             :                 {
     260             :                     translateUnoTypeToDescriptor(
     261         143 :                         manager, *i, false, true, dependencies, 0, signature,
     262         143 :                         needsSignature, 0);
     263             :                 }
     264         113 :                 signature->append('>');
     265         113 :                 *needsSignature = true;
     266             :             }
     267        5701 :             signature->append(';');
     268             :         }
     269        5918 :         return SPECIAL_TYPE_NONE;
     270             :     default:
     271             :         throw CannotDumpException(
     272           0 :             "unexpected nucleus \"" + nucleus
     273           0 :             + "\" in call to translateUnoTypeToDescriptor");
     274             :     }
     275             : }
     276             : 
     277       23848 : SpecialType translateUnoTypeToDescriptor(
     278             :     rtl::Reference< TypeManager > const & manager, OUString const & type,
     279             :     bool array, bool classType, Dependencies * dependencies,
     280             :     OStringBuffer * descriptor, OStringBuffer * signature,
     281             :     bool * needsSignature, PolymorphicUnoType * polymorphicUnoType)
     282             : {
     283             :     assert(manager.is());
     284       23848 :     OUString nucleus;
     285             :     sal_Int32 rank;
     286       47696 :     std::vector< OUString > args;
     287             :     codemaker::UnoType::Sort sort = manager->decompose(
     288       23848 :         type, true, &nucleus, &rank, &args, 0);
     289             :     return translateUnoTypeToDescriptor(
     290             :         manager, sort, nucleus, rank, args, array, classType, dependencies,
     291       47696 :         descriptor, signature, needsSignature, polymorphicUnoType);
     292             : }
     293             : 
     294        6556 : SpecialType getFieldDescriptor(
     295             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
     296             :     OUString const & type, OString * descriptor, OString * signature,
     297             :     PolymorphicUnoType * polymorphicUnoType)
     298             : {
     299             :     assert(descriptor != 0);
     300        6556 :     OStringBuffer desc;
     301       13112 :     OStringBuffer sig;
     302        6556 :     bool needsSig = false;
     303             :     SpecialType specialType = translateUnoTypeToDescriptor(
     304             :         manager, type, false, false, dependencies, &desc, &sig, &needsSig,
     305        6556 :         polymorphicUnoType);
     306        6556 :     *descriptor = desc.makeStringAndClear();
     307        6556 :     if (signature != 0) {
     308        4951 :         if (needsSig) {
     309           2 :             *signature = sig.makeStringAndClear();
     310             :         } else {
     311        4949 :             *signature = OString();
     312             :         }
     313             :     }
     314       13112 :     return specialType;
     315             : }
     316             : 
     317        7815 : class MethodDescriptor {
     318             : public:
     319             :     MethodDescriptor(
     320             :         rtl::Reference< TypeManager > const & manager,
     321             :         Dependencies * dependencies, OUString const & returnType,
     322             :         SpecialType * specialReturnType,
     323             :         PolymorphicUnoType * polymorphicUnoType);
     324             : 
     325             :     SpecialType addParameter(
     326             :         OUString const & type, bool array, bool dependency,
     327             :         PolymorphicUnoType * polymorphicUnoType);
     328             : 
     329             :     void addTypeParameter(OUString const & name);
     330             : 
     331             :     OString getDescriptor() const;
     332             : 
     333             :     OString getSignature() const;
     334             : 
     335             : private:
     336             :     rtl::Reference< TypeManager > m_manager;
     337             :     Dependencies * m_dependencies;
     338             :     OStringBuffer m_descriptorStart;
     339             :     OString m_descriptorEnd;
     340             :     OStringBuffer m_signatureStart;
     341             :     OString m_signatureEnd;
     342             :     bool m_needsSignature;
     343             : };
     344             : 
     345        7815 : MethodDescriptor::MethodDescriptor(
     346             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
     347             :     OUString const & returnType, SpecialType * specialReturnType,
     348             :     PolymorphicUnoType * polymorphicUnoType):
     349        7815 :     m_manager(manager), m_dependencies(dependencies), m_needsSignature(false)
     350             : {
     351             :     assert(dependencies != 0);
     352        7815 :     m_descriptorStart.append('(');
     353        7815 :     m_signatureStart.append('(');
     354        7815 :     OStringBuffer descEnd;
     355        7815 :     descEnd.append(')');
     356       15630 :     OStringBuffer sigEnd;
     357        7815 :     sigEnd.append(')');
     358             :     SpecialType special = translateUnoTypeToDescriptor(
     359             :         m_manager, returnType, false, false, m_dependencies, &descEnd, &sigEnd,
     360        7815 :         &m_needsSignature, polymorphicUnoType);
     361        7815 :     m_descriptorEnd = descEnd.makeStringAndClear();
     362        7815 :     m_signatureEnd = sigEnd.makeStringAndClear();
     363        7815 :     if (specialReturnType != 0) {
     364        6277 :         *specialReturnType = special;
     365        7815 :     }
     366        7815 : }
     367             : 
     368        9334 : SpecialType MethodDescriptor::addParameter(
     369             :     OUString const & type, bool array, bool dependency,
     370             :     PolymorphicUnoType * polymorphicUnoType)
     371             : {
     372             :     return translateUnoTypeToDescriptor(
     373             :         m_manager, type, array, false, dependency ? m_dependencies : 0,
     374             :         &m_descriptorStart, &m_signatureStart, &m_needsSignature,
     375        9334 :         polymorphicUnoType);
     376             : }
     377             : 
     378           8 : void MethodDescriptor::addTypeParameter(OUString const & name) {
     379           8 :     m_descriptorStart.append("Ljava/lang/Object;");
     380           8 :     m_signatureStart.append("T" + codemaker::convertString(name) + ";");
     381           8 :     m_needsSignature = true;
     382           8 : }
     383             : 
     384        8470 : OString MethodDescriptor::getDescriptor() const {
     385        8470 :     OStringBuffer buf(m_descriptorStart);
     386        8470 :     buf.append(m_descriptorEnd);
     387        8470 :     return buf.makeStringAndClear();
     388             : }
     389             : 
     390        7815 : OString MethodDescriptor::getSignature() const {
     391        7815 :     return m_needsSignature ?  m_signatureStart + m_signatureEnd : OString();
     392             : }
     393             : 
     394       40801 : class TypeInfo {
     395             : public:
     396             :     enum Kind { KIND_MEMBER, KIND_ATTRIBUTE, KIND_METHOD, KIND_PARAMETER };
     397             : 
     398             :     // Same values as in com/sun/star/lib/uno/typeinfo/TypeInfo.java:
     399             :     enum Flags {
     400             :         FLAG_READONLY = 0x008, FLAG_BOUND = 0x100
     401             :     };
     402             : 
     403             :     // KIND_MEMBER:
     404             :     TypeInfo(
     405             :         OString const & name, SpecialType specialType, sal_Int32 index,
     406             :         PolymorphicUnoType const & polymorphicUnoType,
     407             :         sal_Int32 typeParameterIndex);
     408             : 
     409             :     // KIND_ATTRIBUTE/METHOD:
     410             :     TypeInfo(
     411             :         Kind kind, OString const & name, SpecialType specialType, Flags flags,
     412             :         sal_Int32 index, PolymorphicUnoType const & polymorphicUnoType);
     413             : 
     414             :     // KIND_PARAMETER:
     415             :     TypeInfo(
     416             :         OString const & parameterName, SpecialType specialType,
     417             :         bool inParameter, bool outParameter, OString const & methodName,
     418             :         sal_Int32 index, PolymorphicUnoType const & polymorphicUnoType);
     419             : 
     420             :     sal_uInt16 generateCode(ClassFile::Code & code, Dependencies * dependencies)
     421             :         const;
     422             : 
     423             :     void generatePolymorphicUnoTypeCode(
     424             :         ClassFile::Code & code, Dependencies * dependencies) const;
     425             : 
     426             : private:
     427             :     Kind m_kind;
     428             :     OString m_name;
     429             :     sal_Int32 m_flags;
     430             :     sal_Int32 m_index;
     431             :     OString m_methodName;
     432             :     PolymorphicUnoType m_polymorphicUnoType;
     433             :     sal_Int32 m_typeParameterIndex;
     434             : };
     435             : 
     436        8125 : sal_Int32 translateSpecialTypeFlags(
     437             :     SpecialType specialType, bool inParameter, bool outParameter)
     438             : {
     439             :     static sal_Int32 const specialTypeFlags[SPECIAL_TYPE_INTERFACE + 1] = {
     440             :         0, 0x0040 /* ANY */, 0x0004 /* UNSIGNED */, 0x0080 /* INTERFACE */ };
     441        8125 :     sal_Int32 flags = specialTypeFlags[specialType];
     442        8125 :     if (inParameter) {
     443         135 :         flags |= 0x0001; /* IN */
     444             :     }
     445        8125 :     if (outParameter) {
     446         157 :         flags |= 0x0002; /* OUT */
     447             :     }
     448        8125 :     return flags;
     449             : }
     450             : 
     451        1613 : TypeInfo::TypeInfo(
     452             :     OString const & name, SpecialType specialType, sal_Int32 index,
     453             :     PolymorphicUnoType const & polymorphicUnoType,
     454             :     sal_Int32 typeParameterIndex):
     455             :     m_kind(KIND_MEMBER), m_name(name),
     456        1613 :     m_flags(translateSpecialTypeFlags(specialType, false, false)),
     457             :     m_index(index), m_polymorphicUnoType(polymorphicUnoType),
     458        3226 :     m_typeParameterIndex(typeParameterIndex)
     459             : {
     460             :     assert(
     461             :         polymorphicUnoType.kind == PolymorphicUnoType::KIND_NONE
     462             :         ? typeParameterIndex >= -1 : typeParameterIndex == -1);
     463        1613 : }
     464             : 
     465        6277 : TypeInfo::TypeInfo(
     466             :     Kind kind, OString const & name, SpecialType specialType, Flags flags,
     467             :     sal_Int32 index, PolymorphicUnoType const & polymorphicUnoType):
     468             :     m_kind(kind), m_name(name),
     469        6277 :     m_flags(flags | translateSpecialTypeFlags(specialType, false, false)),
     470             :     m_index(index), m_polymorphicUnoType(polymorphicUnoType),
     471       12554 :     m_typeParameterIndex(0)
     472             : {
     473             :     assert(kind == KIND_ATTRIBUTE || kind == KIND_METHOD);
     474        6277 : }
     475             : 
     476         235 : TypeInfo::TypeInfo(
     477             :     OString const & parameterName, SpecialType specialType, bool inParameter,
     478             :     bool outParameter, OString const & methodName, sal_Int32 index,
     479             :     PolymorphicUnoType const & polymorphicUnoType):
     480             :     m_kind(KIND_PARAMETER), m_name(parameterName),
     481         235 :     m_flags(translateSpecialTypeFlags(specialType, inParameter, outParameter)),
     482             :     m_index(index), m_methodName(methodName),
     483             :     m_polymorphicUnoType(polymorphicUnoType),
     484         470 :     m_typeParameterIndex(0)
     485         235 : {}
     486             : 
     487        8125 : sal_uInt16 TypeInfo::generateCode(
     488             :     ClassFile::Code & code, Dependencies * dependencies) const
     489             : {
     490        8125 :     switch (m_kind) {
     491             :     case KIND_MEMBER:
     492        1613 :         code.instrNew("com/sun/star/lib/uno/typeinfo/MemberTypeInfo");
     493        1613 :         code.instrDup();
     494        1613 :         code.loadStringConstant(m_name);
     495        1613 :         code.loadIntegerConstant(m_index);
     496        1613 :         code.loadIntegerConstant(m_flags);
     497        1613 :         if (m_polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE) {
     498           2 :             generatePolymorphicUnoTypeCode(code, dependencies);
     499           2 :             code.loadIntegerConstant(m_typeParameterIndex);
     500             :             code.instrInvokespecial(
     501             :                 "com/sun/star/lib/uno/typeinfo/MemberTypeInfo", "<init>",
     502           2 :                 "(Ljava/lang/String;IILcom/sun/star/uno/Type;I)V");
     503           2 :             return 8;
     504        1611 :         } else if (m_typeParameterIndex >= 0) {
     505           8 :             code.instrAconstNull();
     506           8 :             code.loadIntegerConstant(m_typeParameterIndex);
     507             :             code.instrInvokespecial(
     508             :                 "com/sun/star/lib/uno/typeinfo/MemberTypeInfo", "<init>",
     509           8 :                 "(Ljava/lang/String;IILcom/sun/star/uno/Type;I)V");
     510           8 :             return 6;
     511             :         } else {
     512             :             code.instrInvokespecial(
     513             :                 "com/sun/star/lib/uno/typeinfo/MemberTypeInfo", "<init>",
     514        1603 :                 "(Ljava/lang/String;II)V");
     515        1603 :             return 4;
     516             :         }
     517             :     case KIND_ATTRIBUTE:
     518         623 :         code.instrNew("com/sun/star/lib/uno/typeinfo/AttributeTypeInfo");
     519         623 :         code.instrDup();
     520         623 :         code.loadStringConstant(m_name);
     521         623 :         code.loadIntegerConstant(m_index);
     522         623 :         code.loadIntegerConstant(m_flags);
     523         623 :         if (m_polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE) {
     524           4 :             generatePolymorphicUnoTypeCode(code, dependencies);
     525             :             code.instrInvokespecial(
     526             :                 "com/sun/star/lib/uno/typeinfo/AttributeTypeInfo", "<init>",
     527           4 :                 "(Ljava/lang/String;IILcom/sun/star/uno/Type;)V");
     528           4 :             return 8;
     529             :         } else {
     530             :             code.instrInvokespecial(
     531             :                 "com/sun/star/lib/uno/typeinfo/AttributeTypeInfo", "<init>",
     532         619 :                 "(Ljava/lang/String;II)V");
     533         619 :             return 4;
     534             :         }
     535             :     case KIND_METHOD:
     536        5654 :         code.instrNew("com/sun/star/lib/uno/typeinfo/MethodTypeInfo");
     537        5654 :         code.instrDup();
     538        5654 :         code.loadStringConstant(m_name);
     539        5654 :         code.loadIntegerConstant(m_index);
     540        5654 :         code.loadIntegerConstant(m_flags);
     541        5654 :         if (m_polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE) {
     542          19 :             generatePolymorphicUnoTypeCode(code, dependencies);
     543             :             code.instrInvokespecial(
     544             :                 "com/sun/star/lib/uno/typeinfo/MethodTypeInfo", "<init>",
     545          19 :                 "(Ljava/lang/String;IILcom/sun/star/uno/Type;)V");
     546          19 :             return 8;
     547             :         } else {
     548             :             code.instrInvokespecial(
     549             :                 "com/sun/star/lib/uno/typeinfo/MethodTypeInfo", "<init>",
     550        5635 :                 "(Ljava/lang/String;II)V");
     551        5635 :             return 4;
     552             :         }
     553             :     case KIND_PARAMETER:
     554         235 :         code.instrNew("com/sun/star/lib/uno/typeinfo/ParameterTypeInfo");
     555         235 :         code.instrDup();
     556         235 :         code.loadStringConstant(m_name);
     557         235 :         code.loadStringConstant(m_methodName);
     558         235 :         code.loadIntegerConstant(m_index);
     559         235 :         code.loadIntegerConstant(m_flags);
     560         235 :         if (m_polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE) {
     561           5 :             generatePolymorphicUnoTypeCode(code, dependencies);
     562             :             code.instrInvokespecial(
     563             :                 "com/sun/star/lib/uno/typeinfo/ParameterTypeInfo", "<init>",
     564             :                 ("(Ljava/lang/String;Ljava/lang/String;II"
     565           5 :                  "Lcom/sun/star/uno/Type;)V"));
     566           5 :             return 9;
     567             :         } else {
     568             :             code.instrInvokespecial(
     569             :                 "com/sun/star/lib/uno/typeinfo/ParameterTypeInfo", "<init>",
     570         230 :                 "(Ljava/lang/String;Ljava/lang/String;II)V");
     571         230 :             return 5;
     572             :         }
     573             :     default:
     574             :         assert(false);
     575           0 :         return 0;
     576             :     }
     577             : }
     578             : 
     579          30 : void TypeInfo::generatePolymorphicUnoTypeCode(
     580             :     ClassFile::Code & code, Dependencies * dependencies) const
     581             : {
     582             :     assert(dependencies != 0);
     583             :     assert(m_polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE);
     584          30 :     code.instrNew("com/sun/star/uno/Type");
     585          30 :     code.instrDup();
     586             :     code.loadStringConstant(
     587          30 :         codemaker::convertString(m_polymorphicUnoType.name));
     588          30 :     if (m_polymorphicUnoType.kind == PolymorphicUnoType::KIND_STRUCT) {
     589             :         code.instrGetstatic(
     590             :             "com/sun/star/uno/TypeClass", "STRUCT",
     591          26 :             "Lcom/sun/star/uno/TypeClass;");
     592             :     } else {
     593             :         code.instrGetstatic(
     594             :             "com/sun/star/uno/TypeClass", "SEQUENCE",
     595           4 :             "Lcom/sun/star/uno/TypeClass;");
     596             :     }
     597          30 :     dependencies->insert("com.sun.star.uno.TypeClass");
     598             :     code.instrInvokespecial(
     599             :         "com/sun/star/uno/Type", "<init>",
     600          30 :         "(Ljava/lang/String;Lcom/sun/star/uno/TypeClass;)V");
     601          30 : }
     602             : 
     603        3271 : void writeClassFile(
     604             :     JavaOptions const & options, OString const & type,
     605             :     ClassFile const & classFile)
     606             : {
     607        3271 :     OString path;
     608        3271 :     if (options.isValid("-O")) {
     609        3271 :         path = options.getOption("-O");
     610             :     }
     611        6542 :     OString filename(createFileNameFromType(path, type, ".class"));
     612        3271 :     bool check = false;
     613        3271 :     if (fileExists(filename)) {
     614           0 :         if (options.isValid("-G")) {
     615        3271 :             return;
     616             :         }
     617           0 :         check = options.isValid("-Gc");
     618             :     }
     619        6542 :     FileStream tempfile;
     620        3271 :     tempfile.createTempFile(getTempDir(filename));
     621        3271 :     if (!tempfile.isValid()) {
     622             :         throw CannotDumpException(
     623           0 :             "Cannot create temporary file for " + b2u(filename));
     624             :     }
     625        6542 :     OString tempname(tempfile.getName());
     626             :     try {
     627        3271 :         classFile.write(tempfile);
     628           0 :     } catch (...) {
     629             :         // Remove existing file for consistency:
     630           0 :         if (fileExists(filename)) {
     631           0 :             removeTypeFile(filename);
     632             :         }
     633           0 :         tempfile.close();
     634           0 :         removeTypeFile(tempname);
     635           0 :         throw;
     636             :     }
     637        3271 :     tempfile.close();
     638        3271 :     if (!makeValidTypeFile(filename, tempname, check)) {
     639             :         throw CannotDumpException(
     640           0 :             "Cannot create " + b2u(filename) + " from temporary file "
     641           0 :             + b2u(tempname));
     642        3271 :     }
     643             : }
     644             : 
     645        2358 : void addTypeInfo(
     646             :     OString const & className, std::vector< TypeInfo > const & typeInfo,
     647             :     Dependencies * dependencies, ClassFile * classFile)
     648             : {
     649             :     assert(classFile != 0);
     650        2358 :     std::vector< TypeInfo >::size_type typeInfos = typeInfo.size();
     651        2358 :     if (typeInfos > SAL_MAX_INT32) {
     652             :         throw CannotDumpException(
     653           0 :             "UNOTYPEINFO array too big for Java class file format");
     654             :     }
     655        2358 :     if (typeInfos != 0) {
     656             :         classFile->addField(
     657             :             static_cast< ClassFile::AccessFlags >(
     658             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC
     659             :                 | ClassFile::ACC_FINAL),
     660             :             "UNOTYPEINFO", "[Lcom/sun/star/lib/uno/typeinfo/TypeInfo;",
     661        2118 :             0, "");
     662             :         SAL_WNODEPRECATED_DECLARATIONS_PUSH
     663        2118 :         std::auto_ptr< ClassFile::Code > code(classFile->newCode());
     664             :         SAL_WNODEPRECATED_DECLARATIONS_POP
     665        2118 :         code->loadIntegerConstant(static_cast< sal_Int32 >(typeInfos));
     666        2118 :         code->instrAnewarray("com/sun/star/lib/uno/typeinfo/TypeInfo");
     667        2118 :         sal_Int32 index = 0;
     668        2118 :         sal_uInt16 stack = 0;
     669       30729 :         for (std::vector< TypeInfo >::const_iterator i(typeInfo.begin());
     670       20486 :              i != typeInfo.end(); ++i)
     671             :         {
     672        8125 :             code->instrDup();
     673        8125 :             code->loadIntegerConstant(index++);
     674        8125 :             stack = std::max(stack, i->generateCode(*code, dependencies));
     675        8125 :             code->instrAastore();
     676             :         }
     677             :         code->instrPutstatic(
     678             :             className, "UNOTYPEINFO",
     679        2118 :             "[Lcom/sun/star/lib/uno/typeinfo/TypeInfo;");
     680        2118 :         code->instrReturn();
     681        2118 :         if (stack > SAL_MAX_UINT16 - 4) {
     682             :             throw CannotDumpException(
     683           0 :                 "Stack too big for Java class file format");
     684             :         }
     685        2118 :         code->setMaxStackAndLocals(static_cast< sal_uInt16 >(stack + 4), 0);
     686             :         classFile->addMethod(
     687             :             static_cast< ClassFile::AccessFlags >(
     688             :                 ClassFile::ACC_PRIVATE | ClassFile::ACC_STATIC),
     689        2118 :             "<clinit>", "()V", code.get(), std::vector< OString >(), "");
     690             :     }
     691        2358 : }
     692             : 
     693         195 : void handleEnumType(
     694             :     const OUString& name, rtl::Reference< unoidl::EnumTypeEntity > const & entity,
     695             :     JavaOptions const & options)
     696             : {
     697             :     assert(entity.is());
     698         195 :     OString className(codemaker::convertString(name).replace('.', '/'));
     699             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
     700             :     std::auto_ptr< ClassFile > cf(
     701             :         new ClassFile(
     702             :             static_cast< ClassFile::AccessFlags >(
     703             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_FINAL
     704             :                 | ClassFile::ACC_SUPER),
     705         390 :             className, "com/sun/star/uno/Enum", ""));
     706             :     SAL_WNODEPRECATED_DECLARATIONS_POP
     707         390 :     OString classDescriptor("L" + className + ";");
     708        4584 :     for (std::vector< unoidl::EnumTypeEntity::Member >::const_iterator i(
     709         195 :              entity->getMembers().begin());
     710        3056 :          i != entity->getMembers().end(); ++i)
     711             :     {
     712        1333 :         OString fieldName(codemaker::convertString(i->name));
     713             :         cf->addField(
     714             :             static_cast< ClassFile::AccessFlags >(
     715             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC
     716             :                 | ClassFile::ACC_FINAL),
     717        1333 :             fieldName, classDescriptor, 0, OString());
     718             :         cf->addField(
     719             :             static_cast< ClassFile::AccessFlags >(
     720             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC
     721             :                 | ClassFile::ACC_FINAL),
     722        2666 :             fieldName + "_value", "I",
     723        3999 :             cf->addIntegerInfo(i->value), "");
     724        1333 :     }
     725             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
     726         390 :     std::auto_ptr< ClassFile::Code > code(cf->newCode());
     727             :     SAL_WNODEPRECATED_DECLARATIONS_POP
     728         195 :     code->loadLocalReference(0);
     729         195 :     code->loadLocalInteger(1);
     730         195 :     code->instrInvokespecial("com/sun/star/uno/Enum", "<init>", "(I)V");
     731         195 :     code->instrReturn();
     732         195 :     code->setMaxStackAndLocals(2, 2);
     733             :     cf->addMethod(
     734             :         ClassFile::ACC_PRIVATE,
     735         195 :         "<init>", "(I)V", code.get(),
     736         390 :         std::vector< OString >(), "");
     737         195 :     code.reset(cf->newCode());
     738             :     code->instrGetstatic(
     739             :         className,
     740         195 :         codemaker::convertString(entity->getMembers()[0].name),
     741         195 :         classDescriptor);
     742         195 :     code->instrAreturn();
     743         195 :     code->setMaxStackAndLocals(1, 0);
     744             :     cf->addMethod(
     745             :         static_cast< ClassFile::AccessFlags >(
     746             :             ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC),
     747         390 :         "getDefault", "()" + classDescriptor,
     748         585 :         code.get(), std::vector< OString >(), "");
     749         195 :     code.reset(cf->newCode());
     750         195 :     code->loadLocalInteger(0);
     751         390 :     std::map< sal_Int32, OString > map;
     752         195 :     sal_Int32 min = SAL_MAX_INT32;
     753         195 :     sal_Int32 max = SAL_MIN_INT32;
     754        4584 :     for (std::vector< unoidl::EnumTypeEntity::Member >::const_iterator i(
     755         195 :              entity->getMembers().begin());
     756        3056 :          i != entity->getMembers().end(); ++i)
     757             :     {
     758        1333 :         min = std::min(min, i->value);
     759        1333 :         max = std::max(max, i->value);
     760             :         map.insert(
     761             :             std::map< sal_Int32, OString >::value_type(
     762        1333 :                 i->value, codemaker::convertString(i->name)));
     763             :     }
     764         195 :     sal_uInt64 size = static_cast< sal_uInt64 >(map.size());
     765         390 :     if ((static_cast< sal_uInt64 >(max) - static_cast< sal_uInt64 >(min)
     766         195 :          <= 2 * size)
     767           1 :         || size > SAL_MAX_INT32)
     768             :     {
     769             :         SAL_WNODEPRECATED_DECLARATIONS_PUSH
     770         194 :         std::auto_ptr< ClassFile::Code > defCode(cf->newCode());
     771             :         SAL_WNODEPRECATED_DECLARATIONS_POP
     772         194 :         defCode->instrAconstNull();
     773         194 :         defCode->instrAreturn();
     774         388 :         std::list< ClassFile::Code * > blocks;
     775             :             //FIXME: pointers contained in blocks may leak
     776         194 :         sal_Int32 last = SAL_MAX_INT32;
     777        4470 :         for (std::map< sal_Int32, OString >::iterator i(map.begin());
     778        2980 :              i != map.end(); ++i)
     779             :         {
     780        1296 :             sal_Int32 value = i->first;
     781        1296 :             if (last != SAL_MAX_INT32) {
     782        1107 :                 for (sal_Int32 j = last + 1; j < value; ++j) {
     783           5 :                     blocks.push_back(0);
     784             :                 }
     785             :             }
     786        1296 :             last = value;
     787             :             SAL_WNODEPRECATED_DECLARATIONS_PUSH
     788        1296 :             std::auto_ptr< ClassFile::Code > blockCode(cf->newCode());
     789             :             SAL_WNODEPRECATED_DECLARATIONS_POP
     790        1296 :             blockCode->instrGetstatic(className, i->second, classDescriptor);
     791        1296 :             blockCode->instrAreturn();
     792        1296 :             blocks.push_back(blockCode.get());
     793        1296 :             blockCode.release();
     794        1296 :         }
     795         194 :         code->instrTableswitch(defCode.get(), min, blocks);
     796        4485 :         for (std::list< ClassFile::Code * >::iterator i(blocks.begin());
     797        2990 :               i != blocks.end(); ++i)
     798             :         {
     799        1301 :             delete *i;
     800         194 :         }
     801             :     } else{
     802             :         SAL_WNODEPRECATED_DECLARATIONS_PUSH
     803           1 :         std::auto_ptr< ClassFile::Code > defCode(cf->newCode());
     804             :         SAL_WNODEPRECATED_DECLARATIONS_POP
     805           1 :         defCode->instrAconstNull();
     806           1 :         defCode->instrAreturn();
     807           2 :         std::list< std::pair< sal_Int32, ClassFile::Code * > > blocks;
     808             :             //FIXME: pointers contained in blocks may leak
     809         114 :         for (std::map< sal_Int32, OString >::iterator i(map.begin());
     810          76 :              i != map.end(); ++i)
     811             :         {
     812             :             SAL_WNODEPRECATED_DECLARATIONS_PUSH
     813          37 :             std::auto_ptr< ClassFile::Code > blockCode(cf->newCode());
     814             :             SAL_WNODEPRECATED_DECLARATIONS_POP
     815          37 :             blockCode->instrGetstatic(className, i->second, classDescriptor);
     816          37 :             blockCode->instrAreturn();
     817          37 :             blocks.push_back(std::make_pair(i->first, blockCode.get()));
     818          37 :             blockCode.release();
     819          37 :         }
     820           1 :         code->instrLookupswitch(defCode.get(), blocks);
     821         114 :         for (std::list< std::pair< sal_Int32, ClassFile::Code * > >::iterator
     822           1 :                  i(blocks.begin());
     823          76 :              i != blocks.end(); ++i)
     824             :         {
     825          37 :             delete i->second;
     826           1 :         }
     827             :     }
     828         195 :     code->setMaxStackAndLocals(1, 1);
     829             :     cf->addMethod(
     830             :         static_cast< ClassFile::AccessFlags >(
     831             :             ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC),
     832         390 :         "fromInt", "(I)" + classDescriptor, code.get(),
     833         585 :         std::vector< OString >(), "");
     834         195 :     code.reset(cf->newCode());
     835        4584 :     for (std::vector< unoidl::EnumTypeEntity::Member >::const_iterator i(
     836         195 :              entity->getMembers().begin());
     837        3056 :          i != entity->getMembers().end(); ++i)
     838             :     {
     839        1333 :         code->instrNew(className);
     840        1333 :         code->instrDup();
     841        1333 :         code->loadIntegerConstant(i->value);
     842        1333 :         code->instrInvokespecial(className, "<init>", "(I)V");
     843             :         code->instrPutstatic(
     844        1333 :             className, codemaker::convertString(i->name), classDescriptor);
     845             :     }
     846         195 :     code->instrReturn();
     847         195 :     code->setMaxStackAndLocals(3, 0);
     848             :     cf->addMethod(
     849             :         static_cast< ClassFile::AccessFlags >(
     850             :             ClassFile::ACC_PRIVATE | ClassFile::ACC_STATIC),
     851         195 :         "<clinit>", "()V", code.get(), std::vector< OString >(), "");
     852         390 :     writeClassFile(options, className, *cf.get());
     853         195 : }
     854             : 
     855        1613 : void addField(
     856             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
     857             :     ClassFile * classFile, std::vector< TypeInfo > * typeInfo,
     858             :     sal_Int32 typeParameterIndex, OUString const & type, OUString const & name,
     859             :     sal_Int32 index)
     860             : {
     861             :     assert(classFile != 0);
     862             :     assert(typeInfo != 0);
     863        1613 :     OString descriptor;
     864        3226 :     OString signature;
     865             :     SpecialType specialType;
     866        3226 :     PolymorphicUnoType polymorphicUnoType;
     867        1613 :     if (typeParameterIndex >= 0) {
     868           8 :         descriptor = "Ljava/lang/Object;";
     869          32 :         signature = "T" + codemaker::convertString(type).replace('.', '/')
     870          24 :             + ";";
     871           8 :         specialType = SPECIAL_TYPE_NONE; //TODO: SPECIAL_TYPE_TYPE_PARAMETER?
     872             :     } else {
     873             :         specialType = getFieldDescriptor(
     874             :             manager, dependencies, type, &descriptor, &signature,
     875        1605 :             &polymorphicUnoType);
     876             :     }
     877             :     classFile->addField(
     878             :         ClassFile::ACC_PUBLIC, codemaker::convertString(name), descriptor, 0,
     879        1613 :         signature);
     880             :     typeInfo->push_back(
     881             :         TypeInfo(
     882             :             codemaker::convertString(name), specialType, index,
     883        3226 :             polymorphicUnoType, typeParameterIndex));
     884        1613 : }
     885             : 
     886        1765 : sal_uInt16 addFieldInit(
     887             :     rtl::Reference< TypeManager > const & manager, OString const & className,
     888             :     OUString const & fieldName, bool typeParameter, OUString const & fieldType,
     889             :     Dependencies * dependencies, ClassFile::Code * code)
     890             : {
     891             :     assert(manager.is());
     892             :     assert(code != 0);
     893        1765 :     if (typeParameter) {
     894           8 :         return 0;
     895             :     }
     896        1757 :     OString name(codemaker::convertString(fieldName));
     897        3514 :     OUString nucleus;
     898             :     sal_Int32 rank;
     899        3514 :     std::vector< rtl::OUString > args;
     900        3514 :     rtl::Reference< unoidl::Entity > ent;
     901             :     codemaker::UnoType::Sort sort = manager->decompose(
     902        1757 :         fieldType, true, &nucleus, &rank, &args, &ent);
     903        1757 :     if (rank == 0) {
     904        1645 :         switch (sort) {
     905             :         case codemaker::UnoType::SORT_BOOLEAN:
     906             :         case codemaker::UnoType::SORT_BYTE:
     907             :         case codemaker::UnoType::SORT_SHORT:
     908             :         case codemaker::UnoType::SORT_UNSIGNED_SHORT:
     909             :         case codemaker::UnoType::SORT_LONG:
     910             :         case codemaker::UnoType::SORT_UNSIGNED_LONG:
     911             :         case codemaker::UnoType::SORT_HYPER:
     912             :         case codemaker::UnoType::SORT_UNSIGNED_HYPER:
     913             :         case codemaker::UnoType::SORT_FLOAT:
     914             :         case codemaker::UnoType::SORT_DOUBLE:
     915             :         case codemaker::UnoType::SORT_CHAR:
     916             :         case codemaker::UnoType::SORT_INTERFACE_TYPE:
     917         953 :             return 0;
     918             :         case codemaker::UnoType::SORT_STRING:
     919         425 :             code->loadLocalReference(0);
     920         425 :             code->loadStringConstant(OString());
     921         425 :             code->instrPutfield(className, name, "Ljava/lang/String;");
     922         425 :             return 2;
     923             :         case codemaker::UnoType::SORT_TYPE:
     924           5 :             code->loadLocalReference(0);
     925             :             code->instrGetstatic(
     926           5 :                 "com/sun/star/uno/Type", "VOID", "Lcom/sun/star/uno/Type;");
     927           5 :             code->instrPutfield(className, name, "Lcom/sun/star/uno/Type;");
     928           5 :             return 2;
     929             :         case codemaker::UnoType::SORT_ANY:
     930          99 :             code->loadLocalReference(0);
     931             :             code->instrGetstatic(
     932          99 :                 "com/sun/star/uno/Any", "VOID", "Lcom/sun/star/uno/Any;");
     933          99 :             code->instrPutfield(className, name, "Ljava/lang/Object;");
     934          99 :             return 2;
     935             :         case codemaker::UnoType::SORT_ENUM_TYPE:
     936             :             {
     937             :                 rtl::Reference< unoidl::EnumTypeEntity > ent2(
     938          67 :                     dynamic_cast< unoidl::EnumTypeEntity * >(ent.get()));
     939             :                 assert(ent2.is());
     940          67 :                 code->loadLocalReference(0);
     941         134 :                 OStringBuffer descBuf;
     942             :                 translateUnoTypeToDescriptor(
     943             :                     manager, sort, nucleus, 0, std::vector< OUString >(), false,
     944          67 :                     false, dependencies, &descBuf, 0, 0, 0);
     945         134 :                 OString desc(descBuf.makeStringAndClear());
     946             :                 code->instrGetstatic(
     947             :                     codemaker::convertString(nucleus).replace('.', '/'),
     948          67 :                     codemaker::convertString(ent2->getMembers()[0].name), desc);
     949          67 :                 code->instrPutfield(className, name, desc);
     950         134 :                 return 2;
     951             :             }
     952             :         case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
     953             :         case codemaker::UnoType::SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE:
     954             :             {
     955          96 :                 code->loadLocalReference(0);
     956             :                 code->instrNew(
     957          96 :                     codemaker::convertString(nucleus).replace('.', '/'));
     958          96 :                 code->instrDup();
     959             :                 code->instrInvokespecial(
     960             :                     codemaker::convertString(nucleus).replace('.', '/'),
     961          96 :                     "<init>", "()V");
     962          96 :                 OStringBuffer desc;
     963             :                 translateUnoTypeToDescriptor(
     964             :                     manager, sort, nucleus, 0, args, false, false, dependencies,
     965          96 :                     &desc, 0, 0, 0);
     966          96 :                 code->instrPutfield(className, name, desc.makeStringAndClear());
     967          96 :                 return 3;
     968             :             }
     969             :         case codemaker::UnoType::SORT_SEQUENCE_TYPE:
     970             :         case codemaker::UnoType::SORT_TYPEDEF:
     971             :             assert(false); // this cannot happen
     972             :             // fall through
     973             :         default:
     974             :             throw CannotDumpException(
     975           0 :                 "unexpected entity \"" + fieldType
     976           0 :                 + "\" in call to addFieldInit");
     977             :         }
     978             :     }
     979         112 :     code->loadLocalReference(0);
     980         112 :     code->loadIntegerConstant(0);
     981         112 :     if (rank == 1) {
     982         103 :         if (sort >= codemaker::UnoType::SORT_BOOLEAN
     983         103 :             && sort <= codemaker::UnoType::SORT_CHAR)
     984             :         {
     985          27 :             code->instrNewarray(sort);
     986             :         } else {
     987             :             code->instrAnewarray(
     988             :                 codemaker::java::translateUnoToJavaType(
     989             :                     sort, codemaker::convertString(nucleus).replace('.', '/'),
     990          76 :                     false));
     991             :         }
     992             :     } else {
     993           9 :         OStringBuffer desc;
     994             :         translateUnoTypeToDescriptor(
     995             :             manager, sort, nucleus, rank - 1, std::vector< OUString >(), false,
     996           9 :             false, dependencies, &desc, 0, 0, 0);
     997           9 :         code->instrAnewarray(desc.makeStringAndClear());
     998             :     }
     999         112 :     OStringBuffer desc;
    1000             :     translateUnoTypeToDescriptor(
    1001             :         manager, sort, nucleus, rank, std::vector< OUString >(), false, false,
    1002         112 :         dependencies, &desc, 0, 0, 0);
    1003         112 :     code->instrPutfield(className, name, desc.makeStringAndClear());
    1004        1869 :     return 2;
    1005             : }
    1006             : 
    1007        2407 : sal_uInt16 addLoadLocal(
    1008             :     rtl::Reference< TypeManager > const & manager, ClassFile::Code * code,
    1009             :     sal_uInt16 * index, bool typeParameter, OUString const & type, bool any,
    1010             :     Dependencies * dependencies)
    1011             : {
    1012             :     assert(manager.is());
    1013             :     assert(code != 0);
    1014             :     assert(index != 0);
    1015             :     assert(!(typeParameter && any));
    1016             :     assert(dependencies != 0);
    1017        2407 :     sal_uInt16 stack = 1;
    1018        2407 :     sal_uInt16 size = 1;
    1019        2407 :     if (typeParameter) {
    1020           8 :         code->loadLocalReference(*index);
    1021           8 :         stack = size = 1;
    1022             :     } else {
    1023        2399 :         OUString nucleus;
    1024             :         sal_Int32 rank;
    1025        4798 :         std::vector< OUString > args;
    1026             :         codemaker::UnoType::Sort sort = manager->decompose(
    1027        2399 :             type, true, &nucleus, &rank, &args, 0);
    1028        2399 :         if (rank == 0) {
    1029        2251 :             switch (sort) {
    1030             :             case codemaker::UnoType::SORT_BOOLEAN:
    1031         175 :                 if (any) {
    1032          20 :                     code->instrNew("java/lang/Boolean");
    1033          20 :                     code->instrDup();
    1034          20 :                     code->loadLocalInteger(*index);
    1035             :                     code->instrInvokespecial(
    1036          20 :                         "java/lang/Boolean", "<init>", "(Z)V");
    1037          20 :                     stack = 3;
    1038             :                 } else {
    1039         155 :                     code->loadLocalInteger(*index);
    1040         155 :                     stack = 1;
    1041             :                 }
    1042         175 :                 size = 1;
    1043         175 :                 break;
    1044             :             case codemaker::UnoType::SORT_BYTE:
    1045          49 :                 if (any) {
    1046           1 :                     code->instrNew("java/lang/Byte");
    1047           1 :                     code->instrDup();
    1048           1 :                     code->loadLocalInteger(*index);
    1049             :                     code->instrInvokespecial(
    1050           1 :                         "java/lang/Byte", "<init>", "(B)V");
    1051           1 :                     stack = 3;
    1052             :                 } else {
    1053          48 :                     code->loadLocalInteger(*index);
    1054          48 :                     stack = 1;
    1055             :                 }
    1056          49 :                 size = 1;
    1057          49 :                 break;
    1058             :             case codemaker::UnoType::SORT_SHORT:
    1059         142 :                 if (any) {
    1060           3 :                     code->instrNew("java/lang/Short");
    1061           3 :                     code->instrDup();
    1062           3 :                     code->loadLocalInteger(*index);
    1063             :                     code->instrInvokespecial(
    1064           3 :                         "java/lang/Short", "<init>", "(S)V");
    1065           3 :                     stack = 3;
    1066             :                 } else {
    1067         139 :                     code->loadLocalInteger(*index);
    1068         139 :                     stack = 1;
    1069             :                 }
    1070         142 :                 size = 1;
    1071         142 :                 break;
    1072             :             case codemaker::UnoType::SORT_UNSIGNED_SHORT:
    1073          36 :                 if (any) {
    1074           1 :                     code->instrNew("com/sun/star/uno/Any");
    1075           1 :                     code->instrDup();
    1076             :                     code->instrGetstatic(
    1077             :                         "com/sun/star/uno/Type", "UNSIGNED_SHORT",
    1078           1 :                         "Lcom/sun/star/uno/Type;");
    1079           1 :                     code->instrNew("java/lang/Short");
    1080           1 :                     code->instrDup();
    1081           1 :                     code->loadLocalInteger(*index);
    1082             :                     code->instrInvokespecial(
    1083           1 :                         "java/lang/Short", "<init>", "(S)V");
    1084             :                     code->instrInvokespecial(
    1085             :                         "com/sun/star/uno/Any", "<init>",
    1086           1 :                         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1087           1 :                     stack = 6;
    1088             :                 } else {
    1089          35 :                     code->loadLocalInteger(*index);
    1090          35 :                     stack = 1;
    1091             :                 }
    1092          36 :                 size = 1;
    1093          36 :                 break;
    1094             :             case codemaker::UnoType::SORT_LONG:
    1095         325 :                 if (any) {
    1096          10 :                     code->instrNew("java/lang/Integer");
    1097          10 :                     code->instrDup();
    1098          10 :                     code->loadLocalInteger(*index);
    1099             :                     code->instrInvokespecial(
    1100          10 :                         "java/lang/Integer", "<init>", "(I)V");
    1101          10 :                     stack = 3;
    1102             :                 } else {
    1103         315 :                     code->loadLocalInteger(*index);
    1104         315 :                     stack = 1;
    1105             :                 }
    1106         325 :                 size = 1;
    1107         325 :                 break;
    1108             :             case codemaker::UnoType::SORT_UNSIGNED_LONG:
    1109          20 :                 if (any) {
    1110           1 :                     code->instrNew("com/sun/star/uno/Any");
    1111           1 :                     code->instrDup();
    1112             :                     code->instrGetstatic(
    1113             :                         "com/sun/star/uno/Type", "UNSIGNED_LONG",
    1114           1 :                         "Lcom/sun/star/uno/Type;");
    1115           1 :                     code->instrNew("java/lang/Integer");
    1116           1 :                     code->instrDup();
    1117           1 :                     code->loadLocalInteger(*index);
    1118             :                     code->instrInvokespecial(
    1119           1 :                         "java/lang/Integer", "<init>", "(I)V");
    1120             :                     code->instrInvokespecial(
    1121             :                         "com/sun/star/uno/Any", "<init>",
    1122           1 :                         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1123           1 :                     stack = 6;
    1124             :                 } else {
    1125          19 :                     code->loadLocalInteger(*index);
    1126          19 :                     stack = 1;
    1127             :                 }
    1128          20 :                 size = 1;
    1129          20 :                 break;
    1130             :             case codemaker::UnoType::SORT_HYPER:
    1131          29 :                 if (any) {
    1132           1 :                     code->instrNew("java/lang/Long");
    1133           1 :                     code->instrDup();
    1134           1 :                     code->loadLocalLong(*index);
    1135             :                     code->instrInvokespecial(
    1136           1 :                         "java/lang/Long", "<init>", "(J)V");
    1137           1 :                     stack = 4;
    1138             :                 } else {
    1139          28 :                     code->loadLocalLong(*index);
    1140          28 :                     stack = 2;
    1141             :                 }
    1142          29 :                 size = 2;
    1143          29 :                 break;
    1144             :             case codemaker::UnoType::SORT_UNSIGNED_HYPER:
    1145           7 :                 if (any) {
    1146           1 :                     code->instrNew("com/sun/star/uno/Any");
    1147           1 :                     code->instrDup();
    1148             :                     code->instrGetstatic(
    1149             :                         "com/sun/star/uno/Type", "UNSIGNED_HYPER",
    1150           1 :                         "Lcom/sun/star/uno/Type;");
    1151           1 :                     code->instrNew("java/lang/Long");
    1152           1 :                     code->instrDup();
    1153           1 :                     code->loadLocalLong(*index);
    1154             :                     code->instrInvokespecial(
    1155           1 :                         "java/lang/Long", "<init>", "(J)V");
    1156             :                     code->instrInvokespecial(
    1157             :                         "com/sun/star/uno/Any", "<init>",
    1158           1 :                         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1159           1 :                     stack = 7;
    1160             :                 } else {
    1161           6 :                     code->loadLocalLong(*index);
    1162           6 :                     stack = 2;
    1163             :                 }
    1164           7 :                 size = 2;
    1165           7 :                 break;
    1166             :             case codemaker::UnoType::SORT_FLOAT:
    1167          19 :                 if (any) {
    1168           1 :                     code->instrNew("java/lang/Float");
    1169           1 :                     code->instrDup();
    1170           1 :                     code->loadLocalFloat(*index);
    1171             :                     code->instrInvokespecial(
    1172           1 :                         "java/lang/Float", "<init>", "(F)V");
    1173           1 :                     stack = 3;
    1174             :                 } else {
    1175          18 :                     code->loadLocalFloat(*index);
    1176          18 :                     stack = 1;
    1177             :                 }
    1178          19 :                 size = 1;
    1179          19 :                 break;
    1180             :             case codemaker::UnoType::SORT_DOUBLE:
    1181         112 :                 if (any) {
    1182           1 :                     code->instrNew("java/lang/Double");
    1183           1 :                     code->instrDup();
    1184           1 :                     code->loadLocalDouble(*index);
    1185             :                     code->instrInvokespecial(
    1186           1 :                         "java/lang/Double", "<init>", "(D)V");
    1187           1 :                     stack = 4;
    1188             :                 } else {
    1189         111 :                     code->loadLocalDouble(*index);
    1190         111 :                     stack = 2;
    1191             :                 }
    1192         112 :                 size = 2;
    1193         112 :                 break;
    1194             :             case codemaker::UnoType::SORT_CHAR:
    1195          13 :                 if (any) {
    1196           1 :                     code->instrNew("java/lang/Character");
    1197           1 :                     code->instrDup();
    1198           1 :                     code->loadLocalInteger(*index);
    1199             :                     code->instrInvokespecial(
    1200           1 :                         "java/lang/Character", "<init>", "(C)V");
    1201           1 :                     stack = 3;
    1202             :                 } else {
    1203          12 :                     code->loadLocalInteger(*index);
    1204          12 :                     stack = 1;
    1205             :                 }
    1206          13 :                 size = 1;
    1207          13 :                 break;
    1208             :             case codemaker::UnoType::SORT_STRING:
    1209             :             case codemaker::UnoType::SORT_TYPE:
    1210             :             case codemaker::UnoType::SORT_ANY:
    1211         572 :                 code->loadLocalReference(*index);
    1212         572 :                 stack = size = 1;
    1213         572 :                 break;
    1214             :             case codemaker::UnoType::SORT_ENUM_TYPE:
    1215             :                 // Assuming that no Java types are derived from Java types that
    1216             :                 // are directly derived from com.sun.star.uno.Enum:
    1217         106 :                 code->loadLocalReference(*index);
    1218         106 :                 stack = size = 1;
    1219         106 :                 break;
    1220             :             case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
    1221             :             case codemaker::UnoType::SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE:
    1222         137 :                 if (any) {
    1223          43 :                     code->instrNew("com/sun/star/uno/Any");
    1224          43 :                     code->instrDup();
    1225          43 :                     code->instrNew("com/sun/star/uno/Type");
    1226          43 :                     code->instrDup();
    1227             :                     code->loadStringConstant(
    1228             :                         codemaker::convertString(
    1229          43 :                             createUnoName(manager, nucleus, rank, args)));
    1230             :                     code->instrGetstatic(
    1231             :                         "com/sun/star/uno/TypeClass", "STRUCT",
    1232          43 :                         "Lcom/sun/star/uno/TypeClass;");
    1233          43 :                     dependencies->insert("com.sun.star.uno.TypeClass");
    1234             :                     code->instrInvokespecial(
    1235             :                         "com/sun/star/uno/Type", "<init>",
    1236          43 :                         "(Ljava/lang/String;Lcom/sun/star/uno/TypeClass;)V");
    1237          43 :                     code->loadLocalReference(*index);
    1238             :                     code->instrInvokespecial(
    1239             :                         "com/sun/star/uno/Any", "<init>",
    1240          43 :                         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1241          43 :                     stack = 6;
    1242             :                 } else {
    1243          94 :                     code->loadLocalReference(*index);
    1244          94 :                     stack = 1;
    1245             :                 }
    1246         137 :                 size = 1;
    1247         137 :                 break;
    1248             :             case codemaker::UnoType::SORT_INTERFACE_TYPE:
    1249         509 :                 if (any && nucleus != "com.sun.star.uno.XInterface") {
    1250          77 :                     code->instrNew("com/sun/star/uno/Any");
    1251          77 :                     code->instrDup();
    1252          77 :                     code->instrNew("com/sun/star/uno/Type");
    1253          77 :                     code->instrDup();
    1254          77 :                     code->loadStringConstant(codemaker::convertString(nucleus));
    1255             :                     code->instrGetstatic(
    1256             :                         "com/sun/star/uno/TypeClass", "INTERFACE",
    1257          77 :                         "Lcom/sun/star/uno/TypeClass;");
    1258          77 :                     dependencies->insert("com.sun.star.uno.TypeClass");
    1259             :                     code->instrInvokespecial(
    1260             :                         "com/sun/star/uno/Type", "<init>",
    1261          77 :                         "(Ljava/lang/String;Lcom/sun/star/uno/TypeClass;)V");
    1262          77 :                     code->loadLocalReference(*index);
    1263             :                     code->instrInvokespecial(
    1264             :                         "com/sun/star/uno/Any", "<init>",
    1265          77 :                         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1266          77 :                     stack = 6;
    1267             :                 } else {
    1268         432 :                     code->loadLocalReference(*index);
    1269         432 :                     stack = 1;
    1270             :                 }
    1271         509 :                 size = 1;
    1272         509 :                 break;
    1273             :             case codemaker::UnoType::SORT_SEQUENCE_TYPE:
    1274             :             case codemaker::UnoType::SORT_TYPEDEF:
    1275             :                 assert(false); // this cannot happen
    1276             :                 // fall through
    1277             :             default:
    1278             :                 throw CannotDumpException(
    1279           0 :                     "unexpected entity \"" + type
    1280           0 :                     + "\" in call to addLoadLocal");
    1281             :             }
    1282             :         } else {
    1283         148 :             bool wrap = false;
    1284         148 :             if (any) {
    1285          43 :                 switch (sort) {
    1286             :                 case codemaker::UnoType::SORT_BOOLEAN:
    1287             :                 case codemaker::UnoType::SORT_BYTE:
    1288             :                 case codemaker::UnoType::SORT_SHORT:
    1289             :                 case codemaker::UnoType::SORT_LONG:
    1290             :                 case codemaker::UnoType::SORT_HYPER:
    1291             :                 case codemaker::UnoType::SORT_FLOAT:
    1292             :                 case codemaker::UnoType::SORT_DOUBLE:
    1293             :                 case codemaker::UnoType::SORT_CHAR:
    1294             :                 case codemaker::UnoType::SORT_STRING:
    1295             :                 case codemaker::UnoType::SORT_TYPE:
    1296             :                         // assuming that no Java types are derived from
    1297             :                         // com.sun.star.uno.Type
    1298             :                 case codemaker::UnoType::SORT_ENUM_TYPE:
    1299             :                         // assuming that no Java types are derived from Java
    1300             :                         // types that are directly derived from
    1301             :                         // com.sun.star.uno.Enum
    1302          17 :                     break;
    1303             :                 case codemaker::UnoType::SORT_UNSIGNED_SHORT:
    1304             :                 case codemaker::UnoType::SORT_UNSIGNED_LONG:
    1305             :                 case codemaker::UnoType::SORT_UNSIGNED_HYPER:
    1306             :                 case codemaker::UnoType::SORT_ANY:
    1307             :                 case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
    1308             :                 case codemaker::UnoType::
    1309             :                     SORT_INSTANTIATED_POLYMORPHIC_STRUCT_TYPE:
    1310             :                 case codemaker::UnoType::SORT_INTERFACE_TYPE:
    1311          26 :                     wrap = true;
    1312          26 :                     break;
    1313             :                 case codemaker::UnoType::SORT_SEQUENCE_TYPE:
    1314             :                 case codemaker::UnoType::SORT_TYPEDEF:
    1315             :                     assert(false); // this cannot happen
    1316             :                     // fall through
    1317             :                 default:
    1318             :                     throw CannotDumpException(
    1319           0 :                         "unexpected entity \"" + type
    1320           0 :                         + "\" in call to addLoadLocal");
    1321             :                 }
    1322             :             }
    1323         148 :             if (wrap) {
    1324          26 :                 code->instrNew("com/sun/star/uno/Any");
    1325          26 :                 code->instrDup();
    1326          26 :                 code->instrNew("com/sun/star/uno/Type");
    1327          26 :                 code->instrDup();
    1328             :                 code->loadStringConstant(
    1329             :                     codemaker::convertString(
    1330          26 :                         createUnoName(manager, nucleus, rank, args)));
    1331             :                 code->instrInvokespecial(
    1332          26 :                     "com/sun/star/uno/Type", "<init>", "(Ljava/lang/String;)V");
    1333          26 :                 code->loadLocalReference(*index);
    1334             :                 code->instrInvokespecial(
    1335             :                     "com/sun/star/uno/Any", "<init>",
    1336          26 :                     "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)V");
    1337          26 :                 stack = 5;
    1338             :             } else {
    1339         122 :                 code->loadLocalReference(*index);
    1340         122 :                 stack = 1;
    1341             :             }
    1342         148 :             size = 1;
    1343        2399 :         }
    1344             :     }
    1345        2407 :     if (*index > SAL_MAX_UINT16 - size) {
    1346             :         throw CannotDumpException(
    1347           0 :             "Too many local variables for Java class file format");
    1348             :     }
    1349        2407 :     *index = *index + size;
    1350        2407 :     return stack;
    1351             : }
    1352             : 
    1353        1613 : sal_uInt16 addDirectArgument(
    1354             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
    1355             :     MethodDescriptor * methodDescriptor, ClassFile::Code * code,
    1356             :     sal_uInt16 * index, OString const & className, OString const & fieldName,
    1357             :     bool typeParameter, OUString const & fieldType)
    1358             : {
    1359             :     assert(methodDescriptor != 0);
    1360             :     assert(code != 0);
    1361        1613 :     OString desc;
    1362        1613 :     if (typeParameter) {
    1363           8 :         methodDescriptor->addTypeParameter(fieldType);
    1364           8 :         desc = "Ljava/lang/Object;";
    1365             :     } else {
    1366        1605 :         methodDescriptor->addParameter(fieldType, false, true, 0);
    1367        1605 :         getFieldDescriptor(manager, dependencies, fieldType, &desc, 0, 0);
    1368             :     }
    1369        1613 :     code->loadLocalReference(0);
    1370             :     sal_uInt16 stack = addLoadLocal(
    1371        1613 :         manager, code, index, typeParameter, fieldType, false, dependencies);
    1372        1613 :     code->instrPutfield(className, fieldName, desc);
    1373        1613 :     return stack + 1;
    1374             : }
    1375             : 
    1376         115 : void addPlainStructBaseArguments(
    1377             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
    1378             :     MethodDescriptor * methodDescriptor, ClassFile::Code * code,
    1379             :     OUString const & base, sal_uInt16 * index)
    1380             : {
    1381             :     assert(manager.is());
    1382             :     assert(methodDescriptor != 0);
    1383         115 :     rtl::Reference< unoidl::Entity > ent;
    1384         115 :     if (manager->getSort(base, &ent)
    1385             :         != codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE)
    1386             :     {
    1387             :         throw CannotDumpException(
    1388           0 :             "unexpected entity \"" + base
    1389           0 :             + "\" in call to addPlainStructBaseArguments");
    1390             :     }
    1391             :     rtl::Reference< unoidl::PlainStructTypeEntity > ent2(
    1392         230 :         dynamic_cast< unoidl::PlainStructTypeEntity * >(ent.get()));
    1393             :     assert(ent2.is());
    1394         115 :     if (!ent2->getDirectBase().isEmpty()) {
    1395             :         addPlainStructBaseArguments(
    1396             :             manager, dependencies, methodDescriptor, code,
    1397          15 :             ent2->getDirectBase(), index);
    1398             :     }
    1399         936 :     for (std::vector< unoidl::PlainStructTypeEntity::Member >::const_iterator i(
    1400         115 :              ent2->getDirectMembers().begin());
    1401         624 :          i != ent2->getDirectMembers().end(); ++i)
    1402             :     {
    1403         197 :         methodDescriptor->addParameter(i->type, false, true, 0);
    1404         197 :         addLoadLocal(manager, code, index, false, i->type, false, dependencies);
    1405         115 :     }
    1406         115 : }
    1407             : 
    1408         405 : void handlePlainStructType(
    1409             :     const OUString& name,
    1410             :     rtl::Reference< unoidl::PlainStructTypeEntity > const & entity,
    1411             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    1412             :     Dependencies * dependencies)
    1413             : {
    1414             :     assert(entity.is());
    1415             :     assert(dependencies != 0);
    1416         405 :     OString className(codemaker::convertString(name).replace('.', '/'));
    1417         810 :     OString superClass;
    1418         405 :     if (entity->getDirectBase().isEmpty()) {
    1419         305 :         superClass = "java/lang/Object";
    1420             :     } else {
    1421         200 :         superClass = codemaker::convertString(entity->getDirectBase()).
    1422         100 :             replace('.', '/');
    1423         100 :         dependencies->insert(entity->getDirectBase());
    1424             :     }
    1425             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1426             :     std::auto_ptr< ClassFile > cf(
    1427             :         new ClassFile(
    1428             :             static_cast< ClassFile::AccessFlags >(
    1429             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_SUPER),
    1430         810 :             className, superClass, ""));
    1431             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1432         810 :     std::vector< TypeInfo > typeInfo;
    1433         405 :     sal_Int32 index = 0;
    1434        5565 :     for (std::vector< unoidl::PlainStructTypeEntity::Member >::const_iterator i(
    1435         405 :              entity->getDirectMembers().begin());
    1436        3710 :          i != entity->getDirectMembers().end(); ++i)
    1437             :     {
    1438             :         addField(
    1439        2900 :             manager, dependencies, cf.get(), &typeInfo, -1, i->type, i->name,
    1440        4350 :             index++);
    1441             :     }
    1442             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1443         810 :     std::auto_ptr< ClassFile::Code > code(cf->newCode());
    1444             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1445         405 :     code->loadLocalReference(0);
    1446         405 :     code->instrInvokespecial(superClass, "<init>", "()V");
    1447         405 :     sal_uInt16 stack = 0;
    1448        5565 :     for (std::vector< unoidl::PlainStructTypeEntity::Member >::const_iterator i(
    1449         405 :              entity->getDirectMembers().begin());
    1450        3710 :          i != entity->getDirectMembers().end(); ++i)
    1451             :     {
    1452             :         stack = std::max(
    1453             :             stack,
    1454             :             addFieldInit(
    1455        2900 :                 manager, className, i->name, false, i->type, dependencies,
    1456        4350 :                 code.get()));
    1457             :     }
    1458         405 :     code->instrReturn();
    1459         405 :     code->setMaxStackAndLocals(stack + 1, 1);
    1460             :     cf->addMethod(
    1461         405 :         ClassFile::ACC_PUBLIC, "<init>", "()V", code.get(),
    1462         810 :         std::vector< OString >(), "");
    1463         810 :     MethodDescriptor desc(manager, dependencies, "void", 0, 0);
    1464         405 :     code.reset(cf->newCode());
    1465         405 :     code->loadLocalReference(0);
    1466         405 :     sal_uInt16 index2 = 1;
    1467         405 :     if (!entity->getDirectBase().isEmpty()) {
    1468             :         addPlainStructBaseArguments(
    1469             :             manager, dependencies, &desc, code.get(), entity->getDirectBase(),
    1470         100 :             &index2);
    1471             :     }
    1472         405 :     code->instrInvokespecial(superClass, "<init>", desc.getDescriptor());
    1473         405 :     sal_uInt16 maxSize = index2;
    1474        5565 :     for (std::vector< unoidl::PlainStructTypeEntity::Member >::const_iterator i(
    1475         405 :              entity->getDirectMembers().begin());
    1476        3710 :          i != entity->getDirectMembers().end(); ++i)
    1477             :     {
    1478             :         maxSize = std::max(
    1479             :             maxSize,
    1480             :             addDirectArgument(
    1481             :                 manager, dependencies, &desc, code.get(), &index2, className,
    1482        1450 :                 codemaker::convertString(i->name), false, i->type));
    1483             :     }
    1484         405 :     code->instrReturn();
    1485         405 :     code->setMaxStackAndLocals(maxSize, index2);
    1486             :     cf->addMethod(
    1487         405 :         ClassFile::ACC_PUBLIC, "<init>", desc.getDescriptor(), code.get(),
    1488         810 :         std::vector< OString >(), desc.getSignature());
    1489         405 :     addTypeInfo(className, typeInfo, dependencies, cf.get());
    1490         810 :     writeClassFile(options, className, *cf.get());
    1491         405 : }
    1492             : 
    1493           6 : void handlePolyStructType(
    1494             :     const OUString& name,
    1495             :     rtl::Reference< unoidl::PolymorphicStructTypeTemplateEntity > const &
    1496             :         entity,
    1497             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    1498             :     Dependencies * dependencies)
    1499             : {
    1500             :     assert(entity.is());
    1501           6 :     OString className(codemaker::convertString(name).replace('.', '/'));
    1502          12 :     std::map< OUString, sal_Int32 > typeParameters;
    1503          12 :     OStringBuffer sig("<");
    1504           6 :     sal_Int32 index = 0;
    1505          42 :     for (std::vector< OUString >::const_iterator i(
    1506           6 :              entity->getTypeParameters().begin());
    1507          28 :          i != entity->getTypeParameters().end(); ++i)
    1508             :     {
    1509           8 :         sig.append(codemaker::convertString(*i) + ":Ljava/lang/Object;");
    1510          16 :         if (!typeParameters.insert(
    1511          16 :                 std::map< OUString, sal_Int32 >::value_type(*i, index++)).
    1512          16 :             second)
    1513             :         {
    1514           0 :             throw CannotDumpException("Bad type information"); //TODO
    1515             :         }
    1516             :     }
    1517           6 :     sig.append(">Ljava/lang/Object;");
    1518             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1519             :     std::auto_ptr< ClassFile > cf(
    1520             :         new ClassFile(
    1521             :             static_cast< ClassFile::AccessFlags >(
    1522             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_SUPER),
    1523          12 :             className, "java/lang/Object", sig.makeStringAndClear()));
    1524             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1525          12 :     std::vector< TypeInfo > typeInfo;
    1526           6 :     index = 0;
    1527          51 :     for (std::vector< unoidl::PolymorphicStructTypeTemplateEntity::Member >::
    1528           6 :              const_iterator i(entity->getMembers().begin());
    1529          34 :          i != entity->getMembers().end(); ++i)
    1530             :     {
    1531             :         sal_Int32 typeParameterIndex;
    1532          11 :         if (i->parameterized) {
    1533             :             std::map< OUString, sal_Int32 >::iterator it(
    1534           8 :                 typeParameters.find(i->type));
    1535           8 :             if (it == typeParameters.end()) {
    1536           0 :                 throw CannotDumpException("Bad type information"); //TODO
    1537             :             }
    1538           8 :             typeParameterIndex = it->second;
    1539             :         } else {
    1540           3 :             typeParameterIndex = -1;
    1541             :         }
    1542             :         addField(
    1543             :             manager, dependencies, cf.get(), &typeInfo, typeParameterIndex,
    1544          11 :             i->type, i->name, index++);
    1545             :     }
    1546             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1547          12 :     std::auto_ptr< ClassFile::Code > code(cf->newCode());
    1548             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1549           6 :     code->loadLocalReference(0);
    1550           6 :     code->instrInvokespecial("java/lang/Object", "<init>", "()V");
    1551           6 :     sal_uInt16 stack = 0;
    1552          51 :     for (std::vector< unoidl::PolymorphicStructTypeTemplateEntity::Member >::
    1553           6 :              const_iterator i(entity->getMembers().begin());
    1554          34 :          i != entity->getMembers().end(); ++i)
    1555             :     {
    1556             :         stack = std::max(
    1557             :             stack,
    1558             :             addFieldInit(
    1559          33 :                 manager, className, i->name, i->parameterized, i->type,
    1560          44 :                 dependencies, code.get()));
    1561             :     }
    1562           6 :     code->instrReturn();
    1563           6 :     code->setMaxStackAndLocals(stack + 1, 1);
    1564             :     cf->addMethod(
    1565           6 :         ClassFile::ACC_PUBLIC, "<init>", "()V", code.get(),
    1566          12 :         std::vector< OString >(), "");
    1567          12 :     MethodDescriptor desc(manager, dependencies, "void", 0, 0);
    1568           6 :     code.reset(cf->newCode());
    1569           6 :     code->loadLocalReference(0);
    1570           6 :     sal_uInt16 index2 = 1;
    1571             :     code->instrInvokespecial(
    1572           6 :         "java/lang/Object", "<init>", desc.getDescriptor());
    1573           6 :     sal_uInt16 maxSize = index2;
    1574          51 :     for (std::vector< unoidl::PolymorphicStructTypeTemplateEntity::Member >::
    1575           6 :              const_iterator i(entity->getMembers().begin());
    1576          34 :          i != entity->getMembers().end(); ++i)
    1577             :     {
    1578             :         maxSize = std::max(
    1579             :             maxSize,
    1580             :             addDirectArgument(
    1581             :                 manager, dependencies, &desc, code.get(), &index2, className,
    1582          11 :                 codemaker::convertString(i->name), i->parameterized, i->type));
    1583             :     }
    1584           6 :     code->instrReturn();
    1585           6 :     code->setMaxStackAndLocals(maxSize, index2);
    1586             :     cf->addMethod(
    1587           6 :         ClassFile::ACC_PUBLIC, "<init>", desc.getDescriptor(), code.get(),
    1588          12 :         std::vector< OString >(), desc.getSignature());
    1589           6 :     addTypeInfo(className, typeInfo, dependencies, cf.get());
    1590          12 :     writeClassFile(options, className, *cf.get());
    1591           6 : }
    1592             : 
    1593         416 : void addExceptionBaseArguments(
    1594             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies,
    1595             :     MethodDescriptor * methodDescriptor, ClassFile::Code * code,
    1596             :     OUString const & base, sal_uInt16 * index)
    1597             : {
    1598             :     assert(manager.is());
    1599             :     assert(methodDescriptor != 0);
    1600         416 :     rtl::Reference< unoidl::Entity > ent;
    1601         416 :     if (manager->getSort(base, &ent) != codemaker::UnoType::SORT_EXCEPTION_TYPE)
    1602             :     {
    1603             :         throw CannotDumpException(
    1604           0 :             "unexpected entity \"" + base
    1605           0 :             + "\" in call to addExceptionBaseArguments");
    1606             :     }
    1607             :     rtl::Reference< unoidl::ExceptionTypeEntity > ent2(
    1608         832 :         dynamic_cast< unoidl::ExceptionTypeEntity * >(ent.get()));
    1609             :     assert(ent2.is());
    1610         416 :     bool baseException = base == "com.sun.star.uno.Exception";
    1611         416 :     if (!baseException) {
    1612             :         addExceptionBaseArguments(
    1613             :             manager, dependencies, methodDescriptor, code,
    1614         174 :             ent2->getDirectBase(), index);
    1615             :     }
    1616        2961 :     for (std::vector< unoidl::ExceptionTypeEntity::Member >::const_iterator i(
    1617         416 :              ent2->getDirectMembers().begin());
    1618        1974 :          i != ent2->getDirectMembers().end(); ++i)
    1619             :     {
    1620         571 :         if (!baseException || i != ent2->getDirectMembers().begin()) {
    1621         329 :             methodDescriptor->addParameter(i->type, false, true, 0);
    1622             :             addLoadLocal(
    1623         329 :                 manager, code, index, false, i->type, false, dependencies);
    1624             :         }
    1625         416 :     }
    1626         416 : }
    1627             : 
    1628         244 : void handleExceptionType(
    1629             :     const OUString& name, rtl::Reference< unoidl::ExceptionTypeEntity > const & entity,
    1630             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    1631             :     Dependencies * dependencies)
    1632             : {
    1633             :     assert(entity.is());
    1634             :     assert(dependencies != 0);
    1635         244 :     OString className(codemaker::convertString(name).replace('.', '/'));
    1636         244 :     bool baseException = false;
    1637         244 :     bool baseRuntimeException = false;
    1638         488 :     OString superClass;
    1639         244 :     if (className == "com/sun/star/uno/Exception") {
    1640           1 :         baseException = true;
    1641           1 :         superClass = "java/lang/Exception";
    1642         243 :     } else if (className == "com/sun/star/uno/RuntimeException") {
    1643           1 :         baseRuntimeException = true;
    1644           1 :         superClass = "java/lang/RuntimeException";
    1645             :     } else {
    1646         242 :         if (entity->getDirectBase().isEmpty()) {
    1647             :             throw CannotDumpException(
    1648           0 :                 "Exception type \"" + name + "\" lacks base");
    1649             :         }
    1650         484 :         superClass = codemaker::convertString(entity->getDirectBase()).
    1651         242 :             replace('.', '/');
    1652         242 :         dependencies->insert(entity->getDirectBase());
    1653             :     }
    1654             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1655             :     std::auto_ptr< ClassFile > cf(
    1656             :         new ClassFile(
    1657             :             static_cast< ClassFile::AccessFlags >(
    1658             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_SUPER),
    1659         488 :             className, superClass, ""));
    1660             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1661         488 :     std::vector< TypeInfo > typeInfo;
    1662         244 :     sal_Int32 index = 0;
    1663         244 :     if (baseRuntimeException) {
    1664             :         addField(
    1665             :             manager, dependencies, cf.get(), &typeInfo, -1,
    1666           1 :             "com.sun.star.uno.XInterface", "Context", index++);
    1667             :     }
    1668        1188 :     for (std::vector< unoidl::ExceptionTypeEntity::Member >::const_iterator i(
    1669         244 :              entity->getDirectMembers().begin());
    1670         792 :          i != entity->getDirectMembers().end(); ++i)
    1671             :     {
    1672         152 :         if (!baseException || i != entity->getDirectMembers().begin()) {
    1673             :             addField(
    1674         151 :                 manager, dependencies, cf.get(), &typeInfo, -1, i->type,
    1675         302 :                 i->name, index++);
    1676             :         }
    1677             :     }
    1678             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1679         488 :     std::auto_ptr< ClassFile::Code > code(cf->newCode());
    1680             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1681         244 :     code->loadLocalReference(0);
    1682         244 :     code->instrInvokespecial(superClass, "<init>", "()V");
    1683         244 :     sal_uInt16 stack = 0;
    1684         244 :     if (baseRuntimeException) {
    1685             :         stack = std::max(
    1686             :             stack,
    1687             :             addFieldInit(
    1688             :                 manager, className, "Context", false,
    1689           1 :                 "com.sun.star.uno.XInterface", dependencies, code.get()));
    1690             :     }
    1691        1188 :     for (std::vector< unoidl::ExceptionTypeEntity::Member >::const_iterator i(
    1692         244 :              entity->getDirectMembers().begin());
    1693         792 :          i != entity->getDirectMembers().end(); ++i)
    1694             :     {
    1695         152 :         if (!baseException || i != entity->getDirectMembers().begin()) {
    1696             :             stack = std::max(
    1697             :                 stack,
    1698             :                 addFieldInit(
    1699         302 :                     manager, className, i->name, false, i->type, dependencies,
    1700         453 :                     code.get()));
    1701             :         }
    1702             :     }
    1703         244 :     code->instrReturn();
    1704         244 :     code->setMaxStackAndLocals(stack + 1, 1);
    1705             :     cf->addMethod(
    1706         244 :         ClassFile::ACC_PUBLIC, "<init>", "()V", code.get(),
    1707         488 :         std::vector< OString >(), "");
    1708         244 :     code.reset(cf->newCode());
    1709         244 :     code->loadLocalReference(0);
    1710         244 :     code->loadLocalReference(1);
    1711         244 :     code->instrInvokespecial(superClass, "<init>", "(Ljava/lang/String;)V");
    1712         244 :     stack = 0;
    1713         244 :     if (baseRuntimeException) {
    1714             :         stack = std::max(
    1715             :             stack,
    1716             :             addFieldInit(
    1717             :                 manager, className, "Context", false,
    1718           1 :                 "com.sun.star.uno.XInterface", dependencies, code.get()));
    1719             :     }
    1720        1188 :     for (std::vector< unoidl::ExceptionTypeEntity::Member >::const_iterator i(
    1721         244 :              entity->getDirectMembers().begin());
    1722         792 :          i != entity->getDirectMembers().end(); ++i)
    1723             :     {
    1724         152 :         if (!baseException || i != entity->getDirectMembers().begin()) {
    1725             :             stack = std::max(
    1726             :                 stack,
    1727             :                 addFieldInit(
    1728         302 :                     manager, className, i->name, false, i->type, dependencies,
    1729         453 :                     code.get()));
    1730             :         }
    1731             :     }
    1732         244 :     code->instrReturn();
    1733         244 :     code->setMaxStackAndLocals(stack + 2, 2);
    1734             :     cf->addMethod(
    1735         244 :         ClassFile::ACC_PUBLIC, "<init>", "(Ljava/lang/String;)V", code.get(),
    1736         488 :         std::vector< OString >(), "");
    1737         488 :     MethodDescriptor desc(manager, dependencies, "void", 0, 0);
    1738         244 :     code.reset(cf->newCode());
    1739         244 :     code->loadLocalReference(0);
    1740         244 :     sal_uInt16 index2 = 1;
    1741         244 :     desc.addParameter("string", false, true, 0);
    1742         244 :     code->loadLocalReference(index2++);
    1743         244 :     if (!(baseException || baseRuntimeException)) {
    1744             :         addExceptionBaseArguments(
    1745             :             manager, dependencies, &desc, code.get(), entity->getDirectBase(),
    1746         242 :             &index2);
    1747             :     }
    1748         244 :     code->instrInvokespecial(superClass, "<init>", desc.getDescriptor());
    1749         244 :     sal_uInt16 maxSize = index2;
    1750         244 :     if (baseRuntimeException) {
    1751             :         maxSize = std::max(
    1752             :             maxSize,
    1753             :             addDirectArgument(
    1754             :                 manager, dependencies, &desc, code.get(), &index2, className,
    1755           1 :                 "Context", false, "com.sun.star.uno.XInterface"));
    1756             :     }
    1757        1188 :     for (std::vector< unoidl::ExceptionTypeEntity::Member >::const_iterator i(
    1758         244 :              entity->getDirectMembers().begin());
    1759         792 :          i != entity->getDirectMembers().end(); ++i)
    1760             :     {
    1761         152 :         if (!baseException || i != entity->getDirectMembers().begin()) {
    1762             :             maxSize = std::max(
    1763             :                 maxSize,
    1764             :                 addDirectArgument(
    1765             :                     manager, dependencies, &desc, code.get(), &index2,
    1766         151 :                     className, codemaker::convertString(i->name), false,
    1767         302 :                     i->type));
    1768             :         }
    1769             :     }
    1770         244 :     code->instrReturn();
    1771         244 :     code->setMaxStackAndLocals(maxSize, index2);
    1772             :     cf->addMethod(
    1773         244 :         ClassFile::ACC_PUBLIC, "<init>", desc.getDescriptor(), code.get(),
    1774         488 :         std::vector< OString >(), desc.getSignature());
    1775         244 :     addTypeInfo(className, typeInfo, dependencies, cf.get());
    1776         488 :     writeClassFile(options, className, *cf.get());
    1777         244 : }
    1778             : 
    1779        6896 : void createExceptionsAttribute(
    1780             :     rtl::Reference< TypeManager > const & manager,
    1781             :     std::vector< OUString > const & exceptionTypes,
    1782             :     Dependencies * dependencies, std::vector< OString > * exceptions,
    1783             :     codemaker::ExceptionTree * tree)
    1784             : {
    1785             :     assert(dependencies != 0);
    1786             :     assert(exceptions != 0);
    1787       29391 :     for (std::vector< OUString >::const_iterator i(exceptionTypes.begin());
    1788       19594 :          i != exceptionTypes.end(); ++i)
    1789             :     {
    1790        2901 :         dependencies->insert(*i);
    1791        2901 :         OString type(codemaker::convertString(*i).replace('.', '/'));
    1792        2901 :         exceptions->push_back(type);
    1793        2901 :         if (tree != 0) {
    1794          53 :             tree->add(type.replace('/', '.'), manager);
    1795             :         }
    1796        2901 :     }
    1797        6896 : }
    1798             : 
    1799        1703 : void handleInterfaceType(
    1800             :     const OUString& name, rtl::Reference< unoidl::InterfaceTypeEntity > const & entity,
    1801             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    1802             :     Dependencies * dependencies)
    1803             : {
    1804             :     assert(entity.is());
    1805             :     assert(dependencies != 0);
    1806        1703 :     OString className(codemaker::convertString(name).replace('.', '/'));
    1807             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1808             :     std::auto_ptr< ClassFile > cf(
    1809             :         new ClassFile(
    1810             :             static_cast< ClassFile::AccessFlags >(
    1811             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_INTERFACE
    1812             :                 | ClassFile::ACC_ABSTRACT),
    1813        3406 :             className, "java/lang/Object", ""));
    1814             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1815       10914 :     for (std::vector< unoidl::AnnotatedReference >::const_iterator i(
    1816        1703 :              entity->getDirectMandatoryBases().begin());
    1817        7276 :          i != entity->getDirectMandatoryBases().end(); ++i)
    1818             :     {
    1819        1935 :         dependencies->insert(i->name);
    1820        1935 :         cf->addInterface(codemaker::convertString(i->name).replace('.', '/'));
    1821             :     }
    1822             :     // As a special case, let com.sun.star.lang.XEventListener extend
    1823             :     // java.util.EventListener ("A tagging interface that all event listener
    1824             :     // interfaces must extend"):
    1825        1703 :     if (className == "com/sun/star/lang/XEventListener") {
    1826           1 :         cf->addInterface("java/util/EventListener");
    1827             :     }
    1828        3406 :     std::vector< TypeInfo > typeInfo;
    1829        1703 :     if (className != "com/sun/star/uno/XInterface") {
    1830        1702 :         sal_Int32 index = 0;
    1831        6975 :         for (std::vector< unoidl::InterfaceTypeEntity::Attribute >::
    1832        1702 :                  const_iterator i(entity->getDirectAttributes().begin());
    1833        4650 :              i != entity->getDirectAttributes().end(); ++i)
    1834             :         {
    1835             :             SpecialType specialType;
    1836         623 :             PolymorphicUnoType polymorphicUnoType;
    1837             :             MethodDescriptor gdesc(
    1838         623 :                 manager, dependencies, i->type, &specialType,
    1839        1246 :                 &polymorphicUnoType);
    1840        1246 :             std::vector< OString > exc;
    1841             :             createExceptionsAttribute(
    1842         623 :                 manager, i->getExceptions, dependencies, &exc, 0);
    1843        1246 :             OString attrName(codemaker::convertString(i->name));
    1844             :             cf->addMethod(
    1845             :                 static_cast< ClassFile::AccessFlags >(
    1846             :                     ClassFile::ACC_PUBLIC | ClassFile::ACC_ABSTRACT),
    1847        1246 :                 "get" + attrName, gdesc.getDescriptor(), 0, exc,
    1848        1869 :                 gdesc.getSignature());
    1849         623 :             if (!i->readOnly) {
    1850         486 :                 MethodDescriptor sdesc(manager, dependencies, "void", 0, 0);
    1851         486 :                 sdesc.addParameter(i->type, false, true, 0);
    1852         972 :                 std::vector< OString > exc2;
    1853             :                 createExceptionsAttribute(
    1854         486 :                     manager, i->setExceptions, dependencies, &exc2, 0);
    1855             :                 cf->addMethod(
    1856             :                     static_cast< ClassFile::AccessFlags >(
    1857             :                         ClassFile::ACC_PUBLIC | ClassFile::ACC_ABSTRACT),
    1858         972 :                     "set" + attrName, sdesc.getDescriptor(), 0, exc2,
    1859        1944 :                     sdesc.getSignature());
    1860             :             }
    1861             :             typeInfo.push_back(
    1862             :                 TypeInfo(
    1863             :                     TypeInfo::KIND_ATTRIBUTE, attrName, specialType,
    1864             :                     static_cast< TypeInfo::Flags >(
    1865         623 :                         (i->readOnly ? TypeInfo::FLAG_READONLY : 0)
    1866         623 :                         | (i->bound ? TypeInfo::FLAG_BOUND : 0)),
    1867         623 :                     index, polymorphicUnoType));
    1868         623 :             index += (i->readOnly ? 1 : 2);
    1869         623 :         }
    1870       22068 :         for (std::vector< unoidl::InterfaceTypeEntity::Method >::const_iterator
    1871        1702 :                  i(entity->getDirectMethods().begin());
    1872       14712 :              i != entity->getDirectMethods().end(); ++i)
    1873             :         {
    1874        5654 :             OString methodName(codemaker::convertString(i->name));
    1875             :             SpecialType specialReturnType;
    1876       11308 :             PolymorphicUnoType polymorphicUnoReturnType;
    1877             :             MethodDescriptor desc(
    1878        5654 :                 manager, dependencies, i->returnType, &specialReturnType,
    1879       11308 :                 &polymorphicUnoReturnType);
    1880             :             typeInfo.push_back(
    1881             :                 TypeInfo(
    1882             :                     TypeInfo::KIND_METHOD, methodName, specialReturnType,
    1883             :                     static_cast< TypeInfo::Flags >(0), index++,
    1884        5654 :                     polymorphicUnoReturnType));
    1885        5654 :             sal_Int32 paramIndex = 0;
    1886       34383 :             for (std::vector< unoidl::InterfaceTypeEntity::Method::Parameter >::
    1887        5654 :                      const_iterator j(i->parameters.begin());
    1888       22922 :                  j != i->parameters.end(); ++j)
    1889             :             {
    1890        5807 :                 bool in = j->direction
    1891        5807 :                     != (unoidl::InterfaceTypeEntity::Method::Parameter::
    1892        5807 :                         DIRECTION_OUT);
    1893        5807 :                 bool out = j->direction
    1894        5807 :                     != (unoidl::InterfaceTypeEntity::Method::Parameter::
    1895        5807 :                         DIRECTION_IN);
    1896        5807 :                 PolymorphicUnoType polymorphicUnoType;
    1897             :                 SpecialType specialType = desc.addParameter(
    1898        5807 :                     j->type, out, true, &polymorphicUnoType);
    1899       11457 :                 if (out || isSpecialType(specialType)
    1900       11382 :                     || polymorphicUnoType.kind != PolymorphicUnoType::KIND_NONE)
    1901             :                 {
    1902             :                     typeInfo.push_back(
    1903             :                         TypeInfo(
    1904         235 :                             codemaker::convertString(j->name), specialType, in,
    1905         470 :                             out, methodName, paramIndex, polymorphicUnoType));
    1906             :                 }
    1907        5807 :                 ++paramIndex;
    1908        5807 :             }
    1909       11308 :             std::vector< OString > exc2;
    1910             :             createExceptionsAttribute(
    1911        5654 :                 manager, i->exceptions, dependencies, &exc2, 0);
    1912             :             cf->addMethod(
    1913             :                 static_cast< ClassFile::AccessFlags >(
    1914             :                     ClassFile::ACC_PUBLIC | ClassFile::ACC_ABSTRACT),
    1915        5654 :                 methodName, desc.getDescriptor(), 0, exc2, desc.getSignature());
    1916        5654 :         }
    1917             :     }
    1918        1703 :     addTypeInfo(className, typeInfo, dependencies, cf.get());
    1919        3406 :     writeClassFile(options, className, *cf.get());
    1920        1703 : }
    1921             : 
    1922          19 : void handleTypedef(
    1923             :     rtl::Reference< unoidl::TypedefEntity > const & entity,
    1924             :     rtl::Reference< TypeManager > const & manager, Dependencies * dependencies)
    1925             : {
    1926             :     assert(entity.is());
    1927             :     assert(manager.is());
    1928             :     assert(dependencies != 0);
    1929          19 :     OUString nucleus;
    1930          19 :     switch (manager->decompose(entity->getType(), false, &nucleus, 0, 0, 0))
    1931             :     {
    1932             :     case codemaker::UnoType::SORT_BOOLEAN:
    1933             :     case codemaker::UnoType::SORT_BYTE:
    1934             :     case codemaker::UnoType::SORT_SHORT:
    1935             :     case codemaker::UnoType::SORT_UNSIGNED_SHORT:
    1936             :     case codemaker::UnoType::SORT_LONG:
    1937             :     case codemaker::UnoType::SORT_UNSIGNED_LONG:
    1938             :     case codemaker::UnoType::SORT_HYPER:
    1939             :     case codemaker::UnoType::SORT_UNSIGNED_HYPER:
    1940             :     case codemaker::UnoType::SORT_FLOAT:
    1941             :     case codemaker::UnoType::SORT_DOUBLE:
    1942             :     case codemaker::UnoType::SORT_CHAR:
    1943             :     case codemaker::UnoType::SORT_STRING:
    1944             :     case codemaker::UnoType::SORT_TYPE:
    1945             :     case codemaker::UnoType::SORT_ANY:
    1946           7 :         break;
    1947             :     case codemaker::UnoType::SORT_ENUM_TYPE:
    1948             :     case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
    1949             :     case codemaker::UnoType::SORT_INTERFACE_TYPE:
    1950             :     case codemaker::UnoType::SORT_TYPEDEF:
    1951          12 :         dependencies->insert(nucleus);
    1952          12 :         break;
    1953             :     default:
    1954             :         assert(false); // this cannot happen
    1955          19 :     }
    1956          19 : }
    1957             : 
    1958         348 : void handleConstantGroup(
    1959             :     const OUString& name, rtl::Reference< unoidl::ConstantGroupEntity > const & entity,
    1960             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    1961             :     Dependencies * dependencies)
    1962             : {
    1963             :     assert(entity.is());
    1964         348 :     OString className(codemaker::convertString(name).replace('.', '/'));
    1965             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    1966             :     std::auto_ptr< ClassFile > cf(
    1967             :         new ClassFile(
    1968             :             static_cast< ClassFile::AccessFlags >(
    1969             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_INTERFACE
    1970             :                 | ClassFile::ACC_ABSTRACT),
    1971         696 :             className, "java/lang/Object", ""));
    1972             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    1973       11082 :     for (std::vector< unoidl::ConstantGroupEntity::Member >::const_iterator i(
    1974         348 :              entity->getMembers().begin());
    1975        7388 :          i != entity->getMembers().end(); ++i)
    1976             :     {
    1977        3346 :         OUString type;
    1978        3346 :         sal_uInt16 valueIndex = sal_uInt16(); // avoid false warnings
    1979        3346 :         switch (i->value.type) {
    1980             :         case unoidl::ConstantValue::TYPE_BOOLEAN:
    1981           0 :             type = "boolean";
    1982           0 :             valueIndex = cf->addIntegerInfo(sal_Int32(i->value.booleanValue));
    1983           0 :             break;
    1984             :         case unoidl::ConstantValue::TYPE_BYTE:
    1985         245 :             type = "byte";
    1986         245 :             valueIndex = cf->addIntegerInfo(i->value.byteValue);
    1987         245 :             break;
    1988             :         case unoidl::ConstantValue::TYPE_SHORT:
    1989        2064 :             type = "short";
    1990        2064 :             valueIndex = cf->addIntegerInfo(i->value.shortValue);
    1991        2064 :             break;
    1992             :         case unoidl::ConstantValue::TYPE_UNSIGNED_SHORT:
    1993           0 :             type = "unsigned short";
    1994           0 :             valueIndex = cf->addIntegerInfo(i->value.unsignedShortValue);
    1995           0 :             break;
    1996             :         case unoidl::ConstantValue::TYPE_LONG:
    1997         988 :             type = "long";
    1998         988 :             valueIndex = cf->addIntegerInfo(i->value.longValue);
    1999         988 :             break;
    2000             :         case unoidl::ConstantValue::TYPE_UNSIGNED_LONG:
    2001           0 :             type = "unsigned long";
    2002             :             valueIndex = cf->addIntegerInfo(
    2003           0 :                 static_cast< sal_Int32 >(i->value.unsignedLongValue));
    2004           0 :             break;
    2005             :         case unoidl::ConstantValue::TYPE_HYPER:
    2006          29 :             type = "hyper";
    2007          29 :             valueIndex = cf->addLongInfo(i->value.hyperValue);
    2008          29 :             break;
    2009             :         case unoidl::ConstantValue::TYPE_UNSIGNED_HYPER:
    2010           0 :             type = "unsigned hyper";
    2011             :             valueIndex = cf->addLongInfo(
    2012           0 :                 static_cast< sal_Int64 >(i->value.unsignedHyperValue));
    2013           0 :             break;
    2014             :         case unoidl::ConstantValue::TYPE_FLOAT:
    2015          20 :             type = "float";
    2016          20 :             valueIndex = cf->addFloatInfo(i->value.floatValue);
    2017          20 :             break;
    2018             :         case unoidl::ConstantValue::TYPE_DOUBLE:
    2019           0 :             type = "double";
    2020           0 :             valueIndex = cf->addDoubleInfo(i->value.doubleValue);
    2021           0 :             break;
    2022             :         }
    2023        3346 :         OString desc;
    2024        6692 :         OString sig;
    2025        3346 :         getFieldDescriptor(manager, dependencies, type, &desc, &sig, 0);
    2026             :         cf->addField(
    2027             :             static_cast< ClassFile::AccessFlags >(
    2028             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC
    2029             :                 | ClassFile::ACC_FINAL),
    2030        3346 :             codemaker::convertString(i->name), desc, valueIndex, sig);
    2031        3346 :     }
    2032         696 :     writeClassFile(options, className, *cf.get());
    2033         348 : }
    2034             : 
    2035         378 : void addExceptionHandlers(
    2036             :     codemaker::ExceptionTreeNode const * node,
    2037             :     ClassFile::Code::Position start, ClassFile::Code::Position end,
    2038             :     ClassFile::Code::Position handler, ClassFile::Code * code)
    2039             : {
    2040             :     assert(node != 0);
    2041             :     assert(code != 0);
    2042         378 :     if (node->present) {
    2043          14 :         code->addException(start, end, handler, node->name.replace('.', '/'));
    2044             :     } else {
    2045        1137 :         for (codemaker::ExceptionTreeNode::Children::const_iterator i(
    2046         364 :                  node->children.begin());
    2047         758 :              i != node->children.end(); ++i)
    2048             :         {
    2049          15 :             addExceptionHandlers(*i, start, end, handler, code);
    2050             :         }
    2051             :     }
    2052         378 : }
    2053             : 
    2054         366 : void addConstructor(
    2055             :     rtl::Reference< TypeManager > const & manager,
    2056             :     OString const & realJavaBaseName, OString const & unoName,
    2057             :     OString const & className,
    2058             :     unoidl::SingleInterfaceBasedServiceEntity::Constructor const & constructor,
    2059             :     OUString const & returnType, Dependencies * dependencies,
    2060             :     ClassFile * classFile)
    2061             : {
    2062             :     assert(dependencies != 0);
    2063             :     assert(classFile != 0);
    2064         366 :     MethodDescriptor desc(manager, dependencies, returnType, 0, 0);
    2065         366 :     desc.addParameter("com.sun.star.uno.XComponentContext", false, false, 0);
    2066             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    2067         732 :     std::auto_ptr< ClassFile::Code > code(classFile->newCode());
    2068             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    2069         366 :     code->loadLocalReference(0);
    2070             :     // stack: context
    2071             :     code->instrInvokeinterface(
    2072             :         "com/sun/star/uno/XComponentContext", "getServiceManager",
    2073         366 :         "()Lcom/sun/star/lang/XMultiComponentFactory;", 1);
    2074             :     // stack: factory
    2075         366 :     code->loadStringConstant(unoName);
    2076             :     // stack: factory serviceName
    2077         732 :     codemaker::ExceptionTree tree;
    2078             :     ClassFile::Code::Position tryStart;
    2079             :     ClassFile::Code::Position tryEnd;
    2080         732 :     std::vector< OString > exc;
    2081             :     sal_uInt16 stack;
    2082         366 :     sal_uInt16 localIndex = 1;
    2083             :     ClassFile::AccessFlags access = static_cast< ClassFile::AccessFlags >(
    2084         366 :         ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC);
    2085         366 :     if (constructor.defaultConstructor) {
    2086         233 :         code->loadLocalReference(0);
    2087             :         // stack: factory serviceName context
    2088         233 :         tryStart = code->getPosition();
    2089             :         code->instrInvokeinterface(
    2090             :             "com/sun/star/lang/XMultiComponentFactory",
    2091             :             "createInstanceWithContext",
    2092             :             ("(Ljava/lang/String;Lcom/sun/star/uno/XComponentContext;)"
    2093             :              "Ljava/lang/Object;"),
    2094         233 :             3);
    2095         233 :         tryEnd = code->getPosition();
    2096             :         // stack: instance
    2097         233 :         stack = 3;
    2098             :     } else {
    2099         266 :         if (constructor.parameters.size() == 1
    2100         133 :             && constructor.parameters[0].rest)
    2101             :         {
    2102           1 :             desc.addParameter("any", true, true, 0);
    2103           1 :             code->loadLocalReference(localIndex++);
    2104             :             // stack: factory serviceName args
    2105           1 :             stack = 4;
    2106             :             access = static_cast< ClassFile::AccessFlags >(
    2107           1 :                 access | ClassFile::ACC_VARARGS);
    2108             :         } else {
    2109         132 :             code->loadIntegerConstant(constructor.parameters.size());
    2110             :             // stack: factory serviceName N
    2111         132 :             code->instrAnewarray("java/lang/Object");
    2112             :             // stack: factory serviceName args
    2113         132 :             stack = 0;
    2114         132 :             sal_Int32 n = 0;
    2115        1200 :             for (std::vector<
    2116             :                      unoidl::SingleInterfaceBasedServiceEntity::Constructor::
    2117             :                      Parameter >::const_iterator i(
    2118         132 :                          constructor.parameters.begin());
    2119         800 :                  i != constructor.parameters.end(); ++i)
    2120             :             {
    2121         268 :                 desc.addParameter(i->type, false, true, 0);
    2122         268 :                 code->instrDup();
    2123             :                 // stack: factory serviceName args args
    2124         268 :                 code->loadIntegerConstant(n++);
    2125             :                 // stack: factory serviceName args args i
    2126             :                 stack = std::max(
    2127             :                     stack,
    2128             :                     addLoadLocal(
    2129         268 :                         manager, code.get(), &localIndex, false, i->type, true,
    2130         268 :                         dependencies));
    2131             :                 // stack: factory serviceName args args i any
    2132         268 :                 code->instrAastore();
    2133             :                 // stack: factory serviceName args
    2134             :             }
    2135         132 :             stack += 5;
    2136             :         }
    2137         133 :         code->loadLocalReference(0);
    2138             :         // stack: factory serviceName args context
    2139         133 :         tryStart = code->getPosition();
    2140             :         code->instrInvokeinterface(
    2141             :             "com/sun/star/lang/XMultiComponentFactory",
    2142             :             "createInstanceWithArgumentsAndContext",
    2143             :             ("(Ljava/lang/String;[Ljava/lang/Object;"
    2144             :              "Lcom/sun/star/uno/XComponentContext;)Ljava/lang/Object;"),
    2145         133 :             4);
    2146         133 :         tryEnd = code->getPosition();
    2147             :         // stack: instance
    2148             :         createExceptionsAttribute(
    2149         133 :             manager, constructor.exceptions, dependencies, &exc, &tree);
    2150             :     }
    2151         366 :     code->loadLocalReference(0);
    2152             :     // stack: instance context
    2153             :     code->instrInvokestatic(
    2154             :         className, "$castInstance",
    2155             :         ("(Ljava/lang/Object;Lcom/sun/star/uno/XComponentContext;)"
    2156         366 :          "Ljava/lang/Object;"));
    2157             :     // stack: instance
    2158             :     code->instrCheckcast(
    2159         366 :         codemaker::convertString(returnType).replace('.', '/'));
    2160             :     // stack: instance
    2161         366 :     code->instrAreturn();
    2162         366 :     if (!tree.getRoot()->present) {
    2163         363 :         ClassFile::Code::Position pos1 = code->getPosition();
    2164             :         // stack: e
    2165             :         code->instrInvokevirtual(
    2166         363 :             "java/lang/Throwable", "toString", "()Ljava/lang/String;");
    2167             :         // stack: str
    2168         363 :         localIndex = std::max< sal_uInt16 >(localIndex, 2);
    2169         363 :         code->storeLocalReference(1);
    2170             :         // stack: -
    2171         363 :         code->instrNew("com/sun/star/uno/DeploymentException");
    2172             :         // stack: ex
    2173         363 :         code->instrDup();
    2174             :         // stack: ex ex
    2175             :         code->loadStringConstant(
    2176         726 :             "component context fails to supply service " + unoName + " of type "
    2177         363 :             + realJavaBaseName + ": ");
    2178             :         // stack: ex ex "..."
    2179         363 :         code->loadLocalReference(1);
    2180             :         // stack: ex ex "..." str
    2181             :         code->instrInvokevirtual(
    2182             :             "java/lang/String", "concat",
    2183         363 :             "(Ljava/lang/String;)Ljava/lang/String;");
    2184             :         // stack: ex ex "..."
    2185         363 :         code->loadLocalReference(0);
    2186             :         // stack: ex ex "..." context
    2187             :         code->instrInvokespecial(
    2188             :             "com/sun/star/uno/DeploymentException", "<init>",
    2189         363 :             "(Ljava/lang/String;Ljava/lang/Object;)V");
    2190             :         // stack: ex
    2191         363 :         ClassFile::Code::Position pos2 = code->getPosition();
    2192         363 :         code->instrAthrow();
    2193             :         addExceptionHandlers(
    2194         363 :             tree.getRoot(), tryStart, tryEnd, pos2, code.get());
    2195             :         code->addException(
    2196         363 :             tryStart, tryEnd, pos1, "com/sun/star/uno/Exception");
    2197         363 :         dependencies->insert("com.sun.star.uno.Exception");
    2198         363 :         stack = std::max< sal_uInt16 >(stack, 4);
    2199             :     }
    2200         366 :     code->setMaxStackAndLocals(stack, localIndex);
    2201             :     classFile->addMethod(
    2202             :         access,
    2203             :         codemaker::java::translateUnoToJavaIdentifier(
    2204             :             (constructor.defaultConstructor
    2205             :              ? OString("create") : codemaker::convertString(constructor.name)),
    2206             :             "method"),
    2207         732 :         desc.getDescriptor(), code.get(), exc, desc.getSignature());
    2208         366 : }
    2209             : 
    2210         339 : void handleService(
    2211             :     const OUString& name,
    2212             :     rtl::Reference< unoidl::SingleInterfaceBasedServiceEntity > const & entity,
    2213             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    2214             :     Dependencies * dependencies)
    2215             : {
    2216             :     assert(entity.is());
    2217             :     assert(dependencies != 0);
    2218         339 :     OString unoName(codemaker::convertString(name));
    2219             :     OString className(
    2220         678 :         translateUnoidlEntityNameToJavaFullyQualifiedName(name, "service"));
    2221             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    2222             :     std::auto_ptr< ClassFile > cf(
    2223             :         new ClassFile(
    2224             :             static_cast< ClassFile::AccessFlags >(
    2225             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_FINAL
    2226             :                 | ClassFile::ACC_SUPER),
    2227         678 :             className, "java/lang/Object", ""));
    2228             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    2229         339 :     if (!entity->getConstructors().empty()) {
    2230             :         OString realJavaBaseName(
    2231         322 :             codemaker::convertString(entity->getBase()));
    2232         322 :         dependencies->insert(entity->getBase());
    2233         322 :         dependencies->insert("com.sun.star.lang.XMultiComponentFactory");
    2234         322 :         dependencies->insert("com.sun.star.uno.DeploymentException");
    2235         322 :         dependencies->insert("com.sun.star.uno.TypeClass");
    2236         322 :         dependencies->insert("com.sun.star.uno.XComponentContext");
    2237        2064 :         for (std::vector<
    2238             :                  unoidl::SingleInterfaceBasedServiceEntity::Constructor >::
    2239         322 :                  const_iterator i(entity->getConstructors().begin());
    2240        1376 :              i != entity->getConstructors().end(); ++i)
    2241             :         {
    2242             :             addConstructor(
    2243         366 :                 manager, realJavaBaseName, unoName, className, *i,
    2244         732 :                 entity->getBase(), dependencies, cf.get());
    2245             :         }
    2246             :         // Synthetic castInstance method:
    2247             :         {
    2248             :             SAL_WNODEPRECATED_DECLARATIONS_PUSH
    2249         322 :             std::auto_ptr< ClassFile::Code > code(cf->newCode());
    2250             :             SAL_WNODEPRECATED_DECLARATIONS_POP
    2251         322 :             code->instrNew("com/sun/star/uno/Type");
    2252             :             // stack: type
    2253         322 :             code->instrDup();
    2254             :             // stack: type type
    2255         322 :             code->loadStringConstant(realJavaBaseName);
    2256             :             // stack: type type "..."
    2257             :             code->instrGetstatic(
    2258             :                 "com/sun/star/uno/TypeClass", "INTERFACE",
    2259         322 :                 "Lcom/sun/star/uno/TypeClass;");
    2260             :             // stack: type type "..." INTERFACE
    2261             :             code->instrInvokespecial(
    2262             :                 "com/sun/star/uno/Type", "<init>",
    2263         322 :                 "(Ljava/lang/String;Lcom/sun/star/uno/TypeClass;)V");
    2264             :             // stack: type
    2265         322 :             code->loadLocalReference(0);
    2266             :             // stack: type instance
    2267             :             code->instrInvokestatic(
    2268             :                 "com/sun/star/uno/UnoRuntime", "queryInterface",
    2269             :                 ("(Lcom/sun/star/uno/Type;Ljava/lang/Object;)"
    2270         322 :                  "Ljava/lang/Object;"));
    2271             :             // stack: instance
    2272         322 :             code->instrDup();
    2273             :             // stack: instance instance
    2274         322 :             ClassFile::Code::Branch branch = code->instrIfnull();
    2275             :             // stack: instance
    2276         322 :             code->instrAreturn();
    2277         322 :             code->branchHere(branch);
    2278         322 :             code->instrPop();
    2279             :             // stack: -
    2280         322 :             code->instrNew("com/sun/star/uno/DeploymentException");
    2281             :             // stack: ex
    2282         322 :             code->instrDup();
    2283             :             // stack: ex ex
    2284             :             code->loadStringConstant(
    2285         644 :                 "component context fails to supply service " + unoName
    2286         322 :                 + " of type " + realJavaBaseName);
    2287             :             // stack: ex ex "..."
    2288         322 :             code->loadLocalReference(1);
    2289             :             // stack: ex ex "..." context
    2290             :             code->instrInvokespecial(
    2291             :                 "com/sun/star/uno/DeploymentException", "<init>",
    2292         322 :                 "(Ljava/lang/String;Ljava/lang/Object;)V");
    2293             :             // stack: ex
    2294         322 :             code->instrAthrow();
    2295         322 :             code->setMaxStackAndLocals(4, 2);
    2296             :             cf->addMethod(
    2297             :                 static_cast< ClassFile::AccessFlags >(
    2298             :                     ClassFile::ACC_PRIVATE | ClassFile::ACC_STATIC
    2299             :                     | ClassFile::ACC_SYNTHETIC),
    2300             :                 "$castInstance",
    2301             :                 ("(Ljava/lang/Object;Lcom/sun/star/uno/XComponentContext;)"
    2302             :                  "Ljava/lang/Object;"),
    2303         322 :                 code.get(), std::vector< OString >(), "");
    2304         322 :         }
    2305             :     }
    2306         678 :     writeClassFile(options, className, *cf.get());
    2307         339 : }
    2308             : 
    2309          31 : void handleSingleton(
    2310             :     const OUString& name,
    2311             :     rtl::Reference< unoidl::InterfaceBasedSingletonEntity > const & entity,
    2312             :     rtl::Reference< TypeManager > const & manager, JavaOptions const & options,
    2313             :     Dependencies * dependencies)
    2314             : {
    2315             :     assert(entity.is());
    2316             :     assert(dependencies != 0);
    2317          31 :     OString realJavaBaseName(codemaker::convertString(entity->getBase()));
    2318          62 :     OString base(realJavaBaseName.replace('.', '/'));
    2319          31 :     dependencies->insert(entity->getBase());
    2320          62 :     OString unoName(codemaker::convertString(name));
    2321             :     OString className(
    2322          62 :         translateUnoidlEntityNameToJavaFullyQualifiedName(name, "singleton"));
    2323          31 :     dependencies->insert("com.sun.star.uno.DeploymentException");
    2324          31 :     dependencies->insert("com.sun.star.uno.TypeClass");
    2325          31 :     dependencies->insert("com.sun.star.uno.XComponentContext");
    2326             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    2327             :     std::auto_ptr< ClassFile > cf(
    2328             :         new ClassFile(
    2329             :             static_cast< ClassFile::AccessFlags >(
    2330             :                 ClassFile::ACC_PUBLIC | ClassFile::ACC_FINAL
    2331             :                 | ClassFile::ACC_SUPER),
    2332          62 :             className, "java/lang/Object", ""));
    2333             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    2334          62 :     MethodDescriptor desc(manager, dependencies, entity->getBase(), 0, 0);
    2335          31 :     desc.addParameter("com.sun.star.uno.XComponentContext", false, false, 0);
    2336             :     SAL_WNODEPRECATED_DECLARATIONS_PUSH
    2337          62 :     std::auto_ptr< ClassFile::Code > code(cf->newCode());
    2338             :     SAL_WNODEPRECATED_DECLARATIONS_POP
    2339          31 :     code->loadLocalReference(0);
    2340             :     // stack: context
    2341          31 :     code->loadStringConstant("/singletons/" + unoName);
    2342             :     // stack: context "..."
    2343             :     code->instrInvokeinterface(
    2344             :         "com/sun/star/uno/XComponentContext", "getValueByName",
    2345          31 :         "(Ljava/lang/String;)Ljava/lang/Object;", 2);
    2346             :     // stack: value
    2347          31 :     code->instrDup();
    2348             :     // stack: value value
    2349          31 :     code->instrInstanceof("com/sun/star/uno/Any");
    2350             :     // stack: value 0/1
    2351          31 :     ClassFile::Code::Branch branch1 = code->instrIfeq();
    2352             :     // stack: value
    2353          31 :     code->instrCheckcast("com/sun/star/uno/Any");
    2354             :     // stack: value
    2355          31 :     code->instrDup();
    2356             :     // stack: value value
    2357             :     code->instrInvokevirtual(
    2358          31 :         "com/sun/star/uno/Any", "getType", "()Lcom/sun/star/uno/Type;");
    2359             :     // stack: value type
    2360             :     code->instrInvokevirtual(
    2361             :         "com/sun/star/uno/Type", "getTypeClass",
    2362          31 :         "()Lcom/sun/star/uno/TypeClass;");
    2363             :     // stack: value typeClass
    2364             :     code->instrGetstatic(
    2365             :         "com/sun/star/uno/TypeClass", "INTERFACE",
    2366          31 :         "Lcom/sun/star/uno/TypeClass;");
    2367             :     // stack: value typeClass INTERFACE
    2368          31 :     ClassFile::Code::Branch branch2 = code->instrIfAcmpne();
    2369             :     // stack: value
    2370             :     code->instrInvokevirtual(
    2371          31 :         "com/sun/star/uno/Any", "getObject", "()Ljava/lang/Object;");
    2372             :     // stack: value
    2373          31 :     code->branchHere(branch1);
    2374          31 :     code->instrNew("com/sun/star/uno/Type");
    2375             :     // stack: value type
    2376          31 :     code->instrDup();
    2377             :     // stack: value type type
    2378          31 :     code->loadStringConstant(realJavaBaseName);
    2379             :     // stack: value type type "..."
    2380             :     code->instrGetstatic(
    2381             :         "com/sun/star/uno/TypeClass", "INTERFACE",
    2382          31 :         "Lcom/sun/star/uno/TypeClass;");
    2383             :     // stack: value type type "..." INTERFACE
    2384             :     code->instrInvokespecial(
    2385             :         "com/sun/star/uno/Type", "<init>",
    2386          31 :         "(Ljava/lang/String;Lcom/sun/star/uno/TypeClass;)V");
    2387             :     // stack: value type
    2388          31 :     code->instrSwap();
    2389             :     // stack: type value
    2390             :     code->instrInvokestatic(
    2391             :         "com/sun/star/uno/UnoRuntime", "queryInterface",
    2392          31 :         "(Lcom/sun/star/uno/Type;Ljava/lang/Object;)Ljava/lang/Object;");
    2393             :     // stack: instance
    2394          31 :     code->instrDup();
    2395             :     // stack: instance instance
    2396          31 :     ClassFile::Code::Branch branch3 = code->instrIfnull();
    2397             :     // stack: instance
    2398          31 :     code->instrCheckcast(base);
    2399             :     // stack: instance
    2400          31 :     code->instrAreturn();
    2401          31 :     code->branchHere(branch2);
    2402          31 :     code->branchHere(branch3);
    2403          31 :     code->instrPop();
    2404             :     // stack: -
    2405          31 :     code->instrNew("com/sun/star/uno/DeploymentException");
    2406             :     // stack: ex
    2407          31 :     code->instrDup();
    2408             :     // stack: ex ex
    2409             :     code->loadStringConstant(
    2410          62 :         "component context fails to supply singleton " + unoName + " of type "
    2411          31 :         + realJavaBaseName);
    2412             :     // stack: ex ex "..."
    2413          31 :     code->loadLocalReference(0);
    2414             :     // stack: ex ex "..." context
    2415             :     code->instrInvokespecial(
    2416             :         "com/sun/star/uno/DeploymentException", "<init>",
    2417          31 :         "(Ljava/lang/String;Ljava/lang/Object;)V");
    2418             :     // stack: ex
    2419          31 :     code->instrAthrow();
    2420          31 :     code->setMaxStackAndLocals(5, 1);
    2421             :     cf->addMethod(
    2422             :         static_cast< ClassFile::AccessFlags >(
    2423             :             ClassFile::ACC_PUBLIC | ClassFile::ACC_STATIC),
    2424          31 :         "get", desc.getDescriptor(), code.get(), std::vector< OString >(),
    2425          62 :         desc.getSignature());
    2426          62 :     writeClassFile(options, className, *cf.get());
    2427          31 : }
    2428             : 
    2429             : }
    2430             : 
    2431       12403 : void produce(
    2432             :     OUString const & name, rtl::Reference< TypeManager > const & manager,
    2433             :     codemaker::GeneratedTypeSet & generated, JavaOptions const & options)
    2434             : {
    2435       12403 :     if (generated.contains(u2b(name))) {
    2436       15844 :         return;
    2437             :     }
    2438        4653 :     generated.add(u2b(name));
    2439        4653 :     if (!manager->foundAtPrimaryProvider(name)) {
    2440         194 :         return;
    2441             :     }
    2442        4459 :     Dependencies deps;
    2443        8768 :     rtl::Reference< unoidl::Entity > ent;
    2444        8768 :     rtl::Reference< unoidl::MapCursor > cur;
    2445        4459 :     switch (manager->getSort(name, &ent, &cur)) {
    2446             :     case codemaker::UnoType::SORT_MODULE:
    2447             :         {
    2448         150 :             OUString prefix;
    2449         150 :             if (!name.isEmpty()) {
    2450         146 :                 prefix = name + ".";
    2451             :             }
    2452             :             for (;;) {
    2453        4717 :                 OUString mem;
    2454        4717 :                 if (!cur->getNext(&mem).is()) {
    2455         150 :                     break;
    2456             :                 }
    2457        4567 :                 produce(prefix + mem, manager, generated, options);
    2458        4567 :             }
    2459         150 :             return;
    2460             :         }
    2461             :     case codemaker::UnoType::SORT_ENUM_TYPE:
    2462             :         handleEnumType(
    2463         195 :             name, dynamic_cast< unoidl::EnumTypeEntity * >(ent.get()), options);
    2464         195 :         break;
    2465             :     case codemaker::UnoType::SORT_PLAIN_STRUCT_TYPE:
    2466             :         handlePlainStructType(
    2467         405 :             name, dynamic_cast< unoidl::PlainStructTypeEntity * >(ent.get()),
    2468         405 :             manager, options, &deps);
    2469         405 :         break;
    2470             :     case codemaker::UnoType::SORT_POLYMORPHIC_STRUCT_TYPE_TEMPLATE:
    2471             :         handlePolyStructType(
    2472             :             name,
    2473             :             dynamic_cast< unoidl::PolymorphicStructTypeTemplateEntity * >(
    2474           6 :                 ent.get()),
    2475           6 :             manager, options, &deps);
    2476           6 :         break;
    2477             :     case codemaker::UnoType::SORT_EXCEPTION_TYPE:
    2478             :         handleExceptionType(
    2479         244 :             name, dynamic_cast< unoidl::ExceptionTypeEntity * >(ent.get()),
    2480         244 :             manager, options, &deps);
    2481         244 :         break;
    2482             :     case codemaker::UnoType::SORT_INTERFACE_TYPE:
    2483             :         handleInterfaceType(
    2484        1703 :             name, dynamic_cast< unoidl::InterfaceTypeEntity * >(ent.get()),
    2485        1703 :             manager, options, &deps);
    2486        1703 :         break;
    2487             :     case codemaker::UnoType::SORT_TYPEDEF:
    2488             :         handleTypedef(
    2489          19 :             dynamic_cast< unoidl::TypedefEntity * >(ent.get()), manager, &deps);
    2490          19 :         break;
    2491             :     case codemaker::UnoType::SORT_CONSTANT_GROUP:
    2492             :         handleConstantGroup(
    2493         348 :             name, dynamic_cast< unoidl::ConstantGroupEntity * >(ent.get()),
    2494         348 :             manager, options, &deps);
    2495         348 :         break;
    2496             :     case codemaker::UnoType::SORT_SINGLE_INTERFACE_BASED_SERVICE:
    2497             :         handleService(
    2498             :             name,
    2499             :             dynamic_cast< unoidl::SingleInterfaceBasedServiceEntity * >(
    2500         339 :                 ent.get()),
    2501         339 :             manager, options, &deps);
    2502         339 :         break;
    2503             :     case codemaker::UnoType::SORT_INTERFACE_BASED_SINGLETON:
    2504             :         handleSingleton(
    2505             :             name,
    2506          31 :             dynamic_cast< unoidl::InterfaceBasedSingletonEntity * >(ent.get()),
    2507          31 :             manager, options, &deps);
    2508          31 :         break;
    2509             :     case codemaker::UnoType::SORT_ACCUMULATION_BASED_SERVICE:
    2510             :     case codemaker::UnoType::SORT_SERVICE_BASED_SINGLETON:
    2511        1019 :         break;
    2512             :     default:
    2513             :         throw CannotDumpException(
    2514           0 :             "unexpected entity \"" + name + "\" in call to produce");
    2515             :     }
    2516        4309 :     if (!options.isValid("-nD")) {
    2517       12098 :         for (Dependencies::iterator i(deps.begin()); i != deps.end(); ++i) {
    2518        7832 :             produce(*i, manager, generated, options);
    2519             :         }
    2520        4309 :     }
    2521             : }
    2522             : 
    2523             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10