Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Annotations for WebBluetooth functions #14407

Merged
merged 3 commits into from Dec 1, 2016
Merged
Changes from 1 commit
Commits
File filter...
Filter file types
Jump to…
Jump to file
Failed to load files.

Always

Just for now

Prev

Step annotations for WebBluetooth functions

  • Loading branch information
zakorgy authored and dati91 committed Nov 29, 2016
commit 8dd100f74fdabd55d5f3c179b3d5e52d2e0aa0e5

Large diffs are not rendered by default.

@@ -79,7 +79,7 @@ impl<Listener: AsyncBluetoothListener + Reflectable> BluetoothResponseListener f
match response {
Ok(response) => self.receiver.root().handle_response(response, promise_cx, &promise),
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetooth-requestdevice
// Step 3-4.
// Step 3 - 4.
Err(error) => promise.reject_error(promise_cx, Error::from(error)),
}
}
@@ -187,9 +187,9 @@ impl Bluetooth {
let option = RequestDeviceoptions::new(BluetoothScanfilterSequence::new(uuid_filters),
ServiceUUIDSequence::new(optional_services_uuids));

// TODO: Step 3-5: Implement the permission API.
// TODO: Step 3 - 5: Implement the permission API.

// Note: Steps 6-8 are implemented in
// Note: Steps 6 - 8 are implemented in
// components/net/bluetooth_thread.rs in request_device function.
let sender = response_async(p, self);
self.get_bluetooth_thread().send(BluetoothRequest::RequestDevice(option, sender)).unwrap();
@@ -295,7 +295,7 @@ fn canonicalize_filter(filter: &BluetoothLEScanFilterInit) -> Fallible<Bluetooth
None => String::new(),
};

// Step 6 -7.
// Step 6 - 7.
let manufacturer_data = match filter.manufacturerData {
Some(ref manufacturer_data_map) => {
// Note: If manufacturer_data_map is empty, that means there are no key values in it.
@@ -304,23 +304,23 @@ fn canonicalize_filter(filter: &BluetoothLEScanFilterInit) -> Fallible<Bluetooth
}
let mut map = HashMap::new();
for (key, bdfi) in manufacturer_data_map.iter() {
// Step 7.1-7.2.
// Step 7.1 - 7.2.
let manufacturer_id = match u16::from_str(key.as_ref()) {
Ok(id) => id,
Err(err) => return Err(Type(format!("{} {} {}", KEY_CONVERSION_ERROR, key, err))),
};

// Step 7.3: No need to convert to IDL values since this is only used by native code.

// Step 7.4 -7.5.
// Step 7.4 - 7.5.
map.insert(manufacturer_id, try!(canonicalize_bluetooth_data_filter_init(bdfi)));
}
Some(map)
},
None => None,
};

// Step 8-9.
// Step 8 - 9.
let service_data = match filter.serviceData {
Some(ref service_data_map) => {
// Note: If service_data_map is empty, that means there are no key values in it.
@@ -336,7 +336,7 @@ fn canonicalize_filter(filter: &BluetoothLEScanFilterInit) -> Fallible<Bluetooth
_ => StringOrUnsignedLong::String(key.clone())
};

// Step 9.3-9.4.
// Step 9.3 - 9.4.
let service = try!(BluetoothUUID::service(service_name)).to_string();

// Step 9.5.
@@ -346,7 +346,7 @@ fn canonicalize_filter(filter: &BluetoothLEScanFilterInit) -> Fallible<Bluetooth

// Step 9.6: No need to convert to IDL values since this is only used by native code.

// Step 9.7 -9.8.
// Step 9.7 - 9.8.
map.insert(service, try!(canonicalize_bluetooth_data_filter_init(bdfi)));
}
Some(map)
@@ -404,7 +404,7 @@ impl BluetoothMethods for Bluetooth {

// Step 2.
self.request_bluetooth_devices(&p, &option.filters, &option.optionalServices);
//Note: Step 3-4. in response function, Step 5. in handle_response function.
//Note: Step 3 - 4. in response function, Step 5. in handle_response function.
return p;
}

@@ -416,7 +416,7 @@ impl AsyncBluetoothListener for Bluetooth {
fn handle_response(&self, response: BluetoothResponse, promise_cx: *mut JSContext, promise: &Rc<Promise>) {
match response {
// https://webbluetoothcg.github.io/web-bluetooth/#request-bluetooth-devices
// Step 13-14.
// Step 13 - 14.
BluetoothResponse::RequestDevice(device) => {
let mut device_instance_map = self.device_instance_map.borrow_mut();
if let Some(existing_device) = device_instance_map.get(&device.id.clone()) {
@@ -78,6 +78,7 @@ impl BluetoothDeviceMethods for BluetoothDevice {

// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothdevice-gatt
fn Gatt(&self) -> Root<BluetoothRemoteGATTServer> {
// TODO: Step 1 - 2: Implement the Permission API.
self.gatt.or_init(|| {
BluetoothRemoteGATTServer::new(&self.global(), self)
})
@@ -103,24 +103,36 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris

#[allow(unrooted_must_root)]
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-getdescriptor
// https://webbluetoothcg.github.io/web-bluetooth/#getgattchildren
fn GetDescriptor(&self, descriptor: BluetoothDescriptorUUID) -> Rc<Promise> {
let p = Promise::new(&self.global());
let p_cx = p.global().get_cx();

// Step 1.
let uuid = match BluetoothUUID::descriptor(descriptor) {
Ok(uuid) => uuid.to_string(),
Err(e) => {
p.reject_error(p_cx, e);
return p;
}
};

// Step 2.
if uuid_is_blocklisted(uuid.as_ref(), Blocklist::All) {
p.reject_error(p_cx, Security);
return p;
}

// Step 3 - 4.
if !self.Service().Device().Gatt().Connected() {
p.reject_error(p_cx, Network);
return p;
}

// TODO: Step 5: Implement representedService internal slot for BluetoothRemoteGATTService.

// Note: Steps 6 - 7 are implemented in components/bluetooth/lib.rs in get_descriptor function
// and in handle_response function.
let sender = response_async(&p, self);
self.get_bluetooth_thread().send(
BluetoothRequest::GetDescriptor(self.get_instance_id(), uuid, sender)).unwrap();
@@ -129,13 +141,15 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris

#[allow(unrooted_must_root)]
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-getdescriptors
// https://webbluetoothcg.github.io/web-bluetooth/#getgattchildren
fn GetDescriptors(&self,
descriptor: Option<BluetoothDescriptorUUID>)
-> Rc<Promise> {
let p = Promise::new(&self.global());
let p_cx = p.global().get_cx();
let mut uuid: Option<String> = None;
if let Some(d) = descriptor {
// Step 1.
uuid = match BluetoothUUID::descriptor(d) {
Ok(uuid) => Some(uuid.to_string()),
Err(e) => {
@@ -144,16 +158,24 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
}
};
if let Some(ref uuid) = uuid {
// Step 2.
if uuid_is_blocklisted(uuid.as_ref(), Blocklist::All) {
p.reject_error(p_cx, Security);
return p;
}
}
};

// Step 3 - 4.
if !self.Service().Device().Gatt().Connected() {
p.reject_error(p_cx, Network);
return p;
}

// TODO: Step 5: Implement representedService internal slot for BluetoothRemoteGATTService.

// Note: Steps 6 - 7 are implemented in components/bluetooth/lib.rs in get_descriptors function
// and in handle_response function.
let sender = response_async(&p, self);
self.get_bluetooth_thread().send(
BluetoothRequest::GetDescriptors(self.get_instance_id(), uuid, sender)).unwrap();
@@ -170,18 +192,31 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
fn ReadValue(&self) -> Rc<Promise> {
let p = Promise::new(&self.global());
let p_cx = p.global().get_cx();

// Step 1.
if uuid_is_blocklisted(self.uuid.as_ref(), Blocklist::Reads) {
p.reject_error(p_cx, Security);
return p;
}

// Step 2.
if !self.Service().Device().Gatt().Connected() {
p.reject_error(p_cx, Network);
return p;
}

// TODO: Step 3 - 4: Implement representedCharacteristic internal slot for BluetoothRemoteGATTCharacteristic.

// TODO: Step 5: Implement the `connection-checking-wrapper` algorithm for BluetoothRemoteGATTServer.

// Step 5.1.
if !self.Properties().Read() {
p.reject_error(p_cx, NotSupported);
return p;
}

// Note: Remaining substeps of Step 5 are implemented in components/bluetooth/lib.rs in readValue function
// and in handle_response function.
let sender = response_async(&p, self);
self.get_bluetooth_thread().send(
BluetoothRequest::ReadValue(self.get_instance_id(), sender)).unwrap();
@@ -193,25 +228,39 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
fn WriteValue(&self, value: Vec<u8>) -> Rc<Promise> {
let p = Promise::new(&self.global());
let p_cx = p.global().get_cx();

// Step 1.
if uuid_is_blocklisted(self.uuid.as_ref(), Blocklist::Writes) {
p.reject_error(p_cx, Security);
return p;
}

// Step 2 - 3.
if value.len() > MAXIMUM_ATTRIBUTE_LENGTH {
p.reject_error(p_cx, InvalidModification);
return p;
}

// Step 4.
if !self.Service().Device().Gatt().Connected() {
p.reject_error(p_cx, Network);
return p;
}

// TODO: Step 5 - 6: Implement representedCharacteristic internal slot for BluetoothRemoteGATTCharacteristic.

// TODO: Step 7: Implement the `connection-checking-wrapper` algorithm for BluetoothRemoteGATTServer.

// Step 7.1.
if !(self.Properties().Write() ||
self.Properties().WriteWithoutResponse() ||
self.Properties().AuthenticatedSignedWrites()) {
p.reject_error(p_cx, NotSupported);
return p;
}

// Note: Remaining substeps of Step 7 are implemented in components/bluetooth/lib.rs in writeValue function
// and in handle_response function.
let sender = response_async(&p, self);
self.get_bluetooth_thread().send(
BluetoothRequest::WriteValue(self.get_instance_id(), value, sender)).unwrap();
@@ -223,22 +272,32 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
fn StartNotifications(&self) -> Rc<Promise> {
let p = Promise::new(&self.global());
let p_cx = p.global().get_cx();

// Step 1.
if uuid_is_blocklisted(self.uuid.as_ref(), Blocklist::Reads) {
p.reject_error(p_cx, Security);
return p;
}
// Step 3.

// TODO: Step 2 - 3: Implement representedCharacteristic internal slot for BluetoothRemoteGATTCharacteristic.

// Step 4.
if !(self.Properties().Notify() ||
self.Properties().Indicate()) {
p.reject_error(p_cx, NotSupported);
return p;
}

// TODO: Step 5: Implement `active notification context set` for BluetoothRemoteGATTCharacteristic.

// Step 6.
if !self.Service().Device().Gatt().Connected() {
p.reject_error(p_cx, Network);
return p;
}

// Note: Steps 7 - 11 are implemented in components/bluetooth/lib.rs in enable_notification function
// and in handle_response function.
let sender = response_async(&p, self);
self.get_bluetooth_thread().send(
BluetoothRequest::EnableNotification(self.get_instance_id(),
@@ -252,6 +311,12 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
fn StopNotifications(&self) -> Rc<Promise> {
let p = Promise::new(&self.global());
let sender = response_async(&p, self);

// TODO: Step 1 - 4: Implement representedCharacteristic internal slot and
// `active notification context set` for BluetoothRemoteGATTCharacteristic,

// Note: Part of Step 4 and Step 5 are implemented in components/bluetooth/lib.rs in enable_notification
// function and in handle_response function.
self.get_bluetooth_thread().send(
BluetoothRequest::EnableNotification(self.get_instance_id(),
false,
@@ -266,6 +331,9 @@ impl BluetoothRemoteGATTCharacteristicMethods for BluetoothRemoteGATTCharacteris
impl AsyncBluetoothListener for BluetoothRemoteGATTCharacteristic {
fn handle_response(&self, response: BluetoothResponse, promise_cx: *mut JSContext, promise: &Rc<Promise>) {
match response {
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-getdescriptor
// https://webbluetoothcg.github.io/web-bluetooth/#getgattchildren
// Step 7.
BluetoothResponse::GetDescriptor(descriptor) => {
let context = self.service.get().get_device().get_context();
let mut descriptor_map = context.get_descriptor_map().borrow_mut();
@@ -279,6 +347,9 @@ impl AsyncBluetoothListener for BluetoothRemoteGATTCharacteristic {
descriptor_map.insert(descriptor.instance_id, MutHeap::new(&bt_descriptor));
promise.resolve_native(promise_cx, &bt_descriptor);
},
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-getdescriptors
// https://webbluetoothcg.github.io/web-bluetooth/#getgattchildren
// Step 7.
BluetoothResponse::GetDescriptors(descriptors_vec) => {
let mut descriptors = vec!();
let context = self.service.get().get_device().get_context();
@@ -300,17 +371,40 @@ impl AsyncBluetoothListener for BluetoothRemoteGATTCharacteristic {
}
promise.resolve_native(promise_cx, &descriptors);
},
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-readvalue
BluetoothResponse::ReadValue(result) => {
// TODO: Step 5.5.1: Implement activeAlgorithms internal slot for BluetoothRemoteGATTServer.

// Step 5.5.2.
// TODO(#5014): Replace ByteString with ArrayBuffer when it is implemented.
let value = ByteString::new(result);
*self.value.borrow_mut() = Some(value.clone());

// Step 5.5.3.
self.upcast::<EventTarget>().fire_bubbling_event(atom!("characteristicvaluechanged"));

// Step 5.5.4.
promise.resolve_native(promise_cx, &value);
},
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-writevalue
BluetoothResponse::WriteValue(result) => {
// TODO: Step 7.5.1: Implement activeAlgorithms internal slot for BluetoothRemoteGATTServer.

// Step 7.5.2.
// TODO(#5014): Replace ByteString with an ArrayBuffer wrapped in a DataView.
*self.value.borrow_mut() = Some(ByteString::new(result));

// Step 7.5.3.
promise.resolve_native(promise_cx, &());
},
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-startnotifications
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattcharacteristic-stopnotifications
BluetoothResponse::EnableNotification(_result) => {
// (StartNotification) TODO: Step 10: Implement `active notification context set`
// for BluetoothRemoteGATTCharacteristic.

// (StartNotification) Step 11.
// (StopNotification) Step 5.
promise.resolve_native(promise_cx, self);
},
_ => promise.reject_error(promise_cx, Error::Type("Something went wrong...".to_owned())),
ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.