]> git.saurik.com Git - wxWidgets.git/commitdiff
* prgodlgg.h: Update() use wxString instead of 'char *'
authorGuilhem Lavaux <lavaux@easynet.fr>
Mon, 17 May 1999 18:10:57 +0000 (18:10 +0000)
committerGuilhem Lavaux <lavaux@easynet.fr>
Mon, 17 May 1999 18:10:57 +0000 (18:10 +0000)
* wxThread: fixes (all should work fluently now)
* wxSocket: it is at last usable on my computer
     GTK/GLIB problem : reenabling the idle event propagation causes very
     strange problem (Instruction pointer/memory)

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@2490 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

include/wx/generic/progdlgg.h
include/wx/sckint.h
samples/wxsocket/client.cpp
samples/wxsocket/server.cpp
setup/setup.hin
src/common/event.cpp
src/common/sckint.cpp
src/common/socket.cpp
src/common/wincmn.cpp
src/generic/progdlgg.cpp
src/unix/threadpsx.cpp

index 2401275d14d9a0333fa1eeb588e3b571896b4d50..27b5fffe4f9de89cdf86a0b5e320057c024e2b3b 100644 (file)
@@ -53,7 +53,7 @@ public:
        @param newmsg if used, new message to display
        @returns true if ABORT button has not been pressed
    */
-   bool Update(int value = -1, const char *newmsg = NULL);
+   bool Update(int value = -1, const wxString& newmsg = "");
 
    /** Can be called to continue after the cancel button has been pressed, but
        the program decided to continue the operation (e.g., user didn't
index 8d90c4b133e289cb269ef3141435ab13cf664ae9..0a3ca5b5e576d1432085b790693ec92f90ea839c 100644 (file)
@@ -118,6 +118,7 @@ class wxSocketInternal {
   void ReleaseFD();
 
   int GetFD() { return m_fd; }
+  void SetFD(int fd) { m_fd = fd; }
   
   void ResumeWaiter();
   void StopWaiter();
index bbda2d7525fff394986931175c304551c7ca791a..ffb17c4de8d4356b2e2aa5c2c4c3947201ef391c 100644 (file)
@@ -137,7 +137,7 @@ MyFrame::MyFrame():
   wxSocketHandler::Master();
 
   sock = new MyClient();
-  sock->SetFlags(wxSocketBase::WAITALL);
+  sock->SetFlags((wxSocketBase::wxSockFlags) (wxSocketBase::WAITALL | wxSocketBase::SPEED));
   wxSocketHandler::Master().Register(sock);
   sock->frame = this;
   sock->SetNotify(wxSocketBase::REQ_LOST);
@@ -162,8 +162,11 @@ void MyFrame::OnExecOpenConnection(wxCommandEvent& WXUNUSED(evt))
   if (sock->IsConnected())
     sock->Close();
 
+/*
   wxString hname = wxGetTextFromUser("Enter the address of the wxSocket Sample Server", 
                                   "Connect ...", "localhost");
+*/
+  wxString hname = "localhost";
   addr.Hostname(hname);
   addr.Service(3000);
   sock->SetNotify(0);
index 45825d88fbd1018d358bd6fddce9a86c2b2d6cfb..727c8e63a8bf2429732a8706170ff2f4f8ad0ff2 100644 (file)
@@ -132,7 +132,7 @@ void MyFrame::OnSockRequestServer(wxSocketEvent& evt)
   if (sock2 == NULL)
     return;
 
-  sock2->SetFlags(wxSocketBase::NONE);
+  sock2->SetFlags(wxSocketBase::SPEED);
   sock2->Notify(TRUE);
   sock2->SetEventHandler(*this, SKDEMO_SOCKET);
   server->SetNotify(wxSocketBase::REQ_ACCEPT);
@@ -154,6 +154,7 @@ MyFrame::MyFrame(wxFrame *frame):
   wxSocketHandler::Master().Register(sock);
   sock->SetNotify(wxSocketBase::REQ_ACCEPT);
   sock->SetEventHandler(*this, SKDEMO_SOCKET_SERV);
+  sock->SetFlags(wxSocketBase::SPEED);
   sock->Notify(TRUE);
   nb_clients = 0;
 
index 8af73a69d99d366ac550006f5ddf9f51731089d2..5a7f96a985b79d90be2a6259a82c7008c9c98c10 100644 (file)
 /* Define if you have all functions to set thread priority */
 #undef HAVE_THREAD_PRIORITY_FUNCTIONS
 
+/* Define if you can specify exit functions to a thread */
+#undef HAVE_THREAD_CLEANUP_FUNCTIONS
+
 /* Define if your system has its own `getloadavg' function.  */
 #undef HAVE_GETLOADAVG
 
index 00c121814f54fc23d18a9c7fc3f1d94ee0674a4f..3db1b841b362a3ce96759cbe0f48a7e0323c9623 100644 (file)
@@ -527,7 +527,6 @@ bool wxEvtHandler::ProcessThreadEvent(wxEvent& event)
     wxEvent *event_main;
     wxCriticalSectionLocker locker(*m_eventsLocker);
 
-
     // check that we are really in a child thread
     wxASSERT( !wxThread::IsMain() );
 
@@ -543,7 +542,7 @@ bool wxEvtHandler::ProcessThreadEvent(wxEvent& event)
     wxPendingEventsLocker->Leave();
 
 #ifdef __WXGTK__
-    if (g_isIdle) wxapp_install_idle_handler();
+//    if (g_isIdle) wxapp_install_idle_handler();
 #endif
 
     return TRUE;
index de4284bd35675ca1bad126569f8376cdc548eafe..925ffebf7a2d79463f63c8e4d7cb97f619e51b9a 100644 (file)
@@ -1,10 +1,9 @@
 ///////////////////////////////////////////////////////////////////////////////
-// Name:       socket.cpp
-// Purpose:    Socket handler classes
-// Authors:    Guilhem Lavaux (completely rewritten from a basic API of Andrew
-//             Davidson(1995) in wxWeb)
-// Created:    April 1997
-// Updated:    April 1999
+// Name:       sckint.cpp
+// Purpose:    Socket internal classes
+// Authors:    Guilhem Lavaux
+// Created:    April 1999
+// Updated:
 // Copyright:  (C) 1999, 1998, 1997, Guilhem Lavaux
 // RCS_ID:     $Id$
 // License:    see wxWindows license
@@ -87,7 +86,8 @@
 #if wxUSE_THREADS
 SocketWaiter::SocketWaiter(wxSocketBase *socket,
                                 wxSocketInternal *internal)
-  : m_socket(socket), m_internal(internal), m_fd(internal->GetFD())
+  : wxThread(), 
+    m_socket(socket), m_internal(internal), m_fd(internal->GetFD())
 {
 }
 
@@ -110,9 +110,9 @@ void SocketWaiter::ProcessReadEvent()
   
   // Else, no error => there is something to be read else
   // we've lost the connection.
-  if (ret > 0)
+  if (ret > 0) {
     m_socket->OnRequest(wxSocketBase::EVT_READ);
-  else {
+  else {
     m_socket->OnRequest(wxSocketBase::EVT_LOST);
     Exit(NULL);
   }
@@ -140,14 +140,14 @@ void *SocketWaiter::Entry()
 
     FD_ZERO(&sockrd_set);
     FD_ZERO(&sockwr_set);
-    
+
     if ((m_socket->NeededReq() & READ_MASK) != 0)
       FD_SET(m_fd, &sockrd_set);
     if ((m_socket->NeededReq() & WRITE_MASK) != 0)
       FD_SET(m_fd, &sockwr_set);
 
     m_internal->AcquireFD();
-    ret = select(FD_SETSIZE, &sockrd_set, &sockwr_set, NULL, &tv);
+    ret = select(m_fd+1, &sockrd_set, &sockwr_set, NULL, &tv);
     m_internal->ReleaseFD();
 
     if (FD_ISSET(m_fd, &sockrd_set))
@@ -180,7 +180,8 @@ void *SocketWaiter::Entry()
 
 SocketRequester::SocketRequester(wxSocketBase *socket,
                                 wxSocketInternal *internal)
-  : m_socket(socket), m_internal(internal), m_fd(internal->GetFD())
+  : wxThread(),
+    m_socket(socket), m_internal(internal), m_fd(internal->GetFD())
 {
 }
 
@@ -206,7 +207,7 @@ bool SocketRequester::WaitFor(wxSocketBase::wxRequestNotify req, int millisec)
   FD_SET(m_fd, &sockwr_set);
   
   m_internal->AcquireFD();
-  ret = select(FD_SETSIZE, &sockrd_set, &sockwr_set, NULL, &tv);
+  ret = select(m_fd+1, &sockrd_set, &sockwr_set, NULL, &tv);
   m_internal->ReleaseFD();
 
   return (ret != 0);
@@ -253,6 +254,11 @@ void SocketRequester::ProcessWriteEvent(SockRequest *req)
   int ret;
   size_t len;
 
+  if (!WaitFor(wxSocketBase::REQ_WRITE, req->timeout)) {
+    m_internal->EndRequest(req);
+    return;
+  }
+
   m_internal->AcquireFD();
   ret = send(m_fd, req->buffer, req->size, 0);
   m_internal->ReleaseFD();
@@ -287,13 +293,15 @@ void *SocketRequester::Entry()
 {
   SockRequest *req;
 
+  m_internal->m_request_locker.Lock();
   while (1) {
     // Wait for a new request or a destroy message.
     req = m_internal->WaitForReq();
     m_internal->m_end_requester.Lock();
-    if (TestDestroy() || req == NULL) {
+    if (req == NULL) {
       m_internal->m_invalid_requester = TRUE;
       m_internal->m_end_requester.Unlock();
+      m_internal->m_request_locker.Unlock();
       return NULL;
     }
     m_internal->m_end_requester.Unlock();
@@ -328,7 +336,6 @@ wxSocketInternal::wxSocketInternal(wxSocketBase *socket)
   m_thread_requester = NULL;
   m_thread_waiter = NULL;
   m_invalid_requester = TRUE;
-  m_request_locker.Lock();
 #endif
 }
 
@@ -339,7 +346,6 @@ wxSocketInternal::~wxSocketInternal()
   wxASSERT(m_thread_requester == NULL);
   StopWaiter();
   wxASSERT(m_thread_waiter == NULL);
-  m_request_locker.Unlock();
 #endif
 }
 
@@ -354,7 +360,7 @@ SockRequest *wxSocketInternal::WaitForReq()
 
   node = m_requests.First();
   if (node == NULL) {
-    m_socket_cond.Wait(m_request_locker, 1, 0);
+    m_socket_cond.Wait(m_request_locker, 10, 0);
 
     node = m_requests.First();
     if (node == NULL)
@@ -400,44 +406,46 @@ void wxSocketInternal::ResumeRequester()
 #if wxUSE_THREADS
   wxThreadError err;
 
-  wxASSERT(m_thread_requester == NULL);
+  wxASSERT(m_thread_requester == NULL || m_invalid_requester);
 
   m_end_requester.Lock();
   if (m_invalid_requester) {
-    delete m_thread_requester;
+    if (m_thread_requester != NULL)
+      delete m_thread_requester;
+    m_invalid_requester = FALSE;
+  }
+  m_end_requester.Unlock();
 
-    m_thread_requester = new SocketRequester(m_socket, this);
-    m_thread_requester->m_fd = m_socket->m_fd;
+  m_thread_requester = new SocketRequester(m_socket, this);
 
-    err = m_thread_requester->Create();
-    wxASSERT(err == wxTHREAD_NO_ERROR);
+  err = m_thread_requester->Create();
+  wxASSERT(err == wxTHREAD_NO_ERROR);
 
-    err = m_thread_requester->Run();
-    wxASSERT(err == wxTHREAD_NO_ERROR);
+  err = m_thread_requester->Run();
+  wxASSERT(err == wxTHREAD_NO_ERROR);
 
-    m_invalid_requester = FALSE;
-  }
-  m_end_requester.Unlock();
 #endif
 }
 
 void wxSocketInternal::StopRequester()
 {
 #if wxUSE_THREADS
+  m_end_requester.Lock();
   if (m_invalid_requester) {
+    m_end_requester.Unlock();
     delete m_thread_requester;
     m_thread_requester = NULL;
     m_invalid_requester = FALSE;
     return;
   }
+  m_end_requester.Unlock();
 
   wxASSERT(m_thread_requester != NULL);
 
   m_socket_locker.Lock();
 
   // Send a signal to the requester.
-  if (m_requests.Number() == 0)
-    m_socket_cond.Signal();
+  m_socket_cond.Signal();
 
   m_socket_locker.Unlock();
 
@@ -458,7 +466,6 @@ void wxSocketInternal::ResumeWaiter()
     return;
 
   m_thread_waiter = new SocketWaiter(m_socket, this);
-  m_thread_waiter->m_fd = m_socket->m_fd;
 
   err = m_thread_waiter->Create();
   wxASSERT(err == wxTHREAD_NO_ERROR);
@@ -487,9 +494,14 @@ void wxSocketInternal::StopWaiter()
 void wxSocketInternal::QueueRequest(SockRequest *request, bool async)
 {
 #if wxUSE_THREADS
+/*
+  if (m_invalid_requester)
+    ResumeRequester();
+*/
+  m_thread_requester = new SocketRequester(m_socket, this);
+
+/*
   if (async) {
-    if (m_thread_requester == NULL)
-      ResumeRequester();
 
     m_request_locker.Lock();
     request->done = FALSE;
@@ -510,6 +522,7 @@ void wxSocketInternal::QueueRequest(SockRequest *request, bool async)
         }
     }
   } else {
+*/
     m_request_locker.Lock();
 
     if ((request->type & wxSocketBase::REQ_WAIT) != 0) {
@@ -530,7 +543,9 @@ void wxSocketInternal::QueueRequest(SockRequest *request, bool async)
     }
     request->done = TRUE;
     m_request_locker.Unlock();
-  }
+//  }
+  delete m_thread_requester;
+  m_thread_requester = NULL;
 #endif
 }
 
index 2372865175a5af539076b86c05773be378eb93e7..bbfdb4e5d26ce2ec0f02460277c84b70b407ae55 100644 (file)
@@ -736,6 +736,8 @@ wxSocketServer::wxSocketServer(wxSockAddress& addr_man,
     return;
   }
 
+  m_internal->SetFD(m_fd);
+
   Notify(TRUE);
 }
 
@@ -767,6 +769,8 @@ bool wxSocketServer::AcceptWith(wxSocketBase& sock)
   sock.m_fd = fd2;
   sock.m_connected = TRUE;
 
+  sock.m_internal->SetFD(fd2);
+
   sock.m_internal->ResumeWaiter();
 
   return TRUE;
@@ -849,6 +853,8 @@ bool wxSocketClient::Connect(wxSockAddress& addr_man, bool WXUNUSED(wait) )
   if (connect(m_fd, remote, len) != 0)
     return FALSE;
 
+  m_internal->SetFD(m_fd);
+
   // Enables bg events.
   // ------------------
   Notify(TRUE);
index 2fead4a77e5cec2d2bf84b12ae819c63bbb361ad..ac18d99f8622d99423063d3d67af5bccfe9f1522 100644 (file)
@@ -179,7 +179,7 @@ wxWindowBase::~wxWindowBase()
     // we weren't a dialog class
     wxTopLevelWindows.DeleteObject(this);
 
-    wxASSERT_MSG( GetChildren().GetCount() == 0, "children not destroyed" );
+    wxASSERT_MSG( GetChildren().GetCount() == 0, _T("children not destroyed") );
 
     if ( m_windowValidator )
         delete m_windowValidator;
@@ -253,12 +253,12 @@ bool wxWindowBase::DestroyChildren()
 
         wxWindow *child = node->GetData();
 
-        wxASSERT_MSG( child, "children list contains empty nodes" );
+        wxASSERT_MSG( child, _T("children list contains empty nodes") );
 
         delete child;
 
         wxASSERT_MSG( !GetChildren().Find(child),
-                      "child didn't remove itself using RemoveChild()" );
+                      _T("child didn't remove itself using RemoveChild()") );
     }
 
     return TRUE;
@@ -575,7 +575,7 @@ wxWindow *wxWindowBase::FindWindow( const wxString& name )
 
 void wxWindowBase::MakeModal(bool WXUNUSED(modal))
 {
-    wxFAIL_MSG("TODO");
+    wxFAIL_MSG(_T("TODO"));
 }
 
 bool wxWindowBase::Validate()
index c156b612b034e9bd72e1635ce201745d7d9d44a7..c43494211f21aa720e6fbdf57c3da22f24e553ba 100644 (file)
@@ -117,12 +117,12 @@ wxProgressDialog::wxProgressDialog(wxString const &title,
 
 
 bool
-wxProgressDialog::Update(int value, const char *newmsg)
+wxProgressDialog::Update(int value, const wxString& newmsg)
 {
    wxASSERT(value == -1 || m_gauge);
    if(m_gauge)
       m_gauge->SetValue(value);
-   if(newmsg)
+   if(!newmsg.IsNull())
       m_msg->SetLabel(newmsg);
    wxYield();
    return m_state != Canceled;
index 8548b1801428a2d0873f70f77702859385a05292..a1764a30c38cc1647896f21ddd50a4324f88ceb1 100644 (file)
@@ -305,20 +305,19 @@ void *wxThreadInternal::PthreadStart(void *ptr)
     }
 #if HAVE_THREAD_CLEANUP_FUNCTIONS
     // Install the cleanup handler.
-    pthread_cleanup_push(wxThreadInternal::PthreadCleanup, ptr);
+//    pthread_cleanup_push(wxThreadInternal::PthreadCleanup, ptr);
 #endif
 
     // wait for the condition to be signaled from Run()
     // mutex state: currently locked by the thread which created us
     pthread->m_cond.Wait(pthread->m_mutex);
-
     // mutex state: locked again on exit of Wait()
 
     // call the main entry
     status = thread->Entry();
 
 #if HAVE_THREAD_CLEANUP_FUNCTIONS
-    pthread_cleanup_pop(FALSE);
+//    pthread_cleanup_pop(FALSE);
 #endif
 
     // terminate the thread
@@ -360,6 +359,9 @@ wxThreadInternal::wxThreadInternal()
     // unlocked in the very end
     m_mutex.Lock();
  
+    // this mutex is used by wxThreadInternal::Wait() and by
+    // wxThreadInternal::SignalExit(). We don't use m_mutex because of a
+    // possible deadlock in either Wait() or SignalExit().
     m_end_mutex.Lock();
 
     // this mutex is used in Pause()/Resume() and is also locked all the time
@@ -374,6 +376,8 @@ wxThreadInternal::~wxThreadInternal()
 
     // note that m_mutex will be unlocked by the thread which waits for our
     // termination
+
+    // m_end_mutex can be unlocked here.
     m_end_mutex.Unlock();
 }
 
@@ -406,16 +410,17 @@ void wxThreadInternal::Wait()
     if ( wxThread::IsMain() )
         wxMutexGuiLeave();
 
-    printf("Entering wait ...\n");
     // entering Wait() releases the mutex thus allowing SignalExit() to acquire
     // it and to signal us its termination
     m_cond.Wait(m_end_mutex);
-    printf("Exiting wait ...\n");
 
     // mutex is still in the locked state - relocked on exit from Wait(), so
     // unlock it - we don't need it any more, the thread has already terminated
     m_end_mutex.Unlock();
 
+    // After that, we wait for the real end of the other thread.
+    pthread_join(GetId(), NULL);
+
     // reacquire GUI mutex
     if ( wxThread::IsMain() )
         wxMutexGuiEnter();
@@ -423,21 +428,18 @@ void wxThreadInternal::Wait()
 
 void wxThreadInternal::SignalExit()
 {
-    printf("SignalExit\n");
     // GL: Unlock mutexSuspend here.
     m_mutexSuspend.Unlock();
 
     // as mutex is currently locked, this will block until some other thread
     // (normally the same which created this one) unlocks it by entering Wait()
     m_end_mutex.Lock();
-    printf("Mutex acquired\n");
 
     // wake up all the threads waiting for our termination
     m_cond.Broadcast();
 
     // after this call mutex will be finally unlocked
     m_end_mutex.Unlock();
-    printf("Mutex unacquired\n");
 }
 
 void wxThreadInternal::Pause()
@@ -664,11 +666,12 @@ wxThread::ExitCode wxThread::Delete()
 {
     m_critsect.Enter();
     wxThreadState state = p_internal->GetState();
-    m_critsect.Leave();
 
     // ask the thread to stop
     p_internal->SetCancelFlag();
 
+    m_critsect.Leave();
+
     switch ( state )
     {
         case STATE_NEW:
@@ -716,20 +719,16 @@ void wxThread::Exit(void *status)
 {
     // first call user-level clean up code
     OnExit();
-    printf(" ... OnExit()\n");
 
     // next wake up the threads waiting for us (OTOH, this function won't return
     // until someone waited for us!)
     p_internal->SignalExit();
-    printf(" ... SignalExit()\n");
 
     p_internal->SetState(STATE_EXITED);
-    printf(" ... SetState()\n");
 
     // delete both C++ thread object and terminate the OS thread object
     // GL: This is very ugly and buggy ...
 //    delete this;
-    printf(" ... Exit\n");
     pthread_exit(status);
 }