script/dom/
bytelengthqueuingstrategy.rs1use std::rc::Rc;
6
7use dom_struct::dom_struct;
8use js::error::throw_type_error;
9use js::gc::{HandleValue, MutableHandleValue};
10use js::jsapi::{CallArgs, JSContext};
11use js::jsval::{JSVal, UndefinedValue};
12use js::rust::HandleObject;
13
14use super::bindings::codegen::Bindings::FunctionBinding::Function;
15use super::bindings::codegen::Bindings::QueuingStrategyBinding::{
16 ByteLengthQueuingStrategyMethods, QueuingStrategyInit,
17};
18use super::bindings::error::Fallible;
19use super::bindings::reflector::{DomGlobal, Reflector, reflect_dom_object_with_proto};
20use super::bindings::root::DomRoot;
21use super::types::GlobalScope;
22use crate::dom::bindings::utils::get_dictionary_property;
23use crate::native_fn;
24use crate::script_runtime::CanGc;
25
26#[dom_struct]
27pub(crate) struct ByteLengthQueuingStrategy {
28 reflector_: Reflector,
29 high_water_mark: f64,
30}
31
32impl ByteLengthQueuingStrategy {
33 pub(crate) fn new_inherited(init: f64) -> Self {
34 Self {
35 reflector_: Reflector::new(),
36 high_water_mark: init,
37 }
38 }
39
40 pub(crate) fn new(
41 global: &GlobalScope,
42 proto: Option<HandleObject>,
43 init: f64,
44 can_gc: CanGc,
45 ) -> DomRoot<Self> {
46 reflect_dom_object_with_proto(Box::new(Self::new_inherited(init)), global, proto, can_gc)
47 }
48}
49
50impl ByteLengthQueuingStrategyMethods<crate::DomTypeHolder> for ByteLengthQueuingStrategy {
51 fn Constructor(
53 global: &GlobalScope,
54 proto: Option<HandleObject>,
55 can_gc: CanGc,
56 init: &QueuingStrategyInit,
57 ) -> DomRoot<Self> {
58 Self::new(global, proto, init.highWaterMark, can_gc)
59 }
60 fn HighWaterMark(&self) -> f64 {
62 self.high_water_mark
63 }
64
65 fn GetSize(&self, _can_gc: CanGc) -> Fallible<Rc<Function>> {
67 let global = self.global();
68 if let Some(fun) = global.get_byte_length_queuing_strategy_size() {
71 return Ok(fun);
72 }
73
74 let fun = native_fn!(byte_length_queuing_strategy_size, c"size", 1, 0);
80 global.set_byte_length_queuing_strategy_size(fun.clone());
84 Ok(fun)
85 }
86}
87
88#[expect(unsafe_code)]
90pub(crate) unsafe fn byte_length_queuing_strategy_size(
91 cx: *mut JSContext,
92 argc: u32,
93 vp: *mut JSVal,
94) -> bool {
95 let args = unsafe { CallArgs::from_vp(vp, argc) };
96
97 let chunk = unsafe { HandleValue::from_raw(args.get(0)) };
100
101 if chunk.is_undefined() || chunk.is_null() {
104 unsafe {
105 throw_type_error(
106 cx,
107 "ByteLengthQueuingStrategy size called with undefined or nulll",
108 )
109 };
110 return false;
111 }
112
113 if !chunk.is_object() {
114 args.rval().set(UndefinedValue());
117 return true;
118 }
119
120 rooted!(in(cx) let object = chunk.to_object());
121
122 match unsafe {
124 get_dictionary_property(
125 cx,
126 object.handle(),
127 "byteLength",
128 MutableHandleValue::from_raw(args.rval()),
129 CanGc::note(),
130 )
131 } {
132 Ok(true) => true,
133 Ok(false) => {
134 args.rval().set(UndefinedValue());
135 true
136 },
137 Err(()) => false,
138 }
139}