Fawkes API  Fawkes Development Version
shm.h
00001 
00002 /***************************************************************************
00003  *  shm.h - shared memory segment
00004  *
00005  *  Created: Thu Jan 12 13:12:24 2006
00006  *  Copyright  2005-2011  Tim Niemueller [www.niemueller.de]
00007  *
00008  ****************************************************************************/
00009 
00010 /*  This program is free software; you can redistribute it and/or modify
00011  *  it under the terms of the GNU General Public License as published by
00012  *  the Free Software Foundation; either version 2 of the License, or
00013  *  (at your option) any later version. A runtime exception applies to
00014  *  this software (see LICENSE.GPL_WRE file mentioned below for details).
00015  *
00016  *  This program is distributed in the hope that it will be useful,
00017  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00018  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00019  *  GNU Library General Public License for more details.
00020  *
00021  *  Read the full text in the LICENSE.GPL_WRE file in the doc directory.
00022  */
00023 
00024 #ifndef __UTILS_IPC_SHM_H_
00025 #define __UTILS_IPC_SHM_H_
00026 
00027 // for size_t
00028 #include <sys/types.h>
00029 #include <utils/ipc/shm_registry.h>
00030 
00031 namespace fawkes {
00032 
00033 class SharedMemoryHeader {
00034  public:
00035   virtual ~SharedMemoryHeader() {}
00036   virtual bool         matches(void *memptr)                  = 0;
00037   virtual size_t       size()                                 = 0;
00038   virtual void         initialize(void *memptr)               = 0;
00039   virtual void         set(void *memptr)                      = 0;
00040   virtual void         reset()                                = 0;
00041   virtual size_t       data_size()                            = 0;
00042   virtual SharedMemoryHeader *  clone() const                 = 0;
00043   virtual bool         operator==(const SharedMemoryHeader &s) const = 0;
00044 };
00045 
00046 class SharedMemoryLister;
00047 class SemaphoreSet;
00048 
00049 class SharedMemory
00050 {
00051 
00052  public:
00053 
00054   static const unsigned int MagicTokenSize;
00055   static const short        MaxNumConcurrentReaders;
00056 
00057   SharedMemory(const char *magic_token,
00058                SharedMemoryHeader *header,
00059                bool is_read_only, bool create,
00060                bool destroy_on_delete,
00061                const char *registry_name = 0);
00062 
00063   SharedMemory(const SharedMemory &s);
00064 
00065   virtual ~SharedMemory();
00066 
00067   bool                is_read_only() const;
00068   bool                is_destroyed() const;
00069   bool                is_swapable() const;
00070   bool                is_valid() const;
00071   bool                is_creator() const;
00072   bool                is_protected() const;
00073   void *              memptr() const;
00074   size_t              data_size() const;
00075   int                 shmem_id() const;
00076   unsigned int        num_attached() const;
00077 
00078   void                set(void *memptr);
00079   void                set_destroy_on_delete(bool destroy);
00080   void                add_semaphore();
00081   void                set_swapable(bool swapable);
00082 
00083   void                lock_for_read();
00084   bool                try_lock_for_read();
00085   void                lock_for_write();
00086   bool                try_lock_for_write();
00087   void                unlock();
00088 
00089   void *              ptr(void *addr) const;
00090   void *              addr(void *ptr) const;
00091 
00092   static void         list(const char *magic_token,
00093                            SharedMemoryHeader *header, SharedMemoryLister *lister,
00094                            const char *registry_name = 0);
00095 
00096   static void         erase(const char *magic_token,
00097                             SharedMemoryHeader *header,
00098                             SharedMemoryLister *lister = 0,
00099                             const char *registry_name = 0);
00100 
00101   static void         erase_orphaned(const char *magic_token,
00102                                      SharedMemoryHeader *header,
00103                                      SharedMemoryLister *lister = 0,
00104                                      const char *registry_name = 0);
00105 
00106   static bool         exists(const char *magic_token,
00107                              SharedMemoryHeader *header,
00108                              const char *registry_name = 0);
00109 
00110   static bool         is_destroyed(int shm_id);
00111   static bool         is_swapable(int shm_id);
00112   static unsigned int num_attached(int shm_id);
00113 
00114   class SharedMemoryIterator
00115   {
00116    public:
00117     SharedMemoryIterator();
00118     SharedMemoryIterator(const SharedMemoryIterator &shmit);
00119     SharedMemoryIterator(std::list<SharedMemoryRegistry::SharedMemID> ids,
00120                          SharedMemoryHeader *header);
00121     ~SharedMemoryIterator();
00122 
00123     SharedMemoryIterator &      operator++ ();        // prefix
00124     SharedMemoryIterator        operator++ (int inc); // postfix
00125     SharedMemoryIterator &      operator+  (unsigned int i);
00126     SharedMemoryIterator &      operator+= (unsigned int i);
00127     bool                        operator== (const SharedMemoryIterator & s) const;
00128     bool                        operator!= (const SharedMemoryIterator & s) const;
00129     const SharedMemoryHeader *  operator*  () const;
00130     SharedMemoryIterator &      operator=  (const SharedMemoryIterator & shmit);
00131 
00132     const char *                magic_token() const;
00133     int                         shmid() const;
00134     int                         semaphore() const;
00135     size_t                      segmsize() const;
00136     size_t                      segmnattch() const;
00137     void *                      databuf() const;
00138 
00139   private:
00140     void attach();
00141     void reset();
00142 
00143     bool                    __initialized;
00144     char                   *__magic_token;
00145     std::list<SharedMemoryRegistry::SharedMemID> __ids;
00146     std::list<SharedMemoryRegistry::SharedMemID>::iterator __id_it;
00147     int                     __cur_shmid;
00148     SharedMemoryHeader     *__header;
00149     void                   *__shm_buf;
00150     void                   *__data_buf;
00151     int                     __semaphore;
00152     size_t                  __segmsize;
00153     size_t                  __segmnattch;
00154   };
00155 
00156   static SharedMemoryIterator find(const char *magic_token,
00157                                    SharedMemoryHeader *header,
00158                                    const char *registry_name = 0);
00159   static SharedMemoryIterator end();
00160 
00161  protected:
00162 
00163   /** General header.
00164    * This header is stored right after the magic token.
00165    */
00166   typedef struct {
00167     void        *shm_addr;     /**< Desired shared memory address */
00168     int          semaphore;    /**< Semaphore set ID */
00169   } SharedMemory_header_t;
00170 
00171   SharedMemory(const char *magic_token,
00172                bool is_read_only, bool create, bool destroy_on_delete,
00173                const char *registry_name = 0);
00174 
00175   void attach();
00176   void free();
00177 
00178   void                   *_memptr;
00179   size_t                  _mem_size;
00180   size_t                  _data_size;
00181   SharedMemoryHeader     *_header;
00182   bool                    _is_read_only;
00183   bool                    _destroy_on_delete;
00184   bool                    _should_create;
00185   char                   *_magic_token;
00186   char                   *_shm_magic_token;
00187   SharedMemory_header_t  *_shm_header;
00188   void                   *_shm_upper_bound;
00189   long unsigned int       _shm_offset;
00190 
00191 
00192  private:
00193   SharedMemoryRegistry *__shm_registry;
00194   char *                __registry_name;
00195 
00196   void          *__shared_mem;
00197   int            __shared_mem_id;
00198   void          *__shared_mem_upper_bound;
00199 
00200   bool           __created;
00201   SemaphoreSet  *__semset;
00202 
00203   bool           __lock_aquired;
00204   bool           __write_lock_aquired;
00205 
00206 };
00207 
00208 
00209 } // end namespace fawkes
00210 
00211 #endif