SQLite Android Bindings
Hex Artifact Content
Not logged in

Artifact f824fc144781dc1c004dafa8d5cd62905e77d313:


0000: 2f 2a 0a 20 2a 20 43 6f 70 79 72 69 67 68 74 20  /*. * Copyright 
0010: 28 43 29 20 32 30 30 36 20 54 68 65 20 41 6e 64  (C) 2006 The And
0020: 72 6f 69 64 20 4f 70 65 6e 20 53 6f 75 72 63 65  roid Open Source
0030: 20 50 72 6f 6a 65 63 74 0a 20 2a 0a 20 2a 20 4c   Project. *. * L
0040: 69 63 65 6e 73 65 64 20 75 6e 64 65 72 20 74 68  icensed under th
0050: 65 20 41 70 61 63 68 65 20 4c 69 63 65 6e 73 65  e Apache License
0060: 2c 20 56 65 72 73 69 6f 6e 20 32 2e 30 20 28 74  , Version 2.0 (t
0070: 68 65 20 22 4c 69 63 65 6e 73 65 22 29 3b 0a 20  he "License");. 
0080: 2a 20 79 6f 75 20 6d 61 79 20 6e 6f 74 20 75 73  * you may not us
0090: 65 20 74 68 69 73 20 66 69 6c 65 20 65 78 63 65  e this file exce
00a0: 70 74 20 69 6e 20 63 6f 6d 70 6c 69 61 6e 63 65  pt in compliance
00b0: 20 77 69 74 68 20 74 68 65 20 4c 69 63 65 6e 73   with the Licens
00c0: 65 2e 0a 20 2a 20 59 6f 75 20 6d 61 79 20 6f 62  e.. * You may ob
00d0: 74 61 69 6e 20 61 20 63 6f 70 79 20 6f 66 20 74  tain a copy of t
00e0: 68 65 20 4c 69 63 65 6e 73 65 20 61 74 0a 20 2a  he License at. *
00f0: 0a 20 2a 20 20 20 20 20 20 68 74 74 70 3a 2f 2f  . *      http://
0100: 77 77 77 2e 61 70 61 63 68 65 2e 6f 72 67 2f 6c  www.apache.org/l
0110: 69 63 65 6e 73 65 73 2f 4c 49 43 45 4e 53 45 2d  icenses/LICENSE-
0120: 32 2e 30 0a 20 2a 0a 20 2a 20 55 6e 6c 65 73 73  2.0. *. * Unless
0130: 20 72 65 71 75 69 72 65 64 20 62 79 20 61 70 70   required by app
0140: 6c 69 63 61 62 6c 65 20 6c 61 77 20 6f 72 20 61  licable law or a
0150: 67 72 65 65 64 20 74 6f 20 69 6e 20 77 72 69 74  greed to in writ
0160: 69 6e 67 2c 20 73 6f 66 74 77 61 72 65 0a 20 2a  ing, software. *
0170: 20 64 69 73 74 72 69 62 75 74 65 64 20 75 6e 64   distributed und
0180: 65 72 20 74 68 65 20 4c 69 63 65 6e 73 65 20 69  er the License i
0190: 73 20 64 69 73 74 72 69 62 75 74 65 64 20 6f 6e  s distributed on
01a0: 20 61 6e 20 22 41 53 20 49 53 22 20 42 41 53 49   an "AS IS" BASI
01b0: 53 2c 0a 20 2a 20 57 49 54 48 4f 55 54 20 57 41  S,. * WITHOUT WA
01c0: 52 52 41 4e 54 49 45 53 20 4f 52 20 43 4f 4e 44  RRANTIES OR COND
01d0: 49 54 49 4f 4e 53 20 4f 46 20 41 4e 59 20 4b 49  ITIONS OF ANY KI
01e0: 4e 44 2c 20 65 69 74 68 65 72 20 65 78 70 72 65  ND, either expre
01f0: 73 73 20 6f 72 20 69 6d 70 6c 69 65 64 2e 0a 20  ss or implied.. 
0200: 2a 20 53 65 65 20 74 68 65 20 4c 69 63 65 6e 73  * See the Licens
0210: 65 20 66 6f 72 20 74 68 65 20 73 70 65 63 69 66  e for the specif
0220: 69 63 20 6c 61 6e 67 75 61 67 65 20 67 6f 76 65  ic language gove
0230: 72 6e 69 6e 67 20 70 65 72 6d 69 73 73 69 6f 6e  rning permission
0240: 73 20 61 6e 64 0a 20 2a 20 6c 69 6d 69 74 61 74  s and. * limitat
0250: 69 6f 6e 73 20 75 6e 64 65 72 20 74 68 65 20 4c  ions under the L
0260: 69 63 65 6e 73 65 2e 0a 20 2a 2f 0a 0a 23 64 65  icense.. */..#de
0270: 66 69 6e 65 20 4c 4f 47 5f 54 41 47 20 22 4a 4e  fine LOG_TAG "JN
0280: 49 48 65 6c 70 22 0a 0a 23 69 6e 63 6c 75 64 65  IHelp"..#include
0290: 20 22 4a 6e 69 43 6f 6e 73 74 61 6e 74 73 2e 68   "JniConstants.h
02a0: 22 0a 23 69 6e 63 6c 75 64 65 20 22 4a 4e 49 48  ".#include "JNIH
02b0: 65 6c 70 2e 68 22 0a 23 69 6e 63 6c 75 64 65 20  elp.h".#include 
02c0: 22 41 4c 6f 67 2d 70 72 69 76 2e 68 22 0a 0a 23  "ALog-priv.h"..#
02d0: 69 6e 63 6c 75 64 65 20 3c 73 74 64 69 6f 2e 68  include <stdio.h
02e0: 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 73 74 64 6c  >.#include <stdl
02f0: 69 62 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c  ib.h>.#include <
0300: 73 74 72 69 6e 67 2e 68 3e 0a 23 69 6e 63 6c 75  string.h>.#inclu
0310: 64 65 20 3c 61 73 73 65 72 74 2e 68 3e 0a 0a 23  de <assert.h>..#
0320: 69 6e 63 6c 75 64 65 20 3c 73 74 72 69 6e 67 3e  include <string>
0330: 0a 0a 2f 2a 2a 0a 20 2a 20 45 71 75 69 76 61 6c  ../**. * Equival
0340: 65 6e 74 20 74 6f 20 53 63 6f 70 65 64 4c 6f 63  ent to ScopedLoc
0350: 61 6c 52 65 66 2c 20 62 75 74 20 66 6f 72 20 43  alRef, but for C
0360: 5f 4a 4e 49 45 6e 76 20 69 6e 73 74 65 61 64 2e  _JNIEnv instead.
0370: 20 28 41 6e 64 20 73 6c 69 67 68 74 6c 79 20 6d   (And slightly m
0380: 6f 72 65 20 70 6f 77 65 72 66 75 6c 2e 29 0a 20  ore powerful.). 
0390: 2a 2f 0a 74 65 6d 70 6c 61 74 65 3c 74 79 70 65  */.template<type
03a0: 6e 61 6d 65 20 54 3e 0a 63 6c 61 73 73 20 73 63  name T>.class sc
03b0: 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 20 7b  oped_local_ref {
03c0: 0a 70 75 62 6c 69 63 3a 0a 20 20 20 20 73 63 6f  .public:.    sco
03d0: 70 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 28 43 5f  ped_local_ref(C_
03e0: 4a 4e 49 45 6e 76 2a 20 65 6e 76 2c 20 54 20 6c  JNIEnv* env, T l
03f0: 6f 63 61 6c 52 65 66 20 3d 20 4e 55 4c 4c 29 0a  ocalRef = NULL).
0400: 20 20 20 20 3a 20 6d 45 6e 76 28 65 6e 76 29 2c      : mEnv(env),
0410: 20 6d 4c 6f 63 61 6c 52 65 66 28 6c 6f 63 61 6c   mLocalRef(local
0420: 52 65 66 29 0a 20 20 20 20 7b 0a 20 20 20 20 7d  Ref).    {.    }
0430: 0a 0a 20 20 20 20 7e 73 63 6f 70 65 64 5f 6c 6f  ..    ~scoped_lo
0440: 63 61 6c 5f 72 65 66 28 29 20 7b 0a 20 20 20 20  cal_ref() {.    
0450: 20 20 20 20 72 65 73 65 74 28 29 3b 0a 20 20 20      reset();.   
0460: 20 7d 0a 0a 20 20 20 20 76 6f 69 64 20 72 65 73   }..    void res
0470: 65 74 28 54 20 6c 6f 63 61 6c 52 65 66 20 3d 20  et(T localRef = 
0480: 4e 55 4c 4c 29 20 7b 0a 20 20 20 20 20 20 20 20  NULL) {.        
0490: 69 66 20 28 6d 4c 6f 63 61 6c 52 65 66 20 21 3d  if (mLocalRef !=
04a0: 20 4e 55 4c 4c 29 20 7b 0a 20 20 20 20 20 20 20   NULL) {.       
04b0: 20 20 20 20 20 28 2a 6d 45 6e 76 29 2d 3e 44 65       (*mEnv)->De
04c0: 6c 65 74 65 4c 6f 63 61 6c 52 65 66 28 72 65 69  leteLocalRef(rei
04d0: 6e 74 65 72 70 72 65 74 5f 63 61 73 74 3c 4a 4e  nterpret_cast<JN
04e0: 49 45 6e 76 2a 3e 28 6d 45 6e 76 29 2c 20 6d 4c  IEnv*>(mEnv), mL
04f0: 6f 63 61 6c 52 65 66 29 3b 0a 20 20 20 20 20 20  ocalRef);.      
0500: 20 20 20 20 20 20 6d 4c 6f 63 61 6c 52 65 66 20        mLocalRef 
0510: 3d 20 6c 6f 63 61 6c 52 65 66 3b 0a 20 20 20 20  = localRef;.    
0520: 20 20 20 20 7d 0a 20 20 20 20 7d 0a 0a 20 20 20      }.    }..   
0530: 20 54 20 67 65 74 28 29 20 63 6f 6e 73 74 20 7b   T get() const {
0540: 0a 20 20 20 20 20 20 20 20 72 65 74 75 72 6e 20  .        return 
0550: 6d 4c 6f 63 61 6c 52 65 66 3b 0a 20 20 20 20 7d  mLocalRef;.    }
0560: 0a 0a 70 72 69 76 61 74 65 3a 0a 20 20 20 20 43  ..private:.    C
0570: 5f 4a 4e 49 45 6e 76 2a 20 6d 45 6e 76 3b 0a 20  _JNIEnv* mEnv;. 
0580: 20 20 20 54 20 6d 4c 6f 63 61 6c 52 65 66 3b 0a     T mLocalRef;.
0590: 0a 20 20 20 20 2f 2f 20 44 69 73 61 6c 6c 6f 77  .    // Disallow
05a0: 20 63 6f 70 79 20 61 6e 64 20 61 73 73 69 67 6e   copy and assign
05b0: 6d 65 6e 74 2e 0a 20 20 20 20 73 63 6f 70 65 64  ment..    scoped
05c0: 5f 6c 6f 63 61 6c 5f 72 65 66 28 63 6f 6e 73 74  _local_ref(const
05d0: 20 73 63 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65   scoped_local_re
05e0: 66 26 29 3b 0a 20 20 20 20 76 6f 69 64 20 6f 70  f&);.    void op
05f0: 65 72 61 74 6f 72 3d 28 63 6f 6e 73 74 20 73 63  erator=(const sc
0600: 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 26 29  oped_local_ref&)
0610: 3b 0a 7d 3b 0a 0a 73 74 61 74 69 63 20 6a 63 6c  ;.};..static jcl
0620: 61 73 73 20 66 69 6e 64 43 6c 61 73 73 28 43 5f  ass findClass(C_
0630: 4a 4e 49 45 6e 76 2a 20 65 6e 76 2c 20 63 6f 6e  JNIEnv* env, con
0640: 73 74 20 63 68 61 72 2a 20 63 6c 61 73 73 4e 61  st char* classNa
0650: 6d 65 29 20 7b 0a 20 20 20 20 4a 4e 49 45 6e 76  me) {.    JNIEnv
0660: 2a 20 65 20 3d 20 72 65 69 6e 74 65 72 70 72 65  * e = reinterpre
0670: 74 5f 63 61 73 74 3c 4a 4e 49 45 6e 76 2a 3e 28  t_cast<JNIEnv*>(
0680: 65 6e 76 29 3b 0a 20 20 20 20 72 65 74 75 72 6e  env);.    return
0690: 20 28 2a 65 6e 76 29 2d 3e 46 69 6e 64 43 6c 61   (*env)->FindCla
06a0: 73 73 28 65 2c 20 63 6c 61 73 73 4e 61 6d 65 29  ss(e, className)
06b0: 3b 0a 7d 0a 0a 65 78 74 65 72 6e 20 22 43 22 20  ;.}..extern "C" 
06c0: 69 6e 74 20 6a 6e 69 52 65 67 69 73 74 65 72 4e  int jniRegisterN
06d0: 61 74 69 76 65 4d 65 74 68 6f 64 73 28 43 5f 4a  ativeMethods(C_J
06e0: 4e 49 45 6e 76 2a 20 65 6e 76 2c 20 63 6f 6e 73  NIEnv* env, cons
06f0: 74 20 63 68 61 72 2a 20 63 6c 61 73 73 4e 61 6d  t char* classNam
0700: 65 2c 0a 20 20 20 20 63 6f 6e 73 74 20 4a 4e 49  e,.    const JNI
0710: 4e 61 74 69 76 65 4d 65 74 68 6f 64 2a 20 67 4d  NativeMethod* gM
0720: 65 74 68 6f 64 73 2c 20 69 6e 74 20 6e 75 6d 4d  ethods, int numM
0730: 65 74 68 6f 64 73 29 0a 7b 0a 20 20 20 20 4a 4e  ethods).{.    JN
0740: 49 45 6e 76 2a 20 65 20 3d 20 72 65 69 6e 74 65  IEnv* e = reinte
0750: 72 70 72 65 74 5f 63 61 73 74 3c 4a 4e 49 45 6e  rpret_cast<JNIEn
0760: 76 2a 3e 28 65 6e 76 29 3b 0a 0a 20 20 20 20 41  v*>(env);..    A
0770: 4c 4f 47 56 28 22 52 65 67 69 73 74 65 72 69 6e  LOGV("Registerin
0780: 67 20 25 73 27 73 20 25 64 20 6e 61 74 69 76 65  g %s's %d native
0790: 20 6d 65 74 68 6f 64 73 2e 2e 2e 22 2c 20 63 6c   methods...", cl
07a0: 61 73 73 4e 61 6d 65 2c 20 6e 75 6d 4d 65 74 68  assName, numMeth
07b0: 6f 64 73 29 3b 0a 0a 20 20 20 20 73 63 6f 70 65  ods);..    scope
07c0: 64 5f 6c 6f 63 61 6c 5f 72 65 66 3c 6a 63 6c 61  d_local_ref<jcla
07d0: 73 73 3e 20 63 28 65 6e 76 2c 20 66 69 6e 64 43  ss> c(env, findC
07e0: 6c 61 73 73 28 65 6e 76 2c 20 63 6c 61 73 73 4e  lass(env, classN
07f0: 61 6d 65 29 29 3b 0a 20 20 20 20 69 66 20 28 63  ame));.    if (c
0800: 2e 67 65 74 28 29 20 3d 3d 20 4e 55 4c 4c 29 20  .get() == NULL) 
0810: 7b 0a 20 20 20 20 20 20 20 20 63 68 61 72 2a 20  {.        char* 
0820: 6d 73 67 3b 0a 20 20 20 20 20 20 20 20 61 73 70  msg;.        asp
0830: 72 69 6e 74 66 28 26 6d 73 67 2c 20 22 4e 61 74  rintf(&msg, "Nat
0840: 69 76 65 20 72 65 67 69 73 74 72 61 74 69 6f 6e  ive registration
0850: 20 75 6e 61 62 6c 65 20 74 6f 20 66 69 6e 64 20   unable to find 
0860: 63 6c 61 73 73 20 27 25 73 27 3b 20 61 62 6f 72  class '%s'; abor
0870: 74 69 6e 67 2e 2e 2e 22 2c 20 63 6c 61 73 73 4e  ting...", classN
0880: 61 6d 65 29 3b 0a 20 20 20 20 20 20 20 20 65 2d  ame);.        e-
0890: 3e 46 61 74 61 6c 45 72 72 6f 72 28 6d 73 67 29  >FatalError(msg)
08a0: 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 20  ;.    }..    if 
08b0: 28 28 2a 65 6e 76 29 2d 3e 52 65 67 69 73 74 65  ((*env)->Registe
08c0: 72 4e 61 74 69 76 65 73 28 65 2c 20 63 2e 67 65  rNatives(e, c.ge
08d0: 74 28 29 2c 20 67 4d 65 74 68 6f 64 73 2c 20 6e  t(), gMethods, n
08e0: 75 6d 4d 65 74 68 6f 64 73 29 20 3c 20 30 29 20  umMethods) < 0) 
08f0: 7b 0a 20 20 20 20 20 20 20 20 63 68 61 72 2a 20  {.        char* 
0900: 6d 73 67 3b 0a 20 20 20 20 20 20 20 20 61 73 70  msg;.        asp
0910: 72 69 6e 74 66 28 26 6d 73 67 2c 20 22 52 65 67  rintf(&msg, "Reg
0920: 69 73 74 65 72 4e 61 74 69 76 65 73 20 66 61 69  isterNatives fai
0930: 6c 65 64 20 66 6f 72 20 27 25 73 27 3b 20 61 62  led for '%s'; ab
0940: 6f 72 74 69 6e 67 2e 2e 2e 22 2c 20 63 6c 61 73  orting...", clas
0950: 73 4e 61 6d 65 29 3b 0a 20 20 20 20 20 20 20 20  sName);.        
0960: 65 2d 3e 46 61 74 61 6c 45 72 72 6f 72 28 6d 73  e->FatalError(ms
0970: 67 29 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 72  g);.    }..    r
0980: 65 74 75 72 6e 20 30 3b 0a 7d 0a 0a 2f 2a 0a 20  eturn 0;.}../*. 
0990: 2a 20 52 65 74 75 72 6e 73 20 61 20 68 75 6d 61  * Returns a huma
09a0: 6e 2d 72 65 61 64 61 62 6c 65 20 73 75 6d 6d 61  n-readable summa
09b0: 72 79 20 6f 66 20 61 6e 20 65 78 63 65 70 74 69  ry of an excepti
09c0: 6f 6e 20 6f 62 6a 65 63 74 2e 20 20 54 68 65 20  on object.  The 
09d0: 62 75 66 66 65 72 20 77 69 6c 6c 0a 20 2a 20 62  buffer will. * b
09e0: 65 20 70 6f 70 75 6c 61 74 65 64 20 77 69 74 68  e populated with
09f0: 20 74 68 65 20 22 62 69 6e 61 72 79 22 20 63 6c   the "binary" cl
0a00: 61 73 73 20 6e 61 6d 65 20 61 6e 64 2c 20 69 66  ass name and, if
0a10: 20 70 72 65 73 65 6e 74 2c 20 74 68 65 0a 20 2a   present, the. *
0a20: 20 65 78 63 65 70 74 69 6f 6e 20 6d 65 73 73 61   exception messa
0a30: 67 65 2e 0a 20 2a 2f 0a 73 74 61 74 69 63 20 62  ge.. */.static b
0a40: 6f 6f 6c 20 67 65 74 45 78 63 65 70 74 69 6f 6e  ool getException
0a50: 53 75 6d 6d 61 72 79 28 43 5f 4a 4e 49 45 6e 76  Summary(C_JNIEnv
0a60: 2a 20 65 6e 76 2c 20 6a 74 68 72 6f 77 61 62 6c  * env, jthrowabl
0a70: 65 20 65 78 63 65 70 74 69 6f 6e 2c 20 73 74 64  e exception, std
0a80: 3a 3a 73 74 72 69 6e 67 26 20 72 65 73 75 6c 74  ::string& result
0a90: 29 20 7b 0a 20 20 20 20 4a 4e 49 45 6e 76 2a 20  ) {.    JNIEnv* 
0aa0: 65 20 3d 20 72 65 69 6e 74 65 72 70 72 65 74 5f  e = reinterpret_
0ab0: 63 61 73 74 3c 4a 4e 49 45 6e 76 2a 3e 28 65 6e  cast<JNIEnv*>(en
0ac0: 76 29 3b 0a 0a 20 20 20 20 2f 2a 20 67 65 74 20  v);..    /* get 
0ad0: 74 68 65 20 6e 61 6d 65 20 6f 66 20 74 68 65 20  the name of the 
0ae0: 65 78 63 65 70 74 69 6f 6e 27 73 20 63 6c 61 73  exception's clas
0af0: 73 20 2a 2f 0a 20 20 20 20 73 63 6f 70 65 64 5f  s */.    scoped_
0b00: 6c 6f 63 61 6c 5f 72 65 66 3c 6a 63 6c 61 73 73  local_ref<jclass
0b10: 3e 20 65 78 63 65 70 74 69 6f 6e 43 6c 61 73 73  > exceptionClass
0b20: 28 65 6e 76 2c 20 28 2a 65 6e 76 29 2d 3e 47 65  (env, (*env)->Ge
0b30: 74 4f 62 6a 65 63 74 43 6c 61 73 73 28 65 2c 20  tObjectClass(e, 
0b40: 65 78 63 65 70 74 69 6f 6e 29 29 3b 20 2f 2f 20  exception)); // 
0b50: 63 61 6e 27 74 20 66 61 69 6c 0a 20 20 20 20 73  can't fail.    s
0b60: 63 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 3c  coped_local_ref<
0b70: 6a 63 6c 61 73 73 3e 20 63 6c 61 73 73 43 6c 61  jclass> classCla
0b80: 73 73 28 65 6e 76 2c 0a 20 20 20 20 20 20 20 20  ss(env,.        
0b90: 20 20 20 20 28 2a 65 6e 76 29 2d 3e 47 65 74 4f      (*env)->GetO
0ba0: 62 6a 65 63 74 43 6c 61 73 73 28 65 2c 20 65 78  bjectClass(e, ex
0bb0: 63 65 70 74 69 6f 6e 43 6c 61 73 73 2e 67 65 74  ceptionClass.get
0bc0: 28 29 29 29 3b 20 2f 2f 20 6a 61 76 61 2e 6c 61  ())); // java.la
0bd0: 6e 67 2e 43 6c 61 73 73 2c 20 63 61 6e 27 74 20  ng.Class, can't 
0be0: 66 61 69 6c 0a 20 20 20 20 6a 6d 65 74 68 6f 64  fail.    jmethod
0bf0: 49 44 20 63 6c 61 73 73 47 65 74 4e 61 6d 65 4d  ID classGetNameM
0c00: 65 74 68 6f 64 20 3d 0a 20 20 20 20 20 20 20 20  ethod =.        
0c10: 20 20 20 20 28 2a 65 6e 76 29 2d 3e 47 65 74 4d      (*env)->GetM
0c20: 65 74 68 6f 64 49 44 28 65 2c 20 63 6c 61 73 73  ethodID(e, class
0c30: 43 6c 61 73 73 2e 67 65 74 28 29 2c 20 22 67 65  Class.get(), "ge
0c40: 74 4e 61 6d 65 22 2c 20 22 28 29 4c 6a 61 76 61  tName", "()Ljava
0c50: 2f 6c 61 6e 67 2f 53 74 72 69 6e 67 3b 22 29 3b  /lang/String;");
0c60: 0a 20 20 20 20 73 63 6f 70 65 64 5f 6c 6f 63 61  .    scoped_loca
0c70: 6c 5f 72 65 66 3c 6a 73 74 72 69 6e 67 3e 20 63  l_ref<jstring> c
0c80: 6c 61 73 73 4e 61 6d 65 53 74 72 28 65 6e 76 2c  lassNameStr(env,
0c90: 0a 20 20 20 20 20 20 20 20 20 20 20 20 28 6a 73  .            (js
0ca0: 74 72 69 6e 67 29 20 28 2a 65 6e 76 29 2d 3e 43  tring) (*env)->C
0cb0: 61 6c 6c 4f 62 6a 65 63 74 4d 65 74 68 6f 64 28  allObjectMethod(
0cc0: 65 2c 20 65 78 63 65 70 74 69 6f 6e 43 6c 61 73  e, exceptionClas
0cd0: 73 2e 67 65 74 28 29 2c 20 63 6c 61 73 73 47 65  s.get(), classGe
0ce0: 74 4e 61 6d 65 4d 65 74 68 6f 64 29 29 3b 0a 20  tNameMethod));. 
0cf0: 20 20 20 69 66 20 28 63 6c 61 73 73 4e 61 6d 65     if (className
0d00: 53 74 72 2e 67 65 74 28 29 20 3d 3d 20 4e 55 4c  Str.get() == NUL
0d10: 4c 29 20 7b 0a 20 20 20 20 20 20 20 20 28 2a 65  L) {.        (*e
0d20: 6e 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e 43 6c  nv)->ExceptionCl
0d30: 65 61 72 28 65 29 3b 0a 20 20 20 20 20 20 20 20  ear(e);.        
0d40: 72 65 73 75 6c 74 20 3d 20 22 3c 65 72 72 6f 72  result = "<error
0d50: 20 67 65 74 74 69 6e 67 20 63 6c 61 73 73 20 6e   getting class n
0d60: 61 6d 65 3e 22 3b 0a 20 20 20 20 20 20 20 20 72  ame>";.        r
0d70: 65 74 75 72 6e 20 66 61 6c 73 65 3b 0a 20 20 20  eturn false;.   
0d80: 20 7d 0a 20 20 20 20 63 6f 6e 73 74 20 63 68 61   }.    const cha
0d90: 72 2a 20 63 6c 61 73 73 4e 61 6d 65 43 68 61 72  r* classNameChar
0da0: 73 20 3d 20 28 2a 65 6e 76 29 2d 3e 47 65 74 53  s = (*env)->GetS
0db0: 74 72 69 6e 67 55 54 46 43 68 61 72 73 28 65 2c  tringUTFChars(e,
0dc0: 20 63 6c 61 73 73 4e 61 6d 65 53 74 72 2e 67 65   classNameStr.ge
0dd0: 74 28 29 2c 20 4e 55 4c 4c 29 3b 0a 20 20 20 20  t(), NULL);.    
0de0: 69 66 20 28 63 6c 61 73 73 4e 61 6d 65 43 68 61  if (classNameCha
0df0: 72 73 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 20 20  rs == NULL) {.  
0e00: 20 20 20 20 20 20 28 2a 65 6e 76 29 2d 3e 45 78        (*env)->Ex
0e10: 63 65 70 74 69 6f 6e 43 6c 65 61 72 28 65 29 3b  ceptionClear(e);
0e20: 0a 20 20 20 20 20 20 20 20 72 65 73 75 6c 74 20  .        result 
0e30: 3d 20 22 3c 65 72 72 6f 72 20 67 65 74 74 69 6e  = "<error gettin
0e40: 67 20 63 6c 61 73 73 20 6e 61 6d 65 20 55 54 46  g class name UTF
0e50: 2d 38 3e 22 3b 0a 20 20 20 20 20 20 20 20 72 65  -8>";.        re
0e60: 74 75 72 6e 20 66 61 6c 73 65 3b 0a 20 20 20 20  turn false;.    
0e70: 7d 0a 20 20 20 20 72 65 73 75 6c 74 20 2b 3d 20  }.    result += 
0e80: 63 6c 61 73 73 4e 61 6d 65 43 68 61 72 73 3b 0a  classNameChars;.
0e90: 20 20 20 20 28 2a 65 6e 76 29 2d 3e 52 65 6c 65      (*env)->Rele
0ea0: 61 73 65 53 74 72 69 6e 67 55 54 46 43 68 61 72  aseStringUTFChar
0eb0: 73 28 65 2c 20 63 6c 61 73 73 4e 61 6d 65 53 74  s(e, classNameSt
0ec0: 72 2e 67 65 74 28 29 2c 20 63 6c 61 73 73 4e 61  r.get(), classNa
0ed0: 6d 65 43 68 61 72 73 29 3b 0a 0a 20 20 20 20 2f  meChars);..    /
0ee0: 2a 20 69 66 20 74 68 65 20 65 78 63 65 70 74 69  * if the excepti
0ef0: 6f 6e 20 68 61 73 20 61 20 64 65 74 61 69 6c 20  on has a detail 
0f00: 6d 65 73 73 61 67 65 2c 20 67 65 74 20 74 68 61  message, get tha
0f10: 74 20 2a 2f 0a 20 20 20 20 6a 6d 65 74 68 6f 64  t */.    jmethod
0f20: 49 44 20 67 65 74 4d 65 73 73 61 67 65 20 3d 0a  ID getMessage =.
0f30: 20 20 20 20 20 20 20 20 20 20 20 20 28 2a 65 6e              (*en
0f40: 76 29 2d 3e 47 65 74 4d 65 74 68 6f 64 49 44 28  v)->GetMethodID(
0f50: 65 2c 20 65 78 63 65 70 74 69 6f 6e 43 6c 61 73  e, exceptionClas
0f60: 73 2e 67 65 74 28 29 2c 20 22 67 65 74 4d 65 73  s.get(), "getMes
0f70: 73 61 67 65 22 2c 20 22 28 29 4c 6a 61 76 61 2f  sage", "()Ljava/
0f80: 6c 61 6e 67 2f 53 74 72 69 6e 67 3b 22 29 3b 0a  lang/String;");.
0f90: 20 20 20 20 73 63 6f 70 65 64 5f 6c 6f 63 61 6c      scoped_local
0fa0: 5f 72 65 66 3c 6a 73 74 72 69 6e 67 3e 20 6d 65  _ref<jstring> me
0fb0: 73 73 61 67 65 53 74 72 28 65 6e 76 2c 0a 20 20  ssageStr(env,.  
0fc0: 20 20 20 20 20 20 20 20 20 20 28 6a 73 74 72 69            (jstri
0fd0: 6e 67 29 20 28 2a 65 6e 76 29 2d 3e 43 61 6c 6c  ng) (*env)->Call
0fe0: 4f 62 6a 65 63 74 4d 65 74 68 6f 64 28 65 2c 20  ObjectMethod(e, 
0ff0: 65 78 63 65 70 74 69 6f 6e 2c 20 67 65 74 4d 65  exception, getMe
1000: 73 73 61 67 65 29 29 3b 0a 20 20 20 20 69 66 20  ssage));.    if 
1010: 28 6d 65 73 73 61 67 65 53 74 72 2e 67 65 74 28  (messageStr.get(
1020: 29 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 20 20 20  ) == NULL) {.   
1030: 20 20 20 20 20 72 65 74 75 72 6e 20 74 72 75 65       return true
1040: 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 72 65 73  ;.    }..    res
1050: 75 6c 74 20 2b 3d 20 22 3a 20 22 3b 0a 0a 20 20  ult += ": ";..  
1060: 20 20 63 6f 6e 73 74 20 63 68 61 72 2a 20 6d 65    const char* me
1070: 73 73 61 67 65 43 68 61 72 73 20 3d 20 28 2a 65  ssageChars = (*e
1080: 6e 76 29 2d 3e 47 65 74 53 74 72 69 6e 67 55 54  nv)->GetStringUT
1090: 46 43 68 61 72 73 28 65 2c 20 6d 65 73 73 61 67  FChars(e, messag
10a0: 65 53 74 72 2e 67 65 74 28 29 2c 20 4e 55 4c 4c  eStr.get(), NULL
10b0: 29 3b 0a 20 20 20 20 69 66 20 28 6d 65 73 73 61  );.    if (messa
10c0: 67 65 43 68 61 72 73 20 21 3d 20 4e 55 4c 4c 29  geChars != NULL)
10d0: 20 7b 0a 20 20 20 20 20 20 20 20 72 65 73 75 6c   {.        resul
10e0: 74 20 2b 3d 20 6d 65 73 73 61 67 65 43 68 61 72  t += messageChar
10f0: 73 3b 0a 20 20 20 20 20 20 20 20 28 2a 65 6e 76  s;.        (*env
1100: 29 2d 3e 52 65 6c 65 61 73 65 53 74 72 69 6e 67  )->ReleaseString
1110: 55 54 46 43 68 61 72 73 28 65 2c 20 6d 65 73 73  UTFChars(e, mess
1120: 61 67 65 53 74 72 2e 67 65 74 28 29 2c 20 6d 65  ageStr.get(), me
1130: 73 73 61 67 65 43 68 61 72 73 29 3b 0a 20 20 20  ssageChars);.   
1140: 20 7d 20 65 6c 73 65 20 7b 0a 20 20 20 20 20 20   } else {.      
1150: 20 20 72 65 73 75 6c 74 20 2b 3d 20 22 3c 65 72    result += "<er
1160: 72 6f 72 20 67 65 74 74 69 6e 67 20 6d 65 73 73  ror getting mess
1170: 61 67 65 3e 22 3b 0a 20 20 20 20 20 20 20 20 28  age>";.        (
1180: 2a 65 6e 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e  *env)->Exception
1190: 43 6c 65 61 72 28 65 29 3b 20 2f 2f 20 63 6c 65  Clear(e); // cle
11a0: 61 72 20 4f 4f 4d 0a 20 20 20 20 7d 0a 0a 20 20  ar OOM.    }..  
11b0: 20 20 72 65 74 75 72 6e 20 74 72 75 65 3b 0a 7d    return true;.}
11c0: 0a 0a 2f 2a 0a 20 2a 20 52 65 74 75 72 6e 73 20  ../*. * Returns 
11d0: 61 6e 20 65 78 63 65 70 74 69 6f 6e 20 28 77 69  an exception (wi
11e0: 74 68 20 73 74 61 63 6b 20 74 72 61 63 65 29 20  th stack trace) 
11f0: 61 73 20 61 20 73 74 72 69 6e 67 2e 0a 20 2a 2f  as a string.. */
1200: 0a 73 74 61 74 69 63 20 62 6f 6f 6c 20 67 65 74  .static bool get
1210: 53 74 61 63 6b 54 72 61 63 65 28 43 5f 4a 4e 49  StackTrace(C_JNI
1220: 45 6e 76 2a 20 65 6e 76 2c 20 6a 74 68 72 6f 77  Env* env, jthrow
1230: 61 62 6c 65 20 65 78 63 65 70 74 69 6f 6e 2c 20  able exception, 
1240: 73 74 64 3a 3a 73 74 72 69 6e 67 26 20 72 65 73  std::string& res
1250: 75 6c 74 29 20 7b 0a 20 20 20 20 4a 4e 49 45 6e  ult) {.    JNIEn
1260: 76 2a 20 65 20 3d 20 72 65 69 6e 74 65 72 70 72  v* e = reinterpr
1270: 65 74 5f 63 61 73 74 3c 4a 4e 49 45 6e 76 2a 3e  et_cast<JNIEnv*>
1280: 28 65 6e 76 29 3b 0a 0a 20 20 20 20 73 63 6f 70  (env);..    scop
1290: 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 3c 6a 63 6c  ed_local_ref<jcl
12a0: 61 73 73 3e 20 73 74 72 69 6e 67 57 72 69 74 65  ass> stringWrite
12b0: 72 43 6c 61 73 73 28 65 6e 76 2c 20 66 69 6e 64  rClass(env, find
12c0: 43 6c 61 73 73 28 65 6e 76 2c 20 22 6a 61 76 61  Class(env, "java
12d0: 2f 69 6f 2f 53 74 72 69 6e 67 57 72 69 74 65 72  /io/StringWriter
12e0: 22 29 29 3b 0a 20 20 20 20 69 66 20 28 73 74 72  "));.    if (str
12f0: 69 6e 67 57 72 69 74 65 72 43 6c 61 73 73 2e 67  ingWriterClass.g
1300: 65 74 28 29 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a  et() == NULL) {.
1310: 20 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 66          return f
1320: 61 6c 73 65 3b 0a 20 20 20 20 7d 0a 0a 20 20 20  alse;.    }..   
1330: 20 6a 6d 65 74 68 6f 64 49 44 20 73 74 72 69 6e   jmethodID strin
1340: 67 57 72 69 74 65 72 43 74 6f 72 20 3d 20 28 2a  gWriterCtor = (*
1350: 65 6e 76 29 2d 3e 47 65 74 4d 65 74 68 6f 64 49  env)->GetMethodI
1360: 44 28 65 2c 20 73 74 72 69 6e 67 57 72 69 74 65  D(e, stringWrite
1370: 72 43 6c 61 73 73 2e 67 65 74 28 29 2c 20 22 3c  rClass.get(), "<
1380: 69 6e 69 74 3e 22 2c 20 22 28 29 56 22 29 3b 0a  init>", "()V");.
1390: 20 20 20 20 6a 6d 65 74 68 6f 64 49 44 20 73 74      jmethodID st
13a0: 72 69 6e 67 57 72 69 74 65 72 54 6f 53 74 72 69  ringWriterToStri
13b0: 6e 67 4d 65 74 68 6f 64 20 3d 0a 20 20 20 20 20  ngMethod =.     
13c0: 20 20 20 20 20 20 20 28 2a 65 6e 76 29 2d 3e 47         (*env)->G
13d0: 65 74 4d 65 74 68 6f 64 49 44 28 65 2c 20 73 74  etMethodID(e, st
13e0: 72 69 6e 67 57 72 69 74 65 72 43 6c 61 73 73 2e  ringWriterClass.
13f0: 67 65 74 28 29 2c 20 22 74 6f 53 74 72 69 6e 67  get(), "toString
1400: 22 2c 20 22 28 29 4c 6a 61 76 61 2f 6c 61 6e 67  ", "()Ljava/lang
1410: 2f 53 74 72 69 6e 67 3b 22 29 3b 0a 0a 20 20 20  /String;");..   
1420: 20 73 63 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65   scoped_local_re
1430: 66 3c 6a 63 6c 61 73 73 3e 20 70 72 69 6e 74 57  f<jclass> printW
1440: 72 69 74 65 72 43 6c 61 73 73 28 65 6e 76 2c 20  riterClass(env, 
1450: 66 69 6e 64 43 6c 61 73 73 28 65 6e 76 2c 20 22  findClass(env, "
1460: 6a 61 76 61 2f 69 6f 2f 50 72 69 6e 74 57 72 69  java/io/PrintWri
1470: 74 65 72 22 29 29 3b 0a 20 20 20 20 69 66 20 28  ter"));.    if (
1480: 70 72 69 6e 74 57 72 69 74 65 72 43 6c 61 73 73  printWriterClass
1490: 2e 67 65 74 28 29 20 3d 3d 20 4e 55 4c 4c 29 20  .get() == NULL) 
14a0: 7b 0a 20 20 20 20 20 20 20 20 72 65 74 75 72 6e  {.        return
14b0: 20 66 61 6c 73 65 3b 0a 20 20 20 20 7d 0a 0a 20   false;.    }.. 
14c0: 20 20 20 6a 6d 65 74 68 6f 64 49 44 20 70 72 69     jmethodID pri
14d0: 6e 74 57 72 69 74 65 72 43 74 6f 72 20 3d 0a 20  ntWriterCtor =. 
14e0: 20 20 20 20 20 20 20 20 20 20 20 28 2a 65 6e 76             (*env
14f0: 29 2d 3e 47 65 74 4d 65 74 68 6f 64 49 44 28 65  )->GetMethodID(e
1500: 2c 20 70 72 69 6e 74 57 72 69 74 65 72 43 6c 61  , printWriterCla
1510: 73 73 2e 67 65 74 28 29 2c 20 22 3c 69 6e 69 74  ss.get(), "<init
1520: 3e 22 2c 20 22 28 4c 6a 61 76 61 2f 69 6f 2f 57  >", "(Ljava/io/W
1530: 72 69 74 65 72 3b 29 56 22 29 3b 0a 0a 20 20 20  riter;)V");..   
1540: 20 73 63 6f 70 65 64 5f 6c 6f 63 61 6c 5f 72 65   scoped_local_re
1550: 66 3c 6a 6f 62 6a 65 63 74 3e 20 73 74 72 69 6e  f<jobject> strin
1560: 67 57 72 69 74 65 72 28 65 6e 76 2c 0a 20 20 20  gWriter(env,.   
1570: 20 20 20 20 20 20 20 20 20 28 2a 65 6e 76 29 2d           (*env)-
1580: 3e 4e 65 77 4f 62 6a 65 63 74 28 65 2c 20 73 74  >NewObject(e, st
1590: 72 69 6e 67 57 72 69 74 65 72 43 6c 61 73 73 2e  ringWriterClass.
15a0: 67 65 74 28 29 2c 20 73 74 72 69 6e 67 57 72 69  get(), stringWri
15b0: 74 65 72 43 74 6f 72 29 29 3b 0a 20 20 20 20 69  terCtor));.    i
15c0: 66 20 28 73 74 72 69 6e 67 57 72 69 74 65 72 2e  f (stringWriter.
15d0: 67 65 74 28 29 20 3d 3d 20 4e 55 4c 4c 29 20 7b  get() == NULL) {
15e0: 0a 20 20 20 20 20 20 20 20 72 65 74 75 72 6e 20  .        return 
15f0: 66 61 6c 73 65 3b 0a 20 20 20 20 7d 0a 0a 20 20  false;.    }..  
1600: 20 20 6a 6f 62 6a 65 63 74 20 70 72 69 6e 74 57    jobject printW
1610: 72 69 74 65 72 20 3d 0a 20 20 20 20 20 20 20 20  riter =.        
1620: 20 20 20 20 28 2a 65 6e 76 29 2d 3e 4e 65 77 4f      (*env)->NewO
1630: 62 6a 65 63 74 28 65 2c 20 70 72 69 6e 74 57 72  bject(e, printWr
1640: 69 74 65 72 43 6c 61 73 73 2e 67 65 74 28 29 2c  iterClass.get(),
1650: 20 70 72 69 6e 74 57 72 69 74 65 72 43 74 6f 72   printWriterCtor
1660: 2c 20 73 74 72 69 6e 67 57 72 69 74 65 72 2e 67  , stringWriter.g
1670: 65 74 28 29 29 3b 0a 20 20 20 20 69 66 20 28 70  et());.    if (p
1680: 72 69 6e 74 57 72 69 74 65 72 20 3d 3d 20 4e 55  rintWriter == NU
1690: 4c 4c 29 20 7b 0a 20 20 20 20 20 20 20 20 72 65  LL) {.        re
16a0: 74 75 72 6e 20 66 61 6c 73 65 3b 0a 20 20 20 20  turn false;.    
16b0: 7d 0a 0a 20 20 20 20 73 63 6f 70 65 64 5f 6c 6f  }..    scoped_lo
16c0: 63 61 6c 5f 72 65 66 3c 6a 63 6c 61 73 73 3e 20  cal_ref<jclass> 
16d0: 65 78 63 65 70 74 69 6f 6e 43 6c 61 73 73 28 65  exceptionClass(e
16e0: 6e 76 2c 20 28 2a 65 6e 76 29 2d 3e 47 65 74 4f  nv, (*env)->GetO
16f0: 62 6a 65 63 74 43 6c 61 73 73 28 65 2c 20 65 78  bjectClass(e, ex
1700: 63 65 70 74 69 6f 6e 29 29 3b 20 2f 2f 20 63 61  ception)); // ca
1710: 6e 27 74 20 66 61 69 6c 0a 20 20 20 20 6a 6d 65  n't fail.    jme
1720: 74 68 6f 64 49 44 20 70 72 69 6e 74 53 74 61 63  thodID printStac
1730: 6b 54 72 61 63 65 4d 65 74 68 6f 64 20 3d 0a 20  kTraceMethod =. 
1740: 20 20 20 20 20 20 20 20 20 20 20 28 2a 65 6e 76             (*env
1750: 29 2d 3e 47 65 74 4d 65 74 68 6f 64 49 44 28 65  )->GetMethodID(e
1760: 2c 20 65 78 63 65 70 74 69 6f 6e 43 6c 61 73 73  , exceptionClass
1770: 2e 67 65 74 28 29 2c 20 22 70 72 69 6e 74 53 74  .get(), "printSt
1780: 61 63 6b 54 72 61 63 65 22 2c 20 22 28 4c 6a 61  ackTrace", "(Lja
1790: 76 61 2f 69 6f 2f 50 72 69 6e 74 57 72 69 74 65  va/io/PrintWrite
17a0: 72 3b 29 56 22 29 3b 0a 20 20 20 20 28 2a 65 6e  r;)V");.    (*en
17b0: 76 29 2d 3e 43 61 6c 6c 56 6f 69 64 4d 65 74 68  v)->CallVoidMeth
17c0: 6f 64 28 65 2c 20 65 78 63 65 70 74 69 6f 6e 2c  od(e, exception,
17d0: 20 70 72 69 6e 74 53 74 61 63 6b 54 72 61 63 65   printStackTrace
17e0: 4d 65 74 68 6f 64 2c 20 70 72 69 6e 74 57 72 69  Method, printWri
17f0: 74 65 72 29 3b 0a 0a 20 20 20 20 69 66 20 28 28  ter);..    if ((
1800: 2a 65 6e 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e  *env)->Exception
1810: 43 68 65 63 6b 28 65 29 29 20 7b 0a 20 20 20 20  Check(e)) {.    
1820: 20 20 20 20 72 65 74 75 72 6e 20 66 61 6c 73 65      return false
1830: 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20 73 63 6f  ;.    }..    sco
1840: 70 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 3c 6a 73  ped_local_ref<js
1850: 74 72 69 6e 67 3e 20 6d 65 73 73 61 67 65 53 74  tring> messageSt
1860: 72 28 65 6e 76 2c 0a 20 20 20 20 20 20 20 20 20  r(env,.         
1870: 20 20 20 28 6a 73 74 72 69 6e 67 29 20 28 2a 65     (jstring) (*e
1880: 6e 76 29 2d 3e 43 61 6c 6c 4f 62 6a 65 63 74 4d  nv)->CallObjectM
1890: 65 74 68 6f 64 28 65 2c 20 73 74 72 69 6e 67 57  ethod(e, stringW
18a0: 72 69 74 65 72 2e 67 65 74 28 29 2c 20 73 74 72  riter.get(), str
18b0: 69 6e 67 57 72 69 74 65 72 54 6f 53 74 72 69 6e  ingWriterToStrin
18c0: 67 4d 65 74 68 6f 64 29 29 3b 0a 20 20 20 20 69  gMethod));.    i
18d0: 66 20 28 6d 65 73 73 61 67 65 53 74 72 2e 67 65  f (messageStr.ge
18e0: 74 28 29 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 20  t() == NULL) {. 
18f0: 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 66 61         return fa
1900: 6c 73 65 3b 0a 20 20 20 20 7d 0a 0a 20 20 20 20  lse;.    }..    
1910: 63 6f 6e 73 74 20 63 68 61 72 2a 20 75 74 66 43  const char* utfC
1920: 68 61 72 73 20 3d 20 28 2a 65 6e 76 29 2d 3e 47  hars = (*env)->G
1930: 65 74 53 74 72 69 6e 67 55 54 46 43 68 61 72 73  etStringUTFChars
1940: 28 65 2c 20 6d 65 73 73 61 67 65 53 74 72 2e 67  (e, messageStr.g
1950: 65 74 28 29 2c 20 4e 55 4c 4c 29 3b 0a 20 20 20  et(), NULL);.   
1960: 20 69 66 20 28 75 74 66 43 68 61 72 73 20 3d 3d   if (utfChars ==
1970: 20 4e 55 4c 4c 29 20 7b 0a 20 20 20 20 20 20 20   NULL) {.       
1980: 20 72 65 74 75 72 6e 20 66 61 6c 73 65 3b 0a 20   return false;. 
1990: 20 20 20 7d 0a 0a 20 20 20 20 72 65 73 75 6c 74     }..    result
19a0: 20 3d 20 75 74 66 43 68 61 72 73 3b 0a 0a 20 20   = utfChars;..  
19b0: 20 20 28 2a 65 6e 76 29 2d 3e 52 65 6c 65 61 73    (*env)->Releas
19c0: 65 53 74 72 69 6e 67 55 54 46 43 68 61 72 73 28  eStringUTFChars(
19d0: 65 2c 20 6d 65 73 73 61 67 65 53 74 72 2e 67 65  e, messageStr.ge
19e0: 74 28 29 2c 20 75 74 66 43 68 61 72 73 29 3b 0a  t(), utfChars);.
19f0: 20 20 20 20 72 65 74 75 72 6e 20 74 72 75 65 3b      return true;
1a00: 0a 7d 0a 0a 65 78 74 65 72 6e 20 22 43 22 20 69  .}..extern "C" i
1a10: 6e 74 20 6a 6e 69 54 68 72 6f 77 45 78 63 65 70  nt jniThrowExcep
1a20: 74 69 6f 6e 28 43 5f 4a 4e 49 45 6e 76 2a 20 65  tion(C_JNIEnv* e
1a30: 6e 76 2c 20 63 6f 6e 73 74 20 63 68 61 72 2a 20  nv, const char* 
1a40: 63 6c 61 73 73 4e 61 6d 65 2c 20 63 6f 6e 73 74  className, const
1a50: 20 63 68 61 72 2a 20 6d 73 67 29 20 7b 0a 20 20   char* msg) {.  
1a60: 20 20 4a 4e 49 45 6e 76 2a 20 65 20 3d 20 72 65    JNIEnv* e = re
1a70: 69 6e 74 65 72 70 72 65 74 5f 63 61 73 74 3c 4a  interpret_cast<J
1a80: 4e 49 45 6e 76 2a 3e 28 65 6e 76 29 3b 0a 0a 20  NIEnv*>(env);.. 
1a90: 20 20 20 69 66 20 28 28 2a 65 6e 76 29 2d 3e 45     if ((*env)->E
1aa0: 78 63 65 70 74 69 6f 6e 43 68 65 63 6b 28 65 29  xceptionCheck(e)
1ab0: 29 20 7b 0a 20 20 20 20 20 20 20 20 2f 2a 20 54  ) {.        /* T
1ac0: 4f 44 4f 3a 20 63 6f 6e 73 69 64 65 72 20 63 72  ODO: consider cr
1ad0: 65 61 74 69 6e 67 20 74 68 65 20 6e 65 77 20 65  eating the new e
1ae0: 78 63 65 70 74 69 6f 6e 20 77 69 74 68 20 74 68  xception with th
1af0: 69 73 20 61 73 20 22 63 61 75 73 65 22 20 2a 2f  is as "cause" */
1b00: 0a 20 20 20 20 20 20 20 20 73 63 6f 70 65 64 5f  .        scoped_
1b10: 6c 6f 63 61 6c 5f 72 65 66 3c 6a 74 68 72 6f 77  local_ref<jthrow
1b20: 61 62 6c 65 3e 20 65 78 63 65 70 74 69 6f 6e 28  able> exception(
1b30: 65 6e 76 2c 20 28 2a 65 6e 76 29 2d 3e 45 78 63  env, (*env)->Exc
1b40: 65 70 74 69 6f 6e 4f 63 63 75 72 72 65 64 28 65  eptionOccurred(e
1b50: 29 29 3b 0a 20 20 20 20 20 20 20 20 28 2a 65 6e  ));.        (*en
1b60: 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e 43 6c 65  v)->ExceptionCle
1b70: 61 72 28 65 29 3b 0a 0a 20 20 20 20 20 20 20 20  ar(e);..        
1b80: 69 66 20 28 65 78 63 65 70 74 69 6f 6e 2e 67 65  if (exception.ge
1b90: 74 28 29 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 20  t() != NULL) {. 
1ba0: 20 20 20 20 20 20 20 20 20 20 20 73 74 64 3a 3a             std::
1bb0: 73 74 72 69 6e 67 20 74 65 78 74 3b 0a 20 20 20  string text;.   
1bc0: 20 20 20 20 20 20 20 20 20 67 65 74 45 78 63 65           getExce
1bd0: 70 74 69 6f 6e 53 75 6d 6d 61 72 79 28 65 6e 76  ptionSummary(env
1be0: 2c 20 65 78 63 65 70 74 69 6f 6e 2e 67 65 74 28  , exception.get(
1bf0: 29 2c 20 74 65 78 74 29 3b 0a 20 20 20 20 20 20  ), text);.      
1c00: 20 20 20 20 20 20 41 4c 4f 47 57 28 22 44 69 73        ALOGW("Dis
1c10: 63 61 72 64 69 6e 67 20 70 65 6e 64 69 6e 67 20  carding pending 
1c20: 65 78 63 65 70 74 69 6f 6e 20 28 25 73 29 20 74  exception (%s) t
1c30: 6f 20 74 68 72 6f 77 20 25 73 22 2c 20 74 65 78  o throw %s", tex
1c40: 74 2e 63 5f 73 74 72 28 29 2c 20 63 6c 61 73 73  t.c_str(), class
1c50: 4e 61 6d 65 29 3b 0a 20 20 20 20 20 20 20 20 7d  Name);.        }
1c60: 0a 20 20 20 20 7d 0a 0a 20 20 20 20 73 63 6f 70  .    }..    scop
1c70: 65 64 5f 6c 6f 63 61 6c 5f 72 65 66 3c 6a 63 6c  ed_local_ref<jcl
1c80: 61 73 73 3e 20 65 78 63 65 70 74 69 6f 6e 43 6c  ass> exceptionCl
1c90: 61 73 73 28 65 6e 76 2c 20 66 69 6e 64 43 6c 61  ass(env, findCla
1ca0: 73 73 28 65 6e 76 2c 20 63 6c 61 73 73 4e 61 6d  ss(env, classNam
1cb0: 65 29 29 3b 0a 20 20 20 20 69 66 20 28 65 78 63  e));.    if (exc
1cc0: 65 70 74 69 6f 6e 43 6c 61 73 73 2e 67 65 74 28  eptionClass.get(
1cd0: 29 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 20 20 20  ) == NULL) {.   
1ce0: 20 20 20 20 20 41 4c 4f 47 45 28 22 55 6e 61 62       ALOGE("Unab
1cf0: 6c 65 20 74 6f 20 66 69 6e 64 20 65 78 63 65 70  le to find excep
1d00: 74 69 6f 6e 20 63 6c 61 73 73 20 25 73 22 2c 20  tion class %s", 
1d10: 63 6c 61 73 73 4e 61 6d 65 29 3b 0a 20 20 20 20  className);.    
1d20: 20 20 20 20 2f 2a 20 43 6c 61 73 73 4e 6f 74 46      /* ClassNotF
1d30: 6f 75 6e 64 45 78 63 65 70 74 69 6f 6e 20 6e 6f  oundException no
1d40: 77 20 70 65 6e 64 69 6e 67 20 2a 2f 0a 20 20 20  w pending */.   
1d50: 20 20 20 20 20 72 65 74 75 72 6e 20 2d 31 3b 0a       return -1;.
1d60: 20 20 20 20 7d 0a 0a 20 20 20 20 69 66 20 28 28      }..    if ((
1d70: 2a 65 6e 76 29 2d 3e 54 68 72 6f 77 4e 65 77 28  *env)->ThrowNew(
1d80: 65 2c 20 65 78 63 65 70 74 69 6f 6e 43 6c 61 73  e, exceptionClas
1d90: 73 2e 67 65 74 28 29 2c 20 6d 73 67 29 20 21 3d  s.get(), msg) !=
1da0: 20 4a 4e 49 5f 4f 4b 29 20 7b 0a 20 20 20 20 20   JNI_OK) {.     
1db0: 20 20 20 41 4c 4f 47 45 28 22 46 61 69 6c 65 64     ALOGE("Failed
1dc0: 20 74 68 72 6f 77 69 6e 67 20 27 25 73 27 20 27   throwing '%s' '
1dd0: 25 73 27 22 2c 20 63 6c 61 73 73 4e 61 6d 65 2c  %s'", className,
1de0: 20 6d 73 67 29 3b 0a 20 20 20 20 20 20 20 20 2f   msg);.        /
1df0: 2a 20 61 6e 20 65 78 63 65 70 74 69 6f 6e 2c 20  * an exception, 
1e00: 6d 6f 73 74 20 6c 69 6b 65 6c 79 20 4f 4f 4d 2c  most likely OOM,
1e10: 20 77 69 6c 6c 20 6e 6f 77 20 62 65 20 70 65 6e   will now be pen
1e20: 64 69 6e 67 20 2a 2f 0a 20 20 20 20 20 20 20 20  ding */.        
1e30: 72 65 74 75 72 6e 20 2d 31 3b 0a 20 20 20 20 7d  return -1;.    }
1e40: 0a 0a 20 20 20 20 72 65 74 75 72 6e 20 30 3b 0a  ..    return 0;.
1e50: 7d 0a 0a 69 6e 74 20 6a 6e 69 54 68 72 6f 77 45  }..int jniThrowE
1e60: 78 63 65 70 74 69 6f 6e 46 6d 74 28 43 5f 4a 4e  xceptionFmt(C_JN
1e70: 49 45 6e 76 2a 20 65 6e 76 2c 20 63 6f 6e 73 74  IEnv* env, const
1e80: 20 63 68 61 72 2a 20 63 6c 61 73 73 4e 61 6d 65   char* className
1e90: 2c 20 63 6f 6e 73 74 20 63 68 61 72 2a 20 66 6d  , const char* fm
1ea0: 74 2c 20 76 61 5f 6c 69 73 74 20 61 72 67 73 29  t, va_list args)
1eb0: 20 7b 0a 20 20 20 20 63 68 61 72 20 6d 73 67 42   {.    char msgB
1ec0: 75 66 5b 35 31 32 5d 3b 0a 20 20 20 20 76 73 6e  uf[512];.    vsn
1ed0: 70 72 69 6e 74 66 28 6d 73 67 42 75 66 2c 20 73  printf(msgBuf, s
1ee0: 69 7a 65 6f 66 28 6d 73 67 42 75 66 29 2c 20 66  izeof(msgBuf), f
1ef0: 6d 74 2c 20 61 72 67 73 29 3b 0a 20 20 20 20 72  mt, args);.    r
1f00: 65 74 75 72 6e 20 6a 6e 69 54 68 72 6f 77 45 78  eturn jniThrowEx
1f10: 63 65 70 74 69 6f 6e 28 65 6e 76 2c 20 63 6c 61  ception(env, cla
1f20: 73 73 4e 61 6d 65 2c 20 6d 73 67 42 75 66 29 3b  ssName, msgBuf);
1f30: 0a 7d 0a 0a 69 6e 74 20 6a 6e 69 54 68 72 6f 77  .}..int jniThrow
1f40: 4e 75 6c 6c 50 6f 69 6e 74 65 72 45 78 63 65 70  NullPointerExcep
1f50: 74 69 6f 6e 28 43 5f 4a 4e 49 45 6e 76 2a 20 65  tion(C_JNIEnv* e
1f60: 6e 76 2c 20 63 6f 6e 73 74 20 63 68 61 72 2a 20  nv, const char* 
1f70: 6d 73 67 29 20 7b 0a 20 20 20 20 72 65 74 75 72  msg) {.    retur
1f80: 6e 20 6a 6e 69 54 68 72 6f 77 45 78 63 65 70 74  n jniThrowExcept
1f90: 69 6f 6e 28 65 6e 76 2c 20 22 6a 61 76 61 2f 6c  ion(env, "java/l
1fa0: 61 6e 67 2f 4e 75 6c 6c 50 6f 69 6e 74 65 72 45  ang/NullPointerE
1fb0: 78 63 65 70 74 69 6f 6e 22 2c 20 6d 73 67 29 3b  xception", msg);
1fc0: 0a 7d 0a 0a 69 6e 74 20 6a 6e 69 54 68 72 6f 77  .}..int jniThrow
1fd0: 52 75 6e 74 69 6d 65 45 78 63 65 70 74 69 6f 6e  RuntimeException
1fe0: 28 43 5f 4a 4e 49 45 6e 76 2a 20 65 6e 76 2c 20  (C_JNIEnv* env, 
1ff0: 63 6f 6e 73 74 20 63 68 61 72 2a 20 6d 73 67 29  const char* msg)
2000: 20 7b 0a 20 20 20 20 72 65 74 75 72 6e 20 6a 6e   {.    return jn
2010: 69 54 68 72 6f 77 45 78 63 65 70 74 69 6f 6e 28  iThrowException(
2020: 65 6e 76 2c 20 22 6a 61 76 61 2f 6c 61 6e 67 2f  env, "java/lang/
2030: 52 75 6e 74 69 6d 65 45 78 63 65 70 74 69 6f 6e  RuntimeException
2040: 22 2c 20 6d 73 67 29 3b 0a 7d 0a 0a 69 6e 74 20  ", msg);.}..int 
2050: 6a 6e 69 54 68 72 6f 77 49 4f 45 78 63 65 70 74  jniThrowIOExcept
2060: 69 6f 6e 28 43 5f 4a 4e 49 45 6e 76 2a 20 65 6e  ion(C_JNIEnv* en
2070: 76 2c 20 69 6e 74 20 65 72 72 6e 75 6d 29 20 7b  v, int errnum) {
2080: 0a 20 20 20 20 63 68 61 72 20 62 75 66 66 65 72  .    char buffer
2090: 5b 38 30 5d 3b 0a 20 20 20 20 63 6f 6e 73 74 20  [80];.    const 
20a0: 63 68 61 72 2a 20 6d 65 73 73 61 67 65 20 3d 20  char* message = 
20b0: 6a 6e 69 53 74 72 45 72 72 6f 72 28 65 72 72 6e  jniStrError(errn
20c0: 75 6d 2c 20 62 75 66 66 65 72 2c 20 73 69 7a 65  um, buffer, size
20d0: 6f 66 28 62 75 66 66 65 72 29 29 3b 0a 20 20 20  of(buffer));.   
20e0: 20 72 65 74 75 72 6e 20 6a 6e 69 54 68 72 6f 77   return jniThrow
20f0: 45 78 63 65 70 74 69 6f 6e 28 65 6e 76 2c 20 22  Exception(env, "
2100: 6a 61 76 61 2f 69 6f 2f 49 4f 45 78 63 65 70 74  java/io/IOExcept
2110: 69 6f 6e 22 2c 20 6d 65 73 73 61 67 65 29 3b 0a  ion", message);.
2120: 7d 0a 0a 73 74 61 74 69 63 20 73 74 64 3a 3a 73  }..static std::s
2130: 74 72 69 6e 67 20 6a 6e 69 47 65 74 53 74 61 63  tring jniGetStac
2140: 6b 54 72 61 63 65 28 43 5f 4a 4e 49 45 6e 76 2a  kTrace(C_JNIEnv*
2150: 20 65 6e 76 2c 20 6a 74 68 72 6f 77 61 62 6c 65   env, jthrowable
2160: 20 65 78 63 65 70 74 69 6f 6e 29 20 7b 0a 20 20   exception) {.  
2170: 20 20 4a 4e 49 45 6e 76 2a 20 65 20 3d 20 72 65    JNIEnv* e = re
2180: 69 6e 74 65 72 70 72 65 74 5f 63 61 73 74 3c 4a  interpret_cast<J
2190: 4e 49 45 6e 76 2a 3e 28 65 6e 76 29 3b 0a 0a 20  NIEnv*>(env);.. 
21a0: 20 20 20 73 63 6f 70 65 64 5f 6c 6f 63 61 6c 5f     scoped_local_
21b0: 72 65 66 3c 6a 74 68 72 6f 77 61 62 6c 65 3e 20  ref<jthrowable> 
21c0: 63 75 72 72 65 6e 74 45 78 63 65 70 74 69 6f 6e  currentException
21d0: 28 65 6e 76 2c 20 28 2a 65 6e 76 29 2d 3e 45 78  (env, (*env)->Ex
21e0: 63 65 70 74 69 6f 6e 4f 63 63 75 72 72 65 64 28  ceptionOccurred(
21f0: 65 29 29 3b 0a 20 20 20 20 69 66 20 28 65 78 63  e));.    if (exc
2200: 65 70 74 69 6f 6e 20 3d 3d 20 4e 55 4c 4c 29 20  eption == NULL) 
2210: 7b 0a 20 20 20 20 20 20 20 20 65 78 63 65 70 74  {.        except
2220: 69 6f 6e 20 3d 20 63 75 72 72 65 6e 74 45 78 63  ion = currentExc
2230: 65 70 74 69 6f 6e 2e 67 65 74 28 29 3b 0a 20 20  eption.get();.  
2240: 20 20 20 20 20 20 69 66 20 28 65 78 63 65 70 74        if (except
2250: 69 6f 6e 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 20  ion == NULL) {. 
2260: 20 20 20 20 20 20 20 20 20 72 65 74 75 72 6e 20           return 
2270: 22 3c 6e 6f 20 70 65 6e 64 69 6e 67 20 65 78 63  "<no pending exc
2280: 65 70 74 69 6f 6e 3e 22 3b 0a 20 20 20 20 20 20  eption>";.      
2290: 20 20 7d 0a 20 20 20 20 7d 0a 0a 20 20 20 20 69    }.    }..    i
22a0: 66 20 28 63 75 72 72 65 6e 74 45 78 63 65 70 74  f (currentExcept
22b0: 69 6f 6e 2e 67 65 74 28 29 20 21 3d 20 4e 55 4c  ion.get() != NUL
22c0: 4c 29 20 7b 0a 20 20 20 20 20 20 20 20 28 2a 65  L) {.        (*e
22d0: 6e 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e 43 6c  nv)->ExceptionCl
22e0: 65 61 72 28 65 29 3b 0a 20 20 20 20 7d 0a 0a 20  ear(e);.    }.. 
22f0: 20 20 20 73 74 64 3a 3a 73 74 72 69 6e 67 20 74     std::string t
2300: 72 61 63 65 3b 0a 20 20 20 20 69 66 20 28 21 67  race;.    if (!g
2310: 65 74 53 74 61 63 6b 54 72 61 63 65 28 65 6e 76  etStackTrace(env
2320: 2c 20 65 78 63 65 70 74 69 6f 6e 2c 20 74 72 61  , exception, tra
2330: 63 65 29 29 20 7b 0a 20 20 20 20 20 20 20 20 28  ce)) {.        (
2340: 2a 65 6e 76 29 2d 3e 45 78 63 65 70 74 69 6f 6e  *env)->Exception
2350: 43 6c 65 61 72 28 65 29 3b 0a 20 20 20 20 20 20  Clear(e);.      
2360: 20 20 67 65 74 45 78 63 65 70 74 69 6f 6e 53 75    getExceptionSu
2370: 6d 6d 61 72 79 28 65 6e 76 2c 20 65 78 63 65 70  mmary(env, excep
2380: 74 69 6f 6e 2c 20 74 72 61 63 65 29 3b 0a 20 20  tion, trace);.  
2390: 20 20 7d 0a 0a 20 20 20 20 69 66 20 28 63 75 72    }..    if (cur
23a0: 72 65 6e 74 45 78 63 65 70 74 69 6f 6e 2e 67 65  rentException.ge
23b0: 74 28 29 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 20  t() != NULL) {. 
23c0: 20 20 20 20 20 20 20 28 2a 65 6e 76 29 2d 3e 54         (*env)->T
23d0: 68 72 6f 77 28 65 2c 20 63 75 72 72 65 6e 74 45  hrow(e, currentE
23e0: 78 63 65 70 74 69 6f 6e 2e 67 65 74 28 29 29 3b  xception.get());
23f0: 20 2f 2f 20 72 65 74 68 72 6f 77 0a 20 20 20 20   // rethrow.    
2400: 7d 0a 0a 20 20 20 20 72 65 74 75 72 6e 20 74 72  }..    return tr
2410: 61 63 65 3b 0a 7d 0a 0a 76 6f 69 64 20 6a 6e 69  ace;.}..void jni
2420: 4c 6f 67 45 78 63 65 70 74 69 6f 6e 28 43 5f 4a  LogException(C_J
2430: 4e 49 45 6e 76 2a 20 65 6e 76 2c 20 69 6e 74 20  NIEnv* env, int 
2440: 70 72 69 6f 72 69 74 79 2c 20 63 6f 6e 73 74 20  priority, const 
2450: 63 68 61 72 2a 20 74 61 67 2c 20 6a 74 68 72 6f  char* tag, jthro
2460: 77 61 62 6c 65 20 65 78 63 65 70 74 69 6f 6e 29  wable exception)
2470: 20 7b 0a 20 20 20 20 73 74 64 3a 3a 73 74 72 69   {.    std::stri
2480: 6e 67 20 74 72 61 63 65 28 6a 6e 69 47 65 74 53  ng trace(jniGetS
2490: 74 61 63 6b 54 72 61 63 65 28 65 6e 76 2c 20 65  tackTrace(env, e
24a0: 78 63 65 70 74 69 6f 6e 29 29 3b 0a 20 20 20 20  xception));.    
24b0: 5f 5f 61 6e 64 72 6f 69 64 5f 6c 6f 67 5f 77 72  __android_log_wr
24c0: 69 74 65 28 70 72 69 6f 72 69 74 79 2c 20 74 61  ite(priority, ta
24d0: 67 2c 20 74 72 61 63 65 2e 63 5f 73 74 72 28 29  g, trace.c_str()
24e0: 29 3b 0a 7d 0a 0a 63 6f 6e 73 74 20 63 68 61 72  );.}..const char
24f0: 2a 20 6a 6e 69 53 74 72 45 72 72 6f 72 28 69 6e  * jniStrError(in
2500: 74 20 65 72 72 6e 75 6d 2c 20 63 68 61 72 2a 20  t errnum, char* 
2510: 62 75 66 2c 20 73 69 7a 65 5f 74 20 62 75 66 6c  buf, size_t bufl
2520: 65 6e 29 20 7b 0a 23 69 66 20 5f 5f 47 4c 49 42  en) {.#if __GLIB
2530: 43 5f 5f 0a 20 20 20 20 2f 2f 20 4e 6f 74 65 3a  C__.    // Note:
2540: 20 67 6c 69 62 63 20 68 61 73 20 61 20 6e 6f 6e   glibc has a non
2550: 73 74 61 6e 64 61 72 64 20 73 74 72 65 72 72 6f  standard strerro
2560: 72 5f 72 20 74 68 61 74 20 72 65 74 75 72 6e 73  r_r that returns
2570: 20 63 68 61 72 2a 20 72 61 74 68 65 72 20 74 68   char* rather th
2580: 61 6e 20 50 4f 53 49 58 27 73 20 69 6e 74 2e 0a  an POSIX's int..
2590: 20 20 20 20 2f 2f 20 63 68 61 72 20 2a 73 74 72      // char *str
25a0: 65 72 72 6f 72 5f 72 28 69 6e 74 20 65 72 72 6e  error_r(int errn
25b0: 75 6d 2c 20 63 68 61 72 20 2a 62 75 66 2c 20 73  um, char *buf, s
25c0: 69 7a 65 5f 74 20 6e 29 3b 0a 20 20 20 20 72 65  ize_t n);.    re
25d0: 74 75 72 6e 20 73 74 72 65 72 72 6f 72 5f 72 28  turn strerror_r(
25e0: 65 72 72 6e 75 6d 2c 20 62 75 66 2c 20 62 75 66  errnum, buf, buf
25f0: 6c 65 6e 29 3b 0a 23 65 6c 73 65 0a 20 20 20 20  len);.#else.    
2600: 69 6e 74 20 72 63 20 3d 20 73 74 72 65 72 72 6f  int rc = strerro
2610: 72 5f 72 28 65 72 72 6e 75 6d 2c 20 62 75 66 2c  r_r(errnum, buf,
2620: 20 62 75 66 6c 65 6e 29 3b 0a 20 20 20 20 69 66   buflen);.    if
2630: 20 28 72 63 20 21 3d 20 30 29 20 7b 0a 20 20 20   (rc != 0) {.   
2640: 20 20 20 20 20 2f 2f 20 28 50 4f 53 49 58 20 6f       // (POSIX o
2650: 6e 6c 79 20 67 75 61 72 61 6e 74 65 65 73 20 61  nly guarantees a
2660: 20 76 61 6c 75 65 20 6f 74 68 65 72 20 74 68 61   value other tha
2670: 6e 20 30 2e 20 54 68 65 20 73 61 66 65 73 74 0a  n 0. The safest.
2680: 20 20 20 20 20 20 20 20 2f 2f 20 77 61 79 20 74          // way t
2690: 6f 20 69 6d 70 6c 65 6d 65 6e 74 20 74 68 69 73  o implement this
26a0: 20 66 75 6e 63 74 69 6f 6e 20 69 73 20 74 6f 20   function is to 
26b0: 75 73 65 20 43 2b 2b 20 61 6e 64 20 6f 76 65 72  use C++ and over
26c0: 6c 6f 61 64 20 6f 6e 20 74 68 65 0a 20 20 20 20  load on the.    
26d0: 20 20 20 20 2f 2f 20 74 79 70 65 20 6f 66 20 73      // type of s
26e0: 74 72 65 72 72 6f 72 5f 72 20 74 6f 20 61 63 63  trerror_r to acc
26f0: 75 72 61 74 65 6c 79 20 64 69 73 74 69 6e 67 75  urately distingu
2700: 69 73 68 20 47 4e 55 20 66 72 6f 6d 20 50 4f 53  ish GNU from POS
2710: 49 58 2e 29 0a 20 20 20 20 20 20 20 20 73 6e 70  IX.).        snp
2720: 72 69 6e 74 66 28 62 75 66 2c 20 62 75 66 6c 65  rintf(buf, bufle
2730: 6e 2c 20 22 65 72 72 6e 6f 20 25 64 22 2c 20 65  n, "errno %d", e
2740: 72 72 6e 75 6d 29 3b 0a 20 20 20 20 7d 0a 20 20  rrnum);.    }.  
2750: 20 20 72 65 74 75 72 6e 20 62 75 66 3b 0a 23 65    return buf;.#e
2760: 6e 64 69 66 0a 7d 0a 0a 6a 6f 62 6a 65 63 74 20  ndif.}..jobject 
2770: 6a 6e 69 43 72 65 61 74 65 46 69 6c 65 44 65 73  jniCreateFileDes
2780: 63 72 69 70 74 6f 72 28 43 5f 4a 4e 49 45 6e 76  criptor(C_JNIEnv
2790: 2a 20 65 6e 76 2c 20 69 6e 74 20 66 64 29 20 7b  * env, int fd) {
27a0: 0a 20 20 20 20 4a 4e 49 45 6e 76 2a 20 65 20 3d  .    JNIEnv* e =
27b0: 20 72 65 69 6e 74 65 72 70 72 65 74 5f 63 61 73   reinterpret_cas
27c0: 74 3c 4a 4e 49 45 6e 76 2a 3e 28 65 6e 76 29 3b  t<JNIEnv*>(env);
27d0: 0a 20 20 20 20 73 74 61 74 69 63 20 6a 6d 65 74  .    static jmet
27e0: 68 6f 64 49 44 20 63 74 6f 72 20 3d 20 65 2d 3e  hodID ctor = e->
27f0: 47 65 74 4d 65 74 68 6f 64 49 44 28 4a 6e 69 43  GetMethodID(JniC
2800: 6f 6e 73 74 61 6e 74 73 3a 3a 66 69 6c 65 44 65  onstants::fileDe
2810: 73 63 72 69 70 74 6f 72 43 6c 61 73 73 2c 20 22  scriptorClass, "
2820: 3c 69 6e 69 74 3e 22 2c 20 22 28 29 56 22 29 3b  <init>", "()V");
2830: 0a 20 20 20 20 6a 6f 62 6a 65 63 74 20 66 69 6c  .    jobject fil
2840: 65 44 65 73 63 72 69 70 74 6f 72 20 3d 20 28 2a  eDescriptor = (*
2850: 65 6e 76 29 2d 3e 4e 65 77 4f 62 6a 65 63 74 28  env)->NewObject(
2860: 65 2c 20 4a 6e 69 43 6f 6e 73 74 61 6e 74 73 3a  e, JniConstants:
2870: 3a 66 69 6c 65 44 65 73 63 72 69 70 74 6f 72 43  :fileDescriptorC
2880: 6c 61 73 73 2c 20 63 74 6f 72 29 3b 0a 20 20 20  lass, ctor);.   
2890: 20 2f 2f 20 4e 4f 54 45 3a 20 4e 65 77 4f 62 6a   // NOTE: NewObj
28a0: 65 63 74 20 65 6e 73 75 72 65 73 20 74 68 61 74  ect ensures that
28b0: 20 61 6e 20 4f 75 74 4f 66 4d 65 6d 6f 72 79 45   an OutOfMemoryE
28c0: 72 72 6f 72 20 77 69 6c 6c 20 62 65 20 73 65 65  rror will be see
28d0: 6e 20 62 79 20 74 68 65 20 4a 61 76 61 0a 20 20  n by the Java.  
28e0: 20 20 2f 2f 20 63 61 6c 6c 65 72 20 69 66 20 74    // caller if t
28f0: 68 65 20 61 6c 6c 6f 63 20 66 61 69 6c 73 2c 20  he alloc fails, 
2900: 73 6f 20 77 65 20 6a 75 73 74 20 72 65 74 75 72  so we just retur
2910: 6e 20 4e 55 4c 4c 20 77 68 65 6e 20 74 68 61 74  n NULL when that
2920: 20 68 61 70 70 65 6e 73 2e 0a 20 20 20 20 69 66   happens..    if
2930: 20 28 66 69 6c 65 44 65 73 63 72 69 70 74 6f 72   (fileDescriptor
2940: 20 21 3d 20 4e 55 4c 4c 29 20 20 7b 0a 20 20 20   != NULL)  {.   
2950: 20 20 20 20 20 6a 6e 69 53 65 74 46 69 6c 65 44       jniSetFileD
2960: 65 73 63 72 69 70 74 6f 72 4f 66 46 44 28 65 6e  escriptorOfFD(en
2970: 76 2c 20 66 69 6c 65 44 65 73 63 72 69 70 74 6f  v, fileDescripto
2980: 72 2c 20 66 64 29 3b 0a 20 20 20 20 7d 0a 20 20  r, fd);.    }.  
2990: 20 20 72 65 74 75 72 6e 20 66 69 6c 65 44 65 73    return fileDes
29a0: 63 72 69 70 74 6f 72 3b 0a 7d 0a 0a 69 6e 74 20  criptor;.}..int 
29b0: 6a 6e 69 47 65 74 46 44 46 72 6f 6d 46 69 6c 65  jniGetFDFromFile
29c0: 44 65 73 63 72 69 70 74 6f 72 28 43 5f 4a 4e 49  Descriptor(C_JNI
29d0: 45 6e 76 2a 20 65 6e 76 2c 20 6a 6f 62 6a 65 63  Env* env, jobjec
29e0: 74 20 66 69 6c 65 44 65 73 63 72 69 70 74 6f 72  t fileDescriptor
29f0: 29 20 7b 0a 20 20 20 20 4a 4e 49 45 6e 76 2a 20  ) {.    JNIEnv* 
2a00: 65 20 3d 20 72 65 69 6e 74 65 72 70 72 65 74 5f  e = reinterpret_
2a10: 63 61 73 74 3c 4a 4e 49 45 6e 76 2a 3e 28 65 6e  cast<JNIEnv*>(en
2a20: 76 29 3b 0a 20 20 20 20 73 74 61 74 69 63 20 6a  v);.    static j
2a30: 66 69 65 6c 64 49 44 20 66 69 64 20 3d 20 65 2d  fieldID fid = e-
2a40: 3e 47 65 74 46 69 65 6c 64 49 44 28 4a 6e 69 43  >GetFieldID(JniC
2a50: 6f 6e 73 74 61 6e 74 73 3a 3a 66 69 6c 65 44 65  onstants::fileDe
2a60: 73 63 72 69 70 74 6f 72 43 6c 61 73 73 2c 20 22  scriptorClass, "
2a70: 64 65 73 63 72 69 70 74 6f 72 22 2c 20 22 49 22  descriptor", "I"
2a80: 29 3b 0a 20 20 20 20 69 66 20 28 66 69 6c 65 44  );.    if (fileD
2a90: 65 73 63 72 69 70 74 6f 72 20 21 3d 20 4e 55 4c  escriptor != NUL
2aa0: 4c 29 20 7b 0a 20 20 20 20 20 20 20 20 72 65 74  L) {.        ret
2ab0: 75 72 6e 20 28 2a 65 6e 76 29 2d 3e 47 65 74 49  urn (*env)->GetI
2ac0: 6e 74 46 69 65 6c 64 28 65 2c 20 66 69 6c 65 44  ntField(e, fileD
2ad0: 65 73 63 72 69 70 74 6f 72 2c 20 66 69 64 29 3b  escriptor, fid);
2ae0: 0a 20 20 20 20 7d 20 65 6c 73 65 20 7b 0a 20 20  .    } else {.  
2af0: 20 20 20 20 20 20 72 65 74 75 72 6e 20 2d 31 3b        return -1;
2b00: 0a 20 20 20 20 7d 0a 7d 0a 0a 76 6f 69 64 20 6a  .    }.}..void j
2b10: 6e 69 53 65 74 46 69 6c 65 44 65 73 63 72 69 70  niSetFileDescrip
2b20: 74 6f 72 4f 66 46 44 28 43 5f 4a 4e 49 45 6e 76  torOfFD(C_JNIEnv
2b30: 2a 20 65 6e 76 2c 20 6a 6f 62 6a 65 63 74 20 66  * env, jobject f
2b40: 69 6c 65 44 65 73 63 72 69 70 74 6f 72 2c 20 69  ileDescriptor, i
2b50: 6e 74 20 76 61 6c 75 65 29 20 7b 0a 20 20 20 20  nt value) {.    
2b60: 4a 4e 49 45 6e 76 2a 20 65 20 3d 20 72 65 69 6e  JNIEnv* e = rein
2b70: 74 65 72 70 72 65 74 5f 63 61 73 74 3c 4a 4e 49  terpret_cast<JNI
2b80: 45 6e 76 2a 3e 28 65 6e 76 29 3b 0a 20 20 20 20  Env*>(env);.    
2b90: 73 74 61 74 69 63 20 6a 66 69 65 6c 64 49 44 20  static jfieldID 
2ba0: 66 69 64 20 3d 20 65 2d 3e 47 65 74 46 69 65 6c  fid = e->GetFiel
2bb0: 64 49 44 28 4a 6e 69 43 6f 6e 73 74 61 6e 74 73  dID(JniConstants
2bc0: 3a 3a 66 69 6c 65 44 65 73 63 72 69 70 74 6f 72  ::fileDescriptor
2bd0: 43 6c 61 73 73 2c 20 22 64 65 73 63 72 69 70 74  Class, "descript
2be0: 6f 72 22 2c 20 22 49 22 29 3b 0a 20 20 20 20 28  or", "I");.    (
2bf0: 2a 65 6e 76 29 2d 3e 53 65 74 49 6e 74 46 69 65  *env)->SetIntFie
2c00: 6c 64 28 65 2c 20 66 69 6c 65 44 65 73 63 72 69  ld(e, fileDescri
2c10: 70 74 6f 72 2c 20 66 69 64 2c 20 76 61 6c 75 65  ptor, fid, value
2c20: 29 3b 0a 7d 0a 0a 6a 6f 62 6a 65 63 74 20 6a 6e  );.}..jobject jn
2c30: 69 47 65 74 52 65 66 65 72 65 6e 74 28 43 5f 4a  iGetReferent(C_J
2c40: 4e 49 45 6e 76 2a 20 65 6e 76 2c 20 6a 6f 62 6a  NIEnv* env, jobj
2c50: 65 63 74 20 72 65 66 29 20 7b 0a 20 20 20 20 4a  ect ref) {.    J
2c60: 4e 49 45 6e 76 2a 20 65 20 3d 20 72 65 69 6e 74  NIEnv* e = reint
2c70: 65 72 70 72 65 74 5f 63 61 73 74 3c 4a 4e 49 45  erpret_cast<JNIE
2c80: 6e 76 2a 3e 28 65 6e 76 29 3b 0a 20 20 20 20 73  nv*>(env);.    s
2c90: 74 61 74 69 63 20 6a 6d 65 74 68 6f 64 49 44 20  tatic jmethodID 
2ca0: 67 65 74 20 3d 20 65 2d 3e 47 65 74 4d 65 74 68  get = e->GetMeth
2cb0: 6f 64 49 44 28 4a 6e 69 43 6f 6e 73 74 61 6e 74  odID(JniConstant
2cc0: 73 3a 3a 72 65 66 65 72 65 6e 63 65 43 6c 61 73  s::referenceClas
2cd0: 73 2c 20 22 67 65 74 22 2c 20 22 28 29 4c 6a 61  s, "get", "()Lja
2ce0: 76 61 2f 6c 61 6e 67 2f 4f 62 6a 65 63 74 3b 22  va/lang/Object;"
2cf0: 29 3b 0a 20 20 20 20 72 65 74 75 72 6e 20 28 2a  );.    return (*
2d00: 65 6e 76 29 2d 3e 43 61 6c 6c 4f 62 6a 65 63 74  env)->CallObject
2d10: 4d 65 74 68 6f 64 28 65 2c 20 72 65 66 2c 20 67  Method(e, ref, g
2d20: 65 74 29 3b 0a 7d 0a 0a                          et);.}..