%{
/*
 *
 *  BlueZ - Bluetooth protocol stack for Linux
 *
 *  Copyright (C) 2002-2010  Marcel Holtmann <marcel@holtmann.org>
 *
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 *
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <stdio.h>
#include <errno.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <sys/param.h>
#include <sys/socket.h>

#include <bluetooth/bluetooth.h>
#include <bluetooth/rfcomm.h>

#include "kword.h"

int yylex(void);
int yyerror(char *s); 

struct rfcomm_opts *opts;

%}

%union {
	int number;
	char *string;
	bdaddr_t *bdaddr;
}

%token K_BIND K_DEVICE K_CHANNEL K_COMMENT
%token K_YES K_NO

%token <number> NUMBER RFCOMM
%token <string> STRING WORD
%token <bdaddr> BDADDR

%type <number> bool

%%

config		:
		| statement
		| config statement
		;

statement	: section '{' rfcomm_options '}'
		| rfcomm  '{' rfcomm_options '}'
		| WORD
			{
			}
		| error
			{
				yyclearin;
				yyerrok;
			}
		;

section		: WORD
			{
				opts = NULL;
			}
		;

rfcomm		: RFCOMM
			{
				if (($1 >= 0) && ($1 < RFCOMM_MAX_DEV))
					opts = &rfcomm_opts[$1];
				else
					opts = NULL;
			}
		;

rfcomm_options	: rfcomm_option ';'
		| error ';'
		| rfcomm_options rfcomm_option ';'
		;

rfcomm_option	: K_BIND bool
			{
				if (opts)
					opts->bind = $2;
			}
		| K_DEVICE BDADDR
			{
				if (opts)
					bacpy(&opts->bdaddr, $2);
			}
		| K_CHANNEL NUMBER
			{
				if (opts)
					opts->channel = $2;
			}
		| K_COMMENT STRING
			{
				if (opts)
					snprintf(opts->comment, MAXCOMMENTLEN, "%s", $2);
			}
		| WORD
			{
				// Unknown option
			}
		;

bool		: K_YES	{ $$ = 1; }
		| K_NO	{ $$ = 0; }
		;

%%

int yyerror(char *s) 
{
	fprintf(stderr, "%s line %d\n", s, lineno);
	return 0;
}

int rfcomm_read_config(char *filename)
{
	extern FILE *yyin;
	char file[MAXPATHLEN + 1];
	int i;

	for (i = 0; i < RFCOMM_MAX_DEV; i++) {
		rfcomm_opts[i].bind = 0;
		bacpy(&rfcomm_opts[i].bdaddr, BDADDR_ANY);
		rfcomm_opts[i].channel = 1;
	}

	if (filename) {
		snprintf(file, MAXPATHLEN,  "%s", filename);
	} else {
		snprintf(file, MAXPATHLEN, "%s/.bluetooth/rfcomm.conf", getenv("HOME"));

		if ((getuid() == 0) || (access(file, R_OK) < 0))
			snprintf(file, MAXPATHLEN, "%s/rfcomm.conf", CONFIGDIR);
	}

	if (!(yyin = fopen(file, "r")))
		return -1;

	lineno = 1;
	yyparse();

	fclose(yyin);

	return 0;
}
