1 19 20 package gcc.rmi.iiop.compiler; 21 22 import gcc.generator.*; 23 24 import java.lang.reflect.Method; 25 import java.lang.reflect.Modifier; 26 27 import java.util.HashMap; 28 import java.util.Date; 29 import java.io.File; 30 31 public class SkelCompiler 32 extends Compiler 33 { 34 protected ValueTypeContext _vtc = new ValueTypeContext(); 35 protected static JParameter _objInputVar = new JParameter( gcc.rmi.iiop.ObjectInputStream.class, "input"); 36 protected static JParameter _objOutputVar = new JParameter( gcc.rmi.iiop.ObjectOutputStream.class, "output"); 37 38 public SkelCompiler(Class remoteInterface) 39 { 40 super( remoteInterface ); 41 } 42 43 public SkelCompiler( Class remoteInterface, GenOptions go ) 44 { 45 super( remoteInterface, go ); 46 } 47 48 52 public void addMethodGetIds( JClass jc ) 53 { 54 60 61 JMethod jm = jc.newMethod( new JReturnType(String.class, true), 62 "getIds", 63 (JParameter[])null, 64 (Class[])null ); 65 66 jm.addStatement( new JCodeStatement("return _ids;") ); 67 } 68 69 public void addMethodRegisterMethod( JClass jc ) 70 { 71 77 78 JMethod jm = jc.newMethod( new JReturnType(void.class), 79 "registerMethod", 80 new JParameter[] { new JParameter( String.class, "name" ), 81 new JParameter( int.class, "id" ) }, 82 (Class[]) null ); 83 84 jm.addStatement( new JCodeStatement("_methods.put( name, new Integer(id) );") ); 85 } 86 87 public void addMethodGetObjectRef( JClass jc, Class c ) 88 { 89 98 99 JMethod jm = jc.newMethod( new JReturnType("ObjectRef"), 100 "$getObjectRef", 101 (JParameter[])null, 102 (Class[]) null ); 103 104 JLocalVariable jvor = jm.newLocalVariable( gcc.rmi.iiop.ObjectRef.class, "or", new JExpression( new JCodeStatement( "new ObjectRef()" ) ) ); 105 jm.addStatement( new JCodeStatement( jvor.getName() + ".$setID(\"RMI:" + c.getName() + ":0000000000000000\");" ) ); 106 jm.addStatement( new JCodeStatement( jvor.getName() + ".$setObjectKey(\"" + c.getName() + "\");" ) ); 107 jm.addStatement( new JCodeStatement( "return " + jvor.getName() + ";" ) ); 108 } 109 110 public void addMethodGetSkeleton( JClass jc ) 111 { 112 118 119 JMethod jm = jc.newMethod( new JReturnType("RemoteInterface"), 120 "$getSkeleton", 121 (JParameter[])null, 122 (Class[]) null ); 123 124 jm.addStatement( new JCodeStatement("return this;") ); 125 } 126 127 protected boolean throwsAnRMIRemoteException( Method m ) 128 { 129 boolean rc = false; 130 131 Class c[] = m.getExceptionTypes (); 132 int i; 133 134 for( i=0; i<c.length && !rc; i++ ) 135 { 136 rc = java.rmi.RemoteException.class.isAssignableFrom(c[i]); 137 } 138 139 return rc; 140 } 141 142 public void addMethod( Method m, JClass jc ) 143 { 144 String invokeCall; 145 String name = m.getName(); 146 JParameter[] sparms = getMethodParms(m); 147 JParameter[] iparms = new JParameter[] { _objInputVar, _objOutputVar }; 148 149 if (!isSimpleIDL() && !throwsAnRMIRemoteException(m)) 150 { 151 error( "Method " + m.getName() + " does not throw java.rmi.RemoteException or subclass, unable to generate its skeleton method." ); 152 } 153 154 JMethod jm = jc.newMethod( new JReturnType(void.class), name, iparms, null ); 155 156 JVariable jrc = null; 157 String rc = m.getReturnType().getName(); 158 if ( rc != null && rc.length() > 0 && (!rc.equals("void")) ) 159 { 160 jrc = jm.newLocalVariable( m.getReturnType(), "rc" ); 161 } 162 163 JTryCatchFinallyStatement tcfs = new JTryCatchFinallyStatement(); 164 JTryStatement ts = tcfs.getTryStatement(); 165 166 invokeCall = "_servant." + name + "("; 167 168 if (sparms != null && sparms.length > 0) 169 { 170 int i; 171 for( i=0; i<sparms.length; i++ ) 172 { 173 String readMethod = getReadMethod(sparms[i]); 174 JCodeStatement jcs = null; 175 176 if (readMethod != null) 177 { 178 181 jcs = new JCodeStatement( "input." + readMethod + "()" ); 182 } 183 else 184 { 185 String vtVarName = _vtc.getValueTypeVarName( jc, sparms[i] ); 186 if (vtVarName != null) 187 { 188 jcs = new JCodeStatement( "(" + sparms[i].getTypeDecl() + ") input.readObject( " + vtVarName + " )" ); 189 } 190 else 191 { 192 jcs = new JCodeStatement( "// Code Gen Error: Class '" + sparms[i].getTypeDecl() + " is not a valid value type." ); 193 } 194 } 195 196 ts.addStatement( new JDeclareStatement( sparms[i], new JExpression( jcs ) ) ); 197 198 invokeCall += " " + sparms[i].getName(); 199 if (i + 1 < sparms.length) 200 { 201 invokeCall += ","; 202 } 203 } 204 } 205 206 invokeCall += " )"; 207 208 if (jrc != null) 209 { 210 invokeCall = jrc.getName() + " = " + invokeCall; 211 } 212 213 invokeCall = invokeCall + ";"; 214 215 ts.addStatement( new JCodeStatement(invokeCall) ); 216 217 JVariable jv = new JVariable( java.lang.Exception.class, "ex" ); 218 JCatchStatement cs = tcfs.newCatch( jv ); 219 cs.addStatement( new JCodeStatement( jv.getName() + ".printStackTrace();" ) ); 220 221 jv = new JVariable( java.lang.Error.class, "er" ); 222 cs = tcfs.newCatch( jv ); 223 cs.addStatement( new JCodeStatement( jv.getName() + ".printStackTrace();" ) ); 224 225 jm.addStatement( tcfs ); 226 227 if (jrc != null) 228 { 229 String writeMethod = getWriteMethod(jrc); 230 JCodeStatement jcs = null; 231 232 if (writeMethod != null) 233 { 234 237 jcs = new JCodeStatement( "output." + writeMethod + "( " + jrc.getName() + " );" ); 238 } 239 else 240 { 241 String vtVarName = _vtc.getValueTypeVarName( jc, jrc ); 242 if (vtVarName != null) 243 { 244 jcs = new JCodeStatement( "output.writeObject( " + vtVarName + ", " + jrc.getName() +" );" ); 245 } 246 else 247 { 248 jcs = new JCodeStatement( "// Code Gen Error: Class '" + jrc.getTypeDecl() + " is not a valid value type." ); 249 } 250 } 251 252 ts.addStatement( jcs ); 253 } 254 } 255 256 protected boolean isVariableAValueType( JVariable jv ) 257 { 258 boolean rc = false; 259 260 if (jv != null) 261 { 262 Class c = jv.getType(); 263 264 rc = isClassAValueType( c ); 265 } 266 267 return rc; 268 } 269 270 protected boolean isClassAValueType( Class c ) 271 { 272 boolean rc = false; 273 274 if (c != null) 275 { 276 if (java.io.Serializable.class.isAssignableFrom(c)) 277 { 278 if (java.io.Externalizable.class.isAssignableFrom(c)) 279 { 280 } 282 283 if (! isClassARMIRemote(c)) 284 { 285 if ( Modifier.isStatic(c.getModifiers()) && 286 c.getName().indexOf("$") != -1 ) 287 { 288 291 rc = true; 293 } 294 295 rc = true; 296 } 297 else 298 { 299 error( "Class: " + c.getName() + " is not proper value type as it is an instance of java.rmi.Remote or subclass." ); 300 } 301 } 302 } 303 304 return rc; 305 } 306 307 protected boolean isClassARMIRemote( Class c ) 308 { 309 boolean rc = false; 310 311 if (c != null) 312 { 313 rc = java.rmi.Remote.class.isAssignableFrom( c ); 314 } 315 316 return rc; 317 } 318 319 protected void error( String msg ) 320 { 321 System.out.println( "Error: " + msg ); 322 } 323 324 protected void error( String msg, Throwable t ) 325 { 326 error( msg ); 327 t.printStackTrace(); 328 } 329 330 public void generate() 331 throws Exception 332 { 333 _vtc.clear(); 334 335 if (!isSimpleIDL() && !isClassARMIRemote( _riClass )) 336 { 337 error( "Class '" + _riClass.getName() + "' must be an instance of either java.rmi.Remote or of a subclass." ); 338 } 339 340 ClassLoader cl = _riClass.getClassLoader(); 341 if (cl == null) 342 { 343 cl = ClassLoader.getSystemClassLoader(); 344 } 345 346 String fullGenDir = _genOptions.getGenDir(); 347 348 JavaGenerator jg = new JavaGenerator( _genOptions ); 349 350 String className = _riClass.getName(); 351 352 JPackage p = new JPackage( "" ); 353 if (_riClass.getPackage() != null) 354 { 355 p = new JPackage( _riClass.getPackage().getName() ); 356 className = className.substring ( className.lastIndexOf( ".") + 1 ); 357 } 358 359 JClass jc = p.newClass( className + "_Skeleton" ); 360 361 368 369 jc.addImport( "gcc.rmi.iiop", "ObjectInputStream" ); 370 jc.addImport( "gcc.rmi.iiop", "ObjectOutputStream" ); 371 jc.addImport( "gcc.rmi.iiop", "RemoteInterface" ); 372 jc.addImport( "gcc.rmi.iiop", "RemoteInterface" ); 373 jc.addImport( "gcc.rmi.iiop", "ObjectRef" ); 374 jc.addImport( "gcc.rmi.iiop", "RemoteObject" ); 375 jc.addImport( "gcc.rmi.iiop.server", "Adapter" ); 376 jc.addImport( "java.util", "HashMap" ); 377 378 jc.setExtends( "RemoteObject" ); 379 jc.addImplements( "RemoteInterface" ); 380 381 JField idsField = jc.newField( String[].class, "_ids", new JExpression( new JCodeStatement( "{ \"" + _riClass.getName() + "\", \"RMI:" + _riClass.getName() + ":0000000000000000\"}" ) ), true ); 382 JField methodsField = jc.newField( java.util.HashMap.class, "_methods", new JExpression( new JCodeStatement( "new HashMap(10)" ) ) ); 383 JField servantField = jc.newField( _riClass, "_servant", new JExpression( new JCodeStatement( "null" ) ) ); 384 385 JConstructor jcCon = jc.newConstructor( (JParameter[]) null, (Class[]) null ); 386 jcCon.addStatement( new JCodeStatement( "super();" ) ); 387 388 addMethodRegisterMethod( jc ); 389 addMethodGetIds( jc ); 390 addMethodGetSkeleton( jc ); 391 addMethodGetObjectRef( jc, _riClass ); 392 393 JMethod jmInvoke = jc.newMethod( new JReturnType(void.class), 394 "$invoke", 395 new JParameter[] { new JParameter( String.class, "methodName" ), 396 new JParameter( byte[].class, "objectKey" ), 397 new JParameter( Object.class, "instance" ), 398 _objInputVar, 399 _objOutputVar }, 400 (Class[]) null ); 401 402 jmInvoke.setModifier( Modifier.PUBLIC, true ); 403 404 JLocalVariable jvM = jmInvoke.newLocalVariable( Integer.class, "m", new JExpression( new JCodeStatement( "(Integer)_methods.get(methodName)" ) ) ); 405 406 jmInvoke.addStatement( new JCodeStatement( "if (m == null)" ) ); 407 jmInvoke.addStatement( new JCodeStatement( "{" ) ); 408 jmInvoke.addStatement( new JCodeStatement( " throw new org.omg.CORBA.BAD_OPERATION(methodName);" ) ); 409 jmInvoke.addStatement( new JCodeStatement( "}" ) ); 410 jmInvoke.addStatement( new JCodeStatement( "" ) ); 411 jmInvoke.addStatement( new JCodeStatement( "_servant = (" + _riClass.getName() + ")instance;" ) ); 412 jmInvoke.addStatement( new JCodeStatement( "" ) ); 413 jmInvoke.addStatement( new JCodeStatement( "if (m.intValue() < 0)" ) ); 414 jmInvoke.addStatement( new JCodeStatement( "{" ) ); 415 jmInvoke.addStatement( new JCodeStatement( " super.invoke( m.intValue(), objectKey, instance, input, output );" ) ); 416 jmInvoke.addStatement( new JCodeStatement( "}" ) ); 417 jmInvoke.addStatement( new JCodeStatement( "" ) ); 418 419 JSwitchStatement ss = new JSwitchStatement(new JExpression(new JCodeStatement("m.intValue()"))); 420 JCaseStatement cs = null; 421 jmInvoke.addStatement( ss ); 422 423 Method m[] = null; 424 425 if (isSimpleIDL()) 426 { 427 m = _riClass.getMethods(); 428 } 429 else 430 { 431 m = _riClass.getDeclaredMethods(); 432 } 433 434 if (m != null && m.length > 0) 435 { 436 int i; 437 for (i=0; i<m.length; i++) 438 { 439 jcCon.addStatement( new JCodeStatement( "registerMethod( \"" + m[i].getName() + "\", " + i + ");" ) ); 441 442 cs = ss.newCase( new JExpression( new JCodeStatement("" + i) ) ); 444 cs.addStatement( new JCodeStatement( m[i].getName() + "(input,output);" ) ); 445 446 addMethod( m[i], jc ); 448 } 449 } 450 451 jg.generate( p ); 452 } 453 454 public void compile() 455 throws Exception 456 { 457 } 458 459 public Class getSkelClass() 460 { 461 Class c = null; 462 463 try 464 { 465 compile(); 467 } 468 catch( Exception ex ) 469 { 470 ex.printStackTrace(); 471 } 472 473 return c; 474 } 475 476 public static void main( String args[] ) 477 throws Exception 478 { 479 boolean generate = false; 480 boolean compile = false; 481 boolean simpleIDL = false; 482 String ri = ""; 483 GenOptions go = new GenOptions(); 484 485 go.setGenDir( "./src" ); 486 go.setOverwrite( false ); 487 go.setVerbose( false ); 488 489 for( int i=0; i<args.length; i++ ) 490 { 491 if (args[i].equals( "-g" )) 492 { 493 generate = true; 494 } 495 else if (args[i].equals( "-c" )) 496 { 497 compile = true; 498 } 499 else if (args[i].equals( "-d" ) && ((i+1) < args.length)) 500 { 501 go.setGenDir( args[++i] ); 502 } 503 else if (args[i].equals( "-v" )) 504 { 505 go.setVerbose( true ); 506 } 507 else if (args[i].equals( "-o" )) 508 { 509 go.setOverwrite( true ); 510 } 511 else if (args[i].equals( "-s" )) 512 { 513 simpleIDL = true; 514 } 515 else if (args[i].startsWith("-")) 516 { 517 System.out.println( "Warning: Ignoring unrecognized options: '" + args[i] + "'" ); 518 } 519 else 520 { 521 ri = args[i]; 522 } 523 } 524 525 Class riClass = Class.forName( ri ); 526 527 SkelCompiler sg = new SkelCompiler(riClass,go); 528 529 sg.setSimpleIDL( simpleIDL ); 530 531 if (generate) 532 { 533 if (go.isVerbose()) 534 { 535 System.out.println("Generating: " + ri ); 536 } 537 538 sg.generate(); 539 } 540 541 if (compile) 542 { 543 if (go.isVerbose()) 544 { 545 System.out.println("Compiling: " + ri ); 546 } 547 548 sg.compile(); 549 } 550 551 } 554 } 555 556 | Popular Tags |