text:
JIT Compiler Structure
===

# Introduction

RyuJIT is the code name for the next generation Just in Time Compiler (aka "JIT") for the AMD64 .NET runtime. Its first implementation is for the AMD64 architecture. It is derived from a code base that is still in use for the other targets of .NET.

The primary design considerations for RyuJIT are to:

* Maintain a high compatibility bar with previous JITs, especially those for x86 (jit32) and x64 (jit64).
* Support and enable good runtime performance through code optimizations, register allocation, and code generation.
* Ensure good throughput via largely linear-order optimizations and transformations, along with limitations on tracked variables for analyses (such as dataflow) that are inherently super-linear.
* Ensure that the JIT architecture is designed to support a range of targets and scenarios.

The first objective was the primary motivation for evolving the existing code base, rather than starting from scratch or departing more drastically from the existing IR and architecture.

# Execution Environment and External Interface

RyuJIT provides the just in time compilation service for the .NET runtime. The runtime itself is variously called the EE (execution engine), the VM (virtual machine) or simply the CLR (common language runtime). Depending upon the configuration, the EE and JIT may reside in the same or different executable files. RyuJIT implements the JIT side of the JIT/EE interfaces:

* `ICorJitCompiler` – this is the interface that the JIT compiler implements. This interface is defined in [src/inc/corjit.h](https://github.com/dotnet/coreclr/blob/master/src/inc/corjit.h) and its implementation is in [src/jit/ee_il_dll.cpp](https://github.com/dotnet/coreclr/blob/master/src/jit/ee_il_dll.cpp). The following are the key methods on this interface:
  * `compileMethod` is the main entry point for the JIT. The EE passes it a `ICorJitInfo` object, and the "info" containing the IL, the method header, and various other useful tidbits. It returns a pointer to the code, its size, and additional GC, EH and (optionally) debug info.
  * `getVersionIdentifier` is the mechanism by which the JIT/EE interface is versioned. There is a single GUID (manually generated) which the JIT and EE must agree on.
  * `getMaxIntrinsicSIMDVectorLength` communicates to the EE the largest SIMD vector length that the JIT can support.
* `ICorJitInfo` – this is the interface that the EE implements. It has many methods defined on it that allow the JIT to look up metadata tokens, traverse type signatures, compute field and vtable offsets, find method entry points, construct string literals, etc. This bulk of this interface is inherited from `ICorDynamicInfo` which is defined in [src/inc/corinfo.h](https://github.com/dotnet/coreclr/blob/master/src/inc/corinfo.h). The implementation is defined in [src/vm/jitinterface.cpp](https://github.com/dotnet/coreclr/blob/master/src/vm/jitinterface.cpp).

# Internal Representation (IR)

## `Compiler` object

The `Compiler` object is the primary data structure of the JIT. While it is not part of the JIT's IR per se, it serves as the root from which the data structures that implement the IR are accessible. For example, the `Compiler` object points to the head of the function's `BasicBlock` list with the `fgFirstBB` field, as well as having additional pointers to the end of the list, and other distinguished locations. `ICorJit`Compiler`::CompileMethod()` is invoked for each method, and creates a new `Compiler` object. Thus, the JIT need not worry about thread synchronization while accessing `Compiler` state. The EE has the necessary synchronization to ensure there is a single JIT'd copy of a method when two or more threads try to trigger JIT compilation of the same method.

## Overview of the IR

RyuJIT represents a function as a doubly-linked list of `BasicBlock` values. Each `BasicBlock` has explicit edges to its successors that define the function's non-exceptional control flow. Exceptional control flow is implicit, with protected regions and handlers described in a table of `EHblkDsc` values. At the beginning of a compilation, each `BasicBlock` contains nodes in a high-level, statement- and tree-oriented form (HIR); this form persists throughout the JIT's front end. During the first phase of the back end--the rationalization phase--the HIR for each block is lowered to a linearly-ordered, node-oriented form (LIR). The fundamental distinction between HIR and LIR is in ordering semantics, though there are also some restrictions on the types of nodes that may appear in an HIR or LIR block.

Both HIR and LIR blocks are composed of `GenTree` nodes that define the operations performed by the block. A `GenTree` node may consume some number of operands and may produce a singly-defined, at-most-singly-used value as a result. These values are referred to interchangably as *SDSU* temps or *tree* temps. Defs of SDSU temps are represented by `GenTree` nodes themselves, and uses are represented by edges from the using node to the defining node. Furthermore, SDSU temps defined in one block may not be used in a different block. In cases where a value must be multiply-defined, multiply-used, or defined in one block and used in another, the IR provides another class of temporary: the local var. Local vars are defined by assignment nodes in HIR or store nodes in LIR, and are used by local var nodes in both forms.

An HIR block is composed of a doubly-linked list of statement nodes (`Statement`), each of which references a single expression tree (`m_rootNode`). The `GenTree` nodes in this tree execute in "tree order", which is defined as the order produced by a depth-first, left-to-right traversal of the tree, with two notable exceptions:
- Binary nodes marked with the `GTF_REVERSE_OPS` flag execute their right operand tree (`gtOp2`) before their left operand tree (`gtOp1`)
- Dynamically-sized block copy nodes where `gtEvalSizeFirst` is `true` execute the `gtDynamicSize` tree before executing their other operand trees.

In addition to tree order, HIR also requires that no SDSU temp is defined in one statement and used in another. In situations where the requirements of tree and statement order prove onerous (e.g. when code must execute at a particular point in a function), HIR provides `GT_COMMA` nodes as an escape valve: these nodes consume and discard the results of their left-hand side while producing a copy of the value produced by their right-hand side. This allows the compiler to insert code in the middle of a statement without requiring that the statement be split apart.

An LIR block is composed of a doubly-linked list of `GenTree` nodes, each of which describes a single operation in the method. These nodes execute in the order given by the list; there is no relationship between the order in which a node's operands appear and the order in which the operators that produced those operands execute. The only exception to this rule occurs after the register allocator, which may introduce `GT_COPY` and `GT_RELOAD` nodes that execute in "spill order". Spill order is defined as the order in which the register allocator visits a node's operands. For correctness, the code generator must generate code for spills, reloads, and `GT_COPY`/`GT_RELOAD` nodes in this order.

In addition to HIR and LIR `BasicBlock`s, a separate representation--`insGroup` and `instrDesc`--is used during the actual instruction encoding.

![RyuJIT IR Overview](../images/ryujit-ir-overview.png)

## GenTree Nodes

Each operation is represented as a GenTree node, with an opcode (`GT_xxx`), zero or more child/operand `GenTree` nodes, and additional fields as needed to represent the semantics of that node. Every node includes its type, value number, assertions, register assignments, etc. when available.

`GenTree` nodes are doubly-linked in execution order, but the links are not necessarily valid during all phases of the JIT. In HIR these links are primarily a convenience, as the order produced by a traversal of the links must match the order produced by a "tree order" traversal (see above for details). In LIR these links define the execution order of the nodes.

HIR statement nodes utilize the same `GenTree` base type as the operation nodes, though they are not truly related.
* The statement nodes are doubly-linked. The first statement node in a block points to the last node in the block via its `m_prev` link. Note that the last statement node does *not* point to the first; that is, the list is not fully circular.
* Each statement node contains two `GenTree` links – `m_rootNode` points to the top-level node in the statement (i.e. the root of the tree that represents the statement), while `m_treeList` points to the first node in execution order (again, this link is not always valid).

## Local var descriptors

A `LclVarDsc` represents a possibly-multiply-defined, possibly-multiply-used temporary. These temporaries may be used to represent user local variables, arguments or JIT-created temps. Each lclVar has a `gtLclNum` which is the identifier usually associated with the variable in the JIT and its dumps. The `LclVarDsc` contains the type, use count, weighted use count, frame or register assignment etc. A local var may be "tracked" (`lvTracked`), in which case it participates in dataflow analysis, and has a secondary name (`lvVarIndex`) that allows for the use of dense bit vectors.

### Example of Post-Import IR

For this snippet of code (extracted from [tests/src/JIT/CodeGenBringUpTests/DblRoots.cs](https://github.com/dotnet/coreclr/blob/master/tests/src/JIT/CodeGenBringUpTests/DblRoots.cs)):

       r1 = (-b + Math.Sqrt(b*b - 4*a*c))/(2*a);

A stripped-down dump of the `GenTree` nodes just after they are imported looks like this:

```
STMT  (IL 0x000...0x026)
   ▌  ASG       double
   ├──▌  IND       double
   │  └──▌  LCL_VAR   byref  V03 arg3
   └──▌  DIV       double
      ├──▌  ADD       double
      │  ├──▌  NEG       double
      │  │  └──▌  LCL_VAR   double V01 arg1
      │  └──▌  INTRINSIC double sqrt
      │     └──▌  SUB       double
      │        ├──▌  MUL       double
      │        │  ├──▌  LCL_VAR   double V01 arg1
      │        │  └──▌  LCL_VAR   double V01 arg1
      │        └──▌  MUL       double
      │           ├──▌  MUL       double
      │           │  ├──▌  LCL_VAR   double V00 arg0
      │           │  └──▌  CNS_DBL   double 4.0000000000000000
      │           └──▌  LCL_VAR   double V02 arg2
      └──▌  MUL       double
         ├──▌  LCL_VAR   double V00 arg0
         └──▌  CNS_DBL   double 2.0000000000000000
```

## Types

The JIT is primarily concerned with "primitive" types, i.e. integers, reference types, pointers, and floating point types.  It must also be concerned with the format of user-defined value types (i.e. struct types derived from `System.ValueType`) – specifically, their size and the offset of any GC references they contain, so that they can be correctly initialized and copied.  The primitive types are represented in the JIT by the `var_types` enum, and any additional information required for struct types is obtained from the JIT/EE interface by the use of an opaque `CORINFO_CLASS_HANDLE`.

## Dataflow Information

In order to limit throughput impact, the JIT limits the number of lclVars for which liveness information is computed. These are the tracked lclVars (`lvTracked` is true), and they are the only candidates for register allocation (i.e. only these lclVars may be assigned registers over their entire lifetime). Defs and uses of untracked lclVars are treated as stores and loads to/from the appropriate stack location, and the corresponding nodes act as normal operators during register allocation.

The liveness analysis determines the set of defs, as well as the uses that are upward exposed, for each block. It then propagates the liveness information. The result of the analysis is captured in the following:

* The live-in and live-out sets are captured in the `bbLiveIn` and `bbLiveOut` fields of the `BasicBlock`.
* The `GTF_VAR_DEF` flag is set on a lclVar node (all of which are of type `GenTreeLclVarCommon`) that is a definition.
* The `GTF_VAR_USEASG` flag is set (in addition to the `GTF_VAR_DEF` flag) on partial definitions of a local variable (i.e. `GT_LCL_FLD` nodes that do not define the entire variable).

## SSA

Static single assignment (SSA) form is constructed in a traditional manner [[1]](#[1]). The SSA names are recorded on the lclVar references. While SSA form usually retains a pointer or link to the defining reference, RyuJIT currently retains only the `BasicBlock` in which the definition of each SSA name resides.

## Value Numbering

Value numbering utilizes SSA for lclVar values, but also performs value numbering of expression trees. It takes advantage of type safety by not invalidating the value number for field references with a heap write, unless the write is to the same field. The IR nodes are annotated with the value numbers, which are indexes into a type-specific value number store. Value numbering traverses the trees, performing symbolic evaluation of many operations.

# Phases of RyuJIT

The top-level function of interest is `Compiler::compCompile`. It invokes the following phases in order.

| **Phase** | **IR Transformations** |
| --- | --- |
|[Pre-import](#pre-import)|`Compiler->lvaTable` created and filled in for each user argument and variable. BasicBlock list initialized.|
|[Importation](#importation)|`GenTree` nodes created and linked in to `Statement` nodes, and Statements into BasicBlocks. Inlining candidates identified.|
|[Inlining](#inlining)|The IR for inlined methods is incorporated into the flowgraph.|
|[Struct Promotion](#struct-promotion)|New lclVars are created for each field of a promoted struct.|
|[Mark Address-Exposed Locals](#mark-addr-exposed)|lclVars with references occurring in an address-taken context are marked.  This must be kept up-to-date.|
|[Morph Blocks](#morph-blocks)|Performs localized transformations, including mandatory normalization as well as simple optimizations.|
|[Eliminate Qmarks](#eliminate-qmarks)|All `GT_QMARK` nodes are eliminated, other than simple ones that do not require control flow.|
|[Flowgraph Analysis](#flowgraph-analysis)|`BasicBlock` predecessors are computed, and must be kept valid. Loops are identified, and normalized, cloned and/or unrolled.|
|[Normalize IR for Optimization](#normalize-ir)|lclVar references counts are set, and must be kept valid. Evaluation order of `GenTree` nodes (`gtNext`/`gtPrev`) is determined, and must be kept valid.|
|[SSA and Value Numbering Optimizations](#ssa-vn)|Computes liveness (`bbLiveIn` and `bbLiveOut` on `BasicBlocks`), and dominators. Builds SSA for tracked lclVars. Computes value numbers.|
|[Loop Invariant Code Hoisting](#licm)|Hoists expressions out of loops.|
|[Copy Propagation](#copy-propagation)|Copy propagation based on value numbers.|
|[Common Subexpression Elimination (CSE)](#cse)|Elimination of redundant subexressions based on value numbers.|
|[Assertion Propagation](#assertion-propagation)|Utilizes value numbers to propagate and transform based on properties such as non-nullness.|
|[Range analysis](#range-analysis)|Eliminate array index range checks based on value numbers and assertions|
|[Rationalization](#rationalization)|Flowgraph order changes from `FGOrderTree` to `FGOrderLinear`. All `GT_COMMA`, `GT_ASG` and `GT_ADDR` nodes are transformed.|
|[Lowering](#lowering)|Register requirements are fully specified (`gtLsraInfo`). All control flow is explicit.|
|[Register allocation](#reg-alloc)|Registers are assigned (`gtRegNum` and/or `gtRsvdRegs`),and the number of spill temps calculated.|
|[Code Generation](#code-generation)|Determines frame layout. Generates code for each `BasicBlock`. Generates prolog & epilog code for the method. Emit EH, GC and Debug info.|

## Pre-import

Prior to reading in the IL for the method, the JIT initializes the local variable table, and scans the IL to find branch targets and form BasicBlocks.

## Importation

Importation is the phase that creates the IR for the method, reading in one IL instruction at a time, and building up the statements. During this process, it may need to generate IR with multiple, nested expressions. This is the purpose of the non-expression-like IR nodes:

* It may need to evaluate part of the expression into a temp, in which case it will use a comma (`GT_COMMA`) node to ensure that the temp is evaluated in the proper execution order – i.e. `GT_COMMA(GT_ASG(temp, exp), temp)` is inserted into the tree where "exp" would go.
* It may need to create conditional expressions, but adding control flow at this point would be quite messy. In this case it generates question mark/colon (?: or `GT_QMARK`/`GT_COLON`) trees that may be nested within an expression.

During importation, tail call candidates (either explicitly marked or opportunistically identified) are identified and flagged. They are further validated, and possibly unmarked, during morphing.

## Morphing

The `fgMorph` phase includes a number of transformations:

### Inlining

The `fgInline` phase determines whether each call site is a candidate for inlining. The initial determination is made via a state machine that runs over the candidate method's IL. It estimates the native code size corresponding to the inline method, and uses a set of heuristics, including the estimated size of the current method) to determine if inlining would be profitable. If so, a separate Compiler object is created, and the importation phase is called to create the tree for the candidate inline method. Inlining may be aborted prior to completion, if any conditions are encountered that indicate that it may be unprofitable (or otherwise incorrect). If inlining is successful, the inlinee compiler's trees are incorporated into the inliner compiler (the "parent"), with args and returns appropriately transformed.

### Struct Promotion

Struct promotion (`fgPromoteStructs()`) analyzes the local variables and temps, and determines if their fields are candidates for tracking (and possibly enregistering) separately. It first determines whether it is possible to promote, which takes into account whether the layout may have holes or overlapping fields, whether its fields (flattening any contained structs) will fit in registers, etc.

Next, it determines whether it is likely to be profitable, based on the number of fields, and whether the fields are individually referenced.

When a lclVar is promoted, there are now N+1 lclVars for the struct, where N is the number of fields. The original struct lclVar is not considered to be tracked, but its fields may be.

### Mark Address-Exposed Locals

This phase traverses the expression trees, propagating the context (e.g. taking the address, indirecting) to determine which lclVars have their address taken, and which therefore will not be register candidates. If a struct lclVar has been promoted, and is then found to be address-taken, it will be considered "dependently promoted", which is an odd way of saying that the fields will still be separately tracked, but they will not be register candidates.

### Morph Blocks

What is often thought of as "morph" involves localized transformations to the trees. In addition to performing simple optimizing transformations, it performs some normalization that is required, such as converting field and array accesses into pointer arithmetic. It can (and must) be called by subsequent phases on newly added or modified trees. During the main Morph phase, the boolean `fgGlobalMorph` is set on the Compiler argument, which governs which transformations are permissible.

### Eliminate Qmarks

This expands most `GT_QMARK`/`GT_COLON` trees into blocks, except for the case that is instantiating a condition.

## Flowgraph Analysis

At this point, a number of analyses and transformations are done on the flowgraph:

* Computing the predecessors of each block
* Computing edge weights, if profile information is available
* Computing reachability and dominators
* Identifying and normalizing loops (transforming while loops to "do while")
* Cloning and unrolling of loops

## Normalize IR for Optimization

At this point, a number of properties are computed on the IR, and must remain valid for the remaining phases. We will call this "normalization"

* `lvaMarkLocalVars` – if this jit is optimizing, set the reference counts (raw and weighted) for lclVars, sort them, and determine which
will be tracked (currently up to 512). If not optimizing, all locals are given an implicit reference count of one. Reference counts are not incrementally
maintained. They can be recomputed if accurate counts are needed.
* `optOptimizeBools` – this optimizes Boolean expressions, and may change the flowgraph (why is it not done prior to reachability and dominators?)
* Link the trees in evaluation order (setting `gtNext` and `gtPrev` fields): and `fgFindOperOrder()` and `fgSetBlockOrder()`.

## SSA and Value Numbering Optimizations

The next set of optimizations are built on top of SSA and value numbering. First, the SSA representation is built (during which dataflow analysis, aka liveness, is computed on the lclVars), then value numbering is done using SSA.

### Loop Invariant Code Hoisting

This phase traverses all the loop nests, in outer-to-inner order (thus hoisting expressions outside the largest loop in which they are invariant). It traverses all of the statements in the blocks in the loop that are always executed. If the statement is:

* A valid CSE candidate
* Has no side-effects
* Does not raise an exception OR occurs in the loop prior to any side-effects
* Has a valid value number, and it is a lclVar defined outside the loop, or its children (the value numbers from which it was computed) are invariant.

### Copy Propagation

This phase walks each block in the graph (in dominator-first order, maintaining context between dominator and child) keeping track of every live definition. When it encounters a variable that shares the VN with a live definition, it is replaced with the variable in the live definition.

The JIT currently requires that the IR be maintained in conventional SSA form, as there is no "out of SSA" translation (see the comments on `optVnCopyProp()` for more information).

### Common Subexpression Elimination (CSE)

Utilizes value numbers to identify redundant computations, which are then evaluated to a new temp lclVar, and then reused.

### Assertion Propagation

Utilizes value numbers to propagate and transform based on properties such as non-nullness.

### Range analysis

Optimize array index range checks based on value numbers and assertions.

## Rationalization

As the JIT has evolved, changes have been made to improve the ability to reason over the tree in both "tree order" and "linear order". These changes have been termed the "rationalization" of the IR. In the spirit of reuse and evolution, some of the changes have been made only in the later ("backend") components of the JIT. The corresponding transformations are made to the IR by a "Rationalizer" component. It is expected that over time some of these changes will migrate to an earlier place in the JIT phase order:

* Elimination of assignment nodes (`GT_ASG`). The assignment node was problematic because the semantics of its destination (left hand side of the assignment) could not be determined without context. For example, a `GT_LCL_VAR` on the left-hand side of an assignment is a definition of the local variable, but on the right-hand side it is a use. Furthermore, since the execution order requires that the children be executed before the parent, it is unnatural that the left-hand side of the assignment appears in execution order before the assignment operator.
  * During rationalization, all assignments are replaced by stores, which either represent their destination on the store node itself (e.g. `GT_LCL_VAR`), or by the use of a child address node (e.g. `GT_STORE_IND`).
* Elimination of address nodes (`GT_ADDR`). These are problematic because of the need for parent context to analyze the child.
* Elimination of "comma" nodes (`GT_COMMA`). These nodes are introduced for convenience during importation, during which a single tree is constructed at a time, and not incorporated into the statement list until it is completed. When it is necessary, for example, to store a partially-constructed tree into a temporary variable, a `GT_COMMA` node is used to link it into the tree. However, in later phases, these comma nodes are an impediment to analysis, and thus are eliminated.
  * In some cases, it is not possible to fully extract the tree into a separate statement, due to execution order dependencies. In these cases, an "embedded" statement is created. While these are conceptually very similar to the `GT_COMMA` nodes, they do not masquerade as expressions.
* Elimination of "QMark" (`GT_QMARK`/`GT_COLON`) nodes is actually done at the end of morphing, long before the current rationalization phase. The presence of these nodes made analyses (especially dataflow) overly complex.
* Elimination of statements. Without statements, the execution order of a basic block's contents is fully defined by the `gtNext`/`gtPrev` links between `GenTree` nodes.

For our earlier example (Example of Post-Import IR), here is what the simplified dump looks like just prior to Rationalization (the $ annotations are value numbers).  Note that some common subexpressions have been computed into new temporary lclVars, and that computation has been inserted as a `GT_COMMA` (comma) node in the IR:

```
STMT  (IL 0x000...0x026)
   ▌  ASG       double $VN.Void
   ├──▌  IND       double $146
   │  └──▌  LCL_VAR   byref  V03 arg3         u:1 (last use) $c0
   └──▌  DIV       double $146
      ├──▌  ADD       double $144
      │  ├──▌  COMMA     double $83
      │  │  ├──▌  ASG       double $VN.Void
      │  │  │  ├──▌  LCL_VAR   double V06 cse0          $83
      │  │  │  └──▌  INTRINSIC double sqrt $83
      │  │  │     └──▌  SUB       double $143
      │  │  │        ├──▌  MUL       double $140
      │  │  │        │  ├──▌  LCL_VAR   double V01 arg1         u:1 $81
      │  │  │        │  └──▌  LCL_VAR   double V01 arg1         u:1 $81
      │  │  │        └──▌  MUL       double $142
      │  │  │           ├──▌  MUL       double $141
      │  │  │           │  ├──▌  LCL_VAR   double V00 arg0         u:1 $80
      │  │  │           │  └──▌  CNS_DBL   double 4.0000000000000000 $180
      │  │  │           └──▌  LCL_VAR   double V02 arg2         u:1 $82
      │  │  └──▌  LCL_VAR   double V06 cse0          $83
      │  └──▌  COMMA     double $84
      │     ├──▌  ASG       double $VN.Void
      │     │  ├──▌  LCL_VAR   double V08 cse2          $84
      │     │  └──▌  NEG       double $84
      │     │     └──▌  LCL_VAR   double V01 arg1         u:1 $81
      │     └──▌  LCL_VAR   double V08 cse2          $84
      └──▌  COMMA     double $145
         ├──▌  ASG       double $VN.Void
         │  ├──▌  LCL_VAR   double V07 cse1          $145
         │  └──▌  MUL       double $145
         │     ├──▌  LCL_VAR   double V00 arg0         u:1 $80
         │     └──▌  CNS_DBL   double 2.0000000000000000 $181
         └──▌  LCL_VAR   double V07 cse1          $145
```

After rationalization, the nodes are presented in execution order, and the `GT_COMMA` (comma), `GT_ASG` (=), and `Statement` nodes have been eliminated:

```
         IL_OFFSET void   IL offset: 0x0
 t3 =    LCL_VAR   double V01 arg1         u:1 $81
 t4 =    LCL_VAR   double V01 arg1         u:1 $81
     ┌──▌  t3     double
     ├──▌  t4     double
 t5 = ▌  MUL       double $140
 t7 =    LCL_VAR   double V00 arg0         u:1 $80
 t6 =    CNS_DBL   double 4.0000000000000000 $180
     ┌──▌  t7     double
     ├──▌  t6     double
 t8 = ▌  MUL       double $141
 t9 =    LCL_VAR   double V02 arg2         u:1 $82
     ┌──▌  t8     double
     ├──▌  t9     double
t10 = ▌  MUL       double $142
     ┌──▌  t5     double
     ├──▌  t10    double
t11 = ▌  SUB       double $143
     ┌──▌  t11    double
t12 = ▌  INTRINSIC double sqrt $83
     ┌──▌  t12    double
      ▌  STORE_LCL_VAR double V06 cse0
t46 =    LCL_VAR   double V06 cse0          $83
 t1 =    LCL_VAR   double V01 arg1         u:1 $81
     ┌──▌  t1     double
 t2 = ▌  NEG       double $84
     ┌──▌  t2     double
      ▌  STORE_LCL_VAR double V08 cse2
t56 =    LCL_VAR   double V08 cse2          $84
     ┌──▌  t46    double
     ├──▌  t56    double
t13 = ▌  ADD       double $144
t15 =    LCL_VAR   double V00 arg0         u:1 $80
t14 =    CNS_DBL   double 2.0000000000000000 $181
     ┌──▌  t15    double
     ├──▌  t14    double
t16 = ▌  MUL       double $145
     ┌──▌  t16    double
      ▌  STORE_LCL_VAR double V07 cse1
t51 =    LCL_VAR   double V07 cse1          $145
     ┌──▌  t13    double
     ├──▌  t51    double
t17 = ▌  DIV       double $146
 t0 =    LCL_VAR   byref  V03 arg3         u:1 (last use) $c0
     ┌──▌  t0     byref
     ├──▌  t17    double
      ▌  STOREIND  double
```

## Lowering

Lowering is responsible for transforming the IR in such a way that the control flow, and any register requirements, are fully exposed.

It does an execution-order traversal that performs context-dependent transformations such as
* expanding switch statements (using a switch table or a series of conditional branches)
* constructing addressing modes (LEA nodes)
* determining the code generation strategy for block assignments (e.g. `GT_STORE_BLK`) which may become helper calls, unrolled loops, or an instruction like `rep stos`
* generating machine specific instructions (e.g. generating the `BT` x86/64 instruction)
* mark "contained" nodes - such a node does not generate any code and relies on its user to include the node's operation in its own codegen (e.g. memory operands, immediate operands)
* mark "reg optional" nodes - despite the name, such a node may produce a value in a register but its user does not require a register and can consume the value directly from a memory location

For example, this:
```
t47 =    LCL_VAR   ref    V00 arg0
t48 =    LCL_VAR   int    V01 arg1
     ┌──▌  t48    int
t51 = ▌  CAST      long <- int
t52 =    CNS_INT   long   2
     ┌──▌  t51    long
     ├──▌  t52    long
t53 = ▌  LSH       long
t54 =    CNS_INT   long   16 Fseq[#FirstElem]
     ┌──▌  t53    long
     ├──▌  t54    long
t55 = ▌  ADD       long
     ┌──▌  t47    ref
     ├──▌  t55    long
t56 = ▌  ADD       byref
     ┌──▌  t56    byref
t44 = ▌  IND       int
```

Is transformed into this, in which the addressing mode is explicit:
```
t47 =    LCL_VAR   ref    V00 arg0
t48 =    LCL_VAR   int    V01 arg1
     ┌──▌  t48    int
t51 = ▌  CAST      long <- int
     ┌──▌  t47    ref
     ├──▌  t51    long
t79 = ▌  LEA(b+(i*4)+16) byref
     ┌──▌  t79    byref
t44 = ▌  IND       int
```
After all nodes are lowered, liveness is run in preparation for register allocation.

## Register allocation

The RyuJIT register allocator uses a Linear Scan algorithm, with an approach similar to [[2]](#[2]). In discussion it is referred to as either `LinearScan` (the name of the implementing class), or LSRA (Linear Scan Register Allocation). In brief, it operates on two main data structures:

* `Intervals` (representing live ranges of variables or tree expressions) and `RegRecords` (representing physical registers), both of which derive from `Referenceable`.
* `RefPositions`, which represent uses or defs (or variants thereof, such as ExposedUses) of either `Intervals` or physical registers.

`LinearScan::buildIntervals()` traverses the entire method building RefPositions and Intervals as required. For example, for the `STORE_BLK` node in this snippet:
```
t67 =    CNS_INT(h) long   0x2b5acef2c50 static Fseq[s1]
     ┌──▌  t67    long
 t0 = ▌  IND       ref
 t1 =    CNS_INT   long   8 Fseq[#FirstElem]
     ┌──▌  t0     ref
     ├──▌  t1     long
 t2 = ▌  ADD       byref
     ┌──▌  t2     byref
 t3 = ▌  IND       struct
t31 =    LCL_VAR_ADDR byref  V08 tmp1
     ┌──▌  t31    byref
     ├──▌  t3     struct
      ▌  STORE_BLK(40) struct (copy) (Unroll)
```
the following RefPositions are generated:
```
N027 (???,???) [000085] -A-XG-------              ▌  STORE_BLK(40) struct (copy) (Unroll) REG NA
Interval 16: int RefPositions {} physReg:NA Preferences=[allInt]
<RefPosition #40  @27  RefTypeDef <Ivl:16 internal> STORE_BLK BB01 regmask=[allInt] minReg=1>
Interval 17: float RefPositions {} physReg:NA Preferences=[allFloat]
<RefPosition #41  @27  RefTypeDef <Ivl:17 internal> STORE_BLK BB01 regmask=[allFloat] minReg=1>
<RefPosition #42  @27  RefTypeUse <Ivl:15> BB01 regmask=[allInt] minReg=1 last>
<RefPosition #43  @27  RefTypeUse <Ivl:16 internal> STORE_BLK BB01 regmask=[allInt] minReg=1 last>
<RefPosition #44  @27  RefTypeUse <Ivl:17 internal> STORE_BLK BB01 regmask=[allFloat] minReg=1 last>
```
The "@ 27" is the location number of the node. "internal" indicates a register that is internal to the node (in this case 2 internal registers are needed, one float (XMM on XARCH) and one int, as temporaries for copying). "regmask" indicates the register constraints for the `RefPosition`.

### Notable features of RyuJIT LinearScan

Unlike most register allocators, LSRA performs register allocation on an IR (Intermediate Representation) that is not a direct representation of the target instructions. A given IR node may map to 0, 1 or multiple target instructions. Nodes that are "contained" are handled by code generation as part of their parent node and thus may map to 0 instructions. A simple node will have a 1-to-1 mapping to a target instruction, and a more complex node (e.g. `GT_STORE_BLK`) may map to multiple instructions.

### Pre-conditions:

It is the job of the `Lowering` phase to transform the IR such that:
* The nodes are in `LIR` form (i.e. all expression trees have been linearized, and the execution order of the nodes within a BasicBlock is specified by the `gtNext` and `gtPrev` links)
* All contained nodes are identified (`gtFlags` has the `GTF_CONTAINED` bit set)
* All nodes for which a register is optional are identified (`RefPosition::regOptional` is `true`)
  * This is used for x86 and x64 on operands that can be directly consumed from memory if no register is allocated.
* All unused values (nodes that produce a result that is not consumed) are identified (gtLIRFlags has the LIR::Flags::UnusedValue bit set)
  * Since tree temps (the values produced by nodes and consumed by their parent) are expected to be single-def, single-use (SDSU), normally the live range can be determined to end at the use. If there is no use, the register allocator doesn't know where the live range ends.
* Code can be generated without any context from the parent (consumer) of each node.

After `Lowering` has completed, liveness analysis is performed:
* It identifies which `lclVar`s should have their liveness computed.
  * The reason this is done after `Lowering` is that it can introduce new `lclVar`s.
* It then does liveness analysis on those `lclVar`s, updating the `bbLiveIn` and `bbLiveOut` sets for each `BasicBlock`.
  * This tells the register allocator which `lclVars` are live at block boundaries.
  * Note that "tree temps" cannot be live at block boundaries.

### Allocation Overview

Allocation proceeds in 4 phases:

* Prepration:
  * Determine the order in which the `BasicBlocks` will be allocated, and which predecessor of each block will be used to determine the starting location for variables live-in to the `BasicBlock`.
  * Construct an `Interval` for each `lclVar` that may be enregistered.
  * Construct a `RegRecord` for each physical register.
* Walk the `BasicBlocks` in the determined order building `RefPositions` for each register use, def, or kill.
  * Just prior to building `RefPosition`s for the node, the `TreeNodeInfoInit()` method is called to determine its register requirements.
* Allocate the registers by traversing the `RefPositions`.
* Write back the register assignments, and perform any necessary moves at block boundaries where the allocations don't match.

Post-conditions:

* The `gtRegNum` property of all `GenTree` nodes that require a register has been set to `a valid register number.
  * For reg-optional nodes, the `GTF_NOREG_AT_USE` bit is set in `gtFlags` if a register was not allocated.
* The `gtRsvdRegs` field (a set/mask of registers) has the requested number of registers specified for internal use.
* All spilled values (lclVar or expression) are marked with `GTF_SPILL` at their definition. For lclVars, they are also marked with `GTF_SPILLED` at any use at which the value must be reloaded.
* For all lclVars that are register candidates:
  * `lvRegNum` = initial register location (or `REG_STK`)
  * `lvRegister` flag set if it always lives in the same register
  * `lvSpilled` flag is set if it is ever spilled
* The maximum number of simultaneously-live spill locations of each type (used for spilling expression trees) has been communicated via calls to `compiler->tmpPreAllocateTemps(type)`.

## Code Generation

The process of code generation is relatively straightforward, as Lowering has done some of the work already. Code generation proceeds roughly as follows:

* Determine the frame layout – allocating space on the frame for any lclVars that are not fully enregistered, as well as any spill temps required for spilling non-lclVar expressions.
* For each `BasicBlock`, in layout order, and each `GenTree` node in the block, in execution order:
  * If the node is "contained" (i.e. its operation is subsumed by a parent node), do nothing.
  * Otherwise, "consume" all the register operands of the node.
    * This updates the liveness information (i.e. marking a lclVar as dead if this is the last use), and performs any needed copies.
    * This must be done in "spill order" so that any spill/restore code inserted by the register allocator to resolve register conflicts is generated in the correct order. "
  * Track the live variables in registers, as well as the live stack variables that contain GC refs.
  * Produce the `instrDesc(s)` for the operation, with the current live GC references.
  * Update the scope information (debug info) at block boundaries.
* Generate the prolog and epilog code.
* Write the final instruction bytes. It does this by invoking the emitter, which holds all the `instrDescs`.

# Phase-dependent Properties and Invariants of the IR

There are several properties of the IR that are valid only during (or after) specific phases of the JIT. This section describes the phase transitions, and how the IR properties are affected.

## Phase Transitions

* Flowgraph analysis
  * Sets the predecessors of each block, which must be kept valid after this phase.
  * Computes reachability and dominators. These may be invalidated by changes to the flowgraph.
  * Computes edge weights, if profile information is available.
  * Identifies and normalizes loops. These may be invalidated, but must be marked as such.
* Normalization
  * The lclVar reference counts are set by `lvaMarkLocalVars()`.
  * Statement ordering is determined by `fgSetBlockOrder()`. Execution order is a depth-first preorder traversal of the nodes, with the operands usually executed in order. The exceptions are:
    * Binary operators, which can have the `GTF_REVERSE_OPS` flag set to indicate that the RHS (`gtOp2`) should be evaluated before the LHS (`gtOp1`).
    * Dynamically-sized block copy nodes, which can have `gtEvalSizeFirst` set to `true` to indicate that their `gtDynamicSize` tree should be evaluated before executing their other operands.
* Rationalization
  * All `GT_ASG` trees are transformed into `GT_STORE` variants (e.g. `GT_STORE_LCL_VAR`).
  * All `GT_ADDR` nodes are eliminated (e.g. with `GT_LCL_VAR_ADDR`).
  * All `GT_COMMA` and `Statement` nodes are removed and their constituent nodes linked into execution order.
* Lowering
  * `GenTree` nodes are split or transformed as needed to expose all of their register requirements and any necessary `flowgraph` changes (e.g., for switch statements).

## GenTree phase-dependent properties

Ordering:

* For `Statement` nodes, the `m_next` and `m_prev` fields must always be consistent. The last statement in the `BasicBlock` must have `m_next` equal to null. By convention, the `m_prev` of the first statement in the `BasicBlock` must be the last statement of the `BasicBlock`.
  * In all phases, `m_rootNode` points to the top-level node of the expression.
* For 'GenTree' nodes, the `gtNext` and `gtPrev` fields are either null, prior to ordering, or they are consistent (i.e. `A->gtPrev->gtNext = A`, and `A->gtNext->gtPrev == A`, if they are non-null).
* After normalization the `m_treeList` of the containing statement points to the first node to be executed.
* Prior to normalization, the `gtNext` and `gtPrev` pointers on the expression `GenTree` nodes are invalid. The expression nodes are only traversed via the links from parent to child (e.g. `node->gtGetOp1()`, or `node->gtOp.gtOp1`). The `gtNext/gtPrev` links are set by `fgSetBlockOrder()`.
  * After normalization, and prior to rationalization, the parent/child links remain the primary traversal mechanism. The evaluation order of any nested expression-statements (usually assignments) is enforced by the `GT_COMMA` in which they are contained.
* After rationalization, all `GT_COMMA` nodes are eliminated, statements are flattened, and the primary traversal mechanism becomes the `gtNext/gtPrev` links which define the execution order.
* In tree ordering:
  * The `gtPrev` of the first node (`m_treeList`) is always null.
  * The `gtNext` of the last node (`m_rootNode`) is always null.

## LclVar phase-dependent properties

LclVar ref counts track the number of uses and weighted used of a local in the jit IR. There are two sequences of phases over which ref counts are valid,
tracked via `lvaRefCountState`: an early sequence (state `RCS_EARLY`) and the normal sequence (state `RCS_NORMAL`). Requests for ref counts via `lvRefCnt`
and `lvRefCntWtd` must be aware of the ref count state.

Before struct promotion the ref counts are invalid. Struct promotion enables `RCS_EARLY` and it and subsequent phases through morph compute and uses ref counts
on some locals to guide some struct optimizations. After morph the counts go back to longer being valid.

The `RCS_NORMAL` sequence begins at normalization. Ref counts are computed and generally available via for the rest of the compilation phases.
The counts are not incrementally maintained and may go stale as the IR is optimized or transformed, or maybe very approximate if the jit is not optimizing.
They can be recomputed via `lvaComputeRefCounts` at points where accurate counts are valuable. Currently this happens before and after lower.

# Supporting technologies and components

## Instruction encoding

Instruction encoding is performed by the emitter ([emit.h](https://github.com/dotnet/coreclr/blob/master/src/jit/emit.h)), using the `insGroup`/`instrDesc` representation. The code generator calls methods on the emitter to construct `instrDescs`. The encodings information is captured in the following:

* The "instruction" enumeration itemizes the different instructions available on each target, and is used as an index into the various encoding tables (e.g. `instInfo[]`, `emitInsModeFmtTab[]`) generated from the `instrs{tgt}.h` (e.g., [instrsxarch.h](https://github.com/dotnet/coreclr/blob/master/src/jit/instrsxarch.h)).
* The skeleton encodings are contained in the tables, and then there are methods on the emitter that handle the special encoding constraints for the various instructions, addressing modes, register types, etc.

## GC Info

Reporting of live GC references is done in two ways:

* For stack locations that are not tracked (these could be spill locations or lclVars – local variables or temps – that are not register candidates), they are initialized to null in the prolog, and reported as live for the entire method.
* For lclVars with tracked lifetimes, or for expression involving GC references, we report the range over which the reference is live. This is done by the emitter, which adds this information to the instruction group, and which terminates instruction groups when the GC info changes.

The tracking of GC reference lifetimes is done via the `GCInfo` class in the JIT. It is declared in [src/jit/jitgcinfo.h](https://github.com/dotnet/coreclr/blob/master/src/jit/jitgcinfo.h) (to differentiate it from [src/inc/gcinfo.h](https://github.com/dotnet/coreclr/blob/master/src/inc/gcinfo.h)), and implemented in [src/jit/gcinfo.cpp](https://github.com/dotnet/coreclr/blob/master/src/jit/gcinfo.cpp).

In a JitDump, the generated GC info can be seen following the "In gcInfoBlockHdrSave()" line.

## Debugger info

Debug info consists primarily of two types of information in the JIT:

* Mapping of IL offsets to native code offsets. This is accomplished via:
  * the `m_ILOffsetX` on the statement nodes (`Statement`)
  * the `gtLclILoffs` on lclVar references (`GenTreeLclVar`)
  * The IL offsets are captured during CodeGen by calling `CodeGen::genIPmappingAdd()`, and then written to debug tables by `CodeGen::genIPmappingGen()`.
* Mapping of user locals to location (register or stack). This is accomplished via:
  * Struct `siVarLoc` (in [compiler.h](https://github.com/dotnet/coreclr/blob/master/src/jit/compiler.h)) captures the location
  * `VarScopeDsc` ([compiler.h](https://github.com/dotnet/coreclr/blob/master/src/jit/compiler.h)) captures the live range of a local variable in a given location.

## Exception handling

Exception handling information is captured in an `EHblkDsc` for each exception handling region. Each region includes the first and last blocks of the try and handler regions, exception type, enclosing region, among other things. Look at [jiteh.h](https://github.com/dotnet/coreclr/blob/master/src/jit/jiteh.h) and [jiteh.cpp](https://github.com/dotnet/coreclr/blob/master/src/jit/jiteh.cpp), especially, for details. Look at `Compiler::fgVerifyHandlerTab()` to see how the exception table constraints are verified.

# Reading a JitDump

One of the best ways of learning about the JIT compiler is examining a compilation dump in detail. The dump shows you all the really important details of the basic data structures without all the implementation detail of the code. Debugging a JIT bug almost always begins with a JitDump. Only after the problem is isolated by the dump does it make sense to start debugging the JIT code itself.

Dumps are also useful because they give you good places to place breakpoints. If you want to see what is happening at some point in the dump, simply search for the dump text in the source code. This gives you a great place to put a conditional breakpoint.

There is not a strong convention about what or how the information is dumped, but generally you can find phase-specific information by searching for the phase name. Some useful points follow.

## How to create a JitDump

You can enable dumps by setting the `COMPlus_JitDump` environment variable to a space-separated list of the method(s) you want to dump. For example:

```cmd
:: Print out lots of useful info when
:: compiling methods named Main/GetEnumerator
set "COMPlus_JitDump=Main GetEnumerator"
```

See [Setting configuration variables](../building/viewing-jit-dumps.md#setting-configuration-variables) for more details on this.

Full instructions for dumping the compilation of some managed code can be found here: [viewing-jit-dumps.md](../building/viewing-jit-dumps.md)

## Reading expression trees

Expression trees are displayed using a pre-order traversal, with the subtrees of a node being displayed under the node in operand order (e.g. `gtOp1`, `gtOp2`). This is similar to the way trees are displayed in typical user interfaces (e.g. folder trees). Note that the operand order may be different from the actual execution order, determined by `GTF_REVERSE_OPS` or other means. The operand order usually follows the order in high level languages so that the typical infix, left to right expression `a - b` becomes prefix, top to bottom tree:
```
▌  SUB       double
├──▌  LCL_VAR   double V03 a
└──▌  LCL_VAR   double V02 b
```
Assignments are displayed like all other binary operators, with `dest = src` becoming:
```
▌  ASG       double
├──▌  LCL_VAR   double V03 dest
└──▌  LCL_VAR   double V02 src
```
Calls initially display in source order - `Order(1, 2, 3, 4)` is:
```
[000004] --C-G-------              *  CALL      void   Program.Order
[000000] ------------ arg0         +--*  CNS_INT   int    1
[000001] ------------ arg1         +--*  CNS_INT   int    2
[000002] ------------ arg2         +--*  CNS_INT   int    3
[000003] ------------ arg3         \--*  CNS_INT   int    4
```
but call morphing may change the order depending on the ABI so the above may become:
```
[000004] --CXG+------              *  CALL      void   Program.Order
[000002] -----+------ arg2 on STK  +--*  CNS_INT   int    3
[000003] -----+------ arg3 on STK  +--*  CNS_INT   int    4
[000000] -----+------ arg0 in ecx  +--*  CNS_INT   int    1
[000001] -----+------ arg1 in edx  \--*  CNS_INT   int    2
```
where the node labels (e.g. arg0) help identifying the call arguments after reordering.

Here is a full dump of an entire statement:
```
STMT00000 (IL 0x010...  ???)
[000025] --C-G-------              └──▌  RETURN    double
[000023] --C-G-------                 └──▌  CALL      double C.DblSqrt
[000022] ------------ arg0               └──▌  MUL       double
[000018] ------------                       ├──▌  MUL       double
[000014] ------------                       │  ├──▌  MUL       double
[000010] ------------                       │  │  ├──▌  LCL_VAR   double V03 loc0
[000013] ------------                       │  │  └──▌  SUB       double
[000011] ------------                       │  │     ├──▌  LCL_VAR   double V03 loc0
[000012] ------------                       │  │     └──▌  LCL_VAR   double V00 arg0
[000017] ------------                       │  └──▌  SUB       double
[000015] ------------                       │     ├──▌  LCL_VAR   double V03 loc0
[000016] ------------                       │     └──▌  LCL_VAR   double V01 arg1
[000021] ------------                       └──▌  SUB       double
[000019] ------------                          ├──▌  LCL_VAR   double V03 loc0
[000020] ------------                          └──▌  LCL_VAR   double V02 arg2
```

Tree nodes are identified by their `gtTreeID`. This field only exists in DEBUG builds, but is quite useful for debugging, since all tree nodes are created from the routine `gtNewNode` (in [src/jit/gentree.cpp](https://github.com/dotnet/coreclr/blob/master/src/jit/gentree.cpp)). If you find a bad tree and wish to understand how it got corrupted, you can place a conditional breakpoint at the end of `gtNewNode` to see when it is created, and then a data breakpoint on the field that you believe is corrupted.

The trees are connected by line characters (either in ASCII, by default, or in slightly more readable Unicode when `COMPlus_JitDumpAscii=0` is specified), to make it a bit easier to read.

## Variable naming

The dump uses the index into the local variable table as its name. The arguments to the function come first, then the local variables, then any compiler generated temps. Thus in a function with 2 parameters (remember "this" is also a parameter), and one local variable, the first argument would be variable 0, the second argument variable 1, and the local variable would be variable 2. As described earlier, tracked variables are given a tracked variable index which identifies the bit for that variable in the dataflow bit vectors. This can lead to confusion as to whether the variable number is its index into the local variable table, or its tracked index. In the dumps when we refer to a variable by its local variable table index we use the 'V' prefix, and when we print the tracked index we prefix it by a 'T'.

## References

[1] P. Briggs, K. D. Cooper, T. J. Harvey, and L. T. Simpson, "Practical improvements to the construction and destruction of static single assignment form," Software --- Practice and Experience, vol. 28, no. 8, pp. 859---881, Jul. 1998.

[2] Wimmer, C. and Mössenböck, D. "Optimized Interval Splitting in a Linear Scan Register Allocator," ACM VEE 2005, pp. 132-141. [http://portal.acm.org/citation.cfm?id=1064998&dl=ACM&coll=ACM&CFID=105967773&CFTOKEN=80545349](http://portal.acm.org/citation.cfm?id=1064998&dl=ACM&coll=ACM&CFID=105967773&CFTOKEN=80545349)


text:
"use strict";
var viewModelBaseModule = require("../common/view-model-base");
var editTaskViewModelModule = require("../edit-task/edit-task-view-model");
var serviceModule = require("../../utils/service");
var navigationModule = require("../../utils/navigation");
var viewsModule = require("../../utils/views");
var ViewTaskViewModel = (function (_super) {
    __extends(ViewTaskViewModel, _super);
    function ViewTaskViewModel(task) {
        _super.call(this);
        this.task = task;
        this.pictureUrl = null;
        this.loadProject();
    }
    Object.defineProperty(ViewTaskViewModel.prototype, "task", {
        get: function () {
            return this._task;
        },
        set: function (value) {
            if (this._task != value) {
                this._task = value;
                this.notifyPropertyChange("task", value);
            }
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(ViewTaskViewModel.prototype, "project", {
        get: function () {
            return this._project;
        },
        set: function (value) {
            if (this._project != value) {
                this._project = value;
                this.notifyPropertyChange("project", value);
            }
        },
        enumerable: true,
        configurable: true
    });
    Object.defineProperty(ViewTaskViewModel.prototype, "pictureUrl", {
        get: function () {
            return this._pictureUrl;
        },
        set: function (value) {
            if (this._pictureUrl !== value) {
                this._pictureUrl = value;
                this.notifyPropertyChange("pictureUrl", value);
            }
        },
        enumerable: true,
        configurable: true
    });
    ViewTaskViewModel.prototype.editTask = function () {
        navigationModule.navigate({
            moduleName: viewsModule.Views.editTask,
            context: new editTaskViewModelModule.EditTaskViewModel(this.task)
        });
    };
    ViewTaskViewModel.prototype.completeTask = function () {
        var _this = this;
        this.task.IsCompleted = !this.task.IsCompleted;
        this.task.CompletionDate = this.task.IsCompleted ? new Date() : null;
        this.beginLoading();
        serviceModule.service.updateTask(this.task).then(function (data) {
            _this.endLoading();
        }, function (error) {
            _this.endLoading();
        });
    };
    ViewTaskViewModel.prototype.refresh = function () {
        this.loadPhoto();
        this.loadProject();
    };
    ViewTaskViewModel.prototype.loadPhoto = function () {
        var _this = this;
        if (this.task.Photo) {
            if (!this.beginLoading())
                return;
            serviceModule.service.getDownloadUrlFromId(this.task.Photo).then(function (url) {
                _this.pictureUrl = url;
                _this.endLoading();
            }, function (error) {
                _this.endLoading();
            });
        }
    };
    ViewTaskViewModel.prototype.loadProject = function () {
        var _this = this;
        if (this.task.Project) {
            if (!this.beginLoading())
                return;
            serviceModule.service.getProject(this.task.Project).then(function (project) {
                _this.project = project;
                _this.endLoading();
            }, function (error) {
                _this.endLoading();
            });
        }
    };
    return ViewTaskViewModel;
}(viewModelBaseModule.ViewModelBase));
exports.ViewTaskViewModel = ViewTaskViewModel;
//# sourceMappingURL=view-task-view-model.js.map

redpajama_set_name: RedPajamaGithub


text:
This is a sample app with multiple maps that have linked extents.  The application can be easily modified to increase or decrease the default number of maps displayed in the browser, as well as the layers and functionality of each individual map.

## Features

* Written in pure JavaScript using [Leaflet](http://leafletjs.com/index.html) and the [Esri Leaflet Library](https://github.com/Esri/esri-leaflet)
* Uses current versions of Leaflet and Esri Leaflet, 0.7.3 and 1.0.0-rc.4, respectively.
* Responsive design via Bootstrap
* [Live Sample](http://esri.github.io/developer-support/web-leaflet/multiple-maps-connected-extent/index.html)

heatMap code via:
 (c) 2014, Vladimir Agafonkin
 simpleheat, a tiny JavaScript library for drawing heatmaps with Canvas
 https://github.com/mourner/simpleheat


text:
<!DOCTYPE html>

        <title>Modal Component — Sanskrit Notes संस्कृत टिप्पणी</title>
        <meta charset="utf-8">
        <meta name="description" content="Sanskrit Notes संस्कृत टिप्पणी - A easy modern introduction to the ancient language.">
        <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">

        <meta property="og:type" content="article">
        <meta property="og:title" content="Modal Component — Vue.js">
        <meta property="og:description" content="Sanskrit Notes संस्कृत टिप्पणी - A easy modern introduction to the ancient language.">
        <meta property="og:image" content="https://sanskritnotes.com//images/logo.png">

        <meta name="twitter:card" content="summary">
        <meta name="twitter:title" content="Modal Component — Vue.js">
        <meta name="twitter:description" content="Sanskrit Notes संस्कृत टिप्पणी - A easy modern introduction to the ancient language.">
        <meta name="twitter:image" content="https://sanskritnotes.com/images/logo.png">

        <link rel="icon" href="/images/logo.png" type="image/x-icon">

        <link href='//fonts.googleapis.com/css?family=Source+Sans+Pro:300,400,600|Roboto Mono' rel='stylesheet' type='text/css'>
        <link href='//fonts.googleapis.com/css?family=Dosis:500&text=Vue.js' rel='stylesheet' type='text/css'>

        <link rel="stylesheet" href="/css/page.css">

    Sanskrit Notes संस्कृत टिप्पणी

  <form id="search-form">
    <input type="text" id="search-query-nav" class="search-query st-default-search-input">
  </form>

Notes

  <form id="search-form">
    <input type="text" id="search-query-sidebar" class="search-query st-default-search-input">
  </form>

Notes

                    Markdown Editor

                    GitHub Commits

                    Grid Component

                    Tree View

                    SVG Graph

                    Modal Component

                    Elastic Header

                    Wrapper Component

                    Realtime with deepstreamHub

                    Firebase + Validation

                    TodoMVC

                    HackerNews Clone

Modal Component Example

Features used: component, prop passing, content insertion, transitions.

      Caught a mistake or want to contribute to the documentation?

        Edit this page on Github!

        <link href="//cdn.jsdelivr.net/docsearch.js/1/docsearch.min.css" rel='stylesheet' type='text/css'>
        <link rel="stylesheet" href="/css/search.css">


text:
using System.Collections.Generic;
using System.Linq;
using Microsoft.Practices.ServiceLocation;
using SEV.Domain.Model;

namespace SEV.Domain.Services.Validation
{
    public class BusinessRuleProvider : IBusinessRuleProvider
    {
        public IEnumerable<BusinessRule<TEntity>> GetBusinessRules<TEntity>(DomainEvent domainEvent)
            where TEntity : Entity
        {
            try
            {
                var rules = ServiceLocator.Current.GetAllInstances<BusinessRule<TEntity>>();
// ReSharper disable PossibleMultipleEnumeration
                if (rules == null || !rules.Any())
                {
                    return new BusinessRule<TEntity>[0];
                }
                return rules.Where(r => r.RuleScope.HasFlag(domainEvent)).ToArray();
// ReSharper restore PossibleMultipleEnumeration
            }
            catch (ActivationException)
            {
                return new BusinessRule<TEntity>[0];
            }
        }
    }
}


text:
Get details of a command as received by this device.
> [https://m2x.att.com/developer/documentation/v2/commands#Device-s-View-of-Command-Details](https://m2x.att.com/developer/documentation/v2/commands#Device-s-View-of-Command-Details)

```erlang
m2x_device_command:view(Client, <<"DEVICE-ID">>, <<"COMMAND-ID">>).
```

### process
Mark a command as processed by this device.
> [https://m2x.att.com/developer/documentation/v2/device#Device-Marks-a-Command-as-Processed](https://m2x.att.com/developer/documentation/v2/device#Device-Marks-a-Command-as-Processed)

```erlang
m2x_device_command:process(Client, <<"DEVICE-ID">>, <<"COMMAND-ID">>).
m2x_device_command:process(Client, <<"DEVICE-ID">>, <<"COMMAND-ID">>, Params).
```

### reject
Mark a command as rejected by this device.
> [https://m2x.att.com/developer/documentation/v2/device#Device-Marks-a-Command-as-Rejected](https://m2x.att.com/developer/documentation/v2/device#Device-Marks-a-Command-as-Rejected)

```erlang
m2x_device_command:reject(Client, <<"DEVICE-ID">>, <<"COMMAND-ID">>).
m2x_device_command:reject(Client, <<"DEVICE-ID">>, <<"COMMAND-ID">>, Params).
```


text:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using ToolBelt;
using Playroom;
using System.Xml;

namespace BuildContent
{
    class Program
    {
        public static int Main(string[] args)
        {
            BuildContentTool tool = new BuildContentTool();

            try
            {
		        ((IProcessCommandLine)tool).ProcessCommandLine(args);

				tool.Execute();

                return tool.HasOutputErrors ? 1 : 0;
            }
            catch (Exception e)
            {
                ConsoleUtility.WriteMessage(MessageType.Error, e.ToString());
                return 1;
            }

        }
    }
}


text:
package org.scavenge.imprint;

public class ImprintConfig
{
  private static ImprintConfig instance = createDefault();
  public final String CMD_NAME;
  public final String DB_HOSTNAME;
  public final int DB_PORT;
  public final String DB_USER;
  public final String DB_PASSWORD;

  ImprintConfig(String cmdLookupName, String hostname, int port, String user, String password)
  {
    this.CMD_NAME = cmdLookupName;
    this.DB_PORT = port;
    this.DB_USER = user;
    this.DB_PASSWORD = password;
    this.DB_HOSTNAME = hostname;
  }

  public static ImprintConfig getInstance()
  {
    return instance;
  }

  public static void loadDefaultFile()
  {

  }

  private static ImprintConfig createDefault()
  {
    return new ImprintConfig("imprint", "*", 3306, "imprint", "*");
  }
}


text:
<?php

namespace lithium\tests\mocks\template\helper;

class MockHtmlRenderer extends \lithium\template\view\Renderer {

	public function render($template, $data = array(), array $options = array()) {
	}
}

?>


text:
<script>
$('#myTooltip').on('hidden.bs.tooltip', function () {
  // do something…
})
</script>


text:
package com.valtech.source.dependometer.app.core.provider;

/**
 * @author Dietmar Menges (dietmar.menges@valtech.de)
 */
public interface MetricIf extends Comparable<MetricIf>
{
   public boolean hasIndex();

   public String getName();

   public String getDescription();

   public String getValueAsString();
}


text:
ACCEPTED

#### According to
Index Fungorum

#### Published in
Fl. gén. env. Paris (Paris) 1: 261 (1826)

#### Original name
Cladoporus fulvus Chevall.

### Remarks
null


text:
@interface CustomPlacemark : NSObject<MKAnnotation> {
	CLLocationCoordinate2D coordinate;
	MKCoordinateRegion coordinateRegion;
	NSString *title;
	NSString *message;
}
@property (nonatomic, readonly) CLLocationCoordinate2D coordinate;
@property (nonatomic, readonly) MKCoordinateRegion coordinateRegion;
@property (nonatomic, copy) NSString *title;
@property (nonatomic, retain) NSString *message;

-(id)initWithRegion:(MKCoordinateRegion) coordRegion;
@end


text: Samples for JS-evening, winter 2015


text:
@interface PodsDummy_Pods_Minsta : NSObject
@end
@implementation PodsDummy_Pods_Minsta
@end


text:
'use strict';

const _ = require('lodash'),
  chalk = require('chalk');

function enforceFastTest(obj) {
  let title,
    report,
    speed = obj.speed,
    duration = obj.duration;

  // unit tests should never take longer than 15 seconds (we shouldn't be testing IO, because that's not our code)
  if (duration && speed !== 'fast') {
    title = obj.title;
    while (obj.parent) {
      obj = obj.parent;
      title = obj.title + ' ' + title;
    }

    report = speed ? duration + 'ms ' + speed : duration + 'ms';

    report = speed === 'slow' ? chalk.red(report) : chalk.yellow(report);

    return chalk.dim([title, report].join(' '));
  }
}

function enforceFastTestSuite(obj) {
  let messages = [];

  messages = messages.concat(_.filter(_.map(obj.tests, enforceFastTest), _.identity));
  messages = messages.concat(_.flattenDeep(_.map(obj.suites, enforceFastTestSuite)));
  return messages;
}

function enforcePerformance(obj) {
  let messages;

  obj = obj._runnable;
  while (obj.parent) { obj = obj.parent; }

  messages = enforceFastTestSuite(obj);

  if (messages.length) {

    messages = ['\n\nPerformance Report:'].concat(messages);
    console.log(messages.join('\n'));
  }
}

module.exports = enforcePerformance;


text:
title: TEDxHamburg 2011
date: 2011-05-24 15:01:23 +0200
excerpt: Ein Bericht über die TEDxHamburg von 2011.
image: /images/2011/tedxhamburg-2011.jpg
categories: Events
tags: [Conference, German, TED, TEDx]
permalink: /tedxhamburg-2011
lang: de
layout: post
---
Ich war mittlerweile schon auf drei TEDx in Deutschland: [TEDxBerlin 2009](/tedxberlin), [TEDxHamburg 2010](/tedxhamburg-2010) und [TEDxBerlin 2010](http://www.tedxberlin.de/review-2010). Wie ich gerade feststelle, habe ich es wohl versäumt, etwas über die TEDxBerlin 2010 zu bloggen. Ärgerlich. Die TEDxHamburg 2011 war also die vierte, der ich beiwohnen durfte. Wer mehr über das Konzept TEDx erfahren möchte, dem empfehle ich die ersten beiden Artikel zu lesen.

Das Thema dieser TEDxHamburg war [Realities Rebuilt](http://www.tedxhamburg.de/review-2011).

Morgens erst zu vielleicht 80 % gefüllt, gab es ab der zweiten Session um die Mittagszeit herum keine freien Stühle mehr. Das war auch angemessen, da in jeder der drei Sessions sehr interessante Talks dabei waren, die ich ungern versäumt hätte.

Gut fand ich dieses Jahr die sogenannten Short Talks, die nicht über 18 Minuten gehen, sondern mit ca. 5 Minuten deutlich kürzer sind. Das ist meistens absolut ausreichend, um die Idee oder das Projekt zu präsentieren. Viele 18-minütige Talks sind einfach zu langatmig.

Das witzige Zitat <q>Barfuß und in Lederhose</q> stammt aus dem [sehenswerten Video-Beitrag](http://www.interviewproject.de/videos/41/) des [Interview Project Germany](http://www.interviewproject.de/), welches von dem bekannten US-Regisseur [David Lynch](https://www.imdb.com/name/nm0000186/) mitgestaltet wird.

## Mein Eindruck

Insgesamt war das Niveau der Talks auf der TEDx Hamburg sehr hoch, sodass ich froh bin, meine beruflichen Verpflichtungen doch weniger stark priorisiert und mein Ticket genutzt zu haben. Es war zwar der eine oder andere Talk dabei, der leider weniger interessant gehalten wurde, aber es hielt sich in Grenzen. Es ist schade, wenn spannende Themen langweilig gehalten werden und dadurch nicht ihr Potenzial entfalten können.

Besonders schade fand ich, dass ich etwas das Gefühl bekommen hatte, dass ein paar Inhalte zu kommerzieller Natur waren. Das wurde mir auch von ein paar anderen Teilnehmern bestätigt.

## Besonders gut und meine klaren Favoriten

Green & Sexy von Thomas Auer:

Celebrating Crisis – Nature's Key to Our Future von Elisabet Sahtouris:

## Sehr interessant

- [mPedigree](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-bright-simons-mpedigree) von Bright B. Simons
- [Carbohydrate Vaccines – Killing the Deadliest Killers](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-peter-h-seeberger-carbohydrate-vaccines) von Peter H. Seeberger
- [3D Printing – This Century's most disruptive Innovation!?](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-david-f-flanders-3d-printing-this-centurys-most-disruptive-innovation) von David F. Flanders
- [The Contribution of Brain Research to Male Self-Understanding](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-gerald-huether-the-contribution-of-brain-research-to-male-self-understanding) von Gerald Hüther
- [What's Wrong with Humanitarian Aid? A Journalist's Journey](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-linda-polman-whats-wrong-with-humanitarian-aid-a-journalists-journey) von Linda Polman
- [Interview Project Germany – Episode 34, Hans-Dieter](http://www.interviewproject.de/videos/) von David Lynch

## Die immer interessanten gezeigten TED-Videos

[The Invention That Unlocked a Locked-in Artist](https://www.ted.com/talks/mick_ebeling_the_invention_that_unlocked_a_locked_in_artist) von [Mick Ebeling](https://www.ted.com/speakers/mick_ebeling)

[The Greatest TED Talk Ever Sold](https://www.ted.com/talks/morgan_spurlock_the_greatest_ted_talk_ever_sold) von [Morgan Spurlock](https://www.ted.com/speakers/morgan_spurlock)

[The Birth of a Word](https://www.ted.com/talks/deb_roy_the_birth_of_a_word) von [Deb Roy](https://www.ted.com/speakers/deb_roy)

## Weitere

- [.hiv](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-michael-trautmann-hiv) von Michael Trautmann
- [The Power of Art Thinking](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-joerg-reckhenrich-the-power-of-art-thinking) von Jörg Reckhenrich
- [Service Design – Invest in Customer Insights](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-joost-holthuis-service-design) von Joost Holthuis
- [Trinkwasser für die Welt](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-christian-wiebe-clear-like-water) von Christian Wiebe
- Motiv Zukunft von Wolfang Müller-Pietrella
- [WZGÜZSK](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-friedrich-von-borries-wzguezsk) von Friedrich von Börries
- SoVIET – A Combination fo Video and Social Networks von Matthias Oelmann

TEDx-typisch wurden wir musikalisch von [Alin Coen](http://www.tedxhamburg.de/tedxhamburg-2011-realities-rebuilt-alin-coen-performance) und dem Duo Stefan Keller & Martin Grütter unterhalten, wobei das eine immer mehr eine Performance denn reine musikalische Darbietung ist.

## Das "Social Media Experiment" der TEDxHamburg

Tweets, die mit dem Hashtag [#TEDxHH](https://twitter.com/hashtag/TEDxHH) versendet wurden, werden "live" als grafische Representationen auf drei LED-Wänden gezeigt. Langsam pulsierende Blasen in verschiedenen Farben. Sieht nett aus, wirkt aber irgendwie beliebig und überträgt kaum Informationen. Na ja.

Der Twitter-Feed zum Nachlesen findet sich entweder unter [#TEDxHH](https://twitter.com/hashtag/TEDxHH) oder [#TEDxHamburg](https://twitter.com/hashtag/TEDxHamburg).


text:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS>
<TS version="2.0">
<context>
    <name></name>
    <message id="meego_video_title">
        <location filename="../src/appvideospage.cpp" line="52"/>
        <location filename="../src/appwindow.cpp" line="150"/>
        <source>Video player</source>
        <translation type="unfinished">Video player</translation>
    </message>
    <message id="meego_video_search">
        <location filename="../src/appwindow.cpp" line="92"/>
        <source>Search</source>
        <translation type="unfinished">Search</translation>
    </message>
    <message id="meego_video_show_all">
        <location filename="../src/appwindow.cpp" line="97"/>
        <source>Show all</source>
        <translation type="unfinished">Show all</translation>
    </message>
    <message id="meego_video_my_movies">
        <location filename="../src/appwindow.cpp" line="102"/>
        <source>My Movies</source>
        <translation type="unfinished">My Movies</translation>
    </message>
    <message id="meego_video_films">
        <location filename="../src/appwindow.cpp" line="107"/>
        <source>Films</source>
        <translation type="unfinished">Films</translation>
    </message>
    <message id="meego_video_tv_shows">
        <location filename="../src/appwindow.cpp" line="112"/>
        <source>TV Shows</source>
        <translation type="unfinished">TV Shows</translation>
    </message>
    <message id="meego_video_recently_added">
        <location filename="../src/appwindow.cpp" line="117"/>
        <source>Recently Added</source>
        <translation type="unfinished">Recently Added</translation>
    </message>
    <message id="meego_video_recently_viewed">
        <location filename="../src/appwindow.cpp" line="122"/>
        <source>Recently Viewed</source>
        <translation type="unfinished">Recently Viewed</translation>
    </message>
    <message id="meego_video_favorites">
        <location filename="../src/appwindow.cpp" line="127"/>
        <source>Favorites</source>
        <translation type="unfinished">Favorites</translation>
    </message>
    <message id="meegovideo_show_this_message_again">
        <location filename="../src/errormessage.cpp" line="37"/>
        <source>Show this message again</source>
        <translation type="unfinished">Show this message again</translation>
    </message>
    <message id="meegovideo_app_error">
        <location filename="../src/errormessage.cpp" line="52"/>
        <source>%1 - Error</source>
        <translation type="unfinished">%1 - Error</translation>
    </message>
    <message id="Size: %1">
        <location filename="../src/videoinfowidget.cpp" line="140"/>
        <source></source>
        <oldsource>Size: %1</oldsource>
        <translation type="unfinished">Size: %1</translation>
    </message>
    <message id="BitRate: %1">
        <location filename="../src/videoinfowidget.cpp" line="141"/>
        <source></source>
        <oldsource>BitRate: %1</oldsource>
        <translation type="unfinished">BitRate: %1</translation>
    </message>
    <message id="Video Codec: %1">
        <location filename="../src/videoinfowidget.cpp" line="142"/>
        <source></source>
        <oldsource>Video Codec: %1</oldsource>
        <translation type="unfinished">Video Codec: %1</translation>
    </message>
    <message id="Date Created: %1">
        <location filename="../src/videoinfowidget.cpp" line="144"/>
        <source></source>
        <oldsource>Date Created: %1</oldsource>
        <translation type="unfinished">Date Created: %1</translation>
    </message>
    <message id="Last Viewed: %1">
        <location filename="../src/videoinfowidget.cpp" line="145"/>
        <source></source>
        <oldsource>Last Viewed: %1</oldsource>
        <translation type="unfinished">Last Viewed: %1</translation>
    </message>
    <message id="meegovideo_play">
        <location filename="../src/videoslist.cpp" line="35"/>
        <source>Play</source>
        <translation type="unfinished">Play</translation>
    </message>
    <message id="meegovideo_favourite">
        <location filename="../src/videoslist.cpp" line="40"/>
        <source>Favourite</source>
        <translation type="unfinished">Favourite</translation>
    </message>
    <message id="meegovideo_info">
        <location filename="../src/videoslist.cpp" line="45"/>
        <source>Info</source>
        <translation type="unfinished">Info</translation>
    </message>
    <message id="meegovideo_delete">
        <location filename="../src/videoslist.cpp" line="50"/>
        <source>Delete</source>
        <translation type="unfinished">Delete</translation>
    </message>
</context>
<context>
    <name>ThumbnailManager</name>
    <message>
        <location filename="../src/thumbnailmanager.cpp" line="169"/>
        <location filename="../src/thumbnailmanager.cpp" line="178"/>
        <location filename="../src/thumbnailmanager.cpp" line="187"/>
        <location filename="../src/thumbnailmanager.cpp" line="196"/>
        <location filename="../src/thumbnailmanager.cpp" line="205"/>
        <location filename="../src/thumbnailmanager.cpp" line="242"/>
        <location filename="../src/thumbnailmanager.cpp" line="368"/>
        <location filename="../src/thumbnailmanager.cpp" line="369"/>
        <location filename="../src/thumbnailmanager.cpp" line="370"/>
        <location filename="../src/thumbnailmanager.cpp" line="373"/>
        <location filename="../src/thumbnailmanager.cpp" line="374"/>
        <location filename="../src/thumbnailmanager.cpp" line="375"/>
        <source>Unknown</source>
        <translation type="unfinished"></translation>
    </message>
</context>
<context>
    <name>ThumbnailManagerThread</name>
    <message>
        <location filename="../src/thumbnailmanagerthread.cpp" line="147"/>
        <location filename="../src/thumbnailmanagerthread.cpp" line="148"/>
        <location filename="../src/thumbnailmanagerthread.cpp" line="149"/>
        <location filename="../src/thumbnailmanagerthread.cpp" line="152"/>
        <location filename="../src/thumbnailmanagerthread.cpp" line="153"/>
        <location filename="../src/thumbnailmanagerthread.cpp" line="154"/>
        <source>Unknown</source>
        <translation type="unfinished"></translation>
    </message>
</context>
<context>
    <name>VideosList</name>
    <message>
        <location filename="../src/videoslist.cpp" line="245"/>
        <source>Delete</source>
        <translation type="unfinished">Delete</translation>
    </message>
    <message>
        <location filename="../src/videoslist.cpp" line="245"/>
        <source>Do you want to permanently delete %1?</source>
        <translation type="unfinished"></translation>
    </message>
</context>
<context>
    <name>VideosListModel</name>
    <message>
        <location filename="../src/videoslistmodel.cpp" line="442"/>
        <location filename="../src/videoslistmodel.cpp" line="447"/>
        <source>Unknown</source>
        <translation type="unfinished"></translation>
    </message>
</context>
</TS>


text:
.class Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;
.super Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$State;
.source "TargetHandlePanel.java"

# annotations
.annotation system Ldalvik/annotation/EnclosingClass;
    value = Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;
.end annotation

.annotation system Ldalvik/annotation/InnerClass;
    accessFlags = 0x0
    name = "StateUnlockHover"
.end annotation

# instance fields
.field final synthetic this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

# direct methods
.method constructor <init>(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)V
    .locals 0
    .parameter

    .prologue
    .line 448
    iput-object p1, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    invoke-direct {p0, p1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$State;-><init>(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)V

    return-void
.end method

# virtual methods
.method public draw()V
    .locals 3

    .prologue
    .line 457
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetUnlock:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1100(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_VISIBLE:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    const/4 v2, 0x1

    invoke-virtual {p0, v0, v1, v2}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;Z)V

    .line 458
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetMessage:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1700(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_ALPHA:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    invoke-virtual {p0, v0, v1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;)V

    .line 459
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetCamera:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1000(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_ALPHA:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    invoke-virtual {p0, v0, v1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;)V

    .line 460
    invoke-static {}, Lcom/baidu/internal/keyguard/hotword/WordList;->wordListAvaliable()Z

    move-result v0

    if-eqz v0, :cond_1

    .line 461
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetRefresh:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$800(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_ALPHA:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    invoke-virtual {p0, v0, v1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;)V

    .line 465
    :goto_0
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mUnreadCount:I
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1600(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)I

    move-result v0

    if-lez v0, :cond_0

    .line 466
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetMessage:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1700(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_VISIBLE:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    invoke-virtual {p0, v0, v1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;)V

    .line 468
    :cond_0
    return-void

    .line 463
    :cond_1
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mTargetRefresh2:Landroid/widget/ImageView;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$900(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Landroid/widget/ImageView;

    move-result-object v0

    sget-object v1, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;->STATE_ALPHA:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;

    invoke-virtual {p0, v0, v1}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->setViewState(Landroid/view/View;Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$ViewState;)V

    goto :goto_0
.end method

.method public enter(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$State;)V
    .locals 2
    .parameter "oldState"

    .prologue
    .line 451
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #calls: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->vibrate()V
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$1800(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)V

    .line 452
    iget-object v0, p0, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel$StateUnlockHover;->this$0:Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;

    #getter for: Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->mGallery:Lcom/baidu/internal/keyguard/hotword/ConstellationGallery;
    invoke-static {v0}, Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;->access$600(Lcom/baidu/internal/keyguard/hotword/TargetHandlePanel;)Lcom/baidu/internal/keyguard/hotword/ConstellationGallery;

    move-result-object v0

    const/4 v1, 0x1

    invoke-virtual {v0, v1}, Lcom/baidu/internal/keyguard/hotword/ConstellationGallery;->setTransparent(Z)V

    .line 453
    return-void
.end method

.method public getIntent(Landroid/content/Context;)Landroid/content/Intent;
    .locals 2
    .parameter "context"

    .prologue
    .line 472
    invoke-static {p1}, Lcom/baidu/internal/keyguard/hotword/UbcUtils;->getInstance(Landroid/content/Context;)Lcom/baidu/internal/keyguard/hotword/UbcUtils;

    move-result-object v0

    const-string v1, "0200"

    invoke-virtual {v0, v1}, Lcom/baidu/internal/keyguard/hotword/UbcUtils;->addStatistic(Ljava/lang/String;)V

    .line 473
    const/4 v0, 0x0

    return-object v0
.end method


text:
package finspace

import (
	"net/http"
	"net/http/httptest"
	"strings"
	"testing"

	"github.com/aws/aws-sdk-go/aws"
	"github.com/aws/aws-sdk-go/awstesting/unit"
)

func TestClientContentType(t *testing.T) {
	sess := unit.Session.Copy()

	server := httptest.NewServer(http.HandlerFunc(
		func(w http.ResponseWriter, r *http.Request) {
			contentType := r.Header.Get("Content-Type")
			if e, a := contentType, "application/x-amz-json-1.1"; !strings.EqualFold(e, a) {
				t.Errorf("expect %v content-type, got %v", e, a)
			}
		},
	))
	defer server.Close()

	client := New(sess, &aws.Config{Endpoint: &server.URL})
	_, err := client.CreateEnvironment(&CreateEnvironmentInput{
		Name: aws.String("fake name"),
	})
	if err != nil {
		t.Fatalf("expect no error, got %v", err)
	}
}


text:
using UnityEngine.Assertions;

namespace NPBehave
{
    public abstract class Container : Node
    {
        private bool collapse = false;
        public bool Collapse
        {
            get
            {
                return collapse;
            }
            set
            {
                collapse = value;
            }
        }

        public Container(string name) : base(name)
        {
        }

        public void ChildStopped(Node child, bool succeeded)
        {
            // Assert.AreNotEqual(this.currentState, State.INACTIVE, "The Child " + child.Name + " of Container " + this.Name + " was stopped while the container was inactive. PATH: " + GetPath());
            Assert.AreNotEqual(this.currentState, State.INACTIVE, "A Child of a Container was stopped while the container was inactive.");
            this.DoChildStopped(child, succeeded);
        }

        protected abstract void DoChildStopped(Node child, bool succeeded);

#if UNITY_EDITOR
        public abstract Node[] DebugChildren
        {
            get;
        }
#endif
    }
}


text:
class AddBalanceExpiredOnBalance < ActiveRecord::Migration
  def up
    execute %Q{
    create or replace function public.can_expire_on_balance(public.balance_transactions)
        returns boolean
            language sql
                as $$
                   select (case when $1.event_name = 'contribution_refund' and ($1.created_at + '90 days'::interval < now()) then
                       not exists (select true from public.balance_transactions t
                                                  where t.user_id=$1.user_id
                                                      and t.id > $1.id
                                                      and t.event_name in ('balance_transfer_request','balance_transfer_project')
                                              )
                       and not exists (
                                       select true from public.balance_transactions t
                                           where t.user_id = $1.user_id
                                                              and t.contribution_id = $1.contribution_id
                                                              and t.event_name = 'balance_expired'
                                                  )
                                      else false end);
                                          $$;

}
  end

  def down
		execute %Q{
			drop function public.can_expire_on_balance(public.balance_transactions);
		}
  end
end


text:
module OauthHelper
  def ldap_enabled?
    Gitlab.config.ldap.enabled
  end

  def default_providers
    [:twitter, :github, :google_oauth2, :ldap]
  end

  def enabled_oauth_providers
    Devise.omniauth_providers
  end

  def enabled_social_providers
    enabled_oauth_providers.select do |name|
      [:twitter, :github, :google_oauth2].include?(name.to_sym)
    end
  end
end