Initial import from FreeBSD RELENG_4:
[dragonfly.git] / usr.sbin / i4b / isdntel / main.c
1 /*
2  * Copyright (c) 1997, 1999 Hellmuth Michaelis. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
14  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
16  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
17  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
19  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
20  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
21  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
22  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
23  * SUCH DAMAGE.
24  *
25  *---------------------------------------------------------------------------
26  *
27  *      isdntel - isdn4bsd telephone answering machine support
28  *      ======================================================
29  *
30  *      $Id: main.c,v 1.12 1999/12/13 21:25:26 hm Exp $ 
31  *
32  * $FreeBSD: src/usr.sbin/i4b/isdntel/main.c,v 1.8.2.1 2001/08/01 17:45:07 obrien Exp $
33  *
34  *      last edit-date: [Mon Dec 13 21:54:26 1999]
35  *
36  *----------------------------------------------------------------------------*/
37
38 #define MAIN
39 #include <locale.h>
40 #include "defs.h"
41 #include "alias.h"
42
43 static void usage( void );
44
45 static int top_dis = 0;
46 static int bot_dis = 0;
47 static int cur_pos_scr = 0;
48
49 static void makecurrent(int cur_pos, struct onefile *cur_file, int cold);
50
51 /*---------------------------------------------------------------------------*
52  *      program entry
53  *---------------------------------------------------------------------------*/
54 int
55 main(int argc, char **argv)
56 {
57         int i;
58         int kchar;
59         
60         char *spooldir = SPOOLDIR;
61         char *playstring = PLAYCMD;
62         char *aliasfile = ALIASFILE;
63         int rrtimeout = REREADTIMEOUT;
64         
65         extern char *optarg;    
66
67         setlocale( LC_ALL, "");
68         
69         while ((i = getopt(argc, argv, "a:d:p:t:")) != -1)
70         {
71                 switch (i)
72                 {
73                         case 'a':
74                                 aliasfile = optarg;
75                                 break;
76
77                         case 'd':
78                                 spooldir = optarg;
79                                 break;
80
81                         case 'p':
82                                 playstring = optarg;
83                                 break;
84
85                         case 't':
86                                 if(isdigit(*optarg))
87                                 {
88                                         rrtimeout = strtoul(optarg, NULL, 10);
89                                 }
90                                 else
91                                 {
92                                         usage();
93                                 }
94                                 break;
95
96                         case '?':
97                         default:
98                                 usage();
99                                 break;
100                 }
101         }
102
103         if(rrtimeout < 10)
104                 rrtimeout = 10;
105
106         if((chdir(spooldir)) != 0)
107                 fatal("cannot change directory to spooldir %s!", spooldir);
108
109         init_alias(aliasfile);
110         
111         init_screen();
112
113         init_files(0);
114         
115         /* go into loop */
116
117         for (;;)
118         {
119                 fd_set set;
120                 struct timeval timeout;
121
122                 FD_ZERO(&set);
123                 FD_SET(STDIN_FILENO, &set);
124                 timeout.tv_sec = rrtimeout;
125                 timeout.tv_usec = 0;
126
127                 /* if no char is available within timeout, reread spool */
128                 
129                 if((select(STDIN_FILENO + 1, &set, NULL, NULL, &timeout)) <= 0)
130                 {
131                         reread();
132                         continue;
133                 }
134
135                 kchar = wgetch(main_w);         /* get char */
136
137                 switch (kchar)
138                 {
139                         case CR:
140                         case LF:
141 #ifdef KEY_ENTER
142                         case KEY_ENTER:
143 #endif
144                                 do_menu();
145                                 break;
146
147                         case KEY_UP:    /* up-move cursor */
148                                 if(cur_file && cur_file->prev)
149                                 {
150                                         cur_file = cur_file->prev;
151                                         cur_pos--;
152                                 }
153                                 break;
154
155
156                         case TAB:
157                         case KEY_DOWN:  /* down-move cursor */
158                                 if(cur_file && cur_file->next)
159                                 {
160                                         cur_file = cur_file->next;
161                                         cur_pos++;
162                                 }
163                                 break;
164
165                         case KEY_HOME:  /* move cursor to first dir */
166                                 break;
167
168                         case KEY_LL:    /* move cursor to last file */
169                                 break;
170
171                         case CNTRL_D:
172                                 do_quit(0);
173                                 break;
174
175                         case CNTRL_L:   /* refresh */
176                                 touchwin(curscr);
177                                 wrefresh(curscr);
178                                 break;
179
180                 }
181                 makecurrent(cur_pos, cur_file, 0);
182         }
183
184         do_quit(0);
185         
186         return(0);
187 }
188
189 /*---------------------------------------------------------------------------*
190  *      handle horizontal selection bar movement
191  *---------------------------------------------------------------------------*/
192 static void
193 makecurrent(int cur_pos, struct onefile *cur_file, int cold)
194 {
195         static int lastpos;
196         static struct onefile *lastfile;
197         char buffer[256];
198
199         /* un-higlight current horizontal bar */
200
201         if(!cold && lastfile && cur_file)
202         {
203                 sprintf(buffer, "%s %s %-16s %-16s %-20s %-6s%*s",
204                         lastfile->date, lastfile->time,
205                         lastfile->dstnumber, lastfile->srcnumber,
206                         lastfile->alias == NULL ? "-/-" : lastfile->alias,
207                         lastfile->seconds,
208                         COLS - LAST_POS - 2, "");
209                         
210                 wattroff(main_w, A_REVERSE);
211                 mvwprintw(main_w, lastpos, 0, "%s", buffer);
212                 wattroff(main_w, A_REVERSE);
213         }
214
215         if(cur_file == NULL)
216         {
217                 lastpos = cur_pos_scr;
218                 lastfile = cur_file;
219                 return;
220         }
221                 
222         /* have to scroll up or down ? */
223
224         if(cur_pos >= bot_dis)          
225         {
226                 /* scroll up */
227
228                 wscrl(main_w, 1);
229
230                 bot_dis++;
231                 top_dis++;
232                 cur_pos_scr = LINES-START_O-3;
233         }
234         else if(cur_pos < top_dis)
235         {
236                 /* scroll down */
237
238                 wscrl(main_w, -1);
239
240                 bot_dis--;
241                 top_dis--;
242                 cur_pos_scr = 0;                
243         }
244         else
245         {
246                 cur_pos_scr = cur_pos - top_dis;
247         }               
248
249         sprintf(buffer, "%s %s %-16s %-16s %-20s %-6s%*s",
250                         cur_file->date, cur_file->time,
251                         cur_file->dstnumber, cur_file->srcnumber,
252                         cur_file->alias == NULL ? "-/-" : cur_file->alias,
253                         cur_file->seconds,
254                         COLS - LAST_POS - 2, "");
255                         
256         wattron(main_w, A_REVERSE);
257         mvwprintw(main_w, cur_pos_scr, 0, "%s", buffer);
258         wattroff(main_w, A_REVERSE);
259
260         lastpos = cur_pos_scr;
261         lastfile = cur_file;
262
263         wrefresh(main_w);       
264 }
265
266 /*---------------------------------------------------------------------------*
267  *      exit program
268  *---------------------------------------------------------------------------*/
269 void
270 do_quit(int exitval)
271 {
272         move(LINES-1, 0);
273         clrtoeol();
274         refresh();
275         endwin();
276         exit(exitval);
277 }
278
279 /*---------------------------------------------------------------------------*
280  *      usage display and exit
281  *---------------------------------------------------------------------------*/
282 static void
283 usage(void)
284 {
285         fprintf(stderr, "\n");
286         fprintf(stderr, "isdntel - isdn telephone answering management support utility (version %d.%d.%d)\n", VERSION, REL, STEP);
287         fprintf(stderr, "    usage: isdntel -a <filename> -d <directory> -p <command> -t <timeout>\n");
288         fprintf(stderr, "           -a <filename>   use filename as alias file\n");
289         fprintf(stderr, "           -d <directory>  use directory as spool directory\n");
290         fprintf(stderr, "           -p <command>    specify commandline for play command\n");
291         fprintf(stderr, "           -t <timeout>    spool directory reread timeout in seconds\n");      
292         fprintf(stderr, "\n");
293         exit(1);
294 }
295
296 /*---------------------------------------------------------------------------*
297  *      fatal error exit
298  *---------------------------------------------------------------------------*/
299 void
300 fatal(char *fmt, ...)
301 {
302         va_list ap;
303
304         va_start(ap, fmt);
305
306         if(curses_ready)
307         {       
308                 move(LINES-1, 0);
309                 clrtoeol();
310                 refresh();
311                 endwin();
312         }
313
314         fprintf(stderr, "\nFatal error: ");
315         vfprintf(stderr, fmt, ap);
316         fprintf(stderr, "\n\n");
317                 
318         va_end(ap);
319
320         exit(1);
321 }
322
323 /*---------------------------------------------------------------------------*
324  *      error printing
325  *---------------------------------------------------------------------------*/
326 void
327 error(char *fmt, ...)
328 {
329         va_list ap;
330
331         va_start(ap, fmt);
332
333         if(curses_ready)
334         {
335                 wprintw(main_w, "ERROR: ");
336                 vwprintw(main_w, fmt, ap);
337                 wprintw(main_w, "\n");
338                 wrefresh(main_w);
339         }
340         else
341         {
342                 fprintf(stderr, "ERROR: ");
343                 vfprintf(stderr, fmt, ap);
344                 fprintf(stderr, "\n");
345         }
346                 
347         va_end(ap);
348 }
349
350 /*---------------------------------------------------------------------------*
351  *      read files and fill display
352  *---------------------------------------------------------------------------*/
353 void
354 init_files(int inipos)
355 {
356         int i;
357
358         nofiles = fill_list();
359                 
360         top_dis = 0;
361         bot_dis = 0;
362
363         cur_file = first;
364
365         cur_pos = 0;
366         cur_pos_scr = 0;        
367
368         if(nofiles == 0)
369                 return;
370         
371         for(i=0; (i < nofiles) && (i < (LINES-START_O-2)); i++)
372         {
373                 mvwprintw(main_w, i, 0, "%s %s", cur_file->date, cur_file->time);
374                 mvwprintw(main_w, i, DST_POS, "%s", cur_file->dstnumber);
375                 mvwprintw(main_w, i, SRC_POS, "%s", cur_file->srcnumber);
376                 mvwprintw(main_w, i, ALI_POS,"%s", cur_file->alias == NULL ? "-/-" : cur_file->alias);
377                 mvwprintw(main_w, i, SEC_POS,"%s", cur_file->seconds);
378
379                 bot_dis++;
380
381                 if((cur_file = cur_file->next) == NULL)
382                         break;          
383         }
384         
385         cur_file = first;
386
387         if(inipos)
388         {
389                 for(i=0; i < inipos; i++)
390                 {
391                         if(cur_file->next != NULL)
392                                 cur_file = cur_file->next;
393                         else
394                                 break;
395                 }
396         }
397         makecurrent(cur_pos, cur_file, 1);
398 }
399
400 /* EOF */