X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/hpcvm.git/blobdiff_plain/3502bc1e43c70f69ae488cb8418a0ef4fd885d19..b956a81261e5bebb70d8fffc2756b09cfdf9ea91:/src/and/hpcvm/Client.java diff --git a/src/and/hpcvm/Client.java b/src/and/hpcvm/Client.java index 2f1e01b..e3233eb 100644 --- a/src/and/hpcvm/Client.java +++ b/src/and/hpcvm/Client.java @@ -15,6 +15,7 @@ import java.rmi.registry.LocateRegistry; import java.rmi.registry.Registry; import java.rmi.server.UnicastRemoteObject; import java.util.ArrayList; +import java.util.concurrent.Semaphore; public class Client extends UnicastRemoteObject implements ServicesClient @@ -38,11 +39,16 @@ public class Client extends UnicastRemoteObject implements ServicesClient private int wait_start ; private int max_start_try ; private boolean isRestartedSave ; - private long save_interleave ; - private long date_last_save ; +// private long save_interleave ; +// private long date_last_save ; private SaveProcess saveProcess; private int maxRetryVM ; private int timeRetryVM ; + private Semaphore sema ; + private boolean emergencyStop ; + private Process procSave ; + private SaveRequest saveRequest ; + private boolean lastSaveOk ; protected Client() throws RemoteException @@ -50,12 +56,54 @@ public class Client extends UnicastRemoteObject implements ServicesClient super() ; } + @Override + public void emergencyStop() + { + emergencyStop = true ; + + // Saving processus stop + synchronized( saveProcess ) { + saveProcess.setStatus( false ) ; + try { + saveProcess.notifyAll() ; + } catch( Exception e ) {}} + + try { + procSave.destroy() ; + } catch( Exception e ) {} + + // Stopping the save request + synchronized( saveRequest ) + { + saveRequest.setStatus( false ) ; + try { + saveRequest.notifyAll() ; + } catch( Exception e ) {} + } + + stopVM() ; + } + @Override public int startVM( int _mode ) { if( machine != null && ! machine.getStatus().equalsIgnoreCase( "running" ) ) { + try { + sema.acquire() ; + } catch( InterruptedException e2 ) { + System.err.println( "Problem with semaphore acquiring!" ) ; + e2.printStackTrace() ; + } + + + // Checking first start + if( machine.checkVmx() == 1 ) + { + return 1 ; + } + boolean ret = true ; int retry = 0 ; @@ -78,39 +126,57 @@ public class Client extends UnicastRemoteObject implements ServicesClient working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name(), "nogui"} ; while( ret ) - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; + { - if( p.exitValue() == 0 ) + if( emergencyStop ) { - System.out.println( "Virtual machine successfully started." ) ; - ret = false ; - } else { - System.err.println( "Virtual machine not started!" ) ; - ret = printProcessError( p ) ; - - if( ! ret ) + return 1 ; + } + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; + + if( p.exitValue() == 0 ) { - return 1 ; + System.out.println( "Virtual machine successfully started." ) ; + ret = false ; } else { - retry++ ; - if( retry >= maxRetryVM ) + System.err.println( "Virtual machine not started!" ) ; + ret = printProcessError( p ) ; + + if( ! ret ) { - System.err.println( "Unable to start VM!" ) ; + sema.release() ; + return 1 ; + } else { + retry++ ; + if( retry >= maxRetryVM ) + { + System.err.println( "Unable to start VM!" ) ; + + sema.release() ; + + return 1 ; + } + System.out.println( "Retrying (" + retry + ") ... " ) ; + Thread.sleep( timeRetryVM ) ; } - System.out.println( "Retrying (" + retry + ") ... " ) ; - Thread.sleep( timeRetryVM ) ; } + } catch( IOException e ) { + System.err.println( "Error during execution of start command: " ) ; + e.printStackTrace() ; + + sema.release() ; + + return 1 ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + + sema.release() ; + return 1 ; } - } catch( IOException e ) { - System.err.println( "Error during execution of start command: " ) ; - e.printStackTrace() ; - return 1 ; - } catch( InterruptedException e ) { - e.printStackTrace() ; - return 1 ; } @@ -121,6 +187,11 @@ public class Client extends UnicastRemoteObject implements ServicesClient while( ! started ) { + if( emergencyStop ) + { + return 1 ; + } + /** Waiting for VM being started **/ try { Thread.sleep( wait_start ) ; @@ -132,7 +203,7 @@ public class Client extends UnicastRemoteObject implements ServicesClient " -gp " + machine.getVmUserPasswd() + " runScriptInGuest " + working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name() + " " + ushell + - " \"echo ok\"" ;// + " -noWait " ; + " \"echo ok\"" ; try { FileWriter fw = new FileWriter( new File( working_directory + "/testStarted.sh" ) ) ; @@ -141,71 +212,86 @@ public class Client extends UnicastRemoteObject implements ServicesClient fw.close() ; } catch( IOException e1 ) { e1.printStackTrace() ; + + sema.release() ; + return 1 ; } command = new String[]{ ushell, working_directory + "/testStarted.sh"} ; while( ret ) - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) + { + if( emergencyStop ) { - started = true ; -// machine.setStatus( "running" ) ; -// if( _mode == 0 ) -// { -// LocalHost.Instance().getServerStub().changeStatus( -// LocalHost.Instance().getIP(), "running" ) ; -// } - ret = false ; - } else { - System.err.println( "Error while checking if the VM is started!" ) ; -// printProcessError( p.getErrorStream() ) ; - ret = printProcessError( p ) ; - - if( ! ret ) + return 1 ; + } + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; + + if( p.exitValue() == 0 ) { - return 1 ; + started = true ; + ret = false ; } else { - retry++ ; - if( retry >= maxRetryVM ) + System.err.println( "Error while checking if the VM is started!" ) ; + ret = printProcessError( p ) ; + + if( ! ret ) { - System.err.println( "Unable to check VM!" ) ; + sema.release() ; + stopVM() ; return 1 ; + } else { + retry++ ; + if( retry >= maxRetryVM ) + { + System.err.println( "Unable to check VM!" ) ; + + sema.release() ; + stopVM() ; + return 1 ; + } + System.out.println( "Retrying (" + retry + ") ... " ) ; + Thread.sleep( timeRetryVM ) ; } - System.out.println( "Retrying (" + retry + ") ... " ) ; - Thread.sleep( timeRetryVM ) ; + count++ ; } -// wait_start = wait_start / 2 ; - count++ ; + } catch( IOException e ) { + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; } - } catch( IOException e ) { - e.printStackTrace() ; - } catch( InterruptedException e ) { - e.printStackTrace() ; - } - if( count == max_start_try && ! started ) - { - System.err.println( "Virtual machine not responding!!" ) ; + if( count == max_start_try && ! started ) + { + System.err.println( "Virtual machine not responding!!" ) ; - try { - LocalHost.Instance().getServerStub().changeStatus( - LocalHost.Instance().getIP(), "undefined" ) ; - } catch( RemoteException e ) { - e.printStackTrace() ; - } - - stopVM() ; + try { + LocalHost.Instance().getServerStub().changeStatus( + LocalHost.Instance().getIP(), "undefined" ) ; + } catch( RemoteException e ) { + e.printStackTrace() ; + } + + sema.release() ; - return 1 ; - } else { - try { - Thread.sleep( 3000 ) ; - } catch( InterruptedException e ) { - e.printStackTrace() ; + stopVM() ; + + return 1 ; + } else { + try { + Thread.sleep( 3000 ) ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + } } } } @@ -228,6 +314,9 @@ public class Client extends UnicastRemoteObject implements ServicesClient fw.close() ; } catch( IOException e1 ) { e1.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; } command = new String[]{ ushell, working_directory + "/sendHostIP.sh"} ; @@ -236,41 +325,56 @@ public class Client extends UnicastRemoteObject implements ServicesClient retry = 0 ; while( ret ) - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) + { + if( emergencyStop ) { - System.out.println( "VM received the host IP." ) ; - ret = false ; - } else { - System.err.println( "VM did not received the host IP!" ) ; -// printProcessError( p.getErrorStream() ) ; - ret = printProcessError( p ) ; - - if( ! ret ) + return 1 ; + } + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; + + if( p.exitValue() == 0 ) { - return 1 ; + System.out.println( "VM received the host IP." ) ; + ret = false ; } else { - retry++ ; - if( retry >= maxRetryVM ) - { - System.err.println( "Unable to send information to VM!" ) ; + System.err.println( "VM did not received the host IP!" ) ; + ret = printProcessError( p ) ; + if( ! ret ) + { + sema.release() ; stopVM() ; - return 1 ; + } else { + retry++ ; + if( retry >= maxRetryVM ) + { + System.err.println( "Unable to send information to VM!" ) ; + + sema.release() ; + stopVM() ; + + return 1 ; + } + System.out.println( "Retrying (" + retry + ") ... " ) ; + Thread.sleep( timeRetryVM ) ; } - System.out.println( "Retrying (" + retry + ") ... " ) ; - Thread.sleep( timeRetryVM ) ; } + } catch( IOException e ) { + System.err.println( "Error during execution of runScriptInGuest command: " ) ; + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; + } catch( InterruptedException e) { + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; } - } catch( IOException e ) { - System.err.println( "Error during execution of runScriptInGuest command: " ) ; - e.printStackTrace() ; - } catch( InterruptedException e) { - e.printStackTrace() ; } /** Sending the vm ip **/ @@ -291,6 +395,9 @@ public class Client extends UnicastRemoteObject implements ServicesClient fw.close() ; } catch( IOException e1 ) { e1.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; } command = new String[]{ ushell, working_directory + "/sendVmIP.sh"} ; @@ -299,43 +406,57 @@ public class Client extends UnicastRemoteObject implements ServicesClient retry = 0 ; while( ret ) - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) + { + if( emergencyStop ) { - System.out.println( "VM received its assigned IP." ) ; -// return 0 ; - ret = false ; - machine.setStatus( "running" ) ; - } else { - System.err.println( "VM did not received its assigned IP!" ) ; -// printProcessError( p.getErrorStream() ) ; - ret = printProcessError( p ) ; - - if( ! ret ) + return 1 ; + } + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; + + if( p.exitValue() == 0 ) { - return 1 ; + System.out.println( "VM received its assigned IP." ) ; + ret = false ; + machine.setStatus( "running" ) ; } else { - retry++ ; - if( retry >= maxRetryVM ) + System.err.println( "VM did not received its assigned IP!" ) ; + ret = printProcessError( p ) ; + + if( ! ret ) { - System.err.println( "Unable to send information to VM!" ) ; - + sema.release() ; stopVM() ; - return 1 ; + } else { + retry++ ; + if( retry >= maxRetryVM ) + { + System.err.println( "Unable to send information to VM!" ) ; + + sema.release() ; + stopVM() ; + + return 1 ; + } + System.out.println( "Retrying (" + retry + ") ... " ) ; + Thread.sleep( timeRetryVM ) ; } - System.out.println( "Retrying (" + retry + ") ... " ) ; - Thread.sleep( timeRetryVM ) ; } + } catch( IOException e ) { + System.err.println( "Error during execution of runScriptInGuest command: " ) ; + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + sema.release() ; + stopVM() ; + return 1 ; } - } catch( IOException e ) { - System.err.println( "Error during execution of runScriptInGuest command: " ) ; - e.printStackTrace() ; - } catch( InterruptedException e ) { - e.printStackTrace() ; } if( _mode == 0 ) @@ -349,22 +470,35 @@ public class Client extends UnicastRemoteObject implements ServicesClient } } + sema.release() ; + return 0 ; } + sema.release() ; + return 1 ; } + @Override public int stopVM() { if( machine != null && machine.getStatus().equalsIgnoreCase( "stopped" ) ) { + emergencyStop = false ; return 0 ; } if( machine != null && ! machine.getStatus().equalsIgnoreCase( "stopped" ) ) { + try { + sema.acquire() ; + } catch( InterruptedException e2 ) { + System.err.println( "Problem with semaphore acquiring!" ) ; + e2.printStackTrace() ; + } + System.out.print( "Stopping VM ... " ) ; boolean ret = true ; @@ -394,17 +528,18 @@ public class Client extends UnicastRemoteObject implements ServicesClient ret = false ; } else { System.err.println( "Virtual machine not stopped!" ) ; -// printProcessError( p.getErrorStream() ) ; ret = printProcessError( p ) ; if( ! ret ) { + sema.release() ; return 1 ; } else { retry++ ; if( retry >= maxRetryVM ) { System.err.println( "Unable to stop VM!" ) ; + sema.release() ; return 1 ; } System.out.println( "Retrying (" + retry + ") ... " ) ; @@ -416,8 +551,12 @@ public class Client extends UnicastRemoteObject implements ServicesClient } catch( IOException e ) { System.err.println( "Error during execution of stop command: " ) ; e.printStackTrace() ; + sema.release() ; + return 1 ; } catch( InterruptedException e ) { e.printStackTrace() ; + sema.release() ; + return 1 ; } machine.setStatus( "stopped" ) ; @@ -429,39 +568,17 @@ public class Client extends UnicastRemoteObject implements ServicesClient e1.printStackTrace() ; } - if( ! isRestartedSave ) + + if( machine.checkVmx() == 0 ) { - /** Restoring the original vmx file (necessary after a crash) **/ - command = new String[]{ "/bin/cp", - working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name_normal(), - working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name() } ; - - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) - { - System.out.println( "Successfully replaced the VMX file." ) ; - return 0 ; - } else { - System.err.println( "Unsuccessful replacement of the VMX file!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; - - return 1 ; - } - } catch( IOException e ) { - System.err.println( "Error during VMX file replacement: " ) ; - e.printStackTrace() ; - } catch( InterruptedException e ) { - e.printStackTrace() ; - } - } else { + sema.release() ; + emergencyStop = false ; return 0 ; } } + sema.release() ; + return 1 ; } @@ -475,6 +592,13 @@ public class Client extends UnicastRemoteObject implements ServicesClient if( machine != null && ! machine.getStatus().equalsIgnoreCase( "suspended" ) ) { + try { + sema.acquire() ; + } catch( InterruptedException e2 ) { + System.err.println( "Problem with semaphore acquiring!" ) ; + e2.printStackTrace() ; + } + System.out.print( "Suspending VM ... " ) ; boolean ret = true ; @@ -506,17 +630,21 @@ public class Client extends UnicastRemoteObject implements ServicesClient ret = false ; } else { System.err.println( "Virtual machine not suspended!" ) ; -// printProcessError( p.getErrorStream() ) ; ret = printProcessError( p ) ; if( ! ret ) { + sema.release() ; + return 1 ; } else { retry++ ; if( retry >= maxRetryVM ) { System.err.println( "Unable to suspend VM!" ) ; + + sema.release() ; + return 1 ; } System.out.println( "Retrying (" + retry + ") ... " ) ; @@ -544,9 +672,13 @@ public class Client extends UnicastRemoteObject implements ServicesClient } } + sema.release() ; + return 0 ; } - + + sema.release() ; + return 1 ; } @@ -587,7 +719,6 @@ public class Client extends UnicastRemoteObject implements ServicesClient } else { System.err.println( "Virtual machine not restarted!" ) ; -// printProcessError( p.getErrorStream() ) ; ret = printProcessError( p ) ; if( ! ret ) @@ -637,60 +768,25 @@ public class Client extends UnicastRemoteObject implements ServicesClient if( isRestartedSave ) { // Using the specific vmx file - System.out.print( "Changing VMX file after crash ... " ) ; - - String[] command = new String[]{ "/bin/cp", - working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name_crash(), - working_directory + "/" + machine.getDirectory() + "/" + machine.getVmx_name() } ; + machine.setDeployFault( true ) ; + // Writing the restarted save mark try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) - { - System.out.println( "Successfully replaced the VMX file." ) ; - } else { - System.err.println( "Unsuccessful replacement of the VMX file!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; - - return 1 ; - } - } catch( IOException e ) { - System.err.println( "Error during VMX file replacement: " ) ; - e.printStackTrace() ; - } catch( InterruptedException e ) { - e.printStackTrace() ; - } - - // Removing lock files - System.out.print( "Removing lock files ... " ) ; - - command = new String[]{ "/bin/rm", "-rf", - working_directory + "/" + machine.getDirectory() - + "/" + machine.getVmx_name() + ".lck" } ; + FileWriter fw = new FileWriter( new File( working_directory + "/" + machine.getDirectory() + "/fault.hpcvm" ) ) ; + fw.write( "fault!" ) ; + fw.flush() ; + fw.close() ; + fw = null ; + } catch( IOException e1 ) { + e1.printStackTrace() ; + System.err.println( "Unable to mark the fault!" ) ; + } - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - - if( p.exitValue() == 0 ) - { - System.out.println( "Successfully deleted lock files." ) ; - } else { - System.err.println( "Unsuccessful deletion of lock files!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; - - return 1 ; - } - } catch( IOException e ) { - System.err.println( "Error during lock files deletion: " ) ; - e.printStackTrace() ; - } catch( InterruptedException e ) { - e.printStackTrace() ; + if( machine.checkVmx() == 1 ) + { + return 1 ; } + /** Retrieving VM assigned IP **/ String vmIP = null ; @@ -712,7 +808,14 @@ public class Client extends UnicastRemoteObject implements ServicesClient if( startVM( 0 ) == 0 ) { if( sendSaveOkVM() == 0 ) - { + { + try { + LocalHost.Instance().getServerStub().restartOk( LocalHost.Instance().getIP() ) ; + } catch( RemoteException e ) { + System.err.println( "Unable to inform server about my successful restart!" ) ; + e.printStackTrace() ; + } + return 0 ; } } else { @@ -762,7 +865,6 @@ public class Client extends UnicastRemoteObject implements ServicesClient return 0 ; } else { System.err.println( "Signal not sent!" ) ; -// printProcessError( p.getErrorStream() ) ; ret = printProcessError( p ) ; if( ! ret ) @@ -809,6 +911,8 @@ public class Client extends UnicastRemoteObject implements ServicesClient System.out.println( "Saving VM ..." ) ; saveProcess.setStatus( true ) ; + long deb = System.currentTimeMillis() ; + machine.setStatus( "saving" ) ; try { LocalHost.Instance().getServerStub().changeStatus( @@ -821,29 +925,80 @@ public class Client extends UnicastRemoteObject implements ServicesClient String[] command ; String saveName = "" ; boolean error = false ; - boolean errorVM = false ; - if( suspendVM( 1 ) == 1 ) { error = true ; errorVM = true ; } + + if( suspendVM( 1 ) == 1 ) { return 1 ; } + + + if( ! lastSaveOk ) + { + String arch = "" ; + File file = new File( working_directory + "/" + machine.getName() + "_new_" + machine.getComputationId() + ".tar.gz" ) ; + if( file.exists() ) + { + arch = working_directory + "/" + machine.getName() + "_new_" + machine.getComputationId() + ".tar.gz" ; + } + + file = null ; + + if( arch.length() > 0 ) + { + System.out.println( "Deletion of last nok archive ... " ) ; + + command = new String[]{ "/bin/rm", "-rf", arch } ; + + try { + procSave = Runtime.getRuntime().exec( command ) ; + procSave.waitFor() ; + + if( procSave.exitValue() == 0 ) + { + System.out.println( "Last nok archive successfully deleted." ) ; + } else { + System.err.println( "Last nok archive not deleted!" ) ; + printProcessError( procSave ) ; + + error = true ; + } + } catch( IOException e ) { + System.err.println( "Error during nok archive deletion command: " ) ; + error = true ; + e.printStackTrace() ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + error = true ; + } + } + } + if( ! error ) { System.out.print( "Creation of the archive ... " ) ; + /** Archive creation **/ - command = new String[]{ "/bin/tar", "-cvf", - working_directory + "/" + machine.getName() + "_new_" + machine.getComputationId() + ".tar", - working_directory + "/" + machine.getDirectory() } ; - + command = new String[]{ "/bin/tar", "-cz", "-C", working_directory, + "-f", working_directory + "/" + machine.getName() + "_new_" + machine.getComputationId() + ".tar.gz", + machine.getDirectory() } ; + + if( emergencyStop ) + { + return 1 ; + } + try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; + procSave = Runtime.getRuntime().exec( command ) ; + procSave.waitFor() ; - if( p.exitValue() == 0 ) + if( procSave.exitValue() == 0 ) { System.out.println( "Archive successfully created." ) ; + + lastSaveOk = false ; + } else { System.err.println( "Archive not created!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; + printProcessError( procSave ) ; error = true ; } @@ -855,106 +1010,52 @@ public class Client extends UnicastRemoteObject implements ServicesClient e.printStackTrace() ; error = true ; } - - /** Compression of the archive **/ - if( ! error ) - { - System.out.print( "Compression of the archive ... " ) ; - command = new String[]{ "/bin/gzip", - working_directory + "/" + machine.getName() - + "_new_" + machine.getComputationId() + ".tar" } ; - - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; - if( p.exitValue() == 0 ) - { - System.out.println( "Archive successfully compressed." ) ; - } else { - System.err.println( "Archive not compressed!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; - - error = true ; - } - } catch( IOException e ) { - System.err.println( "Error during archive compression command: " ) ; - e.printStackTrace() ; - error = true ; - } catch( InterruptedException e ) { - e.printStackTrace() ; - error = true ; - } - } + long fin = System.currentTimeMillis() ; + + System.out.println( "Time to create the save: " + (fin-deb)/1000 + " seconds." ) ; /** Restarting VM **/ - if( errorVM || startVM( 0 ) == 1 ) { error = true ; } + if( startVM( 0 ) == 1 ) { return 1 ; } /** Sending ok save signal **/ - if( ! error ) - { - if( sendSaveOkVM() == 1 ) { error = true ; } - } - -// /** Deletion of the tar archive **/ -// if( ! error ) -// { -// command = new String[]{ "/bin/rm", -// working_directory + "/" + machine.getName() -// + "_new_" + machine.getComputationId() + ".tar" } ; -// -// try { -// Process p = Runtime.getRuntime().exec( command ) ; -// p.waitFor() ; -// -// if( p.exitValue() == 0 ) -// { -// System.out.println( "Archive (not compressed) successfully deleted." ) ; -// } else { -// System.err.println( "Archive (not compressed) not deleted!" ) ; -// printProcessError( p.getErrorStream() ) ; -// -// error = true ; -// } -// } catch( IOException e ) { -// System.err.println( "Error during archive (not compressed) deletion command: " ) ; -// e.printStackTrace() ; -// error = true ; -// } catch( InterruptedException e ) { -// e.printStackTrace() ; -// error = true ; -// } -// } - - saveName = working_directory + "/" + machine.getName() + "_new_" - + machine.getComputationId() + ".tar.gz" ; + if( sendSaveOkVM() == 1 ) { return 1 ; } + + saveName = machine.getName() + "_new_" + machine.getComputationId() + ".tar.gz" ; /** Sending save to neighbor **/ if( ! error ) { - ArrayList sn = machine.getSaveNeighbors() ; + if( emergencyStop ) + { + return 1 ; + } + + ArrayList sn = machine.getSaveNeighbors() ; for( int i = 0 ; i < sn.size() ; i++ ) { - System.out.print( "Sending save to " + sn.get( i ) + " ... " ) ; - command = new String[]{ "/usr/bin/scp", saveName, - sn.get( i ) + ":" - + working_directory } ; + String name = sn.get( i ).getName() ; + String wd = sn.get( i ).getWorkingDirectory() ; + String snIP = sn.get( i ).getIPHost() ; + + System.out.print( "Sending save to " + name + " ... " ) ; + + command = new String[]{ "/usr/bin/scp", working_directory + "/" + saveName, + snIP + ":" + wd } ; try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; + procSave = Runtime.getRuntime().exec( command ) ; + procSave.waitFor() ; - if( p.exitValue() == 0 ) + if( procSave.exitValue() == 0 ) { System.out.println( "Archive successfully sent." ) ; } else { System.err.println( "Archive not sent!" ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; + printProcessError( procSave ) ; error = true ; } @@ -1020,6 +1121,7 @@ public class Client extends UnicastRemoteObject implements ServicesClient serverStub = null ; saveProcess = new SaveProcess() ; + saveRequest = new SaveRequest() ; machine = new VirtualMachine() ; @@ -1034,13 +1136,17 @@ public class Client extends UnicastRemoteObject implements ServicesClient wait_start = 15000 ; max_start_try = 10 ; + sema = new Semaphore( 1 ) ; + emergencyStop = false ; + maxRetryVM = 10 ; timeRetryVM = 10000 ; - save_interleave = 30 * 60 * 1000 ; - date_last_save = 0 ; +// save_interleave = 30 * 60 * 1000 ; +// date_last_save = 0 ; isRestartedSave = false ; + lastSaveOk = false ; /** Connection to server **/ try { @@ -1064,7 +1170,6 @@ public class Client extends UnicastRemoteObject implements ServicesClient System.out.println( "Connected to server " + server_ip + " on port " + server_port + "." ) ; -// LocalHost.Instance().setServerIP( server_ip ) ; LocalHost.Instance().setServerStub( serverStub ) ; @@ -1077,7 +1182,6 @@ public class Client extends UnicastRemoteObject implements ServicesClient private void exportObject() { -// ServicesClient ref = null ; Registry reg = null ; try @@ -1141,7 +1245,7 @@ public class Client extends UnicastRemoteObject implements ServicesClient while( (line = br.readLine()) != null ) { System.err.println( line ) ; - if( line.contains( "egmentation" ) ) + if( line.contains( "egmentation" ) || _p.exitValue() == 139 ) { ret = true ; } @@ -1154,6 +1258,13 @@ public class Client extends UnicastRemoteObject implements ServicesClient return ret ; } + + @Override + public int echo() + { + return 0 ; + } + @Override public int start() @@ -1205,30 +1316,33 @@ public class Client extends UnicastRemoteObject implements ServicesClient private class PingServer extends Thread { - private boolean run ; + protected boolean go ; PingServer() { - run = true ; + go = true ; } - protected void stopPing() { run = false ; } + protected void stopPing() { go = false ; } @Override public void run() { - while( run ) + while( go ) { try { LocalHost.Instance().getServerStub().ping( LocalHost.Instance().getIP() ) ; - } catch (RemoteException e1) { - e1.printStackTrace(); + } catch( RemoteException e1 ) { + System.err.println( "Unable to ping the server!" ) ; + e1.printStackTrace() ; + yield() ; } try { - Thread.sleep( 2000 ) ; + sleep( 2000 ) ; } catch( InterruptedException e ) { e.printStackTrace() ; + yield() ; } } } @@ -1237,32 +1351,26 @@ public class Client extends UnicastRemoteObject implements ServicesClient private class DialogVMServer extends Thread { - private boolean run ; + protected boolean go ; private Socket socket ; - private ArrayList dialogs = new ArrayList() ; +// private ArrayList dialogs = new ArrayList() ; DialogVMServer() { - run = true ; + go = true ; } protected void stopDialogVMServer() { - run = false ; + go = false ; if( serverSocket != null ) { try { - serverSocket.close() ; -// socket = serverSocket.accept() ; - - for( int i = 0 ; i < dialogs.size() ; i++ ) - { - dialogs.get( i ).stopDialogVM() ; - } - + serverSocket.close() ; } catch( IOException e ) { e.printStackTrace() ; + yield() ; } } } @@ -1279,20 +1387,20 @@ public class Client extends UnicastRemoteObject implements ServicesClient } catch( IOException e ) { System.err.println( "Unable to launch the SocketServer on port " + dialog_port + "!" ) ; e.printStackTrace() ; - - run = false ; + System.exit( 1 ) ; } - while( run ) + while( go ) { try { socket = serverSocket.accept() ; - dialogs.add( new DialogVM( socket ) ) ; - dialogs.get( dialogs.size() - 1 ).start() ; + new DialogVM( socket ).start() ; + } catch( IOException e ) { System.err.println( "Problem with the accept function!" ) ; e.printStackTrace() ; + yield() ; } } } @@ -1301,24 +1409,11 @@ public class Client extends UnicastRemoteObject implements ServicesClient private class DialogVM extends Thread { - private boolean run ; private Socket socket ; private BufferedReader reader ; private String line ; - DialogVM( Socket _socket ) { run = true ; socket = _socket ; } - - protected void stopDialogVM() - { - run = false ; - - try { - reader.close() ; reader = null ; - socket.close() ; socket = null ; - } catch( IOException e ) { - e.printStackTrace() ; - } - } + DialogVM( Socket _socket ) { socket = _socket ; } @Override public void run() @@ -1327,89 +1422,129 @@ public class Client extends UnicastRemoteObject implements ServicesClient reader = new BufferedReader( new InputStreamReader( socket.getInputStream() ) ) ; } catch( IOException e ) { System.err.println( "Unable to open a dialog socket with the VM!" ) ; - e.printStackTrace(); - stopDialogVM() ; + e.printStackTrace() ; + yield() ; } - - while( run ) - { - try { - line = null ; - - if( reader != null ) - { - line = reader.readLine() ; - } - - /** VM is starting -- retrieving informations **/ - if( run && line != null && line.equalsIgnoreCase( "infos" ) ) + + try { + line = null ; + + if( reader != null ) + { + line = reader.readLine() ; + } + + /** VM is starting -- retrieving informations **/ + if( line != null && line.equalsIgnoreCase( "infos" ) ) + { + /* Receiving name */ + machine.setName( reader.readLine() ) ; + + /* Receiving IP */ + String ip = reader.readLine() ; + if( ! ip.equalsIgnoreCase( machine.getIp() ) ) { - /* Receiving name */ - machine.setName( reader.readLine() ) ; - - /* Receiving IP */ - String ip = reader.readLine() ; - if( ! ip.equalsIgnoreCase( machine.getIp() ) ) - { - System.err.println( "VM IP not well configured!!" ) ; - } - - /* Close streams */ - reader.close() ; reader = null ; - socket.close() ; socket = null ; - - run = false ; + System.err.println( "VM IP not well configured!!" ) ; } - + + /* Close streams */ + reader.close() ; reader = null ; + socket.close() ; socket = null ; + + } else if( line != null && line.equalsIgnoreCase( "save" ) ) { /** It's time to do a save **/ - if( run && line != null && line.equalsIgnoreCase( "save" ) ) + + try { + machine.setComputationId( Integer.parseInt( reader.readLine() ) ) ; + } catch( Exception e ) { + System.err.println( "Problem while reading the computation id!" ) ; + e.printStackTrace() ; + } + + synchronized( saveRequest ) { try { - machine.setComputationId( Integer.parseInt( reader.readLine() ) ) ; - } catch( Exception e ) { - System.err.println( "Problem while reading the computation id!" ) ; + LocalHost.Instance().getServerStub().requestSave( LocalHost.Instance().getIP() ) ; + } catch( RemoteException e ) { + System.err.println( "Unable to request save to server!" ) ; e.printStackTrace() ; } - - if( (System.currentTimeMillis() - date_last_save) > save_interleave ) - { - date_last_save = System.currentTimeMillis() ; - - /* Close streams */ - reader.close() ; reader = null ; - socket.close() ; socket = null ; - - run = false ; - - /* Starting the VM save */ - saveVM() ; - } else { - sendSaveOkVM() ; - } - } - - - /** Computation is done, we can shutdown the VM **/ - if( run && line != null && line.equalsIgnoreCase( "quit" ) ) - { + try { - Thread.sleep( 5000 ) ; + saveRequest.wait() ; } catch( InterruptedException e ) { - e.printStackTrace() ; + e.printStackTrace(); } - + } + + if( saveRequest.getStatus() ) + { /* Close streams */ reader.close() ; reader = null ; socket.close() ; socket = null ; - - run = false ; - - stopVM() ; + + saveRequest.setStatus( false ) ; + + /* Requesting the VM save */ + if( saveVM() == 1 ) + { + System.err.println( "Problem while saving. Exiting ..." ) ; + pingServer.stopPing() ; + emergencyStop() ; + System.exit( 1 ) ; + } + } else { + sendSaveOkVM() ; + } + } else if( line != null && line.equalsIgnoreCase( "quit" ) ) { + /** Computation is done, we can shutdown the VM **/ + + try { + Thread.sleep( 5000 ) ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + } + + /* Close streams */ + reader.close() ; reader = null ; + socket.close() ; socket = null ; + + stopVM() ; + + machine.setStatus( "connected" ) ; + try { + LocalHost.Instance().getServerStub().changeStatus( + LocalHost.Instance().getIP(), "connected" ) ; + } catch( RemoteException e ) { + System.err.println( "Unable to inform the server of the VM status!" ) ; + e.printStackTrace() ; } - } catch( IOException e ) { - e.printStackTrace() ; + try { + LocalHost.Instance().getServerStub().endApplication() ; + } catch( RemoteException e ) { + System.err.println( "Unable to inform the server of the end of application!" ) ; + e.printStackTrace() ; + } + } else if( line != null && line.equalsIgnoreCase( "start" ) ) { + /** Computation is starting **/ + + /* Close streams */ + reader.close() ; reader = null ; + socket.close() ; socket = null ; + System.out.println( "Application is starting." ) ; + + try { + LocalHost.Instance().getServerStub().goApplication() ; + } catch( RemoteException e ) { + System.err.println( "Unable to inform the server of the end of application!" ) ; + e.printStackTrace() ; + } } + + } catch( IOException e ) { + e.printStackTrace() ; + yield() ; } } } @@ -1444,14 +1579,15 @@ public class Client extends UnicastRemoteObject implements ServicesClient @Override public void saveOk() { - String save_name = "VmTest_" + machine.getComputationId() + - "_last.tar.gz" ; + String save_name = machine.getName() + "_last_" + machine.getComputationId() + + ".tar.gz" ; - String save_new = working_directory + "/" + machine.getName() + "_new_" + String save_new = machine.getName() + "_new_" + machine.getComputationId() + ".tar.gz" ; String[] command = new String[]{ "/bin/mv", - save_new, save_name } ; + working_directory + "/" + save_new, + working_directory + "/" + save_name } ; try { Process p = Runtime.getRuntime().exec( command ) ; @@ -1459,12 +1595,11 @@ public class Client extends UnicastRemoteObject implements ServicesClient if( p.exitValue() == 0 ) { - System.out.println( "Last save OK" ) ; machine.setSave_last( save_name ) ; + System.out.println( "Last save OK" ) ; } else { System.err.println( "Last save NOK!" ) ; System.err.println( "Error: " ) ; -// printProcessError( p.getErrorStream() ) ; printProcessError( p ) ; } } catch( IOException e ) { @@ -1473,24 +1608,174 @@ public class Client extends UnicastRemoteObject implements ServicesClient } catch( InterruptedException e ) { e.printStackTrace() ; } + + // Changing on save neighbors + for( int i = 0 ; i < machine.getSaveNeighbors().size() ; i++ ) + { + try { + machine.getSaveNeighbors().get( i ).getStub().changeSaveName( save_new, save_name, machine.getComputationId() ) ; + } catch( RemoteException e ) { + System.err.println( "Unable to change save name on " + machine.getSaveNeighbors().get( i ).getName() + "!" ) ; + e.printStackTrace() ; + } + } + + // Informing the server + int ret = 1 ; + try { + ret = LocalHost.Instance().getServerStub().changeSaveName( LocalHost.Instance().getIP(), save_name ) ; + } catch( RemoteException e ) { + System.err.println( "Unable to inform the server about the new save name!" ) ; + e.printStackTrace() ; + } + + if( ret == 0 ) + { + System.out.println( "Successfully informing the server about the new save name." ) ; + } else { + System.err.println( "Problem on the server while informing it about the new save name!" ) ; + } + + // Ok here + lastSaveOk = true ; + } + + + public void changeSaveName( String _n1, String _n2, int _id ) + { + if( _n1 != null && _n1.length() > 0 ) + { + System.out.println( "Changing save name for processus " + _id + " ... " ) ; + + String[] command = new String[]{ "/bin/mv", + working_directory + "/" + _n1, + working_directory + "/" + _n2 } ; + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; + + if( p.exitValue() == 0 ) + { + System.out.println( "Change save name OK" ) ; + } else { + System.err.println( "Change save name NOK!" ) ; + System.err.println( "Error: " ) ; + printProcessError( p ) ; + } + } catch( IOException e ) { + System.err.println( "Error during save renaming:" ) ; + e.printStackTrace() ; + } catch( InterruptedException e ) { + e.printStackTrace() ; + } + } } + @Override - public void setSavingNeighbor( String _sn ) throws RemoteException + public void setSaveNeighbor( SaveNeighbor _sn ) { - if( _sn != null && _sn.length() > 0 ) + if( _sn != null ) { - ArrayList as = new ArrayList() ; + ArrayList as = new ArrayList() ; as.add( _sn ) ; - System.out.println( "Save neighbor: " + _sn ) ; + System.out.println( "Save neighbor: " + _sn.getName() ) ; machine.setSaveNeighbors( as ) ; } } + + + @Override + public void setSaveNeighbors( ArrayList _sn ) + { + if( _sn != null && _sn.size() > 0 ) + { + System.out.print( "Save neighbors: " ) ; + for( int i = 0 ; i < _sn.size() ; i++ ) + { + System.out.print( _sn.get( i ).getName() ) ; + + if( i != _sn.size() - 1 ) + { + System.out.print( ", " ) ; + } else { + System.out.println( "." ) ; + } + } + + machine.setSaveNeighbors( _sn ) ; + } + } + + @Override + public void addSaveNeighbor( SaveNeighbor _sn ) + { + if( _sn != null ) + { + System.out.println( "Adding save neighbor: " + _sn.getName() ) ; + + machine.getSaveNeighbors().add( _sn ) ; + } + } + + @Override - public int retrieveSave( String _saveName ) throws RemoteException + public void addSaveNeighbors( ArrayList _sn ) + { + if( _sn != null && _sn.size() > 0 ) + { + System.out.print( "Adding save neighbors: " ) ; + for( int i = 0 ; i < _sn.size() ; i++ ) + { + System.out.print( _sn.get( i ).getName() ) ; + + if( i != _sn.size() - 1 ) + { + System.out.print( ", " ) ; + } else { + System.out.println( "." ) ; + } + + machine.getSaveNeighbors().add( _sn.get( i ) ) ; + } + } + } + + + @Override + public void replaceSaveNeighbor( SaveNeighbor _old, SaveNeighbor _new ) + { + System.out.print( "Replacing a save neihgbor ... " ) ; + if( _old != null && _new != null ) + { + int i = 0 ; + boolean change = false ; + + for( i = 0 ; i < machine.getSaveNeighbors().size() ; i++ ) + { + if( machine.getSaveNeighbors().get( i ).getIPHost().equalsIgnoreCase( _old.getIPHost() ) ) + { + machine.getSaveNeighbors().set( i, _new ) ; + System.out.println( "Save neighbor successfully changed." ) ; + change = true ; + break ; + } + } + + if( ! change ) + { + System.out.println( "I am not concerned by the modification." ) ; + } + } + } + + + @Override + public int retrieveSave( String _saveName ) { if( _saveName != null ) { @@ -1498,41 +1783,56 @@ public class Client extends UnicastRemoteObject implements ServicesClient { machine.setSave_last( _saveName ) ; } else { - System.err.println( "I have no saving neighbor to contact!!" ) ; + System.err.println( "I have no save to retrieve!!" ) ; return 1 ; } // TODO NEIGHBORS !!!! - //System.out.println( "!!!! NEIGHBORS !!!!!" ) ; - System.out.print( "Retrieving a save on " + machine.getSaveNeighbors().get( 0 ) + " ..." ) ; - String[] command = new String[]{ "/usr/bin/scp", - machine.getSaveNeighbors().get( 0 ) + ":" - + working_directory + "/" + machine.getSave_last(), - working_directory } ; + boolean ok = false ; + int i = 0 ; + + while( ! ok && i < machine.getSaveNeighbors().size() ) + { + System.out.print( "Retrieving a save on " + machine.getSaveNeighbors().get( 0 ).getName() + " ... " ) ; - try { - Process p = Runtime.getRuntime().exec( command ) ; - p.waitFor() ; + String command[] = {} ; + + command = new String[]{ "/usr/bin/scp", + machine.getSaveNeighbors().get( i ).getIPHost() + ":" + + machine.getSaveNeighbors().get( i ).getWorkingDirectory() + "/" + + machine.getSave_last(), + working_directory } ; + + try { + Process p = Runtime.getRuntime().exec( command ) ; + p.waitFor() ; - if( p.exitValue() == 0 ) - { - System.out.println( "Archive successfully retrieved." ) ; - isRestartedSave = true ; - return 0 ; - } else { - System.err.println( "Archive not retrieved!" ) ; - System.err.println( "Error: " ) ; -// printProcessError( p.getErrorStream() ) ; - printProcessError( p ) ; -// error = true ; + if( p.exitValue() == 0 ) + { + System.out.println( "Archive successfully retrieved." ) ; + isRestartedSave = true ; + ok = true ; + } else { + System.err.println( "Archive not retrieved!" ) ; + System.err.println( "Error: " ) ; + + printProcessError( p ) ; + } + } catch( IOException e ) { + System.err.println( "Error during archive retrieve command: " ) ; + e.printStackTrace() ; + } catch( InterruptedException e ) { + e.printStackTrace() ; } - } catch( IOException e ) { - System.err.println( "Error during archive retrieve command: " ) ; - e.printStackTrace() ; -// error = true ; - } catch( InterruptedException e ) { - e.printStackTrace() ; -// error = true ; + + i++ ; + } + + if( ok ) + { + return 0 ; + } else { + System.err.println( "Unable to retrieve a save archive from any neighbor!" ) ; } } @@ -1540,6 +1840,7 @@ public class Client extends UnicastRemoteObject implements ServicesClient } + @Override public String getIPVM() throws RemoteException { @@ -1563,6 +1864,75 @@ public class Client extends UnicastRemoteObject implements ServicesClient } + public String getWorkingDirectory() + { + return working_directory ; + } + + + public Integer deployVM( String _name, String _archive, String _directory ) + { + if( _name != null && _name.length() > 0 && _archive != null && _name.length() > 0 ) + { + File file = new File( working_directory + "/" + _archive ) ; + if( ! file.exists() ) + { + System.err.println( "There is no archive named " + _archive + " in my working directory!" ) ; + file = null ; + return 2 ; + } else if( file.isDirectory() ) { + System.err.println( _archive + " is a directory!" ) ; + file = null ; + return 1 ; + } + + file = null ; + + machine.setName( _name ) ; + machine.setInitial_archive_name( _archive ) ; + machine.setDirectory( _directory ) ; + + if( machine.deployInitialVM() == 1 ) + { + System.err.println( "Unable to deploy the initial VM archive!" ) ; + } else { + return 0 ; + } + } + + return 1 ; + } + + + @Override + public void responseSave( boolean _b ) + { + synchronized( saveRequest ) + { + saveRequest.setStatus( _b ) ; + try { + saveRequest.notifyAll() ; + } catch( Exception e ) { + e.printStackTrace() ; + } + } + } + + + private class SaveRequest + { + boolean status ; + + SaveRequest() + { + status = false ; + } + + protected boolean getStatus() { return status ; } + + protected void setStatus( boolean _b ) { status = _b ; } + } + private class SaveProcess { boolean status ;