@@ -9,7 +9,8 @@ class USBDevice -- USB Device driver
99 supports native USB.
1010
1111USBDevice provides a low-level Python API for implementing USB device functions using
12- Python code.
12+ Python code. This includes both runtime device descriptor configuration and
13+ build-time customization of USB configuration.
1314
1415.. warning :: This low-level API assumes familiarity with the USB standard. There
1516 are high-level `usb driver modules in micropython-lib `_ which provide a
@@ -188,23 +189,39 @@ Methods
188189.. attribute :: USBDevice.builtin_driver
189190
190191 This attribute holds the current built-in driver configuration, and must be
191- set to one of the ``USBDevice.BUILTIN_ `` named constants defined on this object.
192+ set to one of the ``USBDevice.BUILTIN_ `` constants or a combination of them
193+ using the bitwise OR operator (``| ``).
192194
193195 By default it holds the value :data: `USBDevice.BUILTIN_NONE `.
194196
195197 Runtime USB device must be inactive when setting this field. Call the
196198 :func: `USBDevice.active ` function to deactivate before setting if necessary
197199 (and again to activate after setting).
198200
201+ **Combining Built-in Drivers: **
202+
203+ Multiple built-in USB classes can be enabled simultaneously by combining
204+ constants with the bitwise OR operator::
205+
206+ usb = machine.USBDevice()
207+ usb.active(False)
208+ # Enable both CDC and MSC
209+ usb.builtin_driver = usb.BUILTIN_CDC | usb.BUILTIN_MSC
210+ usb.active(True)
211+
212+ The combined configuration will dynamically generate appropriate USB
213+ descriptors containing only the selected classes.
214+
199215 If this value is set to any value other than :data: `USBDevice.BUILTIN_NONE ` then
200216 the following restrictions apply to the :func: `USBDevice.config ` arguments:
201217
202218 - ``desc_cfg `` should begin with the built-in USB interface descriptor data
203219 accessible via :data: `USBDevice.builtin_driver ` attribute ``desc_cfg ``.
204- Descriptors appended after the built-in configuration descriptors should use
205- interface, string and endpoint numbers starting from the max built-in values
206- defined in :data: `USBDevice.builtin_driver ` attributes ``itf_max ``, ``str_max `` and
207- ``ep_max ``.
220+ The descriptor is dynamically generated based on the combination of classes
221+ enabled. Descriptors appended after the built-in configuration descriptors
222+ should use interface, string and endpoint numbers starting from the max
223+ built-in values defined in :data: `USBDevice.builtin_driver ` attributes
224+ ``itf_max ``, ``str_max `` and ``ep_max ``.
208225
209226 - The ``bNumInterfaces `` field in the built-in configuration
210227 descriptor will also need to be updated if any new interfaces
@@ -266,39 +283,134 @@ Constants
266283---------
267284
268285.. data :: USBDevice.BUILTIN_NONE
286+
287+ Constant representing no built-in USB drivers enabled. This is the
288+ default value for :data: `USBDevice.builtin_driver `.
289+
269290.. data :: USBDevice.BUILTIN_DEFAULT
291+
292+ Constant representing the default combination of built-in USB drivers
293+ for this firmware build. The exact combination depends on compile-time
294+ configuration options.
295+
270296.. data :: USBDevice.BUILTIN_CDC
297+
298+ Constant representing the built-in USB CDC (serial port) driver.
299+ Can be combined with other ``BUILTIN_ `` constants using the bitwise
300+ OR operator (``| ``).
301+
271302.. data :: USBDevice.BUILTIN_MSC
303+
304+ Constant representing the built-in USB MSC (mass storage) driver.
305+ Can be combined with other ``BUILTIN_ `` constants using the bitwise
306+ OR operator (``| ``).
307+
308+ .. data :: USBDevice.BUILTIN_NCM
309+
310+ Constant representing the built-in USB NCM (network) driver.
311+ Only available when ``MICROPY_HW_NETWORK_USBNET `` is enabled in the
312+ firmware build. Can be combined with other ``BUILTIN_ `` constants
313+ using the bitwise OR operator (``| ``).
314+
315+ .. note :: When NCM is disabled after being active, the network
316+ interface is automatically cleaned up.
317+
272318.. data :: USBDevice.BUILTIN_CDC_MSC
273319
274- These constant objects hold the built-in descriptor data which is
275- compiled into the MicroPython firmware. ``USBDevice.BUILTIN_NONE `` and
276- ``USBDevice.BUILTIN_DEFAULT `` are always present. Additional objects may be present
277- depending on the firmware build configuration and the actual built-in drivers.
278-
279- .. note :: Currently at most one of ``USBDevice.BUILTIN_CDC``,
280- ``USBDevice.BUILTIN_MSC `` and ``USBDevice.BUILTIN_CDC_MSC `` is defined
281- and will be the same object as ``USBDevice.BUILTIN_DEFAULT ``.
282- These constants are defined to allow run-time detection of
283- the built-in driver (if any). Support for selecting one of
284- multiple built-in driver configurations may be added in the
285- future.
286-
287- These values are assigned to :data: `USBDevice.builtin_driver ` to get/set the
288- built-in configuration.
289-
290- Each object contains the following read-only fields:
291-
292- - ``itf_max `` - One more than the highest bInterfaceNumber value used
293- in the built-in configuration descriptor.
294- - ``ep_max `` - One more than the highest bEndpointAddress value used
295- in the built-in configuration descriptor. Does not include any
296- ``IN `` flag bit (0x80).
297- - ``str_max `` - One more than the highest string descriptor index
298- value used by any built-in descriptor.
299- - ``desc_dev `` - ``bytes `` object containing the built-in USB device
300- descriptor.
301- - ``desc_cfg `` - ``bytes `` object containing the complete built-in USB
302- configuration descriptor.
320+ .. deprecated ::
321+ Use ``USBDevice.BUILTIN_CDC | USBDevice.BUILTIN_MSC `` instead.
322+
323+ Legacy constant for CDC and MSC combination. Provided for backward
324+ compatibility only.
325+
326+ **Combining Built-in Constants: **
327+
328+ Built-in driver constants can be combined using the bitwise OR operator to
329+ create custom USB device configurations::
330+
331+ # CDC serial port only
332+ usb.builtin_driver = USBDevice.BUILTIN_CDC
333+
334+ # CDC and MSC (serial + mass storage)
335+ usb.builtin_driver = USBDevice.BUILTIN_CDC | USBDevice.BUILTIN_MSC
336+
337+ # All available interfaces
338+ usb.builtin_driver = USBDevice.BUILTIN_CDC | USBDevice.BUILTIN_MSC | USBDevice.BUILTIN_NCM
339+
340+ # No built-in drivers (for fully custom USB devices)
341+ usb.builtin_driver = USBDevice.BUILTIN_NONE
342+
343+ The combined configuration dynamically generates the appropriate USB descriptors
344+ and updates the ``itf_max ``, ``ep_max ``, and ``str_max `` properties accordingly.
345+
346+ Each constant object contains the following read-only fields:
347+
348+ - ``itf_max `` - One more than the highest bInterfaceNumber value used
349+ in the configuration. Dynamically calculated based on enabled classes.
350+ - ``ep_max `` - One more than the highest bEndpointAddress value used
351+ in the configuration. Does not include any ``IN `` flag bit (0x80).
352+ Dynamically calculated based on enabled classes.
353+ - ``str_max `` - One more than the highest string descriptor index
354+ value used by any descriptor. Dynamically calculated.
355+ - ``desc_dev `` - ``bytes `` object containing the USB device descriptor.
356+ - ``desc_cfg `` - ``bytes `` object containing the complete USB
357+ configuration descriptor for the enabled classes.
358+
359+ Usage Examples
360+ --------------
361+
362+ **Basic CDC Serial Port: **
363+ ::
364+
365+ import machine
366+
367+ usb = machine.USBDevice()
368+ usb.active(False)
369+ usb.builtin_driver = usb.BUILTIN_CDC
370+ usb.active(True)
371+
372+ **CDC + Mass Storage: **
373+ ::
374+
375+ import machine
376+
377+ usb = machine.USBDevice()
378+ usb.active(False)
379+ usb.builtin_driver = usb.BUILTIN_CDC | usb.BUILTIN_MSC
380+ usb.active(True)
381+
382+ **Network Device with Serial Console: **
383+ ::
384+
385+ import machine
386+
387+ usb = machine.USBDevice()
388+ usb.active(False)
389+ # Enable both CDC for console and NCM for networking
390+ usb.builtin_driver = usb.BUILTIN_CDC | usb.BUILTIN_NCM
391+ usb.active(True)
392+
393+ **Switching Configurations at Runtime: **
394+ ::
395+
396+ import machine
397+
398+ usb = machine.USBDevice()
399+
400+ # Start with CDC only
401+ usb.active(False)
402+ usb.builtin_driver = usb.BUILTIN_CDC
403+ usb.active(True)
404+
405+ # Later, add mass storage
406+ usb.active(False)
407+ usb.builtin_driver = usb.BUILTIN_CDC | usb.BUILTIN_MSC
408+ usb.active(True)
409+
410+ # Remove MSC, add NCM
411+ usb.active(False)
412+ usb.builtin_driver = usb.BUILTIN_CDC | usb.BUILTIN_NCM
413+ usb.active(True)
414+
303415
304416.. _usb driver modules in micropython-lib : https://github.com/micropython/micropython-lib/tree/master/micropython/usb#readme
0 commit comments