docs: private static void addDelegateMethod(ClassWriter cw,
                                            String tieClassName,
                                            Set<String> classConstantFieldNames,
                                            String servantClassName,
                                            String servantDescriptor,
                                            Method method,
                                            String idlName,
                                            boolean isRmiRemote,
                                            int rmicCompatible)
                      throws EJBConfigurationException
      {
          GeneratorAdapter mg;
  
          Class<?>[] methodParameters = method.getParameterTypes();
          Type[] argTypes = getTypes(methodParameters);
          final int numArgs = argTypes.length;
          Class<?> returnClass = method.getReturnType();
          Type returnType = Type.getType(returnClass);
          String methodDescriptor = Type.getMethodDescriptor(returnType,
                                                             argTypes);
          Class<?>[] checkedExceptions = DeploymentUtil.getCheckedExceptions(method,
                                                                             isRmiRemote,
                                                                             DeploymentUtil.DeploymentTarget.TIE); // d660332
          Type[] checkedTypes = getTypes(checkedExceptions);
          int numChecked = checkedExceptions.length;
  
          if (TraceComponent.isAnyTracingEnabled() && tc.isDebugEnabled())
              Tr.debug(tc, INDENT + "adding method : " + idlName +
                           " (Lorg/omg/CORBA_2_3/portable/InputStream;" +
                           "Lorg/omg/CORBA/portable/ResponseHandler;)" +
                           "Lorg/omg/CORBA/portable/OutputStream;");
  
          // -----------------------------------------------------------------------
          // private OutputStream <idl name> (InputStream in , ResponseHandler reply)
          //    throws Throwable
          // -----------------------------------------------------------------------
          Type delegateReturnType = TYPE_CORBA_OutputStream;
          Type[] delegateArgTypes = { TYPE_CORBA_2_3_InputStream,
                                     TYPE_CORBA_ResponseHandler };
          Type[] delegateExceptionTypes = { TYPE_Throwable };
  
          org.objectweb.asm.commons.Method m =
                          new org.objectweb.asm.commons.Method(idlName,
                                          delegateReturnType,
                                          delegateArgTypes);
  
          // Create an ASM GeneratorAdapter object for the ASM Method, which
          // makes generating dynamic code much easier... as it keeps track
          // of the position of the arguements and local variables, etc.
          mg = new GeneratorAdapter(ACC_PRIVATE, m, null, delegateExceptionTypes, cw);
  
          // -----------------------------------------------------------------------
          // Begin Method Code...
          // -----------------------------------------------------------------------
          mg.visitCode();
  
          /*
           * mg.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");
           * mg.visitTypeInsn(NEW, "java/lang/StringBuilder");
           * mg.visitInsn(DUP);
           * mg.visitMethodInsn(INVOKESPECIAL, "java/lang/StringBuilder", "<init>", "()V");
           * mg.visitLdcInsn(idlName + " called!!");
           * mg.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuilder", "append", "(Ljava/lang/String;)Ljava/lang/StringBuilder;");
           * mg.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuilder", "toString", "()Ljava/lang/String;");
           * mg.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "println",
           * "(Ljava/lang/String;)V");
           */
  
          // -----------------------------------------------------------------------
          // <arg type> argX = in.read_<primitive>();
          //              or
          // <arg type> argX = (<arg type>)in.read_value( <arg class> );
          //              or
          // <arg type> argX = (<arg type>)in.read_Object( <arg class> ); // CORBA.Object
          // -----------------------------------------------------------------------
          int[] argValues = new int[numArgs];
  
          for (int i = 0; i < numArgs; i++)
          {
              JITUtils.setLineNumber(mg, JITUtils.LINE_NUMBER_ARG_BEGIN + i); // d726162
  
              argValues[i] = mg.newLocal(argTypes[i]);
              mg.loadArg(0);
              read_value(mg, tieClassName, classConstantFieldNames, // RTC111522
                         method, methodParameters[i], argTypes[i], rmicCompatible); // d450525
              mg.storeLocal(argValues[i]);
          }
  
          JITUtils.setLineNumber(mg, JITUtils.LINE_NUMBER_DEFAULT); // d726162
  
          // -----------------------------------------------------------------------
          // // The try/catch block is only needed if there are
          // // checked exceptions other than RemoteException.
          // try
          // {
          // -----------------------------------------------------------------------
          Label try_begin = null;
          if (numChecked > 0)
          {
              try_begin = new Label();
              mg.visitLabel(try_begin);
          }
  
          // -----------------------------------------------------------------------
          //   target.<servant method>( argX, argX,... );
          //              or
          //   <return type> result = target.<servant method>( argX, argX,... );
          // -----------------------------------------------------------------------
          mg.loadThis();
          mg.visitFieldInsn(GETFIELD, tieClassName,
                            "target", servantDescriptor);
          for (int arg : argValues)
          {
              mg.loadLocal(arg);
          }
          mg.visitMethodInsn(INVOKEVIRTUAL, servantClassName,
                             method.getName(), methodDescriptor);
  
          int result = -1;
          if (returnType != Type.VOID_TYPE)
          {
              result = mg.newLocal(returnType);
              mg.storeLocal(result);
          }
  
          // -----------------------------------------------------------------------
          // }    // end of try - only when checked exceptions
          // -----------------------------------------------------------------------
          Label try_end = null;
          Label try_catch_exit = null;
  
          if (numChecked > 0)
          {
              try_end = new Label();
              mg.visitLabel(try_end);
  
              try_catch_exit = new Label();
              mg.visitJumpInsn(GOTO, try_catch_exit); // jump past catch blocks
          }
  
          // -----------------------------------------------------------------------
          // // For every checked exception (that is NOT a RemoteException).
          // // Note that the exceptions have been sorted in order, so that the
          // // subclasses are first... to avoid 'unreachable' code.
          //
          // catch ( <exception type> ex )
          // {
          //   String id = <idl exception name>;              // "IDL:xxx/XxxEx:1.0"
          //   2_3.OutputStream out = (2_3.OutputStream) reply.createExceptionReply();
          //   out.write_string( id );
          //   out.write_value( ex, <exception type>.class );
          //   return out;
          // }
          // -----------------------------------------------------------------------
          Label[] catch_checked_labels = null;
          if (numChecked > 0)
          {
              catch_checked_labels = new Label[numChecked];
              for (int i = 0; i < numChecked; ++i)
              {
                  JITUtils.setLineNumber(mg, JITUtils.LINE_NUMBER_CATCH_BEGIN + i); // d726162
  
                  // catch ( <exception type> ex )
                  Label catch_label = new Label();
                  catch_checked_labels[i] = catch_label;
                  mg.visitLabel(catch_label);
                  int ex = mg.newLocal(checkedTypes[i]);
                  mg.storeLocal(ex);
  
                  //   String id = <idl exception name>;              // "IDL:xxx/XxxEx:1.0"
                  int id = mg.newLocal(TYPE_String);
                  boolean mangleComponents = com.ibm.wsspi.ejbcontainer.JITDeploy.isRMICCompatibleExceptions(rmicCompatible); // PM94096
                  String exIdlName = getIdlExceptionName(checkedExceptions[i].getName(), mangleComponents);
                  mg.visitLdcInsn(exIdlName);
                  mg.storeLocal(id);
  
                  //   2_3.OutputStream out = (2_3.OutputStream) reply.createExceptionReply();
                  int out = mg.newLocal(TYPE_CORBA_2_3_OutputStream);
                  mg.loadArg(1);
                  mg.visitMethodInsn(INVOKEINTERFACE, "org/omg/CORBA/portable/ResponseHandler",
                                     "createExceptionReply",
                                     "()Lorg/omg/CORBA/portable/OutputStream;");
                  mg.checkCast(TYPE_CORBA_2_3_OutputStream);
                  mg.storeLocal(out);
  
                  //   out.write_string( id );
                  mg.loadLocal(out);
                  mg.loadLocal(id);
                  mg.visitMethodInsn(INVOKEVIRTUAL, "org/omg/CORBA/portable/OutputStream",
                                     "write_string", "(Ljava/lang/String;)V");
  
                  //   out.write_value( ex, <exception type>.class );
                  mg.loadLocal(out);
                  mg.loadLocal(ex);
                  JITUtils.loadClassConstant(mg, tieClassName, classConstantFieldNames, checkedExceptions[i]); // RTC111522
                  mg.visitMethodInsn(INVOKEVIRTUAL, "org/omg/CORBA_2_3/portable/OutputStream",
                                     "write_value", "(Ljava/io/Serializable;Ljava/lang/Class;)V");
  
                  //   return out;
                  mg.loadLocal(out);
                  mg.returnValue();
              }
  
              mg.visitLabel(try_catch_exit);
          }
  
          JITUtils.setLineNumber(mg, JITUtils.LINE_NUMBER_RETURN); // d726162
  
          // -----------------------------------------------------------------------
          // OutputStream out = reply.createReply();
          //              or
          // CORBA_2_3.OutputStream out = (CORBA_2_3.OutputStream)reply.createReply();
          // -----------------------------------------------------------------------
          Type outType = CORBA_Utils.getRequiredOutputStreamType(returnClass, rmicCompatible); // PM46698
          int out = mg.newLocal(TYPE_CORBA_OutputStream);
          mg.loadArg(1);
          mg.visitMethodInsn(INVOKEINTERFACE,
                             "org/omg/CORBA/portable/ResponseHandler",
                             "createReply",
                             "()Lorg/omg/CORBA/portable/OutputStream;");
          if (outType != TYPE_CORBA_OutputStream)
          {
              mg.checkCast(outType);
          }
          mg.storeLocal(out);
  
          // -----------------------------------------------------------------------
          // out.write_<primitive>( result );
          //              or
          // out.write_value( result, <class> );
          //              or
          // Util.writeAny( out, result );
          //              or
          // Util.writeRemoteObject( out, result );
          // -----------------------------------------------------------------------
          if (returnType != Type.VOID_TYPE)
          {
              mg.loadLocal(out);
              mg.loadLocal(result);
              write_value(mg, tieClassName, classConstantFieldNames, // RTC111522
                          method, returnClass, rmicCompatible); // d450525, PM46698
          }
  
          // -----------------------------------------------------------------------
          //   return out;
          // -----------------------------------------------------------------------
          mg.loadLocal(out);
          mg.returnValue();
  
          // -----------------------------------------------------------------------
          // All Try-Catch-Finally definitions for above
          // -----------------------------------------------------------------------
          for (int i = 0; i < numChecked; ++i)
          {
              String exName = convertClassName(checkedExceptions[i].getName());
              mg.visitTryCatchBlock(try_begin, try_end,
                                    catch_checked_labels[i],
                                    exName);
          }
  
          // -----------------------------------------------------------------------
          // End Method Code...
          // -----------------------------------------------------------------------
          mg.endMethod(); // GeneratorAdapter accounts for visitMaxs(x,y)
          mg.visitEnd();
      }