/****************************************************************************/
/* Copyright (c) 2000 MBARI                                                 */
/* MBARI Proprietary Information. All rights reserved.                      */
/****************************************************************************/
/* Summary  :                                                               */
/* Filename : EventTriggers.cc                                              */
/* Author   :                                                               */
/* Project  :                                                               */
/* Version  : 1.0                                                           */
/* Created  : 02/07/2000                                                    */
/* Modified :                                                               */
/* Archived :                                                               */
/****************************************************************************/
/* Modification History:                                                    */
/****************************************************************************/
#include <stdio.h>
#include <sys/kernel.h>
#include <errno.h>
#include "EventTriggers.h"
#include "TaskServer.h"
#include "Syslog.h"


EventTriggers::EventTriggers(pid_t observer)
{
  _observer = observer;
}


EventTriggers::~EventTriggers()
{
}


void EventTriggers::add(EventCode eventCode)
{
  Boolean debug = True;

  EventTrigger *eventTrigger;
  // Check to see if already registered
  for (int i = 0; i < _eventTriggers.size(); i++) {
    _eventTriggers.get(i, &eventTrigger);
    if (eventTrigger->notification->eventCode == eventCode) {
      // Already registered
      return;
    }
  }

  eventTrigger = new EventTrigger();
  eventTrigger->notification = new TaskServer::Event();
  eventTrigger->notification->eventCode = eventCode;
  eventTrigger->notification->forward = True;

  // Server pid will be filled in by associated server
  eventTrigger->notification->serverPid = NoPid;

  dprintf("**** EventTriggers::add() - attaching proxy");

  if ((eventTrigger->proxy = 
       qnx_proxy_attach(_observer, 
			(char *)eventTrigger->notification, 
			sizeof(TaskServer::Event), -1)) == -1) {

    char errorBuf[256];
    sprintf(errorBuf, "EventTriggers::add() - %s", strerror(errno));
    throw Exception(errorBuf);
  }

  // Add to list
  _eventTriggers.add(&eventTrigger);
}



void EventTriggers::notify(EventCode eventCode)
{
  Boolean debug = False;
  dprintf("EventTriggers::notify() - eventCode=%d\n", eventCode);

  EventTrigger *eventTrigger;

  for (int i = 0; i < _eventTriggers.size(); i++) {
    _eventTriggers.get(i, &eventTrigger);

    if (eventTrigger->notification->eventCode == eventCode) {

      dprintf("EventTriggers::notify() - "
	      "triggering proxy %d, send to pid %d\n",
	      eventTrigger->proxy, _observer);

      eventTrigger->notification->forward = True;

      if (Trigger(eventTrigger->proxy) == (pid_t )-1) {
	Syslog::write("EventTriggers::notify() - Trigger() failed: %s\n",
		      strerror(errno));
      }

      return;
    }
  }

  // Event is not yet registered
  dprintf("EventTriggers::notify() - not yet registered; add()\n");
  add(eventCode);
  dprintf("EventTriggers::notify() - NOW notify()\n");
  notify(eventCode);
}
