NEURON
octimer.cpp
Go to the documentation of this file.
1 #include <../../nrnconf.h>
2 
3 #if HAVE_IV
4 #include <Dispatch/iohandler.h>
5 #include <Dispatch/dispatcher.h>
6 
7 #include <stdio.h>
8 #include "oc2iv.h"
9 #include "objcmd.h"
10 #endif /* HAVE_IV */
11 #include "classreg.h"
12 
13 #ifdef MINGW
14 #include <windows.h>
15 #endif
16 
17 #if HAVE_IV
18 #if defined(MINGW)
19 class OcTimer {
20 #else
21 class OcTimer: public IOHandler {
22 #endif
23  public:
24  OcTimer(const char*);
25  OcTimer(Object*);
26  virtual ~OcTimer();
27 
28  virtual void timerExpired(long, long);
29  void start();
30  void stop();
31  double seconds();
32  void seconds(double);
33 
34  private:
35  double seconds_;
36  HocCommand* hc_;
37 #ifdef MINGW
38  HANDLE wtimer_;
39 #endif
40  bool stopped_;
41 };
42 
43 #ifdef MINGW
44 static void CALLBACK callback(PVOID lpParameter, BOOLEAN TimerOrWaitFired) {
45  ((OcTimer*) lpParameter)->timerExpired(0, 0);
46 }
47 #endif
48 
49 #endif /* HAVE_IV */
50 
51 static double t_seconds(void* v) {
52 #if HAVE_IV
53  OcTimer* t = (OcTimer*) v;
54  if (ifarg(1)) {
55  t->seconds(chkarg(1, 1e-6, 1e6));
56  }
57  return double(t->seconds());
58 #else
59  return 0.;
60 #endif /* HAVE_IV */
61 }
62 
63 static double t_start(void* v) {
64 #if HAVE_IV
65  OcTimer* t = (OcTimer*) v;
66  t->start();
67  return 0.;
68 #else
69  return 0.;
70 #endif /* HAVE_IV */
71 }
72 static double t_stop(void* v) {
73 #if HAVE_IV
74  OcTimer* t = (OcTimer*) v;
75  t->stop();
76  return 0.;
77 #else
78  return 0.;
79 #endif /* HAVE_IV */
80 }
81 static void* t_cons(Object*) {
82 #if HAVE_IV
83  if (hoc_is_object_arg(1)) {
84  return new OcTimer(*hoc_objgetarg(1));
85  } else {
86  return new OcTimer(gargstr(1));
87  }
88 #else
89  return nullptr;
90 #endif /* HAVE_IV */
91 }
92 static void t_destruct(void* v) {
93 #if HAVE_IV
94  OcTimer* t = (OcTimer*) v;
95  delete t;
96 #endif /* HAVE_IV */
97 }
98 
99 Member_func t_members[] = {{"seconds", t_seconds},
100  {"start", t_start},
101  {"end", t_stop},
102  {nullptr, nullptr}};
103 
104 void OcTimer_reg() {
105  class2oc("Timer", t_cons, t_destruct, t_members, nullptr, nullptr);
106 }
107 #if HAVE_IV
108 OcTimer::OcTimer(const char* cmd) {
109  hc_ = new HocCommand(cmd);
110  seconds_ = .5;
111 #ifdef MINGW
112  wtimer_ = NULL;
113 #endif
114  stopped_ = true;
115 }
116 OcTimer::OcTimer(Object* cmd) {
117  hc_ = new HocCommand(cmd);
118  seconds_ = .5;
119 #ifdef MINGW
120  wtimer_ = NULL;
121 #endif
122  stopped_ = true;
123 }
124 OcTimer::~OcTimer() {
125  stop();
126  delete hc_;
127 }
128 void OcTimer::start() {
129 #ifdef MINGW
130  stopped_ = false;
131  LARGE_INTEGER nsec100;
132  nsec100.QuadPart = (long long) (-seconds_ * 10000000.);
133  wtimer_ = CreateWaitableTimer(NULL, TRUE, NULL);
134  while (stopped_ == false) {
135  SetWaitableTimer(wtimer_, &nsec100, 0, NULL, NULL, 0);
136  hc_->execute();
137  WaitForSingleObject(wtimer_, INFINITE);
138  }
139  CloseHandle(wtimer_);
140  wtimer_ = NULL;
141 #else
142  long s = long(seconds_);
143  long us = long((seconds_ - double(s)) * 1000000.);
144  stopped_ = false;
145  Dispatcher::instance().startTimer(s, us, this);
146 #endif
147 }
148 void OcTimer::stop() {
149  stopped_ = true;
150 #ifndef MINGW
151  Dispatcher::instance().stopTimer(this);
152 #endif
153 }
154 void OcTimer::timerExpired(long, long) {
155 #ifndef MINGW
156  if (!stopped_) {
157  this->start();
158  }
159 #endif
160  // want it to be part of interval just like on mac
161  hc_->execute();
162 }
163 double OcTimer::seconds() {
164  return seconds_;
165 }
166 void OcTimer::seconds(double sec) {
167  seconds_ = sec;
168 }
169 #endif /* HAVE_IV */
void class2oc(const char *, ctor_f *cons, dtor_f *destruct, Member_func *, Member_ret_obj_func *, Member_ret_str_func *)
Definition: hoc_oop.cpp:1631
char * gargstr(int narg)
Definition: code2.cpp:227
#define v
Definition: md1redef.h:11
#define sec
Definition: md1redef.h:20
double chkarg(int, double low, double high)
Definition: code2.cpp:626
#define TRUE
Definition: grids.h:22
int hoc_is_object_arg(int narg)
Definition: code.cpp:876
Object ** hoc_objgetarg(int)
Definition: code.cpp:1614
s
Definition: multisend.cpp:521
int ifarg(int)
Definition: code.cpp:1607
static void t_destruct(void *v)
Definition: octimer.cpp:92
void OcTimer_reg()
Definition: octimer.cpp:104
Member_func t_members[]
Definition: octimer.cpp:99
static double t_seconds(void *v)
Definition: octimer.cpp:51
static double t_start(void *v)
Definition: octimer.cpp:63
static double t_stop(void *v)
Definition: octimer.cpp:72
static void * t_cons(Object *)
Definition: octimer.cpp:81
#define NULL
Definition: spdefs.h:105
#define BOOLEAN
Definition: spdefs.h:96
Definition: hocdec.h:173