Example #1
0
static int set_sdl_video_size(unsigned short int w, unsigned short int h)
{
	if (window)
		SDL_DestroyWindow(window);
	if (!w || !h) {
		w = 640;
		h = 480;
		if (flags & SDL_WINDOW_FULLSCREEN) {
			SDL_DisplayMode mode;
			if (!SDL_GetDesktopDisplayMode(0, &mode)) {
				w = mode.w;
				h = mode.h;
			} else
				log_e("SDL_GetDesktopDisplayMode: %s",
				      SDL_GetError());
		}
	}
	log_i("%ux%u", w, h);
	window = SDL_CreateWindow("greedy",
				  SDL_WINDOWPOS_CENTERED,
				  SDL_WINDOWPOS_CENTERED,
				  w, h, flags);
	if (!window)
		log_p("SDL_CreateWindow: %s", SDL_GetError());
	SDL_Delay(50);
	return 0;
}
 shared_ptr<arma::mat> log_p_matrix(shared_ptr<arma::mat> z) {
   shared_ptr<arma::mat> log_p( new arma::mat(z->n_rows, z->n_cols) );
   for(arma::uword j=0; j<z->n_cols; ++j) {
     for(arma::uword i=0; i<z->n_rows; ++i) {
       (*log_p)(i, j) = compute_log_p((*z)(i, j));
     }
   }
   return log_p;    
 }
 // TODO: Clean up these similar functions
 shared_ptr<arma::mat> log_p_matrix(shared_ptr<arma::mat> w,
                                    shared_ptr<arma::mat> z,
                                    shared_ptr<arma::mat> z_higher,
                                    shared_ptr<arma::mat> z_bias) {
   arma::mat param = (*w) * (*z_higher);
   if (z_bias != NULL) {
     assert(z_bias->n_cols == 1);
     param.each_col() += z_bias->col(0);
   }
   shared_ptr<arma::mat> log_p( new arma::mat(z->n_rows, z->n_cols) );
   for(arma::uword j=0; j<z->n_cols; ++j) {
     for(arma::uword i=0; i<z->n_rows; ++i) {
       // TODO inline?
       (*log_p)(i, j) = compute_log_p((*z)(i, j), param(i, j));
     }
   }
   return log_p;
 }  
Example #4
0
//-----------------------------------------------------------------------------
int init( int argc, char* argv[] ) {
  mythread = osthread_p( new osthread_c( argv[0] ) );

  quit = false;
  //quit.store( 0, std::memory_order_seq_cst );
  mythread->pid = getpid();

  if( argc < 4 ) {
    printf( "ERROR: client process[%s] was not given enough arguments\nExiting client process.\n", mythread->name );
    exit( 1 );
  }
  rand_seed = (unsigned) atoi( argv[1] );
  min_cycles = (unsigned) atoi( argv[2] );
  max_cycles = (unsigned) atoi( argv[3] );

  //printf( "%s has started with rand_seed[%d], min_cycles[%d], max_cycles[%d].\n", client_name.c_str(), rand_seed, min_cycles, max_cycles ); 
    
  srand( rand_seed );

  rand_delta = max_cycles - min_cycles;

  // open log * only for debugging client process ipc using test_client.cpp*
  char logname[64];
  sprintf( logname, "%s.log", mythread->name );
  info = log_p( new log_c( logname, true ) );
  log_c::error_e log_err = info->allocate( LOG_CAPACITY );
  if( log_err != log_c::ERROR_NONE ) {
    sprintf( spstr, "(client-process.cpp) init() failed calling log_c::allocate(...).\nExiting\n" ); 
    printf( spstr );
    exit( 1 );
  }

  // * install SIGTERM signal handler *
  struct sigaction action;
  memset( &action, 0, sizeof(struct sigaction) );
  action.sa_handler = term_sighandler;
  sigaction( SIGTERM, &action, NULL );

  // close the coordinator side channels
  __close( FD_TIMER_TO_COORDINATOR_READ_CHANNEL );
  __close( FD_TIMER_TO_COORDINATOR_WRITE_CHANNEL );
  __close( FD_WAKEUP_TO_COORDINATOR_READ_CHANNEL );
  __close( FD_WAKEUP_TO_COORDINATOR_WRITE_CHANNEL );
  __close( FD_PREYCONTROLLER_TO_COORDINATOR_READ_CHANNEL );
  __close( FD_PREDCONTROLLER_TO_COORDINATOR_READ_CHANNEL );
  __close( FD_PREDPLANNER_TO_COORDINATOR_READ_CHANNEL );
  __close( FD_COORDINATOR_TO_PREYCONTROLLER_WRITE_CHANNEL );
  __close( FD_COORDINATOR_TO_PREDCONTROLLER_WRITE_CHANNEL );
  __close( FD_COORDINATOR_TO_PREDPLANNER_WRITE_CHANNEL );

  if( strcmp( mythread->name, "prey-controller" ) == 0 ) {
    read_fd = FD_COORDINATOR_TO_PREYCONTROLLER_READ_CHANNEL;
    write_fd = FD_PREYCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL;

    // close the other channels that should not be accessed
    __close( FD_PREDCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREDCONTROLLER_READ_CHANNEL );
    __close( FD_PREDPLANNER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREDPLANNER_READ_CHANNEL );
  } else if( strcmp( mythread->name, "pred-controller" ) == 0 ) {
    read_fd = FD_COORDINATOR_TO_PREDCONTROLLER_READ_CHANNEL;
    write_fd = FD_PREDCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL;

    // close the other channels that should not be accessed
    __close( FD_PREYCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREYCONTROLLER_READ_CHANNEL );
    __close( FD_PREDPLANNER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREDPLANNER_READ_CHANNEL );
  } else if( strcmp( mythread->name, "pred-planner" ) == 0 ) {
    read_fd = FD_COORDINATOR_TO_PREDPLANNER_READ_CHANNEL;
    write_fd = FD_PREDPLANNER_TO_COORDINATOR_WRITE_CHANNEL;

    // close the other channels that should not be accessed
    __close( FD_PREYCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREYCONTROLLER_READ_CHANNEL );
    __close( FD_PREDCONTROLLER_TO_COORDINATOR_WRITE_CHANNEL );
    __close( FD_COORDINATOR_TO_PREDCONTROLLER_READ_CHANNEL );
  } else {
    //printf( "ERROR: unable to reference correct program\nExiting\n" );
    return 1;
  }
  //printf( "%s write_fd:%d; read_fd:%d\n", client_name.c_str(), write_fd, read_fd );

  assert( rand_delta < RAND_MAX && rand_delta != 0 );

  // build the notification prototypes
  // - state notification -
  state_note.source = notification_t::CLIENT;
  state_note.type = notification_t::READ;
  state_note.pid = mythread->pid;

  // - command notification -
  command_note.source = notification_t::CLIENT;
  command_note.type = notification_t::WRITE;
  command_note.pid = mythread->pid;

  // - block notification -
  yield_note.period = max_cycles;
  yield_note.source = notification_t::CLIENT;
  yield_note.type = notification_t::IDLE;
  yield_note.pid = mythread->pid;

  return 0;
}
Example #5
0
autoClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable_dw (Discriminant me, TableOfReal thee, int poolCovarianceMatrices, int useAprioriProbabilities, double alpha, double minProb, autoTableOfReal *displacements) {
    try {
        long g = Discriminant_getNumberOfGroups (me);
        long p = Eigen_getDimensionOfComponents (my eigen.get());
        long m = thy numberOfRows;

        if (p != thy numberOfColumns) Melder_throw
            (U"The number of columns does not agree with the dimension of the discriminant.");

        autoNUMvector<double> log_p (1, g);
        autoNUMvector<double> log_apriori (1, g);
        autoNUMvector<double> ln_determinant (1, g);
        autoNUMvector<double> buf (1, p);
        autoNUMvector<double> displacement (1, p);
        autoNUMvector<double> x (1, p);
        autoNUMvector<SSCP> sscpvec (1, g);
        autoSSCP pool = SSCPList_to_SSCP_pool (my groups.get());
        autoClassificationTable him = ClassificationTable_create (m, g);
        NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, m);
        autoTableOfReal adisplacements = Data_copy (thee);

        // Scale the sscp to become a covariance matrix.

        for (long i = 1; i <= p; i ++) {
            for (long k = i; k <= p; k ++) {
                pool -> data [k] [i] = pool -> data [i] [k] /= pool -> numberOfObservations - g;
            }
        }

        double lnd;
        autoSSCPList agroups;
        SSCPList groups;
        if (poolCovarianceMatrices) {
            // Covariance matrix S can be decomposed as S = L.L'. Calculate L^-1.
            // L^-1 will be used later in the Mahalanobis distance calculation:
            // v'.S^-1.v == v'.L^-1'.L^-1.v == (L^-1.v)'.(L^-1.v).

            NUMlowerCholeskyInverse (pool -> data, p, & lnd);
            for (long j = 1; j <= g; j ++) {
                ln_determinant [j] = lnd;
                sscpvec [j] = pool.get();
            }
            groups = my groups.get();
        } else {
            //Calculate the inverses of all group covariance matrices.
            // In case of a singular matrix, substitute inverse of pooled.

            agroups = Data_copy (my groups.get());
            groups = agroups.get();
            long npool = 0;
            for (long j = 1; j <= g; j ++) {
                SSCP t = groups->at [j];
                long no = (long) floor (SSCP_getNumberOfObservations (t));
                for (long i = 1; i <= p; i ++) {
                    for (long k = i; k <= p; k ++) {
                        t -> data [k] [i] = t -> data [i] [k] /= no - 1;
                    }
                }
                sscpvec [j] = groups->at [j];
                try {
                    NUMlowerCholeskyInverse (t -> data, p, & ln_determinant [j]);
                } catch (MelderError) {
                    // Try the alternative: the pooled covariance matrix.
                    // Clear the error.

                    Melder_clearError ();
                    if (npool == 0) {
                        NUMlowerCholeskyInverse (pool -> data, p, & lnd);
                    }
                    npool ++;
                    sscpvec [j] = pool.get();
                    ln_determinant [j] = lnd;
                }
            }
            if (npool > 0) {
                Melder_warning (npool, U" groups use pooled covariance matrix.");
            }
        }

        // Labels for columns in ClassificationTable

        for (long j = 1; j <= g; j ++) {
            const char32 *name = Thing_getName (my groups->at [j]);
            if (! name) {
                name = U"?";
            }
            TableOfReal_setColumnLabel (him.get(), j, name);
        }

        // Normalize the sum of the apriori probabilities to 1.
        // Next take ln (p) because otherwise probabilities might be too small to represent.

        double logg = log (g);
        NUMvector_normalize1 (my aprioriProbabilities, g);
        for (long j = 1; j <= g; j ++) {
            log_apriori[j] = ( useAprioriProbabilities ? log (my aprioriProbabilities[j]) : - logg );
        }

        // Generalized squared distance function:
        // D^2(x) = (x - mu)' S^-1 (x - mu) + ln (determinant(S)) - 2 ln (apriori)

        for (long i = 1; i <= m; i ++) {
            SSCP winner;
            double norm = 0, pt_max = -1e308;
            long iwinner = 1;
            for (long k = 1; k <= p; k ++) {
                x [k] = thy data [i] [k] + displacement [k];
            }
            for (long j = 1; j <= g; j ++) {
                SSCP t = groups->at [j];
                double md = mahalanobisDistanceSq (sscpvec [j] -> data, p, x.peek(), t -> centroid, buf.peek());
                double pt = log_apriori [j] - 0.5 * (ln_determinant [j] + md);
                if (pt > pt_max) {
                    pt_max = pt;
                    iwinner = j;
                }
                log_p [j] = pt;
            }
            for (long j = 1; j <= g; j ++) {
                norm += log_p [j] = exp (log_p [j] - pt_max);
            }

            for (long j = 1; j <= g; j ++) {
                his data [i] [j] = log_p [j] / norm;
            }

            // Save old displacement, calculate new displacement

            winner = groups->at [iwinner];
            for (long k = 1; k <= p; k ++) {
                adisplacements -> data [i] [k] = displacement [k];
                if (his data [i] [iwinner] > minProb) {
                    double delta_k = winner -> centroid [k] - x [k];
                    displacement [k] += alpha * delta_k;
                }
            }
        }
        *displacements = adisplacements.move();
        return him;
    } catch (MelderError) {
        Melder_throw (U"ClassificationTable for Weenink procedure not created.");
    }
}
Example #6
0
ClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable (Discriminant me, TableOfReal thee,
        int poolCovarianceMatrices, int useAprioriProbabilities) {
	try {
		long g = Discriminant_getNumberOfGroups (me);
		long p = Eigen_getDimensionOfComponents (me);
		long m = thy numberOfRows;

		if (p != thy numberOfColumns) Melder_throw
			(U"The number of columns does not agree with the dimension of the discriminant.");

		autoNUMvector<double> log_p (1, g);
		autoNUMvector<double> log_apriori (1, g);
		autoNUMvector<double> ln_determinant (1, g);
		autoNUMvector<double> buf (1, p);
		autoNUMvector<SSCP> sscpvec (1, g);
		autoSSCP pool = SSCPs_to_SSCP_pool (my groups);
		autoClassificationTable him = ClassificationTable_create (m, g);
		NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, m);

		// Scale the sscp to become a covariance matrix.

		for (long i = 1; i <= p; i++) {
			for (long k = i; k <= p; k++) {
				pool -> data[k][i] = (pool -> data[i][k] /= (pool -> numberOfObservations - g));
			}
		}

		double lnd;
		autoSSCPs agroups = 0; SSCPs groups;
		if (poolCovarianceMatrices) {
			/*
				Covariance matrix S can be decomposed as S = L.L'. Calculate L^-1.
				L^-1 will be used later in the Mahalanobis distance calculation:
				v'.S^-1.v == v'.L^-1'.L^-1.v == (L^-1.v)'.(L^-1.v).
			*/

			NUMlowerCholeskyInverse (pool -> data, p, &lnd);
			for (long j = 1; j <= g; j++) {
				ln_determinant[j] = lnd;
				sscpvec[j] = pool.peek();
			}
			groups = (SSCPs) my groups;
		} else {
			// Calculate the inverses of all group covariance matrices.
			// In case of a singular matrix, substitute inverse of pooled.

			agroups.reset (Data_copy ( (SSCPs) my groups)); groups = agroups.peek();
			long npool = 0;
			for (long j = 1; j <= g; j++) {
				SSCP t = (SSCP) groups -> item[j];
				long no = (long) floor (SSCP_getNumberOfObservations (t));
				for (long i = 1; i <= p; i++) {
					for (long k = i; k <= p; k++) {
						t -> data[k][i] = (t -> data[i][k] /= (no - 1));
					}
				}
				sscpvec[j] = (SSCP) groups -> item[j];
				try {
					NUMlowerCholeskyInverse (t -> data, p, &ln_determinant[j]);
				} catch (MelderError) {
					// Try the alternative: the pooled covariance matrix.
					// Clear the error.

					Melder_clearError ();
					if (npool == 0) {
						NUMlowerCholeskyInverse (pool -> data, p, &lnd);
					}
					npool++;
					sscpvec[j] = pool.peek();
					ln_determinant[j] = lnd;
				}
			}
			if (npool > 0) {
				Melder_warning (npool, U" groups use pooled covariance matrix.");
			}
		}

		// Labels for columns in ClassificationTable

		for (long j = 1; j <= g; j++) {
			const char32 *name = Thing_getName ( (Thing) my groups -> item[j]);
			if (! name) {
				name = U"?";
			}
			TableOfReal_setColumnLabel (him.peek(), j, name);
		}

		// Normalize the sum of the apriori probabilities to 1.
		// Next take ln (p) because otherwise probabilities might be too small to represent.

		NUMvector_normalize1 (my aprioriProbabilities, g);
		double logg = log (g);
		for (long j = 1; j <= g; j++) {
			log_apriori[j] = useAprioriProbabilities ? log (my aprioriProbabilities[j]) : - logg;
		}

		// Generalized squared distance function:
		// D^2(x) = (x - mu)' S^-1 (x - mu) + ln (determinant(S)) - 2 ln (apriori)

		for (long i = 1; i <= m; i++) {
			double norm = 0, pt_max = -1e38;
			for (long j = 1; j <= g; j++) {
				SSCP t = (SSCP) groups -> item[j];
				double md = mahalanobisDistanceSq (sscpvec[j] -> data, p, thy data[i], t -> centroid, buf.peek());
				double pt = log_apriori[j] - 0.5 * (ln_determinant[j] + md);
				if (pt > pt_max) {
					pt_max = pt;
				}
				log_p[j] = pt;
			}
			for (long j = 1; j <= g; j++) {
				norm += (log_p[j] = exp (log_p[j] - pt_max));
			}
			for (long j = 1; j <= g; j++) {
				his data[i][j] = log_p[j] / norm;
			}
		}
		return him.transfer();
	} catch (MelderError) {
		Melder_throw (U"ClassificationTable from Discriminant & TableOfReal not created.");
	}
}
Example #7
0
//-----------------------------------------------------------------------------
void init( int argc, char* argv[] ) {
  //quit = false;
  quit = 0;
  //quit.store( 0, std::memory_order_seq_cst  );
  //quit.store( 0, std::memory_order_relaxed  );

  actual_timer_events = 0;
  caught_timer_events = 0;

  // * set variables from constants *
  cpu = DEFAULT_CPU;

  // * install SIGTERM signal handler *
  struct sigaction action;
  memset( &action, 0, sizeof(struct sigaction) );
  action.sa_handler = term_sighandler;
  sigaction( SIGTERM, &action, NULL );

  // * open log *
#ifdef DO_LOGGING
  info = log_p( new log_c( "info.log", true ) );
  log_c::error_e log_err = info->allocate( LOG_CAPACITY );
  if( log_err != log_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling log_c::allocate(...).\nExiting\n" ); 
    printf( spstr );
    exit( 1 );
  }
#endif

  // * get the process identifier *
  coordinator_pid = getpid( );

  sprintf( spstr, "coordinator pid: %d\n", coordinator_pid );
  if( info ) info->write( spstr );
  printf( "%s", spstr );

  // * bind the process to a single cpu *
  if( cpu_c::bind( coordinator_pid, cpu ) != cpu_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling cpu_c::_bind(coordinator_pid,DEFAULT_CPU).\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    exit( 1 );
  }

  // * set the process to be scheduled with realtime policy and max priority *
  if( scheduler_c::set_realtime_policy( coordinator_pid, coordinator_os_priority ) != scheduler_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling schedule_set_realtime_max(coordinator_pid,coordinator_priority).\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    exit( 1 );
  }
  sprintf( spstr, "coordinator os priority: %d\n", coordinator_os_priority );
  if( info ) info->write( spstr );
  printf( "%s", spstr );

  // * determine if the OS supports high resolution timers *
  struct timespec res;
  clock_getres( CLOCK_MONOTONIC, &res );
  double clock_res = timespec_to_real( res );

  sprintf( spstr, "clock resolution (secs): %10.9f\n", clock_res );
  if( info ) info->write( spstr );
  printf( "%s", spstr );
 
  if( res.tv_sec != 0 && res.tv_nsec != 1 ) {
    sprintf( spstr, "(coordinator.cpp) init() failed.  The host operating system does not support high resolution timers.  Consult your system documentation on enabling this feature.\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    exit( 1 );
  }

  // * get the cpu speed *
  if( cpu_c::get_speed( cpu_speed, cpu ) != cpu_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling cpu_c::get_frequency(cpu_speed,cpu)\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    exit( 1 );
  }
  sprintf( spstr, "cpu speed(hz): %llu\n", cpu_speed );
  if( info ) info->write( spstr );
  printf( "%s", spstr );

  // * initialize pipes *
  if( !init_pipes() ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling init_pipes()\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    exit( 1 );
  }

  // * initialize shared memory *
  msgbuffer = client_message_buffer_c( CLIENT_MESSAGE_BUFFER_NAME, CLIENT_MESSAGE_BUFFER_MUTEX_NAME, true );
  if( msgbuffer.open( ) != client_message_buffer_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling actuator_msg_buffer_c.open(...,true)\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    close_pipes( );
    exit( 1 );
  }

  // * initialize block detection, i.e. wakeup * 
  wakeup_os_priority = coordinator_os_priority - 2;
  wakeup_enabled.store( 1 );
  // set up the wakeup overhead to minimize what changes inside
  wakeup_note.source = notification_t::WAKEUP;
  wakeup_write_fd = FD_WAKEUP_TO_COORDINATOR_WRITE_CHANNEL;

  if( info ) info->flush();

  // lock into memory to prevent pagefaults.  do last before main loop
  mlockall( MCL_CURRENT );

/*
  if( scheduler_c::create( wakeup_thread, wakeup_os_priority, wakeup ) != scheduler_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling wakeup_thread.create(...,wakeup)\nExiting\n" );
    if( info ) info->write( spstr );
    printf( "%s", spstr );
    msgbuffer.close( );
    close_pipes( );
    exit( 1 );
  }
*/
/*
  if( scheduler_c::get_priority( wakeup_thread, wakeup_os_priority ) != scheduler_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling get_priority(wakeup_thread,...)\nExiting\n" );
    info.write( spstr );
    msgbuffer.close( );
    close_pipes( );
    // kill the wakeup thread?
    exit(1);
  }
*/
  sprintf( spstr, "wakeup thread created... priority:%d\n", wakeup_os_priority );
  if( info ) info->write( spstr );
  printf( "%s", spstr );

  // * initialize clients *
  sprintf( spstr, "initializing clients\n" );
  if( info ) info->write( spstr );
  printf( "%s", spstr );

  scheduler_c::error_e schedulererr;

  double controller_floor_seconds = 0.001;
  double controller_ceiling_seconds = 0.01;
  double planner_floor_seconds = 0.01;
  double planner_ceiling_seconds = 0.5;
  std::string controller_seed = "1";

  char numbuf[16];

  sprintf(numbuf,"%llu",seconds_to_cycles(controller_floor_seconds, cpu_speed));
  std::string controller_floor = numbuf;
  sprintf(numbuf,"%llu",seconds_to_cycles(controller_ceiling_seconds, cpu_speed));
  std::string controller_ceiling = numbuf;
  sprintf(numbuf,"%llu",seconds_to_cycles(planner_floor_seconds, cpu_speed));
  std::string planner_floor = numbuf;
  sprintf(numbuf,"%llu",seconds_to_cycles(planner_ceiling_seconds, cpu_speed));
  std::string planner_ceiling = numbuf;

  CLIENT_OS_MAX_PRIORITY = coordinator_os_priority - 1;
  CLIENT_OS_MIN_PRIORITY = coordinator_os_priority - 3;
  int client_os_priority_step = CLIENT_OS_MAX_PRIORITY - CLIENT_OS_MIN_PRIORITY;

  log_c* pinfo = NULL;
  if( info ) pinfo = info.get();
/*
  // - create a processor -
  processor = boost::shared_ptr<processor_c>( new processor_c( "processor_0" ) );
  timesink_p processor_timesink = boost::dynamic_pointer_cast<timesink_c>( processor );
  processor_thread = boost::dynamic_pointer_cast<thread_c>( processor );
  processor->info = pinfo;

  // - create dynamics process -
  dynamics = boost::shared_ptr<dynamics_c>( new dynamics_c( "dynamics", processor_timesink, cpu_speed ) );
  dynamics->info = pinfo;
  processor->run_queue.push( dynamics );

  // - create prey processes -
  prey = boost::shared_ptr<timesink_c>( new timesink_c( "prey", processor_timesink, scheduler_c::PROGRESS) );
  prey->info = pinfo;
  //prey->priority = 0;
  processor->run_queue.push( prey );
  prey_thread = boost::dynamic_pointer_cast<thread_c>(prey);
*/
  prey_controller = boost::shared_ptr<osthread_c>( new osthread_c( "prey_controller", prey, &select, &read_notifications, &process_notifications, pinfo ) );
  prey_controller->_max_os_priority = CLIENT_OS_MAX_PRIORITY;
  prey_controller->_min_os_priority = CLIENT_OS_MIN_PRIORITY;
  prey_controller->_os_priority_step = client_os_priority_step;
  prey_controller->_cpu_speed = cpu_speed;
  prey_controller->priority = 0;
  prey_controller->desired_period = seconds_to_cycles( controller_ceiling_seconds, cpu_speed );
  //prey->run_queue.push( prey_controller );

  schedulererr = scheduler_c::create( prey_controller, 3, DEFAULT_CPU, "client-process", "prey-controller", controller_seed.c_str(), controller_floor.c_str(), controller_ceiling.c_str() );
  //prey_controller->block();

  sprintf( spstr, "created prey-controller: pid[%d], _os_priority[%d], _os_priority_step[%d], _max_os_priority[%d], _min_os_priority[%d]\n", prey_controller->pid, prey_controller->_os_priority, prey_controller->_os_priority_step, prey_controller->_max_os_priority, prey_controller->_min_os_priority );
  if( info ) info->write( spstr );
/*
  // - create predator processes -
  pred = boost::shared_ptr<timesink_c>( new timesink_c( "pred", processor_timesink, scheduler_c::PROGRESS) );
  pred->info = pinfo;
  //prey->priority = 0;
  processor->run_queue.push( pred );
  pred_thread = boost::dynamic_pointer_cast<thread_c>(pred);

  pred_controller = boost::shared_ptr<osthread_c>( new osthread_c( "pred_controller", pred, &select, &read_notifications, &process_notifications, pinfo ) );
  pred_controller->_max_os_priority = CLIENT_OS_MAX_PRIORITY;
  pred_controller->_min_os_priority = CLIENT_OS_MIN_PRIORITY;
  pred_controller->_os_priority_step = client_os_priority_step;
  pred_controller->_cpu_speed = cpu_speed;
  pred_controller->priority = 0;
  pred_controller->desired_period = seconds_to_cycles( controller_ceiling_seconds, cpu_speed );
  pred->run_queue.push( pred_controller );

  schedulererr = scheduler_c::create( pred_controller, 3, DEFAULT_CPU, "client-process", "pred-controller", controller_seed.c_str(), controller_floor.c_str(), controller_ceiling.c_str() );
  //prey_controller->block();

  sprintf( spstr, "created pred-controller: pid[%d], _os_priority[%d], _os_priority_step[%d], _max_os_priority[%d], _min_os_priority[%d]\n", pred_controller->pid, pred_controller->_os_priority, pred_controller->_os_priority_step, pred_controller->_max_os_priority, pred_controller->_min_os_priority );
  if( info ) info->write( spstr );
*/
  // * initialize timer *
  // set up the timer handler overhead to minimize what changes inside
  timer_note.source = notification_t::TIMER;
  timer_write_fd = FD_TIMER_TO_COORDINATOR_WRITE_CHANNEL;

  // create the timer
  if( timer.create( timer_sighandler, RTTIMER_SIGNAL ) != timer_c::ERROR_NONE ) {
    sprintf( spstr, "(coordinator.cpp) init() failed calling timer.create(timer_sighandler,RTTIMER_SIGNAL)\nExiting\n" );
    pthread_cancel( wakeup_thread );
    int status;
    if( pred_controller ) {
      kill( pred_controller->pid, SIGTERM );
      waitpid( pred_controller->pid, &status, 0 );
    }

    if( prey_controller ) {
      kill( prey_controller->pid, SIGTERM );
      waitpid( prey_controller->pid, &status, 0 );
    }

    if( info ) info->write( spstr );
    printf( "%s", spstr );
    msgbuffer.close( );
    close_pipes( );
    exit( 1 );
  }

  // * initialize other resources *

  //clients.push_back( prey_controller );
  //clients.push_back( pred_controller );
  //clients.push_back( pred_planner );
}