Add JetStream to PerformanceTests
[WebKit-https.git] / PerformanceTests / JetStream / Octane2 / typescript-input.js
1 var compiler_input = "//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\nmodule TypeScript {\n    export class AstLogger {\n\n        constructor (public logger: ILogger) { }\n\n        public logScript(script: TypeScript.Script): void {\n            this.logLinemap(script.locationInfo.lineMap);\n\n            var stack: AST[]= [];\n\n            var pre = (cur: TypeScript.AST, parent: TypeScript.AST) => {\n                stack.push(cur);\n                var indent = (stack.length - 1) * 2;\n                this.logComments(script, cur.preComments, indent);\n                this.logNode(script, cur, indent);\n                this.logComments(script, cur.postComments, indent);\n                return cur;\n            }\n\n            var post = (cur: TypeScript.AST, parent: TypeScript.AST) => {\n                stack.pop();\n                return cur;\n            }\n\n            TypeScript.getAstWalkerFactory().walk(script, pre, post);\n        }\n\n\n        public logNode(script: TypeScript.Script, cur: TypeScript.AST, indent: number) {\n            var msg = this.addPadding(\"\", indent, \"| \", true);\n\n            msg = msg.concat(\"+ \" + cur.treeViewLabel());\n            msg = this.addPadding(msg, 70, \" \", false);\n\n            msg = msg + this.addLineColumn(script, cur.minChar);\n            msg = this.addPadding(msg, 80, \" \", false);\n\n            msg = msg + \"=> \";\n            msg = msg + this.addLineColumn(script, cur.limChar);\n            msg = this.addPadding(msg, 102, \" \", false);\n\n            msg = msg.concat(\"[\" + this.addPadding(cur.minChar.toString(), 1, \" \", true) + \", \" + this.addPadding(cur.limChar.toString(), 1, \" \", true) + \"]\");\n\n            msg = this.addPadding(msg, 115, \" \", false);\n            msg = msg.concat(\"sym=\" + (<any>cur).sym);\n\n            msg = this.addPadding(msg, 135, \" \", false);\n            msg = msg.concat(\"type=\" + (cur.type === null ? \"null\" : cur.type.getTypeName()));\n            this.logger.log(msg);\n        }\n\n        private logComments(script: TypeScript.Script, comments: TypeScript.AST[], indent: number) {\n            if (comments == null)\n                return;\n\n            for (var i = 0; i < comments.length; i++) {\n                this.logNode(script, comments[i], indent);\n            }\n        }\n\n        public logLinemap(linemap: number[]) {\n            var result = \"[\";\n            for (var i = 0; i < linemap.length; i++) {\n                if (i > 0)\n                    result += \",\";\n                result += linemap[i];\n            }\n            result += \"]\";\n            this.logger.log(\"linemap: \" + result);\n        }\n\n        private addPadding(s: string, targetLength: number, paddingString: string, leftPadding: bool): string {\n            var result = (leftPadding ? \"\" : s);\n            for (var i = s.length; i < targetLength; i++) {\n                result = result + paddingString;\n            }\n            result = result + (leftPadding ? s : \"\");\n            return result;\n        }\n\n        private addLineColumn(script: TypeScript.Script, position: number): string {\n            // just for calling getSourceLineColFromMap\n            var lineInfo = {\n                line: -1,\n                col: -1\n            }\n            TypeScript.getSourceLineColFromMap(lineInfo, position, script.locationInfo.lineMap);\n\n            if (lineInfo.col !== -1) {\n                lineInfo.col++; //TODO: function above seems to consider line as 1-based, and column as 0-based\n            }\n\n            return \"(\" + lineInfo.line + \", \" + lineInfo.col + \")\";\n        }\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export function lastOf(items: any[]): any {\n        return (items === null || items.length === 0) ? null : items[items.length - 1];\n    }\n\n    export function max(a: number, b: number): number {\n        return a >= b ? a : b;\n    }\n\n    export function min(a: number, b: number): number {\n        return a <= b ? a : b;\n    }\n\n    //\n    // Helper class representing a path from a root ast node to a (grand)child ast node.\n    // This is helpful as our tree don't have parents.\n    //\n    export class AstPath {\n        public asts: TypeScript.AST[] = [];\n        public top: number = -1;\n\n        static reverseIndexOf(items: any[], index: number): any {\n            return (items === null || items.length <= index) ? null : items[items.length - index - 1];\n        }\n\n        public clone(): AstPath {\n            var clone = new AstPath();\n            clone.asts = this.asts.map((value) => { return value; });\n            clone.top = this.top;\n            return clone;\n        }\n\n        public pop(): TypeScript.AST {\n            var head = this.ast();\n            this.up();\n\n            while (this.asts.length > this.count()) {\n                this.asts.pop();\n            }\n            return head;\n        }\n\n        public push(ast: TypeScript.AST) {\n            while (this.asts.length > this.count()) {\n                this.asts.pop();\n            }\n            this.top = this.asts.length;\n            this.asts.push(ast);\n        }\n\n        public up() {\n            if (this.top <= -1)\n                throw new Error(\"Invalid call to 'up'\");\n            this.top--;\n        }\n\n        public down() {\n            if (this.top == this.ast.length - 1)\n                throw new Error(\"Invalid call to 'down'\");\n            this.top++;\n        }\n\n        public nodeType(): TypeScript.NodeType {\n            if (this.ast() == null)\n                return TypeScript.NodeType.None;\n            return this.ast().nodeType;\n        }\n\n        public ast() {\n            return <TypeScript.AST>AstPath.reverseIndexOf(this.asts, this.asts.length - (this.top + 1));\n        }\n\n        public parent() {\n            return <TypeScript.AST>AstPath.reverseIndexOf(this.asts, this.asts.length - this.top);\n        }\n\n        public count() {\n            return this.top + 1;\n        }\n\n        public get(index: number): TypeScript.AST {\n            return this.asts[index];\n        }\n\n        public isNameOfClass(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.ClassDeclaration) &&\n                ((<TypeScript.InterfaceDeclaration>this.parent()).name === this.ast());\n        }\n\n        public isNameOfInterface(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.InterfaceDeclaration) &&\n                ((<TypeScript.InterfaceDeclaration>this.parent()).name === this.ast());\n        }\n\n        public isNameOfArgument(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.ArgDecl) &&\n                ((<TypeScript.ArgDecl>this.parent()).id === this.ast());\n        }\n\n        public isNameOfVariable(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.VarDecl) &&\n                ((<TypeScript.VarDecl>this.parent()).id === this.ast());\n        }\n\n        public isNameOfModule(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.ModuleDeclaration) &&\n                ((<TypeScript.ModuleDeclaration>this.parent()).name === this.ast());\n        }\n\n        public isNameOfFunction(): bool {\n            if (this.ast() === null || this.parent() === null)\n                return false;\n\n            return (this.ast().nodeType === TypeScript.NodeType.Name) &&\n                (this.parent().nodeType === TypeScript.NodeType.FuncDecl) &&\n                ((<TypeScript.FuncDecl>this.parent()).name === this.ast());\n        }\n\n        public isChildOfScript(): bool {\n            var ast = lastOf(this.asts);\n            return this.count() >= 3 &&\n                this.asts[this.top] === ast &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.Script;\n        }\n\n        public isChildOfModule(): bool {\n            var ast = lastOf(this.asts);\n            return this.count() >= 3 &&\n                this.asts[this.top] === ast &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.ModuleDeclaration;\n        }\n\n        public isChildOfClass(): bool {\n            var ast = lastOf(this.asts);\n            return this.count() >= 3 &&\n                this.asts[this.top] === ast &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.ClassDeclaration;\n        }\n\n        public isArgumentOfClassConstructor(): bool {\n            var ast = lastOf(this.asts);\n            return this.count() >= 5 &&\n                this.asts[this.top] === ast &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.FuncDecl &&\n                this.asts[this.top - 3].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 4].nodeType === TypeScript.NodeType.ClassDeclaration &&\n                ((<TypeScript.FuncDecl>this.asts[this.top - 2]).isConstructor) &&\n                ((<TypeScript.FuncDecl>this.asts[this.top - 2]).arguments === this.asts[this.top - 1]) &&\n                ((<TypeScript.ClassDeclaration>this.asts[this.top - 4]).constructorDecl === this.asts[this.top - 2]);\n        }\n\n        public isChildOfInterface(): bool {\n            var ast = lastOf(this.asts);\n            return this.count() >= 3 &&\n                this.asts[this.top] === ast &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.InterfaceDeclaration;\n        }\n\n        public isTopLevelImplicitModule() {\n            return this.count() >= 1 &&\n                this.asts[this.top].nodeType === TypeScript.NodeType.ModuleDeclaration &&\n                TypeScript.hasFlag((<TypeScript.ModuleDeclaration>this.asts[this.top]).modFlags, TypeScript.ModuleFlags.IsWholeFile);\n        }\n\n        public isBodyOfTopLevelImplicitModule() {\n            return this.count() >= 2 &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ModuleDeclaration &&\n                 (<TypeScript.ModuleDeclaration>this.asts[this.top - 1]).members == this.asts[this.top - 0] &&\n                TypeScript.hasFlag((<TypeScript.ModuleDeclaration>this.asts[this.top - 1]).modFlags, TypeScript.ModuleFlags.IsWholeFile);\n        }\n\n        public isBodyOfScript(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Script &&\n                 (<TypeScript.Script>this.asts[this.top - 1]).bod == this.asts[this.top - 0];\n        }\n\n        public isBodyOfSwitch(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Switch &&\n                 (<TypeScript.SwitchStatement>this.asts[this.top - 1]).caseList == this.asts[this.top - 0];\n        }\n\n        public isBodyOfModule(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ModuleDeclaration &&\n                 (<TypeScript.ModuleDeclaration>this.asts[this.top - 1]).members == this.asts[this.top - 0];\n        }\n\n        public isBodyOfClass(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ClassDeclaration &&\n                 (<TypeScript.ClassDeclaration>this.asts[this.top - 1]).members == this.asts[this.top - 0];\n        }\n\n        public isBodyOfFunction(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.FuncDecl &&\n                 (<TypeScript.FuncDecl>this.asts[this.top - 1]).bod == this.asts[this.top - 0];\n        }\n\n        public isBodyOfInterface(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.InterfaceDeclaration &&\n                 (<TypeScript.InterfaceDeclaration>this.asts[this.top - 1]).members == this.asts[this.top - 0];\n        }\n\n        public isBodyOfBlock(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Block &&\n                (<TypeScript.Block>this.asts[this.top - 1]).statements == this.asts[this.top - 0];\n        }\n\n        public isBodyOfFor(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.For &&\n                (<TypeScript.ForStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfCase(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Case &&\n                (<TypeScript.CaseStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfTry(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Try &&\n                (<TypeScript.Try>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfCatch(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Catch &&\n                (<TypeScript.Catch>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfDoWhile(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.DoWhile &&\n                (<TypeScript.DoWhileStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfWhile(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.While &&\n                (<TypeScript.WhileStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfForIn(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ForIn &&\n                (<TypeScript.ForInStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfWith(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.With &&\n                (<TypeScript.WithStatement>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isBodyOfFinally(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Finally &&\n                (<TypeScript.Finally>this.asts[this.top - 1]).body == this.asts[this.top - 0];\n        }\n\n        public isCaseOfSwitch(): bool {\n            return this.count() >= 3 &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.Switch &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.SwitchStatement>this.asts[this.top - 2]).caseList == this.asts[this.top - 1];\n        }\n\n        public isDefaultCaseOfSwitch(): bool {\n            return this.count() >= 3 &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.Switch &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.SwitchStatement>this.asts[this.top - 2]).caseList == this.asts[this.top - 1] &&\n                (<TypeScript.SwitchStatement>this.asts[this.top - 2]).defaultCase == this.asts[this.top - 0];\n        }\n\n        public isListOfObjectLit(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ObjectLit &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.UnaryExpression>this.asts[this.top - 1]).operand == this.asts[this.top - 0];\n        }\n\n        public isBodyOfObjectLit(): bool {\n            return this.isListOfObjectLit();\n        }\n\n        public isEmptyListOfObjectLit(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ObjectLit &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.UnaryExpression>this.asts[this.top - 1]).operand == this.asts[this.top - 0] &&\n                (<TypeScript.ASTList>this.asts[this.top - 0]).members.length == 0;\n        }\n\n        public isMemberOfObjectLit(): bool {\n            return this.count() >= 3 &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.ObjectLit &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.Member &&\n                (<TypeScript.UnaryExpression>this.asts[this.top - 2]).operand == this.asts[this.top - 1];\n        }\n\n        public isNameOfMemberOfObjectLit(): bool {\n            return this.count() >= 4 &&\n                this.asts[this.top - 3].nodeType === TypeScript.NodeType.ObjectLit &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Member &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.Name &&\n                (<TypeScript.UnaryExpression>this.asts[this.top - 3]).operand == this.asts[this.top - 2];\n        }\n\n        public isListOfArrayLit(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.ArrayLit &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.UnaryExpression>this.asts[this.top - 1]).operand == this.asts[this.top - 0];\n        }\n\n        public isTargetOfMember(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Member &&\n                (<TypeScript.BinaryExpression>this.asts[this.top - 1]).operand1 === this.asts[this.top - 0];\n        }\n\n        public isMemberOfMember(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Member &&\n                (<TypeScript.BinaryExpression>this.asts[this.top - 1]).operand2 === this.asts[this.top - 0];\n        }\n\n        public isItemOfList(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List;\n            //(<Tools.ASTList>this.asts[this.top - 1]).operand2 === this.asts[this.top - 0];\n        }\n\n        public isThenOfIf(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.If &&\n                (<TypeScript.IfStatement>this.asts[this.top - 1]).thenBod == this.asts[this.top - 0];\n        }\n\n        public isElseOfIf(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.If &&\n                (<TypeScript.IfStatement>this.asts[this.top - 1]).elseBod == this.asts[this.top - 0];\n        }\n\n        public isBodyOfDefaultCase(): bool {\n            return this.isBodyOfCase();\n        }\n\n        public isSingleStatementList(): bool {\n            return this.count() >= 1 &&\n                this.asts[this.top].nodeType === TypeScript.NodeType.List &&\n                (<TypeScript.ASTList>this.asts[this.top]).members.length === 1;\n        }\n\n        public isArgumentListOfFunction(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.FuncDecl &&\n                (<TypeScript.FuncDecl>this.asts[this.top - 1]).arguments === this.asts[this.top - 0];\n        }\n\n        public isArgumentOfFunction(): bool {\n            return this.count() >= 3 &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 2].nodeType === TypeScript.NodeType.FuncDecl &&\n                (<TypeScript.FuncDecl>this.asts[this.top - 2]).arguments === this.asts[this.top - 1];\n        }\n\n        public isArgumentListOfCall(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.Call &&\n                (<TypeScript.CallExpression>this.asts[this.top - 1]).arguments === this.asts[this.top - 0];\n        }\n\n        public isArgumentListOfNew(): bool {\n            return this.count() >= 2 &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.List &&\n                this.asts[this.top - 1].nodeType === TypeScript.NodeType.New &&\n                (<TypeScript.CallExpression>this.asts[this.top - 1]).arguments === this.asts[this.top - 0];\n        }\n\n        public isSynthesizedBlock(): bool {\n            return this.count() >= 1 &&\n                this.asts[this.top - 0].nodeType === TypeScript.NodeType.Block &&\n                (<TypeScript.Block>this.asts[this.top - 0]).isStatementBlock === false;\n        }\n    }\n\n    export function isValidAstNode(ast: TypeScript.ASTSpan): bool {\n        if (ast === null)\n            return false;\n\n        if (ast.minChar === -1 || ast.limChar === -1)\n            return false;\n\n        return true;\n    }\n\n    export class AstPathContext {\n        public path = new TypeScript.AstPath();\n    }\n\n    export enum GetAstPathOptions {\n        Default = 0,\n        EdgeInclusive = 1,\n        //We need this options dealing with an AST coming from an incomplete AST. For example:\n        //     class foo { // r\n        // If we ask for the AST at the position after the \"r\" character, we won't see we are \n        // inside a comment, because the \"class\" AST node has a limChar corresponding to the position of \n        // the \"{\" character, meaning we don't traverse the tree down to the stmt list of the class, meaning\n        // we don't find the \"precomment\" attached to the errorneous empty stmt.\n        //TODO: It would be nice to be able to get rid of this.\n        DontPruneSearchBasedOnPosition = 1 << 1,\n    }\n\n    ///\n    /// Return the stack of AST nodes containing \"position\"\n    ///\n    export function getAstPathToPosition(script: TypeScript.AST, pos: number, options = GetAstPathOptions.Default): TypeScript.AstPath {\n        var lookInComments = (comments: TypeScript.Comment[]) => {\n            if (comments && comments.length > 0) {\n                for (var i = 0; i < comments.length; i++) {\n                    var minChar = comments[i].minChar;\n                    var limChar = comments[i].limChar;\n                    if (!comments[i].isBlockComment) {\n                        limChar++; // For single line comments, include 1 more character (for the newline)\n                    }\n                    if (pos >= minChar && pos < limChar) {\n                        ctx.path.push(comments[i]);\n                    }\n                }\n            }\n        }\n\n        var pre = function (cur: TypeScript.AST, parent: TypeScript.AST, walker: IAstWalker) {\n            if (isValidAstNode(cur)) {\n\n                // Add \"cur\" to the stack if it contains our position\n                // For \"identifier\" nodes, we need a special case: A position equal to \"limChar\" is\n                // valid, since the position corresponds to a caret position (in between characters)\n                // For example:\n                //  bar\n                //  0123\n                // If \"position == 3\", the caret is at the \"right\" of the \"r\" character, which should be considered valid\n                var inclusive =\n                    hasFlag(options, GetAstPathOptions.EdgeInclusive) ||\n                    cur.nodeType === TypeScript.NodeType.Name ||\n                    pos === script.limChar; // Special \"EOF\" case\n\n                var minChar = cur.minChar;\n                var limChar = cur.limChar + (inclusive ? 1 : 0)\n                if (pos >= minChar && pos < limChar) {\n\n                    // TODO: Since AST is sometimes not correct wrt to position, only add \"cur\" if it's better\n                    //       than top of the stack.\n                    var previous = ctx.path.ast();\n                    if (previous == null || (cur.minChar >= previous.minChar && cur.limChar <= previous.limChar)) {\n                        ctx.path.push(cur);\n                    }\n                    else {\n                        //logger.log(\"TODO: Ignoring node because minChar, limChar not better than previous node in stack\");\n                    }\n                }\n\n                // The AST walker skips comments, but we might be in one, so check the pre/post comments for this node manually\n                if (pos < limChar) {\n                    lookInComments(cur.preComments);\n                }\n                if (pos >= minChar) {\n                    lookInComments(cur.postComments);\n                }\n\n                if (!hasFlag(options, GetAstPathOptions.DontPruneSearchBasedOnPosition)) {\n                    // Don't go further down the tree if pos is outside of [minChar, limChar]\n                    walker.options.goChildren = (minChar <= pos && pos <= limChar);\n                }\n            }\n            return cur;\n        }\n\n        var ctx = new AstPathContext();\n        TypeScript.getAstWalkerFactory().walk(script, pre, null, null, ctx);\n        return ctx.path;\n    }\n\n    //\n    // Find a source text offset that is safe for lexing tokens at the given position.\n    // This is used when \"position\" might be inside a comment or string, etc.\n    //\n    export function getTokenizationOffset(script: TypeScript.Script, position: number): number {\n        var bestOffset = 0;\n        var pre = (cur: TypeScript.AST, parent: TypeScript.AST, walker: TypeScript.IAstWalker): TypeScript.AST => {\n            if (TypeScript.isValidAstNode(cur)) {\n                // Did we find a closer offset?\n                if (cur.minChar <= position) {\n                    bestOffset = max(bestOffset, cur.minChar);\n                }\n\n                // Stop the walk if this node is not related to \"minChar\"\n                if (cur.minChar > position || cur.limChar < bestOffset) {\n                    walker.options.goChildren = false;\n                }\n            }\n\n            return cur;\n        }\n\n        TypeScript.getAstWalkerFactory().walk(script, pre);\n        return bestOffset;\n    }\n\n    ///\n    /// Simple function to Walk an AST using a simple callback function.\n    ///\n    export function walkAST(ast: TypeScript.AST, callback: (path: AstPath, walker: TypeScript.IAstWalker) => void ): void {\n        var pre = function (cur: TypeScript.AST, parent: TypeScript.AST, walker: TypeScript.IAstWalker) {\n            var path: TypeScript.AstPath = walker.state;\n            path.push(cur);\n            callback(path, walker);\n            return cur;\n        }\n        var post = function (cur: TypeScript.AST, parent: TypeScript.AST, walker: TypeScript.IAstWalker) {\n            var path: TypeScript.AstPath = walker.state;\n            path.pop();\n            return cur;\n        }\n\n        var path = new AstPath();\n        TypeScript.getAstWalkerFactory().walk(ast, pre, post, null, path);\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export class ASTSpan {\n        public minChar: number = -1;  // -1 = \"undefined\" or \"compiler generated\"\n        public limChar: number = -1;  // -1 = \"undefined\" or \"compiler generated\"   \n    }\n\n    export class AST extends ASTSpan {\n        public type: Type = null;\n        public flags = ASTFlags.Writeable;\n\n        // REVIEW: for diagnostic purposes\n        public passCreated: number = CompilerDiagnostics.analysisPass;\n\n        public preComments: Comment[] = null;\n        public postComments: Comment[] = null;\n        private docComments: Comment[] = null;\n\n        public isParenthesized = false;\n\n        constructor (public nodeType: NodeType) {\n            super();\n        }\n\n        public isExpression() { return false; }\n\n        public isStatementOrExpression() { return false; }\n\n        public isCompoundStatement() { return false; }\n\n        public isLeaf() { return this.isStatementOrExpression() && (!this.isCompoundStatement()); }\n        \n        public isDeclaration() { return false; }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            switch (this.nodeType) {\n                case NodeType.Error:\n                case NodeType.EmptyExpr:\n                    this.type = typeFlow.anyType;\n                    break;\n                case NodeType.This:\n                    return typeFlow.typeCheckThis(this);\n                case NodeType.Null:\n                    this.type = typeFlow.nullType;\n                    break;\n                case NodeType.False:\n                case NodeType.True:\n                    this.type = typeFlow.booleanType;\n                    break;\n                case NodeType.Super:\n                    return typeFlow.typeCheckSuper(this);\n                case NodeType.EndCode:\n                case NodeType.Empty:\n                case NodeType.Void:\n                    this.type = typeFlow.voidType;\n                    break;\n                default:\n                    throw new Error(\"please implement in derived class\");\n            }\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            switch (this.nodeType) {\n                case NodeType.This:\n                    emitter.recordSourceMappingStart(this);\n                    if (emitter.thisFnc && (hasFlag(emitter.thisFnc.fncFlags, FncFlags.IsFatArrowFunction))) {\n                        emitter.writeToOutput(\"_this\");\n                    }\n                    else {\n                        emitter.writeToOutput(\"this\");\n                    }\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.Null:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.writeToOutput(\"null\");\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.False:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.writeToOutput(\"false\");\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.True:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.writeToOutput(\"true\");\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.Super:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.emitSuperReference();\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.EndCode:\n                case NodeType.Error:\n                case NodeType.EmptyExpr:\n                    break;\n                case NodeType.Empty:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                case NodeType.Void:\n                    emitter.recordSourceMappingStart(this);\n                    emitter.writeToOutput(\"void \");\n                    emitter.recordSourceMappingEnd(this);\n                    break;\n                default:\n                    throw new Error(\"please implement in derived class\");\n            }\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public print(context: PrintContext) {\n            context.startLine();\n            var lineCol = { line: -1, col: -1 };\n            var limLineCol = { line: -1, col: -1 };\n            if (context.parser !== null) {\n                context.parser.getSourceLineCol(lineCol, this.minChar);\n                context.parser.getSourceLineCol(limLineCol, this.limChar);\n                context.write(\"(\" + lineCol.line + \",\" + lineCol.col + \")--\" +\n                              \"(\" + limLineCol.line + \",\" + limLineCol.col + \"): \");\n            }\n            var lab = this.printLabel();\n            if (hasFlag(this.flags, ASTFlags.Error)) {\n                lab += \" (Error)\";\n            }\n            context.writeLine(lab);\n        }\n\n        public printLabel() {\n            if (nodeTypeTable[this.nodeType] !== undefined) {\n                return nodeTypeTable[this.nodeType];\n            }\n            else {\n                return (<any>NodeType)._map[this.nodeType];\n            }\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            // by default, AST adds itself to current basic block and does not check its children\n            context.walker.options.goChildren = false;\n            context.addContent(this);\n        }\n\n        public netFreeUses(container: Symbol, freeUses: StringHashTable) {\n        }\n\n        public treeViewLabel() {\n            return (<any>NodeType)._map[this.nodeType];\n        }\n\n        public static getResolvedIdentifierName(name: string): string {\n            if (!name) return \"\";\n\n            var resolved = \"\";\n            var start = 0;\n            var i = 0;\n            while(i <= name.length - 6) {\n                // Look for escape sequence \\uxxxx\n                if (name.charAt(i) == '\\\\' && name.charAt(i+1) == 'u') {\n                    var charCode = parseInt(name.substr(i + 2, 4), 16);\n                    resolved += name.substr(start, i - start);\n                    resolved += String.fromCharCode(charCode);\n                    i += 6;\n                    start = i;\n                    continue;\n                } \n                i++;\n            }\n            // Append remaining string\n            resolved += name.substring(start);\n            return resolved;\n        }\n\n        public getDocComments() : Comment[] {\n            if (!this.isDeclaration() || !this.preComments || this.preComments.length == 0) {\n                return [];\n            }\n\n            if (!this.docComments) {\n                var preCommentsLength = this.preComments.length;\n                var docComments: Comment[] = [];\n                for (var i = preCommentsLength - 1; i >= 0; i--) {\n                    if (this.preComments[i].isDocComment()) {\n                        var prevDocComment = docComments.length > 0 ? docComments[docComments.length - 1] : null;\n                        if (prevDocComment == null || // If the help comments were not yet set then this is the comment\n                             (this.preComments[i].limLine == prevDocComment.minLine ||\n                              this.preComments[i].limLine + 1 == prevDocComment.minLine)) { // On same line or next line\n                            docComments.push(this.preComments[i]);\n                            continue;\n                        }\n                    }\n                    break;\n                }\n\n                this.docComments = docComments.reverse();\n            }\n\n            return this.docComments;\n        }\n    }\n\n    export class IncompleteAST extends AST {\n        constructor (min: number, lim: number) {\n            super(NodeType.Error);\n\n            this.minChar = min;\n            this.limChar = lim;\n        }\n    }\n\n    export class ASTList extends AST {\n        public enclosingScope: SymbolScope = null;\n        public members: AST[] = new AST[];\n\n        constructor () {\n            super(NodeType.List);\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            var len = this.members.length;\n            for (var i = 0; i < len; i++) {\n                if (context.noContinuation) {\n                    context.addUnreachable(this.members[i]);\n                    break;\n                }\n                else {\n                    this.members[i] = context.walk(this.members[i], this);\n                }\n            }\n            context.walker.options.goChildren = false;\n        }\n\n        public append(ast: AST) {\n            this.members[this.members.length] = ast;\n            return this;\n        }\n\n        public appendAll(ast: AST) {\n            if (ast.nodeType == NodeType.List) {\n                var list = <ASTList>ast;\n                for (var i = 0, len = list.members.length; i < len; i++) {\n                    this.append(list.members[i]);\n                }\n            }\n            else {\n                this.append(ast);\n            }\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.recordSourceMappingStart(this);\n            emitter.emitJavascriptList(this, null, TokenID.Semicolon, startLine, false, false);\n            emitter.recordSourceMappingEnd(this);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            var len = this.members.length;\n            typeFlow.nestingLevel++;\n            for (var i = 0; i < len; i++) {\n                if (this.members[i]) {\n                    this.members[i] = this.members[i].typeCheck(typeFlow);\n                }\n            }\n            typeFlow.nestingLevel--;\n            return this;\n        }\n    }\n\n    export class Identifier extends AST {\n        public sym: Symbol = null;\n        public cloId = -1;\n        public text: string;\n\n        // 'actualText' is the text that the user has entered for the identifier. the text might \n        // include any Unicode escape sequences (e.g.: \\u0041 for 'A'). 'text', however, contains \n        // the resolved value of any escape sequences in the actual text; so in the previous \n        // example, actualText = '\\u0041', text = 'A'.\n        //\n        // For purposes of finding a symbol, use text, as this will allow you to match all \n        // variations of the variable text. For full-fidelity translation of the user input, such\n        // as emitting, use the actualText field.\n        // \n        // Note: \n        //    To change text, and to avoid running into a situation where 'actualText' does not \n        //    match 'text', always use setText.\n        constructor (public actualText: string, public hasEscapeSequence?: bool) {\n            super(NodeType.Name);\n            this.setText(actualText, hasEscapeSequence);\n        }\n\n        public setText(actualText: string, hasEscapeSequence?: bool) {\n            this.actualText = actualText;\n            if (hasEscapeSequence) {\n                this.text = AST.getResolvedIdentifierName(actualText);\n            }\n            else {\n                this.text = actualText;\n            }\n        }\n\n        public isMissing() { return false; }\n        public isLeaf() { return true; }\n\n        public treeViewLabel() {\n            return \"id: \" + this.actualText;\n        }\n\n        public printLabel() {\n            if (this.actualText) {\n                return \"id: \" + this.actualText;\n            }\n            else {\n                return \"name node\";\n            }\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckName(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitJavascriptName(this, true);\n        }\n\n        public static fromToken(token: Token): Identifier {\n            return new Identifier(token.getText(), (<IdentifierToken>token).hasEscapeSequence);\n        }\n    }\n\n    export class MissingIdentifier extends Identifier {\n        constructor () {\n            super(\"__missing\");\n        }\n\n        public isMissing() {\n            return true;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            // Emit nothing for a missing ID\n        }\n    }\n\n    export class Label extends AST {\n        constructor (public id: Identifier) {\n            super(NodeType.Label);\n        }\n\n        public printLabel() { return this.id.actualText + \":\"; }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.type = typeFlow.voidType;\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.recordSourceMappingStart(this.id);\n            emitter.writeToOutput(this.id.actualText);\n            emitter.recordSourceMappingEnd(this.id);\n            emitter.writeLineToOutput(\":\");\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class Expression extends AST {\n        constructor (nodeType: NodeType) {\n            super(nodeType);\n        }\n\n        public isExpression() { return true; }\n\n        public isStatementOrExpression() { return true; }\n    }\n\n    export class UnaryExpression extends Expression {\n        public targetType: Type = null; // Target type for an object literal (null if no target type)\n        public castTerm: AST = null;\n\n        constructor (nodeType: NodeType, public operand: AST) {\n            super(nodeType);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            super.addToControlFlow(context);\n            // TODO: add successor as catch block/finally block if present\n            if (this.nodeType == NodeType.Throw) {\n                context.returnStmt();\n            }\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            switch (this.nodeType) {\n                case NodeType.Not:\n                    return typeFlow.typeCheckBitNot(this);\n\n                case NodeType.LogNot:\n                    return typeFlow.typeCheckLogNot(this);\n\n                case NodeType.Pos:\n                case NodeType.Neg:\n                    return typeFlow.typeCheckUnaryNumberOperator(this);\n\n                case NodeType.IncPost:\n                case NodeType.IncPre:\n                case NodeType.DecPost:\n                case NodeType.DecPre:\n                    return typeFlow.typeCheckIncOrDec(this);\n\n                case NodeType.ArrayLit:\n                    typeFlow.typeCheckArrayLit(this);\n                    return this;\n\n                case NodeType.ObjectLit:\n                    typeFlow.typeCheckObjectLit(this);\n                    return this;\n\n                case NodeType.Throw:\n                    this.operand = typeFlow.typeCheck(this.operand);\n                    this.type = typeFlow.voidType;\n                    return this;\n\n                case NodeType.Typeof:\n                    this.operand = typeFlow.typeCheck(this.operand);\n                    this.type = typeFlow.stringType;\n                    return this;\n\n                case NodeType.Delete:\n                    this.operand = typeFlow.typeCheck(this.operand);\n                    this.type = typeFlow.booleanType;\n                    break;\n\n                case NodeType.TypeAssertion:\n                    this.castTerm = typeFlow.typeCheck(this.castTerm);\n                    var applyTargetType = !this.operand.isParenthesized;\n\n                    var targetType = applyTargetType ? this.castTerm.type : null;\n\n                    typeFlow.checker.typeCheckWithContextualType(targetType, typeFlow.checker.inProvisionalTypecheckMode(), true, this.operand);\n                    typeFlow.castWithCoercion(this.operand, this.castTerm.type, false, true);\n                    this.type = this.castTerm.type;\n                    return this;\n\n                case NodeType.Void:\n                    // REVIEW - Although this is good to do for completeness's sake,\n                    // this shouldn't be strictly necessary from the void operator's\n                    // point of view\n                    this.operand = typeFlow.typeCheck(this.operand);\n                    this.type = typeFlow.checker.undefinedType;\n                    break;\n\n                default:\n                    throw new Error(\"please implement in derived class\");\n            }\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            switch (this.nodeType) {\n                case NodeType.IncPost:\n                    emitter.emitJavascript(this.operand, TokenID.PlusPlus, false);\n                    emitter.writeToOutput(\"++\");\n                    break;\n                case NodeType.LogNot:\n                    emitter.writeToOutput(\"!\");\n                    emitter.emitJavascript(this.operand, TokenID.Exclamation, false);\n                    break;\n                case NodeType.DecPost:\n                    emitter.emitJavascript(this.operand, TokenID.MinusMinus, false);\n                    emitter.writeToOutput(\"--\");\n                    break;\n                case NodeType.ObjectLit:\n                    emitter.emitObjectLiteral(<ASTList>this.operand);\n                    break;\n                case NodeType.ArrayLit:\n                    emitter.emitArrayLiteral(<ASTList>this.operand);\n                    break;\n                case NodeType.Not:\n                    emitter.writeToOutput(\"~\");\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    break;\n                case NodeType.Neg:\n                    emitter.writeToOutput(\"-\");\n                    if (this.operand.nodeType == NodeType.Neg) {\n                        this.operand.isParenthesized = true;\n                    }\n                    emitter.emitJavascript(this.operand, TokenID.Minus, false);\n                    break;\n                case NodeType.Pos:\n                    emitter.writeToOutput(\"+\");\n                    if (this.operand.nodeType == NodeType.Pos) {\n                        this.operand.isParenthesized = true;\n                    }\n                    emitter.emitJavascript(this.operand, TokenID.Plus, false);\n                    break;\n                case NodeType.IncPre:\n                    emitter.writeToOutput(\"++\");\n                    emitter.emitJavascript(this.operand, TokenID.PlusPlus, false);\n                    break;\n                case NodeType.DecPre:\n                    emitter.writeToOutput(\"--\");\n                    emitter.emitJavascript(this.operand, TokenID.MinusMinus, false);\n                    break;\n                case NodeType.Throw:\n                    emitter.writeToOutput(\"throw \");\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    emitter.writeToOutput(\";\");\n                    break;\n                case NodeType.Typeof:\n                    emitter.writeToOutput(\"typeof \");\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    break;\n                case NodeType.Delete:\n                    emitter.writeToOutput(\"delete \");\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    break;\n                case NodeType.Void:\n                    emitter.writeToOutput(\"void \");\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    break;\n                case NodeType.TypeAssertion:\n                    emitter.emitJavascript(this.operand, TokenID.Tilde, false);\n                    break;\n                default:\n                    throw new Error(\"please implement in derived class\");\n            }\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class CallExpression extends Expression {\n        constructor (nodeType: NodeType,\n                     public target: AST,\n                     public arguments: ASTList) {\n            super(nodeType);\n            this.minChar = this.target.minChar;\n        }\n\n        public signature: Signature = null;\n\n        public typeCheck(typeFlow: TypeFlow) {\n            if (this.nodeType == NodeType.New) {\n                return typeFlow.typeCheckNew(this);\n            }\n            else {\n                return typeFlow.typeCheckCall(this);\n            }\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n\n            if (this.nodeType == NodeType.New) {\n                emitter.emitNew(this.target, this.arguments);\n            }\n            else {\n                emitter.emitCall(this, this.target, this.arguments);\n            }\n\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class BinaryExpression extends Expression {\n        constructor (nodeType: NodeType, public operand1: AST, public operand2: AST) {\n            super(nodeType);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            switch (this.nodeType) {\n                case NodeType.Dot:\n                    return typeFlow.typeCheckDotOperator(this);\n                case NodeType.Asg:\n                    return typeFlow.typeCheckAsgOperator(this);\n                case NodeType.Add:\n                case NodeType.Sub:\n                case NodeType.Mul:\n                case NodeType.Div:\n                case NodeType.Mod:\n                case NodeType.Or:\n                case NodeType.And:\n                    return typeFlow.typeCheckArithmeticOperator(this, false);\n                case NodeType.Xor:\n                    return typeFlow.typeCheckBitwiseOperator(this, false);\n                case NodeType.Ne:\n                case NodeType.Eq:\n                    var text: string;\n                    if (typeFlow.checker.styleSettings.eqeqeq) {\n                        text = nodeTypeTable[this.nodeType];\n                        typeFlow.checker.errorReporter.styleError(this, \"use of \" + text);\n                    }\n                    else if (typeFlow.checker.styleSettings.eqnull) {\n                        text = nodeTypeTable[this.nodeType];\n                        if ((this.operand2 !== null) && (this.operand2.nodeType == NodeType.Null)) {\n                            typeFlow.checker.errorReporter.styleError(this, \"use of \" + text + \" to compare with null\");\n                        }\n                    }\n                case NodeType.Eqv:\n                case NodeType.NEqv:\n                case NodeType.Lt:\n                case NodeType.Le:\n                case NodeType.Ge:\n                case NodeType.Gt:\n                    return typeFlow.typeCheckBooleanOperator(this);\n                case NodeType.Index:\n                    return typeFlow.typeCheckIndex(this);\n                case NodeType.Member:\n                    this.type = typeFlow.voidType;\n                    return this;\n                case NodeType.LogOr:\n                    return typeFlow.typeCheckLogOr(this);\n                case NodeType.LogAnd:\n                    return typeFlow.typeCheckLogAnd(this);\n                case NodeType.AsgAdd:\n                case NodeType.AsgSub:\n                case NodeType.AsgMul:\n                case NodeType.AsgDiv:\n                case NodeType.AsgMod:\n                case NodeType.AsgOr:\n                case NodeType.AsgAnd:\n                    return typeFlow.typeCheckArithmeticOperator(this, true);\n                case NodeType.AsgXor:\n                    return typeFlow.typeCheckBitwiseOperator(this, true);\n                case NodeType.Lsh:\n                case NodeType.Rsh:\n                case NodeType.Rs2:\n                    return typeFlow.typeCheckShift(this, false);\n                case NodeType.AsgLsh:\n                case NodeType.AsgRsh:\n                case NodeType.AsgRs2:\n                    return typeFlow.typeCheckShift(this, true);\n                case NodeType.Comma:\n                    return typeFlow.typeCheckCommaOperator(this);\n                case NodeType.InstOf:\n                    return typeFlow.typeCheckInstOf(this);\n                case NodeType.In:\n                    return typeFlow.typeCheckInOperator(this);\n                case NodeType.From:\n                    typeFlow.checker.errorReporter.simpleError(this, \"Illegal use of 'from' keyword in binary expression\");\n                    break;\n                default:\n                    throw new Error(\"please implement in derived class\");\n            }\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            var binTokenId = nodeTypeToTokTable[this.nodeType];\n\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (binTokenId != undefined) {\n\n                emitter.emitJavascript(this.operand1, binTokenId, false);\n\n                if (tokenTable[binTokenId].text == \"instanceof\") {\n                    emitter.writeToOutput(\" instanceof \");\n                }\n                else if (tokenTable[binTokenId].text == \"in\") {\n                    emitter.writeToOutput(\" in \");\n                }\n                else {\n                    emitter.writeToOutputTrimmable(\" \" + tokenTable[binTokenId].text + \" \");\n                }\n\n                emitter.emitJavascript(this.operand2, binTokenId, false);\n            }\n            else {\n                switch (this.nodeType) {\n                    case NodeType.Dot:\n                        if (!emitter.tryEmitConstant(this)) {\n                            emitter.emitJavascript(this.operand1, TokenID.Dot, false);\n                            emitter.writeToOutput(\".\");\n                            emitter.emitJavascriptName(<Identifier>this.operand2, false);\n                        }\n                        break;\n                    case NodeType.Index:\n                        emitter.emitIndex(this.operand1, this.operand2);\n                        break;\n\n                    case NodeType.Member:\n                        if (this.operand2.nodeType == NodeType.FuncDecl && (<FuncDecl>this.operand2).isAccessor()) {\n                            var funcDecl = <FuncDecl>this.operand2;\n                            if (hasFlag(funcDecl.fncFlags, FncFlags.GetAccessor)) {\n                                emitter.writeToOutput(\"get \");\n                            }\n                            else {\n                                emitter.writeToOutput(\"set \");\n                            }\n                            emitter.emitJavascript(this.operand1, TokenID.Colon, false);\n                        }\n                        else {\n                            emitter.emitJavascript(this.operand1, TokenID.Colon, false);\n                            emitter.writeToOutputTrimmable(\": \");\n                        }\n                        emitter.emitJavascript(this.operand2, TokenID.Comma, false);\n                        break;\n                    case NodeType.Comma:\n                        emitter.emitJavascript(this.operand1, TokenID.Comma, false);\n                        if (emitter.emitState.inObjectLiteral) {\n                            emitter.writeLineToOutput(\", \");\n                        }\n                        else {\n                            emitter.writeToOutput(\",\");\n                        }\n                        emitter.emitJavascript(this.operand2, TokenID.Comma, false);\n                        break;\n                    case NodeType.Is:\n                        throw new Error(\"should be de-sugared during type check\");\n                    default:\n                        throw new Error(\"please implement in derived class\");\n                }\n            }\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class ConditionalExpression extends Expression {\n        constructor (public operand1: AST,\n                     public operand2: AST,\n                     public operand3: AST) {\n            super(NodeType.ConditionalExpression);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckQMark(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.emitJavascript(this.operand1, TokenID.Question, false);\n            emitter.writeToOutput(\" ? \");\n            emitter.emitJavascript(this.operand2, TokenID.Question, false);\n            emitter.writeToOutput(\" : \");\n            emitter.emitJavascript(this.operand3, TokenID.Question, false);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class NumberLiteral extends Expression {\n        constructor (public value: number, public hasEmptyFraction?: bool) {\n            super(NodeType.NumberLit);\n        }\n\n        public isNegativeZero = false;\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.type = typeFlow.doubleType;\n            return this;\n        }\n\n        public treeViewLabel() {\n            return \"num: \" + this.printLabel();\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (this.isNegativeZero) {\n                emitter.writeToOutput(\"-\");\n            }\n\n            emitter.writeToOutput(this.value.toString());\n\n            if (this.hasEmptyFraction)\n                emitter.writeToOutput(\".0\");\n\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public printLabel() {\n            if (Math.floor(this.value) != this.value) {\n                return this.value.toFixed(2).toString();\n            }\n            else if (this.hasEmptyFraction) {\n                return this.value.toString() + \".0\";\n            }\n            else {\n                return this.value.toString();\n            }\n        }\n    }\n\n    export class RegexLiteral extends Expression {\n        constructor (public regex) {\n            super(NodeType.Regex);\n        }\n        \n        public typeCheck(typeFlow: TypeFlow) {\n            this.type = typeFlow.regexType;\n            return this;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(this.regex.toString());\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class StringLiteral extends Expression {\n        constructor (public text: string) {\n            super(NodeType.QString);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.emitStringLiteral(this.text);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.type = typeFlow.stringType;\n            return this;\n        }\n\n        public treeViewLabel() {\n            return \"st: \" + this.text;\n        }\n\n        public printLabel() {\n            return this.text;\n        }\n    }\n\n    export class ModuleElement extends AST {\n        constructor (nodeType: NodeType) {\n            super(nodeType);\n        }\n    }\n\n    export class ImportDeclaration extends ModuleElement {\n        public isStatementOrExpression() { return true; }\n        public varFlags = VarFlags.None;\n        public isDynamicImport = false;\n        public isDeclaration() { return true; }\n\n        constructor (public id: Identifier, public alias: AST) {\n            super(NodeType.ImportDeclaration);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            var mod = <ModuleType>this.alias.type;\n            // REVIEW: Only modules may be aliased for now, though there's no real\n            // restriction on what the type symbol may be\n            if (!this.isDynamicImport || (this.id.sym && !(<TypeSymbol>this.id.sym).onlyReferencedAsTypeRef)) {\n                var prevModAliasId = emitter.modAliasId;\n                var prevFirstModAlias = emitter.firstModAlias;\n\n                emitter.recordSourceMappingStart(this);\n                emitter.emitParensAndCommentsInPlace(this, true);\n                emitter.writeToOutput(\"var \" + this.id.actualText + \" = \");\n                emitter.modAliasId = this.id.actualText;\n                emitter.firstModAlias = this.firstAliasedModToString();\n                emitter.emitJavascript(this.alias, TokenID.Tilde, false);\n                // the dynamic import case will insert the semi-colon automatically\n                if (!this.isDynamicImport) {\n                    emitter.writeToOutput(\";\");\n                }\n                emitter.emitParensAndCommentsInPlace(this, false);\n                emitter.recordSourceMappingEnd(this);\n\n                emitter.modAliasId = prevModAliasId;\n                emitter.firstModAlias = prevFirstModAlias;\n            }\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckImportDecl(this);\n        }\n\n        public getAliasName(aliasAST?: AST = this.alias) : string {\n            if (aliasAST.nodeType == NodeType.Name) {\n                return (<Identifier>aliasAST).actualText;\n            } else {\n                var dotExpr = <BinaryExpression>aliasAST;\n                return this.getAliasName(dotExpr.operand1) + \".\" + this.getAliasName(dotExpr.operand2);\n            }\n        }\n\n        public firstAliasedModToString() {\n            if (this.alias.nodeType == NodeType.Name) {\n                return (<Identifier>this.alias).actualText;\n            }\n            else {\n                var dotExpr = <BinaryExpression>this.alias;\n                var firstMod = <Identifier>dotExpr.operand1;\n                return firstMod.actualText;\n            }\n        }\n    }\n\n    export class BoundDecl extends AST {\n        public init: AST = null;\n        public typeExpr: AST = null;\n        public varFlags = VarFlags.None;\n        public sym: Symbol = null;\n        public isDeclaration() { return true; }\n\n        constructor (public id: Identifier, nodeType: NodeType, public nestingLevel: number) {\n            super(nodeType);\n        }\n\n        public isStatementOrExpression() { return true; }\n\n        public isPrivate() { return hasFlag(this.varFlags, VarFlags.Private); }\n        public isPublic() { return hasFlag(this.varFlags, VarFlags.Public); }\n        public isProperty() { return hasFlag(this.varFlags, VarFlags.Property); }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckBoundDecl(this);\n        }\n\n        public printLabel() {\n            return this.treeViewLabel();\n        }\n    }\n\n    export class VarDecl extends BoundDecl {\n        constructor (id: Identifier, nest: number) {\n            super(id, NodeType.VarDecl, nest);\n        }\n\n        public isAmbient() { return hasFlag(this.varFlags, VarFlags.Ambient); }\n        public isExported() { return hasFlag(this.varFlags, VarFlags.Exported); }\n        public isStatic() { return hasFlag(this.varFlags, VarFlags.Static); }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitJavascriptVarDecl(this, tokenId);\n        }\n\n        public treeViewLabel() {\n            return \"var \" + this.id.actualText;\n        }\n    }\n\n    export class ArgDecl extends BoundDecl {\n        constructor (id: Identifier) {\n            super(id, NodeType.ArgDecl, 0);\n        }\n\n        public isOptional = false;\n\n        public isOptionalArg() { return this.isOptional || this.init; }\n\n        public treeViewLabel() {\n            return \"arg: \" + this.id.actualText;\n        }\n\n        public parameterPropertySym: FieldSymbol = null;\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(this.id.actualText);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    var internalId = 0;\n\n    export class FuncDecl extends AST {\n        public hint: string = null;\n        public fncFlags = FncFlags.None;\n        public returnTypeAnnotation: AST = null;\n        public symbols: IHashTable;\n        public variableArgList = false;\n        public signature: Signature;\n        public envids: Identifier[];\n        public jumpRefs: Identifier[] = null;\n        public internalNameCache: string = null;\n        public tmp1Declared = false;\n        public enclosingFnc: FuncDecl = null;\n        public freeVariables: Symbol[] = [];\n        public unitIndex = -1;\n        public classDecl: NamedDeclaration = null;\n        public boundToProperty: VarDecl = null;\n        public isOverload = false;\n        public innerStaticFuncs: FuncDecl[] = [];\n        public isTargetTypedAsMethod = false;\n        public isInlineCallLiteral = false;\n        public accessorSymbol: Symbol = null;\n        public leftCurlyCount = 0;\n        public rightCurlyCount = 0;\n        public returnStatementsWithExpressions: ReturnStatement[] = [];\n        public scopeType: Type = null; // Type of the FuncDecl, before target typing\n        public endingToken: ASTSpan = null;\n        public isDeclaration() { return true; }\n\n        constructor (public name: Identifier, public bod: ASTList, public isConstructor: bool,\n                     public arguments: ASTList, public vars: ASTList, public scopes: ASTList, public statics: ASTList,\n                     nodeType: number) {\n\n            super(nodeType);\n        }\n\n        public internalName(): string {\n            if (this.internalNameCache == null) {\n                var extName = this.getNameText();\n                if (extName) {\n                    this.internalNameCache = \"_internal_\" + extName;\n                }\n                else {\n                    this.internalNameCache = \"_internal_\" + internalId++;\n                }\n            }\n            return this.internalNameCache;\n        }\n\n        public hasSelfReference() { return hasFlag(this.fncFlags, FncFlags.HasSelfReference); }\n        public setHasSelfReference() { this.fncFlags |= FncFlags.HasSelfReference; }\n\n        public hasSuperReferenceInFatArrowFunction() { return hasFlag(this.fncFlags, FncFlags.HasSuperReferenceInFatArrowFunction); }\n        public setHasSuperReferenceInFatArrowFunction() { this.fncFlags |= FncFlags.HasSuperReferenceInFatArrowFunction; }\n\n        public addCloRef(id: Identifier, sym: Symbol): number {\n            if (this.envids == null) {\n                this.envids = new Identifier[];\n            }\n            this.envids[this.envids.length] = id;\n            var outerFnc = this.enclosingFnc;\n            if (sym) {\n                while (outerFnc && (outerFnc.type.symbol != sym.container)) {\n                    outerFnc.addJumpRef(sym);\n                    outerFnc = outerFnc.enclosingFnc;\n                }\n            }\n            return this.envids.length - 1;\n        }\n\n        public addJumpRef(sym: Symbol): void {\n            if (this.jumpRefs == null) {\n                this.jumpRefs = new Identifier[];\n            }\n            var id = new Identifier(sym.name);\n            this.jumpRefs[this.jumpRefs.length] = id;\n            id.sym = sym;\n            id.cloId = this.addCloRef(id, null);\n        }\n\n        public buildControlFlow(): ControlFlowContext {\n            var entry = new BasicBlock();\n            var exit = new BasicBlock();\n\n            var context = new ControlFlowContext(entry, exit);\n\n            var controlFlowPrefix = (ast: AST, parent: AST, walker: IAstWalker) => {\n                ast.addToControlFlow(walker.state);\n                return ast;\n            }\n\n            var walker = getAstWalkerFactory().getWalker(controlFlowPrefix, null, null, context);\n            context.walker = walker;\n            walker.walk(this.bod, this);\n\n            return context;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckFunction(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitJavascriptFunction(this);\n        }\n\n        public getNameText() {\n            if (this.name) {\n                return this.name.actualText;\n            }\n            else {\n                return this.hint;\n            }\n        }\n\n        public isMethod() {\n            return (this.fncFlags & FncFlags.Method) != FncFlags.None;\n        }\n\n        public isCallMember() { return hasFlag(this.fncFlags, FncFlags.CallMember); }\n        public isConstructMember() { return hasFlag(this.fncFlags, FncFlags.ConstructMember); }\n        public isIndexerMember() { return hasFlag(this.fncFlags, FncFlags.IndexerMember); }\n        public isSpecialFn() { return this.isCallMember() || this.isIndexerMember() || this.isConstructMember(); }\n        public isAnonymousFn() { return this.name === null; }\n        public isAccessor() { return hasFlag(this.fncFlags, FncFlags.GetAccessor) || hasFlag(this.fncFlags, FncFlags.SetAccessor); }\n        public isGetAccessor() { return hasFlag(this.fncFlags, FncFlags.GetAccessor); }\n        public isSetAccessor() { return hasFlag(this.fncFlags, FncFlags.SetAccessor); }\n        public isAmbient() { return hasFlag(this.fncFlags, FncFlags.Ambient); }\n        public isExported() { return hasFlag(this.fncFlags, FncFlags.Exported); }\n        public isPrivate() { return hasFlag(this.fncFlags, FncFlags.Private); }\n        public isPublic() { return hasFlag(this.fncFlags, FncFlags.Public); }\n        public isStatic() { return hasFlag(this.fncFlags, FncFlags.Static); }\n\n        public treeViewLabel() {\n            if (this.name == null) {\n                return \"funcExpr\";\n            }\n            else {\n                return \"func: \" + this.name.actualText\n            }\n        }\n\n        public ClearFlags(): void {\n            this.fncFlags = FncFlags.None;\n        }\n\n        public isSignature() { return (this.fncFlags & FncFlags.Signature) != FncFlags.None; }\n    }\n\n    export class LocationInfo {\n        constructor (public filename: string, public lineMap: number[], public unitIndex) { }\n    }\n\n    export var unknownLocationInfo = new LocationInfo(\"unknown\", null, -1);\n\n    export class Script extends FuncDecl {\n        public locationInfo: LocationInfo = null;\n        public referencedFiles: IFileReference[] = [];\n        public requiresGlobal = false;\n        public requiresExtendsBlock = false;\n        public isResident = false;\n        public isDeclareFile = false;\n        public hasBeenTypeChecked = false;\n        public topLevelMod: ModuleDeclaration = null;\n        public leftCurlyCount = 0;\n        public rightCurlyCount = 0;\n        public vars: ASTList;\n        public scopes: ASTList;\n        // Remember if the script contains Unicode chars, that is needed when generating code for this script object to decide the output file correct encoding.\n        public containsUnicodeChar = false;\n        public containsUnicodeCharInComment = false;\n        public cachedEmitRequired: bool;\n\n        private setCachedEmitRequired(value: bool) {\n            this.cachedEmitRequired = value;\n            return this.cachedEmitRequired;\n        }\n\n        constructor (vars: ASTList, scopes: ASTList) {\n            super(new Identifier(\"script\"), null, false, null, vars, scopes, null, NodeType.Script);\n            this.vars = vars;\n            this.scopes = scopes;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckScript(this);\n        }\n\n        public treeViewLabel() {\n            return \"Script\";\n        }\n\n        public emitRequired(emitOptions: EmitOptions) {\n            if (this.cachedEmitRequired != undefined) {\n                return this.cachedEmitRequired;\n            }\n\n            if (!this.isDeclareFile && !this.isResident && this.bod) {\n                if (this.bod.members.length == 0) {\n                    // allow empty files that are not declare files \n                    return this.setCachedEmitRequired(true);\n                }\n\n                for (var i = 0, len = this.bod.members.length; i < len; i++) {\n                    var stmt = this.bod.members[i];\n                    if (stmt.nodeType == NodeType.ModuleDeclaration) {\n                        if (!hasFlag((<ModuleDeclaration>stmt).modFlags, ModuleFlags.ShouldEmitModuleDecl | ModuleFlags.Ambient)) {\n                            return this.setCachedEmitRequired(true);\n                        }\n                    }\n                    else if (stmt.nodeType == NodeType.ClassDeclaration) {\n                        if (!hasFlag((<ClassDeclaration>stmt).varFlags, VarFlags.Ambient)) {\n                            return this.setCachedEmitRequired(true);\n                        }\n                    }\n                    else if (stmt.nodeType == NodeType.VarDecl) {\n                        if (!hasFlag((<VarDecl>stmt).varFlags, VarFlags.Ambient)) {\n                            return this.setCachedEmitRequired(true);\n                        }\n                    }\n                    else if (stmt.nodeType == NodeType.FuncDecl) {\n                        if (!(<FuncDecl>stmt).isSignature()) {\n                            return this.setCachedEmitRequired(true);\n                        }\n                    }\n                    else if (stmt.nodeType != NodeType.InterfaceDeclaration && stmt.nodeType != NodeType.Empty) {\n                        return this.setCachedEmitRequired(true);\n                    }\n                }\n\n                if ( emitOptions.emitComments &&\n                    ((this.bod.preComments && this.bod.preComments.length > 0) || (this.bod.postComments && this.bod.postComments.length > 0))) {\n                    return this.setCachedEmitRequired(true);\n                }\n            }\n            return this.setCachedEmitRequired(false);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            if (this.emitRequired(emitter.emitOptions)) {\n                emitter.emitParensAndCommentsInPlace(this.bod, true);\n                emitter.emitJavascriptList(this.bod, null, TokenID.Semicolon, true, false, false, true, this.requiresExtendsBlock);\n                emitter.emitParensAndCommentsInPlace(this.bod, false);\n            }\n        }\n\n        private externallyVisibleImportedSymbols: Symbol[] = [];\n\n        public AddExternallyVisibleImportedSymbol(symbol: Symbol, checker: TypeChecker) {\n            if (this.isExternallyVisibleSymbol(symbol)) {\n                return;\n            }\n\n            // Before adding check if the external symbol is also marked for visibility\n            if (!symbol.getType().symbol.isExternallyVisible(checker)) {\n                // Report error\n                var quotes = \"\";\n                var moduleName = symbol.getType().symbol.prettyName;\n                if (!isQuoted(moduleName)) {\n                    quotes = \"'\";\n                }\n                checker.errorReporter.simpleError(symbol.declAST, \"Externally visible import statement uses non exported module \" + quotes + moduleName + quotes);\n            }\n            this.externallyVisibleImportedSymbols.push(symbol);\n        }\n\n        public isExternallyVisibleSymbol(symbol: Symbol) {\n            for (var i = 0 ; i < this.externallyVisibleImportedSymbols.length; i++) {\n                if (this.externallyVisibleImportedSymbols[i] == symbol) {\n                    return true;\n                }\n            }\n            return false;\n        }\n    }\n\n    export class NamedDeclaration extends ModuleElement {\n        public leftCurlyCount = 0;\n        public rightCurlyCount = 0;\n        public isDeclaration() { return true; }\n\n        constructor (nodeType: NodeType,\n                     public name: Identifier,\n                     public members: ASTList) {\n            super(nodeType);\n        }\n    }\n\n    export class ModuleDeclaration extends NamedDeclaration {\n        public modFlags = ModuleFlags.ShouldEmitModuleDecl;\n        public mod: ModuleType;\n        public prettyName: string;\n        public amdDependencies: string[] = [];\n        public vars: ASTList;\n        public scopes: ASTList;\n        // Remember if the module contains Unicode chars, that is needed for dynamic module as we will generate a file for each.\n        public containsUnicodeChar = false;\n        public containsUnicodeCharInComment = false;\n\n        constructor (name: Identifier, members: ASTList, vars: ASTList, scopes: ASTList, public endingToken: ASTSpan) {\n            super(NodeType.ModuleDeclaration, name, members);\n\n            this.vars = vars;\n            this.scopes = scopes;\n            this.prettyName = this.name.actualText;\n        }\n\n        public isExported() { return hasFlag(this.modFlags, ModuleFlags.Exported); }\n        public isAmbient() { return hasFlag(this.modFlags, ModuleFlags.Ambient); }\n        public isEnum() { return hasFlag(this.modFlags, ModuleFlags.IsEnum); }\n\n        public recordNonInterface() {\n            this.modFlags &= ~ModuleFlags.ShouldEmitModuleDecl;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckModule(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            if (!hasFlag(this.modFlags, ModuleFlags.ShouldEmitModuleDecl)) {\n                emitter.emitParensAndCommentsInPlace(this, true);\n                emitter.emitJavascriptModule(this);\n                emitter.emitParensAndCommentsInPlace(this, false);\n            }\n        }\n    }\n\n    export class TypeDeclaration extends NamedDeclaration {\n        public varFlags = VarFlags.None;\n\n        constructor (nodeType: NodeType,\n                     name: Identifier,\n                     public extendsList: ASTList,\n                     public implementsList: ASTList,\n                     members: ASTList) {\n            super(nodeType, name, members);\n        }\n\n        public isExported() { \n            return hasFlag(this.varFlags, VarFlags.Exported);\n        }\n\n        public isAmbient() {\n            return hasFlag(this.varFlags, VarFlags.Ambient);\n        }\n    }\n\n    export class ClassDeclaration extends TypeDeclaration {\n        public knownMemberNames: any = {};\n        public constructorDecl: FuncDecl = null;\n        public constructorNestingLevel = 0;\n        public endingToken: ASTSpan = null;\n\n        constructor (name: Identifier,\n                     members: ASTList,\n                     extendsList: ASTList,\n                     implementsList: ASTList) {\n            super(NodeType.ClassDeclaration, name, extendsList, implementsList, members);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckClass(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitJavascriptClass(this);\n        }\n    }\n\n    export class InterfaceDeclaration extends TypeDeclaration {\n        constructor (name: Identifier,\n                     members: ASTList,\n                     extendsList: ASTList,\n                     implementsList: ASTList) {\n            super(NodeType.InterfaceDeclaration, name, extendsList, implementsList, members);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckInterface(this);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n        }\n    }\n\n    export class Statement extends ModuleElement {\n        constructor (nodeType: NodeType) {\n            super(nodeType);\n            this.flags |= ASTFlags.IsStatement;\n        }\n\n        public isLoop() { return false; }\n\n        public isStatementOrExpression() { return true; }\n\n        public isCompoundStatement() { return this.isLoop(); }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.type = typeFlow.voidType;\n            return this;\n        }\n    }\n\n    export class LabeledStatement extends Statement {\n        constructor (public labels: ASTList, public stmt: AST) {\n            super(NodeType.LabeledStatement);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (this.labels) {\n                var labelsLen = this.labels.members.length;\n                for (var i = 0; i < labelsLen; i++) {\n                    this.labels.members[i].emit(emitter, tokenId, startLine);\n                }\n            }\n            this.stmt.emit(emitter, tokenId, true);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            typeFlow.typeCheck(this.labels);\n            this.stmt = this.stmt.typeCheck(typeFlow);\n            return this;\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            var beforeBB = context.current;\n            var bb = new BasicBlock();\n            context.current = bb;\n            beforeBB.addSuccessor(bb);\n        }\n    }\n\n    export class Block extends Statement {\n        constructor (public statements: ASTList,\n                     public isStatementBlock: bool) {\n            super(NodeType.Block);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (this.isStatementBlock) {\n                emitter.writeLineToOutput(\" {\");\n                emitter.indenter.increaseIndent();\n            } else {\n                emitter.setInVarBlock(this.statements.members.length);\n            }\n            var temp = emitter.setInObjectLiteral(false);\n            if (this.statements) {\n                emitter.emitJavascriptList(this.statements, null, TokenID.Semicolon, true, false, false);\n            }\n            if (this.isStatementBlock) {\n                emitter.indenter.decreaseIndent();\n                emitter.emitIndent();\n                emitter.writeToOutput(\"}\");\n            }\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            var afterIfNeeded = new BasicBlock();\n            context.pushStatement(this, context.current, afterIfNeeded);\n            if (this.statements) {\n                context.walk(this.statements, this);\n            }\n            context.walker.options.goChildren = false;\n            context.popStatement();\n            if (afterIfNeeded.predecessors.length > 0) {\n                context.current.addSuccessor(afterIfNeeded);\n                context.current = afterIfNeeded;\n            }\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            if (!typeFlow.checker.styleSettings.emptyBlocks) {\n                if ((this.statements === null) || (this.statements.members.length == 0)) {\n                    typeFlow.checker.errorReporter.styleError(this, \"empty block\");\n                }\n            }\n\n            typeFlow.typeCheck(this.statements);\n            return this;\n        }\n    }\n\n    export class Jump extends Statement {\n        public target: string = null;\n        public hasExplicitTarget() { return (this.target); }\n        public resolvedTarget: Statement = null;\n\n        constructor (nodeType: NodeType) {\n            super(nodeType);\n        }\n\n        public setResolvedTarget(parser: Parser, stmt: Statement): bool {\n            if (stmt.isLoop()) {\n                this.resolvedTarget = stmt;\n                return true;\n            }\n            if (this.nodeType === NodeType.Continue) {\n                parser.reportParseError(\"continue statement applies only to loops\");\n                return false;\n            }\n            else {\n                if ((stmt.nodeType == NodeType.Switch) || this.hasExplicitTarget()) {\n                    this.resolvedTarget = stmt;\n                    return true;\n                }\n                else {\n                    parser.reportParseError(\"break statement with no label can apply only to a loop or switch statement\");\n                    return false;\n                }\n            }\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            super.addToControlFlow(context);\n            context.unconditionalBranch(this.resolvedTarget, (this.nodeType == NodeType.Continue));\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (this.nodeType == NodeType.Break) {\n                emitter.writeToOutput(\"break\");\n            }\n            else {\n                emitter.writeToOutput(\"continue\");\n            }\n            if (this.hasExplicitTarget()) {\n                emitter.writeToOutput(\" \" + this.target);\n            }\n            emitter.recordSourceMappingEnd(this);\n            emitter.writeToOutput(\";\");\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n\n    export class WhileStatement extends Statement {\n        public body: AST = null;\n\n        constructor (public cond: AST) {\n            super(NodeType.While);\n        }\n\n        public isLoop() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.writeToOutput(\"while(\");\n            emitter.emitJavascript(this.cond, TokenID.While, false);\n            emitter.writeToOutput(\")\");\n            emitter.emitJavascriptStatements(this.body, false);\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckWhile(this);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            var loopHeader = context.current;\n            var loopStart = new BasicBlock();\n            var afterLoop = new BasicBlock();\n\n            loopHeader.addSuccessor(loopStart);\n            context.current = loopStart;\n            context.addContent(this.cond);\n            var condBlock = context.current;\n            var targetInfo: ITargetInfo = null;\n            if (this.body) {\n                context.current = new BasicBlock();\n                condBlock.addSuccessor(context.current);\n                context.pushStatement(this, loopStart, afterLoop);\n                context.walk(this.body, this);\n                targetInfo = context.popStatement();\n            }\n            if (!(context.noContinuation)) {\n                var loopEnd = context.current;\n                loopEnd.addSuccessor(loopStart);\n            }\n            context.current = afterLoop;\n            condBlock.addSuccessor(afterLoop);\n            // TODO: check for while (true) and then only continue if afterLoop has predecessors\n            context.noContinuation = false;\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class DoWhileStatement extends Statement {\n        public body: AST = null;\n        public whileAST: AST = null;\n        public cond: AST = null;\n        public isLoop() { return true; }\n\n        constructor () {\n            super(NodeType.DoWhile);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.writeToOutput(\"do\");\n            emitter.emitJavascriptStatements(this.body, true);\n            emitter.recordSourceMappingStart(this.whileAST);\n            emitter.writeToOutput(\"while\");\n            emitter.recordSourceMappingEnd(this.whileAST);\n            emitter.writeToOutput('(');\n            emitter.emitJavascript(this.cond, TokenID.CloseParen, false);\n            emitter.writeToOutput(\")\");\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.writeToOutput(\";\");\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckDoWhile(this);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            var loopHeader = context.current;\n            var loopStart = new BasicBlock();\n            var afterLoop = new BasicBlock();\n            loopHeader.addSuccessor(loopStart);\n            context.current = loopStart;\n            var targetInfo: ITargetInfo = null;\n            if (this.body) {\n                context.pushStatement(this, loopStart, afterLoop);\n                context.walk(this.body, this);\n                targetInfo = context.popStatement();\n            }\n            if (!(context.noContinuation)) {\n                var loopEnd = context.current;\n                loopEnd.addSuccessor(loopStart);\n                context.addContent(this.cond);\n                // TODO: check for while (true) \n                context.current = afterLoop;\n                loopEnd.addSuccessor(afterLoop);\n            }\n            else {\n                context.addUnreachable(this.cond);\n            }\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class IfStatement extends Statement {\n        public thenBod: AST;\n        public elseBod: AST = null;\n        public statement: ASTSpan = new ASTSpan();\n\n        constructor (public cond: AST) {\n            super(NodeType.If);\n        }\n\n        public isCompoundStatement() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.recordSourceMappingStart(this.statement);\n            emitter.writeToOutput(\"if(\");\n            emitter.emitJavascript(this.cond, TokenID.If, false);\n            emitter.writeToOutput(\")\");\n            emitter.recordSourceMappingEnd(this.statement);\n            emitter.emitJavascriptStatements(this.thenBod, true);\n            if (this.elseBod) {\n                if (this.elseBod.nodeType === NodeType.If) {\n                    emitter.writeToOutput(\" else \");\n                    this.elseBod.emit(emitter, tokenId, /*startLine:*/ false);\n                }\n                else {\n                    emitter.writeToOutput(\" else\");\n                    emitter.emitJavascriptStatements(this.elseBod, true);\n                }\n            }\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckIf(this);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            this.cond.addToControlFlow(context);\n            var afterIf = new BasicBlock();\n            var beforeIf = context.current;\n            context.pushStatement(this, beforeIf, afterIf);\n            var hasContinuation = false;\n            context.current = new BasicBlock();\n            beforeIf.addSuccessor(context.current);\n            context.walk(this.thenBod, this);\n            if (!context.noContinuation) {\n                hasContinuation = true;\n                context.current.addSuccessor(afterIf);\n            }\n            if (this.elseBod) {\n                // current block will be thenBod\n                context.current = new BasicBlock();\n                context.noContinuation = false;\n                beforeIf.addSuccessor(context.current);\n                context.walk(this.elseBod, this);\n                if (!context.noContinuation) {\n                    hasContinuation = true;\n                    context.current.addSuccessor(afterIf);\n                }\n                else {\n                    // thenBod created continuation for if statement\n                    if (hasContinuation) {\n                        context.noContinuation = false;\n                    }\n                }\n            }\n            else {\n                beforeIf.addSuccessor(afterIf);\n                context.noContinuation = false;\n                hasContinuation = true;\n            }\n            var targetInfo = context.popStatement();\n            if (afterIf.predecessors.length > 0) {\n                context.noContinuation = false;\n                hasContinuation = true;\n            }\n            if (hasContinuation) {\n                context.current = afterIf;\n            }\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class ReturnStatement extends Statement {\n        public returnExpression: AST = null;\n\n        constructor () {\n            super(NodeType.Return);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            if (this.returnExpression) {\n                emitter.writeToOutput(\"return \");\n                emitter.emitJavascript(this.returnExpression, TokenID.Semicolon, false);\n\n                if (this.returnExpression.nodeType === NodeType.FuncDecl) {\n                    emitter.writeToOutput(\";\");\n                }\n            }\n            else {\n                emitter.writeToOutput(\"return;\");\n            }\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            super.addToControlFlow(context);\n            context.returnStmt();\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckReturn(this);\n        }\n    }\n\n    export class EndCode extends AST {\n        constructor () {\n            super(NodeType.EndCode);\n        }\n    }\n\n    export class ForInStatement extends Statement {\n        constructor (public lval: AST, public obj: AST) {\n            super(NodeType.ForIn);\n            if (this.lval && (this.lval.nodeType == NodeType.VarDecl)) {\n                (<BoundDecl>this.lval).varFlags |= VarFlags.AutoInit;\n            }\n        }\n        public statement: ASTSpan = new ASTSpan();\n        public body: AST;\n\n        public isLoop() { return true; }\n\n        public isFiltered() {\n            if (this.body) {\n                var singleItem: AST = null;\n                if (this.body.nodeType == NodeType.List) {\n                    var stmts = <ASTList>this.body;\n                    if (stmts.members.length == 1) {\n                        singleItem = stmts.members[0];\n                    }\n                }\n                else {\n                    singleItem = this.body;\n                }\n                // match template for filtering 'own' properties from obj\n                if (singleItem !== null) {\n                    if (singleItem.nodeType == NodeType.Block) {\n                        var block = <Block>singleItem;\n                        if ((block.statements !== null) && (block.statements.members.length == 1)) {\n                            singleItem = block.statements.members[0];\n                        }\n                    }\n                    if (singleItem.nodeType == NodeType.If) {\n                        var cond = (<IfStatement>singleItem).cond;\n                        if (cond.nodeType == NodeType.Call) {\n                            var target = (<CallExpression>cond).target;\n                            if (target.nodeType == NodeType.Dot) {\n                                var binex = <BinaryExpression>target;\n                                if ((binex.operand1.nodeType == NodeType.Name) &&\n                                    (this.obj.nodeType == NodeType.Name) &&\n                                    ((<Identifier>binex.operand1).actualText == (<Identifier>this.obj).actualText)) {\n                                    var prop = <Identifier>binex.operand2;\n                                    if (prop.actualText == \"hasOwnProperty\") {\n                                        var args = (<CallExpression>cond).arguments;\n                                        if ((args !== null) && (args.members.length == 1)) {\n                                            var arg = args.members[0];\n                                            if ((arg.nodeType == NodeType.Name) &&\n                                                 (this.lval.nodeType == NodeType.Name)) {\n                                                if (((<Identifier>this.lval).actualText) == (<Identifier>arg).actualText) {\n                                                    return true;\n                                                }\n                                            }\n                                        }\n                                    }\n                                }\n                            }\n                        }\n                    }\n                }\n            }\n            return false;\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.recordSourceMappingStart(this.statement);\n            emitter.writeToOutput(\"for(\");\n            emitter.emitJavascript(this.lval, TokenID.For, false);\n            emitter.writeToOutput(\" in \");\n            emitter.emitJavascript(this.obj, TokenID.For, false);\n            emitter.writeToOutput(\")\");\n            emitter.recordSourceMappingEnd(this.statement);\n            emitter.emitJavascriptStatements(this.body, true);\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            if (typeFlow.checker.styleSettings.forin) {\n                if (!this.isFiltered()) {\n                    typeFlow.checker.errorReporter.styleError(this, \"no hasOwnProperty filter\");\n                }\n            }\n            return typeFlow.typeCheckForIn(this);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            if (this.lval) {\n                context.addContent(this.lval);\n            }\n            if (this.obj) {\n                context.addContent(this.obj);\n            }\n\n            var loopHeader = context.current;\n            var loopStart = new BasicBlock();\n            var afterLoop = new BasicBlock();\n\n            loopHeader.addSuccessor(loopStart);\n            context.current = loopStart;\n            if (this.body) {\n                context.pushStatement(this, loopStart, afterLoop);\n                context.walk(this.body, this);\n                context.popStatement();\n            }\n            if (!(context.noContinuation)) {\n                var loopEnd = context.current;\n                loopEnd.addSuccessor(loopStart);\n            }\n            context.current = afterLoop;\n            context.noContinuation = false;\n            loopHeader.addSuccessor(afterLoop);\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class ForStatement extends Statement {\n        public cond: AST;\n        public body: AST;\n        public incr: AST;\n\n        constructor (public init: AST) {\n            super(NodeType.For);\n        }\n\n        public isLoop() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.writeToOutput(\"for(\");\n            if (this.init) {\n                if (this.init.nodeType != NodeType.List) {\n                    emitter.emitJavascript(this.init, TokenID.For, false);\n                }\n                else {\n                    emitter.setInVarBlock((<ASTList>this.init).members.length); \n                    emitter.emitJavascriptList(this.init, null, TokenID.For, false, false, false);\n                }\n            }\n            emitter.writeToOutput(\"; \");\n            emitter.emitJavascript(this.cond, TokenID.For, false);\n            emitter.writeToOutput(\"; \");\n            emitter.emitJavascript(this.incr, TokenID.For, false);\n            emitter.writeToOutput(\")\");\n            emitter.emitJavascriptStatements(this.body, true);\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckFor(this);\n        }\n\n        public addToControlFlow(context: ControlFlowContext): void {\n            if (this.init) {\n                context.addContent(this.init);\n            }\n            var loopHeader = context.current;\n            var loopStart = new BasicBlock();\n            var afterLoop = new BasicBlock();\n\n            loopHeader.addSuccessor(loopStart);\n            context.current = loopStart;\n            var condBlock: BasicBlock = null;\n            var continueTarget = loopStart;\n            var incrBB: BasicBlock = null;\n            if (this.incr) {\n                incrBB = new BasicBlock();\n                continueTarget = incrBB;\n            }\n            if (this.cond) {\n                condBlock = context.current;\n                context.addContent(this.cond);\n                context.current = new BasicBlock();\n                condBlock.addSuccessor(context.current);\n            }\n            var targetInfo: ITargetInfo = null;\n            if (this.body) {\n                context.pushStatement(this, continueTarget, afterLoop);\n                context.walk(this.body, this);\n                targetInfo = context.popStatement();\n            }\n            if (this.incr) {\n                if (context.noContinuation) {\n                    if (incrBB.predecessors.length == 0) {\n                        context.addUnreachable(this.incr);\n                    }\n                }\n                else {\n                    context.current.addSuccessor(incrBB);\n                    context.current = incrBB;\n                    context.addContent(this.incr);\n                }\n            }\n            var loopEnd = context.current;\n            if (!(context.noContinuation)) {\n                loopEnd.addSuccessor(loopStart);\n\n            }\n            if (condBlock) {\n                condBlock.addSuccessor(afterLoop);\n                context.noContinuation = false;\n            }\n            if (afterLoop.predecessors.length > 0) {\n                context.noContinuation = false;\n                context.current = afterLoop;\n            }\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class WithStatement extends Statement {\n        public body: AST;\n\n        public isCompoundStatement() { return true; }\n\n        public withSym: WithSymbol = null;\n\n        constructor (public expr: AST) {\n            super(NodeType.With);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(\"with (\");\n            if (this.expr) {\n                emitter.emitJavascript(this.expr, TokenID.With, false);\n            }\n\n            emitter.writeToOutput(\")\");\n            emitter.emitJavascriptStatements(this.body, true);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            return typeFlow.typeCheckWith(this);\n        }\n    }\n\n    export class SwitchStatement extends Statement {\n        public caseList: ASTList;\n        public defaultCase: CaseStatement = null;\n        public statement: ASTSpan = new ASTSpan();\n\n        constructor (public val: AST) {\n            super(NodeType.Switch);\n        }\n\n        public isCompoundStatement() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            var temp = emitter.setInObjectLiteral(false);\n            emitter.recordSourceMappingStart(this.statement);\n            emitter.writeToOutput(\"switch(\");\n            emitter.emitJavascript(this.val, TokenID.Identifier, false);\n            emitter.writeToOutput(\")\"); \n            emitter.recordSourceMappingEnd(this.statement);\n            emitter.writeLineToOutput(\" {\");\n            emitter.indenter.increaseIndent();\n            var casesLen = this.caseList.members.length;\n            for (var i = 0; i < casesLen; i++) {\n                var caseExpr = this.caseList.members[i];\n                emitter.emitJavascript(caseExpr, TokenID.Case, true);\n            }\n            emitter.indenter.decreaseIndent();\n            emitter.emitIndent();\n            emitter.writeToOutput(\"}\");\n            emitter.setInObjectLiteral(temp);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            var len = this.caseList.members.length;\n            this.val = typeFlow.typeCheck(this.val);\n            for (var i = 0; i < len; i++) {\n                this.caseList.members[i] = typeFlow.typeCheck(this.caseList.members[i]);\n            }\n            this.defaultCase = <CaseStatement>typeFlow.typeCheck(this.defaultCase);\n            this.type = typeFlow.voidType;\n            return this;\n        }\n\n        // if there are break statements that match this switch, then just link cond block with block after switch\n        public addToControlFlow(context: ControlFlowContext) {\n            var condBlock = context.current;\n            context.addContent(this.val);\n            var execBlock = new BasicBlock();\n            var afterSwitch = new BasicBlock();\n\n            condBlock.addSuccessor(execBlock);\n            context.pushSwitch(execBlock);\n            context.current = execBlock;\n            context.pushStatement(this, execBlock, afterSwitch);\n            context.walk(this.caseList, this);\n            context.popSwitch();\n            var targetInfo = context.popStatement();\n            var hasCondContinuation = (this.defaultCase == null);\n            if (this.defaultCase == null) {\n                condBlock.addSuccessor(afterSwitch);\n            }\n            if (afterSwitch.predecessors.length > 0) {\n                context.noContinuation = false;\n                context.current = afterSwitch;\n            }\n            else {\n                context.noContinuation = true;\n            }\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class CaseStatement extends Statement {\n        public expr: AST = null;\n        public body: ASTList;\n\n        constructor () {\n            super(NodeType.Case);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            if (this.expr) {\n                emitter.writeToOutput(\"case \");\n                emitter.emitJavascript(this.expr, TokenID.Identifier, false);\n            }\n            else {\n                emitter.writeToOutput(\"default\");\n            }\n            emitter.writeToOutput(\":\");\n            if (this.body.members.length == 1 && this.body.members[0].nodeType == NodeType.Block) {\n                // The case statement was written with curly braces, so emit it with the appropriate formatting\n                emitter.emitJavascriptStatements(this.body, false);\n            }\n            else {\n                // No curly braces. Format in the expected way\n                emitter.writeLineToOutput(\"\");\n                emitter.indenter.increaseIndent();\n                emitter.emitBareJavascriptStatements(this.body);\n                emitter.indenter.decreaseIndent();\n            }\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.expr = typeFlow.typeCheck(this.expr);\n            typeFlow.typeCheck(this.body);\n            this.type = typeFlow.voidType;\n            return this;\n        }\n\n        // TODO: more reasoning about unreachable cases (such as duplicate literals as case expressions)\n        // for now, assume all cases are reachable, regardless of whether some cases fall through\n        public addToControlFlow(context: ControlFlowContext) {\n            var execBlock = new BasicBlock();\n            var sw = context.currentSwitch[context.currentSwitch.length - 1];\n            // TODO: fall-through from previous (+ to end of switch)\n            if (this.expr) {\n                var exprBlock = new BasicBlock();\n                context.current = exprBlock;\n                sw.addSuccessor(exprBlock);\n                context.addContent(this.expr);\n                exprBlock.addSuccessor(execBlock);\n            }\n            else {\n                sw.addSuccessor(execBlock);\n            }\n            context.current = execBlock;\n            if (this.body) {\n                context.walk(this.body, this);\n            }\n            context.noContinuation = false;\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class TypeReference extends AST {\n        constructor (public term: AST, public arrayCount: number) {\n            super(NodeType.TypeRef);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            throw new Error(\"should not emit a type ref\");\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            var prevInTCTR = typeFlow.inTypeRefTypeCheck;\n            typeFlow.inTypeRefTypeCheck = true;\n            var typeLink = getTypeLink(this, typeFlow.checker, true);\n            typeFlow.checker.resolveTypeLink(typeFlow.scope, typeLink, false);\n\n            if (this.term) {\n                typeFlow.typeCheck(this.term);\n            }\n\n            typeFlow.checkForVoidConstructor(typeLink.type, this);\n\n            this.type = typeLink.type;\n\n            // in error recovery cases, there may not be a term\n            if (this.term) {\n                this.term.type = this.type;\n            }\n\n            typeFlow.inTypeRefTypeCheck = prevInTCTR;\n            return this;\n        }\n    }\n\n    export class TryFinally extends Statement {\n        constructor (public tryNode: AST, public finallyNode: Finally) {\n            super(NodeType.TryFinally);\n        }\n\n        public isCompoundStatement() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.recordSourceMappingStart(this);\n            emitter.emitJavascript(this.tryNode, TokenID.Try, false);\n            emitter.emitJavascript(this.finallyNode, TokenID.Finally, false);\n            emitter.recordSourceMappingEnd(this);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.tryNode = typeFlow.typeCheck(this.tryNode);\n            this.finallyNode = <Finally>typeFlow.typeCheck(this.finallyNode);\n            this.type = typeFlow.voidType;\n            return this;\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            var afterFinally = new BasicBlock();\n            context.walk(this.tryNode, this);\n            var finBlock = new BasicBlock();\n            if (context.current) {\n                context.current.addSuccessor(finBlock);\n            }\n            context.current = finBlock;\n            context.pushStatement(this, null, afterFinally);\n            context.walk(this.finallyNode, this);\n            if (!context.noContinuation && context.current) {\n                context.current.addSuccessor(afterFinally);\n            }\n            if (afterFinally.predecessors.length > 0) {\n                context.current = afterFinally;\n            }\n            else {\n                context.noContinuation = true;\n            }\n            context.popStatement();\n            context.walker.options.goChildren = false;\n        }\n    }\n\n    export class TryCatch extends Statement {\n        constructor (public tryNode: Try, public catchNode: Catch) {\n            super(NodeType.TryCatch);\n        }\n\n        public isCompoundStatement() { return true; }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.emitJavascript(this.tryNode, TokenID.Try, false);\n            emitter.emitJavascript(this.catchNode, TokenID.Catch, false);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            var beforeTry = context.current;\n            var tryBlock = new BasicBlock();\n            beforeTry.addSuccessor(tryBlock);\n            context.current = tryBlock;\n            var afterTryCatch = new BasicBlock();\n            context.pushStatement(this, null, afterTryCatch);\n            context.walk(this.tryNode, this);\n            if (!context.noContinuation) {\n                if (context.current) {\n                    context.current.addSuccessor(afterTryCatch);\n                }\n            }\n            context.current = new BasicBlock();\n            beforeTry.addSuccessor(context.current);\n            context.walk(this.catchNode, this);\n            context.popStatement();\n            if (!context.noContinuation) {\n                if (context.current) {\n                    context.current.addSuccessor(afterTryCatch);\n                }\n            }\n            context.current = afterTryCatch;\n            context.walker.options.goChildren = false;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.tryNode = <Try>typeFlow.typeCheck(this.tryNode);\n            this.catchNode = <Catch>typeFlow.typeCheck(this.catchNode);\n            this.type = typeFlow.voidType;\n            return this;\n        }\n    }\n\n    export class Try extends Statement {\n        constructor (public body: AST) {\n            super(NodeType.Try);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(\"try \");\n            emitter.emitJavascript(this.body, TokenID.Try, false);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.body = typeFlow.typeCheck(this.body);\n            return this;\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            if (this.body) {\n                context.walk(this.body, this);\n            }\n            context.walker.options.goChildren = false;\n            context.noContinuation = false;\n        }\n    }\n\n    export class Catch extends Statement {\n        constructor (public param: VarDecl, public body: AST) {\n            super(NodeType.Catch);\n            if (this.param) {\n                this.param.varFlags |= VarFlags.AutoInit;\n            }\n        }\n        public statement: ASTSpan = new ASTSpan();\n        public containedScope: SymbolScope = null;\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(\" \");\n            emitter.recordSourceMappingStart(this.statement);\n            emitter.writeToOutput(\"catch (\");\n            emitter.emitJavascript(this.param, TokenID.OpenParen, false);\n            emitter.writeToOutput(\")\");\n            emitter.recordSourceMappingEnd(this.statement);\n            emitter.emitJavascript(this.body, TokenID.Catch, false);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            if (this.param) {\n                context.addContent(this.param);\n                var bodBlock = new BasicBlock();\n                context.current.addSuccessor(bodBlock);\n                context.current = bodBlock;\n            }\n            if (this.body) {\n                context.walk(this.body, this);\n            }\n            context.noContinuation = false;\n            context.walker.options.goChildren = false;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            var prevScope = typeFlow.scope;\n            typeFlow.scope = this.containedScope;\n            this.param = <VarDecl>typeFlow.typeCheck(this.param);\n            var exceptVar = new ValueLocation();\n            var varSym = new VariableSymbol((<VarDecl>this.param).id.text,\n                                          this.param.minChar,\n                                          typeFlow.checker.locationInfo.unitIndex,\n                                          exceptVar);\n            exceptVar.symbol = varSym;\n            exceptVar.typeLink = new TypeLink();\n            // var type for now (add syntax for type annotation)\n            exceptVar.typeLink.type = typeFlow.anyType;\n            var thisFnc = typeFlow.thisFnc;\n            if (thisFnc && thisFnc.type) {\n                exceptVar.symbol.container = thisFnc.type.symbol;\n            }\n            else {\n                exceptVar.symbol.container = null;\n            }\n            this.param.sym = exceptVar.symbol;\n            typeFlow.scope.enter(exceptVar.symbol.container, this.param, exceptVar.symbol,\n                                 typeFlow.checker.errorReporter, false, false, false);\n            this.body = typeFlow.typeCheck(this.body);\n\n            // if we're in provisional typecheck mode, clean up the symbol entry\n            // REVIEW: This is obviously bad form, since we're counting on the internal\n            // layout of the symbol table, but this is also the only place where we insert\n            // symbols during typecheck\n            if (typeFlow.checker.inProvisionalTypecheckMode()) {\n                var table = typeFlow.scope.getTable();\n                (<any>table).secondaryTable.table[exceptVar.symbol.name] = undefined;\n            }\n            this.type = typeFlow.voidType;\n            typeFlow.scope = prevScope;\n            return this;\n        }\n    }\n\n    export class Finally extends Statement {\n        constructor (public body: AST) {\n            super(NodeType.Finally);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeToOutput(\"finally\");\n            emitter.emitJavascript(this.body, TokenID.Finally, false);\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n\n        public addToControlFlow(context: ControlFlowContext) {\n            if (this.body) {\n                context.walk(this.body, this);\n            }\n            context.walker.options.goChildren = false;\n            context.noContinuation = false;\n        }\n\n        public typeCheck(typeFlow: TypeFlow) {\n            this.body = typeFlow.typeCheck(this.body);\n            return this;\n        }\n    }\n\n    export class Comment extends AST {\n\n        public text: string[] = null;\n        public minLine: number;\n        public limLine: number;\n        private docCommentText: string = null;\n\n        constructor (public content: string, public isBlockComment: bool, public endsLine) {\n            super(NodeType.Comment);\n        }\n\n        public getText(): string[] {\n            if (this.text == null) {\n                if (this.isBlockComment) {\n                    this.text = this.content.split(\"\\n\");\n                    for (var i = 0; i < this.text.length; i++) {\n                        this.text[i] = this.text[i].replace(/^\\s+|\\s+$/g, '');\n                    }\n                }\n                else {\n                    this.text = [(this.content.replace(/^\\s+|\\s+$/g, ''))];\n                }\n            }\n\n            return this.text;\n        }\n\n        public isDocComment() {\n            if (this.isBlockComment) {\n                return this.content.charAt(2) == \"*\";\n            }\n\n            return false;\n        }\n\n        public getDocCommentText() {\n            if (this.docCommentText == null) {\n                this.docCommentText = Comment.cleanJSDocComment(this.content);\n            }\n\n            return this.docCommentText;\n        }\n\n        static consumeLeadingSpace(line: string, startIndex: number, maxSpacesToRemove?: number) {\n            var endIndex = line.length;\n            if (maxSpacesToRemove != undefined) {\n                endIndex = min(startIndex + maxSpacesToRemove, endIndex);\n            }\n\n            for (; startIndex < endIndex; startIndex++) {\n                var charCode = line.charCodeAt(startIndex);\n                if (charCode != LexCodeSpace && charCode != LexCodeTAB) {\n                    return startIndex;\n                }\n            }\n            \n            if (endIndex != line.length) {\n                return endIndex;\n            }\n\n            return -1;\n        }\n\n        static isSpaceChar(line: string, index: number) {\n            var length = line.length;\n            if (index < length) {\n                var charCode = line.charCodeAt(index);\n                // If the character is space\n                return charCode == LexCodeSpace || charCode == LexCodeTAB;\n            }\n\n            // If the index is end of the line it is space\n            return index == length;\n        }\n\n        static cleanDocCommentLine(line: string, jsDocStyleComment: bool, jsDocLineSpaceToRemove?: number) {\n            var nonSpaceIndex = Comment.consumeLeadingSpace(line, 0);\n            if (nonSpaceIndex != -1) {\n                var jsDocSpacesRemoved = nonSpaceIndex;\n                if (jsDocStyleComment && line.charAt(nonSpaceIndex) == '*') { // remove leading * in case of jsDocComment\n                    var startIndex = nonSpaceIndex + 1;\n                    nonSpaceIndex = Comment.consumeLeadingSpace(line, startIndex, jsDocLineSpaceToRemove);\n\n                    if (nonSpaceIndex != -1) {\n                        jsDocSpacesRemoved = nonSpaceIndex - startIndex;\n                    } else {\n                        return null;\n                    }\n                }\n\n                return {\n                    minChar: nonSpaceIndex,\n                    limChar: line.charAt(line.length - 1) == \"\\r\" ? line.length - 1 : line.length,\n                    jsDocSpacesRemoved: jsDocSpacesRemoved\n                };\n            }\n\n            return null;\n        }\n\n        static cleanJSDocComment(content: string, spacesToRemove?: number) {\n            var docCommentLines: string[] = [];\n            content = content.replace(\"/**\", \"\"); // remove /**\n            if (content.length >= 2 && content.charAt(content.length - 1) == \"/\" && content.charAt(content.length - 2) == \"*\") {\n                content = content.substring(0, content.length - 2); // remove last */\n            }\n            var lines = content.split(\"\\n\");\n            var inParamTag = false;\n            for (var l = 0; l < lines.length; l++) {\n                var line = lines[l];\n                var cleanLinePos = Comment.cleanDocCommentLine(line, true, spacesToRemove);\n                if (!cleanLinePos) {\n                    // Whole line empty, read next line\n                    continue;\n                }\n\n                var docCommentText = \"\";\n                var prevPos = cleanLinePos.minChar;\n                for (var i = line.indexOf(\"@\", cleanLinePos.minChar); 0 <= i && i < cleanLinePos.limChar; i = line.indexOf(\"@\", i + 1)) {\n                    // We have encoutered @. \n                    // If we were omitting param comment, we dont have to do anything\n                    // other wise the content of the text till @ tag goes as doc comment\n                    var wasInParamtag = inParamTag;\n\n                    // Parse contents next to @\n                    if (line.indexOf(\"param\", i + 1) == i + 1 && Comment.isSpaceChar(line, i + 6)) {\n                        // It is param tag. \n\n                        // If we were not in param tag earlier, push the contents from prev pos of the tag this tag start as docComment\n                        if (!wasInParamtag) {\n                            docCommentText += line.substring(prevPos, i);\n                        }\n\n                        // New start of contents \n                        prevPos = i;\n                        inParamTag = true;\n                    } else if (wasInParamtag) {\n                        // Non param tag start\n                        prevPos = i;\n                        inParamTag = false;\n                    }\n                }\n\n                if (!inParamTag) {\n                    docCommentText += line.substring(prevPos, cleanLinePos.limChar);\n                }\n\n                // Add line to comment text if it is not only white space line\n                var newCleanPos = Comment.cleanDocCommentLine(docCommentText, false);\n                if (newCleanPos) {\n                    if (spacesToRemove == undefined) {\n                        spacesToRemove = cleanLinePos.jsDocSpacesRemoved;\n                    }\n                    docCommentLines.push(docCommentText);\n                }\n            }\n            \n            return docCommentLines.join(\"\\n\");\n        }\n\n        static getDocCommentText(comments: Comment[]) {\n            var docCommentText: string[] = [];\n            for (var c = 0 ; c < comments.length; c++) {\n                var commentText = comments[c].getDocCommentText();\n                if (commentText != \"\") {\n                    docCommentText.push(commentText);\n                }\n            }\n            return docCommentText.join(\"\\n\");\n        }\n\n        static getParameterDocCommentText(param: string, fncDocComments: Comment[]) {\n            if (fncDocComments.length == 0 || !fncDocComments[0].isBlockComment) {\n                // there were no fnc doc comments and the comment is not block comment then it cannot have \n                // @param comment that can be parsed\n                return \"\";\n            }\n            \n            for (var i = 0; i < fncDocComments.length; i++) {\n                var commentContents = fncDocComments[i].content;\n                for (var j = commentContents.indexOf(\"@param\", 0); 0 <= j; j = commentContents.indexOf(\"@param\", j)) {\n                    j += 6;\n                    if (!Comment.isSpaceChar(commentContents, j)) {\n                        // This is not param tag but a tag line @paramxxxxx\n                        continue;\n                    }\n\n                    // This is param tag. Check if it is what we are looking for\n                    j = Comment.consumeLeadingSpace(commentContents, j);\n                    if (j == -1) {\n                        break;\n                    }\n                    \n                    // Ignore the type expression\n                    if (commentContents.charCodeAt(j) == LexCodeLC) {\n                        j++;\n                        // Consume the type\n                        var charCode = 0;\n                        for (var curlies = 1; j < commentContents.length; j++) {\n                            charCode = commentContents.charCodeAt(j);\n                            // { character means we need to find another } to match the found one\n                            if (charCode == LexCodeLC) {\n                                curlies++;\n                                continue;\n                            }\n\n                            // } char\n                            if (charCode == LexCodeRC) {\n                                curlies--;\n                                if (curlies == 0) {\n                                    // We do not have any more } to match the type expression is ignored completely\n                                    break;\n                                } else {\n                                    // there are more { to be matched with }\n                                    continue;\n                                }\n                            }\n\n                            // Found start of another tag\n                            if (charCode == LexCodeAtSign) {\n                                break;\n                            }\n                        }\n\n                        // End of the comment\n                        if (j == commentContents.length) {\n                            break;\n                        }\n\n                        // End of the tag, go onto looking for next tag\n                        if (charCode == LexCodeAtSign) {\n                            continue;\n                        }\n\n                        j = Comment.consumeLeadingSpace(commentContents, j + 1);\n                        if (j == -1) {\n                            break;\n                        }\n                    }\n\n                    // Parameter name\n                    if (param != commentContents.substr(j, param.length) || !Comment.isSpaceChar(commentContents, j + param.length)) {\n                        // this is not the parameter we are looking for\n                        continue;\n                    }\n\n                    // Found the parameter we were looking for\n                    j = Comment.consumeLeadingSpace(commentContents, j + param.length);\n                    if (j == -1) {\n                        return \"\";\n                    }\n                    \n                    var endOfParam = commentContents.indexOf(\"@\", j);\n                    var paramHelpString = commentContents.substring(j, endOfParam < 0 ? commentContents.length : endOfParam);\n\n                    // Find alignement spaces to remove\n                    var paramSpacesToRemove: number = undefined;\n                    var paramLineIndex = commentContents.substring(0, j).lastIndexOf(\"\\n\") + 1;\n                    if (paramLineIndex != 0) {\n                        if (paramLineIndex < j && commentContents.charAt(paramLineIndex + 1) == \"\\r\") {\n                            paramLineIndex++;\n                        }\n                    }\n                    var startSpaceRemovalIndex = Comment.consumeLeadingSpace(commentContents, paramLineIndex);\n                    if (startSpaceRemovalIndex != j && commentContents.charAt(startSpaceRemovalIndex) == \"*\") {\n                        paramSpacesToRemove = j - startSpaceRemovalIndex - 1;\n                    }\n\n                    // Clean jsDocComment and return\n                    return Comment.cleanJSDocComment(paramHelpString, paramSpacesToRemove);\n                }\n            }\n\n            return \"\";\n        }\n\n        static getDocCommentTextOfSignatures(signatures: Signature[]) {\n            var comments: string[] = [];\n            for (var i = 0; i < signatures.length; i++) {\n                var signatureDocComment = TypeScript.Comment.getDocCommentText(signatures[i].declAST.getDocComments());\n                if (signatureDocComment != \"\") {\n                    comments.push(signatureDocComment);\n                }\n            }\n\n            return comments.join(\"\\n\");\n        }\n    }\n\n    export class DebuggerStatement extends Statement {\n        constructor () {\n            super(NodeType.Debugger);\n        }\n\n        public emit(emitter: Emitter, tokenId: TokenID, startLine: bool) {\n            emitter.emitParensAndCommentsInPlace(this, true);\n            emitter.recordSourceMappingStart(this);\n            emitter.writeLineToOutput(\"debugger;\");\n            emitter.recordSourceMappingEnd(this);\n            emitter.emitParensAndCommentsInPlace(this, false);\n        }\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript.AstWalkerWithDetailCallback {\n    export interface AstWalkerDetailCallback {\n        EmptyCallback? (pre, ast: AST): bool;\n        EmptyExprCallback? (pre, ast: AST): bool;\n        TrueCallback? (pre, ast: AST): bool;\n        FalseCallback? (pre, ast: AST): bool;\n        ThisCallback? (pre, ast: AST): bool;\n        SuperCallback? (pre, ast: AST): bool;\n        QStringCallback? (pre, ast: AST): bool;\n        RegexCallback? (pre, ast: AST): bool;\n        NullCallback? (pre, ast: AST): bool;\n        ArrayLitCallback? (pre, ast: AST): bool;\n        ObjectLitCallback? (pre, ast: AST): bool;\n        VoidCallback? (pre, ast: AST): bool;\n        CommaCallback? (pre, ast: AST): bool;\n        PosCallback? (pre, ast: AST): bool;\n        NegCallback? (pre, ast: AST): bool;\n        DeleteCallback? (pre, ast: AST): bool;\n        AwaitCallback? (pre, ast: AST): bool;\n        InCallback? (pre, ast: AST): bool;\n        DotCallback? (pre, ast: AST): bool;\n        FromCallback? (pre, ast: AST): bool;\n        IsCallback? (pre, ast: AST): bool;\n        InstOfCallback? (pre, ast: AST): bool;\n        TypeofCallback? (pre, ast: AST): bool;\n        NumberLitCallback? (pre, ast: AST): bool;\n        NameCallback? (pre, identifierAst: Identifier): bool;\n        TypeRefCallback? (pre, ast: AST): bool;\n        IndexCallback? (pre, ast: AST): bool;\n        CallCallback? (pre, ast: AST): bool;\n        NewCallback? (pre, ast: AST): bool;\n        AsgCallback? (pre, ast: AST): bool;\n        AsgAddCallback? (pre, ast: AST): bool;\n        AsgSubCallback? (pre, ast: AST): bool;\n        AsgDivCallback? (pre, ast: AST): bool;\n        AsgMulCallback? (pre, ast: AST): bool;\n        AsgModCallback? (pre, ast: AST): bool;\n        AsgAndCallback? (pre, ast: AST): bool;\n        AsgXorCallback? (pre, ast: AST): bool;\n        AsgOrCallback? (pre, ast: AST): bool;\n        AsgLshCallback? (pre, ast: AST): bool;\n        AsgRshCallback? (pre, ast: AST): bool;\n        AsgRs2Callback? (pre, ast: AST): bool;\n        QMarkCallback? (pre, ast: AST): bool;\n        LogOrCallback? (pre, ast: AST): bool;\n        LogAndCallback? (pre, ast: AST): bool;\n        OrCallback? (pre, ast: AST): bool;\n        XorCallback? (pre, ast: AST): bool;\n        AndCallback? (pre, ast: AST): bool;\n        EqCallback? (pre, ast: AST): bool;\n        NeCallback? (pre, ast: AST): bool;\n        EqvCallback? (pre, ast: AST): bool;\n        NEqvCallback? (pre, ast: AST): bool;\n        LtCallback? (pre, ast: AST): bool;\n        LeCallback? (pre, ast: AST): bool;\n        GtCallback? (pre, ast: AST): bool;\n        GeCallback? (pre, ast: AST): bool;\n        AddCallback? (pre, ast: AST): bool;\n        SubCallback? (pre, ast: AST): bool;\n        MulCallback? (pre, ast: AST): bool;\n        DivCallback? (pre, ast: AST): bool;\n        ModCallback? (pre, ast: AST): bool;\n        LshCallback? (pre, ast: AST): bool;\n        RshCallback? (pre, ast: AST): bool;\n        Rs2Callback? (pre, ast: AST): bool;\n        NotCallback? (pre, ast: AST): bool;\n        LogNotCallback? (pre, ast: AST): bool;\n        IncPreCallback? (pre, ast: AST): bool;\n        DecPreCallback? (pre, ast: AST): bool;\n        IncPostCallback? (pre, ast: AST): bool;\n        DecPostCallback? (pre, ast: AST): bool;\n        TypeAssertionCallback? (pre, ast: AST): bool;\n        FuncDeclCallback? (pre, funcDecl: FuncDecl): bool;\n        MemberCallback? (pre, ast: AST): bool;\n        VarDeclCallback? (pre, varDecl: VarDecl): bool;\n        ArgDeclCallback? (pre, ast: AST): bool;\n        ReturnCallback? (pre, ast: AST): bool;\n        BreakCallback? (pre, ast: AST): bool;\n        ContinueCallback? (pre, ast: AST): bool;\n        ThrowCallback? (pre, ast: AST): bool;\n        ForCallback? (pre, ast: AST): bool;\n        ForInCallback? (pre, ast: AST): bool;\n        IfCallback? (pre, ast: AST): bool;\n        WhileCallback? (pre, ast: AST): bool;\n        DoWhileCallback? (pre, ast: AST): bool;\n        BlockCallback? (pre, block: Block): bool;\n        CaseCallback? (pre, ast: AST): bool;\n        SwitchCallback? (pre, ast: AST): bool;\n        TryCallback? (pre, ast: AST): bool;\n        TryCatchCallback? (pre, ast: AST): bool;\n        TryFinallyCallback? (pre, ast: AST): bool;\n        FinallyCallback? (pre, ast: AST): bool;\n        CatchCallback? (pre, ast: AST): bool;\n        ListCallback? (pre, astList: ASTList): bool;\n        ScriptCallback? (pre, script: Script): bool;\n        ClassDeclarationCallback? (pre, ast: AST): bool;\n        InterfaceDeclarationCallback? (pre, interfaceDecl: InterfaceDeclaration): bool;\n        ModuleDeclarationCallback? (pre, moduleDecl: ModuleDeclaration): bool;\n        ImportDeclarationCallback? (pre, ast: AST): bool;\n        WithCallback? (pre, ast: AST): bool;\n        LabelCallback? (pre, labelAST: AST): bool;\n        LabeledStatementCallback? (pre, ast: AST): bool;\n        EBStartCallback? (pre, ast: AST): bool;\n        GotoEBCallback? (pre, ast: AST): bool;\n        EndCodeCallback? (pre, ast: AST): bool;\n        ErrorCallback? (pre, ast: AST): bool;\n        CommentCallback? (pre, ast: AST): bool;\n        DebuggerCallback? (pre, ast: AST): bool;\n        DefaultCallback? (pre, ast: AST): bool;\n    }\n\n    export function walk(script: Script, callback: AstWalkerDetailCallback): void {\n        var pre = (cur: AST, parent: AST) => {\n            walker.options.goChildren = AstWalkerCallback(true, cur, callback);\n            return cur;\n        }\n\n        var post = (cur: AST, parent: AST) => {\n            AstWalkerCallback(false, cur, callback);\n            return cur;\n        }\n\n        var walker = TypeScript.getAstWalkerFactory().getWalker(pre, post);\n        walker.walk(script, null);\n    }\n\n    function AstWalkerCallback(pre: bool, ast: AST, callback: AstWalkerDetailCallback): bool {\n        // See if the Callback needs to be handled using specific one or default one\n        var nodeType = ast.nodeType;\n        var callbackString = (<any>NodeType)._map[nodeType] + \"Callback\";\n        if (callback[callbackString]) {\n            return callback[callbackString](pre, ast);\n        }\n\n        if (callback.DefaultCallback) {\n            return callback.DefaultCallback(pre, ast);\n        }\n\n        return true;\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export interface IAstWalker {\n        walk(ast: AST, parent: AST): AST;\n        options: AstWalkOptions;\n        state: any; // user state object\n    }\n\n    export class AstWalkOptions {\n        public goChildren = true;\n        public goNextSibling = true;\n        public reverseSiblings = false; // visit siblings in reverse execution order\n\n        public stopWalk(stop:bool = true) {\n            this.goChildren = !stop;\n            this.goNextSibling = !stop;\n        }\n    }\n\n    export interface IAstWalkCallback {\n        (ast: AST, parent: AST, walker: IAstWalker): AST;\n    }\n\n    export interface IAstWalkChildren {\n        (preAst: AST, parent: AST, walker: IAstWalker): void;\n    }\n\n    class AstWalker implements IAstWalker {\n        constructor (\n            private childrenWalkers: IAstWalkChildren[],\n            private pre: IAstWalkCallback,\n            private post: IAstWalkCallback,\n            public options: AstWalkOptions,\n            public state: any) {\n        }\n\n        public walk(ast: AST, parent: AST): AST {\n            var preAst = this.pre(ast, parent, this);\n            if (preAst === undefined) {\n                preAst = ast;\n            }\n            if (this.options.goChildren) {\n                var svGoSib = this.options.goNextSibling;\n                this.options.goNextSibling = true;\n                // Call the \"walkChildren\" function corresponding to \"nodeType\".\n                this.childrenWalkers[ast.nodeType](ast, parent, this);\n                this.options.goNextSibling = svGoSib;\n            }\n            else {\n                // no go only applies to children of node issuing it\n                this.options.goChildren = true;\n            }\n            if (this.post) {\n                var postAst = this.post(preAst, parent, this);\n                if (postAst === undefined) {\n                    postAst = preAst;\n                }\n                return postAst;\n            }\n            else {\n                return preAst;\n            }\n        }\n    }\n\n    export class AstWalkerFactory {\n        private childrenWalkers: IAstWalkChildren[] = [];\n\n        constructor () {\n            this.initChildrenWalkers();\n        }\n\n        public walk(ast: AST, pre: IAstWalkCallback, post?: IAstWalkCallback, options?: AstWalkOptions, state?: any): AST {\n            return this.getWalker(pre, post, options, state).walk(ast, null)\n        }\n\n        public getWalker(pre: IAstWalkCallback, post?: IAstWalkCallback, options?: AstWalkOptions, state?: any): IAstWalker {\n            return this.getSlowWalker(pre, post, options, state);\n        }\n\n        private getSlowWalker(pre: IAstWalkCallback, post?: IAstWalkCallback, options?: AstWalkOptions, state?: any): IAstWalker {\n            if (!options) {\n                options = new AstWalkOptions();\n            }\n\n            return new AstWalker(this.childrenWalkers, pre, post, options, state);\n        }\n\n        private initChildrenWalkers(): void {\n            this.childrenWalkers[NodeType.None] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Empty] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.EmptyExpr] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.True] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.False] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.This] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Super] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.QString] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Regex] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Null] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.ArrayLit] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.ObjectLit] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.Void] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.Comma] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Pos] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.Neg] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.Delete] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.Await] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.In] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Dot] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.From] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Is] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.InstOf] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Typeof] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.NumberLit] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Name] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.TypeRef] = ChildrenWalkers.walkTypeReferenceChildren;\n            this.childrenWalkers[NodeType.Index] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Call] = ChildrenWalkers.walkCallExpressionChildren;\n            this.childrenWalkers[NodeType.New] = ChildrenWalkers.walkCallExpressionChildren;\n            this.childrenWalkers[NodeType.Asg] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgAdd] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgSub] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgDiv] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgMul] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgMod] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgAnd] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgXor] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgOr] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgLsh] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgRsh] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.AsgRs2] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.ConditionalExpression] = ChildrenWalkers.walkTrinaryExpressionChildren;\n            this.childrenWalkers[NodeType.LogOr] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.LogAnd] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Or] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Xor] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.And] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Eq] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Ne] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Eqv] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.NEqv] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Lt] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Le] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Gt] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Ge] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Add] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Sub] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Mul] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Div] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Mod] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Lsh] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Rsh] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Rs2] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.Not] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.LogNot] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.IncPre] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.DecPre] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.IncPost] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.DecPost] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.TypeAssertion] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.FuncDecl] = ChildrenWalkers.walkFuncDeclChildren;\n            this.childrenWalkers[NodeType.Member] = ChildrenWalkers.walkBinaryExpressionChildren;\n            this.childrenWalkers[NodeType.VarDecl] = ChildrenWalkers.walkBoundDeclChildren;\n            this.childrenWalkers[NodeType.ArgDecl] = ChildrenWalkers.walkBoundDeclChildren;\n            this.childrenWalkers[NodeType.Return] = ChildrenWalkers.walkReturnStatementChildren;\n            this.childrenWalkers[NodeType.Break] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Continue] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Throw] = ChildrenWalkers.walkUnaryExpressionChildren;\n            this.childrenWalkers[NodeType.For] = ChildrenWalkers.walkForStatementChildren;\n            this.childrenWalkers[NodeType.ForIn] = ChildrenWalkers.walkForInStatementChildren;\n            this.childrenWalkers[NodeType.If] = ChildrenWalkers.walkIfStatementChildren;\n            this.childrenWalkers[NodeType.While] = ChildrenWalkers.walkWhileStatementChildren;\n            this.childrenWalkers[NodeType.DoWhile] = ChildrenWalkers.walkDoWhileStatementChildren;\n            this.childrenWalkers[NodeType.Block] = ChildrenWalkers.walkBlockChildren;\n            this.childrenWalkers[NodeType.Case] = ChildrenWalkers.walkCaseStatementChildren;\n            this.childrenWalkers[NodeType.Switch] = ChildrenWalkers.walkSwitchStatementChildren;\n            this.childrenWalkers[NodeType.Try] = ChildrenWalkers.walkTryChildren;\n            this.childrenWalkers[NodeType.TryCatch] = ChildrenWalkers.walkTryCatchChildren;\n            this.childrenWalkers[NodeType.TryFinally] = ChildrenWalkers.walkTryFinallyChildren;\n            this.childrenWalkers[NodeType.Finally] = ChildrenWalkers.walkFinallyChildren;\n            this.childrenWalkers[NodeType.Catch] = ChildrenWalkers.walkCatchChildren;\n            this.childrenWalkers[NodeType.List] = ChildrenWalkers.walkListChildren;\n            this.childrenWalkers[NodeType.Script] = ChildrenWalkers.walkScriptChildren;\n            this.childrenWalkers[NodeType.ClassDeclaration] = ChildrenWalkers.walkClassDeclChildren;\n            this.childrenWalkers[NodeType.InterfaceDeclaration] = ChildrenWalkers.walkTypeDeclChildren;\n            this.childrenWalkers[NodeType.ModuleDeclaration] = ChildrenWalkers.walkModuleDeclChildren;\n            this.childrenWalkers[NodeType.ImportDeclaration] = ChildrenWalkers.walkImportDeclChildren;\n            this.childrenWalkers[NodeType.With] = ChildrenWalkers.walkWithStatementChildren;\n            this.childrenWalkers[NodeType.Label] = ChildrenWalkers.walkLabelChildren;\n            this.childrenWalkers[NodeType.LabeledStatement] = ChildrenWalkers.walkLabeledStatementChildren;\n            this.childrenWalkers[NodeType.EBStart] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.GotoEB] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.EndCode] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Error] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Comment] = ChildrenWalkers.walkNone;\n            this.childrenWalkers[NodeType.Debugger] = ChildrenWalkers.walkNone;\n\n            // Verify the code is up to date with the enum\n            for (var e in (<any>NodeType)._map) {\n                if ((<any>this.childrenWalkers)[e] === undefined) {\n                    throw new Error(\"initWalkers function is not up to date with enum content!\");\n                }\n            }\n        }\n    }\n\n    var globalAstWalkerFactory: AstWalkerFactory;\n\n    export function getAstWalkerFactory(): AstWalkerFactory {\n        if (!globalAstWalkerFactory) {\n            globalAstWalkerFactory = new AstWalkerFactory();\n        }\n        return globalAstWalkerFactory;\n    }\n\n    module ChildrenWalkers {\n        export function walkNone(preAst: ASTList, parent: AST, walker: IAstWalker): void {\n            // Nothing to do\n        }\n\n        export function walkListChildren(preAst: ASTList, parent: AST, walker: IAstWalker): void {\n            var len = preAst.members.length;\n            if (walker.options.reverseSiblings) {\n                for (var i = len - 1; i >= 0; i--) {\n                    if (walker.options.goNextSibling) {\n                        preAst.members[i] = walker.walk(preAst.members[i], preAst);\n                    }\n                }\n            }\n            else {\n                for (var i = 0; i < len; i++) {\n                    if (walker.options.goNextSibling) {\n                        preAst.members[i] = walker.walk(preAst.members[i], preAst);\n                    }\n                }\n            }\n        }\n\n        export function walkUnaryExpressionChildren(preAst: UnaryExpression, parent: AST, walker: IAstWalker): void {\n            if (preAst.castTerm) {\n                preAst.castTerm = walker.walk(preAst.castTerm, preAst);\n            }\n            if (preAst.operand) {\n                preAst.operand = walker.walk(preAst.operand, preAst);\n            }\n        }\n\n        export function walkBinaryExpressionChildren(preAst: BinaryExpression, parent: AST, walker: IAstWalker): void {\n            if (walker.options.reverseSiblings) {\n                if (preAst.operand2) {\n                    preAst.operand2 = walker.walk(preAst.operand2, preAst);\n                }\n                if ((preAst.operand1) && (walker.options.goNextSibling)) {\n                    preAst.operand1 = walker.walk(preAst.operand1, preAst);\n                }\n            } else {\n                if (preAst.operand1) {\n                    preAst.operand1 = walker.walk(preAst.operand1, preAst);\n                }\n                if ((preAst.operand2) && (walker.options.goNextSibling)) {\n                    preAst.operand2 = walker.walk(preAst.operand2, preAst);\n                }\n            }\n        }\n\n        export function walkTypeReferenceChildren(preAst: TypeReference, parent: AST, walker: IAstWalker): void {\n            if (preAst.term) {\n                preAst.term = walker.walk(preAst.term, preAst);\n            }\n        }\n\n        export function walkCallExpressionChildren(preAst: CallExpression, parent: AST, walker: IAstWalker): void {\n            if (!walker.options.reverseSiblings) {\n                preAst.target = walker.walk(preAst.target, preAst);\n            }\n            if (preAst.arguments && (walker.options.goNextSibling)) {\n                preAst.arguments = <ASTList> walker.walk(preAst.arguments, preAst);\n            }\n            if ((walker.options.reverseSiblings) && (walker.options.goNextSibling)) {\n                preAst.target = walker.walk(preAst.target, preAst);\n            }\n        }\n\n        export function walkTrinaryExpressionChildren(preAst: ConditionalExpression, parent: AST, walker: IAstWalker): void {\n            if (preAst.operand1) {\n                preAst.operand1 = walker.walk(preAst.operand1, preAst);\n            }\n            if (preAst.operand2 && (walker.options.goNextSibling)) {\n                preAst.operand2 = walker.walk(preAst.operand2, preAst);\n            }\n            if (preAst.operand3 && (walker.options.goNextSibling)) {\n                preAst.operand3 = walker.walk(preAst.operand3, preAst);\n            }\n        }\n\n        export function walkFuncDeclChildren(preAst: FuncDecl, parent: AST, walker: IAstWalker): void {\n            if (preAst.name) {\n                preAst.name = <Identifier>walker.walk(preAst.name, preAst);\n            }\n            if (preAst.arguments && (preAst.arguments.members.length > 0) && (walker.options.goNextSibling)) {\n                preAst.arguments = <ASTList>walker.walk(preAst.arguments, preAst);\n            }\n            if (preAst.returnTypeAnnotation && (walker.options.goNextSibling)) {\n                preAst.returnTypeAnnotation = walker.walk(preAst.returnTypeAnnotation, preAst);\n            }\n            if (preAst.bod && (preAst.bod.members.length > 0) && (walker.options.goNextSibling)) {\n                preAst.bod = <ASTList>walker.walk(preAst.bod, preAst);\n            }\n        }\n\n        export function walkBoundDeclChildren(preAst: BoundDecl, parent: AST, walker: IAstWalker): void {\n            if (preAst.id) {\n                preAst.id = <Identifier>walker.walk(preAst.id, preAst);\n            }\n            if (preAst.init) {\n                preAst.init = walker.walk(preAst.init, preAst);\n            }\n            if ((preAst.typeExpr) && (walker.options.goNextSibling)) {\n                preAst.typeExpr = walker.walk(preAst.typeExpr, preAst);\n            }\n        }\n\n        export function walkReturnStatementChildren(preAst: ReturnStatement, parent: AST, walker: IAstWalker): void {\n            if (preAst.returnExpression) {\n                preAst.returnExpression = walker.walk(preAst.returnExpression, preAst);\n            }\n        }\n\n        export function walkForStatementChildren(preAst: ForStatement, parent: AST, walker: IAstWalker): void {\n            if (preAst.init) {\n                preAst.init = walker.walk(preAst.init, preAst);\n            }\n\n            if (preAst.cond && walker.options.goNextSibling) {\n                preAst.cond = walker.walk(preAst.cond, preAst);\n            }\n\n            if (preAst.incr && walker.options.goNextSibling) {\n                preAst.incr = walker.walk(preAst.incr, preAst);\n            }\n\n            if (preAst.body && walker.options.goNextSibling) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkForInStatementChildren(preAst: ForInStatement, parent: AST, walker: IAstWalker): void {\n            preAst.lval = walker.walk(preAst.lval, preAst);\n            if (walker.options.goNextSibling) {\n                preAst.obj = walker.walk(preAst.obj, preAst);\n            }\n            if (preAst.body && (walker.options.goNextSibling)) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkIfStatementChildren(preAst: IfStatement, parent: AST, walker: IAstWalker): void {\n            preAst.cond = walker.walk(preAst.cond, preAst);\n            if (preAst.thenBod && (walker.options.goNextSibling)) {\n                preAst.thenBod = walker.walk(preAst.thenBod, preAst);\n            }\n            if (preAst.elseBod && (walker.options.goNextSibling)) {\n                preAst.elseBod = walker.walk(preAst.elseBod, preAst);\n            }\n        }\n\n        export function walkWhileStatementChildren(preAst: WhileStatement, parent: AST, walker: IAstWalker): void {\n            preAst.cond = walker.walk(preAst.cond, preAst);\n            if (preAst.body && (walker.options.goNextSibling)) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkDoWhileStatementChildren(preAst: DoWhileStatement, parent: AST, walker: IAstWalker): void {\n            preAst.cond = walker.walk(preAst.cond, preAst);\n            if (preAst.body && (walker.options.goNextSibling)) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkBlockChildren(preAst: Block, parent: AST, walker: IAstWalker): void {\n            if (preAst.statements) {\n                preAst.statements = <ASTList>walker.walk(preAst.statements, preAst);\n            }\n        }\n\n        export function walkCaseStatementChildren(preAst: CaseStatement, parent: AST, walker: IAstWalker): void {\n            if (preAst.expr) {\n                preAst.expr = walker.walk(preAst.expr, preAst);\n            }\n\n            if (preAst.body && walker.options.goNextSibling) {\n                preAst.body = <ASTList>walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkSwitchStatementChildren(preAst: SwitchStatement, parent: AST, walker: IAstWalker): void {\n            if (preAst.val) {\n                preAst.val = walker.walk(preAst.val, preAst);\n            }\n\n            if ((preAst.caseList) && walker.options.goNextSibling) {\n                preAst.caseList = <ASTList>walker.walk(preAst.caseList, preAst);\n            }\n        }\n\n        export function walkTryChildren(preAst: Try, parent: AST, walker: IAstWalker): void {\n            if (preAst.body) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkTryCatchChildren(preAst: TryCatch, parent: AST, walker: IAstWalker): void {\n            if (preAst.tryNode) {\n                preAst.tryNode = <Try>walker.walk(preAst.tryNode, preAst);\n            }\n\n            if ((preAst.catchNode) && walker.options.goNextSibling) {\n                preAst.catchNode = <Catch>walker.walk(preAst.catchNode, preAst);\n            }\n        }\n\n        export function walkTryFinallyChildren(preAst: TryFinally, parent: AST, walker: IAstWalker): void {\n            if (preAst.tryNode) {\n                preAst.tryNode = walker.walk(preAst.tryNode, preAst);\n            }\n\n            if (preAst.finallyNode && walker.options.goNextSibling) {\n                preAst.finallyNode = <Finally>walker.walk(preAst.finallyNode, preAst);\n            }\n        }\n\n        export function walkFinallyChildren(preAst: Finally, parent: AST, walker: IAstWalker): void {\n            if (preAst.body) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkCatchChildren(preAst: Catch, parent: AST, walker: IAstWalker): void {\n            if (preAst.param) {\n                preAst.param = <VarDecl>walker.walk(preAst.param, preAst);\n            }\n\n            if ((preAst.body) && walker.options.goNextSibling) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkRecordChildren(preAst: NamedDeclaration, parent: AST, walker: IAstWalker): void {\n            preAst.name = <Identifier>walker.walk(preAst.name, preAst);\n            if (walker.options.goNextSibling && preAst.members) {\n                preAst.members = <ASTList>walker.walk(preAst.members, preAst);\n            }\n\n        }\n\n        export function walkNamedTypeChildren(preAst: TypeDeclaration, parent: AST, walker: IAstWalker): void {\n            walkRecordChildren(preAst, parent, walker);\n        }\n\n        export function walkClassDeclChildren(preAst: ClassDeclaration, parent: AST, walker: IAstWalker): void {\n            walkNamedTypeChildren(preAst, parent, walker);\n\n            if (walker.options.goNextSibling && preAst.extendsList) {\n                preAst.extendsList = <ASTList>walker.walk(preAst.extendsList, preAst);\n            }\n\n            if (walker.options.goNextSibling && preAst.implementsList) {\n                preAst.implementsList = <ASTList>walker.walk(preAst.implementsList, preAst);\n            }\n        }\n\n        export function walkScriptChildren(preAst: Script, parent: AST, walker: IAstWalker): void {\n            if (preAst.bod) {\n                preAst.bod = <ASTList>walker.walk(preAst.bod, preAst);\n            }\n        }\n\n        export function walkTypeDeclChildren(preAst: InterfaceDeclaration, parent: AST, walker: IAstWalker): void {\n            walkNamedTypeChildren(preAst, parent, walker);\n\n            // walked arguments as part of members\n            if (walker.options.goNextSibling && preAst.extendsList) {\n                preAst.extendsList = <ASTList>walker.walk(preAst.extendsList, preAst);\n            }\n\n            if (walker.options.goNextSibling && preAst.implementsList) {\n                preAst.implementsList = <ASTList>walker.walk(preAst.implementsList, preAst);\n            }\n        }\n\n        export function walkModuleDeclChildren(preAst: ModuleDeclaration, parent: AST, walker: IAstWalker): void {\n            walkRecordChildren(preAst, parent, walker);\n        }\n\n        export function walkImportDeclChildren(preAst: ImportDeclaration, parent: AST, walker: IAstWalker): void {\n            if (preAst.id) {\n                preAst.id = <Identifier>walker.walk(preAst.id, preAst);\n            }\n            if (preAst.alias) {\n                preAst.alias = walker.walk(preAst.alias, preAst);\n            }\n        }\n\n        export function walkWithStatementChildren(preAst: WithStatement, parent: AST, walker: IAstWalker): void {\n            if (preAst.expr) {\n                preAst.expr = walker.walk(preAst.expr, preAst);\n            }\n\n            if (preAst.body && walker.options.goNextSibling) {\n                preAst.body = walker.walk(preAst.body, preAst);\n            }\n        }\n\n        export function walkLabelChildren(preAst: Label, parent: AST, walker: IAstWalker): void {\n            //TODO: Walk \"id\"?\n        }\n\n        export function walkLabeledStatementChildren(preAst: LabeledStatement, parent: AST, walker: IAstWalker): void {\n            preAst.labels = <ASTList>walker.walk(preAst.labels, preAst);\n            if (walker.options.goNextSibling) {\n                preAst.stmt = walker.walk(preAst.stmt, preAst);\n            }\n        }\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\nmodule TypeScript {\n    class Base64Format {\n        static encodedValues = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';\n        static encode(inValue: number) {\n            if (inValue < 64) {\n                return encodedValues.charAt(inValue);\n            }\n            throw TypeError(inValue + \": not a 64 based value\");\n        }\n\n        static decodeChar(inChar: string) {\n            if (inChar.length === 1) {\n                return encodedValues.indexOf(inChar);\n            } else {\n                throw TypeError('\"' + inChar + '\" must have length 1');\n            }\n        }\n    }\n\n    export class Base64VLQFormat {\n        static encode(inValue: number) {\n            // Add a new least significant bit that has the sign of the value.\n            // if negative number the least significant bit that gets added to the number has value 1\n            // else least significant bit value that gets added is 0\n            // eg. -1 changes to binary : 01 [1] => 3\n            //     +1 changes to binary : 01 [0] => 2\n            if (inValue < 0) {\n                inValue = ((-inValue) << 1) + 1;\n            }\n            else {\n                inValue = inValue << 1;\n            }\n\n            // Encode 5 bits at a time starting from least significant bits\n            var encodedStr = \"\";\n            do {\n                var currentDigit = inValue & 31; // 11111\n                inValue = inValue >> 5;\n                if (inValue > 0) {\n                    // There are still more digits to decode, set the msb (6th bit)\n                    currentDigit = currentDigit | 32; \n                }\n                encodedStr = encodedStr + Base64Format.encode(currentDigit);\n            } while (inValue > 0);\n\n            return encodedStr;\n        }\n\n        static decode(inString: string) {\n            var result = 0;\n            var negative = false;\n\n            var shift = 0;\n            for (var i = 0; i < inString.length; i++) {\n                var byte = Base64Format.decodeChar(inString[i]);\n                if (i === 0) {\n                    // Sign bit appears in the LSBit of the first value\n                    if ((byte & 1) === 1) {\n                        negative = true;\n                    }\n                    result = (byte >> 1) & 15; // 1111x\n                } else {\n                    result = result | ((byte & 31) << shift); // 11111\n                }\n\n                shift += (i == 0) ? 4 : 5;\n\n                if ((byte & 32) === 32) {\n                    // Continue\n                } else {\n                    return { value: negative ? -(result) : result, rest: inString.substr(i + 1) };\n                }\n            }\n\n            throw new Error('Base64 value \"' + inString + '\" finished with a continuation bit');\n        }\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export class Binder {\n        constructor(public checker: TypeChecker) { }\n        \n        public resolveBaseTypeLinks(typeLinks: TypeLink[], scope: SymbolScope) {\n            var extendsList: Type[] = null;\n            if (typeLinks) {\n                extendsList = new Type[];\n                for (var i = 0, len = typeLinks.length; i < len; i++) {\n                    extendsList[i] = this.checker.resolveBaseTypeLink(typeLinks[i], scope);\n                }\n            }\n            return extendsList;\n        }\n\n        public resolveBases(scope: SymbolScope, type: Type) {\n            type.extendsList = this.resolveBaseTypeLinks(type.extendsTypeLinks, scope);\n\n            var i = 0, len = type.extendsList.length;\n            var derivedIsClass = type.isClassInstance();\n            for (; i < len; i++) {\n                var baseIsClass = type.extendsList[i].isClassInstance();\n                if (type.extendsList[i] != this.checker.anyType) {\n                    var baseRef = type.extendsTypeLinks[i].ast;\n                    if (derivedIsClass) {\n                        if (!baseIsClass) {\n                            this.checker.errorReporter.simpleError(baseRef,\n                                                                     \"A class may only extend other classes, \" + type.extendsList[i].symbol.fullName() + \" is not a class.\");\n                        }\n                    }\n                    else {\n                        if (baseIsClass) {\n                            this.checker.errorReporter.simpleError(baseRef,\n                                                                     \"An interface may only extend other interfaces, \" + type.extendsList[i].symbol.fullName() + \" is a class.\");\n                        }\n                    }\n                }\n            }\n\n            type.implementsList = this.resolveBaseTypeLinks(type.implementsTypeLinks, scope);\n\n            if (type.implementsList) {\n                for (i = 0, len = type.implementsList.length; i < len; i++) {\n                    var iface = type.implementsList[i];\n                    var baseRef = type.implementsTypeLinks[i].ast;\n                    if (iface.isClassInstance()) {\n                        if (derivedIsClass) {\n                            this.checker.errorReporter.simpleError(baseRef,\n                                                                     \"A class may only implement an interface; \" + iface.symbol.fullName() + \" is a class.\");\n                        }\n                    }\n                }\n            }\n        }\n\n        public resolveSignatureGroup(signatureGroup: SignatureGroup, scope: SymbolScope, instanceType: Type) {\n            var supplyVar = !(signatureGroup.hasImplementation);\n            for (var i = 0, len = signatureGroup.signatures.length; i < len; i++) {\n                var signature = signatureGroup.signatures[i];\n                if (instanceType) {\n                    signature.returnType.type = instanceType;\n                }\n                else {\n                    this.checker.resolveTypeLink(scope, signature.returnType, supplyVar);\n                }\n                var paramLen = signature.parameters.length;\n                for (var j = 0; j < paramLen; j++) {\n                    this.bindSymbol(scope, signature.parameters[j]);\n                }\n                if (signature.hasVariableArgList) {\n                    // check that last parameter has an array type\n                    var lastParam = <ParameterSymbol>signature.parameters[paramLen - 1];\n                    lastParam.argsOffset = paramLen - 1;\n                    if (!lastParam.getType().isArray()) {\n                        this.checker.errorReporter.simpleErrorFromSym(lastParam,\n                                                                 \"... parameter must have array type\");\n                        lastParam.parameter.typeLink.type = this.checker.makeArrayType(lastParam.parameter.typeLink.type);\n                    }\n                }\n            }\n        }\n\n        public bindType(scope: SymbolScope, type: Type, instanceType: Type): void {\n            if (instanceType) {\n                this.bindType(scope, instanceType, null);\n            }\n            if (type.hasMembers()) {\n                var members = type.members;\n                var ambientMembers = type.ambientMembers;\n                var typeMembers = type.getAllEnclosedTypes(); // REVIEW: Should only be getting exported types?\n                var ambientTypeMembers = type.getAllAmbientEnclosedTypes(); // REVIEW: Should only be getting exported types?\n                var memberScope = new SymbolTableScope(members, ambientMembers, typeMembers, ambientTypeMembers, type.symbol);\n                var agg = new SymbolAggregateScope(type.symbol);\n                var prevCurrentModDecl = this.checker.currentModDecl;\n                var prevBindStatus = this.checker.inBind;\n                agg.addParentScope(memberScope);\n                agg.addParentScope(scope);\n                if (type.isModuleType()) {\n                    this.checker.currentModDecl = <ModuleDeclaration>type.symbol.declAST;\n                    this.checker.inBind = true;\n                }\n                if (members) {\n                    this.bind(agg, type.members.allMembers); // REVIEW: Should only be getting exported types?\n                }\n                if (typeMembers) {\n                    this.bind(agg, typeMembers.allMembers);\n                }\n                if (ambientMembers) {\n                    this.bind(agg, ambientMembers.allMembers);\n                }\n                if (ambientTypeMembers) {\n                    this.bind(agg, ambientTypeMembers.allMembers);\n                }\n                this.checker.currentModDecl = prevCurrentModDecl;\n                this.checker.inBind = prevBindStatus;\n            }\n            if (type.extendsTypeLinks) {\n                this.resolveBases(scope, type);\n            }\n            if (type.construct) {\n                this.resolveSignatureGroup(type.construct, scope, instanceType);\n            }\n            if (type.call) {\n                this.resolveSignatureGroup(type.call, scope, null);\n            }\n            if (type.index) {\n                this.resolveSignatureGroup(type.index, scope, null);\n            }\n            if (type.elementType) {\n                this.bindType(scope, type.elementType, null);\n            }\n        }\n\n        public bindSymbol(scope: SymbolScope, symbol: Symbol) {\n            if (!symbol.bound) {\n                var prevLocationInfo = this.checker.locationInfo;\n                if ((this.checker.units) && (symbol.unitIndex >= 0) && (symbol.unitIndex < this.checker.units.length)) {\n                    this.checker.locationInfo = this.checker.units[symbol.unitIndex];\n                }\n                switch (symbol.kind()) {\n                    case SymbolKind.Type:\n\n                        if (symbol.flags & SymbolFlags.Bound) {\n                            break;\n                        }\n\n                        var typeSymbol = <TypeSymbol>symbol;\n                        typeSymbol.flags |= SymbolFlags.Bound;\n\n                        // Since type collection happens out of order, a dynamic module referenced by an import statement\n                        // may not yet be in scope when the import symbol is created.  In that case, we need to search\n                        // out the module symbol now\n                        // Note that we'll also want to do this in resolveTypeMembers, in case the symbol is set outside the\n                        // context of a given module  (E.g., an outer import statement)\n                        if (typeSymbol.aliasLink && !typeSymbol.type && typeSymbol.aliasLink.alias.nodeType == NodeType.Name) {\n                            var modPath = (<Identifier>typeSymbol.aliasLink.alias).text;\n                            var modSym = this.checker.findSymbolForDynamicModule(modPath, this.checker.locationInfo.filename, (id) => scope.find(id, false, true));\n                            if (modSym) {\n                                typeSymbol.type = modSym.getType();\n                            }\n                        }\n\n                        if (typeSymbol.type && typeSymbol.type != this.checker.gloModType) {\n                            this.bindType(scope, typeSymbol.type, typeSymbol.instanceType);\n\n                            // bind expansions on the parent type symbol\n                            if (typeSymbol.type.isModuleType()) {\n                                for (var i = 0; i < typeSymbol.expansions.length; i++) {\n                                    this.bindType(scope, typeSymbol.expansions[i], typeSymbol.instanceType);\n                                }\n                            }\n                        }\n                        break;\n                    case SymbolKind.Field:\n                        this.checker.resolveTypeLink(scope, (<FieldSymbol>symbol).field.typeLink,\n                                                false);\n                        break;\n                    case SymbolKind.Parameter:\n                        this.checker.resolveTypeLink(scope,\n                                                (<ParameterSymbol>symbol).parameter.typeLink,\n                                                true);\n                        break;\n                }\n                this.checker.locationInfo = prevLocationInfo;\n            }\n            symbol.bound = true;\n        }\n\n        public bind(scope: SymbolScope, table: IHashTable) {\n            table.map(\n                (key, sym, binder) => {\n                    binder.bindSymbol(scope, sym);\n                },\n                this);\n        }\n    }\n\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export class DeclFileWriter {\n        public onNewLine = true;\n        constructor(private declFile: ITextWriter) {\n        }\n\n        public Write(s: string) {\n            this.declFile.Write(s);\n            this.onNewLine = false;\n        }\n\n        public WriteLine(s: string) {\n            this.declFile.WriteLine(s);\n            this.onNewLine = true;\n        }\n\n        public Close() {\n            this.declFile.Close();\n        }\n    }\n\n    export class DeclarationEmitter implements AstWalkerWithDetailCallback.AstWalkerDetailCallback {\n        private declFile: DeclFileWriter = null;\n        private indenter = new Indenter();\n        private declarationContainerStack: AST[] = [];\n        private isDottedModuleName: bool[] = [];\n        private dottedModuleEmit: string;\n        private ignoreCallbackAst: AST = null;\n        private singleDeclFile: DeclFileWriter = null;\n        private varListCount: number = 0;\n\n        private getAstDeclarationContainer() {\n            return this.declarationContainerStack[this.declarationContainerStack.length - 1];\n        }\n\n        private emitDottedModuleName() {\n            return (this.isDottedModuleName.length == 0) ? false : this.isDottedModuleName[this.isDottedModuleName.length - 1];\n        }\n\n        constructor (public checker: TypeChecker, public emitOptions: EmitOptions, public errorReporter: ErrorReporter) {\n        }\n\n        public setDeclarationFile(file: ITextWriter) {\n            this.declFile = new DeclFileWriter(file);\n        }\n\n        public Close() {\n            try {\n                // Closing files could result in exceptions, report them if they occur\n                this.declFile.Close();\n            } catch (ex) {\n                this.errorReporter.emitterError(null, ex.message);\n            }\n        }\n\n        public emitDeclarations(script: TypeScript.Script): void {\n            AstWalkerWithDetailCallback.walk(script, this);\n        }\n\n        private getIndentString(declIndent? = false) {\n            if (this.emitOptions.minWhitespace) {\n                return \"\";\n            }\n            else {\n                return this.indenter.getIndent();\n            }\n        }\n\n        private emitIndent() {\n            this.declFile.Write(this.getIndentString());\n        }\n\n        private canEmitSignature(declFlags: DeclFlags, canEmitGlobalAmbientDecl?: bool = true, useDeclarationContainerTop?: bool = true) {\n            var container: AST;\n            if (useDeclarationContainerTop) {\n                container = this.getAstDeclarationContainer();\n            } else {\n                container = this.declarationContainerStack[this.declarationContainerStack.length - 2];\n            }\n\n            if (container.nodeType == NodeType.ModuleDeclaration && !hasFlag(declFlags, DeclFlags.Exported)) {\n                return false;\n            }\n\n            if (!canEmitGlobalAmbientDecl && container.nodeType == NodeType.Script && hasFlag(declFlags, DeclFlags.Ambient)) {\n                return false;\n            }\n\n            return true;\n        }\n\n        private canEmitPrePostAstSignature(declFlags: DeclFlags, astWithPrePostCallback: AST, preCallback: bool) {\n            if (this.ignoreCallbackAst) {\n                CompilerDiagnostics.assert(this.ignoreCallbackAst != astWithPrePostCallback, \"Ignore Callback AST mismatch\");\n                this.ignoreCallbackAst = null;\n                return false;\n            } else if (preCallback &&\n                !this.canEmitSignature(declFlags, true, preCallback)) {\n                this.ignoreCallbackAst = astWithPrePostCallback;\n                return false;\n            }\n\n            return true;\n        }\n\n        private getDeclFlagsString(declFlags: DeclFlags, typeString: string) {\n            var result = this.getIndentString();\n\n            // Accessor strings\n            var accessorString = \"\";\n            if (hasFlag(declFlags, DeclFlags.GetAccessor)) {\n                accessorString = \"get \";\n            }\n            else if (hasFlag(declFlags, DeclFlags.SetAccessor)) {\n                accessorString = \"set \";\n            }\n\n            // Emit export only for global export statements. The container for this would be dynamic module which is whole file\n            var container = this.getAstDeclarationContainer();\n            if (container.nodeType == NodeType.ModuleDeclaration &&\n                hasFlag((<ModuleDeclaration>container).modFlags, ModuleFlags.IsWholeFile) &&\n                hasFlag(declFlags, DeclFlags.Exported)) {\n                result += \"export \";\n            }\n\n            // Static/public/private/global declare\n            if (hasFlag(declFlags, DeclFlags.LocalStatic) || hasFlag(declFlags, DeclFlags.Static)) {\n                result += \"static \" + accessorString;\n            }\n            else {\n                if (hasFlag(declFlags, DeclFlags.Private)) {\n                    result += \"private \" + accessorString;\n                }\n                else if (hasFlag(declFlags, DeclFlags.Public)) {\n                    result += \"public \" + accessorString;\n                }\n                else {\n                    if (accessorString == \"\") {\n                        result += typeString + \" \";\n                    } else {\n                        result += accessorString;\n                    }\n                }\n            }\n\n            return result;\n        }\n\n        private emitDeclFlags(declFlags: DeclFlags, typeString: string) {\n            this.declFile.Write(this.getDeclFlagsString(declFlags, typeString));\n        }\n\n        private canEmitTypeAnnotationSignature(declFlag: DeclFlags = DeclFlags.None) {\n            // Private declaration, shouldnt emit type any time.\n            return !hasFlag(declFlag, DeclFlags.Private);\n        }\n\n        private pushDeclarationContainer(ast: AST) {\n            this.declarationContainerStack.push(ast);\n        }\n\n        private popDeclarationContainer(ast: AST) {\n            CompilerDiagnostics.assert(ast != this.getAstDeclarationContainer(), 'Declaration container mismatch');\n            this.declarationContainerStack.pop();\n        }\n\n        private emitTypeNamesMember(memberName: MemberName, emitIndent? : bool = false) {\n            if (memberName.prefix == \"{ \") {\n                if (emitIndent) {\n                    this.emitIndent();\n                }\n                this.declFile.WriteLine(\"{\");\n                this.indenter.increaseIndent();\n                emitIndent = true;\n            } else if (memberName.prefix != \"\") {\n                if (emitIndent) {\n                    this.emitIndent();\n                }\n                this.declFile.Write(memberName.prefix);\n                emitIndent = false;\n            }\n\n            if (memberName.isString()) {\n                if (emitIndent) {\n                    this.emitIndent();\n                }\n                this.declFile.Write((<MemberNameString>memberName).text);\n            } else {\n                var ar = <MemberNameArray>memberName;\n                for (var index = 0; index < ar.entries.length; index++) {\n                    this.emitTypeNamesMember(ar.entries[index], emitIndent);\n                    if (ar.delim == \"; \") {\n                        this.declFile.WriteLine(\";\");\n                    }\n                }\n            }\n\n            if (memberName.suffix == \"}\") {\n                this.indenter.decreaseIndent();\n                this.emitIndent();\n                this.declFile.Write(memberName.suffix);\n            } else {\n                this.declFile.Write(memberName.suffix);\n            }\n        }\n\n        private emitTypeSignature(type: Type) {\n            var containingScope: SymbolScope = null;\n            var declarationContainerAst = this.getAstDeclarationContainer();\n            switch (declarationContainerAst.nodeType) {\n                case NodeType.ModuleDeclaration:\n                case NodeType.InterfaceDeclaration:\n                case NodeType.FuncDecl:\n                    if (declarationContainerAst.type) {\n                        containingScope = declarationContainerAst.type.containedScope;\n                    }\n                    break;\n\n                case NodeType.Script:\n                    var script = <Script>declarationContainerAst;\n                    if (script.bod) {\n                        containingScope = script.bod.enclosingScope;\n                    }\n                    break;\n\n                case NodeType.ClassDeclaration:\n                    if (declarationContainerAst.type) {\n                        containingScope = declarationContainerAst.type.instanceType.containedScope;\n                    }\n                    break;\n\n                default:\n                    CompilerDiagnostics.debugPrint(\"Unknown containing scope\");\n            }\n\n            var typeNameMembers = type.getScopedTypeNameEx(containingScope);\n            this.emitTypeNamesMember(typeNameMembers);\n        }\n\n        private emitComment(comment: Comment) {\n            var text = comment.getText();\n            if (this.declFile.onNewLine) {\n                this.emitIndent();\n            } else if (!comment.isBlockComment) {\n                this.declFile.WriteLine(\"\");\n                this.emitIndent();\n            }\n            \n            this.declFile.Write(text[0]);\n\n            for (var i = 1; i < text.length; i++) {\n                this.declFile.WriteLine(\"\");\n                this.emitIndent();\n                this.declFile.Write(text[i]);\n            }\n\n            if (comment.endsLine || !comment.isBlockComment) {\n                this.declFile.WriteLine(\"\");\n            } else {\n                this.declFile.Write(\" \");\n            }\n        }\n\n        private emitDeclarationComments(ast: AST, endLine?: bool);\n        private emitDeclarationComments(symbol: Symbol, endLine?: bool);\n        private emitDeclarationComments(astOrSymbol, endLine = true) {\n            if (!this.emitOptions.emitComments) {\n                return;\n            }\n\n            var declComments = <Comment[]>astOrSymbol.getDocComments();\n            if (declComments.length > 0) {\n                for (var i = 0; i < declComments.length; i++) {\n                    this.emitComment(declComments[i]);\n                }\n\n                if (endLine) {\n                    if (!this.declFile.onNewLine) {\n                        this.declFile.WriteLine(\"\");\n                    }\n                } else {\n                    if (this.declFile.onNewLine) {\n                        this.emitIndent();\n                    }\n                }\n            }\n        }\n\n        public VarDeclCallback(pre: bool, varDecl: VarDecl): bool {\n            if (pre && this.canEmitSignature(ToDeclFlags(varDecl.varFlags), false)) {\n                var interfaceMember = (this.getAstDeclarationContainer().nodeType == NodeType.InterfaceDeclaration);\n                this.emitDeclarationComments(varDecl);\n                if (!interfaceMember) {\n                    // If it is var list of form var a, b, c = emit it only if count > 0 - which will be when emitting first var\n                    // If it is var list of form  var a = varList count will be 0\n                    if (this.varListCount >= 0) {\n                        this.emitDeclFlags(ToDeclFlags(varDecl.varFlags), \"var\");\n                        this.varListCount = -this.varListCount;\n                    }\n                    this.declFile.Write(varDecl.id.text);\n                } else {\n                    this.emitIndent();\n                    this.declFile.Write(varDecl.id.text);\n                    if (hasFlag(varDecl.id.flags, ASTFlags.OptionalName)) {\n                        this.declFile.Write(\"?\");\n                    }\n                }\n\n                var type: Type = null;\n                if (varDecl.typeExpr && varDecl.typeExpr.type) {\n                    type = varDecl.typeExpr.type;\n                }\n                else if (varDecl.sym) {\n                    type = (<FieldSymbol>varDecl.sym).getType();\n                    // Dont emit inferred any\n                    if (type == this.checker.anyType) {\n                        type = null;\n                    }\n                }\n\n                if (type && this.canEmitTypeAnnotationSignature(ToDeclFlags(varDecl.varFlags))) {\n                    this.declFile.Write(\": \");\n                    this.emitTypeSignature(type);\n                }\n               \n                // emitted one var decl\n                if (this.varListCount > 0) { this.varListCount--; } else if (this.varListCount < 0) { this.varListCount++; }\n\n                // Write ; or ,\n                if (this.varListCount < 0) {\n                    this.declFile.Write(\", \");\n                } else {\n                    this.declFile.WriteLine(\";\");\n                }\n            }\n            return false;\n        }\n\n        public BlockCallback(pre: bool, block: Block): bool {\n            if (!block.isStatementBlock) {\n                if (pre) {\n                    this.varListCount = block.statements.members.length;\n                } else {\n                    this.varListCount = 0;\n                }\n                return true;\n            }\n            return false;\n        }\n\n        private emitArgDecl(argDecl: ArgDecl, funcDecl: FuncDecl) {\n            this.emitDeclarationComments(argDecl, false);\n            this.declFile.Write(argDecl.id.text);\n            if (argDecl.isOptionalArg()) {\n                this.declFile.Write(\"?\");\n            }\n            if ((argDecl.typeExpr || argDecl.type != this.checker.anyType) &&\n                this.canEmitTypeAnnotationSignature(ToDeclFlags(funcDecl.fncFlags))) {\n                this.declFile.Write(\": \");\n                this.emitTypeSignature(argDecl.type);\n            }\n        }\n\n        public FuncDeclCallback(pre: bool, funcDecl: FuncDecl): bool {\n            if (!pre) {\n                return false;\n            }\n\n            if (funcDecl.isAccessor()) {\n                return this.emitPropertyAccessorSignature(funcDecl);\n            }\n\n            var isInterfaceMember = (this.getAstDeclarationContainer().nodeType == NodeType.InterfaceDeclaration);\n            if (funcDecl.bod) {\n                if (funcDecl.isConstructor) {\n                    if (funcDecl.type.construct && funcDecl.type.construct.signatures.length > 1) {\n                        return false;\n                    }\n                } else {\n                    if (funcDecl.type.call && funcDecl.type.call.signatures.length > 1) {\n                        // This means its implementation of overload signature. do not emit\n                        return false;\n                    }\n                }\n            } else if (!isInterfaceMember && hasFlag(funcDecl.fncFlags, FncFlags.Private) && funcDecl.type.call && funcDecl.type.call.signatures.length > 1) {\n                // Print only first overload of private function\n                var signatures = funcDecl.type.call.signatures;\n                var firstSignature = signatures[0].declAST;\n                if (firstSignature.bod) {\n                    // Its a implementation, use next one\n                    firstSignature = signatures[1].declAST;\n                }\n\n                if (firstSignature != funcDecl) {\n                    return false;\n                }\n            }\n\n            if (!this.canEmitSignature(ToDeclFlags(funcDecl.fncFlags), false)) {\n                return false;\n            }\n\n            this.emitDeclarationComments(funcDecl);\n            if (funcDecl.isConstructor) {\n                this.emitIndent();\n                this.declFile.Write(\"constructor\");\n            }\n            else {\n                var id = funcDecl.getNameText();\n                if (!isInterfaceMember) {\n                    this.emitDeclFlags(ToDeclFlags(funcDecl.fncFlags), \"function\");\n                    this.declFile.Write(id);\n                } else {\n                    this.emitIndent();\n                    if (funcDecl.isConstructMember()) {\n                        this.declFile.Write(\"new\");\n                    } else if (!funcDecl.isCallMember() && !funcDecl.isIndexerMember()) {\n                        this.declFile.Write(id);\n                        if (hasFlag(funcDecl.name.flags, ASTFlags.OptionalName)) {\n                            this.declFile.Write(\"? \");\n                        }\n                    }\n                }\n            }\n\n            if (!funcDecl.isIndexerMember()) {\n                this.declFile.Write(\"(\");\n            } else {\n                this.declFile.Write(\"[\");\n            }\n\n            this.indenter.increaseIndent();\n\n            if (funcDecl.arguments) {\n                var argsLen = funcDecl.arguments.members.length;\n                if (funcDecl.variableArgList) {\n                    argsLen--;\n                }\n                for (var i = 0; i < argsLen; i++) {\n                    var argDecl = <ArgDecl>funcDecl.arguments.members[i];\n                    this.emitArgDecl(argDecl, funcDecl);\n                    if (i < (argsLen - 1)) {\n                        this.declFile.Write(\", \");\n                    }\n                }\n            }\n\n            if (funcDecl.variableArgList) {\n                var lastArg = <ArgDecl>funcDecl.arguments.members[funcDecl.arguments.members.length - 1];\n                if (funcDecl.arguments.members.length > 1) {\n                    this.declFile.Write(\", ...\");\n                }\n                else {\n                    this.declFile.Write(\"...\");\n                }\n                this.emitArgDecl(lastArg, funcDecl);\n            }\n\n            this.indenter.decreaseIndent();\n\n            if (!funcDecl.isIndexerMember()) {\n                this.declFile.Write(\")\");\n            } else {\n                this.declFile.Write(\"]\");\n            }\n\n            if (!funcDecl.isConstructor &&\n                (funcDecl.returnTypeAnnotation || funcDecl.signature.returnType.type != this.checker.anyType) &&\n                this.canEmitTypeAnnotationSignature(ToDeclFlags(funcDecl.fncFlags))) {\n                this.declFile.Write(\": \");\n                this.emitTypeSignature(funcDecl.signature.returnType.type);\n            }\n\n            this.declFile.WriteLine(\";\");\n\n            return false;\n        }\n\n        private emitBaseList(bases: ASTList, qual: string) {\n            if (bases && (bases.members.length > 0)) {\n                this.declFile.Write(\" \" + qual + \" \");\n                var basesLen = bases.members.length;\n                for (var i = 0; i < basesLen; i++) {\n                    var baseExpr = bases.members[i];\n                    var baseSymbol = baseExpr.type.symbol;\n                    var baseType = baseExpr.type;\n                    if (i > 0) {\n                        this.declFile.Write(\", \");\n                    }\n                    this.emitTypeSignature(baseType);\n                }\n            }\n        }\n\n        private emitPropertyAccessorSignature(funcDecl: FuncDecl) {\n            var accessorSymbol = <FieldSymbol>funcDecl.accessorSymbol;\n            if (accessorSymbol.getter && accessorSymbol.getter.declAST != funcDecl) {\n                // Setter is being used to emit the type info. \n                return false;\n            }\n\n            this.emitDeclarationComments(accessorSymbol);\n            this.emitDeclFlags(ToDeclFlags(accessorSymbol.flags), \"var\");\n            this.declFile.Write(funcDecl.name.text);\n            var propertyType = accessorSymbol.getType();\n            if (this.canEmitTypeAnnotationSignature(ToDeclFlags(accessorSymbol.flags))) {\n                this.declFile.Write(\" : \");\n                this.emitTypeSignature(propertyType);\n            }\n            this.declFile.WriteLine(\";\");\n\n            return false;\n        }\n\n        private emitClassMembersFromConstructorDefinition(funcDecl: FuncDecl) {\n            if (funcDecl.arguments) {\n                var argsLen = funcDecl.arguments.members.length; if (funcDecl.variableArgList) { argsLen--; }\n\n                for (var i = 0; i < argsLen; i++) {\n                    var argDecl = <ArgDecl>funcDecl.arguments.members[i];\n                    if (hasFlag(argDecl.varFlags, VarFlags.Property)) {\n                        this.emitDeclarationComments(argDecl);\n                        this.emitDeclFlags(ToDeclFlags(argDecl.varFlags), \"var\");\n                        this.declFile.Write(argDecl.id.text);\n\n                        if (argDecl.typeExpr && this.canEmitTypeAnnotationSignature(ToDeclFlags(argDecl.varFlags))) {\n                            this.declFile.Write(\": \");\n                            this.emitTypeSignature(argDecl.type);\n                        }\n                        this.declFile.WriteLine(\";\");\n                    }\n                }\n            }\n        }\n\n        public ClassDeclarationCallback(pre: bool, classDecl: ClassDeclaration): bool {\n            if (!this.canEmitPrePostAstSignature(ToDeclFlags(classDecl.varFlags), classDecl, pre)) {\n                return false;\n            }\n\n            if (pre) {\n                var className = classDecl.name.text;\n                this.emitDeclarationComments(classDecl);\n                this.emitDeclFlags(ToDeclFlags(classDecl.varFlags), \"class\");\n                this.declFile.Write(className);\n                this.emitBaseList(classDecl.extendsList, \"extends\");\n                this.emitBaseList(classDecl.implementsList, \"implements\");\n                this.declFile.WriteLine(\" {\");\n\n                this.pushDeclarationContainer(classDecl);\n                this.indenter.increaseIndent();\n                if (classDecl.constructorDecl) {\n                    this.emitClassMembersFromConstructorDefinition(classDecl.constructorDecl);\n                }\n            } else {\n                this.indenter.decreaseIndent();\n                this.popDeclarationContainer(classDecl);\n\n                this.emitIndent();\n                this.declFile.WriteLine(\"}\");\n            }\n\n            return true;\n        }\n\n        public InterfaceDeclarationCallback(pre: bool, interfaceDecl: InterfaceDeclaration): bool {\n            if (!this.canEmitPrePostAstSignature(ToDeclFlags(interfaceDecl.varFlags), interfaceDecl, pre)) {\n                return false;\n            }\n\n            if (pre) {\n                var interfaceName = interfaceDecl.name.text;\n                this.emitDeclarationComments(interfaceDecl);\n                this.emitDeclFlags(ToDeclFlags(interfaceDecl.varFlags), \"interface\");\n                this.declFile.Write(interfaceName);\n                this.emitBaseList(interfaceDecl.extendsList, \"extends\");\n                this.declFile.WriteLine(\" {\");\n\n                this.indenter.increaseIndent();\n                this.pushDeclarationContainer(interfaceDecl);\n            } else {\n                this.indenter.decreaseIndent();\n                this.popDeclarationContainer(interfaceDecl);\n\n                this.emitIndent();\n                this.declFile.WriteLine(\"}\");\n            }\n\n            return true;\n        }\n\n        public ImportDeclarationCallback(pre: bool, importDecl: ImportDeclaration): bool {\n            if (pre) {\n                if ((<Script>this.declarationContainerStack[0]).isExternallyVisibleSymbol(importDecl.id.sym)) {\n                    this.emitDeclarationComments(importDecl);\n                    this.emitIndent();\n                    this.declFile.Write(\"import \");\n\n                    this.declFile.Write(importDecl.id.text + \" = \");\n                    if (importDecl.isDynamicImport) {\n                        this.declFile.WriteLine(\"module (\" + importDecl.getAliasName() + \");\");\n                    } else {\n                        this.declFile.WriteLine(importDecl.getAliasName() + \";\");\n                    }\n                }\n            }\n\n            return false;\n        }\n\n        private emitEnumSignature(moduleDecl: ModuleDeclaration) {\n            if (!this.canEmitSignature(ToDeclFlags(moduleDecl.modFlags))) {\n                return false;\n            }\n\n            this.emitDeclarationComments(moduleDecl);\n            this.emitDeclFlags(ToDeclFlags(moduleDecl.modFlags), \"enum\");\n            this.declFile.WriteLine(moduleDecl.name.text + \" {\");\n\n            this.indenter.increaseIndent();\n            var membersLen = moduleDecl.members.members.length;\n            for (var j = 1; j < membersLen; j++) {\n                var memberDecl: AST = moduleDecl.members.members[j];\n                if (memberDecl.nodeType == NodeType.VarDecl) {\n                    this.emitDeclarationComments(memberDecl);\n                    this.emitIndent();\n                    this.declFile.WriteLine((<VarDecl>memberDecl).id.text + \",\");\n                } else {\n                    CompilerDiagnostics.assert(memberDecl.nodeType != NodeType.Asg, \"We want to catch this\");\n                }\n            }\n            this.indenter.decreaseIndent();\n\n            this.emitIndent();\n            this.declFile.WriteLine(\"}\");\n\n            return false;\n        }\n\n        public ModuleDeclarationCallback(pre: bool, moduleDecl: ModuleDeclaration): bool {\n            if (hasFlag(moduleDecl.modFlags, ModuleFlags.IsWholeFile)) {\n                // This is dynamic modules and we are going to outputing single file, \n                // we need to change the declFile because dynamic modules are always emitted to their corresponding .d.ts\n                if (hasFlag(moduleDecl.modFlags, ModuleFlags.IsDynamic)) {\n                    if (pre) {\n                        if (!this.emitOptions.outputMany) {\n                            this.singleDeclFile = this.declFile;\n                            CompilerDiagnostics.assert(this.indenter.indentAmt == 0, \"Indent has to be 0 when outputing new file\");\n                            // Create new file\n                            var declareFileName = this.emitOptions.mapOutputFileName(stripQuotes(moduleDecl.name.sym.name), TypeScriptCompiler.mapToDTSFileName);\n                            var useUTF8InOutputfile = moduleDecl.containsUnicodeChar || (this.emitOptions.emitComments && moduleDecl.containsUnicodeCharInComment);\n                            try {\n                                // Creating files can cause exceptions, report them.   \n                                this.declFile = new DeclFileWriter(this.emitOptions.ioHost.createFile(declareFileName, useUTF8InOutputfile));\n                            } catch (ex) {\n                                this.errorReporter.emitterError(null, ex.message);\n                            }\n                        }\n                        this.pushDeclarationContainer(moduleDecl);\n                    } else {\n                        if (!this.emitOptions.outputMany) {\n                            CompilerDiagnostics.assert(this.singleDeclFile != this.declFile, \"singleDeclFile cannot be null as we are going to revert back to it\");\n                            CompilerDiagnostics.assert(this.indenter.indentAmt == 0, \"Indent has to be 0 when outputing new file\");\n                            try {\n                                // Closing files could result in exceptions, report them if they occur\n                                this.declFile.Close();\n                            } catch (ex) {\n                                this.errorReporter.emitterError(null, ex.message);\n                            }\n                            this.declFile = this.singleDeclFile;\n                        }\n                        this.popDeclarationContainer(moduleDecl);\n                    }\n                }\n\n                return true;\n            }\n\n            if (moduleDecl.isEnum()) {\n                if (pre) {\n                    this.emitEnumSignature(moduleDecl);\n                }\n                return false;\n            }\n\n            if (!this.canEmitPrePostAstSignature(ToDeclFlags(moduleDecl.modFlags), moduleDecl, pre)) {\n                return false;\n            }\n\n            if (pre) {\n                if (this.emitDottedModuleName()) {\n                    this.dottedModuleEmit += \".\";\n                } else {\n                    this.dottedModuleEmit = this.getDeclFlagsString(ToDeclFlags(moduleDecl.modFlags), \"module\");\n                }\n                this.dottedModuleEmit += moduleDecl.name.text;\n\n                var isCurrentModuleDotted = (moduleDecl.members.members.length == 1 &&\n                    moduleDecl.members.members[0].nodeType == NodeType.ModuleDeclaration &&\n                    !(<ModuleDeclaration>moduleDecl.members.members[0]).isEnum() &&\n                    hasFlag((<ModuleDeclaration>moduleDecl.members.members[0]).modFlags, ModuleFlags.Exported));\n\n                // Module is dotted only if it does not have doc comments for it\n                var moduleDeclComments = moduleDecl.getDocComments();\n                isCurrentModuleDotted = isCurrentModuleDotted && (moduleDeclComments == null || moduleDeclComments.length == 0);\n\n                this.isDottedModuleName.push(isCurrentModuleDotted);\n                this.pushDeclarationContainer(moduleDecl);\n\n                if (!isCurrentModuleDotted) {\n                    this.emitDeclarationComments(moduleDecl);\n                    this.declFile.Write(this.dottedModuleEmit);\n                    this.declFile.WriteLine(\" {\");\n                    this.indenter.increaseIndent();\n                }\n            } else {\n                if (!this.emitDottedModuleName()) {\n                    this.indenter.decreaseIndent();\n                    this.emitIndent();\n                    this.declFile.WriteLine(\"}\");\n                }\n                this.popDeclarationContainer(moduleDecl);\n                this.isDottedModuleName.pop();\n            }\n\n            return true;\n        }\n\n        public ScriptCallback(pre: bool, script: Script): bool {\n            if (pre) {\n                if (this.emitOptions.outputMany) {\n                    for (var i = 0; i < script.referencedFiles.length; i++) {\n                        var referencePath = script.referencedFiles[i].path;\n                        var declareFileName: string;\n                        if (isRooted(referencePath)) {\n                            declareFileName = this.emitOptions.mapOutputFileName(referencePath, TypeScriptCompiler.mapToDTSFileName)\n                        } else {\n                            declareFileName = getDeclareFilePath(script.referencedFiles[i].path);\n                        }\n                        this.declFile.WriteLine('/// <reference path=\"' + declareFileName + '\" />');\n                    }\n                }\n                this.pushDeclarationContainer(script);\n            }\n            else {\n                this.popDeclarationContainer(script);\n            }\n            return true;\n        }\n\n        public DefaultCallback(pre: bool, ast: AST): bool {\n            return !hasFlag(ast.flags, ASTFlags.IsStatement);\n        }\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export module CompilerDiagnostics {\n        export var debug = false;\n        export interface IDiagnosticWriter {\n            Alert(output: string): void;\n        }\n\n        export var diagnosticWriter: IDiagnosticWriter = null;\n\n        export var analysisPass: number = 0;\n\n        export function Alert(output: string) {\n            if (diagnosticWriter) {\n                diagnosticWriter.Alert(output);\n            }\n        }\n\n        export function debugPrint(s: string) {\n            if (debug) {\n                Alert(s);\n            }\n        }\n\n        export function assert(condition: bool, s: string) {\n            if (debug) {\n                if (!condition) {\n                    Alert(s);\n                }\n            }\n        }\n\n    }\n\n    export interface ILogger {\n        information(): bool;\n        debug(): bool;\n        warning(): bool;\n        error(): bool;\n        fatal(): bool;\n        log(s: string): void;\n    }\n\n    export class NullLogger implements ILogger {\n        public information(): bool { return false; }\n        public debug(): bool { return false; }\n        public warning(): bool { return false; }\n        public error(): bool { return false; }\n        public fatal(): bool { return false; }\n        public log(s: string): void {\n        }\n    }\n\n    export class LoggerAdapter implements ILogger {\n        private _information: bool;\n        private _debug: bool;\n        private _warning: bool;\n        private _error: bool;\n        private _fatal: bool;\n\n        constructor (public logger: ILogger) { \n            this._information = this.logger.information();\n            this._debug = this.logger.debug();\n            this._warning = this.logger.warning();\n            this._error = this.logger.error();\n            this._fatal = this.logger.fatal();\n        }\n\n\n        public information(): bool { return this._information; }\n        public debug(): bool { return this._debug; }\n        public warning(): bool { return this._warning; }\n        public error(): bool { return this._error; }\n        public fatal(): bool { return this._fatal; }\n        public log(s: string): void {\n            this.logger.log(s);\n        }\n    }\n\n    export class BufferedLogger implements ILogger {\n        public logContents = [];\n\n        public information(): bool { return false; }\n        public debug(): bool { return false; }\n        public warning(): bool { return false; }\n        public error(): bool { return false; }\n        public fatal(): bool { return false; }\n        public log(s: string): void {\n            this.logContents.push(s);\n        }\n    }\n\n    export function timeFunction(logger: ILogger, funcDescription: string, func: () =>any): any {\n        var start = +new Date();\n        var result = func();\n        var end = +new Date();\n        logger.log(funcDescription + \" completed in \" + (end - start) + \" msec\");\n        return result;\n    }\n\n    export function stringToLiteral(value: string, length: number): string {\n        var result = \"\";\n\n        var addChar = (index: number) => {\n            var ch = value.charCodeAt(index);\n            switch (ch) {\n                case 0x09: // tab\n                    result += \"\\\\t\";\n                    break;\n                case 0x0a: // line feed\n                    result += \"\\\\n\";\n                    break;\n                case 0x0b: // vertical tab\n                    result += \"\\\\v\";\n                    break;\n                case 0x0c: // form feed\n                    result += \"\\\\f\";\n                    break;\n                case 0x0d: // carriage return\n                    result += \"\\\\r\";\n                    break;\n                case 0x22:  // double quote\n                    result += \"\\\\\\\"\";\n                    break;\n                case 0x27: // single quote\n                    result += \"\\\\\\'\";\n                    break;\n                case 0x5c: // Backslash\n                    result += \"\\\\\";\n                    break;\n                default:\n                    result += value.charAt(index);\n            }\n        }\n\n        var tooLong = (value.length > length);\n        if (tooLong) {\n            var mid = length >> 1;\n            for (var i = 0; i < mid; i++) addChar(i);\n            result += \"(...)\";\n            for (var i = value.length - mid; i < value.length; i++) addChar(i);\n        }\n        else {\n            length = value.length;\n            for (var i = 0; i < length; i++) addChar(i);\n        }\n        return result;\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n\n    export enum EmitContainer {\n        Prog,\n        Module,\n        DynamicModule,\n        Class,\n        Constructor,\n        Function,\n        Args,\n        Interface,\n    }\n\n    export class EmitState {\n        public column: number;\n        public line: number;\n        public pretty: bool;\n        public inObjectLiteral: bool;\n        public container: EmitContainer;\n\n        constructor () {\n            this.column = 0;\n            this.line = 0;\n            this.pretty = false;\n            this.inObjectLiteral = false;\n            this.container = EmitContainer.Prog;\n        }\n    }\n\n    export class EmitOptions {\n        public minWhitespace: bool;\n        public propagateConstants: bool;\n        public emitComments: bool;\n        public outputOption: string;\n        public ioHost: EmitterIOHost = null;\n        public outputMany: bool = true;\n        public commonDirectoryPath = \"\";\n\n        constructor(settings: CompilationSettings) {\n            this.minWhitespace = settings.minWhitespace;\n            this.propagateConstants = settings.propagateConstants;\n            this.emitComments = settings.emitComments;\n            this.outputOption = settings.outputOption;\n        }\n\n        public mapOutputFileName(fileName: string, extensionChanger: (fname: string, wholeFileNameReplaced: bool) => string) {\n            if (this.outputMany) {\n                var updatedFileName = fileName;\n                if (this.outputOption != \"\") {\n                    // Replace the common directory path with the option specified\n                    updatedFileName = fileName.replace(this.commonDirectoryPath, \"\");\n                    updatedFileName = this.outputOption + updatedFileName;\n                }\n                return extensionChanger(updatedFileName, false);\n            } else {\n                return extensionChanger(this.outputOption, true);\n            }\n        }\n    }\n\n    export class Indenter {\n        static indentStep : number = 4;\n        static indentStepString : string = \"    \";\n        static indentStrings: string[] = [];\n        public indentAmt: number = 0;\n\n        public increaseIndent() {\n            this.indentAmt += Indenter.indentStep;\n        }\n\n        public decreaseIndent() {\n            this.indentAmt -= Indenter.indentStep;\n        }\n\n        public getIndent() {\n            var indentString = Indenter.indentStrings[this.indentAmt];\n            if (indentString === undefined) {\n                indentString = \"\";\n                for (var i = 0; i < this.indentAmt; i = i + Indenter.indentStep) {\n                    indentString += Indenter.indentStepString;\n                }\n                Indenter.indentStrings[this.indentAmt] = indentString;\n            }\n            return indentString;\n        }\n    }\n\n    export class Emitter {\n        public prologueEmitted = false;\n        public thisClassNode: TypeDeclaration = null;\n        public thisFnc: FuncDecl = null;\n        public moduleDeclList: ModuleDeclaration[] = [];\n        public moduleName = \"\";\n        public emitState = new EmitState();\n        public indenter = new Indenter();\n        public ambientModule = false;\n        public modAliasId: string = null;\n        public firstModAlias: string = null;\n        public allSourceMappers: SourceMapper[] = [];\n        public sourceMapper: SourceMapper = null;\n        public captureThisStmtString = \"var _this = this;\";\n        private varListCountStack: number[] = [0]; \n\n        constructor(public checker: TypeChecker, public emittingFileName: string, public outfile: ITextWriter, public emitOptions: EmitOptions, public errorReporter: ErrorReporter) {\n        }\n\n        public setSourceMappings(mapper: SourceMapper) {\n            this.allSourceMappers.push(mapper);\n            this.sourceMapper = mapper;\n        }\n\n        public writeToOutput(s: string) {\n            this.outfile.Write(s);\n            // TODO: check s for newline\n            this.emitState.column += s.length;\n        }\n\n        public writeToOutputTrimmable(s: string) {\n            if (this.emitOptions.minWhitespace) {\n                s = s.replace(/[\\s]*/g, '');\n            }\n            this.writeToOutput(s);\n        }\n\n        public writeLineToOutput(s: string) {\n            if (this.emitOptions.minWhitespace) {\n                this.writeToOutput(s);\n                var c = s.charCodeAt(s.length - 1);\n                if (!((c == LexCodeSpace) || (c == LexCodeSMC) || (c == LexCodeLBR))) {\n                    this.writeToOutput(' ');\n                }\n            }\n            else {\n                this.outfile.WriteLine(s);\n                this.emitState.column = 0\n                this.emitState.line++;\n            }\n        }\n\n        public writeCaptureThisStatement(ast: AST) {\n            this.emitIndent();\n            this.recordSourceMappingStart(ast);\n            this.writeToOutput(this.captureThisStmtString);\n            this.recordSourceMappingEnd(ast);\n            this.writeLineToOutput(\"\");\n        }\n\n        public setInVarBlock(count: number) {\n            this.varListCountStack[this.varListCountStack.length - 1] = count;\n        }\n\n        public setInObjectLiteral(val: bool): bool {\n            var temp = this.emitState.inObjectLiteral;\n            this.emitState.inObjectLiteral = val;\n            return temp;\n        }\n\n        public setContainer(c: number): number {\n            var temp = this.emitState.container;\n            this.emitState.container = c;\n            return temp;\n        }\n\n        private getIndentString() {\n            if (this.emitOptions.minWhitespace) {\n                return \"\";\n            }\n            else {\n                return this.indenter.getIndent();\n            }\n        }\n\n        public emitIndent() {\n            this.writeToOutput(this.getIndentString());\n        }\n\n        public emitCommentInPlace(comment: Comment) {\n            var text = comment.getText();\n            var hadNewLine = false;\n\n            if (comment.isBlockComment) {\n                if (this.emitState.column == 0) {\n                    this.emitIndent();\n                }\n                this.recordSourceMappingStart(comment);\n                this.writeToOutput(text[0]);\n\n                if (text.length > 1 || comment.endsLine) {\n                    for (var i = 1; i < text.length; i++) {\n                        this.writeLineToOutput(\"\");\n                        this.emitIndent();\n                        this.writeToOutput(text[i]);\n                    }\n                    this.recordSourceMappingEnd(comment);\n                    this.writeLineToOutput(\"\");\n                    hadNewLine = true;\n                } else {\n                    this.recordSourceMappingEnd(comment);\n                }\n            }\n            else {\n                if (this.emitState.column == 0) {\n                    this.emitIndent();\n                }\n                this.recordSourceMappingStart(comment);\n                this.writeToOutput(text[0]);\n                this.recordSourceMappingEnd(comment);\n                this.writeLineToOutput(\"\");\n                hadNewLine = true;\n            }\n\n            if (hadNewLine) {\n                this.emitIndent();\n            }\n            else {\n                this.writeToOutput(\" \");\n            }\n        }\n\n        public emitParensAndCommentsInPlace(ast: AST, pre: bool) {\n            var comments = pre ? ast.preComments : ast.postComments;\n\n            // comments should be printed before the LParen, but after the RParen\n            if (ast.isParenthesized && !pre) {\n                this.writeToOutput(\")\");\n            }\n            if (this.emitOptions.emitComments && comments && comments.length != 0) {\n                for (var i = 0; i < comments.length; i++) {\n                    this.emitCommentInPlace(comments[i]);\n                }\n            }\n            if (ast.isParenthesized && pre) {\n                this.writeToOutput(\"(\");\n            }\n        }\n\n        // TODO: emit accessor pattern\n        public emitObjectLiteral(content: ASTList) {\n            this.writeLineToOutput(\"{\");\n            this.indenter.increaseIndent();\n            var inObjectLiteral = this.setInObjectLiteral(true);\n            this.emitJavascriptList(content, \",\", TokenID.Comma, true, false, false);\n            this.setInObjectLiteral(inObjectLiteral);\n            this.indenter.decreaseIndent();\n            this.emitIndent();\n            this.writeToOutput(\"}\");\n        }\n\n        public emitArrayLiteral(content: ASTList) {\n            this.writeToOutput(\"[\");\n            if (content) {\n                this.writeLineToOutput(\"\");\n                this.indenter.increaseIndent();\n                this.emitJavascriptList(content, \", \", TokenID.Comma, true, false, false);\n                this.indenter.decreaseIndent();\n                this.emitIndent();\n            }\n            this.writeToOutput(\"]\");\n        }\n\n        public emitNew(target: AST, args: ASTList) {\n            this.writeToOutput(\"new \");\n            if (target.nodeType == NodeType.TypeRef) {\n                var typeRef = <TypeReference>target;\n                if (typeRef.arrayCount) {\n                    this.writeToOutput(\"Array()\");\n                }\n                else {\n                    this.emitJavascript(typeRef.term, TokenID.Tilde, false);\n                    this.writeToOutput(\"()\");\n                }\n            }\n            else {\n                this.emitJavascript(target, TokenID.Tilde, false);\n                this.recordSourceMappingStart(args);\n                this.writeToOutput(\"(\");\n                this.emitJavascriptList(args, \", \", TokenID.Comma, false, false, false);\n                this.writeToOutput(\")\");\n                this.recordSourceMappingEnd(args);\n            }\n        }\n\n        public tryEmitConstant(dotExpr: BinaryExpression) {\n            if (!this.emitOptions.propagateConstants) {\n                return false;\n            }\n            var propertyName = <Identifier>dotExpr.operand2;\n            if (propertyName && propertyName.sym && propertyName.sym.isVariable()) {\n                if (hasFlag(propertyName.sym.flags, SymbolFlags.Constant)) {\n                    if (propertyName.sym.declAST) {\n                        var boundDecl = <BoundDecl>propertyName.sym.declAST;\n                        if (boundDecl.init && (boundDecl.init.nodeType == NodeType.NumberLit)) {\n                            var numLit = <NumberLiteral>boundDecl.init;\n                            this.writeToOutput(numLit.value.toString());\n                            var comment = \" /* \";\n                            comment += propertyName.actualText;\n                            comment += \" */ \";\n                            this.writeToOutput(comment);\n                            return true;\n                        }\n                    }\n                }\n            }\n            return false;\n        }\n\n        public emitCall(callNode: CallExpression, target: AST, args: ASTList) {\n            if (!this.emitSuperCall(callNode)) {\n                if (!hasFlag(callNode.flags, ASTFlags.ClassBaseConstructorCall)) {\n                    if (target.nodeType == NodeType.FuncDecl && !target.isParenthesized) {\n                        this.writeToOutput(\"(\");\n                    }\n                    if (callNode.target.nodeType == NodeType.Super && this.emitState.container == EmitContainer.Constructor) {\n                        this.writeToOutput(\"_super.call\");\n                    }\n                    else {\n                        this.emitJavascript(target, TokenID.OpenParen, false);\n                    }\n                    if (target.nodeType == NodeType.FuncDecl && !target.isParenthesized) {\n                        this.writeToOutput(\")\");\n                    }\n                    this.recordSourceMappingStart(args);\n                    this.writeToOutput(\"(\");\n                    if (callNode.target.nodeType == NodeType.Super && this.emitState.container == EmitContainer.Constructor) {\n                        this.writeToOutput(\"this\");\n                        if (args && args.members.length) {\n                            this.writeToOutput(\", \");\n                        }\n                    }\n                    this.emitJavascriptList(args, \", \", TokenID.Comma, false, false, false);\n                    this.writeToOutput(\")\");\n                    this.recordSourceMappingEnd(args);\n                }\n                else {\n                    this.indenter.decreaseIndent();\n                    this.indenter.decreaseIndent();\n                    var constructorCall = new ASTList();\n                    constructorCall.members[0] = callNode;\n                    this.emitConstructorCalls(constructorCall, this.thisClassNode);\n                    this.indenter.increaseIndent();\n                    this.indenter.increaseIndent();\n                }\n            }\n        }\n\n        public emitConstructorCalls(bases: ASTList, classDecl: TypeDeclaration) {\n            if (bases == null) {\n                return;\n            }\n            var basesLen = bases.members.length;\n            this.recordSourceMappingStart(classDecl);\n            for (var i = 0; i < basesLen; i++) {\n                var baseExpr = bases.members[i];\n                var baseSymbol: Symbol = null;\n                if (baseExpr.nodeType == NodeType.Call) {\n                    baseSymbol = (<CallExpression>baseExpr).target.type.symbol;\n                }\n                else {\n                    baseSymbol = baseExpr.type.symbol;\n                }\n                var baseName = baseSymbol.name;\n                if (baseSymbol.declModule != classDecl.type.symbol.declModule) {\n                    baseName = baseSymbol.fullName();\n                }\n                if (baseExpr.nodeType == NodeType.Call) {\n                    this.emitIndent();\n                    this.writeToOutput(\"_super.call(this\");\n                    var args = (<CallExpression>baseExpr).arguments;\n                    if (args && (args.members.length > 0)) {\n                        this.writeToOutput(\", \");\n                        this.emitJavascriptList(args, \", \", TokenID.Comma, false, false, false);\n                    }\n                    this.writeToOutput(\")\");\n                }\n                else {\n                    if (baseExpr.type && (baseExpr.type.isClassInstance())) {\n                        // parameterless constructor call;\n                        this.emitIndent();\n                        this.writeToOutput(classDecl.name.actualText + \"._super.constructor\");\n                        //emitJavascript(baseExpr,TokenID.LParen,false);\n                        this.writeToOutput(\".call(this)\");\n                    }\n                }\n            }\n            this.recordSourceMappingEnd(classDecl);\n        }\n\n        public emitInnerFunction(funcDecl: FuncDecl, printName: bool, isMember: bool,\n            bases: ASTList, hasSelfRef: bool, classDecl: TypeDeclaration) {\n            /// REVIEW: The code below causes functions to get pushed to a newline in cases where they shouldn't\n            /// such as: \n            ///     Foo.prototype.bar = \n            ///         function() {\n            ///         };\n            /// Once we start emitting comments, we should pull this code out to place on the outer context where the function\n            /// is used.\n            //if (funcDecl.preComments!=null && funcDecl.preComments.length>0) {\n            //    this.writeLineToOutput(\"\");\n            //    this.increaseIndent();\n            //    emitIndent();\n            //}\n\n            var isClassConstructor = funcDecl.isConstructor && hasFlag(funcDecl.fncFlags, FncFlags.ClassMethod);\n            var hasNonObjectBaseType = isClassConstructor && hasFlag(this.thisClassNode.type.instanceType.typeFlags, TypeFlags.HasBaseType) && !hasFlag(this.thisClassNode.type.instanceType.typeFlags, TypeFlags.HasBaseTypeOfObject);\n            var classPropertiesMustComeAfterSuperCall = hasNonObjectBaseType && hasFlag((<ClassDeclaration>this.thisClassNode).varFlags, VarFlags.ClassSuperMustBeFirstCallInConstructor);\n\n            // We have no way of knowing if the current function is used as an expression or a statement, so as to enusre that the emitted\n            // JavaScript is always valid, add an extra parentheses for unparenthesized function expressions\n            var shouldParenthesize = hasFlag(funcDecl.fncFlags, FncFlags.IsFunctionExpression) && !funcDecl.isParenthesized && !funcDecl.isAccessor() && (hasFlag(funcDecl.flags, ASTFlags.ExplicitSemicolon) || hasFlag(funcDecl.flags, ASTFlags.AutomaticSemicolon));\n\n            this.emitParensAndCommentsInPlace(funcDecl, true);\n            if (shouldParenthesize) {\n                this.writeToOutput(\"(\");\n            }\n            this.recordSourceMappingStart(funcDecl);\n            if (!(funcDecl.isAccessor() && (<FieldSymbol>funcDecl.accessorSymbol).isObjectLitField)) {\n                this.writeToOutput(\"function \");\n            }\n            if (printName) {\n                var id = funcDecl.getNameText();\n                if (id && !funcDecl.isAccessor()) {\n                    if (funcDecl.name) {\n                        this.recordSourceMappingStart(funcDecl.name);\n                    }\n                    this.writeToOutput(id);\n                    if (funcDecl.name) {\n                        this.recordSourceMappingEnd(funcDecl.name);\n                    }\n                }\n            }\n\n            this.writeToOutput(\"(\");\n            var argsLen = 0;\n            var i = 0;\n            var arg: ArgDecl;\n            var defaultArgs: ArgDecl[] = [];\n            if (funcDecl.arguments) {\n                var tempContainer = this.setContainer(EmitContainer.Args);\n                argsLen = funcDecl.arguments.members.length;\n                var printLen = argsLen;\n                if (funcDecl.variableArgList) {\n                    printLen--;\n                }\n                for (i = 0; i < printLen; i++) {\n                    arg = <ArgDecl>funcDecl.arguments.members[i];\n                    if (arg.init) {\n                        defaultArgs.push(arg);\n                    }\n                    this.emitJavascript(arg, TokenID.OpenParen, false);\n                    if (i < (printLen - 1)) {\n                        this.writeToOutput(\", \");\n                    }\n                }\n                this.setContainer(tempContainer);\n            }\n            this.writeLineToOutput(\") {\");\n\n            if (funcDecl.isConstructor) {\n                this.recordSourceMappingNameStart(\"constructor\");\n            } else if (funcDecl.isGetAccessor()) {\n                this.recordSourceMappingNameStart(\"get_\" + funcDecl.getNameText());\n            } else if (funcDecl.isSetAccessor()) {\n                this.recordSourceMappingNameStart(\"set_\" + funcDecl.getNameText());\n            } else {\n                this.recordSourceMappingNameStart(funcDecl.getNameText());\n            }\n            this.indenter.increaseIndent();\n\n            // set default args first\n            for (i = 0; i < defaultArgs.length; i++) {\n                var arg = defaultArgs[i];\n                this.emitIndent();\n                this.recordSourceMappingStart(arg);\n                this.writeToOutput(\"if (typeof \" + arg.id.actualText + \" === \\\"undefined\\\") { \");//\n                this.recordSourceMappingStart(arg.id);\n                this.writeToOutput(arg.id.actualText);\n                this.recordSourceMappingEnd(arg.id);\n                this.writeToOutput(\" = \");\n                this.emitJavascript(arg.init, TokenID.OpenParen, false);\n                this.writeLineToOutput(\"; }\")\n                this.recordSourceMappingEnd(arg);\n            }\n\n            if (funcDecl.isConstructor && ((<ClassDeclaration>funcDecl.classDecl).varFlags & VarFlags.MustCaptureThis)) {\n                this.writeCaptureThisStatement(funcDecl);\n            }\n\n            if (funcDecl.isConstructor && !classPropertiesMustComeAfterSuperCall) {\n                if (funcDecl.arguments) {\n                    argsLen = funcDecl.arguments.members.length;\n                    for (i = 0; i < argsLen; i++) {\n                        arg = <ArgDecl>funcDecl.arguments.members[i];\n                        if ((arg.varFlags & VarFlags.Property) != VarFlags.None) {\n                            this.emitIndent();\n                            this.recordSourceMappingStart(arg);\n                            this.recordSourceMappingStart(arg.id);\n                            this.writeToOutput(\"this.\" + arg.id.actualText);\n                            this.recordSourceMappingEnd(arg.id);\n                            this.writeToOutput(\" = \");\n                            this.recordSourceMappingStart(arg.id);\n                            this.writeToOutput(arg.id.actualText);\n                            this.recordSourceMappingEnd(arg.id);\n                            this.writeLineToOutput(\";\");\n                            this.recordSourceMappingEnd(arg);\n                        }\n                    }\n                }\n\n                // For classes, the constructor needs to be explicitly called\n                if (!hasFlag(funcDecl.fncFlags, FncFlags.ClassMethod)) {\n                    this.emitConstructorCalls(bases, classDecl);\n                }\n            }\n            if (hasSelfRef) {\n                this.writeCaptureThisStatement(funcDecl);\n            }\n            if (funcDecl.variableArgList) {\n                argsLen = funcDecl.arguments.members.length;\n                var lastArg = <ArgDecl>funcDecl.arguments.members[argsLen - 1];\n                this.emitIndent();\n                this.recordSourceMappingStart(lastArg);\n                this.writeToOutput(\"var \");\n                this.recordSourceMappingStart(lastArg.id);\n                this.writeToOutput(lastArg.id.actualText);\n                this.recordSourceMappingEnd(lastArg.id);\n                this.writeLineToOutput(\" = [];\");\n                this.recordSourceMappingEnd(lastArg);\n                this.emitIndent();\n                this.writeToOutput(\"for (\")\n                this.recordSourceMappingStart(lastArg);\n                this.writeToOutput(\"var _i = 0;\");\n                this.recordSourceMappingEnd(lastArg);\n                this.writeToOutput(\" \");\n                this.recordSourceMappingStart(lastArg);\n                this.writeToOutput(\"_i < (arguments.length - \" + (argsLen - 1) + \")\");\n                this.recordSourceMappingEnd(lastArg);\n                this.writeToOutput(\"; \");\n                this.recordSourceMappingStart(lastArg);\n                this.writeToOutput(\"_i++\");\n                this.recordSourceMappingEnd(lastArg);\n                this.writeLineToOutput(\") {\");\n                this.indenter.increaseIndent();\n                this.emitIndent();\n\n                this.recordSourceMappingStart(lastArg);\n                this.writeToOutput(lastArg.id.actualText + \"[_i] = arguments[_i + \" + (argsLen - 1) + \"];\");\n                this.recordSourceMappingEnd(lastArg);\n                this.writeLineToOutput(\"\");\n                this.indenter.decreaseIndent();\n                this.emitIndent();\n                this.writeLineToOutput(\"}\");\n            }\n\n            // if it's a class, emit the uninitializedMembers, first emit the non-proto class body members\n            if (funcDecl.isConstructor && hasFlag(funcDecl.fncFlags, FncFlags.ClassMethod) && !classPropertiesMustComeAfterSuperCall) {\n\n                var nProps = (<ASTList>this.thisClassNode.members).members.length;\n\n                for (var i = 0; i < nProps; i++) {\n                    if ((<ASTList>this.thisClassNode.members).members[i].nodeType == NodeType.VarDecl) {\n                        var varDecl = <VarDecl>(<ASTList>this.thisClassNode.members).members[i];\n                        if (!hasFlag(varDecl.varFlags, VarFlags.Static) && varDecl.init) {\n                            this.emitIndent();\n                            this.emitJavascriptVarDecl(varDecl, TokenID.Tilde);\n                            this.writeLineToOutput(\"\");\n                        }\n                    }\n                }\n                //this.writeLineToOutput(\"\");\n            }\n\n            this.emitBareJavascriptStatements(funcDecl.bod, classPropertiesMustComeAfterSuperCall);\n\n            this.indenter.decreaseIndent();\n            this.emitIndent();\n            this.recordSourceMappingStart(funcDecl.endingToken);\n            this.writeToOutput(\"}\");\n\n            this.recordSourceMappingNameEnd();\n            this.recordSourceMappingEnd(funcDecl.endingToken);\n            this.recordSourceMappingEnd(funcDecl);\n\n            if (shouldParenthesize) {\n                this.writeToOutput(\")\");\n            }\n\n            // The extra call is to make sure the caller's funcDecl end is recorded, since caller wont be able to record it\n            this.recordSourceMappingEnd(funcDecl);\n\n            this.emitParensAndCommentsInPlace(funcDecl, false);\n\n            if (!isMember &&\n                //funcDecl.name != null &&\n                !hasFlag(funcDecl.fncFlags, FncFlags.IsFunctionExpression) &&\n                (hasFlag(funcDecl.fncFlags, FncFlags.Definition) || funcDecl.isConstructor)) {\n                this.writeLineToOutput(\"\");\n            } else if (hasFlag(funcDecl.fncFlags, FncFlags.IsFunctionExpression)) {\n                if (hasFlag(funcDecl.flags, ASTFlags.ExplicitSemicolon) || hasFlag(funcDecl.flags, ASTFlags.AutomaticSemicolon)) {\n                    // If either of these two flags are set, then the function expression is a statement. Terminate it.\n                    this.writeLineToOutput(\";\");\n                }\n            }\n            /// TODO: See the other part of this at the beginning of function\n            //if (funcDecl.preComments!=null && funcDecl.preComments.length>0) {\n            //    this.decreaseIndent();\n            //}           \n        }\n\n        public emitJavascriptModule(moduleDecl: ModuleDeclaration) {\n            var modName = moduleDecl.name.actualText;\n            if (isTSFile(modName)) {\n                moduleDecl.name.setText(modName.substring(0, modName.length - 3));\n            }\n            else if (isSTRFile(modName)) {\n                moduleDecl.name.setText(modName.substring(0, modName.length - 4));\n            }\n\n            if (!hasFlag(moduleDecl.modFlags, ModuleFlags.Ambient)) {\n                var isDynamicMod = hasFlag(moduleDecl.modFlags, ModuleFlags.IsDynamic);\n                var prevOutFile = this.outfile;\n                var prevOutFileName = this.emittingFileName;\n                var prevAllSourceMappers = this.allSourceMappers;\n                var prevSourceMapper = this.sourceMapper;\n                var prevColumn = this.emitState.column;\n                var prevLine = this.emitState.line;\n                var temp = this.setContainer(EmitContainer.Module);\n                var svModuleName = this.moduleName;\n                var isExported = hasFlag(moduleDecl.modFlags, ModuleFlags.Exported);\n                this.moduleDeclList[this.moduleDeclList.length] = moduleDecl;\n                var isWholeFile = hasFlag(moduleDecl.modFlags, ModuleFlags.IsWholeFile);\n                this.moduleName = moduleDecl.name.actualText;\n\n                // prologue\n                if (isDynamicMod) {\n                    // create the new outfile for this module\n                    var tsModFileName = stripQuotes(moduleDecl.name.actualText);\n                    var modFilePath = trimModName(tsModFileName) + \".js\";\n                    modFilePath = this.emitOptions.mapOutputFileName(modFilePath, TypeScriptCompiler.mapToJSFileName);\n\n                    if (this.emitOptions.ioHost) {\n                        // Ensure that the slashes are normalized so that the comparison is fair\n                        // REVIEW: Note that modFilePath is normalized to forward slashes in Parser.parse, so the \n                        // first call to switchToForwardSlashes is technically a no-op, but it will prevent us from\n                        // regressing if the parser changes\n                        if (switchToForwardSlashes(modFilePath) != switchToForwardSlashes(this.emittingFileName)) {\n                            this.emittingFileName = modFilePath;\n                            var useUTF8InOutputfile = moduleDecl.containsUnicodeChar || (this.emitOptions.emitComments && moduleDecl.containsUnicodeCharInComment);\n                            this.outfile = this.createFile(this.emittingFileName, useUTF8InOutputfile);\n                            if (prevSourceMapper != null) {\n                                this.allSourceMappers = [];\n                                var sourceMappingFile = this.createFile(this.emittingFileName + SourceMapper.MapFileExtension, false);\n                                this.setSourceMappings(new TypeScript.SourceMapper(tsModFileName, this.emittingFileName, this.outfile, sourceMappingFile, this.errorReporter));\n                                this.emitState.column = 0;\n                                this.emitState.line = 0;\n                            }\n                        } else {\n                            CompilerDiagnostics.assert(this.emitOptions.outputMany, \"Cannot have dynamic modules compiling into single file\");\n                        }\n                    }\n\n                    this.setContainer(EmitContainer.DynamicModule); // discard the previous 'Module' container\n\n                    this.recordSourceMappingStart(moduleDecl);\n                    if (moduleGenTarget == ModuleGenTarget.Asynchronous) { // AMD\n                        var dependencyList = \"[\\\"require\\\", \\\"exports\\\"\";\n                        var importList = \"require, exports\";\n                        var importStatement: ImportDeclaration = null;\n\n                        // all dependencies are quoted\n                        for (var i = 0; i < (<ModuleType>moduleDecl.mod).importedModules.length; i++) {\n                            importStatement = (<ModuleType>moduleDecl.mod).importedModules[i]\n\n                            // if the imported module is only used in a type position, do not add it as a requirement\n                            if (importStatement.id.sym &&\n                                !(<TypeSymbol>importStatement.id.sym).onlyReferencedAsTypeRef) {\n                                if (i <= (<ModuleType>moduleDecl.mod).importedModules.length - 1) {\n                                    dependencyList += \", \";\n                                    importList += \", \";\n                                }\n\n                                importList += \"__\" + importStatement.id.actualText + \"__\";\n                                dependencyList += importStatement.firstAliasedModToString();\n                            }\n                        }\n\n                        // emit any potential amd dependencies\n                        for (var i = 0; i < moduleDecl.amdDependencies.length; i++) {\n                            dependencyList += \", \\\"\" + moduleDecl.amdDependencies[i] + \"\\\"\";\n                        }\n\n                        dependencyList += \"]\";\n\n                        this.writeLineToOutput(\"define(\" + dependencyList + \",\" + \" function(\" + importList + \") {\");\n                    }\n                    else { // Node\n\n                    }\n                }\n                else {\n\n                    if (!isExported) {\n                        this.recordSourceMappingStart(moduleDecl);\n                        this.writeToOutput(\"var \");\n                        this.recordSourceMappingStart(moduleDecl.name);\n                        this.writeToOutput(this.moduleName);\n                        this.recordSourceMappingEnd(moduleDecl.name);\n                        this.writeLineToOutput(\";\");\n                        this.recordSourceMappingEnd(moduleDecl);\n                        this.emitIndent();\n                    }\n\n                    this.writeToOutput(\"(\");\n                    this.recordSourceMappingStart(moduleDecl);\n                    this.writeToOutput(\"function (\");\n                    this.recordSourceMappingStart(moduleDecl.name);\n                    this.writeToOutput(this.moduleName);\n                    this.recordSourceMappingEnd(moduleDecl.name);\n                    this.writeLineToOutput(\") {\");\n                }\n\n                if (!isWholeFile) {\n                    this.recordSourceMappingNameStart(this.moduleName);\n                }\n\n                // body - don't indent for Node\n                if (!isDynamicMod || moduleGenTarget == ModuleGenTarget.Asynchronous) {\n                    this.indenter.increaseIndent();\n                }\n\n                if (moduleDecl.modFlags & ModuleFlags.MustCaptureThis) {\n                    this.writeCaptureThisStatement(moduleDecl);\n                }\n\n                this.emitJavascriptList(moduleDecl.members, null, TokenID.Semicolon, true, false, false);\n                if (!isDynamicMod || moduleGenTarget == ModuleGenTarget.Asynchronous) {\n                    this.indenter.decreaseIndent();\n                }\n                this.emitIndent();\n\n                // epilogue\n                if (isDynamicMod) {\n                    if (moduleGenTarget == ModuleGenTarget.Asynchronous) { // AMD\n                        this.writeLineToOutput(\"})\");\n                    }\n                    else { // Node\n                    }\n                    if (!isWholeFile) {\n                        this.recordSourceMappingNameEnd();\n                    }\n                    this.recordSourceMappingEnd(moduleDecl);\n\n                    // close the module outfile, and restore the old one\n                    if (this.outfile != prevOutFile) {\n                        this.Close();\n                        if (prevSourceMapper != null) {\n                            this.allSourceMappers = prevAllSourceMappers;\n                            this.sourceMapper = prevSourceMapper;\n                            this.emitState.column = prevColumn;\n                            this.emitState.line = prevLine;\n                        }\n                        this.outfile = prevOutFile;\n                        this.emittingFileName = prevOutFileName;\n                    }\n                }\n                else {\n                    var containingMod: ModuleDeclaration = null;\n                    if (moduleDecl.type && moduleDecl.type.symbol.container && moduleDecl.type.symbol.container.declAST) {\n                        containingMod = <ModuleDeclaration>moduleDecl.type.symbol.container.declAST;\n                    }\n                    var parentIsDynamic = containingMod && hasFlag(containingMod.modFlags, ModuleFlags.IsDynamic);\n\n                    this.recordSourceMappingStart(moduleDecl.endingToken);\n                    if (temp == EmitContainer.Prog && isExported) {\n                        this.writeToOutput(\"}\");\n                        if (!isWholeFile) {\n                            this.recordSourceMappingNameEnd();\n                        }\n                        this.recordSourceMappingEnd(moduleDecl.endingToken);\n                        this.writeToOutput(\")(this.\" + this.moduleName + \" || (this.\" + this.moduleName + \" = {}));\");\n                    }\n                    else if (isExported || temp == EmitContainer.Prog) {\n                        var dotMod = svModuleName != \"\" ? (parentIsDynamic ? \"exports\" : svModuleName) + \".\" : svModuleName;\n                        this.writeToOutput(\"}\");\n                        if (!isWholeFile) {\n                            this.recordSourceMappingNameEnd();\n                        }\n                        this.recordSourceMappingEnd(moduleDecl.endingToken);\n                        this.writeToOutput(\")(\" + dotMod + this.moduleName + \" || (\" + dotMod + this.moduleName + \" = {}));\");\n                    }\n                    else if (!isExported && temp != EmitContainer.Prog) {\n                        this.writeToOutput(\"}\");\n                        if (!isWholeFile) {\n                            this.recordSourceMappingNameEnd();\n                        }\n                        this.recordSourceMappingEnd(moduleDecl.endingToken);\n                        this.writeToOutput(\")(\" + this.moduleName + \" || (\" + this.moduleName + \" = {}));\");\n                    }\n                    else {\n                        this.writeToOutput(\"}\");\n                        if (!isWholeFile) {\n                            this.recordSourceMappingNameEnd();\n                        }\n                        this.recordSourceMappingEnd(moduleDecl.endingToken);\n                        this.writeToOutput(\")();\");\n                    }\n                    this.recordSourceMappingEnd(moduleDecl);\n                    this.writeLineToOutput(\"\");\n                    if (temp != EmitContainer.Prog && isExported) {\n                        this.emitIndent();\n                        this.recordSourceMappingStart(moduleDecl);\n                        if (parentIsDynamic) {\n                            this.writeLineToOutput(\"var \" + this.moduleName + \" = exports.\" + this.moduleName + \";\");\n                        } else {\n                            this.writeLineToOutput(\"var \" + this.moduleName + \" = \" + svModuleName + \".\" + this.moduleName + \";\");\n                        }\n                        this.recordSourceMappingEnd(moduleDecl);\n                    }\n                }\n\n                this.setContainer(temp);\n                this.moduleName = svModuleName;\n                this.moduleDeclList.length--;\n            }\n        }\n\n        public emitIndex(operand1: AST, operand2: AST) {\n            var temp = this.setInObjectLiteral(false);\n            this.emitJavascript(operand1, TokenID.Tilde, false);\n            this.writeToOutput(\"[\");\n            this.emitJavascriptList(operand2, \", \", TokenID.Comma, false, false, false);\n            this.writeToOutput(\"]\");\n            this.setInObjectLiteral(temp);\n        }\n\n        public emitStringLiteral(text: string) {\n            // should preserve escape etc.\n            // TODO: simplify object literal simple name\n            this.writeToOutput(text);\n        }\n\n        public emitJavascriptFunction(funcDecl: FuncDecl) {\n            if (hasFlag(funcDecl.fncFlags, FncFlags.Signature) || funcDecl.isOverload) {\n                return;\n            }\n            var temp: number;\n            var tempFnc = this.thisFnc;\n            this.thisFnc = funcDecl;\n\n            if (funcDecl.isConstructor) {\n                temp = this.setContainer(EmitContainer.Constructor);\n            }\n            else {\n                temp = this.setContainer(EmitContainer.Function);\n            }\n\n            var bases: ASTList = null;\n            var hasSelfRef = false;\n            var funcName = funcDecl.getNameText();\n\n            if ((this.emitState.inObjectLiteral || !funcDecl.isAccessor()) &&\n                ((temp != EmitContainer.Constructor) ||\n                ((funcDecl.fncFlags & FncFlags.Method) == FncFlags.None))) {\n                var tempLit = this.setInObjectLiteral(false);\n                if (this.thisClassNode) {\n                    bases = this.thisClassNode.extendsList;\n                }\n                hasSelfRef = Emitter.shouldCaptureThis(funcDecl);\n                this.recordSourceMappingStart(funcDecl);\n                if (hasFlag(funcDecl.fncFlags, FncFlags.Exported | FncFlags.ClassPropertyMethodExported) && funcDecl.type.symbol.container == this.checker.gloMod && !funcDecl.isConstructor) {\n                    this.writeToOutput(\"this.\" + funcName + \" = \");\n                    this.emitInnerFunction(funcDecl, false, false, bases, hasSelfRef, this.thisClassNode);\n                }\n                else {\n                    this.emitInnerFunction(funcDecl, (funcDecl.name && !funcDecl.name.isMissing()), false, bases, hasSelfRef, this.thisClassNode);\n                }\n                this.setInObjectLiteral(tempLit);\n            }\n            this.setContainer(temp);\n            this.thisFnc = tempFnc;\n\n            if (hasFlag(funcDecl.fncFlags, FncFlags.Definition)) {\n                if (hasFlag(funcDecl.fncFlags, FncFlags.Static)) {\n                    if (this.thisClassNode) {\n                        if (funcDecl.isAccessor()) {\n                            this.emitPropertyAccessor(funcDecl, this.thisClassNode.name.actualText, false);\n                        }\n                        else {\n                            this.emitIndent();\n                            this.recordSourceMappingStart(funcDecl);\n                            this.writeLineToOutput(this.thisClassNode.name.actualText + \".\" + funcName +\n                                          \" = \" + funcName + \";\");\n                            this.recordSourceMappingEnd(funcDecl);\n                        }\n                    }\n                }\n                else if ((this.emitState.container == EmitContainer.Module || this.emitState.container == EmitContainer.DynamicModule) && hasFlag(funcDecl.fncFlags, FncFlags.Exported | FncFlags.ClassPropertyMethodExported)) {\n                    this.emitIndent();\n                    var modName = this.emitState.container == EmitContainer.Module ? this.moduleName : \"exports\";\n                    this.recordSourceMappingStart(funcDecl);\n                    this.writeLineToOutput(modName + \".\" + funcName +\n                                      \" = \" + funcName + \";\");\n                    this.recordSourceMappingEnd(funcDecl);\n                }\n            }\n        }\n\n        public emitAmbientVarDecl(varDecl: VarDecl) {\n            if (varDecl.init) {\n                this.emitParensAndCommentsInPlace(varDecl, true);\n                this.recordSourceMappingStart(varDecl);\n                this.recordSourceMappingStart(varDecl.id);\n                this.writeToOutput(varDecl.id.actualText);\n                this.recordSourceMappingEnd(varDecl.id);\n                this.writeToOutput(\" = \");\n                this.emitJavascript(varDecl.init, TokenID.Comma, false);\n                this.recordSourceMappingEnd(varDecl);\n                this.writeToOutput(\";\");\n                this.emitParensAndCommentsInPlace(varDecl, false);\n            }\n        }\n\n        private varListCount(): number {\n            return this.varListCountStack[this.varListCountStack.length - 1];\n        }\n\n        // Emits \"var \" if it is allowed\n        private emitVarDeclVar() {\n            // If it is var list of form var a, b, c = emit it only if count > 0 - which will be when emitting first var\n            // If it is var list of form  var a = varList count will be 0\n            if (this.varListCount() >= 0) {\n                this.writeToOutput(\"var \");\n                this.setInVarBlock(-this.varListCount());\n            }\n            return true;\n        }\n\n        private onEmitVar() {\n            if (this.varListCount() > 0) {\n                this.setInVarBlock(this.varListCount() - 1);\n            }\n            else if (this.varListCount() < 0) {\n                this.setInVarBlock(this.varListCount() + 1);\n            }\n        }\n\n        public emitJavascriptVarDecl(varDecl: VarDecl, tokenId: TokenID) {\n            if ((varDecl.varFlags & VarFlags.Ambient) == VarFlags.Ambient) {\n                this.emitAmbientVarDecl(varDecl);\n                this.onEmitVar();\n            }\n            else {\n                var sym = varDecl.sym;\n                var hasInitializer = (varDecl.init != null);\n                this.emitParensAndCommentsInPlace(varDecl, true);\n                this.recordSourceMappingStart(varDecl);\n                if (sym && sym.isMember() && sym.container &&\n                    (sym.container.kind() == SymbolKind.Type)) {\n                    var type = (<TypeSymbol>sym.container).type;\n                    if (type.isClass() && (!hasFlag(sym.flags, SymbolFlags.ModuleMember))) {\n                        // class\n                        if (this.emitState.container != EmitContainer.Args) {\n                            if (hasFlag(sym.flags, SymbolFlags.Static)) {\n                                this.writeToOutput(sym.container.name + \".\");\n                            }\n                            else {\n                                this.writeToOutput(\"this.\");\n                            }\n                        }\n                    }\n                    else if (type.hasImplementation()) {\n                        // module\n                        if (!hasFlag(sym.flags, SymbolFlags.Exported) && (sym.container == this.checker.gloMod || !hasFlag(sym.flags, SymbolFlags.Property))) {\n                            this.emitVarDeclVar();\n                        }\n                        else if (hasFlag(varDecl.varFlags, VarFlags.LocalStatic)) {\n                            this.writeToOutput(\".\");\n                        }\n                        else {\n                            if (this.emitState.container == EmitContainer.DynamicModule) {\n                                this.writeToOutput(\"exports.\");\n                            }\n                            else {\n                                this.writeToOutput(this.moduleName + \".\");\n                            }\n                        }\n                    }\n                    else {\n                        // function, constructor, method etc.\n                        if (tokenId != TokenID.OpenParen) {\n                            if (hasFlag(sym.flags, SymbolFlags.Exported) && sym.container == this.checker.gloMod) {\n                                this.writeToOutput(\"this.\");\n                            }\n                            else {\n                                this.emitVarDeclVar();\n                            }\n                        }\n                    }\n                }\n                else {\n                    if (tokenId != TokenID.OpenParen) {\n                        this.emitVarDeclVar();\n                    }\n                }\n                this.recordSourceMappingStart(varDecl.id);\n                this.writeToOutput(varDecl.id.actualText);\n                this.recordSourceMappingEnd(varDecl.id);\n                if (hasInitializer) {\n                    this.writeToOutputTrimmable(\" = \");\n\n                    // Ensure we have a fresh var list count when recursing into the variable \n                    // initializer.  We don't want our current list of variables to affect how we\n                    // emit nested variable lists.\n                    this.varListCountStack.push(0);\n                    this.emitJavascript(varDecl.init, TokenID.Comma, false);\n                    this.varListCountStack.pop();\n                }\n                this.onEmitVar();\n                if ((tokenId != TokenID.OpenParen)) {\n                    if (this.varListCount() < 0) {\n                        this.writeToOutput(\", \");\n                    } else if (tokenId != TokenID.For) {\n                        this.writeToOutputTrimmable(\";\");\n                    }\n                }\n                this.recordSourceMappingEnd(varDecl);\n                this.emitParensAndCommentsInPlace(varDecl, false);\n            }\n        }\n\n        public declEnclosed(moduleDecl: ModuleDeclaration): bool {\n            if (moduleDecl == null) {\n                return true;\n            }\n            for (var i = 0, len = this.moduleDeclList.length; i < len; i++) {\n                if (this.moduleDeclList[i] == moduleDecl) {\n                    return true;\n                }\n            }\n            return false;\n        }\n\n        public emitJavascriptName(name: Identifier, addThis: bool) {\n            var sym = name.sym;\n            this.emitParensAndCommentsInPlace(name, true);\n            this.recordSourceMappingStart(name);\n            if (!name.isMissing()) {\n                if (addThis && (this.emitState.container != EmitContainer.Args) && sym) {\n                    // TODO: flag global module with marker other than string name\n                    if (sym.container && (sym.container.name != globalId)) {\n                        if (hasFlag(sym.flags, SymbolFlags.Static) && (hasFlag(sym.flags, SymbolFlags.Property))) {\n                            if (sym.declModule && hasFlag(sym.declModule.modFlags, ModuleFlags.IsDynamic)) {\n                                this.writeToOutput(\"exports.\");\n                            }\n                            else {\n                                this.writeToOutput(sym.container.name + \".\");\n                            }\n                        }\n                        else if (sym.kind() == SymbolKind.Field) {\n                            var fieldSym = <FieldSymbol>sym;\n                            if (hasFlag(fieldSym.flags, SymbolFlags.ModuleMember)) {\n                                if ((sym.container != this.checker.gloMod) && ((hasFlag(sym.flags, SymbolFlags.Property)) || hasFlag(sym.flags, SymbolFlags.Exported))) {\n                                    if (hasFlag(sym.declModule.modFlags, ModuleFlags.IsDynamic)) {\n                                        this.writeToOutput(\"exports.\");\n                                    }\n                                    else {\n                                        this.writeToOutput(sym.container.name + \".\");\n                                    }\n                                }\n                            }\n                            else {\n                                if (sym.isInstanceProperty()) {\n                                    this.emitThis();\n                                    this.writeToOutput(\".\");\n                                }\n                            }\n                        }\n                        else if (sym.kind() == SymbolKind.Type) {\n                            if (sym.isInstanceProperty()) {\n                                var typeSym = <TypeSymbol>sym;\n                                var type = typeSym.type;\n                                if (type.call && !hasFlag(sym.flags, SymbolFlags.ModuleMember)) {\n                                    this.emitThis();\n                                    this.writeToOutput(\".\");\n                                }\n                            }\n                            else if ((sym.unitIndex != this.checker.locationInfo.unitIndex) || (!this.declEnclosed(sym.declModule))) {\n                                this.writeToOutput(sym.container.name + \".\")\n                            }\n                        }\n                    }\n                    else if (sym.container == this.checker.gloMod &&\n                                hasFlag(sym.flags, SymbolFlags.Exported) &&\n                                !hasFlag(sym.flags, SymbolFlags.Ambient) &&\n                                // check that it's a not a member of an ambient module...\n                                !((sym.isType() || sym.isMember()) &&\n                                    sym.declModule &&\n                                    hasFlag(sym.declModule.modFlags, ModuleFlags.Ambient)) &&\n                                this.emitState.container == EmitContainer.Prog &&\n                                sym.declAST.nodeType != NodeType.FuncDecl) {\n                        this.writeToOutput(\"this.\");\n                    }\n                }\n\n                // If it's a dynamic module, we need to print the \"require\" invocation\n                if (sym &&\n                    sym.declAST &&\n                    sym.declAST.nodeType == NodeType.ModuleDeclaration &&\n                    (hasFlag((<ModuleDeclaration>sym.declAST).modFlags, ModuleFlags.IsDynamic))) {\n                    var moduleDecl: ModuleDeclaration = <ModuleDeclaration>sym.declAST;\n\n                    if (moduleGenTarget == ModuleGenTarget.Asynchronous) {\n                        this.writeLineToOutput(\"__\" + this.modAliasId + \"__;\");\n                    }\n                    else {\n                        var modPath = name.actualText;//(<ModuleDecl>moduleDecl.mod.symbol.declAST).name.actualText;\n                        var isAmbient = moduleDecl.mod.symbol.declAST && hasFlag((<ModuleDeclaration>moduleDecl.mod.symbol.declAST).modFlags, ModuleFlags.Ambient);\n                        modPath = isAmbient ? modPath : this.firstModAlias ? this.firstModAlias : quoteBaseName(modPath);\n                        modPath = isAmbient ? modPath : (!isRelative(stripQuotes(modPath)) ? quoteStr(\"./\" + stripQuotes(modPath)) : modPath);\n                        this.writeToOutput(\"require(\" + modPath + \")\");\n                    }\n                }\n                else {\n                    this.writeToOutput(name.actualText);\n                }\n            }\n            this.recordSourceMappingEnd(name);\n            this.emitParensAndCommentsInPlace(name, false);\n        }\n\n        public emitJavascriptStatements(stmts: AST, emitEmptyBod: bool) {\n            if (stmts) {\n                if (stmts.nodeType != NodeType.Block) {\n                    var hasContents = (stmts && (stmts.nodeType != NodeType.List || ((<ASTList>stmts).members.length > 0)));\n                    if (emitEmptyBod || hasContents) {\n                        var hasOnlyBlockStatement = ((stmts.nodeType == NodeType.Block) ||\n                            ((stmts.nodeType == NodeType.List) && ((<ASTList>stmts).members.length == 1) && ((<ASTList>stmts).members[0].nodeType == NodeType.Block)));\n\n                        this.recordSourceMappingStart(stmts);\n                        if (!hasOnlyBlockStatement) {\n                            this.writeLineToOutput(\" {\");\n                            this.indenter.increaseIndent();\n                        }\n                        this.emitJavascriptList(stmts, null, TokenID.Semicolon, true, false, false);\n                        if (!hasOnlyBlockStatement) {\n                            this.writeLineToOutput(\"\");\n                            this.indenter.decreaseIndent();\n                            this.emitIndent();\n                            this.writeToOutput(\"}\");\n                        }\n                        this.recordSourceMappingEnd(stmts);\n                    }\n                }\n                else {\n                    this.emitJavascript(stmts, TokenID.Semicolon, true);\n                }\n            }\n            else if (emitEmptyBod) {\n                this.writeToOutput(\"{ }\");\n            }\n        }\n\n        public emitBareJavascriptStatements(stmts: AST, emitClassPropertiesAfterSuperCall: bool = false) {\n            // just the statements without enclosing curly braces\n            if (stmts.nodeType != NodeType.Block) {\n                if (stmts.nodeType == NodeType.List) {\n                    var stmtList = <ASTList>stmts;\n                    if ((stmtList.members.length == 2) &&\n                        (stmtList.members[0].nodeType == NodeType.Block) &&\n                        (stmtList.members[1].nodeType == NodeType.EndCode)) {\n                        this.emitJavascript(stmtList.members[0], TokenID.Semicolon, true);\n                        this.writeLineToOutput(\"\");\n                    }\n                    else {\n                        this.emitJavascriptList(stmts, null, TokenID.Semicolon, true, false, emitClassPropertiesAfterSuperCall);\n                    }\n                }\n                else {\n                    this.emitJavascript(stmts, TokenID.Semicolon, true);\n                }\n            }\n            else {\n                this.emitJavascript(stmts, TokenID.Semicolon, true);\n            }\n        }\n\n        public recordSourceMappingNameStart(name: string) {\n            if (this.sourceMapper) {\n                var finalName = name;\n                if (!name) {\n                    finalName = \"\";\n                } else if (this.sourceMapper.currentNameIndex.length > 0) {\n                    finalName = this.sourceMapper.names[this.sourceMapper.currentNameIndex.length - 1] + \".\" + name;\n                }\n\n                // We are currently not looking for duplicate but that is possible.\n                this.sourceMapper.names.push(finalName);\n                this.sourceMapper.currentNameIndex.push(this.sourceMapper.names.length - 1);\n            }\n        }\n\n        public recordSourceMappingNameEnd() {\n            if (this.sourceMapper) {\n                this.sourceMapper.currentNameIndex.pop();\n            }\n        }\n\n        public recordSourceMappingStart(ast: ASTSpan) {\n            if (this.sourceMapper && isValidAstNode(ast)) {\n                var lineCol = { line: -1, col: -1 };\n                var sourceMapping = new SourceMapping();\n                sourceMapping.start.emittedColumn = this.emitState.column;\n                sourceMapping.start.emittedLine = this.emitState.line;\n                // REVIEW: check time consumed by this binary search (about two per leaf statement)\n                getSourceLineColFromMap(lineCol, ast.minChar, this.checker.locationInfo.lineMap);\n                sourceMapping.start.sourceColumn = lineCol.col;\n                sourceMapping.start.sourceLine = lineCol.line;\n                getSourceLineColFromMap(lineCol, ast.limChar, this.checker.locationInfo.lineMap);\n                sourceMapping.end.sourceColumn = lineCol.col;\n                sourceMapping.end.sourceLine = lineCol.line;\n                if (this.sourceMapper.currentNameIndex.length > 0) {\n                    sourceMapping.nameIndex = this.sourceMapper.currentNameIndex[this.sourceMapper.currentNameIndex.length - 1];\n                }\n                // Set parent and child relationship\n                var siblings = this.sourceMapper.currentMappings[this.sourceMapper.currentMappings.length - 1];\n                siblings.push(sourceMapping);\n                this.sourceMapper.currentMappings.push(sourceMapping.childMappings);\n            }\n        }\n\n        public recordSourceMappingEnd(ast: ASTSpan) {\n            if (this.sourceMapper && isValidAstNode(ast)) {\n                // Pop source mapping childs\n                this.sourceMapper.currentMappings.pop();\n\n                // Get the last source mapping from sibling list = which is the one we are recording end for\n                var siblings = this.sourceMapper.currentMappings[this.sourceMapper.currentMappings.length - 1];\n                var sourceMapping = siblings[siblings.length - 1];\n\n                sourceMapping.end.emittedColumn = this.emitState.column;\n                sourceMapping.end.emittedLine = this.emitState.line;\n            }\n        }\n\n        public Close() {\n            if (this.sourceMapper != null) {\n                SourceMapper.EmitSourceMapping(this.allSourceMappers);\n            }\n            try {\n                // Closing files could result in exceptions, report them if they occur\n                this.outfile.Close();\n            } catch (ex) {\n                this.errorReporter.emitterError(null, ex.message);\n            }\n        }\n\n        public emitJavascriptList(ast: AST, delimiter: string, tokenId: TokenID, startLine: bool, onlyStatics: bool, emitClassPropertiesAfterSuperCall: bool = false, emitPrologue? = false, requiresExtendsBlock?: bool) {\n            if (ast == null) {\n                return;\n            }\n            else if (ast.nodeType != NodeType.List) {\n                this.emitPrologue(emitPrologue);\n                this.emitJavascript(ast, tokenId, startLine);\n            }\n            else {\n                var list = <ASTList>ast;\n                if (list.members.length == 0) {\n                    return;\n                }\n\n                this.emitParensAndCommentsInPlace(ast, true);\n                var len = list.members.length;\n                for (var i = 0; i < len; i++) {\n                    if (emitPrologue) {\n                        // If the list has Strict mode flags, emit prologue after first statement\n                        // otherwise emit before first statement\n                        if (i == 1 || !hasFlag(list.flags, ASTFlags.StrictMode)) {\n                            this.emitPrologue(requiresExtendsBlock);\n                            emitPrologue = false;\n                        }\n                    }\n\n                    // In some circumstances, class property initializers must be emitted immediately after the 'super' constructor\n                    // call which, in these cases, must be the first statement in the constructor body\n                    if (i == 1 && emitClassPropertiesAfterSuperCall) {\n\n                        // emit any parameter properties first\n                        var constructorDecl = (<ClassDeclaration>this.thisClassNode).constructorDecl;\n\n                        if (constructorDecl && constructorDecl.arguments) {\n                            var argsLen = constructorDecl.arguments.members.length;\n                            for (var iArg = 0; iArg < argsLen; iArg++) {\n                                var arg = <BoundDecl>constructorDecl.arguments.members[iArg];\n                                if ((arg.varFlags & VarFlags.Property) != VarFlags.None) {\n                                    this.emitIndent();\n                                    this.recordSourceMappingStart(arg);\n                                    this.recordSourceMappingStart(arg.id);\n                                    this.writeToOutput(\"this.\" + arg.id.actualText);\n                                    this.recordSourceMappingEnd(arg.id);\n                                    this.writeToOutput(\" = \");\n                                    this.recordSourceMappingStart(arg.id);\n                                    this.writeToOutput(arg.id.actualText);\n                                    this.recordSourceMappingEnd(arg.id);\n                                    this.writeLineToOutput(\";\");\n                                    this.recordSourceMappingEnd(arg);\n                                }\n                            }\n                        }\n\n                        var nProps = (<ASTList>this.thisClassNode.members).members.length;\n\n                        for (var iMember = 0; iMember < nProps; iMember++) {\n                            if ((<ASTList>this.thisClassNode.members).members[iMember].nodeType == NodeType.VarDecl) {\n                                var varDecl = <VarDecl>(<ASTList>this.thisClassNode.members).members[iMember];\n                                if (!hasFlag(varDecl.varFlags, VarFlags.Static) && varDecl.init) {\n                                    this.emitIndent();\n                                    this.emitJavascriptVarDecl(varDecl, TokenID.Tilde);\n                                    this.writeLineToOutput(\"\");\n                                }\n                            }\n                        }\n                    }\n\n                    var emitNode = list.members[i];\n\n                    var isStaticDecl =\n                                (emitNode.nodeType == NodeType.FuncDecl && hasFlag((<FuncDecl>emitNode).fncFlags, FncFlags.Static)) ||\n                                (emitNode.nodeType == NodeType.VarDecl && hasFlag((<VarDecl>emitNode).varFlags, VarFlags.Static))\n\n                    if (onlyStatics ? !isStaticDecl : isStaticDecl) {\n                        continue;\n                    }\n                    this.emitJavascript(emitNode, tokenId, startLine);\n\n                    if (delimiter && (i < (len - 1))) {\n                        if (startLine) {\n                            this.writeLineToOutput(delimiter);\n                        }\n                        else {\n                            this.writeToOutput(delimiter);\n                        }\n                    }\n                    else if (startLine &&\n                             (emitNode.nodeType != NodeType.ModuleDeclaration) &&\n                             (emitNode.nodeType != NodeType.InterfaceDeclaration) &&\n                             (!((emitNode.nodeType == NodeType.VarDecl) &&\n                                ((((<VarDecl>emitNode).varFlags) & VarFlags.Ambient) == VarFlags.Ambient) &&\n                                (((<VarDecl>emitNode).init) == null)) && this.varListCount() >= 0) &&\n                             (emitNode.nodeType != NodeType.Block || (<Block>emitNode).isStatementBlock) &&\n                             (emitNode.nodeType != NodeType.EndCode) &&\n                             (emitNode.nodeType != NodeType.FuncDecl)) {\n                        this.writeLineToOutput(\"\");\n                    }\n                }\n                this.emitParensAndCommentsInPlace(ast, false);\n            }\n        }\n\n        // tokenId is the id the preceding token\n        public emitJavascript(ast: AST, tokenId: TokenID, startLine: bool) {\n            if (ast == null) {\n                return;\n            }\n\n            // REVIEW: simplify rules for indenting\n            if (startLine && (this.indenter.indentAmt > 0) && (ast.nodeType != NodeType.List) &&\n                (ast.nodeType != NodeType.Block)) {\n                if ((ast.nodeType != NodeType.InterfaceDeclaration) &&\n                    (!((ast.nodeType == NodeType.VarDecl) &&\n                       ((((<VarDecl>ast).varFlags) & VarFlags.Ambient) == VarFlags.Ambient) &&\n                       (((<VarDecl>ast).init) == null)) && this.varListCount() >= 0) &&\n                    (ast.nodeType != NodeType.EndCode) &&\n                    ((ast.nodeType != NodeType.FuncDecl) ||\n                     (this.emitState.container != EmitContainer.Constructor))) {\n                    this.emitIndent();\n                }\n            }\n\n            ast.emit(this, tokenId, startLine);\n\n            if ((tokenId == TokenID.Semicolon) && (ast.nodeType < NodeType.GeneralNode)) {\n                this.writeToOutput(\";\");\n            }\n        }\n\n        public emitPropertyAccessor(funcDecl: FuncDecl, className: string, isProto: bool) {\n            if (!(<FieldSymbol>funcDecl.accessorSymbol).hasBeenEmitted) {\n                var accessorSymbol = <FieldSymbol>funcDecl.accessorSymbol;\n                this.emitIndent();\n                this.recordSourceMappingStart(funcDecl);\n                this.writeLineToOutput(\"Object.defineProperty(\" + className + (isProto ? \".prototype, \\\"\" : \", \\\"\") + funcDecl.name.actualText + \"\\\"\" + \", {\");\n                this.indenter.increaseIndent();\n\n                if (accessorSymbol.getter) {\n                    var getter: FuncDecl = <FuncDecl>accessorSymbol.getter.declAST;\n\n                    this.emitIndent();\n                    this.recordSourceMappingStart(getter);\n                    this.writeToOutput(\"get: \");\n                    this.emitInnerFunction(getter, false, isProto, null, Emitter.shouldCaptureThis(getter), null);\n                    this.writeLineToOutput(\",\");\n                }\n\n                if (accessorSymbol.setter) {\n                    var setter: FuncDecl = <FuncDecl>accessorSymbol.setter.declAST;\n\n                    this.emitIndent();\n                    this.recordSourceMappingStart(setter);\n                    this.writeToOutput(\"set: \");\n                    this.emitInnerFunction(setter, false, isProto, null, Emitter.shouldCaptureThis(setter), null);\n                    this.writeLineToOutput(\",\");\n                }\n\n                this.emitIndent();\n                this.writeLineToOutput(\"enumerable: true,\");\n                this.emitIndent();\n                this.writeLineToOutput(\"configurable: true\");\n                this.indenter.decreaseIndent();\n                this.emitIndent();\n                this.writeLineToOutput(\"});\");\n                this.recordSourceMappingEnd(funcDecl);\n\n                accessorSymbol.hasBeenEmitted = true;\n            }\n        }\n\n        public emitPrototypeMember(member: AST, className: string) {\n            if (member.nodeType == NodeType.FuncDecl) {\n                var funcDecl = <FuncDecl>member;\n                if (funcDecl.isAccessor()) {\n                    this.emitPropertyAccessor(funcDecl, className, true);\n                }\n                else {\n                    this.emitIndent();\n                    this.recordSourceMappingStart(funcDecl);\n                    this.writeToOutput(className + \".prototype.\" + funcDecl.getNameText() + \" = \");\n                    this.emitInnerFunction(funcDecl, false, true, null, Emitter.shouldCaptureThis(funcDecl), null);\n                    this.writeLineToOutput(\";\");\n                }\n            }\n            else if (member.nodeType == NodeType.VarDecl) {\n                var varDecl = <VarDecl>member;\n\n                if (varDecl.init) {\n                    this.emitIndent();\n                    this.recordSourceMappingStart(varDecl);\n                    this.recordSourceMappingStart(varDecl.id);\n                    this.writeToOutput(className + \".prototype.\" + varDecl.id.actualText);\n                    this.recordSourceMappingEnd(varDecl.id);\n                    this.writeToOutput(\" = \");\n                    this.emitJavascript(varDecl.init, TokenID.Equals, false);\n                    this.recordSourceMappingEnd(varDecl);\n                    this.writeLineToOutput(\";\");\n                }\n            }\n        }\n\n        public emitAddBaseMethods(className: string, base: Type, classDecl: TypeDeclaration): void {\n            if (base.members) {\n                var baseSymbol = base.symbol;\n                var baseName = baseSymbol.name;\n                if (baseSymbol.declModule != classDecl.type.symbol.declModule) {\n                    baseName = baseSymbol.fullName();\n                }\n                base.members.allMembers.map(function(key, s, c) {\n                    var sym = <Symbol>s;\n                    if ((sym.kind() == SymbolKind.Type) && (<TypeSymbol>sym).type.call) {\n                        this.recordSourceMappingStart(sym.declAST);\n                        this.writeLineToOutput(className + \".prototype.\" + sym.name + \" = \" +\n                                          baseName + \".prototype.\" + sym.name + \";\");\n                        this.recordSourceMappingEnd(sym.declAST);\n                    }\n                }, null);\n            }\n            if (base.extendsList) {\n                for (var i = 0, len = base.extendsList.length; i < len; i++) {\n                    this.emitAddBaseMethods(className, base.extendsList[i], classDecl);\n                }\n            }\n        }\n\n        public emitJavascriptClass(classDecl: ClassDeclaration) {\n            if (!hasFlag(classDecl.varFlags, VarFlags.Ambient)) {\n                var svClassNode = this.thisClassNode;\n                var i = 0;\n                this.thisClassNode = classDecl;\n                var className = classDecl.name.actualText;\n                this.emitParensAndCommentsInPlace(classDecl, true);\n                var temp = this.setContainer(EmitContainer.Class);\n\n                this.recordSourceMappingStart(classDecl);\n                if (hasFlag(classDecl.varFlags, VarFlags.Exported) && classDecl.type.symbol.container == this.checker.gloMod) {\n                    this.writeToOutput(\"this.\" + className);\n                }\n                else {\n                    this.writeToOutput(\"var \" + className);\n                }\n\n                //if (hasFlag(classDecl.varFlags, VarFlags.Exported) && (temp == EmitContainer.Module || temp == EmitContainer.DynamicModule)) {\n                //    var modName = temp == EmitContainer.Module ? this.moduleName : \"exports\";\n                //    this.writeToOutput(\" = \" + modName + \".\" + className);\n                //}\n\n                var hasBaseClass = classDecl.extendsList && classDecl.extendsList.members.length;\n                var baseNameDecl: AST = null;\n                var baseName: AST = null;\n\n                if (hasBaseClass) {\n                    this.writeLineToOutput(\" = (function (_super) {\");\n                } else {\n                    this.writeLineToOutput(\" = (function () {\");\n                }\n\n                this.recordSourceMappingNameStart(className);\n                this.indenter.increaseIndent();\n\n                if (hasBaseClass) {\n                    baseNameDecl = classDecl.extendsList.members[0];\n                    baseName = baseNameDecl.nodeType == NodeType.Call ? (<CallExpression>baseNameDecl).target : baseNameDecl;\n                    this.emitIndent();\n                    this.writeLineToOutput(\"__extends(\" + className + \", _super);\");\n                }\n\n                this.emitIndent();\n\n                var constrDecl = classDecl.constructorDecl;\n\n                // output constructor\n                if (constrDecl) {\n                    // declared constructor\n                    this.emitJavascript(classDecl.constructorDecl, TokenID.OpenParen, false);\n\n                }\n                else {\n                    var wroteProps = 0;\n\n                    this.recordSourceMappingStart(classDecl);\n                    // default constructor\n                    this.indenter.increaseIndent();\n                    this.writeToOutput(\"function \" + classDecl.name.actualText + \"() {\");\n                    this.recordSourceMappingNameStart(\"constructor\");\n                    if (hasBaseClass) {\n                        this.writeLineToOutput(\"\");\n                        this.emitIndent();\n                        this.writeLineToOutput(\"_super.apply(this, arguments);\");\n                        wroteProps++;\n                    }\n\n                    if (classDecl.varFlags & VarFlags.MustCaptureThis) {\n                        this.writeCaptureThisStatement(classDecl);\n                    }\n\n                    var members = (<ASTList>this.thisClassNode.members).members\n\n                    // output initialized properties\n                    for (var i = 0; i < members.length; i++) {\n                        if (members[i].nodeType == NodeType.VarDecl) {\n                            var varDecl = <VarDecl>members[i];\n                            if (!hasFlag(varDecl.varFlags, VarFlags.Static) && varDecl.init) {\n                                this.writeLineToOutput(\"\");\n                                this.emitIndent();\n                                this.emitJavascriptVarDecl(varDecl, TokenID.Tilde);\n                                wroteProps++;\n                            }\n                        }\n                    }\n                    if (wroteProps) {\n                        this.writeLineToOutput(\"\");\n                        this.indenter.decreaseIndent();\n                        this.emitIndent();\n                        this.writeLineToOutput(\"}\");\n                    }\n                    else {\n                        this.writeLineToOutput(\" }\");\n                        this.indenter.decreaseIndent();\n                    }\n                    this.recordSourceMappingNameEnd();\n                    this.recordSourceMappingEnd(classDecl);\n                }\n\n                var membersLen = classDecl.members.members.length;\n                for (var j = 0; j < membersLen; j++) {\n\n                    var memberDecl: AST = classDecl.members.members[j];\n\n                    if (memberDecl.nodeType == NodeType.FuncDecl) {\n                        var fn = <FuncDecl>memberDecl;\n\n                        if (hasFlag(fn.fncFlags, FncFlags.Method) && !fn.isSignature()) {\n                            if (!hasFlag(fn.fncFlags, FncFlags.Static)) {\n                                this.emitPrototypeMember(fn, className);\n                            }\n                            else { // static functions\n                                if (fn.isAccessor()) {\n                                    this.emitPropertyAccessor(fn, this.thisClassNode.name.actualText, false);\n                                }\n                                else {\n                                    this.emitIndent();\n                                    this.recordSourceMappingStart(fn)\n                                    this.writeToOutput(classDecl.name.actualText + \".\" + fn.name.actualText + \" = \");\n                                    this.emitInnerFunction(fn, (fn.name && !fn.name.isMissing()), true,\n                                            null, Emitter.shouldCaptureThis(fn), null);\n                                    this.writeLineToOutput(\";\");\n                                }\n                            }\n                        }\n                    }\n                    else if (memberDecl.nodeType == NodeType.VarDecl) {\n                        var varDecl = <VarDecl>memberDecl;\n                        if (hasFlag(varDecl.varFlags, VarFlags.Static)) {\n\n                            if (varDecl.init) {\n                                // EMITREVIEW\n                                this.emitIndent();\n                                this.recordSourceMappingStart(varDecl);\n                                this.writeToOutput(classDecl.name.actualText + \".\" + varDecl.id.actualText + \" = \");\n                                this.emitJavascript(varDecl.init, TokenID.Equals, false);\n                                // EMITREVIEW\n\n                                this.writeLineToOutput(\";\");\n                                this.recordSourceMappingEnd(varDecl);\n                            }\n                        }\n                    }\n                    else {\n                        throw Error(\"We want to catch this\");\n                    }\n                }\n\n                this.emitIndent();\n                this.recordSourceMappingStart(classDecl.endingToken);\n                this.writeLineToOutput(\"return \" + className + \";\");\n                this.recordSourceMappingEnd(classDecl.endingToken);\n                this.indenter.decreaseIndent();\n                this.emitIndent();\n                this.recordSourceMappingStart(classDecl.endingToken);\n                this.writeToOutput(\"}\");\n                this.recordSourceMappingNameEnd();\n                this.recordSourceMappingEnd(classDecl.endingToken);\n                this.recordSourceMappingStart(classDecl);\n                this.writeToOutput(\")(\");\n                if (hasBaseClass)\n                    this.emitJavascript(baseName, TokenID.Tilde, false);\n                this.writeToOutput(\");\");\n                this.recordSourceMappingEnd(classDecl);\n\n                if ((temp == EmitContainer.Module || temp == EmitContainer.DynamicModule) && hasFlag(classDecl.varFlags, VarFlags.Exported)) {\n                    this.writeLineToOutput(\"\");\n                    this.emitIndent();\n                    var modName = temp == EmitContainer.Module ? this.moduleName : \"exports\";\n                    this.recordSourceMappingStart(classDecl);\n                    this.writeToOutput(modName + \".\" + className + \" = \" + className + \";\");\n                    this.recordSourceMappingEnd(classDecl);\n                }\n\n                this.emitIndent();\n                this.recordSourceMappingEnd(classDecl);\n                this.emitParensAndCommentsInPlace(classDecl, false);\n                this.setContainer(temp);\n                this.thisClassNode = svClassNode;\n            }\n        }\n\n        public emitPrologue(reqInherits: bool) {\n            if (!this.prologueEmitted) {\n                if (reqInherits) {\n                    this.prologueEmitted = true;\n                    this.writeLineToOutput(\"var __extends = this.__extends || function (d, b) {\");\n                    this.writeLineToOutput(\"    function __() { this.constructor = d; }\");\n                    this.writeLineToOutput(\"    __.prototype = b.prototype;\");\n                    this.writeLineToOutput(\"    d.prototype = new __();\");\n                    this.writeLineToOutput(\"};\");\n                }\n                if (this.checker.mustCaptureGlobalThis) {\n                    this.prologueEmitted = true;\n                    this.writeLineToOutput(this.captureThisStmtString);\n                }\n            }\n        }\n\n        public emitSuperReference() {\n            this.writeToOutput(\"_super.prototype\");\n        }\n\n        public emitSuperCall(callEx: CallExpression): bool {\n            if (callEx.target.nodeType == NodeType.Dot) {\n                var dotNode = <BinaryExpression>callEx.target;\n                if (dotNode.operand1.nodeType == NodeType.Super) {\n                    this.emitJavascript(dotNode, TokenID.OpenParen, false);\n                    this.writeToOutput(\".call(\");\n                    this.emitThis();\n                    if (callEx.arguments && callEx.arguments.members.length > 0) {\n                        this.writeToOutput(\", \");\n                        this.emitJavascriptList(callEx.arguments, \", \", TokenID.Comma, false, false, false);\n                    }\n                    this.writeToOutput(\")\");\n                    return true;\n                }\n            }\n            return false;\n        }\n\n        public emitThis() {\n            if (this.thisFnc && !this.thisFnc.isMethod() && (!this.thisFnc.isConstructor)) {\n                this.writeToOutput(\"_this\");\n            }\n            else {\n                this.writeToOutput(\"this\");\n            }\n        }\n\n        private static shouldCaptureThis(func: FuncDecl): bool {\n            // Super calls use 'this' reference. If super call is in a lambda, 'this' value needs to be captured in the parent.\n            return func.hasSelfReference() || func.hasSuperReferenceInFatArrowFunction();\n        }\n\n        private createFile(fileName: string, useUTF8: bool): ITextWriter {\n            try {\n                return this.emitOptions.ioHost.createFile(fileName, useUTF8);\n            } catch (ex) {\n                this.errorReporter.emitterError(null, ex.message);\n            }\n        }\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    export interface ILineCol {\n        line: number;\n        col: number;\n    }\n\n    export class ErrorReporter {\n        public parser: Parser = null;\n        public checker: TypeChecker = null;\n        public lineCol = { line: 0, col: 0 };\n        public emitAsComments = true;\n        public hasErrors = false;\n        public pushToErrorSink = false;\n        public errorSink: string[] = [];\n\n        constructor (public outfile: ITextWriter) { }\n\n        public getCapturedErrors() { return this.errorSink; }\n        public freeCapturedErrors() { this.errorSink = []; }\n        public captureError(emsg: string) { this.errorSink[this.errorSink.length] = emsg; }\n\n        public setErrOut(outerr) {\n            this.outfile = outerr;\n            this.emitAsComments = false;\n        }\n\n        public emitPrefix() {\n            if (this.emitAsComments) {\n                this.outfile.Write(\"// \");\n            }\n            this.outfile.Write(this.checker.locationInfo.filename + \"(\" + this.lineCol.line + \",\" + this.lineCol.col + \"): \");\n        }\n\n        public writePrefix(ast: AST): void {\n            if (ast) {\n                this.setError(ast);\n            }\n            else {\n                this.lineCol.line = 0;\n                this.lineCol.col = 0;\n            }\n            this.emitPrefix();\n        }\n\n        public writePrefixFromSym(symbol: Symbol): void {\n            if (symbol && this.checker.locationInfo.lineMap) {\n                getSourceLineColFromMap(this.lineCol, symbol.location,\n                                        this.checker.locationInfo.lineMap);\n            }\n            else {\n                this.lineCol.line = -1;\n                this.lineCol.col = -1;\n            }\n            this.emitPrefix();\n        }\n\n        public setError(ast: AST) {\n            if (ast) {\n                ast.flags |= ASTFlags.Error;\n                if (this.checker.locationInfo.lineMap) {\n                    getSourceLineColFromMap(this.lineCol, ast.minChar, this.checker.locationInfo.lineMap);\n                }\n            }\n        }\n\n        public reportError(ast: AST, message: string) {\n            if (this.pushToErrorSink) {\n                this.captureError(message);\n                return;\n            }\n\n            this.hasErrors = true;\n            if (ast && this.parser.errorRecovery && this.parser.errorCallback) {\n                var len = (ast.limChar - ast.minChar);\n                this.parser.errorCallback(ast.minChar, len, message, this.checker.locationInfo.unitIndex);\n            }\n            else {\n                this.writePrefix(ast);\n                this.outfile.WriteLine(message); // Right after the semi-colon\n            }\n        }\n\n        public reportErrorFromSym(symbol: Symbol, message: string) {\n            if (this.pushToErrorSink) {\n                this.captureError(message);\n                return;\n            }\n\n            this.hasErrors = true;\n            if (this.parser.errorRecovery && this.parser.errorCallback) {\n                this.parser.errorCallback(symbol.location, symbol.length, message, this.checker.locationInfo.unitIndex);\n            }\n            else {\n                this.writePrefixFromSym(symbol);\n                this.outfile.WriteLine(message);\n            }\n        }\n\n        public emitterError(ast: AST, message: string) {\n            this.reportError(ast, message);\n            // Emitter errors are not recoverable, stop immediately\n            throw Error(\"EmitError\");\n        }\n\n        public duplicateIdentifier(ast: AST, name: string) {\n            this.reportError(ast, \"Duplicate identifier '\" + name + \"'\");\n        }\n\n        public showRef(ast: AST, text: string, symbol: Symbol) {\n            var defLineCol = { line: -1, col: -1 };\n            // TODO: multiple def locations\n            this.parser.getSourceLineCol(defLineCol, symbol.location);\n            this.reportError(ast, \"symbol \" + text + \" defined at (\" + defLineCol.line + \",\" +\n                              defLineCol.col + \")\");\n        }\n\n        public unresolvedSymbol(ast: AST, name: string) {\n            this.reportError(ast, \"The name '\" + name + \"' does not exist in the current scope\");\n        }\n\n        public symbolDoesNotReferToAValue(ast: AST, name: string): void {\n            this.reportError(ast, \"The name '\" + name + \"' does not refer to a value\");\n        }\n\n        public styleError(ast: AST, msg: string): void {\n            var bkThrow = this.pushToErrorSink;\n            this.pushToErrorSink = false;\n            this.reportError(ast, \"STYLE: \" + msg);\n            this.pushToErrorSink = bkThrow;\n        }\n\n        public simpleError(ast: AST, msg: string): void {\n            this.reportError(ast, msg);\n        }\n\n        public simpleErrorFromSym(sym: Symbol, msg: string): void {\n            this.reportErrorFromSym(sym, msg);\n        }\n\n        public invalidSuperReference(ast: AST) {\n            this.simpleError(ast, \"Keyword 'super' can only be used inside a class instance method\");\n        }\n\n        public valueCannotBeModified(ast: AST) {\n            this.simpleError(ast, \"The left-hand side of an assignment expression must be a variable, property or indexer\");\n        }\n\n        public invalidCall(ast: CallExpression, nodeType: number, scope: SymbolScope): void {\n            var targetType = ast.target.type;\n            var typeName = targetType.getScopedTypeName(scope);\n            if (targetType.construct && (nodeType == NodeType.Call)) {\n                this.reportError(ast, \"Value of type '\" + typeName + \"' is not callable.  Did you mean to include 'new'?\");\n            } else {\n                var catString = (nodeType == NodeType.Call) ? \"callable\" : \"newable\";\n\n                this.reportError(ast, \"Value of type '\" + typeName + \"' is not \" + catString);\n            }\n        }\n\n        public indexLHS(ast: BinaryExpression, scope: SymbolScope): void {\n            var targetType = ast.operand1.type.getScopedTypeName(scope);\n            var indexType = ast.operand2.type.getScopedTypeName(scope);\n            this.simpleError(ast, \"Value of type '\" + targetType + \"' is not indexable by type '\" + indexType + \"'\");\n        }\n\n        public incompatibleTypes(ast: AST, t1: Type, t2: Type, op: string, scope: SymbolScope, comparisonInfo?:TypeComparisonInfo) {\n            if (!t1) {\n                t1 = this.checker.anyType;\n            }\n            if (!t2) {\n                t2 = this.checker.anyType;\n            }\n\n            var reason = comparisonInfo ? comparisonInfo.message : \"\";\n            if (op) {\n                this.reportError(ast, \"Operator '\" + op + \"' cannot be applied to types '\" + t1.getScopedTypeName(scope) +\n                                  \"' and '\" + t2.getScopedTypeName(scope) + \"'\" + (reason ? \": \" + reason : \"\"));\n            }\n            else {\n                this.reportError(ast, \"Cannot convert '\" + t1.getScopedTypeName(scope) +\n                                  \"' to '\" + t2.getScopedTypeName(scope) + \"'\" + (reason ? \": \" + reason : \"\"));\n            }\n        }\n\n        public expectedClassOrInterface(ast: AST): void {\n            this.simpleError(ast, \"Expected var, class, interface, or module\");\n        }\n\n        public unaryOperatorTypeError(ast: AST, op: string, type: Type) {\n            this.reportError(ast, \"Operator '\" + op + \"' cannot be applied to type '\" + type.getTypeName() + \"'\");\n        }\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n\n    export function hasFlag(val: number, flag: number) {\n        return (val & flag) != 0;\n    }\n\n    export enum ErrorRecoverySet {\n        None = 0,\n        Comma = 1, // Comma\n        SColon = 1 << 1, // SColon\n        Asg = 1 << 2, // Asg\n        BinOp = 1 << 3, // Lsh, Rsh, Rs2, Le, Ge, INSTANCEOF, EQ, NE, Eqv, NEqv, LogAnd, LogOr, AsgMul, AsgDiv\n        // AsgMod, AsgAdd, AsgSub, AsgLsh, AsgRsh, AsgRs2, AsgAnd, AsgXor, AsgOr, QMark, Mult, Div, \n        // Pct, GT, LT, And, Xor, Or\n        RBrack = 1 << 4, // RBrack\n        RCurly = 1 << 5, // RCurly\n        RParen = 1 << 6, // RParen\n        Dot = 1 << 7, // Dot\n        Colon = 1 << 8, // Colon\n        PrimType = 1 << 9, // number, string, bool\n        AddOp = 1 << 10, // Add, Sub\n        LCurly = 1 << 11, // LCurly\n        PreOp = 1 << 12, // Tilde, Bang, Inc, Dec\n        RegExp = 1 << 13, // RegExp\n        LParen = 1 << 14, // LParen\n        LBrack = 1 << 15, // LBrack\n        Scope = 1 << 16, // Scope\n        In = 1 << 17, // IN\n        SCase = 1 << 18, // CASE, DEFAULT\n        Else = 1 << 19, // ELSE\n        Catch = 1 << 20, // CATCH, FINALLY\n        Var = 1 << 21, // \n        Stmt = 1 << 22, // BREAK, RETURN, THROW, DEBUGGER, FOR, SWITCH, DO, IF, TRY, WITH\n        While = 1 << 23, // WHILE\n        ID = 1 << 24, // ID\n        Prefix = 1 << 25, // VOID, DELETE, TYPEOF, AWAIT\n        Literal = 1 << 26, // IntCon, FltCon, StrCon\n        RLit = 1 << 27, // THIS, TRUE, FALSE, NULL\n        Func = 1 << 28, // FUNCTION\n        EOF = 1 << 29, // EOF\n\n        // REVIEW: Name this something clearer.\n        TypeScriptS = 1 << 30, // PROPERTY, PRIVATE, STATIC, INTERFACE, CLASS, MODULE, EXPORT, IMPORT\n        ExprStart = SColon | AddOp | LCurly | PreOp | RegExp | LParen | LBrack | ID | Prefix | RLit | Func | Literal,\n        StmtStart = ExprStart | SColon | Var | Stmt | While | TypeScriptS,\n        Postfix = Dot | LParen | LBrack,\n    }\n\n    export enum AllowedElements {\n        None = 0,\n        ModuleDeclarations = 1 << 2,\n        ClassDeclarations = 1 << 3,\n        InterfaceDeclarations = 1 << 4,\n        AmbientDeclarations = 1 << 10,\n        Properties = 1 << 11,\n\n        Global = ModuleDeclarations | ClassDeclarations | InterfaceDeclarations | AmbientDeclarations,\n        QuickParse = Global | Properties,\n    }\n\n    export enum Modifiers {\n        None = 0,\n        Private = 1,\n        Public = 1 << 1,\n        Readonly = 1 << 2,\n        Ambient = 1 << 3,\n        Exported = 1 << 4,\n        Getter = 1 << 5,\n        Setter = 1 << 6,\n        Static = 1 << 7,\n    }\n\n    export enum ASTFlags {\n        None = 0,\n        ExplicitSemicolon = 1, // statment terminated by an explicit semicolon\n        AutomaticSemicolon = 1 << 1, // statment terminated by an automatic semicolon\n        Writeable = 1 << 2,  // node is lhs that can be modified\n        Error = 1 << 3, // node has an error\n        DotLHSPartial = 1 << 4, // node is the lhs of an incomplete dot expr at cursor\n        DotLHS = 1 << 5, // node is the lhs of a dot expr\n        IsStatement = 1 << 6, // node is a statement\n        StrictMode = 1 << 7, // node is in the strict mode environment\n        PossibleOptionalParameter = 1 << 8,\n        ClassBaseConstructorCall = 1 << 9,\n        OptionalName = 1 << 10,\n        // REVIEW: This flag is to mark lambda nodes to note that the LParen of an expression has already been matched in the lambda header.\n        //         The flag is used to communicate this piece of information to the calling parseTerm, which intern will remove it.\n        //         Once we have a better way to associate information with nodes, this flag should not be used.\n        SkipNextRParen = 1 << 11, \n    }\n\n    export enum DeclFlags {\n        None = 0,\n        Exported = 1,\n        Private = 1 << 1,\n        Public = 1 << 2,\n        Ambient = 1 << 3,\n        Static = 1 << 4,\n        LocalStatic = 1 << 5,\n        GetAccessor = 1 << 6,\n        SetAccessor = 1 << 7,\n    }\n\n    export enum ModuleFlags {\n        None = 0,\n        Exported = 1,\n        Private = 1 << 1,\n        Public = 1 << 2,\n        Ambient = 1 << 3,\n        Static = 1 << 4,\n        LocalStatic = 1 << 5,\n        GetAccessor = 1 << 6,\n        SetAccessor = 1 << 7,\n        IsEnum = 1 << 8,\n        ShouldEmitModuleDecl = 1 << 9,\n        IsWholeFile = 1 << 10,\n        IsDynamic = 1 << 11,\n        MustCaptureThis = 1 << 12,\n    }\n\n    export enum SymbolFlags {\n        None = 0,\n        Exported = 1,\n        Private = 1 << 1,\n        Public = 1 << 2,\n        Ambient = 1 << 3,\n        Static = 1 << 4,\n        LocalStatic = 1 << 5,\n        GetAccessor = 1 << 6,\n        SetAccessor = 1 << 7,\n        Property = 1 << 8,\n        Readonly = 1 << 9,\n        ModuleMember = 1 << 10,\n        InterfaceMember = 1 << 11,\n        ClassMember = 1 << 12,\n        BuiltIn = 1 << 13,\n        TypeSetDuringScopeAssignment = 1 << 14,\n        Constant = 1 << 15,\n        Optional = 1 << 16,\n        RecursivelyReferenced = 1 << 17,\n        Bound = 1 << 18,\n        CompilerGenerated = 1 << 19,\n    }\n\n    export enum VarFlags {\n        None = 0,\n        Exported = 1,\n        Private = 1 << 1,\n        Public = 1 << 2,\n        Ambient = 1 << 3,\n        Static = 1 << 4,\n        LocalStatic = 1 << 5,\n        GetAccessor = 1 << 6,\n        SetAccessor = 1 << 7,\n        AutoInit = 1 << 8,\n        Property = 1 << 9,\n        Readonly = 1 << 10,\n        Class = 1 << 11,\n        ClassProperty = 1 << 12,\n        ClassBodyProperty = 1 << 13,\n        ClassConstructorProperty = 1 << 14,\n        ClassSuperMustBeFirstCallInConstructor = 1 << 15,\n        Constant = 1 << 16,\n        MustCaptureThis = 1 << 17,\n    }\n\n    export enum FncFlags {\n        None = 0,\n        Exported = 1,\n        Private = 1 << 1,\n        Public = 1 << 2,\n        Ambient = 1 << 3,\n        Static = 1 << 4,\n        LocalStatic = 1 << 5,\n        GetAccessor = 1 << 6,\n        SetAccessor = 1 << 7,\n        Definition = 1 << 8,\n        Signature = 1 << 9,\n        Method = 1 << 10,\n        HasReturnExpression = 1 << 11,\n        CallMember = 1 << 12,\n        ConstructMember = 1 << 13,\n        HasSelfReference = 1 << 14,\n        IsFatArrowFunction = 1 << 15,\n        IndexerMember = 1 << 16,\n        IsFunctionExpression = 1 << 17,\n        ClassMethod = 1 << 18,\n        ClassPropertyMethodExported = 1 << 19,\n        HasSuperReferenceInFatArrowFunction = 1 << 20,\n        IsPropertyBound = 1 << 21,\n    }\n\n    export enum SignatureFlags {\n        None = 0,\n        IsIndexer = 1,\n        IsStringIndexer = 1 << 1,\n        IsNumberIndexer = 1 << 2,\n    }\n\n    export function ToDeclFlags(fncFlags: FncFlags) : DeclFlags;\n    export function ToDeclFlags(varFlags: VarFlags) : DeclFlags;\n    export function ToDeclFlags(symFlags: SymbolFlags): DeclFlags;\n    export function ToDeclFlags(moduleFlags: ModuleFlags): DeclFlags;\n    export function ToDeclFlags(fncOrVarOrSymbolOrModuleFlags: any) {\n        return <DeclFlags>fncOrVarOrSymbolOrModuleFlags;\n    }\n\n    export enum TypeFlags {\n        None = 0,\n        HasImplementation = 1,\n        HasSelfReference = 1 << 1,\n        MergeResult = 1 << 2,\n        IsEnum = 1 << 3,\n        BuildingName = 1 << 4,\n        HasBaseType = 1 << 5,\n        HasBaseTypeOfObject = 1 << 6,\n        IsClass = 1 << 7,\n    }\n\n    export enum TypeRelationshipFlags {\n        SuccessfulComparison = 0,\n        SourceIsNullTargetIsVoidOrUndefined = 1,\n        RequiredPropertyIsMissing = 1 << 1,\n        IncompatibleSignatures = 1 << 2,\n        SourceSignatureHasTooManyParameters = 3,\n        IncompatibleReturnTypes = 1 << 4,\n        IncompatiblePropertyTypes = 1 << 5,\n        IncompatibleParameterTypes = 1 << 6,\n    }\n\n    export enum CodeGenTarget {\n        ES3 = 0,\n        ES5 = 1,\n    }\n\n    export enum ModuleGenTarget {\n        Synchronous = 0,\n        Asynchronous = 1,\n        Local = 1 << 1,\n    }\n\n    // Compiler defaults to generating ES5-compliant code for\n    //  - getters and setters\n    export var codeGenTarget: CodeGenTarget = CodeGenTarget.ES3;\n\n    export var moduleGenTarget: ModuleGenTarget = ModuleGenTarget.Synchronous;\n\n    export var optimizeModuleCodeGen = true;\n\n    export function flagsToString(e, flags: number): string {\n        var builder = \"\";\n        for (var i = 1; i < (1 << 31) ; i = i << 1) {\n            if ((flags & i) != 0) {\n                for (var k in e) {\n                    if (e[k] == i) {\n                        if (builder.length > 0) {\n                            builder += \"|\";\n                        }\n                        builder += k;\n                        break;\n                    }\n                }\n            }\n        }\n        return builder;\n    }\n\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n\n    export class BlockIntrinsics {\n        public prototype = undefined;\n        public toString = undefined;\n        public toLocaleString = undefined;\n        public valueOf = undefined;\n        public hasOwnProperty = undefined;\n        public propertyIsEnumerable = undefined;\n        public isPrototypeOf = undefined;\n\n        constructor () {\n            // initialize the 'constructor' field\n            this[\"constructor\"] = undefined;\n        }\n    }\n\n    export interface IHashTable {\n        getAllKeys(): string[];\n        add(key: string, data): bool;\n        addOrUpdate(key: string, data): bool;\n        map(fn: (k: string, v, c) => void , context): void;\n        every(fn: (k: string, v, c) => bool, context): bool;\n        some(fn: (k: string, v, c) => bool, context): bool;\n        count(): number;\n        lookup(key: string): any;\n    }\n\n    export class StringHashTable implements IHashTable {\n        public itemCount = 0;\n        public table = <any>(<any> new BlockIntrinsics());\n\n        public getAllKeys(): string[]{\n            var result: string[] = [];\n            for (var k in this.table) {\n                if (this.table[k] != undefined) {\n                    result[result.length] = k;\n                }\n            }\n            return result;\n        }\n\n        public add(key: string, data): bool {\n            if (this.table[key] != undefined) {\n                return false;\n            }\n            this.table[key] = data;\n            this.itemCount++;\n            return true;\n        }\n\n        public addOrUpdate(key: string, data): bool {\n            if (this.table[key] != undefined) {\n                this.table[key] = data;\n                return false;\n            }\n            this.table[key] = data;\n            this.itemCount++;\n            return true;\n        }\n\n        public map(fn: (k: string, v, c) => void , context) {\n            for (var k in this.table) {\n                var data = this.table[k];\n                if (data != undefined) {\n                    fn(k, this.table[k], context);\n                }\n            }\n        }\n\n        public every(fn: (k: string, v, c) => bool, context) {\n            for (var k in this.table) {\n                var data = this.table[k];\n                if (data != undefined) {\n                    if (!fn(k, this.table[k], context)) {\n                        return false;\n                    }\n                }\n            }\n            return true;\n        }\n\n        public some(fn: (k: string, v, c) => bool, context) {\n            for (var k in this.table) {\n                var data = this.table[k];\n                if (data != undefined) {\n                    if (fn(k, this.table[k], context)) {\n                        return true;\n                    }\n                }\n            }\n            return false;\n        }\n\n        public count(): number { return this.itemCount; }\n\n        public lookup(key: string) {\n            var data = this.table[key];\n            if (data != undefined) {\n                return data;\n            }\n            else {\n                return (null);\n            }\n        }\n    }\n\n    // The resident table is expected to reference the same table object, whereas the \n    // transientTable may reference different objects over time\n    // REVIEW:  WARNING:  For performance reasons, neither the primary nor secondary table may be null\n    export class DualStringHashTable implements IHashTable {\n\n        public insertPrimary = true;\n\n        constructor (public primaryTable: IHashTable,\n                                        public secondaryTable: IHashTable) { }\n\n        public getAllKeys(): string[]{\n            return this.primaryTable.getAllKeys().concat(this.secondaryTable.getAllKeys());\n        }\n\n        public add(key: string, data): bool {\n            if (this.insertPrimary) {\n                return this.primaryTable.add(key, data);\n            }\n            else {\n                return this.secondaryTable.add(key, data);\n            }\n        }\n\n        public addOrUpdate(key: string, data): bool {\n            if (this.insertPrimary) {\n                return this.primaryTable.addOrUpdate(key, data);\n            }\n            else {\n                return this.secondaryTable.addOrUpdate(key, data);\n            }\n        }\n\n        public map(fn: (k: string, v, c) => void , context) {\n            this.primaryTable.map(fn, context);\n            this.secondaryTable.map(fn, context);\n        }\n\n        public every(fn: (k: string, v, c) => bool, context) {\n            return this.primaryTable.every(fn, context) && this.secondaryTable.every(fn, context);\n        }\n\n        public some(fn: (k: string, v, c) => bool, context) {\n            return this.primaryTable.some(fn, context) || this.secondaryTable.some(fn, context);\n        }\n\n        public count() {\n            return this.primaryTable.count() + this.secondaryTable.count();\n        }\n\n        public lookup(key: string) {\n            var data = this.primaryTable.lookup(key);\n            if (data != undefined) {\n                return data;\n            }\n            else {\n                return this.secondaryTable.lookup(key);\n            }\n        }\n    }\n\n    export function numberHashFn(key: number): number {\n        var c2 = 0x27d4eb2d; // a prime or an odd constant\n        key = (key ^ 61) ^ (key >>> 16);\n        key = key + (key << 3);\n        key = key ^ (key >>> 4);\n        key = key * c2;\n        key = key ^ (key >>> 15);\n        return key;\n    }\n\n    export function combineHashes(key1: number, key2: number) {\n        return key2 ^ ((key1 >> 5) + key1);\n    }\n\n    export class HashEntry {\n        public next: HashEntry;\n\n        constructor (public key, public data) { }\n    }\n\n    export class HashTable {\n        public itemCount: number = 0;\n        public table = new HashEntry[];\n\n        constructor (public size: number, public hashFn: (key) =>number,\n                    public equalsFn: (key1, key2) =>bool) {\n            for (var i: number = 0; i < this.size; i++) {\n                this.table[i] = null;\n            }\n        }\n\n        public add(key, data): bool {\n            var current: HashEntry;\n            var entry: HashEntry = new HashEntry(key, data);\n            var val: number = this.hashFn(key);\n            val = val % this.size;\n\n            for (current = this.table[val]; current != null ; current = current.next) {\n                if (this.equalsFn(key, current.key)) {\n                    return false;\n                }\n            }\n            entry.next = this.table[val];\n            this.table[val] = entry;\n            this.itemCount++;\n            return true;\n        }\n\n        public remove(key) {\n            var current: HashEntry;\n            var val: number = this.hashFn(key);\n            val = val % this.size;\n            var result = null;\n            var prevEntry: HashEntry = null;\n\n            for (current = this.table[val]; current != null ; current = current.next) {\n                if (this.equalsFn(key, current.key)) {\n                    result = current.data;\n                    this.itemCount--;\n                    if (prevEntry) {\n                        prevEntry.next = current.next;\n                    }\n                    else {\n                        this.table[val] = current.next;\n                    }\n                    break;\n                }\n                prevEntry = current;\n            }\n            return result;\n        }\n\n        public count(): number { return this.itemCount; }\n\n        public lookup(key) {\n            var current: HashEntry;\n            var val: number = this.hashFn(key);\n            val = val % this.size;\n            for (current = this.table[val]; current != null ; current = current.next) {\n                if (this.equalsFn(key, current.key)) {\n                    return (current.data);\n                }\n            }\n            return (null);\n        }\n    }\n\n    // Simple Hash table with list of keys and values matching each other at the given index\n    export class SimpleHashTable {\n        private keys = [];\n        private values = [];\n\n        public lookup(key, findValue?: bool) {\n            var searchArray = this.keys;\n            if (findValue) {\n                searchArray = this.values;\n            }\n\n            for (var i = 0; i < searchArray.length; i++) {\n                if (searchArray[i] == key) {\n                    return {\n                        key: this.keys[i],\n                        data: this.values[i],\n                    };\n                }\n            }\n            return null;\n        }\n\n        public add(key, data): bool {\n            var lookupData = this.lookup(key);\n            if (lookupData) {\n                return false;\n            }\n\n            this.keys[this.keys.length] = key;\n            this.values[this.values.length] = data;\n\n            return true;\n        }\n    }\n\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n\n    export class IncrementalParser {\n        \n        private astLogger: AstLogger;\n\n        constructor (private logger: TypeScript.ILogger) {\n            this.astLogger = new AstLogger(this.logger);\n        }\n\n        //\n        // Return \"null\" if \"editRange\" cannot be safely determined to be inside a single scope.\n        //\n        public getEnclosingScopeContextIfSingleScopeEdit(previousScript: Script, scriptId: string, newSourceText: ISourceText, editRange: ScriptEditRange): EnclosingScopeContext {\n            this.logger.log(\"checkEditsInsideSingleScope(\\\"\" + scriptId + \"\\\")\");\n\n            if (editRange === null) {\n                throw new Error(\"editRange should be valid\");\n            }\n\n            if (editRange.isUnknown()) {\n                this.logger.log(\"  Bailing out because edit range is unknown\");\n                return null;\n            }\n\n            var scope1 = TypeScript.findEnclosingScopeAt(this.logger, previousScript, newSourceText, editRange.minChar, false/*isMemberCompletion*/);\n            var scope2 = TypeScript.findEnclosingScopeAt(this.logger, previousScript, newSourceText, editRange.limChar, false/*isMemberCompletion*/);\n            if (scope1 == null || scope2 == null) {\n                this.logger.log(\"  Bailing out because containing scopes cannot be determined\");\n                return null;\n            }\n\n            // We only support changes within a single containing scope\n            if (scope1.scopeStartAST !== scope2.scopeStartAST) {\n                this.logger.log(\"  Bailing out because edit overlaps 2 disctint scopes\");\n                return null;\n            }\n\n            var newScopeLength = scope1.scopeStartAST.limChar - scope1.scopeStartAST.minChar + editRange.delta;\n            if (newScopeLength <= 0) {\n                this.logger.log(\"  Bailing out because scope has been entirely removed from new source text\");\n                return null;\n            }\n\n            return scope1;\n        }\n\n        public attemptIncrementalUpdateUnit(previousScript: Script, scriptId: string, newSourceText: ISourceText, editRange: ScriptEditRange): UpdateUnitResult {\n            this.logger.log(\"attemptIncrementalUpdateUnit(\\\"\" + scriptId + \"\\\")\");\n\n            if (editRange === null) {\n                throw new Error(\"editRange should be valid\");\n            }\n\n            var scope1 = this.getEnclosingScopeContextIfSingleScopeEdit(previousScript, scriptId, newSourceText, editRange);\n            if (scope1 === null) {\n                return null;\n            }\n\n            var newScopeLength = scope1.scopeStartAST.limChar - scope1.scopeStartAST.minChar + editRange.delta;\n\n            // Heuristic: if the range to reparse is too big, bail out. \n            // This is because a full parse will be faster than an incremental parse followed by all the necessary fix-ups \n            if (newScopeLength >= newSourceText.getLength() / 2) {\n                this.logger.log(\"  Bailing out because range of scope to reparse (\" + newScopeLength + \" characters) is greater than half the size of the source text\");\n                return null;\n            }\n\n            // Capture parsing errors so that they are part of \"updateResult\"\n            var parseErrors: TypeScript.ErrorEntry[] = [];\n            var errorCapture = function(minChar: number, charLen: number, message: string, unitIndex: number): void {\n                parseErrors.push(new TypeScript.ErrorEntry(unitIndex, minChar, minChar + charLen, message));\n            };\n\n            var quickParseResult = TypeScript.quickParse(this.logger, scope1.scopeStartAST, newSourceText, scope1.scopeStartAST.minChar, scope1.scopeStartAST.minChar + newScopeLength, errorCapture);\n            if (quickParseResult.endLexState != TypeScript.LexState.Start) {\n                this.logger.log(\"  Bailing out because scope contains unterminated comment\");\n                return null;\n            }\n\n            var scriptFragment = quickParseResult.Script;\n            if (scriptFragment.vars.members.length !== 0) {\n                this.logger.log(\"  Bailing out because new source text defines variables\");\n                return null;\n            }\n\n            //if (scriptFragment.scopes.members.length !== 1) {\n            //    logger.log(\"  Bailing out because new source text defines more than one scope (or none)\");\n            //    return null;\n            //}\n\n            // This detects adding close curlies, since they have the side effect of having the parser \n            // parse more members in the scope range.\n            if (scriptFragment.bod.members.length !== 1) {\n                this.logger.log(\"  Bailing out because new source text defines more than one scope (or none)\");\n                return null;\n            }\n\n            var oldScope = scope1.scopeStartAST;\n            var newScope = scriptFragment.bod.members[0];\n\n            if (oldScope.nodeType != newScope.nodeType) {\n                this.logger.log(\"  Bailing out because new source text does not define the same scope type as the existing scope\");\n                return null;\n            }\n\n            if (!(<any>oldScope).leftCurlyCount || !(<any>oldScope).rightCurlyCount) {\n                this.logger.log(\"  Bailing out because sopce doesn't have left/right curly count\");\n                return null;\n            }\n\n            if ((<any>oldScope).leftCurlyCount !== (<any>newScope).leftCurlyCount) {\n                this.logger.log(\"  Bailing out because new source text contains more (or fewer) left curly braces\");\n                return null;\n            }\n\n            if ((<any>oldScope).rightCurlyCount !== (<any>newScope).rightCurlyCount) {\n                this.logger.log(\"  Bailing out because new source text contains more (or fewer) right curly braces\");\n                return null;\n            }\n\n            if (newScope.minChar !== 0) {\n                this.logger.log(\"  Bailing out because new function declaration does not start at position 0\");\n                return null;\n            }\n\n            if (newScope.limChar !== newScopeLength) {\n                this.logger.log(\"  Bailing out because new function declaration does not end at the new end position\");\n                return null;\n            }\n\n            return TypeScript.UpdateUnitResult.singleScopeEdits(previousScript, scriptFragment, oldScope, newScope, editRange, parseErrors);\n        }\n\n        public mergeTrees(updateResult: UpdateUnitResult): void {\n            TypeScript.timeFunction(this.logger, \"mergeTrees()\", () => {\n                var editRange = new ScriptEditRange(updateResult.scope1.minChar, updateResult.scope1.limChar, updateResult.editRange.delta);\n                // Update positions in current ast\n                this.applyDeltaPosition(updateResult.script1, editRange.limChar, editRange.delta);\n                // Update positions in new (partial) ast\n                this.applyDeltaPosition(updateResult.script2, 0, editRange.minChar);\n                // Merge linemaps\n                this.mergeLocationInfo(updateResult.script1, updateResult.script2, editRange);\n                //  Replace old AST for scope with new one\n                this.replaceAST(updateResult.script1, updateResult.scope1, updateResult.scope2);\n            });\n        }\n\n        private replaceAST(script: TypeScript.AST, oldAst: TypeScript.AST, newAst: TypeScript.AST) {\n            var pre = (cur: TypeScript.AST, parent: TypeScript.AST, walker: TypeScript.IAstWalker) => {\n                if (cur === oldAst) {\n                    // Transfer comments ownership to new AST. We need this because when \"quick parsing\" the\n                    // new AST, we don't take into account the text before and after the \"minChar/limChar\" pair\n                    // of the scope, which don't include pre/post-comments.\n                    newAst.preComments = cur.preComments;\n                    newAst.postComments = cur.postComments;\n\n                    this.logger.log(\"replaced old AST node with new one in script AST\");\n                    walker.options.stopWalk();\n                    return newAst;\n                }\n\n                // Avoid visiting sub-trees outside of the edit range\n                if (TypeScript.isValidAstNode(cur)) {\n                    if (cur.limChar < oldAst.minChar || cur.minChar > oldAst.limChar) {\n                        walker.options.goChildren = false;\n                    }\n                }\n                return cur;\n            }\n\n            TypeScript.getAstWalkerFactory().walk(script, pre);\n        }\n\n        private mergeLocationInfo(script: TypeScript.Script, partial: TypeScript.Script, editRange: ScriptEditRange) {\n            // Don't merger these fields, as the original script has the right values\n            //script.locationInfo.unitIndex = partial.locationInfo.unitIndex;\n            //script.locationInfo.filename = partial.locationInfo.filename;\n\n            var lineMap1 = script.locationInfo.lineMap;\n            var lineMap2 = partial.locationInfo.lineMap;\n\n            if (this.logger.information()) {\n                this.logger.log(\"lineMap1 (before):\");\n                this.astLogger.logLinemap(lineMap1);\n                this.logger.log(\"lineMap2 (quick parse):\");\n                this.astLogger.logLinemap(lineMap2);\n                this.logger.log(\"EditRange=\" + editRange);\n            }\n\n            // Skip entries < minChar\n            var i1 = 2; // lineMap[0] is always undefined, lineMap[1] is always 0.\n            var i2 = 2; // lineMap[0] is always undefined, lineMap[1] is always 0.\n            var len1 = lineMap1.length;\n            var len2 = lineMap2.length;\n            while (i1 < len1) {\n                if (lineMap1[i1] <= editRange.minChar) {\n                    // Nothing to do for this entry, since it's before the range of the change\n                    i1++;\n                } else if (lineMap1[i1] >= editRange.limChar) {\n                    // Apply delta to this entry, since it's outside the range of the change\n                    lineMap1[i1] += editRange.delta;\n                    i1++;\n                }\n                else {\n                    if (i2 < len2) {\n                        // Add a new entry to lineMap1 corresponding to lineMap2 in new range\n                        lineMap1.splice(i1, 0, lineMap2[i2] + editRange.minChar);\n                        i1++;\n                        len1++;\n                        i2++;\n                    }\n                    else { /* i2 >= len 2 */\n                        // Remove this entry, since there is no corresponding entry in the new map\n                        lineMap1.splice(i1, 1);\n                        len1--;\n                    }\n                }\n            }\n            // Merge the remaining entries in lineMap2 while maintaing the constraint that a lineMap is sorted\n            if (i2 < len2) {\n                // i1 >= len1 && i2 < len2 \n                if (lineMap1[len1 - 1] >= (lineMap2[i2] + editRange.minChar)) {\n                    // lineMap2 needs to be merged within lineMap1\n                    i1 = 2;\n                    while (i1 < len1 && i2 < len2) {\n                        if (lineMap1[i1] < (lineMap2[i2] + editRange.minChar)) {\n                            i1++;\n                        }\n                        else {\n                            lineMap1.splice(i1, 0, lineMap2[i2] + editRange.minChar);\n                            i1++;\n                            len1++;\n                            i2++;\n                        }\n                    }\n                }\n\n                // Append all the remaining entries in lineMap2 to the end of lineMap1\n                for (; i2 < len2; i2++) {\n                    lineMap1.push(lineMap2[i2] + editRange.minChar);\n                }\n            }\n\n            if (this.logger.information()) {\n                this.logger.log(\"lineMap1 (after merge):\");\n                this.astLogger.logLinemap(lineMap1);\n            }\n        }\n\n        private applyDeltaPosition(ast: TypeScript.AST, start: number, delta: number) {\n            var applyDelta = (ast: TypeScript.AST) => {\n                if (ast.minChar !== -1 && ast.minChar >= start) {\n                    ast.minChar += delta;\n                }\n                if (ast.limChar !== -1 && ast.limChar >= start) {\n                    ast.limChar += delta;\n                }\n            }\n\n            var applyDeltaToComments = (comments: TypeScript.Comment[]) => {\n                if (comments && comments.length > 0) {\n                    for (var i = 0; i < comments.length; i++) {\n                        applyDelta(comments[i]);\n                    }\n                }\n            }\n\n            var pre = function(cur: TypeScript.AST, parent: TypeScript.AST, walker: TypeScript.IAstWalker) {\n                // *Before* applying delta to this, check if we need to go to children\n                if (cur.limChar !== -1 && cur.limChar < start) {\n                    walker.options.goChildren = false; // Done with applying Delta for this sub-tree\n                }\n\n                // Apply delta to this node\n                applyDelta(cur);\n                applyDeltaToComments(cur.preComments);\n                applyDeltaToComments(cur.postComments);\n\n                return cur;\n            }\n\n            TypeScript.getAstWalkerFactory().walk(ast, pre);\n        }\n    }\n}\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\ninterface IResolvedFile {\n    content: string;\n    path: string;\n}\n\ninterface IFileWatcher {\n    close(): void;\n}\n\ninterface IIO {\n    readFile(path: string): string;\n    writeFile(path: string, contents: string): void;\n    createFile(path: string, useUTF8?: bool): ITextWriter;\n    deleteFile(path: string): void;\n    dir(path: string, re?: RegExp, options?: { recursive?: bool; }): string[];\n    fileExists(path: string): bool;\n    directoryExists(path: string): bool;\n    createDirectory(path: string): void;\n    resolvePath(path: string): string;\n    dirName(path: string): string;\n    findFile(rootPath: string, partialFilePath: string): IResolvedFile;\n    print(str: string): void;\n    printLine(str: string): void;\n    arguments: string[];\n    stderr: ITextWriter;\n    stdout: ITextWriter;\n    watchFile(filename: string, callback: (string) => void ): IFileWatcher;\n    run(source: string, filename: string): void;\n    getExecutingFilePath(): string;\n    quit(exitCode?: number);\n}\n\nmodule IOUtils {\n    // Creates the directory including its parent if not already present\n    function createDirectoryStructure(ioHost: IIO, dirName: string) {\n        if (ioHost.directoryExists(dirName)) {\n            return;\n        }\n\n        var parentDirectory = ioHost.dirName(dirName);\n        if (parentDirectory != \"\") {\n            createDirectoryStructure(ioHost, parentDirectory);\n        }\n        ioHost.createDirectory(dirName);\n    }\n\n    // Creates a file including its directory structure if not already present\n    export function createFileAndFolderStructure(ioHost: IIO, fileName: string, useUTF8?: bool) {\n        var path = ioHost.resolvePath(fileName);\n        var dirName = ioHost.dirName(path);\n        createDirectoryStructure(ioHost, dirName);\n        return ioHost.createFile(path, useUTF8);\n    }\n\n    export function throwIOError(message: string, error: Error) {\n        var errorMessage = message;\n        if (error && error.message) {\n            errorMessage += (\" \" + error.message);\n        }\n        throw new Error(errorMessage);\n    }\n}\n\n// Declare dependencies needed for all supported hosts\ndeclare class Enumerator {\n    public atEnd(): bool;\n    public moveNext();\n    public item(): any;\n    constructor (o: any);\n}\ndeclare function setTimeout(callback: () =>void , ms?: number);\ndeclare var require: any;\ndeclare module process {\n    export var argv: string[];\n    export var platform: string;\n    export function on(event: string, handler: (any) => void ): void;\n    export module stdout {\n        export function write(str: string);\n    }\n    export module stderr {\n        export function write(str: string);\n    }\n    export module mainModule {\n        export var filename: string;\n    }\n    export function exit(exitCode?: number);\n}\n\nvar IO = (function() {\n\n    // Create an IO object for use inside WindowsScriptHost hosts\n    // Depends on WSCript and FileSystemObject\n    function getWindowsScriptHostIO(): IIO {\n        var fso = new ActiveXObject(\"Scripting.FileSystemObject\");\n        var streamObjectPool = [];\n\n        function getStreamObject(): any { \n            if (streamObjectPool.length > 0) {\n                return streamObjectPool.pop();\n            }  else {\n                return new ActiveXObject(\"ADODB.Stream\");\n            }\n        }\n\n        function releaseStreamObject(obj: any) { \n            streamObjectPool.push(obj);\n        }\n\n        var args = [];\n        for (var i = 0; i < WScript.Arguments.length; i++) {\n            args[i] = WScript.Arguments.Item(i);\n        }\n\n        return {\n            readFile: function(path) {\n                try {\n                    var streamObj = getStreamObject();\n                    streamObj.Open();\n                    streamObj.Type = 2; // Text data\n                    streamObj.Charset = 'x-ansi'; // Assume we are reading ansi text\n                    streamObj.LoadFromFile(path);\n                    var bomChar = streamObj.ReadText(2); // Read the BOM char\n                    streamObj.Position = 0; // Position has to be at 0 before changing the encoding\n                    if ((bomChar.charCodeAt(0) == 0xFE && bomChar.charCodeAt(1) == 0xFF)\n                        || (bomChar.charCodeAt(0) == 0xFF && bomChar.charCodeAt(1) == 0xFE)) {\n                        streamObj.Charset = 'unicode';\n                    } else if (bomChar.charCodeAt(0) == 0xEF && bomChar.charCodeAt(1) == 0xBB) {\n                        streamObj.Charset = 'utf-8'; \n                    }\n\n                    // Read the whole file\n                    var str = streamObj.ReadText(-1 /* read from the current position to EOS */);\n                    streamObj.Close();\n                    releaseStreamObject(streamObj);\n                    return <string>str;\n                }\n                catch (err) {\n                    IOUtils.throwIOError(\"Error reading file \\\"\" + path + \"\\\".\", err);\n                }\n            },\n\n            writeFile: function(path, contents) {\n                var file = this.createFile(path);\n                file.Write(contents);\n                file.Close();\n            },\n\n            fileExists: function(path: string): bool {\n                return fso.FileExists(path);\n            },\n\n            resolvePath: function(path: string): string {\n                return fso.GetAbsolutePathName(path);\n            },\n\n            dirName: function(path: string): string {\n                return fso.GetParentFolderName(path);\n            },\n\n            findFile: function(rootPath: string, partialFilePath: string): IResolvedFile {\n                var path = fso.GetAbsolutePathName(rootPath) + \"/\" + partialFilePath;\n\n                while (true) {\n                    if (fso.FileExists(path)) {\n                        try {\n                            var content = this.readFile(path);\n                            return { content: content, path: path };\n                        }\n                        catch (err) {\n                            //Tools.CompilerDiagnostics.debugPrint(\"Could not find \" + path + \", trying parent\");\n                        }\n                    }\n                    else {\n                        rootPath = fso.GetParentFolderName(fso.GetAbsolutePathName(rootPath));\n\n                        if (rootPath == \"\") {\n                            return null;\n                        }\n                        else {\n                            path = fso.BuildPath(rootPath, partialFilePath);\n                        }\n                    }\n                }\n            },\n\n            deleteFile: function(path: string): void {\n                try {\n                    if (fso.FileExists(path)) {\n                        fso.DeleteFile(path, true); // true: delete read-only files\n                    }\n                } catch (e) {\n                    IOUtils.throwIOError(\"Couldn't delete file '\" + path + \"'.\", e);\n                }\n            },\n\n            createFile: function (path, useUTF8?) {\n                try {\n                    var streamObj = getStreamObject();\n                    streamObj.Charset = useUTF8 ? 'utf-8' : 'x-ansi';\n                    streamObj.Open();\n                    return {\n                        Write: function (str) { streamObj.WriteText(str, 0); },\n                        WriteLine: function (str) { streamObj.WriteText(str, 1); },\n                        Close: function() {\n                            try {\n                                streamObj.SaveToFile(path, 2);\n                            } catch (saveError) {\n                                IOUtils.throwIOError(\"Couldn't write to file '\" + path + \"'.\", saveError);\n                            }\n                            finally {\n                                if (streamObj.State != 0 /*adStateClosed*/) {\n                                    streamObj.Close();\n                                }\n                                releaseStreamObject(streamObj);\n                            }\n                        }\n                    };\n                } catch (creationError) {\n                    IOUtils.throwIOError(\"Couldn't write to file '\" + path + \"'.\", creationError);\n                }\n            },\n\n            directoryExists: function(path) {\n                return <bool>fso.FolderExists(path);\n            },\n\n            createDirectory: function(path) {\n                try {\n                    if (!this.directoryExists(path)) {\n                        fso.CreateFolder(path);\n                    }\n                } catch (e) {\n                    IOUtils.throwIOError(\"Couldn't create directory '\" + path + \"'.\", e);\n                }\n            },\n\n            dir: function(path, spec?, options?) {\n                options = options || <{ recursive?: bool; }>{};\n                function filesInFolder(folder, root): string[]{\n                    var paths = [];\n                    var fc: Enumerator;\n\n                    if (options.recursive) {\n                        fc = new Enumerator(folder.subfolders);\n\n                        for (; !fc.atEnd() ; fc.moveNext()) {\n                            paths = paths.concat(filesInFolder(fc.item(), root + \"/\" + fc.item().Name));\n                        }\n                    }\n\n                    fc = new Enumerator(folder.files);\n\n                    for (; !fc.atEnd() ; fc.moveNext()) {\n                        if (!spec || fc.item().Name.match(spec)) {\n                            paths.push(root + \"/\" + fc.item().Name);\n                        }\n                    }\n\n                    return paths;\n                }\n\n                var folder = fso.GetFolder(path);\n                var paths = [];\n\n                return filesInFolder(folder, path);\n            },\n\n            print: function(str) {\n                WScript.StdOut.Write(str);\n            },\n\n            printLine: function(str) {\n                WScript.Echo(str);\n            },\n\n            arguments: <string[]>args,\n            stderr: WScript.StdErr,\n            stdout: WScript.StdOut,\n            watchFile: null,\n            run: function(source, filename) {\n                try {\n                    eval(source);\n                } catch (e) {\n                    IOUtils.throwIOError(\"Error while executing file '\" + filename + \"'.\", e);\n                }\n            },\n            getExecutingFilePath: function () {\n                return WScript.ScriptFullName;\n            },\n            quit: function (exitCode? : number = 0) {\n                try {\n                    WScript.Quit(exitCode);\n                } catch (e) {\n                }\n            }\n        }\n\n    };\n\n    // Create an IO object for use inside Node.js hosts\n    // Depends on 'fs' and 'path' modules\n    function getNodeIO(): IIO {\n\n        var _fs = require('fs');\n        var _path = require('path');\n        var _module = require('module');\n\n        return {\n            readFile: function(file) {\n                try {\n                    var buffer = _fs.readFileSync(file);\n                    switch (buffer[0]) {\n                        case 0xFE:\n                            if (buffer[1] == 0xFF) {\n                                // utf16-be. Reading the buffer as big endian is not supported, so convert it to \n                                // Little Endian first\n                                var i = 0;\n                                while ((i + 1) < buffer.length) {\n                                    var temp = buffer[i]\n                                    buffer[i] = buffer[i + 1];\n                                    buffer[i + 1] = temp;\n                                    i += 2;\n                                }\n                                return buffer.toString(\"ucs2\", 2);\n                            }\n                            break;\n                        case 0xFF:\n                            if (buffer[1] == 0xFE) {\n                                // utf16-le \n                                return buffer.toString(\"ucs2\", 2);\n                            }\n                            break;\n                        case 0xEF:\n                            if (buffer[1] == 0xBB) {\n                                // utf-8\n                                return buffer.toString(\"utf8\", 3);\n                            }\n                    }\n                    // Default behaviour\n                    return buffer.toString();\n                } catch (e) {\n                    IOUtils.throwIOError(\"Error reading file \\\"\" + file + \"\\\".\", e);\n                }\n            },\n            writeFile: <(path: string, contents: string) => void >_fs.writeFileSync,\n            deleteFile: function(path) {\n                try {\n                    _fs.unlinkSync(path);\n                } catch (e) {\n                    IOUtils.throwIOError(\"Couldn't delete file '\" + path + \"'.\", e);\n                }\n            },\n            fileExists: function(path): bool {\n                return _fs.existsSync(path);\n            },\n            createFile: function(path, useUTF8?) {\n                function mkdirRecursiveSync(path) {\n                    var stats = _fs.statSync(path);\n                    if (stats.isFile()) {\n                        IOUtils.throwIOError(\"\\\"\" + path + \"\\\" exists but isn't a directory.\", null);\n                    } else if (stats.isDirectory()) {\n                        return;\n                    } else {\n                        mkdirRecursiveSync(_path.dirname(path));\n                        _fs.mkdirSync(path, 0775);\n                    }\n                }\n\n                mkdirRecursiveSync(_path.dirname(path));\n\n                try {\n                    var fd = _fs.openSync(path, 'w');\n                } catch (e) {\n                    IOUtils.throwIOError(\"Couldn't write to file '\" + path + \"'.\", e);\n                }\n                return {\n                    Write: function(str) { _fs.writeSync(fd, str); },\n                    WriteLine: function(str) { _fs.writeSync(fd, str + '\\r\\n'); },\n                    Close: function() { _fs.closeSync(fd); fd = null; }\n                };\n            },\n            dir: function dir(path, spec?, options?) {\n                options = options || <{ recursive?: bool; }>{};\n\n                function filesInFolder(folder: string): string[]{\n                    var paths = [];\n\n                    var files = _fs.readdirSync(folder);\n                    for (var i = 0; i < files.length; i++) {\n                        var stat = _fs.statSync(folder + \"/\" + files[i]);\n                        if (options.recursive && stat.isDirectory()) {\n                            paths = paths.concat(filesInFolder(folder + \"/\" + files[i]));\n                        } else if (stat.isFile() && (!spec || files[i].match(spec))) {\n                            paths.push(folder + \"/\" + files[i]);\n                        }\n                    }\n\n                    return paths;\n                }\n\n                return filesInFolder(path);\n            },\n            createDirectory: function(path: string): void {\n                try {\n                    if (!this.directoryExists(path)) {\n                        _fs.mkdirSync(path);\n                    }\n                } catch (e) {\n                    IOUtils.throwIOError(\"Couldn't create directory '\" + path + \"'.\", e);\n                }\n            },\n\n            directoryExists: function(path: string): bool {\n                return _fs.existsSync(path) && _fs.lstatSync(path).isDirectory();\n            },\n            resolvePath: function(path: string): string {\n                return _path.resolve(path);\n            },\n            dirName: function(path: string): string {\n                return _path.dirname(path);\n            },\n            findFile: function(rootPath: string, partialFilePath): IResolvedFile {\n                var path = rootPath + \"/\" + partialFilePath;\n\n                while (true) {\n                    if (_fs.existsSync(path)) {\n                        try {\n                            var content = this.readFile(path);\n                            return { content: content, path: path };\n                        } catch (err) {\n                            //Tools.CompilerDiagnostics.debugPrint((\"Could not find \" + path) + \", trying parent\");\n                        }\n                    }\n                    else {\n                        var parentPath = _path.resolve(rootPath, \"..\");\n\n                        // Node will just continue to repeat the root path, rather than return null\n                        if (rootPath === parentPath) {\n                            return null;\n                        }\n                        else {\n                            rootPath = parentPath;\n                            path = _path.resolve(rootPath, partialFilePath);\n                        }\n                    }\n                }\n            },\n            print: function(str) { process.stdout.write(str) },\n            printLine: function(str) { process.stdout.write(str + '\\n') },\n            arguments: process.argv.slice(2),\n            stderr: {\n                Write: function(str) { process.stderr.write(str); },\n                WriteLine: function(str) { process.stderr.write(str + '\\n'); },\n                Close: function() { }\n            },\n            stdout: {\n                Write: function(str) { process.stdout.write(str); },\n                WriteLine: function(str) { process.stdout.write(str + '\\n'); },\n                Close: function() { }\n            },\n            watchFile: function(filename: string, callback: (string) => void ): IFileWatcher {\n                var firstRun = true;\n                var processingChange = false;\n\n                var fileChanged: any = function(curr, prev) {\n                    if (!firstRun) {\n                        if (curr.mtime < prev.mtime) {\n                            return;\n                        }\n\n                        _fs.unwatchFile(filename, fileChanged);\n                        if (!processingChange) {\n                            processingChange = true;\n                            callback(filename);\n                            setTimeout(function() { processingChange = false; }, 100);\n                        }\n                    }\n                    firstRun = false;\n                    _fs.watchFile(filename, { persistent: true, interval: 500 }, fileChanged);\n                };\n\n                fileChanged();\n                return {\n                    filename: filename,\n                    close: function() {\n                        _fs.unwatchFile(filename, fileChanged);\n                    }\n                };\n            },\n            run: function(source, filename) {\n                require.main.filename = filename;\n                require.main.paths = _module._nodeModulePaths(_path.dirname(_fs.realpathSync(filename)));\n                require.main._compile(source, filename);\n            }, \n            getExecutingFilePath: function () {\n                return process.mainModule.filename;\n            },\n            quit: process.exit\n        }\n    };\n\n    if (typeof ActiveXObject === \"function\")\n        return getWindowsScriptHostIO();\n    else if (typeof require === \"function\")\n        return getNodeIO();\n    else\n        return null; // Unsupported host\n})();\n//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path='typescript.ts' />\n\nmodule TypeScript {\n    // Note: Any addition to the NodeType should also be supported with addition to AstWalkerDetailCallback\n    export enum NodeType {\n        None,\n        Empty,\n        EmptyExpr,\n        True,\n        False,\n        This,\n        Super,\n        QString,\n        Regex,\n        Null,\n        ArrayLit,\n        ObjectLit,\n        Void,\n        Comma,\n        Pos,\n        Neg,\n        Delete,\n        Await,\n        In,\n        Dot,\n        From,\n        Is,\n        InstOf,\n        Typeof,\n        NumberLit,\n        Name,\n        TypeRef,\n        Index,\n        Call,\n        New,\n        Asg,\n        AsgAdd,\n        AsgSub,\n        AsgDiv,\n        AsgMul,\n        AsgMod,\n        AsgAnd,\n        AsgXor,\n        AsgOr,\n        AsgLsh,\n        AsgRsh,\n        AsgRs2,\n        ConditionalExpression,\n        LogOr,\n        LogAnd,\n        Or,\n        Xor,\n        And,\n        Eq,\n        Ne,\n        Eqv,\n        NEqv,\n        Lt,\n        Le,\n        Gt,\n        Ge,\n        Add,\n        Sub,\n        Mul,\n        Div,\n        Mod,\n        Lsh,\n        Rsh,\n        Rs2,\n        Not,\n        LogNot,\n        IncPre,\n        DecPre,\n        IncPost,\n        DecPost,\n        TypeAssertion,\n        FuncDecl,\n        Member,\n        VarDecl,\n        ArgDecl,\n        Return,\n        Break,\n        Continue,\n        Throw,\n        For,\n        ForIn,\n        If,\n        While,\n        DoWhile,\n        Block,\n        Case,\n        Switch,\n        Try,\n        TryCatch,\n        TryFinally,\n        Finally,\n        Catch,\n        List,\n        Script,\n        ClassDeclaration,\n        InterfaceDeclaration,\n        ModuleDeclaration,\n        ImportDeclaration,\n        With,\n        Label,\n        LabeledStatement,\n        EBStart,\n        GotoEB,\n        EndCode,\n        Error,\n        Comment,\n        Debugger,\n        GeneralNode = FuncDecl,\n        LastAsg = AsgRs2,\n    }\n}//\n// Copyright (c) Microsoft Corporation.  All rights reserved.\n// \n// Licensed under the Apache License, Version 2.0 (the \"License\");\n// you may not use this file except in compliance with the License.\n// You may obtain a copy of the License at\n//   http://www.apache.org/licenses/LICENSE-2.0\n//\n// Unless required by applicable law or agreed to in writing, software\n// distributed under the License is distributed on an \"AS IS\" BASIS,\n// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n// See the License for the specific language governing permissions and\n// limitations under the License.\n//\n\n///<reference path=\"io.ts\" />\n\ninterface IOptions {\n    name?: string;\n    flag?: bool;\n    short?: string;\n    usage?: string;\n    set?: (s: string) => void;\n    type?: string;\n    experimental?: bool;\n}\n\nclass OptionsParser {\n    private DEFAULT_SHORT_FLAG = \"-\";\n    private DEFAULT_LONG_FLAG = \"--\";\n\n    // Find the option record for the given string. Returns null if not found.\n    private findOption(arg: string) {\n\n        for (var i = 0; i < this.options.length; i++) {\n\n            if (arg === this.options[i].short || arg === this.options[i].name) {\n                return this.options[i];\n            }\n        }\n\n        return null;\n    }\n\n    public unnamed: string[] = [];\n\n    public options: IOptions[] = [];\n\n    constructor (public host: IIO) {\n    }\n\n    public printUsage() {\n        this.host.printLine(\"Syntax:   tsc [options] [file ..]\");\n        this.host.printLine(\"\");\n        this.host.printLine(\"Examples: tsc hello.ts\");\n        this.host.printLine(\"          tsc --out foo.js foo.ts\");\n        this.host.printLine(\"          tsc @args.txt\");\n        this.host.printLine(\"\");\n        this.host.printLine(\"Options:\");\n\n        var output = [];\n        var maxLength = 0;\n\n        this.options = this.options.sort(function(a, b) {\n            var aName = a.name.toLowerCase();\n            var bName = b.name.toLowerCase();\n\n            if (aName > bName) {\n                return 1;\n            } else if (aName < bName) {\n                return -1;\n            } else {\n                return 0;\n            }\n        });\n\n        // Build up output array\n        for (var i = 0; i < this.options.length; i++) {\n            var option = this.options[i];\n\n            if (option.experimental) {\n                continue;\n            }\n\n            if (!option.usage) {\n                break;\n            }\n\n            var usageString = \"  \";\n            var type = option.type ? \" \" + option.type.toUpperCase() : \"\";\n\n            if (option.short) {\n                usageString += this.DEFAULT_SHORT_FLAG + option.short + type + \", \";\n            }\n\n            usageString += this.DEFAULT_LONG_FLAG + option.name + type;\n\n            output.push([usageString, option.usage]);\n\n            if (usageString.length > maxLength) {\n                maxLength = usageString.length;\n            }\n        }\n\n        output.push([\"  @<file>\", \"Insert command line options and files from a file.\"]);\n\n        // Print padded output\n        for (var i = 0; i < output.length; i++) {\n            this.host.printLine(output[i][0] + (new Array(maxLength - output[i][0].length + 3)).join(\" \") + output[i][1]);\n        }\n    }\n\n    public option(name: string, config: IOptions, short?: string) {\n        if (!config) {\n            config = <any>short;\n            short = null;\n        }\n\n        config.name = name;\n        config.short = short;\n        config.flag = false;\n\n        this.options.push(config);\n    }\n\n    public flag(name: string, config: IOptions, short?: string) {\n        if (!config) {\n            config = <any>short;\n            short = null;\n        }\n\n        config.name = name;\n        config.short = short;\n        config.flag = true\n\n        this.options.push(config);\n    }\n\n    // Parse an arguments str