diff options
author | Benoit Lamarche <benoitlamarche@google.com> | 2014-10-03 13:14:31 +0000 |
---|---|---|
committer | Gerrit Code Review <noreply-gerritcodereview@google.com> | 2014-10-03 13:14:31 +0000 |
commit | 742c8733779a87b6152e4a335c2ff35c1d99d7a3 (patch) | |
tree | cb059db76a49c7929bbabf00dce65748480d01da | |
parent | 2776adacdc0a7db79ae6d1b881e5f70e68c876c0 (diff) | |
parent | 16ecbd88902f14d28c0ac4f75b54ce9fb69c392b (diff) | |
download | toolchain_jack-742c8733779a87b6152e4a335c2ff35c1d99d7a3.zip toolchain_jack-742c8733779a87b6152e4a335c2ff35c1d99d7a3.tar.gz toolchain_jack-742c8733779a87b6152e4a335c2ff35c1d99d7a3.tar.bz2 |
Merge "Add a DirectDir that can be written to in parallel" into ub-jack
10 files changed, 223 insertions, 115 deletions
diff --git a/jack/src/com/android/jack/Options.java b/jack/src/com/android/jack/Options.java index 697a103..40cb053 100644 --- a/jack/src/com/android/jack/Options.java +++ b/jack/src/com/android/jack/Options.java @@ -36,8 +36,9 @@ import com.android.jack.util.FileUtils; import com.android.jack.util.filter.AllMethods; import com.android.jack.util.filter.Filter; import com.android.sched.util.RunnableHooks; +import com.android.sched.util.codec.DirectDirOutputVDirCodec; import com.android.sched.util.codec.InputOutputVDirCodec; -import com.android.sched.util.codec.OutputVDirCodec; +import com.android.sched.util.codec.ZipOutputVDirCodec; import com.android.sched.util.config.Config; import com.android.sched.util.config.ConfigPrinterFactory; import com.android.sched.util.config.ConfigurationException; @@ -116,13 +117,13 @@ public class Options { @Nonnull public static final PropertyId<OutputVDir> JACK_FILE_OUTPUT_ZIP = PropertyId.create( "jack.jackfile.output.zip", "Output zip archive for jack files", - new OutputVDirCodec(Existence.MAY_EXIST, Container.ZIP)).requiredIf( + new ZipOutputVDirCodec(Existence.MAY_EXIST)).requiredIf( GENERATE_JACK_FILE.getValue().isTrue().and(JACK_OUTPUT_CONTAINER_TYPE.is(Container.ZIP))); @Nonnull public static final PropertyId<OutputVDir> JACK_FILE_OUTPUT_DIR = PropertyId.create( "jack.jackfile.output.dir", "Output folder for jack files", - new OutputVDirCodec(Existence.MAY_EXIST, Container.DIR)).requiredIf( + new DirectDirOutputVDirCodec(Existence.MAY_EXIST)).requiredIf( GENERATE_JACK_FILE.getValue().isTrue().and(JACK_OUTPUT_CONTAINER_TYPE.is(Container.DIR))); @Nonnull @@ -133,13 +134,13 @@ public class Options { @Nonnull public static final PropertyId<OutputVDir> DEX_OUTPUT_DIR = PropertyId.create( "jack.dex.output.dir", "Output folder for dex", - new OutputVDirCodec(Existence.MUST_EXIST, Container.DIR)).requiredIf(DEX_OUTPUT_CONTAINER_TYPE - .is(Container.DIR)); + new DirectDirOutputVDirCodec(Existence.MUST_EXIST)).requiredIf( + DEX_OUTPUT_CONTAINER_TYPE.is(Container.DIR)); @Nonnull public static final PropertyId<OutputVDir> DEX_OUTPUT_ZIP = PropertyId.create( "jack.dex.output.zip", "Output zip archive for dex", - new OutputVDirCodec(Existence.MAY_EXIST, Container.ZIP)).requiredIf( + new ZipOutputVDirCodec(Existence.MAY_EXIST)).requiredIf( DEX_OUTPUT_CONTAINER_TYPE.is(Container.ZIP)); @Nonnull diff --git a/jack/src/com/android/jack/experimental/incremental/JackIncremental.java b/jack/src/com/android/jack/experimental/incremental/JackIncremental.java index 441a4ab..fa266c7 100644 --- a/jack/src/com/android/jack/experimental/incremental/JackIncremental.java +++ b/jack/src/com/android/jack/experimental/incremental/JackIncremental.java @@ -39,7 +39,7 @@ import com.android.sched.scheduler.IllegalRequestException; import com.android.sched.scheduler.PlanBuilder; import com.android.sched.scheduler.Request; import com.android.sched.util.UnrecoverableException; -import com.android.sched.util.codec.OutputVDirCodec; +import com.android.sched.util.codec.DirectDirOutputVDirCodec; import com.android.sched.util.config.ChainedException; import com.android.sched.util.config.ConfigurationException; import com.android.sched.util.config.HasKeyId; @@ -48,7 +48,6 @@ import com.android.sched.util.config.id.BooleanPropertyId; import com.android.sched.util.config.id.PropertyId; import com.android.sched.util.file.FileOrDirectory.Existence; import com.android.sched.util.log.LoggerFactory; -import com.android.sched.vfs.Container; import com.android.sched.vfs.OutputVDir; import com.android.sched.vfs.VPath; @@ -80,7 +79,7 @@ public class JackIncremental extends CommandLine { @Nonnull public static final PropertyId<OutputVDir> COMPILER_STATE_OUTPUT_DIR = PropertyId.create( "jack.experimental.compilerstate.output.dir", "Compiler state output folder", - new OutputVDirCodec(Existence.MAY_EXIST, Container.DIR)).requiredIf( + new DirectDirOutputVDirCodec(Existence.MAY_EXIST)).requiredIf( GENERATE_COMPILER_STATE.getValue().isTrue()); @CheckForNull diff --git a/sched/src/com/android/sched/util/codec/DirectDirOutputVDirCodec.java b/sched/src/com/android/sched/util/codec/DirectDirOutputVDirCodec.java new file mode 100644 index 0000000..1db163e --- /dev/null +++ b/sched/src/com/android/sched/util/codec/DirectDirOutputVDirCodec.java @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * 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.android.sched.util.codec; + +import com.android.sched.util.file.Directory; +import com.android.sched.util.file.FileOrDirectory.Existence; +import com.android.sched.util.file.FileOrDirectory.Permission; +import com.android.sched.util.log.LoggerFactory; +import com.android.sched.vfs.DirectDir; +import com.android.sched.vfs.ParallelOutputVDir; + +import java.io.IOException; +import java.util.logging.Logger; + +import javax.annotation.Nonnull; + +/** + * This {@link StringCodec} is used to create an instance of {@link ParallelOutputVDir} backed by + * a filesystem directory. + */ +public class DirectDirOutputVDirCodec extends OutputVDirCodec { + + @Nonnull + private final Logger logger = LoggerFactory.getLogger(); + + public DirectDirOutputVDirCodec(@Nonnull Existence existence) { + super(existence); + } + + @Override + @Nonnull + public String getUsage() { + StringBuilderAppender sb = new StringBuilderAppender(", "); + + sb.append("a path to an output directory (must "); + + sb.append(existence == Existence.MUST_EXIST, "exist"); + sb.append(existence == Existence.NOT_EXIST, "not exist"); + + sb.append((permissions & Permission.READ) != 0, "be readable"); + sb.append((permissions & Permission.WRITE) != 0, "be writable"); + + sb.append(")"); + + return sb.toString(); + } + + @Override + @Nonnull + public ParallelOutputVDir checkString(@Nonnull CodecContext context, @Nonnull final String string) + throws ParsingException { + try { + return new DirectDir( + new Directory(string, context.getRunnableHooks(), existence, permissions, change)); + } catch (IOException e) { + throw new ParsingException(e.getMessage(), e); + } + } + +} diff --git a/sched/src/com/android/sched/util/codec/OutputVDirCodec.java b/sched/src/com/android/sched/util/codec/OutputVDirCodec.java index f41be15..6acf538 100644 --- a/sched/src/com/android/sched/util/codec/OutputVDirCodec.java +++ b/sched/src/com/android/sched/util/codec/OutputVDirCodec.java @@ -17,41 +17,21 @@ package com.android.sched.util.codec; -import com.android.sched.util.RunnableHooks; import com.android.sched.util.config.ConfigurationError; -import com.android.sched.util.file.Directory; import com.android.sched.util.file.FileOrDirectory.ChangePermission; import com.android.sched.util.file.FileOrDirectory.Existence; import com.android.sched.util.file.FileOrDirectory.Permission; -import com.android.sched.util.file.OutputZipFile; -import com.android.sched.util.log.LoggerFactory; -import com.android.sched.vfs.Container; -import com.android.sched.vfs.DirectDir; import com.android.sched.vfs.OutputVDir; -import com.android.sched.vfs.OutputZipRootVDir; - -import java.io.IOException; -import java.util.logging.Level; -import java.util.logging.Logger; import javax.annotation.Nonnull; /** * This {@link StringCodec} is used to create an instance of {@link OutputVDir}. */ -public class OutputVDirCodec extends FileOrDirCodec - implements StringCodec<OutputVDir> { - - @Nonnull - private final Logger logger = LoggerFactory.getLogger(); +public abstract class OutputVDirCodec extends FileOrDirCodec implements StringCodec<OutputVDir> { - @Nonnull - private final Container type; - - public OutputVDirCodec(@Nonnull Existence existence, @Nonnull Container type) { + public OutputVDirCodec(@Nonnull Existence existence) { super(existence, Permission.READ | Permission.WRITE); - - this.type = type; } @Nonnull @@ -69,68 +49,6 @@ public class OutputVDirCodec extends FileOrDirCodec } @Override - @Nonnull - public String getUsage() { - StringBuilderAppender sb = new StringBuilderAppender(", "); - - String containerName; - switch (type) { - case DIR: - containerName = "an output directory"; - break; - case ZIP: - containerName = "a zip archive"; - break; - default: - throw new AssertionError(); - } - - sb.append("a path to " + containerName + " (must "); - - sb.append(existence == Existence.MUST_EXIST, "exist"); - sb.append(existence == Existence.NOT_EXIST, "not exist"); - - sb.append((permissions & Permission.READ) != 0, "be readable"); - sb.append((permissions & Permission.WRITE) != 0, "be writable"); - - sb.append(")"); - - return sb.toString(); - } - - @Override - @Nonnull - public OutputVDir checkString(@Nonnull CodecContext context, @Nonnull final String string) - throws ParsingException { - OutputVDir dir = null; - RunnableHooks hooks = context.getRunnableHooks(); - try { - if (type == Container.DIR) { - dir = new DirectDir(new Directory(string, hooks, existence, permissions, change)); - } else if (type == Container.ZIP) { - final OutputZipRootVDir vDir = - new OutputZipRootVDir(new OutputZipFile(string, hooks, existence, change)); - assert hooks != null; - hooks.addHook(new Runnable() { - @Override - public void run() { - try { - vDir.close(); - } catch (IOException e) { - logger.log(Level.WARNING, "Failed to close zip for '" + string + "'.", e); - } - } - }); - dir = vDir; - } - assert dir != null; - return dir; - } catch (IOException e) { - throw new ParsingException(e.getMessage(), e); - } - } - - @Override public void checkValue(@Nonnull CodecContext context, @Nonnull OutputVDir dir) { } diff --git a/sched/src/com/android/sched/util/codec/ZipOutputVDirCodec.java b/sched/src/com/android/sched/util/codec/ZipOutputVDirCodec.java new file mode 100644 index 0000000..d64f40f --- /dev/null +++ b/sched/src/com/android/sched/util/codec/ZipOutputVDirCodec.java @@ -0,0 +1,88 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * 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.android.sched.util.codec; + +import com.android.sched.util.RunnableHooks; +import com.android.sched.util.file.FileOrDirectory.Existence; +import com.android.sched.util.file.FileOrDirectory.Permission; +import com.android.sched.util.file.OutputZipFile; +import com.android.sched.util.log.LoggerFactory; +import com.android.sched.vfs.OutputZipRootVDir; +import com.android.sched.vfs.SequentialOutputVDir; + +import java.io.IOException; +import java.util.logging.Level; +import java.util.logging.Logger; + +import javax.annotation.Nonnull; + +/** + * This {@link StringCodec} is used to create an instance of {@link SequentialOutputVDir} backed by + * a zip archive. + */ +public class ZipOutputVDirCodec extends OutputVDirCodec { + + @Nonnull + private final Logger logger = LoggerFactory.getLogger(); + + public ZipOutputVDirCodec(@Nonnull Existence existence) { + super(existence); + } + + @Override + @Nonnull + public String getUsage() { + StringBuilderAppender sb = new StringBuilderAppender(", "); + + sb.append("a path to a zip archive (must "); + + sb.append(existence == Existence.MUST_EXIST, "exist"); + sb.append(existence == Existence.NOT_EXIST, "not exist"); + + sb.append((permissions & Permission.READ) != 0, "be readable"); + sb.append((permissions & Permission.WRITE) != 0, "be writable"); + + sb.append(")"); + + return sb.toString(); + } + + @Override + @Nonnull + public SequentialOutputVDir checkString(@Nonnull CodecContext context, + @Nonnull final String string) throws ParsingException { + RunnableHooks hooks = context.getRunnableHooks(); + try { + final OutputZipRootVDir vDir = + new OutputZipRootVDir(new OutputZipFile(string, hooks, existence, change)); + assert hooks != null; + hooks.addHook(new Runnable() { + @Override + public void run() { + try { + vDir.close(); + } catch (IOException e) { + logger.log(Level.WARNING, "Failed to close zip for '" + string + "'.", e); + } + } + }); + return vDir; + } catch (IOException e) { + throw new ParsingException(e.getMessage(), e); + } + } +} diff --git a/sched/src/com/android/sched/vfs/DirectDir.java b/sched/src/com/android/sched/vfs/DirectDir.java index 9dcf766..f42531a 100644 --- a/sched/src/com/android/sched/vfs/DirectDir.java +++ b/sched/src/com/android/sched/vfs/DirectDir.java @@ -33,9 +33,9 @@ import javax.annotation.CheckForNull; import javax.annotation.Nonnull; /** - * Directory in the file system. + * A VFS directory backed by a real filesystem directory. */ -public class DirectDir extends SequentialOutputVDir implements InputRootVDir, InputOutputVDir { +public class DirectDir extends AbstractVElement implements InputRootVDir, InputOutputVDir { @Nonnull private final File dir; @@ -80,21 +80,21 @@ public class DirectDir extends SequentialOutputVDir implements InputRootVDir, In return Collections.emptyList(); } - list = new ArrayList<InputVElement>(subs.length); + ArrayList<InputVElement> localList = new ArrayList<InputVElement>(subs.length); for (File sub : subs) { try { if (sub.isFile()) { - list.add(new DirectFile(sub, vfsRoot)); + localList.add(new DirectFile(sub, vfsRoot)); } else { - list.add(new DirectDir(sub, vfsRoot)); + localList.add(new DirectDir(sub, vfsRoot)); } } catch (NotFileOrDirectoryException e) { throw new ConcurrentIOException(e); } } + list = localList; } - assert list != null; return list; } diff --git a/sched/src/com/android/sched/vfs/InputOutputVDir.java b/sched/src/com/android/sched/vfs/InputOutputVDir.java index 265d0b2..1cd8f7f 100644 --- a/sched/src/com/android/sched/vfs/InputOutputVDir.java +++ b/sched/src/com/android/sched/vfs/InputOutputVDir.java @@ -19,6 +19,6 @@ package com.android.sched.vfs; /** * Virtual directory to be read or written to. */ -public interface InputOutputVDir extends InputVDir, OutputVDir { +public interface InputOutputVDir extends InputVDir, ParallelOutputVDir { } diff --git a/sched/src/com/android/sched/vfs/OutputZipRootVDir.java b/sched/src/com/android/sched/vfs/OutputZipRootVDir.java index 1d5e442..6260e01 100644 --- a/sched/src/com/android/sched/vfs/OutputZipRootVDir.java +++ b/sched/src/com/android/sched/vfs/OutputZipRootVDir.java @@ -23,6 +23,7 @@ import com.android.sched.util.location.ZipLocation; import java.io.Closeable; import java.io.IOException; import java.util.HashMap; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.zip.ZipEntry; import java.util.zip.ZipOutputStream; @@ -31,7 +32,7 @@ import javax.annotation.Nonnull; /** * A root {@link OutputVDir} backed by a zip archive. */ -public class OutputZipRootVDir extends SequentialOutputVDir implements OutputVDir, Closeable { +public class OutputZipRootVDir extends AbstractVElement implements SequentialOutputVDir, Closeable { @Nonnull protected final HashMap<String, VElement> subs = new HashMap<String, VElement>(); @@ -43,6 +44,8 @@ public class OutputZipRootVDir extends SequentialOutputVDir implements OutputVDi private final String fileName; @Nonnull private final OutputZipFile zipFile; + @Nonnull + private final AtomicBoolean lastVFileOpen = new AtomicBoolean(false); public OutputZipRootVDir(@Nonnull OutputZipFile zipFile) { fileName = zipFile.getName(); @@ -52,6 +55,17 @@ public class OutputZipRootVDir extends SequentialOutputVDir implements OutputVDi } @Override + public void notifyVFileClosed() { + boolean previousState = lastVFileOpen.getAndSet(false); + assert previousState; + } + + @Override + public boolean notifyVFileOpenAndReturnPreviousState() { + return lastVFileOpen.getAndSet(true); + } + + @Override @Nonnull public Location getLocation() { return location; diff --git a/sched/src/com/android/sched/vfs/ParallelOutputVDir.java b/sched/src/com/android/sched/vfs/ParallelOutputVDir.java new file mode 100644 index 0000000..6892eed --- /dev/null +++ b/sched/src/com/android/sched/vfs/ParallelOutputVDir.java @@ -0,0 +1,25 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * 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.android.sched.vfs; + +/** + * {@link OutputVDir} that contains {@link OutputVFile}s that can be opened and written to in + * parallel. + */ +public interface ParallelOutputVDir extends OutputVDir { + +} diff --git a/sched/src/com/android/sched/vfs/SequentialOutputVDir.java b/sched/src/com/android/sched/vfs/SequentialOutputVDir.java index 82f33be..daafb8b 100644 --- a/sched/src/com/android/sched/vfs/SequentialOutputVDir.java +++ b/sched/src/com/android/sched/vfs/SequentialOutputVDir.java @@ -16,27 +16,16 @@ package com.android.sched.vfs; -import java.util.concurrent.atomic.AtomicBoolean; - -import javax.annotation.Nonnull; /** * {@link OutputVDir} that contains {@link OutputVFile}s that must be written to and closed * sequentially. */ -abstract class SequentialOutputVDir extends AbstractVElement implements OutputVDir { - - @Nonnull - private final AtomicBoolean lastVFileOpen = new AtomicBoolean(false); +public interface SequentialOutputVDir extends OutputVDir { - void notifyVFileClosed() { - boolean previousState = lastVFileOpen.getAndSet(false); - assert previousState; - } + void notifyVFileClosed(); - boolean notifyVFileOpenAndReturnPreviousState() { - return lastVFileOpen.getAndSet(true); - } + boolean notifyVFileOpenAndReturnPreviousState(); } |