package org.erlide.core.builder; import java.util.ArrayList; import java.util.Collection; import java.util.List; import java.util.Map; import org.eclipse.core.resources.IProject; import org.eclipse.xtext.xbase.lib.Pair; import org.erlide.core.ErlangCore; import org.erlide.core.builder.CompilerOption.BooleanOption; import org.erlide.core.builder.CompilerOption.DefineOption; import org.erlide.core.builder.CompilerOption.ModuleOption; import org.erlide.core.builder.CompilerOption.PathsOption; import org.erlide.core.builder.CompilerOption.RawOption; import org.erlide.core.builder.CompilerOption.WarningOption; import org.erlide.engine.util.PreferencesHelper; import org.erlide.util.ErlLogger; import org.erlide.util.erlang.OtpErlang; import org.erlide.util.erlang.OtpParserException; import org.osgi.service.prefs.BackingStoreException; import com.ericsson.otp.erlang.OtpErlangList; import com.ericsson.otp.erlang.OtpErlangObject; import com.google.common.base.Strings; import com.google.common.collect.Lists; import com.google.common.collect.Maps; public class CompilerOptions { private static final String QUALIFIER = ErlangCore.PLUGIN_ID + "/compiler"; private final Map<CompilerOption, Object> options; private PreferencesHelper helper; public static OtpErlangList get(final IProject project) { final CompilerOptions prefs = new CompilerOptions(project); prefs.load(); final OtpErlangList compilerOptions = prefs.export(); return compilerOptions; } public CompilerOptions() { helper = PreferencesHelper.getHelper(QUALIFIER); options = Maps.newHashMap(); for (final CompilerOption option : CompilerOption.ALL_OPTIONS) { if (option instanceof BooleanOption) { options.put(option, ((BooleanOption) option).getDefaultValue()); } if (option instanceof DefineOption) { options.put(option, new ArrayList<Pair<String, String>>()); } } } public CompilerOptions(final IProject project) { this(); helper = PreferencesHelper.getHelper(QUALIFIER, project); } public boolean hasOptionsAtLowestScope() { return helper.hasAnyAtLowestScope(); } public void store() throws BackingStoreException { for (final CompilerOption option : CompilerOption.ALL_OPTIONS) { final Object value = options.get(option); if (option instanceof BooleanOption) { final Boolean val = (Boolean) value; helper.putString(option.getName(), val.toString()); } else if (option instanceof PathsOption) { if (value != null) { @SuppressWarnings("unchecked") final Iterable<String> avalue = (Iterable<String>) value; helper.putString(option.getName(), PathsOption.toString(avalue)); } else { helper.remove(option.getName()); } } else if (option instanceof ModuleOption) { if (value != null) { final String avalue = (String) value; helper.putString(option.getName(), avalue); } else { helper.remove(option.getName()); } } else if (option instanceof RawOption) { if (value != null) { final String avalue = (String) value; helper.putString(option.getName(), avalue); } else { helper.remove(option.getName()); } } else { if (value != null) { @SuppressWarnings("unchecked") final Collection<Pair<String, String>> val = (Collection<Pair<String, String>>) value; helper.putString(option.getName(), val.toString()); } else { helper.remove(option.getName()); } } } helper.flush(); } public void load() { options.clear(); for (final CompilerOption option : CompilerOption.ALL_OPTIONS) { final String value = helper.getString(option.getName(), null); if (option instanceof BooleanOption) { options.put(option, value != null ? Boolean.parseBoolean(value) : ((BooleanOption) option).getDefaultValue()); } else if (option instanceof PathsOption) { if (!Strings.isNullOrEmpty(value)) { options.put(option, PathsOption.fromString(value)); } } else if (option instanceof ModuleOption) { if (!Strings.isNullOrEmpty(value)) { options.put(option, value); } } else if (option instanceof RawOption) { if (!Strings.isNullOrEmpty(value)) { options.put(option, value); } } else { if (value != null) { final String[] str = value.split(","); options.put(option, new Pair<>(str[0], str[1])); } } } options.put(CompilerOption.DEBUG_INFO, true); } @SuppressWarnings("unchecked") public OtpErlangList export() { final List<OtpErlangObject> result = new ArrayList<>(); for (final CompilerOption option : CompilerOption.ALL_OPTIONS) { final Object optionValue = options.get(option); if (optionValue != null) { if (option instanceof BooleanOption) { final OtpErlangObject val = ((BooleanOption) option) .toTerm(((Boolean) optionValue).booleanValue()); if (val != null) { result.add(val); } } else if (option instanceof PathsOption) { final Iterable<String> value = (Iterable<String>) optionValue; final OtpErlangList val = (OtpErlangList) ((PathsOption) option) .toTerm(value); for (final OtpErlangObject inc : val.elements()) { result.add(inc); } } else if (option instanceof ModuleOption) { final String value = (String) optionValue; final OtpErlangObject val = ((ModuleOption) option).toTerm(value); result.add(val); } else if (option instanceof RawOption) { final String value = (String) optionValue; final OtpErlangList val = (OtpErlangList) ((RawOption) option) .toTerm(value); for (final OtpErlangObject item : val.elements()) { result.add(item); } } else { try { final OtpErlangList val = ((DefineOption) option) .toTerm((List<Pair<String, String>>) optionValue); if (val != null) { result.addAll(Lists.newArrayList(val.elements())); } } catch (final OtpParserException e) { ErlLogger.warn(e); } } } } final OtpErlangList list = OtpErlang.mkList(result); return list; } @Override public String toString() { return export().toString(); } public void removeAllProjectSpecificSettings() { helper.removeAllAtLowestScope(); } public void removeOption(final CompilerOption opt) { if (opt instanceof WarningOption) { options.put(opt, ((WarningOption) opt).getDefaultValue()); } else { options.remove(opt); } } public void setPathOption(final CompilerOption opt, final Iterable<String> value) { if (value == null || !value.iterator().hasNext()) { removeOption(opt); } else { options.put(opt, value); } } public void setSimpleOption(final CompilerOption opt, final String value0) { final String value = value0.trim(); if (Strings.isNullOrEmpty(value)) { removeOption(opt); } else { options.put(opt, value); } } public void setListOption(final CompilerOption opt, final List<Pair<String, String>> value) { if (value == null || value.isEmpty()) { removeOption(opt); } else { options.put(opt, value); } } public void setListOption(final CompilerOption opt, @SuppressWarnings("unchecked") final Pair<String, String>... values) { if (values == null || values.length == 0) { removeOption(opt); } else { final List<Pair<String, String>> list = Lists.newArrayList(values); setListOption(opt, list); } } public void setBooleanOption(final CompilerOption opt, final boolean selection) { options.put(opt, selection); } public boolean getBooleanOption(final CompilerOption opt) { final Object value = options.get(opt); if (opt instanceof BooleanOption) { return ((Boolean) value).booleanValue(); } return value != null; } @SuppressWarnings("unchecked") public Iterable<String> getPathsOption(final PathsOption option) { return (Iterable<String>) options.get(option); } public String getSimpleOption(final ModuleOption option) { return (String) options.get(option); } public String getSimpleOption(final RawOption option) { return (String) options.get(option); } }