📄 jsxml.c
字号:
if (argc == 0) { name = cx->runtime->emptyString; } else { name = js_ValueToString(cx, nameval); if (!name) return JS_FALSE; /* Use argv[1] as a local root for name, even if it was not passed. */ argv[1] = STRING_TO_JSVAL(name); } nsval = argv[0]; if (argc == 1 || JSVAL_IS_VOID(nsval)) { if (IS_STAR(name)) { nsval = JSVAL_NULL; } else { if (!js_GetDefaultXMLNamespace(cx, &nsval)) return JS_FALSE; } } if (JSVAL_IS_NULL(nsval)) { /* NULL prefix represents *undefined* in ECMA-357 13.3.2 5(a). */ uri = prefix = NULL; } else { /* * Inline specialization of the Namespace constructor called with * nsval passed as the only argument, to compute the uri and prefix * for the constructed namespace, without actually allocating the * object or computing other members. See ECMA-357 13.3.2 6(a) and * 13.2.2. */ isNamespace = isQName = JS_FALSE; if (!JSVAL_IS_PRIMITIVE(nsval)) { nsobj = JSVAL_TO_OBJECT(nsval); clasp = OBJ_GET_CLASS(cx, nsobj); isNamespace = (clasp == &js_NamespaceClass.base); isQName = (clasp == &js_QNameClass.base); }#ifdef __GNUC__ /* suppress bogus gcc warnings */ else nsobj = NULL;#endif if (isNamespace) { ns = (JSXMLNamespace *) JS_GetPrivate(cx, nsobj); uri = ns->uri; prefix = ns->prefix; } else if (isQName && (qn = (JSXMLQName *) JS_GetPrivate(cx, nsobj))->uri) { uri = qn->uri; prefix = qn->prefix; } else { uri = js_ValueToString(cx, nsval); if (!uri) return JS_FALSE; argv[0] = STRING_TO_JSVAL(uri); /* local root */ /* NULL here represents *undefined* in ECMA-357 13.2.2 3(c)iii. */ prefix = IS_EMPTY(uri) ? cx->runtime->emptyString : NULL; } }out: qn = js_NewXMLQName(cx, uri, prefix, name); if (!qn) return JS_FALSE; if (!JS_SetPrivate(cx, obj, qn)) return JS_FALSE; qn->object = obj; return JS_TRUE;}static JSBoolAttributeName(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval){ /* * Since js_AttributeNameClass was initialized, obj will have that as its * class, not js_QNameClass. */ return QName(cx, obj, argc, argv, rval);}/* * XMLArray library functions. */static JSBoolnamespace_identity(const void *a, const void *b){ const JSXMLNamespace *nsa = (const JSXMLNamespace *) a; const JSXMLNamespace *nsb = (const JSXMLNamespace *) b; if (nsa->prefix && nsb->prefix) { if (!js_EqualStrings(nsa->prefix, nsb->prefix)) return JS_FALSE; } else { if (nsa->prefix || nsb->prefix) return JS_FALSE; } return js_EqualStrings(nsa->uri, nsb->uri);}static JSBoolattr_identity(const void *a, const void *b){ const JSXML *xmla = (const JSXML *) a; const JSXML *xmlb = (const JSXML *) b; return qname_identity(xmla->name, xmlb->name);}static voidXMLArrayCursorInit(JSXMLArrayCursor *cursor, JSXMLArray *array){ JSXMLArrayCursor *next; cursor->array = array; cursor->index = 0; next = cursor->next = array->cursors; if (next) next->prevp = &cursor->next; cursor->prevp = &array->cursors; array->cursors = cursor; cursor->root = NULL;}static voidXMLArrayCursorFinish(JSXMLArrayCursor *cursor){ JSXMLArrayCursor *next; if (!cursor->array) return; next = cursor->next; if (next) next->prevp = cursor->prevp; *cursor->prevp = next; cursor->array = NULL;}static void *XMLArrayCursorNext(JSXMLArrayCursor *cursor){ JSXMLArray *array; array = cursor->array; if (!array || cursor->index >= array->length) return NULL; return cursor->root = array->vector[cursor->index++];}static void *XMLArrayCursorItem(JSXMLArrayCursor *cursor){ JSXMLArray *array; array = cursor->array; if (!array || cursor->index >= array->length) return NULL; return cursor->root = array->vector[cursor->index];}static voidXMLArrayCursorMark(JSContext *cx, JSXMLArrayCursor *cursor){ while (cursor) { GC_MARK(cx, cursor->root, "cursor->root"); cursor = cursor->next; }}/* NB: called with null cx from the GC, via xml_mark => XMLArrayTrim. */static JSBoolXMLArraySetCapacity(JSContext *cx, JSXMLArray *array, uint32 capacity){ void **vector; if (capacity == 0) { /* We could let realloc(p, 0) free this, but purify gets confused. */ if (array->vector) free(array->vector); vector = NULL; } else { if ((size_t)capacity > ~(size_t)0 / sizeof(void *) || !(vector = (void **) realloc(array->vector, capacity * sizeof(void *)))) { if (cx) JS_ReportOutOfMemory(cx); return JS_FALSE; } } array->capacity = JSXML_PRESET_CAPACITY | capacity; array->vector = vector; return JS_TRUE;}static voidXMLArrayTrim(JSXMLArray *array){ if (array->capacity & JSXML_PRESET_CAPACITY) return; if (array->length < array->capacity) XMLArraySetCapacity(NULL, array, array->length);}static JSBoolXMLArrayInit(JSContext *cx, JSXMLArray *array, uint32 capacity){ array->length = array->capacity = 0; array->vector = NULL; array->cursors = NULL; return capacity == 0 || XMLArraySetCapacity(cx, array, capacity);}static voidXMLArrayFinish(JSContext *cx, JSXMLArray *array){ JSXMLArrayCursor *cursor; JS_free(cx, array->vector); while ((cursor = array->cursors) != NULL) XMLArrayCursorFinish(cursor);#ifdef DEBUG memset(array, 0xd5, sizeof *array);#endif}#define XML_NOT_FOUND ((uint32) -1)static uint32XMLArrayFindMember(const JSXMLArray *array, void *elt, JSIdentityOp identity){ void **vector; uint32 i, n; /* The identity op must not reallocate array->vector. */ vector = array->vector; if (identity) { for (i = 0, n = array->length; i < n; i++) { if (identity(vector[i], elt)) return i; } } else { for (i = 0, n = array->length; i < n; i++) { if (vector[i] == elt) return i; } } return XML_NOT_FOUND;}/* * Grow array vector capacity by powers of two to LINEAR_THRESHOLD, and after * that, grow by LINEAR_INCREMENT. Both must be powers of two, and threshold * should be greater than increment. */#define LINEAR_THRESHOLD 256#define LINEAR_INCREMENT 32static JSBoolXMLArrayAddMember(JSContext *cx, JSXMLArray *array, uint32 index, void *elt){ uint32 capacity, i; int log2; void **vector; if (index >= array->length) { if (index >= JSXML_CAPACITY(array)) { /* Arrange to clear JSXML_PRESET_CAPACITY from array->capacity. */ capacity = index + 1; if (index >= LINEAR_THRESHOLD) { capacity = JS_ROUNDUP(capacity, LINEAR_INCREMENT); } else { JS_CEILING_LOG2(log2, capacity); capacity = JS_BIT(log2); } if ((size_t)capacity > ~(size_t)0 / sizeof(void *) || !(vector = (void **) realloc(array->vector, capacity * sizeof(void *)))) { JS_ReportOutOfMemory(cx); return JS_FALSE; } array->capacity = capacity; array->vector = vector; for (i = array->length; i < index; i++) vector[i] = NULL; } array->length = index + 1; } array->vector[index] = elt; return JS_TRUE;}static JSBoolXMLArrayInsert(JSContext *cx, JSXMLArray *array, uint32 i, uint32 n){ uint32 j; JSXMLArrayCursor *cursor; j = array->length; JS_ASSERT(i <= j); if (!XMLArraySetCapacity(cx, array, j + n)) return JS_FALSE; array->length = j + n; JS_ASSERT(n != (uint32)-1); while (j != i) { --j; array->vector[j + n] = array->vector[j]; } for (cursor = array->cursors; cursor; cursor = cursor->next) { if (cursor->index > i) cursor->index += n; } return JS_TRUE;}static void *XMLArrayDelete(JSContext *cx, JSXMLArray *array, uint32 index, JSBool compress){ uint32 length; void **vector, *elt; JSXMLArrayCursor *cursor; length = array->length; if (index >= length) return NULL; vector = array->vector; elt = vector[index]; if (compress) { while (++index < length) vector[index-1] = vector[index]; array->length = length - 1; array->capacity = JSXML_CAPACITY(array); } else { vector[index] = NULL; } for (cursor = array->cursors; cursor; cursor = cursor->next) { if (cursor->index > index) --cursor->index; } return elt;}static voidXMLArrayTruncate(JSContext *cx, JSXMLArray *array, uint32 length){ void **vector; JS_ASSERT(!array->cursors); if (length >= array->length) return; if (length == 0) { if (array->vector) free(array->vector); vector = NULL; } else { vector = realloc(array->vector, length * sizeof(void *)); if (!vector) return; } if (array->length > length) array->length = length; array->capacity = length; array->vector = vector;}#define XMLARRAY_FIND_MEMBER(a,e,f) XMLArrayFindMember(a, (void *)(e), f)#define XMLARRAY_HAS_MEMBER(a,e,f) (XMLArrayFindMember(a, (void *)(e), f) != \ XML_NOT_FOUND)#define XMLARRAY_MEMBER(a,i,t) (((i) < (a)->length) \ ? (t *) (a)->vector[i] \ : NULL)#define XMLARRAY_SET_MEMBER(a,i,e) JS_BEGIN_MACRO \ if ((a)->length <= (i)) \ (a)->length = (i) + 1; \ ((a)->vector[i] = (void *)(e)); \ JS_END_MACRO#define XMLARRAY_ADD_MEMBER(x,a,i,e)XMLArrayAddMember(x, a, i, (void *)(e))#define XMLARRAY_INSERT(x,a,i,n) XMLArrayInsert(x, a, i, n)#define XMLARRAY_APPEND(x,a,e) XMLARRAY_ADD_MEMBER(x, a, (a)->length, (e))#define XMLARRAY_DELETE(x,a,i,c,t) ((t *) XMLArrayDelete(x, a, i, c))#define XMLARRAY_TRUNCATE(x,a,n) XMLArrayTruncate(x, a, n)/* * Define XML setting property strings and constants early, so everyone can * use the same names and their magic numbers (tinyids, flags). */static const char js_ignoreComments_str[] = "ignoreComments";static const char js_ignoreProcessingInstructions_str[] = "ignoreProcessingInstructions";static const char js_ignoreWhitespace_str[] = "ignoreWhitespace";static const char js_prettyPrinting_str[] = "prettyPrinting";static const char js_prettyIndent_str[] = "prettyIndent";/* * NB: These XML static property tinyids must * (a) not collide with the generic negative tinyids at the top of jsfun.c; * (b) index their corresponding xml_static_props array elements. * Don't change 'em! */enum xml_static_tinyid { XML_IGNORE_COMMENTS, XML_IGNORE_PROCESSING_INSTRUCTIONS, XML_IGNORE_WHITESPACE, XML_PRETTY_PRINTING, XML_PRETTY_INDENT};static JSBoolxml_setting_getter(JSContext *cx, JSObject *obj, jsval id, jsval *vp){ return JS_TRUE;}static JSBoolxml_setting_setter(JSContext *cx, JSObject *obj, jsval id, jsval *vp){ JSBool b; uint8 flag; JS_ASSERT(JSVAL_IS_INT(id)); if (!js_ValueToBoolean(cx, *vp, &b)) return JS_FALSE; flag = JS_BIT(JSVAL_TO_INT(id)); if (b) cx->xmlSettingFlags |= flag; else
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -