Search in sources :

Example 6 with FaweException

use of com.fastasyncworldedit.core.internal.exception.FaweException in project FastAsyncWorldEdit by IntellectualSites.

the class RegionVisitor method resume.

@Override
public Operation resume(RunContext run) throws WorldEditException {
    // FAWE start > allow chunk preloading
    if (singleQueue != null && Settings.settings().QUEUE.PRELOAD_CHUNK_COUNT > 1) {
        /*
             * The following is done to reduce iteration cost
             *  - Preload chunks just in time
             *  - Only check every 16th block for potential chunk loads
             *  - Stop iteration on exception instead of hasNext
             *  - Do not calculate the stacktrace as it is expensive
             */
        Iterator<? extends BlockVector3> trailIter = iterable.iterator();
        Iterator<? extends BlockVector3> leadIter = iterable.iterator();
        int lastTrailChunkX = Integer.MIN_VALUE;
        int lastTrailChunkZ = Integer.MIN_VALUE;
        int lastLeadChunkX = Integer.MIN_VALUE;
        int lastLeadChunkZ = Integer.MIN_VALUE;
        int loadingTarget = Settings.settings().QUEUE.PRELOAD_CHUNK_COUNT;
        while (trailIter.hasNext()) {
            BlockVector3 pt = trailIter.next();
            apply(pt);
            int cx = pt.getBlockX() >> 4;
            int cz = pt.getBlockZ() >> 4;
            if (cx != lastTrailChunkX || cz != lastTrailChunkZ) {
                lastTrailChunkX = cx;
                lastTrailChunkZ = cz;
                int amount;
                if (lastLeadChunkX == Integer.MIN_VALUE) {
                    lastLeadChunkX = cx;
                    lastLeadChunkZ = cz;
                    amount = loadingTarget;
                } else {
                    amount = 1;
                }
                try {
                    lead: for (int count = 0; count < amount; ) {
                        BlockVector3 v = leadIter.next();
                        int vcx = v.getBlockX() >> 4;
                        int vcz = v.getBlockZ() >> 4;
                        if (vcx != lastLeadChunkX || vcz != lastLeadChunkZ) {
                            lastLeadChunkX = vcx;
                            lastLeadChunkZ = vcz;
                            singleQueue.addChunkLoad(vcx, vcz);
                            count++;
                        }
                        // Skip the next 15 blocks
                        for (int i = 0; i < 16; i++) {
                            if (!leadIter.hasNext()) {
                                break lead;
                            }
                            leadIter.next();
                        }
                    }
                } catch (FaweException e) {
                    // Likely to be a low memory or cancellation exception.
                    throw new RuntimeException(e);
                } catch (Throwable ignored) {
                // Ignore as it is likely not something too important, and we can continue with the operation
                }
            }
            for (int i = 0; i < 16; i++) {
                if (!trailIter.hasNext()) {
                    return null;
                }
                apply(trailIter.next());
            }
        }
    } else {
        for (BlockVector3 pt : region) {
            apply(pt);
        }
    }
    // FAWE end
    return null;
}
Also used : FaweException(com.fastasyncworldedit.core.internal.exception.FaweException) BlockVector3(com.sk89q.worldedit.math.BlockVector3)

Example 7 with FaweException

use of com.fastasyncworldedit.core.internal.exception.FaweException in project FastAsyncWorldEdit by IntellectualSites.

the class ParallelQueueExtent method apply.

@Override
@SuppressWarnings("rawtypes")
public <T extends Filter> T apply(Region region, T filter, boolean full) {
    // The chunks positions to iterate over
    final Set<BlockVector2> chunks = region.getChunks();
    final Iterator<BlockVector2> chunksIter = chunks.iterator();
    // Get a pool, to operate on the chunks in parallel
    final int size = Math.min(chunks.size(), Settings.settings().QUEUE.PARALLEL_THREADS);
    if (size <= 1 && chunksIter.hasNext()) {
        BlockVector2 pos = chunksIter.next();
        getExtent().apply(null, filter, region, pos.getX(), pos.getZ(), full);
    } else {
        final ForkJoinTask[] tasks = IntStream.range(0, size).mapToObj(i -> handler.submit(() -> {
            try {
                final Filter newFilter = filter.fork();
                // Create a chunk that we will reuse/reset for each operation
                final SingleThreadQueueExtent queue = (SingleThreadQueueExtent) getNewQueue();
                queue.setFastMode(fastmode);
                queue.setFaweExceptionArray(faweExceptionReasonsUsed);
                synchronized (queue) {
                    try {
                        ChunkFilterBlock block = null;
                        while (true) {
                            // Get the next chunk posWeakChunk
                            final int chunkX;
                            final int chunkZ;
                            synchronized (chunksIter) {
                                if (!chunksIter.hasNext()) {
                                    break;
                                }
                                final BlockVector2 pos = chunksIter.next();
                                chunkX = pos.getX();
                                chunkZ = pos.getZ();
                            }
                            block = queue.apply(block, newFilter, region, chunkX, chunkZ, full);
                        }
                        queue.flush();
                    } catch (Throwable t) {
                        if (t instanceof FaweException) {
                            Fawe.handleFaweException(faweExceptionReasonsUsed, (FaweException) t, LOGGER);
                        } else if (t.getCause() instanceof FaweException) {
                            Fawe.handleFaweException(faweExceptionReasonsUsed, (FaweException) t.getCause(), LOGGER);
                        } else {
                            throw t;
                        }
                    }
                }
            } catch (Throwable e) {
                String message = e.getMessage();
                int hash = message.hashCode();
                if (lastException != hash) {
                    lastException = hash;
                    exceptionCount = 0;
                    LOGGER.catching(e);
                } else if (exceptionCount < Settings.settings().QUEUE.PARALLEL_THREADS) {
                    exceptionCount++;
                    LOGGER.warn(message);
                }
            }
        })).toArray(ForkJoinTask[]::new);
        // Join filters
        for (ForkJoinTask task : tasks) {
            if (task != null) {
                task.quietlyJoin();
            }
        }
        filter.join();
    }
    return filter;
}
Also used : IntStream(java.util.stream.IntStream) BlockVector2(com.sk89q.worldedit.math.BlockVector2) BlockVector3(com.sk89q.worldedit.math.BlockVector3) World(com.sk89q.worldedit.world.World) ChunkFilterBlock(com.fastasyncworldedit.core.extent.filter.block.ChunkFilterBlock) Fawe(com.fastasyncworldedit.core.Fawe) LinkedFilter(com.fastasyncworldedit.core.extent.filter.LinkedFilter) Filter(com.fastasyncworldedit.core.queue.Filter) DistrFilter(com.fastasyncworldedit.core.extent.filter.DistrFilter) BlockMask(com.sk89q.worldedit.function.mask.BlockMask) FaweException(com.fastasyncworldedit.core.internal.exception.FaweException) PassthroughExtent(com.fastasyncworldedit.core.extent.PassthroughExtent) BlockPattern(com.sk89q.worldedit.function.pattern.BlockPattern) Region(com.sk89q.worldedit.regions.Region) BlockStateHolder(com.sk89q.worldedit.world.block.BlockStateHolder) ExistingBlockMask(com.sk89q.worldedit.function.mask.ExistingBlockMask) ForkJoinTask(java.util.concurrent.ForkJoinTask) Clipboard(com.sk89q.worldedit.extent.clipboard.Clipboard) LogManagerCompat(com.sk89q.worldedit.internal.util.LogManagerCompat) BlockType(com.sk89q.worldedit.world.block.BlockType) Iterator(java.util.Iterator) MaxChangedBlocksException(com.sk89q.worldedit.MaxChangedBlocksException) Set(java.util.Set) CountFilter(com.fastasyncworldedit.core.extent.filter.CountFilter) Settings(com.fastasyncworldedit.core.configuration.Settings) NullExtent(com.fastasyncworldedit.core.extent.NullExtent) BlockMaskBuilder(com.fastasyncworldedit.core.function.mask.BlockMaskBuilder) IQueueChunk(com.fastasyncworldedit.core.queue.IQueueChunk) MultiBatchProcessor(com.fastasyncworldedit.core.extent.processor.MultiBatchProcessor) List(java.util.List) Logger(org.apache.logging.log4j.Logger) BatchProcessorHolder(com.fastasyncworldedit.core.extent.processor.BatchProcessorHolder) FaweCache(com.fastasyncworldedit.core.FaweCache) Countable(com.sk89q.worldedit.util.Countable) BaseBlock(com.sk89q.worldedit.world.block.BaseBlock) Mask(com.sk89q.worldedit.function.mask.Mask) BlockState(com.sk89q.worldedit.world.block.BlockState) WorldCopyClipboard(com.fastasyncworldedit.core.extent.clipboard.WorldCopyClipboard) IQueueExtent(com.fastasyncworldedit.core.queue.IQueueExtent) Pattern(com.sk89q.worldedit.function.pattern.Pattern) FaweException(com.fastasyncworldedit.core.internal.exception.FaweException) ForkJoinTask(java.util.concurrent.ForkJoinTask) BlockVector2(com.sk89q.worldedit.math.BlockVector2) ChunkFilterBlock(com.fastasyncworldedit.core.extent.filter.block.ChunkFilterBlock) LinkedFilter(com.fastasyncworldedit.core.extent.filter.LinkedFilter) Filter(com.fastasyncworldedit.core.queue.Filter) DistrFilter(com.fastasyncworldedit.core.extent.filter.DistrFilter) CountFilter(com.fastasyncworldedit.core.extent.filter.CountFilter)

Example 8 with FaweException

use of com.fastasyncworldedit.core.internal.exception.FaweException in project FastAsyncWorldEdit by IntellectualSites.

the class SingleThreadQueueExtent method pollSubmissions.

private void pollSubmissions(int targetSize, boolean aggressive) {
    final int overflow = submissions.size() - targetSize;
    if (aggressive) {
        if (targetSize == 0) {
            while (!submissions.isEmpty()) {
                iterateSubmissions();
            }
        }
        for (int i = 0; i < overflow; i++) {
            iterateSubmissions();
        }
    } else {
        for (int i = 0; i < overflow; i++) {
            Future next = submissions.peek();
            while (next != null) {
                if (next.isDone()) {
                    Future after = null;
                    try {
                        after = (Future) next.get();
                    } catch (FaweException e) {
                        Fawe.handleFaweException(faweExceptionReasonsUsed, e, LOGGER);
                    } catch (ExecutionException | InterruptedException e) {
                        if (e.getCause() instanceof FaweException) {
                            Fawe.handleFaweException(faweExceptionReasonsUsed, (FaweException) e.getCause(), LOGGER);
                        } else {
                            String message = e.getMessage();
                            int hash = message.hashCode();
                            if (lastException != hash) {
                                lastException = hash;
                                exceptionCount = 0;
                                LOGGER.catching(e);
                            } else if (exceptionCount < Settings.settings().QUEUE.PARALLEL_THREADS) {
                                exceptionCount++;
                                LOGGER.warn(message);
                            }
                        }
                    } finally {
                        /*
                             * If the execution failed, namely next.get() threw an exception,
                             * we don't want to process that Future again. Instead, we just drop
                             * it and set it to null, otherwise to the returned next Future.
                             */
                        next = after;
                    }
                } else {
                    return;
                }
            }
            submissions.poll();
        }
    }
}
Also used : FaweException(com.fastasyncworldedit.core.internal.exception.FaweException) Future(java.util.concurrent.Future) ExecutionException(java.util.concurrent.ExecutionException)

Example 9 with FaweException

use of com.fastasyncworldedit.core.internal.exception.FaweException in project FastAsyncWorldEdit by IntellectualSites.

the class SingleThreadQueueExtent method iterateSubmissions.

private void iterateSubmissions() {
    Future first = submissions.poll();
    try {
        while (first != null) {
            first = (Future) first.get();
        }
    } catch (FaweException e) {
        Fawe.handleFaweException(faweExceptionReasonsUsed, e, LOGGER);
    } catch (ExecutionException | InterruptedException e) {
        if (e.getCause() instanceof FaweException) {
            Fawe.handleFaweException(faweExceptionReasonsUsed, (FaweException) e.getCause(), LOGGER);
        } else {
            String message = e.getMessage();
            int hash = message.hashCode();
            if (lastException != hash) {
                lastException = hash;
                exceptionCount = 0;
                LOGGER.catching(e);
            } else if (exceptionCount < Settings.settings().QUEUE.PARALLEL_THREADS) {
                exceptionCount++;
                LOGGER.warn(message);
            }
        }
    }
}
Also used : FaweException(com.fastasyncworldedit.core.internal.exception.FaweException) Future(java.util.concurrent.Future) ExecutionException(java.util.concurrent.ExecutionException)

Aggregations

FaweException (com.fastasyncworldedit.core.internal.exception.FaweException)9 BlockVector3 (com.sk89q.worldedit.math.BlockVector3)3 NullExtent (com.fastasyncworldedit.core.extent.NullExtent)2 Region (com.sk89q.worldedit.regions.Region)2 List (java.util.List)2 ExecutionException (java.util.concurrent.ExecutionException)2 Future (java.util.concurrent.Future)2 Fawe (com.fastasyncworldedit.core.Fawe)1 FaweCache (com.fastasyncworldedit.core.FaweCache)1 Settings (com.fastasyncworldedit.core.configuration.Settings)1 HistoryExtent (com.fastasyncworldedit.core.extent.HistoryExtent)1 PassthroughExtent (com.fastasyncworldedit.core.extent.PassthroughExtent)1 WorldCopyClipboard (com.fastasyncworldedit.core.extent.clipboard.WorldCopyClipboard)1 CountFilter (com.fastasyncworldedit.core.extent.filter.CountFilter)1 DistrFilter (com.fastasyncworldedit.core.extent.filter.DistrFilter)1 LinkedFilter (com.fastasyncworldedit.core.extent.filter.LinkedFilter)1 ChunkFilterBlock (com.fastasyncworldedit.core.extent.filter.block.ChunkFilterBlock)1 ExtentFilterBlock (com.fastasyncworldedit.core.extent.filter.block.ExtentFilterBlock)1 BatchProcessorHolder (com.fastasyncworldedit.core.extent.processor.BatchProcessorHolder)1 MultiBatchProcessor (com.fastasyncworldedit.core.extent.processor.MultiBatchProcessor)1