L4Re – L4 Runtime Environment
ipc_stream
Go to the documentation of this file.
1 // vi:set ft=cpp: -*- Mode: C++ -*-
6 /*
7  * (c) 2008-2009 Adam Lackorzynski <adam@os.inf.tu-dresden.de>,
8  * Alexander Warg <warg@os.inf.tu-dresden.de>,
9  * Torsten Frenzel <frenzel@os.inf.tu-dresden.de>
10  * economic rights: Technische Universität Dresden (Germany)
11  *
12  * This file is part of TUD:OS and distributed under the terms of the
13  * GNU General Public License 2.
14  * Please see the COPYING-GPL-2 file for details.
15  *
16  * As a special exception, you may use this file as part of a free software
17  * library without restriction. Specifically, if other files instantiate
18  * templates or use macros or inline functions from this file, or you compile
19  * this file and link it with other files to produce an executable, this
20  * file does not by itself cause the resulting executable to be covered by
21  * the GNU General Public License. This exception does not however
22  * invalidate any other reasons why the executable file might be covered by
23  * the GNU General Public License.
24  */
25 #pragma once
26 
27 #include <l4/sys/ipc.h>
28 #include <l4/sys/capability>
29 #include <l4/sys/cxx/ipc_types>
30 #include <l4/sys/cxx/ipc_varg>
31 #include <l4/cxx/type_traits>
32 #include <l4/cxx/minmax>
33 
34 #define L4_CXX_IPC_BACKWARD_COMPAT
35 
36 namespace L4 {
37 namespace Ipc {
38 
39 class Ostream;
40 class Istream;
41 
42 namespace Internal {
60 template< typename T >
61 class Buf_cp_out
62 {
63 public:
70  Buf_cp_out(T const *v, unsigned long size) : _v(v), _s(size) {}
71 
79  unsigned long size() const { return _s; }
80 
88  T const *buf() const { return _v; }
89 
90 private:
91  friend class Ostream;
92  T const *_v;
93  unsigned long _s;
94 };
95 }
96 
112 template< typename T >
113 Internal::Buf_cp_out<T> buf_cp_out(T const *v, unsigned long size)
114 { return Internal::Buf_cp_out<T>(v, size); }
115 
116 
117 namespace Internal {
130 template< typename T >
131 class Buf_cp_in
132 {
133 public:
142  Buf_cp_in(T *v, unsigned long &size) : _v(v), _s(&size) {}
143 
144  unsigned long &size() const { return *_s; }
145  T *buf() const { return _v; }
146 
147 private:
148  friend class Istream;
149  T *_v;
150  unsigned long *_s;
151 };
152 }
153 
171 template< typename T >
172 Internal::Buf_cp_in<T> buf_cp_in(T *v, unsigned long &size)
173 { return Internal::Buf_cp_in<T>(v, size); }
174 
190 template< typename T >
192 {
193 public:
202  Str_cp_in(T *v, unsigned long &size) : _v(v), _s(&size) {}
203 
204  unsigned long &size() const { return *_s; }
205  T *buf() const { return _v; }
206 
207 private:
208  friend class Istream;
209  T *_v;
210  unsigned long *_s;
211 };
212 
225 template< typename T >
226 Str_cp_in<T> str_cp_in(T *v, unsigned long &size)
227 { return Str_cp_in<T>(v, size); }
228 
241 template< typename T >
242 class Msg_ptr
243 {
244 private:
245  T **_p;
246 public:
253  explicit Msg_ptr(T *&p) : _p(&p) {}
254  void set(T *p) const { *_p = p; }
255 };
256 
264 template< typename T >
266 { return Msg_ptr<T>(p); }
267 
268 
269 namespace Internal {
283 template< typename T >
284 class Buf_in
285 {
286 public:
293  Buf_in(T *&v, unsigned long &size) : _v(&v), _s(&size) {}
294 
295  void set_size(unsigned long s) const { *_s = s; }
296  T *&buf() const { return *_v; }
297 
298 private:
299  friend class Istream;
300  T **_v;
301  unsigned long *_s;
302 };
303 }
304 
322 template< typename T >
323 Internal::Buf_in<T> buf_in(T *&v, unsigned long &size)
324 { return Internal::Buf_in<T>(v, size); }
325 
326 namespace Utcb_stream_check
327 {
328  static bool check_utcb_data_offset(unsigned sz)
329  { return sz > sizeof(l4_umword_t) * L4_UTCB_GENERIC_DATA_SIZE; }
330 }
331 
332 
347 class Istream
348 {
349 public:
362  : _tag(), _utcb(utcb),
363  _current_msg(reinterpret_cast<char*>(l4_utcb_mr_u(utcb)->mr)),
364  _pos(0), _current_buf(0)
365  {}
366 
371  void reset()
372  {
373  _pos = 0;
374  _current_buf = 0;
375  _current_msg = reinterpret_cast<char*>(l4_utcb_mr_u(_utcb)->mr);
376  }
377 
381  template< typename T >
382  bool has_more(unsigned long count = 1)
383  {
384  auto const max_bytes = L4_UTCB_GENERIC_DATA_SIZE * sizeof(l4_umword_t);
385  unsigned apos = cxx::Type_traits<T>::align(_pos);
386  return (count <= max_bytes / sizeof(T))
387  && (apos + (sizeof(T) * count)
388  <= _tag.words() * sizeof(l4_umword_t));
389  }
390 
395 
406  template< typename T >
407  unsigned long get(T *buf, unsigned long elems)
408  {
409  if (L4_UNLIKELY(!has_more<T>(elems)))
410  return 0;
411 
412  unsigned long size = elems * sizeof(T);
413  _pos = cxx::Type_traits<T>::align(_pos);
414 
415  __builtin_memcpy(buf, _current_msg + _pos, size);
416  _pos += size;
417  return elems;
418  }
419 
420 
426  template< typename T >
427  void skip(unsigned long elems)
428  {
429  if (L4_UNLIKELY(!has_more<T>(elems)))
430  return;
431 
432  unsigned long size = elems * sizeof(T);
433  _pos = cxx::Type_traits<T>::align(_pos);
434  _pos += size;
435  }
436 
451  template< typename T >
452  unsigned long get(Msg_ptr<T> const &buf, unsigned long elems = 1)
453  {
454  if (L4_UNLIKELY(!has_more<T>(elems)))
455  return 0;
456 
457  unsigned long size = elems * sizeof(T);
458  _pos = cxx::Type_traits<T>::align(_pos);
459 
460  buf.set(reinterpret_cast<T*>(_current_msg + _pos));
461  _pos += size;
462  return elems;
463  }
464 
465 
476  template< typename T >
477  bool get(T &v)
478  {
479  if (L4_UNLIKELY(!has_more<T>()))
480  {
481  v = T();
482  return false;
483  }
484 
485  _pos = cxx::Type_traits<T>::align(_pos);
486  v = *(reinterpret_cast<T*>(_current_msg + _pos));
487  _pos += sizeof(T);
488  return true;
489  }
490 
491 
492  bool get(Ipc::Varg *va)
493  {
494  Ipc::Varg::Tag t;
495  if (!has_more<Ipc::Varg::Tag>())
496  {
497  va->tag(0);
498  return 0;
499  }
500  get(t);
501  va->tag(t);
502  char const *d;
503  get(msg_ptr(d), va->length());
504  va->data(d);
505 
506  return 1;
507  }
508 
518  l4_msgtag_t tag() const { return _tag; }
519 
520 
530  l4_msgtag_t &tag() { return _tag; }
531 
533 
538  inline bool put(Buf_item const &);
539 
544  inline bool put(Small_buf const &);
545 
546 
551 
562  { return wait(src, L4_IPC_NEVER); }
563 
574  inline l4_msgtag_t wait(l4_umword_t *src, l4_timeout_t timeout);
575 
586  { return receive(src, L4_IPC_NEVER); }
587  inline l4_msgtag_t receive(l4_cap_idx_t src, l4_timeout_t timeout);
588 
590 
594  inline l4_utcb_t *utcb() const { return _utcb; }
595 
596 protected:
597  l4_msgtag_t _tag;
598  l4_utcb_t *_utcb;
599  char *_current_msg;
600  unsigned _pos;
601  unsigned char _current_buf;
602 };
603 
604 class Istream_copy : public Istream
605 {
606 private:
607  l4_msg_regs_t _mrs;
608 
609 public:
610  Istream_copy(Istream const &o) : Istream(o), _mrs(*l4_utcb_mr_u(o.utcb()))
611  {
612  // do some reverse mr to utcb trickery
613  _utcb = (l4_utcb_t *)((l4_addr_t)&_mrs - (l4_addr_t)l4_utcb_mr_u((l4_utcb_t *)0));
614  _current_msg = reinterpret_cast<char*>(l4_utcb_mr_u(_utcb)->mr);
615  }
616 
617 };
618 
634 class Ostream
635 {
636 public:
641  : _tag(), _utcb(utcb),
642  _current_msg(reinterpret_cast<char *>(l4_utcb_mr_u(_utcb)->mr)),
643  _pos(0), _current_item(0)
644  {}
645 
649  void reset()
650  {
651  _pos = 0;
652  _current_item = 0;
653  _current_msg = reinterpret_cast<char*>(l4_utcb_mr_u(_utcb)->mr);
654  }
655 
663 
670  template< typename T >
671  bool put(T *buf, unsigned long size)
672  {
673  size *= sizeof(T);
674  _pos = cxx::Type_traits<T>::align(_pos);
675  if (Utcb_stream_check::check_utcb_data_offset(_pos + size))
676  return false;
677 
678  __builtin_memcpy(_current_msg + _pos, buf, size);
679  _pos += size;
680  return true;
681  }
682 
688  template< typename T >
689  bool put(T const &v)
690  {
691  _pos = cxx::Type_traits<T>::align(_pos);
692  if (Utcb_stream_check::check_utcb_data_offset(_pos + sizeof(T)))
693  return false;
694 
695  *(reinterpret_cast<T*>(_current_msg + _pos)) = v;
696  _pos += sizeof(T);
697  return true;
698  }
699 
700  int put(Varg const &va)
701  {
702  put(va.tag());
703  put(va.data(), va.length());
704 
705  return 0;
706  }
707 
708  template< typename T >
709  int put(Varg_t<T> const &va)
710  { return put(static_cast<Varg const &>(va)); }
711 
717  l4_msgtag_t tag() const { return _tag; }
718 
724  l4_msgtag_t &tag() { return _tag; }
725 
727 
732  inline bool put_snd_item(Snd_item const &);
733 
734 
739 
749  inline l4_msgtag_t send(l4_cap_idx_t dst, long proto = 0, unsigned flags = 0);
750 
752 
756  inline l4_utcb_t *utcb() const { return _utcb; }
757 #if 0
761  unsigned long tell() const
762  {
763  unsigned w = (_pos + sizeof(l4_umword_t)-1) / sizeof(l4_umword_t);
764  w -= _current_item * 2;
765  _tag = l4_msgtag(0, w, _current_item, 0);
766  }
767 #endif
768 public:
769  l4_msgtag_t prepare_ipc(long proto = 0, unsigned flags = 0)
770  {
771  unsigned w = (_pos + sizeof(l4_umword_t) - 1) / sizeof(l4_umword_t);
772  w -= _current_item * 2;
773  return l4_msgtag(proto, w, _current_item, flags);
774  }
775 
776  // XXX: this is a hack for <l4/sys/cxx/ipc_server> adaption
777  void set_ipc_params(l4_msgtag_t tag)
778  {
779  _pos = (tag.words() + tag.items() * 2) * sizeof(l4_umword_t);
780  _current_item = tag.items();
781  }
782 protected:
783  l4_msgtag_t _tag;
784  l4_utcb_t *_utcb;
785  char *_current_msg;
786  unsigned _pos;
787  unsigned char _current_item;
788 };
789 
790 
802 class Iostream : public Istream, public Ostream
803 {
804 public:
805 
814  explicit Iostream(l4_utcb_t *utcb)
815  : Istream(utcb), Ostream(utcb)
816  {}
817 
818  // disambiguate those functions
819  l4_msgtag_t tag() const { return Istream::tag(); }
820  l4_msgtag_t &tag() { return Istream::tag(); }
821  l4_utcb_t *utcb() const { return Istream::utcb(); }
822 
828  void reset()
829  {
830  Istream::reset();
831  Ostream::reset();
832  }
833 
834 
842 
843  using Istream::get;
844  using Istream::put;
845  using Ostream::put;
846 
848 
853 
869  inline l4_msgtag_t call(l4_cap_idx_t dst, l4_timeout_t timeout, long proto = 0);
870  inline l4_msgtag_t call(l4_cap_idx_t dst, long proto = 0);
871 
887  inline l4_msgtag_t reply_and_wait(l4_umword_t *src_dst, long proto = 0)
888  { return reply_and_wait(src_dst, L4_IPC_SEND_TIMEOUT_0, proto); }
889 
890  inline l4_msgtag_t send_and_wait(l4_cap_idx_t dest, l4_umword_t *src,
891  long proto = 0)
892  { return send_and_wait(dest, src, L4_IPC_SEND_TIMEOUT_0, proto); }
893 
910  inline l4_msgtag_t reply_and_wait(l4_umword_t *src_dst,
911  l4_timeout_t timeout, long proto = 0);
912  inline l4_msgtag_t send_and_wait(l4_cap_idx_t dest, l4_umword_t *src,
913  l4_timeout_t timeout, long proto = 0);
914  inline l4_msgtag_t reply(l4_timeout_t timeout, long proto = 0);
915  inline l4_msgtag_t reply(long proto = 0)
916  { return reply(L4_IPC_SEND_TIMEOUT_0, proto); }
917 
919 };
920 
921 
922 inline bool
923 Ostream::put_snd_item(Snd_item const &v)
924 {
925  typedef Snd_item T;
926  _pos = cxx::Type_traits<Snd_item>::align(_pos);
927  if (Utcb_stream_check::check_utcb_data_offset(_pos + sizeof(T)))
928  return false;
929 
930  *(reinterpret_cast<T*>(_current_msg + _pos)) = v;
931  _pos += sizeof(T);
932  ++_current_item;
933  return true;
934 }
935 
936 
937 inline bool
938 Istream::put(Buf_item const &item)
939 {
940  if (_current_buf >= L4_UTCB_GENERIC_BUFFERS_SIZE - 3)
941  return false;
942 
943  l4_utcb_br_u(_utcb)->bdr &= ~L4_BDR_OFFSET_MASK;
944 
945  reinterpret_cast<Buf_item&>(l4_utcb_br_u(_utcb)->br[_current_buf]) = item;
946  _current_buf += 2;
947  return true;
948 }
949 
950 
951 inline bool
952 Istream::put(Small_buf const &item)
953 {
954  if (_current_buf >= L4_UTCB_GENERIC_BUFFERS_SIZE - 2)
955  return false;
956 
957  l4_utcb_br_u(_utcb)->bdr &= ~L4_BDR_OFFSET_MASK;
958 
959  reinterpret_cast<Small_buf&>(l4_utcb_br_u(_utcb)->br[_current_buf]) = item;
960  _current_buf += 1;
961  return true;
962 }
963 
964 
965 inline l4_msgtag_t
966 Ostream::send(l4_cap_idx_t dst, long proto, unsigned flags)
967 {
968  l4_msgtag_t tag = prepare_ipc(proto, L4_MSGTAG_FLAGS & flags);
969  return l4_ipc_send(dst, _utcb, tag, L4_IPC_NEVER);
970 }
971 
972 inline l4_msgtag_t
973 Iostream::call(l4_cap_idx_t dst, l4_timeout_t timeout, long label)
974 {
975  l4_msgtag_t tag = prepare_ipc(label);
976  tag = l4_ipc_call(dst, Ostream::_utcb, tag, timeout);
977  Istream::tag() = tag;
978  Istream::_pos = 0;
979  return tag;
980 }
981 
982 inline l4_msgtag_t
983 Iostream::call(l4_cap_idx_t dst, long label)
984 { return call(dst, L4_IPC_NEVER, label); }
985 
986 
987 inline l4_msgtag_t
988 Iostream::reply_and_wait(l4_umword_t *src_dst, l4_timeout_t timeout, long proto)
989 {
990  l4_msgtag_t tag = prepare_ipc(proto);
991  tag = l4_ipc_reply_and_wait(Ostream::_utcb, tag, src_dst, timeout);
992  Istream::tag() = tag;
993  Istream::_pos = 0;
994  return tag;
995 }
996 
997 
998 inline l4_msgtag_t
999 Iostream::send_and_wait(l4_cap_idx_t dest, l4_umword_t *src,
1000  l4_timeout_t timeout, long proto)
1001 {
1002  l4_msgtag_t tag = prepare_ipc(proto);
1003  tag = l4_ipc_send_and_wait(dest, Ostream::_utcb, tag, src, timeout);
1004  Istream::tag() = tag;
1005  Istream::_pos = 0;
1006  return tag;
1007 }
1008 
1009 inline l4_msgtag_t
1010 Iostream::reply(l4_timeout_t timeout, long proto)
1011 {
1012  l4_msgtag_t tag = prepare_ipc(proto);
1013  tag = l4_ipc_send(L4_INVALID_CAP | L4_SYSF_REPLY, Ostream::_utcb, tag, timeout);
1014  Istream::tag() = tag;
1015  Istream::_pos = 0;
1016  return tag;
1017 }
1018 
1019 inline l4_msgtag_t
1021 {
1022  l4_msgtag_t res;
1023  res = l4_ipc_wait(_utcb, src, timeout);
1024  tag() = res;
1025  _pos = 0;
1026  return res;
1027 }
1028 
1029 
1030 inline l4_msgtag_t
1032 {
1033  l4_msgtag_t res;
1034  res = l4_ipc_receive(src, _utcb, timeout);
1035  tag() = res;
1036  _pos = 0;
1037  return res;
1038 }
1039 
1040 } // namespace Ipc
1041 } // namespace L4
1042 
1051 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, bool &v) { s.get(v); return s; }
1052 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, int &v) { s.get(v); return s; }
1053 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, long int &v) { s.get(v); return s; }
1054 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, long long int &v) { s.get(v); return s; }
1055 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, unsigned int &v) { s.get(v); return s; }
1056 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, unsigned long int &v) { s.get(v); return s; }
1057 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, unsigned long long int &v) { s.get(v); return s; }
1058 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, short int &v) { s.get(v); return s; }
1059 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, unsigned short int &v) { s.get(v); return s; }
1060 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, char &v) { s.get(v); return s; }
1061 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, unsigned char &v) { s.get(v); return s; }
1062 inline L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, signed char &v) { s.get(v); return s; }
1063 inline L4::Ipc::Istream &operator << (L4::Ipc::Istream &s, L4::Ipc::Buf_item const &v) { s.put(v); return s; }
1064 inline L4::Ipc::Istream &operator << (L4::Ipc::Istream &s, L4::Ipc::Small_buf const &v) { s.put(v); return s; }
1066 {
1067  l4_umword_t b, d;
1068  s >> b >> d;
1069  v = L4::Ipc::Snd_item(b, d);
1070  return s;
1071 }
1073 { s.get(&v); return s; }
1074 
1075 
1084 inline
1086 {
1087  v = s.tag();
1088  return s;
1089 }
1090 
1108 template< typename T >
1109 inline
1111  L4::Ipc::Internal::Buf_in<T> const &v)
1112 {
1113  unsigned long si;
1114  if (s.get(si) && s.has_more<T>(si))
1115  v.set_size(s.get(L4::Ipc::Msg_ptr<T>(v.buf()), si));
1116  else
1117  v.set_size(0);
1118  return s;
1119 }
1120 
1135 template< typename T >
1136 inline
1138  L4::Ipc::Msg_ptr<T> const &v)
1139 {
1140  s.get(v);
1141  return s;
1142 }
1143 
1156 template< typename T >
1157 inline
1159  L4::Ipc::Internal::Buf_cp_in<T> const &v)
1160 {
1161  unsigned long sz;
1162  s.get(sz);
1163  v.size() = s.get(v.buf(), cxx::min(v.size(), sz));
1164  return s;
1165 }
1166 
1177 template< typename T >
1178 inline
1180  L4::Ipc::Str_cp_in<T> const &v)
1181 {
1182  unsigned long sz;
1183  s.get(sz);
1184  unsigned long rsz = s.get(v.buf(), cxx::min(v.size(), sz));
1185  if (rsz < v.size() && v.buf()[rsz - 1])
1186  ++rsz; // add the zero termination behind the received data
1187 
1188  if (rsz != 0)
1189  v.buf()[rsz - 1] = 0;
1190 
1191  v.size() = rsz;
1192  return s;
1193 }
1194 
1195 
1204 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, bool v) { s.put(v); return s; }
1205 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, int v) { s.put(v); return s; }
1206 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, long int v) { s.put(v); return s; }
1207 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, long long int v) { s.put(v); return s; }
1208 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, unsigned int v) { s.put(v); return s; }
1209 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, unsigned long int v) { s.put(v); return s; }
1210 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, unsigned long long int v) { s.put(v); return s; }
1211 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, short int v) { s.put(v); return s; }
1212 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, unsigned short int v) { s.put(v); return s; }
1213 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, char v) { s.put(v); return s; }
1214 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, unsigned char v) { s.put(v); return s; }
1215 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, signed char v) { s.put(v); return s; }
1216 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, L4::Ipc::Snd_item const &v) { s.put_snd_item(v); return s; }
1217 template< typename T >
1219 { s << L4::Ipc::Snd_fpage(v.fpage()); return s; }
1220 
1222 { s.put(v); return s; }
1223 template< typename T >
1224 inline L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, L4::Ipc::Varg_t<T> const &v)
1225 { s.put(v); return s; }
1226 
1238 inline
1240 {
1241  s.tag() = v;
1242  return s;
1243 }
1244 
1253 template< typename T >
1254 inline
1256  L4::Ipc::Internal::Buf_cp_out<T> const &v)
1257 {
1258  s.put(v.size());
1259  s.put(v.buf(), v.size());
1260  return s;
1261 }
1262 
1275 inline
1277 {
1278  unsigned long l = __builtin_strlen(v) + 1;
1279  s.put(l);
1280  s.put(v, l);
1281  return s;
1282 }
1283 
1284 
1285 #ifdef L4_CXX_IPC_BACKWARD_COMPAT
1286 namespace L4 {
1287 
1288 #if 0
1289 template< typename T > class Ipc_buf_cp_out : public Ipc::Buf_cp_out<T> {};
1290 template< typename T > class Ipc_buf_cp_in : public Ipc::Buf_cp_in<T> {};
1291 template< typename T > class Ipc_buf_in : public Ipc::Buf_in<T> {};
1292 template< typename T > class Msg_ptr : public Ipc::Msg_ptr<T> {};
1293 #endif
1294 
1295 template< typename T >
1296 Ipc::Internal::Buf_cp_out<T> ipc_buf_cp_out(T *v, unsigned long size)
1297  L4_DEPRECATED("Use L4::Ipc::buf_cp_out() now");
1298 
1299 template< typename T >
1300 Ipc::Internal::Buf_cp_out<T> ipc_buf_cp_out(T *v, unsigned long size)
1301 { return Ipc::Internal::Buf_cp_out<T>(v, size); }
1302 
1303 
1304 template< typename T >
1305 Ipc::Internal::Buf_cp_in<T> ipc_buf_cp_in(T *v, unsigned long &size)
1306  L4_DEPRECATED("Use L4::Ipc::buf_cp_in() now");
1307 
1308 template< typename T >
1309 Ipc::Internal::Buf_cp_in<T> ipc_buf_cp_in(T *v, unsigned long &size)
1310 { return Ipc::Internal::Buf_cp_in<T>(v, size); }
1311 
1312 
1313 template< typename T >
1314 Ipc::Internal::Buf_in<T> ipc_buf_in(T *&v, unsigned long &size)
1315  L4_DEPRECATED("Use L4::Ipc::buf_in() now");
1316 
1317 template< typename T >
1318 Ipc::Internal::Buf_in<T> ipc_buf_in(T *&v, unsigned long &size)
1319 { return Ipc::Internal::Buf_in<T>(v, size); }
1320 
1321 
1322 template< typename T >
1323 Ipc::Msg_ptr<T> msg_ptr(T *&p)
1324  L4_DEPRECATED("Use L4::Ipc::msg_ptr() now");
1325 
1326 template< typename T >
1327 Ipc::Msg_ptr<T> msg_ptr(T *&p)
1328 { return Ipc::Msg_ptr<T>(p); }
1329 
1330 typedef Ipc::Istream Ipc_istream L4_DEPRECATED("Use L4::Ipc::Istream now");
1331 typedef Ipc::Ostream Ipc_ostream L4_DEPRECATED("Use L4::Ipc::Ostream now");;
1332 typedef Ipc::Iostream Ipc_iostream L4_DEPRECATED("Use L4::Ipc::Iostream now");;
1333 typedef Ipc::Snd_fpage Snd_fpage L4_DEPRECATED("Use L4::Ipc::Snd_fpage now");;
1334 typedef Ipc::Rcv_fpage Rcv_fpage L4_DEPRECATED("Use L4::Ipc::Rcv_fpage now");;
1335 typedef Ipc::Small_buf Small_buf L4_DEPRECATED("Use L4::Ipc::Small_buf now");;
1336 
1337 
1338 namespace Ipc {
1339 template< typename T > class Buf_cp_in : public Internal::Buf_cp_in<T>
1340 {
1341 public:
1342  Buf_cp_in(T *v, unsigned long &size) : Internal::Buf_cp_in<T>(v, size) {}
1343 };
1344 
1345 template< typename T >
1346 class Buf_cp_out : public Internal::Buf_cp_out<T>
1347 {
1348 public:
1349  Buf_cp_out(T const *v, unsigned long size) : Internal::Buf_cp_out<T>(v, size) {}
1350 };
1351 
1352 template< typename T >
1353 class Buf_in : public Internal::Buf_in<T>
1354 {
1355 public:
1356  Buf_in(T *&v, unsigned long &size) : Internal::Buf_in<T>(v, size) {}
1357 };
1358 } // namespace Ipc
1359 } // namespace L4
1360 
1361 template< typename T >
1362 inline
1363 L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, L4::Ipc::Buf_cp_in<T> const &v)
1364  L4_DEPRECATED("Use L4::Ipc::buf_cp_in() now");
1365 
1366 template< typename T >
1367 inline
1368 L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, L4::Ipc::Buf_cp_in<T> const &v)
1369 { return operator>>(s, static_cast<L4::Ipc::Internal::Buf_cp_in<T> >(v)); }
1370 
1371 template< typename T >
1372 inline
1373 L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, L4::Ipc::Buf_in<T> const &v)
1374  L4_DEPRECATED("Use L4::Ipc::buf_in() now");
1375 
1376 template< typename T >
1377 inline
1378 L4::Ipc::Istream &operator >> (L4::Ipc::Istream &s, L4::Ipc::Buf_in<T> const &v)
1379 { return operator>>(s, static_cast<L4::Ipc::Internal::Buf_in<T> >(v)); }
1380 
1381 template< typename T >
1382 inline
1383 L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, L4::Ipc::Buf_cp_out<T> const &v)
1384  L4_DEPRECATED("Use L4::Ipc::buf_cp_out() now");
1385 
1386 template< typename T >
1387 inline
1388 L4::Ipc::Ostream &operator << (L4::Ipc::Ostream &s, L4::Ipc::Buf_cp_out<T> const &v)
1389 { return operator<<(s, static_cast<L4::Ipc::Internal::Buf_cp_out<T> >(v)); }
1390 #endif
1391 
1392 namespace L4 { namespace Ipc {
1402 template< typename T >
1403 inline
1404 T read(Istream &s) { T t; s >> t; return t; }
1405 
1406 } // namespace Ipc
1407 } // namespace L4
L4::Cap related definitions.
l4_fpage_t fpage(unsigned rights=L4_CAP_FPAGE_RWS) const noexcept
Return flex-page for the capability.
Definition: capability.h:72
C++ interface for capabilities.
Definition: capability.h:219
RPC warpper for a receive item.
Definition: ipc_types:306
Input/Output stream for IPC [un]marshalling.
Definition: ipc_stream:803
void reset()
Reset the stream to its initial state.
Definition: ipc_stream:828
l4_msgtag_t call(l4_cap_idx_t dst, l4_timeout_t timeout, long proto=0)
Do an IPC call using the message in the output stream and receive the reply in the input stream.
Definition: ipc_stream:973
l4_msgtag_t reply_and_wait(l4_umword_t *src_dst, long proto=0)
Do an IPC reply and wait.
Definition: ipc_stream:887
Iostream(l4_utcb_t *utcb)
Create an IPC IO stream with a single message buffer.
Definition: ipc_stream:814
Input stream for IPC unmarshalling.
Definition: ipc_stream:348
l4_msgtag_t receive(l4_cap_idx_t src)
Wait for a message from the specified sender.
Definition: ipc_stream:585
void skip(unsigned long elems)
Skip size elements of type T in the stream.
Definition: ipc_stream:427
void reset()
Reset the stream to empty, and ready for receive()/wait().
Definition: ipc_stream:371
bool get(T &v)
Extract a single element of type T from the stream.
Definition: ipc_stream:477
l4_msgtag_t tag() const
Get the message tag of a received IPC.
Definition: ipc_stream:518
l4_msgtag_t & tag()
Get the message tag of a received IPC.
Definition: ipc_stream:530
bool has_more(unsigned long count=1)
Check whether a value of type T can be obtained from the stream.
Definition: ipc_stream:382
l4_utcb_t * utcb() const
Return utcb pointer.
Definition: ipc_stream:594
Istream(l4_utcb_t *utcb)
Create an input stream for the given message buffer.
Definition: ipc_stream:361
unsigned long get(Msg_ptr< T > const &buf, unsigned long elems=1)
Read one size elements of type T from the stream and return a pointer.
Definition: ipc_stream:452
l4_msgtag_t wait(l4_umword_t *src)
Wait for an incoming message from any sender.
Definition: ipc_stream:561
unsigned long get(T *buf, unsigned long elems)
Copy out an array of type T with size elements.
Definition: ipc_stream:407
Pointer to an element of type T in an Ipc::Istream.
Definition: ipc_stream:243
Msg_ptr(T *&p)
Create a Msg_ptr object that set pointer p to point into the message buffer.
Definition: ipc_stream:253
Output stream for IPC marshalling.
Definition: ipc_stream:635
Ostream(l4_utcb_t *utcb)
Create an IPC output stream using the given message buffer utcb.
Definition: ipc_stream:640
l4_msgtag_t send(l4_cap_idx_t dst, long proto=0, unsigned flags=0)
Send the message via IPC to the given receiver.
Definition: ipc_stream:966
bool put(T const &v)
Insert an element of type T into the stream.
Definition: ipc_stream:689
bool put(T *buf, unsigned long size)
Put an array with size elements of type T into the stream.
Definition: ipc_stream:671
l4_msgtag_t tag() const
Extract the L4 message tag from the stream.
Definition: ipc_stream:717
l4_msgtag_t & tag()
Extract a reference to the L4 message tag from the stream.
Definition: ipc_stream:724
l4_utcb_t * utcb() const
Return utcb pointer.
Definition: ipc_stream:756
void reset()
Reset the stream to empty, same state as a newly created stream.
Definition: ipc_stream:649
A receive item for receiving a single capability.
Definition: ipc_types:269
RPC wrapper for a send item.
Definition: ipc_types:295
Abstraction for extracting a zero-terminated string from an Ipc::Istream.
Definition: ipc_stream:192
Str_cp_in(T *v, unsigned long &size)
Create a buffer for extracting an array from an Ipc::Istream.
Definition: ipc_stream:202
Variably sized RPC argument.
Definition: ipc_varg:97
l4_umword_t Tag
The data type for the tag.
Definition: ipc_varg:106
unsigned length() const
Get the size of the RPC argument.
Definition: ipc_varg:114
Tag tag() const
Definition: ipc_varg:116
void data(char const *d)
Set Varg to indirect data value (usually in UTCB)
Definition: ipc_varg:120
#define L4_UNLIKELY(x)
Expression is unlikely to execute.
Definition: compiler.h:238
#define L4_DEPRECATED(s)
Mark symbol deprecated.
Definition: compiler.h:243
T1 min(T1 a, T1 b)
Get the minimum of a and b.
Definition: minmax:35
unsigned long l4_umword_t
Unsigned machine word.
Definition: l4int.h:51
unsigned long l4_addr_t
Address type.
Definition: l4int.h:45
unsigned long l4_cap_idx_t
L4 Capability selector Type.
Definition: types.h:342
@ L4_INVALID_CAP
Invalid capability selector.
Definition: consts.h:141
l4_msgtag_t l4_ipc_reply_and_wait(l4_utcb_t *utcb, l4_msgtag_t tag, l4_umword_t *label, l4_timeout_t timeout) L4_NOTHROW
Reply and wait operation (uses the reply capability).
Definition: ipc.h:471
l4_msgtag_t l4_ipc_receive(l4_cap_idx_t object, l4_utcb_t *utcb, l4_timeout_t timeout) L4_NOTHROW
Wait for a message from a specific source.
Definition: ipc.h:505
l4_msgtag_t l4_ipc_send_and_wait(l4_cap_idx_t dest, l4_utcb_t *utcb, l4_msgtag_t tag, l4_umword_t *label, l4_timeout_t timeout) L4_NOTHROW
Send a message and do an open wait.
Definition: ipc.h:479
l4_msgtag_t l4_ipc_send(l4_cap_idx_t dest, l4_utcb_t *utcb, l4_msgtag_t tag, l4_timeout_t timeout) L4_NOTHROW
Send a message to an object (do not wait for a reply).
Definition: ipc.h:488
l4_msgtag_t l4_ipc_call(l4_cap_idx_t object, l4_utcb_t *utcb, l4_msgtag_t tag, l4_timeout_t timeout) L4_NOTHROW
Object call (usual invocation).
Definition: ipc.h:463
l4_msgtag_t l4_ipc_wait(l4_utcb_t *utcb, l4_umword_t *label, l4_timeout_t timeout) L4_NOTHROW
Wait for an incoming message from any possible sender.
Definition: ipc.h:496
@ L4_SYSF_REPLY
Reply flag.
Definition: consts.h:89
l4_msgtag_t l4_msgtag(long label, unsigned words, unsigned items, unsigned flags) L4_NOTHROW
Create a message tag from the specified values.
Definition: types.h:408
@ L4_MSGTAG_FLAGS
Mask for all flags.
Definition: types.h:139
@ L4_UTCB_GENERIC_DATA_SIZE
Total number of message register (MRs) available.
Definition: utcb.h:47
@ L4_UTCB_GENERIC_BUFFERS_SIZE
Total number of buffer registers (BRs) available.
Definition: utcb.h:50
struct l4_utcb_t l4_utcb_t
Opaque type for the UTCB.
Definition: utcb.h:67
L4::Ipc::Istream & operator>>(L4::Ipc::Istream &s, bool &v)
Extract one element of type T from the stream s.
Definition: ipc_stream:1051
L4::Ipc::Ostream & operator<<(L4::Ipc::Ostream &s, bool v)
Insert an element to type T into the stream s.
Definition: ipc_stream:1204
Str_cp_in< T > str_cp_in(T *v, unsigned long &size)
Create a Str_cp_in for the given values.
Definition: ipc_stream:226
Msg_ptr< T > msg_ptr(T *&p)
Create an Msg_ptr to adjust the given pointer.
Definition: ipc_stream:265
Internal::Buf_cp_out< T > buf_cp_out(T const *v, unsigned long size)
Insert an array into an Ipc::Ostream.
Definition: ipc_stream:113
Gen_fpage< Snd_item > Snd_fpage
Send flex-page.
Definition: ipc_types:477
Gen_fpage< Buf_item > Rcv_fpage
Rcv flex-page.
Definition: ipc_types:479
T read(Istream &s)
Read a value out of a stream.
Definition: ipc_stream:1404
Internal::Buf_in< T > buf_in(T *&v, unsigned long &size)
Return a pointer to stream array data.
Definition: ipc_stream:323
Internal::Buf_cp_in< T > buf_cp_in(T *v, unsigned long &size)
Extract an array from an Ipc::Istream.
Definition: ipc_stream:172
L4 low-level kernel interface.
l4_umword_t br[L4_UTCB_GENERIC_BUFFERS_SIZE]
Buffer registers.
Definition: utcb.h:99
l4_umword_t bdr
Buffer descriptor.
Definition: utcb.h:96
Message tag data structure.
Definition: types.h:160
unsigned words() const L4_NOTHROW
Get the number of untyped words.
Definition: types.h:168
unsigned items() const L4_NOTHROW
Get the number of typed items.
Definition: types.h:170
Encapsulation of the message-register block in the UTCB.
Definition: utcb.h:79
l4_umword_t mr[L4_UTCB_GENERIC_DATA_SIZE]
Message registers.
Definition: utcb.h:80
Timeout pair.
Definition: __timeout.h:59