`
三月沙
  • 浏览: 620097 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

ECMA-262-3 in detail. Chapter 1. Execution Contexts

 
阅读更多

 by Dmitry Soshnikov

 

 

In this note we will mention execution contexts of ECMAScript and types of executable code related with them.

Every time when control is transferred to ECMAScript executable code, control is entered an execution context.

Execution context (abbreviated form — EC) is the abstract concept used by ECMA-262 specification for typification and differentiation of an executable code.

The standard does not define accurate structure and kind of EC from the technical implementation viewpoint; it is a question of the ECMAScript-engines implementing the standard.

Logically, set of active execution contexts forms a stack. The bottom of this stack is always a global context, the top — a current (active) execution context. The stack is modified (pushed/popped) during the entering and exiting various kinds of EC.

With abstract concept of an execution context, the concept of type of an executable code is related. Speaking about code type, it is possible in the certain moments to mean an execution context.

For examples, we define the stack of execution contexts as an array:

ECStack = [];

The stack is pushed every time on entering a function (even if the function is called recursively or as theconstructor), and also at built-in eval function work.

This type of code is processed at level Program: i.e. the loaded external .js-file or the local inline-code (inside the <script></script> tags). The global code does not include any parts of a code which are in bodies of functions.

At initialization (program start), ECStack looks like:

ECStack = [
  globalContext
];

On entering the function code (all kinds of functions), ECStack is pushed with new elements. It is necessary to notice that the code of concrete function does not include codes of the inner functions.

For example, let’s take the function which calls itself recursively once:

(function foo(flag) {
  if (flag) {
    return;
  }
  foo(true);
})(false);

Then, ECStack is modified as follows:

// first activation of foo
ECStack = [
  <foo> functionContext
  globalContext
];
 
// recursive activation of foo
ECStack = [
  <foo> functionContext – recursively
  <foo> functionContext
  globalContext
];

Every return from a function exits the current execution context and ECStack popped accordingly — consecutively and upside-down — quite natural implementation of a stack. After the work of this code is finished, ECStack again contains only globalContext — until the program end.

A thrown but not caught exception may also exit one or more execution contexts:

(function foo() {
  (function bar() {
    throw 'Exit from bar and foo contexts';
  })();
})();

Things are more interesting with eval code. In this case, there is a concept of a calling context, i.e. a context from which eval function is called.

The actions made by eval, such as variable or function definition, influence exactly the calling context:

// influence global context
eval('var x = 10');
 
(function foo() {
  // and here, variable "y" is
  // created in the local context
  // of "foo" function
  eval('var y = 20');
})();
 
alert(x); // 10
alert(y); // "y" is not defined

Note, in the strict-mode of ES5eval already does not influence the calling context, but instead evaluates the code in the local sandbox.

For the example above we have the following ECStack modifications:

ECStack = [
  globalContext
];
 
// eval('var x = 10');
ECStack.push({
  context: evalContext,
  callingContext: globalContext
});
 
// eval exited context
ECStack.pop();
 
// foo funciton call
ECStack.push(<foo> functionContext);
 
// eval('var y = 20');
ECStack.push({
  context: evalContext,
  callingContext: <foo> functionContext
});
 
// return from eval
ECStack.pop();
 
// return from foo
ECStack.pop();

I.e. quite casual and logical call-stack.

In old SpiderMonkey implementations (Firefox), up to version 1.7, it was possible to pass a calling context as a second argument for eval function. Thus, if the context still exists, it is possible to influence private variables:

 

function foo() {
  var x = 1;
  return function () { alert(x); };
};
 
var bar = foo();
 
bar(); // 1
 
eval('x = 2', bar); // pass context, influence internal var "x"
 
bar(); // 2

However, due to security reasons in modern engines it was fixed and is not significant anymore.

This theoretical minimum is required for the further analysis of details related with execution contexts, such as variable object or scope chain, which descriptions can be found in the appropriate chapters.

Corresponding section of ECMA-262-3 specification — 10. Execution Contexts.

 

中文版 转载自 http://www.cnblogs.com/justinw/archive/2010/04/16/1713086.html

 

 

[JavaScript]ECMA-262-3 深入解析.第一章.执行上下文

JavaScript]ECMA-262-3 深入解析.第一章.

这篇文章我们主要探讨ECMAScript执行上下文和相关的ECMAScript可执行代码。

每次当控制器转到ECMAScript可执行代码的时候,即会进入到一个执行上下文

执行上下文(简称-EC)是一个抽象概念,ECMA-262标准用这个概念同可执行代码(executable code)概念进行区分。

标准规范没有从技术实现的角度准确定义EC的类型和结构;这应该是具体实现ECMAScript引擎时要考虑的问题。

活动的执行上下文在逻辑上组成一个堆栈。堆栈底部永远都是全局上下文(global context),堆栈顶部是当前(活动的)执行上下文。堆栈在EC类型的变量(various kingds of EC)被推入或弹出的同时被修改。

可执行代码的概念与抽象的执行上下文的概念是相对的。在某些时刻,可执行代码与执行上下文是等价的。

例如,我们可以定义一个数组来模拟执行上下文堆栈:

1
ECStack = [];

每次进入函数 (即使函数被递归调用或作为构造函数) 的时候或者内置的eval函数工作的时候,这个堆栈都会被推入。

这种类型的代码是在"程序"级处理的:例如加载外部的js文件或者本地的在<script></script>标签内的代码。全局代码不包括任何函数体内的代码。

在初始化(程序启动)阶段,ECStack是这样的:

 

1
2
3
ECStack = [
  globalContext
];

 

当进入函数代码(所有类型的函数),ECStack被推入新元素。要注意的是,具体的函数代码不包括内部函数(inner functions)代码。如下所示,我们使函数自己调自己的方式递归一次:

1
2
3
4
5
6
(function  foo(bar) {
  if (bar) {
    return;
  }
  foo(true);
})();

那么,ECStack以如下方式被改变:

1
2
3
4
5
6
7
8
9
10
11
12
// first activation of foo
ECStack = [
  <foo> functionContext
  globalContext
];
  
// recursive activation of foo
ECStack = [
  <foo> functionContext – recursively
  <foo> functionContext
  globalContext
];

每次返回存在的当前执行上下文和ECStack弹出相应的执行上下文的时候,栈指针会自动移动位置,这是一个典型的堆栈实现方式。一个被抛出但是没有被截获的异常,同样存在一个或多个执行上下文。当相关段代码执行完以后,直到整个应用程序结束,ECStack都只包括全局上下文(global context)。

 eval 代码有点儿意思。它有一个概念: 调用上下文(calling context), 这是一个当eval函数被调用的时候产生的上下文。eval(变量或函数声明)活动会影响调用上下文(calling context)

1
2
3
4
5
6
7
8
eval('var x = 10');
  
(function foo() {
  eval('var y = 20');
})();
  
alert(x); // 10
alert(y); // "y" is not defined

ECStack的变化过程:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
ECStack = [
  globalContext
];
  
// eval('var x = 10');
ECStack.push(
  evalContext,
  callingContext: globalContext
);
  
// eval exited context
ECStack.pop();
  
// foo funciton call
ECStack.push(<foo> functionContext);
  
// eval('var y = 20');
ECStack.push(
  evalContext,
  callingContext: <foo> functionContext
);
  
// return from eval
ECStack.pop();
  
// return from foo
ECStack.pop();

看到了吧,这是一个非常普通的逻辑调用堆栈

在版本号1.7以上的SpiderMonkey(内置于Firefox,Thunderbird)的实现中,可以把调用上下文作为第二个参数传递给eval。那么,如果这个上下文存在,就有可能影响“私有”(类似以private关键字命名的变量一样)变量。

1
2
3
4
5
6
7
8
9
10
11
12
function foo() {
  var x = 1;
  return function () { alert(x); };
};
  
var bar = foo();
  
bar(); // 1
  
eval('x = 2', bar); // pass context, influence on internal var "x"
  
bar(); // 2

这篇文章的内容是未来分析其他跟执行上下文相关的主题(例如变量对象,作用域链,等等)的最起码的理论基础,这些主题将在后续章节中讲到。

这篇文章的内容在ECMA-262-3 标准规范中对应的章节— 10. Execution Contexts.

分享到:
评论

相关推荐

    ECMA-262-语言标准中文版.pdf

    ECMA-262是JavaScript语言的标准,由ECMA国际组织制定并维护。这个标准定义了JavaScript的核心语法和语义,确保所有实现JavaScript的引擎都能按照一致的方式运行代码。中文版的ECMA-262文档对于中国开发者来说是一份...

    ECMA-262.pdf

    标题“ECMA-262.pdf”指的是ECMAScript 2020语言规范,这是ECMAScript标准的官方文档。ECMAScript是一种由Ecma国际标准化组织定义的脚本语言规范,它为JavaScript等语言提供了基础。ECMA-262是该规范的编号,通常被...

    ECMA-262-3 in detail

    ECMA-262-3 是 ECMAScript 的第三版规范,它定义了JavaScript语言的语法和行为。本文将深入探讨该规范中的“执行上下文”(Execution Contexts)及其相关概念,这对于理解JavaScript的执行机制至关重要。 1. **执行...

    《ECMA-262》js标准-英文版

    **JavaScript(JS)标准——深入理解ECMA-262** JavaScript,通常简称为JS,是一种广泛应用于网页和网络应用的轻量级编程语言。它以其动态类型、原型继承和函数作为第一类对象等特性而著称。ECMA-262是JavaScript的...

    ECMA-262标准

    3. **创新性**:随着每年新版本的发布,ECMA-262不断引入新的语言特性,推动JavaScript语言的发展。 4. **可维护性**:标准为语言提供了一个清晰的定义,有助于开发者理解和维护代码。 5. **社区支持**:由于ECMA-...

    ES规范-ECMA-262_6th_edition_june_2015.zip

    **ES2015,全称ECMAScript 2015,是JavaScript语言的一个重要版本,也被称为ES6或ECMA-262第6版。这一版本的发布为JavaScript带来了许多现代化的特性和改进,极大地提升了开发者的效率和代码的可维护性。以下是对ES...

    ECMA-262官方规范

    ECMA-262官方规范,javascript开发的标准参考

    ECMA javascript corejava: ECMA-262, 3rd edition, 2rd 5rd edition。三个版本英文版.rar

    ECMA-262, 2nd edition, August 1998.pdf ECMA-262, 3rd edition, December 1999.pdf ECMA-262. 5rd edition, December 2009.pdf 三个标准的合集,

    ECMA-335 ECMA-335

    1. **概述**:这部分介绍了ECMA-335的基本概念,包括运行时环境、程序集、类型系统以及IL和元数据的定义。它强调了标准的目标是促进语言的互操作性,使得不同语言编写的代码能够无缝地在.NET平台上运行。 2. **元...

    Ecma标准Ecma-262.pdf

    《ECMA-262标准:ECMAScript语言规范》 **一、ECMA-262标准概览** ECMA-262是ECMA国际(原欧洲计算机制造商协会)发布的一系列标准之一,专注于定义ECMAScript编程语言的规范。ECMAScript是一种轻量级、解释型或...

    ECMA-262 JavaScript 标准

    "ECMA-262_Edition 3 中文.pdf"是这一版本的中文翻译,方便中文用户理解和学习。 每个版本的ECMA-262规范都是JavaScript开发者必须了解的重要参考资料。它们不仅详细描述了语言的语法结构,还包含了许多最佳实践和...

    ECMA-262-5.1中文版

    此版本(ECMA-262第5.1版)详细介绍了JavaScript的各个方面,包括语法、数据类型、内置对象以及执行模型等。本文将基于提供的部分目录内容,深入探讨其中的关键知识点。 #### 二、核心概念与术语 **1. 对象** 在...

    Ecma-262.pdf

    ### Ecma-262标准概述 #### 一、标题解析 **Ecma-262** 是一个关于 ECMAScript 语言规范的标准文档。该文档由欧洲计算机制造商协会(ECMA International)发布,旨在标准化 ECMAScript 语言,使其成为国际上广泛...

    ECMA-262中文版及英文原版

    ECMA-262是ECMAScript语言标准的官方文档,它定义了JavaScript和JScript等脚本语言的核心语法和语义。这份标准由欧洲计算机制造商协会(ECMA)发布,旨在促进脚本语言的互操作性和一致性。ECMA-262的各个版本反映了...

    ECMA-262-5.1_CN.zip_ecma_javascript

    ECMA-262是ECMAScript语言规范的官方编号,它是JavaScript编程语言的标准定义。5.1版本是该标准的一个重要里程碑,发布于2011年,为JavaScript提供了更严谨的定义和扩展。这个中文版的ECMA-262-5.1对于中国开发者来...

    Ecma-262.rar_ECMA-262_ECMAScript_javascript

    标题中的"Ecma-262.rar"指的是这个规范的文档集合,而"ECMA-262"是该规范的正式版本号,它定义了JavaScript编程语言的语法和语义规则。"ECMAScript_javascript"表明此规范与JavaScript语言密切相关,JavaScript是...

    ECMA-262-3 中文 版 下载

    这里下载的是ECMA-262标准 的第三版 的中文 翻译。格式为PDF。 如果需要,随手拿去。 声名:这不是我翻译的。我只是把 Lich_Ray 翻译好的HTML版 整理成 更加易于学习的 PDF版。 正文内容来自: Lich_Ray 的...

    Ecma-262(ECMAScript5.1中文版+英文版)

    Ecma-262是ECMAScript规范的官方编号,这是一种定义JavaScript语言标准的文档。ECMAScript 5.1是该规范的一个重要版本,它在2009年发布,是JavaScript发展历史上的一个里程碑。这个规范为JavaScript提供了一个稳定的...

Global site tag (gtag.js) - Google Analytics