// Copyright 2018 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

package fuchsia.developer.plugin.fidl;

import java.util.Arrays;

import com.google.common.collect.ImmutableSet;
import com.intellij.lexer.FlexLexer;
import com.intellij.psi.tree.IElementType;
import com.intellij.psi.TokenType;
import static fuchsia.developer.plugin.fidl.psi.Types.*;

import static com.intellij.psi.TokenType.BAD_CHARACTER;
import static com.intellij.psi.TokenType.WHITE_SPACE;

%%

%{
  public FidlLexer() {
    this((java.io.Reader)null);
  }
%}

%public
%class FidlLexer
%implements FlexLexer
%function advance
%type IElementType
%unicode

WHITE_SPACE=\s+

// NOTE: All keywords that require syntax highlighting and can also be used
// as identifiers must go in:
//   This list
//   The ImmutableSet defined below.
//   The identifier-token production in Fidl.bnf

// Reserved words
ALIAS=alias
ARRAY=array
AS=as
BITS=bits
BYTES=bytes
COMPOSE=compose
CONST=const
ENUM=enum
ERROR=error
FLEXIBLE=flexible
HANDLE=handle
INTERFACE=interface
LIBRARY=library
PROTOCOL=protocol
PROPERTIES=properties
REQUEST=request
RESERVED=reserved
RESOURCE=resource
RESOURCE_DEFINITION=resource_definition
SERVICE=service
STRING=string
STRICT=strict
STRUCT=struct
TABLE=table
TYPE=type
UNION=union
USING_T=using
VECTOR=vector
XUNION=xunion

// Handle subtypes
CHANNEL=channel
CLOCK=clock
EVENT=event
EVENTPAIR=eventpair
EXCEPTION=exception
FIFO=fifo
GUEST=guest
INTERRUPT=interrupt
IOMMU=iommu
JOB=job
LOG=log
PAGER=pager
PCIDEVICE=pcidevice
PMT=pmt
PORT=port
PROCESS=process
RESOURCE=resource
SOCKET=socket
SUSPENDTOKEN=suspendtoken
THREAD=thread
TIMER=timer
VCPU=vcpu
VMAR=vmar
VMO=vmo

// Scalar types
BOOL=bool
FLOAT32=float32
FLOAT64=float64
INT8=int8
INT16=int16
INT32=int32
INT64=int64
UINT8=uint8
UINT16=uint16
UINT32=uint32
UINT64=uint64

%{
  public static ImmutableSet<String> ALL_KEYWORDS;
  static {
    ImmutableSet.Builder<String> builder = ImmutableSet.builder();
    builder.addAll(
        Arrays.asList(
            "alias",
            "array",
            "as",
            "bits",
            "bytes",
            "compose",
            "const",
            "enum",
            "error",
            "flexible",
            "handle",
            "interface",
            "library",
            "protocol",
            "properties",
            "request",
            "reserved",
            "resource",
            "resource_definition",
            "service",
            "string",
            "strict",
            "struct",
            "table",
            "type",
            "union",
            "using",
            "vector",
            "xunion",
            "channel",
            "clock",
            "event",
            "eventpair",
            "exception",
            "fifo",
            "guest",
            "interrupt",
            "iommu",
            "job",
            "log",
            "pager",
            "pcidevice",
            "pmt",
            "port",
            "process",
            "resource",
            "socket",
            "suspendtoken",
            "thread",
            "timer",
            "vcpu",
            "vmar",
            "vmo",
            "bool",
            "float32",
            "float64",
            "int8",
            "int16",
            "int32",
            "int64",
            "uint8",
            "uint16",
            "uint32",
            "uint64"));
    ALL_KEYWORDS = builder.build();
  }
%}


// Operators, etc.
AT="@"
OBRACE="{"
CBRACE="}"
SEMICOLON=";"
DOT="."
COMMA=","
OPAREN="("
CPAREN=")"
EQUALS="="
COLON=":"
ARROW="->"
LANGLE="<"
RANGLE=">"

// Literals
TRUE="true"
FALSE="false"
STRING_LITERAL=\"([^\"\\]|\\.)*\"
DECIMAL_FLOAT_LITERAL=[+-]?[0-9]+(\.[0-9]+)
DECIMAL_INTEGRAL_LITERAL=[+-]?[0-9]+
HEX_INTEGRAL_LITERAL=[+-]?0[Xx][0-9a-fA-F]+
BINARY_INTEGRAL_LITERAL=[+-]?0[Bb][0-1]+

IDENTIFIER=[:letter:][a-zA-Z_0-9]*
DOC_COMMENT="///".*
LINE_COMMENT="//".*

%%
<YYINITIAL> {
  {WHITE_SPACE} { return WHITE_SPACE; }

  {TRUE} { return TRUE; }
  {FALSE}  { return FALSE; }
  {LIBRARY} { return LIBRARY; }
  {ALIAS} { return ALIAS; }
  {USING_T} { return USING_T; }
  {AS} { return AS; }
  {BITS} { return BITS; }
  {BYTES} { return BYTES; }
  {CONST} { return CONST; }
  {ENUM} { return ENUM; }
  {INTERFACE} { return INTERFACE; }
  {PROTOCOL} { return PROTOCOL; }
  {COMPOSE} { return COMPOSE; }
  {SERVICE} { return SERVICE; }
  {STRUCT} { return STRUCT; }
  {TABLE} { return TABLE; }
  {TYPE} { return TYPE; }
  {UNION} { return UNION; }
  {XUNION} { return XUNION; }
  {ERROR} { return ERROR; }
  {ARRAY} { return ARRAY; }
  {VECTOR} { return VECTOR; }
  {STRING} { return STRING; }
  {HANDLE} { return HANDLE; }
  {RESERVED} { return RESERVED; }
  {RESOURCE} { return RESOURCE; }
  {RESOURCE_DEFINITION} { return RESOURCE_DEFINITION; }
  {PROPERTIES} { return PROPERTIES; }
  {STRICT} { return STRICT; }
  {FLEXIBLE} { return FLEXIBLE; }

  {CHANNEL} { return CHANNEL; }
  {CLOCK} { return CLOCK; }
  {EVENT}  { return EVENT; }
  {EVENTPAIR} { return EVENTPAIR; }
  {EXCEPTION} { return EXCEPTION; }
  {FIFO} { return FIFO; }
  {GUEST} { return GUEST; }
  {INTERRUPT} { return INTERRUPT; }
  {IOMMU} { return IOMMU; }
  {JOB} { return JOB; }
  {LOG} { return LOG; }
  {PAGER} { return PAGER; }
  {PCIDEVICE} { return PCIDEVICE; }
  {PMT} { return PMT; }
  {PORT} { return PORT; }
  {PROCESS} { return PROCESS; }
  {REQUEST} { return REQUEST; }
  {SUSPENDTOKEN} { return SUSPENDTOKEN; }
  {SOCKET} { return SOCKET; }
  {RESOURCE} { return RESOURCE; }
  {TIMER} { return TIMER; }
  {THREAD} { return THREAD; }
  {VCPU} { return VCPU; }
  {VMAR} { return VMAR; }
  {VMO} { return VMO; }

  {BOOL} { return BOOL; }
  {FLOAT32} { return FLOAT32; }
  {FLOAT64} { return FLOAT64; }
  {INT8} { return INT8; }
  {INT16} { return INT16; }
  {INT32} { return INT32; }
  {INT64} { return INT64; }
  {UINT8} { return UINT8; }
  {UINT16} { return UINT16; }
  {UINT32} { return UINT32; }
  {UINT64} { return UINT64; }

  {AT} { return AT; }
  {OBRACE} { return OBRACE; }
  {CBRACE} { return CBRACE; }
  {SEMICOLON} { return SEMICOLON; }
  {DOT} { return DOT; }
  {COMMA} { return COMMA; }
  {OPAREN} { return OPAREN; }
  {CPAREN} { return CPAREN; }
  {EQUALS} { return EQUALS; }
  {COLON} { return COLON; }
  {ARROW} { return ARROW; }
  {LANGLE} { return LANGLE; }
  {RANGLE} { return RANGLE; }
  {IDENTIFIER} { return IDENTIFIER; }
  {STRING_LITERAL} { return STRING_LITERAL; }
  {DECIMAL_FLOAT_LITERAL} { return DECIMAL_FLOAT_LITERAL; }
  {DECIMAL_INTEGRAL_LITERAL} { return DECIMAL_INTEGRAL_LITERAL; }
  {HEX_INTEGRAL_LITERAL} { return HEX_INTEGRAL_LITERAL; }
  {BINARY_INTEGRAL_LITERAL} { return BINARY_INTEGRAL_LITERAL; }
  {DOC_COMMENT} { return DOC_COMMENT; }
  {LINE_COMMENT} { return LINE_COMMENT; }

[^] { return BAD_CHARACTER; }
}
