diff options
author | Benny Prijono <bennylp@teluu.com> | 2005-11-13 19:40:44 +0000 |
---|---|---|
committer | Benny Prijono <bennylp@teluu.com> | 2005-11-13 19:40:44 +0000 |
commit | a08b589d09d5197f9a76d549a189e4686bd2ca8c (patch) | |
tree | 549904e7680dfab96b3ce579b1843c5d58107100 /pjlib/include/pj++ | |
parent | 8df70c6d5fef443506618bf31b686d53fef3f259 (diff) |
Applying license to pjproject
git-svn-id: http://svn.pjsip.org/repos/pjproject/trunk@49 74dad513-b988-da41-8d7b-12977e46ad98
Diffstat (limited to 'pjlib/include/pj++')
-rw-r--r-- | pjlib/include/pj++/file.hpp | 363 | ||||
-rw-r--r-- | pjlib/include/pj++/hash.hpp | 299 | ||||
-rw-r--r-- | pjlib/include/pj++/list.hpp | 643 | ||||
-rw-r--r-- | pjlib/include/pj++/lock.hpp | 285 | ||||
-rw-r--r-- | pjlib/include/pj++/os.hpp | 1597 | ||||
-rw-r--r-- | pjlib/include/pj++/pool.hpp | 529 | ||||
-rw-r--r-- | pjlib/include/pj++/proactor.hpp | 1025 | ||||
-rw-r--r-- | pjlib/include/pj++/scanner.hpp | 367 | ||||
-rw-r--r-- | pjlib/include/pj++/sock.hpp | 875 | ||||
-rw-r--r-- | pjlib/include/pj++/string.hpp | 839 | ||||
-rw-r--r-- | pjlib/include/pj++/timer.hpp | 383 | ||||
-rw-r--r-- | pjlib/include/pj++/tree.hpp | 245 | ||||
-rw-r--r-- | pjlib/include/pj++/types.hpp | 309 |
13 files changed, 4016 insertions, 3743 deletions
diff --git a/pjlib/include/pj++/file.hpp b/pjlib/include/pj++/file.hpp index e45810c5..1c35123a 100644 --- a/pjlib/include/pj++/file.hpp +++ b/pjlib/include/pj++/file.hpp @@ -1,171 +1,192 @@ -/* $Id$ - */ -#ifndef __PJPP_FILE_HPP__ -#define __PJPP_FILE_HPP__ - -#include <pj/file_io.h> -#include <pj/file_access.h> -#include <pj++/types.hpp> -#include <pj++/pool.hpp> - -// -// File API. -// -class Pj_File_API -{ -public: - // - // Check file existance. - // - static bool file_exists(const char *filename) - { - return pj_file_exists(filename) != 0; - } - - // - // Get file size. - // - static pj_off_t file_size(const char *filename) - { - return pj_file_size(filename); - } - - // - // Delete file. - // - static pj_status_t file_delete(const char *filename) - { - return pj_file_delete(filename); - } - - // - // Move/rename file. - // - static pj_status_t file_move(const char *oldname, const char *newname) - { - return pj_file_move(oldname, newname); - } - - // - // Get stat. - // - static pj_status_t file_stat(const char *filename, pj_file_stat *buf) - { - return pj_file_getstat(filename, buf); - } -}; - - -// -// File. -// -class Pj_File : public Pj_Object -{ -public: - // - // Offset type to be used in setpos. - // - enum Offset_Type - { - SEEK_SET = PJ_SEEK_SET, - SEEK_CUR = PJ_SEEK_CUR, - SEEK_END = PJ_SEEK_END, - }; - - // - // Default constructor. - // - Pj_File() - : hnd_(0) - { - } - - // - // Construct and open a file. - // - Pj_File(Pj_Pool *pool, const char *filename, - unsigned access = PJ_O_RDONLY) - : hnd_(NULL) - { - open(pool, filename, access); - } - - // - // Destructor closes the file. - // - ~Pj_File() - { - close(); - } - - // - // Open a file. - // - pj_status_t open(Pj_Pool *pool, const char *filename, - unsigned access = PJ_O_RDONLY ) - { - close(); - return pj_file_open(pool->pool_(), filename, access, &hnd_); - } - - // - // Close a file. - // - void close() - { - if (hnd_ != 0) { - pj_file_close(hnd_); - hnd_ = 0; - } - } - - // - // Write data. - // - pj_ssize_t write(const void *buff, pj_size_t size) - { - pj_ssize_t bytes = size; - if (pj_file_write(hnd_, buff, &bytes) != PJ_SUCCESS) - return -1; - return bytes; - } - - // - // Read data. - // - pj_ssize_t read(void *buf, pj_size_t size) - { - pj_ssize_t bytes = size; - if (pj_file_read(hnd_, buf, &bytes) != PJ_SUCCESS) - return -1; - return bytes; - } - - // - // Set file position. - // - pj_status_t setpos(pj_off_t offset, Offset_Type whence) - { - return pj_file_setpos(hnd_, offset, - (enum pj_file_seek_type)whence); - } - - // - // Get file position. - // - pj_off_t getpos() - { - pj_off_t pos; - if (pj_file_getpos(hnd_, &pos) != PJ_SUCCESS) - return -1; - return pos; - } - -private: - pj_oshandle_t hnd_; -}; - - - -#endif /* __PJPP_FILE_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_FILE_HPP__
+#define __PJPP_FILE_HPP__
+
+#include <pj/file_io.h>
+#include <pj/file_access.h>
+#include <pj++/types.hpp>
+#include <pj++/pool.hpp>
+
+//
+// File API.
+//
+class Pj_File_API
+{
+public:
+ //
+ // Check file existance.
+ //
+ static bool file_exists(const char *filename)
+ {
+ return pj_file_exists(filename) != 0;
+ }
+
+ //
+ // Get file size.
+ //
+ static pj_off_t file_size(const char *filename)
+ {
+ return pj_file_size(filename);
+ }
+
+ //
+ // Delete file.
+ //
+ static pj_status_t file_delete(const char *filename)
+ {
+ return pj_file_delete(filename);
+ }
+
+ //
+ // Move/rename file.
+ //
+ static pj_status_t file_move(const char *oldname, const char *newname)
+ {
+ return pj_file_move(oldname, newname);
+ }
+
+ //
+ // Get stat.
+ //
+ static pj_status_t file_stat(const char *filename, pj_file_stat *buf)
+ {
+ return pj_file_getstat(filename, buf);
+ }
+};
+
+
+//
+// File.
+//
+class Pj_File : public Pj_Object
+{
+public:
+ //
+ // Offset type to be used in setpos.
+ //
+ enum Offset_Type
+ {
+ SEEK_SET = PJ_SEEK_SET,
+ SEEK_CUR = PJ_SEEK_CUR,
+ SEEK_END = PJ_SEEK_END,
+ };
+
+ //
+ // Default constructor.
+ //
+ Pj_File()
+ : hnd_(0)
+ {
+ }
+
+ //
+ // Construct and open a file.
+ //
+ Pj_File(Pj_Pool *pool, const char *filename,
+ unsigned access = PJ_O_RDONLY)
+ : hnd_(NULL)
+ {
+ open(pool, filename, access);
+ }
+
+ //
+ // Destructor closes the file.
+ //
+ ~Pj_File()
+ {
+ close();
+ }
+
+ //
+ // Open a file.
+ //
+ pj_status_t open(Pj_Pool *pool, const char *filename,
+ unsigned access = PJ_O_RDONLY )
+ {
+ close();
+ return pj_file_open(pool->pool_(), filename, access, &hnd_);
+ }
+
+ //
+ // Close a file.
+ //
+ void close()
+ {
+ if (hnd_ != 0) {
+ pj_file_close(hnd_);
+ hnd_ = 0;
+ }
+ }
+
+ //
+ // Write data.
+ //
+ pj_ssize_t write(const void *buff, pj_size_t size)
+ {
+ pj_ssize_t bytes = size;
+ if (pj_file_write(hnd_, buff, &bytes) != PJ_SUCCESS)
+ return -1;
+ return bytes;
+ }
+
+ //
+ // Read data.
+ //
+ pj_ssize_t read(void *buf, pj_size_t size)
+ {
+ pj_ssize_t bytes = size;
+ if (pj_file_read(hnd_, buf, &bytes) != PJ_SUCCESS)
+ return -1;
+ return bytes;
+ }
+
+ //
+ // Set file position.
+ //
+ pj_status_t setpos(pj_off_t offset, Offset_Type whence)
+ {
+ return pj_file_setpos(hnd_, offset,
+ (enum pj_file_seek_type)whence);
+ }
+
+ //
+ // Get file position.
+ //
+ pj_off_t getpos()
+ {
+ pj_off_t pos;
+ if (pj_file_getpos(hnd_, &pos) != PJ_SUCCESS)
+ return -1;
+ return pos;
+ }
+
+private:
+ pj_oshandle_t hnd_;
+};
+
+
+
+#endif /* __PJPP_FILE_HPP__ */
+
diff --git a/pjlib/include/pj++/hash.hpp b/pjlib/include/pj++/hash.hpp index 691ac3a8..c362625b 100644 --- a/pjlib/include/pj++/hash.hpp +++ b/pjlib/include/pj++/hash.hpp @@ -1,139 +1,160 @@ -/* $Id$ - */ -#ifndef __PJPP_HASH_HPP__ -#define __PJPP_HASH_HPP__ - -#include <pj++/types.hpp> -#include <pj++/pool.hpp> -#include <pj/hash.h> - -// -// Hash table. -// -class Pj_Hash_Table : public Pj_Object -{ -public: - // - // Hash table iterator. - // - class iterator - { - public: - iterator() - { - } - explicit iterator(pj_hash_table_t *h, pj_hash_iterator_t *i) - : ht_(h), it_(i) - { - } - iterator(const iterator &rhs) - : ht_(rhs.ht_), it_(rhs.it_) - { - } - void operator++() - { - it_ = pj_hash_next(ht_, it_); - } - bool operator==(const iterator &rhs) - { - return ht_ == rhs.ht_ && it_ == rhs.it_; - } - iterator & operator=(const iterator &rhs) - { - ht_=rhs.ht_; it_=rhs.it_; - return *this; - } - private: - pj_hash_table_t *ht_; - pj_hash_iterator_t it_val_; - pj_hash_iterator_t *it_; - - friend class Pj_Hash_Table; - }; - - // - // Construct hash table. - // - Pj_Hash_Table(Pj_Pool *pool, unsigned size) - { - table_ = pj_hash_create(pool->pool_(), size); - } - - // - // Destroy hash table. - // - ~Pj_Hash_Table() - { - } - - // - // Calculate hash value. - // - static pj_uint32_t calc( pj_uint32_t initial_hval, - const void *key, - unsigned keylen = PJ_HASH_KEY_STRING) - { - return pj_hash_calc(initial_hval, key, keylen); - } - - // - // Return pjlib compatible hash table object. - // - pj_hash_table_t *pj_hash_table_t_() - { - return table_; - } - - // - // Get the value associated with the specified key. - // - void *get(const void *key, unsigned keylen = PJ_HASH_KEY_STRING) - { - return pj_hash_get(table_, key, keylen); - } - - // - // Associate a value with a key. - // Set the value to NULL to delete the key from the hash table. - // - void set(Pj_Pool *pool, - const void *key, - void *value, - unsigned keylen = PJ_HASH_KEY_STRING) - { - pj_hash_set(pool->pool_(), table_, key, keylen, value); - } - - // - // Get number of items in the hash table. - // - unsigned count() - { - return pj_hash_count(table_); - } - - // - // Iterate hash table. - // - iterator begin() - { - iterator it(table_, NULL); - it.it_ = pj_hash_first(table_, &it.it_val_); - return it; - } - - // - // End of items. - // - iterator end() - { - return iterator(table_, NULL); - } - -private: - pj_hash_table_t *table_; -}; - - -#endif /* __PJPP_HASH_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_HASH_HPP__
+#define __PJPP_HASH_HPP__
+
+#include <pj++/types.hpp>
+#include <pj++/pool.hpp>
+#include <pj/hash.h>
+
+//
+// Hash table.
+//
+class Pj_Hash_Table : public Pj_Object
+{
+public:
+ //
+ // Hash table iterator.
+ //
+ class iterator
+ {
+ public:
+ iterator()
+ {
+ }
+ explicit iterator(pj_hash_table_t *h, pj_hash_iterator_t *i)
+ : ht_(h), it_(i)
+ {
+ }
+ iterator(const iterator &rhs)
+ : ht_(rhs.ht_), it_(rhs.it_)
+ {
+ }
+ void operator++()
+ {
+ it_ = pj_hash_next(ht_, it_);
+ }
+ bool operator==(const iterator &rhs)
+ {
+ return ht_ == rhs.ht_ && it_ == rhs.it_;
+ }
+ iterator & operator=(const iterator &rhs)
+ {
+ ht_=rhs.ht_; it_=rhs.it_;
+ return *this;
+ }
+ private:
+ pj_hash_table_t *ht_;
+ pj_hash_iterator_t it_val_;
+ pj_hash_iterator_t *it_;
+
+ friend class Pj_Hash_Table;
+ };
+
+ //
+ // Construct hash table.
+ //
+ Pj_Hash_Table(Pj_Pool *pool, unsigned size)
+ {
+ table_ = pj_hash_create(pool->pool_(), size);
+ }
+
+ //
+ // Destroy hash table.
+ //
+ ~Pj_Hash_Table()
+ {
+ }
+
+ //
+ // Calculate hash value.
+ //
+ static pj_uint32_t calc( pj_uint32_t initial_hval,
+ const void *key,
+ unsigned keylen = PJ_HASH_KEY_STRING)
+ {
+ return pj_hash_calc(initial_hval, key, keylen);
+ }
+
+ //
+ // Return pjlib compatible hash table object.
+ //
+ pj_hash_table_t *pj_hash_table_t_()
+ {
+ return table_;
+ }
+
+ //
+ // Get the value associated with the specified key.
+ //
+ void *get(const void *key, unsigned keylen = PJ_HASH_KEY_STRING)
+ {
+ return pj_hash_get(table_, key, keylen);
+ }
+
+ //
+ // Associate a value with a key.
+ // Set the value to NULL to delete the key from the hash table.
+ //
+ void set(Pj_Pool *pool,
+ const void *key,
+ void *value,
+ unsigned keylen = PJ_HASH_KEY_STRING)
+ {
+ pj_hash_set(pool->pool_(), table_, key, keylen, value);
+ }
+
+ //
+ // Get number of items in the hash table.
+ //
+ unsigned count()
+ {
+ return pj_hash_count(table_);
+ }
+
+ //
+ // Iterate hash table.
+ //
+ iterator begin()
+ {
+ iterator it(table_, NULL);
+ it.it_ = pj_hash_first(table_, &it.it_val_);
+ return it;
+ }
+
+ //
+ // End of items.
+ //
+ iterator end()
+ {
+ return iterator(table_, NULL);
+ }
+
+private:
+ pj_hash_table_t *table_;
+};
+
+
+#endif /* __PJPP_HASH_HPP__ */
+
diff --git a/pjlib/include/pj++/list.hpp b/pjlib/include/pj++/list.hpp index c3a8f386..363c1fad 100644 --- a/pjlib/include/pj++/list.hpp +++ b/pjlib/include/pj++/list.hpp @@ -1,311 +1,332 @@ -/* $Id$ - */ -#ifndef __PJPP_LIST_HPP__ -#define __PJPP_LIST_HPP__ - -#include <pj/list.h> -#include <pj++/pool.hpp> - - -// -// Linked-list. -// -// Note: -// List_Node must have public member next and prev. Normally -// it will be declared like: -// -// struct my_node -// { -// PJ_DECL_LIST_MEMBER(struct my_node); -// .. -// }; -// -// -template <class List_Node> -class Pj_List : public Pj_Object -{ -public: - // - // List const_iterator. - // - class const_iterator - { - public: - const_iterator() - : node_(NULL) - {} - const_iterator(const List_Node *nd) - : node_((List_Node*)nd) - {} - const List_Node * operator *() - { - return node_; - } - const List_Node * operator -> () - { - return node_; - } - const_iterator operator++() - { - return const_iterator(node_->next); - } - bool operator==(const const_iterator &rhs) - { - return node_ == rhs.node_; - } - bool operator!=(const const_iterator &rhs) - { - return node_ != rhs.node_; - } - - protected: - List_Node *node_; - }; - - // - // List iterator. - // - class iterator : public const_iterator - { - public: - iterator() - {} - iterator(List_Node *nd) - : const_iterator(nd) - {} - List_Node * operator *() - { - return node_; - } - List_Node * operator -> () - { - return node_; - } - iterator operator++() - { - return iterator(node_->next); - } - bool operator==(const iterator &rhs) - { - return node_ == rhs.node_; - } - bool operator!=(const iterator &rhs) - { - return node_ != rhs.node_; - } - }; - - // - // Default constructor. - // - Pj_List() - { - pj_list_init(&root_); - if (0) compiletest(); - } - - // - // Check if list is empty. - // - bool empty() const - { - return pj_list_empty(&root_); - } - - // - // Get first element. - // - iterator begin() - { - return iterator(root_.next); - } - - // - // Get first element. - // - const_iterator begin() const - { - return const_iterator(root_.next); - } - - // - // Get end-of-element - // - const_iterator end() const - { - return const_iterator((List_Node*)&root_); - } - - // - // Get end-of-element - // - iterator end() - { - return iterator((List_Node*)&root_); - } - - // - // Insert node. - // - void insert_before (iterator &pos, List_Node *node) - { - pj_list_insert_before( *pos, node ); - } - - // - // Insert node. - // - void insert_after(iterator &pos, List_Node *node) - { - pj_list_insert_after(*pos, node); - } - - // - // Merge list. - // - void merge_first(List_Node *list2) - { - pj_list_merge_first(&root_, list2); - } - - // - // Merge list. - // - void merge_last(Pj_List *list) - { - pj_list_merge_last(&root_, &list->root_); - } - - // - // Insert list. - // - void insert_nodes_before(iterator &pos, Pj_List *list2) - { - pj_list_insert_nodes_before(*pos, &list2->root_); - } - - // - // Insert list. - // - void insert_nodes_after(iterator &pos, Pj_List *list2) - { - pj_list_insert_nodes_after(*pos, &list2->root_); - } - - // - // Erase an element. - // - void erase(iterator &it) - { - pj_list_erase(*it); - } - - // - // Get first element. - // - List_Node *front() - { - return root_.next; - } - - // - // Get first element. - // - const List_Node *front() const - { - return root_.next; - } - - // - // Remove first element. - // - void pop_front() - { - pj_list_erase(root_.next); - } - - // - // Get last element. - // - List_Node *back() - { - return root_.prev; - } - - // - // Get last element. - // - const List_Node *back() const - { - return root_.prev; - } - - // - // Remove last element. - // - void pop_back() - { - pj_list_erase(root_.prev); - } - - // - // Find a node. - // - iterator find(List_Node *node) - { - List_Node *n = pj_list_find_node(&root_, node); - return n ? iterator(n) : end(); - } - - // - // Find a node. - // - const_iterator find(List_Node *node) const - { - List_Node *n = pj_list_find_node(&root_, node); - return n ? const_iterator(n) : end(); - } - - // - // Insert a node in the back. - // - void push_back(List_Node *node) - { - pj_list_insert_after(root_.prev, node); - } - - // - // Insert a node in the front. - // - void push_front(List_Node *node) - { - pj_list_insert_before(root_.next, node); - } - - // - // Remove all elements. - // - void clear() - { - root_.next = &root_; - root_.prev = &root_; - } - -private: - struct RootNode - { - PJ_DECL_LIST_MEMBER(List_Node); - } root_; - - void compiletest() - { - // If you see error in this line, - // it's because List_Node is not derived from Pj_List_Node. - List_Node *n = (List_Node*)0; - n = n->next; n = n->prev; - } -}; - - -#endif /* __PJPP_LIST_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_LIST_HPP__
+#define __PJPP_LIST_HPP__
+
+#include <pj/list.h>
+#include <pj++/pool.hpp>
+
+
+//
+// Linked-list.
+//
+// Note:
+// List_Node must have public member next and prev. Normally
+// it will be declared like:
+//
+// struct my_node
+// {
+// PJ_DECL_LIST_MEMBER(struct my_node);
+// ..
+// };
+//
+//
+template <class List_Node>
+class Pj_List : public Pj_Object
+{
+public:
+ //
+ // List const_iterator.
+ //
+ class const_iterator
+ {
+ public:
+ const_iterator()
+ : node_(NULL)
+ {}
+ const_iterator(const List_Node *nd)
+ : node_((List_Node*)nd)
+ {}
+ const List_Node * operator *()
+ {
+ return node_;
+ }
+ const List_Node * operator -> ()
+ {
+ return node_;
+ }
+ const_iterator operator++()
+ {
+ return const_iterator(node_->next);
+ }
+ bool operator==(const const_iterator &rhs)
+ {
+ return node_ == rhs.node_;
+ }
+ bool operator!=(const const_iterator &rhs)
+ {
+ return node_ != rhs.node_;
+ }
+
+ protected:
+ List_Node *node_;
+ };
+
+ //
+ // List iterator.
+ //
+ class iterator : public const_iterator
+ {
+ public:
+ iterator()
+ {}
+ iterator(List_Node *nd)
+ : const_iterator(nd)
+ {}
+ List_Node * operator *()
+ {
+ return node_;
+ }
+ List_Node * operator -> ()
+ {
+ return node_;
+ }
+ iterator operator++()
+ {
+ return iterator(node_->next);
+ }
+ bool operator==(const iterator &rhs)
+ {
+ return node_ == rhs.node_;
+ }
+ bool operator!=(const iterator &rhs)
+ {
+ return node_ != rhs.node_;
+ }
+ };
+
+ //
+ // Default constructor.
+ //
+ Pj_List()
+ {
+ pj_list_init(&root_);
+ if (0) compiletest();
+ }
+
+ //
+ // Check if list is empty.
+ //
+ bool empty() const
+ {
+ return pj_list_empty(&root_);
+ }
+
+ //
+ // Get first element.
+ //
+ iterator begin()
+ {
+ return iterator(root_.next);
+ }
+
+ //
+ // Get first element.
+ //
+ const_iterator begin() const
+ {
+ return const_iterator(root_.next);
+ }
+
+ //
+ // Get end-of-element
+ //
+ const_iterator end() const
+ {
+ return const_iterator((List_Node*)&root_);
+ }
+
+ //
+ // Get end-of-element
+ //
+ iterator end()
+ {
+ return iterator((List_Node*)&root_);
+ }
+
+ //
+ // Insert node.
+ //
+ void insert_before (iterator &pos, List_Node *node)
+ {
+ pj_list_insert_before( *pos, node );
+ }
+
+ //
+ // Insert node.
+ //
+ void insert_after(iterator &pos, List_Node *node)
+ {
+ pj_list_insert_after(*pos, node);
+ }
+
+ //
+ // Merge list.
+ //
+ void merge_first(List_Node *list2)
+ {
+ pj_list_merge_first(&root_, list2);
+ }
+
+ //
+ // Merge list.
+ //
+ void merge_last(Pj_List *list)
+ {
+ pj_list_merge_last(&root_, &list->root_);
+ }
+
+ //
+ // Insert list.
+ //
+ void insert_nodes_before(iterator &pos, Pj_List *list2)
+ {
+ pj_list_insert_nodes_before(*pos, &list2->root_);
+ }
+
+ //
+ // Insert list.
+ //
+ void insert_nodes_after(iterator &pos, Pj_List *list2)
+ {
+ pj_list_insert_nodes_after(*pos, &list2->root_);
+ }
+
+ //
+ // Erase an element.
+ //
+ void erase(iterator &it)
+ {
+ pj_list_erase(*it);
+ }
+
+ //
+ // Get first element.
+ //
+ List_Node *front()
+ {
+ return root_.next;
+ }
+
+ //
+ // Get first element.
+ //
+ const List_Node *front() const
+ {
+ return root_.next;
+ }
+
+ //
+ // Remove first element.
+ //
+ void pop_front()
+ {
+ pj_list_erase(root_.next);
+ }
+
+ //
+ // Get last element.
+ //
+ List_Node *back()
+ {
+ return root_.prev;
+ }
+
+ //
+ // Get last element.
+ //
+ const List_Node *back() const
+ {
+ return root_.prev;
+ }
+
+ //
+ // Remove last element.
+ //
+ void pop_back()
+ {
+ pj_list_erase(root_.prev);
+ }
+
+ //
+ // Find a node.
+ //
+ iterator find(List_Node *node)
+ {
+ List_Node *n = pj_list_find_node(&root_, node);
+ return n ? iterator(n) : end();
+ }
+
+ //
+ // Find a node.
+ //
+ const_iterator find(List_Node *node) const
+ {
+ List_Node *n = pj_list_find_node(&root_, node);
+ return n ? const_iterator(n) : end();
+ }
+
+ //
+ // Insert a node in the back.
+ //
+ void push_back(List_Node *node)
+ {
+ pj_list_insert_after(root_.prev, node);
+ }
+
+ //
+ // Insert a node in the front.
+ //
+ void push_front(List_Node *node)
+ {
+ pj_list_insert_before(root_.next, node);
+ }
+
+ //
+ // Remove all elements.
+ //
+ void clear()
+ {
+ root_.next = &root_;
+ root_.prev = &root_;
+ }
+
+private:
+ struct RootNode
+ {
+ PJ_DECL_LIST_MEMBER(List_Node);
+ } root_;
+
+ void compiletest()
+ {
+ // If you see error in this line,
+ // it's because List_Node is not derived from Pj_List_Node.
+ List_Node *n = (List_Node*)0;
+ n = n->next; n = n->prev;
+ }
+};
+
+
+#endif /* __PJPP_LIST_HPP__ */
+
diff --git a/pjlib/include/pj++/lock.hpp b/pjlib/include/pj++/lock.hpp index 95ea63b6..cf5a57da 100644 --- a/pjlib/include/pj++/lock.hpp +++ b/pjlib/include/pj++/lock.hpp @@ -1,132 +1,153 @@ -/* $Id$ - */ -#ifndef __PJPP_LOCK_HPP__ -#define __PJPP_LOCK_HPP__ - -#include <pj++/types.hpp> -#include <pj/lock.h> -#include <pj++/pool.hpp> - -////////////////////////////////////////////////////////////////////////////// -// Lock object. -// -class Pj_Lock : public Pj_Object -{ -public: - // - // Constructor. - // - explicit Pj_Lock(pj_lock_t *lock) - : lock_(lock) - { - } - - // - // Destructor. - // - ~Pj_Lock() - { - if (lock_) - pj_lock_destroy(lock_); - } - - // - // Get pjlib compatible lock object. - // - pj_lock_t *pj_lock_t_() - { - return lock_; - } - - // - // acquire lock. - // - pj_status_t acquire() - { - return pj_lock_acquire(lock_); - } - - // - // release lock,. - // - pj_status_t release() - { - return pj_lock_release(lock_); - } - -protected: - pj_lock_t *lock_; -}; - - -////////////////////////////////////////////////////////////////////////////// -// Null lock object. -// -class Pj_Null_Lock : public Pj_Lock -{ -public: - // - // Default constructor. - // - explicit Pj_Null_Lock(Pj_Pool *pool, const char *name = NULL) - : Pj_Lock(NULL) - { - pj_lock_create_null_mutex(pool->pool_(), name, &lock_); - } -}; - -////////////////////////////////////////////////////////////////////////////// -// Simple mutex lock object. -// -class Pj_Simple_Mutex_Lock : public Pj_Lock -{ -public: - // - // Default constructor. - // - explicit Pj_Simple_Mutex_Lock(Pj_Pool *pool, const char *name = NULL) - : Pj_Lock(NULL) - { - pj_lock_create_simple_mutex(pool->pool_(), name, &lock_); - } -}; - -////////////////////////////////////////////////////////////////////////////// -// Recursive mutex lock object. -// -class Pj_Recursive_Mutex_Lock : public Pj_Lock -{ -public: - // - // Default constructor. - // - explicit Pj_Recursive_Mutex_Lock(Pj_Pool *pool, const char *name = NULL) - : Pj_Lock(NULL) - { - pj_lock_create_recursive_mutex(pool->pool_(), name, &lock_); - } -}; - -////////////////////////////////////////////////////////////////////////////// -// Semaphore lock object. -// -class Pj_Semaphore_Lock : public Pj_Lock -{ -public: - // - // Default constructor. - // - explicit Pj_Semaphore_Lock(Pj_Pool *pool, - unsigned max=PJ_MAXINT32, - unsigned initial=0, - const char *name=NULL) - : Pj_Lock(NULL) - { - pj_lock_create_semaphore(pool->pool_(), name, initial, max, &lock_); - } -}; - - - -#endif /* __PJPP_LOCK_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_LOCK_HPP__
+#define __PJPP_LOCK_HPP__
+
+#include <pj++/types.hpp>
+#include <pj/lock.h>
+#include <pj++/pool.hpp>
+
+//////////////////////////////////////////////////////////////////////////////
+// Lock object.
+//
+class Pj_Lock : public Pj_Object
+{
+public:
+ //
+ // Constructor.
+ //
+ explicit Pj_Lock(pj_lock_t *lock)
+ : lock_(lock)
+ {
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Lock()
+ {
+ if (lock_)
+ pj_lock_destroy(lock_);
+ }
+
+ //
+ // Get pjlib compatible lock object.
+ //
+ pj_lock_t *pj_lock_t_()
+ {
+ return lock_;
+ }
+
+ //
+ // acquire lock.
+ //
+ pj_status_t acquire()
+ {
+ return pj_lock_acquire(lock_);
+ }
+
+ //
+ // release lock,.
+ //
+ pj_status_t release()
+ {
+ return pj_lock_release(lock_);
+ }
+
+protected:
+ pj_lock_t *lock_;
+};
+
+
+//////////////////////////////////////////////////////////////////////////////
+// Null lock object.
+//
+class Pj_Null_Lock : public Pj_Lock
+{
+public:
+ //
+ // Default constructor.
+ //
+ explicit Pj_Null_Lock(Pj_Pool *pool, const char *name = NULL)
+ : Pj_Lock(NULL)
+ {
+ pj_lock_create_null_mutex(pool->pool_(), name, &lock_);
+ }
+};
+
+//////////////////////////////////////////////////////////////////////////////
+// Simple mutex lock object.
+//
+class Pj_Simple_Mutex_Lock : public Pj_Lock
+{
+public:
+ //
+ // Default constructor.
+ //
+ explicit Pj_Simple_Mutex_Lock(Pj_Pool *pool, const char *name = NULL)
+ : Pj_Lock(NULL)
+ {
+ pj_lock_create_simple_mutex(pool->pool_(), name, &lock_);
+ }
+};
+
+//////////////////////////////////////////////////////////////////////////////
+// Recursive mutex lock object.
+//
+class Pj_Recursive_Mutex_Lock : public Pj_Lock
+{
+public:
+ //
+ // Default constructor.
+ //
+ explicit Pj_Recursive_Mutex_Lock(Pj_Pool *pool, const char *name = NULL)
+ : Pj_Lock(NULL)
+ {
+ pj_lock_create_recursive_mutex(pool->pool_(), name, &lock_);
+ }
+};
+
+//////////////////////////////////////////////////////////////////////////////
+// Semaphore lock object.
+//
+class Pj_Semaphore_Lock : public Pj_Lock
+{
+public:
+ //
+ // Default constructor.
+ //
+ explicit Pj_Semaphore_Lock(Pj_Pool *pool,
+ unsigned max=PJ_MAXINT32,
+ unsigned initial=0,
+ const char *name=NULL)
+ : Pj_Lock(NULL)
+ {
+ pj_lock_create_semaphore(pool->pool_(), name, initial, max, &lock_);
+ }
+};
+
+
+
+#endif /* __PJPP_LOCK_HPP__ */
+
diff --git a/pjlib/include/pj++/os.hpp b/pjlib/include/pj++/os.hpp index 461a36e8..65553b00 100644 --- a/pjlib/include/pj++/os.hpp +++ b/pjlib/include/pj++/os.hpp @@ -1,788 +1,809 @@ -/* $Id$ - */ -#ifndef __PJPP_OS_HPP__ -#define __PJPP_OS_HPP__ - -#include <pj/os.h> -#include <pj++/types.hpp> -#include <pj++/pool.hpp> - -class Pj_Thread; - -// -// Thread API. -// -class Pj_Thread_API -{ -public: - // - // Create a thread. - // - static pj_status_t create( Pj_Pool *pool, pj_thread_t **thread, - pj_thread_proc *proc, void *arg, - unsigned flags = 0, - const char *name = NULL, - pj_size_t stack_size = 0 ) - { - return pj_thread_create(pool->pool_(), name, proc, arg, stack_size, - flags, thread); - } - - // - // Register a thread. - // - static pj_status_t register_this_thread( pj_thread_desc desc, - pj_thread_t **thread, - const char *name = NULL ) - { - return pj_thread_register( name, desc, thread ); - } - - // - // Get current thread. - // Will return pj_thread_t (sorry folks, not Pj_Thread). - // - static pj_thread_t *this_thread() - { - return pj_thread_this(); - } - - // - // Get thread name. - // - static const char *get_name(pj_thread_t *thread) - { - return pj_thread_get_name(thread); - } - - // - // Resume thread. - // - static pj_status_t resume(pj_thread_t *thread) - { - return pj_thread_resume(thread); - } - - // - // Sleep. - // - static pj_status_t sleep(unsigned msec) - { - return pj_thread_sleep(msec); - } - - // - // Join the specified thread. - // - static pj_status_t join(pj_thread_t *thread) - { - return pj_thread_join(thread); - } - - // - // Destroy thread - // - static pj_status_t destroy(pj_thread_t *thread) - { - return pj_thread_destroy(thread); - } -}; - - - -// -// Thread object. -// -// How to use: -// Derive a class from this class, then override main(). -// -class Pj_Thread : public Pj_Object -{ -public: - enum Flags - { - FLAG_SUSPENDED = PJ_THREAD_SUSPENDED - }; - - // - // Default constructor. - // - Pj_Thread() - : thread_(NULL) - { - } - - // - // Destroy thread. - // - ~Pj_Thread() - { - destroy(); - } - - // - // This is the main thread function. - // - virtual int main() = 0; - - // - // Start a thread. - // - pj_status_t create( Pj_Pool *pool, - unsigned flags = 0, - const char *thread_name = NULL, - pj_size_t stack_size = PJ_THREAD_DEFAULT_STACK_SIZE) - { - destroy(); - return Pj_Thread_API::create( pool, &thread_, &thread_proc, this, - flags, thread_name); - } - - // - // Get pjlib compatible thread object. - // - pj_thread_t *pj_thread_t_() - { - return thread_; - } - - // - // Get thread name. - // - const char *get_name() - { - return Pj_Thread_API::get_name(thread_); - } - - // - // Resume a suspended thread. - // - pj_status_t resume() - { - return Pj_Thread_API::resume(thread_); - } - - // - // Join this thread. - // - pj_status_t join() - { - return Pj_Thread_API::join(thread_); - } - - // - // Destroy thread. - // - pj_status_t destroy() - { - if (thread_) { - Pj_Thread_API::destroy(thread_); - thread_ = NULL; - } - } - -protected: - pj_thread_t *thread_; - - static int PJ_THREAD_FUNC thread_proc(void *obj) - { - Pj_Thread *thread_class = (Pj_Thread*)obj; - return thread_class->main(); - } -}; - - -// -// External Thread -// (threads that were started by external means, i.e. not -// with Pj_Thread::create). -// -// This class will normally be defined as local variable in -// external thread's stack, normally inside thread's main proc. -// But be aware that the handle will be destroyed on destructor! -// -class Pj_External_Thread : public Pj_Thread -{ -public: - Pj_External_Thread() - { - } - - // - // Register external thread so that pjlib functions can work - // in that thread. - // - pj_status_t register_this_thread( const char *name=NULL ) - { - return Pj_Thread_API::register_this_thread(desc_, &thread_,name); - } - -private: - pj_thread_desc desc_; -}; - - -// -// Thread specific data/thread local storage/TLS. -// -class Pj_Thread_Local_API -{ -public: - // - // Allocate thread local storage (TLS) index. - // - static pj_status_t alloc(long *index) - { - return pj_thread_local_alloc(index); - } - - // - // Free TLS index. - // - static void free(long index) - { - pj_thread_local_free(index); - } - - // - // Set thread specific data. - // - static pj_status_t set(long index, void *value) - { - return pj_thread_local_set(index, value); - } - - // - // Get thread specific data. - // - static void *get(long index) - { - return pj_thread_local_get(index); - } - -}; - -// -// Atomic variable -// -// How to use: -// Pj_Atomic_Var var(pool, 0); -// var.set(..); -// -class Pj_Atomic_Var : public Pj_Object -{ -public: - // - // Default constructor, initialize variable with NULL. - // - Pj_Atomic_Var() - : var_(NULL) - { - } - - // - // Construct atomic variable. - // - Pj_Atomic_Var(Pj_Pool *pool, pj_atomic_value_t value) - : var_(NULL) - { - create(pool, value); - } - - // - // Destructor. - // - ~Pj_Atomic_Var() - { - destroy(); - } - - // - // Create atomic variable. - // - pj_status_t create( Pj_Pool *pool, pj_atomic_value_t value) - { - destroy(); - return pj_atomic_create(pool->pool_(), value, &var_); - } - - // - // Destroy. - // - void destroy() - { - if (var_) { - pj_atomic_destroy(var_); - var_ = NULL; - } - } - - // - // Get pjlib compatible atomic variable. - // - pj_atomic_t *pj_atomic_t_() - { - return var_; - } - - // - // Set the value. - // - void set(pj_atomic_value_t val) - { - pj_atomic_set(var_, val); - } - - // - // Get the value. - // - pj_atomic_value_t get() - { - return pj_atomic_get(var_); - } - - // - // Increment. - // - void inc() - { - pj_atomic_inc(var_); - } - - // - // Increment and get the result. - // - pj_atomic_value_t inc_and_get() - { - return pj_atomic_inc_and_get(var_); - } - - // - // Decrement. - // - void dec() - { - pj_atomic_dec(var_); - } - - // - // Decrement and get the result. - // - pj_atomic_value_t dec_and_get() - { - return pj_atomic_dec_and_get(var_); - } - - // - // Add the variable. - // - void add(pj_atomic_value_t value) - { - pj_atomic_add(var_, value); - } - - // - // Add the variable and get the value. - // - pj_atomic_value_t add_and_get(pj_atomic_value_t value) - { - return pj_atomic_add_and_get(var_, value ); - } - -private: - pj_atomic_t *var_; -}; - - -// -// Mutex -// -class Pj_Mutex : public Pj_Object -{ -public: - // - // Mutex type. - // - enum Type - { - DEFAULT = PJ_MUTEX_DEFAULT, - SIMPLE = PJ_MUTEX_SIMPLE, - RECURSE = PJ_MUTEX_RECURSE, - }; - - // - // Default constructor will create default mutex. - // - explicit Pj_Mutex(Pj_Pool *pool, Type type = DEFAULT, - const char *name = NULL) - : mutex_(NULL) - { - create(pool, type, name); - } - - // - // Destructor. - // - ~Pj_Mutex() - { - destroy(); - } - - // - // Create mutex. - // - pj_status_t create( Pj_Pool *pool, Type type, const char *name = NULL) - { - destroy(); - return pj_mutex_create( pool->pool_(), name, type, - &mutex_ ); - } - - // - // Create simple mutex. - // - pj_status_t create_simple( Pj_Pool *pool,const char *name = NULL) - { - return create(pool, SIMPLE, name); - } - - // - // Create recursive mutex. - // - pj_status_t create_recursive( Pj_Pool *pool, const char *name = NULL ) - { - return create(pool, RECURSE, name); - } - - // - // Get pjlib compatible mutex object. - // - pj_mutex_t *pj_mutex_t_() - { - return mutex_; - } - - // - // Destroy mutex. - // - void destroy() - { - if (mutex_) { - pj_mutex_destroy(mutex_); - mutex_ = NULL; - } - } - - // - // Lock mutex. - // - pj_status_t acquire() - { - return pj_mutex_lock(mutex_); - } - - // - // Unlock mutex. - // - pj_status_t release() - { - return pj_mutex_unlock(mutex_); - } - - // - // Try locking the mutex. - // - pj_status_t tryacquire() - { - return pj_mutex_trylock(mutex_); - } - -private: - pj_mutex_t *mutex_; -}; - - -// -// Semaphore -// -class Pj_Semaphore : public Pj_Object -{ -public: - // - // Construct semaphore - // - Pj_Semaphore(Pj_Pool *pool, unsigned max, - unsigned initial = 0, const char *name = NULL) - : sem_(NULL) - { - } - - // - // Destructor. - // - ~Pj_Semaphore() - { - destroy(); - } - - // - // Create semaphore - // - pj_status_t create( Pj_Pool *pool, unsigned max, - unsigned initial = 0, const char *name = NULL ) - { - destroy(); - return pj_sem_create( pool->pool_(), name, initial, max, &sem_); - } - - // - // Destroy semaphore. - // - void destroy() - { - if (sem_) { - pj_sem_destroy(sem_); - sem_ = NULL; - } - } - - // - // Get pjlib compatible semaphore object. - // - pj_sem_t *pj_sem_t_() - { - return (pj_sem_t*)this; - } - - // - // Wait semaphore. - // - pj_status_t wait() - { - return pj_sem_wait(this->pj_sem_t_()); - } - - // - // Wait semaphore. - // - pj_status_t acquire() - { - return wait(); - } - - // - // Try wait semaphore. - // - pj_status_t trywait() - { - return pj_sem_trywait(this->pj_sem_t_()); - } - - // - // Try wait semaphore. - // - pj_status_t tryacquire() - { - return trywait(); - } - - // - // Post semaphore. - // - pj_status_t post() - { - return pj_sem_post(this->pj_sem_t_()); - } - - // - // Post semaphore. - // - pj_status_t release() - { - return post(); - } - -private: - pj_sem_t *sem_; -}; - - -// -// Event object. -// -class Pj_Event -{ -public: - // - // Construct event object. - // - Pj_Event( Pj_Pool *pool, bool manual_reset = false, - bool initial = false, const char *name = NULL ) - : event_(NULL) - { - create(pool, manual_reset, initial, name); - } - - // - // Destructor. - // - ~Pj_Event() - { - destroy(); - } - - // - // Create event object. - // - pj_status_t create( Pj_Pool *pool, bool manual_reset = false, - bool initial = false, const char *name = NULL) - { - destroy(); - return pj_event_create(pool->pool_(), name, manual_reset, initial, - &event_); - } - - // - // Get pjlib compatible event object. - // - pj_event_t *pj_event_t_() - { - return event_; - } - - // - // Destroy event object. - // - void destroy() - { - if (event_) { - pj_event_destroy(event_); - event_ = NULL; - } - } - - // - // Wait. - // - pj_status_t wait() - { - return pj_event_wait(event_); - } - - // - // Try wait. - // - pj_status_t trywait() - { - return pj_event_trywait(event_); - } - - // - // Set event state to signalled. - // - pj_status_t set() - { - return pj_event_set(this->pj_event_t_()); - } - - // - // Release one waiting thread. - // - pj_status_t pulse() - { - return pj_event_pulse(this->pj_event_t_()); - } - - // - // Set a non-signalled. - // - pj_status_t reset() - { - return pj_event_reset(this->pj_event_t_()); - } - -private: - pj_event_t *event_; -}; - -// -// OS abstraction. -// -class Pj_OS_API -{ -public: - // - // Get current time. - // - static pj_status_t gettimeofday( Pj_Time_Val *tv ) - { - return pj_gettimeofday(tv); - } - - // - // Parse to time of day. - // - static pj_status_t time_decode( const Pj_Time_Val *tv, - pj_parsed_time *pt ) - { - return pj_time_decode(tv, pt); - } - - // - // Parse from time of day. - // - static pj_status_t time_encode( const pj_parsed_time *pt, - Pj_Time_Val *tv) - { - return pj_time_encode(pt, tv); - } - - // - // Convert to GMT. - // - static pj_status_t time_local_to_gmt( Pj_Time_Val *tv ) - { - return pj_time_local_to_gmt( tv ); - } - - // - // Convert time to local. - // - static pj_status_t time_gmt_to_local( Pj_Time_Val *tv) - { - return pj_time_gmt_to_local( tv ); - } -}; - -// -// Timeval inlines. -// -inline pj_status_t Pj_Time_Val::gettimeofday() -{ - return Pj_OS_API::gettimeofday(this); -} - -inline pj_parsed_time Pj_Time_Val::decode() -{ - pj_parsed_time pt; - Pj_OS_API::time_decode(this, &pt); - return pt; -} - -inline pj_status_t Pj_Time_Val::encode(const pj_parsed_time *pt) -{ - return Pj_OS_API::time_encode(pt, this); -} - -inline pj_status_t Pj_Time_Val::to_gmt() -{ - return Pj_OS_API::time_local_to_gmt(this); -} - -inline pj_status_t Pj_Time_Val::to_local() -{ - return Pj_OS_API::time_gmt_to_local(this); -} - -#endif /* __PJPP_OS_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_OS_HPP__
+#define __PJPP_OS_HPP__
+
+#include <pj/os.h>
+#include <pj++/types.hpp>
+#include <pj++/pool.hpp>
+
+class Pj_Thread;
+
+//
+// Thread API.
+//
+class Pj_Thread_API
+{
+public:
+ //
+ // Create a thread.
+ //
+ static pj_status_t create( Pj_Pool *pool, pj_thread_t **thread,
+ pj_thread_proc *proc, void *arg,
+ unsigned flags = 0,
+ const char *name = NULL,
+ pj_size_t stack_size = 0 )
+ {
+ return pj_thread_create(pool->pool_(), name, proc, arg, stack_size,
+ flags, thread);
+ }
+
+ //
+ // Register a thread.
+ //
+ static pj_status_t register_this_thread( pj_thread_desc desc,
+ pj_thread_t **thread,
+ const char *name = NULL )
+ {
+ return pj_thread_register( name, desc, thread );
+ }
+
+ //
+ // Get current thread.
+ // Will return pj_thread_t (sorry folks, not Pj_Thread).
+ //
+ static pj_thread_t *this_thread()
+ {
+ return pj_thread_this();
+ }
+
+ //
+ // Get thread name.
+ //
+ static const char *get_name(pj_thread_t *thread)
+ {
+ return pj_thread_get_name(thread);
+ }
+
+ //
+ // Resume thread.
+ //
+ static pj_status_t resume(pj_thread_t *thread)
+ {
+ return pj_thread_resume(thread);
+ }
+
+ //
+ // Sleep.
+ //
+ static pj_status_t sleep(unsigned msec)
+ {
+ return pj_thread_sleep(msec);
+ }
+
+ //
+ // Join the specified thread.
+ //
+ static pj_status_t join(pj_thread_t *thread)
+ {
+ return pj_thread_join(thread);
+ }
+
+ //
+ // Destroy thread
+ //
+ static pj_status_t destroy(pj_thread_t *thread)
+ {
+ return pj_thread_destroy(thread);
+ }
+};
+
+
+
+//
+// Thread object.
+//
+// How to use:
+// Derive a class from this class, then override main().
+//
+class Pj_Thread : public Pj_Object
+{
+public:
+ enum Flags
+ {
+ FLAG_SUSPENDED = PJ_THREAD_SUSPENDED
+ };
+
+ //
+ // Default constructor.
+ //
+ Pj_Thread()
+ : thread_(NULL)
+ {
+ }
+
+ //
+ // Destroy thread.
+ //
+ ~Pj_Thread()
+ {
+ destroy();
+ }
+
+ //
+ // This is the main thread function.
+ //
+ virtual int main() = 0;
+
+ //
+ // Start a thread.
+ //
+ pj_status_t create( Pj_Pool *pool,
+ unsigned flags = 0,
+ const char *thread_name = NULL,
+ pj_size_t stack_size = PJ_THREAD_DEFAULT_STACK_SIZE)
+ {
+ destroy();
+ return Pj_Thread_API::create( pool, &thread_, &thread_proc, this,
+ flags, thread_name);
+ }
+
+ //
+ // Get pjlib compatible thread object.
+ //
+ pj_thread_t *pj_thread_t_()
+ {
+ return thread_;
+ }
+
+ //
+ // Get thread name.
+ //
+ const char *get_name()
+ {
+ return Pj_Thread_API::get_name(thread_);
+ }
+
+ //
+ // Resume a suspended thread.
+ //
+ pj_status_t resume()
+ {
+ return Pj_Thread_API::resume(thread_);
+ }
+
+ //
+ // Join this thread.
+ //
+ pj_status_t join()
+ {
+ return Pj_Thread_API::join(thread_);
+ }
+
+ //
+ // Destroy thread.
+ //
+ pj_status_t destroy()
+ {
+ if (thread_) {
+ Pj_Thread_API::destroy(thread_);
+ thread_ = NULL;
+ }
+ }
+
+protected:
+ pj_thread_t *thread_;
+
+ static int PJ_THREAD_FUNC thread_proc(void *obj)
+ {
+ Pj_Thread *thread_class = (Pj_Thread*)obj;
+ return thread_class->main();
+ }
+};
+
+
+//
+// External Thread
+// (threads that were started by external means, i.e. not
+// with Pj_Thread::create).
+//
+// This class will normally be defined as local variable in
+// external thread's stack, normally inside thread's main proc.
+// But be aware that the handle will be destroyed on destructor!
+//
+class Pj_External_Thread : public Pj_Thread
+{
+public:
+ Pj_External_Thread()
+ {
+ }
+
+ //
+ // Register external thread so that pjlib functions can work
+ // in that thread.
+ //
+ pj_status_t register_this_thread( const char *name=NULL )
+ {
+ return Pj_Thread_API::register_this_thread(desc_, &thread_,name);
+ }
+
+private:
+ pj_thread_desc desc_;
+};
+
+
+//
+// Thread specific data/thread local storage/TLS.
+//
+class Pj_Thread_Local_API
+{
+public:
+ //
+ // Allocate thread local storage (TLS) index.
+ //
+ static pj_status_t alloc(long *index)
+ {
+ return pj_thread_local_alloc(index);
+ }
+
+ //
+ // Free TLS index.
+ //
+ static void free(long index)
+ {
+ pj_thread_local_free(index);
+ }
+
+ //
+ // Set thread specific data.
+ //
+ static pj_status_t set(long index, void *value)
+ {
+ return pj_thread_local_set(index, value);
+ }
+
+ //
+ // Get thread specific data.
+ //
+ static void *get(long index)
+ {
+ return pj_thread_local_get(index);
+ }
+
+};
+
+//
+// Atomic variable
+//
+// How to use:
+// Pj_Atomic_Var var(pool, 0);
+// var.set(..);
+//
+class Pj_Atomic_Var : public Pj_Object
+{
+public:
+ //
+ // Default constructor, initialize variable with NULL.
+ //
+ Pj_Atomic_Var()
+ : var_(NULL)
+ {
+ }
+
+ //
+ // Construct atomic variable.
+ //
+ Pj_Atomic_Var(Pj_Pool *pool, pj_atomic_value_t value)
+ : var_(NULL)
+ {
+ create(pool, value);
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Atomic_Var()
+ {
+ destroy();
+ }
+
+ //
+ // Create atomic variable.
+ //
+ pj_status_t create( Pj_Pool *pool, pj_atomic_value_t value)
+ {
+ destroy();
+ return pj_atomic_create(pool->pool_(), value, &var_);
+ }
+
+ //
+ // Destroy.
+ //
+ void destroy()
+ {
+ if (var_) {
+ pj_atomic_destroy(var_);
+ var_ = NULL;
+ }
+ }
+
+ //
+ // Get pjlib compatible atomic variable.
+ //
+ pj_atomic_t *pj_atomic_t_()
+ {
+ return var_;
+ }
+
+ //
+ // Set the value.
+ //
+ void set(pj_atomic_value_t val)
+ {
+ pj_atomic_set(var_, val);
+ }
+
+ //
+ // Get the value.
+ //
+ pj_atomic_value_t get()
+ {
+ return pj_atomic_get(var_);
+ }
+
+ //
+ // Increment.
+ //
+ void inc()
+ {
+ pj_atomic_inc(var_);
+ }
+
+ //
+ // Increment and get the result.
+ //
+ pj_atomic_value_t inc_and_get()
+ {
+ return pj_atomic_inc_and_get(var_);
+ }
+
+ //
+ // Decrement.
+ //
+ void dec()
+ {
+ pj_atomic_dec(var_);
+ }
+
+ //
+ // Decrement and get the result.
+ //
+ pj_atomic_value_t dec_and_get()
+ {
+ return pj_atomic_dec_and_get(var_);
+ }
+
+ //
+ // Add the variable.
+ //
+ void add(pj_atomic_value_t value)
+ {
+ pj_atomic_add(var_, value);
+ }
+
+ //
+ // Add the variable and get the value.
+ //
+ pj_atomic_value_t add_and_get(pj_atomic_value_t value)
+ {
+ return pj_atomic_add_and_get(var_, value );
+ }
+
+private:
+ pj_atomic_t *var_;
+};
+
+
+//
+// Mutex
+//
+class Pj_Mutex : public Pj_Object
+{
+public:
+ //
+ // Mutex type.
+ //
+ enum Type
+ {
+ DEFAULT = PJ_MUTEX_DEFAULT,
+ SIMPLE = PJ_MUTEX_SIMPLE,
+ RECURSE = PJ_MUTEX_RECURSE,
+ };
+
+ //
+ // Default constructor will create default mutex.
+ //
+ explicit Pj_Mutex(Pj_Pool *pool, Type type = DEFAULT,
+ const char *name = NULL)
+ : mutex_(NULL)
+ {
+ create(pool, type, name);
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Mutex()
+ {
+ destroy();
+ }
+
+ //
+ // Create mutex.
+ //
+ pj_status_t create( Pj_Pool *pool, Type type, const char *name = NULL)
+ {
+ destroy();
+ return pj_mutex_create( pool->pool_(), name, type,
+ &mutex_ );
+ }
+
+ //
+ // Create simple mutex.
+ //
+ pj_status_t create_simple( Pj_Pool *pool,const char *name = NULL)
+ {
+ return create(pool, SIMPLE, name);
+ }
+
+ //
+ // Create recursive mutex.
+ //
+ pj_status_t create_recursive( Pj_Pool *pool, const char *name = NULL )
+ {
+ return create(pool, RECURSE, name);
+ }
+
+ //
+ // Get pjlib compatible mutex object.
+ //
+ pj_mutex_t *pj_mutex_t_()
+ {
+ return mutex_;
+ }
+
+ //
+ // Destroy mutex.
+ //
+ void destroy()
+ {
+ if (mutex_) {
+ pj_mutex_destroy(mutex_);
+ mutex_ = NULL;
+ }
+ }
+
+ //
+ // Lock mutex.
+ //
+ pj_status_t acquire()
+ {
+ return pj_mutex_lock(mutex_);
+ }
+
+ //
+ // Unlock mutex.
+ //
+ pj_status_t release()
+ {
+ return pj_mutex_unlock(mutex_);
+ }
+
+ //
+ // Try locking the mutex.
+ //
+ pj_status_t tryacquire()
+ {
+ return pj_mutex_trylock(mutex_);
+ }
+
+private:
+ pj_mutex_t *mutex_;
+};
+
+
+//
+// Semaphore
+//
+class Pj_Semaphore : public Pj_Object
+{
+public:
+ //
+ // Construct semaphore
+ //
+ Pj_Semaphore(Pj_Pool *pool, unsigned max,
+ unsigned initial = 0, const char *name = NULL)
+ : sem_(NULL)
+ {
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Semaphore()
+ {
+ destroy();
+ }
+
+ //
+ // Create semaphore
+ //
+ pj_status_t create( Pj_Pool *pool, unsigned max,
+ unsigned initial = 0, const char *name = NULL )
+ {
+ destroy();
+ return pj_sem_create( pool->pool_(), name, initial, max, &sem_);
+ }
+
+ //
+ // Destroy semaphore.
+ //
+ void destroy()
+ {
+ if (sem_) {
+ pj_sem_destroy(sem_);
+ sem_ = NULL;
+ }
+ }
+
+ //
+ // Get pjlib compatible semaphore object.
+ //
+ pj_sem_t *pj_sem_t_()
+ {
+ return (pj_sem_t*)this;
+ }
+
+ //
+ // Wait semaphore.
+ //
+ pj_status_t wait()
+ {
+ return pj_sem_wait(this->pj_sem_t_());
+ }
+
+ //
+ // Wait semaphore.
+ //
+ pj_status_t acquire()
+ {
+ return wait();
+ }
+
+ //
+ // Try wait semaphore.
+ //
+ pj_status_t trywait()
+ {
+ return pj_sem_trywait(this->pj_sem_t_());
+ }
+
+ //
+ // Try wait semaphore.
+ //
+ pj_status_t tryacquire()
+ {
+ return trywait();
+ }
+
+ //
+ // Post semaphore.
+ //
+ pj_status_t post()
+ {
+ return pj_sem_post(this->pj_sem_t_());
+ }
+
+ //
+ // Post semaphore.
+ //
+ pj_status_t release()
+ {
+ return post();
+ }
+
+private:
+ pj_sem_t *sem_;
+};
+
+
+//
+// Event object.
+//
+class Pj_Event
+{
+public:
+ //
+ // Construct event object.
+ //
+ Pj_Event( Pj_Pool *pool, bool manual_reset = false,
+ bool initial = false, const char *name = NULL )
+ : event_(NULL)
+ {
+ create(pool, manual_reset, initial, name);
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Event()
+ {
+ destroy();
+ }
+
+ //
+ // Create event object.
+ //
+ pj_status_t create( Pj_Pool *pool, bool manual_reset = false,
+ bool initial = false, const char *name = NULL)
+ {
+ destroy();
+ return pj_event_create(pool->pool_(), name, manual_reset, initial,
+ &event_);
+ }
+
+ //
+ // Get pjlib compatible event object.
+ //
+ pj_event_t *pj_event_t_()
+ {
+ return event_;
+ }
+
+ //
+ // Destroy event object.
+ //
+ void destroy()
+ {
+ if (event_) {
+ pj_event_destroy(event_);
+ event_ = NULL;
+ }
+ }
+
+ //
+ // Wait.
+ //
+ pj_status_t wait()
+ {
+ return pj_event_wait(event_);
+ }
+
+ //
+ // Try wait.
+ //
+ pj_status_t trywait()
+ {
+ return pj_event_trywait(event_);
+ }
+
+ //
+ // Set event state to signalled.
+ //
+ pj_status_t set()
+ {
+ return pj_event_set(this->pj_event_t_());
+ }
+
+ //
+ // Release one waiting thread.
+ //
+ pj_status_t pulse()
+ {
+ return pj_event_pulse(this->pj_event_t_());
+ }
+
+ //
+ // Set a non-signalled.
+ //
+ pj_status_t reset()
+ {
+ return pj_event_reset(this->pj_event_t_());
+ }
+
+private:
+ pj_event_t *event_;
+};
+
+//
+// OS abstraction.
+//
+class Pj_OS_API
+{
+public:
+ //
+ // Get current time.
+ //
+ static pj_status_t gettimeofday( Pj_Time_Val *tv )
+ {
+ return pj_gettimeofday(tv);
+ }
+
+ //
+ // Parse to time of day.
+ //
+ static pj_status_t time_decode( const Pj_Time_Val *tv,
+ pj_parsed_time *pt )
+ {
+ return pj_time_decode(tv, pt);
+ }
+
+ //
+ // Parse from time of day.
+ //
+ static pj_status_t time_encode( const pj_parsed_time *pt,
+ Pj_Time_Val *tv)
+ {
+ return pj_time_encode(pt, tv);
+ }
+
+ //
+ // Convert to GMT.
+ //
+ static pj_status_t time_local_to_gmt( Pj_Time_Val *tv )
+ {
+ return pj_time_local_to_gmt( tv );
+ }
+
+ //
+ // Convert time to local.
+ //
+ static pj_status_t time_gmt_to_local( Pj_Time_Val *tv)
+ {
+ return pj_time_gmt_to_local( tv );
+ }
+};
+
+//
+// Timeval inlines.
+//
+inline pj_status_t Pj_Time_Val::gettimeofday()
+{
+ return Pj_OS_API::gettimeofday(this);
+}
+
+inline pj_parsed_time Pj_Time_Val::decode()
+{
+ pj_parsed_time pt;
+ Pj_OS_API::time_decode(this, &pt);
+ return pt;
+}
+
+inline pj_status_t Pj_Time_Val::encode(const pj_parsed_time *pt)
+{
+ return Pj_OS_API::time_encode(pt, this);
+}
+
+inline pj_status_t Pj_Time_Val::to_gmt()
+{
+ return Pj_OS_API::time_local_to_gmt(this);
+}
+
+inline pj_status_t Pj_Time_Val::to_local()
+{
+ return Pj_OS_API::time_gmt_to_local(this);
+}
+
+#endif /* __PJPP_OS_HPP__ */
+
diff --git a/pjlib/include/pj++/pool.hpp b/pjlib/include/pj++/pool.hpp index 1fa75759..22365117 100644 --- a/pjlib/include/pj++/pool.hpp +++ b/pjlib/include/pj++/pool.hpp @@ -1,254 +1,275 @@ -/* $Id$ - */ -#ifndef __PJPP_POOL_HPP__ -#define __PJPP_POOL_HPP__ - -#include <pj/pool.h> - -class Pj_Pool; -class Pj_Caching_Pool; - -// -// Base class for all Pjlib objects -// -class Pj_Object -{ -public: - void *operator new(unsigned int class_size, Pj_Pool *pool); - void *operator new(unsigned int class_size, Pj_Pool &pool); - - void operator delete(void*) - { - } - - void operator delete(void*, Pj_Pool*) - { - } - - void operator delete(void*, Pj_Pool&) - { - } - - // - // Inline implementations at the end of this file. - // - -private: - // Can not use normal new operator; must use pool. - // e.g.: - // obj = new(pool) Pj_The_Object(pool, ...); - // - void *operator new(unsigned int) - {} -}; - - -// -// Pool. -// -class Pj_Pool : public Pj_Object -{ -public: - // - // Default constructor, initializes internal pool to NULL. - // Application must call attach() some time later. - // - Pj_Pool() - : p_(NULL) - { - } - - // - // Create pool. - // - Pj_Pool(Pj_Caching_Pool &caching_pool, - pj_size_t initial_size, - pj_size_t increment_size, - const char *name = NULL, - pj_pool_callback *callback = NULL); - - // - // Construct from existing pool. - // - explicit Pj_Pool(pj_pool_t *pool) - : p_(pool) - { - } - - // - // Attach existing pool. - // - void attach(pj_pool_t *pool) - { - p_ = pool; - } - - // - // Destructor. - // - // Release pool back to factory. Remember: if you delete pool, then - // make sure that all objects that have been allocated from this pool - // have been properly destroyed. - // - // This is where C++ is trickier than plain C!! - // - ~Pj_Pool() - { - if (p_) - pj_pool_release(p_); - } - - // - // Get name. - // - const char *getobjname() const - { - return pj_pool_getobjname(p_); - } - - // - // Get pjlib compatible pool object. - // - pj_pool_t *pool_() - { - return p_; - } - - // - // Get pjlib compatible pool object. - // - const pj_pool_t *pool_() const - { - return p_; - } - - // - // Get pjlib compatible pool object. - // - pj_pool_t *pj_pool_t_() - { - return p_; - } - - // - // Reset pool. - // - void reset() - { - pj_pool_reset(p_); - } - - // - // Get current capacity. - // - pj_size_t get_capacity() - { - pj_pool_get_capacity(p_); - } - - // - // Get current total bytes allocated from the pool. - // - pj_size_t get_used_size() - { - pj_pool_get_used_size(p_); - } - - // - // Allocate. - // - void *alloc(pj_size_t size) - { - return pj_pool_alloc(p_, size); - } - - // - // Allocate elements and zero fill the memory. - // - void *calloc(pj_size_t count, pj_size_t elem) - { - return pj_pool_calloc(p_, count, elem); - } - - // - // Allocate and zero fill memory. - // - void *zalloc(pj_size_t size) - { - return pj_pool_zalloc(p_, size); - } - -private: - pj_pool_t *p_; -}; - - -// -// Caching pool. -// -class Pj_Caching_Pool -{ -public: - // - // Construct caching pool. - // - Pj_Caching_Pool( pj_size_t cache_capacity = 0, - const pj_pool_factory_policy *pol=&pj_pool_factory_default_policy) - { - pj_caching_pool_init(&cp_, pol, cache_capacity); - } - - // - // Destroy caching pool. - // - ~Pj_Caching_Pool() - { - pj_caching_pool_destroy(&cp_); - } - - // - // Create pool. - // - pj_pool_t *create_pool( pj_size_t initial_size, - pj_size_t increment_size, - const char *name = NULL, - pj_pool_callback *callback = NULL) - { - return (pj_pool_t*)(*cp_.factory.create_pool)(&cp_.factory, name, - initial_size, - increment_size, - callback); - } - -private: - pj_caching_pool cp_; -}; - -// -// Inlines for Pj_Object -// -inline void *Pj_Object::operator new(unsigned int class_size, Pj_Pool *pool) -{ - return pool->alloc(class_size); -} -inline void *Pj_Object::operator new(unsigned int class_size, Pj_Pool &pool) -{ - return pool.alloc(class_size); -} - -// -// Inlines for Pj_Pool -// -inline Pj_Pool::Pj_Pool( Pj_Caching_Pool &caching_pool, - pj_size_t initial_size, - pj_size_t increment_size, - const char *name, - pj_pool_callback *callback) -{ - p_ = caching_pool.create_pool(initial_size, increment_size, name, - callback); -} - - -#endif /* __PJPP_POOL_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_POOL_HPP__
+#define __PJPP_POOL_HPP__
+
+#include <pj/pool.h>
+
+class Pj_Pool;
+class Pj_Caching_Pool;
+
+//
+// Base class for all Pjlib objects
+//
+class Pj_Object
+{
+public:
+ void *operator new(unsigned int class_size, Pj_Pool *pool);
+ void *operator new(unsigned int class_size, Pj_Pool &pool);
+
+ void operator delete(void*)
+ {
+ }
+
+ void operator delete(void*, Pj_Pool*)
+ {
+ }
+
+ void operator delete(void*, Pj_Pool&)
+ {
+ }
+
+ //
+ // Inline implementations at the end of this file.
+ //
+
+private:
+ // Can not use normal new operator; must use pool.
+ // e.g.:
+ // obj = new(pool) Pj_The_Object(pool, ...);
+ //
+ void *operator new(unsigned int)
+ {}
+};
+
+
+//
+// Pool.
+//
+class Pj_Pool : public Pj_Object
+{
+public:
+ //
+ // Default constructor, initializes internal pool to NULL.
+ // Application must call attach() some time later.
+ //
+ Pj_Pool()
+ : p_(NULL)
+ {
+ }
+
+ //
+ // Create pool.
+ //
+ Pj_Pool(Pj_Caching_Pool &caching_pool,
+ pj_size_t initial_size,
+ pj_size_t increment_size,
+ const char *name = NULL,
+ pj_pool_callback *callback = NULL);
+
+ //
+ // Construct from existing pool.
+ //
+ explicit Pj_Pool(pj_pool_t *pool)
+ : p_(pool)
+ {
+ }
+
+ //
+ // Attach existing pool.
+ //
+ void attach(pj_pool_t *pool)
+ {
+ p_ = pool;
+ }
+
+ //
+ // Destructor.
+ //
+ // Release pool back to factory. Remember: if you delete pool, then
+ // make sure that all objects that have been allocated from this pool
+ // have been properly destroyed.
+ //
+ // This is where C++ is trickier than plain C!!
+ //
+ ~Pj_Pool()
+ {
+ if (p_)
+ pj_pool_release(p_);
+ }
+
+ //
+ // Get name.
+ //
+ const char *getobjname() const
+ {
+ return pj_pool_getobjname(p_);
+ }
+
+ //
+ // Get pjlib compatible pool object.
+ //
+ pj_pool_t *pool_()
+ {
+ return p_;
+ }
+
+ //
+ // Get pjlib compatible pool object.
+ //
+ const pj_pool_t *pool_() const
+ {
+ return p_;
+ }
+
+ //
+ // Get pjlib compatible pool object.
+ //
+ pj_pool_t *pj_pool_t_()
+ {
+ return p_;
+ }
+
+ //
+ // Reset pool.
+ //
+ void reset()
+ {
+ pj_pool_reset(p_);
+ }
+
+ //
+ // Get current capacity.
+ //
+ pj_size_t get_capacity()
+ {
+ pj_pool_get_capacity(p_);
+ }
+
+ //
+ // Get current total bytes allocated from the pool.
+ //
+ pj_size_t get_used_size()
+ {
+ pj_pool_get_used_size(p_);
+ }
+
+ //
+ // Allocate.
+ //
+ void *alloc(pj_size_t size)
+ {
+ return pj_pool_alloc(p_, size);
+ }
+
+ //
+ // Allocate elements and zero fill the memory.
+ //
+ void *calloc(pj_size_t count, pj_size_t elem)
+ {
+ return pj_pool_calloc(p_, count, elem);
+ }
+
+ //
+ // Allocate and zero fill memory.
+ //
+ void *zalloc(pj_size_t size)
+ {
+ return pj_pool_zalloc(p_, size);
+ }
+
+private:
+ pj_pool_t *p_;
+};
+
+
+//
+// Caching pool.
+//
+class Pj_Caching_Pool
+{
+public:
+ //
+ // Construct caching pool.
+ //
+ Pj_Caching_Pool( pj_size_t cache_capacity = 0,
+ const pj_pool_factory_policy *pol=&pj_pool_factory_default_policy)
+ {
+ pj_caching_pool_init(&cp_, pol, cache_capacity);
+ }
+
+ //
+ // Destroy caching pool.
+ //
+ ~Pj_Caching_Pool()
+ {
+ pj_caching_pool_destroy(&cp_);
+ }
+
+ //
+ // Create pool.
+ //
+ pj_pool_t *create_pool( pj_size_t initial_size,
+ pj_size_t increment_size,
+ const char *name = NULL,
+ pj_pool_callback *callback = NULL)
+ {
+ return (pj_pool_t*)(*cp_.factory.create_pool)(&cp_.factory, name,
+ initial_size,
+ increment_size,
+ callback);
+ }
+
+private:
+ pj_caching_pool cp_;
+};
+
+//
+// Inlines for Pj_Object
+//
+inline void *Pj_Object::operator new(unsigned int class_size, Pj_Pool *pool)
+{
+ return pool->alloc(class_size);
+}
+inline void *Pj_Object::operator new(unsigned int class_size, Pj_Pool &pool)
+{
+ return pool.alloc(class_size);
+}
+
+//
+// Inlines for Pj_Pool
+//
+inline Pj_Pool::Pj_Pool( Pj_Caching_Pool &caching_pool,
+ pj_size_t initial_size,
+ pj_size_t increment_size,
+ const char *name,
+ pj_pool_callback *callback)
+{
+ p_ = caching_pool.create_pool(initial_size, increment_size, name,
+ callback);
+}
+
+
+#endif /* __PJPP_POOL_HPP__ */
+
diff --git a/pjlib/include/pj++/proactor.hpp b/pjlib/include/pj++/proactor.hpp index 73be85f4..7c4f9928 100644 --- a/pjlib/include/pj++/proactor.hpp +++ b/pjlib/include/pj++/proactor.hpp @@ -1,502 +1,523 @@ -/* $Id$ - */ -#ifndef __PJPP_PROACTOR_HPP__ -#define __PJPP_PROACTOR_HPP__ - -#include <pj/ioqueue.h> -#include <pj++/pool.hpp> -#include <pj++/sock.hpp> -#include <pj++/timer.hpp> -#include <pj/errno.h> - -class Pj_Proactor; -class Pj_Event_Handler; - - -////////////////////////////////////////////////////////////////////////////// -// Asynchronous operation key. -// -// Applications may inheric this class to put their application -// specific data. -// -class Pj_Async_Op : public pj_ioqueue_op_key_t -{ -public: - // - // Construct with null handler. - // App must call set_handler() before use. - // - Pj_Async_Op() - : handler_(NULL) - { - pj_ioqueue_op_key_init(this, sizeof(*this)); - } - - // - // Constructor. - // - explicit Pj_Async_Op(Pj_Event_Handler *handler) - : handler_(handler) - { - pj_ioqueue_op_key_init(this, sizeof(*this)); - } - - // - // Set handler. - // - void set_handler(Pj_Event_Handler *handler) - { - handler_ = handler; - } - - // - // Check whether operation is still pending for this key. - // - bool is_pending(); - - // - // Cancel the operation. - // - bool cancel(pj_ssize_t bytes_status=-PJ_ECANCELLED); - -protected: - Pj_Event_Handler *handler_; -}; - - -////////////////////////////////////////////////////////////////////////////// -// Event handler. -// -// Applications should inherit this class to receive various event -// notifications. -// -// Applications should implement get_socket_handle(). -// -class Pj_Event_Handler : public Pj_Object -{ - friend class Pj_Proactor; -public: - // - // Default constructor. - // - Pj_Event_Handler() - : key_(NULL) - { - pj_memset(&timer_, 0, sizeof(timer_)); - timer_.user_data = this; - timer_.cb = &timer_callback; - } - - // - // Destroy. - // - virtual ~Pj_Event_Handler() - { - unregister(); - } - - // - // Unregister this handler from the ioqueue. - // - void unregister() - { - if (key_) { - pj_ioqueue_unregister(key_); - key_ = NULL; - } - } - - // - // Get socket handle associated with this. - // - virtual pj_sock_t get_socket_handle() - { - return PJ_INVALID_SOCKET; - } - - // - // Start async receive. - // - pj_status_t recv( Pj_Async_Op *op_key, - void *buf, pj_ssize_t *len, - unsigned flags) - { - return pj_ioqueue_recv( key_, op_key, - buf, len, flags); - } - - // - // Start async recvfrom() - // - pj_status_t recvfrom( Pj_Async_Op *op_key, - void *buf, pj_ssize_t *len, unsigned flags, - Pj_Inet_Addr *addr) - { - addr->addrlen_ = sizeof(Pj_Inet_Addr); - return pj_ioqueue_recvfrom( key_, op_key, buf, len, flags, - addr, &addr->addrlen_ ); - } - - // - // Start async send() - // - pj_status_t send( Pj_Async_Op *op_key, - const void *data, pj_ssize_t *len, - unsigned flags) - { - return pj_ioqueue_send( key_, op_key, data, len, flags); - } - - // - // Start async sendto() - // - pj_status_t sendto( Pj_Async_Op *op_key, - const void *data, pj_ssize_t *len, unsigned flags, - const Pj_Inet_Addr &addr) - { - return pj_ioqueue_sendto(key_, op_key, data, len, flags, - &addr, sizeof(addr)); - } - -#if PJ_HAS_TCP - // - // Start async connect() - // - pj_status_t connect(const Pj_Inet_Addr &addr) - { - return pj_ioqueue_connect(key_, &addr, sizeof(addr)); - } - - // - // Start async accept(). - // - pj_status_t accept( Pj_Async_Op *op_key, - Pj_Socket *sock, - Pj_Inet_Addr *local = NULL, - Pj_Inet_Addr *remote = NULL) - { - int *addrlen = local ? &local->addrlen_ : NULL; - return pj_ioqueue_accept( key_, op_key, &sock->sock_, - local, remote, addrlen ); - } - -#endif - -protected: - ////////////////// - // Overridables - ////////////////// - - // - // Timeout callback. - // - virtual void on_timeout(int data) - { - } - - // - // On read complete callback. - // - virtual void on_read_complete( Pj_Async_Op *op_key, - pj_ssize_t bytes_read) - { - } - - // - // On write complete callback. - // - virtual void on_write_complete( Pj_Async_Op *op_key, - pj_ssize_t bytes_sent) - { - } - -#if PJ_HAS_TCP - // - // On connect complete callback. - // - virtual void on_connect_complete(pj_status_t status) - { - } - - // - // On new connection callback. - // - virtual void on_accept_complete( Pj_Async_Op *op_key, - pj_sock_t new_sock, - pj_status_t status) - { - } - -#endif - - -private: - pj_ioqueue_key_t *key_; - pj_timer_entry timer_; - - friend class Pj_Proactor; - friend class Pj_Async_Op; - - // - // Static timer callback. - // - static void timer_callback( pj_timer_heap_t *timer_heap, - struct pj_timer_entry *entry) - { - Pj_Event_Handler *handler = - (Pj_Event_Handler*) entry->user_data; - - handler->on_timeout(entry->id); - } -}; - -inline bool Pj_Async_Op::is_pending() -{ - return pj_ioqueue_is_pending(handler_->key_, this) != 0; -} - -inline bool Pj_Async_Op::cancel(pj_ssize_t bytes_status) -{ - return pj_ioqueue_post_completion(handler_->key_, this, - bytes_status) == PJ_SUCCESS; -} - -////////////////////////////////////////////////////////////////////////////// -// Proactor -// -class Pj_Proactor : public Pj_Object -{ -public: - // - // Default constructor, initializes to NULL. - // - Pj_Proactor() - : ioq_(NULL), th_(NULL) - { - cb_.on_read_complete = &read_complete_cb; - cb_.on_write_complete = &write_complete_cb; - cb_.on_accept_complete = &accept_complete_cb; - cb_.on_connect_complete = &connect_complete_cb; - } - - // - // Construct proactor. - // - Pj_Proactor( Pj_Pool *pool, pj_size_t max_fd, - pj_size_t max_timer_entries ) - : ioq_(NULL), th_(NULL) - { - cb_.on_read_complete = &read_complete_cb; - cb_.on_write_complete = &write_complete_cb; - cb_.on_accept_complete = &accept_complete_cb; - cb_.on_connect_complete = &connect_complete_cb; - - create(pool, max_fd, max_timer_entries); - } - - // - // Destructor. - // - ~Pj_Proactor() - { - destroy(); - } - - // - // Create proactor. - // - pj_status_t create( Pj_Pool *pool, pj_size_t max_fd, - pj_size_t timer_entry_count) - { - pj_status_t status; - - destroy(); - - status = pj_ioqueue_create(pool->pool_(), max_fd, &ioq_); - if (status != PJ_SUCCESS) - return status; - - status = pj_timer_heap_create(pool->pool_(), - timer_entry_count, &th_); - if (status != PJ_SUCCESS) { - pj_ioqueue_destroy(ioq_); - ioq_ = NULL; - return NULL; - } - - return status; - } - - // - // Destroy proactor. - // - void destroy() - { - if (ioq_) { - pj_ioqueue_destroy(ioq_); - ioq_ = NULL; - } - if (th_) { - pj_timer_heap_destroy(th_); - th_ = NULL; - } - } - - // - // Register handler. - // This will call handler->get_socket_handle() - // - pj_status_t register_socket_handler(Pj_Pool *pool, - Pj_Event_Handler *handler) - { - return pj_ioqueue_register_sock( pool->pool_(), ioq_, - handler->get_socket_handle(), - handler, &cb_, &handler->key_ ); - } - - // - // Unregister handler. - // - static void unregister_handler(Pj_Event_Handler *handler) - { - if (handler->key_) { - pj_ioqueue_unregister( handler->key_ ); - handler->key_ = NULL; - } - } - - // - // Scheduler timer. - // - bool schedule_timer( Pj_Event_Handler *handler, - const Pj_Time_Val &delay, - int id=-1) - { - return schedule_timer(th_, handler, delay, id); - } - - // - // Cancel timer. - // - bool cancel_timer(Pj_Event_Handler *handler) - { - return pj_timer_heap_cancel(th_, &handler->timer_) == 1; - } - - // - // Handle events. - // - int handle_events(Pj_Time_Val *max_timeout) - { - Pj_Time_Val timeout(0, 0); - int timer_count; - - timer_count = pj_timer_heap_poll( th_, &timeout ); - - if (timeout.get_sec() < 0) - timeout.sec = PJ_MAXINT32; - - /* If caller specifies maximum time to wait, then compare the value - * with the timeout to wait from timer, and use the minimum value. - */ - if (max_timeout && timeout >= *max_timeout) { - timeout = *max_timeout; - } - - /* Poll events in ioqueue. */ - int ioqueue_count; - - ioqueue_count = pj_ioqueue_poll(ioq_, &timeout); - if (ioqueue_count < 0) - return ioqueue_count; - - return ioqueue_count + timer_count; - } - - // - // Get the internal ioqueue object. - // - pj_ioqueue_t *get_io_queue() - { - return ioq_; - } - - // - // Get the internal timer heap object. - // - pj_timer_heap_t *get_timer_heap() - { - return th_; - } - -private: - pj_ioqueue_t *ioq_; - pj_timer_heap_t *th_; - pj_ioqueue_callback cb_; - - static bool schedule_timer( pj_timer_heap_t *timer, - Pj_Event_Handler *handler, - const Pj_Time_Val &delay, - int id=-1) - { - handler->timer_.id = id; - return pj_timer_heap_schedule(timer, &handler->timer_, &delay) == 0; - } - - - // - // Static read completion callback. - // - static void read_complete_cb( pj_ioqueue_key_t *key, - pj_ioqueue_op_key_t *op_key, - pj_ssize_t bytes_read) - { - Pj_Event_Handler *handler = - (Pj_Event_Handler*) pj_ioqueue_get_user_data(key); - - handler->on_read_complete((Pj_Async_Op*)op_key, bytes_read); - } - - // - // Static write completion callback. - // - static void write_complete_cb(pj_ioqueue_key_t *key, - pj_ioqueue_op_key_t *op_key, - pj_ssize_t bytes_sent) - { - Pj_Event_Handler *handler = - (Pj_Event_Handler*) pj_ioqueue_get_user_data(key); - - handler->on_write_complete((Pj_Async_Op*)op_key, bytes_sent); - } - - // - // Static accept completion callback. - // - static void accept_complete_cb(pj_ioqueue_key_t *key, - pj_ioqueue_op_key_t *op_key, - pj_sock_t new_sock, - pj_status_t status) - { - Pj_Event_Handler *handler = - (Pj_Event_Handler*) pj_ioqueue_get_user_data(key); - - handler->on_accept_complete((Pj_Async_Op*)op_key, new_sock, status); - } - - // - // Static connect completion callback. - // - static void connect_complete_cb(pj_ioqueue_key_t *key, - pj_status_t status) - { - Pj_Event_Handler *handler = - (Pj_Event_Handler*) pj_ioqueue_get_user_data(key); - - handler->on_connect_complete(status); - } - -}; - -#endif /* __PJPP_PROACTOR_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_PROACTOR_HPP__
+#define __PJPP_PROACTOR_HPP__
+
+#include <pj/ioqueue.h>
+#include <pj++/pool.hpp>
+#include <pj++/sock.hpp>
+#include <pj++/timer.hpp>
+#include <pj/errno.h>
+
+class Pj_Proactor;
+class Pj_Event_Handler;
+
+
+//////////////////////////////////////////////////////////////////////////////
+// Asynchronous operation key.
+//
+// Applications may inheric this class to put their application
+// specific data.
+//
+class Pj_Async_Op : public pj_ioqueue_op_key_t
+{
+public:
+ //
+ // Construct with null handler.
+ // App must call set_handler() before use.
+ //
+ Pj_Async_Op()
+ : handler_(NULL)
+ {
+ pj_ioqueue_op_key_init(this, sizeof(*this));
+ }
+
+ //
+ // Constructor.
+ //
+ explicit Pj_Async_Op(Pj_Event_Handler *handler)
+ : handler_(handler)
+ {
+ pj_ioqueue_op_key_init(this, sizeof(*this));
+ }
+
+ //
+ // Set handler.
+ //
+ void set_handler(Pj_Event_Handler *handler)
+ {
+ handler_ = handler;
+ }
+
+ //
+ // Check whether operation is still pending for this key.
+ //
+ bool is_pending();
+
+ //
+ // Cancel the operation.
+ //
+ bool cancel(pj_ssize_t bytes_status=-PJ_ECANCELLED);
+
+protected:
+ Pj_Event_Handler *handler_;
+};
+
+
+//////////////////////////////////////////////////////////////////////////////
+// Event handler.
+//
+// Applications should inherit this class to receive various event
+// notifications.
+//
+// Applications should implement get_socket_handle().
+//
+class Pj_Event_Handler : public Pj_Object
+{
+ friend class Pj_Proactor;
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Event_Handler()
+ : key_(NULL)
+ {
+ pj_memset(&timer_, 0, sizeof(timer_));
+ timer_.user_data = this;
+ timer_.cb = &timer_callback;
+ }
+
+ //
+ // Destroy.
+ //
+ virtual ~Pj_Event_Handler()
+ {
+ unregister();
+ }
+
+ //
+ // Unregister this handler from the ioqueue.
+ //
+ void unregister()
+ {
+ if (key_) {
+ pj_ioqueue_unregister(key_);
+ key_ = NULL;
+ }
+ }
+
+ //
+ // Get socket handle associated with this.
+ //
+ virtual pj_sock_t get_socket_handle()
+ {
+ return PJ_INVALID_SOCKET;
+ }
+
+ //
+ // Start async receive.
+ //
+ pj_status_t recv( Pj_Async_Op *op_key,
+ void *buf, pj_ssize_t *len,
+ unsigned flags)
+ {
+ return pj_ioqueue_recv( key_, op_key,
+ buf, len, flags);
+ }
+
+ //
+ // Start async recvfrom()
+ //
+ pj_status_t recvfrom( Pj_Async_Op *op_key,
+ void *buf, pj_ssize_t *len, unsigned flags,
+ Pj_Inet_Addr *addr)
+ {
+ addr->addrlen_ = sizeof(Pj_Inet_Addr);
+ return pj_ioqueue_recvfrom( key_, op_key, buf, len, flags,
+ addr, &addr->addrlen_ );
+ }
+
+ //
+ // Start async send()
+ //
+ pj_status_t send( Pj_Async_Op *op_key,
+ const void *data, pj_ssize_t *len,
+ unsigned flags)
+ {
+ return pj_ioqueue_send( key_, op_key, data, len, flags);
+ }
+
+ //
+ // Start async sendto()
+ //
+ pj_status_t sendto( Pj_Async_Op *op_key,
+ const void *data, pj_ssize_t *len, unsigned flags,
+ const Pj_Inet_Addr &addr)
+ {
+ return pj_ioqueue_sendto(key_, op_key, data, len, flags,
+ &addr, sizeof(addr));
+ }
+
+#if PJ_HAS_TCP
+ //
+ // Start async connect()
+ //
+ pj_status_t connect(const Pj_Inet_Addr &addr)
+ {
+ return pj_ioqueue_connect(key_, &addr, sizeof(addr));
+ }
+
+ //
+ // Start async accept().
+ //
+ pj_status_t accept( Pj_Async_Op *op_key,
+ Pj_Socket *sock,
+ Pj_Inet_Addr *local = NULL,
+ Pj_Inet_Addr *remote = NULL)
+ {
+ int *addrlen = local ? &local->addrlen_ : NULL;
+ return pj_ioqueue_accept( key_, op_key, &sock->sock_,
+ local, remote, addrlen );
+ }
+
+#endif
+
+protected:
+ //////////////////
+ // Overridables
+ //////////////////
+
+ //
+ // Timeout callback.
+ //
+ virtual void on_timeout(int data)
+ {
+ }
+
+ //
+ // On read complete callback.
+ //
+ virtual void on_read_complete( Pj_Async_Op *op_key,
+ pj_ssize_t bytes_read)
+ {
+ }
+
+ //
+ // On write complete callback.
+ //
+ virtual void on_write_complete( Pj_Async_Op *op_key,
+ pj_ssize_t bytes_sent)
+ {
+ }
+
+#if PJ_HAS_TCP
+ //
+ // On connect complete callback.
+ //
+ virtual void on_connect_complete(pj_status_t status)
+ {
+ }
+
+ //
+ // On new connection callback.
+ //
+ virtual void on_accept_complete( Pj_Async_Op *op_key,
+ pj_sock_t new_sock,
+ pj_status_t status)
+ {
+ }
+
+#endif
+
+
+private:
+ pj_ioqueue_key_t *key_;
+ pj_timer_entry timer_;
+
+ friend class Pj_Proactor;
+ friend class Pj_Async_Op;
+
+ //
+ // Static timer callback.
+ //
+ static void timer_callback( pj_timer_heap_t *timer_heap,
+ struct pj_timer_entry *entry)
+ {
+ Pj_Event_Handler *handler =
+ (Pj_Event_Handler*) entry->user_data;
+
+ handler->on_timeout(entry->id);
+ }
+};
+
+inline bool Pj_Async_Op::is_pending()
+{
+ return pj_ioqueue_is_pending(handler_->key_, this) != 0;
+}
+
+inline bool Pj_Async_Op::cancel(pj_ssize_t bytes_status)
+{
+ return pj_ioqueue_post_completion(handler_->key_, this,
+ bytes_status) == PJ_SUCCESS;
+}
+
+//////////////////////////////////////////////////////////////////////////////
+// Proactor
+//
+class Pj_Proactor : public Pj_Object
+{
+public:
+ //
+ // Default constructor, initializes to NULL.
+ //
+ Pj_Proactor()
+ : ioq_(NULL), th_(NULL)
+ {
+ cb_.on_read_complete = &read_complete_cb;
+ cb_.on_write_complete = &write_complete_cb;
+ cb_.on_accept_complete = &accept_complete_cb;
+ cb_.on_connect_complete = &connect_complete_cb;
+ }
+
+ //
+ // Construct proactor.
+ //
+ Pj_Proactor( Pj_Pool *pool, pj_size_t max_fd,
+ pj_size_t max_timer_entries )
+ : ioq_(NULL), th_(NULL)
+ {
+ cb_.on_read_complete = &read_complete_cb;
+ cb_.on_write_complete = &write_complete_cb;
+ cb_.on_accept_complete = &accept_complete_cb;
+ cb_.on_connect_complete = &connect_complete_cb;
+
+ create(pool, max_fd, max_timer_entries);
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Proactor()
+ {
+ destroy();
+ }
+
+ //
+ // Create proactor.
+ //
+ pj_status_t create( Pj_Pool *pool, pj_size_t max_fd,
+ pj_size_t timer_entry_count)
+ {
+ pj_status_t status;
+
+ destroy();
+
+ status = pj_ioqueue_create(pool->pool_(), max_fd, &ioq_);
+ if (status != PJ_SUCCESS)
+ return status;
+
+ status = pj_timer_heap_create(pool->pool_(),
+ timer_entry_count, &th_);
+ if (status != PJ_SUCCESS) {
+ pj_ioqueue_destroy(ioq_);
+ ioq_ = NULL;
+ return NULL;
+ }
+
+ return status;
+ }
+
+ //
+ // Destroy proactor.
+ //
+ void destroy()
+ {
+ if (ioq_) {
+ pj_ioqueue_destroy(ioq_);
+ ioq_ = NULL;
+ }
+ if (th_) {
+ pj_timer_heap_destroy(th_);
+ th_ = NULL;
+ }
+ }
+
+ //
+ // Register handler.
+ // This will call handler->get_socket_handle()
+ //
+ pj_status_t register_socket_handler(Pj_Pool *pool,
+ Pj_Event_Handler *handler)
+ {
+ return pj_ioqueue_register_sock( pool->pool_(), ioq_,
+ handler->get_socket_handle(),
+ handler, &cb_, &handler->key_ );
+ }
+
+ //
+ // Unregister handler.
+ //
+ static void unregister_handler(Pj_Event_Handler *handler)
+ {
+ if (handler->key_) {
+ pj_ioqueue_unregister( handler->key_ );
+ handler->key_ = NULL;
+ }
+ }
+
+ //
+ // Scheduler timer.
+ //
+ bool schedule_timer( Pj_Event_Handler *handler,
+ const Pj_Time_Val &delay,
+ int id=-1)
+ {
+ return schedule_timer(th_, handler, delay, id);
+ }
+
+ //
+ // Cancel timer.
+ //
+ bool cancel_timer(Pj_Event_Handler *handler)
+ {
+ return pj_timer_heap_cancel(th_, &handler->timer_) == 1;
+ }
+
+ //
+ // Handle events.
+ //
+ int handle_events(Pj_Time_Val *max_timeout)
+ {
+ Pj_Time_Val timeout(0, 0);
+ int timer_count;
+
+ timer_count = pj_timer_heap_poll( th_, &timeout );
+
+ if (timeout.get_sec() < 0)
+ timeout.sec = PJ_MAXINT32;
+
+ /* If caller specifies maximum time to wait, then compare the value
+ * with the timeout to wait from timer, and use the minimum value.
+ */
+ if (max_timeout && timeout >= *max_timeout) {
+ timeout = *max_timeout;
+ }
+
+ /* Poll events in ioqueue. */
+ int ioqueue_count;
+
+ ioqueue_count = pj_ioqueue_poll(ioq_, &timeout);
+ if (ioqueue_count < 0)
+ return ioqueue_count;
+
+ return ioqueue_count + timer_count;
+ }
+
+ //
+ // Get the internal ioqueue object.
+ //
+ pj_ioqueue_t *get_io_queue()
+ {
+ return ioq_;
+ }
+
+ //
+ // Get the internal timer heap object.
+ //
+ pj_timer_heap_t *get_timer_heap()
+ {
+ return th_;
+ }
+
+private:
+ pj_ioqueue_t *ioq_;
+ pj_timer_heap_t *th_;
+ pj_ioqueue_callback cb_;
+
+ static bool schedule_timer( pj_timer_heap_t *timer,
+ Pj_Event_Handler *handler,
+ const Pj_Time_Val &delay,
+ int id=-1)
+ {
+ handler->timer_.id = id;
+ return pj_timer_heap_schedule(timer, &handler->timer_, &delay) == 0;
+ }
+
+
+ //
+ // Static read completion callback.
+ //
+ static void read_complete_cb( pj_ioqueue_key_t *key,
+ pj_ioqueue_op_key_t *op_key,
+ pj_ssize_t bytes_read)
+ {
+ Pj_Event_Handler *handler =
+ (Pj_Event_Handler*) pj_ioqueue_get_user_data(key);
+
+ handler->on_read_complete((Pj_Async_Op*)op_key, bytes_read);
+ }
+
+ //
+ // Static write completion callback.
+ //
+ static void write_complete_cb(pj_ioqueue_key_t *key,
+ pj_ioqueue_op_key_t *op_key,
+ pj_ssize_t bytes_sent)
+ {
+ Pj_Event_Handler *handler =
+ (Pj_Event_Handler*) pj_ioqueue_get_user_data(key);
+
+ handler->on_write_complete((Pj_Async_Op*)op_key, bytes_sent);
+ }
+
+ //
+ // Static accept completion callback.
+ //
+ static void accept_complete_cb(pj_ioqueue_key_t *key,
+ pj_ioqueue_op_key_t *op_key,
+ pj_sock_t new_sock,
+ pj_status_t status)
+ {
+ Pj_Event_Handler *handler =
+ (Pj_Event_Handler*) pj_ioqueue_get_user_data(key);
+
+ handler->on_accept_complete((Pj_Async_Op*)op_key, new_sock, status);
+ }
+
+ //
+ // Static connect completion callback.
+ //
+ static void connect_complete_cb(pj_ioqueue_key_t *key,
+ pj_status_t status)
+ {
+ Pj_Event_Handler *handler =
+ (Pj_Event_Handler*) pj_ioqueue_get_user_data(key);
+
+ handler->on_connect_complete(status);
+ }
+
+};
+
+#endif /* __PJPP_PROACTOR_HPP__ */
+
diff --git a/pjlib/include/pj++/scanner.hpp b/pjlib/include/pj++/scanner.hpp index 8a3d9897..2131d4df 100644 --- a/pjlib/include/pj++/scanner.hpp +++ b/pjlib/include/pj++/scanner.hpp @@ -1,173 +1,194 @@ -/* $Id$ - */ -#ifndef __PJPP_SCANNER_HPP__ -#define __PJPP_SCANNER_HPP__ - -#include <pjlib-util/scanner.h> -#include <pj++/string.hpp> - -class Pj_Char_Spec -{ -public: - Pj_Char_Spec() { pj_cs_init(cs__); } - - void set(int c) { pj_cs_set(cs__, c); } - void add_range(int begin, int end) { pj_cs_add_range(cs__, begin, end); } - void add_alpha() { pj_cs_add_alpha(cs__); } - void add_num() { pj_cs_add_num(cs__); } - void add_str(const char *str) { pj_cs_add_str(cs__, str); } - void del_range(int begin, int end) { pj_cs_del_range(cs__, begin, end); } - void del_str(const char *str) { pj_cs_del_str(cs__, str); } - void invert() { pj_cs_invert(cs__); } - int match(int c) { return pj_cs_match(cs__, c); } - - pj_char_spec_element_t *cs_() - { - return cs__; - } - - const pj_char_spec_element_t *cs_() const - { - return cs__; - } - -private: - pj_char_spec cs__; -}; - -class Pj_Scanner -{ -public: - Pj_Scanner() {} - - enum - { - SYNTAX_ERROR = 101 - }; - static void syntax_error_handler_throw_pj(pj_scanner *); - - typedef pj_scan_state State; - - void init(char *buf, int len, unsigned options=PJ_SCAN_AUTOSKIP_WS, - pj_syn_err_func_ptr callback = &syntax_error_handler_throw_pj) - { - pj_scan_init(&scanner_, buf, len, options, callback); - } - - void fini() - { - pj_scan_fini(&scanner_); - } - - int eof() const - { - return pj_scan_is_eof(&scanner_); - } - - int peek_char() const - { - return *scanner_.curptr; - } - - int peek(const Pj_Char_Spec *cs, Pj_String *out) - { - return pj_scan_peek(&scanner_, cs->cs_(), out); - } - - int peek_n(pj_size_t len, Pj_String *out) - { - return pj_scan_peek_n(&scanner_, len, out); - } - - int peek_until(const Pj_Char_Spec *cs, Pj_String *out) - { - return pj_scan_peek_until(&scanner_, cs->cs_(), out); - } - - void get(const Pj_Char_Spec *cs, Pj_String *out) - { - pj_scan_get(&scanner_, cs->cs_(), out); - } - - void get_n(unsigned N, Pj_String *out) - { - pj_scan_get_n(&scanner_, N, out); - } - - int get_char() - { - return pj_scan_get_char(&scanner_); - } - - void get_quote(int begin_quote, int end_quote, Pj_String *out) - { - pj_scan_get_quote(&scanner_, begin_quote, end_quote, out); - } - - void get_newline() - { - pj_scan_get_newline(&scanner_); - } - - void get_until(const Pj_Char_Spec *cs, Pj_String *out) - { - pj_scan_get_until(&scanner_, cs->cs_(), out); - } - - void get_until_ch(int until_ch, Pj_String *out) - { - pj_scan_get_until_ch(&scanner_, until_ch, out); - } - - void get_until_chr(const char *spec, Pj_String *out) - { - pj_scan_get_until_chr(&scanner_, spec, out); - } - - void advance_n(unsigned N, bool skip_ws=true) - { - pj_scan_advance_n(&scanner_, N, skip_ws); - } - - int strcmp(const char *s, int len) - { - return pj_scan_strcmp(&scanner_, s, len); - } - - int stricmp(const char *s, int len) - { - return pj_scan_stricmp(&scanner_, s, len); - } - - void skip_ws() - { - pj_scan_skip_whitespace(&scanner_); - } - - void save_state(State *state) - { - pj_scan_save_state(&scanner_, state); - } - - void restore_state(State *state) - { - pj_scan_restore_state(&scanner_, state); - } - - int get_pos_line() const - { - return scanner_.line; - } - - int get_pos_col() const - { - return scanner_.col; - } - - -private: - pj_scanner scanner_; -}; - -#endif /* __PJPP_SCANNER_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_SCANNER_HPP__
+#define __PJPP_SCANNER_HPP__
+
+#include <pjlib-util/scanner.h>
+#include <pj++/string.hpp>
+
+class Pj_Char_Spec
+{
+public:
+ Pj_Char_Spec() { pj_cs_init(cs__); }
+
+ void set(int c) { pj_cs_set(cs__, c); }
+ void add_range(int begin, int end) { pj_cs_add_range(cs__, begin, end); }
+ void add_alpha() { pj_cs_add_alpha(cs__); }
+ void add_num() { pj_cs_add_num(cs__); }
+ void add_str(const char *str) { pj_cs_add_str(cs__, str); }
+ void del_range(int begin, int end) { pj_cs_del_range(cs__, begin, end); }
+ void del_str(const char *str) { pj_cs_del_str(cs__, str); }
+ void invert() { pj_cs_invert(cs__); }
+ int match(int c) { return pj_cs_match(cs__, c); }
+
+ pj_char_spec_element_t *cs_()
+ {
+ return cs__;
+ }
+
+ const pj_char_spec_element_t *cs_() const
+ {
+ return cs__;
+ }
+
+private:
+ pj_char_spec cs__;
+};
+
+class Pj_Scanner
+{
+public:
+ Pj_Scanner() {}
+
+ enum
+ {
+ SYNTAX_ERROR = 101
+ };
+ static void syntax_error_handler_throw_pj(pj_scanner *);
+
+ typedef pj_scan_state State;
+
+ void init(char *buf, int len, unsigned options=PJ_SCAN_AUTOSKIP_WS,
+ pj_syn_err_func_ptr callback = &syntax_error_handler_throw_pj)
+ {
+ pj_scan_init(&scanner_, buf, len, options, callback);
+ }
+
+ void fini()
+ {
+ pj_scan_fini(&scanner_);
+ }
+
+ int eof() const
+ {
+ return pj_scan_is_eof(&scanner_);
+ }
+
+ int peek_char() const
+ {
+ return *scanner_.curptr;
+ }
+
+ int peek(const Pj_Char_Spec *cs, Pj_String *out)
+ {
+ return pj_scan_peek(&scanner_, cs->cs_(), out);
+ }
+
+ int peek_n(pj_size_t len, Pj_String *out)
+ {
+ return pj_scan_peek_n(&scanner_, len, out);
+ }
+
+ int peek_until(const Pj_Char_Spec *cs, Pj_String *out)
+ {
+ return pj_scan_peek_until(&scanner_, cs->cs_(), out);
+ }
+
+ void get(const Pj_Char_Spec *cs, Pj_String *out)
+ {
+ pj_scan_get(&scanner_, cs->cs_(), out);
+ }
+
+ void get_n(unsigned N, Pj_String *out)
+ {
+ pj_scan_get_n(&scanner_, N, out);
+ }
+
+ int get_char()
+ {
+ return pj_scan_get_char(&scanner_);
+ }
+
+ void get_quote(int begin_quote, int end_quote, Pj_String *out)
+ {
+ pj_scan_get_quote(&scanner_, begin_quote, end_quote, out);
+ }
+
+ void get_newline()
+ {
+ pj_scan_get_newline(&scanner_);
+ }
+
+ void get_until(const Pj_Char_Spec *cs, Pj_String *out)
+ {
+ pj_scan_get_until(&scanner_, cs->cs_(), out);
+ }
+
+ void get_until_ch(int until_ch, Pj_String *out)
+ {
+ pj_scan_get_until_ch(&scanner_, until_ch, out);
+ }
+
+ void get_until_chr(const char *spec, Pj_String *out)
+ {
+ pj_scan_get_until_chr(&scanner_, spec, out);
+ }
+
+ void advance_n(unsigned N, bool skip_ws=true)
+ {
+ pj_scan_advance_n(&scanner_, N, skip_ws);
+ }
+
+ int strcmp(const char *s, int len)
+ {
+ return pj_scan_strcmp(&scanner_, s, len);
+ }
+
+ int stricmp(const char *s, int len)
+ {
+ return pj_scan_stricmp(&scanner_, s, len);
+ }
+
+ void skip_ws()
+ {
+ pj_scan_skip_whitespace(&scanner_);
+ }
+
+ void save_state(State *state)
+ {
+ pj_scan_save_state(&scanner_, state);
+ }
+
+ void restore_state(State *state)
+ {
+ pj_scan_restore_state(&scanner_, state);
+ }
+
+ int get_pos_line() const
+ {
+ return scanner_.line;
+ }
+
+ int get_pos_col() const
+ {
+ return scanner_.col;
+ }
+
+
+private:
+ pj_scanner scanner_;
+};
+
+#endif /* __PJPP_SCANNER_HPP__ */
+
diff --git a/pjlib/include/pj++/sock.hpp b/pjlib/include/pj++/sock.hpp index f1a1e45f..3a401b04 100644 --- a/pjlib/include/pj++/sock.hpp +++ b/pjlib/include/pj++/sock.hpp @@ -1,427 +1,448 @@ -/* $Id$ - */ -#ifndef __PJPP_SOCK_HPP__ -#define __PJPP_SOCK_HPP__ - -#include <pj/sock.h> -#include <pj/string.h> - -class Pj_Event_Handler; - -// -// Base class for address. -// -class Pj_Addr -{ -}; - -// -// Internet address. -// -class Pj_Inet_Addr : public pj_sockaddr_in, public Pj_Addr -{ -public: - // - // Get port number. - // - pj_uint16_t get_port_number() const - { - return pj_sockaddr_in_get_port(this); - } - - // - // Set port number. - // - void set_port_number(pj_uint16_t port) - { - sin_family = PJ_AF_INET; - pj_sockaddr_in_set_port(this, port); - } - - // - // Get IP address. - // - pj_uint32_t get_ip_address() const - { - return pj_sockaddr_in_get_addr(this).s_addr; - } - - // - // Get address string. - // - const char *get_address() const - { - return pj_inet_ntoa(sin_addr); - } - - // - // Set IP address. - // - void set_ip_address(pj_uint32_t addr) - { - sin_family = PJ_AF_INET; - pj_sockaddr_in_set_addr(this, addr); - } - - // - // Set address. - // - pj_status_t set_address(const pj_str_t *addr) - { - return pj_sockaddr_in_set_str_addr(this, addr); - } - - // - // Set address. - // - pj_status_t set_address(const char *addr) - { - pj_str_t s; - return pj_sockaddr_in_set_str_addr(this, pj_cstr(&s, addr)); - } - - // - // Compare for equality. - // - bool operator==(const Pj_Inet_Addr &rhs) const - { - return sin_family == rhs.sin_family && - sin_addr.s_addr == rhs.sin_addr.s_addr && - sin_port == rhs.sin_port; - } - -private: - // - // Dummy length used in pj_ioqueue_recvfrom() etc - // - friend class Pj_Event_Handler; - friend class Pj_Socket; - friend class Pj_Sock_Stream; - friend class Pj_Sock_Dgram; - - int addrlen_; -}; - - -// -// Socket base class. -// -// Note: -// socket will not automatically be closed on destructor. -// -class Pj_Socket -{ -public: - // - // Default constructor. - // - Pj_Socket() - : sock_(PJ_INVALID_SOCKET) - { - } - - // - // Initialize from a socket handle. - // - explicit Pj_Socket(pj_sock_t sock) - : sock_(sock) - { - } - - // - // Copy constructor. - // - Pj_Socket(const Pj_Socket &rhs) - : sock_(rhs.sock_) - { - } - - // - // Destructor will not close the socket. - // You must call close() explicitly. - // - ~Pj_Socket() - { - } - - // - // Set socket handle. - // - void set_handle(pj_sock_t sock) - { - sock_ = sock; - } - - // - // Get socket handle. - // - pj_sock_t get_handle() const - { - return sock_; - } - - // - // Get socket handle. - // - pj_sock_t& get_handle() - { - return sock_; - } - - // - // See if the socket is valid. - // - bool is_valid() const - { - return sock_ != PJ_INVALID_SOCKET; - } - - // - // Create the socket. - // - pj_status_t create(int af, int type, int proto) - { - return pj_sock_socket(af, type, proto, &sock_); - } - - // - // Bind socket. - // - pj_status_t bind(const Pj_Inet_Addr &addr) - { - return pj_sock_bind(sock_, &addr, sizeof(Pj_Inet_Addr)); - } - - // - // Close socket. - // - pj_status_t close() - { - pj_sock_close(sock_); - } - - // - // Get peer socket name. - // - pj_status_t getpeername(Pj_Inet_Addr *addr) - { - return pj_sock_getpeername(sock_, addr, &addr->addrlen_); - } - - // - // getsockname - // - pj_status_t getsockname(Pj_Inet_Addr *addr) - { - return pj_sock_getsockname(sock_, addr, &addr->addrlen_); - } - - // - // getsockopt. - // - pj_status_t getsockopt(int level, int optname, - void *optval, int *optlen) - { - return pj_sock_getsockopt(sock_, level, optname, optval, optlen); - } - - // - // setsockopt - // - pj_status_t setsockopt(int level, int optname, - const void *optval, int optlen) - { - return pj_sock_setsockopt(sock_, level, optname, optval, optlen); - } - - // - // receive data. - // - pj_ssize_t recv(void *buf, pj_size_t len, int flag = 0) - { - pj_ssize_t bytes = len; - if (pj_sock_recv(sock_, buf, &bytes, flag) != PJ_SUCCESS) - return -1; - return bytes; - } - - // - // send data. - // - pj_ssize_t send(const void *buf, pj_ssize_t len, int flag = 0) - { - pj_ssize_t bytes = len; - if (pj_sock_send(sock_, buf, &bytes, flag) != PJ_SUCCESS) - return -1; - return bytes; - } - - // - // connect. - // - pj_status_t connect(const Pj_Inet_Addr &addr) - { - return pj_sock_connect(sock_, &addr, sizeof(Pj_Inet_Addr)); - } - - // - // assignment. - // - Pj_Socket &operator=(const Pj_Socket &rhs) - { - sock_ = rhs.sock_; - return *this; - } - -protected: - friend class Pj_Event_Handler; - pj_sock_t sock_; -}; - - -#if PJ_HAS_TCP -// -// Stream socket. -// -class Pj_Sock_Stream : public Pj_Socket -{ -public: - // - // Default constructor. - // - Pj_Sock_Stream() - { - } - - // - // Initialize from a socket handle. - // - explicit Pj_Sock_Stream(pj_sock_t sock) - : Pj_Socket(sock) - { - } - - // - // Copy constructor. - // - Pj_Sock_Stream(const Pj_Sock_Stream &rhs) : Pj_Socket(rhs) - { - } - - // - // Assignment. - // - Pj_Sock_Stream &operator=(const Pj_Sock_Stream &rhs) - { - sock_ = rhs.sock_; - return *this; - } - - // - // listen() - // - pj_status_t listen(int backlog = 5) - { - return pj_sock_listen(sock_, backlog); - } - - // - // blocking accept() - // - Pj_Sock_Stream accept(Pj_Inet_Addr *remote_addr = NULL) - { - pj_sock_t newsock; - int *addrlen = remote_addr ? &remote_addr->addrlen_ : NULL; - pj_status_t status; - - status = pj_sock_accept(sock_, &newsock, remote_addr, addrlen); - if (status != PJ_SUCCESS) - return Pj_Sock_Stream(-1); - - return Pj_Sock_Stream(newsock); - } - - // - // shutdown() - // - pj_status_t shutdown(int how = PJ_SHUT_RDWR) - { - return pj_sock_shutdown(sock_, how); - } - -}; -#endif - -// -// Datagram socket. -// -class Pj_Sock_Dgram : public Pj_Socket -{ -public: - // - // Default constructor. - // - Pj_Sock_Dgram() - { - } - - // - // Initialize from a socket handle. - // - explicit Pj_Sock_Dgram(pj_sock_t sock) - : Pj_Socket(sock) - { - } - - // - // Copy constructor. - // - Pj_Sock_Dgram(const Pj_Sock_Dgram &rhs) - : Pj_Socket(rhs) - { - } - - // - // Assignment. - // - Pj_Sock_Dgram &operator=(const Pj_Sock_Dgram &rhs) - { - Pj_Socket::operator =(rhs); - return *this; - } - - // - // recvfrom() - // - pj_ssize_t recvfrom( void *buf, pj_size_t len, int flag = 0, - Pj_Inet_Addr *fromaddr = NULL) - { - pj_ssize_t bytes = len; - int *addrlen = fromaddr ? &fromaddr->addrlen_ : NULL; - if (pj_sock_recvfrom( sock_, buf, &bytes, flag, - fromaddr, addrlen) != PJ_SUCCESS) - { - return -1; - } - return bytes; - } - - // - // sendto() - // - pj_ssize_t sendto( const void *buf, pj_size_t len, int flag, - const Pj_Inet_Addr &addr) - { - pj_ssize_t bytes = len; - if (pj_sock_sendto( sock_, buf, &bytes, flag, - &addr, sizeof(pj_sockaddr_in)) != PJ_SUCCESS) - { - return -1; - } - return bytes; - } -}; - - -#endif /* __PJPP_SOCK_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_SOCK_HPP__
+#define __PJPP_SOCK_HPP__
+
+#include <pj/sock.h>
+#include <pj/string.h>
+
+class Pj_Event_Handler;
+
+//
+// Base class for address.
+//
+class Pj_Addr
+{
+};
+
+//
+// Internet address.
+//
+class Pj_Inet_Addr : public pj_sockaddr_in, public Pj_Addr
+{
+public:
+ //
+ // Get port number.
+ //
+ pj_uint16_t get_port_number() const
+ {
+ return pj_sockaddr_in_get_port(this);
+ }
+
+ //
+ // Set port number.
+ //
+ void set_port_number(pj_uint16_t port)
+ {
+ sin_family = PJ_AF_INET;
+ pj_sockaddr_in_set_port(this, port);
+ }
+
+ //
+ // Get IP address.
+ //
+ pj_uint32_t get_ip_address() const
+ {
+ return pj_sockaddr_in_get_addr(this).s_addr;
+ }
+
+ //
+ // Get address string.
+ //
+ const char *get_address() const
+ {
+ return pj_inet_ntoa(sin_addr);
+ }
+
+ //
+ // Set IP address.
+ //
+ void set_ip_address(pj_uint32_t addr)
+ {
+ sin_family = PJ_AF_INET;
+ pj_sockaddr_in_set_addr(this, addr);
+ }
+
+ //
+ // Set address.
+ //
+ pj_status_t set_address(const pj_str_t *addr)
+ {
+ return pj_sockaddr_in_set_str_addr(this, addr);
+ }
+
+ //
+ // Set address.
+ //
+ pj_status_t set_address(const char *addr)
+ {
+ pj_str_t s;
+ return pj_sockaddr_in_set_str_addr(this, pj_cstr(&s, addr));
+ }
+
+ //
+ // Compare for equality.
+ //
+ bool operator==(const Pj_Inet_Addr &rhs) const
+ {
+ return sin_family == rhs.sin_family &&
+ sin_addr.s_addr == rhs.sin_addr.s_addr &&
+ sin_port == rhs.sin_port;
+ }
+
+private:
+ //
+ // Dummy length used in pj_ioqueue_recvfrom() etc
+ //
+ friend class Pj_Event_Handler;
+ friend class Pj_Socket;
+ friend class Pj_Sock_Stream;
+ friend class Pj_Sock_Dgram;
+
+ int addrlen_;
+};
+
+
+//
+// Socket base class.
+//
+// Note:
+// socket will not automatically be closed on destructor.
+//
+class Pj_Socket
+{
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Socket()
+ : sock_(PJ_INVALID_SOCKET)
+ {
+ }
+
+ //
+ // Initialize from a socket handle.
+ //
+ explicit Pj_Socket(pj_sock_t sock)
+ : sock_(sock)
+ {
+ }
+
+ //
+ // Copy constructor.
+ //
+ Pj_Socket(const Pj_Socket &rhs)
+ : sock_(rhs.sock_)
+ {
+ }
+
+ //
+ // Destructor will not close the socket.
+ // You must call close() explicitly.
+ //
+ ~Pj_Socket()
+ {
+ }
+
+ //
+ // Set socket handle.
+ //
+ void set_handle(pj_sock_t sock)
+ {
+ sock_ = sock;
+ }
+
+ //
+ // Get socket handle.
+ //
+ pj_sock_t get_handle() const
+ {
+ return sock_;
+ }
+
+ //
+ // Get socket handle.
+ //
+ pj_sock_t& get_handle()
+ {
+ return sock_;
+ }
+
+ //
+ // See if the socket is valid.
+ //
+ bool is_valid() const
+ {
+ return sock_ != PJ_INVALID_SOCKET;
+ }
+
+ //
+ // Create the socket.
+ //
+ pj_status_t create(int af, int type, int proto)
+ {
+ return pj_sock_socket(af, type, proto, &sock_);
+ }
+
+ //
+ // Bind socket.
+ //
+ pj_status_t bind(const Pj_Inet_Addr &addr)
+ {
+ return pj_sock_bind(sock_, &addr, sizeof(Pj_Inet_Addr));
+ }
+
+ //
+ // Close socket.
+ //
+ pj_status_t close()
+ {
+ pj_sock_close(sock_);
+ }
+
+ //
+ // Get peer socket name.
+ //
+ pj_status_t getpeername(Pj_Inet_Addr *addr)
+ {
+ return pj_sock_getpeername(sock_, addr, &addr->addrlen_);
+ }
+
+ //
+ // getsockname
+ //
+ pj_status_t getsockname(Pj_Inet_Addr *addr)
+ {
+ return pj_sock_getsockname(sock_, addr, &addr->addrlen_);
+ }
+
+ //
+ // getsockopt.
+ //
+ pj_status_t getsockopt(int level, int optname,
+ void *optval, int *optlen)
+ {
+ return pj_sock_getsockopt(sock_, level, optname, optval, optlen);
+ }
+
+ //
+ // setsockopt
+ //
+ pj_status_t setsockopt(int level, int optname,
+ const void *optval, int optlen)
+ {
+ return pj_sock_setsockopt(sock_, level, optname, optval, optlen);
+ }
+
+ //
+ // receive data.
+ //
+ pj_ssize_t recv(void *buf, pj_size_t len, int flag = 0)
+ {
+ pj_ssize_t bytes = len;
+ if (pj_sock_recv(sock_, buf, &bytes, flag) != PJ_SUCCESS)
+ return -1;
+ return bytes;
+ }
+
+ //
+ // send data.
+ //
+ pj_ssize_t send(const void *buf, pj_ssize_t len, int flag = 0)
+ {
+ pj_ssize_t bytes = len;
+ if (pj_sock_send(sock_, buf, &bytes, flag) != PJ_SUCCESS)
+ return -1;
+ return bytes;
+ }
+
+ //
+ // connect.
+ //
+ pj_status_t connect(const Pj_Inet_Addr &addr)
+ {
+ return pj_sock_connect(sock_, &addr, sizeof(Pj_Inet_Addr));
+ }
+
+ //
+ // assignment.
+ //
+ Pj_Socket &operator=(const Pj_Socket &rhs)
+ {
+ sock_ = rhs.sock_;
+ return *this;
+ }
+
+protected:
+ friend class Pj_Event_Handler;
+ pj_sock_t sock_;
+};
+
+
+#if PJ_HAS_TCP
+//
+// Stream socket.
+//
+class Pj_Sock_Stream : public Pj_Socket
+{
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Sock_Stream()
+ {
+ }
+
+ //
+ // Initialize from a socket handle.
+ //
+ explicit Pj_Sock_Stream(pj_sock_t sock)
+ : Pj_Socket(sock)
+ {
+ }
+
+ //
+ // Copy constructor.
+ //
+ Pj_Sock_Stream(const Pj_Sock_Stream &rhs) : Pj_Socket(rhs)
+ {
+ }
+
+ //
+ // Assignment.
+ //
+ Pj_Sock_Stream &operator=(const Pj_Sock_Stream &rhs)
+ {
+ sock_ = rhs.sock_;
+ return *this;
+ }
+
+ //
+ // listen()
+ //
+ pj_status_t listen(int backlog = 5)
+ {
+ return pj_sock_listen(sock_, backlog);
+ }
+
+ //
+ // blocking accept()
+ //
+ Pj_Sock_Stream accept(Pj_Inet_Addr *remote_addr = NULL)
+ {
+ pj_sock_t newsock;
+ int *addrlen = remote_addr ? &remote_addr->addrlen_ : NULL;
+ pj_status_t status;
+
+ status = pj_sock_accept(sock_, &newsock, remote_addr, addrlen);
+ if (status != PJ_SUCCESS)
+ return Pj_Sock_Stream(-1);
+
+ return Pj_Sock_Stream(newsock);
+ }
+
+ //
+ // shutdown()
+ //
+ pj_status_t shutdown(int how = PJ_SHUT_RDWR)
+ {
+ return pj_sock_shutdown(sock_, how);
+ }
+
+};
+#endif
+
+//
+// Datagram socket.
+//
+class Pj_Sock_Dgram : public Pj_Socket
+{
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Sock_Dgram()
+ {
+ }
+
+ //
+ // Initialize from a socket handle.
+ //
+ explicit Pj_Sock_Dgram(pj_sock_t sock)
+ : Pj_Socket(sock)
+ {
+ }
+
+ //
+ // Copy constructor.
+ //
+ Pj_Sock_Dgram(const Pj_Sock_Dgram &rhs)
+ : Pj_Socket(rhs)
+ {
+ }
+
+ //
+ // Assignment.
+ //
+ Pj_Sock_Dgram &operator=(const Pj_Sock_Dgram &rhs)
+ {
+ Pj_Socket::operator =(rhs);
+ return *this;
+ }
+
+ //
+ // recvfrom()
+ //
+ pj_ssize_t recvfrom( void *buf, pj_size_t len, int flag = 0,
+ Pj_Inet_Addr *fromaddr = NULL)
+ {
+ pj_ssize_t bytes = len;
+ int *addrlen = fromaddr ? &fromaddr->addrlen_ : NULL;
+ if (pj_sock_recvfrom( sock_, buf, &bytes, flag,
+ fromaddr, addrlen) != PJ_SUCCESS)
+ {
+ return -1;
+ }
+ return bytes;
+ }
+
+ //
+ // sendto()
+ //
+ pj_ssize_t sendto( const void *buf, pj_size_t len, int flag,
+ const Pj_Inet_Addr &addr)
+ {
+ pj_ssize_t bytes = len;
+ if (pj_sock_sendto( sock_, buf, &bytes, flag,
+ &addr, sizeof(pj_sockaddr_in)) != PJ_SUCCESS)
+ {
+ return -1;
+ }
+ return bytes;
+ }
+};
+
+
+#endif /* __PJPP_SOCK_HPP__ */
+
diff --git a/pjlib/include/pj++/string.hpp b/pjlib/include/pj++/string.hpp index 6be1e50a..dbb2d57f 100644 --- a/pjlib/include/pj++/string.hpp +++ b/pjlib/include/pj++/string.hpp @@ -1,409 +1,430 @@ -/* $Id$ - */ -#ifndef __PJPP_STRING_HPP__ -#define __PJPP_STRING_HPP__ - -#include <pj/string.h> -#include <pj++/pool.hpp> -#include <pj/assert.h> - -// -// String wrapper class for pj_str_t. -// -class Pj_String : public pj_str_t -{ -public: - // - // Default constructor. - // - Pj_String() - { - pj_assert(sizeof(Pj_String) == sizeof(pj_str_t)); - ptr=NULL; - slen=0; - } - - // - // Construct the buffer from a char*. - // - explicit Pj_String(char *str) - { - set(str); - } - - // - // Construct from a const char*. - // - Pj_String(Pj_Pool *pool, const char *src) - { - set(pool, src); - } - - // - // Construct from pj_str_t*. - // - explicit Pj_String(pj_str_t *s) - { - set(s); - } - - // - // Construct by copying from const pj_str_t*. - // - Pj_String(Pj_Pool *pool, const pj_str_t *s) - { - set(pool, s); - } - - // - // Construct from another Pj_String - // - explicit Pj_String(Pj_String &rhs) - { - set(rhs); - } - - // - // Construct by copying from Pj_String - // - Pj_String(Pj_Pool *pool, const Pj_String &rhs) - { - set(pool, rhs); - } - - // - // Construct from a char* and a length. - // - Pj_String(char *str, pj_size_t len) - { - set(str, len); - } - - // - // Construct from pair of pointer. - // - Pj_String(char *begin, char *end) - { - pj_strset3(this, begin, end); - } - - // - // Get the length of the string. - // - pj_size_t length() const - { - return pj_strlen(this); - } - - // - // Get the length of the string. - // - pj_size_t size() const - { - return length(); - } - - // - // Get the string buffer. - // - const char *buf() const - { - return ptr; - } - - // - // Initialize buffer from char*. - // - void set(char *str) - { - pj_strset2(this, str); - } - - // - // Initialize by copying from a const char*. - // - void set(Pj_Pool *pool, const char *s) - { - pj_strdup2(pool->pool_(), this, s); - } - - // - // Initialize from pj_str_t*. - // - void set(pj_str_t *s) - { - pj_strassign(this, s); - } - - // - // Initialize by copying from const pj_str_t*. - // - void set(Pj_Pool *pool, const pj_str_t *s) - { - pj_strdup(pool->pool_(), this, s); - } - - // - // Initialize from char* and length. - // - void set(char *str, pj_size_t len) - { - pj_strset(this, str, len); - } - - // - // Initialize from pair of pointers. - // - void set(char *begin, char *end) - { - pj_strset3(this, begin, end); - } - - // - // Initialize from other Pj_String. - // - void set(Pj_String &rhs) - { - pj_strassign(this, &rhs); - } - - // - // Initialize by copying from a Pj_String*. - // - void set(Pj_Pool *pool, const Pj_String *s) - { - pj_strdup(pool->pool_(), this, s); - } - - // - // Initialize by copying from other Pj_String. - // - void set(Pj_Pool *pool, const Pj_String &s) - { - pj_strdup(pool->pool_(), this, &s); - } - - // - // Copy the contents of other string. - // - void strcpy(const pj_str_t *s) - { - pj_strcpy(this, s); - } - - // - // Copy the contents of other string. - // - void strcpy(const Pj_String &rhs) - { - pj_strcpy(this, &rhs); - } - - // - // Copy the contents of other string. - // - void strcpy(const char *s) - { - pj_strcpy2(this, s); - } - - // - // Compare string. - // - int strcmp(const char *s) const - { - return pj_strcmp2(this, s); - } - - // - // Compare string. - // - int strcmp(const pj_str_t *s) const - { - return pj_strcmp(this, s); - } - - // - // Compare string. - // - int strcmp(const Pj_String &rhs) const - { - return pj_strcmp(this, &rhs); - } - - // - // Compare string. - // - int strncmp(const char *s, pj_size_t len) const - { - return pj_strncmp2(this, s, len); - } - - // - // Compare string. - // - int strncmp(const pj_str_t *s, pj_size_t len) const - { - return pj_strncmp(this, s, len); - } - - // - // Compare string. - // - int strncmp(const Pj_String &rhs, pj_size_t len) const - { - return pj_strncmp(this, &rhs, len); - } - - // - // Compare string. - // - int stricmp(const char *s) const - { - return pj_stricmp2(this, s); - } - - // - // Compare string. - // - int stricmp(const pj_str_t *s) const - { - return pj_stricmp(this, s); - } - - // - // Compare string. - // - int stricmp(const Pj_String &rhs) const - { - return stricmp(&rhs); - } - - // - // Compare string. - // - int strnicmp(const char *s, pj_size_t len) const - { - return pj_strnicmp2(this, s, len); - } - - // - // Compare string. - // - int strnicmp(const pj_str_t *s, pj_size_t len) const - { - return pj_strnicmp(this, s, len); - } - - // - // Compare string. - // - int strnicmp(const Pj_String &rhs, pj_size_t len) const - { - return strnicmp(&rhs, len); - } - - // - // Compare contents for equality. - // - bool operator==(const char *s) const - { - return strcmp(s) == 0; - } - - // - // Compare contents for equality. - // - bool operator==(const pj_str_t *s) const - { - return strcmp(s) == 0; - } - - // - // Compare contents for equality. - // - bool operator==(const Pj_String &rhs) const - { - return pj_strcmp(this, &rhs) == 0; - } - - // - // Find a character in the string. - // - char *strchr(int chr) - { - return pj_strchr(this, chr); - } - - // - // Find a character in the string. - // - char *find(int chr) - { - return strchr(chr); - } - - // - // Concatenate string. - // - void strcat(const Pj_String &rhs) - { - pj_strcat(this, &rhs); - } - - // - // Left trim. - // - void ltrim() - { - pj_strltrim(this); - } - - // - // Right trim. - // - void rtrim() - { - pj_strrtrim(this); - } - - // - // Left and right trim. - // - void trim() - { - pj_strtrim(this); - } - - // - // Convert to unsigned long. - // - unsigned long to_ulong() const - { - return pj_strtoul(this); - } - - // - // Convert from unsigned long. - // - void from_ulong(unsigned long value) - { - slen = pj_utoa(value, ptr); - } - - // - // Convert from unsigned long with padding. - // - void from_ulong_with_pad(unsigned long value, int min_dig=0, int pad=' ') - { - slen = pj_utoa_pad(value, ptr, min_dig, pad); - } - - -private: - //Pj_String(const Pj_String &rhs) {} - void operator=(const Pj_String &rhs) { pj_assert(false); } -}; - -#endif /* __PJPP_STRING_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_STRING_HPP__
+#define __PJPP_STRING_HPP__
+
+#include <pj/string.h>
+#include <pj++/pool.hpp>
+#include <pj/assert.h>
+
+//
+// String wrapper class for pj_str_t.
+//
+class Pj_String : public pj_str_t
+{
+public:
+ //
+ // Default constructor.
+ //
+ Pj_String()
+ {
+ pj_assert(sizeof(Pj_String) == sizeof(pj_str_t));
+ ptr=NULL;
+ slen=0;
+ }
+
+ //
+ // Construct the buffer from a char*.
+ //
+ explicit Pj_String(char *str)
+ {
+ set(str);
+ }
+
+ //
+ // Construct from a const char*.
+ //
+ Pj_String(Pj_Pool *pool, const char *src)
+ {
+ set(pool, src);
+ }
+
+ //
+ // Construct from pj_str_t*.
+ //
+ explicit Pj_String(pj_str_t *s)
+ {
+ set(s);
+ }
+
+ //
+ // Construct by copying from const pj_str_t*.
+ //
+ Pj_String(Pj_Pool *pool, const pj_str_t *s)
+ {
+ set(pool, s);
+ }
+
+ //
+ // Construct from another Pj_String
+ //
+ explicit Pj_String(Pj_String &rhs)
+ {
+ set(rhs);
+ }
+
+ //
+ // Construct by copying from Pj_String
+ //
+ Pj_String(Pj_Pool *pool, const Pj_String &rhs)
+ {
+ set(pool, rhs);
+ }
+
+ //
+ // Construct from a char* and a length.
+ //
+ Pj_String(char *str, pj_size_t len)
+ {
+ set(str, len);
+ }
+
+ //
+ // Construct from pair of pointer.
+ //
+ Pj_String(char *begin, char *end)
+ {
+ pj_strset3(this, begin, end);
+ }
+
+ //
+ // Get the length of the string.
+ //
+ pj_size_t length() const
+ {
+ return pj_strlen(this);
+ }
+
+ //
+ // Get the length of the string.
+ //
+ pj_size_t size() const
+ {
+ return length();
+ }
+
+ //
+ // Get the string buffer.
+ //
+ const char *buf() const
+ {
+ return ptr;
+ }
+
+ //
+ // Initialize buffer from char*.
+ //
+ void set(char *str)
+ {
+ pj_strset2(this, str);
+ }
+
+ //
+ // Initialize by copying from a const char*.
+ //
+ void set(Pj_Pool *pool, const char *s)
+ {
+ pj_strdup2(pool->pool_(), this, s);
+ }
+
+ //
+ // Initialize from pj_str_t*.
+ //
+ void set(pj_str_t *s)
+ {
+ pj_strassign(this, s);
+ }
+
+ //
+ // Initialize by copying from const pj_str_t*.
+ //
+ void set(Pj_Pool *pool, const pj_str_t *s)
+ {
+ pj_strdup(pool->pool_(), this, s);
+ }
+
+ //
+ // Initialize from char* and length.
+ //
+ void set(char *str, pj_size_t len)
+ {
+ pj_strset(this, str, len);
+ }
+
+ //
+ // Initialize from pair of pointers.
+ //
+ void set(char *begin, char *end)
+ {
+ pj_strset3(this, begin, end);
+ }
+
+ //
+ // Initialize from other Pj_String.
+ //
+ void set(Pj_String &rhs)
+ {
+ pj_strassign(this, &rhs);
+ }
+
+ //
+ // Initialize by copying from a Pj_String*.
+ //
+ void set(Pj_Pool *pool, const Pj_String *s)
+ {
+ pj_strdup(pool->pool_(), this, s);
+ }
+
+ //
+ // Initialize by copying from other Pj_String.
+ //
+ void set(Pj_Pool *pool, const Pj_String &s)
+ {
+ pj_strdup(pool->pool_(), this, &s);
+ }
+
+ //
+ // Copy the contents of other string.
+ //
+ void strcpy(const pj_str_t *s)
+ {
+ pj_strcpy(this, s);
+ }
+
+ //
+ // Copy the contents of other string.
+ //
+ void strcpy(const Pj_String &rhs)
+ {
+ pj_strcpy(this, &rhs);
+ }
+
+ //
+ // Copy the contents of other string.
+ //
+ void strcpy(const char *s)
+ {
+ pj_strcpy2(this, s);
+ }
+
+ //
+ // Compare string.
+ //
+ int strcmp(const char *s) const
+ {
+ return pj_strcmp2(this, s);
+ }
+
+ //
+ // Compare string.
+ //
+ int strcmp(const pj_str_t *s) const
+ {
+ return pj_strcmp(this, s);
+ }
+
+ //
+ // Compare string.
+ //
+ int strcmp(const Pj_String &rhs) const
+ {
+ return pj_strcmp(this, &rhs);
+ }
+
+ //
+ // Compare string.
+ //
+ int strncmp(const char *s, pj_size_t len) const
+ {
+ return pj_strncmp2(this, s, len);
+ }
+
+ //
+ // Compare string.
+ //
+ int strncmp(const pj_str_t *s, pj_size_t len) const
+ {
+ return pj_strncmp(this, s, len);
+ }
+
+ //
+ // Compare string.
+ //
+ int strncmp(const Pj_String &rhs, pj_size_t len) const
+ {
+ return pj_strncmp(this, &rhs, len);
+ }
+
+ //
+ // Compare string.
+ //
+ int stricmp(const char *s) const
+ {
+ return pj_stricmp2(this, s);
+ }
+
+ //
+ // Compare string.
+ //
+ int stricmp(const pj_str_t *s) const
+ {
+ return pj_stricmp(this, s);
+ }
+
+ //
+ // Compare string.
+ //
+ int stricmp(const Pj_String &rhs) const
+ {
+ return stricmp(&rhs);
+ }
+
+ //
+ // Compare string.
+ //
+ int strnicmp(const char *s, pj_size_t len) const
+ {
+ return pj_strnicmp2(this, s, len);
+ }
+
+ //
+ // Compare string.
+ //
+ int strnicmp(const pj_str_t *s, pj_size_t len) const
+ {
+ return pj_strnicmp(this, s, len);
+ }
+
+ //
+ // Compare string.
+ //
+ int strnicmp(const Pj_String &rhs, pj_size_t len) const
+ {
+ return strnicmp(&rhs, len);
+ }
+
+ //
+ // Compare contents for equality.
+ //
+ bool operator==(const char *s) const
+ {
+ return strcmp(s) == 0;
+ }
+
+ //
+ // Compare contents for equality.
+ //
+ bool operator==(const pj_str_t *s) const
+ {
+ return strcmp(s) == 0;
+ }
+
+ //
+ // Compare contents for equality.
+ //
+ bool operator==(const Pj_String &rhs) const
+ {
+ return pj_strcmp(this, &rhs) == 0;
+ }
+
+ //
+ // Find a character in the string.
+ //
+ char *strchr(int chr)
+ {
+ return pj_strchr(this, chr);
+ }
+
+ //
+ // Find a character in the string.
+ //
+ char *find(int chr)
+ {
+ return strchr(chr);
+ }
+
+ //
+ // Concatenate string.
+ //
+ void strcat(const Pj_String &rhs)
+ {
+ pj_strcat(this, &rhs);
+ }
+
+ //
+ // Left trim.
+ //
+ void ltrim()
+ {
+ pj_strltrim(this);
+ }
+
+ //
+ // Right trim.
+ //
+ void rtrim()
+ {
+ pj_strrtrim(this);
+ }
+
+ //
+ // Left and right trim.
+ //
+ void trim()
+ {
+ pj_strtrim(this);
+ }
+
+ //
+ // Convert to unsigned long.
+ //
+ unsigned long to_ulong() const
+ {
+ return pj_strtoul(this);
+ }
+
+ //
+ // Convert from unsigned long.
+ //
+ void from_ulong(unsigned long value)
+ {
+ slen = pj_utoa(value, ptr);
+ }
+
+ //
+ // Convert from unsigned long with padding.
+ //
+ void from_ulong_with_pad(unsigned long value, int min_dig=0, int pad=' ')
+ {
+ slen = pj_utoa_pad(value, ptr, min_dig, pad);
+ }
+
+
+private:
+ //Pj_String(const Pj_String &rhs) {}
+ void operator=(const Pj_String &rhs) { pj_assert(false); }
+};
+
+#endif /* __PJPP_STRING_HPP__ */
+
diff --git a/pjlib/include/pj++/timer.hpp b/pjlib/include/pj++/timer.hpp index fbb15f7a..7a5618d0 100644 --- a/pjlib/include/pj++/timer.hpp +++ b/pjlib/include/pj++/timer.hpp @@ -1,181 +1,202 @@ -/* $Id$ - */ -#ifndef __PJPP_TIMER_HPP__ -#define __PJPP_TIMER_HPP__ - -#include <pj/timer.h> -#include <pj++/types.hpp> -#include <pj/assert.h> -#include <pj++/lock.hpp> - -class Pj_Timer_Heap; - -////////////////////////////////////////////////////////////////////////////// -// Timer entry. -// -// How to use: -// Derive class from Pj_Timer_Entry and override on_timeout(). -// Scheduler timer in Pj_Timer_Heap. -// -class Pj_Timer_Entry : public Pj_Object -{ - friend class Pj_Timer_Heap; - -public: - // - // Default constructor. - // - Pj_Timer_Entry() - { - entry_.user_data = this; - entry_.cb = &timer_heap_callback; - } - - // - // Destructor, do nothing. - // - ~Pj_Timer_Entry() - { - } - - // - // Override this to get the timeout notification. - // - virtual void on_timeout(int id) = 0; - -private: - pj_timer_entry entry_; - - static void timer_heap_callback(pj_timer_heap_t *th, pj_timer_entry *e) - { - Pj_Timer_Entry *entry = (Pj_Timer_Entry*) e->user_data; - entry->on_timeout(e->id); - } - -}; - -////////////////////////////////////////////////////////////////////////////// -// Timer heap. -// -class Pj_Timer_Heap : public Pj_Object -{ -public: - // - // Default constructor. - // - Pj_Timer_Heap() - : ht_(NULL) - { - } - - // - // Construct timer heap. - // - Pj_Timer_Heap(Pj_Pool *pool, pj_size_t initial_count) - : ht_(NULL) - { - create(pool, initial_count); - } - - // - // Destructor. - // - ~Pj_Timer_Heap() - { - destroy(); - } - - // - // Create - // - pj_status_t create(Pj_Pool *pool, pj_size_t initial_count) - { - destroy(); - return pj_timer_heap_create(pool->pool_(), initial_count, &ht_); - } - - // - // Destroy - // - void destroy() - { - if (ht_) { - pj_timer_heap_destroy(ht_); - ht_ = NULL; - } - } - - // - // Get pjlib compatible timer heap object. - // - pj_timer_heap_t *get_timer_heap() - { - return ht_; - } - - // - // Set the lock object. - // - void set_lock( Pj_Lock *lock, bool auto_delete ) - { - pj_timer_heap_set_lock( ht_, lock->pj_lock_t_(), auto_delete); - } - - // - // Set maximum number of timed out entries to be processed per poll. - // - unsigned set_max_timed_out_per_poll(unsigned count) - { - return pj_timer_heap_set_max_timed_out_per_poll(ht_, count); - } - - // - // Schedule a timer. - // - bool schedule( Pj_Timer_Entry *ent, const Pj_Time_Val &delay, - int id) - { - ent->entry_.id = id; - return pj_timer_heap_schedule(ht_, &ent->entry_, &delay) == 0; - } - - // - // Cancel a timer. - // - bool cancel(Pj_Timer_Entry *ent) - { - return pj_timer_heap_cancel(ht_, &ent->entry_) == 1; - } - - // - // Get current number of timers - // - pj_size_t count() - { - return pj_timer_heap_count(ht_); - } - - // - // Get the earliest time. - // Return false if no timer is found. - // - bool earliest_time(Pj_Time_Val *t) - { - return pj_timer_heap_earliest_time(ht_, t) == PJ_SUCCESS; - } - - // - // Poll the timer. - // Return number of timed out entries has been called. - // - unsigned poll(Pj_Time_Val *next_delay = NULL) - { - return pj_timer_heap_poll(ht_, next_delay); - } - -private: - pj_timer_heap_t *ht_; -}; - -#endif /* __PJPP_TIMER_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_TIMER_HPP__
+#define __PJPP_TIMER_HPP__
+
+#include <pj/timer.h>
+#include <pj++/types.hpp>
+#include <pj/assert.h>
+#include <pj++/lock.hpp>
+
+class Pj_Timer_Heap;
+
+//////////////////////////////////////////////////////////////////////////////
+// Timer entry.
+//
+// How to use:
+// Derive class from Pj_Timer_Entry and override on_timeout().
+// Scheduler timer in Pj_Timer_Heap.
+//
+class Pj_Timer_Entry : public Pj_Object
+{
+ friend class Pj_Timer_Heap;
+
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Timer_Entry()
+ {
+ entry_.user_data = this;
+ entry_.cb = &timer_heap_callback;
+ }
+
+ //
+ // Destructor, do nothing.
+ //
+ ~Pj_Timer_Entry()
+ {
+ }
+
+ //
+ // Override this to get the timeout notification.
+ //
+ virtual void on_timeout(int id) = 0;
+
+private:
+ pj_timer_entry entry_;
+
+ static void timer_heap_callback(pj_timer_heap_t *th, pj_timer_entry *e)
+ {
+ Pj_Timer_Entry *entry = (Pj_Timer_Entry*) e->user_data;
+ entry->on_timeout(e->id);
+ }
+
+};
+
+//////////////////////////////////////////////////////////////////////////////
+// Timer heap.
+//
+class Pj_Timer_Heap : public Pj_Object
+{
+public:
+ //
+ // Default constructor.
+ //
+ Pj_Timer_Heap()
+ : ht_(NULL)
+ {
+ }
+
+ //
+ // Construct timer heap.
+ //
+ Pj_Timer_Heap(Pj_Pool *pool, pj_size_t initial_count)
+ : ht_(NULL)
+ {
+ create(pool, initial_count);
+ }
+
+ //
+ // Destructor.
+ //
+ ~Pj_Timer_Heap()
+ {
+ destroy();
+ }
+
+ //
+ // Create
+ //
+ pj_status_t create(Pj_Pool *pool, pj_size_t initial_count)
+ {
+ destroy();
+ return pj_timer_heap_create(pool->pool_(), initial_count, &ht_);
+ }
+
+ //
+ // Destroy
+ //
+ void destroy()
+ {
+ if (ht_) {
+ pj_timer_heap_destroy(ht_);
+ ht_ = NULL;
+ }
+ }
+
+ //
+ // Get pjlib compatible timer heap object.
+ //
+ pj_timer_heap_t *get_timer_heap()
+ {
+ return ht_;
+ }
+
+ //
+ // Set the lock object.
+ //
+ void set_lock( Pj_Lock *lock, bool auto_delete )
+ {
+ pj_timer_heap_set_lock( ht_, lock->pj_lock_t_(), auto_delete);
+ }
+
+ //
+ // Set maximum number of timed out entries to be processed per poll.
+ //
+ unsigned set_max_timed_out_per_poll(unsigned count)
+ {
+ return pj_timer_heap_set_max_timed_out_per_poll(ht_, count);
+ }
+
+ //
+ // Schedule a timer.
+ //
+ bool schedule( Pj_Timer_Entry *ent, const Pj_Time_Val &delay,
+ int id)
+ {
+ ent->entry_.id = id;
+ return pj_timer_heap_schedule(ht_, &ent->entry_, &delay) == 0;
+ }
+
+ //
+ // Cancel a timer.
+ //
+ bool cancel(Pj_Timer_Entry *ent)
+ {
+ return pj_timer_heap_cancel(ht_, &ent->entry_) == 1;
+ }
+
+ //
+ // Get current number of timers
+ //
+ pj_size_t count()
+ {
+ return pj_timer_heap_count(ht_);
+ }
+
+ //
+ // Get the earliest time.
+ // Return false if no timer is found.
+ //
+ bool earliest_time(Pj_Time_Val *t)
+ {
+ return pj_timer_heap_earliest_time(ht_, t) == PJ_SUCCESS;
+ }
+
+ //
+ // Poll the timer.
+ // Return number of timed out entries has been called.
+ //
+ unsigned poll(Pj_Time_Val *next_delay = NULL)
+ {
+ return pj_timer_heap_poll(ht_, next_delay);
+ }
+
+private:
+ pj_timer_heap_t *ht_;
+};
+
+#endif /* __PJPP_TIMER_HPP__ */
+
diff --git a/pjlib/include/pj++/tree.hpp b/pjlib/include/pj++/tree.hpp index f4fe8fc1..d58d6a04 100644 --- a/pjlib/include/pj++/tree.hpp +++ b/pjlib/include/pj++/tree.hpp @@ -1,112 +1,133 @@ -/* $Id$ - */ -#ifndef __PJPP_TREE_HPP__ -#define __PJPP_TREE_HPP__ - -#include <pj/rbtree.h> - -// -// Tree. -// -class PJ_Tree -{ -public: - typedef pj_rbtree_comp Comp; - class iterator; - class reverse_iterator; - - class Node : private pj_rbtree_node - { - friend class PJ_Tree; - friend class iterator; - friend class reverse_iterator; - - public: - Node() {} - explicit Node(void *data) { user_data = data; } - void set_user_data(void *data) { user_data = data; } - void *get_user_data() const { return user_data; } - }; - - class iterator - { - public: - iterator() {} - iterator(const iterator &rhs) : tr_(rhs.tr_), nd_(rhs.nd_) {} - iterator(pj_rbtree *tr, pj_rbtree_node *nd) : tr_(tr), nd_(nd) {} - Node *operator*() { return (Node*)nd_; } - bool operator==(const iterator &rhs) const { return tr_==rhs.tr_ && nd_==rhs.nd_; } - iterator &operator=(const iterator &rhs) { tr_=rhs.tr_; nd_=rhs.nd_; return *this; } - void operator++() { nd_=pj_rbtree_next(tr_, nd_); } - void operator--() { nd_=pj_rbtree_prev(tr_, nd_); } - protected: - pj_rbtree *tr_; - pj_rbtree_node *nd_; - }; - - class reverse_iterator : public iterator - { - public: - reverse_iterator() {} - reverse_iterator(const reverse_iterator &it) : iterator(it) {} - reverse_iterator(pj_rbtree *t, pj_rbtree_node *n) : iterator(t, n) {} - reverse_iterator &operator=(const reverse_iterator &rhs) { iterator::operator=(rhs); return *this; } - Node *operator*() { return (Node*)nd_; } - bool operator==(const reverse_iterator &rhs) const { return iterator::operator==(rhs); } - void operator++() { nd_=pj_rbtree_prev(tr_, nd_); } - void operator--() { nd_=pj_rbtree_next(tr_, nd_); } - }; - - explicit PJ_Tree(Comp *comp) { pj_rbtree_init(&t_, comp); } - - iterator begin() - { - return iterator(&t_, pj_rbtree_first(&t_)); - } - - iterator end() - { - return iterator(&t_, NULL); - } - - reverse_iterator rbegin() - { - return reverse_iterator(&t_, pj_rbtree_last(&t_)); - } - - reverse_iterator rend() - { - return reverse_iterator(&t_, NULL); - } - - bool insert(Node *node) - { - return pj_rbtree_insert(&t_, node)==0 ? true : false; - } - - Node *find(const void *key) - { - return (Node*)pj_rbtree_find(&t_, key); - } - - Node *erase(Node *node) - { - return (Node*)pj_rbtree_erase(&t_, node); - } - - unsigned max_height(Node *node=NULL) - { - return pj_rbtree_max_height(&t_, node); - } - - unsigned min_height(Node *node=NULL) - { - return pj_rbtree_min_height(&t_, node); - } - -private: - pj_rbtree t_; -}; - -#endif /* __PJPP_TREE_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_TREE_HPP__
+#define __PJPP_TREE_HPP__
+
+#include <pj/rbtree.h>
+
+//
+// Tree.
+//
+class PJ_Tree
+{
+public:
+ typedef pj_rbtree_comp Comp;
+ class iterator;
+ class reverse_iterator;
+
+ class Node : private pj_rbtree_node
+ {
+ friend class PJ_Tree;
+ friend class iterator;
+ friend class reverse_iterator;
+
+ public:
+ Node() {}
+ explicit Node(void *data) { user_data = data; }
+ void set_user_data(void *data) { user_data = data; }
+ void *get_user_data() const { return user_data; }
+ };
+
+ class iterator
+ {
+ public:
+ iterator() {}
+ iterator(const iterator &rhs) : tr_(rhs.tr_), nd_(rhs.nd_) {}
+ iterator(pj_rbtree *tr, pj_rbtree_node *nd) : tr_(tr), nd_(nd) {}
+ Node *operator*() { return (Node*)nd_; }
+ bool operator==(const iterator &rhs) const { return tr_==rhs.tr_ && nd_==rhs.nd_; }
+ iterator &operator=(const iterator &rhs) { tr_=rhs.tr_; nd_=rhs.nd_; return *this; }
+ void operator++() { nd_=pj_rbtree_next(tr_, nd_); }
+ void operator--() { nd_=pj_rbtree_prev(tr_, nd_); }
+ protected:
+ pj_rbtree *tr_;
+ pj_rbtree_node *nd_;
+ };
+
+ class reverse_iterator : public iterator
+ {
+ public:
+ reverse_iterator() {}
+ reverse_iterator(const reverse_iterator &it) : iterator(it) {}
+ reverse_iterator(pj_rbtree *t, pj_rbtree_node *n) : iterator(t, n) {}
+ reverse_iterator &operator=(const reverse_iterator &rhs) { iterator::operator=(rhs); return *this; }
+ Node *operator*() { return (Node*)nd_; }
+ bool operator==(const reverse_iterator &rhs) const { return iterator::operator==(rhs); }
+ void operator++() { nd_=pj_rbtree_prev(tr_, nd_); }
+ void operator--() { nd_=pj_rbtree_next(tr_, nd_); }
+ };
+
+ explicit PJ_Tree(Comp *comp) { pj_rbtree_init(&t_, comp); }
+
+ iterator begin()
+ {
+ return iterator(&t_, pj_rbtree_first(&t_));
+ }
+
+ iterator end()
+ {
+ return iterator(&t_, NULL);
+ }
+
+ reverse_iterator rbegin()
+ {
+ return reverse_iterator(&t_, pj_rbtree_last(&t_));
+ }
+
+ reverse_iterator rend()
+ {
+ return reverse_iterator(&t_, NULL);
+ }
+
+ bool insert(Node *node)
+ {
+ return pj_rbtree_insert(&t_, node)==0 ? true : false;
+ }
+
+ Node *find(const void *key)
+ {
+ return (Node*)pj_rbtree_find(&t_, key);
+ }
+
+ Node *erase(Node *node)
+ {
+ return (Node*)pj_rbtree_erase(&t_, node);
+ }
+
+ unsigned max_height(Node *node=NULL)
+ {
+ return pj_rbtree_max_height(&t_, node);
+ }
+
+ unsigned min_height(Node *node=NULL)
+ {
+ return pj_rbtree_min_height(&t_, node);
+ }
+
+private:
+ pj_rbtree t_;
+};
+
+#endif /* __PJPP_TREE_HPP__ */
+
diff --git a/pjlib/include/pj++/types.hpp b/pjlib/include/pj++/types.hpp index 3155eb02..18a2f52b 100644 --- a/pjlib/include/pj++/types.hpp +++ b/pjlib/include/pj++/types.hpp @@ -1,144 +1,165 @@ -/* $Id$ - */ -#ifndef __PJPP_TYPES_HPP__ -#define __PJPP_TYPES_HPP__ - -#include <pj/types.h> - -class Pj_Pool; -class Pj_Socket ; -class Pj_Lock; - - -// -// PJLIB initializer. -// -class Pjlib -{ -public: - Pjlib() - { - pj_init(); - } -}; - -// -// Class Pj_Object is declared in pool.hpp -// - -// -// Time value wrapper. -// -class Pj_Time_Val : public pj_time_val -{ -public: - Pj_Time_Val() - { - } - - Pj_Time_Val(long init_sec, long init_msec) - { - sec = init_sec; - msec = init_msec; - } - - Pj_Time_Val(const Pj_Time_Val &rhs) - { - sec=rhs.sec; - msec=rhs.msec; - } - - explicit Pj_Time_Val(const pj_time_val &tv) - { - sec = tv.sec; - msec = tv.msec; - } - - long get_sec() const - { - return sec; - } - - long get_msec() const - { - return msec; - } - - void set_sec (long s) - { - sec = s; - } - - void set_msec(long ms) - { - msec = ms; - normalize(); - } - - long to_msec() const - { - return PJ_TIME_VAL_MSEC((*this)); - } - - bool operator == (const Pj_Time_Val &rhs) const - { - return PJ_TIME_VAL_EQ((*this), rhs); - } - - bool operator > (const Pj_Time_Val &rhs) const - { - return PJ_TIME_VAL_GT((*this), rhs); - } - - bool operator >= (const Pj_Time_Val &rhs) const - { - return PJ_TIME_VAL_GTE((*this), rhs); - } - - bool operator < (const Pj_Time_Val &rhs) const - { - return PJ_TIME_VAL_LT((*this), rhs); - } - - bool operator <= (const Pj_Time_Val &rhs) const - { - return PJ_TIME_VAL_LTE((*this), rhs); - } - - Pj_Time_Val & operator = (const Pj_Time_Val &rhs) - { - sec = rhs.sec; - msec = rhs.msec; - return *this; - } - - Pj_Time_Val & operator += (const Pj_Time_Val &rhs) - { - PJ_TIME_VAL_ADD((*this), rhs); - return *this; - } - - Pj_Time_Val & operator -= (const Pj_Time_Val &rhs) - { - PJ_TIME_VAL_SUB((*this), rhs); - return *this; - } - - /* Must include os.hpp to use these, otherwise unresolved in linking */ - inline pj_status_t gettimeofday(); - inline pj_parsed_time decode(); - inline pj_status_t encode(const pj_parsed_time *pt); - inline pj_status_t to_gmt(); - inline pj_status_t to_local(); - - -private: - void normalize() - { - pj_time_val_normalize(this); - } - -}; - -#endif /* __PJPP_TYPES_HPP__ */ - +/* $Id$
+ */
+/*
+ * PJLIB - PJ Foundation Library
+ * (C)2003-2005 Benny Prijono <bennylp@bulukucing.org>
+ *
+ * Author:
+ * Benny Prijono <bennylp@bulukucing.org>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+#ifndef __PJPP_TYPES_HPP__
+#define __PJPP_TYPES_HPP__
+
+#include <pj/types.h>
+
+class Pj_Pool;
+class Pj_Socket ;
+class Pj_Lock;
+
+
+//
+// PJLIB initializer.
+//
+class Pjlib
+{
+public:
+ Pjlib()
+ {
+ pj_init();
+ }
+};
+
+//
+// Class Pj_Object is declared in pool.hpp
+//
+
+//
+// Time value wrapper.
+//
+class Pj_Time_Val : public pj_time_val
+{
+public:
+ Pj_Time_Val()
+ {
+ }
+
+ Pj_Time_Val(long init_sec, long init_msec)
+ {
+ sec = init_sec;
+ msec = init_msec;
+ }
+
+ Pj_Time_Val(const Pj_Time_Val &rhs)
+ {
+ sec=rhs.sec;
+ msec=rhs.msec;
+ }
+
+ explicit Pj_Time_Val(const pj_time_val &tv)
+ {
+ sec = tv.sec;
+ msec = tv.msec;
+ }
+
+ long get_sec() const
+ {
+ return sec;
+ }
+
+ long get_msec() const
+ {
+ return msec;
+ }
+
+ void set_sec (long s)
+ {
+ sec = s;
+ }
+
+ void set_msec(long ms)
+ {
+ msec = ms;
+ normalize();
+ }
+
+ long to_msec() const
+ {
+ return PJ_TIME_VAL_MSEC((*this));
+ }
+
+ bool operator == (const Pj_Time_Val &rhs) const
+ {
+ return PJ_TIME_VAL_EQ((*this), rhs);
+ }
+
+ bool operator > (const Pj_Time_Val &rhs) const
+ {
+ return PJ_TIME_VAL_GT((*this), rhs);
+ }
+
+ bool operator >= (const Pj_Time_Val &rhs) const
+ {
+ return PJ_TIME_VAL_GTE((*this), rhs);
+ }
+
+ bool operator < (const Pj_Time_Val &rhs) const
+ {
+ return PJ_TIME_VAL_LT((*this), rhs);
+ }
+
+ bool operator <= (const Pj_Time_Val &rhs) const
+ {
+ return PJ_TIME_VAL_LTE((*this), rhs);
+ }
+
+ Pj_Time_Val & operator = (const Pj_Time_Val &rhs)
+ {
+ sec = rhs.sec;
+ msec = rhs.msec;
+ return *this;
+ }
+
+ Pj_Time_Val & operator += (const Pj_Time_Val &rhs)
+ {
+ PJ_TIME_VAL_ADD((*this), rhs);
+ return *this;
+ }
+
+ Pj_Time_Val & operator -= (const Pj_Time_Val &rhs)
+ {
+ PJ_TIME_VAL_SUB((*this), rhs);
+ return *this;
+ }
+
+ /* Must include os.hpp to use these, otherwise unresolved in linking */
+ inline pj_status_t gettimeofday();
+ inline pj_parsed_time decode();
+ inline pj_status_t encode(const pj_parsed_time *pt);
+ inline pj_status_t to_gmt();
+ inline pj_status_t to_local();
+
+
+private:
+ void normalize()
+ {
+ pj_time_val_normalize(this);
+ }
+
+};
+
+#endif /* __PJPP_TYPES_HPP__ */
+
|