// Path: src/main/java/guichaguri/betterfps/BetterFpsHelper.java
// public class BetterFpsHelper {
// 
//     public static final Logger LOG = LogManager.getLogger("BetterFps");
// 
//     private static BetterFpsConfig INSTANCE = null;
//     private static File CONFIG_FILE = null;
// 
//     public static BetterFpsConfig getConfig() {
//         if(INSTANCE == null) loadConfig();
//         return INSTANCE;
//     }
// 
//     public static void loadConfig() {
//         File configPath;
//         if(BetterFps.GAME_DIR == null) {
//             configPath = new File("config");
//         } else {
//             configPath = new File(BetterFps.GAME_DIR, "config");
//         }
// 
//         CONFIG_FILE = new File(configPath, "betterfps.json");
// 
//         // Temporary code - Import old config file to the new one
//         File oldConfig;
//         if(BetterFps.GAME_DIR == null) {
//             oldConfig = new File("config" + File.pathSeparator + "betterfps.json");
//         } else {
//             oldConfig = new File(BetterFps.GAME_DIR, "config" + File.pathSeparator + "betterfps.json");
//         }
//         if(oldConfig.exists()) {
//             FileReader reader = null;
//             try {
//                 reader = new FileReader(oldConfig);
//                 INSTANCE = new Gson().fromJson(reader, BetterFpsConfig.class);
//                 saveConfig();
//                 return;
//             } catch(Exception ex) {
//                 LOG.error("Could not load the old config file. It will be deleted.");
//             } finally {
//                 IOUtils.closeQuietly(reader);
//                 oldConfig.deleteOnExit();
//             }
//         }
//         // -------
// 
//         FileReader reader = null;
//         try {
//             if(CONFIG_FILE.exists()) {
//                 reader = new FileReader(CONFIG_FILE);
//                 INSTANCE = new Gson().fromJson(reader, BetterFpsConfig.class);
//             }
//         } catch(Exception ex) {
//             LOG.error("Could not load the config file", ex);
//         } finally {
//             IOUtils.closeQuietly(reader);
//         }
// 
//         if(INSTANCE == null) INSTANCE = new BetterFpsConfig();
// 
//         saveConfig();
//     }
// 
//     public static void saveConfig() {
//         FileWriter writer = null;
//         try {
//             if(!CONFIG_FILE.exists()) CONFIG_FILE.getParentFile().mkdirs();
//             writer = new FileWriter(CONFIG_FILE);
//             new Gson().toJson(INSTANCE, writer);
//         } catch(Exception ex) {
//             LOG.error("Could not save the config file", ex);
//         } finally {
//             IOUtils.closeQuietly(writer);
//         }
//     }
// 
// }


import guichaguri.betterfps.BetterFpsHelper;
import guichaguri.betterfps.transformers.annotations.Copy;
import guichaguri.betterfps.transformers.annotations.Copy.Mode;
import guichaguri.betterfps.transformers.annotations.Patcher;
import guichaguri.betterfps.transformers.annotations.Reference;
import java.util.HashMap;
import org.objectweb.asm.Type;
import org.objectweb.asm.tree.AnnotationNode;
import org.objectweb.asm.tree.ClassNode;
import org.objectweb.asm.tree.FieldNode;
import org.objectweb.asm.tree.MethodNode;
            }
        }

        // Copy Interfaces
        for(String i : sourceClass.interfaces) {
            if(!targetClass.interfaces.contains(i)) {
                targetClass.interfaces.add(i);
            }
        }
    }

    /**
     * Patches methods using a custom {@link IClassPatcher}
     */
    protected void patch() {
        AnnotationNode patcher = ASMUtils.getAnnotation(sourceClass.invisibleAnnotations, Patcher.class);

        if(patcher != null) {
            Type patcherClass = ASMUtils.getAnnotationValue(patcher, "value", Type.class);

            try {
                Class c = Class.forName(patcherClass.getClassName());
                IClassPatcher cp = (IClassPatcher)c.newInstance();

                // Find the references for the custom patcher
                findReferences();
                // Patch it!
                cp.patch(this);

            } catch(Exception ex) {
// Path: src/main/java/guichaguri/betterfps/BetterFpsHelper.java
// public class BetterFpsHelper {
// 
//     public static final Logger LOG = LogManager.getLogger("BetterFps");
// 
//     private static BetterFpsConfig INSTANCE = null;
//     private static File CONFIG_FILE = null;
// 
//     public static BetterFpsConfig getConfig() {
//         if(INSTANCE == null) loadConfig();
//         return INSTANCE;
//     }
// 
//     public static void loadConfig() {
//         File configPath;
//         if(BetterFps.GAME_DIR == null) {
//             configPath = new File("config");
//         } else {
//             configPath = new File(BetterFps.GAME_DIR, "config");
//         }
// 
//         CONFIG_FILE = new File(configPath, "betterfps.json");
// 
//         // Temporary code - Import old config file to the new one
//         File oldConfig;
//         if(BetterFps.GAME_DIR == null) {
//             oldConfig = new File("config" + File.pathSeparator + "betterfps.json");
//         } else {
//             oldConfig = new File(BetterFps.GAME_DIR, "config" + File.pathSeparator + "betterfps.json");
//         }
//         if(oldConfig.exists()) {
//             FileReader reader = null;
//             try {
//                 reader = new FileReader(oldConfig);
//                 INSTANCE = new Gson().fromJson(reader, BetterFpsConfig.class);
//                 saveConfig();
//                 return;
//             } catch(Exception ex) {
//                 LOG.error("Could not load the old config file. It will be deleted.");
//             } finally {
//                 IOUtils.closeQuietly(reader);
//                 oldConfig.deleteOnExit();
//             }
//         }
//         // -------
// 
//         FileReader reader = null;
//         try {
//             if(CONFIG_FILE.exists()) {
//                 reader = new FileReader(CONFIG_FILE);
//                 INSTANCE = new Gson().fromJson(reader, BetterFpsConfig.class);
//             }
//         } catch(Exception ex) {
//             LOG.error("Could not load the config file", ex);
//         } finally {
//             IOUtils.closeQuietly(reader);
//         }
// 
//         if(INSTANCE == null) INSTANCE = new BetterFpsConfig();
// 
//         saveConfig();
//     }
// 
//     public static void saveConfig() {
//         FileWriter writer = null;
//         try {
//             if(!CONFIG_FILE.exists()) CONFIG_FILE.getParentFile().mkdirs();
//             writer = new FileWriter(CONFIG_FILE);
//             new Gson().toJson(INSTANCE, writer);
//         } catch(Exception ex) {
//             LOG.error("Could not save the config file", ex);
//         } finally {
//             IOUtils.closeQuietly(writer);
//         }
//     }
// 
// }


// Path: src/main/java/guichaguri/betterfps/transformers/Patch.java
import guichaguri.betterfps.BetterFpsHelper;
import guichaguri.betterfps.transformers.annotations.Copy;
import guichaguri.betterfps.transformers.annotations.Copy.Mode;
import guichaguri.betterfps.transformers.annotations.Patcher;
import guichaguri.betterfps.transformers.annotations.Reference;
import java.util.HashMap;
import org.objectweb.asm.Type;
import org.objectweb.asm.tree.AnnotationNode;
import org.objectweb.asm.tree.ClassNode;
import org.objectweb.asm.tree.FieldNode;
import org.objectweb.asm.tree.MethodNode;

            }
        }

        // Copy Interfaces
        for(String i : sourceClass.interfaces) {
            if(!targetClass.interfaces.contains(i)) {
                targetClass.interfaces.add(i);
            }
        }
    }

    /**
     * Patches methods using a custom {@link IClassPatcher}
     */
    protected void patch() {
        AnnotationNode patcher = ASMUtils.getAnnotation(sourceClass.invisibleAnnotations, Patcher.class);

        if(patcher != null) {
            Type patcherClass = ASMUtils.getAnnotationValue(patcher, "value", Type.class);

            try {
                Class c = Class.forName(patcherClass.getClassName());
                IClassPatcher cp = (IClassPatcher)c.newInstance();

                // Find the references for the custom patcher
                findReferences();
                // Patch it!
                cp.patch(this);

            } catch(Exception ex) {
                BetterFpsHelper.LOG.error("Couldn't patch class {} with {}", targetClass.name, sourceClass.name);