1/*++
2/* NAME
3/*	smtp_map11 3
4/* SUMMARY
5/*	one-to-one address mapping
6/* SYNOPSIS
7/*	#include <smtp.h>
8/*
9/*	int	smtp_map11_external(addr, maps, propagate)
10/*	VSTRING	*addr;
11/*	MAPS	*maps;
12/*	int	propagate;
13/*
14/*	int	smtp_map11_internal(addr, maps, propagate)
15/*	VSTRING	*addr;
16/*	MAPS	*maps;
17/*	int	propagate;
18/*
19/*	int	smtp_map11_tree(tree, maps, propagate)
20/*	TOK822	*tree;
21/*	MAPS	*maps;
22/*	int	propagate;
23/* DESCRIPTION
24/*	This module performs non-recursive one-to-one address mapping.
25/*	An unmatched address extension is propagated when
26/*	\fIpropagate\fR is non-zero.
27/*
28/*	smtp_map11_external() looks up the RFC 822 external (quoted) string
29/*	form of an address in the maps specified via the \fImaps\fR argument.
30/*
31/*	smtp_map11_internal() is a wrapper around the
32/*	smtp_map11_external() routine that transforms from
33/*	internal (quoted) string form to external form and back.
34/*
35/*	smtp_map11_tree() is a wrapper around the
36/*	smtp_map11_external() routine that transforms from
37/*	internal parse tree form to external form and back.
38/* DIAGNOSTICS
39/*	Table lookup errors are fatal.
40/* SEE ALSO
41/*	mail_addr_map(3) address mappings
42/* LICENSE
43/* .ad
44/* .fi
45/*	The Secure Mailer license must be distributed with this software.
46/* AUTHOR(S)
47/*	Wietse Venema
48/*	IBM T.J. Watson Research
49/*	P.O. Box 704
50/*	Yorktown Heights, NY 10598, USA
51/*--*/
52
53/* System library. */
54
55#include <sys_defs.h>
56#include <string.h>
57
58/* Utility library. */
59
60#include <msg.h>
61#include <vstring.h>
62#include <dict.h>
63#include <argv.h>
64#include <tok822.h>
65#include <valid_hostname.h>
66
67/* Global library. */
68
69#include <mail_addr_map.h>
70#include <quote_822_local.h>
71
72/* Application-specific. */
73
74#include <smtp.h>
75
76/* smtp_map11_external - one-to-one table lookups */
77
78int     smtp_map11_external(VSTRING *addr, MAPS *maps, int propagate)
79{
80    const char *myname = "smtp_map11_external";
81    ARGV   *new_addr;
82    const char *result;
83
84    if ((new_addr = mail_addr_map(maps, STR(addr), propagate)) != 0) {
85	if (new_addr->argc > 1)
86	    msg_warn("multi-valued %s result for %s", maps->title, STR(addr));
87	result = new_addr->argv[0];
88	if (msg_verbose)
89	    msg_info("%s: %s -> %s", myname, STR(addr), result);
90	vstring_strcpy(addr, result);
91	argv_free(new_addr);
92	return (1);
93    } else {
94	if (maps->error != 0)
95	    msg_fatal("%s map lookup problem for %s", maps->title, STR(addr));
96	if (msg_verbose)
97	    msg_info("%s: %s not found", myname, STR(addr));
98	return (0);
99    }
100}
101
102/* smtp_map11_tree - rewrite address node */
103
104int     smtp_map11_tree(TOK822 *tree, MAPS *maps, int propagate)
105{
106    VSTRING *temp = vstring_alloc(100);
107    int     ret;
108
109    tok822_externalize(temp, tree->head, TOK822_STR_DEFL);
110    ret = smtp_map11_external(temp, maps, propagate);
111    tok822_free_tree(tree->head);
112    tree->head = tok822_scan(STR(temp), &tree->tail);
113    vstring_free(temp);
114    return (ret);
115}
116
117/* smtp_map11_internal - rewrite address internal form */
118
119int     smtp_map11_internal(VSTRING *addr, MAPS *maps, int propagate)
120{
121    VSTRING *temp = vstring_alloc(100);
122    int     ret;
123
124    quote_822_local(temp, STR(addr));
125    ret = smtp_map11_external(temp, maps, propagate);
126    unquote_822_local(addr, STR(temp));
127    vstring_free(temp);
128    return (ret);
129}
130
131#ifdef TEST
132
133#include <msg_vstream.h>
134#include <stringops.h>
135#include <mail_params.h>
136
137int     main(int argc, char **argv)
138{
139    VSTRING *buf = vstring_alloc(100);
140    MAPS   *maps;
141
142    msg_vstream_init(basename(argv[0]), VSTREAM_ERR);
143    if (argc < 3)
144	msg_fatal("usage: %s maptype:mapname address...", argv[0]);
145
146    maps = maps_create(argv[1], argv[1], DICT_FLAG_FOLD_FIX);
147    mail_params_init();
148    if (chdir(var_queue_dir) < 0)
149	msg_fatal("chdir(%s): %m", var_queue_dir);
150    argv += 1;
151
152    msg_verbose = 1;
153    while (--argc && *++argv) {
154	msg_info("-- start %s --", *argv);
155	smtp_map11_external(vstring_strcpy(buf, *argv), maps, 1);
156	msg_info("-- end %s --", *argv);
157    }
158    vstring_free(buf);
159    maps_free(maps);
160    return (0);
161}
162
163#endif
164