#define Ident "1B01" /*---------------------------------------------------------------------------*/ #ifdef __DECC #pragma module LWL_CLIENT Ident #endif /* ** Link_options - Here is the Linker Option File **! lwl_client **! tas_src:[lib]sinq_olb/lib **! sys$share:decw$xlibshr/share **!! **!! To build LWL_CLIENT on LNSA09 **!! **!! $ import tasmad **!! $ define/job deltat_c_tlb sinq_c_tlb **!! $ sss := tas_src:[sinqhm] **!! $ bui 'sss'lwl_client debug ** Link_options_end ** ** +--------------------------------------------------------------+ ** | Paul Scherrer Institute | ** | Computing Section | ** | | ** | This software may be used freely by non-profit organizations.| ** | It may be copied provided that the name of P.S.I. and of the | ** | author is included. Neither P.S.I. nor the author assume any | ** | responsibility for the use of this software outside of P.S.I.| ** +--------------------------------------------------------------+ ** ** Module Name . . . . . . . . : [...SINQHM]LWL_CLIENT.C ** ** Author . . . . . . . . . . : D. Maden ** Date of creation . . . . . . : Jan 1997 ** ** LWL_CLIENT is the main program of an Internet Client which transmits ** messages to a LWL_SERVER running on a front-end processor. The server ** writes the data into a LWL Test Generator. ** ** Updates: ** 9-Jan-1997 DM. Initial version. ** 17-Jun-1998 1A05 DM. Set 5 sec time-out on "connect" on VMS systems. ** Add TOF data packet generation. ** 1B01 8-May-2000 DM. Use command line options instead of env variables. **==================================================================== */ #include #include #include #include #include #include #include #include #include #include #include #ifdef __VMS #include #include #include #else #include #endif #ifdef __VMS #include #include #else #define SS$_NORMAL EXIT_SUCCESS #define SS$_BADPARAM EXIT_FAILURE #define SS$_IVBUFLEN EXIT_FAILURE #define NO_MEMORY 4 #endif #include #include #include /* **==================== Global Definitions ===================================== */ #include #include "SinqHM_def.h" #define DFLT_PORT 3501 #define NIL '\0' #define NL '\n' #define MAXARR 4000000 #define MAXREC 65563 /*------------------------------------------------------------ ** Definitions for the LWL Datagrams */ #define b_LWL_HM_NC 0x10 /* Hist-Mode/No-Coinc Datagram Header */ #define b_LWL_HM_NC3 0x13 /* Hist-Mode/No-Coinc/3-chan Datagram Header */ #define b_LWL_HM_C 0x10 /* Hist-Mode+Coinc Datagram Header */ #define b_LWL_TOF 0x00 /* TOF-Mode Datagram Header */ #define b_LWL_STR_NC 0x10 /* Strobo-Mode/No-Coinc Datagram Header */ #define b_LWL_STR_C 0x10 /* Strobo-Mode+Coinc Datagram Header */ #define b_LWL_TR_TSI 0x1f /* Transp-Mode Time Status Info */ #define b_LWL_HM_NC_TSI 0x1f /* Hist-Mode/No-Coinc Time Status Info */ #define b_LWL_TOF_TSI 0x1f /* TOF-Mode Time Status Info */ #define b_LWL_STR_NC_TSI 0x1f /* Strobo-Mode/No-Coinc Time Status Info */ #define b_LWL_HM_C_TSI 0x0e /* Hist-Mode+Coinc Time Status Info */ #define b_LWL_STR_C_TSI 0x0e /* Strobo-Mode+Coinc Time Status Info */ #define b_LWL_TR_ETSI 0x0e /* Transp-Mode Extended Time Status Info */ #define b_LWL_FIFO_EMPTY 0x1e /* FIFO Empty */ #define b_LWL_HDR_NRL_MASK 0x20 /* Mask for Neutron Rate Low bit */ #define b_LWL_HDR_BIT8 0x10 /* Pattern for getting Bit-8 set */ /*------------------------------------------------------------*/ /* ** Define the Data Structures we need */ /* **==================== Global Variables ====================================== */ int My_errno, My_vaxc_errno; char Rmt_host[32]; int Rmt_port; int Pkt_size; int Verbose; static int Cnct_skt = 0; /* Connect socket */ static int Ctrl_C_has_happened; static XrmOptionDescRec OptTable[] = { {"-name", ".name", XrmoptionSepArg, (XPointer) NULL}, {"-host", ".lwlHost", XrmoptionSepArg, (XPointer) NULL}, {"-port", ".lwlPort", XrmoptionSepArg, (XPointer) NULL}, {"-size", ".lwlSize", XrmoptionSepArg, (XPointer) NULL}, }; /* **============================================================================= ** Local routines. ** ** CtrlC_Handler : Catch a Ctrl-C interrupt. ** Do_ETSI : Generate an Extended Time Status Info datagram. ** Do_File : Read and send contents of file to LWL. ** Do_HM : Generate data stream in Histogram Mode. ** Do_HRPT : Generate data stream in HRPT Mode. ** Do_Misc : Generate a miscellaneous datagram. ** Do_TOF : Generate data stream in TOF Mode. ** Do_TS : Generate a Time Status datagram. ** exit_handler : Exit handler in case a forced exit is made. ** openConnection : Open connection to LWL_SERVER. **---------------------------------------------------------------------------- ** Prototypes */ void CtrlC_Handler (int sigint); void Do_ESTI (); void Do_File (); void Do_HM (int silent); void Do_Misc (); void Do_TOF (int silent); void Do_TS (); void exit_handler (); void openConnection (char *node, int port); /* **-------------------------------------------------------------------------- ** CtrlC_Handler: Signal handler to detect on keyboard. */ void CtrlC_Handler (int sigint) { /* ============= */ Ctrl_C_has_happened = 1; } /* **--------------------------------------------------------------------------*/ void Do_ETSI () { /* ======= Generate an Extended Time Status Info (hdr + 9 bytes) */ int i, j, status; char *p_p1, *p_p2, *p_p3, *p_p4, *p_p5, *p_p6, *p_p7, *p_p8, *p_p9; int p1, p2, p3, p4, p5, p6, p7, p8, p9; static unsigned char etsi[] = {0, b_LWL_HDR_BIT8, b_LWL_TR_ETSI, 0xa5, 0xb6, 0xc7, 0xd8, 0xe9, 0xfa, 0x0b, 0x1c, 0x2d}; etsi[0] = sizeof (etsi) - 1; p_p1 = p_p2 = p_p3 = p_p4 = p_p5 = p_p6 = p_p7 = p_p8 = p_p9 = NULL; p_p1 = strtok (NULL, " ,"); if (p_p1 != NULL) p_p2 = strtok (NULL, " ,"); if (p_p2 != NULL) p_p3 = strtok (NULL, " ,"); if (p_p3 != NULL) p_p4 = strtok (NULL, " ,"); if (p_p4 != NULL) p_p5 = strtok (NULL, " ,"); if (p_p5 != NULL) p_p6 = strtok (NULL, " ,"); if (p_p6 != NULL) p_p7 = strtok (NULL, " ,"); if (p_p7 != NULL) p_p8 = strtok (NULL, " ,"); if (p_p8 != NULL) p_p9 = strtok (NULL, " ,"); if (p_p1 != NULL) {sscanf (p_p1, "%x", &p1); etsi[ 3] = p1 & 0xff;} if (p_p2 != NULL) {sscanf (p_p2, "%x", &p2); etsi[ 4] = p2 & 0xff;} if (p_p3 != NULL) {sscanf (p_p3, "%x", &p3); etsi[ 5] = p3 & 0xff;} if (p_p4 != NULL) {sscanf (p_p4, "%x", &p4); etsi[ 6] = p4 & 0xff;} if (p_p5 != NULL) {sscanf (p_p5, "%x", &p5); etsi[ 7] = p5 & 0xff;} if (p_p6 != NULL) {sscanf (p_p6, "%x", &p6); etsi[ 8] = p6 & 0xff;} if (p_p7 != NULL) {sscanf (p_p7, "%x", &p7); etsi[ 9] = p7 & 0xff;} if (p_p8 != NULL) {sscanf (p_p8, "%x", &p8); etsi[10] = p8 & 0xff;} if (p_p9 != NULL) {sscanf (p_p9, "%x", &p9); etsi[11] = p9 & 0xff;} status = send (Cnct_skt, etsi, etsi[0]+1, 0); printf ("Sent: 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x " "0x%02x 0x%02x 0x%02x 0x%02x\n", etsi[1], etsi[2], etsi[3], etsi[4], etsi[5], etsi[6], etsi[7], etsi[8], etsi[9], etsi[10], etsi[11]); etsi[ 3] += 1; etsi[ 4] += 1; etsi[ 5] += 1; etsi[ 6] += 1; etsi[ 7] += 1; etsi[ 8] += 1; etsi[ 9] += 1; etsi[10] += 1; etsi[11] += 1; } /* **--------------------------------------------------------------------------*/ void Do_File () { /* ======= Read and send the contents of a file. ** ** The file format is: ** ** $ <== all records prior to this "$" are skipped. ** <== subsequent records specify datagrams. ** ** . ** ** End-of-File ** ** The format of a datagram record is: ** ... ** where ** is a hex counter (not used - it can be used to label records) ** is the control byte for the datagram header. Set to 0x10 ** to get Bit-8 of the datagram header set to 1. ** specifies Bits 0-7 of the datagram header. ** ... specify subsequent bytes (Bit-8 = 0). ** All items should be in hex, with or without a 0x prefix. ** For valid datagrams, there should be an even number of bytes. ** ** The file is read into an internal data structure, buff. Pointers ** to the individual records are kept in array p_recs, i.e. p_recs[i] ** is the address of the first byte of record i. This bytes in the ** record are: ** Byte 0 - the number of bytes in the record (excl this one); ** Byte 1 - the Bit-8 control byte for the datagram header; ** Byte 2 - Bits 0-7 of the datagram header; ** Byte 3 ... - subsequent bytes in the datagram. */ int i, j, status, nrec, l_recd; FILE *stream; char *p_recd, recd[256], recd1[256]; char *p_ln, *p_bit8, *p_data; char *p_file, *p_ncycles; int ncycles; static char last_file[128] = {NIL}; static int last_ncycles = 1; unsigned char *nxt_data; unsigned char *p_recs[MAXREC]; /* Array of Pointers to the Records */ unsigned char buff[MAXARR]; /* Array to hold the Records */ /* ** ---------- process the arguments and <#-cycles> ---- */ p_file = p_ncycles = NULL; p_file = strtok (NULL, " "); if (p_file != NULL) p_ncycles = strtok (NULL, " "); if (p_file == NULL) p_file = last_file; if (p_file[0] == NIL) { printf ("\007No file name specified!\n"); return; } if (p_ncycles != NULL) { sscanf (p_ncycles, "%i", &ncycles); if (ncycles <= 0) ncycles = 1; }else { ncycles = last_ncycles; } /* ** ---------- Input File einlesen --------------- */ printf ("Opening file %s ...", p_file); stream = fopen (p_file, "r"); if (stream == NULL) { printf ("\n\007Couldn't open %s\n", p_file); return; }else { printf ("\nSkipping over preamble ..."); recd[0] = NIL; do { p_recd = fgets (recd, sizeof (recd), stream); } while ((p_recd != NULL) && (recd[0] != '$')); if (p_recd == NULL) { printf ("\n\007Couldn't find end of preamble!\n"); return; } } printf (" reading data ..."); nrec = 0; nxt_data = buff; while (fgets (recd, sizeof (recd), stream) != NULL) { p_recs[nrec] = nxt_data; nxt_data++; if (nxt_data > &buff[MAXARR-3]) { fclose (stream); printf ("\n\007Abandoned -- more than %d bytes in file!\n", MAXARR-3); return; } l_recd = sizeof (recd1); StrEdit (recd1, recd, "uncomment compress", &l_recd); p_ln = strtok (recd1, " \n"); p_bit8 = (p_ln == NULL) ? NULL : strtok (NULL, " \n"); p_data = (p_bit8 == NULL) ? NULL : strtok (NULL, " \n"); if ((p_ln == NULL) || (p_bit8 == NULL) || (p_data == NULL)) { fclose (stream); printf ("\n\007Abandoned -- Record %d bad\n \"%s\"\n", nrec, recd); return; } sscanf (p_bit8, "%x", &j); *nxt_data = j; nxt_data++; sscanf (p_data, "%x", &j); *nxt_data = j; nxt_data++; *p_recs[nrec] = 2; while ((p_data = strtok (NULL, " \n")) != NULL) { sscanf (p_data, "%x", &j); *nxt_data = j; nxt_data++; *p_recs[nrec] += 1; /* Count the bytes in the record */ if (nxt_data > &buff[MAXARR]) { fclose (stream); printf ("\n\007Abandoned -- more than %d bytes in file!\n", MAXARR); return; } } printf ("\n%5s", p_ln); for (i = 0; i != *p_recs[nrec]; i++) { printf (" 0x%02x", *(p_recs[nrec]+i+1)); } nrec++; if (nrec >= MAXREC) { fclose (stream); printf ("\n\007Abandoned -- more than %d records in file!\n", MAXREC); return; } } fclose (stream); /* **====== Now loop ncycles times sending the data ======== */ for (i = 0; i < ncycles; i++) { printf ("\nCycle %5d", i+1); for (j = 0; j < nrec; j++) { status = send (Cnct_skt, p_recs[j], (*p_recs[j])+1, 0); /* sleep(2); */ } } printf ("\nDone.\n"); last_ncycles = ncycles; /* Save last used values */ strcpy (last_file, p_file); } /* **--------------------------------------------------------------------------*/ void Do_HM (int silent) { /* ===== Generate a stream of events in "Histogram" Mode */ int i, j, status; long int nrl; char *p_nevents, *p_nchans, *p_maxchn[3]; int nevents, nchans, maxchn[3]; unsigned char buff[64]; float scale[3]; void (* sig_status) (int); union { int wire; unsigned char b_wire[4]; } u; p_nevents = p_nchans = p_maxchn[0] = p_maxchn[1] = p_maxchn[2] = NULL; p_nevents = strtok (NULL, " ,"); if (p_nevents != NULL) p_nchans = strtok (NULL, " ,"); if (p_nchans != NULL) p_maxchn[0] = strtok (NULL, " ,"); if (p_maxchn[0] != NULL) p_maxchn[1] = strtok (NULL, " ,"); if (p_maxchn[1] != NULL) p_maxchn[2] = strtok (NULL, " ,"); if ((p_nevents == NULL) || (sscanf (p_nevents, "%i", &nevents) != 1)) nevents = 10; if ((p_nchans == NULL) || (sscanf (p_nchans, "%i", &nchans) != 1)) nchans = 1; if ((p_maxchn[0] == NULL) || (sscanf (p_maxchn[0], "%i", &maxchn[0]) != 1)) maxchn[0] = 1024; if ((p_maxchn[1] == NULL) || (sscanf (p_maxchn[1], "%i", &maxchn[1]) != 1)) maxchn[1] = 1024; if ((p_maxchn[2] == NULL) || (sscanf (p_maxchn[2], "%i", &maxchn[2]) != 1)) maxchn[2] = 1024; if (nevents <= 0) nevents = 10; if ((nchans <= 0) || (nchans > 3)) nchans = 1; if ((maxchn[0] < 0) || (maxchn[0] > 32767)) maxchn[0] = 1024; if ((maxchn[1] < 0) || (maxchn[1] > 32767)) maxchn[1] = 1024; if ((maxchn[2] < 0) || (maxchn[2] > 32767)) maxchn[2] = 1024; switch (nchans) { case 1: printf ("HM: %d events, 1 channel, max-channel-value = %d\n", nevents, maxchn[0]); break; case 2: printf ("HM: %d events, 2 channels\n" " max-channel-0-value = %d\n" " max-channel-1-value = %d\n", nevents, maxchn[0], maxchn[1]); break; case 3: printf ("HM: %d events, 3 channels\n" " max-channel-0-value = %d\n" " max-channel-1-value = %d\n" " max-channel-2-value = %d\n", nevents, maxchn[0], maxchn[1], maxchn[2]); } Ctrl_C_has_happened = 0; sig_status = signal (SIGINT, CtrlC_Handler); /* Catch Ctrl-C interrupts */ if (sig_status == SIG_ERR) { printf (" Problem setting up a signal handler. You probably\n" " will not be able to stop by hitting !\n"); }else { printf (" Hit to stop: "); } buff[0] = 0x81; /* Get LWL_SERVER to zero message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"zero-message\" request. " "Abandoning!\n", status); return; } scale[0] = ((float) maxchn[0])/(((float) RAND_MAX) + 1.0); if (nchans > 1) scale[1] = ((float) maxchn[1])/(((float) RAND_MAX) + 1.0); if (nchans > 2) scale[2] = ((float) maxchn[2])/(((float) RAND_MAX) + 1.0); if (silent == 0) { printf ("\n "); if (nchans == 1) printf (" Value"); if (nchans == 2) printf (" Val0 Val1"); if (nchans == 3) printf (" Val0 Val1 Val2"); } buff[0] = 5 + (nchans * 2); /* Set up length of datagram */ buff[1] = b_LWL_HDR_BIT8; buff[2] = b_LWL_HM_NC | nchans; /* Header for Hist-Mode/No-Coinc/n-Chans */ buff[3] = 0x00; buff[4] = 0x00; buff[5] = 0x00; i = 0; do { buff[5] = i & 0xff; if (silent == 0) printf ("\n%5d", i); for (j = 0; j < nchans; j++) { u.wire = (int) (rand () * scale[j]); buff[6+2*j] = u.b_wire[1]; buff[7+2*j] = u.b_wire[0]; if (silent == 0) printf (" %5d", u.wire); } status = send (Cnct_skt, buff, buff[0]+1, 0); if (silent == 0) { printf (" 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x", buff[1], buff[2], buff[3], buff[4], buff[5], buff[6], buff[7]); if (nchans > 1) printf (" 0x%02x 0x%02x", buff[8], buff[9]); if (nchans > 2) printf (" 0x%02x 0x%02x", buff[10], buff[11]); } if (status != (buff[0] + 1)) { printf ("\nBad send status (%d) on event %d. Abandoning!\n", status, i); return; } i++; } while ((i != nevents) && (Ctrl_C_has_happened == 0)); printf ("\nDone: %d\n", i); signal (SIGINT, SIG_DFL); buff[0] = 0x82; /* Get LWL_SERVER to display message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"display-message\" request. " "Abandoning!\n", status); return; } } /* **--------------------------------------------------------------------------*/ void Do_HRPT (int silent) { /* ======= Generate a stream of events in "HRPT" Mode */ int i, j, status, wire, cnt; long int nrl; char *p_nevents, *p_minwire, *p_maxwire, *p_maxcnt; int nevents, minwire, maxwire, maxcnt; unsigned char buff[64]; float scale[2]; void (* sig_status) (int); p_nevents = p_minwire = p_maxwire = p_maxcnt = NULL; p_nevents = strtok (NULL, " ,"); if (p_nevents != NULL) p_minwire = strtok (NULL, " ,"); if (p_minwire != NULL) p_maxwire = strtok (NULL, " ,"); if (p_maxwire != NULL) p_maxcnt = strtok (NULL, " ,"); if ((p_nevents == NULL) || (sscanf (p_nevents, "%i", &nevents) != 1)) nevents = 10; if ((p_minwire == NULL) || (sscanf (p_minwire, "%i", &minwire) != 1)) minwire = 1; if ((p_maxwire == NULL) || (sscanf (p_maxwire, "%i", &maxwire) != 1)) maxwire = 1600; if ((p_maxcnt == NULL) || (sscanf (p_maxcnt, "%i", &maxcnt) != 1)) maxcnt = 0x3ff; if (nevents <= 0) nevents = 10; if ((minwire < 0) || (minwire > 0x7fff)) minwire = 1; if ((maxwire < minwire) || (maxwire > 0x7fff)) maxwire = 1600; if ((maxcnt < 0) || (maxcnt > 0x3ff)) maxcnt = 0x3ff; printf ("HRPT: %d events, Wire# %d to Wire# %d, max-cnts-per-wire = %d\n", nevents, minwire, maxwire, maxcnt); Ctrl_C_has_happened = 0; sig_status = signal (SIGINT, CtrlC_Handler); /* Catch Ctrl-C interrupts */ if (sig_status == SIG_ERR) { printf (" Problem setting up a signal handler. You probably\n" " will not be able to stop by hitting !\n"); }else { printf (" Hit to stop: "); } buff[0] = 0x81; /* Get LWL_SERVER to zero message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"zero-message\" request. " "Abandoning!\n", status); return; } scale[0] = ((float) (maxwire - minwire + 1))/(((float) RAND_MAX) + 1.0); scale[1] = ((float) (maxcnt))/(((float) RAND_MAX) + 1.0); if (silent == 0) { printf ("\n Wire Cnts"); } buff[0] = 11; /* Set up length of datagram */ buff[1] = b_LWL_HDR_BIT8; buff[2] = b_LWL_HM_NC3; /* Header for Hist-Mode/No-Coinc/3-Chans */ buff[3] = 0x00; buff[4] = 0x00; i = 0; do { buff[5] = i & 0xff; if (silent == 0) printf ("\n%5d", i); wire = (int) (rand () * scale[0]); wire += minwire; cnt = (int) (rand () * scale[1]); buff[6] = (wire & 0x0000ff00) >> 8; buff[7] = wire & 0xff; buff[8] = (cnt & 0x0000ff00) >> 8; buff[9] = cnt & 0xff; buff[10] = (i & 0x0000ff00) >> 8; buff[11] = i & 0xff; if (silent == 0) printf (" %5d %5d", wire, cnt); status = send (Cnct_skt, buff, buff[0]+1, 0); if (silent == 0) { printf (" 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x" " 0x%02x 0x%02x 0x%02x 0x%02x", buff[1], buff[2], buff[3], buff[4], buff[5], buff[6], buff[7], buff[8], buff[9], buff[10], buff[11]); } if (status != (buff[0] + 1)) { printf ("\nBad send status (%d) on event %d. Abandoning!\n", status, i); return; } i++; } while ((i != nevents) && (Ctrl_C_has_happened == 0)); printf ("\nDone: %d\n", i); signal (SIGINT, SIG_DFL); buff[0] = 0x82; /* Get LWL_SERVER to display message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"display-message\" request. " "Abandoning!\n", status); return; } } /* **--------------------------------------------------------------------------*/ void Do_Misc () { /* ======= Generate a Miscellaneous Datagram */ int i, j, status; char *p_p00, *p_p01, *p_p02, *p_p03, *p_p04, *p_p05, *p_p06, *p_p07, *p_p08, *p_p09, *p_p10, *p_p11, *p_p12, *p_p13, *p_p14, *p_p15, *p_p16, *p_p17, *p_p18, *p_p19, *p_p20, *p_p21, *p_p22, *p_p23; int p00, p01, p02, p03, p04, p05, p06, p07, p08, p09, p10, p11, p12, p13, p14, p15, p16, p17, p18, p19, p20, p21, p22, p23; char *tmp; unsigned char misc[32]; p_p00 = p_p01 = p_p02 = p_p03 = p_p04 = p_p05 = p_p06 = p_p07 = p_p08 = p_p09 = p_p10 = p_p11 = p_p12 = p_p13 = p_p14 = p_p15 = p_p16 = p_p17 = p_p18 = p_p19 = p_p20 = p_p21 = p_p22 = p_p23 = NULL; misc[0] = 0; /* Initialise number of bytes to be sent */ p_p00 = strtok (NULL, " ,"); if (p_p00 != NULL) {misc[0]++; p_p01 = strtok (NULL, " ,");} if (p_p01 != NULL) {misc[0]++; p_p02 = strtok (NULL, " ,");} if (p_p02 != NULL) {misc[0]++; p_p03 = strtok (NULL, " ,");} if (p_p03 != NULL) {misc[0]++; p_p04 = strtok (NULL, " ,");} if (p_p04 != NULL) {misc[0]++; p_p05 = strtok (NULL, " ,");} if (p_p05 != NULL) {misc[0]++; p_p06 = strtok (NULL, " ,");} if (p_p06 != NULL) {misc[0]++; p_p07 = strtok (NULL, " ,");} if (p_p07 != NULL) {misc[0]++; p_p08 = strtok (NULL, " ,");} if (p_p08 != NULL) {misc[0]++; p_p09 = strtok (NULL, " ,");} if (p_p09 != NULL) {misc[0]++; p_p10 = strtok (NULL, " ,");} if (p_p10 != NULL) {misc[0]++; p_p11 = strtok (NULL, " ,");} if (p_p11 != NULL) {misc[0]++; p_p12 = strtok (NULL, " ,");} if (p_p12 != NULL) {misc[0]++; p_p13 = strtok (NULL, " ,");} if (p_p13 != NULL) {misc[0]++; p_p14 = strtok (NULL, " ,");} if (p_p14 != NULL) {misc[0]++; p_p15 = strtok (NULL, " ,");} if (p_p15 != NULL) {misc[0]++; p_p16 = strtok (NULL, " ,");} if (p_p16 != NULL) {misc[0]++; p_p17 = strtok (NULL, " ,");} if (p_p17 != NULL) {misc[0]++; p_p18 = strtok (NULL, " ,");} if (p_p18 != NULL) {misc[0]++; p_p19 = strtok (NULL, " ,");} if (p_p19 != NULL) {misc[0]++; p_p20 = strtok (NULL, " ,");} if (p_p20 != NULL) {misc[0]++; p_p21 = strtok (NULL, " ,");} if (p_p21 != NULL) {misc[0]++; p_p22 = strtok (NULL, " ,");} if (p_p22 != NULL) {misc[0]++; p_p23 = strtok (NULL, " ,");} if (p_p23 != NULL) misc[0]++; tmp = (p_p23 != NULL) ? strtok (NULL, " ,") : NULL; if (tmp != NULL) { printf ("\007Too many bytes specified. The current maximum is 24!\n"); return; } if ((misc[0] & 0x01) != 0) { printf ("\007Warning - an odd number of bytes was specified.\n" " This generates an illegal datagram!\n"); } if (misc[0] == 0) { printf ("\007No bytes specified!\n"); return; } misc[1] = b_LWL_HDR_BIT8; /* The first byte is the Bit-8 byte */ misc[0]++; /* Count it too */ if (p_p00 != NULL) {sscanf (p_p00, "%x", &p00); misc[ 2] = p00 & 0xff;} if (p_p01 != NULL) {sscanf (p_p01, "%x", &p01); misc[ 3] = p01 & 0xff;} if (p_p02 != NULL) {sscanf (p_p02, "%x", &p02); misc[ 4] = p02 & 0xff;} if (p_p03 != NULL) {sscanf (p_p03, "%x", &p03); misc[ 5] = p03 & 0xff;} if (p_p04 != NULL) {sscanf (p_p04, "%x", &p04); misc[ 6] = p04 & 0xff;} if (p_p05 != NULL) {sscanf (p_p05, "%x", &p05); misc[ 7] = p05 & 0xff;} if (p_p06 != NULL) {sscanf (p_p06, "%x", &p06); misc[ 8] = p06 & 0xff;} if (p_p07 != NULL) {sscanf (p_p07, "%x", &p07); misc[ 9] = p07 & 0xff;} if (p_p08 != NULL) {sscanf (p_p08, "%x", &p08); misc[10] = p08 & 0xff;} if (p_p09 != NULL) {sscanf (p_p09, "%x", &p09); misc[11] = p09 & 0xff;} if (p_p10 != NULL) {sscanf (p_p10, "%x", &p10); misc[12] = p10 & 0xff;} if (p_p11 != NULL) {sscanf (p_p11, "%x", &p11); misc[13] = p11 & 0xff;} if (p_p12 != NULL) {sscanf (p_p12, "%x", &p12); misc[14] = p12 & 0xff;} if (p_p13 != NULL) {sscanf (p_p13, "%x", &p13); misc[15] = p13 & 0xff;} if (p_p14 != NULL) {sscanf (p_p14, "%x", &p14); misc[16] = p14 & 0xff;} if (p_p15 != NULL) {sscanf (p_p15, "%x", &p15); misc[17] = p15 & 0xff;} if (p_p16 != NULL) {sscanf (p_p16, "%x", &p16); misc[18] = p16 & 0xff;} if (p_p17 != NULL) {sscanf (p_p17, "%x", &p17); misc[19] = p17 & 0xff;} if (p_p18 != NULL) {sscanf (p_p18, "%x", &p18); misc[20] = p18 & 0xff;} if (p_p19 != NULL) {sscanf (p_p19, "%x", &p19); misc[21] = p19 & 0xff;} if (p_p20 != NULL) {sscanf (p_p20, "%x", &p20); misc[22] = p20 & 0xff;} if (p_p21 != NULL) {sscanf (p_p21, "%x", &p21); misc[23] = p21 & 0xff;} if (p_p22 != NULL) {sscanf (p_p22, "%x", &p22); misc[24] = p22 & 0xff;} if (p_p23 != NULL) {sscanf (p_p23, "%x", &p23); misc[25] = p23 & 0xff;} status = send (Cnct_skt, misc, misc[0]+1, 0); printf ("Sent: 0x%02x 0x%02x", misc[1], misc[2]); if (misc[0] > 2) printf (" 0x%02x", misc[ 3]); if (misc[0] > 3) printf (" 0x%02x", misc[ 4]); if (misc[0] > 4) printf (" 0x%02x", misc[ 5]); if (misc[0] > 5) printf (" 0x%02x", misc[ 6]); if (misc[0] > 6) printf (" 0x%02x", misc[ 7]); if (misc[0] > 7) printf (" 0x%02x", misc[ 8]); if (misc[0] > 8) printf ("\n 0x%02x", misc[ 9]); if (misc[0] > 9) printf (" 0x%02x", misc[10]); if (misc[0] > 10) printf (" 0x%02x", misc[11]); if (misc[0] > 11) printf (" 0x%02x", misc[12]); if (misc[0] > 12) printf (" 0x%02x", misc[13]); if (misc[0] > 13) printf (" 0x%02x", misc[14]); if (misc[0] > 14) printf (" 0x%02x", misc[15]); if (misc[0] > 15) printf (" 0x%02x", misc[16]); if (misc[0] > 16) printf ("\n 0x%02x", misc[17]); if (misc[0] > 17) printf (" 0x%02x", misc[18]); if (misc[0] > 18) printf (" 0x%02x", misc[19]); if (misc[0] > 19) printf (" 0x%02x", misc[20]); if (misc[0] > 20) printf (" 0x%02x", misc[21]); if (misc[0] > 21) printf (" 0x%02x", misc[22]); if (misc[0] > 22) printf (" 0x%02x", misc[23]); if (misc[0] > 23) printf (" 0x%02x", misc[24]); if (misc[0] > 24) printf (" 0x%02x", misc[25]); printf ("\n"); } /* **--------------------------------------------------------------------------*/ void Do_TOF (int silent) { /* ====== Generate a stream of events in "TOF" Mode */ int i, j, status; long int nrl; char *p_nevents, *p_hi_cntr, *p_hi_time, *p_lo_cntr, *p_lo_time; unsigned int nevents, hi_cntr, hi_time, lo_cntr, lo_time; unsigned char buff[64]; float cntr_scale, time_scale; void (* sig_status) (int); union { int i4; unsigned char byt[4]; } cntr, time; p_nevents = p_hi_cntr = p_hi_time = p_lo_cntr = p_lo_time = NULL; p_nevents = strtok (NULL, " ,"); if (p_nevents != NULL) p_hi_cntr = strtok (NULL, " ,"); if (p_hi_cntr != NULL) p_hi_time = strtok (NULL, " ,"); if (p_hi_time != NULL) p_lo_cntr = strtok (NULL, " ,"); if (p_lo_cntr != NULL) p_lo_time = strtok (NULL, " ,"); if ((p_nevents == NULL) || (sscanf (p_nevents, "%u", &nevents) != 1)) nevents = 10; if ((p_hi_cntr == NULL) || (sscanf (p_hi_cntr, "%u", &hi_cntr) != 1)) hi_cntr = 127; if ((p_hi_time == NULL) || (sscanf (p_hi_time, "%u", &hi_time) != 1)) hi_time = LWL_HDR_TS_MASK; if ((p_lo_cntr == NULL) || (sscanf (p_lo_cntr, "%u", &lo_cntr) != 1)) lo_cntr = 0; if ((p_lo_time == NULL) || (sscanf (p_lo_time, "%u", &lo_time) != 1)) lo_time = 0; if (nevents == 0) nevents = 10; if (hi_cntr > MAX_TOF_CNTR) hi_cntr = 127; if (hi_time > (LWL_HDR_TS_MASK)) hi_time = LWL_HDR_TS_MASK; if (lo_cntr > hi_cntr) lo_cntr = 0; if (lo_time > hi_time) lo_time = 0; printf ("TOF: %u events\n" " Counters from %u to %u\n" " Time-values from 0x%x to 0x%x\n", nevents, lo_cntr, hi_cntr, lo_time, hi_time); Ctrl_C_has_happened = 0; sig_status = signal (SIGINT, CtrlC_Handler); /* Catch Ctrl-C interrupts */ if (sig_status == SIG_ERR) { printf (" Problem setting up a signal handler. You probably\n" " will not be able to stop by hitting !\n"); }else { printf (" Hit to stop: "); } buff[0] = 0x81; /* Get LWL_SERVER to zero message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"zero-message\" request. " "Abandoning!\n", status); return; } cntr_scale = ((float) (hi_cntr - lo_cntr + 1))/(((float) RAND_MAX) + 1.0); time_scale = ((float) (hi_time - lo_time + 1))/(((float) RAND_MAX) + 1.0); if (silent == 0) printf ("\n Time Cntr"); buff[0] = 7; /* Set up length of datagram */ buff[1] = b_LWL_HDR_BIT8; buff[2] = b_LWL_TOF | 1; /* Header for TOF-Mode/1-Chan */ buff[3] = 0x00; buff[4] = 0x00; buff[5] = 0x00; buff[6] = 0x00; buff[7] = 0x00; i = 0; do { time.i4 = (int) (rand () * time_scale); time.i4 += lo_time; if (time.i4 > hi_time) time.i4 = hi_time; time.i4 &= LWL_HDR_TS_MASK; buff[3] = time.byt[2]; buff[4] = time.byt[1]; buff[5] = time.byt[0]; cntr.i4 = (int) (rand () * cntr_scale); cntr.i4 += lo_cntr; if (cntr.i4 > hi_cntr) cntr.i4 = hi_cntr; buff[6] = cntr.byt[1]; buff[7] = cntr.byt[0]; status = send (Cnct_skt, buff, buff[0]+1, 0); if (silent == 0) { printf ("\n%5d %8d %5d 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x", i, time.i4, cntr.i4, buff[1], buff[2], buff[3], buff[4], buff[5], buff[6], buff[7]); } if (status != (buff[0] + 1)) { printf ("\nBad send status (%d) on event %d. Abandoning!\n", status, i); return; } i++; } while ((i != nevents) && (Ctrl_C_has_happened == 0)); printf ("\nDone: %d\n", i); signal (SIGINT, SIG_DFL); buff[0] = 0x82; /* Get LWL_SERVER to display message count */ status = send (Cnct_skt, buff, 1, 0); if (status != 1) { printf ("\nBad send status (%d) on \"display-message\" request. " "Abandoning!\n", status); return; } } /* **--------------------------------------------------------------------------*/ void Do_TS () { /* ===== Generate a Time Status packet (hdr + 5 bytes) */ int i, j, status; char *p_p1, *p_p2, *p_p3, *p_p4, *p_p5; int p1, p2, p3, p4, p5; static unsigned char ts[] = {0, b_LWL_HDR_BIT8, b_LWL_TR_TSI, 0x2e, 0x3d, 0x4c, 0x5b, 0x6a}; ts[0] = sizeof (ts) - 1; p_p1 = p_p2 = p_p3 = p_p4 = p_p5 = NULL; p_p1 = strtok (NULL, " ,"); if (p_p1 != NULL) p_p2 = strtok (NULL, " ,"); if (p_p2 != NULL) p_p3 = strtok (NULL, " ,"); if (p_p3 != NULL) p_p4 = strtok (NULL, " ,"); if (p_p4 != NULL) p_p5 = strtok (NULL, " ,"); if (p_p1 != NULL) {sscanf (p_p1, "%x", &p1); ts[3] = p1 & 0xff;} if (p_p2 != NULL) {sscanf (p_p2, "%x", &p2); ts[4] = p2 & 0xff;} if (p_p3 != NULL) {sscanf (p_p3, "%x", &p3); ts[5] = p3 & 0xff;} if (p_p4 != NULL) {sscanf (p_p4, "%x", &p4); ts[6] = p4 & 0xff;} if (p_p5 != NULL) {sscanf (p_p5, "%x", &p5); ts[7] = p5 & 0xff;} status = send (Cnct_skt, ts, ts[0]+1, 0); printf ("Sent: 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x\n", ts[1], ts[2], ts[3], ts[4], ts[5], ts[6], ts[7]); ts[3] += 1; ts[4] += 1; ts[5] += 1; ts[6] += 1; ts[7] += 1; } /* **---------------------------------------------------------------------------*/ void exit_handler () { /* ============ ** We must exit. Tidy up first. ** Close TCP/IP link to front-end. */ int status; char buff[16]; /* ** Tell server we're quitting. */ if (Cnct_skt != 0) { printf ("Closing connection to %s ...\n", Rmt_host); buff[0] = 0x00; status = send (Cnct_skt, buff, 1, 0); status = close (Cnct_skt); Cnct_skt = 0; if (status != 0) FailInet ("EXIT_HANDLER -- R/W-Socket close error\n"); } } /* **--------------------------------------------------------------------------*/ void openConnection ( /* ============== ** Open connection to histogram memory front-end. */ char *node, int port) { int i, status; struct sockaddr_in lcl_sockname; struct sockaddr_in rmt_sockname; int rmt_inet_addr; struct in_addr *rmt_inet_addr_pntr; struct hostent *rmt_hostent; int rmt_sockname_len; unsigned int oto_len, oto_status; char old_time_out[4]; union { char chars[4]; int val; } time_out; /* ** Get Internet address of the front-end. */ for (i=0; i < strlen (node); i++) node[i] = tolower (node[i]); rmt_hostent = gethostbyname (node); if (rmt_hostent == NULL) { /* ** The following code is to handle nodes which are not yet ** in the BIND data base. */ if (strcmp (node, "sqfe01") == 0) { rmt_inet_addr_pntr = (struct in_addr *) &rmt_inet_addr; rmt_inet_addr = inet_addr ("129.129.56.181"); }else { printf ("Server Node is %s.\n", node); FailInet ("\nGethostbyname error."); } }else { rmt_inet_addr_pntr = (struct in_addr *) rmt_hostent->h_addr_list[0]; } printf (" LWL_SERVER is running on %s ", node); printf ("(%s),", inet_ntoa (*rmt_inet_addr_pntr)); printf (" Port %d\n", port); /* ** Create a TCP/IP socket for prelim. connect to server and bind it. */ Cnct_skt = socket (AF_INET, SOCK_STREAM, 0); if (Cnct_skt == -1) FailInet ("Socket error.\n"); lcl_sockname.sin_family = AF_INET; lcl_sockname.sin_port = htons (0); lcl_sockname.sin_addr.s_addr = 0; status = bind (Cnct_skt, (struct sockaddr *) &lcl_sockname, sizeof (lcl_sockname)); if (status == -1) FailInet ("Bind error.\n"); /*--------------------------- ** Set short time-out (VMS systems only) */ #ifdef __VMS oto_len = sizeof (old_time_out); /* Save current time-out first */ oto_status = getsockopt (Cnct_skt, IPPROTO_TCP, UCX$C_TCP_PROBE_IDLE, old_time_out, &oto_len); if (oto_status == 0) { time_out.val = 5; /* Set new time-out */ status = setsockopt (Cnct_skt, IPPROTO_TCP, UCX$C_TCP_PROBE_IDLE, time_out.chars, sizeof (time_out)); } #endif /* **========================================= Now connect to the server. */ rmt_sockname_len = sizeof (rmt_sockname); rmt_sockname.sin_family = AF_INET; rmt_sockname.sin_port = htons (port); rmt_sockname.sin_addr.s_addr = rmt_inet_addr_pntr->s_addr; status = connect (Cnct_skt, (struct sockaddr *) &rmt_sockname, sizeof (rmt_sockname)); if (status == -1) { GetErrno (&My_errno, &My_vaxc_errno); FailInet ("Connect error\n"); } /*--------------------------- ** Restore time-out (VMS only) */ #ifdef __VMS if (oto_status == 0) { setsockopt (Cnct_skt, IPPROTO_TCP, UCX$C_TCP_PROBE_IDLE, old_time_out, oto_len); } #endif } /* **--------------------------------------------------------------------------- ** setup_xrm_database - setup Resource Manager Database */ int setup_xrm_database ( /* ================== */ XrmDatabase *db, char *name[], int *argc, char *argv[], int verbose) { static char our_name[80] = "Unknown"; /* This holds the program name */ static char lkup_name[80] = "Unknown"; /* Name for looking in database */ int status, i, first = True; char text[80]; char full_nm0[80]; char full_nm1[80]; char *p_fil[] = {0,0,0,0,0,0,0,0,0,0}; char *my_name; char *my_name_last; char *name_type; XrmValue name_value; XrmDatabase cmnd_line_db = NULL; XrmDatabase lcl_db = NULL; /*----------------------------------------------------- ** This routine merges some resource databases with options specified on ** the command line. Resources can then be looked up using XrmGetResource. ** This is a bit like the X-toolkit routine XtAppInitialize does for the ** extraction of resources by XtGetApplicationResources. ** ** I can't help but think that there's a simpler way of doing this but I ** can't find it in the X manuals. Basically, the problem arises with wanting ** to avoid the calling program being associated with an X-display, i.e. it ** is intended for use by "command-line oriented" programs. All the nice, ** easy-to-use resource/command-line setup routines in Xlib or Xtlib seem to ** assume one is going to use a display -- not surprising, I suppose, ** since the concept of Xlib is for writing window based applications! ** ** Anyway, the point is that the following way turns out to be lacking ** when it gets tested in anger. */ status = True; /* Assume success */ our_name[0] = NIL; /* ** Make a list of the databases to be merged, highest priority first. */ #ifdef __VMS p_fil[0] = "decw$user_defaults:SinQ_rc.dat"; p_fil[1] = "decw$group_defaults:SinQ_rc.dat"; p_fil[2] = "decw$system_defaults:SinQ_rc.dat"; p_fil[3] = "decw$user_defaults:decw$xdefaults.dat"; p_fil[4] = "decw$group_defaults:decw$xdefaults.dat"; p_fil[5] = "decw$system_defaults:decw$xdefaults.dat"; p_fil[6] = NULL; if (*argc > 0) { /* Find out what we are called - parse file nm */ my_name = strstr (argv[0], "]"); /* Find end of directory, i.e. "]" */ my_name++; /* Skip over "]" */ if (my_name[0] == '[') { /* Handle possible concealed device */ my_name = strstr (my_name, "]"); my_name++; } i = sizeof (our_name); StrEdit (our_name, my_name, "lowercase", &i); /* Copy the rest */ strtok (our_name, "."); /* Close it off at "." */ } #else p_fil[0] = StrJoin (full_nm0, sizeof (full_nm0), getenv ("HOME"), "/SinQ_rc"); p_fil[1] = "/usr/lib/X11/app-defaults/SinQ_rc"; p_fil[2] = StrJoin (full_nm1, sizeof (full_nm1), getenv ("HOME"), "/.Xdefaults"); p_fil[3] = "/usr/lib/X11/app-defaults/Xdefaults"; p_fil[4] = NULL; if (*argc > 0) { /* Find out what we are called - parse file nm */ /* Find end of directories */ my_name = argv[0] - 1; while (my_name != NULL) { my_name_last = my_name; my_name_last++; my_name = strstr (my_name_last, "/"); } StrJoin (our_name, sizeof (our_name), my_name_last, ""); } #endif if (verbose) printf ("My name is \"%s\"\n", our_name); /* ** Initialise and combine all databases */ XrmInitialize (); for (i = 0; i < XtNumber (p_fil); i++) { if (p_fil[i] == NULL) break; status = XrmCombineFileDatabase (p_fil[i], &lcl_db, False); if ((status != 0) && verbose) { if (first) printf ("Resource database created from file %s.\n", p_fil[i]); if (!first) printf ("File %s merged into resource database.\n", p_fil[i]); first = False; } } /*---------------------------------------------------------------- ** See if there's anything specified on cmnd line, incl "name". */ XrmParseCommand (&cmnd_line_db, OptTable, XtNumber(OptTable), our_name, argc, argv); if (cmnd_line_db != NULL) { /* ** There was at least 1 item on cmnd line. Process the line. ** If -name was specified, adopt it. */ status = XrmGetResource (cmnd_line_db, /* See if a name was specified */ StrJoin (text, sizeof (text), our_name, ".name"), "ProgramName.Values", &name_type, &name_value); if (status) { i = sizeof (lkup_name); StrEdit (lkup_name, name_value.addr, "lowercase", &i); printf ("Option list name is \"%s\"\n", lkup_name); }else { strcpy (lkup_name, our_name); } /* ** Loop over all items in OptTable and merge them into database, ** taking care of any possible name changes. */ for (i = 0; i < XtNumber (OptTable); i++) { if (strcmp (OptTable[i].option, "-name") == 0) continue; status = XrmGetResource (cmnd_line_db, StrJoin (text, sizeof (text), our_name, OptTable[i].specifier), "ProgramName.Values", &name_type, &name_value); if (status) { StrJoin (text, sizeof (text), lkup_name, OptTable[i].specifier); XrmPutResource (&lcl_db, text, "String", &name_value); } } } /*---------------------------------------------------------------- */ *name = lkup_name; *db = lcl_db; if ((lcl_db == NULL) && verbose) printf ("\007Warning -- no resource database found.\n"); XrmDestroyDatabase (cmnd_line_db); /* ** XrmPutFileDatabase (lcl_db, "lwl_client.db"); */ return status; } /* **========================================================================== ** ** Main line program ** ------------------ **==========================================================================*/ int main (int argc, char *argv[]) { /* ==== */ int i, j, k, status, is, silent; unsigned char ubuff[16]; unsigned char fe[] = {5, b_LWL_HDR_BIT8, b_LWL_FIFO_EMPTY, 0x00, 0x00, 0x00}; char recd[256], recd1[256]; char last_recd[256] = {NIL}; char *verb; int l_recd; time_t startTime; char cmndLine[132]; char buff[80], *appName; XrmDatabase my_db; XrmValue value; char *type; /*============================================================================ */ startTime = time (NULL); printf ("LWL_CLIENT Ident %s started.\n", Ident); printf ("Started at %s", asctime (localtime (&startTime))); StrJoin (cmndLine, sizeof (cmndLine), argv[0], ""); for (i = 1; i < argc; i++) { StrJoin (cmndLine, sizeof (cmndLine), cmndLine, " "); StrJoin (cmndLine, sizeof (cmndLine), cmndLine, argv[i]); } printf ("Command: %s\n", cmndLine); /*============================================================================ ** Declare an exit handler to tidy up if we get forced to exit. */ is = atexit (exit_handler); if (is != 0) { printf ("LWL_CLIENT -- error setting up exit handler."); return EXIT_FAILURE; } /*============================================================================ ** Setup the resource database and look up the resources. ** If there is a single item left on the command line, assume ** that it is the target host. */ Verbose = False; for (i = 1; i < argc; i++) if (strcmp ("-v", argv[i]) == 0) Verbose = True; setup_xrm_database (&my_db, &appName, &argc, argv, Verbose); /* - - - - - - - - - - - - - - - - - - - - - - - - */ status = XrmGetResource (my_db, StrJoin (buff, sizeof (buff), appName, ".lwlHost"), "ProgramName.Values", &type, &value); if (status) { StrJoin (Rmt_host, sizeof (Rmt_host), value.addr, ""); }else { if (argc == 2) { StrJoin (Rmt_host, sizeof (Rmt_host), argv[1], ""); argc--; }else { printf ("\n" "Host name not defined via the\n" " \"lwlHost\" resource or the\n" " \"-host\" option.\n" "There is no default!\n"); exit (EXIT_FAILURE); } } /* - - - - - - - - - - - - - - - - - - - - - - - - */ if (argc > 1) { printf ("The following illegal options were specified:\n "); for (i = 1; i < argc; i++) printf (" %s", argv[i]); printf ("\nThe following options are recognised:\n"); for (i = 1; i < XtNumber (OptTable); i++) { printf (" %s\n", OptTable[i].option); } exit (EXIT_FAILURE); } /* - - - - - - - - - - - - - - - - - - - - - - - - */ status = XrmGetResource (my_db, StrJoin (buff, sizeof (buff), appName, ".lwlPort"), "ProgramName.Values", &type, &value); if (!status) { Rmt_port = 3501; }else if ((sscanf (value.addr, "%d", &Rmt_port) != 1) || (Rmt_port < 1024) || (Rmt_port > 65535)) { printf ("\n" " \"-port %s\" is illegal! It must be an integer in the range " "1024 to 65535\n" "\n", value.addr); exit (EXIT_FAILURE); } /* - - - - - - - - - - - - - - - - - - - - - - - - */ status = XrmGetResource (my_db, StrJoin (buff, sizeof (buff), appName, ".lwlSize"), "ProgramName.Values", &type, &value); if (!status) { Pkt_size = 8192; }else if ((sscanf (value.addr, "%d", &Pkt_size) != 1) || (Pkt_size < 256) || (Pkt_size > 65536)) { printf ("\n" " \"-size %s\" is illegal! It must be an integer in the range " "256 to 65536\n" "\n", value.addr); exit (EXIT_FAILURE); } /*============================================================================ ** Find out the location of the LWL Server and make ** a connection to it. Any errors during this phase cause the program ** to exit with an error status. */ openConnection (Rmt_host, Rmt_port); /* **====================================================== Wait for work ========= */ recd[0] = NIL; printf ("> "); while (fgets (recd, sizeof (recd), stdin) != NULL) { if (strlen (recd) == (sizeof (recd) - 1)) { printf ("\n\n\007Input buffer overflow -- command ignored!\n\n"); do { /* Flush the remains */ fgets (recd, sizeof (recd), stdin); } while (strlen (recd) == (sizeof (recd) - 1)); printf ("> "); continue; } i = strlen (recd) - 1; if (recd[i] == NL) recd[i] = NIL; /* Suppress the trailing \n */ if (recd[0] == NIL) { /* If just , repeat */ strcpy (recd, last_recd); } l_recd = sizeof (recd1); StrEdit (recd1, recd, "trim compress uncomment lowercase", &l_recd); if (l_recd <= 0) { /* Skip empty lines */ printf ("\n> "); continue; } /* ** Parse the command */ verb = strtok (recd1, " ,"); if ((strcmp (verb, "q") == 0) || /* Quit */ (strcmp (verb, "qu") == 0) || (strcmp (verb, "qui") == 0) || (strcmp (verb, "quit") == 0) || (strcmp (verb, "ex") == 0) || (strcmp (verb, "exi") == 0) || (strcmp (verb, "exit") == 0)) { break; }else if ((strcmp (verb, "et") == 0) || /* Send Extended T Status Info */ (strcmp (verb, "ets") == 0) || (strcmp (verb, "etsi") == 0)) { Do_ETSI (); }else if (strcmp (verb, "fe") == 0) { /* Send Fifo-empty */ status = send (Cnct_skt, fe, fe[0]+1, 0); printf ("Sent: 0x%02x 0x%02x 0x%02x 0x%02x\n", fe[1], fe[2], fe[3], fe[4]); }else if ((strcmp (verb, "fi") == 0) || /* Send File */ (strcmp (verb, "fil") == 0) || (strcmp (verb, "file") == 0)) { Do_File (); }else if ((strcmp (verb, "hm") == 0) || /* Histogram Mode */ (strcmp (verb, "hm/s") == 0)) { /* Params are: ** <#-events> ** <#-chans> (1, 2 or 3) ** ** ** ... */ silent = 0; if (strcmp (verb, "hm/s") == 0) silent = 1; Do_HM (silent); }else if ((strcmp (verb, "hr") == 0) || /* HRPT Mode */ (strcmp (verb, "hrp") == 0) || (strcmp (verb, "hrpt") == 0) || (strcmp (verb, "hr/s") == 0) || (strcmp (verb, "hrp/s") == 0) || (strcmp (verb, "hrpt/s") == 0)) { /* Params are: ** <#-events> ** ** ** ** ... */ silent = 0; if (strcmp (verb, "hr/s") == 0) silent = 1; if (strcmp (verb, "hrp/s") == 0) silent = 1; if (strcmp (verb, "hrpt/s") == 0) silent = 1; Do_HRPT (silent); }else if ((strcmp (verb, "mi") == 0) || /* Send Miscellaneous Datagram */ (strcmp (verb, "mis") == 0) || (strcmp (verb, "misc") == 0)) { Do_Misc (); }else if ((strcmp (verb, "tof") == 0) || /* TOF Mode */ (strcmp (verb, "tof/s") == 0)) { /* Params are: ** <#-events> (dflt=10) ** (dflt=127) ** (dflt=0xfffff) ** (dflt=0) ** (dflt=0) */ silent = (strcmp (verb, "tof/s") == 0) ? 1 : 0; Do_TOF (silent); }else if (strcmp (verb, "ts") == 0) { /* Send Time Stamp */ Do_TS (); }else if ((strcmp (verb, "?") == 0) || (strcmp (verb, "h") == 0) || (strcmp (verb, "he") == 0) || (strcmp (verb, "hel") == 0) || (strcmp (verb, "help") == 0)) { printf ("\n" " The following commands are recognised by LWL_CLIENT:\n" "\n" " ETSI ... - Send Extended Time Stamp Info (0x0e + 9 bytes)\n" "\n" " FE - Send FIFO-Empty (0x1e, 0, 0, 0)\n" "\n" " FILE <#-cycles> - Send file to LWL <#-cycles> times.\n" "\n" " HM <#-events> <#chans> ... - generate\n" " data flow in \"Histogram\" Mode.\n" "\n" " HM/S <#-events> <#chans> ... - same as HM only" " silent.\n" "\n" " HRPT <#-events> ... " "- generate\n" " data flow in \"HRPT\" Mode.\n" "\n" " HRPT/S <#-events> ... - same as HRPT only" " silent.\n" "\n" " TOF <#-events> " "- generate\n" " data flow in \"TOF\" Mode.\n" "\n" " TOF/S <#-events> ... - same as TOF only" " silent.\n" "\n" " MISC ... - Send miscellaneous datagram (up to 10 bytes)\n" " \" ...\" are in hex, without \"0x\" prefix.\n" "\n" " TS ... - Send Time Stamp (0x1f + 5 bytes)\n" "\n" " HELP or ? - generate this help text.\n" "\n" " To run the program:\n" " lwl_client [-host] [-port ] [-size ]\n" "\n" " Default for = 3501\n" " Default for = 8192\n" "\n"); }else { printf ("\n Illegal command - type \"?\" for help.\n"); } strcpy (last_recd, recd); /* ** Get another command. */ printf ("> "); } /* ** Tell server we're quitting. */ printf ("Closing connection to %s ...\n", Rmt_host); ubuff[0] = 0x00; status = send (Cnct_skt, ubuff, 1, 0); status = close (Cnct_skt); Cnct_skt = 0; if (status != 0) FailInet ("LWL_CLIENT -- R/W-Socket close error\n"); return EXIT_SUCCESS; } /*============================================= End of LWL_CLIENT.C ======*/