Skip to content

USBSerialDevice on Fomu PVT fails with Windows host #294

@JustinCWeiler

Description

@JustinCWeiler

When I create a simple loopback program, Windows recognizes the COM port but gives an error saying "This device cannot start" (see screenshots below).

Toolchain versions:

  • yosys 0.54+23
  • nextpnr-ice40 0.8-43

Code:

import os, shutil, subprocess

from amaranth import *
from amaranth.lib import wiring

from amaranth_boards.fomu_pvt import FomuPVTPlatform

from luna.full_devices import USBSerialDevice

class Top(wiring.Component):
    def __init__(self, with_usb=False):
        self.with_usb = with_usb

    def elaborate(self, platform):
        m = Module()

        input_clock = platform.request('clk48').i

        # Raw Clock Domains
        m.domains.clk48 = cd_clk48 = ClockDomain(local=True)
        m.domains.clk12 = cd_clk12 = ClockDomain(local=True)

        m.submodules += Instance('SB_PLL40_CORE',
                                 p_DIVR = 0,
                                 p_DIVF = 15,
                                 p_DIVQ = 5,
                                 p_FILTER_RANGE = 1,
                                 p_FEEDBACK_PATH = 'SIMPLE',
                                 p_DELAY_ADJUSTMENT_MODE_FEEDBACK = 'FIXED',
                                 p_FDA_FEEDBACK = 15,
                                 p_DELAY_ADJUSTMENT_MODE_RELATIVE = 'FIXED',
                                 p_FDA_RELATIVE = 0,
                                 p_SHIFTREG_DIV_MODE = 1,
                                 p_PLLOUT_SELECT = 'GENCLK_HALF',
                                 p_ENABLE_ICEGATE = 0,
                                 # IO
                                 i_REFERENCECLK = ClockSignal('clk48'),
                                 o_PLLOUTCORE = ClockSignal('clk12'),
                                 i_BYPASS = 0,
                                 i_RESETB = 1,
                                )

        # Named Clock Domains
        m.domains.sync = ClockDomain(local=True)
        m.domains.usb = ClockDomain(local=True)
        m.domains.usb_io = ClockDomain(local=True)

        m.d.comb += [
            ClockSignal('clk48').eq(input_clock),
            ClockSignal('sync').eq(ClockSignal('clk12')),
            ClockSignal('usb').eq(ClockSignal('clk12')),
            ClockSignal('usb_io').eq(ClockSignal('clk48')),

            ResetSignal('sync').eq(ResetSignal('clk12')),
            ResetSignal('usb').eq(ResetSignal('clk12')),
            ResetSignal('usb_io').eq(ResetSignal('clk48')),
        ]

        platform.add_clock_constraint(cd_clk48.clk, frequency=48e6)
        platform.add_clock_constraint(cd_clk12.clk, frequency=12e6)

        # USB module
        usb_pads = platform.request('usb')
        m.submodules.usb_serial = usb_serial = USBSerialDevice(bus=usb_pads, idVendor=0x1209, idProduct=0x70b1)

        m.d.comb += [
            usb_serial.connect.eq(1),

            usb_serial.tx.payload  .eq(usb_serial.rx.payload),
            usb_serial.tx.valid    .eq(usb_serial.rx.valid),
            usb_serial.tx.first    .eq(usb_serial.rx.first),
            usb_serial.tx.last     .eq(usb_serial.rx.last),
            usb_serial.rx.ready    .eq(usb_serial.tx.ready),
        ]

        return m

def add_dfu_suffix(fn):
    fn_base, _ = os.path.splitext(fn)
    fn_dfu = fn_base + '.dfu'
    shutil.copyfile(fn, fn_dfu)
    subprocess.check_call(['dfu-suffix', '--pid', '1209', '--vid', '70b1', '--add', fn_dfu])

def main():
    platform = FomuPVTPlatform()

    platform.build(Top(with_usb=True), build_dir='bin')

    add_dfu_suffix('bin/top.bin')

    return 0

if __name__ == '__main__':
    exit(main())

Device manager:

Image

Image

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions