/*
 * Keyboard input helper functions (too small to be called a layer)
 *
 * Copyright (c) 2011 The Chromium OS Authors.
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * 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., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 */

#ifndef _INPUT_H
#define _INPUT_H

enum {
	INPUT_MAX_MODIFIERS	= 4,
	INPUT_BUFFER_LEN	= 16,
};

enum {
	/* Keyboard LEDs */
	INPUT_LED_SCROLL	= 1 << 0,
	INPUT_LED_CAPS		= 1 << 1,
	INPUT_LED_NUM		= 1 << 2,
};

/*
 * This table translates key codes to ASCII. Most of the entries are ASCII
 * codes, but entries after KEY_FIRST_MOD indicate that this key is a
 * modifier key, like shift, ctrl. KEY_FIRST_MOD + MOD_SHIFT is the shift
 * key, for example.
 */
struct input_key_xlate {
	/* keycode of the modifiers which select this table, -1 if none */
	int left_keycode;
	int right_keycode;
	const uchar *xlate;	/* keycode to ASCII table */
	int num_entries;	/* number of entries in this table */
};

struct input_config {
	uchar fifo[INPUT_BUFFER_LEN];
	int fifo_in, fifo_out;

	/* Which modifiers are active (1 bit for each MOD_... value) */
	uchar modifiers;
	uchar flags;		/* active state keys (FLAGS_...) */
	uchar leds;		/* active LEDS (INPUT_LED_...) */
	uchar num_tables;	/* number of modifier tables */
	int prev_keycodes[INPUT_BUFFER_LEN];	/* keys held last time */
	int num_prev_keycodes;	/* number of prev keys */
	struct input_key_xlate table[INPUT_MAX_MODIFIERS];

	/**
	 * Function the input helper calls to scan the keyboard
	 *
	 * @param config	Input state
	 * @return 0 if no keys read, otherwise number of keys read, or 1 if
	 *		unknown
	 */
	int (*read_keys)(struct input_config *config);
	unsigned int next_repeat_ms;	/* Next time we repeat a key */
	unsigned int repeat_delay_ms;	/* Time before autorepeat starts */
	unsigned int repeat_rate_ms;	/* Autorepeat rate in ms */
};

struct stdio_dev;

/**
 * Convert a list of key codes into ASCII and send them
 *
 * @param config	Input state
 * @param keycode	List of key codes to examine
 * @param num_keycodes	Number of key codes
 */
int input_send_keycodes(struct input_config *config, int keycode[], int count);

/**
 * Add a new key translation table to the input
 *
 * @param config	Input state
 * @param left_keycode	Key to hold to get into this table
 * @param right_keycode	Another key to hold to get into this table
 * @param xlate		Conversion table from key codes to ASCII
 * @param num_entries	Number of entries in xlate table
 */
int input_add_table(struct input_config *config, int left_keycode,
		    int right_keycode, const uchar *xlate, int num_entries);

/**
 * Test if keys are available to be read
 *
 * @param config	Input state
 * @return 0 if no keys available, 1 if keys are available
 */
int input_tstc(struct input_config *config);

/**
 * Read a key
 *
 * TODO: U-Boot wants 0 for no key, but Ctrl-@ is a valid key...
 *
 * @param config	Input state
 * @return key, or 0 if no key, or -1 if error
 */
int input_getc(struct input_config *config);

/**
 * Register a new device with stdio and switch to it if wanted
 *
 * @param dev	Pointer to device
 * @return 0 if ok, -1 on error
 */
int input_stdio_register(struct stdio_dev *dev);

/**
 * Set up the input handler with basic key maps.
 *
 * @param config	Input state
 * @param leds		Initial LED value (INPUT_LED_ mask), 0 suggested
 * @param repeat_delay_ms	Delay before key auto-repeat starts (in ms)
 * @param repeat_rate_ms	Delay between successive key repeats (in ms)
 * @return 0 if ok, -1 on error
 */
int input_init(struct input_config *config, int leds, int repeat_delay_ms,
	       int repeat_rate_ms);

#ifdef CONFIG_SYS_CONSOLE_OVERWRITE_ROUTINE
extern int overwrite_console(void);
#define OVERWRITE_CONSOLE overwrite_console()
#else
#define OVERWRITE_CONSOLE 0
#endif /* CONFIG_SYS_CONSOLE_OVERWRITE_ROUTINE */

#endif
