Coder Social home page Coder Social logo

webusb's People

Contributors

autokagami avatar balazs avatar beaufortfrancois avatar cavokz avatar chengweih001 avatar clelland avatar dontcallmedom avatar dsanders11 avatar facchinm avatar foolip avatar fvibert avatar gredler avatar krockot avatar littledivy avatar marcoscaceres avatar nondebug avatar odejesush avatar onlykey avatar pes10k avatar reillyeon avatar rreverser avatar samccone avatar saschanaz avatar scheib avatar thegecko avatar travisleithead avatar yoavweiss avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

webusb's Issues

Propose HTML Tag Addition for Compliance

With WebUSB, and other Such Libraries being Developed, what if we Added "Scheme" Data too the Meta Tags in the HTML Itself? Much like the Allowed Policies, that other Applications Do. Verifying, that the Site is Requesting This, This, and This. Example.

<meta headset="OculusDK2">
<meta name="controller" content="LeapMotion" version="*">

I am Testing something similar too that for Direct Interaction with the Website, towards VR-Web Compliance.

Attack vector by emulating site-trusted devices

Feedback from one of our USB subsystem maintainers:

With devices like Edison, Beaglebone, RasPI and the like, we have a full Linux machine with a USB peripheral controller inside. Given they also come with sources and sdk, anybody in the world can make these hacker platforms look like anything they want.

Say e.g. st.com wants to access their STM32 discovery boards over the web using WebUSB, so they'll look for devices which have st.com as allowed URLs and discovery boards will ship with a bootloader containing
that support. Now, the only thing they have to check that they are, indeed, talking to an stm32 discovery board, are the USB descriptors themselves.

What prevents anybody from getting an Edison and copying these descriptors to force st.com to talk to their boards?

Now, with that out of the way, how can force st.com to crash & burn by returning oddling formed packets or descriptors larger/smaller then they should be, or
returning much more data than asked and so on.

Filter by serialNumber

Could we extends the filter to filter by serialNumber value too (in requestDevice and getDevices)?

Use case: I want to expose in the usb.requestDevice window only a list of devices (i.e. mass storages, smartcard readers, ...) that were previously added in the settings section of my web application.

Read Data from Pen Drive

I am quite new to WebUSB, but it seems that it can support in what I would like to implement.

Is it possible that a PHP-based web-application would be able to read data from a pen drive?

The idea is to have an encryption key stored on a pen drive. when the web-application detects the presence of the drive it should decrypt certain data in the database and show it to the user.

However, it is a little hard to understand how one should go about this? Can you provide an example, or point me in the right direction?

GET_URL vs GET_ALLOWED_ORIGINS

If the former is just for getting an individual index of the allowed origins, I find it weird that the name is so different. Why not just GET_ALLOWED_ORIGIN or GET_ALLOWED_ORIGIN_AT

User agent should infer protocol in landing/allowed origins

The landing page and allowed-origin descriptors take up a reasonably large amount of firmware space on small devices. It would help if the spec required the host to prepend https:// to origins that do not specify a protocol. E.g., example.com becomes https://example.com.

Local whitelist

It is very important to have the option to do a local whitelist for development (at least until a well functioning online db/repo is up... could we use a file/subrepo here on github?). Otherwise, it will only be explored by arduino makers and not by larger industry with legacy devices on the market. Remember that for most existing devices out there, it's not a simple task to change the USB communication (headers) for shipped units and even units in the pipeline for some time to come.

Enable mechanism to disambiguate identical devices

When handling multiple otherwise identical USB devices, it is useful to try to keep track of which device is which. USB doesn't reliably provide this information, since the serial number is optional (and often duplicated).

If topology information is provided (it can be obfuscated if necessary), then clients can compute a reasonable heuristic based on a combination of serial number, topology, and product+vendor id.

Windows provides a heuristic with its Container ID mechanism: https://msdn.microsoft.com/en-us/library/windows/hardware/ff546243(v=vs.85).aspx

Feature is a major security hole

This project must be immediately stopped, because it opens a critical security hole.
Web browser NEVER should have access to physical devices !

USBConnectionEvent needs a constructor

http://wicg.github.io/webusb/#events

It has a constructor in Chromium:
https://chromium.googlesource.com/chromium/src/+/2fe96ea775a73ad5dcc05105f57be096d302baa2/third_party/WebKit/Source/modules/webusb/USBConnectionEvent.idl

But unless device is made nullable, some tweaks are needed to ensure that it's never null, a non-optional dict with a required member:

[Constructor(DOMString type, USBConnectionEventInit eventInitDict)]
interface USBConnectionEventB : Event {
    [SameObject] readonly attribute USBDevice device;
};

dictionary USBConnectionEventInit : EventInit {
    required USBDevice device;
};

Android - NFC - source of inspiration

I think the NFC implementation on android could be a good source of inspiration.
http://developer.android.com/guide/topics/connectivity/nfc/nfc.html
Because you are doing something pretty similar.

The way NDEF messages are defined.
https://w3c.github.io/web-nfc/#dfn-ndef-record

Intent filter (way to integrate NFC and an application specific to a website/protocol)
< intent-filter>
< action android:name="android.nfc.action.NDEF_DISCOVERED"/>
< category android:name="android.intent.category.DEFAULT"/>
< data
android:host="nfc.nuage.ch"
android:scheme="https"/>
< /intent-filter>

Add Security Considerations and Privacy Considerations sections

Example security considerations:

  • What stops malicious web origins from attacking vulnerabilities in USB devices/device controllers? Devices and their controllers do some non-trivial packet handling and they are programmed on the cheap and not updated.
  • vendorId and deviceId make potential exploits somewhat easier to make reliable ("Don't try all vulns we have exploits for; that might crash the device controller. Instead, we know we can use the exploit we have for FooCorp Device Model 123.")

Example privacy consideration:

  • This API creates long-lived, high-resolution, undeletable device/user/client IDs via serialNumber, vendorId, and deviceId.

Example mitigation:

  • WebUSB is a special permission that browsers only give origins with explicit user knowledge and consent (like Geolocation, for example).

...but then the spec needs to describe the requirements for the knowledge and consent ceremony.

Define WebUSB from Service Workers

It makes sense for a service worker to be able to react to a device being plugged in. It also makes sense for a service worker to be able to provide driver-like functionality for a device to other origins through navigator.connect. This issue is a reminder to figure out how this should work.

How to handle legacy permissions for FTDI/Prolific/etc USB-Serial interfaces

Have you considered what happens with USB-Serial devices like FTDI and Prolific? If FTDI decided to allow access publicly, they would effectively claim ownership of any device that used their chips (or was connected by a cable containing their chips), regardless of whether it was theirs or not? Given their history of bricking counterfeit devices, that's a bit scary.

It works the other way too - many older Arduino boards would be unusable because they use FTDI chips and so have their VID and PID, and FTDI wouldn't want to risk putting another company's URL into allowed origins. It'd be really nice to have some 'advanced' way to override it, perhaps by having the option to specify which 'Public URLs' contained the descriptors for legacy devices.

Also many devices now have a USB DFU bootloader burnt into the device. I'm not saying it should be a 'single click' to enable it (that'd be a security disaster) but it'd be nice for people who knew what they were doing to be able to work around it (if only with chrome://flags/)

Background

I develop Espruino (an Open Source JavaScript interpreter for microcontrollers) and most users have been dependent on the Chrome Serial API via a Chrome app for years - while it works fine now, driver support is always a nightmare and there's no support on Android.

I'm using Web Bluetooth in a new product specifically because of the promise of communication directly from a website. Adding Web USB too would be amazing.

Given the driver issue, I was lazy and have my devices the PID and VID that ST used for the USB CDC examples for the microcontrollers I was using, as they provided a set of drivers that 'just worked' - obviously that would now cause my users problems (unless I can update the firmware to serve up descriptors).

Maybe just emulate HTTP server via USB CDC NCM virtual network interface?

Thinking about #50 I got the following idea:

In the end, what you want to do is let a webapp communicate with a USB-connected device running a cooperating firmware. You might be able to achieve this by doing the following:

  • Have the device enumerate as an USB CDC NCM (network) device in addition to its usual interfaces. (AFAIK Android adb uses something like this)
  • Have the device provide DHCP on a company-owned, not globally routed network range on that interface, but do not annouce DNS or a default route.
  • Emulate an HTTP server listening on this virtual network port on the device that sends the appropriate headers to allow access from vendor website despite Same-Origin-Policy.

This requires a bit of code on the firmware side of things, but that's mostly a barebones stripped-down IP/DHCP/TCP/HTTP stack. The advantage of this would be that it is fully compatible with existing systems, since USB network drivers (hopefully) are already installed on any system and browsers are already good at talking to "network" devices.

This solution would IMO be cleaner than what is currently proposed as it does not require new client-side code and the attack surface is clearly limited on the embedded HTTP thingamabob which could conceivably be secured. There still remains a lot of potential for ownage, but I guess that's what you get for plugging the internet into your things.

Numeric type usage is weird

float for usbVersion; octet for deviceClass etc.; ...

If there's no intention for people to do arithmetic on these, I'd definitely suggest strings.

Floats are especially problematic since e.g. usbVersion: 3.1 actually means usbVersion: 3.10000000000000008882.

should access to USB devices be controlled by device vendor or user?

The TAG started to discuss (briefly) the specification at our London face-to-face, as part of the request for TAG review (w3ctag/design-reviews#108).

One issue that came up is that the specification currently uses the model where the USB device vendor decides what origins can communicate with the USB device. Some people were wondering the alternative model where the decisions are made by the user rather than the device vendor, or perhaps a model that allows both mechanisms.

We're certainly not ready to say that one model or the other was better. However, it would be interesting to hear (maybe in the explainer or the spec draft?) about whether you considered a user-mediated model, and if so, what led you to make the choices that you did.

Transfer types and result types

Interrupt and bulk transfers are joined together and just called "transfers", control and isochromous are separate in functions and result types.

Some result types carry the exact same data (USBIsochronousInTransferPacket and USBInTransferResult, for instance).

interface USBInTransferResult {
    readonly attribute DataView          data;
    readonly attribute USBTransferStatus status;
};

interface USBOutTransferResult {
    readonly attribute unsigned long     bytesWritten;
    readonly attribute USBTransferStatus status;
};

interface USBIsochronousInTransferPacket {
    readonly attribute DataView          data;
    readonly attribute USBTransferStatus status;
};

interface USBIsochronousInTransferResult {
    readonly attribute DataView                                    data;
    readonly attribute FrozenArray<USBIsochronousInTransferPacket> packets;
};

interface USBIsochronousOutTransferPacket {
    readonly attribute unsigned long     bytesWritten;
    readonly attribute USBTransferStatus status;
};

interface USBIsochronousOutTransferResult {
    readonly attribute FrozenArray<USBIsochronousOutTransferPacket> packets;
};

Why not simplify this:

interface USBOutTransferResult {
    readonly attribute TransferType      type; // "isochronous", "interrupt", "bulk", "control"
    readonly attribute FrozenArray<USBOutTransferPacketResult> packets;
}

interface USBInTransferResult {
    readonly attribute TransferType      type; // "isochronous", "interrupt", "bulk", "control"
    readonly attribute FrozenArray<USBInTransferPacketResult> packets;
};

interface USBOutTransferPacketResult {
    readonly attribute unsigned long     bytesWritten;
    readonly attribute USBTransferStatus status;
};

interface USBInTransferPacketResult {
    readonly attribute DataView          data;
    readonly attribute USBTransferStatus status;
};

Yes this means that you would need to do result.packets[0].bytesWritten for instance for a bulk transfer, but I don't think that should be much of an issue. It might be possible to have a shorthand like result.packet as well.

As the endpoint type is fixed (unless reconfigured), I also think we can safely merge transferIn(octet endpointNumber, unsigned long length); and Promise<USBIsochronousInTransferResult> isochronousTransferIn(octet endpointNumber, sequence<unsigned long> packetLengths);

to

Promise<USBInTransferResult>  transferIn(octet endpointNumber, sequence<unsigned long> packetLengths);

A sequence with size more than 1 for non-isochronous transfers makes no sense and can just result in a failed promise, with an appropriate error.

I still like having controlTransferIn separate as it is really a special endpoint, but for that reason, it make sense to rename transferIn(..) to dataTransferIn

Should open really reject when already opened?

I guess calling open on something opened might not be too bad, and it is kind of required by other methods like reset. Having to handle this with promises is ugly but doable, even with ES2017 async/await.

async function doStuff() {
  try {
    await open();
  } catch() {
    ... ignore invalid state
  }
  try {
    await reset();
    ...
   }
}

Maybe it should be possible to query the state or have open not tread this as an error (option?)

Alternate setting retrieval should be asynchronous

We have an attribute on USBInterface to get the current alternate setting. There's probably no perfect way for us to cache this information to make it available synchronously, so we should always query the device instead. Should change to an async interface:

Promise<octet> getAlternateSetting();

Plan for USB HID support?

I'm trying to figure out what the long-term plan for web access to exotic input devices should be. Would it make sense for WebUSB to someday be extended to support HID devices somehow? Eg. consider a USB mouse or stylus with some extra non-standard capability (eg. extra buttons, wheel, z-axis, etc.). How would a device vendor build such a device such that it still behaves just like a normal mouse/stylus while also making the additional input data available to a web app such that it can be used in concert with the standard data? Synchronization of event streams might be challenging here.

Said another way, what's the open web equivalent of the Chrome.hid API?

Any thoughts? I'm happy to brainstorm further if/when you feel the time is right.

Potential privacy issue

Feedback from one of our USB maintainers:

There's a privacy concern which, while mentioned in the spec, doesn't seem to be fully considered either. Say someone gives me an STM32 discovery board which acts as a keylogger but I don't know about it. From all I can tell st.com is in the list of allowed URLs and st.com
will happily talk to it; however the domain mrhanky-keylogger.com is also in the list of allowed URLs because whoever gave me this stm32 discovery board hacked it.

Whatever keys stm32 discovery hacked managed to log will be periodically sent over to mrhanky-keylogger.com.

Transfer calls need timeout/cancellation

Callers should be able to cancel transfers, at least with a timeout argument if not a more general solution. Two ways I could see cancellation happening:

1. Introduce a new interface for return

interface PendingTransfer {
    readonly attribute Promise<ArrayBuffer> promise;
    void cancel();
};

All transfer calls would return this instead of a Promise<ArrayBuffer>. This seems undesirable to me because then usage looks like:

device.controlTransferIn(foo, bar, ...).promise.then(() => ...)

Pretty ugly.

2. Introduce a new Waiter interface that can be passed to transfer calls

interface TransferWaiter {
    void cancel();
};

The pattern then looks like this:

let waiter = new TransferWaiter;
device.controlTransferIn(foo, bar, ..., waiter).then(...).catch(...);
setTimeout(function() { waiter.cancel(); }, 100);

This would address the more general cancellation concern without a need to introduce an explicit timeout argument. Still not a common pattern, but it seems reasonable to me.

Note: "waiter" may be a misnomer.

No constructors

In some cases it is OK for an interface to not have a WebIDL-defined constructor. Those are the cases when an object is meant to only be created by the UA. (In which case, it has a constructor, but one that is not callable by normal JS code.)

Are all of the objects in the spec such cases? Is there a way to design the architecture better so that there are fewer magically-created objects, and more normal-constructible-from-JS objects?

USBConfiguration, USBAlternateInterface, USBEndpoint should provide access to non-standard descriptors

Some USB standards (e.g. DFU, CDC-ACM) define class-specific descriptors that are included in the set of descriptors returned with the configuration descriptor. These descriptors are not necessarily accessible via GET_DESCRIPTOR requests.

Currently, the only way to access these descriptors via WebUSB is to retrieve the configuration descriptor set and manually parse all of the descriptors, standard and class-specific alike.

One way to simplify this would be to stash non-standard descriptors into a buffer while parsing the set of descriptors. For example, LibUSB stores a copy of any unknown descriptors and associates them with the closest configuration / interface / endpoint descriptor.

This would allow the user to parse just the class-specific descriptors without needing to repeat the entire descriptor parsing process.

Document how the list of acceptable origins is authenticated

"""New devices (or firmware updates) may include a list of acceptable origins that the user agent can query, similar to the CORS mechanism for HTTP requests. Device vendors may enable existing devices by registering them in an open directory which maps device IDs to acceptable origins."""

How do we make sure the list is not supplied by the attacker?

Should the spec make it clear that you can loosen "CORS" like restriction for dev purposes?

Service Workers have something like this:

6 Security Considerations
Service workers should be implemented to be HTTPS-only. The reasons for SSL-only support include:

Better to protect end users from man-in-the-middle attacks
Do good by encouraging HTTPS adoption
Existing "playground" services (e.g. github.io) now work with HTTPS
HTTPS is coming across much more of the web quickly
Devtools can loosen the restriction for development (file://, localhost, etc.)

Extra word and missing punctuation in the first sentence of the second paragraph belonging to the "What is it not?" section of explainer.md.

In explainer.md, navigate to the second paragraph of the "What is it not?" section. Observe the first sentence.

Now:

Instead USB devices will be associated with a web origin and can only be connected to from a page from the same origin.

Proposed Changes:

  • Add a comma after the adverb "instead"
  • Remove the extra "from" before the preposition "to"

After:

Instead, USB devices will be associated with a web origin and can only be connected to a page from the same origin.

I originally made the changes myself and was going to create a pull request, but, as I understand it, I would have to be accepted in the CG before I can contribute. Perhaps creating an issue is still beneficial.

make setConfiguration more tolerant

It would be better (hear easier) in my opinion if setConfiguration would succeed even if the active configuration is already the one we're trying to set.

For now, here's what we have to write...

device.getConfiguration()
.then(config => {
  if (config.configurationValue == 1) {
    return Promise.resolve();
  } else {
    return Promise.reject();
  }
})
.catch(error => device.setConfiguration(1))
.then(() => { ... })

How about instead?

device.setConfiguration(1)
.then(() => { ... })

Currently if I try device.setConfiguration(1) while active configuratuion configurationValue is 1, I get a "DOMException: Unable to set device configutation" error.
And my about:device-log page says "Failed to set configuration 1: Resource busy".

How do you access a USBDeviceEnumeration?

The spec contains a getDevices method on USBDeviceEnumeration, but I can't see how to access a USBDeviceEnumeration. Is it supposed to be a property of navigator or something?

Make port part of origin

https://url.spec.whatwg.org/#concept-url-origin makes it clear that origin is a tuple of (scheme, host, port) but URL Descriptor contains only "scheme", and "url".

As URL normally contains scheme, and this is actually an origin, why not make it:

Offset         Field             Size     Value       Description
0              bLength           1        Number      Size of this descriptor.
1              bDescriptorType   1        Constant    WEBUSB_ORIGIN.
2              bScheme           1        Number      Origin scheme prefix.
3              Host Variable              String      UTF-8 encoded Origin host.
4              bPort             1        Number      Origin port.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.