Reply by Les Cargill June 8, 20162016-06-08
Dave Nadler wrote:
> On Wednesday, June 8, 2016 at 7:28:47 AM UTC-4, Les Cargill wrote: >> pozz wrote: >>> Is there a possibility to share the USB Host stack between bootloader >>> and application in some way? >> >> Tactically, this isn't that great of an idea. You sort of want the >> bootloader to be ... firewalled from the application. Applications >> updates fail. USB drives are unreliable. >> >> If the applications update fails and leaves the device bricked.... > > If the USB code is within the bootloader, the application cannot > interfere with bootloading nor brick the device. > > USB drivers ARE unreliable, weekly we have to tell a customer to > reformat a USB drive and try again (after FAT corruption on > pulling stick out prior writes completed). > > Tactically it is an OK idea IFF you're willing to live with inability > to update the USB stack. Two weeks ago I had to update the USB stack > in a product, and that would not have been possible if the USB stack > was in the bootloader... > > Hope that clarifies! > Best Regards, Dave >
1) Add an MicroSD card. 2) Use OTB. IMO. -- Les Cargill
Reply by Don Y June 8, 20162016-06-08
On 6/8/2016 6:24 AM, Dave Nadler wrote:
> On Wednesday, June 8, 2016 at 7:28:47 AM UTC-4, Les Cargill wrote: >> pozz wrote: >>> Is there a possibility to share the USB Host stack between bootloader >>> and application in some way? >> >> Tactically, this isn't that great of an idea. You sort of want the >> bootloader to be ... firewalled from the application. Applications >> updates fail. USB drives are unreliable. >> >> If the applications update fails and leaves the device bricked.... > > If the USB code is within the bootloader, the application cannot > interfere with bootloading nor brick the device. > > USB drivers ARE unreliable, weekly we have to tell a customer to > reformat a USB drive and try again (after FAT corruption on > pulling stick out prior writes completed). > > Tactically it is an OK idea IFF you're willing to live with inability > to update the USB stack. Two weeks ago I had to update the USB stack > in a product, and that would not have been possible if the USB stack > was in the bootloader...
Nothing prevents the "application" from using a different instance of the USB stack (though the OP doesn't ant to incur the resource penalty this would require). And, you can also arrange (at some potential peril) to allow the bootloader to be updated in the field -- with the assistance of an application (or portion thereof) designed to do exactly this. [I use this approach to update the network stack in my bootloader. But, there are no "fallible humans" involved in the process!]
Reply by Dave Nadler June 8, 20162016-06-08
On Wednesday, June 8, 2016 at 10:20:42 AM UTC-4, Jack wrote:
> Il giorno mercoledì 8 giugno 2016 15:24:31 UTC+2, Dave Nadler ha scritto: > > > USB drivers ARE unreliable, weekly we have to tell a customer to > > reformat a USB drive and try again (after FAT corruption on > > pulling stick out prior writes completed). > > it's not the USB the problem here, it's how the data in the FAT FS are handled. > You would have the same problem with a SD Card. > > Bye Jack
Yep, but to the user its a "USB stick problem" Too bad these buggers don't all use a journaling file system, but then the file system code might not fit into small embedded devices...
Reply by Jack June 8, 20162016-06-08
Il giorno mercoledì 8 giugno 2016 15:24:31 UTC+2, Dave Nadler ha scritto:

> USB drivers ARE unreliable, weekly we have to tell a customer to > reformat a USB drive and try again (after FAT corruption on > pulling stick out prior writes completed).
it's not the USB the problem here, it's how the data in the FAT FS are handled. You would have the same problem with a SD Card. Bye Jack
Reply by Dave Nadler June 8, 20162016-06-08
On Wednesday, June 8, 2016 at 7:28:47 AM UTC-4, Les Cargill wrote:
> pozz wrote: > > Is there a possibility to share the USB Host stack between bootloader > > and application in some way? > > Tactically, this isn't that great of an idea. You sort of want the > bootloader to be ... firewalled from the application. Applications > updates fail. USB drives are unreliable. > > If the applications update fails and leaves the device bricked....
If the USB code is within the bootloader, the application cannot interfere with bootloading nor brick the device. USB drivers ARE unreliable, weekly we have to tell a customer to reformat a USB drive and try again (after FAT corruption on pulling stick out prior writes completed). Tactically it is an OK idea IFF you're willing to live with inability to update the USB stack. Two weeks ago I had to update the USB stack in a product, and that would not have been possible if the USB stack was in the bootloader... Hope that clarifies! Best Regards, Dave
Reply by Don Y June 8, 20162016-06-08
On 6/8/2016 4:31 AM, Les Cargill wrote:
> pozz wrote: >> I will use one MCU with integrated USB OTG peripheral for two purposes: >> >> - bootloader for firmware upgrade from USB pendrive >> - USB connection to an Android smartphone during application >> >> As you know, USB Host stack is a complex piece of code that has a high >> Flash size. >> In my scenario, I need two different USB Host: one for bootloader and >> one for application. >> >> Is there a possibility to share the USB Host stack between bootloader >> and application in some way? > > Tactically, this isn't that great of an idea. You sort of want the > bootloader to be ... firewalled from the application. Applications > updates fail. USB drives are unreliable. > > If the applications update fails and leaves the device bricked....
There's no reason that the stack can't be in a protected "boot sector" of the flash -- and still accessed by the application (whether that application is loaded into an "unprotected" portion of the flash *or* executes out of RAM).
Reply by Les Cargill June 8, 20162016-06-08
pozz wrote:
> I will use one MCU with integrated USB OTG peripheral for two purposes: > > - bootloader for firmware upgrade from USB pendrive > - USB connection to an Android smartphone during application > > As you know, USB Host stack is a complex piece of code that has a high > Flash size. > In my scenario, I need two different USB Host: one for bootloader and > one for application. > > Is there a possibility to share the USB Host stack between bootloader > and application in some way? >
Tactically, this isn't that great of an idea. You sort of want the bootloader to be ... firewalled from the application. Applications updates fail. USB drives are unreliable. If the applications update fails and leaves the device bricked....
> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain.
-- Les Cargill
Reply by Don Y June 7, 20162016-06-07
On 6/7/2016 1:23 PM, Tim Wescott wrote:
> On Tue, 07 Jun 2016 12:02:47 -0700, Don Y wrote: > >> On 6/7/2016 11:21 AM, Tim Wescott wrote: >>> On Tue, 07 Jun 2016 06:43:04 -0700, Don Y wrote: >>> >>>> On 6/7/2016 3:49 AM, pozz wrote: >>>>> I will use one MCU with integrated USB OTG peripheral for two >>>>> purposes: >>>>> >>>>> - bootloader for firmware upgrade from USB pendrive - USB connection >>>>> to an Android smartphone during application >>>>> >>>>> As you know, USB Host stack is a complex piece of code that has a >>>>> high Flash size. >>>>> In my scenario, I need two different USB Host: one for bootloader and >>>>> one for application. >>>>> >>>>> Is there a possibility to share the USB Host stack between bootloader >>>>> and application in some way? >>>>> >>>>> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain. >>>> >>>> That depends on the capabilities that you require in each "instance" >>>> of the stack. Also, on the environment in which you expect each >>>> instance to operate! It's usually easier to write a piece of code to >>>> rely on MORE facilities (than less). >>>> >>>> Typically, boot loaders want to be as "slim" as possible. This helps >>>> ensure they are "correct" (no latent bugs that will cause your boot >>>> loader to misperform at a later date -- leaving you "stuck"). It also >>>> tends to make it easier to "step away" from the boot loader after the >>>> image has been pulled in -- less scaffolding to tear down as you >>>> transition to "application mode" (e.g., did you remember to disable >>>> any services upon which the loader relied that might conflict with >>>> services in the application's run-time?) >>> >>> If he needs to read USB drives from the bootloader, he's already >>> crossed the Rubicon as far as code complexity goes. Beyond that he >>> just needs to control risks. >> >> I disagree. I can see lots of opportunities to trim a USB stack that is >> intended to: >> - have COMPLETE control of the hardware - only talk to one endpoint at a >> time ("ever") >> - has no need to poll - only support a single ("simple") device class - >> not support sub-devices - operate at a (reduced) data rate that *it* >> controls - only support bulk transfers (infinite retries) >> - etc. >> >> The OP can potentially pick a single "device" and refuse to "understand" >> other devices -- even those in the same device class! >> >> Look at the alternative of a full-fledged stack that has to potentially >> be able to talk to any device class, multiple endpoints per device, >> multiple devices concurrently, support isochronous transfers, etc. all >> WHILE ALSO SUPPORTING THE CONCURRENT PRESENCE OF COMPETING >> "APPLICATIONS". >> >> It's comparable to talking to a UART in *simplex* mode from userland >> without the benefit of a driver: just spinning on the status register >> waiting for a character to arrive, retrieving the character, then >> spinning again -- until the 289 characters that you EXPECT to receive >> have arrived (in that buffer[289]), THEN checking to see if they make >> sense before using them. >> >> Contrast that with pulling in characters while "doing something else", >> parsing the message on the fly and being able to tolerate variations in >> the data stream (without "Please reboot") >> >>> I might implement a bootloader for the bootloader, for when things >>> REALLY mess up. > > I suspect that unless you're an absolute freaking USB expert that you'd > end up with fragile code. The first thing I would expect is code that > only works with certain USB sticks. Not being a freaking USB expert I > wouldn't know what else may happen -- but I'd be wary of Something Bad > happening. > > But, yes, if you pulled it off it may well be smaller.
My point isn't that you end up making it smaller. Rather, that you write the *real* USB stack but with an eye towards how you could implement it to run in different "environments". (given the desire to have a single instance handle both applications) Taking a "bootloader stack" and trying to use it as a "runtime stack" is usually impractical as your hands have been tied by the assumptions you made when writing it (see above). Similarly, taking a "runtime stack" and trying to use it as a "bootloader stack" leaves you just as disadvantaged. You have to design a stack that *can* run in both environments by carefully virtualizing the services on which it relies (so the bootloader versions can essentially be stubbed as virtual no-ops without a loss of functionality). E.g., parameterize the implementation to that you can impose constraints on it FROM THE OUTSIDE without having to recode its inner workings. My gesture recognizer will run in different "OS" containers and with different capabilities -- without changing any of the code but, instead, by stubbing the services on which it relies. I.e., instead of issuing an SQL query sent over an encrypted wireless network link to fetch templates from a real RDBMS, in the "pared down" environment those queries return carefully chosen ("design time") templates "out of ROM". The code doesn't need to know how complex the execution environment happens to be; it just sees it through the same viewport. No need for me to provision RAM from which a "real" gesture recognizer's code can execute (while the flash-based recognizer code just sits there doing nothing)
Reply by Tim Wescott June 7, 20162016-06-07
On Tue, 07 Jun 2016 22:57:38 +0200, pozz wrote:

> Il 07/06/2016 20:25, Tim Wescott ha scritto: >> On Tue, 07 Jun 2016 21:15:13 +1000, Clifford Heath wrote: >> >>> On 07/06/16 20:49, pozz wrote: >>>> I will use one MCU with integrated USB OTG peripheral for two >>>> purposes: >>>> >>>> - bootloader for firmware upgrade from USB pendrive - USB connection >>>> to an Android smartphone during application >>>> >>>> As you know, USB Host stack is a complex piece of code that has a >>>> high Flash size. >>>> In my scenario, I need two different USB Host: one for bootloader and >>>> one for application. >>>> >>>> Is there a possibility to share the USB Host stack between bootloader >>>> and application in some way? >>>> >>>> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain. >>> >>> Overlay linkers used to do this kind of thing, but really the right >>> answer now is to create a jump table or a C++ object that implements a >>> virtual interface, and expose it from the bootloader. Then in the >>> application code all you need is a single pointer. Essentially it >>> becomes your USB Host BIOS. >>> >>> You just need to ensure that any and all library code that gets >>> dragged in is appropriate to both environments, for example, any >>> memory that gets allocated in the bootloader gets freed there too, not >>> by a free() in the app code. >>> >>> Clifford Heath. >> >> What everyone has said so far, plus: >> >> I'm going to go ahead and call it a BIOS here, because that's basically >> what you're doing. >> >> Whatever you do you need to make sure to make the API between BIOS and >> application code as consistent as possible. So -- a jump table, or a >> single address that gets called with parameters, or possibly a >> guaranteed- >> unused interrupt that you hijack to branch to the BIOS. >> >> What you absolutely positively don't want to do is to just link the >> boot code, then link the application code against the boot code's >> 'native' addresses -- that will pretty much guarantee that each >> application version will be firmly tied to a boot code version. You >> want to have a system that maintains interoperability between as wide a >> range of boot and applications versions. The less interoperability >> there is, the bigger the configuration nightmare gets. >> > Il 07/06/2016 20:25, Tim Wescott ha scritto: > > On Tue, 07 Jun 2016 21:15:13 +1000, Clifford Heath wrote: > > > >> On 07/06/16 20:49, pozz wrote: > >>> I will use one MCU with integrated USB OTG peripheral for two > >>> purposes: > >>> > >>> - bootloader for firmware upgrade from USB pendrive - USB > >>> connection to an Android smartphone during application > >>> > >>> As you know, USB Host stack is a complex piece of code that has a > >>> high Flash size. > >>> In my scenario, I need two different USB Host: one for bootloader > >>> and one for application. > >>> > >>> Is there a possibility to share the USB Host stack between > >>> bootloader and application in some way? > >>> > >>> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain. > >> > >> Overlay linkers used to do this kind of thing, but really the right > >> answer now is to create a jump table or a C++ object that implements > >> a virtual interface, and expose it from the bootloader. Then in the > >> application code all you need is a single pointer. Essentially it > >> becomes your USB Host BIOS. > >> > >> You just need to ensure that any and all library code that gets > >> dragged in is appropriate to both environments, for example, any > >> memory that gets allocated in the bootloader gets freed there too, > >> not by a free() in the app code. > >> > >> Clifford Heath. > > > > What everyone has said so far, plus: > > > > I'm going to go ahead and call it a BIOS here, because that's > > basically what you're doing. > > > > Whatever you do you need to make sure to make the API between BIOS > > and application code as consistent as possible. So -- a jump table, > > or a single address that gets called with parameters, or possibly a > guaranteed- > > unused interrupt that you hijack to branch to the BIOS. > > > > What you absolutely positively don't want to do is to just link the > > boot code, then link the application code against the boot code's > > 'native' addresses -- that will pretty much guarantee that each > > application version will be firmly tied to a boot code version. You > > want to have a system that maintains interoperability between as wide > > a range of boot and applications versions. The less interoperability > > there is, the bigger the configuration nightmare gets. > > > > > Thank for your suggestions and advices. I understand perfectly what you > are saying, but it's very difficult for me to really implement them in C > and linker script.
Then either your tools or you need upgrading. Sorry if that's too blunt -- but there's no softer way to put it. On the bright side, the self-upgrade should be fun.
> It should be nice if there is some example, even about a totally > different application, on the net that shows how to achieve what I'd > like to do: sharing a set of functions (USB Host stack) between > bootloader and application.
Locate a function or a jump vector at some fixed point in the boot code, in a way that it will never, ever change. Then use an ioctl-like call to that one spot from the app code. Make sure that the boot code has adequate RAM. This WILL require dinking with the linker script, or with the project parameters if you use an IDE -- and if you use an IDE, you're almost guaranteed that the protection will be broken with some future upgrade.
> Nowadays silicon manufacturers (NXP, Freescale, Microchip, Atmel, ...) > publish a lot of example code for their evaluation boards, maybe one of > those example shows what I'm trying to do.
In general the example code that I see is written by applications engineers who are both fresh out of school and borderline incompetent. They serve to demonstrate how bits of hardware work, but they usually do so in the stupidest possible manner, which is usually also a manner that makes it impossible to incorporate them into reasonably-written code. Not that I'm, like, biased or anything, but I would not expect the authors of the crap that I see to even be able to do what's necessary, much less express it in an understandable manner. -- Tim Wescott Wescott Design Services http://www.wescottdesign.com I'm looking for work -- see my website!
Reply by pozz June 7, 20162016-06-07
Il 07/06/2016 20:25, Tim Wescott ha scritto:
> On Tue, 07 Jun 2016 21:15:13 +1000, Clifford Heath wrote: > >> On 07/06/16 20:49, pozz wrote: >>> I will use one MCU with integrated USB OTG peripheral for two purposes: >>> >>> - bootloader for firmware upgrade from USB pendrive - USB connection to >>> an Android smartphone during application >>> >>> As you know, USB Host stack is a complex piece of code that has a high >>> Flash size. >>> In my scenario, I need two different USB Host: one for bootloader and >>> one for application. >>> >>> Is there a possibility to share the USB Host stack between bootloader >>> and application in some way? >>> >>> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain. >> >> Overlay linkers used to do this kind of thing, but really the right >> answer now is to create a jump table or a C++ object that implements a >> virtual interface, and expose it from the bootloader. Then in the >> application code all you need is a single pointer. Essentially it >> becomes your USB Host BIOS. >> >> You just need to ensure that any and all library code that gets dragged >> in is appropriate to both environments, for example, any memory that >> gets allocated in the bootloader gets freed there too, not by a free() >> in the app code. >> >> Clifford Heath. > > What everyone has said so far, plus: > > I'm going to go ahead and call it a BIOS here, because that's basically > what you're doing. > > Whatever you do you need to make sure to make the API between BIOS and > application code as consistent as possible. So -- a jump table, or a > single address that gets called with parameters, or possibly a guaranteed- > unused interrupt that you hijack to branch to the BIOS. > > What you absolutely positively don't want to do is to just link the boot > code, then link the application code against the boot code's 'native' > addresses -- that will pretty much guarantee that each application > version will be firmly tied to a boot code version. You want to have a > system that maintains interoperability between as wide a range of boot > and applications versions. The less interoperability there is, the > bigger the configuration nightmare gets. >
Il 07/06/2016 20:25, Tim Wescott ha scritto: > On Tue, 07 Jun 2016 21:15:13 +1000, Clifford Heath wrote: > >> On 07/06/16 20:49, pozz wrote: >>> I will use one MCU with integrated USB OTG peripheral for two purposes: >>> >>> - bootloader for firmware upgrade from USB pendrive - USB connection to >>> an Android smartphone during application >>> >>> As you know, USB Host stack is a complex piece of code that has a high >>> Flash size. >>> In my scenario, I need two different USB Host: one for bootloader and >>> one for application. >>> >>> Is there a possibility to share the USB Host stack between bootloader >>> and application in some way? >>> >>> Most probably, I'll use a Cortex-Mx MCU with gcc toolchain. >> >> Overlay linkers used to do this kind of thing, but really the right >> answer now is to create a jump table or a C++ object that implements a >> virtual interface, and expose it from the bootloader. Then in the >> application code all you need is a single pointer. Essentially it >> becomes your USB Host BIOS. >> >> You just need to ensure that any and all library code that gets dragged >> in is appropriate to both environments, for example, any memory that >> gets allocated in the bootloader gets freed there too, not by a free() >> in the app code. >> >> Clifford Heath. > > What everyone has said so far, plus: > > I'm going to go ahead and call it a BIOS here, because that's basically > what you're doing. > > Whatever you do you need to make sure to make the API between BIOS and > application code as consistent as possible. So -- a jump table, or a > single address that gets called with parameters, or possibly a guaranteed- > unused interrupt that you hijack to branch to the BIOS. > > What you absolutely positively don't want to do is to just link the boot > code, then link the application code against the boot code's 'native' > addresses -- that will pretty much guarantee that each application > version will be firmly tied to a boot code version. You want to have a > system that maintains interoperability between as wide a range of boot > and applications versions. The less interoperability there is, the > bigger the configuration nightmare gets. > Thank for your suggestions and advices. I understand perfectly what you are saying, but it's very difficult for me to really implement them in C and linker script. It should be nice if there is some example, even about a totally different application, on the net that shows how to achieve what I'd like to do: sharing a set of functions (USB Host stack) between bootloader and application. Nowadays silicon manufacturers (NXP, Freescale, Microchip, Atmel, ...) publish a lot of example code for their evaluation boards, maybe one of those example shows what I'm trying to do.