[mythtv] dvbdiseqc.cpp & dvbdiseqc.h patches for DiSEqC 1.2 HH Motor Support

Taylor Jacob rtjacob at earthlink.net
Mon Mar 29 00:47:30 EST 2004


Attached is a patch to make DiSEqC switches work with DVB-S cards, and
simple "goto stored position xx" support for DiSEqC HH Motors.

Notes for this patch:

DiSEqC 1.x switches work.
DiSEqC HH Motors now work only with the goto stored position xx command.
The diseqc_type must be set to 6, and the stored position of the sat set
in diseqc_port (both fields in dvb_sat).

I am going to need to make some changes to the DB for the dvb_sat table to
change the Position to be a float to support USALS (Set Motor to angle x.x
degrees), and add a column that will store the DiSEqC motor saved position
number.  This is required because if you use a switch in combintion with a
motor you will be required to have 2 "positions" one being the switch, and
the other the motor saved position. Should I just make the changes in
dbcheck.cpp, and send them here, or do these changes need to be approved
before being applied?

I also would like to suggest that each satellite entry for DVB create a
new "input source".  This way for example if you are using a motor to get
2 different providers programming you can have you can attach the correct
videosource entry to the new input.
(continued example)
For example if I get NASA off of DishNetwork, and EuroNews off of Bell
ExpressVu with the same DVB card, I can obtain the guide for these 2
channels from xmltv for DishNetwork and Bell ExpressVu, but currently I
can only attach one videosource to a DVB card.  I do not know who would
need to approve these changes, but I can look into doing this, but I
suspect there is someone far more familiar with the code than I am that
could quickly do this.

I would like to appoligize for my message a day ago, I was pulling my hair
out trying to hunt down why the attached code stopped working.  The PIDs
of one of the channels I was testing with changed, and I thought my code
was not changing the switches.  It was changing the switches, but there
was no video to be displayed.

-------------- next part --------------
8a9,11
>  *      Taylor Jacob (rtjacob at earthlink.net)
>  *	    - Finished Implimenting Petri's DiSEqC 1.0 - 1.1 code
>  *          - DiSEqC 1.2 Positioner control 
41a45,46
> 
>     // Number of repeats for DiSEqC 1.1 devices
50a56
> 
61,63c67,71
<         case 2: // v1.0
<         case 3: // v1.1
<             if (!OneWayProtocol(tuning, reset, havetuned))
---
>         case 2: // v1.0 2 Way
>         case 3: // v1.1 2 Way
>         case 4: // v1.0 4 Way
>         case 5: // v1.1 4 Way
>             if (!Diseqc1xSwitch(tuning, reset, havetuned))
65a74,78
>         case 6: // 1.2 Positioner (HH Motor)
>             if (!PositionerGoto(tuning,reset,havetuned))
> 		return false;
>             break;
>  
79,81c92
<     CHANNEL(QString("Setting LNB: %1 %2")
<             .arg(tuning.tone==SEC_TONE_ON?"Tone ON":"Tone OFF")
<             .arg(tuning.voltage==SEC_VOLTAGE_13?"13V":"18V"));
---
>     CHANNEL(QString("Setting LNB: %1 %2").arg(tuning.tone==SEC_TONE_ON?"Tone ON":"Tone OFF").arg(tuning.voltage==SEC_VOLTAGE_13?"13V":"18V"));
94a106,107
>     usleep(DISEQC_SHORT_WAIT);
> 
112c125
<     CHANNEL(QString("Tone Switch - Port %1/2").arg(tuning.diseqc_port));
---
>     CHANNEL(QString("DiSEqC Tone Switch - Port %1/2").arg(tuning.diseqc_port));
137c150,229
< bool DVBDiSEqC::OneWayProtocol(dvb_tuning_t& tuning, bool reset, bool& havetuned)
---
> bool DVBDiSEqC::SendDiSEqCMessage(dvb_tuning_t& tuning, dvb_diseqc_master_cmd &cmd)
> {
> 
>    // Turn off tone burst
>    if (ioctl(fd_frontend, FE_SET_TONE, SEC_TONE_OFF) == -1) {
>       ERROR("FE_SET_TONE failed");
>       return false;
>    }
> 
> /* 
>    Old version of the code set the voltage to 13V everytime.  After looking at the EutelSat
>    specs I saw no reason that this was done. I have tested this with my DiSEqC switch and all
>    is fine. 
> */
> 
>    if (ioctl(fd_frontend, FE_SET_VOLTAGE, tuning.voltage) == -1) {
>       ERROR("FE_SET_VOLTAGE failed");
>       return false;
>    }   
> 
>    usleep(DISEQC_SHORT_WAIT);
> 
>    GENERAL(QString("DiSEqC Sending 1.0 Command: %1 %2 %3 %4").
>         arg(cmd.msg[0],2,16).arg(cmd.msg[1],2,16).arg(cmd.msg[2],2,16).arg(cmd.msg[3],2,16));
> 
>    if (ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &cmd) == -1) {
>       ERROR("FE_DISEQC_SEND_MASTER_CMD failed");
>       return false;
>    }
> 
>    usleep(DISEQC_SHORT_WAIT);
> 
>    // Check to see if its a 1.1 or 1.2 device. If so repeat the message repeats times.
>    if ((tuning.diseqc_type == 3) || 
>        (tuning.diseqc_type == 5) || 
>        (tuning.diseqc_type == 6)) {
> 
>       int repeats = repeat;
>       while (repeats--) {
> 
>           GENERAL(QString("DiSEqC Sending 1.1/1.2 Repeat Command: %1 %2 %3 %4").
>             arg(cmd.msg[0],2,16).arg(cmd.msg[1],2,16).arg(cmd.msg[2],2,16).arg(cmd.msg[3],2,16));
> 
>           cmd.msg[0] = CMD_REPEAT;      
>           if (ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &cmd) == -1) {
>               ERROR("FE_DISEQC_SEND_MASTER_CMD failed");
>               return false;
>           }
>           usleep(DISEQC_SHORT_WAIT);
>     
>           cmd.msg[0] = CMD_FIRST;      
>           if (ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &cmd) == -1) {
>               ERROR("FE_DISEQC_SEND_MASTER_CMD failed");
>               return false;
>           }
>           usleep(DISEQC_SHORT_WAIT);
>      
>       }
> 
> 
>    }
> 
>    if (ioctl(fd_frontend, FE_DISEQC_SEND_BURST, SEC_MINI_A ) == -1) {
>       ERROR("FE_DISEQC_SEND_BURST failed");
>       return false;
>    }
> 
>    usleep(DISEQC_SHORT_WAIT);
> 
>    if (ioctl(fd_frontend, FE_SET_TONE, tuning.tone) == -1) {
>       ERROR("FE_SET_TONE failed");
>       return false;
>    }
> 
>    return true;
> }
> 
> 
> 
> bool DVBDiSEqC::Diseqc1xSwitch(dvb_tuning_t& tuning, bool reset, bool& havetuned)
138a231,240
> 
>     if (reset) {
>       	if(!DiseqcReset()) {
>       	    ERROR("DiseqcReset() failed");
>       	    return false;
>       	}
>     }
> 
>     GENERAL(QString("DiSEqC 1.0 Switch - Port %1").arg(tuning.diseqc_port));
> 
144c246
<         if (tuning.diseqc_port > 4)
---
>         if (tuning.diseqc_port > 3)
150c252,259
<         if (!WritePortGroup(tuning))
---
>         dvb_diseqc_master_cmd cmd = {{CMD_FIRST, MASTER_TO_LSS, WRITE_N0, 0xf0, 0x00, 0x00}, 4};
> 
>         cmd.msg[DATA_1] = 0xF0 
>                           | (((tuning.diseqc_port) * 4) & 0x0F) 
>                           | ((tuning.voltage == SEC_VOLTAGE_18) ? 2 : 0) 
>                           | ((tuning.tone == SEC_TONE_ON) ? 0 : 1);
> 
>         if(!SendDiSEqCMessage(tuning,cmd)) 
160d268
<     }
162,163c270
<     if (!ToneVoltageLnb(tuning, reset, havetuned))
<         return false;
---
>     }
167a275,276
> /*
> 
170c279,281
<     struct dvb_diseqc_master_cmd cmd =
---
> 
> 
>     dvb_diseqc_master_cmd cmd =
176,180c287,293
<         ((((tuning.diseqc_port-1) * 4) & 0x0f) |
<         ((tuning.voltage == SEC_VOLTAGE_13) ? 1 : 0) |
<         ((tuning.tone == SEC_TONE_ON) ? 0 : 2));
<    
<     if (!PreDiseqcCmd())
---
>         (((tuning.diseqc_port) * 4) & 0x0f) |
>         ((tuning.voltage == SEC_VOLTAGE_18) ? 2 : 0) |
>         ((tuning.tone == SEC_TONE_ON) ? 0 : 1);
> 
>     GENERAL(QString("DiSEqC 1.0 Switch Command %1").arg(cmd.msg[DATA_1]));
> 
>     if (!PreDiseqcCmd(tuning))
183d295
<     /*
188d299
<     */
196a308,311
>     usleep(DISEQC_LONG_WAIT);
>     usleep(DISEQC_LONG_WAIT);
> 
>     // v1.1 of DiSEqC you are to repeat the message once
201c316
<         if(tuning.diseqc_type == 3)
---
>         if((tuning.diseqc_type == 5) || (tuning.diseqc_type == 3))
203a319
>             GENERAL(QString("DiSEqC 1.1 Switch Command %1").arg(cmd.msg[DATA_1]));
211c327
<         }
---
>         
213,216c329,333
<         if(ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &cmd) < 0)
<         {
<             ERRNO("OneWayProtocol: Sending committed command failed.");
<             return false;
---
>             if(ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &cmd) < 0)
>             {
>                ERRNO("OneWayProtocol: Sending committed command failed.");            return false;
>             }
>             usleep(DISEQC_LONG_WAIT);
218d334
<         usleep(DISEQC_LONG_WAIT);
221,229c337
<     usleep(DISEQC_SHORT_WAIT);
<     if(ioctl(fd_frontend, FE_DISEQC_SEND_BURST,
<         ((tuning.diseqc_port-1) / 4) % 2 ? SEC_MINI_B : SEC_MINI_A) < 0)
<     {
<         ERRNO("OneWayProtocol: Sending burst failed.");
<         return false;
<     }
<     usleep(DISEQC_SHORT_WAIT);
<     
---
> 
233c341
< bool DVBDiSEqC::PreDiseqcCmd()
---
> bool DVBDiSEqC::PreDiseqcCmd(dvb_tuning_t& tuning)
234a343
> 
242a352
>     if (ioctl(fd_frontend, FE_SET_VOLTAGE, tuning.voltage) < 0)
251a362
> */
254a366
> 
256c368
<        {{CMD_FIRST, MASTER_TO_LSS, RESET, 0x00, 0x00, 0x00}, 3};
---
>        {{CMD_FIRST, MASTER_TO_LSS, RESET, 0x00, 0x00}, 3};
259c371
<        {{CMD_FIRST, MASTER_TO_LSS, POWERON, 0x00, 0x00, 0x00}, 3};
---
>        {{CMD_FIRST, MASTER_TO_LSS, POWERON, 0x00, 0x00}, 3};
301c413,414
< bool DVBDiSEqC::Positioner_Goto(int satpos)
---
> 
> bool DVBDiSEqC::PositionerGoto(dvb_tuning_t& tuning, bool reset, bool& havetuned)
303,304c416,447
<     (void)satpos;
<     return false;
---
> 
> // A reset seems to be required for my positioner to work consistently.
> //    if (reset) {
>       	if(!DiseqcReset()) {
>       	    ERROR("DiseqcReset() failed");
>       	    return false;
>       	}
> //    }
> 
>     GENERAL(QString("DiSEqC 1.2 Motor - Stored Position %1").arg(tuning.diseqc_port));
> 
>     if ((prev_tuning.diseqc_port != tuning.diseqc_port ||
>           prev_tuning.tone != tuning.tone ||
>           prev_tuning.voltage != tuning.voltage) || reset)
>     {
> 
>         dvb_diseqc_master_cmd cmd = {{CMD_FIRST, MASTER_TO_POSITIONER, GOTO, tuning.diseqc_port , 0x00, 0x00}, 4};
> 
>         if(!SendDiSEqCMessage(tuning,cmd)) 
>         {
>             ERROR("Setting DiSEqC failed.\n");
>             return false;
>         }
> 
>         prev_tuning.diseqc_port = tuning.diseqc_port;
>         prev_tuning.tone = tuning.tone;
>         prev_tuning.voltage = tuning.voltage;
>         havetuned = true;
> 
>     }
> 
>     return true;
-------------- next part --------------
33a34
>     bool SendDiSEqCMessage(dvb_tuning_t& tuning, dvb_diseqc_master_cmd &cmd);
36,38c37,44
<     bool PreDiseqcCmd();
<     bool OneWayProtocol(dvb_tuning_t& tuning, bool reset, bool& havetuned);
<     bool WritePortGroup(dvb_tuning_t& tuning);
---
>     bool Diseqc1xSwitch(dvb_tuning_t& tuning, bool reset, bool& havetuned);
>     bool PositionerGoto(dvb_tuning_t& tuning, bool reset, bool& havetuned);
> 
> //  Depreciated Code
> //    bool PreDiseqcCmd(dvb_tuning_t& tuning);
> //    bool WritePortGroup(dvb_tuning_t& tuning);
> 
> // Code still to be written
42d47
<     bool Positioner_Goto(int satpos);
71,74c76,80
<         MASTER_TO_ALL       = 0x00,
<         MASTER_TO_LSS       = 0x10,
<         MASTER_TO_LNB       = 0x11,
<         MASTER_TO_SWITCH    = 0x14
---
>         MASTER_TO_ALL        = 0x00,
>         MASTER_TO_LSS        = 0x10,
>         MASTER_TO_LNB        = 0x11,
>         MASTER_TO_SWITCH     = 0x14,
>         MASTER_TO_POSITIONER = 0x31
76a83
> 


More information about the mythtv-dev mailing list