aboutsummaryrefslogtreecommitdiff
path: root/src/main/java/ftbsc/lll/processor/tools/ProcessorOptions.java
blob: 0ef8a1836a977a09711e3abc6c23aa4ac16c0170 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
package ftbsc.lll.processor.tools;

import ftbsc.lll.IInjector;
import ftbsc.lll.exceptions.InvalidResourceException;
import ftbsc.lll.processor.tools.obfuscation.ObfuscationMapper;

import javax.annotation.processing.ProcessingEnvironment;
import java.io.*;
import java.net.URI;
import java.net.URISyntaxException;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Set;

/**
 * Class in charge of containing, parsing and processing all processor options,
 * from the simpler booleans to the more complicated mapper.
 */
public class ProcessorOptions {

   /**
    * A {@link Set} of options currently supported by the processor.
    */
   public static final Set<String> SUPPORTED = new HashSet<>(Arrays.asList(
      "mappingsFile", "anonymousClassWarning", "obfuscateInjectorMetadata",
      "noServiceProvider"
   ));

   /**
    * The environment the processor is acting in.
    */
   public final ProcessingEnvironment env;

   /**
    * The {@link ObfuscationMapper} used to convert classes and variables
    * to their obfuscated equivalent. Will be null when no mapper is in use.
    */
   public final ObfuscationMapper mapper;

   /**
    * Whether the processor should issue warnings when compiling code anonymous
    * classes which can't be checked for validity.
    */
   public final boolean anonymousClassWarning;

   /**
    * Whether injector metadata (what is returned by the functions of {@link IInjector})
    * is to use obfuscated names instead of its normal names.
    */
   public final boolean obfuscateInjectorMetadata;

   /**
    * Whether the processor should skip the generation of the service provider.
    */
   public final boolean noServiceProvider;

   /**
    * The public constructor, parses and stores all given arguments.
    * @param env the environment the processor is working in
    */
   public ProcessorOptions(ProcessingEnvironment env) {
      this.env = env;
      String location = env.getOptions().get("mappingsFile");
      if(location == null)
         this.mapper = null;
      else {
         InputStream targetStream;
         try {
            URI target = new URI(location);
            targetStream = target.toURL().openStream();
         } catch(URISyntaxException | IOException e) {
            //may be a local file path
            File f = new File(location);
            if(!f.exists())
               throw new InvalidResourceException(location);
            try {
               targetStream = new FileInputStream(f);
            } catch(FileNotFoundException ex) {
               throw new InvalidResourceException(location);
            }
         }
         //assuming its tsrg file
         //todo: replace crappy homebaked parser with actual library
         this.mapper = new ObfuscationMapper(new BufferedReader(new InputStreamReader(targetStream,
            StandardCharsets.UTF_8)).lines());
      }
      this.anonymousClassWarning = parseBooleanArg(env.getOptions().get("anonymousClassWarning"), true);
      this.obfuscateInjectorMetadata = parseBooleanArg(env.getOptions().get("obfuscateInjectorMetadata"), true);
      this.noServiceProvider = parseBooleanArg(env.getOptions().get("noServiceProvider"), false);
   }

   /**
    * Parses a boolean arg from a String.
    * @param arg the arg to parse
    * @return the parsed boolean
    */
   private static boolean parseBooleanArg(String arg, boolean defaultValue) {
      if(arg == null) return defaultValue;
      try { // 0 = false, any other integer = true
         int i = Integer.parseInt(arg);
         return i != 0;
      } catch(NumberFormatException ignored) {
         return Boolean.parseBoolean(arg);
      }
   }
}