Modified manager output/protocol, added "basic" AI, made Asmodeus better
[progcomp2012.git] / manager / program.cpp
index ea5304c..3fca369 100644 (file)
@@ -10,6 +10,7 @@
 
 using namespace std;
 
+
 /**
  * Constructor
  * @param executablePath - path to the program that will be run
@@ -21,6 +22,18 @@ using namespace std;
  */
 Program::Program(const char * executablePath) : input(NULL), output(NULL), pid(0)
 {
+       //See if file exists...
+       FILE * file = fopen(executablePath, "r");
+       if (file != NULL)
+       {
+               fclose(file);
+       }
+       else
+       {
+               pid = -1;
+               return;
+       }
+       
        int readPipe[2]; int writePipe[2];
        assert(pipe(readPipe) == 0);
        assert(pipe(writePipe) == 0);
@@ -44,8 +57,8 @@ Program::Program(const char * executablePath) : input(NULL), output(NULL), pid(0
 
 
                execl(executablePath, executablePath, (char*)(NULL)); ///Replace process with desired executable
-               fprintf(stderr, "Program::Program - Could not run program \"%s\"!\n", executablePath);
-               exit(EXIT_FAILURE); //We will probably have to terminate the whole program if this happens
+               //fprintf(stderr, "Program::Program - Could not run program \"%s\"!\n", executablePath);
+               //exit(EXIT_FAILURE); //We will probably have to terminate the whole program if this happens
        }
        else
        {
@@ -66,17 +79,28 @@ Program::Program(const char * executablePath) : input(NULL), output(NULL), pid(0
  */
 Program::~Program()
 {
-       if (kill(pid, 0) == 0) //Check if the process created is still running...
+       if (Running()) //Check if the process created is still running...
        {
                fputc(EOF, output); //If it was, tell it to stop with EOF
-               sleep(1); //Give it 1 second to respond...
-               if (kill(pid, 0) == 0) //Check if its still running
+
+               TimerThread timer(2); //Wait for 2 seconds
+               timer.Start();          
+               while (!timer.Finished())
                {
-                       kill(pid, 9); //Slay the infidel mercilessly!
+                       if (!Running())
+                       {
+                               timer.Stop();
+                               break;
+                       }
                }
+               timer.Stop();
+               kill(pid, SIGKILL);
+       }
+       if (pid > 0)
+       {
+               fclose(input);
+               fclose(output);
        }
-       fclose(input);
-       fclose(output);
        
 }
 
@@ -88,21 +112,25 @@ Program::~Program()
  * Sends a message to the wrapped AI program
  * WARNING: Always prints a new line after the message (so don't include a new line)
  *     This is because everything is always line buffered.
+ * @returns true if the message was successfully sent; false if it was not (ie: the process was not running!)
  */
 bool Program::SendMessage(const char * print, ...)
 {
-       if (kill(pid, 0) != 0) //Is the process running...
+       if (!Running()) //Is the process running...
                return false; 
 
        va_list ap;
        va_start(ap, print);
 
-       vfprintf(output, print, ap);
-       fprintf(output, "\n");
-
+       if (vfprintf(output, print, ap) < 0 || fprintf(output, "\n") < 0)
+       {
+               va_end(ap);
+               return false;
+       }
+       va_end(ap);
        
 
-       va_end(ap);
+
 
        return true;
 }
@@ -116,7 +144,7 @@ bool Program::SendMessage(const char * print, ...)
  */
 bool Program::GetMessage(string & buffer, double timeout)
 {
-       if (kill(pid, 0) != 0)
+       if (!Running())
                return false;
 
        assert(&buffer != NULL);
@@ -157,7 +185,9 @@ bool Program::GetMessage(string & buffer, double timeout)
  */
 bool Program::Running() const
 {
-       return (kill(pid,0) == 0);
+       return (pid > 0 && kill(pid,0) == 0);
 }
 
 
+
+

UCC git Repository :: git.ucc.asn.au