
/*
 * master.hh
 * Copyright (C) 2002 by John Heidemann <johnh@isi.edu>
 * $Id: master.hh,v 1.6 2002/04/05 21:36:56 johnh Exp $
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License,
 * version 2, as published by the Free Software Foundation.
 * 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License along
 * with this program; if not, write to the Free Software Foundation, Inc.,
 * 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
 *
 */

/*
 * master.hh implements the master process functionality
 */


#include <list>
#include <map>

#include "gen.hh"

class MasterRouter : public BaseRouter {
	// the master's view of routers (from the config file)
	int fd_;
	int pid_;
	int udp_port_;
public:
	MasterRouter(int id) : BaseRouter(id), fd_(-1), pid_(0), udp_port_(0) {}
	void assign(int fd, int pid, int udp_port);
	int port() { return udp_port_; }
	int fd() { return fd_; }
	int pid() { return pid_; }
};

typedef map<int, MasterRouter*> RouterMap;

/*
 * class Master represents all of the state
 * needed by the manager, including
 * the config file info,
 * plus the ports of all the routers.
 */
class Master {
	// all state held by the master
protected:
	int stage_;
	int num_nodes_;
	int loss_rate_;
	bool any_external_routes_;

	list<Edge> edges_;
	RouterMap routers_;

	int master_port_;
	int master_socket_;
	list<int> router_fds_;

	MasterRouter *find_or_make_router(int id);

	void input_model(istream &instr);
	void create_master_tcp();
	void create_router_processes();
	void loop();

	void output_stage_1();

 public:
	Master(istream &instr);

	void set_stage(int stage) { stage_ = stage; }
	void num_nodes(int nn) {num_nodes_ = nn;}
	void loss_rate(int lr) {loss_rate_ = lr;}

	void add_edge(int a, int b);
	void add_internal_route(int id, Route *rte);
	void add_external_route(int id, Route *rte);

};
