/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef AST_H_

#define AST_H_

#include <android-base/macros.h>
#include <map>
#include <set>
#include <string>
#include <vector>

#include "FQName.h"
#include "Type.h"

namespace android {

struct Coordinator;
struct Formatter;
struct Interface;
struct Location;
struct Method;
struct NamedType;
struct TypedVar;
struct Scope;
struct EnumValue;

struct AST {
    AST(Coordinator *coordinator, const std::string &path);
    ~AST();

    bool setPackage(const char *package);
    bool addImport(const char *import);

    // package and version really.
    FQName package() const;
    bool isInterface(std::string *ifaceName) const;
    bool containsInterfaces() const;

    void enterScope(Scope *container);
    void leaveScope();
    Scope *scope();

    // Returns true iff successful.
    bool addTypeDef(const char *localName, Type *type, const Location &location,
            std::string *errorMsg);

    // Returns true iff successful.
    bool addScopedType(NamedType *type, std::string *errorMsg);

    void *scanner();
    void setScanner(void *scanner);

    const std::string &getFilename() const;

    // Look up an enum value by "FQName:valueName".
    EnumValue *lookupEnumValue(const FQName &fqName, std::string *errorMsg);

    // Look up a type by FQName, "pure" names, i.e. those without package
    // or version are first looked up in the current scope chain.
    // After that lookup proceeds to imports.
    Type *lookupType(const FQName &fqName);

    void addImportedAST(AST *ast);

    status_t generateCpp(const std::string &outputPath) const;
    status_t generateCppImpl(const std::string &outputPath) const;

    status_t generateJava(
            const std::string &outputPath,
            const std::string &limitToType) const;

    status_t generateJavaTypes(
            const std::string &outputPath,
            const std::string &limitToType) const;

    void getImportedPackages(std::set<FQName> *importSet) const;

    // Run getImportedPackages on this, then run getImportedPackages on
    // each AST in each package referenced in importSet.
    void getImportedPackagesHierarchy(std::set<FQName> *importSet) const;

    status_t generateVts(const std::string &outputPath) const;

    bool isJavaCompatible() const;

    // Return the set of FQNames for those interfaces and types that are
    // actually referenced in the AST, not merely imported.

    const std::set<FQName>& getImportedNames() const {
        return mImportedNames;
    }

    void appendToExportedTypesVector(
            std::vector<const Type *> *exportedTypes) const;

    // used by the parser.
    void addSyntaxError();
    size_t syntaxErrors() const;

    bool isIBase() const;

private:
    Coordinator *mCoordinator;
    std::string mPath;
    std::vector<Scope *> mScopePath;

    void *mScanner;
    Scope *mRootScope;

    FQName mPackage;

    // A set of all external interfaces/types that are _actually_ referenced
    // in this AST, this is a subset of those specified in import statements.
    std::set<FQName> mImportedNames;

    // A set of all ASTs we explicitly or implicitly (types.hal) import.
    std::set<AST *> mImportedASTs;

    // If a single type (instead of the whole AST) is imported, the AST will be
    // present as a key to this map, with the value being a list of types
    // imported from this AST. If an AST appears in mImportedASTs but not in
    // mImportedTypes, then the whole AST is imported.
    std::map<AST *, std::set<Type *>> mImportedTypes;

    // Types keyed by full names defined in this AST.
    std::map<FQName, Type *> mDefinedTypesByFullName;

    // used by the parser.
    size_t mSyntaxErrors = 0;

    bool addScopedTypeInternal(
            NamedType *type,
            std::string *errorMsg);

    // Find a type matching fqName (which may be partial) and if found
    // return the associated type and fill in the full "matchingName".
    // Only types defined in this very AST are considered.
    Type *findDefinedType(const FQName &fqName, FQName *matchingName) const;

    void getPackageComponents(std::vector<std::string> *components) const;

    void getPackageAndVersionComponents(
            std::vector<std::string> *components, bool cpp_compatible) const;

    static void generateCppPackageInclude(
            Formatter &out,
            const FQName &package,
            const std::string &klass);

    std::string makeHeaderGuard(const std::string &baseName,
                                bool indicateGenerated = true) const;
    void enterLeaveNamespace(Formatter &out, bool enter) const;

    static void generateCheckNonNull(Formatter &out, const std::string &nonNull);

    status_t generateInterfaceHeader(const std::string &outputPath) const;
    status_t generateHwBinderHeader(const std::string &outputPath) const;
    status_t generateStubHeader(const std::string &outputPath) const;
    status_t generateProxyHeader(const std::string &outputPath) const;
    status_t generateAllSource(const std::string &outputPath) const;
    status_t generatePassthroughHeader(const std::string &outputPath) const;

    status_t generateTypeSource(
            Formatter &out, const std::string &ifaceName) const;

    // a method, and in which interface is it originally defined.
    // be careful of the case where method.isHidlReserved(), where interface
    // is effectively useless.
    using MethodGenerator = std::function<status_t(const Method *, const Interface *)>;

    status_t generateStubImplHeader(const std::string &outputPath) const;
    status_t generateStubImplSource(const std::string &outputPath) const;

    status_t generateMethods(Formatter &out, MethodGenerator gen) const;
    status_t generateStubImplMethod(Formatter &out,
                                    const std::string &className,
                                    const Method *method) const;
    status_t generatePassthroughMethod(Formatter &out,
                                       const Method *method) const;
    status_t generateProxyMethodSource(Formatter &out,
                                       const std::string &className,
                                       const Method *method,
                                       const Interface *superInterface) const;

    void generateFetchSymbol(Formatter &out, const std::string &ifaceName) const;

    status_t generateProxySource(
            Formatter &out, const std::string &baseName) const;

    status_t generateStubSource(
            Formatter &out, const Interface *iface, const std::string &baseName) const;

    status_t generateStubSourceForMethod(
            Formatter &out, const Interface *iface, const Method *method) const;

    status_t generatePassthroughSource(Formatter &out) const;

    status_t generateInterfaceSource(Formatter &out) const;

    enum InstrumentationEvent {
        SERVER_API_ENTRY = 0,
        SERVER_API_EXIT,
        CLIENT_API_ENTRY,
        CLIENT_API_EXIT,
        SYNC_CALLBACK_ENTRY,
        SYNC_CALLBACK_EXIT,
        ASYNC_CALLBACK_ENTRY,
        ASYNC_CALLBACK_EXIT,
        PASSTHROUGH_ENTRY,
        PASSTHROUGH_EXIT,
    };

    status_t generateCppAtraceCall(
            Formatter &out,
            InstrumentationEvent event,
            const Method *method) const;

    status_t generateCppInstrumentationCall(
            Formatter &out,
            InstrumentationEvent event,
            const Method *method) const;

    void declareCppReaderLocals(
            Formatter &out,
            const std::vector<TypedVar *> &arg,
            bool forResults) const;

    void emitCppReaderWriter(
            Formatter &out,
            const std::string &parcelObj,
            bool parcelObjIsPointer,
            const TypedVar *arg,
            bool isReader,
            Type::ErrorMode mode,
            bool addPrefixToName) const;

    void emitCppResolveReferences(
            Formatter &out,
            const std::string &parcelObj,
            bool parcelObjIsPointer,
            const TypedVar *arg,
            bool isReader,
            Type::ErrorMode mode,
            bool addPrefixToName) const;

    void emitJavaReaderWriter(
            Formatter &out,
            const std::string &parcelObj,
            const TypedVar *arg,
            bool isReader,
            bool addPrefixToName) const;

    status_t emitTypeDeclarations(Formatter &out) const;
    status_t emitJavaTypeDeclarations(Formatter &out) const;
    status_t emitVtsTypeDeclarations(Formatter &out) const;

    // Helper function that generates vts type declaration from the current
    // AST and the transitive closure of imported ASTs.
    status_t emitVtsTypeDeclarationsHelper(
                Formatter &out,
                std::set<AST*> *allImportSet) const;

    DISALLOW_COPY_AND_ASSIGN(AST);
};

}  // namespace android

#endif  // AST_H_
