001package net.bramp.ffmpeg.io; 002 003import java.util.concurrent.TimeUnit; 004import java.util.concurrent.TimeoutException; 005 006/** 007 * @author bramp 008 */ 009public final class ProcessUtils { 010 011 private ProcessUtils() { 012 throw new AssertionError("No instances for you!"); 013 } 014 015 private static class ProcessThread extends Thread { 016 final Process p; 017 boolean finished = false; 018 int exitValue = -1; 019 020 private ProcessThread(Process p) { 021 this.p = p; 022 } 023 024 @Override 025 public void run() { 026 try { 027 exitValue = p.waitFor(); 028 finished = true; 029 } catch (InterruptedException e) { 030 Thread.currentThread().interrupt(); 031 } 032 } 033 034 public boolean hasFinished() { 035 return finished; 036 } 037 038 public int exitValue() { 039 return exitValue; 040 } 041 } 042 043 /** 044 * Waits until a process finishes or a timeout occurs 045 * 046 * @param p process 047 * @param timeout timeout in given unit 048 * @param unit time unit 049 * @return the process exit value 050 * @throws TimeoutException if a timeout occurs 051 */ 052 public static int waitForWithTimeout(final Process p, long timeout, TimeUnit unit) 053 throws TimeoutException { 054 055 ProcessThread t = new ProcessThread(p); 056 t.start(); 057 try { 058 unit.timedJoin(t, timeout); 059 060 } catch (InterruptedException e) { 061 t.interrupt(); 062 Thread.currentThread().interrupt(); 063 } 064 065 if (!t.hasFinished()) { 066 throw new TimeoutException("Process did not finish within timeout"); 067 } 068 069 return t.exitValue(); 070 } 071}