1 /*:ts=8*/
2 /*****************************************************************************
3  * FIDOGATE --- Gateway UNIX Mail/News <-> FTN NetMail/EchoMail
4  *
5  * $Id: ftnhatch.c,v 4.17 2004/08/22 20:19:13 n0ll Exp $
6  *
7  * Hatch file into file area
8  *
9  *****************************************************************************
10  * Copyright (C) 1990-2004
11  *  _____ _____
12  * |     |___  |   Martin Junius             <mj.at.n0ll.dot.net>
13  * | | | |   | |   Radiumstr. 18
14  * |_|_|_|@home|   D-51069 Koeln, Germany
15  *
16  * This file is part of FIDOGATE.
17  *
18  * FIDOGATE is free software; you can redistribute it and/or modify it
19  * under the terms of the GNU General Public License as published by the
20  * Free Software Foundation; either version 2, or (at your option) any
21  * later version.
22  *
23  * FIDOGATE is distributed in the hope that it will be useful, but
24  * WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
26  * General Public License for more details.
27  *
28  * You should have received a copy of the GNU General Public License
29  * along with FIDOGATE; see the file COPYING.  If not, write to the Free
30  * Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
31  *****************************************************************************/
32 
33 #include "fidogate.h"
34 #include "getopt.h"
35 
36 
37 
38 #define PROGRAM		"ftnhatch"
39 #define VERSION		"$Revision: 4.17 $"
40 #define CONFIG		DEFAULT_CONFIG_MAIN
41 
42 
43 
44 #define CREATOR		"by FIDOGATE/ftnhatch"
45 
46 #define MY_AREASBBS	"FAreasBBS"
47 #define MY_CONTEXT	"ff"
48 
49 
50 
51 /*
52  * Prototypes
53  */
54 int	hatch			(char *, char *, char *, char *);
55 
56 void	short_usage		(void);
57 void	usage			(void);
58 
59 
60 
61 /*
62  * Hatch file
63  */
hatch(char * area,char * file,char * desc,char * replaces)64 int hatch(char *area, char *file, char *desc, char *replaces)
65 {
66     char file_name[MAXPATH];
67     AreasBBS *bbs;
68     struct stat st;
69     unsigned long file_size, file_crc;
70     time_t file_time, now;
71     Tick tic;
72     Node node;
73     LNode *p;
74     int ret;
75 
76     /*
77      * Lookup area
78      */
79     if( (bbs = areasbbs_lookup(area)) == NULL )
80     {
81 	/* Unknown area: log it, dump it. ;-) */
82 	logit("ERROR: unknown area %s", area);
83 	return EXIT_ERROR;
84     }
85     cf_set_zone(bbs->zone);
86 
87 
88     /*
89      * Make sure that file exists
90      */
91     BUF_COPY3(file_name, bbs->dir, "/", file);
92     if(stat(file_name, &st) == ERROR)
93     {
94 	logit("$ERROR: can't stat() file %s", file_name);
95 	return EXIT_ERROR;
96     }
97     file_size = st.st_size;
98     file_time = st.st_mtime;
99     file_crc  = crc32_file(file_name);
100 
101     debug(4, "file: name=%s size=%ld time=%ld crc=%08lx",
102 	  file_name, file_size, file_time, file_crc);
103 
104     /*
105      * Build Tick struct
106      */
107     tick_init(&tic);
108 
109     now = time(NULL);
110 
111     tic.origin   = cf_n_addr();
112     tic.from     = cf_n_addr();
113     /* tic.to set by hatch_one() */
114     tic.area     = area;
115     tic.file     = file;
116     tic.replaces = replaces;
117     tl_append(&tic.desc, desc);
118     tic.crc      = file_crc;
119     tic.created  = CREATOR;
120     tic.size     = file_size;
121     tl_appendf(&tic.path, "%s %ld %s",
122 	       znf1(cf_addr()), now, date(NULL, &now) );
123     lon_add(&tic.seenby, cf_addr());
124     lon_join(&tic.seenby, &bbs->nodes);
125     /* tic.pw set by hatch_one() */
126     tic.date     = file_time;
127 
128     /*
129      * Send to all nodes
130      */
131     ret = EXIT_OK;
132     for(p=bbs->nodes.first; p; p=p->next)
133     {
134 	node = p->node;
135 	debug(4, "sending to %s", znfp1(&node));
136 	if(tick_send(&tic, &node, file_name) == ERROR)
137 	    ret = EXIT_ERROR;
138     }
139 
140     return ret;
141 }
142 
143 
144 
145 /*
146  * Usage messages
147  */
short_usage(void)148 void short_usage(void)
149 {
150     fprintf(stderr, "usage: %s [-options] AREA FILE \"DESCRIPTION\"\n",
151 	    PROGRAM);
152     fprintf(stderr, "       %s --help  for more information\n", PROGRAM);
153     exit(EX_USAGE);
154 }
155 
156 
usage(void)157 void usage(void)
158 {
159     fprintf(stderr, "FIDOGATE %s  %s %s\n\n",
160 	    version_global(), PROGRAM, version_local(VERSION) );
161 
162     fprintf(stderr, "usage:   %s [-options] AREA FILE \"DESCRIPTION\"\n\n",
163 	    PROGRAM);
164     fprintf(stderr, "\
165 options: -b --fareas-bbs NAME         use alternate FAREAS.BBS\n\
166          -r --replaces FILES          add Replaces entry\n\
167 \n\
168          -v --verbose                 more verbose\n\
169 	 -h --help                    this help\n\
170          -c --config name             read config file (\"\" = none)\n\
171 	 -a --addr Z:N/F.P            set FTN address\n\
172 	 -u --uplink-addr Z:N/F.P     set FTN uplink address\n");
173 
174     exit(0);
175 }
176 
177 
178 
main(int argc,char ** argv)179 int main(int argc, char **argv)
180 {
181     char *areas_bbs = NULL;
182     char *r_flag=NULL;
183     int c;
184     char *c_flag=NULL;
185     char *a_flag=NULL, *u_flag=NULL;
186     int ret;
187     char *area, *file, *desc;
188 
189     int option_index;
190     static struct option long_options[] =
191     {
192         { "fareas-bbs",	  1, 0, 'b'},
193         { "replaces",	  1, 0, 'r'},
194 
195 	{ "verbose",      0, 0, 'v'},	/* More verbose */
196 	{ "help",         0, 0, 'h'},	/* Help */
197 	{ "config",       1, 0, 'c'},	/* Config file */
198 	{ "addr",         1, 0, 'a'},	/* Set FIDO address */
199 	{ "uplink-addr",  1, 0, 'u'},	/* Set FIDO uplink address */
200 	{ 0,              0, 0, 0  }
201     };
202 
203     log_program(PROGRAM);
204 
205     /* Init configuration */
206     cf_initialize();
207 
208 
209     while ((c = getopt_long(argc, argv, "b:r:vhc:a:u:",
210 			    long_options, &option_index     )) != EOF)
211 	switch (c) {
212 	/***** ftnhatch options *****/
213 	case 'b':
214 	    areas_bbs = optarg;
215 	    break;
216 	case 'r':
217 	    r_flag = optarg;
218 	    break;
219 
220 	/***** Common options *****/
221 	case 'v':
222 	    verbose++;
223 	    break;
224 	case 'h':
225 	    usage();
226 	    exit(0);
227 	    break;
228 	case 'c':
229 	    c_flag = optarg;
230 	    break;
231 	case 'a':
232 	    a_flag = optarg;
233 	    break;
234 	case 'u':
235 	    u_flag = optarg;
236 	    break;
237 	default:
238 	    short_usage();
239 	    exit(EX_USAGE);
240 	    break;
241 	}
242 
243     /*
244      * Read config file
245      */
246     cf_read_config_file(c_flag ? c_flag : CONFIG);
247 
248     /*
249      * Process config options
250      */
251     if(a_flag)
252 	cf_set_addr(a_flag);
253     if(u_flag)
254 	cf_set_uplink(u_flag);
255 
256     cf_debug();
257 
258     /*
259      * Command line parameters
260      */
261     if(argc-optind != 3)
262 	short_usage();
263     area = argv[optind++];
264     file = argv[optind++];
265     desc = argv[optind++];
266 
267     /*
268      * Get name of fareas.bbs file from config file
269      */
270     if( !areas_bbs && (areas_bbs = cf_get_string(MY_AREASBBS, TRUE)) )
271     {
272 	debug(8, "config: %s %s", MY_AREASBBS, areas_bbs);
273     }
274     if(!areas_bbs)
275     {
276 	fprintf(stderr, "%s: no areas.bbs specified\n", PROGRAM);
277 	exit(EX_USAGE);
278     }
279 
280     /* Read PASSWD */
281     passwd_init();
282     /* Read FAreas.BBS */
283     if(areasbbs_init(areas_bbs) == ERROR)
284     {
285 	logit("$ERROR: can't open %s", areas_bbs);
286 	ret = EX_OSFILE;
287     }
288 
289     /* Hatch it! */
290     ret = hatch(area, file, desc, r_flag);
291     tmps_freeall();
292 
293     exit(ret);
294 }
295