# include "wx/wx.h"
#endif
-# include "wx/socket.h"
-# include "wx/url.h"
-# include "wx/protocol/http.h"
-# include "wx/progdlg.h"
+#include "wx/socket.h"
+#include "wx/url.h"
+#include "wx/protocol/http.h"
+#include "wx/progdlg.h"
// --------------------------------------------------------------------------
// resources
void OnTest3(wxCommandEvent& event);
void OnCloseConnection(wxCommandEvent& event);
void OnSocketEvent(wxSocketEvent& event);
+ void OnDatagram(wxCommandEvent& event);
// convenience functions
void UpdateStatusBar();
wxTextCtrl *m_text;
wxMenu *m_menuFile;
wxMenu *m_menuSocket;
+ wxMenu *m_menuDatagramSocket;
wxMenuBar *m_menuBar;
bool m_busy;
CLIENT_TEST2,
CLIENT_TEST3,
CLIENT_CLOSE,
+ CLIENT_DGRAM,
// id for socket
SOCKET_ID
EVT_MENU(CLIENT_TEST2, MyFrame::OnTest2)
EVT_MENU(CLIENT_TEST3, MyFrame::OnTest3)
EVT_MENU(CLIENT_CLOSE, MyFrame::OnCloseConnection)
+ EVT_MENU(CLIENT_DGRAM, MyFrame::OnDatagram)
EVT_SOCKET(SOCKET_ID, MyFrame::OnSocketEvent)
END_EVENT_TABLE()
m_menuSocket->AppendSeparator();
m_menuSocket->Append(CLIENT_CLOSE, _T("&Close session"), _T("Close connection"));
+ m_menuDatagramSocket = new wxMenu();
+ m_menuDatagramSocket->Append(CLIENT_DGRAM, _T("Send Datagram"), _("Test UDP sockets"));
+
// Append menus to the menubar
m_menuBar = new wxMenuBar();
m_menuBar->Append(m_menuFile, _T("&File"));
m_menuBar->Append(m_menuSocket, _T("&Socket"));
+ m_menuBar->Append(m_menuDatagramSocket, _T("&DatagramSocket"));
SetMenuBar(m_menuBar);
// Status bar
// Non-blocking connect
m_text->AppendText(_T("Trying to connect (timeout = 10 sec) ...\n"));
- m_sock->Connect(addr, FALSE);
- m_sock->WaitOnConnect(10);
+ m_sock->Connect(addr, TRUE);
+// m_sock->WaitOnConnect(10);
if (m_sock->IsConnected())
m_text->AppendText(_T("Succeeded ! Connection established\n"));
void MyFrame::OnTest1(wxCommandEvent& WXUNUSED(event))
{
- char *buf1, *buf2;
- char len;
+ char *buf1;
+ char *buf2;
+ unsigned char len;
// Disable socket menu entries (exception: Close Session)
m_busy = TRUE;
// Send some data and read it back. We know the size of the
// buffer, so we can specify the exact number of bytes to be
- // sent or received and use the WAITALL flag. Also, we have
- // disabled menu entries which could interfere with the test,
- // so we can safely avoid the BLOCK (formerly SPEED) flag.
+ // sent or received and use the wxSOCKET_WAITALL flag. Also,
+ // we have disabled menu entries which could interfere with
+ // the test, so we can safely avoid the wxSOCKET_BLOCK flag.
//
// First we send a byte with the length of the string, then
// we send the string itself (do NOT try to send any integral
- // value larger than a byte "as is" acrosss the network, or
+ // value larger than a byte "as is" across the network, or
// you might be in trouble! Ever heard about big and little
// endian computers?)
//
m_sock->SetFlags(wxSOCKET_WAITALL);
- buf1 = _T("Test string (less than 127 chars!)");
+ buf1 = _T("Test string (less than 256 chars!)");
len = wxStrlen(buf1) + 1;
buf2 = new char[len];
m_text->AppendText(_T("Sending a test buffer to the server ..."));
- m_sock->Write(&len, 1);
+ m_sock->Write((char *)&len, 1);
m_sock->Write(buf1, len);
m_text->AppendText(m_sock->Error() ? _T("failed !\n") : _T("done\n"));
msg1 = (char *)s.c_str();
len = wxStrlen(msg1) + 1;
- msg2 = (char *)malloc(len);
+ msg2 = new char[len];
m_text->AppendText(_T("Sending the string with WriteMsg ..."));
m_sock->WriteMsg(msg1, len);
m_text->AppendText(_T("=== Test 2 ends ===\n"));
- free(msg2);
+ delete[] msg2;
m_busy = FALSE;
UpdateStatusBar();
}
void MyFrame::OnTest3(wxCommandEvent& WXUNUSED(event))
{
+ char *buf1;
+ char *buf2;
+ unsigned char len;
+
+ // Disable socket menu entries (exception: Close Session)
+ m_busy = TRUE;
+ UpdateStatusBar();
+
m_text->AppendText(_T("\n=== Test 3 begins ===\n"));
- m_text->AppendText(_T("Test 3 not implemented\n"));
+
+ // Tell the server which test we are running
+ char c = 0xDE;
+ m_sock->Write(&c, 1);
+
+ // This test also is similar to the first one but it sends a
+ // large buffer so that wxSocket is actually forced to split
+ // it into pieces and take care of sending everything before
+ // returning.
+ //
+ m_sock->SetFlags(wxSOCKET_WAITALL);
+
+ // Note that len is in kbytes here!
+ len = 32;
+ buf1 = new char[len * 1024];
+ buf2 = new char[len * 1024];
+
+ for (int i = 0; i < len * 1024; i ++)
+ buf1[i] = (char)(i % 256);
+
+ m_text->AppendText(_T("Sending a large buffer (32K) to the server ..."));
+ m_sock->Write((char *)&len, 1);
+ m_sock->Write(buf1, len * 1024);
+ m_text->AppendText(m_sock->Error() ? _T("failed !\n") : _T("done\n"));
+
+ m_text->AppendText(_T("Receiving the buffer back from server ..."));
+ m_sock->Read(buf2, len * 1024);
+ m_text->AppendText(m_sock->Error() ? _T("failed !\n") : _T("done\n"));
+
+ m_text->AppendText(_T("Comparing the two buffers ..."));
+ if (memcmp(buf1, buf2, len) != 0)
+ {
+ m_text->AppendText(_T("failed!\n"));
+ m_text->AppendText(_T("Test 3 failed !\n"));
+ }
+ else
+ {
+ m_text->AppendText(_T("done\n"));
+ m_text->AppendText(_T("Test 3 passed !\n"));
+ }
m_text->AppendText(_T("=== Test 3 ends ===\n"));
+
+ delete[] buf2;
+ m_busy = FALSE;
+ UpdateStatusBar();
}
void MyFrame::OnCloseConnection(wxCommandEvent& WXUNUSED(event))
UpdateStatusBar();
}
+void MyFrame::OnDatagram(wxCommandEvent& WXUNUSED(event))
+{
+}
+
void MyFrame::OnSocketEvent(wxSocketEvent& event)
{
wxString s = _T("OnSocketEvent: ");
IMPLEMENT_APP(MyApp)
-// To append sockets for delayed deletion
-extern wxList wxPendingDelete;
+// To append sockets for delayed deletion [XXX: this should be removed]
+extern WXDLLEXPORT wxList wxPendingDelete;
// ==========================================================================
wxPoint(0, 0), m_panel->GetClientSize(),
wxTE_MULTILINE | wxTE_READONLY);
- // Create the socket
+ // Create the socket - defaults to localhost:0
wxIPV4address addr;
addr.Service(3000);
- addr.LocalHost();
m_server = new wxSocketServer(addr);
m_server->SetEventHandler(*this, SERVER_ID);
// Receive data from socket and send it back. We will first
// get a byte with the buffer size, so we can specify the
- // exact size and use the WAITALL flag. Also, we disabled
- // input events so we won't have unwanted reentrance. This
- // way we can avoid the infamous BLOCK (formerly SPEED) flag.
+ // exact size and use the wxSOCKET_WAITALL flag. Also, we
+ // disabled input events so we won't have unwanted reentrance.
+ // This way we can avoid the infamous wxSOCKET_BLOCK flag.
//
sock->SetFlags(wxSOCKET_WAITALL);
sock->Read((char *)&len, 1);
- buf = (char *)malloc(len);
+ buf = new char[len];
sock->Read(buf, len);
sock->Write(buf, len);
- free(buf);
+ delete[] buf;
m_text->AppendText(_T("Test 1 ends\n"));
}
#define MAX_MSG_SIZE 10000
wxString s;
- char *buf = (char *)malloc(MAX_MSG_SIZE);
+ char *buf = new char[MAX_MSG_SIZE];
wxUint32 len;
m_text->AppendText(_T("Test 2 begins\n"));
m_text->AppendText(s);
sock->WriteMsg(buf, len);
- free(buf);
+ delete[] buf;
m_text->AppendText(_T("Test 2 ends\n"));
void MyFrame::Test3(wxSocketBase *sock)
{
+ unsigned char len;
+ char *buf;
+
m_text->AppendText(_T("Test 3 begins\n"));
- m_text->AppendText(_T("(not implemented)\n"));
+
+ // This test is similar to the first one, but the len is
+ // expressed in kbytes - this tests large data transfers.
+ //
+ sock->SetFlags(wxSOCKET_WAITALL);
+
+ sock->Read((char *)&len, 1);
+ buf = new char[len * 1024];
+ sock->Read(buf, len * 1024);
+ sock->Write(buf, len * 1024);
+ delete[] buf;
+
m_text->AppendText(_T("Test 3 ends\n"));
}