summaryrefslogtreecommitdiff
path: root/usr/src/lib/print
diff options
context:
space:
mode:
authorGordon Ross <gwr@nexenta.com>2015-02-11 22:03:23 -0500
committerGordon Ross <gwr@nexenta.com>2015-02-20 17:39:46 -0500
commitb0e753dd6a955fb2f10a0ce17d32bd33172e0400 (patch)
tree0f7dce01db9bba61fdfbc85e8bc39a74bad6fca1 /usr/src/lib/print
parente6cb0f7efa539f8e48e8c1be930a922d8f78ff21 (diff)
downloadillumos-joyent-b0e753dd6a955fb2f10a0ce17d32bd33172e0400.tar.gz
5609 port mod_ipp to Apache 2.2
Reviewed by: Garrett D'Amore <garrett@damore.org> Reviewed by: Alexander Pyhalov <alp@rsu.ru> Approved by: Garrett D'Amore <garrett@damore.org>
Diffstat (limited to 'usr/src/lib/print')
-rw-r--r--usr/src/lib/print/mod_ipp/Makefile40
-rw-r--r--usr/src/lib/print/mod_ipp/httpd-standalone-ipp.conf38
-rw-r--r--usr/src/lib/print/mod_ipp/httpd-syms.map43
-rw-r--r--usr/src/lib/print/mod_ipp/ipp-listener.xml3
-rw-r--r--usr/src/lib/print/mod_ipp/mod_ipp.c129
5 files changed, 162 insertions, 91 deletions
diff --git a/usr/src/lib/print/mod_ipp/Makefile b/usr/src/lib/print/mod_ipp/Makefile
index 8d6500fb41..395c75e0e3 100644
--- a/usr/src/lib/print/mod_ipp/Makefile
+++ b/usr/src/lib/print/mod_ipp/Makefile
@@ -22,6 +22,8 @@
# Copyright 2010 Sun Microsystems, Inc. All rights reserved.
# Use is subject to license terms.
#
+# Copyright 2015 Nexenta Systems, Inc. All rights reserved.
+#
LIBRARY = mod_ipp.a
VERS =
@@ -30,13 +32,22 @@ OBJECTS = mod_ipp.o
include ../../Makefile.lib
include ../../Makefile.rootfs
-APACHEMODDIR = $(ROOT)/usr/apache/libexec
-APACHECONFDIR = $(ROOT)/etc/apache
+# These *BASE paths are used ONLY at build time to locate headers.
+# This builds against Apache 2.2 but the module should work with
+# any Apache 2.x version
+APACHEBASE = /usr/apache2/2.2
+APR_BASE = /usr/apr
+APRUBASE = /usr/apr-util
+
+IPPCONFDIR = $(ROOT)/etc/lp/ipp
+IPPLIBDIR = $(ROOT)/usr/lib/lp/ipp
LISTENERDIR = $(ROOT)/var/lp/ipp-listener
-ROOTDIRS = $(ROOT)/usr/apache $(APACHEMODDIR) $(APACHECONFDIR) \
+ROOTDIRS = $(ROOT)/etc/lp $(IPPCONFDIR) \
+ $(ROOT)/usr/lib/lp $(IPPLIBDIR) \
$(ROOT)/var/lp $(LISTENERDIR)
+$(ROOT)/etc/lp:= DIRMODE = 775
$(ROOT)/var/lp:= DIRMODE = 775
$(ROOT)/var/lp:= FILEMODE = 775
@@ -48,11 +59,17 @@ SRCS = $(OBJECTS:%.o = %.c)
CFLAGS += $(CCVERBOSE)
CPPFLAGS += -I../libipp-listener/common
CPPFLAGS += -I../libipp-core/common
-CPPFLAGS += -I/usr/apache/include
+CPPFLAGS += -I$(ADJUNCT_PROTO)$(APACHEBASE)/include
+CPPFLAGS += -I$(ADJUNCT_PROTO)$(APR_BASE)/include
+CPPFLAGS += -I$(ADJUNCT_PROTO)$(APRUBASE)/include
+CPPFLAGS += -DAPACHE2
CPPFLAGS += -DEAPI
-ZDEFS = $(ZNODEFS)
-MAPFILES = mapfile
+# See: /usr/apache2/2.2/build/config_vars.mk
+# Make sure to build with compatible flags.
+CPPFLAGS += -D_REENTRANT -D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64
+
+MAPFILES = mapfile httpd-syms.map
LDLIBS += -lipp-listener -lipp-core -lpapi -lc
@@ -63,19 +80,20 @@ ROOTMANIFEST= $(MANIFEST:%=$(ROOTMANIFESTDIR)/%)
$(ROOTMANIFEST) := FILEMODE= 444
# Apache module
-$(APACHEMODDIR)/$(LIBLINKS): $(ROOTDIRS)
+# LIBLINKS is not a link here, just the bare *.so name
+$(IPPLIBDIR)/$(LIBLINKS): $(ROOTDIRS)
# Apache config
-APACHECONFFILE= $(APACHECONFDIR)/httpd-standalone-ipp.conf
+APACHECONFFILE= $(IPPCONFDIR)/httpd-standalone-ipp.conf
$(APACHECONFFILE) := FILEMODE= 644
LISTENERFILE= $(LISTENERDIR)/index.html
$(LISTENERFILE) := FILEMODE= 444
$(ROOT)/var/lp:= FILEMODE = 0775
-$(APACHEMODDIR)/$(LIBLINKS):= FILEMODE = 0555
+$(IPPLIBDIR)/$(LIBLINKS):= FILEMODE = 0555
-$(ROOTMANIFESTDIR)/% $(APACHEMODDIR)/% $(APACHECONFDIR)/% $(LISTENERDIR)/%: %
+$(ROOTMANIFESTDIR)/% $(IPPLIBDIR)/% $(IPPCONFDIR)/% $(LISTENERDIR)/%: %
$(INS.file)
$(ROOTDIRS):
@@ -85,7 +103,7 @@ $(ROOTDIRS):
all: $(LIBS)
-install: all $(APACHEMODDIR)/$(LIBLINKS) $(APACHECONFFILE) \
+install: all $(IPPLIBDIR)/$(LIBLINKS) $(APACHECONFFILE) \
$(LISTENERFILE) $(ROOTMANIFEST)
install_h:
diff --git a/usr/src/lib/print/mod_ipp/httpd-standalone-ipp.conf b/usr/src/lib/print/mod_ipp/httpd-standalone-ipp.conf
index 07a4b8dc11..419f23fb93 100644
--- a/usr/src/lib/print/mod_ipp/httpd-standalone-ipp.conf
+++ b/usr/src/lib/print/mod_ipp/httpd-standalone-ipp.conf
@@ -28,8 +28,6 @@
# "$Id: httpd-standalone-ipp.conf,v 1.4 2006/03/24 00:26:54 njacobs Exp $"
#
-# ident "%Z%%M% %I% %E% SMI"
-
##
## httpd-standalone-ipp.conf -- Apache HTTP server configuration file for
## an Internet Print Protocol (IPP) listener
@@ -53,12 +51,6 @@
#
#
-# ServerType is either inetd, or standalone. Inetd mode is only supported on
-# Unix platforms.
-#
-ServerType standalone
-
-#
# ServerRoot: The top of the directory tree under which the server's
# configuration, error, and log files are kept.
#
@@ -67,7 +59,8 @@ ServerType standalone
# (available at <URL:http://www.apache.org/docs/mod/core.html#lockfile>);
# you will save yourself a lot of trouble.
#
-ServerRoot "/usr/apache"
+# Change /usr/apache2/... if Apache 2.x is elsewhere.
+ServerRoot "/usr/apache2/2.2"
#
# The LockFile directive sets the path to the lockfile used when Apache
@@ -192,24 +185,14 @@ MaxRequestsPerChild 10
# Note: The order in which modules are loaded is important. Don't change
# the order below without expert advice.
#
-LoadModule access_module libexec/mod_access.so
LoadModule alias_module libexec/mod_alias.so
-LoadModule auth_module libexec/mod_auth.so
+LoadModule auth_basic_module libexec/mod_auth_basic.so
+LoadModule authn_file_module libexec/mod_authn_file.so
+LoadModule authz_host_module libexec/mod_authz_host.so
+LoadModule authz_user_module libexec/mod_authz_user.so
LoadModule mime_module libexec/mod_mime.so
LoadModule mime_magic_module libexec/mod_mime_magic.so
-LoadModule ipp_module libexec/mod_ipp.so
-
-# Reconstruction of the complete module list from all available modules
-# (static and shared ones) to achieve correct module execution order.
-# [WHENEVER YOU CHANGE THE LOADMODULE SECTION ABOVE UPDATE THIS, TOO]
-ClearModuleList
-AddModule mod_access.c
-AddModule mod_alias.c
-AddModule mod_auth.c
-AddModule mod_mime.c
-AddModule mod_mime_magic.c
-AddModule mod_ipp.c
-AddModule mod_so.c
+LoadModule ipp_module /usr/lib/lp/ipp/mod_ipp.so
### Section 2: 'Main' server configuration
#
@@ -234,11 +217,11 @@ AddModule mod_so.c
# Port: The port to which the standalone server listens. For
# ports < 1023, you will need httpd to be run as root initially.
#
-Port 631
+Listen 631
#
# If you wish httpd to run as a different user or group, you must run
-# httpd as root initially and it will switch.
+# httpd as root initially and it will switch.
#
# User/Group: The name (or #number) of the user/group to run httpd as.
# . On SCO (ODT 3) use "User nouser" and "Group nogroup".
@@ -327,6 +310,8 @@ Alias /etc/lp/ppd/ /etc/lp/ppd/
# ipp-default-user nobody
ipp-default-service lpsched
+ # To be more restrictive, use this intead:
+ # ipp-operation required on
ipp-operation all on
AuthType Basic
@@ -338,4 +323,3 @@ Alias /etc/lp/ppd/ /etc/lp/ppd/
ErrorDocument 404 /index.html
</Location>
</IfModule>
-
diff --git a/usr/src/lib/print/mod_ipp/httpd-syms.map b/usr/src/lib/print/mod_ipp/httpd-syms.map
new file mode 100644
index 0000000000..2a08f20538
--- /dev/null
+++ b/usr/src/lib/print/mod_ipp/httpd-syms.map
@@ -0,0 +1,43 @@
+#
+# This file and its contents are supplied under the terms of the
+# Common Development and Distribution License ("CDDL"), version 1.0.
+# You may only use this file in accordance with the terms of version
+# 1.0 of the CDDL.
+#
+# A full copy of the text of the CDDL should have accompanied this
+# source. A copy of the CDDL is also available via the Internet at
+# http://www.illumos.org/license/CDDL.
+#
+
+#
+# Copyright 2015 Nexenta Systems, Inc. All rights reserved.
+#
+
+#
+# These are the symbols in Apache (httpd) that this module needs
+# to bind with. By explicitly telling the linker these are external,
+# we can detect any other binding problems at link time.
+#
+
+$mapfile_version 2
+
+SYMBOL_SCOPE {
+ core_module { TYPE = data; FLAGS = extern };
+
+ ap_discard_request_body { TYPE = function; FLAGS = extern };
+ ap_get_client_block { TYPE = function; FLAGS = extern };
+ ap_get_remote_host { TYPE = function; FLAGS = extern };
+ ap_get_server_name { TYPE = function; FLAGS = extern };
+ ap_get_server_port { TYPE = function; FLAGS = extern };
+ ap_hook_default_port { TYPE = function; FLAGS = extern };
+ ap_hook_handler { TYPE = function; FLAGS = extern };
+ ap_hook_http_scheme { TYPE = function; FLAGS = extern };
+ ap_log_rerror { TYPE = function; FLAGS = extern };
+ ap_rwrite { TYPE = function; FLAGS = extern };
+ ap_setup_client_block { TYPE = function; FLAGS = extern };
+ ap_should_client_block { TYPE = function; FLAGS = extern };
+
+ apr_os_sock_get { TYPE = function; FLAGS = extern };
+ apr_palloc { TYPE = function; FLAGS = extern };
+ apr_table_get { TYPE = function; FLAGS = extern };
+};
diff --git a/usr/src/lib/print/mod_ipp/ipp-listener.xml b/usr/src/lib/print/mod_ipp/ipp-listener.xml
index 686646a78c..9b4c15f17c 100644
--- a/usr/src/lib/print/mod_ipp/ipp-listener.xml
+++ b/usr/src/lib/print/mod_ipp/ipp-listener.xml
@@ -41,10 +41,11 @@ CDDL HEADER END
<service_fmri value='svc:/application/print/server' />
</dependency>
+ <!-- Change /usr/apache2/... if Apache 2.x is elsewhere. -->
<exec_method
type='method'
name='start'
- exec='/usr/apache/bin/httpd -f /etc/apache/httpd-standalone-ipp.conf'
+ exec='/usr/apache2/2.2/bin/httpd -f /etc/lp/ipp/httpd-standalone-ipp.conf'
timeout_seconds='10' />
<exec_method
diff --git a/usr/src/lib/print/mod_ipp/mod_ipp.c b/usr/src/lib/print/mod_ipp/mod_ipp.c
index 2d9ece2287..813b04723c 100644
--- a/usr/src/lib/print/mod_ipp/mod_ipp.c
+++ b/usr/src/lib/print/mod_ipp/mod_ipp.c
@@ -23,12 +23,11 @@
* Copyright 2006 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*
+ * Copyright 2015 Nexenta Systems, Inc. All rights reserved.
*/
/* $Id: mod_ipp.c 149 2006-04-25 16:55:01Z njacobs $ */
-#pragma ident "%Z%%M% %I% %E% SMI"
-
/*
* Internet Printing Protocol (IPP) module for Apache.
*/
@@ -36,6 +35,7 @@
#include "ap_config.h"
#include <stdio.h>
+#include <unistd.h>
#include <time.h>
#include <sys/time.h>
#include <values.h>
@@ -48,11 +48,12 @@
#include "http_protocol.h"
#include "http_log.h"
#include "http_main.h"
-#include "papi.h"
-#ifndef APACHE_RELEASE /* appears to only exist in Apache 1.X */
-#define APACHE2
+#ifndef APACHE2
#include "apr_compat.h"
-#endif
+#define apr_table_get ap_table_get
+#endif /* APACHE2 */
+
+#include "papi.h"
#include <papi.h>
#include <ipp-listener.h>
@@ -123,7 +124,7 @@ read_data(void *fd, void *buf, size_t siz)
#ifdef DEBUG
fprintf(stderr, "read_data(0x%8.8x, 0x%8.8x, %d): %d",
- fd, buf, siz, len_read);
+ fd, buf, siz, len_read);
if (len_read < 0)
fprintf(stderr, ": %s", strerror(errno));
putc('\n', stderr);
@@ -194,7 +195,7 @@ void _log_rerror(const char *file, int line, int level, request_rec *r,
va_end(args);
#ifdef APACHE2
- ap_log_rerror(file, line, level, NULL, r, message);
+ ap_log_rerror(file, line, level, APR_SUCCESS, r, message);
#else
ap_log_rerror(file, line, level, r, message);
#endif
@@ -206,28 +207,26 @@ ipp_handler(request_rec *r)
papi_attribute_t **request = NULL, **response = NULL;
IPPListenerConfig *config;
papi_status_t status;
+ const char *s;
+ int sockfd = -1;
int ret;
/* Really, IPP is all POST requests */
if (r->method_number != M_POST)
return (DECLINED);
-#ifndef APACHE2
/*
* An IPP request must have a MIME type of "application/ipp"
* (RFC-2910, Section 4, page 19). If it doesn't match this
* MIME type, we should decline the request and let someone else
* try and handle it.
*/
- if (r->headers_in != NULL) {
- char *mime_type = (char *)ap_table_get(r->headers_in,
- "Content-Type");
+ if (r->headers_in == NULL)
+ return (DECLINED);
+ s = apr_table_get(r->headers_in, "Content-Type");
+ if ((s == NULL) || (strcasecmp(s, "application/ipp") != 0))
+ return (DECLINED);
- if ((mime_type == NULL) ||
- (strcasecmp(mime_type, "application/ipp") != 0))
- return (DECLINED);
- }
-#endif
/* CHUNKED_DECHUNK might not work right for IPP? */
if ((ret = ap_setup_client_block(r, REQUEST_CHUNKED_DECHUNK)) != OK)
return (ret);
@@ -243,49 +242,50 @@ ipp_handler(request_rec *r)
if (status != PAPI_OK)
_log_rerror(APLOG_MARK, APLOG_ERR, r,
- "read failed: %s\n", papiStatusString(status));
+ "read failed: %s\n", papiStatusString(status));
#ifdef DEBUG
papiAttributeListPrint(stderr, request, "request (%d) ", getpid());
#endif
- (void) papiAttributeListAddString(&request, PAPI_ATTR_EXCL,
- "originating-host", (char *)
#ifdef APACHE2
- ap_get_remote_host
- (r->connection, r->per_dir_config, REMOTE_NAME, NULL));
+ s = ap_get_remote_host(r->connection, r->per_dir_config,
+ REMOTE_NAME, NULL);
#else
- ap_get_remote_host
- (r->connection, r->per_dir_config, REMOTE_NAME));
+ s = ap_get_remote_host(r->connection, r->per_dir_config,
+ REMOTE_NAME);
#endif
+ (void) papiAttributeListAddString(&request, PAPI_ATTR_EXCL,
+ "originating-host", (char *)s);
(void) papiAttributeListAddInteger(&request, PAPI_ATTR_EXCL,
- "uri-port", ap_get_server_port(r));
+ "uri-port", ap_get_server_port(r));
+
if (r->headers_in != NULL) {
- char *host = (char *)ap_table_get(r->headers_in, "Host");
+ char *host = (char *)apr_table_get(r->headers_in, "Host");
if ((host == NULL) || (host[0] == '\0'))
host = (char *)ap_get_server_name(r);
(void) papiAttributeListAddString(&request, PAPI_ATTR_EXCL,
- "uri-host", host);
+ "uri-host", host);
}
(void) papiAttributeListAddString(&request, PAPI_ATTR_EXCL,
- "uri-path", r->uri);
+ "uri-path", r->uri);
config = ap_get_module_config(r->per_dir_config, &ipp_module);
if (config != NULL) {
(void) papiAttributeListAddInteger(&request, PAPI_ATTR_EXCL,
- "conformance", config->conformance);
+ "conformance", config->conformance);
(void) papiAttributeListAddCollection(&request, PAPI_ATTR_EXCL,
- "operations", config->operations);
+ "operations", config->operations);
if (config->default_user != NULL)
(void) papiAttributeListAddString(&request,
- PAPI_ATTR_EXCL, "default-user",
- config->default_user);
+ PAPI_ATTR_EXCL, "default-user",
+ config->default_user);
if (config->default_svc != NULL)
(void) papiAttributeListAddString(&request,
- PAPI_ATTR_EXCL, "default-service",
- config->default_svc);
+ PAPI_ATTR_EXCL, "default-service",
+ config->default_svc);
}
/*
@@ -294,15 +294,35 @@ ipp_handler(request_rec *r)
* service to retrieve the sensativity label off of a multi-level
* port.
*/
- (void) papiAttributeListAddInteger(&request, PAPI_ATTR_EXCL,
- "peer-socket", ap_bfileno(r->connection->client, B_RD));
+#ifdef APACHE2
+ /*
+ * In Apache 2.4 and later, could use: ap_get_conn_socket()
+ * Apache 2.2 uses ap_get_module_config() but that needs
+ * &core_module, for .module_index (which is just zero).
+ * Could either inline that with index zero, or declare
+ * core_module here. Latter seems less evil.
+ */
+ {
+ extern module core_module;
+ apr_socket_t *csd = ap_get_module_config(
+ r->connection->conn_config, &core_module);
+ if (csd != NULL)
+ (void) apr_os_sock_get(&sockfd, csd);
+ }
+#else
+ sockfd = ap_bfileno(r->connection->client, B_RD);
+#endif
+ if (sockfd != -1) {
+ (void) papiAttributeListAddInteger(&request,
+ PAPI_ATTR_EXCL, "peer-socket", sockfd);
+ }
/* process the request */
status = ipp_process_request(request, &response, read_data, r);
if (status != PAPI_OK) {
errno = 0;
_log_rerror(APLOG_MARK, APLOG_ERR, r,
- "request failed: %s\n", papiStatusString(status));
+ "request failed: %s\n", papiStatusString(status));
discard_data(r);
}
#ifdef DEBUG
@@ -316,7 +336,7 @@ ipp_handler(request_rec *r)
* remain in the post request.
*/
if ((r->read_chunked != 0) &&
- (ap_table_get(r->headers_in, "Content-Length") == NULL))
+ (apr_table_get(r->headers_in, "Content-Length") == NULL))
discard_data(r);
/* write an IPP response back to the network */
@@ -329,7 +349,7 @@ ipp_handler(request_rec *r)
status = ipp_write_message(write_data, r, response);
if (status != PAPI_OK)
_log_rerror(APLOG_MARK, APLOG_ERR, r,
- "write failed: %s\n", papiStatusString(status));
+ "write failed: %s\n", papiStatusString(status));
#ifdef DEBUG
fprintf(stderr, "write result: %s\n", papiStatusString(status));
fflush(stderr);
@@ -342,7 +362,7 @@ ipp_handler(request_rec *r)
ap_kill_timeout(r);
if (ap_rflush(r) < 0)
_log_rerror(APLOG_MARK, APLOG_ERR, r,
- "flush failed, response may not have been sent");
+ "flush failed, response may not have been sent");
#endif
return (OK);
@@ -359,11 +379,11 @@ create_ipp_dir_config(
#endif
char *dirspec)
{
- IPPListenerConfig *config =
+ IPPListenerConfig *config;
#ifndef APACHE2
- ap_pcalloc(p, sizeof (*config));
+ config = ap_pcalloc(p, sizeof (*config));
#else
- apr_pcalloc(p, sizeof (*config));
+ config = apr_pcalloc(p, sizeof (*config));
#endif
if (config != NULL) {
@@ -371,8 +391,8 @@ create_ipp_dir_config(
config->conformance = IPP_PARSE_CONFORMANCE_RASH;
config->default_user = NULL;
config->default_svc = NULL;
- (void) ipp_configure_operation(&config->operations, "required",
- "enable");
+ (void) ipp_configure_operation(&config->operations,
+ "required", "enable");
}
return (config);
@@ -399,12 +419,13 @@ ipp_conformance(cmd_parms *cmd, void *cfg, const char *arg)
/*ARGSUSED0*/
static const char *
-ipp_operation(cmd_parms *cmd, void *cfg, char *op, char *toggle)
+ipp_operation(cmd_parms *cmd, void *cfg, const char *op, const char *toggle)
{
IPPListenerConfig *config = (IPPListenerConfig *)cfg;
papi_status_t status;
- status = ipp_configure_operation(&config->operations, op, toggle);
+ status = ipp_configure_operation(&config->operations,
+ (char *)op, (char *)toggle);
switch (status) {
case PAPI_OK:
return (NULL);
@@ -440,13 +461,17 @@ ipp_default_svc(cmd_parms *cmd, void *cfg, const char *arg)
#ifdef DEBUG
/*ARGSUSED0*/
+volatile int ipp_module_hang_sleeping = 1;
static const char *
ipp_module_hang(cmd_parms *cmd, void *cfg)
{
- static int i = 1;
- /* wait so we can attach a debugger, assign i = 0, and step through */
- while (i);
+ /*
+ * Wait so we can attach with a debugger. Once attached,
+ * assign ipp_module_hang_sleeping = 0 and step through.
+ */
+ while (ipp_module_hang_sleeping)
+ sleep(1);
return (NULL);
}
@@ -472,7 +497,7 @@ static const command_rec ipp_cmds[] =
#ifdef APACHE2
/*ARGSUSED0*/
static const char *
-ipp_method(const request_rec *r)
+ipp_scheme(const request_rec *r)
{
return ("ipp");
}
@@ -494,7 +519,7 @@ ipp_register_hooks(apr_pool_t *p)
/* Need to make sure we don't get directory listings by accident */
ap_hook_handler(ipp_handler, NULL, modules, APR_HOOK_MIDDLE);
ap_hook_default_port(ipp_port, NULL, NULL, APR_HOOK_MIDDLE);
- ap_hook_http_method(ipp_method, NULL, NULL, APR_HOOK_MIDDLE);
+ ap_hook_http_scheme(ipp_scheme, NULL, NULL, APR_HOOK_MIDDLE);
}
module AP_MODULE_DECLARE_DATA ipp_module = {