/*
+ * $Id: queries.c,v 1.8.2.1 2002-03-12 15:44:38 srittau Exp $
+ *
* Copyright (c) 1990,1994 Regents of The University of Michigan.
* All Rights Reserved. See COPYRIGHT.
*/
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif /* HAVE_CONFIG_H */
+
#include <string.h>
-#include <sys/syslog.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <syslog.h>
#include <sys/param.h>
#include <sys/time.h>
#include <sys/types.h>
#ifdef KRB
#ifdef SOLARIS
#include <kerberos/krb.h>
-#else
+#else /* SOLARIS */
#include <krb.h>
-#endif
-#endif KRB
+#endif /* SOLARIS */
+#endif /* KRB */
#include "file.h"
#include "comment.h"
#include "printer.h"
#include "ppd.h"
+#include "lp.h"
+#include "uam_auth.h"
+
+int cq_default( struct papfile *, struct papfile * );
+int cq_k4login( struct papfile *, struct papfile * );
+int cq_uameth( struct papfile *, struct papfile * );
+
+int gq_balance( struct papfile * );
+int gq_pagecost( struct papfile * );
+int gq_true( struct papfile * );
+int gq_rbispoolerid( struct papfile * );
+int gq_rbiuamlist( struct papfile * );
+
+int cq_query( struct papfile *, struct papfile * );
+void cq_font_answer( char *, char *, struct papfile * );
+int cq_font( struct papfile *, struct papfile * );
+int cq_feature( struct papfile *, struct papfile * );
+int cq_printer( struct papfile *, struct papfile * );
+int cq_rmjob( struct papfile *, struct papfile * );
+int cq_listq( struct papfile *, struct papfile * );
+int cq_rbilogin( struct papfile *, struct papfile * );
-cq_default( in, out )
+
+
+int cq_default( in, out )
struct papfile *in, *out;
{
char *start, *stop, *p;
- struct comment *comment = compeek();
+ int linelength, crlflength;
+ struct papd_comment *comment = compeek();
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
return( CH_MORE );
}
+ stop = start+linelength;
+
if ( comgetflags() == 0 ) { /* started */
if ( comment->c_end ) {
comsetflags( 1 );
} else {
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
} else {
/* return default */
- if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
+ if ( comcmp( start, start+linelength, comment->c_end, 0 ) == 0 ) {
for ( p = start; p < stop; p++ ) {
if ( *p == ':' ) {
break;
p++;
}
- *stop = '\n';
- APPEND( out, p, stop - p + 1 );
+ append( out, p, stop - p + crlflength );
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
#define h2b(x) (isdigit((x))?(x)-'0':(isupper((x))?(x)-'A':(x)-'a')+10)
-cq_k4login( in, out )
+int cq_k4login( in, out )
struct papfile *in, *out;
{
- char *start, *stop, *p;
+ char *start, *p;
+ int linelength, crlflength;
unsigned char *t;
- struct comment *comment = compeek();
+ struct papd_comment *comment = compeek();
KTEXT_ST tkt;
AUTH_DAT ad;
int rc, i;
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
}
bzero( &tkt, sizeof( tkt ));
+ stop = start+linelength;
for ( i = 0, t = tkt.dat; p < stop; p += 2, t++, i++ ) {
*t = ( h2b( (unsigned char)*p ) << 4 ) +
h2b( (unsigned char)*( p + 1 ));
if (( rc = krb_rd_req( &tkt, "LaserWriter", printer->p_name,
0, &ad, "" )) != RD_AP_OK ) {
syslog( LOG_ERR, "cq_k4login: %s", krb_err_txt[ rc ] );
- APPEND( out, LoginFailed, strlen( LoginFailed ));
+ append( out, LoginFailed, strlen( LoginFailed ));
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
syslog( LOG_INFO, "cq_k4login: %s.%s@%s", ad.pname, ad.pinst,
lp_person( ad.pname );
lp_host( ad.prealm );
- APPEND( out, LoginOK, strlen( LoginOK ));
+ append( out, LoginOK, strlen( LoginOK ));
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength);
return( CH_DONE );
}
char *uameth = "UMICHKerberosIV\n*\n";
-cq_uameth( in, out )
+int cq_uameth( in, out )
struct papfile *in, *out;
{
- char *start, *stop;
- struct comment *c, *comment = compeek();
+ char *start;
+ int linelength, crlflength;
+ struct papd_comment *c, *comment = compeek();
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
}
if ( comgetflags() == 0 ) { /* start */
- if (( printer->p_flags & P_AUTH ) == 0 ) { /* no kerberos */
+ if (( printer->p_flags & P_KRB ) == 0 ) { /* no kerberos */
if ( comswitch( queries, cq_default ) < 0 ) {
syslog( LOG_ERR, "cq_uameth: can't find default!" );
exit( 1 );
comsetflags( 1 );
} else {
if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) { /* end */
- APPEND( out, uameth, strlen( uameth ));
+ append( out, uameth, strlen( uameth ));
compop();
return( CH_DONE );
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
-#endif KRB
+#endif /* KRB */
-gq_true( out )
+int gq_true( out )
struct papfile *out;
{
if ( printer->p_flags & P_SPOOLED ) {
- APPEND( out, "true\n", 5 );
+ append( out, "true\n", 5 );
return( 0 );
} else {
return( -1 );
}
}
-gq_pagecost( out )
+int gq_pagecost( out )
struct papfile *out;
{
char cost[ 60 ];
/* check for spooler? XXX */
if ( printer->p_pagecost_msg != NULL ) {
- APPEND( out, printer->p_pagecost_msg,
+ append( out, printer->p_pagecost_msg,
strlen( printer->p_pagecost_msg ));
} else if ( printer->p_flags & P_ACCOUNT ) {
#ifdef ABS_PRINT
lp_pagecost();
-#endif ABS_PRINT
+#endif /* ABS_PRINT */
sprintf( cost, "%d", printer->p_pagecost );
- APPEND( out, cost, strlen( cost ));
+ append( out, cost, strlen( cost ));
} else {
return( -1 );
}
- APPEND( out, "\n", 1 );
+ append( out, "\n", 1 );
return( 0 );
}
#ifdef ABS_PRINT
-gq_balance( out )
+int gq_balance( out )
struct papfile *out;
{
char balance[ 60 ];
return( -1 );
}
sprintf( balance, "$%1.2f\n", printer->p_balance );
- APPEND( out, balance, strlen( balance ));
+ append( out, balance, strlen( balance ));
return( 0 );
}
-#endif ABS_PRINT
+#endif /* ABS_PRINT */
+
+
+/*
+ * Handler for RBISpoolerID
+ */
+
+static const char *spoolerid = "(PAPD Spooler) 2.1 (2.1.4 pre-release)\n";
+
+int gq_rbispoolerid( out )
+ struct papfile *out;
+{
+ append( out, spoolerid, strlen( spoolerid ));
+ return(0);
+}
+
+
+
+/*
+ * Handler for RBIUAMListQuery
+ */
+
+static const char *nouams = "*\n";
+
+int gq_rbiuamlist( out )
+ struct papfile *out;
+{
+ char uamnames[128] = "\0";
+
+ if (printer->p_flags & P_AUTH_PSSP) {
+ if (getuamnames(UAM_SERVER_PRINTAUTH, uamnames) < 0) {
+ append(out, nouams, strlen(nouams));
+ return(0);
+ } else {
+ append(out, uamnames, strlen(uamnames));
+ return(0);
+ }
+ } else {
+ append(out, nouams, strlen(nouams));
+ return(0);
+ }
+}
+
struct genquery {
char *gq_name;
{ "UMICHCostPerPage", gq_pagecost },
#ifdef notdef
{ "UMICHUserBalance", gq_balance },
-#endif
+#endif /* notdef */
+ { "RBISpoolerID", gq_rbispoolerid },
+ { "RBIUAMListQuery", gq_rbiuamlist },
{ "UMICHListQueue", gq_true },
{ "UMICHDeleteJob", gq_true },
{ NULL },
};
-cq_query( in, out )
+int cq_query( in, out )
struct papfile *in, *out;
{
char *start, *stop, *p, *q;
- struct comment *comment = compeek();
+ int linelength, crlflength;
+ struct papd_comment *comment = compeek();
struct genquery *gq;
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
return( CH_MORE );
}
+ stop = start+linelength;
+
if ( comgetflags() == 0 ) { /* started */
comsetflags( 1 );
} else {
if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
-cq_font_answer( start, stop, out )
+void cq_font_answer( start, stop, out )
char *start, *stop;
struct papfile *out;
{
if ( q != buf ) {
*q = '\0';
- APPEND( out, "/", 1 );
- APPEND( out, buf, strlen( buf ));
- APPEND( out, ":", 1 );
+ append( out, "/", 1 );
+ append( out, buf, strlen( buf ));
+ append( out, ":", 1 );
if (( pfo = ppd_font( buf )) == NULL ) {
- APPEND( out, "No\n", 3 );
+ append( out, "No\n", 3 );
} else {
- APPEND( out, "Yes\n", 4 );
+ append( out, "Yes\n", 4 );
}
}
}
return;
}
-cq_font( in, out )
+int cq_font( in, out )
struct papfile *in, *out;
{
char *start, *stop, *p;
- struct comment *comment = compeek();
+ int linelength, crlflength;
+ struct papd_comment *comment = compeek();
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
return( CH_MORE );
}
+ stop = start + linelength;
+
if ( comgetflags() == 0 ) {
comsetflags( 1 );
} else {
comsetflags( 2 );
if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
- APPEND( out, "*\n", 2 );
+ append( out, "*\n", 2 );
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
-cq_feature( in, out )
+int cq_feature( in, out )
struct papfile *in, *out;
{
char *start, *stop, *p;
- struct comment *comment = compeek();
+ int linelength, crlflength;
+ struct papd_comment *comment = compeek();
struct ppd_feature *pfe;
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
return( CH_MORE );
}
+ stop = start + linelength;
+
if ( comgetflags() == 0 ) {
comsetflags( 1 );
return( CH_DONE );
}
- APPEND( out, pfe->pd_value, strlen( pfe->pd_value ));
- APPEND( out, "\r", 1 );
+ append( out, pfe->pd_value, strlen( pfe->pd_value ));
+ append( out, "\r", 1 );
} else {
if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
static const char *psver = "*PSVersion\n";
static const char *prod = "*Product\n";
-cq_printer( in, out )
+int cq_printer( in, out )
struct papfile *in, *out;
{
- char *start, *stop, *p;
- struct comment *c, *comment = compeek();
+ char *start, *p;
+ int linelength, crlflength;
+ struct papd_comment *comment = compeek();
struct ppd_feature *pdpsver, *pdprod;
for (;;) {
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
}
/* revision */
- APPEND( out, p + 1, strlen( p + 1 ));
- APPEND( out, "\r", 1 );
+ append( out, p + 1, strlen( p + 1 ));
+ append( out, "\r", 1 );
/* version */
- APPEND( out, pdpsver->pd_value, p - pdpsver->pd_value );
- APPEND( out, "\r", 1 );
+ append( out, pdpsver->pd_value, p - pdpsver->pd_value );
+ append( out, "\r", 1 );
/* product */
- APPEND( out, pdprod->pd_value, strlen( pdprod->pd_value ));
- APPEND( out, "\r", 1 );
+ append( out, pdprod->pd_value, strlen( pdprod->pd_value ));
+ append( out, "\r", 1 );
} else {
- if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
+ if ( comcmp( start, start+linelength, comment->c_end, 0 ) == 0 ) {
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
}
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
}
}
static const char *rmjobfailed = "Failed\n";
static const char *rmjobok = "Ok\n";
-cq_rmjob( in, out )
+int cq_rmjob( in, out )
struct papfile *in, *out;
{
char *start, *stop, *p;
+ int linelength, crlflength;
int job;
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
return( CH_MORE );
}
+ stop = start + linelength;
+
for ( p = start; p < stop; p++ ) {
if ( *p == ' ' || *p == '\t' ) {
break;
*stop = '\0';
if ( p < stop && ( job = atoi( p )) > 0 ) {
lp_rmjob( job );
- APPEND( out, rmjobok, strlen( rmjobok ));
+ append( out, rmjobok, strlen( rmjobok ));
} else {
- APPEND( out, rmjobfailed, strlen( rmjobfailed ));
+ append( out, rmjobfailed, strlen( rmjobfailed ));
}
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
-cq_listq( in, out )
+int cq_listq( in, out )
struct papfile *in, *out;
{
- char *start, *stop;
+ char *start;
+ int linelength, crlflength;
- switch ( markline( &start, &stop, in )) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
case 0 :
return( 0 );
}
compop();
- consumetomark( start, stop, in );
+ CONSUME( in, linelength + crlflength );
return( CH_DONE );
}
+
+/*
+ * Handler for RBILogin
+ */
+
+static struct uam_obj *papd_uam = NULL;
+static const char *rbiloginok = "0\r";
+static const char *rbiloginbad = "-1\r";
+static const char *rbiloginerrstr = "%%[Error: SecurityError; \
+SecurityViolation: Unknown user, incorrect password or log on is \
+disabled ]%%\r%%Flushing: rest of job (to end-of-file) will be \
+ignored ]%%\r";
+
+int cq_rbilogin( in, out )
+ struct papfile *in, *out;
+{
+ char *start, *stop, *p, *begin;
+ int linelength, crlflength;
+ char username[9] = "\0";
+ struct papd_comment *comment = compeek();
+ char uamtype[20] = "\0";
+
+ for (;;) {
+ switch ( markline( in, &start, &linelength, &crlflength )) {
+ case 0 :
+ return( 0 );
+
+ case -1 :
+ return( CH_MORE );
+ }
+
+ stop = start + linelength;
+
+ if ( comgetflags() == 0 ) { /* first line */
+ begin = start + strlen(comment->c_begin);
+ p = begin;
+
+ while (*p != ' ') {
+ p++;
+ }
+
+ strncat(uamtype, begin, p - begin);
+
+ if ((papd_uam = auth_uamfind(UAM_SERVER_PRINTAUTH,
+ uamtype, strlen(uamtype))) == NULL) {
+ syslog(LOG_INFO, "Could not find uam: %s", uamtype);
+ append(out, rbiloginbad, strlen(rbiloginbad));
+ append(out, rbiloginerrstr, strlen(rbiloginerrstr));
+ } else {
+ if ( (papd_uam->u.uam_printer(p,stop,username,out)) == 0 ) {
+ lp_person( username );
+ } else {
+ append(out, rbiloginbad, strlen( rbiloginbad));
+ append(out, rbiloginerrstr, strlen(rbiloginerrstr));
+ }
+ }
+ comsetflags( 1 );
+ } else {
+ if ( comcmp( start, stop, comment->c_end, 0 ) == 0 ) {
+ compop();
+ return( CH_DONE );
+ }
+ }
+
+ CONSUME( in, linelength + crlflength );
+ }
+}
+
+
/*
* All queries start with %%?Begin and end with %%?End. Note that the
* "Begin"/"End" general queries have to be last.
*/
-struct comment queries[] = {
+struct papd_comment queries[] = {
#ifdef KRB
{ "%%Login: UMICHKerberosIV", 0, cq_k4login, 0 },
{ "%%?BeginUAMethodsQuery", "%%?EndUAMethodsQuery:", cq_uameth, C_FULL },
-#endif KRB
+#endif /* KRB */
{ "%UMICHListQueue", 0, cq_listq, C_FULL },
{ "%UMICHDeleteJob", 0, cq_rmjob, 0 },
+ { "%%?BeginQuery: RBILogin ", "%%?EndQuery", cq_rbilogin, 0 },
{ "%%?BeginQuery", "%%?EndQuery", cq_query, 0 },
{ "%%?BeginFeatureQuery", "%%?EndFeatureQuery", cq_feature, 0 },
{ "%%?BeginFontQuery", "%%?EndFontQuery", cq_font, 0 },