[领域]javascript hacking guide part 6

news/2024/7/3 5:44:57
2007年02月06日 21:22:00

书接上回,我们说到global对象的初始创建已经完成了。那,你肯定会问了,为什么说是初始创建,而不是完整的创建呢?要回答这个问题,还要从ECMA262说起:

ECMA262,强调了Global这个全局函数的很多信息,比如说,这个内置对象是先于Context就存在了的。比方说,在默认的情况下,我们调用的方法,其实都是Global这个对象的方法。比方说

var obj = new Object();

其实也就等于

var obj = new this.Object();

parseInt这样的方法,其实也都是挂在Global名下的。Global对象下,有若干属性,包括Object,Array,Boolean,String.. 这么说你肯定就明白了。其他的内置对象,都是Global的一个属性值。其实,不光内置对象,所有的新定义的function ,也都会在定义后(即通过function关键字)在Global的属性列表中增加一个指向自己的属性。

那么,我们可以想一下,GlobalObject之间的关系,真的是很微妙啊。Global.prototypeObject.prototype会是什么样的关系呢?

如果你是一个心急的人,一点会说:"写一段代码不就知道了吗?"。你的程序是不是这样写的?

document.writeln(global.prototype = = .

sorry,忘了告诉你了,global对象是不能这么访问的。你在程序中写:

document.writeln(global);

将会打出undefined.不过,这个Global对象又缺省存在,我们应该怎么去访问它呢?请让我先卖一个关子吧。

有了Global的这个概念以后,我们继续来分析源代码。从part4part5,我们基本上只在围绕着一个函数做文章,

glob = JS_NewObject(cx, &global_class, NULL, NULL);

这个函数的调用关系讲完之后,我们就要看下面的代码段了。

JS_InitStandardClasses(cx, glob)

JS_DefineFunctions(cx, glob, shell_functions)

从名字上看,我们是要在glob这个对象下,创建并挂接系统内置的对象了(事实也果真如此)。

JS_InitStandardClasses这个函数定义在jsapi.c 这个文件中,我们可以很容易的找到其中的重要部分:

/* Define a top-level property 'undefined' with the undefined value. */

atom = cx-

if (!OBJ_DEFINE_PROPERTY(cx, obj, ATOM_TO_JSID(atom), JSVAL_VOID,

NULL, NULL, JSPROP_PERMANENT, NULL)) {

return JS_FALSE;

}

/* Function and Object require cooperative bootstrapping magic. */

if (!js_InitFunctionAndObjectClasses(cx, obj))

return JS_FALSE;

/* Initialize the rest of the standard objects and functions. */

return js_InitArrayClass(cx, obj) &&

js_InitBlockClass(cx, obj) &&

js_InitBooleanClass(cx, obj) &&

js_InitCallClass(cx, obj) &&

js_InitExceptionClasses(cx, obj) &&

js_InitMathClass(cx, obj) &&

。。。。

我在这段代码中,找到的几个处比较重要的函数调用,用红颜色圈了出来。

第一个部分是一个宏:OBJ_DEFINE_PROPERTY这个宏的主要作用是调用函数指针,来给glob对象创建一个新的属性,属性的类型是JSVAL_VOID,这说明,ECMA262中要求的,Undefined属性是Global的一个属性,已经得到了实现。

第二部分,是我们的主角,弄懂了这个函数,基本上就可以初步理解ECMAScript的对象模型了。而且,它的注释也很有意思,使用了cooperative bootstrapping magic这样的字眼。好的,那就让我们跑到后台去,看看魔术师的鬼把戏是怎么出来的吧。

js_InitFunctionAndObjectClasses仍然在同文件中,所以不用调转就可以找到。

/* If cx has no global object, use obj so prototypes can be found. */

if (!cx-

JS_SetGlobalObject(cx, obj);

/* Record Function and Object in cx-

。。。。

/* Initialize the function class first so constructors can be made. */

fun_proto = js_InitFunctionClass(cx, obj);

if (!fun_proto)

goto out;

/* Initialize the object class next so Object.prototype works. */

obj_proto = js_InitObjectClass(cx, obj);

if (!obj_proto) {

fun_proto = NULL;

goto out;

}

/* Function.prototype and the global object delegate to Object.prototype. */

OBJ_SET_PROTO(cx, fun_proto, obj_proto);

if (!OBJ_GET_PROTO(cx, obj))

OBJ_SET_PROTO(cx, obj, obj_proto);

这个程序的开头两大段,做的工作,我猜想我们可以跳过,不知道正不正确,我更想从js_InitFunctionClass(cx, obj)开始(标红的部分)。我们可以看到,我们还是把global当成参数传到了这个函数体中,这样,我们得到的的返回值,就是Function.prototype;同样,如果我们继续向下看,就会看到js_InitObjectClass(cx, obj)这个函数,从返回值、注释加上对函数名的推测,我们会看到,函数运行后返回了Object.prototype

然后呢,我们留意一下注释,哦,我的老天啊。我的猜测是没有错的Function.prototypeGlobal对象的prototype被委托给了Object.prototype.这还不够让我们兴奋的吗?

允许兴奋,可不要兴奋大发劲了啊。我们还有正事没有做呢。js_InitFunctionClass还在等着我们去解密呢。

这个函数在jsfun.c中有定义,麻烦你动手先将它找出来。

JSObject *

js_InitFunctionClass(JSContext *cx, JSObject *obj)

{

JSObject *proto;

JSAtom *atom;

JSFunction *fun;

proto = JS_InitClass(cx, obj, NULL, &js_FunctionClass, Function, 1,

function_props, function_methods, NULL, NULL);

if (!proto)

return NULL;

atom = js_Atomize(cx, js_FunctionClass.name, strlen(js_FunctionClass.name),

0);

if (!atom)

goto bad;

fun = js_NewFunction(cx, proto, NULL, 0, 0, obj, NULL);

if (!fun)

goto bad;

fun-

if (!fun-

goto bad;

fun-

fun-

return proto;

为了简单起见,我将这个函数的调用图先列出来:

js_InitFunctionClass

JS_InitClass

js_Atomize

js_NewObject

js_NewGCThing

js_Atomize

js_NewFunction

js_NewGCThing

那么,我们可以从这个调用图中推导出什么来呢?咱们下回书接着说。



Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=1503725



http://www.niftyadmin.cn/n/3661256.html

相关文章

[领域]javascript hacking guide 第5部分

2007年02月06日 11:49:00 map是JSObject的一个重要属性,存放一个对象的所有的属性的入口。要想了解map,就需要打开jsobj.h文件,看里面的定义。struct JSObject {JSObjectMap *map;jsval *slots;};很自然的,我们还要找到JSObjectMa…

arcgis分隔图层重复出文件_ArcGIS实用制图技巧 | 处理好这些细节才能让图更专业...

地理信息系统(Geographic Information System或 Geo-Information system,GIS)有时又称为“地学信息系统”。它是一种特定的十分重要的空间信息系统。它是在计算机硬、软件系统支持下,对整个或部分地球表层(包括大气层)空间中的有关地理分布数…

postman是做什么的_Postman +Newman+Jenkins+钉钉实现持续集成的接口自动化

一、为什么选用postman工具做接口自动化测试postman调试工具无论对于开发和测试小白,还是技术大牛来说应该都耳熟能详,在过去的几年里大家对这款工具应用最广的用途是把当作接口调试的测试工具,它能发送几乎所有类型的HTTP请求,操…

基于DSL的组织机构模型 之一:预告

2007年05月31日 21:07:00 最近我对组织机构领域模型的ruby实现很是着迷。本来,已经知道今天下午要考IBM SOA Test 665,可是我昨天下午就已经开始开小差了,昨天晚上更是在几张白纸上写写画画的,搞到凌晨2点才算完,早晨起…

浏览器打印不居中_页面布局——绘图区域、文档类型和打印

2.1 绘图区域(The Drawing Area)文档窗口的大小可能与页面的绘图区域不同。文档窗口只能显示页面绘图区域的一部分。可以使用以下选项来设置绘图区域在屏幕上的显示:⑴Document Settings和 Page Setup可以设置页面大小和方向、页边距、页眉、…

arial字体可以商用吗_别人的PPT那些好看的字体哪里找的?免费可商用,都给你准备好了...

今天和大家说说在制作PPT时,应该如何快速替换字体,别人那些漂亮的字体,又是在哪里找到的?马上为大家揭晓!一、怎么快速更换PPT字体?1、自定义字体平时经常需要用到PPT制作的朋友,就可以自己预设…

放弃完美的需求管理

2007年05月24日 22:41:00 我当然晓得需求管理是怎么回事,我当然知道需求管理要做什么,我当然知道Telelogic的Doors比IBM的requisitepro的功能要强大,我当然知道在IBM和Telelogic的pk中,cc/cq的扩展功能要synergy/CM 和synergy / c…

python语言的内置对象类型_Python内置对象类型

核心数字类型:数字:int,long,float,complex,bool字符:str,unicode列表:list字典:dict元组:tuple文件:file其他类型:集合(s…