23 #define LIRCD_EXACT_GAP_THRESHOLD 10000    25 #ifdef HAVE_KERNEL_LIRC_H    26 #include <linux/lirc.h>    28 #include "media/lirc.h"    31 #include "lirc/lirc_log.h"    32 #include "lirc/transmit.h"    42         lirc_t  _data[WBUF_SIZE]; 
    52 static void send_signals(lirc_t* signals, 
int n);
    53 static int init_send_or_sim(
struct ir_remote* remote, 
struct ir_ncode* code, 
int sim, 
int repeat_preset);
    64         memset(&send_buffer, 0, 
sizeof(send_buffer));
    67 static void clear_send_buffer(
void)
    71         send_buffer.too_long = 0;
    72         send_buffer.is_biphase = 0;
    73         send_buffer.pendingp = 0;
    74         send_buffer.pendings = 0;
    78 static void add_send_buffer(lirc_t data)
    80         if (send_buffer.wptr < WBUF_SIZE) {
    81                 log_trace2(
"adding to transmit buffer: %u", data);
    82                 send_buffer.sum += data;
    83                 send_buffer._data[send_buffer.wptr] = data;
    86                 send_buffer.too_long = 1;
    90 static void send_pulse(lirc_t data)
    92         if (send_buffer.pendingp > 0) {
    93                 send_buffer.pendingp += data;
    95                 if (send_buffer.pendings > 0) {
    96                         add_send_buffer(send_buffer.pendings);
    97                         send_buffer.pendings = 0;
    99                 send_buffer.pendingp = data;
   103 static void send_space(lirc_t data)
   105         if (send_buffer.wptr == 0 && send_buffer.pendingp == 0) {
   109         if (send_buffer.pendings > 0) {
   110                 send_buffer.pendings += data;
   112                 if (send_buffer.pendingp > 0) {
   113                         add_send_buffer(send_buffer.pendingp);
   114                         send_buffer.pendingp = 0;
   116                 send_buffer.pendings = data;
   120 static int bad_send_buffer(
void)
   122         if (send_buffer.too_long != 0)
   124         if (send_buffer.wptr == WBUF_SIZE && send_buffer.pendingp > 0)
   129 static int check_send_buffer(
void)
   133         if (send_buffer.wptr == 0) {
   137         for (i = 0; i < send_buffer.wptr; i++) {
   138                 if (send_buffer.data[i] == 0) {
   151 static void flush_send_buffer(
void)
   153         if (send_buffer.pendingp > 0) {
   154                 add_send_buffer(send_buffer.pendingp);
   155                 send_buffer.pendingp = 0;
   157         if (send_buffer.pendings > 0) {
   158                 add_send_buffer(send_buffer.pendings);
   159                 send_buffer.pendings = 0;
   163 static void sync_send_buffer(
void)
   165         if (send_buffer.pendingp > 0) {
   166                 add_send_buffer(send_buffer.pendingp);
   167                 send_buffer.pendingp = 0;
   169         if (send_buffer.wptr > 0 && send_buffer.wptr % 2 == 0)
   173 static void send_header(
struct ir_remote* remote)
   175         if (has_header(remote)) {
   176                 send_pulse(remote->phead);
   177                 send_space(remote->
shead);
   181 static void send_foot(
struct ir_remote* remote)
   183         if (has_foot(remote)) {
   184                 send_space(remote->
sfoot);
   185                 send_pulse(remote->pfoot);
   189 static void send_lead(
struct ir_remote* remote)
   191         if (remote->
plead != 0)
   192                 send_pulse(remote->
plead);
   195 static void send_trail(
struct ir_remote* remote)
   198                 send_pulse(remote->
ptrail);
   201 static void send_data(
struct ir_remote* remote, 
ir_code data, 
int bits, 
int done)
   204         int all_bits = bit_count(remote);
   208         data = reverse(data, bits);
   209         if (is_rcmm(remote)) {
   210                 mask = 1 << (all_bits - 1 - done);
   211                 if (bits % 2 || done % 2) {
   215                 for (i = 0; i < bits; i += 2, mask >>= 2) {
   218                                 send_pulse(remote->pzero);
   219                                 send_space(remote->
szero);
   223                                 send_pulse(remote->pone);
   224                                 send_space(remote->
sone);
   227                                 send_pulse(remote->ptwo);
   228                                 send_space(remote->
stwo);
   231                                 send_pulse(remote->pthree);
   232                                 send_space(remote->
sthree);
   238         } 
else if (is_xmp(remote)) {
   239                 if (bits % 4 || done % 4) {
   243                 for (i = 0; i < bits; i += 4) {
   246                         nibble = reverse(data & 0xf, 4);
   247                         send_pulse(remote->pzero);
   248                         send_space(remote->
szero + nibble * remote->
sone);
   254         mask = ((
ir_code)1) << (all_bits - 1 - done);
   255         for (i = 0; i < bits; i++, mask >>= 1) {
   257                         if (toggle_bit_mask_bits == 1) {
   260                                 if (remote->toggle_bit_mask_state & mask)
   263                                 if (remote->toggle_bit_mask_state & mask)
   267                 if (has_toggle_mask(remote) && mask & remote->
toggle_mask && remote->toggle_mask_state % 2)
   270                         if (is_biphase(remote)) {
   272                                         send_space(2 * remote->
sone);
   273                                         send_pulse(2 * remote->pone);
   275                                         send_space(remote->
sone);
   276                                         send_pulse(remote->pone);
   278                         } 
else if (is_space_first(remote)) {
   279                                 send_space(remote->
sone);
   280                                 send_pulse(remote->pone);
   282                                 send_pulse(remote->pone);
   283                                 send_space(remote->
sone);
   287                                 send_pulse(2 * remote->pzero);
   288                                 send_space(2 * remote->
szero);
   289                         } 
else if (is_space_first(remote)) {
   290                                 send_space(remote->
szero);
   291                                 send_pulse(remote->pzero);
   293                                 send_pulse(remote->pzero);
   294                                 send_space(remote->
szero);
   301 static void send_pre(
struct ir_remote* remote)
   303         if (has_pre(remote)) {
   305                 if (remote->pre_p > 0 && remote->
pre_s > 0) {
   306                         send_pulse(remote->pre_p);
   307                         send_space(remote->
pre_s);
   312 static void send_post(
struct ir_remote* remote)
   314         if (has_post(remote)) {
   315                 if (remote->post_p > 0 && remote->
post_s > 0) {
   316                         send_pulse(remote->post_p);
   317                         send_space(remote->
post_s);
   323 static void send_repeat(
struct ir_remote* remote)
   326         send_pulse(remote->prepeat);
   344                 send_buffer.sum -= remote->phead + remote->
shead;
   347 static void send_signals(lirc_t* signals, 
int n)
   351         for (i = 0; i < n; i++)
   352                 add_send_buffer(signals[i]);
   357         return init_send_or_sim(remote, code, 0, 0);
   366         return init_send_or_sim(remote, code, 1, repeat_preset);
   375         return send_buffer.wptr;
   381         return send_buffer.data;
   386         return send_buffer.sum;
   389 static int init_send_or_sim(
struct ir_remote* remote, 
struct ir_ncode* code, 
int sim, 
int repeat_preset)
   391         int i, repeat = repeat_preset;
   393         if (is_grundig(remote) || is_goldstar(remote) || is_serial(remote) || is_bo(remote)) {
   395                         log_error(
"sorry, can't send this protocol yet");
   399         if (strcmp(remote->
name, 
"lirc") == 0) {
   400                 send_buffer.data[send_buffer.wptr] = 
LIRC_EOF | 1;
   401                 send_buffer.wptr += 1;
   405         if (is_biphase(remote))
   406                 send_buffer.is_biphase = 1;
   409                         remote->repeat_countdown = remote->
min_repeat;
   415         if (repeat && has_repeat(remote)) {
   420                 if (!is_raw(remote)) {
   424                                 next_code = code->
code;
   428                         if (repeat && has_repeat_mask(remote))
   431                         send_code(remote, next_code, repeat);
   432                         if (!sim && has_toggle_mask(remote)) {
   433                                 remote->toggle_mask_state++;
   434                                 if (remote->toggle_mask_state == 4)
   435                                         remote->toggle_mask_state = 2;
   437                         send_buffer.data = send_buffer._data;
   444                         if (send_buffer.wptr > 0) {
   447                                 send_buffer.data = code->
signals;
   448                                 send_buffer.wptr = code->
length;
   449                                 for (i = 0; i < code->
length; i++)
   450                                         send_buffer.sum += code->
signals[i];
   455         if (bad_send_buffer()) {
   463         if (has_repeat_gap(remote) && repeat && has_repeat(remote)) {
   466         } 
else if (is_const(remote)) {
   467                 if (min_gap(remote) > send_buffer.sum) {
   481         if (code->
next != NULL) {
   490         if ((remote->repeat_countdown > 0 || code->
transmit_state != NULL)
   492                 if (send_buffer.data != send_buffer._data) {
   496                         log_trace(
"unrolling raw signal optimisation");
   497                         signals = send_buffer.data;
   498                         n = send_buffer.wptr;
   499                         send_buffer.data = send_buffer._data;
   500                         send_buffer.wptr = 0;
   502                         send_signals(signals, n);
   504                 log_trace(
"concatenating low gap signals");
   506                         remote->repeat_countdown--;
   517         if (!check_send_buffer()) {
   520                         log_error(
"this remote configuration cannot be used to transmit");
 lirc_t min_remaining_gap
remember gap for CONST_LENGTH remotes 
One remote as represented in the configuration file. 
int bits
bits (length of code) 
const lirc_t * send_buffer_data(void)
#define NO_FOOT_REP
no foot for key repeats 
ir_code post_data
data which the remote sends after actual keycode 
lirc_t post_s
signal between keycode and post_code 
lirc_t plead
leading pulse 
ir_code repeat_mask
mask defines which bits are inverted for repeats 
struct ir_code_node * next
Linked list of the subsequent ir_code's, after the first one. 
const char * name
name of remote control 
lirc_t * signals
(private) 
#define LIRC_EOF
Bit manipulator in lirc_t, see lirc.h . 
lirc_t ptrail
trailing pulse 
int pre_data_bits
length of pre_data 
logchannel_t
Log channels used to filter messages. 
#define log_trace2(fmt,...)
Log a trace2 message. 
int post_data_bits
length of post_data 
lirc_t sthree
3 (only used for RC-MM) 
ir_code toggle_mask
Sharp (?) error detection scheme. 
#define log_error(fmt,...)
Log an error message. 
ir_code pre_data
data which the remote sends before actual keycode 
lirc_t send_buffer_sum(void)
uint32_t gap
time between signals in usecs 
#define log_trace(fmt,...)
Log a trace message. 
void send_buffer_init(void)
Initializes the global sending buffer. 
uint32_t repeat_gap
time between two repeat codes if different from gap 
#define REPEAT_HEADER
header is also sent before repeat code 
int send_buffer_put(struct ir_remote *remote, struct ir_ncode *code)
Initializes the global send buffer for transmitting the code in the second argument, residing in the remote in the first. 
#define CONST_LENGTH
signal length+gap is always constant 
#define NO_HEAD_REP
no header for key repeats 
lirc_t pre_s
signal between pre_data and keycode 
IR Command, corresponding to one (command defining) line of the configuration file. 
lirc_t stwo
2 (only used for RC-MM) 
lirc_t srepeat
indicate repeating 
struct ir_code_node * transmit_state
(private) 
lirc_t max_remaining_gap
gap range 
ir_code code
The first code of the command. 
ir_code rc6_mask
RC-6 doubles signal length of some bits. 
int send_buffer_length(void)
Do not document this function. 
struct ir_remote * repeat_remote
Global pointer to the remote that contains the code currently repeating. 
ir_code toggle_bit_mask
previously only one bit called toggle_bit 
int min_repeat
code is repeated at least x times code sent once -> min_repeat=0 
uint64_t ir_code
Denotes an internal coded representation for an IR transmission.