简体   繁体   中英

ocamlmktop error: both define a module named Parser; both define a module named Lexer;

I am green man on ML, now study ocaml only hours to build my compiler with it. Lexer and the Parser is generated without any problem. But ther issue happen when the compiler code is build by ocamlmktop.
The error message likes the following, but the binary file myc.top is done and can be run.

Would you please help me to resolve the error message, thank you so much for your support.

$ ocamlyacc parser.mly
$ ocamllex lexer.mll
24 states, 1124 transitions, table size 4640 bytes
$ ocamlmktop syntax.ml parser.mli parser.ml lexer.ml -o myc.top
File "parser.cmo", line 1:
Error (warning 31): files parser.cmo and /usr/local/lib/ocaml/compiler-libs/ocamlcommon.cma(Parser) both define a module named Parser
File "lexer.cmo", line 1:
Error (warning 31): files lexer.cmo and /usr/local/lib/ocaml/compiler-libs/ocamlcommon.cma(Lexer) both define a module named Lexer

1.The lexer file lexer.mll

{
open Parser
}

let space = [' ' '\t' '\n' '\r']
let digit = ['0'-'9']
let alpha = ['A'-'Z' 'a'-'z' '_']

rule token = parse
| "while"
    { WHILE }
| "print"
    { PRINT }
| alpha (digit|alpha)*
    (* reserve key word *)
    { VAR(Lexing.lexeme lexbuf) }
| '-'? digit+
    { CONST(int_of_string (Lexing.lexeme lexbuf)) }
| space+
    (* skip spaces *)
    { token lexbuf }
| '='
    { EQUAL }
| '+'
    { PLUS }
| '('
    { LPAREN }
| ')'
    { RPAREN }
| '>'
    { GREATER }
| '{'
    { LBRACE }
| '}'
    { RBRACE }
| ';'
    { SEMICOLON }
| _
    (* other case: error heppen *)
    { failwith
        (Printf.sprintf
           "unknown token %s near characters %d-%d"
           (Lexing.lexeme lexbuf)
           (Lexing.lexeme_start lexbuf)
           (Lexing.lexeme_end lexbuf)) }

2 The parser file Parser.mly

%{
open Syntax
%}

%token <string> VAR /* variable */
%token <int> CONST  /* integer */
%token EQUAL        /* = */
%token PLUS         /* - */
%token WHILE        /* keyword「while」 */
%token LPAREN       /* ( */
%token RPAREN       /* ) */
%token GREATER      /* > */
%token LBRACE       /* { */
%token RBRACE       /* } */
%token SEMICOLON    /* ; */
%token PRINT        /* keyword「print」 */

%type <Syntax.statement> statement
%start statement

%%

statement: /* start */
| VAR EQUAL CONST
    { Const($1, $3) }
| VAR EQUAL VAR PLUS VAR
    { Add($1, $3, $5) }
| WHILE LPAREN VAR GREATER VAR RPAREN statement
    { While($3, $5, $7) }
| LBRACE statement_list RBRACE
    { Seq($2) }
| PRINT VAR
    { Print($2) }
| error /* other cases, error happens */
    { failwith
        (Printf.sprintf
           "parse error near characters %d-%d"
           (Parsing.symbol_start ())
           (Parsing.symbol_end ())) }

statement_list: /* start */
| statement SEMICOLON statement_list
    /* one by one */
    { $1 :: $3 }
| /* 空列 */
    { [] } /* nil return */

3. file syntax.ml

type var = string (* variable *)

type statement = (* statement *)
  | Const of var * int
      (* x = i *)
  | Add of var * var * var
      (* x = y + z *)
  | While of var * var * statement
      (* while (x > y) *)
  | Seq of statement list
      (* { s1; s2; …; sn } *)
  | Print of var
      (* print x *)

There are already modules named Lexer and Parser in the OCaml standard library. These conflict with your module names when you try to build a toplevel executable.

One way to make things work is to rename your modules to something else.

$ cat parser.ml
let f x = x * 2
$ ocamlmktop -o mytop parser.ml
File "parser.cmo", line 1:
Error (warning 31): files parser.cmo and
  /Users/jeffsco/.opam/4.06.1/lib/ocaml/compiler-
  libs/ocamlcommon.cma(Parser) both define a module named Parser
$ mv parser.ml myparser.ml
$ ocamlmktop -o mytop myparser.ml
$ ./mytop
        OCaml version 4.06.1

# Myparser.f 13;;
- : int = 26

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM