00001
00020 #ifndef RTC_INPORT_H
00021 #define RTC_INPORT_H
00022
00023 #include <string>
00024 #include <vector>
00025 #include <iostream>
00026
00027 #include <coil/TimeValue.h>
00028 #include <coil/Time.h>
00029 #include <coil/OS.h>
00030
00031 #include <rtm/RTC.h>
00032 #include <rtm/Typename.h>
00033 #include <rtm/InPortBase.h>
00034 #include <rtm/CdrBufferBase.h>
00035 #include <rtm/PortCallback.h>
00036 #include <rtm/InPortConnector.h>
00037
00038 namespace RTC
00039 {
00174 template <class DataType>
00175 class InPort
00176 : public InPortBase
00177 {
00178 public:
00179 DATAPORTSTATUS_ENUM
00231 InPort(const char* name, DataType& value,
00232 int bufsize=64,
00233 bool read_block = false, bool write_block = false,
00234 int read_timeout = 0, int write_timeout = 0)
00235 : InPortBase(name, toTypename<DataType>()),
00236 m_name(name), m_value(value),
00237 m_OnRead(NULL), m_OnReadConvert(NULL)
00238 {
00239 }
00240
00256 virtual ~InPort(void){};
00257
00277 virtual const char* name()
00278 {
00279 return m_name.c_str();
00280 }
00281
00282
00307 virtual bool isNew()
00308 {
00309 RTC_TRACE(("isNew()"));
00310
00311
00312
00313
00314 int r(0);
00315 {
00316 Guard guard(m_connectorsMutex);
00317 if (m_connectors.size() == 0)
00318 {
00319 RTC_DEBUG(("no connectors"));
00320 return false;
00321 }
00322 r = m_connectors[0]->getBuffer()->readable();
00323 }
00324
00325 if (r > 0)
00326 {
00327 RTC_DEBUG(("isNew() = true, readable data: %d", r));
00328 return true;
00329 }
00330
00331 RTC_DEBUG(("isNew() = false, no readable data"));
00332 return false;
00333 }
00334
00358 virtual bool isEmpty()
00359 {
00360 RTC_TRACE(("isEmpty()"));
00361 int r(0);
00362
00363 {
00364 Guard guard(m_connectorsMutex);
00365 if (m_connectors.size() == 0)
00366 {
00367 RTC_DEBUG(("no connectors"));
00368 return true;
00369 }
00370
00371
00372
00373 r = m_connectors[0]->getBuffer()->readable();
00374 }
00375
00376 if (r == 0)
00377 {
00378 RTC_DEBUG(("isEmpty() = true, buffer is empty"));
00379 return true;
00380 }
00381
00382 RTC_DEBUG(("isEmpty() = false, data exists in the buffer"));
00383 return false;
00384 }
00385
00460 bool read()
00461 {
00462 RTC_TRACE(("DataType read()"));
00463
00464 if (m_OnRead != NULL)
00465 {
00466 (*m_OnRead)();
00467 RTC_TRACE(("OnRead called"));
00468 }
00469
00470 cdrMemoryStream cdr;
00471 ReturnCode ret;
00472 {
00473 Guard guard(m_connectorsMutex);
00474 if (m_connectors.size() == 0)
00475 {
00476 RTC_DEBUG(("no connectors"));
00477 return false;
00478 }
00479
00480
00481
00482
00483 ret = m_connectors[0]->read(cdr);
00484 }
00485 if (ret == PORT_OK)
00486 {
00487 RTC_DEBUG(("data read succeeded"));
00488 m_value <<= cdr;
00489 if (m_OnReadConvert != 0)
00490 {
00491 m_value = (*m_OnReadConvert)(m_value);
00492 RTC_DEBUG(("OnReadConvert called"));
00493 return true;
00494 }
00495 return true;
00496 }
00497 else if (ret == BUFFER_EMPTY)
00498 {
00499 RTC_WARN(("buffer empty"));
00500 return false;
00501 }
00502 else if (ret == BUFFER_TIMEOUT)
00503 {
00504 RTC_WARN(("buffer read timeout"));
00505 return false;
00506 }
00507 RTC_ERROR(("unknown retern value from buffer.read()"));
00508 return false;
00509 }
00510
00511
00534 virtual void update()
00535 {
00536 this->read();
00537 };
00538
00559 void operator>>(DataType& rhs)
00560 {
00561 this->read();
00562 rhs = m_value;
00563 return;
00564 }
00565
00587 inline void setOnRead(OnRead<DataType>* on_read)
00588 {
00589 m_OnRead = on_read;
00590 }
00591
00615 inline void setOnReadConvert(OnReadConvert<DataType>* on_rconvert)
00616 {
00617 m_OnReadConvert = on_rconvert;
00618 }
00619
00620 private:
00621 std::string m_typename;
00629 std::string m_name;
00630
00638 DataType& m_value;
00639
00647 OnRead<DataType>* m_OnRead;
00648
00656 OnReadConvert<DataType>* m_OnReadConvert;
00657
00658 };
00659 };
00660
00661 #endif // RTC_INPORT_H