// Copyright 2014 The Bazel Authors. All rights reserved. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. package com.google.devtools.build.lib.analysis.config; import com.google.devtools.build.lib.cmdline.Label; import com.google.devtools.build.lib.cmdline.LabelSyntaxException; import com.google.devtools.build.lib.shell.ShellUtils; import com.google.devtools.build.lib.shell.ShellUtils.TokenizationException; import com.google.devtools.common.options.Converter; import com.google.devtools.common.options.OptionsParsingException; import java.util.ArrayList; import java.util.List; import java.util.Objects; /** * --run_under options converter. */ public class RunUnderConverter implements Converter<RunUnder> { @Override public RunUnder convert(final String input) throws OptionsParsingException { final List<String> runUnderList = new ArrayList<>(); try { ShellUtils.tokenize(runUnderList, input); } catch (TokenizationException e) { throw new OptionsParsingException("Not a valid command prefix " + e.getMessage()); } if (runUnderList.isEmpty()) { throw new OptionsParsingException("Empty command"); } final String runUnderCommand = runUnderList.get(0); if (runUnderCommand.startsWith("//")) { try { final Label runUnderLabel = Label.parseAbsolute(runUnderCommand); return new RunUnderLabel(input, runUnderLabel, runUnderList); } catch (LabelSyntaxException e) { throw new OptionsParsingException("Not a valid label " + e.getMessage()); } } else { return new RunUnderCommand(input, runUnderCommand, runUnderList); } } private static final class RunUnderLabel implements RunUnder { private final String input; private final Label runUnderLabel; private final List<String> runUnderList; public RunUnderLabel(String input, Label runUnderLabel, List<String> runUnderList) { this.input = input; this.runUnderLabel = runUnderLabel; this.runUnderList = new ArrayList<>(runUnderList.subList(1, runUnderList.size())); } @Override public String getValue() { return input; } @Override public Label getLabel() { return runUnderLabel; } @Override public String getCommand() { return null; } @Override public List<String> getOptions() { return runUnderList; } @Override public String toString() { return input; } @Override public boolean equals(Object other) { if (this == other) { return true; } else if (other instanceof RunUnderLabel) { RunUnderLabel otherRunUnderLabel = (RunUnderLabel) other; return Objects.equals(input, otherRunUnderLabel.input) && Objects.equals(runUnderLabel, otherRunUnderLabel.runUnderLabel) && Objects.equals(runUnderList, otherRunUnderLabel.runUnderList); } else { return false; } } @Override public int hashCode() { return Objects.hash(input, runUnderLabel, runUnderList); } } private static final class RunUnderCommand implements RunUnder { private final String input; private final String runUnderCommand; private final List<String> runUnderList; public RunUnderCommand(String input, String runUnderCommand, List<String> runUnderList) { this.input = input; this.runUnderCommand = runUnderCommand; this.runUnderList = new ArrayList<>(runUnderList.subList(1, runUnderList.size())); } @Override public String getValue() { return input; } @Override public Label getLabel() { return null; } @Override public String getCommand() { return runUnderCommand; } @Override public List<String> getOptions() { return runUnderList; } @Override public String toString() { return input; } @Override public boolean equals(Object other) { if (this == other) { return true; } else if (other instanceof RunUnderCommand) { RunUnderCommand otherRunUnderCommand = (RunUnderCommand) other; return Objects.equals(input, otherRunUnderCommand.input) && Objects.equals(runUnderCommand, otherRunUnderCommand.runUnderCommand) && Objects.equals(runUnderList, otherRunUnderCommand.runUnderList); } else { return false; } } @Override public int hashCode() { return Objects.hash(input, runUnderCommand, runUnderList); } } @Override public String getTypeDescription() { return "a prefix in front of command"; } }