diff options
author | Mauro Carvalho Chehab <mchehab@redhat.com> | 2010-08-01 09:35:49 -0400 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@redhat.com> | 2010-08-02 15:43:51 -0400 |
commit | d3c501d1938c56c9998fd51fc8dadb49ddd6110e (patch) | |
tree | fafd97aa47e92c5ed54d0f9580a0a7e39f36b4a3 | |
parent | 0ffd1ab34a00b1e92af50ef11e696839f4cf642b (diff) |
V4L/DVB: dib0700: Fix RC protocol logic to properly handle NEC/NECx and RC-5
Simplifies the logic for handling firmware 1.20 RC messages, fixing the
logic.
While here, I tried to use a RC-6 remote controller from my TV set, but it
didn't work with dib0700. Not sure why, but maybe this never worked.
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
-rw-r--r-- | drivers/media/dvb/dvb-usb/dib0700_core.c | 66 |
1 files changed, 35 insertions, 31 deletions
diff --git a/drivers/media/dvb/dvb-usb/dib0700_core.c b/drivers/media/dvb/dvb-usb/dib0700_core.c index d73a688acabb..fe818348b8a3 100644 --- a/drivers/media/dvb/dvb-usb/dib0700_core.c +++ b/drivers/media/dvb/dvb-usb/dib0700_core.c | |||
@@ -499,7 +499,7 @@ int dib0700_change_protocol(void *priv, u64 ir_type) | |||
499 | return ret; | 499 | return ret; |
500 | } | 500 | } |
501 | 501 | ||
502 | d->props.rc.core.protocol = new_proto; | 502 | d->props.rc.core.protocol = ir_type; |
503 | 503 | ||
504 | return ret; | 504 | return ret; |
505 | } | 505 | } |
@@ -511,7 +511,13 @@ int dib0700_change_protocol(void *priv, u64 ir_type) | |||
511 | struct dib0700_rc_response { | 511 | struct dib0700_rc_response { |
512 | u8 report_id; | 512 | u8 report_id; |
513 | u8 data_state; | 513 | u8 data_state; |
514 | u16 system; | 514 | union { |
515 | u16 system16; | ||
516 | struct { | ||
517 | u8 system; | ||
518 | u8 not_system; | ||
519 | }; | ||
520 | }; | ||
515 | u8 data; | 521 | u8 data; |
516 | u8 not_data; | 522 | u8 not_data; |
517 | }; | 523 | }; |
@@ -521,9 +527,8 @@ static void dib0700_rc_urb_completion(struct urb *purb) | |||
521 | { | 527 | { |
522 | struct dvb_usb_device *d = purb->context; | 528 | struct dvb_usb_device *d = purb->context; |
523 | struct dib0700_state *st; | 529 | struct dib0700_state *st; |
524 | struct dib0700_rc_response poll_reply; | 530 | struct dib0700_rc_response *poll_reply; |
525 | u8 *buf; | 531 | u32 uninitialized_var(keycode); |
526 | u32 keycode; | ||
527 | u8 toggle; | 532 | u8 toggle; |
528 | 533 | ||
529 | deb_info("%s()\n", __func__); | 534 | deb_info("%s()\n", __func__); |
@@ -537,7 +542,7 @@ static void dib0700_rc_urb_completion(struct urb *purb) | |||
537 | } | 542 | } |
538 | 543 | ||
539 | st = d->priv; | 544 | st = d->priv; |
540 | buf = (u8 *)purb->transfer_buffer; | 545 | poll_reply = purb->transfer_buffer; |
541 | 546 | ||
542 | if (purb->status < 0) { | 547 | if (purb->status < 0) { |
543 | deb_info("discontinuing polling\n"); | 548 | deb_info("discontinuing polling\n"); |
@@ -550,52 +555,51 @@ static void dib0700_rc_urb_completion(struct urb *purb) | |||
550 | goto resubmit; | 555 | goto resubmit; |
551 | } | 556 | } |
552 | 557 | ||
553 | deb_data("IR raw %02X %02X %02X %02X %02X %02X (len %d)\n", buf[0], | 558 | deb_data("IR ID = %02X state = %02X System = %02X %02X Cmd = %02X %02X (len %d)\n", |
554 | buf[1], buf[2], buf[3], buf[4], buf[5], purb->actual_length); | 559 | poll_reply->report_id, poll_reply->data_state, |
560 | poll_reply->system, poll_reply->not_system, | ||
561 | poll_reply->data, poll_reply->not_data, | ||
562 | purb->actual_length); | ||
555 | 563 | ||
556 | switch (d->props.rc.core.protocol) { | 564 | switch (d->props.rc.core.protocol) { |
557 | case IR_TYPE_NEC: | 565 | case IR_TYPE_NEC: |
558 | poll_reply.data_state = 0; | ||
559 | poll_reply.system = buf[2]; | ||
560 | poll_reply.data = buf[4]; | ||
561 | poll_reply.not_data = buf[5]; | ||
562 | toggle = 0; | 566 | toggle = 0; |
563 | 567 | ||
564 | /* NEC protocol sends repeat code as 0 0 0 FF */ | 568 | /* NEC protocol sends repeat code as 0 0 0 FF */ |
565 | if ((poll_reply.system == 0x00) && (poll_reply.data == 0x00) | 569 | if ((poll_reply->system == 0x00) && (poll_reply->data == 0x00) |
566 | && (poll_reply.not_data == 0xff)) { | 570 | && (poll_reply->not_data == 0xff)) { |
567 | poll_reply.data_state = 2; | 571 | poll_reply->data_state = 2; |
568 | break; | 572 | break; |
569 | } | 573 | } |
570 | 574 | ||
575 | if ((poll_reply->system ^ poll_reply->not_system) != 0xff) { | ||
576 | deb_data("NEC extended protocol\n"); | ||
577 | /* NEC extended code - 24 bits */ | ||
578 | keycode = poll_reply->system16 << 8 | poll_reply->data; | ||
579 | } else { | ||
580 | deb_data("NEC normal protocol\n"); | ||
581 | /* normal NEC code - 16 bits */ | ||
582 | keycode = poll_reply->system << 8 | poll_reply->data; | ||
583 | } | ||
584 | |||
571 | break; | 585 | break; |
572 | default: | 586 | default: |
587 | deb_data("RC5 protocol\n"); | ||
573 | /* RC5 Protocol */ | 588 | /* RC5 Protocol */ |
574 | /* TODO: need to check the mapping for RC6 */ | 589 | toggle = poll_reply->report_id; |
575 | poll_reply.report_id = buf[0]; | 590 | keycode = poll_reply->system16 << 8 | poll_reply->data; |
576 | poll_reply.data_state = buf[1]; | ||
577 | poll_reply.system = (buf[2] << 8) | buf[3]; | ||
578 | poll_reply.data = buf[4]; | ||
579 | poll_reply.not_data = buf[5]; | ||
580 | |||
581 | toggle = poll_reply.report_id; | ||
582 | 591 | ||
583 | break; | 592 | break; |
584 | } | 593 | } |
585 | 594 | ||
586 | if ((poll_reply.data + poll_reply.not_data) != 0xff) { | 595 | if ((poll_reply->data + poll_reply->not_data) != 0xff) { |
587 | /* Key failed integrity check */ | 596 | /* Key failed integrity check */ |
588 | err("key failed integrity check: %04x %02x %02x", | 597 | err("key failed integrity check: %04x %02x %02x", |
589 | poll_reply.system, | 598 | poll_reply->system, |
590 | poll_reply.data, poll_reply.not_data); | 599 | poll_reply->data, poll_reply->not_data); |
591 | goto resubmit; | 600 | goto resubmit; |
592 | } | 601 | } |
593 | 602 | ||
594 | deb_data("rid=%02x ds=%02x sm=%04x d=%02x nd=%02x\n", | ||
595 | poll_reply.report_id, poll_reply.data_state, | ||
596 | poll_reply.system, poll_reply.data, poll_reply.not_data); | ||
597 | |||
598 | keycode = poll_reply.system << 8 | poll_reply.data; | ||
599 | ir_keydown(d->rc_input_dev, keycode, toggle); | 603 | ir_keydown(d->rc_input_dev, keycode, toggle); |
600 | 604 | ||
601 | resubmit: | 605 | resubmit: |