@@ -13,10 +13,10 @@ By subclassing an abstract class used by the JavaScript analysis and implementin
1313member predicates we can teach the analysis to handle further instances of abstract concepts it
1414already understands. For example, the standard library defines an abstract class
1515``SystemCommandExecution `` that covers various APIs for executing operating-system commands. This
16- class is used by the command-injection analysis to identify potentially problematic flows where
17- input from a potentially malicious user is interpreted as the name of a system command to execute.
18- By defining additional subclasses of ``SystemCommandExecution ``, we can make this analysis more
19- powerful without touching its implementation.
16+ class is used by the command-injection analysis to identify problematic flows where input from a
17+ potentially malicious user is interpreted as the name of a system command to execute. By defining
18+ additional subclasses of ``SystemCommandExecution ``, we can make this analysis more powerful without
19+ touching its implementation.
2020
2121By overriding a member predicate defined in the library, we can change its behavior either for all
2222its receivers or only a subset. For example, the standard library predicate
@@ -28,20 +28,25 @@ analysis queries pick it up. This can be done by adding the customizing definiti
2828``Customizations.qll ``, an initially empty library file that is imported by the default library
2929``javascript.qll ``.
3030
31- Sometimes you may want to apply the two customization mechanisms of subclassing to provide new
32- implementations of an API and of overriding to selectively change the implementation of the API to
33- the same base class . This is not always easy to do, since the former requires the base class to be
34- abstract, while the latter requires it to be concrete.
31+ Sometimes you may want to perform both kinds of customizations at the same time: subclass a base
32+ class to provide new implementations of an API, and override some member predicates of the same base
33+ class to selectively change the implementation of the API . This is not always easy to do, since the
34+ former requires the base class to be abstract, while the latter requires it to be concrete.
3535
3636To work around this, the JavaScript library uses the so-called `range pattern `: the base class
37- ``Base `` itself is concrete, but it has an abstract companion class called ``Base::Range `` with the
38- same member predicates and covering the same set of values. The default implementation of all
39- predicates in ``Base `` simply delegates to their implementations in ``Base::Range ``. To extend
40- ``Base `` with new implementations, we subclass ``Base::Range `` and implement its API. To customize
41- ``Base ``, on the other hand, we subclass ``Base `` itself and override the predicates we want to
42- adjust.
43-
44- Note that currently the range pattern is not yet used everywhere, so you will find some abstract
37+ ``Base `` itself is concrete, but it has an abstract companion class called ``Base::Range `` covering
38+ the same set of values. To change the implementation of the API, subclass ``Base `` and override its
39+ member predicates. To provide new implementations of the API, subclass ``Base::Range `` and implement
40+ its abstract member predicates.
41+
42+ For example, the class ``Base64::Encode `` in the standard library models base64-encoding libraries
43+ using the range pattern. To add support for a new library, subclass ``Base64::Encode::Range `` and
44+ implement the member predicates ``getInput `` and ``getOutput ``. (Subclasses for many popular base64
45+ encoders are included in the standard library.) To customize the definition of ``getInput `` or
46+ ``getOutput `` for a library that is already supported, extend ``Base64::Encode `` itself and override
47+ the predicate you want to customize.
48+
49+ Note that currently the range pattern is not used everywhere yet, so you will find some abstract
4550classes without a concrete companion. We are planning on eventually migrating most abstract classes
4651to use the range pattern.
4752
@@ -130,7 +135,8 @@ Framework models
130135~~~~~~~~~~~~~~~~
131136
132137The libraries under ``semmle/javascript/frameworks `` model a broad range of popular JavaScript
133- libraries and frameworks, such as Express or Vue.js.
138+ libraries and frameworks, such as Express or Vue.js. Some framework modeling libraries are located
139+ under ``semmle/javascript `` directly, for instance ``Base64 ``, ``EmailClients `` and ``JsonParsers ``.
134140
135141Global data flow and taint tracking
136142~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@@ -163,7 +169,7 @@ It is not normally necessary to customize this layer.
163169Local data flow
164170~~~~~~~~~~~~~~~
165171
166- The ``DataFlow::SourceNode `` class implements the range pattern, so new kinds of source nodes can be
172+ The ``DataFlow::SourceNode `` class uses the range pattern, so new kinds of source nodes can be
167173added by extending ``Dataflow::SourceNode::Range ``. Some of its subclasses can similarly be
168174extended: ``DataFlow::ModuleImportNode `` models module imports, and ``DataFlow::ClassNode `` models
169175class definitions. The former provides default implementations covering CommonJS, AMD and ECMAScript
@@ -178,13 +184,13 @@ You can override ``AnalyzedNode::getAValue`` to customize the type inference. No
178184
179185You can also extend the set of abstract values in one of two ways:
180186
181- 1. To add individual abstract values that are independent of the program being analyzed, define a
182- subclass of ``CustomAbstractValueTag `` describing the new abstract value. There will then be a
183- corresponding value of class ``CustomAbstractValue `` that you can use in overriding
184- definitions of the ``getAValue `` predicate.
185- 2. To add abstract values that are induced by a program element, define a subclass of
186- ``CustomAbstractValueDefinition ``, and use its corresponding
187- ``CustomAbstractValueFromDefinition ``.
187+ 1. To add individual abstract values that are independent of the program being analyzed, define a
188+ subclass of ``CustomAbstractValueTag `` describing the new abstract value. There will then be a
189+ corresponding value of class ``CustomAbstractValue `` that you can use in overriding
190+ definitions of the ``getAValue `` predicate.
191+ 2. To add abstract values that are induced by a program element, define a subclass of
192+ ``CustomAbstractValueDefinition ``, and use its corresponding
193+ ``CustomAbstractValueFromDefinition ``.
188194
189195Call graph
190196~~~~~~~~~~
0 commit comments