Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SPIFFS, FLASH SPI and PWM (Timer1) bug #604

Open
Zaltora opened this issue Apr 5, 2018 · 9 comments
Open

SPIFFS, FLASH SPI and PWM (Timer1) bug #604

Zaltora opened this issue Apr 5, 2018 · 9 comments

Comments

@Zaltora
Copy link
Contributor

Zaltora commented Apr 5, 2018

Hi i got a recent bug,
It is feel that receive UART interrupt > Timer1 interrupt. The motor is disrupting when i wrote on keyboard some text.
Before, this problem was not present.
I try to found what PR or sub-module does this bug. recent "lock" change maybe ?
It is not a HW bug, and i didn't change the uart part of my app.

@Zaltora
Copy link
Contributor Author

Zaltora commented Apr 5, 2018

I use uart_getc_nowait(bus).
I try to checkout old commit 3 month ago, but i got same problem. The good program was made 19 feb 2018.
I don't no what happens.

@Zaltora
Copy link
Contributor Author

Zaltora commented Apr 12, 2018

Okay, i was wrong.
Is not uart problem, it is the filesystem spiffs/ libc API when a save or close file.
Each time a file is saved, the pwm is disturbed.
Maybe the FLASH acces.

@Zaltora Zaltora changed the title UART Receive and PWM (Timer1) bug SPIFFS, FLASH SPI and PWM (Timer1) bug Apr 12, 2018
@ourairquality
Copy link
Contributor

Interrupts are disabled while accessing the flash, for reading or writing. This is necessary because code can not be run from the flash while accessing it. Writing might be especially slow and could this cause the pwm problems? The extras/pwm implementation appears to use an interrupt that would be disabled.

It might be possible to run the pwm from a NMI. All the code in the interrupt handler would need to be in the IRAM. Never tried this, but perhaps sdk_wDev_MacTimSetFunc and sdk_wDev_MacTimArm or sdk_wDev_MacTim1SetFunc and sdk_wDev_MacTim1Arm could be used for the pwm timer?? These appears to generate NMIs. The sdk_wDev_MacTim1Arm appears to be used for a soft wdt, so perhaps try the other.

Also saw some discussion that the esp8266 might have a hardware pwm, and perhaps support could be added for that. For example, see esp8266/Arduino#1654 Does anyone know or a hardware pwm implementation?

@ourairquality
Copy link
Contributor

Fwiw the hardware pwm seems to work, and the registers appear to be already defined. Where this were adequate it might be smoother than a software pwm and less burden on the system. The example below could dim the blue led on a nodemcu. If someone could confirm the frequency and duty calculations then we could add a description to gpio_regs.h and perhaps even some supporting functions and an example.

    uint8_t gpio_num = 2; // Blue led
    gpio_enable(gpio_num, GPIO_OUTPUT);
    GPIO.CONF[gpio_num] |= GPIO_CONF_SOURCE_PWM;
    // Freq = (80,000,000/prescale) * (target / 256) HZ           (0   < target < 128)
    // Freq = (80,000,000/prescale) * ((256 - target) / 256)  HZ  (128 < target < 256)
    uint8_t prescale = 0xff;
    uint8_t duty = 32;
    GPIO.PWM = GPIO_PWM_ENABLE | (prescale << 16) | duty;

@Zaltora
Copy link
Contributor Author

Zaltora commented Apr 14, 2018

o yeah, That will be nice to get this HW pwm !!
I will try this. I a mreally surprise to learn today that exist this HW pwm.

Before, i was trying to work with overlap SPI without succes to connect the flash SPI wire with my screen.
I am no sure if it is possible to put esp8266 in SPI slave mode too.

Edit: the resolution is 256 ? or it can be greater ?

@flannelhead
Copy link
Contributor

Wow @ourairquality, where did you learn about this HW PWM capability? I thought there wasn't one. So is this really different from the HW delta-sigma modulator that has been known to exists? Do you know if it supports multiple channels?

@ourairquality
Copy link
Contributor

@flannelhead The definitions were already in the include files, and it is described there as a PWM. I think this is the sigma-delta modulator. It seems to support only one channel, but it seems possible to route that one channel to all of gpio 0 to 15. It does appear to be limited to a resolution of 256. So it is limited, but still it might suit some uses and be smoother and less burden than the software solutions. If the name 'PWM' is misleading then perhaps we should rename the definitions in the include file, and we need to confirm and documentation the frequency and duty cycle.

@Zaltora Can this PWM address your use case? If not then have you tried using the NMI timer? I could try to write an example if needed?

@nochkin
Copy link
Contributor

nochkin commented Apr 15, 2018

I'm not 100% positive what you are referring to, but I believe this is Espressif's implementation of their software PWM. The most noticable issue is that it does not work well on 100% duty.
Hardware PWM is available in ESP32 though.

@Zaltora
Copy link
Contributor Author

Zaltora commented Apr 15, 2018

i had begin to write a HW PWM driver with same API that SOFT PWM driver.
If 100% duty don't work well, it is doesn't matter. like soft pwm, the pin will be set as output at level high.
After looking register definition, i found that the correct setting for PWM is :
GPIO.PWM = GPIO_PWM_ENABLE | (prescale << 8) | duty;

I can't confirm this:

    // Freq = (80,000,000/prescale) * (target / 256) HZ           (0   < target < 128)
    // Freq = (80,000,000/prescale) * ((256 - target) / 256)  HZ  (128 < target < 256)

I don't no how set the variable "target". We got just a prescale in register definition.
After test, i can change duty from 0(0%) to 127(100%) for my motor. I think the problem is the frequency. It is too high. With a prescale of 0, my motor can just be on or off.

@ourairquality : I can't use this HW PWM for my app. I need more precision on duty. I didn't test NMI yet, i don't no what i need to change. My first thought was to use sdk_wDev_MacTimSetFunc and call the interupt handler. i don't no if i need to disable thing related to Timer1 or it is just a way to tell the system that this function will be masked ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants