1/*
2 * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
3 * Use is subject to license terms.
4 */
5
6#pragma ident	"%Z%%M%	%I%	%E% SMI"
7
8 /*
9  * Routines for controlled update/initialization of request structures.
10  *
11  * request_init() initializes its argument. Pointers and string-valued members
12  * are initialized to zero, to indicate that no lookup has been attempted.
13  *
14  * request_set() adds information to an already initialized request structure.
15  *
16  * Both functions take a variable-length name-value list.
17  *
18  * Diagnostics are reported through syslog(3).
19  *
20  * Author: Wietse Venema, Eindhoven University of Technology, The Netherlands.
21  */
22
23#ifndef lint
24static char sccsid[] = "@(#) update.c 1.1 94/12/28 17:42:56";
25#endif
26
27/* System libraries */
28
29#include <stdio.h>
30#include <stdlib.h>
31#include <unistd.h>
32#include <syslog.h>
33#include <string.h>
34
35/* Local stuff. */
36
37#include "mystdarg.h"
38#include "tcpd.h"
39
40/* request_fill - request update engine */
41
42static struct request_info *request_fill(request, ap)
43struct request_info *request;
44va_list ap;
45{
46    int     key;
47    char   *ptr;
48
49    while ((key = va_arg(ap, int)) > 0) {
50	switch (key) {
51	default:
52	    tcpd_warn("request_fill: invalid key: %d", key);
53	    return (request);
54	case RQ_FILE:
55	    request->fd = va_arg(ap, int);
56	    continue;
57	case RQ_CLIENT_SIN:
58	    request->client->sin = va_arg(ap, struct sockaddr_gen *);
59	    continue;
60	case RQ_SERVER_SIN:
61	    request->server->sin = va_arg(ap, struct sockaddr_gen *);
62	    continue;
63
64	    /*
65	     * All other fields are strings with the same maximal length.
66	     */
67
68	case RQ_DAEMON:
69	    ptr = request->daemon;
70	    break;
71	case RQ_USER:
72	    ptr = request->user;
73	    break;
74	case RQ_CLIENT_NAME:
75	    ptr = request->client->name;
76	    break;
77	case RQ_CLIENT_ADDR:
78	    ptr = request->client->addr;
79	    break;
80	case RQ_SERVER_NAME:
81	    ptr = request->server->name;
82	    break;
83	case RQ_SERVER_ADDR:
84	    ptr = request->server->addr;
85	    break;
86	}
87	STRN_CPY(ptr, va_arg(ap, char *), STRING_LENGTH);
88    }
89    return (request);
90}
91
92/* request_init - initialize request structure */
93
94struct request_info *VARARGS(request_init, struct request_info *, request)
95{
96    static struct request_info default_info;
97    struct request_info *r;
98    va_list ap;
99
100    /*
101     * Initialize data members. We do not assign default function pointer
102     * members, to avoid pulling in the whole socket module when it is not
103     * really needed.
104     */
105    VASTART(ap, struct request_info *, request);
106    *request = default_info;
107    request->fd = -1;
108    strcpy(request->daemon, unknown);
109    sprintf(request->pid, "%d", getpid());
110    request->client->request = request;
111    request->server->request = request;
112    r = request_fill(request, ap);
113    VAEND(ap);
114    return (r);
115}
116
117/* request_set - update request structure */
118
119struct request_info *VARARGS(request_set, struct request_info *, request)
120{
121    struct request_info *r;
122    va_list ap;
123
124    VASTART(ap, struct request_info *, request);
125    r = request_fill(request, ap);
126    VAEND(ap);
127    return (r);
128}
129