LibreOffice Module bridges (master)  1
jni_base.h
Go to the documentation of this file.
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 #pragma once
21 
22 #include <sal/config.h>
23 
24 #include <cassert>
25 
28 
29 #include <osl/diagnose.h>
30 
31 #include <rtl/alloc.h>
32 #include <rtl/ustring.hxx>
33 #include <sal/log.hxx>
34 
35 #include <uno/environment.h>
36 #include <typelib/typedescription.h>
37 
38 
39 namespace jni_uno
40 {
41 
42 class JNI_info;
43 
45 {
46  OUString m_message;
47 
48  explicit BridgeRuntimeError( OUString const & message )
49  : m_message( message )
50  {}
51 };
52 
53 
55 {
57  JNIEnv * m_env;
58  jobject m_class_loader;
59 
60  JNI_context( JNI_context const & ) = delete;
61  JNI_context& operator = ( JNI_context const &) = delete;
62 
63  void java_exc_occurred() const;
64 public:
65  explicit JNI_context(
66  JNI_info const * jni_info, JNIEnv * env, jobject class_loader )
67  : m_jni_info( jni_info ),
68  m_env( env ),
69  m_class_loader( class_loader )
70  {}
71 
72  JNI_info const * get_info() const
73  { return m_jni_info; }
74 
75  JNIEnv * operator -> () const
76  { return m_env; }
77  JNIEnv * get_jni_env() const
78  { return m_env; }
79 
80  // does not handle exceptions, *classClass will be null if exception
81  // occurred:
82  void getClassForName(jclass * classClass, jmethodID * methodForName) const;
83 
84  // if inException, does not handle exceptions, in which case returned value
85  // will be null if exception occurred:
86  jclass findClass(
87  char const * name, jclass classClass, jmethodID methodForName,
88  bool inException) const;
89 
90  inline void ensure_no_exception() const; // throws BridgeRuntimeError
91  inline bool assert_no_exception() const; // asserts and clears exception
92 
93  OUString get_stack_trace( jobject jo_exc = nullptr ) const;
94 };
95 
97 {
98  if (m_env->ExceptionCheck())
99  {
101  }
102 }
103 
105 {
106  if (m_env->ExceptionCheck())
107  {
108  SAL_WARN("bridges", "unexpected java exception occurred");
109 #if OSL_DEBUG_LEVEL > 0
110  m_env->ExceptionDescribe();
111 #endif
112  m_env->ExceptionClear();
113  return false;
114  }
115  return true;
116 }
117 
118 
121  public JNI_context
122 {
123  JNI_guarded_context( JNI_guarded_context const & ) = delete;
125 
126 public:
128  JNI_info const * jni_info,
130  : AttachGuard( vm_access->getVirtualMachine() ),
131  JNI_context(
132  jni_info, AttachGuard::getEnvironment(),
133  static_cast< jobject >(vm_access->getClassLoader()) )
134  {}
135 };
136 
137 
139 {
141  jobject m_jo;
142 
143 public:
144  explicit JLocalAutoRef( JNI_context const & jni )
145  : m_jni( jni ),
146  m_jo( nullptr )
147  {}
148  explicit JLocalAutoRef( JNI_context const & jni, jobject jo )
149  : m_jni( jni ),
150  m_jo( jo )
151  {}
152  inline JLocalAutoRef( JLocalAutoRef & auto_ref );
153  inline ~JLocalAutoRef();
154 
155  jobject get() const
156  { return m_jo; }
157  bool is() const
158  { return (nullptr != m_jo); }
159  inline jobject release();
160  inline void reset( jobject jo );
161  inline JLocalAutoRef & operator = ( JLocalAutoRef & auto_ref );
162 };
163 
165 {
166  if (nullptr != m_jo)
167  m_jni->DeleteLocalRef( m_jo );
168 }
169 
171  : m_jni( auto_ref.m_jni ),
172  m_jo( auto_ref.m_jo )
173 {
174  auto_ref.m_jo = nullptr;
175 }
176 
177 inline jobject JLocalAutoRef::release()
178 {
179  jobject jo = m_jo;
180  m_jo = nullptr;
181  return jo;
182 }
183 
184 inline void JLocalAutoRef::reset( jobject jo )
185 {
186  if (jo != m_jo)
187  {
188  if (nullptr != m_jo)
189  m_jni->DeleteLocalRef( m_jo );
190  m_jo = jo;
191  }
192 }
193 
195 {
196  assert( m_jni.get_jni_env() == auto_ref.m_jni.get_jni_env() );
197  reset( auto_ref.m_jo );
198  auto_ref.m_jo = nullptr;
199  return *this;
200 }
201 
202 
203 
204 struct rtl_mem
205 {
206  static void * operator new ( size_t nSize )
207  { return std::malloc( nSize ); }
208  static void operator delete ( void * mem )
209  { std::free( mem ); }
210  static void * operator new ( size_t, void * mem )
211  { return mem; }
212  static void operator delete ( void *, void * )
213  {}
214 
215  static inline rtl_mem * allocate( std::size_t bytes );
216 };
217 
218 inline rtl_mem * rtl_mem::allocate( std::size_t bytes )
219 {
220  void * p = std::malloc( bytes );
221  if (nullptr == p)
222  throw BridgeRuntimeError( "out of memory!" );
223  return static_cast<rtl_mem *>(p);
224 }
225 
226 
228 {
230 
231  TypeDescr( TypeDescr const & ) = delete;
232  TypeDescr& operator = ( TypeDescr const & ) = delete;
233 
234 public:
235  inline explicit TypeDescr( typelib_TypeDescriptionReference * td_ref );
237  { TYPELIB_DANGER_RELEASE( m_td ); }
238 
240  { return m_td; }
241 };
242 
243 inline TypeDescr::TypeDescr( typelib_TypeDescriptionReference * td_ref )
244  : m_td( nullptr )
245 {
246  TYPELIB_DANGER_GET( &m_td, td_ref );
247  if (nullptr == m_td)
248  {
249  throw BridgeRuntimeError(
250  "cannot get comprehensive type description for " +
251  OUString::unacquired( &td_ref->pTypeName ) );
252  }
253 }
254 
255 }
256 
257 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
BridgeRuntimeError(OUString const &message)
Definition: jni_base.h:48
void java_exc_occurred() const
Definition: jni_bridge.cxx:276
JNI_context(JNI_info const *jni_info, JNIEnv *env, jobject class_loader)
Definition: jni_base.h:65
JNIEnv * get_jni_env() const
Definition: jni_base.h:77
std::vector< sal_uInt8 > bytes
JLocalAutoRef(JNI_context const &jni, jobject jo)
Definition: jni_base.h:148
JNI_context(JNI_context const &)=delete
bool assert_no_exception() const
Definition: jni_base.h:104
jobject m_class_loader
Definition: jni_base.h:58
JNI_info const * get_info() const
Definition: jni_base.h:72
OUString get_stack_trace(jobject jo_exc=nullptr) const
Definition: jni_bridge.cxx:377
TypeDescr(TypeDescr const &)=delete
const BorderLinePrimitive2D *pCandidateB assert(pCandidateA)
AttachGuard(rtl::Reference< VirtualMachine > const &rMachine)
JNI_info const * m_jni_info
Definition: jni_base.h:56
void ensure_no_exception() const
Definition: jni_base.h:96
bool is() const
Definition: jni_base.h:157
void reset(jobject jo)
Definition: jni_base.h:184
JLocalAutoRef(JNI_context const &jni)
Definition: jni_base.h:144
typelib_TypeDescription * m_td
Definition: jni_base.h:229
JNI_guarded_context & operator=(JNI_guarded_context const &)=delete
JNI_guarded_context(JNI_guarded_context const &)=delete
jclass findClass(char const *name, jclass classClass, jmethodID methodForName, bool inException) const
Definition: jni_bridge.cxx:356
JNI_guarded_context(JNI_info const *jni_info, rtl::Reference< jvmaccess::UnoVirtualMachine > const &vm_access)
Definition: jni_base.h:127
JLocalAutoRef & operator=(JLocalAutoRef &auto_ref)
Definition: jni_base.h:194
struct _typelib_TypeDescription typelib_TypeDescription
Definition: msvc/except.hxx:52
friend friend class AttachGuard
JNIEnv * operator->() const
Definition: jni_base.h:75
void getClassForName(jclass *classClass, jmethodID *methodForName) const
Definition: jni_bridge.cxx:343
void * p
#define SAL_WARN(area, stream)
static rtl_mem * allocate(std::size_t bytes)
Definition: jni_base.h:218
JNI_context const & m_jni
Definition: jni_base.h:140
TypeDescr & operator=(TypeDescr const &)=delete
JNI_context & operator=(JNI_context const &)=delete
char const * name