summaryrefslogtreecommitdiff
path: root/support/dktools/WxpqdicFrame.wxc
diff options
context:
space:
mode:
authorNorbert Preining <norbert@preining.info>2019-09-02 13:46:59 +0900
committerNorbert Preining <norbert@preining.info>2019-09-02 13:46:59 +0900
commite0c6872cf40896c7be36b11dcc744620f10adf1d (patch)
tree60335e10d2f4354b0674ec22d7b53f0f8abee672 /support/dktools/WxpqdicFrame.wxc
Initial commit
Diffstat (limited to 'support/dktools/WxpqdicFrame.wxc')
-rw-r--r--support/dktools/WxpqdicFrame.wxc1540
1 files changed, 1540 insertions, 0 deletions
diff --git a/support/dktools/WxpqdicFrame.wxc b/support/dktools/WxpqdicFrame.wxc
new file mode 100644
index 0000000000..9b28dae9ab
--- /dev/null
+++ b/support/dktools/WxpqdicFrame.wxc
@@ -0,0 +1,1540 @@
+%% options
+
+copyright owner = Dirk Krause
+
+copyright year = 2016-xxxx
+
+license = bsd
+
+
+
+%% wx-gui
+
+type = frame
+contents = mainSizer
+icon = wxpqdic_icon
+status bar = 1 sTexts[8]
+menu bar = mbMain
+tool bar = tbMain
+
+[wxMenuBar mbMain]
+contents = menuFile
+contents = menuView
+contents = menuHelp
+
+[wxMenu menuFile]
+text = sTexts[0]
+contents = miFileExit
+
+[wxMenuItem miFileExit]
+id = WxpqdicFrame_Quit
+text = sTexts[1]
+tip = sTexts[2]
+
+[wxMenu menuView]
+text = sTexts[22]
+contents = miViewUpdate
+
+[wxMenuItem miViewUpdate]
+id = WxpqdicFrame_View_Update
+text = sTexts[23]
+tip = sTexts[24]
+
+[wxMenu menuHelp]
+text = sTexts[3]
+contents = miHelpAbout
+contents = miHelpContents
+
+[wxMenuItem miHelpAbout]
+id = WxpqdicFrame_Help_About
+text = sTexts[4]
+tip = sTexts[5]
+
+[wxMenuItem miHelpContents]
+id = WxpqdicFrame_Help_Contents
+text = sTexts[6]
+tip = sTexts[7]
+
+[wxBoxSizer mainSizer]
+direction = horizontal
+contents = $space(10)
+contents = verticalSizer
+contents = $space(10)
+
+[wxBoxSizer verticalSizer]
+direction = vertical
+grow = yes
+proportion = 1
+contents = $space(10)
+contents = contentsSizer
+contents = $space(10)
+
+[wxGridBagSizer contentsSizer]
+grid = 2 2
+contents = lLimit 0 0 1 1 right
+contents = tLimit . +1 1 1
+contents = lUsed +1 0 1 1 right
+contents = tUsed . +1 1 1
+contents = $space(5) +1 0 1 1
+contents = lAccount +1 0 1 1 right
+contents = tAccount . +1 1 1
+contents = $space(5) +1 0 1 1
+contents = lAllowed +1 0 1 1 right
+contents = tAllowed . +1 1 1
+contents = $space(5) +1 0 1 1
+contents = lStatus +1 0 1 2
+
+[wxStaticText lLimit]
+text = sTexts[13]
+
+[wxStaticText tLimit]
+text = sTexts[14]
+
+[wxStaticText lUsed]
+text = sTexts[15]
+
+[wxStaticText tUsed]
+text = sTexts[27]
+
+[wxStaticText lAccount]
+text = sTexts[17]
+
+[wxStaticText tAccount]
+text = sTexts[16]
+
+[wxStaticText lAllowed]
+text = sTexts[18]
+
+[wxStaticText tAllowed]
+text = sTexts[27]
+
+[wxStaticText lStatus]
+text = sTexts[21]
+
+
+[wxToolBar tbMain]
+contents = bUpdate
+contents = bExit
+
+[wxToolBarToolBase bUpdate]
+text = sTexts[25]
+tip = sTexts[24]
+bitmap = xpm_run_conversion
+id = WxpqdicFrame_View_Update
+
+[wxToolBarToolBase bExit]
+text = sTexts[26]
+tip = sTexts[2]
+bitmap = xpm_exit_program
+id = WxpqdicFrame_Quit
+
+
+%% header start
+
+
+
+%% class start
+class WxpqdicFrame : public Dk4WxFrame
+{
+ private:
+
+ /** Event table for frame.
+ */
+ DECLARE_EVENT_TABLE()
+
+ protected:
+
+ /** Buffer for response processing.
+ */
+ char bResponse[32 * sizeof(dk4_um_t)];
+
+ /** Address pair, 0=remote, 1=local.
+ */
+ dk4_sockaddr_storage_t aAddresses[2];
+
+ /** Remote host name as wxChar string.
+ */
+ wxString sHostname;
+
+ /** Queue name as wxChar string.
+ */
+ wxString sQueuename;
+
+ /** User name as wxChar string.
+ */
+ wxString sUsername;
+
+ /** Localized texts.
+ */
+ wxChar const * const *sTexts;
+
+ /** Non-localized texts.
+ */
+ wxChar const * const *sNlWx;
+
+ /** Non-localized texts.
+ */
+ dkChar const * const *sNlDk;
+
+ /** Copy of the command line arguments poiner.
+ */
+ wxChar **copyArgv;
+
+ /* __CHANGE__ 011: Add further member variables.
+ */
+
+ /** Critical section to protect socket and timer.
+ */
+ wxCriticalSection csProtect;
+
+ /** Black color for normal status text.
+ */
+ wxColour cBlack;
+
+ /** Red color for not allowed to print.
+ */
+ wxColour cRed;
+
+ /** Green color for allowed to print.
+ */
+ wxColour cGreen;
+
+ /** Timer for periodic updates.
+ */
+ wxTimer timer;
+
+ /** Error report from socket subsystem initialization.
+ */
+ dk4_er_t sockerr;
+
+ /** Host name to query.
+ */
+ dkChar *pHostname;
+
+ /** Print queue to check.
+ */
+ char *pQueuename;
+
+ /** User name to use in check.
+ */
+ char *pUsername;
+
+ /** Request to send to server.
+ */
+ char *pRequest;
+
+ /** Previous limit value.
+ */
+ dk4_um_t uLimit;
+
+ /** Previous used value.
+ */
+ dk4_um_t uUsed;
+
+ /** Previous account value.
+ */
+ dk4_um_t uAccount;
+
+ /** Length of request.
+ */
+ size_t szRequest;
+
+ /** Size of response buffer.
+ */
+ size_t szResponse;
+
+ /** Time last request was sended.
+ */
+ dk4_time_t tRequestSended;
+
+ /** Update interval in seconds.
+ */
+ long lUpdateInterval;
+
+ /** Timeout interval before complaining about missing response.
+ */
+ long lWaitResponse;
+
+ /** Previous summary value.
+ */
+ int iSummary;
+
+ /** Number of command line arguments.
+ */
+ int copyArgc;
+
+ /** Current state.
+ */
+ int iState;
+
+ /** Socket for data exchange
+ */
+ dk4_socket_t sock;
+
+ /** Port number on remote host.
+ */
+ unsigned short usPortnumber;
+
+ /** Local port number to use.
+ */
+ unsigned short usLocalPort;
+
+ /** Flag: Socket subsystem initialized.
+ */
+ bool bSockInit;
+
+ /** Flag: Remote host uses UTF-8 encoding (user name and queue name).
+ */
+ bool bIsUtf8;
+
+ /** Flag: This idle event is the first one (no idle events before).
+ */
+ bool bFirstIdle;
+
+ /** Flag: All components initialized completely.
+ */
+ bool bIsInitialized;
+
+ /** Flag: This is the first response.
+ */
+ bool bFirstResponse;
+
+%% class end
+
+ public:
+
+ /** Constructor.
+ @param wxid Window ID.
+ @param applicationHelper Application helper object.
+ @param hc Help controller for online help.
+ @param argc Number of command line arguments.
+ @param argv Command line arguments array.
+ @param localizedTexts Localized wxChar texts.
+ @param nlWx Non-localized wxChar texts.
+ @param nlDk Non-localized dkChar texts.
+ @param bSocketsInitialized Flag: Socket subsys initialized.
+ @param psockerr Error report from socket initialization.
+ */
+ WxpqdicFrame(
+ int wxid,
+ Dk4WxApplicationHelper *applicationHelper,
+ Dk4WxHelpController *hc,
+ int argc,
+ wxChar **argv,
+ wxChar const * const *localizedTexts,
+ wxChar const * const *nlWx,
+ dkChar const * const *nlDk,
+ bool bSocketsInitialized,
+ dk4_er_t *psockerr
+ );
+
+ /** Destructor.
+ */
+ ~WxpqdicFrame();
+
+ /** Check whether we can close the window.
+ @param isLast Flag: Last main window to close.
+ */
+ bool
+ CanClose(bool isFinal);
+
+ /** Handler for File/Exit.
+ @param event Event to process.
+ */
+ void
+ OnQuit(wxCommandEvent & event);
+
+ /** Handler for File/Update.
+ @param event Event to process.
+ */
+ void
+ OnRun(wxCommandEvent & event);
+
+ /** Handler for Help/About.
+ @param event Event to process.
+ */
+ void
+ OnAbout(wxCommandEvent & event);
+
+ /** Handler for Help/Contents.
+ @param event Event to process.
+ */
+ void
+ OnHelpContents(wxCommandEvent & event);
+
+ /* __CHANGE__ 008: Remove OnIdle if no idle processing required.
+ */
+ /** Handler for idle events.
+ */
+ void
+ OnIdle(wxIdleEvent & event);
+
+ /* __CHANGE__ 017: Event handlers for further events.
+ */
+
+ /** Handler for timer event.
+ @param event Timer event to process.
+ */
+ void
+ OnTimer(wxTimerEvent & event);
+
+
+ /* __CHANGE__ 014: Add further methods.
+ */
+
+ private:
+
+ /** Attempt to configure.
+ @param perrc Address of error code variable.
+ @return True if configuration failed and the application should
+ exit, false on success.
+ */
+ bool
+ ConfigureAndCheckNeedToClose(int *perrc);
+
+ /** Attempt to receive data, send request again if interval is over.
+ @return True if the windows requires an update, false otherwise.
+ */
+ bool
+ DataExchangeWithServer(void);
+
+ bool
+ RetrieveResponse(void);
+
+ bool
+ ProcessResponse(bool & found);
+
+ bool
+ SendRequest(bool force = false);
+
+};
+
+%% header end
+
+%% module start
+
+#include "wxpqdic.h"
+#include "dk4user.h"
+#include "dk4enc.h"
+#include "dk4strd.h"
+#include "dk4rec.h"
+#include "dk4str8.h"
+#include "dk4strx.h"
+#include "dk4recwx.h"
+#include "dk4maasz.h"
+#include "dk4mai8ddu.h"
+#include "dk4mai8dii.h"
+#include "dk4mao8d.h"
+#include "dk4maowd.h"
+#include "dk4numco.h"
+
+
+#include "exit-program.xpm"
+#include "run-conversion.xpm"
+
+#include "dk4verswx.h"
+
+#if !defined(__WXMSW__)
+#include "dkicon.xpm"
+#endif
+
+
+
+$!trace-include
+
+
+
+/* __CHANGE__ 017: Add further events. */
+/* __CHANGE__ 008: Remove OnIdle if no idle processing required. */
+BEGIN_EVENT_TABLE(WxpqdicFrame, wxFrame)
+ EVT_MENU(WxpqdicFrame_View_Update, WxpqdicFrame::OnRun)
+ EVT_MENU(WxpqdicFrame_Quit, WxpqdicFrame::OnQuit)
+ EVT_MENU(WxpqdicFrame_Help_About, WxpqdicFrame::OnAbout)
+ EVT_MENU(WxpqdicFrame_Help_Contents, WxpqdicFrame::OnHelpContents)
+ EVT_TIMER(WxpqdicFrame_Timer, WxpqdicFrame::OnTimer)
+ EVT_IDLE(WxpqdicFrame::OnIdle)
+END_EVENT_TABLE()
+
+
+
+static const wxChar versionNumber[] = { DKT_VERSION_WX };
+
+
+
+static const wxCmdLineEntryDesc wxpqdic_cmd_line_entries[] = {
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("h"),
+ wxT_2("host"),
+ wxT_2("Host to connect to."),
+ wxCMD_LINE_VAL_STRING,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("p"),
+ wxT_2("port"),
+ wxT_2("Port number to connect to."),
+ wxCMD_LINE_VAL_NUMBER,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("l"),
+ wxT_2("local-port"),
+ wxT_2("Local port number to use."),
+ wxCMD_LINE_VAL_NUMBER,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("q"),
+ wxT_2("queue"),
+ wxT_2("Queue name to check."),
+ wxCMD_LINE_VAL_STRING,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("u"),
+ wxT_2("user"),
+ wxT_2("User name to check."),
+ wxCMD_LINE_VAL_STRING,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("i"),
+ wxT_2("interval"),
+ wxT_2("Time interval for automatic update."),
+ wxCMD_LINE_VAL_NUMBER,
+ 0
+ },
+ {
+ wxCMD_LINE_OPTION,
+ wxT_2("a"),
+ wxT_2("ascii"),
+ wxT_2("Remote host uses ASCII encoding, not UTF-8."),
+ wxCMD_LINE_VAL_NONE,
+ 0
+ },
+ { wxCMD_LINE_NONE }
+};
+
+
+
+/** Key names for preferences.
+*/
+static const wxChar * const wxpqdic_pref_key_names[] = {
+$!string-table macro=wxT
+printqd.host
+printqd.port
+printqd.queue
+printqd.interval
+printqd.local
+printqd.encoding
+$!end
+};
+
+
+
+/** Constant 8-bit strings, not localized.
+*/
+static const char * const wxpqdic_kw[] = {
+$!string-table
+#
+# 0 newline
+#
+\n
+#
+# 1 space
+#
+
+#
+# 2 keyword info
+#
+info
+$!end
+};
+
+
+%% constructor start
+WxpqdicFrame::WxpqdicFrame(
+ int wxid,
+ Dk4WxApplicationHelper *applicationHelper,
+ Dk4WxHelpController *hc,
+ int argc,
+ wxChar **argv,
+ wxChar const * const *localizedTexts,
+ wxChar const * const *nlWx,
+ dkChar const * const *nlDk,
+ bool bSocketsInitialized,
+ dk4_er_t *psockerr
+) : Dk4WxFrame(nlWx[0], applicationHelper, hc, wxid),
+ sHostname(wxT("")),
+ sQueuename(wxT("")),
+ sUsername(wxT("")),
+ cBlack(0, 0, 0),
+ cRed(127, 0, 0),
+ cGreen(0, 127, 0),
+ timer(this, WxpqdicFrame_Timer)
+
+{
+ /* __CHANGE__ 012: Add further local variables.
+ */
+
+ /* __CHANGE__ 012: Initialize further local variables.
+ */
+
+ sTexts = localizedTexts;
+ sNlWx = nlWx;
+ sNlDk = nlDk;
+#if defined(__WXMSW__)
+ wxIcon wxpqdic_icon(sNlWx[4]);
+#else
+ wxIcon wxpqdic_icon(xpm_dkicon);
+#endif
+
+ /* __CHANGE__ 011: Initialize further class members.
+ */
+ bSockInit = bSocketsInitialized;
+ DK4_MEMCPY(&sockerr, psockerr, sizeof(dk4_er_t));
+ pHostname = NULL;
+ pQueuename = NULL;
+ pUsername = NULL;
+ pRequest = NULL;
+ szRequest = (size_t)0UL;
+ lUpdateInterval = 30L;
+ lWaitResponse = 1L;
+ usPortnumber = 9100;
+ usLocalPort = 9100;
+ bIsUtf8 = true;
+ bFirstIdle = true;
+ bFirstResponse = true;
+ bIsInitialized = false;
+ copyArgc = argc;
+ copyArgv = argv;
+ sock = INVALID_SOCKET;
+ iState = WXPQDIC_STATE_OK;
+ tRequestSended = (dk4_time_t)0UL;
+ szResponse = sizeof(bResponse);
+ DK4_MEMRES(&(aAddresses[0]), (2*sizeof(dk4_sockaddr_storage_t)));
+
+%% constructor end
+ if(dkctGUILayoutOK) {
+ SetTitle(nlWx[0]);
+ }
+
+
+ /* __CHANGE__ 012: Release resources allocated by local variables.
+ */
+}
+
+%% module end
+
+
+
+WxpqdicFrame::~WxpqdicFrame()
+{
+
+ /* __CHANGE__ 011: Release resources allocated by further class members.
+ */
+}
+
+
+
+bool
+WxpqdicFrame::CanClose(bool isLast)
+{
+ bool back = true;
+
+ return back;
+}
+
+
+void
+WxpqdicFrame::OnQuit(wxCommandEvent & event)
+{
+ {
+ wxCriticalSectionLocker lockCsProtect(csProtect);
+ if (bIsInitialized) {
+ timer.Stop();
+ bIsInitialized = false;
+ }
+ }
+ if (INVALID_SOCKET != sock) {
+ dk4socket_close(sock, NULL);
+ sock = INVALID_SOCKET;
+ }
+ dk4mem_release(pUsername);
+ dk4mem_release(pQueuename);
+ dk4mem_release(pHostname);
+ dk4mem_release(pRequest);
+ Show(false);
+ /* !!!!! TODO: Release resources */
+ Close();
+}
+
+
+
+void
+WxpqdicFrame::OnAbout(wxCommandEvent & event)
+{
+ wxString text(wxT(""));
+ wxString title(wxT(""));
+
+ /* Construct message text. */
+ text.Append(sNlWx[0]);
+ text.Append(sNlWx[7]);
+#if 0
+ text.Append(sNlWx[1]);
+#endif
+ text.Append(versionNumber);
+ text.Append(sNlWx[8]);
+ text.Append(sTexts[9]);
+ text.Append(sNlWx[2]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[8]);
+ text.Append(sTexts[11]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[9]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[8]);
+ text.Append(sTexts[12]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[10]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[11]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[12]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[13]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[14]);
+ text.Append(sNlWx[8]);
+ text.Append(sNlWx[15]);
+ text.Append(sNlWx[8]);
+
+ /* Construct dialog box title. */
+ title.Append(sTexts[10]);
+ title.Append(sNlWx[0]);
+
+ /* Show dialog box. */
+ wxMessageBox(text, title);
+
+}
+
+
+
+void
+WxpqdicFrame::OnHelpContents(wxCommandEvent & event)
+{
+ DisplayContents();
+}
+
+/* __CHANGE__ 017: Event handlers for further events.
+*/
+
+/* __CHANGE__ 014: Implementation of further methods.
+*/
+
+
+bool
+WxpqdicFrame::ConfigureAndCheckNeedToClose(int *perrc)
+{
+
+ dkChar buf[1024];
+ char c8b[1024];
+ dk4_er_t er;
+ wxChar *pv[] = { NULL, NULL, NULL, NULL, NULL, NULL };
+ const wxChar *cptr;
+ const size_t szbuf = DK4_SIZEOF(buf,dkChar);
+ const size_t szc8b = sizeof(c8b);
+ long l = 0L;
+ int res = 0;
+ bool back = true;
+
+ /* Retrieve some fallback values from preferences.
+ */
+ pAppHelp->GetMultiple(wxpqdic_pref_key_names, pv, 6);
+ $? ". host = \"%!ws\"", TR_WXSTR(pv[0])
+ $? ". port = \"%!ws\"", TR_WXSTR(pv[1])
+ $? ". queue = \"%!ws\"", TR_WXSTR(pv[2])
+ $? ". interval = \"%!ws\"", TR_WXSTR(pv[3])
+ $? ". local = \"%!ws\"", TR_WXSTR(pv[4])
+ $? ". encoding = \"%!ws\"", TR_WXSTR(pv[5])
+
+ /* Check command line arguments
+ */
+ {
+ wxLogNull log;
+ wxCmdLineParser parser(wxpqdic_cmd_line_entries, copyArgc, copyArgv);
+ res = parser.Parse(false);
+ /*
+ Check overall parsing of arguments
+ */
+ if (0 != res) { $? "! failed to parse cmd line args"
+ /* ERROR: Failed to parse command line arguments */
+ *perrc = WXPQDIC_FRAME_ERROR_PARSE;
+ goto finished;
+ }
+ /*
+ Option -a means the remote host wants ASCII data.
+ */
+ if (parser.Found(wxT_2("a"))) {
+ bIsUtf8 = false;
+ } else {
+ if (NULL != pv[5]) {
+ if (0 != dk4strx_casecmp(pv[5], sNlWx[16])) {
+ if (0 != dk4strx_casecmp(pv[5], sNlWx[17])) {
+ bIsUtf8 = false;
+ }
+ }
+ }
+ }
+ /*
+ Try to obtain host name from arguments or from preferences.
+ */
+ dk4error_init(&er);
+ cptr = NULL;
+ if (parser.Found(wxT_2("h"), &sHostname)) {
+ cptr = sHostname.c_str();
+ }
+ else {
+ cptr = pv[0];
+ }
+ if (NULL != cptr) {
+ if (pAppHelp->StringToDk(buf, szbuf, cptr, &er)) {
+ pHostname = dk4str_dup(buf, NULL);
+ if (NULL == pHostname) { $? ". pHostname = \"%!ds\"", pHostname
+ /* ERROR: Memory */
+ *perrc = WXPQDIC_FRAME_ERROR_MEMORY;
+ goto finished;
+ }
+ } else {
+ /* ERROR: Failed to convert string */
+ *perrc = WXPQDIC_FRAME_ERROR_STRCONV_HOSTNAME;
+ goto finished;
+ }
+ }
+ if (NULL == pHostname) {
+ /* ERROR: Missing host name */
+ *perrc = WXPQDIC_FRAME_ERROR_HOSTNAME;
+ goto finished;
+ }
+ /*
+ Queue name is required.
+ */
+ cptr = NULL;
+ if (parser.Found(wxT_2("q"), &sQueuename)) {
+ cptr = sQueuename.c_str();
+ }
+ else {
+ cptr = pv[2];
+ }
+ if (NULL != cptr) {
+ res = dk4recwx_wxchar_to_char(
+ c8b, szc8b, ((bIsUtf8) ? (DK4_ENCODING_UTF8) : (DK4_ENCODING_ASCII)),
+ cptr, pAppHelp->GetWxEncoding(), NULL
+ );
+ if (0 != res) {
+ pQueuename = dk4str8_dup(c8b, NULL);
+ if (NULL == pQueuename) { $? ". pQueuename = \"%!8s\"", pQueuename
+ /* ERROR: Memory */
+ *perrc = WXPQDIC_FRAME_ERROR_MEMORY;
+ goto finished;
+ }
+ } else {
+ /* ERROR: String conversion failed */
+ *perrc = WXPQDIC_FRAME_ERROR_STRCONV_QUEUENAME;
+ goto finished;
+ }
+ }
+ else {
+ /* ERROR: Missing queue name */
+ *perrc = WXPQDIC_FRAME_ERROR_QUEUENAME;
+ goto finished;
+ }
+ if (NULL == pQueuename) {
+ /* ERROR: Missing queue name */
+ *perrc = WXPQDIC_FRAME_ERROR_QUEUENAME;
+ goto finished;
+ }
+ /*
+ Port number is optional.
+ */
+ {
+ bool portnoFound = false;
+ l = 0L;
+ if (parser.Found(wxT_2("p"), &l)) {
+ portnoFound = true;
+ }
+ else {
+ if (NULL != pv[1]) {
+ wxString s(pv[1]);
+ if (s.ToLong(&l, 0)) {
+ portnoFound = true;
+ }
+ }
+ }
+ if (portnoFound) {
+ if ((long)(USHRT_MAX) < l) {
+ /* ERROR: Port number out of range */
+ *perrc = WXPQDIC_FRAME_ERROR_PORT_OOR;
+ goto finished;
+ }
+ if (0L == l) {
+ /* ERROR: Illegal port number 0 */
+ *perrc = WXPQDIC_FRAME_ERROR_PORT_ZERO;
+ goto finished;
+ }
+ usPortnumber = (unsigned short)l;
+ }
+ }
+ /*
+ Local port number is optional.
+ */
+ {
+ bool portnoFound = false;
+ l = 0L;
+ if (parser.Found(wxT_2("l"), &l)) {
+ portnoFound = true;
+ }
+ else {
+ if (NULL != pv[4]) {
+ wxString s(pv[4]);
+ if (s.ToLong(&l, 0)) {
+ portnoFound = true;
+ }
+ }
+ }
+ if (portnoFound) {
+ if ((long)(USHRT_MAX) < l) {
+ /* ERROR: Port number out of range */
+ *perrc = WXPQDIC_FRAME_ERROR_LOCALPORT_OOR;
+ goto finished;
+ }
+ if (0L == l) {
+ /* ERROR: Illegal port number 0 */
+ *perrc = WXPQDIC_FRAME_ERROR_LOCALPORT_ZERO;
+ goto finished;
+ }
+ usLocalPort = (unsigned short)l;
+ }
+ }
+ /*
+ User name is optional, use current user by default.
+ */
+ if (parser.Found(wxT_2("u"), &sUsername)) {
+ res = dk4recwx_wxchar_to_char(
+ c8b, szc8b, ((bIsUtf8) ? (DK4_ENCODING_UTF8) : (DK4_ENCODING_ASCII)),
+ sUsername.c_str(), pAppHelp->GetWxEncoding(), NULL
+ );
+ if (0 != res) {
+ pUsername = dk4str8_dup(c8b, NULL);
+ if (NULL == pUsername) {
+ /* ERROR: Memory */
+ *perrc = WXPQDIC_FRAME_ERROR_MEMORY;
+ goto finished;
+ }
+ }
+ else {
+ /* ERROR: Failed to convert user name */
+ *perrc = WXPQDIC_FRAME_ERROR_STRCONV_USERNAME;
+ goto finished;
+ }
+ }
+ else {
+ res = dk4user_get_logname(buf, szbuf, 0, NULL);
+ if (0 != res) {
+ res = dk4recode_dk_to_any(
+ c8b, szc8b, ((bIsUtf8) ? (DK4_ENCODING_UTF8) : (DK4_ENCODING_ASCII)),
+ buf, pAppHelp->GetDkEncoding(), NULL
+ );
+ if (0 != res) {
+ pUsername = dk4str8_dup(c8b, NULL);
+ if (NULL == pUsername) {
+ /* ERROR: Memory */
+ *perrc = WXPQDIC_FRAME_ERROR_MEMORY;
+ goto finished;
+ }
+ }
+ else {
+ /* ERROR: Failed to convert user name */
+ *perrc = WXPQDIC_FRAME_ERROR_STRCONV_USERNAME;
+ goto finished;
+ }
+ } else {
+ /* ERROR: User name not found! */
+ *perrc = WXPQDIC_FRAME_ERROR_USERNAME;
+ goto finished;
+ }
+ }
+ if (NULL == pUsername) {
+ /* ERROR: No user name */
+ *perrc = WXPQDIC_FRAME_ERROR_USERNAME;
+ goto finished;
+ }
+ /*
+ Interval length is optional.
+ */
+ {
+ bool intervalFound = false;
+ l = 0L;
+ if (parser.Found(wxT_2("p"), &l)) {
+ intervalFound = true;
+ }
+ else {
+ if (NULL != pv[3]) {
+ wxString s(pv[3]);
+ if (s.ToLong(&l, 0)) {
+ intervalFound = true;
+ }
+ }
+ }
+ if (intervalFound) {
+ if (5L <= l) {
+ lUpdateInterval = l;
+ } else {
+ lUpdateInterval = 5L;
+ }
+ }
+ }
+ /*
+ Now build request
+ */
+ dk4error_init(&er);
+ szRequest = strlen(wxpqdic_kw[2]);
+ szRequest = dk4ma_size_t_add(szRequest, dk4str8_len(pQueuename), &er);
+ szRequest = dk4ma_size_t_add(szRequest, dk4str8_len(pUsername), &er);
+ szRequest = dk4ma_size_t_add(szRequest, dk4str8_len(wxpqdic_kw[2]), &er);
+ szRequest = dk4ma_size_t_add(szRequest, 4, &er);
+ if (DK4_E_NONE == er.ec) {
+ pRequest = dk4mem_new(char,szRequest,NULL);
+ if (NULL != pRequest) {
+ if (0 == dk4str8_cpy_s(pRequest, szRequest, wxpqdic_kw[2], NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ if (0 == dk4str8_cat_s(pRequest, szRequest, wxpqdic_kw[1], NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ if (0 == dk4str8_cat_s(pRequest, szRequest, pQueuename, NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ if (0 == dk4str8_cat_s(pRequest, szRequest, wxpqdic_kw[1], NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ if (0 == dk4str8_cat_s(pRequest, szRequest, pUsername, NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ if (0 == dk4str8_cat_s(pRequest, szRequest, wxpqdic_kw[0], NULL)) {
+ /* ERROR: BUG */
+ *perrc = WXPQDIC_FRAME_ERROR_BUG;
+ goto finished;
+ }
+ szRequest = dk4str8_len(pRequest);
+ $? ". request = \"%s\"", TR_8STR(pRequest)
+ } else {
+ /* ERROR: Memory */
+ *perrc = WXPQDIC_FRAME_ERROR_MEMORY;
+ goto finished;
+ }
+ } else {
+ /* ERROR: Numeric overflow in size calculation */
+ *perrc = WXPQDIC_FRAME_ERROR_SIZE_CALC_OVERFLOW;
+ goto finished;
+ }
+ /*
+ Create socket.
+ */
+ sock = dk4socket_udp_client_for_host(
+ aAddresses, pHostname, usPortnumber, usLocalPort, 1, NULL
+ );
+ if (INVALID_SOCKET == sock) {
+ *perrc = WXPQDIC_FRAME_ERROR_SOCKET;
+ goto finished;
+ }
+
+ }
+
+ $? ". successfully completed setup"
+
+ tLimit->SetLabel(sTexts[27]);
+ tUsed->SetLabel(sTexts[27]);
+ tAccount->SetLabel(sTexts[27]);
+
+ /* Finally indicate success.
+ */
+ timer.Start(500);
+ bIsInitialized = true;
+ back = false;
+
+ /* Clean up at end and return result.
+ */
+ finished:
+ pAppHelp->ReleaseWxcharStringArray(pv, 6);
+ if (back) {
+ if (INVALID_SOCKET != sock) {
+ dk4socket_close(sock, NULL);
+ sock = INVALID_SOCKET;
+ }
+ dk4mem_release(pUsername);
+ dk4mem_release(pQueuename);
+ dk4mem_release(pHostname);
+ dk4mem_release(pRequest);
+ }
+ return back;
+}
+
+
+
+void
+WxpqdicFrame::OnIdle(wxIdleEvent & event)
+{
+ int errorCode = WXPQDIC_FRAME_ERROR_NONE;
+ bool mustClose = false;
+ $? "+ OnIdle"
+ /* __CHANGE__
+ */
+ {
+ wxCriticalSectionLocker lockCsProtect(csProtect);
+ if (bFirstIdle) {
+ bFirstIdle = false;
+ mustClose = ConfigureAndCheckNeedToClose(&errorCode);
+ }
+ }
+ if (mustClose) { $? "! error in setup, must close window"
+ const wxChar *ti;
+ const wxChar *tx;
+ ti = sTexts[58]; tx = sTexts[59];
+ switch (errorCode) {
+ case WXPQDIC_FRAME_ERROR_PARSE : {
+ ti = sTexts[30]; tx = sTexts[31];
+ } break;
+ case WXPQDIC_FRAME_ERROR_MEMORY : {
+ ti = sTexts[32]; tx = sTexts[33];
+ } break;
+ case WXPQDIC_FRAME_ERROR_STRCONV_HOSTNAME : {
+ ti = sTexts[34]; tx = sTexts[35];
+ } break;
+ case WXPQDIC_FRAME_ERROR_HOSTNAME : {
+ ti = sTexts[36]; tx = sTexts[37];
+ } break;
+ case WXPQDIC_FRAME_ERROR_STRCONV_QUEUENAME : {
+ ti = sTexts[38]; tx = sTexts[39];
+ } break;
+ case WXPQDIC_FRAME_ERROR_QUEUENAME : {
+ ti = sTexts[40]; tx = sTexts[41];
+ } break;
+ case WXPQDIC_FRAME_ERROR_PORT_OOR : {
+ ti = sTexts[42]; tx = sTexts[43];
+ } break;
+ case WXPQDIC_FRAME_ERROR_PORT_ZERO : {
+ ti = sTexts[42]; tx = sTexts[44];
+ } break;
+ case WXPQDIC_FRAME_ERROR_STRCONV_USERNAME : {
+ ti = sTexts[45]; tx = sTexts[46];
+ } break;
+ case WXPQDIC_FRAME_ERROR_USERNAME : {
+ ti = sTexts[47]; tx = sTexts[48];
+ } break;
+ case WXPQDIC_FRAME_ERROR_LOCALPORT_OOR : {
+ ti = sTexts[49]; tx = sTexts[50];
+ } break;
+ case WXPQDIC_FRAME_ERROR_LOCALPORT_ZERO : {
+ ti = sTexts[49]; tx = sTexts[51];
+ } break;
+ case WXPQDIC_FRAME_ERROR_BUG : {
+ ti = sTexts[52]; tx = sTexts[53];
+ } break;
+ case WXPQDIC_FRAME_ERROR_SIZE_CALC_OVERFLOW : {
+ ti = sTexts[54]; tx = sTexts[55];
+ } break;
+ case WXPQDIC_FRAME_ERROR_SOCKET : {
+ ti = sTexts[56]; tx = sTexts[57];
+ } break;
+ }
+ wxMessageBox(tx, ti, (wxICON_ERROR | wxOK), this);
+ Show(false);
+ Close();
+ }
+
+ /* Allow idle handlers from the base class.
+ */
+ $? "- OnIdle"
+ event.Skip();
+}
+
+
+void
+WxpqdicFrame::OnTimer(wxTimerEvent & event)
+{
+ bool mustUpdate = false;
+ $? "+ OnTimer"
+ {
+ wxCriticalSectionLocker lockCsProtect(csProtect);
+ $? ". entered critical section"
+ if (bIsInitialized) { $? ". already initialized"
+ mustUpdate = DataExchangeWithServer();
+ }
+#if TRACE_DEBUG
+ else { $? "! not yet initialized"
+ }
+#endif
+ $? ". exiting critical section"
+ }
+ if (mustUpdate) {
+ Refresh();
+ Update();
+ }
+ $? "- OnTimer"
+}
+
+
+
+bool
+WxpqdicFrame::ProcessResponse(bool & found)
+{
+ wxChar wxb[16*sizeof(dk4_um_t)];
+ char *tokens[8]; /* Tokens in the response */
+ const char *ep; /* End part of text */
+ dk4_um_t limit; /* Print limit */
+ dk4_um_t used; /* Pages used with in limit */
+ dk4_um_t account; /* Personal account */
+ size_t sz; /* Number of tokens used */
+ size_t szwxb; /* Size of wxb */
+ int founddet; /* Details found. */
+ int res; /* Text to number conversion result */
+ int summary; /* Flag: Can print */
+ bool force; /* Flag: Force use of values */
+ bool back = false;
+ $? "+ ProcessResponse"
+ sz = dk4str8_tokenize(tokens, 8, bResponse, NULL, NULL);
+ if (4 == sz) { $? ". 4 tokens"
+ founddet = 0;
+ force = bFirstResponse;
+ switch (iState) {
+ case WXPQDIC_STATE_TIMEOUT :
+ case WXPQDIC_STATE_SEND_FAILED :
+ {
+ force = true; $? ". recover from error"
+ } break;
+ } $? ". force = %d", (force ? 1 : 0)
+ if (0 == dk4str8_cmp("-1", tokens[0])) { $? ". 0 = unlimited"
+ limit = DK4_UM_MAX;
+ founddet |= 1;
+ } else {
+ limit = (dk4_um_t)0UL;
+ ep = NULL;
+ res = dk4ma_input_c8_dec_dk4_um_t(&limit, tokens[0], &ep, 1, NULL);
+ if (0 != res) { $? ". 0 = %lu", (unsigned long)limit
+ founddet |= 1;
+ }
+#if TRACE_DEBUG
+ else { $? "! 0 not a number"
+ }
+#endif
+ }
+ used = (dk4_um_t)0UL;
+ ep = NULL;
+ res = dk4ma_input_c8_dec_dk4_um_t(&used, tokens[1], &ep, 1, NULL);
+ if (0 != res) { $? ". 1 = %lu", (unsigned long)used
+ founddet |= 2;
+ }
+#if TRACE_DEBUG
+ else { $? "! 1 not a number"
+ }
+#endif
+ account = (dk4_um_t)0UL;
+ ep = NULL;
+ res = dk4ma_input_c8_dec_dk4_um_t(&account, tokens[2], &ep, 1, NULL);
+ if (0 != res) { $? ". 2 = %lu", (unsigned long)account
+ founddet |= 4;
+ }
+#if TRACE_DEBUG
+ else { $? "! 2 not a number"
+ }
+#endif
+ summary = 0;
+ ep = NULL;
+ res = dk4ma_input_c8_dec_int(&summary, tokens[3], &ep, 1, NULL);
+ if (0 != res) { $? ". 3 = %d", summary
+ founddet |= 8;
+ }
+#if TRACE_DEBUG
+ else { $? "! 3 not a number"
+ }
+#endif
+ if (15 == (15 & founddet)) { $? ". processed successfully"
+ /* Renew text labels
+ */
+#if DK4_SIZEOF_WXCHAR > 1
+ szwxb = DK4_SIZEOF(wxb,wxChar);
+ if ((force) || (limit != uLimit)) {
+ if (DK4_UM_MAX == limit) {
+ tLimit->SetLabel(sTexts[14]);
+ } else {
+ res = dk4ma_write_wc_decimal_unsigned(wxb, szwxb, limit, 0, NULL);
+ if (0 != res) {
+ wxString s(wxb);
+ tLimit->SetLabel(s);
+ }
+ }
+ back = true;
+ }
+ if ((force) || (used != uUsed)) {
+ res = dk4ma_write_wc_decimal_unsigned(wxb, szwxb, used, 0, NULL);
+ if (0 != res) {
+ wxString s(wxb);
+ tUsed->SetLabel(s);
+ }
+ back = true;
+ }
+ if ((force) || (account != uAccount)) {
+ res = dk4ma_write_wc_decimal_unsigned(wxb, szwxb, account, 0, NULL);
+ if (0 != res) {
+ wxString s(wxb);
+ tAccount->SetLabel(s);
+ }
+ back = true;
+ }
+#else
+ if ((force) || (limit != uLimit)) {
+ if (DK4_UM_MAX == limit) {
+ tLimit->SetLabel(sTexts[14]);
+ } else {
+ wxString s(tokens[0]);
+ tLimit->SetLabel(s);
+ }
+ back = true; $? ". update for limit"
+ }
+ if ((force) || (used != uUsed)) {
+ wxString s(tokens[1]);
+ tUsed->SetLabel(s);
+ back = true; $? ". update for used"
+ }
+ if ((force) || (account != uAccount)) {
+ wxString s(tokens[2]);
+ tAccount->SetLabel(s);
+ back = true; $? ". update for account"
+ }
+#endif
+ if ((force) || (summary != iSummary)) {
+ wxString s(sTexts[(0 != summary) ? 19 : 20]);
+ tAllowed->SetLabel(s);
+ if (0 != summary) {
+ tAllowed->SetForegroundColour(cGreen);
+ } else {
+ tAllowed->SetForegroundColour(cRed);
+ }
+ back = true; $? ". update for summary"
+ }
+ if (force) {
+ lStatus->SetLabel(sNlWx[5]);
+ switch (iState) {
+ case WXPQDIC_STATE_TIMEOUT :
+ case WXPQDIC_STATE_SEND_FAILED :
+ {
+ lStatus->SetForegroundColour(cBlack);
+ } break;
+ }
+ }
+ /* Save values for later comparisons
+ */
+ uLimit = limit;
+ uUsed = used;
+ uAccount = account;
+ iSummary = summary;
+ bFirstResponse = false;
+ /* Change state
+ */
+ iState = WXPQDIC_STATE_OK;
+ found = true;
+ }
+#if TRACE_DEBUG
+ else { $? "! processing failed"
+ }
+#endif
+ }
+#if TRACE_DEBUG
+ else { $? "! not 4 tokens"
+ }
+#endif
+ $? "- ProcessResponse %d", ((back) ? (1) : (0))
+ return back;
+}
+
+
+
+bool
+WxpqdicFrame::RetrieveResponse(void)
+{
+ dk4_sockaddr_storage_t remaddr; /* Source address */
+ size_t sz; /* Buffer size */
+ size_t szrema; /* Address size */
+ int res; /* Conversion result */
+ bool back = false;
+ bool found = false; /* Flag: Found */
+ $? "+ RetrieveResponse"
+ sz = szResponse;
+ szrema = sizeof(remaddr);
+ res = dk4socket_recvfrom(
+ sock, bResponse, &sz, 0,
+ (struct sockaddr *)(&remaddr), &szrema,
+ 0L, 10000L, NULL
+ );
+ switch (res) {
+ case DK4_SOCKET_RESULT_SUCCESS :
+ case DK4_SOCKET_RESULT_IN_PROGRESS :
+ { $? ". data"
+ if (0 < sz) { $? ". data length"
+ bResponse[(szResponse > sz) ? (sz) : (szResponse - 1)] = '\0';
+#if TRACE_DEBUG
+ dk4str8_delnl(bResponse); $? ". response = \"%!8s\"", bResponse
+#endif
+ if (1 /* ##### TODO: Compare addresses */ ) { $? ". addr ok"
+ back = ProcessResponse(found);
+ }
+#if TRACE_DEBUG
+ else { $? "! addr mismatch"
+ }
+#endif
+ }
+#if TRACE_DEBUG
+ else { $? "! data length 0"
+ }
+#endif
+ } break;
+ default : { $? ". no data"
+ } break;
+ }
+ if (!(found)) {
+ if (WXPQDIC_STATE_SENDED == iState) {
+ iState = WXPQDIC_STATE_TIMEOUT;
+ tLimit->SetLabel(sTexts[27]);
+ tUsed->SetLabel(sTexts[27]);
+ tAccount->SetLabel(sTexts[27]);
+ tAllowed->SetLabel(sTexts[27]);
+ tAllowed->SetForegroundColour(cBlack);
+ lStatus->SetLabel(sTexts[29]);
+ lStatus->SetForegroundColour(cRed);
+ back = true;
+ }
+ }
+ $? "- RetrieveResponse %d", ((back) ? (1) : (0))
+ return back;
+}
+
+
+
+bool
+WxpqdicFrame::SendRequest(bool force)
+{
+ dk4_time_t currenttime = (dk4_time_t)0UL;
+ size_t sz = 0;
+ int res = 0;
+ bool mustsend = false;
+ bool back = false;
+ $? "+ SendRequest"
+ if ((dk4_time_t)0UL == tRequestSended) {
+ mustsend = true;
+ } else {
+ if (force) {
+ mustsend = true;
+ } else {
+ dk4time_get(&currenttime);
+ if ((tRequestSended + (dk4_time_t)lUpdateInterval) <= currenttime) {
+ mustsend = true;
+ }
+ }
+ }
+ if (mustsend) { $? ". must send"
+ sz = szRequest;
+ if ((dk4_um_t)0UL == currenttime) {
+ dk4time_get(&currenttime);
+ }
+ res = dk4socket_sendto(
+ sock, pRequest, &sz, 0,
+ (struct sockaddr *)(&(aAddresses[0])), sizeof(dk4_sockaddr_storage_t),
+ 0L, 0L, NULL
+ );
+ tRequestSended = currenttime;
+ switch (res) {
+ case DK4_SOCKET_RESULT_SUCCESS :
+ case DK4_SOCKET_RESULT_IN_PROGRESS :
+ { $? ". success, sended"
+ switch (iState) {
+ case WXPQDIC_STATE_OK : {
+ iState = WXPQDIC_STATE_SENDED;
+ } break;
+ }
+ } break;
+ default : { $? "! send"
+ if (WXPQDIC_STATE_SEND_FAILED != iState) {
+ tLimit->SetLabel(sTexts[27]);
+ tUsed->SetLabel(sTexts[27]);
+ tAccount->SetLabel(sTexts[27]);
+ tAllowed->SetLabel(sTexts[27]);
+ lStatus->SetLabel(sTexts[28]);
+ lStatus->SetForegroundColour(cRed);
+ back = true;
+ }
+ iState = WXPQDIC_STATE_SEND_FAILED;
+ } break;
+ }
+ }
+#if TRACE_DEBUG
+ else { $? ". no need to send"
+ }
+#endif
+ $? "- SendRequest %d", ((back) ? (1) : (0))
+ return back;
+}
+
+
+
+void
+WxpqdicFrame::OnRun(wxCommandEvent & event)
+{
+ bool mustUpdate = false;
+ $? "+ OnRun"
+ {
+ wxCriticalSectionLocker lockCsProtect(csProtect);
+ if (bIsInitialized) {
+ mustUpdate = SendRequest(true);
+ }
+ }
+ if (mustUpdate) {
+ Refresh();
+ Update();
+ }
+ $? "- OnRun"
+}
+
+
+
+bool
+WxpqdicFrame::DataExchangeWithServer(void)
+{
+ bool back = false;
+ $? "+ DataExchangeWithServer"
+ if (RetrieveResponse()) {
+ back = true;
+ }
+ if (SendRequest()) {
+ back = true;
+ }
+ $? "- DataExchangeWithServer %d", ((back) ? (1) : (0))
+ return back;
+}
+