diff --git a/src/input/mpegts/linuxdvb/linuxdvb_en50494.c b/src/input/mpegts/linuxdvb/linuxdvb_en50494.c index 10cbb9dc..eb143770 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_en50494.c +++ b/src/input/mpegts/linuxdvb/linuxdvb_en50494.c @@ -157,10 +157,10 @@ const idclass_t linuxdvb_en50494_class = static int linuxdvb_en50494_tune - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *sc, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *sc, int vol ) { - int ret = 0; - int i; + int ret = 0, i, fd = linuxdvb_satconf_fe_fd(lsp); linuxdvb_en50494_t *le = (linuxdvb_en50494_t*) ld; linuxdvb_lnb_t *lnb = sc->lse_lnb; @@ -211,7 +211,7 @@ linuxdvb_en50494_tune } /* use 18V */ - ret = linuxdvb_diseqc_set_volt(fd, SEC_VOLTAGE_18); + ret = linuxdvb_diseqc_set_volt(lsp, 1); if (ret) { tvherror("en50494", "error setting lnb voltage to 18V"); break; @@ -245,7 +245,7 @@ linuxdvb_en50494_tune usleep(50000); /* standard: 2ms < x < 60ms */ /* return to 13V */ - ret = linuxdvb_diseqc_set_volt(fd, SEC_VOLTAGE_13); + ret = linuxdvb_diseqc_set_volt(lsp, 0); if (ret) { tvherror("en50494", "error setting lnb voltage back to 13V"); break; diff --git a/src/input/mpegts/linuxdvb/linuxdvb_lnb.c b/src/input/mpegts/linuxdvb/linuxdvb_lnb.c index c91bdebc..664f112d 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_lnb.c +++ b/src/input/mpegts/linuxdvb/linuxdvb_lnb.c @@ -110,7 +110,8 @@ linuxdvb_lnb_inverted_pol static int linuxdvb_lnb_standard_tune - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls, int vol ) { /* en50494 does not use the voltage tune. this is happend in the switch */ if (ls->lse_en50494) @@ -119,12 +120,7 @@ linuxdvb_lnb_standard_tune /* note: differentiate between linuxdvb_lnb_standard_pol / linuxdvb_lnb_inverted_pol */ int pol = ((linuxdvb_lnb_t*)ld)->lnb_pol((linuxdvb_lnb_t*)ld, lm); - if (ls->lse_parent->ls_diseqc_full || ls->lse_parent->ls_last_pol != pol + 1) { - ls->lse_parent->ls_last_pol = pol + 1; - return linuxdvb_diseqc_set_volt(fd, pol); - } - - return 0; + return linuxdvb_diseqc_set_volt(ls->lse_parent, pol); } /* @@ -166,7 +162,8 @@ linuxdvb_lnb_bandstack_pol static int linuxdvb_lnb_bandstack_tune - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls, int vol ) { int pol = linuxdvb_lnb_bandstack_pol((linuxdvb_lnb_t*)ld, lm); @@ -174,11 +171,7 @@ linuxdvb_lnb_bandstack_tune if (ls->lse_en50494) return 0; - if (ls->lse_parent->ls_diseqc_full || ls->lse_parent->ls_last_pol != pol + 1) { - ls->lse_parent->ls_last_pol = pol + 1; - return linuxdvb_diseqc_set_volt(fd, pol); - } - return 0; + return linuxdvb_diseqc_set_volt(ls->lse_parent, pol); } /* ************************************************************************** diff --git a/src/input/mpegts/linuxdvb/linuxdvb_private.h b/src/input/mpegts/linuxdvb/linuxdvb_private.h index c085d1b4..6c5814ed 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_private.h +++ b/src/input/mpegts/linuxdvb/linuxdvb_private.h @@ -158,7 +158,7 @@ struct linuxdvb_satconf */ linuxdvb_satconf_ele_list_t ls_elements; linuxdvb_satconf_ele_t *ls_last_switch; - int ls_last_pol; + int ls_last_vol; int ls_last_toneburst; int ls_last_tone_off; int ls_last_orbital_pos; @@ -204,9 +204,9 @@ struct linuxdvb_diseqc linuxdvb_satconf_ele_t *ld_satconf; int (*ld_grace) (linuxdvb_diseqc_t *ld, dvb_mux_t *lm); int (*ld_tune) (linuxdvb_diseqc_t *ld, dvb_mux_t *lm, - linuxdvb_satconf_ele_t *ls, int fd); + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls, int pol); int (*ld_post) (linuxdvb_diseqc_t *ld, dvb_mux_t *lm, - linuxdvb_satconf_ele_t *ls, int fd); + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls); }; struct linuxdvb_lnb @@ -309,7 +309,7 @@ void linuxdvb_en50494_init (void); int linuxdvb_diseqc_send (int fd, uint8_t framing, uint8_t addr, uint8_t cmd, uint8_t len, ...); -int linuxdvb_diseqc_set_volt (int fd, int volt); +int linuxdvb_diseqc_set_volt ( linuxdvb_satconf_t *ls, int volt ); /* * Satconf @@ -340,9 +340,11 @@ void linuxdvb_satconf_post_stop_mux( linuxdvb_satconf_t *ls ); int linuxdvb_satconf_start_mux ( linuxdvb_satconf_t *ls, mpegts_mux_instance_t *mmi ); -int linuxdvb_satconf_tone_off( linuxdvb_satconf_ele_t *ls, int fd, int delay ); +int linuxdvb_satconf_start ( linuxdvb_satconf_t *ls, int delay, int vol ); -void linuxdvb_satconf_reset - ( linuxdvb_satconf_t *ls ); +void linuxdvb_satconf_reset ( linuxdvb_satconf_t *ls ); + +static inline int linuxdvb_satconf_fe_fd ( linuxdvb_satconf_t *ls ) + { return ((linuxdvb_frontend_t *)ls->ls_frontend)->lfe_fe_fd; } #endif /* __TVH_LINUXDVB_PRIVATE_H__ */ diff --git a/src/input/mpegts/linuxdvb/linuxdvb_rotor.c b/src/input/mpegts/linuxdvb/linuxdvb_rotor.c index adbb8520..4b59f60c 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_rotor.c +++ b/src/input/mpegts/linuxdvb/linuxdvb_rotor.c @@ -346,9 +346,10 @@ linuxdvb_rotor_check_orbital_pos /* GotoX */ static int linuxdvb_rotor_gotox_tune - ( linuxdvb_rotor_t *lr, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_rotor_t *lr, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls ) { - int i; + int i, fd = linuxdvb_satconf_fe_fd(lsp); for (i = 0; i <= ls->lse_parent->ls_diseqc_repeats; i++) { if (linuxdvb_diseqc_send(fd, 0xE0, 0x31, 0x6B, 1, (int)lr->lr_position)) { @@ -366,13 +367,13 @@ linuxdvb_rotor_gotox_tune /* USALS */ static int linuxdvb_rotor_usals_tune - ( linuxdvb_rotor_t *lr, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_rotor_t *lr, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls ) { static const uint8_t xtable[10] = { 0x00, 0x02, 0x03, 0x05, 0x06, 0x08, 0x0A, 0x0B, 0x0D, 0x0E }; - linuxdvb_satconf_t *lsp = ls->lse_parent; - int i, angle = sat_angle(lr, ls); + int i, angle = sat_angle(lr, ls), fd = linuxdvb_satconf_fe_fd(lsp); uint32_t cmd = 0xE000; if (angle < 0) { @@ -399,39 +400,34 @@ linuxdvb_rotor_usals_tune static int linuxdvb_rotor_tune - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls, int vol ) { linuxdvb_rotor_t *lr = (linuxdvb_rotor_t*)ld; if (linuxdvb_rotor_check_orbital_pos(lr, lm, ls)) return 0; - if (linuxdvb_satconf_tone_off(ls, fd, 1)) - return -1; - /* Force to 18v (quicker movement) */ - if (ioctl(fd, FE_SET_VOLTAGE, SEC_VOLTAGE_18)) { - tvherror("diseqc", "failed to set 18v for rotor movement"); + if (linuxdvb_satconf_start(lsp, 1, 1)) return -1; - } - usleep(15000); - ls->lse_parent->ls_last_pol = 2; /* GotoX */ if (idnode_is_instance(&lr->ld_id, &linuxdvb_rotor_gotox_class)) - return linuxdvb_rotor_gotox_tune(lr, lm, ls, fd); + return linuxdvb_rotor_gotox_tune(lr, lm, lsp, ls); /* USALS */ - return linuxdvb_rotor_usals_tune(lr, lm, ls, fd); + return linuxdvb_rotor_usals_tune(lr, lm, lsp, ls); } static int linuxdvb_rotor_post - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *ls, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, + linuxdvb_satconf_t *lsp, linuxdvb_satconf_ele_t *ls ) { linuxdvb_rotor_t *lr = (linuxdvb_rotor_t*)ld; - ls->lse_parent->ls_last_orbital_pos = pos_to_integer(lr->lr_sat_lon); + lsp->ls_last_orbital_pos = pos_to_integer(lr->lr_sat_lon); return 0; } diff --git a/src/input/mpegts/linuxdvb/linuxdvb_satconf.c b/src/input/mpegts/linuxdvb/linuxdvb_satconf.c index a785124b..9f8dc556 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_satconf.c +++ b/src/input/mpegts/linuxdvb/linuxdvb_satconf.c @@ -657,8 +657,7 @@ linuxdvb_satconf_post_stop_mux { gtimer_disarm(&ls->ls_diseqc_timer); if (ls->ls_frontend && ls->ls_lnb_poweroff) { - linuxdvb_diseqc_set_volt( - ((linuxdvb_frontend_t *)ls->ls_frontend)->lfe_fe_fd, -1); + linuxdvb_diseqc_set_volt(ls, -1); linuxdvb_satconf_reset(ls); } } @@ -689,13 +688,14 @@ linuxdvb_satconf_get_grace } int -linuxdvb_satconf_tone_off ( linuxdvb_satconf_ele_t *lse, int fd, int delay ) +linuxdvb_satconf_start ( linuxdvb_satconf_t *ls, int delay, int vol ) { - linuxdvb_satconf_t *ls = lse->lse_parent; + if (vol >= 0 && linuxdvb_diseqc_set_volt(ls, vol)) + return -1; if (ls->ls_last_tone_off != 1) { tvhtrace("diseqc", "initial tone off"); - if (ioctl(fd, FE_SET_TONE, SEC_TONE_OFF)) { + if (ioctl(linuxdvb_satconf_fe_fd(ls), FE_SET_TONE, SEC_TONE_OFF)) { tvherror("diseqc", "failed to disable tone"); return -1; } @@ -728,6 +728,12 @@ linuxdvb_satconf_ele_tune ( linuxdvb_satconf_ele_t *lse ) (linuxdvb_diseqc_t*)lse->lse_lnb }; + if (!lse->lse_en50494) { + pol = (lse->lse_lnb) ? lse->lse_lnb->lnb_pol(lse->lse_lnb, lm) & 0x1 : 0; + } else { + pol = 0; /* 13V */ + } + /* * Disable tone (en50494 don't use tone) * The 22khz tone is used for signalling band (universal LNB) @@ -738,7 +744,7 @@ linuxdvb_satconf_ele_tune ( linuxdvb_satconf_ele_t *lse ) if (!lse->lse_en50494 || lse->lse_switch || lse->lse_rotor) { if (ls->ls_diseqc_full) { ls->ls_last_tone_off = 0; /* force */ - if (linuxdvb_satconf_tone_off(lse, lfe->lfe_fe_fd, 0)) + if (linuxdvb_satconf_start(ls, 0, pol)) return -1; } } @@ -746,7 +752,7 @@ linuxdvb_satconf_ele_tune ( linuxdvb_satconf_ele_t *lse ) /* Diseqc */ for (i = ls->ls_diseqc_idx; i < ARRAY_SIZE(lds); i++) { if (!lds[i]) continue; - r = lds[i]->ld_tune(lds[i], lm, lse, lfe->lfe_fe_fd); + r = lds[i]->ld_tune(lds[i], lm, ls, lse, pol); /* Error */ if (r < 0) return r; @@ -762,24 +768,14 @@ linuxdvb_satconf_ele_tune ( linuxdvb_satconf_ele_t *lse ) /* Do post things (store position for rotor) */ if (lse->lse_rotor) - lse->lse_rotor->ld_post(lse->lse_rotor, lm, lse, lfe->lfe_fe_fd); + lse->lse_rotor->ld_post(lse->lse_rotor, lm, ls, lse); /* LNB settings */ - pol = (lse->lse_lnb) ? lse->lse_lnb->lnb_pol (lse->lse_lnb, lm) & 0x1 : 0; - - if (ls->ls_diseqc_full || ls->ls_last_pol != pol + 1) { - - ls->ls_last_pol = 0; - - /* EN50494 devices have another mechanism to select polarization */ - if (!lse->lse_en50494) { - - /* Set the voltage */ - if (linuxdvb_diseqc_set_volt(lfe->lfe_fe_fd, pol)) - return -1; - - ls->ls_last_pol = pol + 1; - } + /* EN50494 devices have another mechanism to select polarization */ + if (!lse->lse_en50494) { + /* Set the voltage */ + if (linuxdvb_diseqc_set_volt(ls, pol)) + return -1; } /* Set the tone (en50494 don't use tone) */ @@ -867,7 +863,7 @@ linuxdvb_satconf_reset ( linuxdvb_satconf_t *ls ) { ls->ls_last_switch = NULL; - ls->ls_last_pol = 0; + ls->ls_last_vol = 0; ls->ls_last_toneburst = 0; ls->ls_last_tone_off = 0; } @@ -1438,17 +1434,22 @@ linuxdvb_diseqc_send } int -linuxdvb_diseqc_set_volt ( int fd, int vol ) +linuxdvb_diseqc_set_volt ( linuxdvb_satconf_t *ls, int vol ) { + /* Already set ? */ + if (vol >= 0 && ls->ls_last_vol == vol + 1) + return 0; /* Set voltage */ tvhtrace("diseqc", "set voltage %dV", vol ? (vol < 0 ? 0 : 18) : 13); - if (ioctl(fd, FE_SET_VOLTAGE, - vol ? (vol < 0 ? SEC_VOLTAGE_OFF : SEC_VOLTAGE_18) : SEC_VOLTAGE_13)) { + if (ioctl(linuxdvb_satconf_fe_fd(ls), FE_SET_VOLTAGE, + vol ? (vol < 0 ? SEC_VOLTAGE_OFF : SEC_VOLTAGE_18) : SEC_VOLTAGE_13)) { tvherror("diseqc", "failed to set voltage (e=%s)", strerror(errno)); + ls->ls_last_vol = 0; return -1; } if (vol >= 0) usleep(15000); + ls->ls_last_vol = vol ? (vol < 0 ? 0 : 2) : 1; return 0; } diff --git a/src/input/mpegts/linuxdvb/linuxdvb_switch.c b/src/input/mpegts/linuxdvb/linuxdvb_switch.c index 8b524e78..53cffda6 100644 --- a/src/input/mpegts/linuxdvb/linuxdvb_switch.c +++ b/src/input/mpegts/linuxdvb/linuxdvb_switch.c @@ -144,18 +144,19 @@ const idclass_t linuxdvb_switch_class = static int linuxdvb_switch_tune - ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_ele_t *sc, int fd ) + ( linuxdvb_diseqc_t *ld, dvb_mux_t *lm, linuxdvb_satconf_t *lsp, + linuxdvb_satconf_ele_t *sc, int vol ) { int i, com, r1 = 0, r2 = 0; int pol, band; + int fd = linuxdvb_satconf_fe_fd(lsp); linuxdvb_switch_t *ls = (linuxdvb_switch_t*)ld; - linuxdvb_satconf_t *lsp = sc->lse_parent; if (lsp->ls_diseqc_full || lsp->ls_last_switch != sc) { lsp->ls_last_switch = NULL; - if (linuxdvb_satconf_tone_off(sc, fd, 1)) + if (linuxdvb_satconf_start(lsp, 1, vol)) return -1; pol = (sc->lse_lnb) ? sc->lse_lnb->lnb_pol (sc->lse_lnb, lm) & 0x1 : 0; @@ -204,7 +205,7 @@ linuxdvb_switch_tune if (ls->ls_toneburst >= 0 && (lsp->ls_diseqc_full || lsp->ls_last_toneburst != ls->ls_toneburst + 1)) { - if (linuxdvb_satconf_tone_off(sc, fd, 1)) + if (linuxdvb_satconf_start(lsp, 1, vol)) return -1; lsp->ls_last_toneburst = 0;