// $Id$ // Test the persistence capabilities of when configured // for mmap-based shared memory management. #include "ace/Malloc.h" #include "ace/streams.h" ACE_RCSID(Shared_Malloc, test_persistence, "$Id$") typedef ACE_Malloc MALLOC; typedef ACE_Malloc_Iterator MALLOC_ITERATOR; // Shared memory manager. static MALLOC *shmem_allocator = 0; // Backing store name. static const char *backing_store = ACE_DEFAULT_BACKING_STORE; class Employee { public: Employee (void): name_ (0), id_ (0) {} Employee (const char *name, u_long id) : id_ (id) { size_t len = ACE_OS::strlen (name) + 1; this->name_ = ACE_reinterpret_cast (char *, shmem_allocator->malloc (len)); ACE_OS::strcpy (this->name_, name); } ~Employee (void) { shmem_allocator->free (this->name_); } const char *name (void) const { return this->name_; } void name (const char *name) { if (this->name_) shmem_allocator->free (this->name_); size_t len = ACE_OS::strlen (name) + 1; this->name_ = ACE_reinterpret_cast (char *, shmem_allocator->malloc (len)); ACE_OS::strcpy (this->name_, name); } u_long id (void) const { return id_; } void id (u_long id) { id_ = id; } void *operator new (size_t) { return shmem_allocator->malloc (sizeof (Employee)); } void operator delete (void *pointer) { shmem_allocator->free (pointer); } private: char *name_; // Employee name. u_long id_; // Employee ID. }; class GUI_Handler { public: GUI_Handler (void) { menu (); } ~GUI_Handler (void) { MALLOC::MEMORY_POOL &pool = shmem_allocator->memory_pool (); pool.sync (); } int service(void) { char option[BUFSIZ]; char buf1[BUFSIZ]; char buf2[BUFSIZ]; if (::scanf ("%s", option) <= 0) { ACE_ERROR ((LM_ERROR, "try again\n")); return 0; } int result = 0; switch (option[0]) { case 'I' : case 'i' : if (::scanf ("%s %s", buf1, buf2) <= 0) break; result = insert_employee (buf1, ACE_OS::atoi (buf2)); break; case 'F' : case 'f' : if (::scanf ("%s", buf1) <= 0) break; result = find_employee (buf1); break; case 'D' : case 'd' : if (::scanf ("%s", buf1) <= 0) break; result = delete_employee (buf1); break; case 'L' : case 'l' : result = list_employees (); break; case 'Q' : case 'q' : return -1; ACE_NOTREACHED(break); default : cout << "unrecognized command" << endl; } if (result == 0) cout << "Last operation was successful!!" << endl; else cout << "Last operation failed!! " << endl; menu (); return 0; } void menu(void) { cout << endl; cout << "\t************************** " << endl; cout << "\tThe employee database menu " << endl; cout << endl; cout << "\t Insert " << endl; cout << "\t Delete " << endl; cout << "\t Find " << endl; cout << endl; cout << "\t List all employees " << endl; cout << endl; cout << "\t Quit " << endl; cout << "\t************************** " << endl; } private: int insert_employee (const char *name, u_long id); int find_employee (const char *name); int list_employees (void); int delete_employee (const char *name); }; int GUI_Handler::insert_employee (const char *name, u_long id) { if (find_employee (name) == 0) ACE_ERROR_RETURN ((LM_ERROR, "Employee already exists\n"), -1); Employee *new_employee = 0; ACE_NEW_RETURN (new_employee, Employee (name, id), -1); if (shmem_allocator->bind (name, new_employee) == -1) ACE_ERROR_RETURN ((LM_ERROR, "bind failed\n"), -1); return 0; } int GUI_Handler::find_employee (const char *name) { void *temp; if (shmem_allocator->find (name, temp) == 0) { Employee *employee = ACE_reinterpret_cast (Employee *, temp); ACE_DEBUG ((LM_DEBUG, "The following employee was found.......\n\n")); ACE_DEBUG ((LM_DEBUG, "Employee name: %s\nEmployee id: %d\n", employee->name (), employee->id ())); return 0; } return -1; } int GUI_Handler::list_employees (void) { MALLOC_ITERATOR iterator (*shmem_allocator); ACE_DEBUG ((LM_DEBUG, "The following employees were found.......\n\n")); for (void *temp = 0; iterator.next (temp) != 0; iterator.advance ()) { Employee *employee = ACE_reinterpret_cast (Employee *, temp); ACE_DEBUG ((LM_DEBUG, "Employee name: %s\nEmployee id: %d\n", employee->name (), employee->id ())); } return 0; } int GUI_Handler::delete_employee (const char *name) { void *temp; if (shmem_allocator->unbind (name, temp) == 0) { Employee *employee = ACE_reinterpret_cast (Employee *, temp); ACE_DEBUG ((LM_DEBUG, "The following employee was found and deleted.......\n\n")); ACE_DEBUG ((LM_DEBUG, "Employee name: %s\nEmployee id: %d\n", employee->name (), employee->id ())); delete employee; return 0; } ACE_DEBUG ((LM_DEBUG, "There is no employee with name %s", name)); return -1; } void parse_args (int argc, char *argv[]) { if (argc > 1); backing_store = argv[1]; } int main (int argc, char *argv[]) { parse_args (argc, argv); ACE_NEW_RETURN (shmem_allocator, MALLOC (backing_store), -1); GUI_Handler handler; for(;;) if (handler.service() == -1) { ACE_DEBUG ((LM_DEBUG, "closing down ....\n")); break; } return 0; } #if defined (ACE_HAS_EXPLICIT_TEMPLATE_INSTANTIATION) // The following instantiation is in ace/System_Time.cpp: // template class ACE_Malloc ; template class ACE_Malloc_Iterator ; #elif defined (ACE_HAS_TEMPLATE_INSTANTIATION_PRAGMA) // The following instantiation is in ace/System_Time.cpp: // #pragma instantiate ACE_Malloc #pragma instantiate ACE_Malloc_Iterator #endif /* ACE_HAS_EXPLICIT_TEMPLATE_INSTANTIATION */