import { CompiledProgram, CompiledBlock } from './compiled/blocks';
import OpcodeBuilder from './compiled/opcodes/builder';
import Environment from './environment';
import { Option } from '@glimmer/util';
import { SerializedTemplateBlock, TemplateMeta, SerializedBlock, Statement as SerializedStatement } from '@glimmer/wire-format';
import * as WireFormat from '@glimmer/wire-format';
import { Opaque, SymbolTable, ProgramSymbolTable } from '@glimmer/interfaces';
export declare type DeserializedStatement = WireFormat.Statement | WireFormat.Statements.Attribute | WireFormat.Statements.Argument;
export declare function compileStatement(statement: BaselineSyntax.AnyStatement, builder: OpcodeBuilder): void;
export declare class Template {
    statements: BaselineSyntax.AnyStatement[];
    symbolTable: SymbolTable;
    constructor(statements: BaselineSyntax.AnyStatement[], symbolTable: SymbolTable);
}
export declare class Layout extends Template {
    symbolTable: ProgramSymbolTable;
}
export declare class EntryPoint extends Template {
    private compiled;
    symbolTable: ProgramSymbolTable;
    compile(env: Environment): CompiledProgram;
}
export declare class InlineBlock extends Template {
    private compiled;
    splat(builder: OpcodeBuilder): void;
    compile(env: Environment): CompiledBlock;
}
export declare class PartialBlock extends Template {
    private compiled;
    symbolTable: ProgramSymbolTable;
    compile(env: Environment): CompiledProgram;
}
export default class Scanner {
    private block;
    private meta;
    private env;
    constructor(block: SerializedTemplateBlock, meta: TemplateMeta, env: Environment);
    scanEntryPoint(): EntryPoint;
    scanLayout(): Layout;
    scanPartial(symbolTable: SymbolTable): PartialBlock;
}
export declare function scanBlock({statements}: SerializedBlock, symbolTable: SymbolTable, env: Environment): InlineBlock;
import { PublicVM } from './vm';
import { PathReference } from '@glimmer/reference';
export declare namespace BaselineSyntax {
    import Core = WireFormat.Core;
    type ScannedComponent = [number, string, RawInlineBlock, WireFormat.Core.Hash, Option<RawInlineBlock>];
    const isScannedComponent: (value: any[]) => value is [number, string, RawInlineBlock, Option<[string[], WireFormat.Expressions.Expression[]]>, Option<RawInlineBlock>];
    import Params = WireFormat.Core.Params;
    import Hash = WireFormat.Core.Hash;
    type Block = InlineBlock;
    type OpenPrimitiveElement = [number, string, string[]];
    const isPrimitiveElement: (value: any[]) => value is [number, string, string[]];
    type OptimizedAppend = [number, WireFormat.Expression, boolean];
    const isOptimizedAppend: (value: any[]) => value is [number, WireFormat.Expressions.Expression, boolean];
    type UnoptimizedAppend = [number, WireFormat.Expression, boolean];
    const isUnoptimizedAppend: (value: any[]) => value is [number, WireFormat.Expressions.Expression, boolean];
    type AnyDynamicAttr = [number, string, WireFormat.Expression, Option<string>, boolean];
    const isAnyAttr: (value: any[]) => value is [number, string, WireFormat.Expressions.Expression, string | null, boolean];
    type StaticPartial = [number, string];
    const isStaticPartial: (value: any[]) => value is [number, string];
    type DynamicPartial = [number, WireFormat.Expression];
    const isDynamicPartial: (value: any[]) => value is [number, WireFormat.Expressions.Expression];
    type FunctionExpressionCallback<T> = (VM: PublicVM, symbolTable: SymbolTable) => PathReference<T>;
    type FunctionExpression = [number, FunctionExpressionCallback<Opaque>];
    const isFunctionExpression: (value: any[]) => value is [number, FunctionExpressionCallback<void | {} | null | undefined>];
    type NestedBlock = [number, WireFormat.Core.Path, WireFormat.Core.Params, WireFormat.Core.Hash, Option<Block>, Option<Block>];
    const isNestedBlock: (value: any[]) => value is [number, string[], WireFormat.Expressions.Expression[], Option<[string[], WireFormat.Expressions.Expression[]]>, Option<InlineBlock>, Option<InlineBlock>];
    type ScannedBlock = [number, Core.Path, Core.Params, Core.Hash, Option<RawInlineBlock>, Option<RawInlineBlock>];
    const isScannedBlock: (value: any[]) => value is [number, string[], WireFormat.Expressions.Expression[], Option<[string[], WireFormat.Expressions.Expression[]]>, Option<RawInlineBlock>, Option<RawInlineBlock>];
    type Debugger = [number];
    const isDebugger: (value: any[]) => value is [number];
    type Args = [Params, Hash, Option<Block>, Option<Block>];
    namespace NestedBlock {
        function defaultBlock(sexp: NestedBlock): Option<InlineBlock>;
        function inverseBlock(sexp: NestedBlock): Option<InlineBlock>;
        function params(sexp: NestedBlock): WireFormat.Core.Params;
        function hash(sexp: NestedBlock): WireFormat.Core.Hash;
    }
    type Statement = ScannedComponent | OpenPrimitiveElement | OptimizedAppend | UnoptimizedAppend | StaticPartial | DynamicPartial | AnyDynamicAttr | NestedBlock | ScannedBlock | Debugger;
    type AnyStatement = Statement | WireFormat.Statement;
    type AnyExpression = FunctionExpression | WireFormat.Expression;
    type Program = AnyStatement[];
}
export declare class RawInlineBlock {
    private env;
    private table;
    private statements;
    constructor(env: Environment, table: SymbolTable, statements: SerializedStatement[]);
    scan(): InlineBlock;
    private specializeBlock(block);
    private specializeComponent(sexp);
    child(block: Option<SerializedBlock>): Option<RawInlineBlock>;
}
