/*
 * 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.
 */

%{

#include "AST.h"
#include "Declaration.h"
#include "Type.h"
#include "VarDeclaration.h"
#include "FunctionDeclaration.h"
#include "CompositeDeclaration.h"
#include "Define.h"
#include "Include.h"
#include "EnumVarDeclaration.h"
#include "Note.h"
#include "TypeDef.h"
#include "Expression.h"

#include "c2hal_y.h"

#include <stdio.h>
#include <algorithm>

using namespace android;

extern int yylex(YYSTYPE *yylval_param, YYLTYPE *llocp, void *);

int yyerror(YYLTYPE *llocp, AST *, const char *s) {
    extern bool should_report_errors;

    if (!should_report_errors) {
      return 0;
    }

    fflush(stdout);
    LOG(ERROR) << " "
               << s
               << " near line "
               << llocp->first_line;

    return 0;
}

#define scanner ast->scanner()

std::string get_last_comment() {
    extern std::string last_comment;

    std::string ret{last_comment};

    // clear the last comment now that it's been taken
    last_comment = "";

    return ret;
}

%}

%parse-param { android::AST *ast }
%lex-param   { void *scanner }
%locations
%define api.pure
%glr-parser

/* These have to do with the fact that
 * struct_or_union_declaration and enum_declaration
 * both start with STRUCT/UNION/ENUM opt_id
 * and type_qualifiers contain these.
 */
%expect 3

%token START_HEADER
%token START_EXPR

%token STRUCT
%token UNION
%token ENUM
%token CLASS
%token CONST
%token VOID
%token INCLUDE
%token DEFINE
%token TYPEDEF
%token UNSIGNED
%token SIGNED
%token LSHIFT
%token RSHIFT
%token VARARGS
%token NAMESPACE
%token EXTERN
%token C_STRING

%left ','
%right '?' ':'
%left '|'
%left '^'
%left '&'
%left RSHIFT LSHIFT
%left '+' '-'
%left '*' '/' '%'
%right '~' '!' UMINUS UPLUS
%left ARRAY_SUBSCRIPT FUNCTION_CALL

%right STRUCT ENUM

%token<str> ID
%token<str> COMMENT
%token<str> VALUE
%token<str> INTEGRAL_VALUE
%token<str> INCLUDE_FILE
%token<str> FUNCTION
%token<str> DEFINE_SLURP
%token<str> OTHER_STATEMENT

%type<expression> array
%type<expressions> arrays
%type<expression> expr
%type<expressions> args
%type<type> type
%type<type> opt_enum_base_type
%type<qualifier> type_qualifier
%type<qualifiers> type_qualifiers
%type<declaration> declaration
%type<declarations> declarations
%type<composite> struct_or_union_declaration
%type<composite> enum_declaration
%type<param> param
%type<params> params
%type<qualification> struct_or_union
%type<str> opt_id
%type<include> include
%type<enum_var> enum_var
%type<declarations> enum_vars enum_vars_all_but_last
%type<declaration> enum_var_line enum_var_last_line

%start parse_selector

%union {
    const char *str;
    int count;
    android::Declaration *declaration;
    android::CompositeDeclaration *composite;
    std::vector<android::Declaration *> *declarations;
    android::EnumVarDeclaration *enum_var;
    android::Declaration *param;
    std::vector<android::Declaration *> *params;
    android::Type *type;
    android::Type::Qualifier *qualifier;
    android::Type::Qualifier::Qualification qualification;
    std::vector<android::Type::Qualifier*> *qualifiers;
    android::Include *include;
    std::vector<android::Include *> *includes;
    android::Expression *expression;
    std::vector<android::Expression *> *expressions;
}

%%

parse_selector
    : START_HEADER header
    | START_EXPR expr_parser
    ;

expr_parser
    : expr
      {
        ast->setExpression($1);
      }
    ;

header
    : declarations /* well, we are a header file */
      {
        ast->setDeclarations($1);
      }
    ;

declarations
    : /* EMPTY */
      {
        $$ = new std::vector<Declaration *>;
      }
    | declarations declaration
      {
        $$ = $1;
        $$->push_back($2);
      }
    | declarations EXTERN C_STRING '{' declarations '}'
      {
        $1->push_back(new Note("extern \"C\" { "));
        $1->insert($1->end(), $5->begin(), $5->end());
        $1->push_back(new Note("} // end of extern C"));
        delete $5;

        $$ = $1;
      }
    ;

declaration
    : param ';'
      {
        $$ = $1;
        $$->setComment(get_last_comment());
      }
    | struct_or_union_declaration ';'
      {
        $$ = $1;
      }
    | enum_declaration ';'
      {
        $$ = $1;
      }
    | TYPEDEF struct_or_union_declaration ';'
      {
        // ignore that it is a typedef, for our purposes it doesn't matter
        $$ = $2;
      }
    | TYPEDEF enum_declaration ';'
      {
        // ignore that it is a typedef, for our purposes it doesn't matter
        $$ = $2;
      }
    | TYPEDEF param ';' /* looks like 'typedef const int8_t store;' */
      {
        $$ = new TypeDef($2->getName(), $2);
        $$->setComment(get_last_comment());
      }
    | DEFINE ID DEFINE_SLURP
      {
        $$ = new Define($2, $3);
        $$->setComment(get_last_comment());
      }
    | OTHER_STATEMENT
      {
        $$ = new Note($1);
        $$->setComment(get_last_comment());
      }
    | FUNCTION
      {
        $$ = new Note($1);
        $$->setComment(get_last_comment());
      }
    | type ID '=' expr ';'
      {
        $$ = new Note($1->decorateName($2) + " = " + $4->toString());
      }
    | include
      {
        $$ = $1;
        $$->setComment(get_last_comment());
      }
    | NAMESPACE ID '{' declarations '}'
      {
        $$ = new CompositeDeclaration(Type::Qualifier::STRUCT,
                                               $2,
                                               $4);

        get_last_comment(); // clear it
        $$->setComment("/* from namespace declaration */");
      }
    ;

include
    : INCLUDE '<' INCLUDE_FILE '>'
      {
        $$ = new Include($3, true /* isLibrary */);
      }
    | INCLUDE '"' INCLUDE_FILE '"'
      {
        $$ = new Include($3, false /* isLibrary */);
      }
    ;

struct_or_union_declaration
    : struct_or_union opt_id
      {
        $<str>$ = strdup(get_last_comment().c_str());
      }
                             '{' declarations '}' opt_id
      {
        $$ = new CompositeDeclaration($1, $2, $5);
        $$->setComment($<str>3);

        if(!std::string($7).empty()) {
          $$->setName($7);
        }
      }
    ;

opt_comma
    : /* EMPTY */
    | ','
    ;

enum_key
    : ENUM
    | ENUM CLASS  /* c++11 */
    | ENUM STRUCT /* c++11 */
    ;

opt_enum_base_type
    : /* EMPTY */ { $$ = NULL; }
    | ':' type    { $$ = $2; }
    ;

enum_declaration
    : enum_key opt_id
      {
        $<str>$ = strdup(get_last_comment().c_str());
      }
                        opt_enum_base_type '{' enum_vars '}' opt_id
      {
        $$ = new CompositeDeclaration(Type::Qualifier::ENUM, $2, $6);
        $$->setComment($<str>3);

        if($4) {
          $$->setEnumTypeName($4->decorateName(""));
          delete $4;
        }

        if(!std::string($8).empty()) {
          $$->setName($8);
        }
      }
    ;

enum_vars
    : /* EMPTY */
      {
        $$ = new std::vector<Declaration *>;
      }
    | enum_vars_all_but_last enum_var_last_line
      {
        $$ = $1;
        $$->push_back($2);
      }

enum_vars_all_but_last
    : /* EMPTY */
      {
        $$ = new std::vector<Declaration *>;
      }
    | enum_vars_all_but_last enum_var_line
      {
        $$ = $1;
        $$->push_back($2);
      }
    ;

enum_var_last_line
    : enum_var opt_comma { $$ = $1; }
    | OTHER_STATEMENT
      {
        $$ = new Note($1);
        $$->setComment(get_last_comment());
      }
    ;

enum_var_line
    : enum_var ',' { $$ = $1; }
    | OTHER_STATEMENT
      {
        $$ = new Note($1);
        $$->setComment(get_last_comment());
      }
    ;

enum_var
    : ID
      {
        $$ = new EnumVarDeclaration($1, NULL);
        $$->setComment(get_last_comment());
      }
    | ID '=' expr
      {
        $$ = new EnumVarDeclaration($1, $3);
        $$->setComment(get_last_comment());
      }
    ;

params
    : /* EMPTY */
      {
        $$ = new std::vector<Declaration *>;
      }
    | param
      {
        $$ = new std::vector<Declaration *>;
        $$->push_back($1);
      }
    | params ',' param
      {
        $$ = $1;
        $$->push_back($3);
      }
    ;

param
    : type arrays
      {
        $1->setArrays($2);

        // allow for either "const int myvar" or "const int"
        // as a parameter declaration
        std::string lastId = $1->removeLastId();

        $$ = new VarDeclaration($1, lastId);
      }
    | type '(' '*' ID arrays ')' '(' params ')'
      {
        $1->setArrays($5);
        $$ = new FunctionDeclaration($1, $4, $8);
      }
    | type ID '(' params ')'
      {
        $$ = new FunctionDeclaration($1, $2, $4);
      }
    | type '(' ID ')' '(' params ')'
      {
        $$ = new FunctionDeclaration($1, $3, $6);
      }
    | VARARGS
      {
        $$ = new VarDeclaration(new Type(NULL), "...");
      }
    ;

type
    : type_qualifiers
      {
        $$ = new Type($1);
      }
    ;

type_qualifiers
    : type_qualifier
     {
        $$ = new std::vector<Type::Qualifier *>;
        $$->push_back($1);
     }
    | type_qualifiers type_qualifier
     {
        $$ = $1;
        $$->push_back($2);
     }
    ;

opt_id
    : /* EMPTY */             { $$ = ""; }
    |
     ID                       { $$ = $1; }
    ;

expr
    : ID
      {
        $$ = Expression::atom(Expression::Type::UNKNOWN, $1, true /* isId*/ );
      }
    | VALUE                   { $$ = Expression::atom(Expression::Type::UNKNOWN, $1); }
    | INTEGRAL_VALUE          { $$ = Expression::atom(Expression::integralType($1), $1); }
    | '(' expr ')'            { $$ = Expression::parenthesize($2); }
    | ID '[' expr ']' %prec ARRAY_SUBSCRIPT {
                                $$ = Expression::arraySubscript($1, $3);
                              }
    | ID '(' args ')' %prec FUNCTION_CALL {
                                $$ = Expression::functionCall($1, $3);
                              }
    | expr '?' expr ':' expr  { $$ = Expression::ternary($1, $3, $5); }
    | expr '+' expr           { $$ = Expression::binary($1, "+", $3); }
    | expr '-' expr           { $$ = Expression::binary($1, "-", $3); }
    | expr '/' expr           { $$ = Expression::binary($1, "/", $3); }
    | expr '*' expr           { $$ = Expression::binary($1, "*", $3); }
    | expr '%' expr           { $$ = Expression::binary($1, "%%", $3); }
    | expr '&' expr           { $$ = Expression::binary($1, "&", $3); }
    | expr '|' expr           { $$ = Expression::binary($1, "|", $3); }
    | expr '^' expr           { $$ = Expression::binary($1, "^", $3); }
    | expr LSHIFT expr        { $$ = Expression::binary($1, "<<", $3); }
    | expr RSHIFT expr        { $$ = Expression::binary($1, ">>", $3); }
    | '~' expr                { $$ = Expression::unary("~", $2); }
    | '-' expr %prec UMINUS   { $$ = Expression::unary("-", $2); }
    | '+' expr %prec UPLUS    { $$ = Expression::unary("+", $2); }
    ;

args
    : /* empty */
      {
        $$ = new std::vector<Expression *>;
      }
    | expr
      {
        $$ = new std::vector<Expression *>;
        $$->push_back($1);
      }
    | args ',' expr
      {
        $$ = $1;
        $$->push_back($3);
      }
    ;

type_qualifier
    : UNSIGNED                { $$ = new Type::Qualifier(Type::Qualifier::UNSIGNED); }
    | SIGNED                  { $$ = new Type::Qualifier(Type::Qualifier::SIGNED); }
    | VOID                    { $$ = new Type::Qualifier(Type::Qualifier::VOID); }
    | '*'                     { $$ = new Type::Qualifier(Type::Qualifier::POINTER); }
    | CONST                   { $$ = new Type::Qualifier(Type::Qualifier::CONST); }
    | ID                      { $$ = new Type::Qualifier(Type::Qualifier::ID, $1); }
    | '<' type '>'            { $$ = new Type::Qualifier(Type::Qualifier::GENERICS, $2); }
    | enum_key                { $$ = new Type::Qualifier(Type::Qualifier::ENUM); }
    | struct_or_union         { $$ = new Type::Qualifier($1); }
    ;

struct_or_union
    : STRUCT                  { $$ = android::Type::Qualifier::STRUCT; }
    | UNION                   { $$ = android::Type::Qualifier::UNION; }
    ;

arrays
    : /* empty */             { $$ = new std::vector<Expression *>; }
    | arrays array            {
                                $$ = $1;
                                $$->push_back($2);
                              }
    ;

array
    : '[' ']'                 { $$ = Expression::atom(Expression::Type::UNKNOWN, " "); }
    | '[' expr ']'            { $$ = $2; }
    ;

%%
