gt:             if ((finfo.getAccessFlags() & AccessFlag.STATIC) == 0) {
context: /*
   * Javassist, a Java-bytecode translator toolkit.
   * Copyright (C) 1999- Shigeru Chiba. All Rights Reserved.
   *
   * The contents of this file are subject to the Mozilla Public License Version
   * 1.1 (the "License"); you may not use this file except in compliance with
   * the License.  Alternatively, the contents of this file may be used under
   * the terms of the GNU Lesser General Public License Version 2.1 or later,
   * or the Apache License Version 2.0.
   *
   * Software distributed under the License is distributed on an "AS IS" basis,
   * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
   * for the specific language governing rights and limitations under the
   * License.
   */
  
  package io.github.proxyhotswap.javassist;
  
  import io.github.proxyhotswap.javassist.CtMethod.ConstParameter;
  import io.github.proxyhotswap.javassist.bytecode.*;
  import io.github.proxyhotswap.javassist.compiler.CompileError;
  import io.github.proxyhotswap.javassist.compiler.Javac;
  
  /**
   * A collection of static methods for creating a <code>CtMethod</code>.
   * An instance of this class does not make any sense.
   *
   * @see CtClass#addMethod(CtMethod)
   */
  public class CtNewMethod {
  
      /**
       * Compiles the given source code and creates a method.
       * The source code must include not only the method body
       * but the whole declaration, for example,
       *
       * <ul><pre>"public Object id(Object obj) { return obj; }"</pre></ul>
       *
       * @param src               the source text. 
       * @param declaring    the class to which the created method is added.
       */
      public static CtMethod make(String src, CtClass declaring)
          throws CannotCompileException
      {
          return make(src, declaring, null, null);
      }
  
      /**
       * Compiles the given source code and creates a method.
       * The source code must include not only the method body
       * but the whole declaration, for example,
       *
       * <ul><pre>"public Object id(Object obj) { return obj; }"</pre></ul>
       *
       * <p>If the source code includes <code>$proceed()</code>, then
       * it is compiled into a method call on the specified object.
       *
       * @param src               the source text. 
       * @param declaring    the class to which the created method is added.
       * @param delegateObj       the source text specifying the object
       *                          that is called on by <code>$proceed()</code>.
       * @param delegateMethod    the name of the method
       *                          that is called by <code>$proceed()</code>.
       */
      public static CtMethod make(String src, CtClass declaring,
                                  String delegateObj, String delegateMethod)
          throws CannotCompileException
      {
          Javac compiler = new Javac(declaring);
          try {
              if (delegateMethod != null)
                  compiler.recordProceed(delegateObj, delegateMethod);
  
              CtMember obj = compiler.compile(src);
              if (obj instanceof CtMethod)
                  return (CtMethod)obj;
          }
          catch (CompileError e) {
              throw new CannotCompileException(e);
          }
  
          throw new CannotCompileException("not a method");
      }
  
      /**
       * Creates a public (non-static) method.  The created method cannot
       * be changed to a static method later.
       *
       * @param returnType        the type of the returned value.
       * @param mname             the method name.
       * @param parameters        a list of the parameter types.
       * @param exceptions        a list of the exception types.
       * @param body              the source text of the method body.
       *                  It must be a block surrounded by <code>{}</code>.
       *                  If it is <code>null</code>, the created method
       *                  does nothing except returning zero or null.
       * @param declaring    the class to which the created method is added.
       * @see #make(int, CtClass, String, CtClass[], CtClass[], String, CtClass)
       */
      public static CtMethod make(CtClass returnType,
                                  String mname, CtClass[] parameters,
                                  CtClass[] exceptions,
                                  String body, CtClass declaring)
          throws CannotCompileException
      {
          return make(Modifier.PUBLIC, returnType, mname, parameters, exceptions,
                      body, declaring);
      }
  
      /**
       * Creates a method.  <code>modifiers</code> can contain
       * <code>Modifier.STATIC</code>.
       *
       * @param modifiers         access modifiers.
       * @param returnType        the type of the returned value.
       * @param mname             the method name.
       * @param parameters        a list of the parameter types.
       * @param exceptions        a list of the exception types.
       * @param body              the source text of the method body.
       *                  It must be a block surrounded by <code>{}</code>.
       *                  If it is <code>null</code>, the created method
       *                  does nothing except returning zero or null.
       * @param declaring    the class to which the created method is added.
       *
       * @see Modifier
       */
      public static CtMethod make(int modifiers, CtClass returnType,
                                  String mname, CtClass[] parameters,
                                  CtClass[] exceptions,
                                  String body, CtClass declaring)
          throws CannotCompileException
      {
          try {
              CtMethod cm
                  = new CtMethod(returnType, mname, parameters, declaring);
              cm.setModifiers(modifiers);
              cm.setExceptionTypes(exceptions);
              cm.setBody(body);
              return cm;
          }
          catch (NotFoundException e) {
              throw new CannotCompileException(e);
          }
      }
  
      /**
       * Creates a copy of a method.  This method is provided for creating
       * a new method based on an existing method.
       * This is a convenience method for calling
       * {@link CtMethod#CtMethod(CtMethod, CtClass, ClassMap) this constructor}.
       * See the description of the constructor for particular behavior of the copying.
       *
       * @param src       the source method.
       * @param declaring    the class to which the created method is added.
       * @param map       the hash table associating original class names
       *                  with substituted names.
       *                  It can be <code>null</code>.
       *
       * @see CtMethod#CtMethod(CtMethod,CtClass,ClassMap)
       */
      public static CtMethod copy(CtMethod src, CtClass declaring,
                                  ClassMap map) throws CannotCompileException {
          return new CtMethod(src, declaring, map);
      }
  
      /**
       * Creates a copy of a method with a new name.
       * This method is provided for creating
       * a new method based on an existing method.
       * This is a convenience method for calling
       * {@link CtMethod#CtMethod(CtMethod, CtClass, ClassMap) this constructor}.
       * See the description of the constructor for particular behavior of the copying.
       *
       * @param src       the source method.
       * @param name      the name of the created method.
       * @param declaring    the class to which the created method is added.
       * @param map       the hash table associating original class names
       *                  with substituted names.
       *                  It can be <code>null</code>.
       *
       * @see CtMethod#CtMethod(CtMethod,CtClass,ClassMap)
       */
      public static CtMethod copy(CtMethod src, String name, CtClass declaring,
                                  ClassMap map) throws CannotCompileException {
          CtMethod cm = new CtMethod(src, declaring, map);
          cm.setName(name);
          return cm;
      }
  
      /**
       * Creates a public abstract method.
       *
       * @param returnType        the type of the returned value
       * @param mname             the method name
       * @param parameters        a list of the parameter types
       * @param exceptions        a list of the exception types
       * @param declaring    the class to which the created method is added.
       *
       * @see CtMethod#CtMethod(CtClass,String,CtClass[],CtClass)
       */
      public static CtMethod abstractMethod(CtClass returnType,
                                            String mname,
                                            CtClass[] parameters,
                                            CtClass[] exceptions,
                                            CtClass declaring)
          throws NotFoundException
      {
          CtMethod cm = new CtMethod(returnType, mname, parameters, declaring);
          cm.setExceptionTypes(exceptions);
          return cm;
      }
  
      /**
       * Creates a public getter method.  The getter method returns the value
       * of the specified field in the class to which this method is added.
       * The created method is initially not static even if the field is
       * static.  Change the modifiers if the method should be static.
       *
       * @param methodName        the name of the getter
       * @param field             the field accessed.
       */
      public static CtMethod getter(String methodName, CtField field)
          throws CannotCompileException
      {
          FieldInfo finfo = field.getFieldInfo2();
          String fieldType = finfo.getDescriptor();
          String desc = "()" + fieldType;
          ConstPool cp = finfo.getConstPool();
          MethodInfo minfo = new MethodInfo(cp, methodName, desc);
          minfo.setAccessFlags(AccessFlag.PUBLIC);
  
          Bytecode code = new Bytecode(cp, 2, 1);
          try {
              String fieldName = finfo.getName();
              if ((finfo.getAccessFlags() & AccessFlag.STATIC) == 0) {
                  code.addAload(0);
                  code.addGetfield(Bytecode.THIS, fieldName, fieldType);
              }
              else
                  code.addGetstatic(Bytecode.THIS, fieldName, fieldType);
  
              code.addReturn(field.getType());
          }
          catch (NotFoundException e) {
              throw new CannotCompileException(e);
          }
  
          minfo.setCodeAttribute(code.toCodeAttribute());
          CtClass cc = field.getDeclaringClass();
          // a stack map is not needed.
          return new CtMethod(minfo, cc);
      }
  
      /**
       * Creates a public setter method.  The setter method assigns the
       * value of the first parameter to the specified field
       * in the class to which this method is added.
       * The created method is not static even if the field is
       * static.  You may not change it to be static
       * by <code>setModifiers()</code> in <code>CtBehavior</code>.
       *
       * @param methodName        the name of the setter
       * @param field             the field accessed.
       */
      public static CtMethod setter(String methodName, CtField field)
          throws CannotCompileException
      {
          FieldInfo finfo = field.getFieldInfo2();
          String fieldType = finfo.getDescriptor();
          String desc = "(" + fieldType + ")V";
          ConstPool cp = finfo.getConstPool();
          MethodInfo minfo = new MethodInfo(cp, methodName, desc);
          minfo.setAccessFlags(AccessFlag.PUBLIC);
  
          Bytecode code = new Bytecode(cp, 3, 3);
          try {
              String fieldName = finfo.getName();
  