package org.apache.maven.surefire.booter;

/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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.
 */

import org.apache.maven.surefire.api.booter.DumpErrorSingleton;

import javax.annotation.Nonnull;
import java.io.File;
import java.io.IOException;
import java.nio.charset.Charset;
import java.text.SimpleDateFormat;
import java.util.Queue;
import java.util.Scanner;
import java.util.TimeZone;
import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import static java.lang.Integer.parseInt;
import static java.lang.Long.parseLong;
import static java.util.concurrent.TimeUnit.DAYS;
import static java.util.concurrent.TimeUnit.HOURS;
import static java.util.concurrent.TimeUnit.MINUTES;
import static java.util.regex.Pattern.compile;
import static org.apache.maven.surefire.shared.io.IOUtils.closeQuietly;
import static org.apache.maven.surefire.shared.lang3.StringUtils.isNotBlank;
import static org.apache.maven.surefire.shared.lang3.SystemUtils.IS_OS_HP_UX;
import static org.apache.maven.surefire.shared.lang3.SystemUtils.IS_OS_LINUX;
import static org.apache.maven.surefire.shared.lang3.SystemUtils.IS_OS_UNIX;
import static org.apache.maven.surefire.shared.lang3.SystemUtils.IS_OS_WINDOWS;
import static org.apache.maven.surefire.booter.ProcessInfo.unixProcessInfo;
import static org.apache.maven.surefire.booter.ProcessInfo.windowsProcessInfo;
import static org.apache.maven.surefire.booter.ProcessInfo.ERR_PROCESS_INFO;
import static org.apache.maven.surefire.booter.ProcessInfo.INVALID_PROCESS_INFO;
import static org.apache.maven.surefire.api.util.internal.StringUtils.NL;

/**
 * Recognizes PID of Plugin process and determines lifetime.
 *
 * @author <a href="mailto:tibordigana@apache.org">Tibor Digana (tibor17)</a>
 * @since 2.20.1
 */
final class PpidChecker
{
    private static final int MINUTES_TO_MILLIS = 60 * 1000;
    // 25 chars https://superuser.com/questions/937380/get-creation-time-of-file-in-milliseconds/937401#937401
    private static final int WMIC_CREATION_DATE_VALUE_LENGTH = 25;
    private static final int WMIC_CREATION_DATE_TIMESTAMP_LENGTH = 18;
    private static final SimpleDateFormat WMIC_CREATION_DATE_FORMAT =
            IS_OS_WINDOWS ? createWindowsCreationDateFormat() : null;
    private static final String WMIC_CREATION_DATE = "CreationDate";
    private static final String WINDOWS_SYSTEM_ROOT_ENV = "SystemRoot";
    private static final String RELATIVE_PATH_TO_WMIC = "System32\\Wbem";
    private static final String SYSTEM_PATH_TO_WMIC =
            "%" + WINDOWS_SYSTEM_ROOT_ENV + "%\\" + RELATIVE_PATH_TO_WMIC + "\\";
    private static final String PS_ETIME_HEADER = "ELAPSED";
    private static final String PS_PID_HEADER = "PID";

    private final Queue<Process> destroyableCommands = new ConcurrentLinkedQueue<>();

    /**
     * The etime is in the form of [[dd-]hh:]mm:ss on Unix like systems.
     * See the workaround https://issues.apache.org/jira/browse/SUREFIRE-1451.
     */
    static final Pattern UNIX_CMD_OUT_PATTERN = compile( "^(((\\d+)-)?(\\d{1,2}):)?(\\d{1,2}):(\\d{1,2})\\s+(\\d+)$" );

    static final Pattern BUSYBOX_CMD_OUT_PATTERN = compile( "^(\\d+)[hH](\\d{1,2})\\s+(\\d+)$" );

    private final String ppid;

    private volatile ProcessInfo parentProcessInfo;
    private volatile boolean stopped;

    PpidChecker( @Nonnull String ppid )
    {
        this.ppid = ppid;
    }

    boolean canUse()
    {
        if ( isStopped() )
        {
            return false;
        }
        final ProcessInfo ppi = parentProcessInfo;
        return ppi == null ? IS_OS_WINDOWS || IS_OS_UNIX && canExecuteUnixPs() : ppi.canUse();
    }

    /**
     * This method can be called only after {@link #canUse()} has returned {@code true}.
     *
     * @return {@code true} if parent process is alive; {@code false} otherwise
     * @throws IllegalStateException if {@link #canUse()} returns {@code false}, error to read process
     *                               or this object has been {@link #destroyActiveCommands() destroyed}
     * @throws NullPointerException if extracted e-time is null
     */
    boolean isProcessAlive()
    {
        if ( !canUse() )
        {
            throw new IllegalStateException( "irrelevant to call isProcessAlive()" );
        }

        final ProcessInfo previousInfo = parentProcessInfo;
        if ( IS_OS_WINDOWS )
        {
            parentProcessInfo = windows();
            checkProcessInfo();

            // let's compare creation time, should be same unless killed or PID is reused by OS into another process
            return !parentProcessInfo.isInvalid()
                    && ( previousInfo == null || parentProcessInfo.isTimeEqualTo( previousInfo ) );
        }
        else if ( IS_OS_UNIX )
        {
            parentProcessInfo = unix();
            checkProcessInfo();

            // let's compare elapsed time, should be greater or equal if parent process is the same and still alive
            return !parentProcessInfo.isInvalid()
                    && ( previousInfo == null || !parentProcessInfo.isTimeBefore( previousInfo ) );
        }
        parentProcessInfo = ERR_PROCESS_INFO;
        throw new IllegalStateException( "unknown platform or you did not call canUse() before isProcessAlive()" );
    }

    private void checkProcessInfo()
    {
        if ( isStopped() )
        {
            throw new IllegalStateException( "error [STOPPED] to read process " + ppid );
        }

        if ( !parentProcessInfo.canUse() )
        {
            throw new IllegalStateException( "Cannot use PPID " + ppid + " process information. "
                    + "Going to use NOOP events." );
        }
    }

    // https://www.freebsd.org/cgi/man.cgi?ps(1)
    // etimes elapsed running time, in decimal integer seconds

    // http://manpages.ubuntu.com/manpages/xenial/man1/ps.1.html
    // etimes elapsed time since the process was started, in seconds.

    // http://hg.openjdk.java.net/jdk7/jdk7/jdk/file/9b8c96f96a0f/test/java/lang/ProcessBuilder/Basic.java#L167
    ProcessInfo unix()
    {
        ProcessInfoConsumer reader = new ProcessInfoConsumer( Charset.defaultCharset().name() )
        {
            @Override
            @Nonnull
            ProcessInfo consumeLine( String line, ProcessInfo previousOutputLine )
            {
                if ( previousOutputLine.isInvalid() )
                {
                    if ( hasHeader )
                    {
                        Matcher matcher = UNIX_CMD_OUT_PATTERN.matcher( line );
                        if ( matcher.matches() && ppid.equals( fromPID( matcher ) ) )
                        {
                            long pidUptime = fromDays( matcher )
                                                     + fromHours( matcher )
                                                     + fromMinutes( matcher )
                                                     + fromSeconds( matcher );
                            return unixProcessInfo( ppid, pidUptime );
                        }
                        matcher = BUSYBOX_CMD_OUT_PATTERN.matcher( line );
                        if ( matcher.matches() && ppid.equals( fromBusyboxPID( matcher ) ) )
                        {
                            long pidUptime = fromBusyboxHours( matcher ) + fromBusyboxMinutes( matcher );
                            return unixProcessInfo( ppid, pidUptime );
                        }
                    }
                    else
                    {
                        hasHeader = line.contains( PS_ETIME_HEADER ) && line.contains( PS_PID_HEADER );
                    }
                }
                return previousOutputLine;
            }
        };
        String cmd = unixPathToPS() + " -o etime,pid " + ( IS_OS_LINUX ? "" : "-p " ) + ppid;
        return reader.execute( "/bin/sh", "-c", cmd );
    }

    ProcessInfo windows()
    {
        ProcessInfoConsumer reader = new ProcessInfoConsumer( "US-ASCII" )
        {
            @Override
            @Nonnull
            ProcessInfo consumeLine( String line, ProcessInfo previousProcessInfo ) throws Exception
            {
                if ( previousProcessInfo.isInvalid() && !line.isEmpty() )
                {
                    if ( hasHeader )
                    {
                        // now the line is CreationDate, e.g. 20180406142327.741074+120
                        if ( line.length() != WMIC_CREATION_DATE_VALUE_LENGTH )
                        {
                            throw new IllegalStateException( "WMIC CreationDate should have 25 characters "
                                    + line );
                        }
                        String startTimestamp = line.substring( 0, WMIC_CREATION_DATE_TIMESTAMP_LENGTH );
                        int indexOfTimeZone = WMIC_CREATION_DATE_VALUE_LENGTH - 4;
                        long startTimestampMillisUTC =
                                WMIC_CREATION_DATE_FORMAT.parse( startTimestamp ).getTime()
                                        - parseInt( line.substring( indexOfTimeZone ) ) * MINUTES_TO_MILLIS;
                        return windowsProcessInfo( ppid, startTimestampMillisUTC );
                    }
                    else
                    {
                        hasHeader = WMIC_CREATION_DATE.equals( line );
                    }
                }
                return previousProcessInfo;
            }
        };
        String wmicPath = hasWmicStandardSystemPath() ? SYSTEM_PATH_TO_WMIC : "";
        return reader.execute( "CMD", "/A", "/X", "/C",
                wmicPath + "wmic process where (ProcessId=" + ppid + ") get " + WMIC_CREATION_DATE
        );
    }

    void destroyActiveCommands()
    {
        stopped = true;
        for ( Process p = destroyableCommands.poll(); p != null; p = destroyableCommands.poll() )
        {
            p.destroy();
        }
    }

    private boolean isStopped()
    {
        return stopped;
    }

    private static String unixPathToPS()
    {
        return canExecuteLocalUnixPs() ? "/usr/bin/ps" : "/bin/ps";
    }

    static boolean canExecuteUnixPs()
    {
        return canExecuteLocalUnixPs() || canExecuteStandardUnixPs();
    }

    private static boolean canExecuteLocalUnixPs()
    {
        try
        {
            return new File( "/usr/bin/ps" ).canExecute();
        }
        catch ( SecurityException e )
        {
            return false;
        }
    }

    private static boolean canExecuteStandardUnixPs()
    {
        try
        {
            return new File( "/bin/ps" ).canExecute();
        }
        catch ( SecurityException e )
        {
            return false;
        }
    }

    private static boolean hasWmicStandardSystemPath()
    {
        String systemRoot = System.getenv( WINDOWS_SYSTEM_ROOT_ENV );
        return isNotBlank( systemRoot ) && new File( systemRoot, RELATIVE_PATH_TO_WMIC + "\\wmic.exe" ).isFile();
    }

    static long fromDays( Matcher matcher )
    {
        String s = matcher.group( 3 );
        return s == null ? 0L : DAYS.toSeconds( parseLong( s ) );
    }

    static long fromHours( Matcher matcher )
    {
        String s = matcher.group( 4 );
        return s == null ? 0L : HOURS.toSeconds( parseLong( s ) );
    }

    static long fromMinutes( Matcher matcher )
    {
        String s = matcher.group( 5 );
        return s == null ? 0L : MINUTES.toSeconds( parseLong( s ) );
    }

    static long fromSeconds( Matcher matcher )
    {
        String s = matcher.group( 6 );
        return s == null ? 0L : parseLong( s );
    }

    static String fromPID( Matcher matcher )
    {
        return matcher.group( 7 );
    }

    static long fromBusyboxHours( Matcher matcher )
    {
        String s = matcher.group( 1 );
        return s == null ? 0L : HOURS.toSeconds( parseLong( s ) );
    }

    static long fromBusyboxMinutes( Matcher matcher )
    {
        String s = matcher.group( 2 );
        return s == null ? 0L : MINUTES.toSeconds( parseLong( s ) );
    }

    static String fromBusyboxPID( Matcher matcher )
    {
        return matcher.group( 3 );
    }

    private static void checkValid( Scanner scanner )
            throws IOException
    {
        IOException exception = scanner.ioException();
        if ( exception != null )
        {
            throw exception;
        }
    }

    /**
     * The beginning part of Windows WMIC format yyyymmddHHMMSS.xxx <br>
     * https://technet.microsoft.com/en-us/library/ee198928.aspx <br>
     * We use UTC time zone which avoids DST changes, see SUREFIRE-1512.
     *
     * @return Windows WMIC format yyyymmddHHMMSS.xxx
     */
    private static SimpleDateFormat createWindowsCreationDateFormat()
    {
        SimpleDateFormat formatter = new SimpleDateFormat( "yyyyMMddHHmmss'.'SSS" );
        formatter.setTimeZone( TimeZone.getTimeZone( "UTC" ) );
        return formatter;
    }

    public void stop()
    {
        stopped = true;
    }

    /**
     * Reads standard output from {@link Process}.
     * <br>
     * The artifact maven-shared-utils has non-daemon Threads which is an issue in Surefire to satisfy System.exit.
     * This implementation is taylor made without using any Thread.
     * It's easy to destroy Process from other Thread.
     */
    private abstract class ProcessInfoConsumer
    {
        private final String charset;

        boolean hasHeader;

        ProcessInfoConsumer( String charset )
        {
            this.charset = charset;
        }

        abstract @Nonnull ProcessInfo consumeLine( String line, ProcessInfo previousProcessInfo ) throws Exception;

        ProcessInfo execute( String... command )
        {
            ProcessBuilder processBuilder = new ProcessBuilder( command );
            processBuilder.redirectErrorStream( true );
            Process process = null;
            ProcessInfo processInfo = INVALID_PROCESS_INFO;
            StringBuilder out = new StringBuilder( 64 );
            try
            {
                if ( IS_OS_HP_UX ) // force to run shell commands in UNIX Standard mode on HP-UX
                {
                    processBuilder.environment().put( "UNIX95", "1" );
                }
                process = processBuilder.start();
                destroyableCommands.add( process );
                Scanner scanner = new Scanner( process.getInputStream(), charset );
                while ( scanner.hasNextLine() )
                {
                    String line = scanner.nextLine();
                    out.append( line ).append( NL );
                    processInfo = consumeLine( line.trim(), processInfo );
                }
                checkValid( scanner );
                int exitCode = process.waitFor();
                if ( exitCode != 0 || isStopped() )
                {
                    out.append( "<<exit>> <<" ).append( exitCode ).append( ">>" ).append( NL );
                    DumpErrorSingleton.getSingleton()
                            .dumpText( out.toString() );
                }
                return isStopped() ? ERR_PROCESS_INFO : exitCode == 0 ? processInfo : INVALID_PROCESS_INFO;
            }
            catch ( Exception e )
            {
                if ( !( e instanceof InterruptedException ) && !( e.getCause() instanceof InterruptedException ) )
                {
                    DumpErrorSingleton.getSingleton()
                            .dumpText( out.toString() );

                    DumpErrorSingleton.getSingleton()
                            .dumpException( e );
                }

                return ERR_PROCESS_INFO;
            }
            finally
            {
                if ( process != null )
                {
                    destroyableCommands.remove( process );
                    process.destroy();
                    closeQuietly( process.getInputStream() );
                    closeQuietly( process.getErrorStream() );
                    closeQuietly( process.getOutputStream() );
                }
            }
        }
    }

    @Override
    public String toString()
    {
        String args = "ppid=" + ppid
                + ", stopped=" + stopped;

        ProcessInfo processInfo = parentProcessInfo;
        if ( processInfo != null )
        {
            args += ", invalid=" + processInfo.isInvalid()
                    + ", error=" + processInfo.isError();
        }

        if ( IS_OS_UNIX )
        {
            args += ", canExecuteLocalUnixPs=" + canExecuteLocalUnixPs()
                    + ", canExecuteStandardUnixPs=" + canExecuteStandardUnixPs();
        }

        return "PpidChecker{" + args + '}';
    }
}
