solokeys / solo1

Solo 1 firmware in C
https://solokeys.com/
Other
2.28k stars 273 forks source link

CTAP Error - NOT_ALLOWED when trying to program firmware #614

Closed whosnorman closed 1 year ago

whosnorman commented 1 year ago

Heyo, just got a hacker solokey that was at version "3.1.2 unlocked" and was able to run solo1 key update to get it to version "4.1.5 unlocked".

However when I try to upload custom firmware with solo1 program bootloader teal-led-all.hex it results in two CTAP errors. I've also tried putting it into bootloader mode manually by holding down the button while plugging in. Both ways result in the same errors when trying to push custom firmware.

I'm running:

I've also tried running it with fido2==0.9.1 and the current production solo1 and I get the same errors.

Error logs:

$ sudo solo1 program bootloader teal-led-all.hex
erasing firmware...
Not in bootloader mode.  Attempting to switch...
Solo rebooted.  Reconnecting...
Traceback (most recent call last):
  File "/opt/homebrew/lib/python3.9/site-packages/solo/cli/program.py", line 168, in bootloader
    p.program_file(firmware)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 344, in program_file
    self.write_flash(i, data)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 174, in write_flash
    self.exchange(SoloBootloader.write, addr, data)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 118, in exchange_hid
    data = self.send_data_hid(SoloBootloader.CommandBoot, req)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/base.py", line 53, in send_data_hid
    return self.get_current_hid_device().call(cmd, data, event)
  File "/opt/homebrew/lib/python3.9/site-packages/fido2/hid/__init__.py", line 214, in call
    raise CtapError(struct.unpack_from(">B", recv)[0])
fido2.ctap.CtapError: CTAP error: 0x01 - INVALID_COMMAND

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/opt/homebrew/bin/solo1", line 8, in <module>
    sys.exit(solo_cli())
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1130, in __call__
    return self.main(*args, **kwargs)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1055, in main
    rv = self.invoke(ctx)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1657, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1657, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1404, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 760, in invoke
    return __callback(*args, **kwargs)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/cli/program.py", line 179, in bootloader
    p = solo.client.find(serial)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/client.py", line 31, in find
    p.find_device(dev=raw_device, solo_serial=solo_serial)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 49, in find_device
    devices = list(CtapHidDevice.list_devices())
  File "/opt/homebrew/lib/python3.9/site-packages/fido2/hid/__init__.py", line 259, in list_devices
    yield cls(d, open_connection(d))
  File "/opt/homebrew/lib/python3.9/site-packages/fido2/hid/__init__.py", line 107, in __init__
    response = self.call(CTAPHID.INIT, nonce)
  File "/opt/homebrew/lib/python3.9/site-packages/fido2/hid/__init__.py", line 174, in call
    self._connection.write_packet(packet.ljust(self._packet_size, b"\0"))
  File "/opt/homebrew/lib/python3.9/site-packages/fido2/hid/macos.py", line 317, in write_packet
    raise OSError(f"Failed to write report to device: {result}")
OSError: Failed to write report to device: 3758097131

# On running it again, after its in bootloader mode, I get the NOT_ALLOWED error. 
$ sudo solo1 program bootloader teal-led-all.hex
erasing firmware...
Traceback (most recent call last):
  File "/opt/homebrew/bin/solo1", line 8, in <module>
    sys.exit(solo_cli())
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1130, in __call__
    return self.main(*args, **kwargs)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1055, in main
    rv = self.invoke(ctx)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1657, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1657, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 1404, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/opt/homebrew/lib/python3.9/site-packages/click/core.py", line 760, in invoke
    return __callback(*args, **kwargs)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/cli/program.py", line 173, in bootloader
    raise e
  File "/opt/homebrew/lib/python3.9/site-packages/solo/cli/program.py", line 168, in bootloader
    p.program_file(firmware)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 344, in program_file
    self.write_flash(i, data)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 174, in write_flash
    self.exchange(SoloBootloader.write, addr, data)
  File "/opt/homebrew/lib/python3.9/site-packages/solo/devices/solo_v1.py", line 122, in exchange_hid
    raise CtapError(ret)
fido2.ctap.CtapError: CTAP error: 0x30 - NOT_ALLOWED

I've tried programming custom firmware and regular firmware to two different hacker solokeys and a hacker somu and always get NOT_ALLOWED once they're in bootloader mode.

whosnorman commented 1 year ago

Also I should've opened this in the cli repo. Figured it out, was trying to push a bundled .hex that included a bootloader using the bootloader instead of dfu. Wound up pushing an unbundled .hex using the bootloader instead!