diff options
| author | Mauro Carvalho Chehab <mchehab@redhat.com> | 2012-01-01 14:11:12 -0500 |
|---|---|---|
| committer | Mauro Carvalho Chehab <mchehab@redhat.com> | 2012-01-04 14:29:17 -0500 |
| commit | 9682cea27e9ce7ede8e5c608900a52edaeb57a6b (patch) | |
| tree | ead6478080bd82d69896c221dff8d9da8cfa30fc | |
| parent | 9a27e6a0b70966ee141c8f576cc4836d5001d44f (diff) | |
[media] dvb: move dvb_set_frontend logic into a separate routine
This change is there in order to prepare the code to avoid calling
dvb_frontend_ioctl_legacy() from FE_SET_PROPERTY.
A call to dvb_frontend_ioctl_legacy() would require to update the
DVBv3 cache without need, mangling calls for newer delivery system
without any reason.
No functional changes here.
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
| -rw-r--r-- | drivers/media/dvb/dvb-core/dvb_frontend.c | 182 |
1 files changed, 93 insertions, 89 deletions
diff --git a/drivers/media/dvb/dvb-core/dvb_frontend.c b/drivers/media/dvb/dvb-core/dvb_frontend.c index 33ce309e8a9b..eefcb7f885a3 100644 --- a/drivers/media/dvb/dvb-core/dvb_frontend.c +++ b/drivers/media/dvb/dvb-core/dvb_frontend.c | |||
| @@ -1786,6 +1786,97 @@ out: | |||
| 1786 | return err; | 1786 | return err; |
| 1787 | } | 1787 | } |
| 1788 | 1788 | ||
| 1789 | static int dtv_set_frontend(struct file *file, unsigned int cmd, void *parg) | ||
| 1790 | { | ||
| 1791 | struct dvb_device *dvbdev = file->private_data; | ||
| 1792 | struct dvb_frontend *fe = dvbdev->priv; | ||
| 1793 | struct dvb_frontend_private *fepriv = fe->frontend_priv; | ||
| 1794 | struct dtv_frontend_properties *c = &fe->dtv_property_cache; | ||
| 1795 | struct dvb_frontend_tune_settings fetunesettings; | ||
| 1796 | |||
| 1797 | if (c->state == DTV_TUNE) { | ||
| 1798 | if (dvb_frontend_check_parameters(fe, &fepriv->parameters_in) < 0) | ||
| 1799 | return -EINVAL; | ||
| 1800 | } else { | ||
| 1801 | if (dvb_frontend_check_parameters(fe, parg) < 0) | ||
| 1802 | return -EINVAL; | ||
| 1803 | |||
| 1804 | memcpy (&fepriv->parameters_in, parg, | ||
| 1805 | sizeof (struct dvb_frontend_parameters)); | ||
| 1806 | dtv_property_cache_init(fe, c); | ||
| 1807 | dtv_property_cache_sync(fe, c, &fepriv->parameters_in); | ||
| 1808 | } | ||
| 1809 | |||
| 1810 | /* | ||
| 1811 | * Initialize output parameters to match the values given by | ||
| 1812 | * the user. FE_SET_FRONTEND triggers an initial frontend event | ||
| 1813 | * with status = 0, which copies output parameters to userspace. | ||
| 1814 | */ | ||
| 1815 | fepriv->parameters_out = fepriv->parameters_in; | ||
| 1816 | |||
| 1817 | memset(&fetunesettings, 0, sizeof(struct dvb_frontend_tune_settings)); | ||
| 1818 | |||
| 1819 | /* force auto frequency inversion if requested */ | ||
| 1820 | if (dvb_force_auto_inversion) { | ||
| 1821 | c->inversion = INVERSION_AUTO; | ||
| 1822 | } | ||
| 1823 | if (fe->ops.info.type == FE_OFDM) { | ||
| 1824 | /* without hierarchical coding code_rate_LP is irrelevant, | ||
| 1825 | * so we tolerate the otherwise invalid FEC_NONE setting */ | ||
| 1826 | if (c->hierarchy == HIERARCHY_NONE && | ||
| 1827 | c->code_rate_LP == FEC_NONE) | ||
| 1828 | c->code_rate_LP = FEC_AUTO; | ||
| 1829 | } | ||
| 1830 | |||
| 1831 | /* get frontend-specific tuning settings */ | ||
| 1832 | if (fe->ops.get_tune_settings && (fe->ops.get_tune_settings(fe, &fetunesettings) == 0)) { | ||
| 1833 | fepriv->min_delay = (fetunesettings.min_delay_ms * HZ) / 1000; | ||
| 1834 | fepriv->max_drift = fetunesettings.max_drift; | ||
| 1835 | fepriv->step_size = fetunesettings.step_size; | ||
| 1836 | } else { | ||
| 1837 | /* default values */ | ||
| 1838 | switch(fe->ops.info.type) { | ||
| 1839 | case FE_QPSK: | ||
| 1840 | fepriv->min_delay = HZ/20; | ||
| 1841 | fepriv->step_size = c->symbol_rate / 16000; | ||
| 1842 | fepriv->max_drift = c->symbol_rate / 2000; | ||
| 1843 | break; | ||
| 1844 | |||
| 1845 | case FE_QAM: | ||
| 1846 | fepriv->min_delay = HZ/20; | ||
| 1847 | fepriv->step_size = 0; /* no zigzag */ | ||
| 1848 | fepriv->max_drift = 0; | ||
| 1849 | break; | ||
| 1850 | |||
| 1851 | case FE_OFDM: | ||
| 1852 | fepriv->min_delay = HZ/20; | ||
| 1853 | fepriv->step_size = fe->ops.info.frequency_stepsize * 2; | ||
| 1854 | fepriv->max_drift = (fe->ops.info.frequency_stepsize * 2) + 1; | ||
| 1855 | break; | ||
| 1856 | case FE_ATSC: | ||
| 1857 | fepriv->min_delay = HZ/20; | ||
| 1858 | fepriv->step_size = 0; | ||
| 1859 | fepriv->max_drift = 0; | ||
| 1860 | break; | ||
| 1861 | } | ||
| 1862 | } | ||
| 1863 | if (dvb_override_tune_delay > 0) | ||
| 1864 | fepriv->min_delay = (dvb_override_tune_delay * HZ) / 1000; | ||
| 1865 | |||
| 1866 | fepriv->state = FESTATE_RETUNE; | ||
| 1867 | |||
| 1868 | /* Request the search algorithm to search */ | ||
| 1869 | fepriv->algo_status |= DVBFE_ALGO_SEARCH_AGAIN; | ||
| 1870 | |||
| 1871 | dvb_frontend_clear_events(fe); | ||
| 1872 | dvb_frontend_add_event(fe, 0); | ||
| 1873 | dvb_frontend_wakeup(fe); | ||
| 1874 | fepriv->status = 0; | ||
| 1875 | |||
| 1876 | return 0; | ||
| 1877 | } | ||
| 1878 | |||
| 1879 | |||
| 1789 | static int dvb_frontend_ioctl_legacy(struct file *file, | 1880 | static int dvb_frontend_ioctl_legacy(struct file *file, |
| 1790 | unsigned int cmd, void *parg) | 1881 | unsigned int cmd, void *parg) |
| 1791 | { | 1882 | { |
| @@ -1969,96 +2060,9 @@ static int dvb_frontend_ioctl_legacy(struct file *file, | |||
| 1969 | err = fe->ops.enable_high_lnb_voltage(fe, (long) parg); | 2060 | err = fe->ops.enable_high_lnb_voltage(fe, (long) parg); |
| 1970 | break; | 2061 | break; |
| 1971 | 2062 | ||
| 1972 | case FE_SET_FRONTEND: { | 2063 | case FE_SET_FRONTEND: |
| 1973 | struct dtv_frontend_properties *c = &fe->dtv_property_cache; | 2064 | err = dtv_set_frontend(file, cmd, parg); |
| 1974 | struct dvb_frontend_tune_settings fetunesettings; | ||
| 1975 | |||
| 1976 | if (c->state == DTV_TUNE) { | ||
| 1977 | if (dvb_frontend_check_parameters(fe, &fepriv->parameters_in) < 0) { | ||
| 1978 | err = -EINVAL; | ||
| 1979 | break; | ||
| 1980 | } | ||
| 1981 | } else { | ||
| 1982 | if (dvb_frontend_check_parameters(fe, parg) < 0) { | ||
| 1983 | err = -EINVAL; | ||
| 1984 | break; | ||
| 1985 | } | ||
| 1986 | |||
| 1987 | memcpy (&fepriv->parameters_in, parg, | ||
| 1988 | sizeof (struct dvb_frontend_parameters)); | ||
| 1989 | dtv_property_cache_init(fe, c); | ||
| 1990 | dtv_property_cache_sync(fe, c, &fepriv->parameters_in); | ||
| 1991 | } | ||
| 1992 | |||
| 1993 | /* | ||
| 1994 | * Initialize output parameters to match the values given by | ||
| 1995 | * the user. FE_SET_FRONTEND triggers an initial frontend event | ||
| 1996 | * with status = 0, which copies output parameters to userspace. | ||
| 1997 | */ | ||
| 1998 | fepriv->parameters_out = fepriv->parameters_in; | ||
| 1999 | |||
| 2000 | memset(&fetunesettings, 0, sizeof(struct dvb_frontend_tune_settings)); | ||
| 2001 | |||
| 2002 | /* force auto frequency inversion if requested */ | ||
| 2003 | if (dvb_force_auto_inversion) { | ||
| 2004 | c->inversion = INVERSION_AUTO; | ||
| 2005 | } | ||
| 2006 | if (fe->ops.info.type == FE_OFDM) { | ||
| 2007 | /* without hierarchical coding code_rate_LP is irrelevant, | ||
| 2008 | * so we tolerate the otherwise invalid FEC_NONE setting */ | ||
| 2009 | if (c->hierarchy == HIERARCHY_NONE && | ||
| 2010 | c->code_rate_LP == FEC_NONE) | ||
| 2011 | c->code_rate_LP = FEC_AUTO; | ||
| 2012 | } | ||
| 2013 | |||
| 2014 | /* get frontend-specific tuning settings */ | ||
| 2015 | if (fe->ops.get_tune_settings && (fe->ops.get_tune_settings(fe, &fetunesettings) == 0)) { | ||
| 2016 | fepriv->min_delay = (fetunesettings.min_delay_ms * HZ) / 1000; | ||
| 2017 | fepriv->max_drift = fetunesettings.max_drift; | ||
| 2018 | fepriv->step_size = fetunesettings.step_size; | ||
| 2019 | } else { | ||
| 2020 | /* default values */ | ||
| 2021 | switch(fe->ops.info.type) { | ||
| 2022 | case FE_QPSK: | ||
| 2023 | fepriv->min_delay = HZ/20; | ||
| 2024 | fepriv->step_size = c->symbol_rate / 16000; | ||
| 2025 | fepriv->max_drift = c->symbol_rate / 2000; | ||
| 2026 | break; | ||
| 2027 | |||
| 2028 | case FE_QAM: | ||
| 2029 | fepriv->min_delay = HZ/20; | ||
| 2030 | fepriv->step_size = 0; /* no zigzag */ | ||
| 2031 | fepriv->max_drift = 0; | ||
| 2032 | break; | ||
| 2033 | |||
| 2034 | case FE_OFDM: | ||
| 2035 | fepriv->min_delay = HZ/20; | ||
| 2036 | fepriv->step_size = fe->ops.info.frequency_stepsize * 2; | ||
| 2037 | fepriv->max_drift = (fe->ops.info.frequency_stepsize * 2) + 1; | ||
| 2038 | break; | ||
| 2039 | case FE_ATSC: | ||
| 2040 | fepriv->min_delay = HZ/20; | ||
| 2041 | fepriv->step_size = 0; | ||
| 2042 | fepriv->max_drift = 0; | ||
| 2043 | break; | ||
| 2044 | } | ||
| 2045 | } | ||
| 2046 | if (dvb_override_tune_delay > 0) | ||
| 2047 | fepriv->min_delay = (dvb_override_tune_delay * HZ) / 1000; | ||
| 2048 | |||
| 2049 | fepriv->state = FESTATE_RETUNE; | ||
| 2050 | |||
| 2051 | /* Request the search algorithm to search */ | ||
| 2052 | fepriv->algo_status |= DVBFE_ALGO_SEARCH_AGAIN; | ||
| 2053 | |||
| 2054 | dvb_frontend_clear_events(fe); | ||
| 2055 | dvb_frontend_add_event(fe, 0); | ||
| 2056 | dvb_frontend_wakeup(fe); | ||
| 2057 | fepriv->status = 0; | ||
| 2058 | err = 0; | ||
| 2059 | break; | 2065 | break; |
| 2060 | } | ||
| 2061 | |||
| 2062 | case FE_GET_EVENT: | 2066 | case FE_GET_EVENT: |
| 2063 | err = dvb_frontend_get_event (fe, parg, file->f_flags); | 2067 | err = dvb_frontend_get_event (fe, parg, file->f_flags); |
| 2064 | break; | 2068 | break; |
