Showing the changes to java/tools/javal/LimboGen.java (1 of 18352 files). Show all
Unified · Split
| @@ -0,0 +1,677 @@ | ||
| 1 | +package javal; | |
| 2 | + | |
| 3 | +import java.io.File; | |
| 4 | +import java.io.DataOutputStream; | |
| 5 | +import java.io.FileOutputStream; | |
| 6 | +import java.io.IOException; | |
| 7 | + | |
| 8 | +import java.lang.reflect.*; | |
| 9 | + | |
| 10 | + | |
| 11 | +public | |
| 12 | +class LimboGen | |
| 13 | +{ | |
| 14 | + public LimboGen( Class cl, Field[] fields, Method[] methods, boolean verbose ) | |
| 15 | + { | |
| 16 | + theClass = cl; | |
| 17 | + this.fields = fields; | |
| 18 | + this.methods = methods; | |
| 19 | + opt_verbose = verbose; | |
| 20 | + | |
| 21 | + // create names | |
| 22 | + String full_name = cl.getName(); | |
| 23 | + base_name = ClassBaseName( full_name ); | |
| 24 | + mod_name = base_name +"_L"; | |
| 25 | + limbo_dotm = mod_name +".m"; | |
| 26 | + limbo_dotb = mod_name +".b"; | |
| 27 | + | |
| 28 | + // some class are "special" to javal | |
| 29 | + // if it is a special class we don't | |
| 30 | + // want to generate adt's for it and | |
| 31 | + // will use a special ADT name | |
| 32 | + special = true; //assume special | |
| 33 | + obj_adt = SpecialClass( full_name ); | |
| 34 | + | |
| 35 | + if ( obj_adt == null ) | |
| 36 | + { | |
| 37 | + special = false; | |
| 38 | + obj_adt = base_name +"_obj"; | |
| 39 | + } | |
| 40 | + | |
| 41 | + // will only generate skeleton for native methods | |
| 42 | + natives = GetNatives( methods ); | |
| 43 | + has_natives = natives.length > 0; | |
| 44 | + | |
| 45 | + // need to distinguish between instance and static fields | |
| 46 | + iFields = GetInstanceFields( fields ); | |
| 47 | + sFields = GetStaticFields( fields ); | |
| 48 | + } | |
| 49 | + | |
| 50 | + | |
| 51 | + /** | |
| 52 | + * Generate a Limbo Module Declaration | |
| 53 | + * file (.m) for a java class containing | |
| 54 | + * native methods. | |
| 55 | + */ | |
| 56 | + public void DotM() throws IOException | |
| 57 | + { | |
| 58 | + // open a file | |
| 59 | + out = MkFile( limbo_dotm ); | |
| 60 | + | |
| 61 | + // emit the Limbo Module File | |
| 62 | + | |
| 63 | + Emit( "# generated file edit with care\n\n" ); | |
| 64 | + Emit( mod_name +" : module\n" ); | |
| 65 | + Emit( "{\n" ); | |
| 66 | + | |
| 67 | + GenADT(); | |
| 68 | + | |
| 69 | + Emit( "\n" ); | |
| 70 | + | |
| 71 | + GenFct(false); | |
| 72 | + | |
| 73 | + Emit( "\n};\n" ); | |
| 74 | + | |
| 75 | + out.close(); | |
| 76 | + | |
| 77 | + if ( merge ) | |
| 78 | + { | |
| 79 | + // save off existing .m and rename | |
| 80 | + // tmp to .m | |
| 81 | + File f = new File( limbo_dotm ); | |
| 82 | + File o = new File("old_"+limbo_dotm); | |
| 83 | + File t = new File( tmpname ); | |
| 84 | + | |
| 85 | + if ( o.exists() ) o.delete(); | |
| 86 | + f.renameTo( o ); | |
| 87 | + t.renameTo( f ); | |
| 88 | + | |
| 89 | + } | |
| 90 | + | |
| 91 | + } | |
| 92 | + | |
| 93 | + | |
| 94 | + /** | |
| 95 | + * Generate a Limbo Module Implementation | |
| 96 | + * Skeleton containing native methods for | |
| 97 | + * a java class. | |
| 98 | + */ | |
| 99 | + public void DotB() throws IOException | |
| 100 | + { | |
| 101 | + // don't generate a .b if no natives | |
| 102 | + if ( ! has_natives ) return; | |
| 103 | + | |
| 104 | + // open a file | |
| 105 | + out = MkFile( limbo_dotb ); | |
| 106 | + | |
| 107 | + // generate file prolog | |
| 108 | + Emit("implement "+ mod_name +";\n\n" ); | |
| 109 | + Emit("include \"jni.m\";\n" ); | |
| 110 | + Emit(T1+"jni : JNI;\n" ); | |
| 111 | + Emit(T2+"ClassModule,\n"); | |
| 112 | + Emit(T2+ T_JString +",\n"); | |
| 113 | + Emit(T2+ T_JArray +",\n"); | |
| 114 | + Emit(T2+ T_JArrayI +",\n"); | |
| 115 | + Emit(T2+ T_JArrayC +",\n"); | |
| 116 | + Emit(T2+ T_JArrayB +",\n"); | |
| 117 | + Emit(T2+ T_JArrayS +",\n"); | |
| 118 | + Emit(T2+ T_JArrayJ +",\n"); | |
| 119 | + Emit(T2+ T_JArrayF +",\n"); | |
| 120 | + Emit(T2+ T_JArrayD +",\n"); | |
| 121 | + Emit(T2+ T_JArrayZ +",\n"); | |
| 122 | + Emit(T2+ T_JArrayJObject +",\n"); | |
| 123 | + Emit(T2+ T_JArrayJClass +",\n"); | |
| 124 | + Emit(T2+ T_JArrayJString +",\n"); | |
| 125 | + Emit(T2+ T_JClass +",\n"); | |
| 126 | + Emit(T2+T_JObject +" : import jni;\n\n"); | |
| 127 | + | |
| 128 | + Emit("#>> extra pre includes here\n\n#<<\n\n"); | |
| 129 | + | |
| 130 | + Emit("include \""+ limbo_dotm +"\";\n\n" ); | |
| 131 | + | |
| 132 | + Emit("#>> extra post includes here\n\n#<<\n\n"); | |
| 133 | + | |
| 134 | + // generate a skeleton for init() and each native method | |
| 135 | + GenFct( true ); | |
| 136 | + | |
| 137 | + out.close(); | |
| 138 | + | |
| 139 | + if ( merge ) | |
| 140 | + FileMerge.Merge( limbo_dotb, tmpname ); | |
| 141 | + } | |
| 142 | + | |
| 143 | + | |
| 144 | + /** | |
| 145 | + * Generate an ADT declaration for the class | |
| 146 | + * instance fields. | |
| 147 | + */ | |
| 148 | + private void GenADT() throws IOException | |
| 149 | + { | |
| 150 | + // don't generate an ADT decl for "special" clases | |
| 151 | + if ( special ) return; | |
| 152 | + | |
| 153 | + Emit( T1+ obj_adt +" : adt\n"+ T1+ "{\n" ); | |
| 154 | + | |
| 155 | + // emit the std object header | |
| 156 | + Emit( T2+ "cl_mod : ClassModule;\n" ); | |
| 157 | + | |
| 158 | + // walk through instance data emitting Limbo decl | |
| 159 | + for( int x=0; x<iFields.length; x++ ) | |
| 160 | + { | |
| 161 | + Emit( T2+ GenFieldDecl( iFields[x] ) +";\n" ); | |
| 162 | + } | |
| 163 | + | |
| 164 | + Emit( T1+ "};\n" ); | |
| 165 | + } | |
| 166 | + | |
| 167 | + private void GenFct( boolean skel ) throws IOException | |
| 168 | + { | |
| 169 | + // generate init fct | |
| 170 | + GenInit( skel ); | |
| 171 | + | |
| 172 | + // walk native methods and generate | |
| 173 | + // a limbo fct | |
| 174 | + for( int x=0; x<natives.length; x++ ) | |
| 175 | + { | |
| 176 | + String fct_name = MkFctName( natives[x] ); | |
| 177 | + String this_param = ""; | |
| 178 | + | |
| 179 | + // if fct is virtual generate implicit this param | |
| 180 | + if ( ! Modifier.isStatic( natives[x].getModifiers() ) ) | |
| 181 | + { | |
| 182 | + // if this is a special class then don't use ref | |
| 183 | + // because the generated special name is already a ref | |
| 184 | + this_param = ( special ? "this : " : "this : ref " ); | |
| 185 | + this_param += obj_adt; | |
| 186 | + } | |
| 187 | + | |
| 188 | + // determine fct parameters | |
| 189 | + String params = GenFctParams( natives[x].getParameterTypes() ); | |
| 190 | + | |
| 191 | + StringBuffer fct_params = new StringBuffer(80); | |
| 192 | + if ( this_param != "" ) | |
| 193 | + { | |
| 194 | + fct_params.append( this_param ); | |
| 195 | + if ( params != "" ) | |
| 196 | + fct_params.append( ", " ); | |
| 197 | + } | |
| 198 | + | |
| 199 | + fct_params.append( params ); | |
| 200 | + | |
| 201 | + // determine fct return type...if any | |
| 202 | + String fct_t = LimboType( natives[x].getReturnType() ); | |
| 203 | + if ( ! fct_t.equals("") ) | |
| 204 | + fct_t = " : "+ fct_t; | |
| 205 | + | |
| 206 | + if ( skel ) | |
| 207 | + { | |
| 208 | + Emit( fct_name +"( "+ | |
| 209 | + fct_params.toString() +")"+ | |
| 210 | + fct_t +"\n{#>>\n}#<<\n\n" ); | |
| 211 | + | |
| 212 | + } | |
| 213 | + else | |
| 214 | + { | |
| 215 | + Emit( T1+ fct_name +" : fn( "+ | |
| 216 | + fct_params.toString() +")"+ | |
| 217 | + fct_t +";\n" ); | |
| 218 | + } | |
| 219 | + } | |
| 220 | + } | |
| 221 | + | |
| 222 | + | |
| 223 | + /** | |
| 224 | + * every Limbo Native module has a init() | |
| 225 | + * function which the loader will call | |
| 226 | + * when the native mod is loaded. This | |
| 227 | + * method generates that fct. | |
| 228 | + * | |
| 229 | + * @param skel If true gen a fct skel; else fct decl | |
| 230 | + * | |
| 231 | + */ | |
| 232 | + private void GenInit( boolean skel ) throws IOException | |
| 233 | + { | |
| 234 | + if ( skel ) | |
| 235 | + { | |
| 236 | + Emit( "init( jni_p : JNI )\n{\n" ); | |
| 237 | + Emit( T1+"# save java native inteface mod instance\n" ); | |
| 238 | + Emit( T1+"jni = jni_p;\n" ); | |
| 239 | + Emit( T1+"#>>extra initialization here\n"+T1+"#<<\n" ); | |
| 240 | + Emit( "}\n\n" ); | |
| 241 | + } | |
| 242 | + else | |
| 243 | + { | |
| 244 | + Emit( T1+"init : fn( jni_p : JNI );\n" ); | |
| 245 | + } | |
| 246 | + } | |
| 247 | + | |
| 248 | + /** | |
| 249 | + * Given an array of types return a string with | |
| 250 | + * a comma seperated sequence of java method | |
| 251 | + * parameter declarations | |
| 252 | + * | |
| 253 | + * @param ptypes An array of types | |
| 254 | + * | |
| 255 | + * @return A string representing method param decls | |
| 256 | + */ | |
| 257 | + private String GenFctParams( Class[] ptypes ) | |
| 258 | + { | |
| 259 | + String fct_params = ""; | |
| 260 | + for( int x=0; x<ptypes.length; x++ ) | |
| 261 | + { | |
| 262 | + fct_params = fct_params +"p"+ x +" : "+ LimboType( ptypes[x] ); | |
| 263 | + if ( x <ptypes.length-1 ) | |
| 264 | + fct_params = fct_params +","; | |
| 265 | + } | |
| 266 | + | |
| 267 | + return( fct_params ); | |
| 268 | + } | |
| 269 | + | |
| 270 | + | |
| 271 | + /** | |
| 272 | + * Take a Java class data-field and | |
| 273 | + * return a string with a coresponding | |
| 274 | + * Limbo adt field declaration. | |
| 275 | + * | |
| 276 | + * @param fi The Java field descriptor | |
| 277 | + * | |
| 278 | + * @return Limbo Declaration | |
| 279 | + */ | |
| 280 | + private String GenFieldDecl( Field fi ) | |
| 281 | + { | |
| 282 | + String fi_name = fi.getName(); | |
| 283 | + Class java_type = fi.getType(); | |
| 284 | + | |
| 285 | + String limbo_type = LimboType( java_type ); | |
| 286 | + | |
| 287 | + return( fi_name +" : "+ limbo_type ); | |
| 288 | + } | |
| 289 | + | |
| 290 | + | |
| 291 | + /** | |
| 292 | + * Accept a java Type descriptor and | |
| 293 | + * return a corresponding limbo type | |
| 294 | + * as a string. Return a empty string | |
| 295 | + * if the type is void or an unknown. | |
| 296 | + * | |
| 297 | + * @param java_t Java type | |
| 298 | + * | |
| 299 | + * @return Limbo type | |
| 300 | + */ | |
| 301 | + private String LimboType( Class java_t ) | |
| 302 | + { | |
| 303 | + String limbo_t; | |
| 304 | + | |
| 305 | + if ( java_t.isPrimitive() ) | |
| 306 | + { | |
| 307 | + // a java primitive type convert to appropriate limbo type | |
| 308 | + String t_name = java_t.getName(); | |
| 309 | + if ( t_name.equals( "short" ) || | |
| 310 | + t_name.equals( "char" ) || | |
| 311 | + t_name.equals( "int" ) ) | |
| 312 | + limbo_t = "int"; | |
| 313 | + else if ( t_name.equals( "long" ) ) | |
| 314 | + limbo_t = "big"; | |
| 315 | + else if ( t_name.equals( "float" ) || | |
| 316 | + t_name.equals( "double" ) ) | |
| 317 | + limbo_t = "real"; | |
| 318 | + else if ( t_name.equals( "byte" ) || | |
| 319 | + t_name.equals( "boolean" ) ) | |
| 320 | + limbo_t = "byte"; | |
| 321 | + else | |
| 322 | + limbo_t = ""; // void | |
| 323 | + | |
| 324 | + } | |
| 325 | + else | |
| 326 | + { | |
| 327 | + // a java reference (i.e. object or array) | |
| 328 | + String t_name = java_t.getName(); | |
| 329 | + | |
| 330 | + if ( t_name.startsWith( "[" ) ) | |
| 331 | + limbo_t = ArrayType( t_name ); | |
| 332 | + else | |
| 333 | + limbo_t = ClassName( t_name ); | |
| 334 | + } | |
| 335 | + | |
| 336 | + return( limbo_t ); | |
| 337 | + } | |
| 338 | + | |
| 339 | + private String ArrayType( String name ) | |
| 340 | + { | |
| 341 | + StringBuffer aryname = new StringBuffer(20); | |
| 342 | + aryname.append( T_JArray ); | |
| 343 | + | |
| 344 | + char let = name.charAt(1); | |
| 345 | + | |
| 346 | + if ( let == 'L' ) | |
| 347 | + { | |
| 348 | + // array of some class, determine Limo name | |
| 349 | + aryname.append( ClassName( name.substring(2, name.length()-1) ) ); | |
| 350 | + } | |
| 351 | + else if ( let == '[' ) | |
| 352 | + { | |
| 353 | + // array of array... | |
| 354 | + // we only care about first level | |
| 355 | + ; | |
| 356 | + } | |
| 357 | + else | |
| 358 | + aryname.append( name.substring(1) ); //append type | |
| 359 | + | |
| 360 | + return( aryname.toString() ); | |
| 361 | + } | |
| 362 | + | |
| 363 | + | |
| 364 | + private String ClassName( String clname ) | |
| 365 | + { | |
| 366 | + // we treat some classes special and | |
| 367 | + // use specific Limbo adt's otherwise | |
| 368 | + // use the generic JObject | |
| 369 | + String sp_class = SpecialClass( clname ); | |
| 370 | + if ( sp_class != null ) | |
| 371 | + return( sp_class ); | |
| 372 | + else if ( "java.io.FileDescriptor".equals(clname) ) | |
| 373 | + return( T_JFd ); | |
| 374 | + else if ( "inferno.vm.FD".equals(clname) ) | |
| 375 | + return( T_JInfernoFD ); | |
| 376 | + else if ( clname.endsWith( base_name ) ) | |
| 377 | + return( "ref "+ obj_adt ); | |
| 378 | + return( T_JObject ); | |
| 379 | + } | |
| 380 | + | |
| 381 | + | |
| 382 | + private String SpecialClass( String clname ) | |
| 383 | + { | |
| 384 | + if ( "java.lang.String".equals(clname) ) | |
| 385 | + return( T_JString ); | |
| 386 | + else if ( "java.lang.Class".equals(clname) ) | |
| 387 | + return( T_JClass ); | |
| 388 | + else if ( "java.lang.Object".equals(clname) ) | |
| 389 | + return( T_JObject ); | |
| 390 | + else | |
| 391 | + return( null ); | |
| 392 | + } | |
| 393 | + | |
| 394 | + /** | |
| 395 | + * Scan methods list and return list of | |
| 396 | + * native methods. | |
| 397 | + * | |
| 398 | + * @return Array of native methods, else array of length 0. | |
| 399 | + */ | |
| 400 | + private Method[] GetNatives( Method[] methods ) | |
| 401 | + { | |
| 402 | + // walk the methods array and count natives | |
| 403 | + int native_count = 0; | |
| 404 | + for( int x=0; x<methods.length; x++ ) | |
| 405 | + if ( Modifier.isNative( methods[x].getModifiers() ) ) | |
| 406 | + native_count++; | |
| 407 | + | |
| 408 | + if ( native_count == 0 ) return( new Method[0] ); | |
| 409 | + | |
| 410 | + if ( opt_verbose ) | |
| 411 | + System.out.println( "Native Methods:" ); | |
| 412 | + | |
| 413 | + // now create an array to hold natives and fill it | |
| 414 | + Method[] natives = new Method[native_count]; | |
| 415 | + native_count = 0; | |
| 416 | + for( int x=0; x<methods.length; x++ ) | |
| 417 | + if ( Modifier.isNative( methods[x].getModifiers() ) ) | |
| 418 | + { | |
| 419 | + natives[native_count++] = methods[x]; | |
| 420 | + if ( opt_verbose ) | |
| 421 | + System.out.println( "\t"+ methods[x] ); | |
| 422 | + } | |
| 423 | + | |
| 424 | + return( natives ); | |
| 425 | + } | |
| 426 | + | |
| 427 | + | |
| 428 | + /** | |
| 429 | + * Scan fields list and return list of | |
| 430 | + * instance fields. | |
| 431 | + * | |
| 432 | + * @return Array of instnace fields, else array oflen 0 | |
| 433 | + */ | |
| 434 | + private Field[] GetInstanceFields( Field[] fields ) | |
| 435 | + { | |
| 436 | + // walk the fields array and count non-statics | |
| 437 | + int count = 0; | |
| 438 | + for( int x=0; x<fields.length; x++ ) | |
| 439 | + if ( ! Modifier.isStatic( fields[x].getModifiers() ) ) | |
| 440 | + count++; | |
| 441 | + | |
| 442 | + if ( count == 0 ) return( new Field[0] ); | |
| 443 | + | |
| 444 | + if ( opt_verbose ) | |
| 445 | + System.out.println( "Instance Fields:" ); | |
| 446 | + | |
| 447 | + // now create an array to hold instance-fields and fill it | |
| 448 | + Field[] iFields = new Field[count]; | |
| 449 | + count = 0; | |
| 450 | + for( int x=0; x<fields.length; x++ ) | |
| 451 | + if ( ! Modifier.isStatic( fields[x].getModifiers() ) ) | |
| 452 | + { | |
| 453 | + iFields[count++] = fields[x]; | |
| 454 | + if ( opt_verbose ) | |
| 455 | + System.out.println( "\t"+ fields[x] ); | |
| 456 | + } | |
| 457 | + | |
| 458 | + return( iFields ); | |
| 459 | + } | |
| 460 | + | |
| 461 | + | |
| 462 | + /** | |
| 463 | + * Scan fields list and return list of | |
| 464 | + * static fields. | |
| 465 | + * | |
| 466 | + * @return Array of static fields, else array oflen 0 | |
| 467 | + */ | |
| 468 | + private Field[] GetStaticFields( Field[] fields ) | |
| 469 | + { | |
| 470 | + // walk the fields array and count non-statics | |
| 471 | + int count = 0; | |
| 472 | + for( int x=0; x<fields.length; x++ ) | |
| 473 | + if ( Modifier.isStatic( fields[x].getModifiers() ) ) | |
| 474 | + count++; | |
| 475 | + | |
| 476 | + if ( count == 0 ) return( new Field[0] ); | |
| 477 | + | |
| 478 | + if ( opt_verbose ) | |
| 479 | + System.out.println( "Instance Fields:" ); | |
| 480 | + | |
| 481 | + // now create an array to hold instance-fields and fill it | |
| 482 | + Field[] sFields = new Field[count]; | |
| 483 | + count = 0; | |
| 484 | + for( int x=0; x<fields.length; x++ ) | |
| 485 | + if ( Modifier.isStatic( fields[x].getModifiers() ) ) | |
| 486 | + { | |
| 487 | + sFields[count++] = fields[x]; | |
| 488 | + if ( opt_verbose ) | |
| 489 | + System.out.println( "\t"+ fields[x] ); | |
| 490 | + } | |
| 491 | + | |
| 492 | + return( sFields ); | |
| 493 | + } | |
| 494 | + | |
| 495 | + | |
| 496 | + private String ClassBaseName( String name ) | |
| 497 | + { | |
| 498 | + // for java.lang.Object return Object | |
| 499 | + // if last char is ';' strip it off (arrays) | |
| 500 | + | |
| 501 | + int start = name.lastIndexOf( '.' ); | |
| 502 | + int end = name.lastIndexOf( ';' ); | |
| 503 | + | |
| 504 | + // if neither found return name | |
| 505 | + if ( (start == -1) && (end==-1) ) return( name ); | |
| 506 | + | |
| 507 | + // adjust if ';' not found | |
| 508 | + end = ( (end==-1)? name.length() : end ); | |
| 509 | + | |
| 510 | + return( name.substring( start+1, end ) ); | |
| 511 | + } | |
| 512 | + | |
| 513 | + | |
| 514 | + private String MkFctName( Method meth ) | |
| 515 | + { | |
| 516 | + // build name from java method name | |
| 517 | + // java method param types, and the | |
| 518 | + // java method return type | |
| 519 | + | |
| 520 | + StringBuffer encode = new StringBuffer(50); | |
| 521 | + encode.append(meth.getName()); | |
| 522 | + | |
| 523 | + // append parmeter encoding | |
| 524 | + Class[] jparam = meth.getParameterTypes(); | |
| 525 | + for( int x=0; x<jparam.length; x++ ) | |
| 526 | + { | |
| 527 | + encode.append( "_" ); | |
| 528 | + encode.append( JTypeEncode( jparam[x] ) ); | |
| 529 | + } | |
| 530 | + | |
| 531 | + // append the method return type encoding | |
| 532 | + encode.append("_"); | |
| 533 | + encode.append( JTypeEncode( meth.getReturnType() ) ); | |
| 534 | + | |
| 535 | + if ( opt_verbose ) | |
| 536 | + System.out.println( "--mangled fct name:"+ encode ); | |
| 537 | + | |
| 538 | + return( encode.toString() ); | |
| 539 | + } | |
| 540 | + | |
| 541 | + | |
| 542 | + private String JTypeEncode( Class jtype ) | |
| 543 | + { | |
| 544 | + String t_name; //types name | |
| 545 | + String encode = ""; //limbo encoding | |
| 546 | + | |
| 547 | + if ( jtype.isPrimitive() ) | |
| 548 | + { | |
| 549 | + // a java primitive type convert to appropriate limbo type | |
| 550 | + t_name = jtype.getName(); | |
| 551 | + | |
| 552 | + // determine | |
| 553 | + if ( t_name.equals( "int" ) ) | |
| 554 | + encode = "I"; | |
| 555 | + else if ( t_name.equals( "char" ) ) | |
| 556 | + encode = "C"; | |
| 557 | + else if ( t_name.equals( "short" ) ) | |
| 558 | + encode = "S"; | |
| 559 | + else if ( t_name.equals( "long" ) ) | |
| 560 | + encode = "J"; | |
| 561 | + else if ( t_name.equals( "boolean" ) ) | |
| 562 | + encode = "Z"; | |
| 563 | + else if ( t_name.equals( "byte" ) ) | |
| 564 | + encode = "B"; | |
| 565 | + else if ( t_name.equals( "float" ) ) | |
| 566 | + encode = "F"; | |
| 567 | + else if ( t_name.equals( "double" ) ) | |
| 568 | + encode = "D"; | |
| 569 | + else | |
| 570 | + encode = "V"; | |
| 571 | + } | |
| 572 | + else | |
| 573 | + { | |
| 574 | + // a java reference (i.e. object or array) | |
| 575 | + t_name = jtype.getName(); | |
| 576 | + | |
| 577 | + if ( t_name.indexOf( '[' ) == -1 ) | |
| 578 | + { | |
| 579 | + // just an object reference | |
| 580 | + encode = "r"+ ClassBaseName( t_name ); | |
| 581 | + } | |
| 582 | + else | |
| 583 | + { | |
| 584 | + // array | |
| 585 | + int x=0; | |
| 586 | + StringBuffer buf = new StringBuffer(40); | |
| 587 | + while( t_name.charAt(x)== '[' ) | |
| 588 | + { | |
| 589 | + buf.append('a'); | |
| 590 | + x++; | |
| 591 | + } | |
| 592 | + if ( t_name.charAt(x) == 'L' ) | |
| 593 | + buf.append( ClassBaseName(t_name.substring(x+1)) ); | |
| 594 | + else | |
| 595 | + buf.append( t_name.substring(x) ); | |
| 596 | + encode = buf.toString(); | |
| 597 | + } | |
| 598 | + } | |
| 599 | + | |
| 600 | + return( encode ); | |
| 601 | + } | |
| 602 | + | |
| 603 | + | |
| 604 | + private DataOutputStream MkFile( String name ) throws IOException | |
| 605 | + { | |
| 606 | + File f = new File( name ); | |
| 607 | + FileOutputStream fout; | |
| 608 | + | |
| 609 | + tmpname = "tmp_"+ name; | |
| 610 | + | |
| 611 | + if ( f.exists() ) | |
| 612 | + { | |
| 613 | + fout = new FileOutputStream( tmpname ); | |
| 614 | + merge = true; | |
| 615 | + } | |
| 616 | + else | |
| 617 | + fout = new FileOutputStream( name ); | |
| 618 | + | |
| 619 | + return( new DataOutputStream( fout ) ); | |
| 620 | + } | |
| 621 | + | |
| 622 | + private void Emit( String info ) throws IOException | |
| 623 | + { | |
| 624 | + out.writeBytes( info ); | |
| 625 | + } | |
| 626 | + | |
| 627 | + | |
| 628 | + // data fields | |
| 629 | + private String base_name; // name of class | |
| 630 | + private String mod_name; // module name of native "peer" module | |
| 631 | + private String limbo_dotm; // name of limbo module decl .m file | |
| 632 | + private String limbo_dotb; // name of limbo module impl .b file | |
| 633 | + private String obj_adt; // adt describing objects instance fields | |
| 634 | + private boolean special; // set true if a special class; a special | |
| 635 | + // class is one known to this tool. | |
| 636 | + | |
| 637 | + Class theClass; // class descriptor object | |
| 638 | + | |
| 639 | + DataOutputStream out; // current gen output file | |
| 640 | + boolean merge = false; // merge old and new gen'ed files | |
| 641 | + String tmpname; | |
| 642 | + | |
| 643 | + Method[] methods; // all methods | |
| 644 | + Method[] natives; // native methods | |
| 645 | + | |
| 646 | + Field[] fields; // all fields | |
| 647 | + Field[] iFields; // instance fields | |
| 648 | + Field[] sFields; // static fields | |
| 649 | + | |
| 650 | + boolean opt_verbose; // print stuff if true | |
| 651 | + boolean has_natives; // set true if class has native methods | |
| 652 | + | |
| 653 | + // consts | |
| 654 | + private static final String T1 = " "; | |
| 655 | + private static final String T2 = " "; | |
| 656 | + private static final String T3 = " "; | |
| 657 | + | |
| 658 | + // generated Limbo/Java type names | |
| 659 | + private static final String T_JObject = "JObject"; | |
| 660 | + private static final String T_JString = "JString"; | |
| 661 | + private static final String T_JClass = "JClass"; | |
| 662 | + private static final String T_JArrayI = "JArrayI"; | |
| 663 | + private static final String T_JArrayC = "JArrayC"; | |
| 664 | + private static final String T_JArrayS = "JArrayS"; | |
| 665 | + private static final String T_JArrayB = "JArrayB"; | |
| 666 | + private static final String T_JArrayJ = "JArrayJ"; | |
| 667 | + private static final String T_JArrayF = "JArrayF"; | |
| 668 | + private static final String T_JArrayD = "JArrayD"; | |
| 669 | + private static final String T_JArrayZ = "JArrayZ"; | |
| 670 | + private static final String T_JArrayJObject = "JArrayJObject"; | |
| 671 | + private static final String T_JArrayJClass = "JArrayJClass"; | |
| 672 | + private static final String T_JArrayJString = "JArrayJString"; | |
| 673 | + private static final String T_JArray = "JArray"; | |
| 674 | + private static final String T_JFd = "ref FileDescriptor_obj"; | |
| 675 | + private static final String T_JInfernoFD = "ref Sys->FD"; | |
| 676 | + | |
| 677 | +} | |