New Ethernet library with improved TCP/IP Stack
Re: New Ethernet library with improved TCP/IP Stack
Things are going along nicely, but I'm still about to have some hair loss.
I've finished my "generic" webserver and have integrated some great features for a small server. I was having the problem of missing packets from time to time on the 8Mhz AVR so I went with the STM32F407VG at 150Mhz to take care of those pesky missing packets.
Well you guessed it. Performance is a little better but still the same behavior. Missing packets.
I've polled the do_packet as fast as the MCU will go. I've optimized until my eyes bleed. Still. Missing packets.
Any advice you have for me? Anything I can check?
I've measured how many uSecs takes from the time it calls do_packet till it exits and found the time to be under 1 ms.
42 uSec for getting the full 512 byte request
51 uSec to parse the request
2 uSec to search and find the file
90 uSec to generate and send the header
585 uSec to fill the Ethernet buffer
Exit for another round of filling the buffer until end.
I've reduced the buffer size to 512 bytes and found 285 uSec for filling the buffer but still no joy. I have the strangest feeling that it is somewhere in the library and how it checks for packets?
When I have the ENC28j60 being executed from an ISR, the performance was AWESOME, but worried about a re-entrant or taking up too long inside the ISR.
I need some advice.
I've finished my "generic" webserver and have integrated some great features for a small server. I was having the problem of missing packets from time to time on the 8Mhz AVR so I went with the STM32F407VG at 150Mhz to take care of those pesky missing packets.
Well you guessed it. Performance is a little better but still the same behavior. Missing packets.
I've polled the do_packet as fast as the MCU will go. I've optimized until my eyes bleed. Still. Missing packets.
Any advice you have for me? Anything I can check?
I've measured how many uSecs takes from the time it calls do_packet till it exits and found the time to be under 1 ms.
42 uSec for getting the full 512 byte request
51 uSec to parse the request
2 uSec to search and find the file
90 uSec to generate and send the header
585 uSec to fill the Ethernet buffer
Exit for another round of filling the buffer until end.
I've reduced the buffer size to 512 bytes and found 285 uSec for filling the buffer but still no joy. I have the strangest feeling that it is somewhere in the library and how it checks for packets?
When I have the ENC28j60 being executed from an ISR, the performance was AWESOME, but worried about a re-entrant or taking up too long inside the ISR.
I need some advice.
- Attachments
-
- Wireshard
- Wireshark.jpg (202.3 KiB) Viewed 15320 times
-
- Yep, demo from MikroC
- WebLoad.jpg (50.25 KiB) Viewed 15320 times
Re: New Ethernet library with improved TCP/IP Stack
I disable the INT in the ISR and run do_packet. At the conclusion I re-enable the INT.
Behavior: I do not miss any packets, but page load speed is pathetic. 2-3 minutes per page.
Here is something from the datasheet:
Behavior: I do not miss any packets, but page load speed is pathetic. 2-3 minutes per page.
Here is something from the datasheet:
Since I cannot see what do_packet is doing. Does it scan from the last recorded position?Interrupts are not queued and if the interrupt event occurs before the driver has responded
to it, no additional interrupts are generated. For example, the Receive Interrupt bit
(ETH_DMASR register [6]) indicates that one or more frames were transferred to the
STM32F4xx buffer. The driver must scan all descriptors, from the last recorded position to
the first one owned by the DMA.
Last edited by borris on 27 Jun 2013 23:49, edited 1 time in total.
Re: New Ethernet library with improved TCP/IP Stack
I've got some poor performance in the library. Logically, this should be great performance. Here's what is happening code wise:
First thing is I clear the FIFO buffers on the MAC to clear out any garbage left from last reset
Then enable some DMA interrupts:
Now, I don't call the do_packet from the ISR. I have a flag that represents a packet is present on the FIFO buffer:
Finally in the main loop I check for the packet flag. Making sure to clear the flag on entrance. That way, if there is another packet on exit from do_packet, then it will continue to process packets:
Seems to me that the issues that come from a single threaded application like this is the timing. Behavior is no missed packets, but load speed is 40x slower.
I'm still looking for advice on how to optimize the ethernet side of things. My first time using ethernet at this level, so any experts out there with some clues on how to increase performance I'm excited to hear from you.
First thing is I clear the FIFO buffers on the MAC to clear out any garbage left from last reset
Code: Select all
Ethernet_DMA_DMAOMR |= (1 << FTF); //Flush transmit fifo
Code: Select all
Ethernet_DMA_DMAIER |= (1 << NISE) | (1 << RIE); //Normal interrupts
NVIC_IntEnable(IVT_INT_ETH);
Code: Select all
// Ethernet IRQ
void packet_ISR() iv packetVector ics ICS_AUTO {
if(Ethernet_DMA_DMASR & (1 << NIS)) {
if(Ethernet_DMA_DMASR & (1 << RS)){
packet = 1;
}
Ethernet_DMA_DMASR |= (1 << NIS);
}
}
Code: Select all
while(packet){
packet = 0;
Net_Ethernet_doPacket();
}
I'm still looking for advice on how to optimize the ethernet side of things. My first time using ethernet at this level, so any experts out there with some clues on how to increase performance I'm excited to hear from you.
Re: New Ethernet library with improved TCP/IP Stack
I'm just full of questions. Sorry.
Does the library do any DMA transfers from the buffers to the MAC? I did notice some buffers:
I've been changing all the buffers int eh __Lib_NetEthInternal_STM.Defs.c to the ccm memory specifier and found no real difference in transfer speed. Which is good and bad. Meaning, since we can not do DMA transfers to or from ccm memory regions, I'm guessing the answer to my question is no.
I know you guys don't like to give out your source code and all that, but could you at least point me in a direction where I might be able to utilize DMA transfers? OR if I wanted to change the buffer sizes on the above variables, how would I do that?
I'm getting closer on performance though, check these stats:
Does the library do any DMA transfers from the buffers to the MAC? I did notice some buffers:
I've been changing all the buffers int eh __Lib_NetEthInternal_STM.Defs.c to the ccm memory specifier and found no real difference in transfer speed. Which is good and bad. Meaning, since we can not do DMA transfers to or from ccm memory regions, I'm guessing the answer to my question is no.
I know you guys don't like to give out your source code and all that, but could you at least point me in a direction where I might be able to utilize DMA transfers? OR if I wanted to change the buffer sizes on the above variables, how would I do that?
I'm getting closer on performance though, check these stats:
Re: New Ethernet library with improved TCP/IP Stack
I've got the same problem with the library either on AVR or ARM.
Once the system is up, it is very reliable for a day or so. Then, for some unknown reason the webserver accepts no new requests and forces me to reset the mcu.
I enabled the "abnormal interrupts" on the STM32F4 and found that when the system goes unresponsive it is generating a RBUS error.
"Receive buffer unavailable" found in the DMA_DMASR register.
RBUS:Receive buffer unavailable status
This bit indicates that the next descriptor in the receive list is owned by the host and cannot
be acquired by the DMA. Receive process is suspended. To resume processing receive
descriptors, the host should change the ownership of the descriptor and issue a Receive Poll
Demand command. If no Receive Poll Demand is issued, receive process resumes when the
next recognized incoming frame is received. ETH_DMASR [7] is set only when the previous
receive descriptor was owned by the DMA
Any clues as to why this is happening?
Once the system is up, it is very reliable for a day or so. Then, for some unknown reason the webserver accepts no new requests and forces me to reset the mcu.
I enabled the "abnormal interrupts" on the STM32F4 and found that when the system goes unresponsive it is generating a RBUS error.
"Receive buffer unavailable" found in the DMA_DMASR register.
RBUS:Receive buffer unavailable status
This bit indicates that the next descriptor in the receive list is owned by the host and cannot
be acquired by the DMA. Receive process is suspended. To resume processing receive
descriptors, the host should change the ownership of the descriptor and issue a Receive Poll
Demand command. If no Receive Poll Demand is issued, receive process resumes when the
next recognized incoming frame is received. ETH_DMASR [7] is set only when the previous
receive descriptor was owned by the DMA
Any clues as to why this is happening?
- darko.jola
- Posts: 51
- Joined: 03 Aug 2011 16:18
Re: New Ethernet library with improved TCP/IP Stack
Hi,
currently you can not access to DMA buffers in library. It is library task to manage DMA descriptors and transfers, so it is not recommended to do this in interrupt routine.
About missing packets, I can see from your picture that there is a some strange value of SEQ of last packet (SEQ = 25, it should be 26). That is probably reason for later multiple packets from remote side. Also, RBUS error is illegal case. I will try to reproduce and solve it. Thanks for these notes.
Best regards
Darko
currently you can not access to DMA buffers in library. It is library task to manage DMA descriptors and transfers, so it is not recommended to do this in interrupt routine.
About missing packets, I can see from your picture that there is a some strange value of SEQ of last packet (SEQ = 25, it should be 26). That is probably reason for later multiple packets from remote side. Also, RBUS error is illegal case. I will try to reproduce and solve it. Thanks for these notes.
Best regards
Darko
Re: New Ethernet library with improved TCP/IP Stack
Thank you for checking these issues out. Seems like there is little interest in this part of the forum, or people don't have any issues with the Ethernet library. Lucky me.
I am having terrible issues with the reliability of the DNS_resolve function. I'm not sure if it is my network, or the library. I have the webserver part of the project on libstock http://www.libstock.com/projects/view/7 ... l-featured. Seems to be very unpredictable on how many times I need to call the resolve before it actually works.
I've watched the calls and the destination is 0.0.0.0 when it fails, then, for no reason I get the correct DNS address. Any clues or others that might have the same issue?
I am having terrible issues with the reliability of the DNS_resolve function. I'm not sure if it is my network, or the library. I have the webserver part of the project on libstock http://www.libstock.com/projects/view/7 ... l-featured. Seems to be very unpredictable on how many times I need to call the resolve before it actually works.
I've watched the calls and the destination is 0.0.0.0 when it fails, then, for no reason I get the correct DNS address. Any clues or others that might have the same issue?
- darko.jola
- Posts: 51
- Joined: 03 Aug 2011 16:18
Re: New Ethernet library with improved TCP/IP Stack
I just tried some simple code which test dnsResolve:
Addresses mikroeIP and libstockIP I resolved with some online dns (like http://www.dnsqueries.com/en/dns_lookup.php).
I tried this code several time, and I got one unsuccessful resolve after average 200 iterations (watch counter variable in ICD).
If I understood you, you get this problem more often?
Best regards
Darko
Code: Select all
GPIO_Digital_Output(&GPIOD_BASE, _GPIO_PINMASK_ALL);
GPIOD_ODR = 0;
while(1) {
counter++;
memcpy(resolvedAddr, Net_Ethernet_Intern_dnsResolve("www.mikroe.com", 5), 4);
if( memcmp(resolvedAddr, mikroeIP, 4)!=0 ) {
GPIOD_ODR = 0xff;
while(1);
}
memcpy(resolvedAddr, Net_Ethernet_Intern_dnsResolve("www.libstock.com", 5), 4);
if( memcmp(resolvedAddr, libstockIP, 4)!=0 ) {
GPIOD_ODR = 0xff;
while(1);
}
Delay_ms(1000);
}
I tried this code several time, and I got one unsuccessful resolve after average 200 iterations (watch counter variable in ICD).
If I understood you, you get this problem more often?
Best regards
Darko
Re: New Ethernet library with improved TCP/IP Stack
Wow. Maybe it's my hardware here then. I have 1 successful DNS resolve every 3-15 calls. I will try some other DNS servers and see what my results are.
Re: New Ethernet library with improved TCP/IP Stack
I've tried a variety of DNS addresses and still no luck in getting your results. I am, however using a different method than your example. Do you see any issues with the following:
Code: Select all
uint8_t* remoteIP;
if( remoteIP = Net_Ethernet_Intern_dnsResolve( ntpSrv, 5 ) )
{
uint8_t remoteIpAddr[4] = {0};
uint8_t sntpPkt[48] = {0};
memcpy( remoteIpAddr, remoteIP, 4 );
....
Net_Ethernet_Intern_sendUDP( remoteIpAddr, SNTP_PORT, SNTP_PORT, sntpPkt, 48 );
}
- darko.jola
- Posts: 51
- Joined: 03 Aug 2011 16:18
Re: New Ethernet library with improved TCP/IP Stack
I can't see any issue with your code. Can you tell me, did you try DNS resolve in some simple project (which only initialize ethernet module, and periodically call dnsResolve in some loop)? We can see from that if you hardware works.
Best regards
Darko
Best regards
Darko
Re: New Ethernet library with improved TCP/IP Stack
Absolutely. The libstock project: http://www.libstock.com/projects/view/7 ... l-featured is pretty close to only Ethernet.
What it has is: FAT32, Ethernet, timer.
Could these simple things interfere with the Ethernet functions to that level?
What it has is: FAT32, Ethernet, timer.
Could these simple things interfere with the Ethernet functions to that level?
Re: New Ethernet library with improved TCP/IP Stack
Here are the results for as basic as it gets:
I am adding a delay after the ethernet initializations and it seems to make no difference as to how long or short that is, errors always occur at the beginning.
Something like this fixes it:
, but I'd like to figure out why my first requests do not work.
I've also noticed on wireshark that NO TRAFFIC is happening during those first requests. Which leads me to believe that the issue is definitely somewhere within the library code.
However, it seems all my failed requests are always the first requests made. Once the first succeeds then there is no issue with additional requests.200 succeeded, 4 failed
I am adding a delay after the ethernet initializations and it seems to make no difference as to how long or short that is, errors always occur at the beginning.
Something like this fixes it:
Code: Select all
uint8_t tries = 5;
do
{
remoteIP = Net_Ethernet_Intern_dnsResolve( ntpSrv, 5 );
}
while( remoteIP == NULL && tries-- > 0 );
I've also noticed on wireshark that NO TRAFFIC is happening during those first requests. Which leads me to believe that the issue is definitely somewhere within the library code.
- darko.jola
- Posts: 51
- Joined: 03 Aug 2011 16:18
Re: New Ethernet library with improved TCP/IP Stack
If there is no traffic during first _dnsResolve it is most likely that ethernet module is still in initialization state, so try to increase time between _Init and _dnsResolve calls.
Best regards
Darko
Best regards
Darko
Re: New Ethernet library with improved TCP/IP Stack
That's exactly what I thought, however, even waiting 15 minutes won't change anything. Once the first attempt is successful then it works every time.
Weird weird issue. I still think it is in the library.
This is on the STM32F4 series. I've noticed a strange behavior with the Ethernet library on those MCUs. I run the exact same code on the AVR with an external 2860 chip and here is what I notice:
After a period of time not querying the webserver on the MCU the STM will appear to go to sleep and then when I request a page the first time from the STM it will timeout. I hit refresh 1 or 2 times and then it is there.
That problem does not exist on the AVR. No matter how much time passes, when I request a page, it is alot more responsive than the STM. ARM is much faster when loading, but not anywhere as responsive.
Could this give you a hint on what might be happening?
Weird weird issue. I still think it is in the library.
This is on the STM32F4 series. I've noticed a strange behavior with the Ethernet library on those MCUs. I run the exact same code on the AVR with an external 2860 chip and here is what I notice:
After a period of time not querying the webserver on the MCU the STM will appear to go to sleep and then when I request a page the first time from the STM it will timeout. I hit refresh 1 or 2 times and then it is there.
That problem does not exist on the AVR. No matter how much time passes, when I request a page, it is alot more responsive than the STM. ARM is much faster when loading, but not anywhere as responsive.
Could this give you a hint on what might be happening?