A typical code fragment was copied across many dvb-frontend drivers and
causes large stack frames when built with with CONFIG_KASAN on gcc-5/6/7:
drivers/media/dvb-frontends/cxd2841er.c:3225:1: error: the frame size of 3992 bytes is larger than 3072 bytes [-Werror=frame-larger-than=]
drivers/media/dvb-frontends/cxd2841er.c:3404:1: error: the frame size of 3136 bytes is larger than 3072 bytes [-Werror=frame-larger-than=]
drivers/media/dvb-frontends/stv0367.c:3143:1: error: the frame size of 4016 bytes is larger than 3072 bytes [-Werror=frame-larger-than=]
drivers/media/dvb-frontends/stv090x.c:3430:1: error: the frame size of 5312 bytes is larger than 3072 bytes [-Werror=frame-larger-than=]
drivers/media/dvb-frontends/stv090x.c:4248:1: error: the frame size of 4872 bytes is larger than 3072 bytes [-Werror=frame-larger-than=]
gcc-8 now solves this by consolidating the stack slots for the argument
variables, but on older compilers we can get the same behavior by taking
the pointer of a local variable rather than the inline function argument.
Link: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81715
Cc: stable@vger.kernel.org
Signed-off-by: Arnd Bergmann <arnd@arndb.de>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The loop with read status use a dynamic timeout value, calculated
from symbol rate. It should run the loop at least one time for
the status to be handled after the loop.
While this should, in practice, happen every time, it doesn't
hurt to change the logic to make it explicit.
This solves a smatch warning:
drivers/media/dvb-frontends/cxd2841er.c:3350 cxd2841er_set_frontend_s() error: uninitialized symbol 'status'.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Using the ARRAY_SIZE macro improves the readability of the code. Also,
it is not always useful to use a variable to store this constant
calculated at compile time.
Found with Coccinelle with the following semantic patch:
@r depends on (org || report)@
type T;
T[] E;
position p;
@@
(
(sizeof(E)@p /sizeof(*E))
|
(sizeof(E)@p /sizeof(E[...]))
|
(sizeof(E)@p /sizeof(T))
)
Signed-off-by: Jérémy Lefaure <jeremy.lefaure@lse.epita.fr>
Reviewed-by: Michael Ira Krufky <mkrufky@linuxtv.org>
Signed-off-by: Hans Verkuil <hans.verkuil@cisco.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Since the driver now recognizes and supports more chip variants, reflect
this fact in the module description accordingly.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Discovered using w_scan when scanning DVB-T/T2: When w_scan goes from -T
to -T2, it does so without stopping the frontend using .sleep. Due to
this, the demod operation mode isn't re-setup, but as it still is in
STATE_ACTIVE_TC, PLP and T2 Profile are set up, but only retune_active()
is called, leaving the demod in T mode, thus not operable on any T2
frequency.
Fix this by putting the demod to sleep if priv->system isn't equal to
p->delsys. To properly accomplish this, sleep_tc() is split into
sleep_tc() and shutdown_tc(), where sleep_tc() will only perform the
sleep operation, while shutdown_tc() additionally performs the full
demod shutdown (to keep the behaviour when the .sleep FE_OP is called).
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Don't populate arrays on the stack but make them static. Makes
the object code smaller:
Before:
text data bss dec hex filename
89299 21704 64 111067 1b1db cxd2841er.o
After:
text data bss dec hex filename
85823 23432 64 109319 1ab07 cxd2841er.o
Signed-off-by: Colin Ian King <colin.king@canonical.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
When the demod driver puts the demod into sleep or shutdown state and it's
status is then polled e.g. via "dvb-fe-tool -m", i2c errors are printed
to the kernel log. If the last delsys was DVB-T/T2:
cxd2841er: i2c wr failed=-5 addr=6c reg=00 len=1
cxd2841er: i2c rd failed=-5 addr=6c reg=26
and if it was DVB-C:
cxd2841er: i2c wr failed=-5 addr=6c reg=00 len=1
cxd2841er: i2c rd failed=-5 addr=6c reg=49
This happens when read_status unconditionally calls into the
read_signal_strength() function which triggers the read_agc_gain_*()
functions, where these registered are polled.
This isn't a critical thing since when the demod is active again, no more
such errors are logged, however this might make users suspecting defects.
Fix this by requiring STATE_ACTIVE_* in priv->state. If it isn't in any
active state, additionally set the strength scale to NOT_AVAILABLE.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
On DVB-T/T2 at least, SNR might be reported as >2500dB, which not only is
just wrong but also ridiculous, so fix this by improving the conversion
of the register value.
The INTLOG10X100 function/macro and the way the values are converted were
both taken from DD's cxd2843 driver.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Bits 3 and 4 of the TSCONFIG register are important for certain hardware
constellations, in that they need to be zeroed. Add a configuration flag
to toggle this.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Adds a flag to enable or disable the IFAGCNEG bit in cxd2841er_init_tc().
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Don't wait for FE_HAS_LOCK in set_frontend_tc() and thus don't hammer the
lock status register with inquiries when CXD2841ER_NO_WAIT_LOCK is set
in the configuration, which also unneccessarily blocks applications until
a TS LOCK has been acquired. Rather, API and applications will check for
a TS LOCK by utilising the tune fe_op, read_status and get_frontend ops,
which is sufficient.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
When AUTO_IFHZ is set and the tuner is supposed to provide proper IF speed
values, it should be possible to have the tuner setup take place before
the demod is configured, else the demod might be configured with either
wrong (old), or even no values at all, which obviously will cause issues.
To set this behaviour in the most flexible way, this is done with a
separate flag instead of making this depend on AUTO_IFHZ.
It should be evaluated if tuning shouldn't take place earlier in all cases
and hardware constellations.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The Sony CXD28xx demods may have other tuner types attached to them (e.g.
NXP TDA18212), so don't mandatorily configure and enable the ASCOT
functionality, but make this conditional by a config flag.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Some constellations work/need a serial TS transport mode. This adds a flag
that will toggle set up of such mode.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Add a AUTO_IFHZ flag and a function that will read IF speed values from any
attached tuner if the tuner supports this and if AUTO_IFHZ is enabled, and
else the passed default value (which probably matches Sony ASCOT tuners)
will be passed back. The returned value is then used to calculate the iffeq
which the demod will be programmed with.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Some cards/bridges wrap i2c_gate_ctrl handling with a mutex_lock(). This is
e.g. done in ddbridge to protect against concurrent tuner access with
regards to the dual tuner HW, where concurrent tuner reconfiguration can
result in tuning fails or bad reception quality. When the tuner driver
additionally tries to open the I2C gate (which e.g. the tda18212 driver
does) when the demod already did this, this will lead to a deadlock. This
makes the calls to i2c_gatectrl from the demod driver optional when the
flag is set, leaving this to the tuner driver. For readability reasons and
to not have the check duplicated multiple times, the setup is factored
into cxd2841er_tuner_set().
This commit also updates the netup card driver (which seems to be the only
consumer of the cxd2841er as of now).
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Throughout the patch series some configuration flags will be added to the
demod driver. This patch prepares this by adding the flags var to
struct cxd2841er_config, which will serve as a bitmask to toggle various
options and behaviour in the driver.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The way the MAKE_IFFREQ_CONFIG macros are written make it impossible to
pass regular integers for iffreq calculation, since this will cause "SSE
register return with SSE disabled" compile errors. This changes the
calculation into C functions which also might help when debugging. Also,
expand all passed frequencies from MHz to Hz scale.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Those demods are programmed in the same way as the CXD2841ER/54ER and can
be handled by this driver. Support added in a way matching the existing
code, supported delivery systems are set according to what each demod
supports.
Updates the type string setting used for printing the "attaching..." log
line aswell.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Do unfreeze_regs() directly when accessing the demod registers is done,
and don't have multiple unfreeze's on different conditions, which even
can get prone to errors.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Doing the I2C read operation with two calls to i2c_transfer() causes the
exclusive I2C bus lock of the underlying adapter to be released. While this
isn't an issue if only one demodulator is attached to the bus, having two
or even more causes troubles in that concurrent accesses to the different
demods will cause all kinds of issues due to wrong data being returned on
read operations (for example, the TS config register will be set wrong).
This changes the read_regs() function to do the operation in one go (by
calling i2c_transfer with the whole msg list instead of one by one) to not
loose the I2C bus lock, fixing all sorts of random runtime failures.
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
This moves the I2C debug dump into the preceding dev_dbg() call by
utilising the %*ph format macro and removes the call to
print_hex_debug_bytes().
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Fixes "w_scan -f c" complaining with
This dvb driver is *buggy*: the symbol rate limits are undefined - please
report to linuxtv.org)
Signed-off-by: Daniel Scheller <d.scheller@gmx.net>
Acked-by: Abylay Ospan <aospan@netup.ru>
Cc: stable@vger.kernel.org
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
These are immutable. Making them "const" allows the compiler to move
them to the "rodata" section.
Note that cxd2841er_t_c_ops cannot be made "const", because
cxd2841er_attach() modifies it. Ouch!
[mchehab@s-opensource.com: fix merge conflicts]
Signed-off-by: Max Kellermann <max.kellermann@gmail.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
if specified DVB-C bandwidth not supported then force 8MHz.
Should work for most cases.
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Added function to read BER for ISDB-T
Also SNR values fixed for ISDB-T
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
ensure multiple separate register reads are from the same snapshot
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The addition of jump label support in dynamic_debug caused an unexpected
warning in exactly one file in the kernel:
drivers/media/dvb-frontends/cxd2841er.c: In function 'cxd2841er_tune_tc':
include/linux/dynamic_debug.h:134:3: error: 'carrier_offset' may be used uninitialized in this function [-Werror=maybe-uninitialized]
__dynamic_dev_dbg(&descriptor, dev, fmt, \
^~~~~~~~~~~~~~~~~
drivers/media/dvb-frontends/cxd2841er.c:3177:11: note: 'carrier_offset' was declared here
int ret, carrier_offset;
^~~~~~~~~~~~~~
The problem seems to be that the compiler gets confused by the extra
conditionals in static_branch_unlikely, to the point where it can no
longer keep track of which branches have already been taken, and it
doesn't realize that this variable is now always initialized when it
gets used.
I have done lots of randconfig kernel builds and could not find any
other file with this behavior, so I assume it's a rare enough glitch
that we don't need to change the jump label support but instead just
work around the warning in the driver.
To achieve that, I'm moving the check for the return value into the
switch() statement, which is an obvious transformation, but is enough to
un-confuse the compiler here. The resulting code is not as nice to
read, but at least we retain the behavior of warning if it gets changed
to actually access an uninitialized carrier offset value in the future.
Link: http://lkml.kernel.org/r/20160713204342.1221511-1-arnd@arndb.de
Signed-off-by: Arnd Bergmann <arnd@arndb.de>
Acked-by: Abylay Ospan <aospan@netup.ru>
Cc: Sergey Kozlov <serjk@netup.ru>
Cc: Mauro Carvalho Chehab <mchehab@kernel.org>
Cc: Jason Baron <jbaron@akamai.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Now driver returns correct values for DVB-C:
SNR (in dB)
[mchehab@s-opensource.com: fix a new function to be static]
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
now driver returns correct values for DVB-C:
BER (post_bit_count and post_bit_error values)
UCB (count of uncorrected errors)
also, some code cleanup was done - checkpatch.pl now is happy
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
DVB-C should use cxd2841er_read_agc_gain_c() to get the gain. The same
function is used for all DVB-C annex delivery systems.
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The scale for ISDB-T was wrong too: it was inverted, and
on a relative scale.
Use a linear interpolation to make it look better.
The formula was empirically determined, using 3 frequencies
(175 MHz, 410 MHz and 800 MHz), measuring from -50dBm to
-12dBm in steps of 0.5dB.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Instead of using a relative frequency range, calibrate it to
show the results in dB. The callibration was done getting
samples with a signal generated from -50dBm to -12dBm,
incremented in steps of 0.5 dB, using 3 frequencies:
175 MHz, 410 MHz and 800 MHz. The modulated signal was
using QAM64, and it was used a linear interpolation of all
the results.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Currently, there's no stats for DVB-C. Let's at least return
signal strength. The scale is different than on DVB-T, so let's
use a relative scale, for now.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
What userspace expects is to receive both bit_error and bit_count
counters. So, instead of doing the division at the Kernel,
return the counters for userspace to handle it the way it
wants.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The current code will expose a zero value if one of the stats is
not available, but this is not what userspace expects. Instead,
if something goes wrong on providing some stats, it should be
changing the scale to FE_SCALE_NOT_AVAILABLE.
So, change the logic to do the right thing.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
cxd2841er_read_agc_gain_c added to obtain signal strength.
signal strength now relay on AGC value.
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
The signal strength value is reversed: the bigger the number,
the weaker is the signal.
Fix the logic and present it in dBm. Please notice that the
dBm measure is actually an estimation, as the ratio is not
fully linear. It also varies with the frequency.
Yet, the estimation should be good enough for programs like
Kaffeine to indicate when the signal is good or bad.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
It is a good idea to measure the signal strength while
tuning, as this helps to identify if the antenna is ok.
Also, such measure helps to identify the quality of the
signal.
Do some changes to enable it before signal lock. While
here, optimize the code to only initialize the stats
length once, and make sure that, just after set_frontend,
any reading for the stats that depends on lock to return
FE_SCALE_NOT_AVAILABLE.
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
Acked-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>
correct is CXD2841ER and CXD2854ER
incorrect was CXD2441ER and CXD2454ER
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
now when new tuning parameters specified demod should retune.
Also ISDB-T frequency offset calculation added
(cxd2841er_get_carrier_offset_i).
While here, fix re-tune for DVB-C Annex A, using the desired
bandwidth, instead of using 8MHz.
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
Avoid error message:
cxd2841er_read_status_s(): invalid state 1
Always force demod to shutdown state before initializing
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
CXD2854ER is identical to CXD2841ER except ISDB-T/S added.
New method 'cxd2841er_attach_i' is added
xtal frequency now configurable. Available options:
20.5MHz, 24MHz, 41MHz
Signed-off-by: Abylay Ospan <aospan@netup.ru>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
Instead of using the DTV properties cache directly, pass the get
frontend data as an argument. For now, everything should remain
the same, but the next patch will prevent get_frontend to
affect the global cache.
This is needed because several drivers don't care enough to only
change the properties if locked. Due to that, calling
G_PROPERTY before locking on those drivers will make them to
never lock. Ok, those drivers are crap and should never be
merged like that, but the core should not rely that the drivers
would be doing the right thing.
Reviewed-by: Michael Ira Krufky <mkrufky@linuxtv.org>
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>
The Linux stack is short; we need to be able to count the number
of bytes used at stack on each function. So, we don't like to
use variable-length arrays, as complained by smatch:
drivers/media/dvb-frontends/cxd2841er.c:205:19: warning: Variable length array is used.
The max usecase of the driver seems to be 15 bytes + 1 for the
register.
So, let's be safe and allocate 17 bytes for the write buffer.
This should be enough to cover all cases. If not, let's print
an error message.
Signed-off-by: Mauro Carvalho Chehab <mchehab@osg.samsung.com>