Creating a custom serial driver w/o modifying ASF4 files

Go To Last Post
12 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This may be a fool's errand, but I'd like to create a custom serial driver (more on that in a moment) and I'd prefer not to monkey patch any of the ASF4 / START source files.   However, run-time modification is permissible.

 

My application requires byte-at-a-time asynch processing, so I need to install custom interrupt handlers on SERCOM3 (for a SAMD21).  But I haven't found a way to get control of the interrupt handlers without patching the START-generated source files, which I want to avoid.  Things that DON'T work:

  • If I include the HAL:Driver:USART_Async driver, it installs SERCOM3_Handler in the exception_table and gives me useful hal and hpl files to work with.  But I can't define my own SERCOM3_Handler because that results in multiple definition of `SERCOM3_Handler`.  And calling exception_table.pfnSERCOM3_Handler = (void *)MyHandler; results in an error (as expected) because exception_table is declared `const`.
  • If I don't include a USART module at all in START, none of the hal and hpl files get added to the project.  I don't mind copying and pasting SOME code, but manually installing all the required files defeats the purpose of working with START rather than fighting it.
  • If I include the HAL:Driver:USART_Sync driver, I get *most* of the hal and hpl files, but again, I cannot install an interrupt handler in the exception_table because it's read-only.

 

(Nerdy details for those who have looked at the code: It *almost* works to replace the tx_byte_sent, tx_done_cb, rx_done_cb and error_cb callback functions in hpl_sercom.c, except for one thing: the top-level interrupt function _sercom_usart_interrupt_handler() reads the USART data register, which has the effect of clearing the RXC bit.  I need to RXC to stay set.)

 

One way to accomplish what I need is to install my own callbacks at runtime.  The rx_done_cb could cache the RX data and the RXC bit to work around the fact that _sercom_usart_interrupt_handler() has already read the data register and cleared the RXC bit.

 

But what approaches have others taken when tackling this sort of problem?

 

This topic has a solution.

- rdp

 

Last Edited: Wed. Jul 29, 2020 - 01:15 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

fearless_fool wrote:
for a SAMD21

So why are you posting in the AVR section?

 

fearless_fool wrote:
My application requires byte-at-a-time asynch processing, so I need (sic?) to install custom interrupt handlers on SERCOM3

Irrespective of what particular microcontroller you use, I'm not sure that follows - you need to explain / justify that.

 

What's wrong with the standard Ring Buffer approach ?

 

 

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You have to at least modify the demo program to be able to use the handlers.

Will need some chasing links and redirects, but there is a point were all the handlers are defined/prototyped as "weak" 

these are the ones you can takeover by making your on redefinition.

 

I do not have the code at hand else I could have pointed you to it.

But if you take your time and just keep on tracing back you should be able to get to that level and then see how the definition is done and take over that.

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

meslomp wrote:
there is a point were all the handlers are defined/prototyped as "weak" 

these are the ones you can takeover by making your own redefinition.

This part is specific to SAM - not relevant to AVR.

 

See  https://community.atmel.com/forum/interrupt-handler-atmel-studio-7-samd-without-asf  for details 

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

So why are you posting in the AVR section?

Insufficient caffeine. 

 

Thanks for pointing that out -- I'll repost.

 

- rdp

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

No need to repost - an Admin has moved it.

 

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

What's wrong with the standard Ring Buffer approach ?

Imagine a case where the user code needs to be notified on each received character. 

 

As written, ASF4's asynch interface doesn't notify you until N characters have been received, where N is established in the read() call.  Of course, you can specify N=1, but that's a hella lotta overhead for byte-at-a-time notifications.

 

- rdp

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

No need to repost - an Admin has moved it.

 

Bless the admins.

- rdp

 

Last Edited: Wed. Jul 29, 2020 - 11:00 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

there is a point were all the handlers are defined/prototyped as "weak" 

these are the ones you can takeover by making your on redefinition.

Yes, but read my original post.  I tried that:

 

If I include the async driver, I cannot take over SERCOM3_Handler because the ASF4 code has defined it.

 

If I omit the async driver, none of the SERCOM code is generated.  And what's worse, the exceptions_table entry for SERCOM3 will be set to "Dummy_Handler".  I could take over that weak handler, but -- as best I understand -- I'd end up receiving events from all other modules as well. 

 

- rdp

 

This reply has been marked as the solution. 
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

fearless_fool wrote:
I could take over that weak handler, but -- as best I understand -- I'd end up receiving events from all other modules as well. 

Surely,  SERCOM3_Handler only handles SERCOM3 ?

 

EDIT

 

void SERCOM0_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
void SERCOM1_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
void SERCOM2_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
void SERCOM3_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
#ifdef ID_SERCOM4
void SERCOM4_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
#endif
#ifdef ID_SERCOM5
void SERCOM5_Handler         ( void ) __attribute__ ((weak, alias("Dummy_Handler")));
#endif

Yes - one handler per SERCOM

 

Again, see  https://community.atmel.com/forum/interrupt-handler-atmel-studio-7-samd-without-asf for how to set up your own handler

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...
Last Edited: Wed. Jul 29, 2020 - 11:28 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I understand now: I should not shy away from modifying startup_samd21.c -- no different than (say) modifying main.c.  That solves pretty much everything.

 

What's interesting is that when you as START to view the generated code, the Device_Startup directory doesn't appear.  I suppose that's because it's provided by a different mechanism.

 

Thanks much. 

 

- rdp

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

No!

 

You don't modify the startup file!

 

The startup provides weak defaults - so that you can override them without having to change the startup!

Top Tips:

  1. How to properly post source code - see: https://www.avrfreaks.net/comment... - also how to properly include images/pictures
  2. "Garbage" characters on a serial terminal are (almost?) invariably due to wrong baud rate - see: https://learn.sparkfun.com/tutorials/serial-communication
  3. Wrong baud rate is usually due to not running at the speed you thought; check by blinking a LED to see if you get the speed you expected
  4. Difference between a crystal, and a crystal oscillatorhttps://www.avrfreaks.net/comment...
  5. When your question is resolved, mark the solution: https://www.avrfreaks.net/comment...
  6. Beginner's "Getting Started" tips: https://www.avrfreaks.net/comment...