
/****************************************************************************
 ** ir_remote_types.h *******************************************************
 ****************************************************************************
 *
 * ir_remote_types.h - describes and decodes the signals from IR remotes
 *
 * Copyright (C) 1996,97 Ralph Metzler <rjkm@thp.uni-koeln.de>
 * Copyright (C) 1998 Christoph Bartelmus <lirc@bartelmus.de>
 *
 */

/**
 * @file ir_remote_types.h
 * @ingroup private_api
 * @ingroup private_api
 * @brief Describes and decodes the signals from IR remotes.
 */

#ifndef IR_REMOTE_TYPES_H
#define IR_REMOTE_TYPES_H

#ifdef	__cplusplus
extern "C" {
#endif

#if defined(__linux__)
#include <sys/types.h>
#else
#include <stdint.h>
typedef int8_t   __s8;
typedef uint8_t  __u8;
typedef int16_t  __s16;
typedef uint16_t __u16;
typedef int32_t  __s32;
typedef uint32_t __u32;
typedef int64_t  __s64;
typedef uint64_t __u64;
#endif

#include <sys/time.h>
#include <unistd.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#if defined(__linux__)
#include <linux/types.h>
#endif

#include "include/media/lirc.h"

/**
 * Denotes an internal coded representation for an IR transmission.
 *  Note that there may be more than one ir_code in one ir_ncode.
 */
typedef __u64 ir_code;

/**
 * An ir_code for entering into (singly) linked lists,
 *  i.e. with a pointer to other ir_code_node.
 */
struct ir_code_node {
	ir_code code;
	struct ir_code_node *next;
};

/**
 * IR Command, corresponding to one (command defining) line of the
 * configuration file.
 * Normally, there is only one ir_code herein (field code), however, there
 *  may be more, namely in the linked list in the field next.
 */
struct ir_ncode {
	/** Name of command */
	char *name;

	/** The first code of the command*/
	ir_code code;

	/** (private) */
	int length;

	/** (private) */
	lirc_t *signals;

	/** Linked list of the subsequent ir_code's, after the first one.
	 *  NULL if there is only one ir_code (normal case). */
	struct ir_code_node *next;

	/** Should point at the ir_code currently being transmitted,
	 * or NULL if none. */
	struct ir_code_node *current;

	/** (private) */
	struct ir_code_node *transmit_state;
};

/*
  struct ir_remote
  defines the encoding of a remote control
*/

/* definitions for flags */

#define IR_PROTOCOL_MASK 0x07ff

/* protocols: must not be combined */
/* Don't forget to take a look at config_file.h when adding new flags */

#define RAW_CODES       0x0001	/**< for internal use only */
#define RC5             0x0002	/**< IR data follows RC5 protocol */
#define SHIFT_ENC	   RC5	/**< IR data is shift encoded (name obsolete) */
/* Hm, RC6 protocols seem to have changed the biphase semantics so
   that lircd will calculate the bit-wise complement of the codes. But
   this is only a guess as I did not have a datasheet... */

#define RC6             0x0004	/**< IR data follows RC6 protocol */
#define RCMM            0x0008	/**< IR data follows RC-MM protocol */
#define SPACE_ENC	0x0010	/**< IR data is space encoded */
#define SPACE_FIRST     0x0020	/**< bits are encoded as space+pulse */
#define GOLDSTAR        0x0040	/**< encoding found on Goldstar remote */
#define GRUNDIG         0x0080	/**< encoding found on Grundig remote */
#define BO              0x0100	/**< encoding found on Bang & Olufsen remote */
#define SERIAL          0x0200	/**< serial protocol */
#define XMP             0x0400	/**< XMP protocol */

/* additinal flags: can be orred together with protocol flag */
#define REVERSE		0x0800
#define NO_HEAD_REP	0x1000	/**< no header for key repeats */
#define NO_FOOT_REP	0x2000	/**< no foot for key repeats */
#define CONST_LENGTH    0x4000	/**< signal length+gap is always constant */
#define REPEAT_HEADER   0x8000	/**< header is also sent before repeat code */

#define COMPAT_REVERSE  0x00010000	/**< compatibility mode for REVERSE flag */

/** stop repeating after 600 signals (approx. 1 minute)
 * update technical.html when changing this value
 */
#define REPEAT_MAX_DEFAULT 600

#define DEFAULT_FREQ 38000

#define IR_PARITY_NONE 0
#define IR_PARITY_EVEN 1
#define IR_PARITY_ODD  2

/** State describing code, pre, post + gap and repeat state. */
struct decode_ctx_t {
        ir_code code;     /**< Code part, matched to code defintion. */
        ir_code pre;      /**< pre data, before code. */
        ir_code post;     /**< post data, sent after code. */
        int     repeat_flag; /**< True if code is a repeated one. */
        lirc_t  max_remaining_gap; /**< Estimated max time of trailing gap.*/
        lirc_t  min_remaining_gap; /**< Estimated min time of trailing gap.*/
};


/**
 * One remote as represented in the configuration file.
 */
struct ir_remote {
	const char* name;	/**< name of remote control */
	const char* driver;     /**< Name of driver for LIRCCODE cases. */
	struct ir_ncode* codes;
	int bits;		/**< bits (length of code) */
	int flags;		/**< flags */
	int eps;		/**< eps (_relative_ tolerance) */
       				/** detecting _very short_ pulses is
				  * difficult with relative tolerance
				  * for some remotes,
				  * this is an _absolute_ tolerance
				  * to solve this problem
				  * usually you can say 0 here. */
	int aeps;
	char* dyncodes_name;	/**< name for unknown buttons */
	int dyncode;		/**< last received code */
	struct ir_ncode dyncodes[2];	/**< helper structs for unknown buttons */

	/* pulse and space lengths of: */

	lirc_t phead, shead;	/**< header */
	lirc_t pthree, sthree;	/**< 3 (only used for RC-MM) */
	lirc_t ptwo, stwo;	/**< 2 (only used for RC-MM) */
	lirc_t pone, sone;	/**< 1 */
	lirc_t pzero, szero;	/**< 0 */
	lirc_t plead;		/**< leading pulse */
	lirc_t ptrail;		/**< trailing pulse */
	lirc_t pfoot, sfoot;	/**< foot */
	lirc_t prepeat, srepeat;	/**< indicate repeating */

	int pre_data_bits;	/**< length of pre_data */
	ir_code pre_data;	/**< data which the remote sends before actual keycode */
	int post_data_bits;	/**< length of post_data */
	ir_code post_data;	/**< data which the remote sends after actual keycode */
	lirc_t pre_p, pre_s;	/**< signal between pre_data and keycode */
	lirc_t post_p, post_s;	/**< signal between keycode and post_code */

	__u32 gap;		/**< time between signals in usecs */
	__u32 gap2;		/**< time between signals in usecs */
	__u32 repeat_gap;	/**< time between two repeat codes if different from gap */
	int toggle_bit;		/**< obsolete */
	ir_code toggle_bit_mask; /**< previously only one bit called toggle_bit */
	int suppress_repeat;	/**< suppress unwanted repeats */
	/** code is repeated at least x times
	* code sent once -> min_repeat=0 */
	int min_repeat;
	/**
	 * meaningful only if remote sends
	*				   a repeat code: in this case
	*				   this value indicates how often
	*				   the real code is repeated
	*				   before the repeat code is being
	*				   sent */
	unsigned int min_code_repeat;
	unsigned int freq;	/**< modulation frequency */
	unsigned int duty_cycle;	/**< 0<duty cycle<=100 */
	ir_code toggle_mask;	/**< Sharp (?) error detection scheme */
	ir_code rc6_mask;	/**< RC-6 doubles signal length of some bits */

	/* serial protocols */
	unsigned int baud;	/**< can be overridden by [p|s]zero, [p|s]one */
	unsigned int bits_in_byte;	/**< default: 8 */
	unsigned int parity;	/**< currently unsupported */
	unsigned int stop_bits;	/**< mapping: 1->2 1.5->3 2->4 */

	/** mask defines which bits can be
	   ignored when matching a code */
	ir_code ignore_mask;
	ir_code repeat_mask;	/**< mask defines which bits are inverted for repeats */
	/* end of user editable values */

	ir_code toggle_bit_mask_state;
	int toggle_mask_state;
	int repeat_countdown;
	struct ir_ncode* last_code;	/**< code received or sent last */
	struct ir_ncode* toggle_code;	/**< toggle code received or sent last */
	int reps;
	struct timeval last_send;	/**< time last_code was received or sent */
	lirc_t min_remaining_gap;	/**< remember gap for CONST_LENGTH remotes */
	lirc_t max_remaining_gap;	/**< gap range */

	lirc_t min_total_signal_length;	/**< how long is the shortest signal including gap */
	lirc_t max_total_signal_length;	/**< how long is the longest signal including gap */
	lirc_t min_gap_length;	/**< how long is the shortest gap */
	lirc_t max_gap_length;	/**< how long is the longest gap */
	lirc_t min_pulse_length, max_pulse_length;
	lirc_t min_space_length, max_space_length;
	int release_detected;	/**< set by release generator */
	int manual_sort;        /**< If set in any remote, disables automatic sorting. */
	struct ir_remote* next;
};

#ifdef	__cplusplus
}
#endif

#endif
