aboutsummaryrefslogtreecommitdiffstats
path: root/src/components/script
diff options
context:
space:
mode:
Diffstat (limited to 'src/components/script')
-rw-r--r--src/components/script/dom/attrlist.rs2
-rw-r--r--src/components/script/dom/bindings/callback.rs8
-rw-r--r--src/components/script/dom/bindings/codegen/Bindings.conf6
-rw-r--r--src/components/script/dom/bindings/codegen/CodegenRust.py158
-rw-r--r--src/components/script/dom/bindings/error.rs2
-rw-r--r--src/components/script/dom/bindings/js.rs8
-rw-r--r--src/components/script/dom/bindings/proxyhandler.rs4
-rw-r--r--src/components/script/dom/bindings/trace.rs2
-rw-r--r--src/components/script/dom/bindings/utils.rs23
-rw-r--r--src/components/script/dom/document.rs32
-rw-r--r--src/components/script/dom/domexception.rs43
-rw-r--r--src/components/script/dom/domimplementation.rs12
-rw-r--r--src/components/script/dom/element.rs35
-rw-r--r--src/components/script/dom/event.rs16
-rw-r--r--src/components/script/dom/eventdispatcher.rs24
-rw-r--r--src/components/script/dom/eventtarget.rs2
-rw-r--r--src/components/script/dom/formdata.rs2
-rw-r--r--src/components/script/dom/htmlelement.rs7
-rw-r--r--src/components/script/dom/htmlfieldsetelement.rs17
-rw-r--r--src/components/script/dom/htmliframeelement.rs8
-rw-r--r--src/components/script/dom/htmlimageelement.rs19
-rw-r--r--src/components/script/dom/htmlobjectelement.rs2
-rw-r--r--src/components/script/dom/htmlserializer.rs4
-rw-r--r--src/components/script/dom/location.rs4
-rw-r--r--src/components/script/dom/mouseevent.rs5
-rw-r--r--src/components/script/dom/node.rs294
-rw-r--r--src/components/script/dom/webidls/Document.webidl1
-rw-r--r--src/components/script/dom/webidls/Element.webidl4
-rw-r--r--src/components/script/dom/webidls/Event.webidl1
-rw-r--r--src/components/script/dom/webidls/HTMLElement.webidl4
-rw-r--r--src/components/script/dom/webidls/MouseEvent.webidl1
-rw-r--r--src/components/script/dom/webidls/Node.webidl1
-rw-r--r--src/components/script/dom/webidls/Window.webidl14
-rw-r--r--src/components/script/dom/window.rs57
-rw-r--r--src/components/script/html/cssparse.rs3
-rw-r--r--src/components/script/html/hubbub_html_parser.rs83
-rw-r--r--src/components/script/layout_interface.rs6
-rw-r--r--src/components/script/macros.rs6
-rw-r--r--src/components/script/script.rs22
-rw-r--r--src/components/script/script_task.rs112
40 files changed, 677 insertions, 377 deletions
diff --git a/src/components/script/dom/attrlist.rs b/src/components/script/dom/attrlist.rs
index b172e976705..839043becf1 100644
--- a/src/components/script/dom/attrlist.rs
+++ b/src/components/script/dom/attrlist.rs
@@ -35,7 +35,7 @@ impl AttrList {
}
pub fn Item(&self, index: u32) -> Option<JS<Attr>> {
- self.owner.get().attrs.get_opt(index as uint).map(|x| x.clone())
+ self.owner.get().attrs.get(index as uint).map(|x| x.clone())
}
pub fn IndexedGetter(&self, index: u32, found: &mut bool) -> Option<JS<Attr>> {
diff --git a/src/components/script/dom/bindings/callback.rs b/src/components/script/dom/bindings/callback.rs
index b965fcbfb72..dff5aeb6a2b 100644
--- a/src/components/script/dom/bindings/callback.rs
+++ b/src/components/script/dom/bindings/callback.rs
@@ -12,17 +12,17 @@ use std::cast;
use std::libc;
use std::ptr;
-use extra::serialize::{Encodable, Encoder};
+use serialize::{Encodable, Encoder};
pub enum ExceptionHandling {
// Report any exception and don't throw it to the caller code.
- eReportExceptions,
+ ReportExceptions,
// Throw an exception to the caller code if the thrown exception is a
// binding object for a DOMError from the caller's scope, otherwise report
// it.
- eRethrowContentExceptions,
+ RethrowContentExceptions,
// Throw any exception to the caller code.
- eRethrowExceptions
+ RethrowExceptions
}
#[deriving(Clone,Eq)]
diff --git a/src/components/script/dom/bindings/codegen/Bindings.conf b/src/components/script/dom/bindings/codegen/Bindings.conf
index 6718071ac7d..eac06e8454d 100644
--- a/src/components/script/dom/bindings/codegen/Bindings.conf
+++ b/src/components/script/dom/bindings/codegen/Bindings.conf
@@ -52,6 +52,7 @@ DOMInterfaces = {
'Element': {
'needsAbstract': [
'attributes',
+ 'className',
'getBoundingClientRect',
'getClientRects',
'getElementsByClassName',
@@ -82,11 +83,14 @@ DOMInterfaces = {
'needsAbstract': [
'appendChild',
'childNodes',
+ 'cloneNode',
+ 'compareDocumentPosition',
'contains',
'insertBefore',
'isEqualNode',
'nodeName',
'nodeValue',
+ 'normalize',
'removeChild',
'replaceChild',
'textContent',
@@ -143,7 +147,7 @@ addHTMLElement('HTMLDirectoryElement')
addHTMLElement('HTMLDListElement')
addHTMLElement('HTMLElement')
addHTMLElement('HTMLEmbedElement')
-addHTMLElement('HTMLFieldSetElement')
+addHTMLElement('HTMLFieldSetElement', needsAbstract=['elements'])
addHTMLElement('HTMLFontElement')
addHTMLElement('HTMLFormElement')
addHTMLElement('HTMLFrameElement')
diff --git a/src/components/script/dom/bindings/codegen/CodegenRust.py b/src/components/script/dom/bindings/codegen/CodegenRust.py
index 2162d445c24..d06bfb0bc31 100644
--- a/src/components/script/dom/bindings/codegen/CodegenRust.py
+++ b/src/components/script/dom/bindings/codegen/CodegenRust.py
@@ -184,7 +184,7 @@ class CGMethodCall(CGThing):
if requiredArgs > 0:
code = (
- "if (argc < %d) {\n"
+ "if argc < %d {\n"
" return 0; //XXXjdm throw exception\n"
" //return ThrowErrorMessage(cx, MSG_MISSING_ARGUMENTS, %s);\n"
"}" % (requiredArgs, methodName))
@@ -370,7 +370,7 @@ class CGMethodCall(CGThing):
overloadCGThings = []
overloadCGThings.append(
- CGGeneric("let argcount = argc.min(&%d);" %
+ CGGeneric("let argcount = cmp::min(argc, %d);" %
maxArgCount))
overloadCGThings.append(
CGSwitch("argcount",
@@ -389,7 +389,7 @@ class CGMethodCall(CGThing):
class FakeCastableDescriptor():
def __init__(self, descriptor):
self.castable = True
- self.nativeType = "*Box<%s>" % descriptor.concreteType
+ self.nativeType = "*%s" % descriptor.concreteType
self.name = descriptor.name
class FakeInterface:
def inheritanceDepth(self):
@@ -720,7 +720,7 @@ def getJSToNativeConversionTemplate(type, descriptorProvider, failureCode=None,
return handleDefault(conversionCode,
"${declName}.SetNull()")
- value = "str::from_utf8(data).to_owned()"
+ value = "str::from_utf8(data).unwrap().to_owned()"
if type.nullable():
value = "Some(%s)" % value
@@ -993,7 +993,7 @@ def instantiateJSToNativeConversionTemplate(templateTuple, replacements,
conversion = CGList(
[CGGeneric(
- string.Template("if (${index} < ${argc}) {").substitute(
+ string.Template("if ${index} < ${argc} {").substitute(
argcAndIndex
)),
declConstruct,
@@ -1132,7 +1132,7 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode,
raise TypeError("We don't support nullable enumerated return types "
"yet")
return ("""assert!((%(result)s as uint) < %(strings)s.len());
-let %(resultStr)s: *JSString = JS_NewStringCopyN(cx, ptr::to_unsafe_ptr(&%(strings)s[%(result)s as u32].value[0]) as *i8, %(strings)s[%(result)s as u32].length as libc::size_t);
+let %(resultStr)s: *JSString = JS_NewStringCopyN(cx, &%(strings)s[%(result)s as u32].value[0] as *i8, %(strings)s[%(result)s as u32].length as libc::size_t);
if %(resultStr)s.is_null() {
return 0;
}
@@ -1225,36 +1225,36 @@ def memberIsCreator(member):
def getRetvalDeclarationForType(returnType, descriptorProvider):
if returnType is None or returnType.isVoid():
# Nothing to declare
- return None, False
+ return None
if returnType.isPrimitive() and returnType.tag() in builtinNames:
result = CGGeneric(builtinNames[returnType.tag()])
if returnType.nullable():
result = CGWrapper(result, pre="Option<", post=">")
- return result, False
+ return result
if returnType.isString():
result = CGGeneric("DOMString")
if returnType.nullable():
result = CGWrapper(result, pre="Option<", post=">")
- return result, False
+ return result
if returnType.isEnum():
if returnType.nullable():
raise TypeError("We don't support nullable enum return values")
- return CGGeneric(returnType.inner.identifier.name), False
+ return CGGeneric(returnType.inner.identifier.name)
if returnType.isGeckoInterface():
descriptor = descriptorProvider.getDescriptor(
returnType.unroll().inner.identifier.name)
result = CGGeneric(descriptor.nativeType)
if returnType.nullable():
result = CGWrapper(result, pre="Option<", post=">")
- return result, False
+ return result
if returnType.isCallback():
# XXXbz we're going to assume that callback types are always
# nullable for now.
- return CGGeneric("*JSObject"), False
+ return CGGeneric("*JSObject")
if returnType.isAny():
- return CGGeneric("JSVal"), False
+ return CGGeneric("JSVal")
if returnType.isObject() or returnType.isSpiderMonkeyInterface():
- return CGGeneric("*JSObject"), False
+ return CGGeneric("*JSObject")
if returnType.isSequence():
raise TypeError("We don't support sequence return values")
@@ -1641,7 +1641,9 @@ class CGImports(CGWrapper):
# sometimes produces two 'break's in a row. See for example
# CallbackMember.getArgConversions.
'unreachable_code',
+ 'non_camel_case_types',
'non_uppercase_statics',
+ 'unnecessary_parens',
'unused_imports',
'unused_variable',
'unused_unsafe',
@@ -1688,11 +1690,11 @@ class CGNamespace(CGWrapper):
def DOMClass(descriptor):
protoList = ['PrototypeList::id::' + proto for proto in descriptor.prototypeChain]
- # Pad out the list to the right length with _ID_Count so we
- # guarantee that all the lists are the same length. _ID_Count
+ # Pad out the list to the right length with IDCount so we
+ # guarantee that all the lists are the same length. IDCount
# is never the ID of any prototype, so it's safe to use as
# padding.
- protoList.extend(['PrototypeList::id::_ID_Count'] * (descriptor.config.maxProtoChainLength - len(protoList)))
+ protoList.extend(['PrototypeList::id::IDCount'] * (descriptor.config.maxProtoChainLength - len(protoList)))
prototypeChainString = ', '.join(protoList)
return """DOMClass {
interface_chain: [ %s ],
@@ -2066,7 +2068,7 @@ def CreateBindingJSObject(descriptor, parent=None):
let handler = js_info.get().get_ref().dom_static.proxy_handlers.get(&(PrototypeList::id::%s as uint));
""" % descriptor.name
create += handler + """ let obj = NewProxyObject(aCx, *handler,
- ptr::to_unsafe_ptr(&PrivateValue(squirrel_away_unique(aObject) as *libc::c_void)),
+ &PrivateValue(squirrel_away_unboxed(aObject) as *libc::c_void),
proto, %s,
ptr::null(), ptr::null());
if obj.is_null() {
@@ -2084,7 +2086,7 @@ def CreateBindingJSObject(descriptor, parent=None):
}
JS_SetReservedSlot(obj, DOM_OBJECT_SLOT as u32,
- PrivateValue(squirrel_away_unique(aObject) as *libc::c_void));
+ PrivateValue(squirrel_away_unboxed(aObject) as *libc::c_void));
"""
return create
@@ -2230,7 +2232,7 @@ class CGCreateInterfaceObjectsMethod(CGAbstractMethod):
val = ('%(' + name + ')s') % self.properties.variableNames(False)
if val == "ptr::null()":
return val
- return "ptr::to_unsafe_ptr(&%s[0])" % val
+ return "&%s[0]" % val
call = """return CreateInterfaceObjects2(aCx, aGlobal, aReceiver, parentProto,
%s, %s, %d,
@@ -2376,7 +2378,7 @@ class CGDefineDOMInterfaceMethod(CGAbstractMethod):
trace: %s
};
js_info.dom_static.proxy_handlers.insert(PrototypeList::id::%s as uint,
- CreateProxyHandler(ptr::to_unsafe_ptr(&traps), ptr::to_unsafe_ptr(&Class) as *libc::c_void));
+ CreateProxyHandler(&traps, cast::transmute(&Class)));
""" % (FINALIZE_HOOK_NAME,
('Some(%s)' % TRACE_HOOK_NAME),
@@ -2388,7 +2390,7 @@ class CGDefineDOMInterfaceMethod(CGAbstractMethod):
body = "" #XXXjdm xray stuff isn't necessary yet
return (body + """ let cx = js_info.js_context.borrow().ptr;
- let receiver = js_info.js_compartment.borrow().global_obj.borrow().ptr;
+ let receiver = js_info.js_compartment.borrow().global_obj;
let global: *JSObject = JS_GetGlobalForObject(cx, receiver);
return %s(cx, global, receiver).is_not_null();""" % (getter))
@@ -2420,8 +2422,7 @@ class CGCallGenerator(CGThing):
isFallible = errorReport is not None
- (result, resultOutParam) = getRetvalDeclarationForType(returnType,
- descriptorProvider)
+ result = getRetvalDeclarationForType(returnType, descriptorProvider)
args = CGList([CGGeneric(arg) for arg in argsPre], ", ")
for (a, name) in arguments:
@@ -2437,10 +2438,6 @@ class CGCallGenerator(CGThing):
name = "&" + name
args.append(CGGeneric(name))
- # Return values that go in outparams go here
- if resultOutParam:
- args.append(CGGeneric("result"))
-
needsCx = (typeNeedsCx(returnType, True) or
any(typeNeedsCx(a.type) for (a, _) in arguments))
@@ -2467,17 +2464,17 @@ class CGCallGenerator(CGThing):
if isFallible:
call = CGWrapper(call, pre="result_fallible = ")
- elif result is not None and not resultOutParam:
+ elif result is not None:
call = CGWrapper(call, pre="result = ")
call = CGWrapper(call)
self.cgRoot.append(call)
if isFallible:
- self.cgRoot.append(CGGeneric("if (result_fallible.is_err()) {"))
+ self.cgRoot.append(CGGeneric("if result_fallible.is_err() {"))
self.cgRoot.append(CGIndenter(errorReport))
self.cgRoot.append(CGGeneric("}"))
- if result is not None and not resultOutParam:
+ if result is not None:
self.cgRoot.append(CGGeneric("result = result_fallible.unwrap();"))
def define(self):
@@ -2698,7 +2695,7 @@ class CGAbstractBindingMethod(CGAbstractExternMethod):
" return false as JSBool;\n"
"}\n"
"\n"
- "let this: *Box<%s>;" % self.descriptor.concreteType))
+ "let this: *%s;" % self.descriptor.concreteType))
def generate_code(self):
assert(False) # Override me
@@ -2726,7 +2723,7 @@ class CGSpecializedMethod(CGAbstractExternMethod):
self.method = method
name = method.identifier.name
args = [Argument('*JSContext', 'cx'), Argument('JSHandleObject', 'obj'),
- Argument('*mut Box<%s>' % descriptor.concreteType, 'this'),
+ Argument('*mut %s' % descriptor.concreteType, 'this'),
Argument('libc::c_uint', 'argc'), Argument('*mut JSVal', 'vp')]
CGAbstractExternMethod.__init__(self, descriptor, name, 'JSBool', args)
@@ -2737,13 +2734,13 @@ class CGSpecializedMethod(CGAbstractExternMethod):
argsPre = []
if name in self.descriptor.needsAbstract:
abstractName = re.sub(r'<\w+>', '', self.descriptor.nativeType)
- extraPre = ' let mut abstract_this = %s::from_box(this);\n' % abstractName
+ extraPre = ' let mut abstract_this = %s::from_raw(this);\n' % abstractName
argsPre = ['&mut abstract_this']
return CGWrapper(CGMethodCall(argsPre, nativeName, self.method.isStatic(),
self.descriptor, self.method),
pre=extraPre +
- " let obj = (*obj.unnamed);\n" +
- " let this = &mut (*this).data;\n").define()
+ " let obj = *obj.unnamed;\n" +
+ " let this = &mut *this;\n").define()
class CGGenericGetter(CGAbstractBindingMethod):
"""
@@ -2781,7 +2778,7 @@ class CGSpecializedGetter(CGAbstractExternMethod):
name = 'get_' + attr.identifier.name
args = [ Argument('*JSContext', 'cx'),
Argument('JSHandleObject', 'obj'),
- Argument('*mut Box<%s>' % descriptor.concreteType, 'this'),
+ Argument('*mut %s' % descriptor.concreteType, 'this'),
Argument('*mut JSVal', 'vp') ]
CGAbstractExternMethod.__init__(self, descriptor, name, "JSBool", args)
@@ -2790,22 +2787,20 @@ class CGSpecializedGetter(CGAbstractExternMethod):
nativeName = MakeNativeName(name)
extraPre = ''
argsPre = []
- (_, resultOutParam) = getRetvalDeclarationForType(self.attr.type,
- self.descriptor)
infallible = ('infallible' in
self.descriptor.getExtendedAttributes(self.attr,
getter=True))
if name in self.descriptor.needsAbstract:
abstractName = re.sub(r'<\w+>', '', self.descriptor.nativeType)
- extraPre = ' let mut abstract_this = %s::from_box(this);\n' % abstractName
+ extraPre = ' let mut abstract_this = %s::from_raw(this);\n' % abstractName
argsPre = ['&mut abstract_this']
- if resultOutParam or self.attr.type.nullable() or not infallible:
+ if self.attr.type.nullable() or not infallible:
nativeName = "Get" + nativeName
return CGWrapper(CGIndenter(CGGetterCall(argsPre, self.attr.type, nativeName,
self.descriptor, self.attr)),
pre=extraPre +
- " let obj = (*obj.unnamed);\n" +
- " let this = &mut (*this).data;\n").define()
+ " let obj = *obj.unnamed;\n" +
+ " let this = &mut *this;\n").define()
class CGGenericSetter(CGAbstractBindingMethod):
"""
@@ -2849,7 +2844,7 @@ class CGSpecializedSetter(CGAbstractExternMethod):
name = 'set_' + attr.identifier.name
args = [ Argument('*JSContext', 'cx'),
Argument('JSHandleObject', 'obj'),
- Argument('*mut Box<%s>' % descriptor.concreteType, 'this'),
+ Argument('*mut %s' % descriptor.concreteType, 'this'),
Argument('*mut JSVal', 'argv')]
CGAbstractExternMethod.__init__(self, descriptor, name, "JSBool", args)
@@ -2860,13 +2855,13 @@ class CGSpecializedSetter(CGAbstractExternMethod):
extraPre = ''
if name in self.descriptor.needsAbstract:
abstractName = re.sub(r'<\w+>', '', self.descriptor.nativeType)
- extraPre = ' let mut abstract_this = %s::from_box(this);\n' % abstractName
+ extraPre = ' let mut abstract_this = %s::from_raw(this);\n' % abstractName
argsPre = ['&mut abstract_this']
return CGWrapper(CGIndenter(CGSetterCall(argsPre, self.attr.type, nativeName,
self.descriptor, self.attr)),
pre=extraPre +
- " let obj = (*obj.unnamed);\n" +
- " let this = &mut (*this).data;\n").define()
+ " let obj = *obj.unnamed;\n" +
+ " let this = &mut *this;\n").define()
def infallibleForMember(member, type, descriptorProvider):
"""
@@ -2977,6 +2972,34 @@ class CGEnum(CGThing):
""" % (",\n ".join(map(getEnumValueName, self.enum.values())),
",\n ".join(['EnumEntry {value: &"' + val + '", length: ' + str(len(val)) + '}' for val in self.enum.values()]))
+
+def convertConstIDLValueToRust(value):
+ tag = value.type.tag()
+ if tag in [IDLType.Tags.int8, IDLType.Tags.uint8,
+ IDLType.Tags.int16, IDLType.Tags.uint16,
+ IDLType.Tags.int32, IDLType.Tags.uint32,
+ IDLType.Tags.int64, IDLType.Tags.uint64,
+ IDLType.Tags.float, IDLType.Tags.double]:
+ return str(value.value)
+
+ if tag == IDLType.Tags.bool:
+ return toStringBool(value.value)
+
+ raise TypeError("Const value of unhandled type: " + value.type)
+
+class CGConstant(CGThing):
+ def __init__(self, constants):
+ CGThing.__init__(self)
+ self.constants = constants
+
+ def define(self):
+ def stringDecl(const):
+ name = const.identifier.name
+ value = convertConstIDLValueToRust(const.value)
+ return CGGeneric("pub static %s: %s = %s;\n" % (name, builtinNames[const.value.type.tag()], value))
+
+ return CGIndenter(CGList(stringDecl(m) for m in self.constants)).define()
+
def getUnionAccessorSignatureType(type, descriptorProvider):
"""
Returns the types that are used in the getter and setter signatures for
@@ -3870,8 +3893,8 @@ class CGProxyUnwrap(CGAbstractMethod):
obj = js::UnwrapObject(obj);
}*/
//MOZ_ASSERT(IsProxy(obj));
- let box_: *Box<%s> = cast::transmute(GetProxyPrivate(obj).to_private());
- return ptr::to_unsafe_ptr(&(*box_).data);""" % (self.descriptor.concreteType)
+ let box_: *%s = cast::transmute(GetProxyPrivate(obj).to_private());
+ return box_;""" % (self.descriptor.concreteType)
class CGDOMJSProxyHandler_getOwnPropertyDescriptor(CGAbstractExternMethod):
def __init__(self, descriptor):
@@ -3892,7 +3915,7 @@ class CGDOMJSProxyHandler_getOwnPropertyDescriptor(CGAbstractExternMethod):
if indexedGetter:
readonly = toStringBool(self.descriptor.operations['IndexedSetter'] is None)
fillDescriptor = "FillPropertyDescriptor(&mut *desc, proxy, %s);\nreturn 1;" % readonly
- templateValues = {'jsvalRef': '(*desc).value', 'jsvalPtr': 'ptr::to_mut_unsafe_ptr(&mut (*desc).value)',
+ templateValues = {'jsvalRef': '(*desc).value', 'jsvalPtr': '&mut (*desc).value',
'obj': 'proxy', 'successCode': fillDescriptor}
get = ("if index.is_some() {\n" +
" let index = index.unwrap();\n" +
@@ -3934,7 +3957,7 @@ class CGDOMJSProxyHandler_getOwnPropertyDescriptor(CGAbstractExternMethod):
if namedGetter:
readonly = toStringBool(self.descriptor.operations['NamedSetter'] is None)
fillDescriptor = "FillPropertyDescriptor(&mut *desc, proxy, %s);\nreturn 1;" % readonly
- templateValues = {'jsvalRef': '(*desc).value', 'jsvalPtr': 'ptr::to_unsafe_ptr(&(*desc).value)',
+ templateValues = {'jsvalRef': '(*desc).value', 'jsvalPtr': '&mut(*desc).value',
'obj': 'proxy', 'successCode': fillDescriptor}
# Once we start supporting OverrideBuiltins we need to make
# ResolveOwnProperty or EnumerateOwnProperties filter out named
@@ -4080,7 +4103,7 @@ class CGDOMJSProxyHandler_get(CGAbstractExternMethod):
getFromExpando = """let expando = GetExpandoObject(proxy);
if expando.is_not_null() {
let hasProp = 0;
- if JS_HasPropertyById(cx, expando, id, ptr::to_unsafe_ptr(&hasProp)) == 0 {
+ if JS_HasPropertyById(cx, expando, id, &hasProp) == 0 {
return 0;
}
@@ -4180,7 +4203,7 @@ class CGAbstractClassHook(CGAbstractExternMethod):
def definition_body_prologue(self):
return """
- let this: *%s = &(*unwrap::<*Box<%s>>(obj)).data;
+ let this: *%s = unwrap::<*%s>(obj);
""" % (self.descriptor.concreteType, self.descriptor.concreteType)
def definition_body(self):
@@ -4316,6 +4339,10 @@ class CGDescriptor(CGThing):
cgThings.append(CGGeneric(str(properties)))
cgThings.append(CGCreateInterfaceObjectsMethod(descriptor, properties))
+ cgThings.append(CGNamespace.build([descriptor.name + "Constants"],
+ CGConstant(m for m in descriptor.interface.members if m.isConst()),
+ public=True))
+
# Set up our Xray callbacks as needed.
if descriptor.interface.hasInterfacePrototypeObject():
if descriptor.concrete and descriptor.proxy:
@@ -4382,7 +4409,7 @@ class CGNamespacedEnum(CGThing):
entries.append(entry)
# Append a Count.
- entries.append('_' + enumName + '_Count = ' + str(len(entries)))
+ entries.append(enumName + 'Count = ' + str(len(entries)))
# Indent.
entries = [' ' + e for e in entries]
@@ -4512,7 +4539,7 @@ class CGDictionary(CGThing):
"\n"
" pub fn Init(&mut self, cx: *JSContext, val: JSVal) -> JSBool {\n"
" unsafe {\n"
- " if (!initedIds && !self.InitIds(cx)) {\n"
+ " if !initedIds && !self.InitIds(cx) {\n"
" return 0;\n"
" }\n"
"${initParent}"
@@ -4579,15 +4606,15 @@ class CGDictionary(CGThing):
if True: #XXXjdm hack until 'static mut' exists for global jsids
propName = member.identifier.name
- propCheck = ('"%s".to_c_str().with_ref(|s| { JS_HasProperty(cx, val.to_object(), s, ptr::to_unsafe_ptr(&found)) })' %
+ propCheck = ('"%s".to_c_str().with_ref(|s| { JS_HasProperty(cx, val.to_object(), s, &found) })' %
propName)
- propGet = ('"%s".to_c_str().with_ref(|s| { JS_GetProperty(cx, val.to_object(), s, ptr::to_unsafe_ptr(&temp)) })' %
+ propGet = ('"%s".to_c_str().with_ref(|s| { JS_GetProperty(cx, val.to_object(), s, &temp) })' %
propName)
else:
propId = self.makeIdName(member.identifier.name);
- propCheck = ("JS_HasPropertyById(cx, val.to_object(), %s, ptr::to_unsafe_ptr(&found))" %
+ propCheck = ("JS_HasPropertyById(cx, val.to_object(), %s, &found)" %
propId)
- propGet = ("JS_GetPropertyById(cx, val.to_object(), %s, ptr::to_unsafe_ptr(&temp))" %
+ propGet = ("JS_GetPropertyById(cx, val.to_object(), %s, &temp)" %
propId)
conversionReplacements = {
@@ -4771,7 +4798,7 @@ class CGBindingRoot(CGThing):
'dom::bindings::utils::{NativePropertyHooks}',
'dom::bindings::utils::global_object_for_js_object',
'dom::bindings::utils::{Reflectable}',
- 'dom::bindings::utils::{squirrel_away_unique}',
+ 'dom::bindings::utils::{squirrel_away_unboxed}',
'dom::bindings::utils::{ThrowingConstructor, unwrap, unwrap_jsmanaged}',
'dom::bindings::utils::{unwrap_object, VoidVal, with_gc_disabled}',
'dom::bindings::utils::{with_gc_enabled, XrayResolveProperty}',
@@ -4793,12 +4820,13 @@ class CGBindingRoot(CGThing):
'servo_util::str::DOMString',
'servo_util::vec::zip_copies',
'std::cast',
+ 'std::cmp',
'std::libc',
'std::ptr',
'std::vec',
'std::str',
'std::num',
- 'std::unstable::raw::Box',
+ 'std::intrinsics::uninit',
])
# Add the auto-generated comment.
@@ -5198,7 +5226,7 @@ class CGCallback(CGClass):
# method, insert our optional argument for deciding whether the
# CallSetup should re-throw exceptions on aRv.
args.append(Argument("ExceptionHandling", "aExceptionHandling",
- "eReportExceptions"))
+ "ReportExceptions"))
args[0] = Argument('&' + args[0].argType, args[0].name, args[0].default)
method.args[2] = args[0]
@@ -5490,7 +5518,7 @@ class CallbackMember(CGNativeMember):
args.append(Argument("JSCompartment*", "aCompartment", "nullptr"))
else:
args.append(Argument("ExceptionHandling", "aExceptionHandling",
- "eReportExceptions"))
+ "ReportExceptions"))
return args
# We want to allow the caller to pass in a "this" object, as
# well as a JSContext.
@@ -5505,7 +5533,7 @@ class CallbackMember(CGNativeMember):
if self.rethrowContentException:
# getArgs doesn't add the aExceptionHandling argument but does add
# aCompartment for us.
- callSetup += ", eRethrowContentExceptions, aCompartment"
+ callSetup += ", RethrowContentExceptions, aCompartment"
else:
callSetup += ", aExceptionHandling"
callSetup += ");"
@@ -5742,7 +5770,7 @@ class GlobalGenRoots():
CGGeneric("use dom::types::*;\n"),
CGGeneric("use dom::bindings::js::JS;\n"),
CGGeneric("use dom::bindings::trace::Traceable;\n"),
- CGGeneric("use extra::serialize::{Encodable, Encoder};\n"),
+ CGGeneric("use serialize::{Encodable, Encoder};\n"),
CGGeneric("use js::jsapi::JSTracer;\n\n")]
for descriptor in descriptors:
name = descriptor.name
diff --git a/src/components/script/dom/bindings/error.rs b/src/components/script/dom/bindings/error.rs
index 8ea949b28f6..da30f40588b 100644
--- a/src/components/script/dom/bindings/error.rs
+++ b/src/components/script/dom/bindings/error.rs
@@ -7,7 +7,7 @@ use js::jsapi::{JS_IsExceptionPending};
use js::glue::{ReportError};
-#[deriving(ToStr)]
+#[deriving(Show)]
pub enum Error {
FailureUnknown,
NotFound,
diff --git a/src/components/script/dom/bindings/js.rs b/src/components/script/dom/bindings/js.rs
index 9f8e44ba06f..69758f2980a 100644
--- a/src/components/script/dom/bindings/js.rs
+++ b/src/components/script/dom/bindings/js.rs
@@ -9,7 +9,6 @@ use layout_interface::TrustedNodeAddress;
use std::cast;
use std::cell::RefCell;
-use std::unstable::raw::Box;
pub struct JS<T> {
priv ptr: RefCell<*mut T>
@@ -50,13 +49,6 @@ impl<T: Reflectable> JS<T> {
}
- pub unsafe fn from_box(box_: *mut Box<T>) -> JS<T> {
- let raw: *mut T = &mut (*box_).data;
- JS {
- ptr: RefCell::new(raw)
- }
- }
-
pub unsafe fn from_trusted_node_address(inner: TrustedNodeAddress) -> JS<T> {
JS {
ptr: RefCell::new(inner as *mut T)
diff --git a/src/components/script/dom/bindings/proxyhandler.rs b/src/components/script/dom/bindings/proxyhandler.rs
index aaf75a7bc7a..81c36d639ad 100644
--- a/src/components/script/dom/bindings/proxyhandler.rs
+++ b/src/components/script/dom/bindings/proxyhandler.rs
@@ -19,12 +19,10 @@ use std::ptr;
use std::str;
use std::mem::size_of;
-type c_bool = libc::c_int;
-
static JSPROXYSLOT_EXPANDO: u32 = 0;
pub extern fn getPropertyDescriptor(cx: *JSContext, proxy: *JSObject, id: jsid,
- set: c_bool, desc: *mut JSPropertyDescriptor) -> c_bool {
+ set: libc::c_int, desc: *mut JSPropertyDescriptor) -> libc::c_int {
unsafe {
let handler = GetProxyHandler(proxy);
if InvokeGetOwnPropertyDescriptor(handler, cx, proxy, id, set, desc) == 0 {
diff --git a/src/components/script/dom/bindings/trace.rs b/src/components/script/dom/bindings/trace.rs
index 342c3110f5d..1cedf246728 100644
--- a/src/components/script/dom/bindings/trace.rs
+++ b/src/components/script/dom/bindings/trace.rs
@@ -11,7 +11,7 @@ use std::cast;
use std::libc;
use std::ptr;
use std::ptr::null;
-use extra::serialize::{Encodable, Encoder};
+use serialize::{Encodable, Encoder};
// IMPORTANT: We rely on the fact that we never attempt to encode DOM objects using
// any encoder but JSTracer. Since we derive trace hooks automatically,
diff --git a/src/components/script/dom/bindings/utils.rs b/src/components/script/dom/bindings/utils.rs
index 54e518fcc97..e7385fc1ddd 100644
--- a/src/components/script/dom/bindings/utils.rs
+++ b/src/components/script/dom/bindings/utils.rs
@@ -8,16 +8,15 @@ use dom::bindings::js::JS;
use dom::window;
use servo_util::str::DOMString;
+use collections::hashmap::HashMap;
use std::libc::c_uint;
use std::cast;
use std::cmp::Eq;
-use std::hashmap::HashMap;
use std::libc;
use std::ptr;
use std::ptr::null;
use std::str;
use std::vec;
-use std::unstable::raw::Box;
use js::glue::*;
use js::glue::{js_IsObjectProxyClass, js_IsFunctionProxyClass, IsProxyHandlerFamily};
use js::jsapi::{JS_AlreadyHasOwnProperty, JS_NewFunction};
@@ -121,10 +120,10 @@ pub fn unwrap_object<T>(obj: *JSObject, proto_id: PrototypeList::id::ID, proto_d
pub fn unwrap_jsmanaged<T: Reflectable>(obj: *JSObject,
proto_id: PrototypeList::id::ID,
proto_depth: uint) -> Result<JS<T>, ()> {
- let result: Result<*mut Box<T>, ()> = unwrap_object(obj, proto_id, proto_depth);
+ let result: Result<*mut T, ()> = unwrap_object(obj, proto_id, proto_depth);
result.map(|unwrapped| {
unsafe {
- JS::from_box(unwrapped)
+ JS::from_raw(unwrapped)
}
})
}
@@ -136,10 +135,6 @@ pub fn unwrap_value<T>(val: *JSVal, proto_id: PrototypeList::id::ID, proto_depth
}
}
-pub unsafe fn squirrel_away_unique<T>(x: ~T) -> *Box<T> {
- cast::transmute(x)
-}
-
pub unsafe fn squirrel_away_unboxed<T>(x: ~T) -> *T {
cast::transmute(x)
}
@@ -149,7 +144,7 @@ pub fn jsstring_to_str(cx: *JSContext, s: *JSString) -> DOMString {
let length = 0;
let chars = JS_GetStringCharsAndLength(cx, s, &length);
vec::raw::buf_as_slice(chars, length as uint, |char_vec| {
- str::from_utf16(char_vec)
+ str::from_utf16(char_vec).unwrap()
})
}
}
@@ -412,7 +407,7 @@ pub extern fn ThrowingConstructor(_cx: *JSContext, _argc: c_uint, _vp: *mut JSVa
}
pub fn initialize_global(global: *JSObject) {
- let protoArray = ~([0 as *JSObject, ..PrototypeList::id::_ID_Count as uint]);
+ let protoArray = ~([0 as *JSObject, ..PrototypeList::id::IDCount as uint]);
unsafe {
let box_ = squirrel_away_unboxed(protoArray);
JS_SetReservedSlot(global,
@@ -437,7 +432,6 @@ pub fn reflect_dom_object<T: Reflectable>
#[deriving(Eq)]
pub struct Reflector {
object: *JSObject,
- force_box_layout: @int,
}
impl Reflector {
@@ -455,7 +449,6 @@ impl Reflector {
pub fn new() -> Reflector {
Reflector {
object: ptr::null(),
- force_box_layout: @1,
}
}
}
@@ -470,7 +463,7 @@ pub fn GetPropertyOnPrototype(cx: *JSContext, proxy: *JSObject, id: jsid, found:
return true;
}
let hasProp = 0;
- if JS_HasPropertyById(cx, proto, id, ptr::to_unsafe_ptr(&hasProp)) == 0 {
+ if JS_HasPropertyById(cx, proto, id, &hasProp) == 0 {
return false;
}
*found = hasProp != 0;
@@ -651,8 +644,8 @@ pub fn global_object_for_js_object(obj: *JSObject) -> JS<window::Window> {
let clasp = JS_GetClass(global);
assert!(((*clasp).flags & (JSCLASS_IS_DOMJSCLASS | JSCLASS_IS_GLOBAL)) != 0);
// FIXME(jdm): Either don't hardcode or sanity assert prototype stuff.
- match unwrap_object::<*mut Box<window::Window>>(global, PrototypeList::id::Window, 1) {
- Ok(win) => JS::from_box(win),
+ match unwrap_object::<*mut window::Window>(global, PrototypeList::id::Window, 1) {
+ Ok(win) => JS::from_raw(win),
Err(_) => fail!("found DOM global that doesn't unwrap to Window"),
}
}
diff --git a/src/components/script/dom/document.rs b/src/components/script/dom/document.rs
index 07660e30e88..3cf1d35459a 100644
--- a/src/components/script/dom/document.rs
+++ b/src/components/script/dom/document.rs
@@ -38,12 +38,12 @@ use layout_interface::{DocumentDamageLevel, ContentChangedDocumentDamage};
use servo_util::namespace::{Namespace, Null};
use servo_util::str::DOMString;
+use collections::hashmap::HashMap;
use extra::url::{Url, from_str};
use js::jsapi::{JSObject, JSContext};
use std::ascii::StrAsciiExt;
-use std::hashmap::HashMap;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
#[deriving(Eq,Encodable)]
pub enum IsHTMLDocument {
@@ -61,7 +61,7 @@ pub struct Document {
content_type: DOMString,
encoding_name: DOMString,
is_html_document: bool,
- extra: Untraceable,
+ priv extra: Untraceable,
}
struct Untraceable {
@@ -139,6 +139,12 @@ impl Document {
}
impl Document {
+ pub fn url<'a>(&'a self) -> &'a Url {
+ &self.extra.url
+ }
+}
+
+impl Document {
// http://dom.spec.whatwg.org/#dom-document
pub fn Constructor(owner: &JS<Window>) -> Fallible<JS<Document>> {
Ok(Document::new(owner, None, NonHTMLDocument, None))
@@ -166,7 +172,7 @@ impl Document {
// http://dom.spec.whatwg.org/#dom-document-url
pub fn URL(&self) -> DOMString {
- self.extra.url.to_str()
+ self.url().to_str()
}
// http://dom.spec.whatwg.org/#dom-document-documenturi
@@ -182,6 +188,10 @@ impl Document {
}
}
+ pub fn quirks_mode(&self) -> QuirksMode {
+ self.extra.quirks_mode
+ }
+
pub fn set_quirks_mode(&mut self, mode: QuirksMode) {
self.extra.quirks_mode = mode;
}
@@ -331,17 +341,17 @@ impl Document {
match title_node {
Some(ref mut title_node) => {
for mut title_child in title_node.children() {
- title_node.RemoveChild(&mut title_child);
+ assert!(title_node.RemoveChild(&mut title_child).is_ok());
}
let new_text = self.CreateTextNode(abstract_self, title.clone());
- title_node.AppendChild(&mut NodeCast::from(&new_text));
+ assert!(title_node.AppendChild(&mut NodeCast::from(&new_text)).is_ok());
},
None => {
let mut new_title: JS<Node> =
NodeCast::from(&HTMLTitleElement::new(~"title", abstract_self));
let new_text = self.CreateTextNode(abstract_self, title.clone());
- new_title.AppendChild(&mut NodeCast::from(&new_text));
- head.AppendChild(&mut new_title);
+ assert!(new_title.AppendChild(&mut NodeCast::from(&new_text)).is_ok());
+ assert!(head.AppendChild(&mut new_title).is_ok());
},
}
});
@@ -408,9 +418,9 @@ impl Document {
match old_body {
Some(child) => {
let mut child: JS<Node> = NodeCast::from(&child);
- root.ReplaceChild(&mut new_body, &mut child)
+ assert!(root.ReplaceChild(&mut new_body, &mut child).is_ok())
}
- None => root.AppendChild(&mut new_body)
+ None => assert!(root.AppendChild(&mut new_body).is_ok())
};
}
}
@@ -425,7 +435,7 @@ impl Document {
}
let element: JS<Element> = ElementCast::to(node);
- element.get().get_attribute(Null, "name").map_default(false, |attr| {
+ element.get().get_attribute(Null, "name").map_or(false, |attr| {
attr.get().value_ref() == name
})
})
diff --git a/src/components/script/dom/domexception.rs b/src/components/script/dom/domexception.rs
index 9d8142ac938..fe439a944e2 100644
--- a/src/components/script/dom/domexception.rs
+++ b/src/components/script/dom/domexception.rs
@@ -3,34 +3,35 @@
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
use dom::bindings::codegen::DOMExceptionBinding;
+use dom::bindings::codegen::DOMExceptionBinding::DOMExceptionConstants;
use dom::bindings::js::JS;
use dom::bindings::utils::{Reflectable, Reflector, reflect_dom_object};
use dom::window::Window;
use servo_util::str::DOMString;
#[repr(uint)]
-#[deriving(ToStr, Encodable)]
+#[deriving(Show, Encodable)]
enum DOMErrorName {
- IndexSizeError = 1,
- HierarchyRequestError = 3,
- WrongDocumentError = 4,
- InvalidCharacterError = 5,
- NoModificationAllowedError = 7,
- NotFoundError = 8,
- NotSupportedError = 9,
- InvalidStateError = 11,
- SyntaxError = 12,
- InvalidModificationError = 13,
- NamespaceError = 14,
- InvalidAccessError = 15,
- SecurityError = 18,
- NetworkError = 19,
- AbortError = 20,
- URLMismatchError = 21,
- QuotaExceededError = 22,
- TimeoutError = 23,
- InvalidNodeTypeError = 24,
- DataCloneError = 25,
+ IndexSizeError = DOMExceptionConstants::INDEX_SIZE_ERR,
+ HierarchyRequestError = DOMExceptionConstants::HIERARCHY_REQUEST_ERR,
+ WrongDocumentError = DOMExceptionConstants::WRONG_DOCUMENT_ERR,
+ InvalidCharacterError = DOMExceptionConstants::INVALID_CHARACTER_ERR,
+ NoModificationAllowedError = DOMExceptionConstants::NO_MODIFICATION_ALLOWED_ERR,
+ NotFoundError = DOMExceptionConstants::NOT_FOUND_ERR,
+ NotSupportedError = DOMExceptionConstants::NOT_SUPPORTED_ERR,
+ InvalidStateError = DOMExceptionConstants::INVALID_STATE_ERR,
+ SyntaxError = DOMExceptionConstants::SYNTAX_ERR,
+ InvalidModificationError = DOMExceptionConstants::INVALID_MODIFICATION_ERR,
+ NamespaceError = DOMExceptionConstants::NAMESPACE_ERR,
+ InvalidAccessError = DOMExceptionConstants::INVALID_ACCESS_ERR,
+ SecurityError = DOMExceptionConstants::SECURITY_ERR,
+ NetworkError = DOMExceptionConstants::NETWORK_ERR,
+ AbortError = DOMExceptionConstants::ABORT_ERR,
+ URLMismatchError = DOMExceptionConstants::URL_MISMATCH_ERR,
+ QuotaExceededError = DOMExceptionConstants::QUOTA_EXCEEDED_ERR,
+ TimeoutError = DOMExceptionConstants::TIMEOUT_ERR,
+ InvalidNodeTypeError = DOMExceptionConstants::INVALID_NODE_TYPE_ERR,
+ DataCloneError = DOMExceptionConstants::DATA_CLONE_ERR,
EncodingError
}
diff --git a/src/components/script/dom/domimplementation.rs b/src/components/script/dom/domimplementation.rs
index 5a11d0119d4..71f63f52066 100644
--- a/src/components/script/dom/domimplementation.rs
+++ b/src/components/script/dom/domimplementation.rs
@@ -72,18 +72,18 @@ impl DOMImplementation {
{
// Step 3.
let doc_type = DocumentType::new(~"html", None, None, &doc);
- doc_node.AppendChild(&mut NodeCast::from(&doc_type));
+ assert!(doc_node.AppendChild(&mut NodeCast::from(&doc_type)).is_ok());
}
{
// Step 4.
let mut doc_html = NodeCast::from(&HTMLHtmlElement::new(~"html", &doc));
- doc_node.AppendChild(&mut doc_html);
+ assert!(doc_node.AppendChild(&mut doc_html).is_ok());
{
// Step 5.
let mut doc_head = NodeCast::from(&HTMLHeadElement::new(~"head", &doc));
- doc_html.AppendChild(&mut doc_head);
+ assert!(doc_html.AppendChild(&mut doc_head).is_ok());
// Step 6.
match title {
@@ -91,18 +91,18 @@ impl DOMImplementation {
Some(title_str) => {
// Step 6.1.
let mut doc_title = NodeCast::from(&HTMLTitleElement::new(~"title", &doc));
- doc_head.AppendChild(&mut doc_title);
+ assert!(doc_head.AppendChild(&mut doc_title).is_ok());
// Step 6.2.
let title_text = Text::new(title_str, &doc);
- doc_title.AppendChild(&mut NodeCast::from(&title_text));
+ assert!(doc_title.AppendChild(&mut NodeCast::from(&title_text)).is_ok());
}
}
}
// Step 7.
let doc_body = HTMLBodyElement::new(~"body", &doc);
- doc_html.AppendChild(&mut NodeCast::from(&doc_body));
+ assert!(doc_html.AppendChild(&mut NodeCast::from(&doc_body)).is_ok());
}
// Step 8.
diff --git a/src/components/script/dom/element.rs b/src/components/script/dom/element.rs
index 95e4e7f9af9..96f5bf8f7f4 100644
--- a/src/components/script/dom/element.rs
+++ b/src/components/script/dom/element.rs
@@ -156,6 +156,17 @@ impl Element {
self.node.owner_doc().get().is_html_document
}
+ pub unsafe fn html_element_in_html_document_for_layout(&self) -> bool {
+ if self.namespace != namespace::HTML {
+ return false
+ }
+ let owner_doc: *JS<Document> = self.node.owner_doc();
+ let owner_doc: **Document = cast::transmute::<*JS<Document>,
+ **Document>(
+ owner_doc);
+ (**owner_doc).is_html_document
+ }
+
pub fn get_attribute(&self,
namespace: Namespace,
name: &str) -> Option<JS<Attr>> {
@@ -192,9 +203,9 @@ impl Element {
let (prefix, local_name) = get_attribute_parts(name.clone());
match prefix {
Some(ref prefix_str) => {
- if (namespace == namespace::Null ||
- ("xml" == prefix_str.as_slice() && namespace != namespace::XML) ||
- ("xmlns" == prefix_str.as_slice() && namespace != namespace::XMLNS)) {
+ if namespace == namespace::Null ||
+ ("xml" == prefix_str.as_slice() && namespace != namespace::XML) ||
+ ("xmlns" == prefix_str.as_slice() && namespace != namespace::XMLNS) {
return Err(NamespaceError);
}
},
@@ -241,7 +252,7 @@ impl Element {
match local_name.as_slice() {
"style" => {
let doc = self.node.owner_doc();
- let base_url = doc.get().extra.url.clone();
+ let base_url = doc.get().url().clone();
self.style_attribute = Some(style::parse_style_attribute(value, &base_url))
}
"id" => {
@@ -249,7 +260,7 @@ impl Element {
if self_node.is_in_doc() {
// XXX: this dual declaration are workaround to avoid the compile error:
// "borrowed value does not live long enough"
- let mut doc = self.node.owner_doc();
+ let mut doc = self.node.owner_doc().clone();
let doc = doc.get_mut();
doc.register_named_element(abstract_self, value.clone());
}
@@ -318,7 +329,7 @@ impl Element {
if self_node.is_in_doc() {
// XXX: this dual declaration are workaround to avoid the compile error:
// "borrowed value does not live long enough"
- let mut doc = self.node.owner_doc();
+ let mut doc = self.node.owner_doc().clone();
let doc = doc.get_mut();
doc.unregister_named_element(old_value);
}
@@ -399,7 +410,7 @@ impl Element {
pub fn set_string_attribute(&mut self, abstract_self: &JS<Element>,
name: &str, value: DOMString) {
assert!(name == name.to_ascii_lower());
- self.set_attribute(abstract_self, Null, name.to_owned(), value);
+ assert!(self.set_attribute(abstract_self, Null, name.to_owned(), value).is_ok());
}
}
@@ -419,6 +430,16 @@ impl Element {
self.set_string_attribute(abstract_self, "id", id);
}
+ // http://dom.spec.whatwg.org/#dom-element-classname
+ pub fn ClassName(&self, _abstract_self: &JS<Element>) -> DOMString {
+ self.get_string_attribute("class")
+ }
+
+ // http://dom.spec.whatwg.org/#dom-element-classname
+ pub fn SetClassName(&mut self, abstract_self: &JS<Element>, class: DOMString) {
+ self.set_string_attribute(abstract_self, "class", class);
+ }
+
// http://dom.spec.whatwg.org/#dom-element-attributes
pub fn Attributes(&mut self, abstract_self: &JS<Element>) -> JS<AttrList> {
match self.attr_list {
diff --git a/src/components/script/dom/event.rs b/src/components/script/dom/event.rs
index 6b612b4a220..c54688626d3 100644
--- a/src/components/script/dom/event.rs
+++ b/src/components/script/dom/event.rs
@@ -3,9 +3,10 @@
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
use dom::bindings::codegen::EventBinding;
+use dom::bindings::codegen::EventBinding::EventConstants;
use dom::bindings::js::JS;
use dom::bindings::utils::{Reflectable, Reflector, reflect_dom_object};
-use dom::bindings::error::{Fallible, ErrorResult};
+use dom::bindings::error::Fallible;
use dom::eventtarget::EventTarget;
use dom::window::Window;
use servo_util::str::DOMString;
@@ -23,10 +24,10 @@ pub enum Event_ {
#[deriving(Encodable)]
pub enum EventPhase {
- Phase_None = 0,
- Phase_Capturing,
- Phase_At_Target,
- Phase_Bubbling
+ PhaseNone = EventConstants::NONE,
+ PhaseCapturing = EventConstants::CAPTURING_PHASE,
+ PhaseAtTarget = EventConstants::AT_TARGET,
+ PhaseBubbling = EventConstants::BUBBLING_PHASE,
}
#[deriving(Eq, Encodable)]
@@ -62,7 +63,7 @@ impl Event {
reflector_: Reflector::new(),
current_target: None,
target: None,
- phase: Phase_None,
+ phase: PhaseNone,
type_: ~"",
default_prevented: false,
cancelable: true,
@@ -131,12 +132,11 @@ impl Event {
pub fn InitEvent(&mut self,
type_: DOMString,
bubbles: bool,
- cancelable: bool) -> ErrorResult {
+ cancelable: bool) {
self.type_ = type_;
self.cancelable = cancelable;
self.bubbles = bubbles;
self.initialized = true;
- Ok(())
}
pub fn IsTrusted(&self) -> bool {
diff --git a/src/components/script/dom/eventdispatcher.rs b/src/components/script/dom/eventdispatcher.rs
index 699dc1f68b5..bd55cb69909 100644
--- a/src/components/script/dom/eventdispatcher.rs
+++ b/src/components/script/dom/eventdispatcher.rs
@@ -2,11 +2,11 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-use dom::bindings::callback::eReportExceptions;
+use dom::bindings::callback::ReportExceptions;
use dom::bindings::codegen::InheritTypes::{EventTargetCast, NodeCast, NodeDerived};
use dom::bindings::js::JS;
use dom::eventtarget::{Capturing, Bubbling, EventTarget};
-use dom::event::{Event, Phase_At_Target, Phase_None, Phase_Bubbling, Phase_Capturing};
+use dom::event::{Event, PhaseAtTarget, PhaseNone, PhaseBubbling, PhaseCapturing};
use dom::node::{Node, NodeHelpers};
// See http://dom.spec.whatwg.org/#concept-event-dispatch for the full dispatch algorithm
@@ -35,7 +35,7 @@ pub fn dispatch_event(target: &JS<EventTarget>,
}
}
- event.get_mut().phase = Phase_Capturing;
+ event.get_mut().phase = PhaseCapturing;
//FIXME: The "callback this value" should be currentTarget
@@ -45,7 +45,9 @@ pub fn dispatch_event(target: &JS<EventTarget>,
Some(listeners) => {
event.get_mut().current_target = Some(cur_target.clone());
for listener in listeners.iter() {
- listener.HandleEvent__(event, eReportExceptions);
+ //FIXME: this should have proper error handling, or explicitly
+ // drop the exception on the floor
+ assert!(listener.HandleEvent__(event, ReportExceptions).is_ok());
if event.get().stop_immediate {
break;
@@ -66,14 +68,16 @@ pub fn dispatch_event(target: &JS<EventTarget>,
if !event.get().stop_propagation {
{
let event = event.get_mut();
- event.phase = Phase_At_Target;
+ event.phase = PhaseAtTarget;
event.current_target = Some(target.clone());
}
let opt_listeners = target.get().get_listeners(type_);
for listeners in opt_listeners.iter() {
for listener in listeners.iter() {
- listener.HandleEvent__(event, eReportExceptions);
+ //FIXME: this should have proper error handling, or explicitly drop the
+ // exception on the floor.
+ assert!(listener.HandleEvent__(event, ReportExceptions).is_ok());
if event.get().stop_immediate {
break;
}
@@ -83,14 +87,16 @@ pub fn dispatch_event(target: &JS<EventTarget>,
/* bubbling */
if event.get().bubbles && !event.get().stop_propagation {
- event.get_mut().phase = Phase_Bubbling;
+ event.get_mut().phase = PhaseBubbling;
for cur_target in chain.iter() {
let stopped = match cur_target.get().get_listeners_for(type_, Bubbling) {
Some(listeners) => {
event.get_mut().current_target = Some(cur_target.clone());
for listener in listeners.iter() {
- listener.HandleEvent__(event, eReportExceptions);
+ //FIXME: this should have proper error handling or explicitly
+ // drop exceptions on the floor.
+ assert!(listener.HandleEvent__(event, ReportExceptions).is_ok());
if event.get().stop_immediate {
break;
@@ -109,7 +115,7 @@ pub fn dispatch_event(target: &JS<EventTarget>,
let event = event.get_mut();
event.dispatching = false;
- event.phase = Phase_None;
+ event.phase = PhaseNone;
event.current_target = None;
!event.DefaultPrevented()
diff --git a/src/components/script/dom/eventtarget.rs b/src/components/script/dom/eventtarget.rs
index 5b4d2d52412..a1a3a9d7514 100644
--- a/src/components/script/dom/eventtarget.rs
+++ b/src/components/script/dom/eventtarget.rs
@@ -11,7 +11,7 @@ use dom::eventdispatcher::dispatch_event;
use dom::node::NodeTypeId;
use servo_util::str::DOMString;
-use std::hashmap::HashMap;
+use collections::hashmap::HashMap;
#[deriving(Eq,Encodable)]
pub enum ListenerPhase {
diff --git a/src/components/script/dom/formdata.rs b/src/components/script/dom/formdata.rs
index bd4c7a03d6e..ac6cdac403e 100644
--- a/src/components/script/dom/formdata.rs
+++ b/src/components/script/dom/formdata.rs
@@ -11,7 +11,7 @@ use dom::htmlformelement::HTMLFormElement;
use dom::window::Window;
use servo_util::str::DOMString;
-use std::hashmap::HashMap;
+use collections::hashmap::HashMap;
#[deriving(Encodable)]
enum FormDatum {
diff --git a/src/components/script/dom/htmlelement.rs b/src/components/script/dom/htmlelement.rs
index 8464d23aec0..f8a1cd96a9b 100644
--- a/src/components/script/dom/htmlelement.rs
+++ b/src/components/script/dom/htmlelement.rs
@@ -140,13 +140,6 @@ impl HTMLElement {
Ok(())
}
- pub fn ClassName(&self) -> DOMString {
- ~""
- }
-
- pub fn SetClassName(&self, _class: DOMString) {
- }
-
pub fn GetOffsetParent(&self) -> Option<JS<Element>> {
None
}
diff --git a/src/components/script/dom/htmlfieldsetelement.rs b/src/components/script/dom/htmlfieldsetelement.rs
index 4dec639d041..5bbd13c2b79 100644
--- a/src/components/script/dom/htmlfieldsetelement.rs
+++ b/src/components/script/dom/htmlfieldsetelement.rs
@@ -3,16 +3,16 @@
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
use dom::bindings::codegen::HTMLFieldSetElementBinding;
-use dom::bindings::codegen::InheritTypes::HTMLFieldSetElementDerived;
+use dom::bindings::codegen::InheritTypes::{ElementCast, HTMLFieldSetElementDerived, NodeCast};
use dom::bindings::js::JS;
use dom::bindings::error::ErrorResult;
use dom::document::Document;
-use dom::element::HTMLFieldSetElementTypeId;
+use dom::element::{Element, HTMLFieldSetElementTypeId};
use dom::eventtarget::{EventTarget, NodeTargetTypeId};
use dom::htmlformelement::HTMLFormElement;
use dom::htmlcollection::HTMLCollection;
use dom::htmlelement::HTMLElement;
-use dom::node::{Node, ElementNodeTypeId};
+use dom::node::{Node, ElementNodeTypeId, window_from_node};
use dom::validitystate::ValidityState;
use servo_util::str::DOMString;
@@ -68,11 +68,12 @@ impl HTMLFieldSetElement {
~""
}
- pub fn Elements(&self) -> JS<HTMLCollection> {
- // FIXME: https://github.com/mozilla/servo/issues/1843
- let doc = self.htmlelement.element.node.owner_doc();
- let doc = doc.get();
- HTMLCollection::new(&doc.window, ~[])
+ pub fn Elements(&self, abstract_self: &JS<HTMLFieldSetElement>) -> JS<HTMLCollection> {
+ let node: JS<Node> = NodeCast::from(abstract_self);
+ let element: JS<Element> = ElementCast::from(abstract_self);
+ let window = &window_from_node(&node);
+ let listed_elements = ["button", "fieldset", "input", "keygen", "object", "output", "select", "textarea"];
+ HTMLCollection::create(window, &node, |elem| *elem != element && listed_elements.iter().any(|&tag_name| tag_name == elem.get().tag_name))
}
pub fn WillValidate(&self) -> bool {
diff --git a/src/components/script/dom/htmliframeelement.rs b/src/components/script/dom/htmliframeelement.rs
index 160ecc6c175..5098972ec15 100644
--- a/src/components/script/dom/htmliframeelement.rs
+++ b/src/components/script/dom/htmliframeelement.rs
@@ -15,9 +15,9 @@ use dom::windowproxy::WindowProxy;
use servo_util::str::DOMString;
use extra::url::Url;
+use serialize::{Encoder, Encodable};
use servo_msg::constellation_msg::{PipelineId, SubpageId};
use std::ascii::StrAsciiExt;
-use extra::serialize::{Encoder, Encodable};
enum SandboxAllowance {
AllowNothing = 0x00,
@@ -32,7 +32,7 @@ enum SandboxAllowance {
#[deriving(Encodable)]
pub struct HTMLIFrameElement {
htmlelement: HTMLElement,
- extra: Untraceable,
+ priv extra: Untraceable,
size: Option<IFrameSize>,
sandbox: Option<u8>
}
@@ -65,6 +65,10 @@ impl HTMLIFrameElement {
pub fn is_sandboxed(&self) -> bool {
self.sandbox.is_some()
}
+
+ pub fn set_frame(&mut self, frame: Url) {
+ self.extra.frame = Some(frame);
+ }
}
impl HTMLIFrameElement {
diff --git a/src/components/script/dom/htmlimageelement.rs b/src/components/script/dom/htmlimageelement.rs
index 5f2566ed089..861b8ca5633 100644
--- a/src/components/script/dom/htmlimageelement.rs
+++ b/src/components/script/dom/htmlimageelement.rs
@@ -19,12 +19,12 @@ use servo_net::image_cache_task;
use servo_util::url::parse_url;
use servo_util::str::DOMString;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
#[deriving(Encodable)]
pub struct HTMLImageElement {
htmlelement: HTMLElement,
- extra: Untraceable,
+ priv extra: Untraceable,
}
struct Untraceable {
@@ -62,6 +62,10 @@ impl HTMLImageElement {
}
impl HTMLImageElement {
+ pub fn image<'a>(&'a self) -> &'a Option<Url> {
+ &self.extra.image
+ }
+
/// Makes the local `image` member match the status of the `src` attribute and starts
/// prefetching the image. This method must be called after `src` is changed.
fn update_image(&mut self, value: Option<DOMString>, url: Option<Url>) {
@@ -89,7 +93,7 @@ impl HTMLImageElement {
pub fn AfterSetAttr(&mut self, name: DOMString, value: DOMString) {
if "src" == name {
- let document = self.htmlelement.element.node.owner_doc();
+ let document = self.htmlelement.element.node.owner_doc().clone();
let window = document.get().window.get();
let url = Some(window.get_url());
self.update_image(Some(value), url);
@@ -116,8 +120,7 @@ impl HTMLImageElement {
pub fn SetSrc(&mut self, abstract_self: &JS<HTMLImageElement>, src: DOMString) -> ErrorResult {
let node = &mut self.htmlelement.element;
- node.set_attr(&ElementCast::from(abstract_self), ~"src", src.clone());
- Ok(())
+ node.set_attr(&ElementCast::from(abstract_self), ~"src", src.clone())
}
pub fn CrossOrigin(&self) -> DOMString {
@@ -160,8 +163,7 @@ impl HTMLImageElement {
pub fn SetWidth(&mut self, abstract_self: &JS<HTMLImageElement>, width: u32) -> ErrorResult {
let mut elem: JS<Element> = ElementCast::from(abstract_self);
let mut elem_clone = elem.clone();
- elem.get_mut().set_attr(&mut elem_clone, ~"width", width.to_str());
- Ok(())
+ elem.get_mut().set_attr(&mut elem_clone, ~"width", width.to_str())
}
pub fn Height(&self, abstract_self: &JS<HTMLImageElement>) -> u32 {
@@ -180,8 +182,7 @@ impl HTMLImageElement {
pub fn SetHeight(&mut self, abstract_self: &JS<HTMLImageElement>, height: u32) -> ErrorResult {
let node = &mut self.htmlelement.element;
- node.set_attr(&ElementCast::from(abstract_self), ~"height", height.to_str());
- Ok(())
+ node.set_attr(&ElementCast::from(abstract_self), ~"height", height.to_str())
}
pub fn NaturalWidth(&self) -> u32 {
diff --git a/src/components/script/dom/htmlobjectelement.rs b/src/components/script/dom/htmlobjectelement.rs
index fba1a979e43..4c6e21012cf 100644
--- a/src/components/script/dom/htmlobjectelement.rs
+++ b/src/components/script/dom/htmlobjectelement.rs
@@ -73,7 +73,7 @@ impl HTMLObjectElement {
pub fn AfterSetAttr(&mut self, name: DOMString, _value: DOMString) {
if "data" == name {
- let document = self.htmlelement.element.node.owner_doc();
+ let document = self.htmlelement.element.node.owner_doc().clone();
let window = document.get().window.clone();
let url = Some(window.get().get_url());
self.process_data_url(window.get().image_cache_task.clone(), url);
diff --git a/src/components/script/dom/htmlserializer.rs b/src/components/script/dom/htmlserializer.rs
index e6822e79215..82c215c7d2f 100644
--- a/src/components/script/dom/htmlserializer.rs
+++ b/src/components/script/dom/htmlserializer.rs
@@ -25,7 +25,7 @@ pub fn serialize(iterator: &mut NodeIterator) -> ~str {
for node in *iterator {
while open_elements.len() > iterator.depth {
- html.push_str(~"</" + open_elements.pop() + ">");
+ html.push_str(~"</" + open_elements.pop().unwrap().as_slice() + ">");
}
html.push_str(
match node.type_id() {
@@ -59,7 +59,7 @@ pub fn serialize(iterator: &mut NodeIterator) -> ~str {
);
}
while open_elements.len() > 0 {
- html.push_str(~"</" + open_elements.pop() + ">");
+ html.push_str(~"</" + open_elements.pop().unwrap().as_slice() + ">");
}
html
}
diff --git a/src/components/script/dom/location.rs b/src/components/script/dom/location.rs
index 2fc06fb353b..8e7e1ca5ced 100644
--- a/src/components/script/dom/location.rs
+++ b/src/components/script/dom/location.rs
@@ -12,13 +12,13 @@ use servo_util::str::DOMString;
use script_task::{Page};
use std::rc::Rc;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
#[deriving(Encodable)]
pub struct Location {
reflector_: Reflector, //XXXjdm cycle: window->Location->window
- extra: Untraceable,
+ priv extra: Untraceable,
}
struct Untraceable {
diff --git a/src/components/script/dom/mouseevent.rs b/src/components/script/dom/mouseevent.rs
index 8741ea48a68..a261de252d7 100644
--- a/src/components/script/dom/mouseevent.rs
+++ b/src/components/script/dom/mouseevent.rs
@@ -5,7 +5,7 @@
use dom::bindings::codegen::MouseEventBinding;
use dom::bindings::codegen::InheritTypes::MouseEventDerived;
use dom::bindings::js::JS;
-use dom::bindings::error::{ErrorResult, Fallible};
+use dom::bindings::error::Fallible;
use dom::bindings::utils::{Reflectable, Reflector, reflect_dom_object};
use dom::event::{Event, MouseEventTypeId};
use dom::eventtarget::EventTarget;
@@ -135,7 +135,7 @@ impl MouseEvent {
shiftKeyArg: bool,
metaKeyArg: bool,
buttonArg: u16,
- relatedTargetArg: Option<JS<EventTarget>>) -> ErrorResult {
+ relatedTargetArg: Option<JS<EventTarget>>) {
self.mouseevent.InitUIEvent(typeArg, canBubbleArg, cancelableArg, viewArg, detailArg);
self.screen_x = screenXArg;
self.screen_y = screenYArg;
@@ -147,7 +147,6 @@ impl MouseEvent {
self.meta_key = metaKeyArg;
self.button = buttonArg;
self.related_target = relatedTargetArg;
- Ok(())
}
}
diff --git a/src/components/script/dom/node.rs b/src/components/script/dom/node.rs
index 9999503a758..71b2b121136 100644
--- a/src/components/script/dom/node.rs
+++ b/src/components/script/dom/node.rs
@@ -4,15 +4,20 @@
//! The core DOM types. Defines the basic DOM hierarchy as well as all the HTML elements.
-use dom::bindings::codegen::InheritTypes::{DocumentTypeCast, ElementCast, TextCast, NodeCast};
+use dom::attr::Attr;
+use dom::bindings::codegen::InheritTypes::{CommentCast, DocumentCast, DocumentTypeCast};
+use dom::bindings::codegen::InheritTypes::{ElementCast, TextCast, NodeCast};
use dom::bindings::codegen::InheritTypes::{CharacterDataCast, NodeBase, NodeDerived};
use dom::bindings::codegen::InheritTypes::ProcessingInstructionCast;
+use dom::bindings::codegen::NodeBinding::NodeConstants;
use dom::bindings::js::JS;
use dom::bindings::utils::{Reflectable, Reflector, reflect_dom_object};
use dom::bindings::error::{ErrorResult, Fallible, NotFound, HierarchyRequest};
use dom::bindings::utils;
use dom::characterdata::CharacterData;
-use dom::document::Document;
+use dom::comment::Comment;
+use dom::document::{Document, HTMLDocument, NonHTMLDocument};
+use dom::documentfragment::DocumentFragment;
use dom::documenttype::DocumentType;
use dom::element::{Element, ElementTypeId, HTMLAnchorElementTypeId, IElement};
use dom::eventtarget::{EventTarget, NodeTargetTypeId};
@@ -20,6 +25,7 @@ use dom::nodelist::{NodeList};
use dom::text::Text;
use dom::processinginstruction::ProcessingInstruction;
use dom::window::Window;
+use html::hubbub_html_parser::build_element_from_tag;
use layout_interface::{LayoutChan, ReapLayoutDataMsg, UntrustedNodeAddress};
use layout_interface::TrustedNodeAddress;
use servo_util::str::{DOMString, null_str_as_empty};
@@ -31,10 +37,9 @@ use std::cast;
use std::cell::{RefCell, Ref, RefMut};
use std::iter::{Map, Filter};
use std::libc::uintptr_t;
-use std::unstable::raw::Box;
-use std::util;
+use std::mem;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
//
// The basic Node structure
@@ -399,10 +404,12 @@ impl NodeHelpers for JS<Node> {
assert!(self.parent_node().is_some());
let document = document_from_node(self);
- for node in self.traverse_preorder() {
- if node.is_element() {
- let element: JS<Element> = ElementCast::to(&node);
- element.bind_to_tree_impl();
+ if self.is_in_doc() {
+ for node in self.traverse_preorder() {
+ if node.is_element() {
+ let element: JS<Element> = ElementCast::to(&node);
+ element.bind_to_tree_impl();
+ }
}
}
@@ -555,8 +562,8 @@ impl NodeHelpers for JS<Node> {
if object.is_null() {
fail!("Attempted to create a `JS<Node>` from an invalid pointer!")
}
- let boxed_node: *mut Box<Node> = utils::unwrap(object);
- JS::from_box(boxed_node)
+ let boxed_node: *mut Node = utils::unwrap(object);
+ JS::from_raw(boxed_node)
}
}
@@ -721,6 +728,14 @@ fn gather_abstract_nodes(cur: &JS<Node>, refs: &mut ~[JS<Node>], postorder: bool
}
}
+/// Specifies whether children must be recursively cloned or not.
+enum CloneChildrenFlag {
+ CloneChildren,
+ DoNotCloneChildren
+}
+
+fn as_uintptr<T>(t: &T) -> uintptr_t { t as *T as uintptr_t }
+
impl Node {
pub fn ancestors(&self) -> AncestorIterator {
AncestorIterator {
@@ -728,8 +743,8 @@ impl Node {
}
}
- pub fn owner_doc(&self) -> JS<Document> {
- self.owner_doc.clone().unwrap()
+ pub fn owner_doc<'a>(&'a self) -> &'a JS<Document> {
+ self.owner_doc.get_ref()
}
pub fn set_owner_doc(&mut self, document: &JS<Document>) {
@@ -793,11 +808,14 @@ impl Node {
/// Sends layout data, if any, back to the script task to be destroyed.
pub unsafe fn reap_layout_data(&mut self) {
if self.layout_data.is_present() {
- let layout_data = util::replace(&mut self.layout_data, LayoutDataRef::new());
+ let layout_data = mem::replace(&mut self.layout_data, LayoutDataRef::new());
let layout_chan = layout_data.take_chan();
match layout_chan {
None => {}
- Some(chan) => chan.send(ReapLayoutDataMsg(layout_data)),
+ Some(chan) => {
+ let LayoutChan(chan) = chan;
+ chan.send(ReapLayoutDataMsg(layout_data))
+ },
}
}
}
@@ -805,13 +823,13 @@ impl Node {
// http://dom.spec.whatwg.org/#dom-node-nodetype
pub fn NodeType(&self) -> u16 {
match self.type_id {
- ElementNodeTypeId(_) => 1,
- TextNodeTypeId => 3,
- ProcessingInstructionNodeTypeId => 7,
- CommentNodeTypeId => 8,
- DocumentNodeTypeId => 9,
- DoctypeNodeTypeId => 10,
- DocumentFragmentNodeTypeId => 11,
+ ElementNodeTypeId(_) => NodeConstants::ELEMENT_NODE,
+ TextNodeTypeId => NodeConstants::TEXT_NODE,
+ ProcessingInstructionNodeTypeId => NodeConstants::PROCESSING_INSTRUCTION_NODE,
+ CommentNodeTypeId => NodeConstants::COMMENT_NODE,
+ DocumentNodeTypeId => NodeConstants::DOCUMENT_NODE,
+ DoctypeNodeTypeId => NodeConstants::DOCUMENT_TYPE_NODE,
+ DocumentFragmentNodeTypeId => NodeConstants::DOCUMENT_FRAGMENT_NODE,
}
}
@@ -852,7 +870,7 @@ impl Node {
TextNodeTypeId |
ProcessingInstructionNodeTypeId |
DoctypeNodeTypeId |
- DocumentFragmentNodeTypeId => Some(self.owner_doc()),
+ DocumentFragmentNodeTypeId => Some(self.owner_doc().clone()),
DocumentNodeTypeId => None
}
}
@@ -878,7 +896,7 @@ impl Node {
pub fn ChildNodes(&mut self, abstract_self: &JS<Node>) -> JS<NodeList> {
match self.child_list {
None => {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
let doc = doc.get();
let list = NodeList::new_child_list(&doc.window, abstract_self);
self.child_list = Some(list.clone());
@@ -930,11 +948,10 @@ impl Node {
CommentNodeTypeId |
TextNodeTypeId |
ProcessingInstructionNodeTypeId => {
- self.SetTextContent(abstract_self, val);
+ self.SetTextContent(abstract_self, val)
}
- _ => {}
+ _ => Ok(())
}
- Ok(())
}
// http://dom.spec.whatwg.org/#dom-node-textcontent
@@ -976,7 +993,7 @@ impl Node {
None
} else {
let document = self.owner_doc();
- Some(NodeCast::from(&document.get().CreateTextNode(&document, value)))
+ Some(NodeCast::from(&document.get().CreateTextNode(document, value)))
};
// Step 3.
Node::replace_all(node, abstract_self);
@@ -1255,7 +1272,7 @@ impl Node {
// http://dom.spec.whatwg.org/#concept-node-remove
fn remove(node: &mut JS<Node>, parent: &mut JS<Node>, suppress_observers: SuppressObserver) {
- assert!(node.parent_node().map_default(false, |ref node_parent| node_parent == parent));
+ assert!(node.parent_node().map_or(false, |ref node_parent| node_parent == parent));
// Step 1-5: ranges.
// Step 6-7: mutation observers.
@@ -1270,6 +1287,124 @@ impl Node {
}
}
+ // http://dom.spec.whatwg.org/#concept-node-clone
+ fn clone(node: &JS<Node>, maybe_doc: Option<&JS<Document>>, clone_children: CloneChildrenFlag)
+ -> JS<Node> {
+ fn clone_recursively(node: &JS<Node>, copy: &mut JS<Node>, doc: &JS<Document>) {
+ for ref child in node.get().children() {
+ let mut cloned = Node::clone(child, Some(doc), DoNotCloneChildren);
+ match Node::pre_insert(&mut cloned, copy, None) {
+ Ok(ref mut appended) => clone_recursively(child, appended, doc),
+ Err(..) => fail!("an error occurred while appending children")
+ }
+ }
+ }
+
+ // Step 1.
+ let mut document = match maybe_doc {
+ Some(doc) => doc.clone(),
+ None => node.get().owner_doc().clone()
+ };
+
+ // Step 2.
+ // XXXabinader: clone() for each node as trait?
+ let mut copy: JS<Node> = match node.type_id() {
+ DoctypeNodeTypeId => {
+ let doctype: JS<DocumentType> = DocumentTypeCast::to(node);
+ let doctype = doctype.get();
+ let doctype = DocumentType::new(doctype.name.clone(),
+ Some(doctype.public_id.clone()),
+ Some(doctype.system_id.clone()), &document);
+ NodeCast::from(&doctype)
+ },
+ DocumentFragmentNodeTypeId => {
+ let doc_fragment = DocumentFragment::new(&document);
+ NodeCast::from(&doc_fragment)
+ },
+ CommentNodeTypeId => {
+ let comment: JS<Comment> = CommentCast::to(node);
+ let comment = comment.get();
+ let comment = Comment::new(comment.characterdata.data.clone(), &document);
+ NodeCast::from(&comment)
+ },
+ DocumentNodeTypeId => {
+ let document: JS<Document> = DocumentCast::to(node);
+ let document = document.get();
+ let is_html_doc = match document.is_html_document {
+ true => HTMLDocument,
+ false => NonHTMLDocument
+ };
+ let document = Document::new(&document.window, Some(document.url().clone()),
+ is_html_doc, None);
+ NodeCast::from(&document)
+ },
+ ElementNodeTypeId(..) => {
+ let element: JS<Element> = ElementCast::to(node);
+ let element = element.get();
+ let element = build_element_from_tag(element.tag_name.clone(), &document);
+ NodeCast::from(&element)
+ },
+ TextNodeTypeId => {
+ let text: JS<Text> = TextCast::to(node);
+ let text = text.get();
+ let text = Text::new(text.characterdata.data.clone(), &document);
+ NodeCast::from(&text)
+ },
+ ProcessingInstructionNodeTypeId => {
+ let pi: JS<ProcessingInstruction> = ProcessingInstructionCast::to(node);
+ let pi = pi.get();
+ let pi = ProcessingInstruction::new(pi.target.clone(),
+ pi.characterdata.data.clone(), &document);
+ NodeCast::from(&pi)
+ },
+ };
+
+ // Step 3.
+ if copy.is_document() {
+ document = DocumentCast::to(&copy);
+ }
+ assert_eq!(copy.get().owner_doc(), &document);
+
+ // Step 4 (some data already copied in step 2).
+ match node.type_id() {
+ DocumentNodeTypeId => {
+ let node_doc: JS<Document> = DocumentCast::to(node);
+ let node_doc = node_doc.get();
+ let mut copy_doc: JS<Document> = DocumentCast::to(&copy);
+ let copy_doc = copy_doc.get_mut();
+ copy_doc.set_encoding_name(node_doc.encoding_name.clone());
+ copy_doc.set_quirks_mode(node_doc.quirks_mode());
+ },
+ ElementNodeTypeId(..) => {
+ let node_elem: JS<Element> = ElementCast::to(node);
+ let node_elem = node_elem.get();
+ let mut copy_elem: JS<Element> = ElementCast::to(&copy);
+ let copy_elem = copy_elem.get_mut();
+ // FIXME: https://github.com/mozilla/servo/issues/1737
+ copy_elem.namespace = node_elem.namespace.clone();
+ for attr in node_elem.attrs.iter() {
+ let attr = attr.get();
+ copy_elem.attrs.push(Attr::new_ns(&document.get().window,
+ attr.local_name.clone(), attr.value.clone(),
+ attr.name.clone(), attr.namespace.clone(),
+ attr.prefix.clone()));
+ }
+ },
+ _ => ()
+ }
+
+ // Step 5: cloning steps.
+
+ // Step 6.
+ match clone_children {
+ CloneChildren => clone_recursively(node, &mut copy, &document),
+ DoNotCloneChildren => ()
+ }
+
+ // Step 7.
+ copy
+ }
+
// http://dom.spec.whatwg.org/#dom-node-insertbefore
pub fn InsertBefore(&self, abstract_self: &mut JS<Node>, node: &mut JS<Node>, child: Option<JS<Node>>)
-> Fallible<JS<Node>> {
@@ -1422,14 +1557,36 @@ impl Node {
}
// http://dom.spec.whatwg.org/#dom-node-normalize
- pub fn Normalize(&mut self) {
- // FIXME (#1823) implement.
+ pub fn Normalize(&mut self, abstract_self: &mut JS<Node>) {
+ let mut prev_text = None;
+ for mut child in self.children() {
+ if child.is_text() {
+ let characterdata: JS<CharacterData> = CharacterDataCast::to(&child);
+ if characterdata.get().Length() == 0 {
+ abstract_self.remove_child(&mut child);
+ } else {
+ match prev_text {
+ Some(ref text_node) => {
+ let mut prev_characterdata: JS<CharacterData> = CharacterDataCast::to(text_node);
+ let _ = prev_characterdata.get_mut().AppendData(characterdata.get().Data());
+ abstract_self.remove_child(&mut child);
+ },
+ None => prev_text = Some(child)
+ }
+ }
+ } else {
+ prev_text = None;
+ }
+
+ }
}
// http://dom.spec.whatwg.org/#dom-node-clonenode
- pub fn CloneNode(&self, _deep: bool) -> Fallible<JS<Node>> {
- // FIXME: stub - https://github.com/mozilla/servo/issues/1240
- fail!("stub")
+ pub fn CloneNode(&self, abstract_self: &mut JS<Node>, deep: bool) -> JS<Node> {
+ match deep {
+ true => Node::clone(abstract_self, None, CloneChildren),
+ false => Node::clone(abstract_self, None, DoNotCloneChildren)
+ }
}
// http://dom.spec.whatwg.org/#dom-node-isequalnode
@@ -1507,9 +1664,57 @@ impl Node {
}
// http://dom.spec.whatwg.org/#dom-node-comparedocumentposition
- pub fn CompareDocumentPosition(&self, _other: &JS<Node>) -> u16 {
- // FIXME (#1794) implement.
- 0
+ pub fn CompareDocumentPosition(&self, abstract_self: &JS<Node>, other: &JS<Node>) -> u16 {
+ if abstract_self == other {
+ // step 2.
+ 0
+ } else {
+ let mut lastself = abstract_self.clone();
+ let mut lastother = other.clone();
+ for ancestor in abstract_self.ancestors() {
+ if &ancestor == other {
+ // step 4.
+ return NodeConstants::DOCUMENT_POSITION_CONTAINS +
+ NodeConstants::DOCUMENT_POSITION_PRECEDING;
+ }
+ lastself = ancestor;
+ }
+ for ancestor in other.ancestors() {
+ if &ancestor == abstract_self {
+ // step 5.
+ return NodeConstants::DOCUMENT_POSITION_CONTAINED_BY +
+ NodeConstants::DOCUMENT_POSITION_FOLLOWING;
+ }
+ lastother = ancestor;
+ }
+
+ if lastself != lastother {
+ let abstract_uint: uintptr_t = as_uintptr(&abstract_self.get());
+ let other_uint: uintptr_t = as_uintptr(&other.get());
+
+ let random = if abstract_uint < other_uint {
+ NodeConstants::DOCUMENT_POSITION_FOLLOWING
+ } else {
+ NodeConstants::DOCUMENT_POSITION_PRECEDING
+ };
+ // step 3.
+ return random +
+ NodeConstants::DOCUMENT_POSITION_DISCONNECTED +
+ NodeConstants::DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC;
+ }
+
+ for child in lastself.traverse_preorder() {
+ if &child == other {
+ // step 6.
+ return NodeConstants::DOCUMENT_POSITION_PRECEDING;
+ }
+ if &child == abstract_self {
+ // step 7.
+ return NodeConstants::DOCUMENT_POSITION_FOLLOWING;
+ }
+ }
+ unreachable!()
+ }
}
// http://dom.spec.whatwg.org/#dom-node-contains
@@ -1558,31 +1763,31 @@ impl Node {
//
pub fn set_parent_node(&mut self, new_parent_node: Option<JS<Node>>) {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
doc.get().wait_until_safe_to_modify_dom();
self.parent_node = new_parent_node
}
pub fn set_first_child(&mut self, new_first_child: Option<JS<Node>>) {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
doc.get().wait_until_safe_to_modify_dom();
self.first_child = new_first_child
}
pub fn set_last_child(&mut self, new_last_child: Option<JS<Node>>) {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
doc.get().wait_until_safe_to_modify_dom();
self.last_child = new_last_child
}
pub fn set_prev_sibling(&mut self, new_prev_sibling: Option<JS<Node>>) {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
doc.get().wait_until_safe_to_modify_dom();
self.prev_sibling = new_prev_sibling
}
pub fn set_next_sibling(&mut self, new_next_sibling: Option<JS<Node>>) {
- let doc = self.owner_doc();
+ let doc = self.owner_doc().clone();
doc.get().wait_until_safe_to_modify_dom();
self.next_sibling = new_next_sibling
}
@@ -1619,6 +1824,11 @@ impl Node {
pub fn next_sibling_ref<'a>(&'a self) -> Option<&'a JS<Node>> {
self.next_sibling.as_ref()
}
+
+ pub unsafe fn get_hover_state_for_layout(&self) -> bool {
+ let unsafe_this: *Node = cast::transmute::<&Node,*Node>(self);
+ (*unsafe_this).flags.get_in_hover_state()
+ }
}
impl Reflectable for Node {
diff --git a/src/components/script/dom/webidls/Document.webidl b/src/components/script/dom/webidls/Document.webidl
index 98df0b2aef9..41d20631bde 100644
--- a/src/components/script/dom/webidls/Document.webidl
+++ b/src/components/script/dom/webidls/Document.webidl
@@ -44,6 +44,7 @@ interface Document : Node {
partial interface Document {
[SetterThrows]
attribute DOMString title;
+ [SetterThrows]
attribute HTMLElement? body;
readonly attribute HTMLHeadElement? head;
NodeList getElementsByName(DOMString elementName);
diff --git a/src/components/script/dom/webidls/Element.webidl b/src/components/script/dom/webidls/Element.webidl
index e26c9415d4a..2211fd5c887 100644
--- a/src/components/script/dom/webidls/Element.webidl
+++ b/src/components/script/dom/webidls/Element.webidl
@@ -28,10 +28,8 @@ interface Element : Node {
[Pure]
attribute DOMString id;
-/*
- FIXME Bug 810677 Move className from HTMLElement to Element
+ [Pure]
attribute DOMString className;
-*/
/*[Constant]
readonly attribute DOMTokenList? classList;*/
diff --git a/src/components/script/dom/webidls/Event.webidl b/src/components/script/dom/webidls/Event.webidl
index d33093d76e9..6e574427548 100644
--- a/src/components/script/dom/webidls/Event.webidl
+++ b/src/components/script/dom/webidls/Event.webidl
@@ -33,7 +33,6 @@ interface Event {
readonly attribute boolean isTrusted;
readonly attribute DOMTimeStamp timeStamp;
- [Throws]
void initEvent(DOMString type, boolean bubbles, boolean cancelable);
};
diff --git a/src/components/script/dom/webidls/HTMLElement.webidl b/src/components/script/dom/webidls/HTMLElement.webidl
index e0ce18aaff9..8f1315d011d 100644
--- a/src/components/script/dom/webidls/HTMLElement.webidl
+++ b/src/components/script/dom/webidls/HTMLElement.webidl
@@ -43,10 +43,6 @@ interface HTMLElement : Element {
readonly attribute boolean isContentEditable;
[SetterThrows, Pure]
attribute boolean spellcheck;
-
- // Mozilla specific stuff
- // FIXME Bug 810677 Move className from HTMLElement to Element
- attribute DOMString className;
};
// http://dev.w3.org/csswg/cssom-view/#extensions-to-the-htmlelement-interface
diff --git a/src/components/script/dom/webidls/MouseEvent.webidl b/src/components/script/dom/webidls/MouseEvent.webidl
index 68a273ebaaf..5bb4a84a90a 100644
--- a/src/components/script/dom/webidls/MouseEvent.webidl
+++ b/src/components/script/dom/webidls/MouseEvent.webidl
@@ -23,7 +23,6 @@ interface MouseEvent : UIEvent {
readonly attribute unsigned short buttons;
readonly attribute EventTarget? relatedTarget;
// Deprecated in DOM Level 3:
- [Throws]
void initMouseEvent(DOMString typeArg,
boolean canBubbleArg,
boolean cancelableArg,
diff --git a/src/components/script/dom/webidls/Node.webidl b/src/components/script/dom/webidls/Node.webidl
index 0670e6eb3f6..2a13d6ab381 100644
--- a/src/components/script/dom/webidls/Node.webidl
+++ b/src/components/script/dom/webidls/Node.webidl
@@ -52,7 +52,6 @@ interface Node : EventTarget {
attribute DOMString? textContent;
void normalize();
- [Throws]
Node cloneNode(optional boolean deep = true);
boolean isEqualNode(Node? node);
diff --git a/src/components/script/dom/webidls/Window.webidl b/src/components/script/dom/webidls/Window.webidl
index de53cd2342c..0260324b91e 100644
--- a/src/components/script/dom/webidls/Window.webidl
+++ b/src/components/script/dom/webidls/Window.webidl
@@ -67,13 +67,13 @@ partial interface Window {
[NoInterfaceObject]
interface WindowTimers {
- //long setTimeout(Function handler, optional long timeout, any... arguments);
+ //long setTimeout(Function handler, optional long timeout = 0, any... arguments);
//XXXjdm No support for Function or variadic arguments yet
- long setTimeout(any handler, optional long timeout/*, any... arguments*/);
- void clearTimeout(long handle);
- /*long setTimeout(DOMString handler, optional long timeout, any... arguments);
- long setInterval(Function handler, optional long timeout, any... arguments);
- long setInterval(DOMString handler, optional long timeout, any... arguments);
- void clearInterval(long handle);*/
+ long setTimeout(any handler, optional long timeout = 0/*, any... arguments*/);
+ void clearTimeout(optional long handle = 0);
+ /*long setTimeout(DOMString handler, optional long timeout = 0, any... arguments);
+ long setInterval(Function handler, optional long timeout = 0, any... arguments);
+ long setInterval(DOMString handler, optional long timeout = 0, any... arguments);
+ void clearInterval(optional long handle = 0);*/
};
Window implements WindowTimers;
diff --git a/src/components/script/dom/window.rs b/src/components/script/dom/window.rs
index 7c3d2e90280..2ef70b0eac7 100644
--- a/src/components/script/dom/window.rs
+++ b/src/components/script/dom/window.rs
@@ -25,22 +25,22 @@ use js::jsval::JSVal;
use js::jsval::{NullValue, ObjectValue};
use js::JSPROP_ENUMERATE;
+use collections::hashmap::HashSet;
use std::cast;
-use std::comm::SharedChan;
+use std::cmp;
+use std::comm::Chan;
use std::comm::Select;
-use std::hashmap::HashSet;
+use std::hash::{Hash, sip};
use std::io::timer::Timer;
-use std::num;
use std::rc::Rc;
-use std::to_bytes::Cb;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
use extra::url::{Url};
pub enum TimerControlMsg {
- TimerMessage_Fire(~TimerData),
- TimerMessage_Close,
- TimerMessage_TriggerExit //XXXjdm this is just a quick hack to talk to the script task
+ TimerMessageFire(~TimerData),
+ TimerMessageClose,
+ TimerMessageTriggerExit //XXXjdm this is just a quick hack to talk to the script task
}
pub struct TimerHandle {
@@ -53,9 +53,9 @@ impl<S: Encoder> Encodable<S> for TimerHandle {
}
}
-impl IterBytes for TimerHandle {
- fn iter_bytes(&self, lsb0: bool, f: Cb) -> bool {
- self.handle.iter_bytes(lsb0, f)
+impl Hash for TimerHandle {
+ fn hash(&self, state: &mut sip::SipState) {
+ self.handle.hash(state);
}
}
@@ -81,13 +81,13 @@ pub struct Window {
image_cache_task: ImageCacheTask,
active_timers: ~HashSet<TimerHandle>,
next_timer_handle: i32,
- extra: Untraceable
+ priv extra: Untraceable
}
struct Untraceable {
page: Rc<Page>,
compositor: ~ScriptListener,
- timer_chan: SharedChan<TimerControlMsg>,
+ timer_chan: Chan<TimerControlMsg>,
}
impl<S: Encoder> Encodable<S> for Untraceable {
@@ -115,7 +115,7 @@ impl Window {
#[unsafe_destructor]
impl Drop for Window {
fn drop(&mut self) {
- self.extra.timer_chan.send(TimerMessage_Close);
+ self.extra.timer_chan.send(TimerMessageClose);
for handle in self.active_timers.iter() {
handle.cancel();
}
@@ -134,11 +134,11 @@ pub struct TimerData {
impl Window {
pub fn Alert(&self, s: DOMString) {
// Right now, just print to the console
- println(format!("ALERT: {:s}", s));
+ println!("ALERT: {:s}", s);
}
pub fn Close(&self) {
- self.extra.timer_chan.send(TimerMessage_TriggerExit);
+ self.extra.timer_chan.send(TimerMessageTriggerExit);
}
pub fn Document(&self) -> JS<Document> {
@@ -226,7 +226,7 @@ impl Reflectable for Window {
impl Window {
pub fn SetTimeout(&mut self, _cx: *JSContext, callback: JSVal, timeout: i32) -> i32 {
- let timeout = num::max(0, timeout) as u64;
+ let timeout = cmp::max(0, timeout) as u64;
let handle = self.next_timer_handle;
self.next_timer_handle += 1;
@@ -237,15 +237,17 @@ impl Window {
let chan = self.extra.timer_chan.clone();
spawn_named("Window:SetTimeout", proc() {
let mut tm = tm;
- let mut timeout_port = tm.oneshot(timeout);
- let mut cancel_port = cancel_port;
+ let timeout_port = tm.oneshot(timeout);
+ let cancel_port = cancel_port;
let select = Select::new();
- let timeout_handle = select.add(&mut timeout_port);
- let _cancel_handle = select.add(&mut cancel_port);
+ let mut timeout_handle = select.handle(&timeout_port);
+ unsafe { timeout_handle.add() };
+ let mut cancel_handle = select.handle(&cancel_port);
+ unsafe { cancel_handle.add() };
let id = select.wait();
- if id == timeout_handle.id {
- chan.send(TimerMessage_Fire(~TimerData {
+ if id == timeout_handle.id() {
+ chan.send(TimerMessageFire(~TimerData {
handle: handle,
funval: callback,
args: ~[],
@@ -290,14 +292,15 @@ impl Window {
compositor: compositor,
page: page.clone(),
timer_chan: {
- let (timer_port, timer_chan): (Port<TimerControlMsg>, SharedChan<TimerControlMsg>) = SharedChan::new();
+ let (timer_port, timer_chan): (Port<TimerControlMsg>, Chan<TimerControlMsg>) = Chan::new();
let id = page.borrow().id.clone();
spawn_named("timer controller", proc() {
+ let ScriptChan(script_chan) = script_chan;
loop {
match timer_port.recv() {
- TimerMessage_Close => break,
- TimerMessage_Fire(td) => script_chan.send(FireTimerMsg(id, td)),
- TimerMessage_TriggerExit => script_chan.send(ExitWindowMsg(id)),
+ TimerMessageClose => break,
+ TimerMessageFire(td) => script_chan.send(FireTimerMsg(id, td)),
+ TimerMessageTriggerExit => script_chan.send(ExitWindowMsg(id)),
}
}
});
diff --git a/src/components/script/html/cssparse.rs b/src/components/script/html/cssparse.rs
index 073b8562df4..846af813461 100644
--- a/src/components/script/html/cssparse.rs
+++ b/src/components/script/html/cssparse.rs
@@ -34,10 +34,11 @@ pub fn spawn_css_parser(provenance: StylesheetProvenance,
resource_task.send(Load(url, input_chan));
let LoadResponse { metadata: metadata, progress_port: progress_port }
= input_port.recv();
+ let final_url = &metadata.final_url;
let protocol_encoding_label = metadata.charset.as_ref().map(|s| s.as_slice());
let iter = ProgressMsgPortIterator { progress_port: progress_port };
Stylesheet::from_bytes_iter(
- iter, metadata.final_url,
+ iter, final_url.clone(),
protocol_encoding_label, Some(environment_encoding))
}
InlineProvenance(base_url, data) => {
diff --git a/src/components/script/html/hubbub_html_parser.rs b/src/components/script/html/hubbub_html_parser.rs
index 67a05c94386..34cbd08a59b 100644
--- a/src/components/script/html/hubbub_html_parser.rs
+++ b/src/components/script/html/hubbub_html_parser.rs
@@ -22,12 +22,13 @@ use hubbub::hubbub;
use servo_msg::constellation_msg::SubpageId;
use servo_net::resource_task::{Load, Payload, Done, ResourceTask, load_whole_resource};
use servo_util::namespace::Null;
-use servo_util::str::DOMString;
+use servo_util::str::{DOMString, HTML_SPACE_CHARACTERS};
use servo_util::task::spawn_named;
use servo_util::url::parse_url;
+use std::ascii::StrAsciiExt;
use std::cast;
use std::cell::RefCell;
-use std::comm::{Port, SharedChan};
+use std::comm::{Port, Chan};
use std::str;
use style::Stylesheet;
@@ -102,7 +103,7 @@ spawned, collates them, and sends them to the given result channel.
* `from_parent` - A port on which to receive new links.
*/
-fn css_link_listener(to_parent: SharedChan<HtmlDiscoveryMessage>,
+fn css_link_listener(to_parent: Chan<HtmlDiscoveryMessage>,
from_parent: Port<CSSMessage>,
resource_task: ResourceTask) {
let mut result_vec = ~[];
@@ -125,7 +126,7 @@ fn css_link_listener(to_parent: SharedChan<HtmlDiscoveryMessage>,
}
}
-fn js_script_listener(to_parent: SharedChan<HtmlDiscoveryMessage>,
+fn js_script_listener(to_parent: Chan<HtmlDiscoveryMessage>,
from_parent: Port<JSMessage>,
resource_task: ResourceTask) {
let mut result_vec = ~[];
@@ -139,7 +140,7 @@ fn js_script_listener(to_parent: SharedChan<HtmlDiscoveryMessage>,
}
Ok((metadata, bytes)) => {
result_vec.push(JSFile {
- data: str::from_utf8(bytes).to_owned(),
+ data: str::from_utf8(bytes).unwrap().to_owned(),
url: metadata.final_url,
});
}
@@ -255,9 +256,9 @@ pub fn parse_html(page: &Page,
// Spawn a CSS parser to receive links to CSS style sheets.
let resource_task2 = resource_task.clone();
- let (discovery_port, discovery_chan) = SharedChan::new();
+ let (discovery_port, discovery_chan) = Chan::new();
let stylesheet_chan = discovery_chan.clone();
- let (css_msg_port, css_chan) = SharedChan::new();
+ let (css_msg_port, css_chan) = Chan::new();
spawn_named("parse_html:css", proc() {
css_link_listener(stylesheet_chan, css_msg_port, resource_task2.clone());
});
@@ -265,7 +266,7 @@ pub fn parse_html(page: &Page,
// Spawn a JS parser to receive JavaScript.
let resource_task2 = resource_task.clone();
let js_result_chan = discovery_chan.clone();
- let (js_msg_port, js_chan) = SharedChan::new();
+ let (js_msg_port, js_chan) = Chan::new();
spawn_named("parse_html:js", proc() {
js_script_listener(js_result_chan, js_msg_port, resource_task2.clone());
});
@@ -302,11 +303,16 @@ pub fn parse_html(page: &Page,
let next_subpage_id = RefCell::new(next_subpage_id);
+ let doc_cell = RefCell::new(document);
+
let tree_handler = hubbub::TreeHandler {
create_comment: |data: ~str| {
debug!("create comment");
- let comment: JS<Node> = NodeCast::from(&Comment::new(data, document));
- unsafe { comment.to_hubbub_node() }
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let tmp_borrow = doc_cell.borrow();
+ let tmp = tmp_borrow.get();
+ let comment: JS<Node> = NodeCast::from(&Comment::new(data, *tmp));
+ unsafe { comment.to_hubbub_node() }
},
create_doctype: |doctype: ~hubbub::Doctype| {
debug!("create doctype");
@@ -314,21 +320,29 @@ pub fn parse_html(page: &Page,
public_id: public_id,
system_id: system_id,
force_quirks: _ } = doctype;
- let doctype_node = DocumentType::new(name, public_id, system_id, document);
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let tmp_borrow = doc_cell.borrow();
+ let tmp = tmp_borrow.get();
+ let doctype_node = DocumentType::new(name, public_id, system_id, *tmp);
unsafe {
doctype_node.to_hubbub_node()
}
},
create_element: |tag: ~hubbub::Tag| {
debug!("create element");
- let mut element = build_element_from_tag(tag.name.clone(), document);
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let tmp_borrow = doc_cell.borrow();
+ let tmp = tmp_borrow.get();
+ let mut element = build_element_from_tag(tag.name.clone(), *tmp);
debug!("-- attach attrs");
for attr in tag.attributes.iter() {
let elem = element.clone();
- element.get_mut().set_attr(&elem,
- attr.name.clone(),
- attr.value.clone());
+ //FIXME: this should have proper error handling or explicitly drop
+ // exceptions on the ground
+ assert!(element.get_mut().set_attr(&elem,
+ attr.name.clone(),
+ attr.value.clone()).is_ok());
}
// Spawn additional parsing, network loads, etc. from tag and attrs
@@ -337,12 +351,16 @@ pub fn parse_html(page: &Page,
ElementNodeTypeId(HTMLLinkElementTypeId) => {
match (element.get().get_attribute(Null, "rel"),
element.get().get_attribute(Null, "href")) {
- (Some(rel), Some(href)) => {
- if "stylesheet" == rel.get().value_ref() {
- debug!("found CSS stylesheet: {:s}", href.get().value_ref());
- let url = parse_url(href.get().value_ref(), Some(url2.clone()));
- css_chan2.send(CSSTaskNewFile(UrlProvenance(url)));
- }
+ (Some(ref rel), Some(ref href)) if rel.get()
+ .value_ref()
+ .split(HTML_SPACE_CHARACTERS.
+ as_slice())
+ .any(|s| {
+ s.eq_ignore_ascii_case("stylesheet")
+ }) => {
+ debug!("found CSS stylesheet: {:s}", href.get().value_ref());
+ let url = parse_url(href.get().value_ref(), Some(url2.clone()));
+ css_chan2.send(CSSTaskNewFile(UrlProvenance(url)));
}
_ => {}
}
@@ -357,11 +375,12 @@ pub fn parse_html(page: &Page,
let src_opt = elem.get().get_attribute(Null, "src").map(|x| x.get().Value());
for src in src_opt.iter() {
let iframe_url = parse_url(*src, Some(url2.clone()));
- iframe_element.get_mut().extra.frame = Some(iframe_url.clone());
+ iframe_element.get_mut().set_frame(iframe_url.clone());
// Subpage Id
let subpage_id = next_subpage_id.get();
- next_subpage_id.set(SubpageId(*subpage_id + 1));
+ let SubpageId(id_num) = subpage_id;
+ next_subpage_id.set(SubpageId(id_num + 1));
iframe_element.get_mut().size = Some(IFrameSize {
pipeline_id: pipeline_id,
@@ -379,7 +398,10 @@ pub fn parse_html(page: &Page,
},
create_text: |data: ~str| {
debug!("create text");
- let text = Text::new(data, document);
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let tmp_borrow = doc_cell.borrow();
+ let tmp = tmp_borrow.get();
+ let text = Text::new(data, *tmp);
unsafe { text.to_hubbub_node() }
},
ref_node: |_| {},
@@ -389,7 +411,7 @@ pub fn parse_html(page: &Page,
debug!("append child {:x} {:x}", parent, child);
let mut parent: JS<Node> = NodeWrapping::from_hubbub_node(parent);
let mut child: JS<Node> = NodeWrapping::from_hubbub_node(child);
- parent.AppendChild(&mut child);
+ assert!(parent.AppendChild(&mut child).is_ok());
}
child
},
@@ -426,11 +448,17 @@ pub fn parse_html(page: &Page,
},
set_quirks_mode: |mode| {
debug!("set quirks mode");
- document.get_mut().set_quirks_mode(mode);
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let mut tmp_borrow = doc_cell.borrow_mut();
+ let tmp = tmp_borrow.get();
+ tmp.get_mut().set_quirks_mode(mode);
},
encoding_change: |encname| {
debug!("encoding change");
- document.get_mut().set_encoding_name(encname);
+ // NOTE: tmp vars are workaround for lifetime issues. Both required.
+ let mut tmp_borrow = doc_cell.borrow_mut();
+ let tmp = tmp_borrow.get();
+ tmp.get_mut().set_encoding_name(encname);
},
complete_script: |script| {
unsafe {
@@ -495,6 +523,7 @@ pub fn parse_html(page: &Page,
}
}
+ debug!("finished parsing");
css_chan.send(CSSTaskExit);
js_chan.send(JSTaskExit);
diff --git a/src/components/script/layout_interface.rs b/src/components/script/layout_interface.rs
index 6ebea1809af..4ccf959f8ab 100644
--- a/src/components/script/layout_interface.rs
+++ b/src/components/script/layout_interface.rs
@@ -15,7 +15,7 @@ use geom::size::Size2D;
use script_task::{ScriptChan};
use servo_util::geometry::Au;
use std::cmp;
-use std::comm::{Chan, SharedChan};
+use std::comm::Chan;
use std::libc::c_void;
use style::Stylesheet;
@@ -132,11 +132,11 @@ pub struct Reflow {
/// Encapsulates a channel to the layout task.
#[deriving(Clone)]
-pub struct LayoutChan(SharedChan<Msg>);
+pub struct LayoutChan(Chan<Msg>);
impl LayoutChan {
pub fn new() -> (Port<Msg>, LayoutChan) {
- let (port, chan) = SharedChan::new();
+ let (port, chan) = Chan::new();
(port, LayoutChan(chan))
}
}
diff --git a/src/components/script/macros.rs b/src/components/script/macros.rs
index f8eaa07cc05..0ebdd7c6b7e 100644
--- a/src/components/script/macros.rs
+++ b/src/components/script/macros.rs
@@ -9,12 +9,14 @@ macro_rules! bitfield(
impl $bitfieldname {
#[inline]
pub fn $getter(self) -> bool {
- (*self & $value) != 0
+ let $bitfieldname(s) = self;
+ (s & $value) != 0
}
#[inline]
pub fn $setter(&mut self, value: bool) {
- *self = $bitfieldname((**self & !$value) | (if value { $value } else { 0 }))
+ let $bitfieldname(s) = *self;
+ *self = $bitfieldname((s & !$value) | (if value { $value } else { 0 }))
}
}
)
diff --git a/src/components/script/script.rs b/src/components/script/script.rs
index 3d57daa995f..4c5a53efbe6 100644
--- a/src/components/script/script.rs
+++ b/src/components/script/script.rs
@@ -10,16 +10,18 @@
#[feature(globs, macro_rules, struct_variant, managed_boxes)];
-extern mod geom;
-extern mod hubbub;
-extern mod encoding;
-extern mod js;
-extern mod servo_net = "net";
-extern mod servo_util = "util";
-extern mod style;
-extern mod servo_msg = "msg";
-extern mod extra;
-extern mod native;
+extern crate collections;
+extern crate geom;
+extern crate hubbub;
+extern crate encoding;
+extern crate js;
+extern crate serialize;
+extern crate servo_net = "net";
+extern crate servo_util = "util";
+extern crate style;
+extern crate servo_msg = "msg";
+extern crate extra;
+extern crate native;
// Macros
mod macros;
diff --git a/src/components/script/script_task.rs b/src/components/script/script_task.rs
index d4561ebc21b..e82a0e87647 100644
--- a/src/components/script/script_task.rs
+++ b/src/components/script/script_task.rs
@@ -50,13 +50,13 @@ use servo_util::task::send_on_failure;
use servo_util::namespace::Null;
use std::cast;
use std::cell::{RefCell, Ref, RefMut};
-use std::comm::{Port, SharedChan};
+use std::comm::{Port, Chan, Empty, Disconnected, Data};
+use std::mem::replace;
use std::ptr;
use std::rc::Rc;
use std::task;
-use std::util::replace;
-use extra::serialize::{Encoder, Encodable};
+use serialize::{Encoder, Encodable};
/// Messages used to control the script task.
pub enum ScriptMsg {
@@ -90,7 +90,7 @@ pub struct NewLayoutInfo {
/// Encapsulates external communication with the script task.
#[deriving(Clone)]
-pub struct ScriptChan(SharedChan<ScriptMsg>);
+pub struct ScriptChan(Chan<ScriptMsg>);
impl<S: Encoder> Encodable<S> for ScriptChan {
fn encode(&self, _s: &mut S) {
@@ -100,7 +100,7 @@ impl<S: Encoder> Encodable<S> for ScriptChan {
impl ScriptChan {
/// Creates a new script chan.
pub fn new() -> (Port<ScriptMsg>, ScriptChan) {
- let (port, chan) = SharedChan::new();
+ let (port, chan) = Chan::new();
(port, ScriptChan(chan))
}
}
@@ -164,7 +164,7 @@ pub struct PageTreeIterator<'a> {
impl PageTree {
fn new(id: PipelineId, layout_chan: LayoutChan, window_size: Size2D<uint>) -> PageTree {
PageTree {
- page: unsafe { Rc::new_unchecked(Page {
+ page: Rc::new(Page {
id: id,
frame: RefCell::new(None),
layout_chan: layout_chan,
@@ -177,7 +177,7 @@ impl PageTree {
resize_event: RefCell::new(None),
fragment_node: RefCell::new(None),
last_reflow_id: RefCell::new(0)
- }) },
+ }),
inner: ~[],
}
}
@@ -220,7 +220,7 @@ impl PageTree {
.map(|(idx, _)| idx)
};
match remove_idx {
- Some(idx) => return Some(self.inner.remove(idx)),
+ Some(idx) => return Some(self.inner.remove(idx).unwrap()),
None => {
for page_tree in self.inner.mut_iter() {
match page_tree.remove(id) {
@@ -237,11 +237,9 @@ impl PageTree {
impl<'a> Iterator<Rc<Page>> for PageTreeIterator<'a> {
fn next(&mut self) -> Option<Rc<Page>> {
if !self.stack.is_empty() {
- let next = self.stack.pop();
- {
- for child in next.inner.mut_iter() {
- self.stack.push(child);
- }
+ let next = self.stack.pop().unwrap();
+ for child in next.inner.mut_iter() {
+ self.stack.push(child);
}
Some(next.page.clone())
} else {
@@ -307,7 +305,7 @@ impl Page {
pub fn get_url(&self) -> Url {
let url = self.url();
- url.get().get_ref().first().clone()
+ url.get().get_ref().ref0().clone()
}
/// Sends a ping to layout and waits for the response. The response will arrive when the
@@ -319,11 +317,14 @@ impl Page {
match join_port {
Some(ref join_port) => {
match join_port.try_recv() {
- None => {
+ Empty => {
info!("script: waiting on layout");
join_port.recv();
}
- Some(_) => {}
+ Data(_) => {}
+ Disconnected => {
+ fail!("Layout task failed while script was waiting for a result.");
+ }
}
debug!("script: layout joined")
@@ -339,7 +340,8 @@ impl Page {
response_port: Port<T>)
-> T {
self.join_layout();
- self.layout_chan.send(QueryMsg(query));
+ let LayoutChan(ref chan) = self.layout_chan;
+ chan.send(QueryMsg(query));
response_port.recv()
}
@@ -397,7 +399,8 @@ impl Page {
id: *last_reflow_id.get(),
};
- self.layout_chan.send(ReflowMsg(reflow));
+ let LayoutChan(ref chan) = self.layout_chan;
+ chan.send(ReflowMsg(reflow));
debug!("script: layout forked")
}
@@ -493,8 +496,7 @@ impl ScriptTask {
-> Rc<ScriptTask> {
let js_runtime = js::rust::rt();
- unsafe {
- Rc::new_unchecked(ScriptTask {
+ Rc::new(ScriptTask {
page_tree: RefCell::new(PageTree::new(id, layout_chan, window_size)),
image_cache_task: img_cache_task,
@@ -507,8 +509,7 @@ impl ScriptTask {
js_runtime: js_runtime,
mouse_over_targets: RefCell::new(None)
- })
- }
+ })
}
/// Starts the script task. After calling this method, the script task will loop receiving
@@ -530,9 +531,9 @@ impl ScriptTask {
resource_task: ResourceTask,
image_cache_task: ImageCacheTask,
window_size: Size2D<uint>) {
- let mut builder = task::task();
- send_on_failure(&mut builder, FailureMsg(failure_msg), (*constellation_chan).clone());
- builder.name("ScriptTask");
+ let mut builder = task::task().named("ScriptTask");
+ let ConstellationChan(const_chan) = constellation_chan.clone();
+ send_on_failure(&mut builder, FailureMsg(failure_msg), const_chan);
builder.spawn(proc() {
let script_task = ScriptTask::new(id,
compositor as ~ScriptListener,
@@ -593,8 +594,8 @@ impl ScriptTask {
}
match self.port.try_recv() {
- None => break,
- Some(ev) => event = ev,
+ Empty | Disconnected => break,
+ Data(ev) => event = ev,
}
}
@@ -652,7 +653,7 @@ impl ScriptTask {
let this_value = if timer_data.args.len() > 0 {
fail!("NYI")
} else {
- js_info.get().get_ref().js_compartment.borrow().global_obj.borrow().ptr
+ js_info.get().get_ref().js_compartment.borrow().global_obj
};
// TODO: Support extra arguments. This requires passing a `*JSVal` array as `argv`.
@@ -683,7 +684,8 @@ impl ScriptTask {
/// Handles a navigate forward or backward message.
/// TODO(tkuehn): is it ever possible to navigate only on a subframe?
fn handle_navigate_msg(&self, direction: NavigationDirection) {
- self.constellation_chan.send(constellation_msg::NavigateMsg(direction));
+ let ConstellationChan(ref chan) = self.constellation_chan;
+ chan.send(constellation_msg::NavigateMsg(direction));
}
/// Window was resized, but this script was not active, so don't reflow yet
@@ -696,7 +698,7 @@ impl ScriptTask {
let mut page_url = page.mut_url();
let last_loaded_url = replace(page_url.get(), None);
for url in last_loaded_url.iter() {
- *page_url.get() = Some((url.first(), true));
+ *page_url.get() = Some((url.ref0().clone(), true));
}
}
@@ -823,19 +825,22 @@ impl ScriptTask {
js_scripts = Some(scripts);
}
Some(HtmlDiscoveredStyle(sheet)) => {
- page.layout_chan.send(AddStylesheetMsg(sheet));
+ let LayoutChan(ref chan) = page.layout_chan;
+ chan.send(AddStylesheetMsg(sheet));
}
Some(HtmlDiscoveredIFrame((iframe_url, subpage_id, sandboxed))) => {
- page.next_subpage_id.set(SubpageId(*subpage_id + 1));
+ let SubpageId(num) = subpage_id;
+ page.next_subpage_id.set(SubpageId(num + 1));
let sandboxed = if sandboxed {
IFrameSandboxed
} else {
IFrameUnsandboxed
};
- self.constellation_chan.send(LoadIframeUrlMsg(iframe_url,
- pipeline_id,
- subpage_id,
- sandboxed));
+ let ConstellationChan(ref chan) = self.constellation_chan;
+ chan.send(LoadIframeUrlMsg(iframe_url,
+ pipeline_id,
+ subpage_id,
+ sandboxed));
}
None => break
}
@@ -862,7 +867,7 @@ impl ScriptTask {
let js_info = page.js_info();
let js_info = js_info.get().get_ref();
let compartment = js_info.js_compartment.borrow();
- compartment.define_functions(DEBUG_FNS);
+ assert!(compartment.define_functions(DEBUG_FNS).is_ok());
js_info.js_context.borrow().ptr
};
@@ -873,12 +878,14 @@ impl ScriptTask {
let (cx, global_obj) = {
let js_info = page.js_info();
(js_info.get().get_ref().js_context.clone(),
- js_info.get().get_ref().js_compartment.borrow().global_obj.clone())
+ js_info.get().get_ref().js_compartment.borrow().global_obj)
};
- cx.borrow().evaluate_script(global_obj,
- file.data.clone(),
- file.url.to_str(),
- 1);
+ //FIXME: this should have some kind of error handling, or explicitly
+ // drop an exception on the floor.
+ assert!(cx.borrow().evaluate_script(global_obj,
+ file.data.clone(),
+ file.url.to_str(),
+ 1).is_ok());
});
}
@@ -890,12 +897,13 @@ impl ScriptTask {
let doctarget = EventTargetCast::from(&document);
let mut wintarget: JS<EventTarget> = EventTargetCast::from(&window);
let winclone = wintarget.clone();
- wintarget.get_mut().dispatch_event_with_target(&winclone, Some(doctarget), &mut event);
+ let _ = wintarget.get_mut().dispatch_event_with_target(&winclone, Some(doctarget), &mut event);
let mut fragment_node = page.fragment_node.borrow_mut();
- *fragment_node.get() = fragment.map_default(None, |fragid| self.find_fragment_node(page, fragid));
+ *fragment_node.get() = fragment.map_or(None, |fragid| self.find_fragment_node(page, fragid));
- self.constellation_chan.send(LoadCompleteMsg(page.id, url));
+ let ConstellationChan(ref chan) = self.constellation_chan;
+ chan.send(LoadCompleteMsg(page.id, url));
}
fn find_fragment_node(&self, page: &Page, fragid: ~str) -> Option<JS<Element>> {
@@ -908,7 +916,7 @@ impl ScriptTask {
let mut anchors = doc_node.traverse_preorder().filter(|node| node.is_anchor_element());
anchors.find(|node| {
let elem: JS<Element> = ElementCast::to(node);
- elem.get().get_attribute(Null, "name").map_default(false, |attr| {
+ elem.get().get_attribute(Null, "name").map_or(false, |attr| {
attr.get().value_ref() == fragid
})
}).map(|node| ElementCast::to(&node))
@@ -973,7 +981,7 @@ impl ScriptTask {
// FIXME: this event should be dispatch on WindowProxy. See #1715
let mut wintarget: JS<EventTarget> = EventTargetCast::from(&frame.window);
let winclone = wintarget.clone();
- wintarget.get_mut().dispatch_event_with_target(&winclone, None, event);
+ let _ = wintarget.get_mut().dispatch_event_with_target(&winclone, None, event);
}
None =>()
}
@@ -1121,8 +1129,9 @@ impl ScriptTask {
None => {}
}
} else {
- self.constellation_chan.send(LoadUrlMsg(page.id, url));
- }
+ let ConstellationChan(ref chan) = self.constellation_chan;
+ chan.send(LoadUrlMsg(page.id, url));
+ }
}
}
}
@@ -1133,7 +1142,8 @@ fn shut_down_layout(page: &Page) {
// Tell the layout task to begin shutting down.
let (response_port, response_chan) = Chan::new();
- page.layout_chan.send(layout_interface::PrepareToExitMsg(response_chan));
+ let LayoutChan(ref chan) = page.layout_chan;
+ chan.send(layout_interface::PrepareToExitMsg(response_chan));
response_port.recv();
// Destroy all nodes. Setting frame and js_info to None will trigger our
@@ -1149,5 +1159,5 @@ fn shut_down_layout(page: &Page) {
*js_info.get() = None;
// Destroy the layout task. If there were node leaks, layout will now crash safely.
- page.layout_chan.send(layout_interface::ExitNowMsg);
+ chan.send(layout_interface::ExitNowMsg);
}