/*
 * Copyright (c) 2015, 2024, Oracle and/or its affiliates. All rights reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit www.oracle.com if you need additional information or have any
 * questions.
 */

import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.Path2D;
import static java.awt.geom.Path2D.WIND_NON_ZERO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;

/**
 * @test
 * @summary Simple crash rendering test using huge GeneralPaths with the Marlin renderer
 * @run main/othervm -Xmx512m CrashTest
 * @ignore tests that take a long time and consumes 5Gb memory
 * @run main/othervm -Xms4g -Xmx4g CrashTest -slow
*/
public class CrashTest {

    static final boolean SAVE_IMAGE = false;
    static boolean USE_ROUND_CAPS_AND_JOINS = true;

    public static void main(String[] args) {
        boolean runSlowTests = (args.length != 0 && "-slow".equals(args[0]));

        // First display which renderer is tested:
        System.setProperty("sun.java2d.renderer.verbose", "true");

        // try insane image sizes:

        // subpixel coords may overflow:
        // check MAX_VALUE / (8 * 2); overflow may happen due to orientation flag
        // But as it is impossible to allocate an image larger than 2Gb (byte) then
        // it is also impossible to have rowAAChunk larger than 2Gb !

        // Disabled test as it consumes 4GB heap + offheap (2Gb) ie > 6Gb !
        if (runSlowTests) {
            testHugeImage((Integer.MAX_VALUE >> 4) - 100, 16);
        }

        // larger than 23 bits: (RLE)
        testHugeImage(8388608 + 1, 10);

        if (runSlowTests) {
            test(0.1f, false, 0);
            test(0.1f, true, 7f);
        }

        // Exceed 2Gb OffHeap buffer for edges:
        try {
            USE_ROUND_CAPS_AND_JOINS = true;
            test(0.1f, true, 0.1f);
            System.out.println("Exception MISSING.");
        }
        catch (Throwable th) {
            if (th instanceof ArrayIndexOutOfBoundsException) {
                System.out.println("ArrayIndexOutOfBoundsException expected.");
            } else {
                throw new RuntimeException("Unexpected exception", th);
            }
        }
    }

    private static void test(final float lineStroke,
                             final boolean useDashes,
                             final float dashMinLen)
        throws ArrayIndexOutOfBoundsException
    {
        System.out.println("---\n" + "test: "
            + "lineStroke=" + lineStroke
            + ", useDashes=" + useDashes
            +", dashMinLen=" + dashMinLen
        );

        final BasicStroke stroke = createStroke(lineStroke, useDashes, dashMinLen);

        // TODO: test Dasher.firstSegmentsBuffer resizing ?
// array.dasher.firstSegmentsBuffer.d_float[2] sum: 6 avg: 3.0 [3 | 3]
        /*
         // Marlin growable arrays:
         = new StatLong("array.dasher.firstSegmentsBuffer.d_float");
         = new StatLong("array.stroker.polystack.curves.d_float");
         = new StatLong("array.stroker.polystack.curveTypes.d_byte");
         = new StatLong("array.marlincache.rowAAChunk.d_byte");
         = new StatLong("array.marlincache.touchedTile.int");
         = new StatLong("array.renderer.alphaline.int");
         = new StatLong("array.renderer.crossings.int");
         = new StatLong("array.renderer.aux_crossings.int");
         = new StatLong("array.renderer.edgeBuckets.int");
         = new StatLong("array.renderer.edgeBucketCounts.int");
         = new StatLong("array.renderer.edgePtrs.int");
         = new StatLong("array.renderer.aux_edgePtrs.int");
         */
        // size > 8192 (exceed both tile and buckets arrays)
        final int size = 9000;
        System.out.println("image size = " + size);

        final BufferedImage image = new BufferedImage(size, size, BufferedImage.TYPE_INT_ARGB);

        final Graphics2D g2d = (Graphics2D) image.getGraphics();
        try {
            g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);

            g2d.setClip(0, 0, size, size);
            g2d.setBackground(Color.WHITE);
            g2d.clearRect(0, 0, size, size);

            g2d.setStroke(stroke);
            g2d.setColor(Color.BLACK);

            final long start = System.nanoTime();

            paint(g2d, size - 10f);

            final long time = System.nanoTime() - start;

            System.out.println("paint: duration= " + (1e-6 * time) + " ms.");

            if (SAVE_IMAGE) {
                try {
                    final File file = new File("CrashTest-dash-" + useDashes + ".bmp");

                    System.out.println("Writing file: " + file.getAbsolutePath());
                    ImageIO.write(image, "BMP", file);
                } catch (IOException ex) {
                    System.out.println("Writing file failure:");
                    ex.printStackTrace();
                }
            }
        } finally {
            g2d.dispose();
        }
    }

    private static void testHugeImage(final int width, final int height)
        throws ArrayIndexOutOfBoundsException
    {
        System.out.println("---\n" + "testHugeImage: "
            + "width=" + width + ", height=" + height);

        final BasicStroke stroke = createStroke(2.5f, false, 0);

        // size > 24bits (exceed both tile and buckets arrays)
        System.out.println("image size = " + width + " x "+height);

        final BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_BYTE_GRAY);

        final Graphics2D g2d = (Graphics2D) image.getGraphics();
        try {
            g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);

            g2d.setBackground(Color.WHITE);
            g2d.clearRect(0, 0, width, height);

            g2d.setStroke(stroke);
            g2d.setColor(Color.BLACK);

            final Path2D.Float path = new Path2D.Float(WIND_NON_ZERO, 32);
            path.moveTo(0, 0);
            path.lineTo(width, 0);
            path.lineTo(width, height);
            path.lineTo(0, height);
            path.lineTo(0, 0);

            final long start = System.nanoTime();

            g2d.draw(path);

            final long time = System.nanoTime() - start;

            System.out.println("paint: duration= " + (1e-6 * time) + " ms.");

            if (SAVE_IMAGE) {
                try {
                    final File file = new File("CrashTest-huge-"
                        + width + "x" +height + ".bmp");

                    System.out.println("Writing file: " + file.getAbsolutePath());
                    ImageIO.write(image, "BMP", file);
                } catch (IOException ex) {
                    System.out.println("Writing file failure:");
                    ex.printStackTrace();
                }
            }
        } finally {
            g2d.dispose();
        }
    }

    private static void paint(final Graphics2D g2d, final float size) {
        final double halfSize = size / 2.0;

        final Path2D.Float path = new Path2D.Float(WIND_NON_ZERO, 32 * 1024);

        // show cross:
        path.moveTo(0, 0);
        path.lineTo(size, size);

        path.moveTo(size, 0);
        path.lineTo(0, size);

        path.moveTo(0, 0);
        path.lineTo(size, 0);

        path.moveTo(0, 0);
        path.lineTo(0, size);

        path.moveTo(0, 0);

        double r = size;

        final int ratio = 100;
        int repeats = 1;

        int n = 0;

        while (r > 1.0) {
            repeats *= ratio;

            if (repeats > 10000) {
                repeats = 10000;
            }

            for (int i = 0; i < repeats; i++) {
                path.lineTo(halfSize - 0.5 * r + i * r / repeats,
                            halfSize - 0.5 * r);
                n++;
                path.lineTo(halfSize - 0.5 * r + i * r / repeats + 0.1,
                            halfSize + 0.5 * r);
                n++;
            }

            r -= halfSize;
        }
        System.out.println("draw : " + n + " lines.");
        g2d.draw(path);
    }

    private static BasicStroke createStroke(final float width,
                                            final boolean useDashes,
                                            final float dashMinLen) {
        final float[] dashes;

        if (useDashes) {
            // huge dash array (exceed Dasher.INITIAL_ARRAY)
            dashes = new float[512];

            float cur = dashMinLen;
            float step = 0.01f;

            for (int i = 0; i < dashes.length; i += 2) {
                dashes[i] = cur;
                dashes[i + 1] = cur;
                cur += step;
            }
        } else {
            dashes = null;
        }

        if (USE_ROUND_CAPS_AND_JOINS) {
            // Use both round Caps & Joins:
            return new BasicStroke(width, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND, 100.0f, dashes, 0.0f);
        }
        return new BasicStroke(width, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 100.0f, dashes, 0.0f);
    }
}
