%{
    #include "rss.h"
%}    

%token USERS LINE IDENTIFIER DESTINATIONS NUMBER DIRECT EXTRA USING
	SCRATCH PATH GETTYPATH MODEMGETTY LOGIN EMAIL PANICLOG LOGFILE
	EMAIL RETRY NOKILLS SHOWNUMS LOGIN CALL LOG ON DEFAULT OFF
	MODE CALLBACK DIALIN

%%

input:
    MODE
    colon
    modetype

modetype:
    callback
    defaultlist
    destinationsection
    usersection
|
    dialin
    defaultlist
;

callback:
    CALLBACK
    {
	cb_mode = mode_callback;
    }
;

dialin:
    DIALIN
    {
	cb_mode = mode_dialin;
    }
;

defaultlist:
    defaults
    {
	checkdefaults();
    }
;

defaults:
    defaults 
    default
|
    default			/* at least one default (line) needed */
;

default:
    linesection
|
    scratchfile
|
    pathsection
|
    gettydefault
|
    modemgetty
|
    nokills
|
    retry
|
    shownums
|
    paniclog
|
    logfile
|
    email
|
    login
|
    call
|
    logtype
|
    error
;

call:
    CALL
    {
	if (cb_mode != mode_callback)
	    yysemantic("'call' only valid for mode callback");
	call = 1;
    }
;
    
logtype:
    LOG
    colon
    logvalue
;

logvalue:
    ON
    {
	log_type = log_on;
    }
|
    OFF
    {
	log_type = log_off;
    }
|
    DEFAULT
    {
	log_type = log_default;
    }
|
    {
	expect = "log type (on, off, or default)";
    }
    error
;

login:
    login_keyword
    colon
    loginprog
;

login_keyword:
    LOGIN
    {
	if (cb_mode != mode_callback)
	    yysemantic("'login: ...' only valid for mode callback");
    }
;

loginprog:
    IDENTIFIER
    {
	login_program = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "login programname";
    }
    error
;

email:
    EMAIL
    colon
    address
;

address:
    IDENTIFIER
    {
	email_address = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "e-mail address";
    }
    error
;

logfile:
    LOGFILE
    colon
    log
;

log:
    IDENTIFIER
    {
	log_filename = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "logfilename";
    }
    error
;

paniclog:
    PANICLOG
    colon
    panic
;

panic:
    IDENTIFIER
    {
	panic_filename = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "panic-logfilename";
    }
    error
;

nokills:
    NOKILLS
    {
	kill_processes = 0;
    };

shownums:
    SHOWNUMS
    {
	if (cb_mode != mode_callback)
	    yysemantic("'phonenumbers' only valid for mode callback");
	show_phonenumbers = 1;
    };

retry:
    RETRY
    {
	if (cb_mode != mode_callback)
	    yysemantic("'retry' only valid for mode callback");
    }
    colon
    nretries;

nretries:
    NUMBER
    {
	ntries = atoi(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "Maximum callback retries expected";
    }
    error
;
    
modemgetty:
    MODEMGETTY
    colon
    modem
;

modem:
    IDENTIFIER
    {
	modem_getty = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "modem_getty specification";
    }
    error
;

gettydefault:
    GETTYPATH
    colon
    getty
;

getty:
    IDENTIFIER
    {
	getty_path = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "getty-configuration filename";
    }
    error
;

linesection:
    LINE
    colon
    ttyline
;

ttyline:
    IDENTIFIER
    {
	tty_line = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "default ttyline";
    }
    error
;

pathsection:
    PATH
    colon
    pathname
;

pathname:
    IDENTIFIER
    {
	base_path = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "Callback path";
    }
    error
;

scratchfile:
    scratch_keyword
    colon
    tmpname
;

scratch_keyword:
    SCRATCH
    {
	if (cb_mode != mode_callback)
	    yysemantic("'scratch' only valid for mode callback");
    }
;

tmpname:
    IDENTIFIER
    {
	tmp_filename = xstrdup(yytext);
	expect = "default setting or 'users'";
    }
|
    {
	expect = "Scratch-filename";
    }
    error
;

usersection:
    USERS
    colon
    users
;

users:
    users
    user
|
    user
;    

user:
    username
    colon
    grouplist
|
    {
	expect = "username";
    }
    error
;

username:
    IDENTIFIER
    {
	define_user(yytext);
    }
;

grouplist:
    grouplist
    {
	expect = "','";
    }
    ','
    group
|
    group
;    

group:
    IDENTIFIER
    {
	addgroup(yytext);
    }
|
    {
	expect = "groupname";
    }
    error
;

destinationsection:
    DESTINATIONS
    colon
    destinations
;

destinations:
    destinations
    destination
|
    destination
;    

destination:
    groupid
    {
	expect = "earlier 'using' or ':'";
    }
    ':'
    target
    mode
;

groupid:
    IDENTIFIER
    {
	define_group(yytext);
    }
|
    {
	expect = "groupname";
    }
    error
;

target:
    IDENTIFIER
    {
	set_target(yytext);
    }
|
    {
	expect = "target computer";
    }
    error
;

mode:
    DIRECT
    {
	set_mode(direct_mode);
    }
|
    EXTRA
    {
	set_mode(extra_mode);
    }
|
    phone_number
|
    {
	expect = "'direct', 'extra', or phonenumber";
    }
    error
;

phone_number:
    NUMBER
    {
	set_phone(yytext);
	expect = "'using' or groupname";
    }
    opt_file
;


opt_file:
    USING
    filename
|
    /*	empty */
;    

filename:
    IDENTIFIER
    {
	set_file(yytext);
    }
|
    {
	expect = "filename";
    }
    error
;


colon:
    {
	expect = "':'";
    }
    ':'
;
