Base::Base():
mode(M_READ),
- events(P_NONE),
eof_flag(false)
{ }
return static_cast<unsigned char>(c);
}
-void Base::set_events(PollEvent e)
-{
- events = e;
- signal_events_changed.emit(events);
-}
-
-void Base::event(PollEvent ev)
-{
- if(ev&P_INPUT)
- signal_data_available.emit();
-
- on_event(ev);
-}
-
} // namespace IO
} // namespace Msp
namespace Msp {
namespace IO {
-struct Handle;
-
/**
Common interface for all I/O objects.
class Base
{
public:
- /** Emitted when there is data available for reading. If all data is not
- read, the signal is emitted again immediately. */
- sigc::signal<void> signal_data_available;
-
/** Emitted when there is no more data to be read. */
sigc::signal<void> signal_end_of_file;
/** Emitted when the I/O object has closed. */
sigc::signal<void> signal_closed;
- /** Emitted when the mask of interesting events changes. Mainly for use by
- EventDispatcher. */
- sigc::signal<void, PollEvent> signal_events_changed;
-
/** Emitted when the object is deleted. Mainly for use by
EventDispatcher. */
sigc::signal<void> signal_deleted;
protected:
Mode mode;
- PollEvent events;
bool eof_flag;
Base();
/** Returns the end-of-file flag. */
bool eof() const { return eof_flag; }
-
-protected:
- void set_events(PollEvent);
-
-public:
- /** Returns a mask of the currently interesting events. Used by
- EventDispatcher. */
- PollEvent get_events() const { return events; }
-
- /** Returns a handle for polling. Should throw if the object does not have
- an event handle. */
- virtual const Handle &get_event_handle() = 0;
-
- /** Notifies the object of an event. Used by EventDispatcher. */
- void event(PollEvent);
-
-protected:
- virtual void on_event(PollEvent) { }
};
} // namespace IO
return end-begin;
}
-const Handle &Buffered::get_event_handle()
-{
- throw logic_error("Buffered doesn't support events");
-}
-
} // namespace IO
} // namespace Msp
public:
Mode get_current_op() const { return cur_op; }
unsigned get_current_size() const;
-
- virtual const Handle &get_event_handle();
};
} // namespace IO
#ifndef MSP_IO_CONSOLE_H_
#define MSP_IO_CONSOLE_H_
-#include "base.h"
+#include "eventobject.h"
#include "handle.h"
namespace Msp {
be instantiated directly - use one of the cin, cout and cerr references
instead.
*/
-class Console: public Base
+class Console: public EventObject
{
private:
Handle handle;
#include <msp/time/units.h>
#include "base.h"
#include "eventdispatcher.h"
+#include "eventobject.h"
#include "poll.h"
namespace Msp {
EventDispatcher::EventDispatcher()
{ }
-void EventDispatcher::add(Base &obj)
+void EventDispatcher::add(EventObject &obj)
{
SlotMap::iterator i = objects.find(&obj);
if(i==objects.end())
}
}
-void EventDispatcher::remove(Base &obj)
+void EventDispatcher::remove(EventObject &obj)
{
SlotMap::iterator i = objects.find(&obj);
if(i!=objects.end())
dispatch();
}
-void EventDispatcher::object_events_changed(PollEvent ev, Base *obj)
+void EventDispatcher::object_events_changed(PollEvent ev, EventObject *obj)
{
poller.set_object(*obj, ev);
}
-void EventDispatcher::object_deleted(Base *obj)
+void EventDispatcher::object_deleted(EventObject *obj)
{
remove(*obj);
}
private:
struct Slot
{
- Base *obj;
+ EventObject *obj;
sigc::connection evch_conn;
sigc::connection del_conn;
- Slot(Base *o): obj(o) { }
+ Slot(EventObject *o): obj(o) { }
};
- typedef std::map<Base *, Slot> SlotMap;
+ typedef std::map<EventObject *, Slot> SlotMap;
Poller poller;
SlotMap objects;
public:
EventDispatcher();
- void add(Base &);
- void remove(Base &);
+ void add(EventObject &);
+ void remove(EventObject &);
/** Checks for and dispatches events. If there are no events available,
blocks until there are. */
void tick(const Time::TimeDelta &);
private:
- void object_events_changed(PollEvent, Base *);
- void object_deleted(Base *);
+ void object_events_changed(PollEvent, EventObject *);
+ void object_deleted(EventObject *);
void dispatch();
};
--- /dev/null
+#include "eventobject.h"
+
+namespace Msp {
+namespace IO {
+
+EventObject::EventObject():
+ events(P_NONE)
+{ }
+
+void EventObject::set_events(PollEvent e)
+{
+ events = e;
+ signal_events_changed.emit(events);
+}
+
+void EventObject::event(PollEvent ev)
+{
+ if(ev&P_INPUT)
+ signal_data_available.emit();
+
+ on_event(ev);
+}
+} // namespace IO
+} // namespace Msp
--- /dev/null
+#ifndef MSP_IO_EVENTOBJECT_H_
+#define MSP_IO_EVENTOBJECT_H_
+
+#include "base.h"
+
+namespace Msp {
+namespace IO {
+
+struct Handle;
+
+/**
+Interface class for objects that can provide event-based I/O. These objects
+can be fed to the various poll functions in poll.h, or added to an
+EventDispatcher to generate event signals.
+*/
+class EventObject: public Base
+{
+public:
+ /** Emitted when there is data available for reading. If all data is not
+ read, the signal is emitted again immediately. */
+ sigc::signal<void> signal_data_available;
+
+ /** Emitted when the mask of interesting events changes. Mainly for use by
+ EventDispatcher. */
+ sigc::signal<void, PollEvent> signal_events_changed;
+
+private:
+ PollEvent events;
+
+protected:
+ EventObject();
+
+ void set_events(PollEvent);
+public:
+ /** Returns a mask of the currently interesting events. Used by
+ EventDispatcher. */
+ PollEvent get_events() const { return events; }
+
+ /** Returns a handle for polling. */
+ virtual const Handle &get_event_handle() = 0;
+
+ /** Notifies the object of an event. Used by EventDispatcher. */
+ void event(PollEvent);
+
+protected:
+ /** Called when an event occurs. Derived classes can implement this to
+ process events. */
+ virtual void on_event(PollEvent) { }
+};
+
+} // namespace IO
+} // namespace Msp
+
+#endif
throw system_error(format("open(%s)", fn), err);
}
#endif
-
- set_events(P_INPUT);
}
File::~File()
if(!handle)
return;
- set_events(P_NONE);
-
signal_flush_required.emit();
#ifdef WIN32
virtual unsigned seek(int, SeekType);
virtual unsigned tell() const;
- virtual const Handle &get_event_handle() { return handle; }
-
private:
void check_access(Mode) const;
};
return pos-begin;
}
-const Handle &Memory::get_event_handle()
-{
- throw logic_error("Memory doesn't support events");
-}
-
void Memory::check_mode(Mode m) const
{
if(m==M_WRITE && !(mode&M_WRITE))
virtual unsigned seek(int, SeekType);
virtual unsigned tell() const { return pos-begin; }
- virtual const Handle &get_event_handle();
-
private:
void check_mode(Mode) const;
};
#ifndef MSP_IO_PIPE_H_
#define MSP_IO_PIPE_H_
-#include "base.h"
+#include "eventobject.h"
#include "handle.h"
namespace Msp {
namespace IO {
-class Pipe: public Base
+class Pipe: public EventObject
{
private:
struct Private;
#include <msp/core/systemerror.h>
#include <msp/strings/format.h>
#include <msp/time/units.h>
-#include "base.h"
+#include "eventobject.h"
#include "handle.h"
#include "handle_private.h"
#include "poll.h"
return result;
}
-inline PollEvent do_poll(Base &obj, PollEvent pe, int timeout)
+inline PollEvent do_poll(EventObject &obj, PollEvent pe, int timeout)
{
#ifdef WIN32
if(timeout<0)
objs_changed(false)
{ }
-void Poller::set_object(Base &obj, PollEvent ev)
+void Poller::set_object(EventObject &obj, PollEvent ev)
{
// Verify that the object has an event handle
if(ev)
}
-PollEvent poll(Base &obj, PollEvent pe)
+PollEvent poll(EventObject &obj, PollEvent pe)
{
return do_poll(obj, pe, -1);
}
-PollEvent poll(Base &obj, PollEvent pe, const Time::TimeDelta &timeout)
+PollEvent poll(EventObject &obj, PollEvent pe, const Time::TimeDelta &timeout)
{
if(timeout<Time::zero)
throw invalid_argument("poll");
namespace Msp {
namespace IO {
-class Base;
+class EventObject;
enum PollEvent
{
public:
struct Slot
{
- Base *object;
+ EventObject *object;
PollEvent events;
- Slot(Base *o, PollEvent e): object(o), events(e) { }
+ Slot(EventObject *o, PollEvent e): object(o), events(e) { }
};
typedef std::list<Slot> SlotList;
private:
- typedef std::map<Base *, PollEvent> EventMap;
+ typedef std::map<EventObject *, PollEvent> EventMap;
struct Private;
public:
Poller();
- void set_object(Base &, PollEvent);
+ void set_object(EventObject &, PollEvent);
int poll();
int poll(const Time::TimeDelta &);
private:
const SlotList &get_result() const { return poll_result; }
};
-PollEvent poll(Base &, PollEvent);
-PollEvent poll(Base &, PollEvent, const Time::TimeDelta &);
+PollEvent poll(EventObject &, PollEvent);
+PollEvent poll(EventObject &, PollEvent, const Time::TimeDelta &);
} // namespace IO
} // namespace Msp
#ifndef MSP_IO_SERIAL_H_
#define MSP_IO_SERIAL_H_
-#include "base.h"
+#include "eventobject.h"
#include "handle.h"
namespace Msp {
namespace IO {
-class Serial: public Base
+class Serial: public EventObject
{
public:
enum Parity