2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these librararies and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
23 /* $TOG: ParseJobs.C /main/12 1998/08/03 16:30:29 mgreess $ */
25 * (c) Copyright 1993, 1994 Hewlett-Packard Company *
26 * (c) Copyright 1993, 1994 International Business Machines Corp. *
27 * (c) Copyright 1993, 1994 Sun Microsystems, Inc. *
28 * (c) Copyright 1993, 1994 Novell, Inc. *
33 #include <sys/types.h>
34 #include <sys/socket.h>
35 #include <netinet/in.h>
38 * XXXXX - AIX hack alert!!! This is needed for an AIX defect
39 * in the definition of inet_addr in <arpa/inet.h>
41 extern "C" in_addr_t inet_addr(const char *);
43 #include <arpa/inet.h>
54 #include <X11/Intrinsic.h>
56 #include "dtprintinfomsg.h"
60 #if defined(SVR4) || defined(SYSV)
67 #if defined(aix) || defined(__osf__) || defined(USL) || defined(__uxp__)
68 extern "C" { int rresvport(int *); }
72 #define SETEUID(id) setresuid(getuid(), (uid_t)id, (uid_t)0);
74 #if defined(aix) || defined(USL) || defined(__uxp__)
75 extern "C" { extern int seteuid(uid_t); }
77 #define SETEUID(id) seteuid((uid_t)id)
80 #include "ParseJobs.h"
83 static int G_AIX_LOCAL = 0;
85 int RemotePrintJobs(char *server, char *printer, char **job_list, int *n_jobs)
92 if ((sockfd = ConnectToPrintServer(server, 15)) == -1)
97 if (SendPrintJobStatusReguest(sockfd, printer))
102 output = (char *)malloc(512);
104 char *out2 = out1 + 511;
108 if ((n = read(sockfd, out1, len)) == len)
112 output = (char *)realloc(output, (ctr * 512));
113 out1 = output + ((ctr - 1) * 512);
119 len = out2 - out1 + 1;
131 rc = ParseRemotePrintJobs(printer, output, job_list, n_jobs);
137 int ParseRemotePrintJobs(char *printer, char *jobs, char **job_list,
146 switch (DetermineOutput(jobs))
149 rc = ParseAIXv2PrintJobs(printer, jobs, job_list, n_jobs);
152 rc = ParseAIXv3PrintJobs(printer, jobs, job_list, n_jobs);
155 rc = ParseBSDPrintJobs(printer, jobs, job_list, n_jobs);
166 static void connect_timeout(int not_used)
171 // Create a connection to the remote printer server.
172 int ConnectToPrintServer(const char *rhost, int timeout)
176 struct sockaddr_in sin;
177 int s, lport = IPPORT_RESERVED - 1;
179 // Get the host address and port number to connect to.
180 #if defined(__uxp__) || (defined(USL) && (OSMAJORVERSION > 1))
181 if (!(hp = gethostbyname((char *) rhost)))
183 unsigned long tmpaddr = inet_addr((char *) rhost);
185 if (!(hp = gethostbyname(rhost)))
187 unsigned long tmpaddr = inet_addr(rhost);
189 hp = gethostbyaddr((char *)&tmpaddr, sizeof(tmpaddr), AF_INET);
193 if (!(sp = getservbyname("printer", "tcp")))
196 memset((char *)&sin, 0, sizeof(sin));
197 memcpy((char *)&sin.sin_addr, hp->h_addr, hp->h_length);
198 sin.sin_family = hp->h_addrtype;
199 sin.sin_port = sp->s_port;
201 // run as user's UID, but with privileges from root
204 // Try connecting to the server.
205 s = rresvport(&lport);
207 signal(SIGALRM, connect_timeout);
212 if (connect(s, (struct sockaddr *)&sin, sizeof(sin)) < 0)
222 int SendPrintJobStatusReguest(int sockfd, const char *printer)
224 char *buf = new char[100];
227 sprintf(buf, "%c%s \n", '\4', printer);
230 size = write(sockfd, buf, size);
231 if (write(sockfd, buf, size) != size)
241 JobOutputType DetermineOutput(char *output)
245 static int first_time = 1;
247 static char *aixv2_pattern;
248 static char *aixv3_pattern;
249 static char *bsd_pattern;
251 * Due to bug in regcmp/regex (bug id 1191772), change to C locale for
252 * this parsing work. And change back at end of procedure. This workaround
253 * appears to be ok since the print service output parsed here is in a
254 * "C locale" 8-bit form for inter-machine networking.
256 setlocale(LC_ALL, "C");
260 aixv2_pattern = regcmp("dev.*arg.*status.*request", (char *)NULL);
261 aixv3_pattern = regcmp("Queue.*Dev.*Status.*Job", (char *)NULL);
262 bsd_pattern = regcmp(":.*\\[.*\\]", (char *)NULL);
266 static regex_t aixv2_pattern;
267 static regex_t aixv3_pattern;
268 static regex_t bsd_pattern;
272 regcomp(&aixv2_pattern, "dev.*arg.*status.*request", REG_NOSUB);
273 regcomp(&aixv3_pattern, "Queue.*Dev.*Status.*Job", REG_NOSUB);
274 regcomp(&bsd_pattern, ":.*\\[.*\\]", REG_NOSUB);
280 if (s1 = strchr(s, '\n'))
283 while (i < 10 && s && *s)
286 if (regex(bsd_pattern, s)) {
287 setlocale(LC_ALL, "");
290 if (regex(aixv3_pattern, s)) {
291 setlocale(LC_ALL, "");
292 return AIX_V3_OUTPUT;
294 if (regex(aixv2_pattern, s)) {
295 setlocale(LC_ALL, "");
296 return AIX_V2_OUTPUT;
299 if (!regexec(&bsd_pattern, s, (size_t)0, NULL, 0))
301 if (!regexec(&aixv3_pattern, s, (size_t)0, NULL, 0))
302 return AIX_V3_OUTPUT;
303 if (!regexec(&aixv2_pattern, s, (size_t)0, NULL, 0))
304 return AIX_V2_OUTPUT;
307 if (s1 = strchr(s, '\n'))
312 setlocale(LC_ALL, "");
314 return UNKNOWN_OUTPUT;
317 ///////////////////////////// LOCAL PARSERS /////////////////////////////////
320 void LocalPrintJobs(char *printer, char **job_list, int *n_jobs)
323 char *cmd = new char[60];
325 sprintf(cmd, "LANG=C enq -LP%s", printer);
326 Invoke *_thread = new Invoke(cmd, &output);
328 // run as user's UID, but with privileges from root
331 ParseAIXv3PrintJobs(printer, output, job_list, n_jobs);
341 #if defined(sun) || defined(USL) || defined(__uxp__)
343 // SUN LOCAL PARSER, actually this gets the local information from the file
344 // system, it should have the good performance since no processes (lpstat)
352 } StatusLineStruct, *StatusLine, **StatusLineList;
354 #define TMP_DIR "/usr/spool/lp/tmp"
355 #define REQ_DIR "/usr/spool/lp/requests/%s/"
356 #define SPOOL_DIR "/var/spool/lp/tmp/%s/"
358 static void check_dir(char *printer, char *tmp_dir, StatusLineList *job_list,
359 int *n_jobs, int prev_n_jobs);
360 static int SortJobs(const void *, const void *);
362 void LocalPrintJobs(char *printer, char **return_job_list, int *return_n_jobs)
365 struct dirent *dir_struct;
366 struct stat statbuff;
373 static char *job_list1 = NULL;
374 static int prev_buf_size = 0;
375 static StatusLineList job_list = NULL;
376 static int prev_n_jobs = 0;
378 if (prev_buf_size == 0)
380 prev_buf_size = BUFSIZ;
381 job_list1 = (char *)malloc(prev_buf_size);
388 // run as user's UID, but with privileges from root
392 if (getenv("TMP_DIR"))
393 chdir(getenv("TMP_DIR"));
396 if (!(lp_tmp_dir = opendir(".")))
398 *return_job_list = NULL;
405 dir_struct = readdir(lp_tmp_dir);
406 for ( ; dir_struct ; dir_struct = readdir(lp_tmp_dir))
408 if (*dir_struct->d_name == '.')
410 if (stat(dir_struct->d_name, &statbuff) >= 0 &&
411 statbuff.st_mode & S_IFDIR)
413 chdir(dir_struct->d_name);
414 check_dir(printer, dir_struct->d_name, &job_list, &n_jobs,
419 closedir(lp_tmp_dir);
420 prev_n_jobs = prev_n_jobs > n_jobs ? prev_n_jobs : n_jobs;
421 qsort(job_list, n_jobs, sizeof(StatusLineList), SortJobs);
422 for (i = 0; i < n_jobs; i++)
424 len = strlen(job_list[i]->line);
425 if (prev_buf_size < (current_size + len + 1))
426 job_list1 = (char *) realloc(job_list1, (current_size + len + 1) *
428 memcpy(job_list1 + current_size, job_list[i]->line, len);
431 *(job_list1 + current_size) = '\0';
432 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
433 *return_job_list = job_list1;
434 *return_n_jobs = n_jobs;
439 static void check_dir(char *printer, char *tmp_dir, StatusLineList *job_list,
440 int *n_jobs, int prev_n_jobs)
443 struct dirent *dir_struct;
459 StatusLineList j_list;
461 char *filename = new char[200];
462 char *filename1 = new char[200];
463 char *request = new char[300];
464 char *spool_dir = new char[300];
466 if (getenv("REQ_DIR"))
467 sprintf(request, getenv("REQ_DIR"), tmp_dir);
469 sprintf(request, REQ_DIR, tmp_dir);
470 req_len = strlen(request);
471 sprintf(spool_dir, SPOOL_DIR, tmp_dir);
472 spool_len = strlen(spool_dir);
474 if (!(lp_tmp_dir = opendir(".")))
483 dir_struct = readdir(lp_tmp_dir);
484 for ( ; dir_struct ; dir_struct = readdir(lp_tmp_dir))
486 int len = strlen(dir_struct->d_name);
489 if (strcmp(dir_struct->d_name + len - 2, "-0"))
491 *(request + req_len) = '\0';
492 strcat(request + req_len, dir_struct->d_name);
493 if (!(req = fopen(request, "r")))
495 if (!(job = fopen(dir_struct->d_name, "r")))
508 while (found && fgets(buf, 100, job))
510 line = strtok(buf, "\n");
514 if (!strcmp("immediate", line + 2))
518 if (strcmp(printer, line + 2))
522 *(spool_dir + spool_len) = '\0';
523 strncat(spool_dir, dir_struct->d_name, len - 1);
524 strcat(spool_dir, "1");
525 if (strcmp(spool_dir, line + 2))
526 strcpy(filename1, line + 2);
531 if (s = strrchr(line, ':'))
533 if (s = strrchr(line, '\''))
536 for ( ; *s == ' '; s++)
542 if (s = strstr(line, "-T"))
558 if (filename[i] != '\\')
573 if (s = strstr(line, "\\n"))
575 strcpy(title, line + 2);
584 fgets(buf, 100, req);
585 line = strtok(buf, "\n");
589 if (s = strchr(line, '!'))
596 if (s = strchr(owner, '.'))
602 case 5: strcpy(job_size, line); break;
604 secs = (time_t)atoi(line);
605 strftime(date_str, 100, "%b %e|%T", localtime(&secs));
611 if (s = strstr(dir_struct->d_name, "-0"))
621 sprintf(filename, "%s-%s", printer, dir_struct->d_name);
624 if (*n_jobs >= prev_n_jobs)
627 *job_list = (StatusLineList) malloc(sizeof(StatusLine));
629 *job_list = (StatusLineList) realloc(*job_list, (*n_jobs + 1) *
632 j_list[*n_jobs] = (StatusLine) malloc(sizeof(StatusLineStruct));
633 len = 7 + strlen(printer) + strlen(jobname) + strlen(date_str) +
634 strlen(dir_struct->d_name) + strlen(owner) + strlen(job_size);
635 j_list[*n_jobs]->line = (char *) malloc(len);
640 len = 7 + strlen(printer) + strlen(jobname) + strlen(date_str) +
641 strlen(dir_struct->d_name) + strlen(owner) + strlen(job_size);
642 j_list[*n_jobs]->line = (char *)realloc(j_list[*n_jobs]->line, len);
644 sprintf(j_list[*n_jobs]->line, "%s|%s|%s|%s|%s|%s\n", printer,
645 jobname, dir_struct->d_name, owner, date_str, job_size);
646 j_list[*n_jobs]->secs = (long) secs;
647 j_list[*n_jobs]->immediate = immediate;
653 closedir(lp_tmp_dir);
660 static int SortJobs(const void *_first, const void *_second)
662 StatusLineList first = (StatusLineList)_first;
663 StatusLineList second = (StatusLineList)_second;
665 if ((**first).immediate && !(**second).immediate)
667 if (!(**first).immediate && (**second).immediate)
669 if ((**first).immediate)
670 return (int)((**second).secs - (**first).secs);
672 return (int)((**first).secs - (**second).secs);
675 #endif // SUN and USL LOCAL PARSER
679 /* HP LOCAL PARSER - have to parse the following
681 Need to parse the following 2 forms of output:
683 coseps-28 guest priority 0 Aug 9 12:54 on coseps
688 coseps-29 guest priority 0 Aug 9 12:56 on hostname
689 (standard input) 31160 bytes
692 void LocalPrintJobs(char *printer, char **return_job_list, int *return_n_jobs)
694 char *buf = new char[300];
709 static char *job_list = NULL;
710 static int prev_buf_size = 0;
712 sprintf(buf, "lpstat -i -o%s", printer);
713 Invoke *_thread = new Invoke(buf, &output);
715 if (prev_buf_size == 0)
717 prev_buf_size = BUFSIZ;
718 job_list = (char *)malloc(prev_buf_size);
725 if (s1 = strchr(s, '\n'))
729 qname = strtok(s, "-");
730 jnumber = strtok(NULL, " ");
731 owner = strtok(NULL, " ");
734 month = strtok(NULL, " ");
735 day = strtok(NULL, " ");
736 stime = strtok(NULL, " \n");
738 hostname = strtok(NULL, " \n");
740 if (s1 = strchr(s, '\n'))
742 for (jname = s; *jname == '\t' || *jname == ' '; jname++)
744 jsize = strrchr(s, ' ');
746 jsize = strrchr(s, ' ') + 1;
747 for (c = jsize - 1; *c == ' '; c--)
750 if (hostname && strcmp(qname, hostname))
751 sprintf(buf, "%s|%s|%s|%s@%s|%s %s|%s|%s\n", qname, jname, jnumber,
752 owner, hostname, month, day, stime, jsize);
754 sprintf(buf, "%s|%s|%s|%s|%s %s|%s|%s\n", qname, jname, jnumber,
755 owner, month, day, stime, jsize);
758 if (prev_buf_size < (current_size + len + 1))
759 job_list = (char *) realloc(job_list, (current_size + len + 1) *
761 memcpy(job_list + current_size, buf, len);
765 if (s1 = strchr(s, '\n'))
768 *(job_list + current_size) = '\0';
769 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
770 *return_job_list = job_list;
775 #endif // HP LOCAL PARSER
777 #if defined(__osf__) || defined(linux) || defined(CSRG_BASED)
779 // DEC/OSF1 PARSER - Output from "lpstat -o<printer>
783 // everest.unx.dec.com: Tue Nov 29 18:44:33 1994:
784 // lps20 is ready and printing via network
785 // Rank Owner Job Files Total Size
786 // active vsp 231 /etc/printcap 845 bytes
787 // Requests on lps20:
791 // Wed Nov 30 12:20:24 1994: Attempting to print dfA000globe.unx.dec.com
792 // Rank Pri Owner Job Files Total Size
793 // active 0 root 0 /etc/printcap 407 bytes
798 // DEC/OSF1 PARSER - Output from "lpq -p<printer>
800 // No Jobs in progress:
802 // build-dec.qte.x.org: Thu Oct 3 11:17:18 1996:
807 // build-dec.qte.x.org: Fri Oct 4 09:08:48 1996:
808 // federal is ready and printing via dev
809 // Rank Owner Job Files Total Size
810 // active mgreess 65 (standard input) 13482 bytes
811 // 1st mgreess 66 (standard input) 13482 bytes
812 // 2nd mgreess 67 (standard input) 13482 bytes
817 // DEC/OSF1 V4.0 386 alpha PARSER - Output from "lpstat -o<printer>
819 // No Jobs in progress:
821 // Requests on ansel:
822 // build-dec.osf.org: Wed Jul 2 11:29:53 1997:
829 // Requests on ansel:
830 // build-dec.osf.org: Wed Jul 2 11:31:12 1997:
831 // Rank Pri Owner Job Files Total Size
832 // 1st 0 mgreess 7 ParseJobs.C 33367 bytes
838 #define NEXT_OUTPUT_LINE(line,rest) \
842 if (line && (rest = strchr(line, '\n'))) \
844 } while (NULL != line && 0 == *line);
846 void LocalPrintJobs(char *printer, char **return_job_list, int *return_n_jobs)
848 char *buf = new char[1000];
867 static char *job_list = NULL;
868 static int prev_buf_size = 0;
871 sprintf(buf, "lpstat -o%s", printer);
873 #if defined(linux) || defined(CSRG_BASED)
874 sprintf(buf, "lpq -P%s", printer);
877 Invoke *_thread = new Invoke(buf, &output);
879 if (prev_buf_size == 0)
881 prev_buf_size = BUFSIZ;
882 job_list = (char*) malloc(prev_buf_size);
890 NEXT_OUTPUT_LINE(s,s1);
893 // Parse the optional "Requests on" line of output to verify printer name.
894 // "Requests on ansel:"
897 char *opt_requests_on_line = "Requests on ";
898 if (0 == strncmp(s, opt_requests_on_line, strlen(opt_requests_on_line)))
900 char *requests = strtok(s, " ");
901 char *on = strtok(NULL, " ");
903 qname = strtok(NULL, " :\n");
904 if (0 != strncmp(qname, printer, strlen(qname)))
907 "Found the wrong printer: looking for '%s'; found '%s'\n",
910 NEXT_OUTPUT_LINE(s,s1);
915 // Parse the host/date line of output to collect host, date, and time.
916 // "build-dec.qte.x.org: Fri Oct 4 09:08:48 1996: "
919 hostname = strtok(s, ":");
920 day = strtok(NULL, " ");
921 month = strtok(NULL, " ");
922 date = strtok(NULL, " ");
923 stime = strtok(NULL, " ");
924 year = strtok(NULL, " \n");
927 NEXT_OUTPUT_LINE(s,s1);
930 // If this is the "no entries" line, we're done. Return.
934 char *no_entries_line = "no entries";
935 if (0 == strncmp(s, no_entries_line, strlen(no_entries_line)))
937 *return_job_list = job_list;
944 // Parse the optional printer status line.
945 // "federal is ready and printing via dev"
948 char *buffer = new char[128];
949 char *opt_status_line = buffer;
951 sprintf(buffer, "%s is ready and printing via ", printer);
952 if (0 == strncmp(s, opt_status_line, strlen(opt_status_line)))
954 qname = strtok(s, " \t");
960 network = strtok(s, " \n");
962 NEXT_OUTPUT_LINE(s,s1);
969 // Parse the legend line.
970 // "Rank Owner Job Files Total Size"
972 // "Rank Pri Owner Job Files Total Size"
977 tmp = strtok(s, " ");
978 if (strcmp(tmp, "Rank"))
979 fprintf(stderr, "Unexpected legend column: %s != Rank\n", tmp);
981 tmp = strtok(NULL, " ");
982 if (0 == strcmp(tmp, "Pri"))
985 tmp = strtok(NULL, " ");
987 if (strcmp(tmp, "Owner"))
988 fprintf(stderr, "Unexpected legend column: %s != Owner\n", tmp);
990 tmp = strtok(NULL, " ");
991 if (strcmp(tmp, "Job"))
992 fprintf(stderr, "Unexpected legend column: %s != Job\n", tmp);
994 tmp = strtok(NULL, " ");
995 if (strcmp(tmp, "Files"))
996 fprintf(stderr, "Unexpected legend column: %s != Files\n", tmp);
998 tmp = strtok(NULL, " ");
999 if (strcmp(tmp, "Total"))
1000 fprintf(stderr, "Unexpected legend column: %s != Total\n", tmp);
1002 tmp = strtok(NULL, " \n");
1003 if (strcmp(tmp, "Size"))
1004 fprintf(stderr, "Unexpected legend column: %s != Size\n", tmp);
1008 NEXT_OUTPUT_LINE(s,s1);
1011 // Parse the job lines.
1012 // "active mgreess 65 (standard input) 13482 bytes"
1014 // "1st 0 mgreess 7 ParseJobs.C 33367 bytes"
1021 owner = strtok(NULL, " ");
1022 jnumber = strtok(NULL, " ");
1023 jname = strtok(NULL," ");
1024 jsize = strtok(NULL," ");
1026 if (NULL == owner || NULL == jnumber || NULL == jname || NULL == jsize)
1028 NEXT_OUTPUT_LINE(s,s1);
1035 if (hostname && strcmp(qname, hostname))
1036 sprintf(buf, "%s|%s|%s|%s@%s|%s %s|%s|%s\n", qname, jname, jnumber,
1037 owner, hostname, month, date, stime, jsize);
1039 sprintf(buf, "%s|%s|%s|%s|%s %s|%s|%s\n", qname, jname, jnumber,
1040 owner, month, date, stime, jsize);
1042 printf("qname, jname, jnumber, owner, ");
1043 printf("hostname, month, date, stime, jsize\n");
1044 printf("%s\n", buf);
1047 if (prev_buf_size < (current_size + len + 1))
1049 (char*) realloc(job_list, (current_size + len + 1) * sizeof(char*));
1050 memcpy(job_list + current_size, buf, len);
1051 current_size += len;
1054 NEXT_OUTPUT_LINE(s,s1);
1057 *(job_list + current_size) = '\0';
1058 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
1059 *return_job_list = job_list;
1063 #endif // DEC local parser
1066 /* BSD PARSER - have to parse the following
1068 BSD, HP, and SUN output
1069 Warning: test1 is down: b906ps3 is ready and printing
1070 Warning: no daemon present
1072 root: 1st [job 006b906ps3.austin.ibm.com]
1074 root: 2nd [job 006b906ps3.austin.ibm.com]
1075 <File name not available> 421 bytes
1078 int ParseBSDPrintJobs(char *printer, char *jobs,
1079 char **return_job_list, int *return_n_jobs)
1091 char *buf = new char[300];
1092 static char *job_list = NULL;
1093 static int prev_buf_size = 0;
1094 static int first_time = 1;
1098 static char *bsd_pattern;
1100 * Due to bug in regcmp/regex (bug id 1191772), change to C locale for
1101 * this parsing work. And change back at end of procedure. This workaround
1102 * appears to be ok since the print service output parsed here is in a
1103 * "C locale" 8-bit form for inter-machine networking.
1105 setlocale(LC_ALL, "C");
1109 bsd_pattern = regcmp(":.*\\[.*\\]", (char *)NULL);
1113 static regex_t bsd_pattern;
1117 regcomp(&bsd_pattern, ":.*\\[.*\\]", REG_NOSUB);
1122 if (prev_buf_size == 0)
1124 prev_buf_size = BUFSIZ;
1125 job_list = (char *)malloc(prev_buf_size);
1131 sdate = MESSAGE(NotAvailableL);
1134 s = strtok(jobs, "\n");
1138 if (regex(bsd_pattern, s))
1140 if (!regexec(&bsd_pattern, s, (size_t)0, NULL, 0))
1148 for (s = strchr(s, ' ') + 1; isdigit((int)*s); s++)
1151 for (s1 = s; *s1 == ' '; s1++)
1154 if (s = strchr(hostname, '.'))
1157 *(strchr(hostname, ']')) = '\0';
1159 s = strtok(NULL, "\n");
1160 for (s1 = s; *s1 == ' ' || *s1 == '\t'; s1++)
1163 s1 = strrchr(s, ' ');
1165 s1 = strrchr(s, ' ');
1167 for ( ; *s1 == ' '; s1--)
1170 sprintf(buf, "%s|%s|%s|%s@%s|%s|%s|%s\n", printer, jname, jnumber,
1171 owner, hostname, sdate, stime, jsize);
1173 if (prev_buf_size < (current_size + len + 1))
1174 job_list = (char *) realloc(job_list, (current_size + len + 1) *
1176 memcpy(job_list + current_size, buf, len);
1177 current_size += len;
1182 if (strstr(s, "down"))
1185 s = strtok(NULL, "\n");
1187 *(job_list + current_size) = '\0';
1188 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
1189 *return_job_list = job_list;
1192 setlocale(LC_ALL, "");
1199 /* AIX version 3 and 4 PARSER - have to parse the following
1201 Queue Dev Status Job Name From To
1202 Submitted Rnk Pri Blks Cp PP %
1203 ------- ----- --------- --------- --- --- ----- --- ---- --
1204 bsh bshde RUNNING 956 STDIN.14937 root root
1205 08/02/94 09:55:44 1 15 1 1 0 0
1206 /var/spool/qdaemon/tOlkCSM
1210 Queue Dev Status Job Name From To
1211 Submitted Rnk Pri Blks Cp PP %
1212 ------- ----- --------- --------- --- --- ----- --- ---- --
1214 QUEUED 957 STDIN.14952 root root
1215 08/02/94 10:17:53 1 15 1 1
1216 /var/spool/qdaemon/tOmgCrx
1219 Also need to parse filenames that are titles: Example, "My Report" below.
1221 QUEUED 957 My Report root root
1222 08/02/94 10:17:53 1 15 1 1
1223 /var/spool/qdaemon/tOmgCrx
1227 int ParseAIXv3PrintJobs(char *_printer, char *jobs,
1228 char **return_job_list, int *return_n_jobs)
1230 char *buf = new char[300];
1231 struct stat statbuff;
1245 static char *job_list = NULL;
1246 static int prev_buf_size = 0;
1248 strcpy(printer, _printer);
1249 if (s = strchr(printer, ':'))
1252 if (prev_buf_size == 0)
1254 prev_buf_size = BUFSIZ;
1255 job_list = (char *)malloc(prev_buf_size);
1263 s1 = strchr(s, '\n');
1265 s1 = strchr(s, '\n');
1267 s1 = strchr(s, '\n');
1269 if (s1 = strchr(s, '\n'))
1271 if (strstr(s, "DOWN"))
1275 dollar1 = strtok(s, " ");
1276 if (!strncmp(dollar1, printer, strlen(dollar1)))
1281 jnumber = strtok(NULL, " ");
1282 if (!(jnumber && *jnumber))
1285 if (s1 = strchr(s, '\n'))
1289 jname = strtok(NULL, "\n");
1290 if (!(jname && *jname))
1293 if (s1 = strchr(s, '\n'))
1297 for (c = jname + strlen(jname) - 1; *c == ' '; c--)
1299 for ( ; *c != ' '; c--)
1301 for ( ; *c == ' '; c--)
1304 for ( ; *c != ' '; c--)
1307 for ( ; *c == ' '; c--)
1310 for (c = jname; *c == ' '; c++)
1314 if (s1 = strchr(s, '\n'))
1316 sdate = strtok(s, " ");
1317 stime = strtok(NULL, " ");
1320 jsize = strtok(NULL, " ");
1322 if (s1 = strchr(s, '\n'))
1324 c = strtok(s, " \n");
1325 if (strstr(c, jname))
1328 statbuff.st_size = atoi(jsize) * 512;
1329 else if (stat(c, &statbuff) < 0)
1330 statbuff.st_size = atoi(jsize) * 512;
1332 sprintf(buf, "%s|%s|%s|%s|%s|%s|%d\n", printer, jname, jnumber,
1333 owner, sdate, stime, (int)statbuff.st_size);
1335 if (prev_buf_size < (current_size + len + 1))
1336 job_list = (char *) realloc(job_list, (current_size + len + 1) *
1338 memcpy(job_list + current_size, buf, len);
1339 current_size += len;
1342 if (s1 = strchr(s, '\n'))
1345 *(job_list + current_size) = '\0';
1346 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
1347 *return_job_list = job_list;
1352 /* AIX version 2 PARSER - have to parse the following
1354 dev arg status request pp output % done
1355 --- ---------- ---------- -------------------- --------- ------
1362 queue user request blks cops pri time to
1363 ----- ----------------- -------------------- ---- ---- --- ----- --------
1364 ts1 root /etc/motd 2 1 15 15:57 root
1365 ts1 root@warpspeed /etc/rc.afs 3 1 15 16:03 root@war
1366 ts2 root /.profile 1 1 15 16:05 root
1367 ts2 root /.profile 1 1 15 16:06 root
1368 ts2 root@warpspeed /etc/rc.afs 3 1 15 16:07 root@war
1372 int ParseAIXv2PrintJobs(char *printer, char *jobs,
1373 char **return_job_list, int *return_n_jobs)
1375 char *buf = new char[300];
1389 static char *job_list = NULL;
1390 static int prev_buf_size = 0;
1392 if (prev_buf_size == 0)
1394 prev_buf_size = BUFSIZ;
1395 job_list = (char *)malloc(prev_buf_size);
1401 sdate = MESSAGE(NotAvailableL);
1405 s1 = strchr(s, '\n');
1407 s1 = strchr(s, '\n');
1409 if (s1 = strchr(s, '\n'))
1413 device = strtok(s, " ");
1414 tmp = strtok(NULL, " ");
1415 c = strtok(NULL, " ");
1416 if (!strcmp(tmp, printer))
1418 if (strstr(c, "OFF"))
1423 if (s1 = strchr(s, '\n'))
1427 if (s1 = strchr(s, '\n'))
1431 tmp = strtok(s, " ");
1432 if (!tmp || strcmp(tmp, device))
1436 if (s1 = strchr(s, '\n'))
1440 owner = strtok(NULL, " ");
1441 jname = strtok(NULL, " ");
1442 jsize = strtok(NULL, " ");
1445 stime = strtok(NULL, " ");
1446 if (c = strchr(owner, '.'))
1448 sprintf(buf, "%s|%s|%s|%s|%s|%s|%d\n", printer, jname, jnumber,
1449 owner, sdate, stime, atoi(jsize) * 512);
1451 if (prev_buf_size < (current_size + len + 1))
1452 job_list = (char *) realloc(job_list, (current_size + len + 1) *
1454 memcpy(job_list + current_size, buf, len);
1455 current_size += len;
1458 if (s1 = strchr(s, '\n'))
1461 *(job_list + current_size) = '\0';
1462 prev_buf_size = prev_buf_size > current_size ? prev_buf_size : current_size;
1463 *return_job_list = job_list;