The value of a GPIO input is only sampled when the peripheral clock for
the port controller the GPIO resides in is enabled. Therefore we need
to enable the clock even when polling a GPIO.
Per documentation SAM4S and SAM4E have the BMR register values
as they are already defined. No need for chip specific values.
In addition:
- CONFIG_ARCH_CHIP_SAM4s has wrong lower case 's' so the definitions would
not be used anyways for SAM4S builds.
- TC_BMR_TC2XC2S_TIOA2 does not make sense. There is no way to loop back
TC2's TIOA2 into itself.
"This is a fix to a problem in the handling of the oneshot timer. Due to a wrong assumption concerning the behavior directly after the start of the timer/counter the function sam_oneshot_cancel(…) calculates the wrong remaining time. The code assumes that the counter register is zero directly after the start of the timer, but this is not true. To start the time/counter a software trigger is invoked, this trigger starts the timer/count and sets the counter register to zero, but the reset of the counter register is not performed instantly. According to the datasheet: “The counter can be reset by a trigger. In this case, the counter value passes to zero on the next valid edge of the selected clock.” Thus the counter is set to zero between 0 and USEC_PER_TICK microseconds after the clock was started.
"In my fix I use the freerun count value to determine if at least one tick passed since the start of the timer and thus if the value of the oneshot counter is correct. I also tried to use the function up_timer_gettime(…) to achieve this but, at least if compiled with no optimization the problem vanishes without using the value of the function, the function call takes too long.
"Another problem treated in the fix is that if the oneshot timer/counter is canceled, we only know the remaining time with a precision of USEC_PER_TICK microseconds. This means the calculated remaining time is between 0 and USEC_PER_TICK microseconds too long. To fix this I subtract one tick if the calculated remaining time is greater than one tick and otherwise set the remaining time to zero. By doing so the measured times are much more precise as without it."
sam_i2cbus_initialize
sam_i2cbus_uninitialize
sam_i2cbus_initialize
Or twi_reset is called.
I found this a while back in the stm32 family, so there may be more arch-es with this sort of bug. I suppose any driver that has the notion of "do not set the freq if it is already set" could be suspect.