/*
 *
 *
 *    select.h
 *
 *    C++ source code for enhanced select() and support types.
 *
 *    =========================================================================
 *
 *    Copyright (C) 2003 by Matt Roberts, KK5JY.
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License as published by the Free Software Foundation; either
 *    version 2.1 of the License, or (at your option) any later version.
 *
 *    This library 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
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 *    =========================================================================
 *
 *
 */


#ifndef __MY_SELECT_H
#define __MY_SELECT_H

	#include <list>

	#include <sys/select.h>
	#include <sys/types.h>
	#include <unistd.h>
	#include <time.h>

	#include <my++/device.h>

	namespace my {

		/*
		 *
		 *   fdset
		 *
		 */

		struct fdset : public ::fd_set {
			private:
				std::list<int> __fds;
				::fd_set __fd_set;

			public:
				fdset(void);
				explicit fdset(const ::fd_set &f);
				explicit fdset(const my::fdset &f);

			public:
				my::fdset &operator = (const ::fd_set &f);
				my::fdset &operator = (const my::fdset &f);

			public:
				void zero  (void)   { __fds.clear();       };

				void set   (int fd) { __fds.push_back(fd); };
				void clear (int fd) { __fds.remove(fd);    };
				bool isset (int fd) { return (bool)(FD_ISSET(fd, &__fd_set)); };

				void set   (my::device &d) { __fds.push_back(d.getfd()); };
				void clear (my::device &d) { __fds.remove(d.getfd());    };
				bool isset (my::device &d) { return (bool)(FD_ISSET(d.getfd(), &__fd_set)); };

				int maxfd (void);

			protected:
				void rebuild (void);
				::fd_set *c_set (void) { rebuild(); return &__fd_set; };

			protected:
				friend int my::select (my::fdset *rs, my::fdset *ws, my::fdset *es, timeval *tv);
		};

		extern int select (my::fdset *rs, my::fdset *ws, my::fdset *es, timeval *tv = NULL);

	}

#endif /* __MY_SELECT_H */
