blob: d5a9274893e7737de9255563851ebba7fd208bf4 [file] [log] [blame]
// Copyright (c) 2017, the R8 project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
package com.android.tools.r8.utils;
import com.android.tools.r8.CompilationException;
import com.android.tools.r8.CompilationFailedException;
import com.android.tools.r8.DiagnosticsHandler;
import com.android.tools.r8.ResourceException;
import com.android.tools.r8.StringConsumer;
import com.android.tools.r8.errors.CompilationError;
import java.io.IOException;
import java.util.function.Consumer;
public abstract class ExceptionUtils {
public static final int STATUS_ERROR = 1;
public static void withConsumeResourceHandler(
Reporter reporter, StringConsumer consumer, String data) {
withConsumeResourceHandler(reporter, handler -> consumer.accept(data, handler));
}
public static void withConsumeResourceHandler(
Reporter reporter, Consumer<DiagnosticsHandler> consumer) {
// Unchecked exceptions simply propagate out, aborting the compilation forcefully.
consumer.accept(reporter);
// Fail fast for now. We might consider delaying failure since consumer failure does not affect
// the compilation. We might need to be careful to correctly identify errors so as to exit
// compilation with an error code.
reporter.failIfPendingErrors();
}
public interface CompileAction {
void run() throws IOException, CompilationException, CompilationError, ResourceException;
}
private enum Compiler {
D8,
R8;
}
public static void withD8CompilationHandler(Reporter reporter, CompileAction action)
throws CompilationFailedException {
withCompilationHandler(reporter, action, Compiler.D8);
}
public static void withR8CompilationHandler(Reporter reporter, CompileAction action)
throws CompilationFailedException {
withCompilationHandler(reporter, action, Compiler.R8);
}
public static void withCompilationHandler(
Reporter reporter, CompileAction action, Compiler compiler)
throws CompilationFailedException {
try {
try {
action.run();
} catch (IOException e) {
throw reporter.fatalError(new IOExceptionDiagnostic(e));
} catch (CompilationException e) {
throw reporter.fatalError(
new StringDiagnostic(
compiler == Compiler.D8 ? e.getMessageForD8() : e.getMessageForR8()),
e);
} catch (CompilationError e) {
throw reporter.fatalError(e);
} catch (ResourceException e) {
throw reporter.fatalError(
e.getCause() instanceof IOException
? new IOExceptionDiagnostic((IOException) e.getCause(), e.getOrigin())
: new StringDiagnostic(e.getMessage(), e.getOrigin()));
}
reporter.failIfPendingErrors();
} catch (AbortException e) {
throw new CompilationFailedException(e);
}
}
public interface MainAction {
void run() throws CompilationFailedException;
}
public static void withMainProgramHandler(MainAction action) {
try {
action.run();
} catch (CompilationFailedException | AbortException e) {
// Detail of the errors were already reported
System.err.println("Compilation failed");
System.exit(STATUS_ERROR);
} catch (RuntimeException e) {
System.err.println("Compilation failed with an internal error.");
Throwable cause = e.getCause() == null ? e : e.getCause();
cause.printStackTrace();
System.exit(STATUS_ERROR);
}
}
}